1// Copyright 2009 The Go Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style
3// license that can be found in the LICENSE file.
4
5// DWARF type information structures.
6// The format is heavily biased toward C, but for simplicity
7// the String methods use a pseudo-Go syntax.
8
9package dwarf
10
11import "strconv"
12
13// A Type conventionally represents a pointer to any of the
14// specific Type structures ([CharType], [StructType], etc.).
15type Type interface {
16	Common() *CommonType
17	String() string
18	Size() int64
19}
20
21// A CommonType holds fields common to multiple types.
22// If a field is not known or not applicable for a given type,
23// the zero value is used.
24type CommonType struct {
25	ByteSize int64  // size of value of this type, in bytes
26	Name     string // name that can be used to refer to type
27}
28
29func (c *CommonType) Common() *CommonType { return c }
30
31func (c *CommonType) Size() int64 { return c.ByteSize }
32
33// Basic types
34
35// A BasicType holds fields common to all basic types.
36//
37// See the documentation for [StructField] for more info on the interpretation of
38// the BitSize/BitOffset/DataBitOffset fields.
39type BasicType struct {
40	CommonType
41	BitSize       int64
42	BitOffset     int64
43	DataBitOffset int64
44}
45
46func (b *BasicType) Basic() *BasicType { return b }
47
48func (t *BasicType) String() string {
49	if t.Name != "" {
50		return t.Name
51	}
52	return "?"
53}
54
55// A CharType represents a signed character type.
56type CharType struct {
57	BasicType
58}
59
60// A UcharType represents an unsigned character type.
61type UcharType struct {
62	BasicType
63}
64
65// An IntType represents a signed integer type.
66type IntType struct {
67	BasicType
68}
69
70// A UintType represents an unsigned integer type.
71type UintType struct {
72	BasicType
73}
74
75// A FloatType represents a floating point type.
76type FloatType struct {
77	BasicType
78}
79
80// A ComplexType represents a complex floating point type.
81type ComplexType struct {
82	BasicType
83}
84
85// A BoolType represents a boolean type.
86type BoolType struct {
87	BasicType
88}
89
90// An AddrType represents a machine address type.
91type AddrType struct {
92	BasicType
93}
94
95// An UnspecifiedType represents an implicit, unknown, ambiguous or nonexistent type.
96type UnspecifiedType struct {
97	BasicType
98}
99
100// qualifiers
101
102// A QualType represents a type that has the C/C++ "const", "restrict", or "volatile" qualifier.
103type QualType struct {
104	CommonType
105	Qual string
106	Type Type
107}
108
109func (t *QualType) String() string { return t.Qual + " " + t.Type.String() }
110
111func (t *QualType) Size() int64 { return t.Type.Size() }
112
113// An ArrayType represents a fixed size array type.
114type ArrayType struct {
115	CommonType
116	Type          Type
117	StrideBitSize int64 // if > 0, number of bits to hold each element
118	Count         int64 // if == -1, an incomplete array, like char x[].
119}
120
121func (t *ArrayType) String() string {
122	return "[" + strconv.FormatInt(t.Count, 10) + "]" + t.Type.String()
123}
124
125func (t *ArrayType) Size() int64 {
126	if t.Count == -1 {
127		return 0
128	}
129	return t.Count * t.Type.Size()
130}
131
132// A VoidType represents the C void type.
133type VoidType struct {
134	CommonType
135}
136
137func (t *VoidType) String() string { return "void" }
138
139// A PtrType represents a pointer type.
140type PtrType struct {
141	CommonType
142	Type Type
143}
144
145func (t *PtrType) String() string { return "*" + t.Type.String() }
146
147// A StructType represents a struct, union, or C++ class type.
148type StructType struct {
149	CommonType
150	StructName string
151	Kind       string // "struct", "union", or "class".
152	Field      []*StructField
153	Incomplete bool // if true, struct, union, class is declared but not defined
154}
155
156// A StructField represents a field in a struct, union, or C++ class type.
157//
158// # Bit Fields
159//
160// The BitSize, BitOffset, and DataBitOffset fields describe the bit
161// size and offset of data members declared as bit fields in C/C++
162// struct/union/class types.
163//
164// BitSize is the number of bits in the bit field.
165//
166// DataBitOffset, if non-zero, is the number of bits from the start of
167// the enclosing entity (e.g. containing struct/class/union) to the
168// start of the bit field. This corresponds to the DW_AT_data_bit_offset
169// DWARF attribute that was introduced in DWARF 4.
170//
171// BitOffset, if non-zero, is the number of bits between the most
172// significant bit of the storage unit holding the bit field to the
173// most significant bit of the bit field. Here "storage unit" is the
174// type name before the bit field (for a field "unsigned x:17", the
175// storage unit is "unsigned"). BitOffset values can vary depending on
176// the endianness of the system. BitOffset corresponds to the
177// DW_AT_bit_offset DWARF attribute that was deprecated in DWARF 4 and
178// removed in DWARF 5.
179//
180// At most one of DataBitOffset and BitOffset will be non-zero;
181// DataBitOffset/BitOffset will only be non-zero if BitSize is
182// non-zero. Whether a C compiler uses one or the other
183// will depend on compiler vintage and command line options.
184//
185// Here is an example of C/C++ bit field use, along with what to
186// expect in terms of DWARF bit offset info. Consider this code:
187//
188//	struct S {
189//		int q;
190//		int j:5;
191//		int k:6;
192//		int m:5;
193//		int n:8;
194//	} s;
195//
196// For the code above, one would expect to see the following for
197// DW_AT_bit_offset values (using GCC 8):
198//
199//	       Little   |     Big
200//	       Endian   |    Endian
201//	                |
202//	"j":     27     |     0
203//	"k":     21     |     5
204//	"m":     16     |     11
205//	"n":     8      |     16
206//
207// Note that in the above the offsets are purely with respect to the
208// containing storage unit for j/k/m/n -- these values won't vary based
209// on the size of prior data members in the containing struct.
210//
211// If the compiler emits DW_AT_data_bit_offset, the expected values
212// would be:
213//
214//	"j":     32
215//	"k":     37
216//	"m":     43
217//	"n":     48
218//
219// Here the value 32 for "j" reflects the fact that the bit field is
220// preceded by other data members (recall that DW_AT_data_bit_offset
221// values are relative to the start of the containing struct). Hence
222// DW_AT_data_bit_offset values can be quite large for structs with
223// many fields.
224//
225// DWARF also allow for the possibility of base types that have
226// non-zero bit size and bit offset, so this information is also
227// captured for base types, but it is worth noting that it is not
228// possible to trigger this behavior using mainstream languages.
229type StructField struct {
230	Name          string
231	Type          Type
232	ByteOffset    int64
233	ByteSize      int64 // usually zero; use Type.Size() for normal fields
234	BitOffset     int64
235	DataBitOffset int64
236	BitSize       int64 // zero if not a bit field
237}
238
239func (t *StructType) String() string {
240	if t.StructName != "" {
241		return t.Kind + " " + t.StructName
242	}
243	return t.Defn()
244}
245
246func (f *StructField) bitOffset() int64 {
247	if f.BitOffset != 0 {
248		return f.BitOffset
249	}
250	return f.DataBitOffset
251}
252
253func (t *StructType) Defn() string {
254	s := t.Kind
255	if t.StructName != "" {
256		s += " " + t.StructName
257	}
258	if t.Incomplete {
259		s += " /*incomplete*/"
260		return s
261	}
262	s += " {"
263	for i, f := range t.Field {
264		if i > 0 {
265			s += "; "
266		}
267		s += f.Name + " " + f.Type.String()
268		s += "@" + strconv.FormatInt(f.ByteOffset, 10)
269		if f.BitSize > 0 {
270			s += " : " + strconv.FormatInt(f.BitSize, 10)
271			s += "@" + strconv.FormatInt(f.bitOffset(), 10)
272		}
273	}
274	s += "}"
275	return s
276}
277
278// An EnumType represents an enumerated type.
279// The only indication of its native integer type is its ByteSize
280// (inside [CommonType]).
281type EnumType struct {
282	CommonType
283	EnumName string
284	Val      []*EnumValue
285}
286
287// An EnumValue represents a single enumeration value.
288type EnumValue struct {
289	Name string
290	Val  int64
291}
292
293func (t *EnumType) String() string {
294	s := "enum"
295	if t.EnumName != "" {
296		s += " " + t.EnumName
297	}
298	s += " {"
299	for i, v := range t.Val {
300		if i > 0 {
301			s += "; "
302		}
303		s += v.Name + "=" + strconv.FormatInt(v.Val, 10)
304	}
305	s += "}"
306	return s
307}
308
309// A FuncType represents a function type.
310type FuncType struct {
311	CommonType
312	ReturnType Type
313	ParamType  []Type
314}
315
316func (t *FuncType) String() string {
317	s := "func("
318	for i, t := range t.ParamType {
319		if i > 0 {
320			s += ", "
321		}
322		s += t.String()
323	}
324	s += ")"
325	if t.ReturnType != nil {
326		s += " " + t.ReturnType.String()
327	}
328	return s
329}
330
331// A DotDotDotType represents the variadic ... function parameter.
332type DotDotDotType struct {
333	CommonType
334}
335
336func (t *DotDotDotType) String() string { return "..." }
337
338// A TypedefType represents a named type.
339type TypedefType struct {
340	CommonType
341	Type Type
342}
343
344func (t *TypedefType) String() string { return t.Name }
345
346func (t *TypedefType) Size() int64 { return t.Type.Size() }
347
348// An UnsupportedType is a placeholder returned in situations where we
349// encounter a type that isn't supported.
350type UnsupportedType struct {
351	CommonType
352	Tag Tag
353}
354
355func (t *UnsupportedType) String() string {
356	if t.Name != "" {
357		return t.Name
358	}
359	return t.Name + "(unsupported type " + t.Tag.String() + ")"
360}
361
362// typeReader is used to read from either the info section or the
363// types section.
364type typeReader interface {
365	Seek(Offset)
366	Next() (*Entry, error)
367	clone() typeReader
368	offset() Offset
369	// AddressSize returns the size in bytes of addresses in the current
370	// compilation unit.
371	AddressSize() int
372}
373
374// Type reads the type at off in the DWARF “info” section.
375func (d *Data) Type(off Offset) (Type, error) {
376	return d.readType("info", d.Reader(), off, d.typeCache, nil)
377}
378
379type typeFixer struct {
380	typedefs   []*TypedefType
381	arraytypes []*Type
382}
383
384func (tf *typeFixer) recordArrayType(t *Type) {
385	if t == nil {
386		return
387	}
388	_, ok := (*t).(*ArrayType)
389	if ok {
390		tf.arraytypes = append(tf.arraytypes, t)
391	}
392}
393
394func (tf *typeFixer) apply() {
395	for _, t := range tf.typedefs {
396		t.Common().ByteSize = t.Type.Size()
397	}
398	for _, t := range tf.arraytypes {
399		zeroArray(t)
400	}
401}
402
403// readType reads a type from r at off of name. It adds types to the
404// type cache, appends new typedef types to typedefs, and computes the
405// sizes of types. Callers should pass nil for typedefs; this is used
406// for internal recursion.
407func (d *Data) readType(name string, r typeReader, off Offset, typeCache map[Offset]Type, fixups *typeFixer) (Type, error) {
408	if t, ok := typeCache[off]; ok {
409		return t, nil
410	}
411	r.Seek(off)
412	e, err := r.Next()
413	if err != nil {
414		return nil, err
415	}
416	addressSize := r.AddressSize()
417	if e == nil || e.Offset != off {
418		return nil, DecodeError{name, off, "no type at offset"}
419	}
420
421	// If this is the root of the recursion, prepare to resolve
422	// typedef sizes and perform other fixups once the recursion is
423	// done. This must be done after the type graph is constructed
424	// because it may need to resolve cycles in a different order than
425	// readType encounters them.
426	if fixups == nil {
427		var fixer typeFixer
428		defer func() {
429			fixer.apply()
430		}()
431		fixups = &fixer
432	}
433
434	// Parse type from Entry.
435	// Must always set typeCache[off] before calling
436	// d.readType recursively, to handle circular types correctly.
437	var typ Type
438
439	nextDepth := 0
440
441	// Get next child; set err if error happens.
442	next := func() *Entry {
443		if !e.Children {
444			return nil
445		}
446		// Only return direct children.
447		// Skip over composite entries that happen to be nested
448		// inside this one. Most DWARF generators wouldn't generate
449		// such a thing, but clang does.
450		// See golang.org/issue/6472.
451		for {
452			kid, err1 := r.Next()
453			if err1 != nil {
454				err = err1
455				return nil
456			}
457			if kid == nil {
458				err = DecodeError{name, r.offset(), "unexpected end of DWARF entries"}
459				return nil
460			}
461			if kid.Tag == 0 {
462				if nextDepth > 0 {
463					nextDepth--
464					continue
465				}
466				return nil
467			}
468			if kid.Children {
469				nextDepth++
470			}
471			if nextDepth > 0 {
472				continue
473			}
474			return kid
475		}
476	}
477
478	// Get Type referred to by Entry's AttrType field.
479	// Set err if error happens. Not having a type is an error.
480	typeOf := func(e *Entry) Type {
481		tval := e.Val(AttrType)
482		var t Type
483		switch toff := tval.(type) {
484		case Offset:
485			if t, err = d.readType(name, r.clone(), toff, typeCache, fixups); err != nil {
486				return nil
487			}
488		case uint64:
489			if t, err = d.sigToType(toff); err != nil {
490				return nil
491			}
492		default:
493			// It appears that no Type means "void".
494			return new(VoidType)
495		}
496		return t
497	}
498
499	switch e.Tag {
500	case TagArrayType:
501		// Multi-dimensional array.  (DWARF v2 §5.4)
502		// Attributes:
503		//	AttrType:subtype [required]
504		//	AttrStrideSize: size in bits of each element of the array
505		//	AttrByteSize: size of entire array
506		// Children:
507		//	TagSubrangeType or TagEnumerationType giving one dimension.
508		//	dimensions are in left to right order.
509		t := new(ArrayType)
510		typ = t
511		typeCache[off] = t
512		if t.Type = typeOf(e); err != nil {
513			goto Error
514		}
515		t.StrideBitSize, _ = e.Val(AttrStrideSize).(int64)
516
517		// Accumulate dimensions,
518		var dims []int64
519		for kid := next(); kid != nil; kid = next() {
520			// TODO(rsc): Can also be TagEnumerationType
521			// but haven't seen that in the wild yet.
522			switch kid.Tag {
523			case TagSubrangeType:
524				count, ok := kid.Val(AttrCount).(int64)
525				if !ok {
526					// Old binaries may have an upper bound instead.
527					count, ok = kid.Val(AttrUpperBound).(int64)
528					if ok {
529						count++ // Length is one more than upper bound.
530					} else if len(dims) == 0 {
531						count = -1 // As in x[].
532					}
533				}
534				dims = append(dims, count)
535			case TagEnumerationType:
536				err = DecodeError{name, kid.Offset, "cannot handle enumeration type as array bound"}
537				goto Error
538			}
539		}
540		if len(dims) == 0 {
541			// LLVM generates this for x[].
542			dims = []int64{-1}
543		}
544
545		t.Count = dims[0]
546		for i := len(dims) - 1; i >= 1; i-- {
547			t.Type = &ArrayType{Type: t.Type, Count: dims[i]}
548		}
549
550	case TagBaseType:
551		// Basic type.  (DWARF v2 §5.1)
552		// Attributes:
553		//	AttrName: name of base type in programming language of the compilation unit [required]
554		//	AttrEncoding: encoding value for type (encFloat etc) [required]
555		//	AttrByteSize: size of type in bytes [required]
556		//	AttrBitOffset: bit offset of value within containing storage unit
557		//	AttrDataBitOffset: bit offset of value within containing storage unit
558		//	AttrBitSize: size in bits
559		//
560		// For most languages BitOffset/DataBitOffset/BitSize will not be present
561		// for base types.
562		name, _ := e.Val(AttrName).(string)
563		enc, ok := e.Val(AttrEncoding).(int64)
564		if !ok {
565			err = DecodeError{name, e.Offset, "missing encoding attribute for " + name}
566			goto Error
567		}
568		switch enc {
569		default:
570			err = DecodeError{name, e.Offset, "unrecognized encoding attribute value"}
571			goto Error
572
573		case encAddress:
574			typ = new(AddrType)
575		case encBoolean:
576			typ = new(BoolType)
577		case encComplexFloat:
578			typ = new(ComplexType)
579			if name == "complex" {
580				// clang writes out 'complex' instead of 'complex float' or 'complex double'.
581				// clang also writes out a byte size that we can use to distinguish.
582				// See issue 8694.
583				switch byteSize, _ := e.Val(AttrByteSize).(int64); byteSize {
584				case 8:
585					name = "complex float"
586				case 16:
587					name = "complex double"
588				}
589			}
590		case encFloat:
591			typ = new(FloatType)
592		case encSigned:
593			typ = new(IntType)
594		case encUnsigned:
595			typ = new(UintType)
596		case encSignedChar:
597			typ = new(CharType)
598		case encUnsignedChar:
599			typ = new(UcharType)
600		}
601		typeCache[off] = typ
602		t := typ.(interface {
603			Basic() *BasicType
604		}).Basic()
605		t.Name = name
606		t.BitSize, _ = e.Val(AttrBitSize).(int64)
607		haveBitOffset := false
608		haveDataBitOffset := false
609		t.BitOffset, haveBitOffset = e.Val(AttrBitOffset).(int64)
610		t.DataBitOffset, haveDataBitOffset = e.Val(AttrDataBitOffset).(int64)
611		if haveBitOffset && haveDataBitOffset {
612			err = DecodeError{name, e.Offset, "duplicate bit offset attributes"}
613			goto Error
614		}
615
616	case TagClassType, TagStructType, TagUnionType:
617		// Structure, union, or class type.  (DWARF v2 §5.5)
618		// Attributes:
619		//	AttrName: name of struct, union, or class
620		//	AttrByteSize: byte size [required]
621		//	AttrDeclaration: if true, struct/union/class is incomplete
622		// Children:
623		//	TagMember to describe one member.
624		//		AttrName: name of member [required]
625		//		AttrType: type of member [required]
626		//		AttrByteSize: size in bytes
627		//		AttrBitOffset: bit offset within bytes for bit fields
628		//		AttrDataBitOffset: field bit offset relative to struct start
629		//		AttrBitSize: bit size for bit fields
630		//		AttrDataMemberLoc: location within struct [required for struct, class]
631		// There is much more to handle C++, all ignored for now.
632		t := new(StructType)
633		typ = t
634		typeCache[off] = t
635		switch e.Tag {
636		case TagClassType:
637			t.Kind = "class"
638		case TagStructType:
639			t.Kind = "struct"
640		case TagUnionType:
641			t.Kind = "union"
642		}
643		t.StructName, _ = e.Val(AttrName).(string)
644		t.Incomplete = e.Val(AttrDeclaration) != nil
645		t.Field = make([]*StructField, 0, 8)
646		var lastFieldType *Type
647		var lastFieldBitSize int64
648		var lastFieldByteOffset int64
649		for kid := next(); kid != nil; kid = next() {
650			if kid.Tag != TagMember {
651				continue
652			}
653			f := new(StructField)
654			if f.Type = typeOf(kid); err != nil {
655				goto Error
656			}
657			switch loc := kid.Val(AttrDataMemberLoc).(type) {
658			case []byte:
659				// TODO: Should have original compilation
660				// unit here, not unknownFormat.
661				b := makeBuf(d, unknownFormat{}, "location", 0, loc)
662				if b.uint8() != opPlusUconst {
663					err = DecodeError{name, kid.Offset, "unexpected opcode"}
664					goto Error
665				}
666				f.ByteOffset = int64(b.uint())
667				if b.err != nil {
668					err = b.err
669					goto Error
670				}
671			case int64:
672				f.ByteOffset = loc
673			}
674
675			f.Name, _ = kid.Val(AttrName).(string)
676			f.ByteSize, _ = kid.Val(AttrByteSize).(int64)
677			haveBitOffset := false
678			haveDataBitOffset := false
679			f.BitOffset, haveBitOffset = kid.Val(AttrBitOffset).(int64)
680			f.DataBitOffset, haveDataBitOffset = kid.Val(AttrDataBitOffset).(int64)
681			if haveBitOffset && haveDataBitOffset {
682				err = DecodeError{name, e.Offset, "duplicate bit offset attributes"}
683				goto Error
684			}
685			f.BitSize, _ = kid.Val(AttrBitSize).(int64)
686			t.Field = append(t.Field, f)
687
688			if lastFieldBitSize == 0 && lastFieldByteOffset == f.ByteOffset && t.Kind != "union" {
689				// Last field was zero width. Fix array length.
690				// (DWARF writes out 0-length arrays as if they were 1-length arrays.)
691				fixups.recordArrayType(lastFieldType)
692			}
693			lastFieldType = &f.Type
694			lastFieldByteOffset = f.ByteOffset
695			lastFieldBitSize = f.BitSize
696		}
697		if t.Kind != "union" {
698			b, ok := e.Val(AttrByteSize).(int64)
699			if ok && b == lastFieldByteOffset {
700				// Final field must be zero width. Fix array length.
701				fixups.recordArrayType(lastFieldType)
702			}
703		}
704
705	case TagConstType, TagVolatileType, TagRestrictType:
706		// Type modifier (DWARF v2 §5.2)
707		// Attributes:
708		//	AttrType: subtype
709		t := new(QualType)
710		typ = t
711		typeCache[off] = t
712		if t.Type = typeOf(e); err != nil {
713			goto Error
714		}
715		switch e.Tag {
716		case TagConstType:
717			t.Qual = "const"
718		case TagRestrictType:
719			t.Qual = "restrict"
720		case TagVolatileType:
721			t.Qual = "volatile"
722		}
723
724	case TagEnumerationType:
725		// Enumeration type (DWARF v2 §5.6)
726		// Attributes:
727		//	AttrName: enum name if any
728		//	AttrByteSize: bytes required to represent largest value
729		// Children:
730		//	TagEnumerator:
731		//		AttrName: name of constant
732		//		AttrConstValue: value of constant
733		t := new(EnumType)
734		typ = t
735		typeCache[off] = t
736		t.EnumName, _ = e.Val(AttrName).(string)
737		t.Val = make([]*EnumValue, 0, 8)
738		for kid := next(); kid != nil; kid = next() {
739			if kid.Tag == TagEnumerator {
740				f := new(EnumValue)
741				f.Name, _ = kid.Val(AttrName).(string)
742				f.Val, _ = kid.Val(AttrConstValue).(int64)
743				n := len(t.Val)
744				if n >= cap(t.Val) {
745					val := make([]*EnumValue, n, n*2)
746					copy(val, t.Val)
747					t.Val = val
748				}
749				t.Val = t.Val[0 : n+1]
750				t.Val[n] = f
751			}
752		}
753
754	case TagPointerType:
755		// Type modifier (DWARF v2 §5.2)
756		// Attributes:
757		//	AttrType: subtype [not required!  void* has no AttrType]
758		//	AttrAddrClass: address class [ignored]
759		t := new(PtrType)
760		typ = t
761		typeCache[off] = t
762		if e.Val(AttrType) == nil {
763			t.Type = &VoidType{}
764			break
765		}
766		t.Type = typeOf(e)
767
768	case TagSubroutineType:
769		// Subroutine type.  (DWARF v2 §5.7)
770		// Attributes:
771		//	AttrType: type of return value if any
772		//	AttrName: possible name of type [ignored]
773		//	AttrPrototyped: whether used ANSI C prototype [ignored]
774		// Children:
775		//	TagFormalParameter: typed parameter
776		//		AttrType: type of parameter
777		//	TagUnspecifiedParameter: final ...
778		t := new(FuncType)
779		typ = t
780		typeCache[off] = t
781		if t.ReturnType = typeOf(e); err != nil {
782			goto Error
783		}
784		t.ParamType = make([]Type, 0, 8)
785		for kid := next(); kid != nil; kid = next() {
786			var tkid Type
787			switch kid.Tag {
788			default:
789				continue
790			case TagFormalParameter:
791				if tkid = typeOf(kid); err != nil {
792					goto Error
793				}
794			case TagUnspecifiedParameters:
795				tkid = &DotDotDotType{}
796			}
797			t.ParamType = append(t.ParamType, tkid)
798		}
799
800	case TagTypedef:
801		// Typedef (DWARF v2 §5.3)
802		// Attributes:
803		//	AttrName: name [required]
804		//	AttrType: type definition [required]
805		t := new(TypedefType)
806		typ = t
807		typeCache[off] = t
808		t.Name, _ = e.Val(AttrName).(string)
809		t.Type = typeOf(e)
810
811	case TagUnspecifiedType:
812		// Unspecified type (DWARF v3 §5.2)
813		// Attributes:
814		//	AttrName: name
815		t := new(UnspecifiedType)
816		typ = t
817		typeCache[off] = t
818		t.Name, _ = e.Val(AttrName).(string)
819
820	default:
821		// This is some other type DIE that we're currently not
822		// equipped to handle. Return an abstract "unsupported type"
823		// object in such cases.
824		t := new(UnsupportedType)
825		typ = t
826		typeCache[off] = t
827		t.Tag = e.Tag
828		t.Name, _ = e.Val(AttrName).(string)
829	}
830
831	if err != nil {
832		goto Error
833	}
834
835	{
836		b, ok := e.Val(AttrByteSize).(int64)
837		if !ok {
838			b = -1
839			switch t := typ.(type) {
840			case *TypedefType:
841				// Record that we need to resolve this
842				// type's size once the type graph is
843				// constructed.
844				fixups.typedefs = append(fixups.typedefs, t)
845			case *PtrType:
846				b = int64(addressSize)
847			}
848		}
849		typ.Common().ByteSize = b
850	}
851	return typ, nil
852
853Error:
854	// If the parse fails, take the type out of the cache
855	// so that the next call with this offset doesn't hit
856	// the cache and return success.
857	delete(typeCache, off)
858	return nil, err
859}
860
861func zeroArray(t *Type) {
862	at := (*t).(*ArrayType)
863	if at.Type.Size() == 0 {
864		return
865	}
866	// Make a copy to avoid invalidating typeCache.
867	tt := *at
868	tt.Count = 0
869	*t = &tt
870}
871