podman

Форк
0
896 строк · 27.0 Кб
1
/*
2
 * Copyright (c) 2012-2014 Dave Collins <dave@davec.name>
3
 *
4
 * Permission to use, copy, modify, and distribute this software for any
5
 * purpose with or without fee is hereby granted, provided that the above
6
 * copyright notice and this permission notice appear in all copies.
7
 *
8
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11
 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13
 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14
 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
15
 */
16

17
package xdr
18

19
import (
20
	"fmt"
21
	"io"
22
	"math"
23
	"reflect"
24
	"time"
25
)
26

27
var (
28
	errMaxSlice = "data exceeds max slice limit"
29
	errIODecode = "%s while decoding %d bytes"
30
)
31

32
/*
33
Unmarshal parses XDR-encoded data into the value pointed to by v reading from
34
reader r and returning the total number of bytes read.  An addressable pointer
35
must be provided since Unmarshal needs to both store the result of the decode as
36
well as obtain target type information.  Unmarhsal traverses v recursively and
37
automatically indirects pointers through arbitrary depth, allocating them as
38
necessary, to decode the data into the underlying value pointed to.
39

40
Unmarshal uses reflection to determine the type of the concrete value contained
41
by v and performs a mapping of underlying XDR types to Go types as follows:
42

43
	Go Type <- XDR Type
44
	--------------------
45
	int8, int16, int32, int <- XDR Integer
46
	uint8, uint16, uint32, uint <- XDR Unsigned Integer
47
	int64 <- XDR Hyper Integer
48
	uint64 <- XDR Unsigned Hyper Integer
49
	bool <- XDR Boolean
50
	float32 <- XDR Floating-Point
51
	float64 <- XDR Double-Precision Floating-Point
52
	string <- XDR String
53
	byte <- XDR Integer
54
	[]byte <- XDR Variable-Length Opaque Data
55
	[#]byte <- XDR Fixed-Length Opaque Data
56
	[]<type> <- XDR Variable-Length Array
57
	[#]<type> <- XDR Fixed-Length Array
58
	struct <- XDR Structure
59
	map <- XDR Variable-Length Array of two-element XDR Structures
60
	time.Time <- XDR String encoded with RFC3339 nanosecond precision
61

62
Notes and Limitations:
63

64
	* Automatic unmarshalling of variable and fixed-length arrays of uint8s
65
	  requires a special struct tag `xdropaque:"false"` since byte slices
66
	  and byte arrays are assumed to be opaque data and byte is a Go alias
67
	  for uint8 thus indistinguishable under reflection
68
	* Cyclic data structures are not supported and will result in infinite
69
	  loops
70

71
If any issues are encountered during the unmarshalling process, an
72
UnmarshalError is returned with a human readable description as well as
73
an ErrorCode value for further inspection from sophisticated callers.  Some
74
potential issues are unsupported Go types, attempting to decode a value which is
75
too large to fit into a specified Go type, and exceeding max slice limitations.
76
*/
77
func Unmarshal(r io.Reader, v interface{}) (int, error) {
78
	d := Decoder{r: r}
79
	return d.Decode(v)
80
}
81

82
// UnmarshalLimited is identical to Unmarshal but it sets maxReadSize in order
83
// to cap reads.
84
func UnmarshalLimited(r io.Reader, v interface{}, maxSize uint) (int, error) {
85
	d := Decoder{r: r, maxReadSize: maxSize}
86
	return d.Decode(v)
87
}
88

89
// TypeDecoder lets a caller provide a custom decode routine for a custom type.
90
type TypeDecoder interface {
91
	Decode(*Decoder, reflect.Value) (int, error)
92
}
93

94
// A Decoder wraps an io.Reader that is expected to provide an XDR-encoded byte
95
// stream and provides several exposed methods to manually decode various XDR
96
// primitives without relying on reflection.  The NewDecoder function can be
97
// used to get a new Decoder directly.
98
//
99
// Typically, Unmarshal should be used instead of manual decoding.  A Decoder
100
// is exposed so it is possible to perform manual decoding should it be
101
// necessary in complex scenarios where automatic reflection-based decoding
102
// won't work.
103
type Decoder struct {
104
	r io.Reader
105

106
	// maxReadSize is the default maximum bytes an element can contain.  0
107
	// is unlimited and provides backwards compatability.  Setting it to a
108
	// non-zero value caps reads.
109
	maxReadSize uint
110

111
	// customTypes is a map allowing the caller to provide decoder routines for
112
	// custom types known only to itself.
113
	customTypes map[string]TypeDecoder
114
}
115

116
// DecodeInt treats the next 4 bytes as an XDR encoded integer and returns the
117
// result as an int32 along with the number of bytes actually read.
118
//
119
// An UnmarshalError is returned if there are insufficient bytes remaining.
120
//
121
// Reference:
122
// 	RFC Section 4.1 - Integer
123
// 	32-bit big-endian signed integer in range [-2147483648, 2147483647]
124
func (d *Decoder) DecodeInt() (int32, int, error) {
125
	var buf [4]byte
126
	n, err := io.ReadFull(d.r, buf[:])
127
	if err != nil {
128
		msg := fmt.Sprintf(errIODecode, err.Error(), 4)
129
		err := unmarshalError("DecodeInt", ErrIO, msg, buf[:n], err)
130
		return 0, n, err
131
	}
132

133
	rv := int32(buf[3]) | int32(buf[2])<<8 |
134
		int32(buf[1])<<16 | int32(buf[0])<<24
135
	return rv, n, nil
136
}
137

138
// DecodeUint treats the next 4 bytes as an XDR encoded unsigned integer and
139
// returns the result as a uint32 along with the number of bytes actually read.
140
//
141
// An UnmarshalError is returned if there are insufficient bytes remaining.
142
//
143
// Reference:
144
// 	RFC Section 4.2 - Unsigned Integer
145
// 	32-bit big-endian unsigned integer in range [0, 4294967295]
146
func (d *Decoder) DecodeUint() (uint32, int, error) {
147
	var buf [4]byte
148
	n, err := io.ReadFull(d.r, buf[:])
149
	if err != nil {
150
		msg := fmt.Sprintf(errIODecode, err.Error(), 4)
151
		err := unmarshalError("DecodeUint", ErrIO, msg, buf[:n], err)
152
		return 0, n, err
153
	}
154

155
	rv := uint32(buf[3]) | uint32(buf[2])<<8 |
156
		uint32(buf[1])<<16 | uint32(buf[0])<<24
157
	return rv, n, nil
158
}
159

160
// DecodeEnum treats the next 4 bytes as an XDR encoded enumeration value and
161
// returns the result as an int32 after verifying that the value is in the
162
// provided map of valid values.   It also returns the number of bytes actually
163
// read.
164
//
165
// An UnmarshalError is returned if there are insufficient bytes remaining or
166
// the parsed enumeration value is not one of the provided valid values.
167
//
168
// Reference:
169
// 	RFC Section 4.3 - Enumeration
170
// 	Represented as an XDR encoded signed integer
171
func (d *Decoder) DecodeEnum(validEnums map[int32]bool) (int32, int, error) {
172
	val, n, err := d.DecodeInt()
173
	if err != nil {
174
		return 0, n, err
175
	}
176

177
	if !validEnums[val] {
178
		err := unmarshalError("DecodeEnum", ErrBadEnumValue,
179
			"invalid enum", val, nil)
180
		return 0, n, err
181
	}
182
	return val, n, nil
183
}
184

185
// DecodeBool treats the next 4 bytes as an XDR encoded boolean value and
186
// returns the result as a bool along with the number of bytes actually read.
187
//
188
// An UnmarshalError is returned if there are insufficient bytes remaining or
189
// the parsed value is not a 0 or 1.
190
//
191
// Reference:
192
// 	RFC Section 4.4 - Boolean
193
// 	Represented as an XDR encoded enumeration where 0 is false and 1 is true
194
func (d *Decoder) DecodeBool() (bool, int, error) {
195
	val, n, err := d.DecodeInt()
196
	if err != nil {
197
		return false, n, err
198
	}
199
	switch val {
200
	case 0:
201
		return false, n, nil
202
	case 1:
203
		return true, n, nil
204
	}
205

206
	err = unmarshalError("DecodeBool", ErrBadEnumValue, "bool not 0 or 1",
207
		val, nil)
208
	return false, n, err
209
}
210

211
// DecodeHyper treats the next 8 bytes as an XDR encoded hyper value and
212
// returns the result as an int64  along with the number of bytes actually read.
213
//
214
// An UnmarshalError is returned if there are insufficient bytes remaining.
215
//
216
// Reference:
217
// 	RFC Section 4.5 - Hyper Integer
218
// 	64-bit big-endian signed integer in range [-9223372036854775808, 9223372036854775807]
219
func (d *Decoder) DecodeHyper() (int64, int, error) {
220
	var buf [8]byte
221
	n, err := io.ReadFull(d.r, buf[:])
222
	if err != nil {
223
		msg := fmt.Sprintf(errIODecode, err.Error(), 8)
224
		err := unmarshalError("DecodeHyper", ErrIO, msg, buf[:n], err)
225
		return 0, n, err
226
	}
227

228
	rv := int64(buf[7]) | int64(buf[6])<<8 |
229
		int64(buf[5])<<16 | int64(buf[4])<<24 |
230
		int64(buf[3])<<32 | int64(buf[2])<<40 |
231
		int64(buf[1])<<48 | int64(buf[0])<<56
232
	return rv, n, err
233
}
234

235
// DecodeUhyper treats the next 8  bytes as an XDR encoded unsigned hyper value
236
// and returns the result as a uint64  along with the number of bytes actually
237
// read.
238
//
239
// An UnmarshalError is returned if there are insufficient bytes remaining.
240
//
241
// Reference:
242
// 	RFC Section 4.5 - Unsigned Hyper Integer
243
// 	64-bit big-endian unsigned integer in range [0, 18446744073709551615]
244
func (d *Decoder) DecodeUhyper() (uint64, int, error) {
245
	var buf [8]byte
246
	n, err := io.ReadFull(d.r, buf[:])
247
	if err != nil {
248
		msg := fmt.Sprintf(errIODecode, err.Error(), 8)
249
		err := unmarshalError("DecodeUhyper", ErrIO, msg, buf[:n], err)
250
		return 0, n, err
251
	}
252

253
	rv := uint64(buf[7]) | uint64(buf[6])<<8 |
254
		uint64(buf[5])<<16 | uint64(buf[4])<<24 |
255
		uint64(buf[3])<<32 | uint64(buf[2])<<40 |
256
		uint64(buf[1])<<48 | uint64(buf[0])<<56
257
	return rv, n, nil
258
}
259

260
// DecodeFloat treats the next 4 bytes as an XDR encoded floating point and
261
// returns the result as a float32 along with the number of bytes actually read.
262
//
263
// An UnmarshalError is returned if there are insufficient bytes remaining.
264
//
265
// Reference:
266
// 	RFC Section 4.6 - Floating Point
267
// 	32-bit single-precision IEEE 754 floating point
268
func (d *Decoder) DecodeFloat() (float32, int, error) {
269
	var buf [4]byte
270
	n, err := io.ReadFull(d.r, buf[:])
271
	if err != nil {
272
		msg := fmt.Sprintf(errIODecode, err.Error(), 4)
273
		err := unmarshalError("DecodeFloat", ErrIO, msg, buf[:n], err)
274
		return 0, n, err
275
	}
276

277
	val := uint32(buf[3]) | uint32(buf[2])<<8 |
278
		uint32(buf[1])<<16 | uint32(buf[0])<<24
279
	return math.Float32frombits(val), n, nil
280
}
281

282
// DecodeDouble treats the next 8 bytes as an XDR encoded double-precision
283
// floating point and returns the result as a float64 along with the number of
284
// bytes actually read.
285
//
286
// An UnmarshalError is returned if there are insufficient bytes remaining.
287
//
288
// Reference:
289
// 	RFC Section 4.7 -  Double-Precision Floating Point
290
// 	64-bit double-precision IEEE 754 floating point
291
func (d *Decoder) DecodeDouble() (float64, int, error) {
292
	var buf [8]byte
293
	n, err := io.ReadFull(d.r, buf[:])
294
	if err != nil {
295
		msg := fmt.Sprintf(errIODecode, err.Error(), 8)
296
		err := unmarshalError("DecodeDouble", ErrIO, msg, buf[:n], err)
297
		return 0, n, err
298
	}
299

300
	val := uint64(buf[7]) | uint64(buf[6])<<8 |
301
		uint64(buf[5])<<16 | uint64(buf[4])<<24 |
302
		uint64(buf[3])<<32 | uint64(buf[2])<<40 |
303
		uint64(buf[1])<<48 | uint64(buf[0])<<56
304
	return math.Float64frombits(val), n, nil
305
}
306

307
// RFC Section 4.8 -  Quadruple-Precision Floating Point
308
// 128-bit quadruple-precision floating point
309
// Not Implemented
310

311
// DecodeFixedOpaque treats the next 'size' bytes as XDR encoded opaque data and
312
// returns the result as a byte slice along with the number of bytes actually
313
// read.
314
//
315
// An UnmarshalError is returned if there are insufficient bytes remaining to
316
// satisfy the passed size, including the necessary padding to make it a
317
// multiple of 4.
318
//
319
// Reference:
320
// 	RFC Section 4.9 - Fixed-Length Opaque Data
321
// 	Fixed-length uninterpreted data zero-padded to a multiple of four
322
func (d *Decoder) DecodeFixedOpaque(size int32) ([]byte, int, error) {
323
	// Nothing to do if size is 0.
324
	if size == 0 {
325
		return nil, 0, nil
326
	}
327

328
	pad := (4 - (size % 4)) % 4
329
	paddedSize := size + pad
330
	if uint(paddedSize) > uint(math.MaxInt32) {
331
		err := unmarshalError("DecodeFixedOpaque", ErrOverflow,
332
			errMaxSlice, paddedSize, nil)
333
		return nil, 0, err
334
	}
335

336
	buf := make([]byte, paddedSize)
337
	n, err := io.ReadFull(d.r, buf)
338
	if err != nil {
339
		msg := fmt.Sprintf(errIODecode, err.Error(), paddedSize)
340
		err := unmarshalError("DecodeFixedOpaque", ErrIO, msg, buf[:n],
341
			err)
342
		return nil, n, err
343
	}
344
	return buf[0:size], n, nil
345
}
346

347
// DecodeOpaque treats the next bytes as variable length XDR encoded opaque
348
// data and returns the result as a byte slice along with the number of bytes
349
// actually read.
350
//
351
// An UnmarshalError is returned if there are insufficient bytes remaining or
352
// the opaque data is larger than the max length of a Go slice.
353
//
354
// Reference:
355
// 	RFC Section 4.10 - Variable-Length Opaque Data
356
// 	Unsigned integer length followed by fixed opaque data of that length
357
func (d *Decoder) DecodeOpaque() ([]byte, int, error) {
358
	dataLen, n, err := d.DecodeUint()
359
	if err != nil {
360
		return nil, n, err
361
	}
362
	if uint(dataLen) > uint(math.MaxInt32) ||
363
		(d.maxReadSize != 0 && uint(dataLen) > d.maxReadSize) {
364
		err := unmarshalError("DecodeOpaque", ErrOverflow, errMaxSlice,
365
			dataLen, nil)
366
		return nil, n, err
367
	}
368

369
	rv, n2, err := d.DecodeFixedOpaque(int32(dataLen))
370
	n += n2
371
	if err != nil {
372
		return nil, n, err
373
	}
374
	return rv, n, nil
375
}
376

377
// DecodeString treats the next bytes as a variable length XDR encoded string
378
// and returns the result as a string along with the number of bytes actually
379
// read.  Character encoding is assumed to be UTF-8 and therefore ASCII
380
// compatible.  If the underlying character encoding is not compatibile with
381
// this assumption, the data can instead be read as variable-length opaque data
382
// (DecodeOpaque) and manually converted as needed.
383
//
384
// An UnmarshalError is returned if there are insufficient bytes remaining or
385
// the string data is larger than the max length of a Go slice.
386
//
387
// Reference:
388
// 	RFC Section 4.11 - String
389
// 	Unsigned integer length followed by bytes zero-padded to a multiple of
390
// 	four
391
func (d *Decoder) DecodeString() (string, int, error) {
392
	dataLen, n, err := d.DecodeUint()
393
	if err != nil {
394
		return "", n, err
395
	}
396
	if uint(dataLen) > uint(math.MaxInt32) ||
397
		(d.maxReadSize != 0 && uint(dataLen) > d.maxReadSize) {
398
		err = unmarshalError("DecodeString", ErrOverflow, errMaxSlice,
399
			dataLen, nil)
400
		return "", n, err
401
	}
402

403
	opaque, n2, err := d.DecodeFixedOpaque(int32(dataLen))
404
	n += n2
405
	if err != nil {
406
		return "", n, err
407
	}
408
	return string(opaque), n, nil
409
}
410

411
// decodeFixedArray treats the next bytes as a series of XDR encoded elements
412
// of the same type as the array represented by the reflection value and decodes
413
// each element into the passed array.  The ignoreOpaque flag controls whether
414
// or not uint8 (byte) elements should be decoded individually or as a fixed
415
// sequence of opaque data.  It returns the  the number of bytes actually read.
416
//
417
// An UnmarshalError is returned if any issues are encountered while decoding
418
// the array elements.
419
//
420
// Reference:
421
// 	RFC Section 4.12 - Fixed-Length Array
422
// 	Individually XDR encoded array elements
423
func (d *Decoder) decodeFixedArray(v reflect.Value, ignoreOpaque bool) (int, error) {
424
	// Treat [#]byte (byte is alias for uint8) as opaque data unless
425
	// ignored.
426
	if !ignoreOpaque && v.Type().Elem().Kind() == reflect.Uint8 {
427
		data, n, err := d.DecodeFixedOpaque(int32(v.Len()))
428
		if err != nil {
429
			return n, err
430
		}
431
		reflect.Copy(v, reflect.ValueOf(data))
432
		return n, nil
433
	}
434

435
	// Decode each array element.
436
	var n int
437
	for i := 0; i < v.Len(); i++ {
438
		n2, err := d.decode(v.Index(i))
439
		n += n2
440
		if err != nil {
441
			return n, err
442
		}
443
	}
444
	return n, nil
445
}
446

447
// decodeArray treats the next bytes as a variable length series of XDR encoded
448
// elements of the same type as the array represented by the reflection value.
449
// The number of elements is obtained by first decoding the unsigned integer
450
// element count.  Then each element is decoded into the passed array. The
451
// ignoreOpaque flag controls whether or not uint8 (byte) elements should be
452
// decoded individually or as a variable sequence of opaque data.  It returns
453
// the number of bytes actually read.
454
//
455
// An UnmarshalError is returned if any issues are encountered while decoding
456
// the array elements.
457
//
458
// Reference:
459
// 	RFC Section 4.13 - Variable-Length Array
460
// 	Unsigned integer length followed by individually XDR encoded array
461
// 	elements
462
func (d *Decoder) decodeArray(v reflect.Value, ignoreOpaque bool) (int, error) {
463
	dataLen, n, err := d.DecodeUint()
464
	if err != nil {
465
		return n, err
466
	}
467
	if uint(dataLen) > uint(math.MaxInt32) ||
468
		(d.maxReadSize != 0 && uint(dataLen) > d.maxReadSize) {
469
		err := unmarshalError("decodeArray", ErrOverflow, errMaxSlice,
470
			dataLen, nil)
471
		return n, err
472
	}
473

474
	// Allocate storage for the slice elements (the underlying array) if
475
	// existing slice does not have enough capacity.
476
	sliceLen := int(dataLen)
477
	if v.Cap() < sliceLen {
478
		v.Set(reflect.MakeSlice(v.Type(), sliceLen, sliceLen))
479
	}
480
	if v.Len() < sliceLen {
481
		v.SetLen(sliceLen)
482
	}
483

484
	// Treat []byte (byte is alias for uint8) as opaque data unless ignored.
485
	if !ignoreOpaque && v.Type().Elem().Kind() == reflect.Uint8 {
486
		data, n2, err := d.DecodeFixedOpaque(int32(sliceLen))
487
		n += n2
488
		if err != nil {
489
			return n, err
490
		}
491
		v.SetBytes(data)
492
		return n, nil
493
	}
494

495
	// Decode each slice element.
496
	for i := 0; i < sliceLen; i++ {
497
		n2, err := d.decode(v.Index(i))
498
		n += n2
499
		if err != nil {
500
			return n, err
501
		}
502
	}
503
	return n, nil
504
}
505

506
// decodeStruct treats the next bytes as a series of XDR encoded elements
507
// of the same type as the exported fields of the struct represented by the
508
// passed reflection value.  Pointers are automatically indirected and
509
// allocated as necessary.  It returns the  the number of bytes actually read.
510
//
511
// An UnmarshalError is returned if any issues are encountered while decoding
512
// the elements.
513
//
514
// Reference:
515
// 	RFC Section 4.14 - Structure
516
// 	XDR encoded elements in the order of their declaration in the struct
517
func (d *Decoder) decodeStruct(v reflect.Value) (int, error) {
518
	var n int
519
	vt := v.Type()
520
	for i := 0; i < v.NumField(); i++ {
521
		// Skip unexported fields.
522
		vtf := vt.Field(i)
523
		if vtf.PkgPath != "" {
524
			continue
525
		}
526

527
		// Indirect through pointers allocating them as needed and
528
		// ensure the field is settable.
529
		vf := v.Field(i)
530
		vf, err := d.indirect(vf)
531
		if err != nil {
532
			return n, err
533
		}
534
		if !vf.CanSet() {
535
			msg := fmt.Sprintf("can't decode to unsettable '%v'",
536
				vf.Type().String())
537
			err := unmarshalError("decodeStruct", ErrNotSettable,
538
				msg, nil, nil)
539
			return n, err
540
		}
541

542
		// Handle non-opaque data to []uint8 and [#]uint8 based on
543
		// struct tag.
544
		tag := vtf.Tag.Get("xdropaque")
545
		if tag == "false" {
546
			switch vf.Kind() {
547
			case reflect.Slice:
548
				n2, err := d.decodeArray(vf, true)
549
				n += n2
550
				if err != nil {
551
					return n, err
552
				}
553
				continue
554

555
			case reflect.Array:
556
				n2, err := d.decodeFixedArray(vf, true)
557
				n += n2
558
				if err != nil {
559
					return n, err
560
				}
561
				continue
562
			}
563
		}
564

565
		// Decode each struct field.
566
		n2, err := d.decode(vf)
567
		n += n2
568
		if err != nil {
569
			return n, err
570
		}
571
	}
572

573
	return n, nil
574
}
575

576
// RFC Section 4.15 - Discriminated Union
577
// RFC Section 4.16 - Void
578
// RFC Section 4.17 - Constant
579
// RFC Section 4.18 - Typedef
580
// RFC Section 4.19 - Optional data
581
// RFC Sections 4.15 though 4.19 only apply to the data specification language
582
// which is not implemented by this package.  In the case of discriminated
583
// unions, struct tags are used to perform a similar function.
584

585
// decodeMap treats the next bytes as an XDR encoded variable array of 2-element
586
// structures whose fields are of the same type as the map keys and elements
587
// represented by the passed reflection value.  Pointers are automatically
588
// indirected and allocated as necessary.  It returns the  the number of bytes
589
// actually read.
590
//
591
// An UnmarshalError is returned if any issues are encountered while decoding
592
// the elements.
593
func (d *Decoder) decodeMap(v reflect.Value) (int, error) {
594
	dataLen, n, err := d.DecodeUint()
595
	if err != nil {
596
		return n, err
597
	}
598

599
	// Allocate storage for the underlying map if needed.
600
	vt := v.Type()
601
	if v.IsNil() {
602
		v.Set(reflect.MakeMap(vt))
603
	}
604

605
	// Decode each key and value according to their type.
606
	keyType := vt.Key()
607
	elemType := vt.Elem()
608
	for i := uint32(0); i < dataLen; i++ {
609
		key := reflect.New(keyType).Elem()
610
		n2, err := d.decode(key)
611
		n += n2
612
		if err != nil {
613
			return n, err
614
		}
615

616
		val := reflect.New(elemType).Elem()
617
		n2, err = d.decode(val)
618
		n += n2
619
		if err != nil {
620
			return n, err
621
		}
622
		v.SetMapIndex(key, val)
623
	}
624
	return n, nil
625
}
626

627
// decodeInterface examines the interface represented by the passed reflection
628
// value to detect whether it is an interface that can be decoded into and
629
// if it is, extracts the underlying value to pass back into the decode function
630
// for decoding according to its type.  It returns the  the number of bytes
631
// actually read.
632
//
633
// An UnmarshalError is returned if any issues are encountered while decoding
634
// the interface.
635
func (d *Decoder) decodeInterface(v reflect.Value) (int, error) {
636
	if v.IsNil() || !v.CanInterface() {
637
		msg := fmt.Sprintf("can't decode to nil interface")
638
		err := unmarshalError("decodeInterface", ErrNilInterface, msg,
639
			nil, nil)
640
		return 0, err
641
	}
642

643
	// Extract underlying value from the interface and indirect through
644
	// pointers allocating them as needed.
645
	ve := reflect.ValueOf(v.Interface())
646
	ve, err := d.indirect(ve)
647
	if err != nil {
648
		return 0, err
649
	}
650
	if !ve.CanSet() {
651
		msg := fmt.Sprintf("can't decode to unsettable '%v'",
652
			ve.Type().String())
653
		err := unmarshalError("decodeInterface", ErrNotSettable, msg,
654
			nil, nil)
655
		return 0, err
656
	}
657
	return d.decode(ve)
658
}
659

660
// decode is the main workhorse for unmarshalling via reflection.  It uses
661
// the passed reflection value to choose the XDR primitives to decode from
662
// the encapsulated reader.  It is a recursive function,
663
// so cyclic data structures are not supported and will result in an infinite
664
// loop.  It returns the  the number of bytes actually read.
665
func (d *Decoder) decode(v reflect.Value) (int, error) {
666
	if !v.IsValid() {
667
		msg := fmt.Sprintf("type '%s' is not valid", v.Kind().String())
668
		err := unmarshalError("decode", ErrUnsupportedType, msg, nil, nil)
669
		return 0, err
670
	}
671

672
	// Indirect through pointers allocating them as needed.
673
	ve, err := d.indirect(v)
674
	if err != nil {
675
		return 0, err
676
	}
677

678
	// Handle time.Time values by decoding them as an RFC3339 formatted
679
	// string with nanosecond precision.  Check the type string rather
680
	// than doing a full blown conversion to interface and type assertion
681
	// since checking a string is much quicker.
682
	switch ve.Type().String() {
683
	case "time.Time":
684
		// Read the value as a string and parse it.
685
		timeString, n, err := d.DecodeString()
686
		if err != nil {
687
			return n, err
688
		}
689
		ttv, err := time.Parse(time.RFC3339, timeString)
690
		if err != nil {
691
			err := unmarshalError("decode", ErrParseTime,
692
				err.Error(), timeString, err)
693
			return n, err
694
		}
695
		ve.Set(reflect.ValueOf(ttv))
696
		return n, nil
697
	}
698
	// If this type is in our custom types map, call the decode routine set up
699
	// for it.
700
	if dt, ok := d.customTypes[ve.Type().String()]; ok {
701
		return dt.Decode(d, v)
702
	}
703

704
	// Handle native Go types.
705
	switch ve.Kind() {
706
	case reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int:
707
		i, n, err := d.DecodeInt()
708
		if err != nil {
709
			return n, err
710
		}
711
		if ve.OverflowInt(int64(i)) {
712
			msg := fmt.Sprintf("signed integer too large to fit '%s'",
713
				ve.Kind().String())
714
			err = unmarshalError("decode", ErrOverflow, msg, i, nil)
715
			return n, err
716
		}
717
		ve.SetInt(int64(i))
718
		return n, nil
719

720
	case reflect.Int64:
721
		i, n, err := d.DecodeHyper()
722
		if err != nil {
723
			return n, err
724
		}
725
		ve.SetInt(i)
726
		return n, nil
727

728
	case reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint:
729
		ui, n, err := d.DecodeUint()
730
		if err != nil {
731
			return n, err
732
		}
733
		if ve.OverflowUint(uint64(ui)) {
734
			msg := fmt.Sprintf("unsigned integer too large to fit '%s'",
735
				ve.Kind().String())
736
			err = unmarshalError("decode", ErrOverflow, msg, ui, nil)
737
			return n, err
738
		}
739
		ve.SetUint(uint64(ui))
740
		return n, nil
741

742
	case reflect.Uint64:
743
		ui, n, err := d.DecodeUhyper()
744
		if err != nil {
745
			return n, err
746
		}
747
		ve.SetUint(ui)
748
		return n, nil
749

750
	case reflect.Bool:
751
		b, n, err := d.DecodeBool()
752
		if err != nil {
753
			return n, err
754
		}
755
		ve.SetBool(b)
756
		return n, nil
757

758
	case reflect.Float32:
759
		f, n, err := d.DecodeFloat()
760
		if err != nil {
761
			return n, err
762
		}
763
		ve.SetFloat(float64(f))
764
		return n, nil
765

766
	case reflect.Float64:
767
		f, n, err := d.DecodeDouble()
768
		if err != nil {
769
			return n, err
770
		}
771
		ve.SetFloat(f)
772
		return n, nil
773

774
	case reflect.String:
775
		s, n, err := d.DecodeString()
776
		if err != nil {
777
			return n, err
778
		}
779
		ve.SetString(s)
780
		return n, nil
781

782
	case reflect.Array:
783
		n, err := d.decodeFixedArray(ve, false)
784
		if err != nil {
785
			return n, err
786
		}
787
		return n, nil
788

789
	case reflect.Slice:
790
		n, err := d.decodeArray(ve, false)
791
		if err != nil {
792
			return n, err
793
		}
794
		return n, nil
795

796
	case reflect.Struct:
797
		n, err := d.decodeStruct(ve)
798
		if err != nil {
799
			return n, err
800
		}
801
		return n, nil
802

803
	case reflect.Map:
804
		n, err := d.decodeMap(ve)
805
		if err != nil {
806
			return n, err
807
		}
808
		return n, nil
809

810
	case reflect.Interface:
811
		n, err := d.decodeInterface(ve)
812
		if err != nil {
813
			return n, err
814
		}
815
		return n, nil
816
	}
817

818
	// The only unhandled types left are unsupported.  At the time of this
819
	// writing the only remaining unsupported types that exist are
820
	// reflect.Uintptr and reflect.UnsafePointer.
821
	msg := fmt.Sprintf("unsupported Go type '%s'", ve.Kind().String())
822
	err = unmarshalError("decode", ErrUnsupportedType, msg, nil, nil)
823
	return 0, err
824
}
825

826
// indirect dereferences pointers allocating them as needed until it reaches
827
// a non-pointer.  This allows transparent decoding through arbitrary levels
828
// of indirection.
829
func (d *Decoder) indirect(v reflect.Value) (reflect.Value, error) {
830
	rv := v
831
	for rv.Kind() == reflect.Ptr {
832
		// Allocate pointer if needed.
833
		isNil := rv.IsNil()
834
		if isNil && !rv.CanSet() {
835
			msg := fmt.Sprintf("unable to allocate pointer for '%v'",
836
				rv.Type().String())
837
			err := unmarshalError("indirect", ErrNotSettable, msg,
838
				nil, nil)
839
			return rv, err
840
		}
841
		if isNil {
842
			rv.Set(reflect.New(rv.Type().Elem()))
843
		}
844
		rv = rv.Elem()
845
	}
846
	return rv, nil
847
}
848

849
// Decode operates identically to the Unmarshal function with the exception of
850
// using the reader associated with the Decoder as the source of XDR-encoded
851
// data instead of a user-supplied reader.  See the Unmarhsal documentation for
852
// specifics.
853
func (d *Decoder) Decode(v interface{}) (int, error) {
854
	if v == nil {
855
		msg := "can't unmarshal to nil interface"
856
		return 0, unmarshalError("Unmarshal", ErrNilInterface, msg, nil,
857
			nil)
858
	}
859

860
	vv := reflect.ValueOf(v)
861
	if vv.Kind() != reflect.Ptr {
862
		msg := fmt.Sprintf("can't unmarshal to non-pointer '%v' - use "+
863
			"& operator", vv.Type().String())
864
		err := unmarshalError("Unmarshal", ErrBadArguments, msg, nil, nil)
865
		return 0, err
866
	}
867
	if vv.IsNil() && !vv.CanSet() {
868
		msg := fmt.Sprintf("can't unmarshal to unsettable '%v' - use "+
869
			"& operator", vv.Type().String())
870
		err := unmarshalError("Unmarshal", ErrNotSettable, msg, nil, nil)
871
		return 0, err
872
	}
873

874
	return d.decode(vv)
875
}
876

877
// NewDecoder returns a Decoder that can be used to manually decode XDR data
878
// from a provided reader.  Typically, Unmarshal should be used instead of
879
// manually creating a Decoder.
880
func NewDecoder(r io.Reader) *Decoder {
881
	return &Decoder{r: r}
882
}
883

884
// NewDecoderLimited is identical to NewDecoder but it sets maxReadSize in
885
// order to cap reads.
886
func NewDecoderLimited(r io.Reader, maxSize uint) *Decoder {
887
	return &Decoder{r: r, maxReadSize: maxSize}
888
}
889

890
// NewDecoderCustomTypes returns a decoder with support for custom types known
891
// to the caller. The second parameter is a map of the type name to the decoder
892
// routine. When the decoder finds a type matching one of the entries in the map
893
// it will call the custom routine for that type.
894
func NewDecoderCustomTypes(r io.Reader, maxSize uint, ct map[string]TypeDecoder) *Decoder {
895
	return &Decoder{r: r, maxReadSize: maxSize, customTypes: ct}
896
}
897

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.