func TestUnmarshal(t *testing.T) {
	structTestIn := []byte{
		0x00, 0x00, 0x00, 0x7F,  
		0x00, 0x00, 0x00, 0xFF,  
		0x00, 0x00, 0x7F, 0xFF,  
		0x00, 0x00, 0xFF, 0xFF,  
		0x7F, 0xFF, 0xFF, 0xFF,  
		0xFF, 0xFF, 0xFF, 0xFF,  
		0x7F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,  
		0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,  
		0x00, 0x00, 0x00, 0x01,  
		0x40, 0x48, 0xF5, 0xC3,  
		0x40, 0x09, 0x21, 0xfb, 0x54, 0x44, 0x2d, 0x18,  
		0x00, 0x00, 0x00, 0x03, 0x78, 0x64, 0x72, 0x00,  
		0x00, 0x00, 0x00, 0x04, 0x01, 0x02, 0x03, 0x04,  
		0x01, 0x02, 0x03, 0x00,  
		0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x02, 0x00,
		0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x08, 0x00,  
		0x00, 0x00, 0x00, 0x03, 0x6F, 0x6E, 0x65, 0x00,  
		0x00, 0x00, 0x00, 0x01,  
		0x00, 0x00, 0x00, 0x03, 0x74, 0x77, 0x6F, 0x00,  
		0x00, 0x00, 0x00, 0x02,  
		0x00, 0x00, 0x00, 0x03, 0x62, 0x61, 0x72, 0x00,  
		0x00, 0x00, 0x00, 0x03,  
		0x00, 0x00, 0x00, 0x02,  
		0x00, 0x00, 0x00, 0x04, 0x6D, 0x61, 0x70, 0x31,  
		0x00, 0x00, 0x00, 0x01,  
		0x00, 0x00, 0x00, 0x04, 0x6D, 0x61, 0x70, 0x32,  
		0x00, 0x00, 0x00, 0x02,  
		0x00, 0x00, 0x00, 0x14, 0x32, 0x30, 0x31, 0x34,
		0x2d, 0x30, 0x34, 0x2d, 0x30, 0x34, 0x54, 0x30,
		0x33, 0x3a, 0x32, 0x34, 0x3a, 0x34, 0x38, 0x5a,  
	}
	structTestWant := allTypesTest{
		127,                                      
		255,                                      
		32767,                                    
		65535,                                    
		2147483647,                               
		4294967295,                               
		9223372036854775807,                      
		18446744073709551615,                     
		true,                                     
		3.14,                                     
		3.141592653589793,                        
		"xdr",                                    
		[]byte{1, 2, 3, 4},                       
		[3]byte{1, 2, 3},                         
		[]int16{512, 1024, 2048},                 
		[2]subTest{{"one", 1}, {"two", 2}},       
		subTest{"bar", 3},                        
		map[string]uint32{"map1": 1, "map2": 2},  
		time.Unix(1396581888, 0).UTC(),           
	}
	tests := []struct {
		in   []byte
		want interface{}
		err  error
	}{
		{[]byte{0x00, 0x00, 0x00, 0x00}, int8(0), nil},
		{[]byte{0x00, 0x00, 0x00, 0x40}, int8(64), nil},
		{[]byte{0x00, 0x00, 0x00, 0x7F}, int8(127), nil},
		{[]byte{0xFF, 0xFF, 0xFF, 0xFF}, int8(-1), nil},
		{[]byte{0xFF, 0xFF, 0xFF, 0x80}, int8(-128), nil},
		{[]byte{0x00, 0x00, 0x00, 0x80}, int8(0), &UnmarshalError{ErrorCode: ErrOverflow}},
		{[]byte{0xFF, 0xFF, 0xFF, 0x7F}, int8(0), &UnmarshalError{ErrorCode: ErrOverflow}},
		{[]byte{0x00, 0x00, 0x00, 0x00}, uint8(0), nil},
		{[]byte{0x00, 0x00, 0x00, 0x40}, uint8(64), nil},
		{[]byte{0x00, 0x00, 0x00, 0xFF}, uint8(255), nil},
		{[]byte{0x00, 0x00, 0x01, 0x00}, uint8(0), &UnmarshalError{ErrorCode: ErrOverflow}},
		{[]byte{0xFF, 0xFF, 0xFF, 0xFF}, uint8(0), &UnmarshalError{ErrorCode: ErrOverflow}},
		{[]byte{0x00, 0x00, 0x00, 0x00}, int16(0), nil},
		{[]byte{0x00, 0x00, 0x04, 0x00}, int16(1024), nil},
		{[]byte{0x00, 0x00, 0x7F, 0xFF}, int16(32767), nil},
		{[]byte{0xFF, 0xFF, 0xFF, 0xFF}, int16(-1), nil},
		{[]byte{0xFF, 0xFF, 0x80, 0x00}, int16(-32768), nil},
		{[]byte{0x00, 0x00, 0x80, 0x00}, int16(0), &UnmarshalError{ErrorCode: ErrOverflow}},
		{[]byte{0xFF, 0xFF, 0x7F, 0xFF}, int16(0), &UnmarshalError{ErrorCode: ErrOverflow}},
		{[]byte{0x00, 0x00, 0x00, 0x00}, uint16(0), nil},
		{[]byte{0x00, 0x00, 0x04, 0x00}, uint16(1024), nil},
		{[]byte{0x00, 0x00, 0xFF, 0xFF}, uint16(65535), nil},
		{[]byte{0x00, 0x01, 0x00, 0x00}, uint16(0), &UnmarshalError{ErrorCode: ErrOverflow}},
		{[]byte{0xFF, 0xFF, 0xFF, 0xFF}, uint16(0), &UnmarshalError{ErrorCode: ErrOverflow}},
		{[]byte{0x00, 0x00, 0x00, 0x00}, int32(0), nil},
		{[]byte{0x00, 0x04, 0x00, 0x00}, int32(262144), nil},
		{[]byte{0x7F, 0xFF, 0xFF, 0xFF}, int32(2147483647), nil},
		{[]byte{0xFF, 0xFF, 0xFF, 0xFF}, int32(-1), nil},
		{[]byte{0x80, 0x00, 0x00, 0x00}, int32(-2147483648), nil},
		{[]byte{0x00, 0x00, 0x00, 0x00}, uint32(0), nil},
		{[]byte{0x00, 0x04, 0x00, 0x00}, uint32(262144), nil},
		{[]byte{0xFF, 0xFF, 0xFF, 0xFF}, uint32(4294967295), nil},
		{[]byte{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, int64(0), nil},
		{[]byte{0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00}, int64(1 << 34), nil},
		{[]byte{0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00}, int64(1 << 42), nil},
		{[]byte{0x7F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}, int64(9223372036854775807), nil},
		{[]byte{0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}, int64(-1), nil},
		{[]byte{0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, int64(-9223372036854775808), nil},
		{[]byte{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, uint64(0), nil},
		{[]byte{0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00}, uint64(1 << 34), nil},
		{[]byte{0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00}, uint64(1 << 42), nil},
		{[]byte{0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}, uint64(18446744073709551615), nil},
		{[]byte{0x80, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, uint64(9223372036854775808), nil},
		{[]byte{0x00, 0x00, 0x00, 0x00}, false, nil},
		{[]byte{0x00, 0x00, 0x00, 0x01}, true, nil},
		{[]byte{0x01, 0x00, 0x00, 0x00}, true, &UnmarshalError{ErrorCode: ErrBadEnumValue}},
		{[]byte{0x00, 0x00, 0x40, 0x00}, true, &UnmarshalError{ErrorCode: ErrBadEnumValue}},
		{[]byte{0x00, 0x00, 0x00, 0x00}, float32(0), nil},
		{[]byte{0x40, 0x48, 0xF5, 0xC3}, float32(3.14), nil},
		{[]byte{0x49, 0x96, 0xB4, 0x38}, float32(1234567.0), nil},
		{[]byte{0xFF, 0x80, 0x00, 0x00}, float32(math.Inf(-1)), nil},
		{[]byte{0x7F, 0x80, 0x00, 0x00}, float32(math.Inf(0)), nil},
		{[]byte{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, float64(0), nil},
		{[]byte{0x40, 0x09, 0x21, 0xfb, 0x54, 0x44, 0x2d, 0x18}, float64(3.141592653589793), nil},
		{[]byte{0xFF, 0xF0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, float64(math.Inf(-1)), nil},
		{[]byte{0x7F, 0xF0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, float64(math.Inf(0)), nil},
		{[]byte{0x00, 0x00, 0x00, 0x00}, "", nil},
		{[]byte{0x00, 0x00, 0x00, 0x03, 0x78, 0x64, 0x72, 0x00}, "xdr", nil},
		{[]byte{0x00, 0x00, 0x00, 0x06, 0xCF, 0x84, 0x3D, 0x32, 0xCF, 0x80, 0x00, 0x00}, "τ=2π", nil},
		{[]byte{0x00, 0x00, 0x00, 0xFF}, "", &UnmarshalError{ErrorCode: ErrUnexpectedEnd}},
		{[]byte{0x00, 0x00, 0x00, 0x01, 0x01, 0x00, 0x00, 0x00}, []byte{0x01}, nil},
		{[]byte{0x00, 0x00, 0x00, 0x03, 0x01, 0x02, 0x03, 0x00}, []byte{0x01, 0x02, 0x03}, nil},
		{[]byte{0x00, 0x00, 0x00, 0xFF}, []byte{}, &UnmarshalError{ErrorCode: ErrUnexpectedEnd}},
		{[]byte{0x01, 0x00, 0x00, 0x00}, [1]byte{0x01}, nil},
		{[]byte{0x01, 0x02, 0x00, 0x00}, [2]byte{0x01, 0x02}, nil},
		{[]byte{0x01, 0x02, 0x03, 0x00}, [3]byte{0x01, 0x02, 0x03}, nil},
		{[]byte{0x01, 0x02, 0x03, 0x04}, [4]byte{0x01, 0x02, 0x03, 0x04}, nil},
		{[]byte{0x01, 0x02, 0x03, 0x04, 0x05, 0x00, 0x00, 0x00}, [5]byte{0x01, 0x02, 0x03, 0x04, 0x05}, nil},
		{[]byte{0x01}, [1]byte{}, &UnmarshalError{ErrorCode: ErrUnexpectedEnd}},
		{[]byte{0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x08, 0x00},
			[]int16{512, 1024, 2048}, nil},
		{[]byte{0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00}, []bool{true, false}, nil},
		{[]byte{0x00, 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x01}, []bool{}, &UnmarshalError{ErrorCode: ErrUnexpectedEnd}},
		{[]byte{0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x04, 0x00}, [2]uint32{512, 1024}, nil},
		{[]byte{0x00, 0x00, 0x02, 0x00}, [2]uint32{}, &UnmarshalError{ErrorCode: ErrUnexpectedEnd}},
		{[]byte{0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x04, 0x6D, 0x61, 0x70, 0x31, 0x00, 0x00, 0x00, 0x01},
			map[string]uint32{"map1": 1}, nil},
		{[]byte{0x00, 0x00, 0x00, 0x01}, map[string]uint32{}, &UnmarshalError{ErrorCode: ErrUnexpectedEnd}},
		{[]byte{
			0x00, 0x00, 0x00, 0x14, 0x32, 0x30, 0x31, 0x34,
			0x2d, 0x30, 0x34, 0x2d, 0x30, 0x34, 0x54, 0x30,
			0x33, 0x3a, 0x32, 0x34, 0x3a, 0x34, 0x38, 0x5a,
		}, time.Unix(1396581888, 0).UTC(), nil},
		{structTestIn, structTestWant, nil},
	}
	for i, test := range tests {
		want := reflect.New(reflect.TypeOf(test.want)).Interface()
		rest, err := Unmarshal(test.in, want)
		if reflect.TypeOf(err) != reflect.TypeOf(test.err) {
			t.Errorf("Unmarshal #%d failed to detect error - got: %v <%T> want: %T",
				i, err, err, test.err)
			continue
		}
		if rerr, ok := err.(*UnmarshalError); ok {
			if terr, ok := test.err.(*UnmarshalError); ok {
				if rerr.ErrorCode != terr.ErrorCode {
					t.Errorf("Unmarshal #%d failed to detect error code - got: %v want: %v",
						i, rerr.ErrorCode, terr.ErrorCode)
					continue
				}
				continue
			}
		}
		if len(rest) != 0 {
			t.Errorf("Unmarshal #%d len got: %v want: %v\n", i, len(rest), 0)
			continue
		}
		wantElem := reflect.Indirect(reflect.ValueOf(want)).Interface()
		if !reflect.DeepEqual(wantElem, test.want) {
			t.Errorf("Unmarshal #%d got: %v want: %v\n", i, wantElem, test.want)
			continue
		}
	}
}
TestUnmarshal executes all of the tests described by unmarshalTests.
package xdr
import (
	"fmt"
	"math"
	"reflect"
	"testing"
	"time"
)
type subTest struct {
	A string
	B uint8
}
type allTypesTest struct {
	A int8
	B uint8
	C int16
	D uint16
	E int32
	F uint32
	G int64
	H uint64
	I bool
	J float32
	K float64
	L string
	M []byte
	N [3]byte
	O []int16
	P [2]subTest
	Q subTest
	R map[string]uint32
	S time.Time
}