// Copyright 2010 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.

// TODO/NICETOHAVE:
//   - eliminate DW_CLS_ if not used
//   - package info in compilation units
//   - assign global variables and types to their packages
//   - gdb uses c syntax, meaning clumsy quoting is needed for go identifiers. eg
//     ptype struct '[]uint8' and qualifiers need to be quoted away
//   - lexical scoping is lost, so gdb gets confused as to which 'main.i' you mean.
//   - file:line info for variables
//   - make strings a typedef so prettyprinters can see the underlying string type

package ld

import (
	"cmd/internal/obj"
	"fmt"
	"os"
	"strings"
)

/*
 * Offsets and sizes of the debug_* sections in the cout file.
 */
var abbrevo int64

var abbrevsize int64

var abbrevsym *LSym

var abbrevsympos int64

var lineo int64

var linesize int64

var linesym *LSym

var linesympos int64

var infoo int64 // also the base for DWDie->offs and reference attributes.

var infosize int64

var infosym *LSym

var infosympos int64

var frameo int64

var framesize int64

var framesym *LSym

var framesympos int64

var pubnameso int64

var pubnamessize int64

var pubtypeso int64

var pubtypessize int64

var arangeso int64

var arangessize int64

var gdbscripto int64

var gdbscriptsize int64

var infosec *LSym

var inforeloco int64

var inforelocsize int64

var arangessec *LSym

var arangesreloco int64

var arangesrelocsize int64

var linesec *LSym

var linereloco int64

var linerelocsize int64

var framesec *LSym

var framereloco int64

var framerelocsize int64

var gdbscript string

/*
 *  Basic I/O
 */
func addrput(addr int64) {
	switch Thearch.Ptrsize {
	case 4:
		Thearch.Lput(uint32(addr))

	case 8:
		Thearch.Vput(uint64(addr))
	}
}

func uleb128enc(v uint64, dst []byte) int {
	var c uint8

	length := uint8(0)
	for {
		c = uint8(v & 0x7f)
		v >>= 7
		if v != 0 {
			c |= 0x80
		}
		if dst != nil {
			dst[0] = byte(c)
			dst = dst[1:]
		}
		length++
		if c&0x80 == 0 {
			break
		}
	}

	return int(length)
}

func sleb128enc(v int64, dst []byte) int {
	var c uint8
	var s uint8

	length := uint8(0)
	for {
		c = uint8(v & 0x7f)
		s = uint8(v & 0x40)
		v >>= 7
		if (v != -1 || s == 0) && (v != 0 || s != 0) {
			c |= 0x80
		}
		if dst != nil {
			dst[0] = byte(c)
			dst = dst[1:]
		}
		length++
		if c&0x80 == 0 {
			break
		}
	}

	return int(length)
}

var encbuf [10]byte

func uleb128put(v int64) {
	n := uleb128enc(uint64(v), encbuf[:])
	Cwrite(encbuf[:n])
}

func sleb128put(v int64) {
	n := sleb128enc(v, encbuf[:])
	Cwrite(encbuf[:n])
}

/*
 * Defining Abbrevs.  This is hardcoded, and there will be
 * only a handful of them.  The DWARF spec places no restriction on
 * the ordering of attributes in the Abbrevs and DIEs, and we will
 * always write them out in the order of declaration in the abbrev.
 */
type DWAttrForm struct {
	attr uint16
	form uint8
}

// Go-specific type attributes.
const (
	DW_AT_go_kind = 0x2900
	DW_AT_go_key  = 0x2901
	DW_AT_go_elem = 0x2902

	DW_AT_internal_location = 253 // params and locals; not emitted
)

// Index into the abbrevs table below.
// Keep in sync with ispubname() and ispubtype() below.
// ispubtype considers >= NULLTYPE public
const (
	DW_ABRV_NULL = iota
	DW_ABRV_COMPUNIT
	DW_ABRV_FUNCTION
	DW_ABRV_VARIABLE
	DW_ABRV_AUTO
	DW_ABRV_PARAM
	DW_ABRV_STRUCTFIELD
	DW_ABRV_FUNCTYPEPARAM
	DW_ABRV_DOTDOTDOT
	DW_ABRV_ARRAYRANGE
	DW_ABRV_NULLTYPE
	DW_ABRV_BASETYPE
	DW_ABRV_ARRAYTYPE
	DW_ABRV_CHANTYPE
	DW_ABRV_FUNCTYPE
	DW_ABRV_IFACETYPE
	DW_ABRV_MAPTYPE
	DW_ABRV_PTRTYPE
	DW_ABRV_BARE_PTRTYPE // only for void*, no DW_AT_type attr to please gdb 6.
	DW_ABRV_SLICETYPE
	DW_ABRV_STRINGTYPE
	DW_ABRV_STRUCTTYPE
	DW_ABRV_TYPEDECL
	DW_NABRV
)

type DWAbbrev struct {
	tag      uint8
	children uint8
	attr     []DWAttrForm
}

var abbrevs = [DW_NABRV]DWAbbrev{
	/* The mandatory DW_ABRV_NULL entry. */
	{0, 0, []DWAttrForm{}},

	/* COMPUNIT */
	{
		DW_TAG_compile_unit,
		DW_CHILDREN_yes,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_language, DW_FORM_data1},
			{DW_AT_low_pc, DW_FORM_addr},
			{DW_AT_high_pc, DW_FORM_addr},
			{DW_AT_stmt_list, DW_FORM_data4},
			{DW_AT_comp_dir, DW_FORM_string},
		},
	},

	/* FUNCTION */
	{
		DW_TAG_subprogram,
		DW_CHILDREN_yes,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_low_pc, DW_FORM_addr},
			{DW_AT_high_pc, DW_FORM_addr},
			{DW_AT_external, DW_FORM_flag},
		},
	},

	/* VARIABLE */
	{
		DW_TAG_variable,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_location, DW_FORM_block1},
			{DW_AT_type, DW_FORM_ref_addr},
			{DW_AT_external, DW_FORM_flag},
		},
	},

	/* AUTO */
	{
		DW_TAG_variable,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_location, DW_FORM_block1},
			{DW_AT_type, DW_FORM_ref_addr},
		},
	},

	/* PARAM */
	{
		DW_TAG_formal_parameter,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_location, DW_FORM_block1},
			{DW_AT_type, DW_FORM_ref_addr},
		},
	},

	/* STRUCTFIELD */
	{
		DW_TAG_member,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_data_member_location, DW_FORM_block1},
			{DW_AT_type, DW_FORM_ref_addr},
		},
	},

	/* FUNCTYPEPARAM */
	{
		DW_TAG_formal_parameter,
		DW_CHILDREN_no,

		// No name!
		[]DWAttrForm{
			{DW_AT_type, DW_FORM_ref_addr},
		},
	},

	/* DOTDOTDOT */
	{
		DW_TAG_unspecified_parameters,
		DW_CHILDREN_no,
		[]DWAttrForm{},
	},

	/* ARRAYRANGE */
	{
		DW_TAG_subrange_type,
		DW_CHILDREN_no,

		// No name!
		[]DWAttrForm{
			{DW_AT_type, DW_FORM_ref_addr},
			{DW_AT_count, DW_FORM_udata},
		},
	},

	// Below here are the types considered public by ispubtype
	/* NULLTYPE */
	{
		DW_TAG_unspecified_type,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
		},
	},

	/* BASETYPE */
	{
		DW_TAG_base_type,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_encoding, DW_FORM_data1},
			{DW_AT_byte_size, DW_FORM_data1},
			{DW_AT_go_kind, DW_FORM_data1},
		},
	},

	/* ARRAYTYPE */
	// child is subrange with upper bound
	{
		DW_TAG_array_type,
		DW_CHILDREN_yes,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_type, DW_FORM_ref_addr},
			{DW_AT_byte_size, DW_FORM_udata},
			{DW_AT_go_kind, DW_FORM_data1},
		},
	},

	/* CHANTYPE */
	{
		DW_TAG_typedef,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_type, DW_FORM_ref_addr},
			{DW_AT_go_kind, DW_FORM_data1},
			{DW_AT_go_elem, DW_FORM_ref_addr},
		},
	},

	/* FUNCTYPE */
	{
		DW_TAG_subroutine_type,
		DW_CHILDREN_yes,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			// {DW_AT_type,	DW_FORM_ref_addr},
			{DW_AT_go_kind, DW_FORM_data1},
		},
	},

	/* IFACETYPE */
	{
		DW_TAG_typedef,
		DW_CHILDREN_yes,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_type, DW_FORM_ref_addr},
			{DW_AT_go_kind, DW_FORM_data1},
		},
	},

	/* MAPTYPE */
	{
		DW_TAG_typedef,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_type, DW_FORM_ref_addr},
			{DW_AT_go_kind, DW_FORM_data1},
			{DW_AT_go_key, DW_FORM_ref_addr},
			{DW_AT_go_elem, DW_FORM_ref_addr},
		},
	},

	/* PTRTYPE */
	{
		DW_TAG_pointer_type,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_type, DW_FORM_ref_addr},
			{DW_AT_go_kind, DW_FORM_data1},
		},
	},

	/* BARE_PTRTYPE */
	{
		DW_TAG_pointer_type,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
		},
	},

	/* SLICETYPE */
	{
		DW_TAG_structure_type,
		DW_CHILDREN_yes,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_byte_size, DW_FORM_udata},
			{DW_AT_go_kind, DW_FORM_data1},
			{DW_AT_go_elem, DW_FORM_ref_addr},
		},
	},

	/* STRINGTYPE */
	{
		DW_TAG_structure_type,
		DW_CHILDREN_yes,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_byte_size, DW_FORM_udata},
			{DW_AT_go_kind, DW_FORM_data1},
		},
	},

	/* STRUCTTYPE */
	{
		DW_TAG_structure_type,
		DW_CHILDREN_yes,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_byte_size, DW_FORM_udata},
			{DW_AT_go_kind, DW_FORM_data1},
		},
	},

	/* TYPEDECL */
	{
		DW_TAG_typedef,
		DW_CHILDREN_no,
		[]DWAttrForm{
			{DW_AT_name, DW_FORM_string},
			{DW_AT_type, DW_FORM_ref_addr},
		},
	},
}

func writeabbrev() {
	abbrevo = Cpos()
	for i := 1; i < DW_NABRV; i++ {
		// See section 7.5.3
		uleb128put(int64(i))

		uleb128put(int64(abbrevs[i].tag))
		Cput(abbrevs[i].children)
		for _, f := range abbrevs[i].attr {
			uleb128put(int64(f.attr))
			uleb128put(int64(f.form))
		}
		uleb128put(0)
		uleb128put(0)
	}

	Cput(0)
	abbrevsize = Cpos() - abbrevo
}

/*
 * Debugging Information Entries and their attributes.
 */
const (
	HASHSIZE = 107
)

func dwarfhashstr(s string) uint32 {
	h := uint32(0)
	for s != "" {
		h = h + h + h + uint32(s[0])
		s = s[1:]
	}
	return h % HASHSIZE
}

// For DW_CLS_string and _block, value should contain the length, and
// data the data, for _reference, value is 0 and data is a DWDie* to
// the referenced instance, for all others, value is the whole thing
// and data is null.

type DWAttr struct {
	link  *DWAttr
	atr   uint16 // DW_AT_
	cls   uint8  // DW_CLS_
	value int64
	data  interface{}
}

type DWDie struct {
	abbrev int
	link   *DWDie
	child  *DWDie
	attr   *DWAttr
	// offset into .debug_info section, i.e relative to
	// infoo. only valid after call to putdie()
	offs  int64
	hash  []*DWDie // optional index of children by name, enabled by mkindex()
	hlink *DWDie   // bucket chain in parent's index
}

/*
 * Root DIEs for compilation units, types and global variables.
 */
var dwroot DWDie

var dwtypes DWDie

var dwglobals DWDie

func newattr(die *DWDie, attr uint16, cls int, value int64, data interface{}) *DWAttr {
	a := new(DWAttr)
	a.link = die.attr
	die.attr = a
	a.atr = attr
	a.cls = uint8(cls)
	a.value = value
	a.data = data
	return a
}

// Each DIE (except the root ones) has at least 1 attribute: its
// name. getattr moves the desired one to the front so
// frequently searched ones are found faster.
func getattr(die *DWDie, attr uint16) *DWAttr {
	if die.attr.atr == attr {
		return die.attr
	}

	a := die.attr
	b := a.link
	for b != nil {
		if b.atr == attr {
			a.link = b.link
			b.link = die.attr
			die.attr = b
			return b
		}

		a = b
		b = b.link
	}

	return nil
}

// Every DIE has at least a DW_AT_name attribute (but it will only be
// written out if it is listed in the abbrev).	If its parent is
// keeping an index, the new DIE will be inserted there.
func newdie(parent *DWDie, abbrev int, name string) *DWDie {
	die := new(DWDie)
	die.abbrev = abbrev
	die.link = parent.child
	parent.child = die

	newattr(die, DW_AT_name, DW_CLS_STRING, int64(len(name)), name)

	if parent.hash != nil {
		h := int(dwarfhashstr(name))
		die.hlink = parent.hash[h]
		parent.hash[h] = die
	}

	return die
}

func mkindex(die *DWDie) {
	die.hash = make([]*DWDie, HASHSIZE)
}

func walktypedef(die *DWDie) *DWDie {
	// Resolve typedef if present.
	if die.abbrev == DW_ABRV_TYPEDECL {
		for attr := die.attr; attr != nil; attr = attr.link {
			if attr.atr == DW_AT_type && attr.cls == DW_CLS_REFERENCE && attr.data != nil {
				return attr.data.(*DWDie)
			}
		}
	}

	return die
}

// Find child by AT_name using hashtable if available or linear scan
// if not.
func find(die *DWDie, name string) *DWDie {
	var a *DWDie
	var b *DWDie
	var die2 *DWDie
	var h int

top:
	if die.hash == nil {
		for a = die.child; a != nil; a = a.link {
			if name == getattr(a, DW_AT_name).data {
				return a
			}
		}
		goto notfound
	}

	h = int(dwarfhashstr(name))
	a = die.hash[h]

	if a == nil {
		goto notfound
	}

	if name == getattr(a, DW_AT_name).data {
		return a
	}

	// Move found ones to head of the list.
	b = a.hlink

	for b != nil {
		if name == getattr(b, DW_AT_name).data {
			a.hlink = b.hlink
			b.hlink = die.hash[h]
			die.hash[h] = b
			return b
		}

		a = b
		b = b.hlink
	}

notfound:
	die2 = walktypedef(die)
	if die2 != die {
		die = die2
		goto top
	}

	return nil
}

func mustFind(die *DWDie, name string) *DWDie {
	r := find(die, name)
	if r == nil {
		Exitf("dwarf find: %s %p has no %s", getattr(die, DW_AT_name).data, die, name)
	}
	return r
}

func adddwarfrel(sec *LSym, sym *LSym, offsetbase int64, siz int, addend int64) {
	r := Addrel(sec)
	r.Sym = sym
	r.Xsym = sym
	r.Off = int32(Cpos() - offsetbase)
	r.Siz = uint8(siz)
	r.Type = obj.R_ADDR
	r.Add = addend
	r.Xadd = addend
	if Iself && Thearch.Thechar == '6' {
		addend = 0
	}
	if HEADTYPE == obj.Hdarwin {
		addend += sym.Value
	}
	switch siz {
	case 4:
		Thearch.Lput(uint32(addend))

	case 8:
		Thearch.Vput(uint64(addend))

	default:
		Diag("bad size in adddwarfrel")
	}
}

func newrefattr(die *DWDie, attr uint16, ref *DWDie) *DWAttr {
	if ref == nil {
		return nil
	}
	return newattr(die, attr, DW_CLS_REFERENCE, 0, ref)
}

var fwdcount int

func putattr(abbrev int, form int, cls int, value int64, data interface{}) {
	switch form {
	case DW_FORM_addr: // address
		if Linkmode == LinkExternal {
			value -= (data.(*LSym)).Value
			adddwarfrel(infosec, data.(*LSym), infoo, Thearch.Ptrsize, value)
			break
		}

		addrput(value)

	case DW_FORM_block1: // block
		if cls == DW_CLS_ADDRESS {
			Cput(uint8(1 + Thearch.Ptrsize))
			Cput(DW_OP_addr)
			if Linkmode == LinkExternal {
				value -= (data.(*LSym)).Value
				adddwarfrel(infosec, data.(*LSym), infoo, Thearch.Ptrsize, value)
				break
			}

			addrput(value)
			break
		}

		value &= 0xff
		Cput(uint8(value))
		p := data.([]byte)
		for i := 0; int64(i) < value; i++ {
			Cput(uint8(p[i]))
		}

	case DW_FORM_block2: // block
		value &= 0xffff

		Thearch.Wput(uint16(value))
		p := data.([]byte)
		for i := 0; int64(i) < value; i++ {
			Cput(uint8(p[i]))
		}

	case DW_FORM_block4: // block
		value &= 0xffffffff

		Thearch.Lput(uint32(value))
		p := data.([]byte)
		for i := 0; int64(i) < value; i++ {
			Cput(uint8(p[i]))
		}

	case DW_FORM_block: // block
		uleb128put(value)

		p := data.([]byte)
		for i := 0; int64(i) < value; i++ {
			Cput(uint8(p[i]))
		}

	case DW_FORM_data1: // constant
		Cput(uint8(value))

	case DW_FORM_data2: // constant
		Thearch.Wput(uint16(value))

	case DW_FORM_data4: // constant, {line,loclist,mac,rangelist}ptr
		if Linkmode == LinkExternal && cls == DW_CLS_PTR {
			adddwarfrel(infosec, linesym, infoo, 4, value)
			break
		}

		Thearch.Lput(uint32(value))

	case DW_FORM_data8: // constant, {line,loclist,mac,rangelist}ptr
		Thearch.Vput(uint64(value))

	case DW_FORM_sdata: // constant
		sleb128put(value)

	case DW_FORM_udata: // constant
		uleb128put(value)

	case DW_FORM_string: // string
		strnput(data.(string), int(value+1))

	case DW_FORM_flag: // flag
		if value != 0 {
			Cput(1)
		} else {
			Cput(0)
		}

		// In DWARF 2 (which is what we claim to generate),
	// the ref_addr is the same size as a normal address.
	// In DWARF 3 it is always 32 bits, unless emitting a large
	// (> 4 GB of debug info aka "64-bit") unit, which we don't implement.
	case DW_FORM_ref_addr: // reference to a DIE in the .info section
		if data == nil {
			Diag("dwarf: null reference in %d", abbrev)
			if Thearch.Ptrsize == 8 {
				Thearch.Vput(0) // invalid dwarf, gdb will complain.
			} else {
				Thearch.Lput(0) // invalid dwarf, gdb will complain.
			}
		} else {
			off := (data.(*DWDie)).offs
			if off == 0 {
				fwdcount++
			}
			if Linkmode == LinkExternal {
				adddwarfrel(infosec, infosym, infoo, Thearch.Ptrsize, off)
				break
			}

			addrput(off)
		}

	case DW_FORM_ref1, // reference within the compilation unit
		DW_FORM_ref2,      // reference
		DW_FORM_ref4,      // reference
		DW_FORM_ref8,      // reference
		DW_FORM_ref_udata, // reference

		DW_FORM_strp,     // string
		DW_FORM_indirect: // (see Section 7.5.3)
		fallthrough
	default:
		Exitf("dwarf: unsupported attribute form %d / class %d", form, cls)
	}
}

// Note that we can (and do) add arbitrary attributes to a DIE, but
// only the ones actually listed in the Abbrev will be written out.
func putattrs(abbrev int, attr *DWAttr) {
Outer:
	for _, f := range abbrevs[abbrev].attr {
		for ap := attr; ap != nil; ap = ap.link {
			if ap.atr == f.attr {
				putattr(abbrev, int(f.form), int(ap.cls), ap.value, ap.data)
				continue Outer
			}
		}

		putattr(abbrev, int(f.form), 0, 0, nil)
	}
}

func putdies(die *DWDie) {
	for ; die != nil; die = die.link {
		putdie(die)
	}
}

func putdie(die *DWDie) {
	die.offs = Cpos() - infoo
	uleb128put(int64(die.abbrev))
	putattrs(die.abbrev, die.attr)
	if abbrevs[die.abbrev].children != 0 {
		putdies(die.child)
		Cput(0)
	}
}

func reverselist(list **DWDie) {
	curr := *list
	var prev *DWDie
	for curr != nil {
		var next *DWDie = curr.link
		curr.link = prev
		prev = curr
		curr = next
	}

	*list = prev
}

func reversetree(list **DWDie) {
	reverselist(list)
	for die := *list; die != nil; die = die.link {
		if abbrevs[die.abbrev].children != 0 {
			reversetree(&die.child)
		}
	}
}

func newmemberoffsetattr(die *DWDie, offs int32) {
	var block [20]byte

	i := 0
	block[i] = DW_OP_plus_uconst
	i++
	i += uleb128enc(uint64(offs), block[i:])
	newattr(die, DW_AT_data_member_location, DW_CLS_BLOCK, int64(i), block[:i])
}

// GDB doesn't like DW_FORM_addr for DW_AT_location, so emit a
// location expression that evals to a const.
func newabslocexprattr(die *DWDie, addr int64, sym *LSym) {
	newattr(die, DW_AT_location, DW_CLS_ADDRESS, addr, sym)
	// below
}

// Lookup predefined types
func lookup_or_diag(n string) *LSym {
	s := Linkrlookup(Ctxt, n, 0)
	if s == nil || s.Size == 0 {
		Exitf("dwarf: missing type: %s", n)
	}

	return s
}

func dotypedef(parent *DWDie, name string, def *DWDie) {
	// Only emit typedefs for real names.
	if strings.HasPrefix(name, "map[") {
		return
	}
	if strings.HasPrefix(name, "struct {") {
		return
	}
	if strings.HasPrefix(name, "chan ") {
		return
	}
	if name[0] == '[' || name[0] == '*' {
		return
	}
	if def == nil {
		Diag("dwarf: bad def in dotypedef")
	}

	// The typedef entry must be created after the def,
	// so that future lookups will find the typedef instead
	// of the real definition. This hooks the typedef into any
	// circular definition loops, so that gdb can understand them.
	die := newdie(parent, DW_ABRV_TYPEDECL, name)

	newrefattr(die, DW_AT_type, def)
}

// Define gotype, for composite ones recurse into constituents.
func defgotype(gotype *LSym) *DWDie {
	if gotype == nil {
		return mustFind(&dwtypes, "<unspecified>")
	}

	if !strings.HasPrefix(gotype.Name, "type.") {
		Diag("dwarf: type name doesn't start with \".type\": %s", gotype.Name)
		return mustFind(&dwtypes, "<unspecified>")
	}

	name := gotype.Name[5:] // could also decode from Type.string

	die := find(&dwtypes, name)

	if die != nil {
		return die
	}

	if false && Debug['v'] > 2 {
		fmt.Printf("new type: %v\n", gotype)
	}

	kind := decodetype_kind(gotype)
	bytesize := decodetype_size(gotype)

	switch kind {
	case obj.KindBool:
		die = newdie(&dwtypes, DW_ABRV_BASETYPE, name)
		newattr(die, DW_AT_encoding, DW_CLS_CONSTANT, DW_ATE_boolean, 0)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)

	case obj.KindInt,
		obj.KindInt8,
		obj.KindInt16,
		obj.KindInt32,
		obj.KindInt64:
		die = newdie(&dwtypes, DW_ABRV_BASETYPE, name)
		newattr(die, DW_AT_encoding, DW_CLS_CONSTANT, DW_ATE_signed, 0)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)

	case obj.KindUint,
		obj.KindUint8,
		obj.KindUint16,
		obj.KindUint32,
		obj.KindUint64,
		obj.KindUintptr:
		die = newdie(&dwtypes, DW_ABRV_BASETYPE, name)
		newattr(die, DW_AT_encoding, DW_CLS_CONSTANT, DW_ATE_unsigned, 0)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)

	case obj.KindFloat32,
		obj.KindFloat64:
		die = newdie(&dwtypes, DW_ABRV_BASETYPE, name)
		newattr(die, DW_AT_encoding, DW_CLS_CONSTANT, DW_ATE_float, 0)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)

	case obj.KindComplex64,
		obj.KindComplex128:
		die = newdie(&dwtypes, DW_ABRV_BASETYPE, name)
		newattr(die, DW_AT_encoding, DW_CLS_CONSTANT, DW_ATE_complex_float, 0)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)

	case obj.KindArray:
		die = newdie(&dwtypes, DW_ABRV_ARRAYTYPE, name)
		dotypedef(&dwtypes, name, die)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)
		s := decodetype_arrayelem(gotype)
		newrefattr(die, DW_AT_type, defgotype(s))
		fld := newdie(die, DW_ABRV_ARRAYRANGE, "range")

		// use actual length not upper bound; correct for 0-length arrays.
		newattr(fld, DW_AT_count, DW_CLS_CONSTANT, decodetype_arraylen(gotype), 0)

		newrefattr(fld, DW_AT_type, mustFind(&dwtypes, "uintptr"))

	case obj.KindChan:
		die = newdie(&dwtypes, DW_ABRV_CHANTYPE, name)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)
		s := decodetype_chanelem(gotype)
		newrefattr(die, DW_AT_go_elem, defgotype(s))

	case obj.KindFunc:
		die = newdie(&dwtypes, DW_ABRV_FUNCTYPE, name)
		dotypedef(&dwtypes, name, die)
		newrefattr(die, DW_AT_type, mustFind(&dwtypes, "void"))
		nfields := decodetype_funcincount(gotype)
		var fld *DWDie
		var s *LSym
		for i := 0; i < nfields; i++ {
			s = decodetype_funcintype(gotype, i)
			fld = newdie(die, DW_ABRV_FUNCTYPEPARAM, s.Name[5:])
			newrefattr(fld, DW_AT_type, defgotype(s))
		}

		if decodetype_funcdotdotdot(gotype) != 0 {
			newdie(die, DW_ABRV_DOTDOTDOT, "...")
		}
		nfields = decodetype_funcoutcount(gotype)
		for i := 0; i < nfields; i++ {
			s = decodetype_funcouttype(gotype, i)
			fld = newdie(die, DW_ABRV_FUNCTYPEPARAM, s.Name[5:])
			newrefattr(fld, DW_AT_type, defptrto(defgotype(s)))
		}

	case obj.KindInterface:
		die = newdie(&dwtypes, DW_ABRV_IFACETYPE, name)
		dotypedef(&dwtypes, name, die)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)
		nfields := int(decodetype_ifacemethodcount(gotype))
		var s *LSym
		if nfields == 0 {
			s = lookup_or_diag("type.runtime.eface")
		} else {
			s = lookup_or_diag("type.runtime.iface")
		}
		newrefattr(die, DW_AT_type, defgotype(s))

	case obj.KindMap:
		die = newdie(&dwtypes, DW_ABRV_MAPTYPE, name)
		s := decodetype_mapkey(gotype)
		newrefattr(die, DW_AT_go_key, defgotype(s))
		s = decodetype_mapvalue(gotype)
		newrefattr(die, DW_AT_go_elem, defgotype(s))

	case obj.KindPtr:
		die = newdie(&dwtypes, DW_ABRV_PTRTYPE, name)
		dotypedef(&dwtypes, name, die)
		s := decodetype_ptrelem(gotype)
		newrefattr(die, DW_AT_type, defgotype(s))

	case obj.KindSlice:
		die = newdie(&dwtypes, DW_ABRV_SLICETYPE, name)
		dotypedef(&dwtypes, name, die)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)
		s := decodetype_arrayelem(gotype)
		newrefattr(die, DW_AT_go_elem, defgotype(s))

	case obj.KindString:
		die = newdie(&dwtypes, DW_ABRV_STRINGTYPE, name)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)

	case obj.KindStruct:
		die = newdie(&dwtypes, DW_ABRV_STRUCTTYPE, name)
		dotypedef(&dwtypes, name, die)
		newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, bytesize, 0)
		nfields := decodetype_structfieldcount(gotype)
		var f string
		var fld *DWDie
		var s *LSym
		for i := 0; i < nfields; i++ {
			f = decodetype_structfieldname(gotype, i)
			s = decodetype_structfieldtype(gotype, i)
			if f == "" {
				f = s.Name[5:] // skip "type."
			}
			fld = newdie(die, DW_ABRV_STRUCTFIELD, f)
			newrefattr(fld, DW_AT_type, defgotype(s))
			newmemberoffsetattr(fld, int32(decodetype_structfieldoffs(gotype, i)))
		}

	case obj.KindUnsafePointer:
		die = newdie(&dwtypes, DW_ABRV_BARE_PTRTYPE, name)

	default:
		Diag("dwarf: definition of unknown kind %d: %s", kind, gotype.Name)
		die = newdie(&dwtypes, DW_ABRV_TYPEDECL, name)
		newrefattr(die, DW_AT_type, mustFind(&dwtypes, "<unspecified>"))
	}

	newattr(die, DW_AT_go_kind, DW_CLS_CONSTANT, int64(kind), 0)

	return die
}

// Find or construct *T given T.
func defptrto(dwtype *DWDie) *DWDie {
	ptrname := fmt.Sprintf("*%s", getattr(dwtype, DW_AT_name).data)
	die := find(&dwtypes, ptrname)
	if die == nil {
		die = newdie(&dwtypes, DW_ABRV_PTRTYPE, ptrname)
		newrefattr(die, DW_AT_type, dwtype)
	}

	return die
}

// Copies src's children into dst. Copies attributes by value.
// DWAttr.data is copied as pointer only.  If except is one of
// the top-level children, it will not be copied.
func copychildrenexcept(dst *DWDie, src *DWDie, except *DWDie) {
	var c *DWDie
	var a *DWAttr

	for src = src.child; src != nil; src = src.link {
		if src == except {
			continue
		}
		c = newdie(dst, src.abbrev, getattr(src, DW_AT_name).data.(string))
		for a = src.attr; a != nil; a = a.link {
			newattr(c, a.atr, int(a.cls), a.value, a.data)
		}
		copychildrenexcept(c, src, nil)
	}

	reverselist(&dst.child)
}

func copychildren(dst *DWDie, src *DWDie) {
	copychildrenexcept(dst, src, nil)
}

// Search children (assumed to have DW_TAG_member) for the one named
// field and set its DW_AT_type to dwtype
func substitutetype(structdie *DWDie, field string, dwtype *DWDie) {
	child := mustFind(structdie, field)
	if child == nil {
		return
	}

	a := getattr(child, DW_AT_type)
	if a != nil {
		a.data = dwtype
	} else {
		newrefattr(child, DW_AT_type, dwtype)
	}
}

func synthesizestringtypes(die *DWDie) {
	prototype := walktypedef(defgotype(lookup_or_diag("type.runtime._string")))
	if prototype == nil {
		return
	}

	for ; die != nil; die = die.link {
		if die.abbrev != DW_ABRV_STRINGTYPE {
			continue
		}
		copychildren(die, prototype)
	}
}

func synthesizeslicetypes(die *DWDie) {
	prototype := walktypedef(defgotype(lookup_or_diag("type.runtime.slice")))
	if prototype == nil {
		return
	}

	var elem *DWDie
	for ; die != nil; die = die.link {
		if die.abbrev != DW_ABRV_SLICETYPE {
			continue
		}
		copychildren(die, prototype)
		elem = getattr(die, DW_AT_go_elem).data.(*DWDie)
		substitutetype(die, "array", defptrto(elem))
	}
}

func mkinternaltypename(base string, arg1 string, arg2 string) string {
	var buf string

	if arg2 == "" {
		buf = fmt.Sprintf("%s<%s>", base, arg1)
	} else {
		buf = fmt.Sprintf("%s<%s,%s>", base, arg1, arg2)
	}
	n := buf
	return n
}

// synthesizemaptypes is way too closely married to runtime/hashmap.c
const (
	MaxKeySize = 128
	MaxValSize = 128
	BucketSize = 8
)

func synthesizemaptypes(die *DWDie) {
	hash := walktypedef(defgotype(lookup_or_diag("type.runtime.hmap")))
	bucket := walktypedef(defgotype(lookup_or_diag("type.runtime.bmap")))

	if hash == nil {
		return
	}

	var a *DWAttr
	var dwh *DWDie
	var dwhb *DWDie
	var dwhk *DWDie
	var dwhv *DWDie
	var fld *DWDie
	var indirect_key int
	var indirect_val int
	var keysize int
	var keytype *DWDie
	var t *DWDie
	var valsize int
	var valtype *DWDie
	for ; die != nil; die = die.link {
		if die.abbrev != DW_ABRV_MAPTYPE {
			continue
		}

		keytype = walktypedef(getattr(die, DW_AT_go_key).data.(*DWDie))
		valtype = walktypedef(getattr(die, DW_AT_go_elem).data.(*DWDie))

		// compute size info like hashmap.c does.
		a = getattr(keytype, DW_AT_byte_size)

		if a != nil {
			keysize = int(a.value)
		} else {
			keysize = Thearch.Ptrsize
		}
		a = getattr(valtype, DW_AT_byte_size)
		if a != nil {
			valsize = int(a.value)
		} else {
			valsize = Thearch.Ptrsize
		}
		indirect_key = 0
		indirect_val = 0
		if keysize > MaxKeySize {
			keysize = Thearch.Ptrsize
			indirect_key = 1
		}

		if valsize > MaxValSize {
			valsize = Thearch.Ptrsize
			indirect_val = 1
		}

		// Construct type to represent an array of BucketSize keys
		dwhk = newdie(&dwtypes, DW_ABRV_ARRAYTYPE, mkinternaltypename("[]key", getattr(keytype, DW_AT_name).data.(string), ""))

		newattr(dwhk, DW_AT_byte_size, DW_CLS_CONSTANT, BucketSize*int64(keysize), 0)
		t = keytype
		if indirect_key != 0 {
			t = defptrto(keytype)
		}
		newrefattr(dwhk, DW_AT_type, t)
		fld = newdie(dwhk, DW_ABRV_ARRAYRANGE, "size")
		newattr(fld, DW_AT_count, DW_CLS_CONSTANT, BucketSize, 0)
		newrefattr(fld, DW_AT_type, mustFind(&dwtypes, "uintptr"))

		// Construct type to represent an array of BucketSize values
		dwhv = newdie(&dwtypes, DW_ABRV_ARRAYTYPE, mkinternaltypename("[]val", getattr(valtype, DW_AT_name).data.(string), ""))

		newattr(dwhv, DW_AT_byte_size, DW_CLS_CONSTANT, BucketSize*int64(valsize), 0)
		t = valtype
		if indirect_val != 0 {
			t = defptrto(valtype)
		}
		newrefattr(dwhv, DW_AT_type, t)
		fld = newdie(dwhv, DW_ABRV_ARRAYRANGE, "size")
		newattr(fld, DW_AT_count, DW_CLS_CONSTANT, BucketSize, 0)
		newrefattr(fld, DW_AT_type, mustFind(&dwtypes, "uintptr"))

		// Construct bucket<K,V>
		dwhb = newdie(&dwtypes, DW_ABRV_STRUCTTYPE, mkinternaltypename("bucket", getattr(keytype, DW_AT_name).data.(string), getattr(valtype, DW_AT_name).data.(string)))

		// Copy over all fields except the field "data" from the generic bucket.
		// "data" will be replaced with keys/values below.
		copychildrenexcept(dwhb, bucket, find(bucket, "data"))

		fld = newdie(dwhb, DW_ABRV_STRUCTFIELD, "keys")
		newrefattr(fld, DW_AT_type, dwhk)
		newmemberoffsetattr(fld, BucketSize)
		fld = newdie(dwhb, DW_ABRV_STRUCTFIELD, "values")
		newrefattr(fld, DW_AT_type, dwhv)
		newmemberoffsetattr(fld, BucketSize+BucketSize*int32(keysize))
		fld = newdie(dwhb, DW_ABRV_STRUCTFIELD, "overflow")
		newrefattr(fld, DW_AT_type, defptrto(dwhb))
		newmemberoffsetattr(fld, BucketSize+BucketSize*(int32(keysize)+int32(valsize)))
		if Thearch.Regsize > Thearch.Ptrsize {
			fld = newdie(dwhb, DW_ABRV_STRUCTFIELD, "pad")
			newrefattr(fld, DW_AT_type, mustFind(&dwtypes, "uintptr"))
			newmemberoffsetattr(fld, BucketSize+BucketSize*(int32(keysize)+int32(valsize))+int32(Thearch.Ptrsize))
		}

		newattr(dwhb, DW_AT_byte_size, DW_CLS_CONSTANT, BucketSize+BucketSize*int64(keysize)+BucketSize*int64(valsize)+int64(Thearch.Regsize), 0)

		// Construct hash<K,V>
		dwh = newdie(&dwtypes, DW_ABRV_STRUCTTYPE, mkinternaltypename("hash", getattr(keytype, DW_AT_name).data.(string), getattr(valtype, DW_AT_name).data.(string)))

		copychildren(dwh, hash)
		substitutetype(dwh, "buckets", defptrto(dwhb))
		substitutetype(dwh, "oldbuckets", defptrto(dwhb))
		newattr(dwh, DW_AT_byte_size, DW_CLS_CONSTANT, getattr(hash, DW_AT_byte_size).value, nil)

		// make map type a pointer to hash<K,V>
		newrefattr(die, DW_AT_type, defptrto(dwh))
	}
}

func synthesizechantypes(die *DWDie) {
	sudog := walktypedef(defgotype(lookup_or_diag("type.runtime.sudog")))
	waitq := walktypedef(defgotype(lookup_or_diag("type.runtime.waitq")))
	hchan := walktypedef(defgotype(lookup_or_diag("type.runtime.hchan")))
	if sudog == nil || waitq == nil || hchan == nil {
		return
	}

	sudogsize := int(getattr(sudog, DW_AT_byte_size).value)

	var a *DWAttr
	var dwh *DWDie
	var dws *DWDie
	var dww *DWDie
	var elemsize int
	var elemtype *DWDie
	for ; die != nil; die = die.link {
		if die.abbrev != DW_ABRV_CHANTYPE {
			continue
		}
		elemtype = getattr(die, DW_AT_go_elem).data.(*DWDie)
		a = getattr(elemtype, DW_AT_byte_size)
		if a != nil {
			elemsize = int(a.value)
		} else {
			elemsize = Thearch.Ptrsize
		}

		// sudog<T>
		dws = newdie(&dwtypes, DW_ABRV_STRUCTTYPE, mkinternaltypename("sudog", getattr(elemtype, DW_AT_name).data.(string), ""))

		copychildren(dws, sudog)
		substitutetype(dws, "elem", elemtype)
		if elemsize > 8 {
			elemsize -= 8
		} else {
			elemsize = 0
		}
		newattr(dws, DW_AT_byte_size, DW_CLS_CONSTANT, int64(sudogsize)+int64(elemsize), nil)

		// waitq<T>
		dww = newdie(&dwtypes, DW_ABRV_STRUCTTYPE, mkinternaltypename("waitq", getattr(elemtype, DW_AT_name).data.(string), ""))

		copychildren(dww, waitq)
		substitutetype(dww, "first", defptrto(dws))
		substitutetype(dww, "last", defptrto(dws))
		newattr(dww, DW_AT_byte_size, DW_CLS_CONSTANT, getattr(waitq, DW_AT_byte_size).value, nil)

		// hchan<T>
		dwh = newdie(&dwtypes, DW_ABRV_STRUCTTYPE, mkinternaltypename("hchan", getattr(elemtype, DW_AT_name).data.(string), ""))

		copychildren(dwh, hchan)
		substitutetype(dwh, "recvq", dww)
		substitutetype(dwh, "sendq", dww)
		newattr(dwh, DW_AT_byte_size, DW_CLS_CONSTANT, getattr(hchan, DW_AT_byte_size).value, nil)

		newrefattr(die, DW_AT_type, defptrto(dwh))
	}
}

// For use with pass.c::genasmsym
func defdwsymb(sym *LSym, s string, t int, v int64, size int64, ver int, gotype *LSym) {
	if strings.HasPrefix(s, "go.string.") {
		return
	}
	if strings.HasPrefix(s, "runtime.gcbits.") {
		return
	}

	if strings.HasPrefix(s, "type.") && s != "type.*" && !strings.HasPrefix(s, "type..") {
		defgotype(sym)
		return
	}

	var dv *DWDie

	var dt *DWDie
	switch t {
	default:
		return

	case 'd', 'b', 'D', 'B':
		dv = newdie(&dwglobals, DW_ABRV_VARIABLE, s)
		newabslocexprattr(dv, v, sym)
		if ver == 0 {
			newattr(dv, DW_AT_external, DW_CLS_FLAG, 1, 0)
		}
		fallthrough

	case 'a', 'p':
		dt = defgotype(gotype)
	}

	if dv != nil {
		newrefattr(dv, DW_AT_type, dt)
	}
}

func movetomodule(parent *DWDie) {
	die := dwroot.child.child
	for die.link != nil {
		die = die.link
	}
	die.link = parent.child
}

// If the pcln table contains runtime/runtime.go, use that to set gdbscript path.
func finddebugruntimepath(s *LSym) {
	if gdbscript != "" {
		return
	}

	var f *LSym
	var p string
	for i := 0; i < s.Pcln.Nfile; i++ {
		f = s.Pcln.File[i]
		_ = p
		if i := strings.Index(f.Name, "runtime/runtime.go"); i >= 0 {
			gdbscript = f.Name[:i] + "runtime/runtime-gdb.py"
			break
		}
	}
}

/*
 * Generate short opcodes when possible, long ones when necessary.
 * See section 6.2.5
 */
const (
	LINE_BASE   = -1
	LINE_RANGE  = 4
	OPCODE_BASE = 10
)

func putpclcdelta(delta_pc int64, delta_lc int64) {
	if LINE_BASE <= delta_lc && delta_lc < LINE_BASE+LINE_RANGE {
		var opcode int64 = OPCODE_BASE + (delta_lc - LINE_BASE) + (LINE_RANGE * delta_pc)
		if OPCODE_BASE <= opcode && opcode < 256 {
			Cput(uint8(opcode))
			return
		}
	}

	if delta_pc != 0 {
		Cput(DW_LNS_advance_pc)
		sleb128put(delta_pc)
	}

	Cput(DW_LNS_advance_line)
	sleb128put(delta_lc)
	Cput(DW_LNS_copy)
}

func newcfaoffsetattr(die *DWDie, offs int32) {
	var block [20]byte

	i := 0

	block[i] = DW_OP_call_frame_cfa
	i++
	if offs != 0 {
		block[i] = DW_OP_consts
		i++
		i += sleb128enc(int64(offs), block[i:])
		block[i] = DW_OP_plus
		i++
	}

	newattr(die, DW_AT_location, DW_CLS_BLOCK, int64(i), block[:i])
}

func mkvarname(name string, da int) string {
	buf := fmt.Sprintf("%s#%d", name, da)
	n := buf
	return n
}

/*
 * Walk prog table, emit line program and build DIE tree.
 */

// flush previous compilation unit.
func flushunit(dwinfo *DWDie, pc int64, pcsym *LSym, unitstart int64, header_length int32) {
	if dwinfo != nil && pc != 0 {
		newattr(dwinfo, DW_AT_high_pc, DW_CLS_ADDRESS, pc+1, pcsym)
	}

	if unitstart >= 0 {
		Cput(0) // start extended opcode
		uleb128put(1)
		Cput(DW_LNE_end_sequence)

		here := Cpos()
		Cseek(unitstart)
		Thearch.Lput(uint32(here - unitstart - 4)) // unit_length
		Thearch.Wput(2)                            // dwarf version
		Thearch.Lput(uint32(header_length))        // header length starting here
		Cseek(here)
	}
}

func getCompilationDir() string {
	if dir, err := os.Getwd(); err == nil {
		return dir
	}
	return "/"
}

func writelines() {
	if linesec == nil {
		linesec = Linklookup(Ctxt, ".dwarfline", 0)
	}
	linesec.R = linesec.R[:0]

	unitstart := int64(-1)
	headerend := int64(-1)
	epc := int64(0)
	var epcs *LSym
	lineo = Cpos()
	var dwinfo *DWDie

	flushunit(dwinfo, epc, epcs, unitstart, int32(headerend-unitstart-10))
	unitstart = Cpos()

	lang := DW_LANG_Go

	s := Ctxt.Textp

	dwinfo = newdie(&dwroot, DW_ABRV_COMPUNIT, "go")
	newattr(dwinfo, DW_AT_language, DW_CLS_CONSTANT, int64(lang), 0)
	newattr(dwinfo, DW_AT_stmt_list, DW_CLS_PTR, unitstart-lineo, 0)
	newattr(dwinfo, DW_AT_low_pc, DW_CLS_ADDRESS, s.Value, s)
	// OS X linker requires compilation dir or absolute path in comp unit name to output debug info.
	compDir := getCompilationDir()
	newattr(dwinfo, DW_AT_comp_dir, DW_CLS_STRING, int64(len(compDir)), compDir)

	// Write .debug_line Line Number Program Header (sec 6.2.4)
	// Fields marked with (*) must be changed for 64-bit dwarf
	Thearch.Lput(0) // unit_length (*), will be filled in by flushunit.
	Thearch.Wput(2) // dwarf version (appendix F)
	Thearch.Lput(0) // header_length (*), filled in by flushunit.

	// cpos == unitstart + 4 + 2 + 4
	Cput(1)                // minimum_instruction_length
	Cput(1)                // default_is_stmt
	Cput(LINE_BASE & 0xFF) // line_base
	Cput(LINE_RANGE)       // line_range
	Cput(OPCODE_BASE)      // opcode_base
	Cput(0)                // standard_opcode_lengths[1]
	Cput(1)                // standard_opcode_lengths[2]
	Cput(1)                // standard_opcode_lengths[3]
	Cput(1)                // standard_opcode_lengths[4]
	Cput(1)                // standard_opcode_lengths[5]
	Cput(0)                // standard_opcode_lengths[6]
	Cput(0)                // standard_opcode_lengths[7]
	Cput(0)                // standard_opcode_lengths[8]
	Cput(1)                // standard_opcode_lengths[9]
	Cput(0)                // include_directories  (empty)

	files := make([]*LSym, Ctxt.Nhistfile)

	for f := Ctxt.Filesyms; f != nil; f = f.Next {
		files[f.Value-1] = f
	}

	for i := 0; int32(i) < Ctxt.Nhistfile; i++ {
		strnput(files[i].Name, len(files[i].Name)+4)
	}

	// 4 zeros: the string termination + 3 fields.
	Cput(0)
	// terminate file_names.
	headerend = Cpos()

	Cput(0) // start extended opcode
	uleb128put(1 + int64(Thearch.Ptrsize))
	Cput(DW_LNE_set_address)

	pc := s.Value
	line := 1
	file := 1
	if Linkmode == LinkExternal {
		adddwarfrel(linesec, s, lineo, Thearch.Ptrsize, 0)
	} else {
		addrput(pc)
	}

	var a *Auto
	var da int
	var dt int
	var dwfunc *DWDie
	var dws **DWDie
	var dwvar *DWDie
	var n string
	var nn string
	var offs int64
	var pcfile Pciter
	var pcline Pciter
	var varhash [HASHSIZE]*DWDie
	for Ctxt.Cursym = Ctxt.Textp; Ctxt.Cursym != nil; Ctxt.Cursym = Ctxt.Cursym.Next {
		s = Ctxt.Cursym

		dwfunc = newdie(dwinfo, DW_ABRV_FUNCTION, s.Name)
		newattr(dwfunc, DW_AT_low_pc, DW_CLS_ADDRESS, s.Value, s)
		epc = s.Value + s.Size
		epcs = s
		newattr(dwfunc, DW_AT_high_pc, DW_CLS_ADDRESS, epc, s)
		if s.Version == 0 {
			newattr(dwfunc, DW_AT_external, DW_CLS_FLAG, 1, 0)
		}

		if s.Pcln == nil {
			continue
		}

		finddebugruntimepath(s)

		pciterinit(Ctxt, &pcfile, &s.Pcln.Pcfile)
		pciterinit(Ctxt, &pcline, &s.Pcln.Pcline)
		epc = pc
		for pcfile.done == 0 && pcline.done == 0 {
			if epc-s.Value >= int64(pcfile.nextpc) {
				pciternext(&pcfile)
				continue
			}

			if epc-s.Value >= int64(pcline.nextpc) {
				pciternext(&pcline)
				continue
			}

			if int32(file) != pcfile.value {
				Cput(DW_LNS_set_file)
				uleb128put(int64(pcfile.value))
				file = int(pcfile.value)
			}

			putpclcdelta(s.Value+int64(pcline.pc)-pc, int64(pcline.value)-int64(line))

			pc = s.Value + int64(pcline.pc)
			line = int(pcline.value)
			if pcfile.nextpc < pcline.nextpc {
				epc = int64(pcfile.nextpc)
			} else {
				epc = int64(pcline.nextpc)
			}
			epc += s.Value
		}

		da = 0
		dwfunc.hash = varhash[:] // enable indexing of children by name
		varhash = [HASHSIZE]*DWDie{}
		for a = s.Autom; a != nil; a = a.Link {
			switch a.Name {
			case obj.A_AUTO:
				dt = DW_ABRV_AUTO
				offs = int64(a.Aoffset)
				if !haslinkregister() {
					offs -= int64(Thearch.Ptrsize)
				}

			case obj.A_PARAM:
				dt = DW_ABRV_PARAM
				offs = int64(a.Aoffset)
				if haslinkregister() {
					offs += int64(Thearch.Ptrsize)
				}

			default:
				continue
			}

			if strings.Contains(a.Asym.Name, ".autotmp_") {
				continue
			}
			if find(dwfunc, a.Asym.Name) != nil {
				n = mkvarname(a.Asym.Name, da)
			} else {
				n = a.Asym.Name
			}

			// Drop the package prefix from locals and arguments.
			_ = nn
			if i := strings.LastIndex(n, "."); i >= 0 {
				n = n[i+1:]
			}

			dwvar = newdie(dwfunc, dt, n)
			newcfaoffsetattr(dwvar, int32(offs))
			newrefattr(dwvar, DW_AT_type, defgotype(a.Gotype))

			// push dwvar down dwfunc->child to preserve order
			newattr(dwvar, DW_AT_internal_location, DW_CLS_CONSTANT, offs, nil)

			dwfunc.child = dwvar.link // take dwvar out from the top of the list
			for dws = &dwfunc.child; *dws != nil; dws = &(*dws).link {
				if offs > getattr(*dws, DW_AT_internal_location).value {
					break
				}
			}
			dwvar.link = *dws
			*dws = dwvar

			da++
		}

		dwfunc.hash = nil
	}

	flushunit(dwinfo, epc, epcs, unitstart, int32(headerend-unitstart-10))
	linesize = Cpos() - lineo
}

/*
 *  Emit .debug_frame
 */
const (
	CIERESERVE          = 16
	DATAALIGNMENTFACTOR = -4
)

func putpccfadelta(deltapc int64, cfa int64) {
	Cput(DW_CFA_def_cfa_offset_sf)
	sleb128put(cfa / DATAALIGNMENTFACTOR)

	if deltapc < 0x40 {
		Cput(uint8(DW_CFA_advance_loc + deltapc))
	} else if deltapc < 0x100 {
		Cput(DW_CFA_advance_loc1)
		Cput(uint8(deltapc))
	} else if deltapc < 0x10000 {
		Cput(DW_CFA_advance_loc2)
		Thearch.Wput(uint16(deltapc))
	} else {
		Cput(DW_CFA_advance_loc4)
		Thearch.Lput(uint32(deltapc))
	}
}

func writeframes() {
	if framesec == nil {
		framesec = Linklookup(Ctxt, ".dwarfframe", 0)
	}
	framesec.R = framesec.R[:0]
	frameo = Cpos()

	// Emit the CIE, Section 6.4.1
	Thearch.Lput(CIERESERVE)              // initial length, must be multiple of thearch.ptrsize
	Thearch.Lput(0xffffffff)              // cid.
	Cput(3)                               // dwarf version (appendix F)
	Cput(0)                               // augmentation ""
	uleb128put(1)                         // code_alignment_factor
	sleb128put(DATAALIGNMENTFACTOR)       // guess
	uleb128put(int64(Thearch.Dwarfreglr)) // return_address_register

	Cput(DW_CFA_def_cfa)

	uleb128put(int64(Thearch.Dwarfregsp)) // register SP (**ABI-dependent, defined in l.h)
	if haslinkregister() {
		uleb128put(int64(0)) // offset
	} else {
		uleb128put(int64(Thearch.Ptrsize)) // offset
	}

	Cput(DW_CFA_offset_extended)
	uleb128put(int64(Thearch.Dwarfreglr)) // return address
	if haslinkregister() {
		uleb128put(int64(0) / DATAALIGNMENTFACTOR) // at cfa - 0
	} else {
		uleb128put(int64(-Thearch.Ptrsize) / DATAALIGNMENTFACTOR) // at cfa - x*4
	}

	// 4 is to exclude the length field.
	pad := CIERESERVE + frameo + 4 - Cpos()

	if pad < 0 {
		Exitf("dwarf: CIERESERVE too small by %d bytes.", -pad)
	}

	strnput("", int(pad))

	var fdeo int64
	var fdesize int64
	var nextpc uint32
	var pcsp Pciter
	var s *LSym
	for Ctxt.Cursym = Ctxt.Textp; Ctxt.Cursym != nil; Ctxt.Cursym = Ctxt.Cursym.Next {
		s = Ctxt.Cursym
		if s.Pcln == nil {
			continue
		}

		fdeo = Cpos()

		// Emit a FDE, Section 6.4.1, starting wit a placeholder.
		Thearch.Lput(0) // length, must be multiple of thearch.ptrsize
		Thearch.Lput(0) // Pointer to the CIE above, at offset 0
		addrput(0)      // initial location
		addrput(0)      // address range

		for pciterinit(Ctxt, &pcsp, &s.Pcln.Pcsp); pcsp.done == 0; pciternext(&pcsp) {
			nextpc = pcsp.nextpc

			// pciterinit goes up to the end of the function,
			// but DWARF expects us to stop just before the end.
			if int64(nextpc) == s.Size {
				nextpc--
				if nextpc < pcsp.pc {
					continue
				}
			}

			if haslinkregister() {
				putpccfadelta(int64(nextpc)-int64(pcsp.pc), int64(pcsp.value))
			} else {
				putpccfadelta(int64(nextpc)-int64(pcsp.pc), int64(Thearch.Ptrsize)+int64(pcsp.value))
			}
		}

		fdesize = Cpos() - fdeo - 4 // exclude the length field.
		pad = Rnd(fdesize, int64(Thearch.Ptrsize)) - fdesize
		strnput("", int(pad))
		fdesize += pad

		// Emit the FDE header for real, Section 6.4.1.
		Cseek(fdeo)

		Thearch.Lput(uint32(fdesize))
		if Linkmode == LinkExternal {
			adddwarfrel(framesec, framesym, frameo, 4, 0)
			adddwarfrel(framesec, s, frameo, Thearch.Ptrsize, 0)
		} else {
			Thearch.Lput(0)
			addrput(s.Value)
		}

		addrput(s.Size)
		Cseek(fdeo + 4 + fdesize)
	}

	Cflush()
	framesize = Cpos() - frameo
}

/*
 *  Walk DWarfDebugInfoEntries, and emit .debug_info
 */
const (
	COMPUNITHEADERSIZE = 4 + 2 + 4 + 1
)

func writeinfo() {
	fwdcount = 0
	if infosec == nil {
		infosec = Linklookup(Ctxt, ".dwarfinfo", 0)
	}
	infosec.R = infosec.R[:0]

	if arangessec == nil {
		arangessec = Linklookup(Ctxt, ".dwarfaranges", 0)
	}
	arangessec.R = arangessec.R[:0]

	var here int64
	var unitstart int64
	for compunit := dwroot.child; compunit != nil; compunit = compunit.link {
		unitstart = Cpos()

		// Write .debug_info Compilation Unit Header (sec 7.5.1)
		// Fields marked with (*) must be changed for 64-bit dwarf
		// This must match COMPUNITHEADERSIZE above.
		Thearch.Lput(0) // unit_length (*), will be filled in later.
		Thearch.Wput(2) // dwarf version (appendix F)

		// debug_abbrev_offset (*)
		if Linkmode == LinkExternal {
			adddwarfrel(infosec, abbrevsym, infoo, 4, 0)
		} else {
			Thearch.Lput(0)
		}

		Cput(uint8(Thearch.Ptrsize)) // address_size

		putdie(compunit)

		here = Cpos()
		Cseek(unitstart)
		Thearch.Lput(uint32(here - unitstart - 4)) // exclude the length field.
		Cseek(here)
	}

	Cflush()
}

/*
 *  Emit .debug_pubnames/_types.  _info must have been written before,
 *  because we need die->offs and infoo/infosize;
 */
func ispubname(die *DWDie) bool {
	switch die.abbrev {
	case DW_ABRV_FUNCTION, DW_ABRV_VARIABLE:
		a := getattr(die, DW_AT_external)
		return a != nil && a.value != 0
	}

	return false
}

func ispubtype(die *DWDie) bool {
	return die.abbrev >= DW_ABRV_NULLTYPE
}

func writepub(ispub func(*DWDie) bool) int64 {
	var die *DWDie
	var dwa *DWAttr
	var unitstart int64
	var unitend int64
	var here int64

	sectionstart := Cpos()

	for compunit := dwroot.child; compunit != nil; compunit = compunit.link {
		unitstart = compunit.offs - COMPUNITHEADERSIZE
		if compunit.link != nil {
			unitend = compunit.link.offs - COMPUNITHEADERSIZE
		} else {
			unitend = infoo + infosize
		}

		// Write .debug_pubnames/types	Header (sec 6.1.1)
		Thearch.Lput(0)                           // unit_length (*), will be filled in later.
		Thearch.Wput(2)                           // dwarf version (appendix F)
		Thearch.Lput(uint32(unitstart))           // debug_info_offset (of the Comp unit Header)
		Thearch.Lput(uint32(unitend - unitstart)) // debug_info_length

		for die = compunit.child; die != nil; die = die.link {
			if !ispub(die) {
				continue
			}
			Thearch.Lput(uint32(die.offs - unitstart))
			dwa = getattr(die, DW_AT_name)
			strnput(dwa.data.(string), int(dwa.value+1))
		}

		Thearch.Lput(0)

		here = Cpos()
		Cseek(sectionstart)
		Thearch.Lput(uint32(here - sectionstart - 4)) // exclude the length field.
		Cseek(here)
	}

	return sectionstart
}

/*
 *  emit .debug_aranges.  _info must have been written before,
 *  because we need die->offs of dw_globals.
 */
func writearanges() int64 {
	var b *DWAttr
	var e *DWAttr
	var value int64

	sectionstart := Cpos()
	headersize := int(Rnd(4+2+4+1+1, int64(Thearch.Ptrsize))) // don't count unit_length field itself

	for compunit := dwroot.child; compunit != nil; compunit = compunit.link {
		b = getattr(compunit, DW_AT_low_pc)
		if b == nil {
			continue
		}
		e = getattr(compunit, DW_AT_high_pc)
		if e == nil {
			continue
		}

		// Write .debug_aranges	 Header + entry	 (sec 6.1.2)
		Thearch.Lput(uint32(headersize) + 4*uint32(Thearch.Ptrsize) - 4) // unit_length (*)
		Thearch.Wput(2)                                                  // dwarf version (appendix F)

		value = compunit.offs - COMPUNITHEADERSIZE // debug_info_offset
		if Linkmode == LinkExternal {
			adddwarfrel(arangessec, infosym, sectionstart, 4, value)
		} else {
			Thearch.Lput(uint32(value))
		}

		Cput(uint8(Thearch.Ptrsize))        // address_size
		Cput(0)                             // segment_size
		strnput("", headersize-(4+2+4+1+1)) // align to thearch.ptrsize

		if Linkmode == LinkExternal {
			adddwarfrel(arangessec, b.data.(*LSym), sectionstart, Thearch.Ptrsize, b.value-(b.data.(*LSym)).Value)
		} else {
			addrput(b.value)
		}

		addrput(e.value - b.value)
		addrput(0)
		addrput(0)
	}

	Cflush()
	return sectionstart
}

func writegdbscript() int64 {
	sectionstart := Cpos()

	if gdbscript != "" {
		Cput(1) // magic 1 byte?
		strnput(gdbscript, len(gdbscript)+1)
		Cflush()
	}

	return sectionstart
}

func align(size int64) {
	if HEADTYPE == obj.Hwindows { // Only Windows PE need section align.
		strnput("", int(Rnd(size, PEFILEALIGN)-size))
	}
}

func writedwarfreloc(s *LSym) int64 {
	var i int
	var r *Reloc

	start := Cpos()
	for ri := 0; ri < len(s.R); ri++ {
		r = &s.R[ri]
		if Iself {
			i = Thearch.Elfreloc1(r, int64(r.Off))
		} else if HEADTYPE == obj.Hdarwin {
			i = Thearch.Machoreloc1(r, int64(r.Off))
		} else {
			i = -1
		}
		if i < 0 {
			Diag("unsupported obj reloc %d/%d to %s", r.Type, r.Siz, r.Sym.Name)
		}
	}

	return start
}

func addmachodwarfsect(prev *Section, name string) *Section {
	sect := addsection(&Segdwarf, name, 04)
	sect.Extnum = prev.Extnum + 1
	sym := Linklookup(Ctxt, name, 0)
	sym.Sect = sect
	return sect
}

/*
 * This is the main entry point for generating dwarf.  After emitting
 * the mandatory debug_abbrev section, it calls writelines() to set up
 * the per-compilation unit part of the DIE tree, while simultaneously
 * emitting the debug_line section.  When the final tree contains
 * forward references, it will write the debug_info section in 2
 * passes.
 *
 */
func Dwarfemitdebugsections() {
	if Debug['w'] != 0 { // disable dwarf
		return
	}

	if Linkmode == LinkExternal {
		if !Iself && HEADTYPE != obj.Hdarwin {
			return
		}
		if HEADTYPE == obj.Hdarwin {
			sect := Segdata.Sect
			// find the last section.
			for sect.Next != nil {
				sect = sect.Next
			}
			sect = addmachodwarfsect(sect, ".debug_abbrev")
			sect = addmachodwarfsect(sect, ".debug_line")
			sect = addmachodwarfsect(sect, ".debug_frame")
			sect = addmachodwarfsect(sect, ".debug_info")

			infosym = Linklookup(Ctxt, ".debug_info", 0)
			infosym.Hide = 1

			abbrevsym = Linklookup(Ctxt, ".debug_abbrev", 0)
			abbrevsym.Hide = 1

			linesym = Linklookup(Ctxt, ".debug_line", 0)
			linesym.Hide = 1

			framesym = Linklookup(Ctxt, ".debug_frame", 0)
			framesym.Hide = 1
		}
	}

	// For diagnostic messages.
	newattr(&dwtypes, DW_AT_name, DW_CLS_STRING, int64(len("dwtypes")), "dwtypes")

	mkindex(&dwroot)
	mkindex(&dwtypes)
	mkindex(&dwglobals)

	// Some types that must exist to define other ones.
	newdie(&dwtypes, DW_ABRV_NULLTYPE, "<unspecified>")

	newdie(&dwtypes, DW_ABRV_NULLTYPE, "void")
	newdie(&dwtypes, DW_ABRV_BARE_PTRTYPE, "unsafe.Pointer")

	die := newdie(&dwtypes, DW_ABRV_BASETYPE, "uintptr") // needed for array size
	newattr(die, DW_AT_encoding, DW_CLS_CONSTANT, DW_ATE_unsigned, 0)
	newattr(die, DW_AT_byte_size, DW_CLS_CONSTANT, int64(Thearch.Ptrsize), 0)
	newattr(die, DW_AT_go_kind, DW_CLS_CONSTANT, obj.KindUintptr, 0)

	// Needed by the prettyprinter code for interface inspection.
	defgotype(lookup_or_diag("type.runtime._type"))

	defgotype(lookup_or_diag("type.runtime.interfacetype"))
	defgotype(lookup_or_diag("type.runtime.itab"))

	genasmsym(defdwsymb)

	writeabbrev()
	align(abbrevsize)
	writelines()
	align(linesize)
	writeframes()
	align(framesize)

	synthesizestringtypes(dwtypes.child)
	synthesizeslicetypes(dwtypes.child)
	synthesizemaptypes(dwtypes.child)
	synthesizechantypes(dwtypes.child)

	reversetree(&dwroot.child)
	reversetree(&dwtypes.child)
	reversetree(&dwglobals.child)

	movetomodule(&dwtypes)
	movetomodule(&dwglobals)

	infoo = Cpos()
	writeinfo()
	infoe := Cpos()
	pubnameso = infoe
	pubtypeso = infoe
	arangeso = infoe
	gdbscripto = infoe

	if fwdcount > 0 {
		if Debug['v'] != 0 {
			fmt.Fprintf(&Bso, "%5.2f dwarf pass 2.\n", obj.Cputime())
		}
		Cseek(infoo)
		writeinfo()
		if fwdcount > 0 {
			Exitf("dwarf: unresolved references after first dwarf info pass")
		}

		if infoe != Cpos() {
			Exitf("dwarf: inconsistent second dwarf info pass")
		}
	}

	infosize = infoe - infoo
	align(infosize)

	pubnameso = writepub(ispubname)
	pubnamessize = Cpos() - pubnameso
	align(pubnamessize)

	pubtypeso = writepub(ispubtype)
	pubtypessize = Cpos() - pubtypeso
	align(pubtypessize)

	arangeso = writearanges()
	arangessize = Cpos() - arangeso
	align(arangessize)

	gdbscripto = writegdbscript()
	gdbscriptsize = Cpos() - gdbscripto
	align(gdbscriptsize)

	for Cpos()&7 != 0 {
		Cput(0)
	}
	if HEADTYPE != obj.Hdarwin {
		dwarfemitreloc()
	}
}

func dwarfemitreloc() {
	if Debug['w'] != 0 { // disable dwarf
		return
	}
	inforeloco = writedwarfreloc(infosec)
	inforelocsize = Cpos() - inforeloco
	align(inforelocsize)

	arangesreloco = writedwarfreloc(arangessec)
	arangesrelocsize = Cpos() - arangesreloco
	align(arangesrelocsize)

	linereloco = writedwarfreloc(linesec)
	linerelocsize = Cpos() - linereloco
	align(linerelocsize)

	framereloco = writedwarfreloc(framesec)
	framerelocsize = Cpos() - framereloco
	align(framerelocsize)
}

/*
 *  Elf.
 */
const (
	ElfStrDebugAbbrev = iota
	ElfStrDebugAranges
	ElfStrDebugFrame
	ElfStrDebugInfo
	ElfStrDebugLine
	ElfStrDebugLoc
	ElfStrDebugMacinfo
	ElfStrDebugPubNames
	ElfStrDebugPubTypes
	ElfStrDebugRanges
	ElfStrDebugStr
	ElfStrGDBScripts
	ElfStrRelDebugInfo
	ElfStrRelDebugAranges
	ElfStrRelDebugLine
	ElfStrRelDebugFrame
	NElfStrDbg
)

var elfstrdbg [NElfStrDbg]int64

func dwarfaddshstrings(shstrtab *LSym) {
	if Debug['w'] != 0 { // disable dwarf
		return
	}

	elfstrdbg[ElfStrDebugAbbrev] = Addstring(shstrtab, ".debug_abbrev")
	elfstrdbg[ElfStrDebugAranges] = Addstring(shstrtab, ".debug_aranges")
	elfstrdbg[ElfStrDebugFrame] = Addstring(shstrtab, ".debug_frame")
	elfstrdbg[ElfStrDebugInfo] = Addstring(shstrtab, ".debug_info")
	elfstrdbg[ElfStrDebugLine] = Addstring(shstrtab, ".debug_line")
	elfstrdbg[ElfStrDebugLoc] = Addstring(shstrtab, ".debug_loc")
	elfstrdbg[ElfStrDebugMacinfo] = Addstring(shstrtab, ".debug_macinfo")
	elfstrdbg[ElfStrDebugPubNames] = Addstring(shstrtab, ".debug_pubnames")
	elfstrdbg[ElfStrDebugPubTypes] = Addstring(shstrtab, ".debug_pubtypes")
	elfstrdbg[ElfStrDebugRanges] = Addstring(shstrtab, ".debug_ranges")
	elfstrdbg[ElfStrDebugStr] = Addstring(shstrtab, ".debug_str")
	elfstrdbg[ElfStrGDBScripts] = Addstring(shstrtab, ".debug_gdb_scripts")
	if Linkmode == LinkExternal {
		switch Thearch.Thechar {
		case '6', '7', '9':
			elfstrdbg[ElfStrRelDebugInfo] = Addstring(shstrtab, ".rela.debug_info")
			elfstrdbg[ElfStrRelDebugAranges] = Addstring(shstrtab, ".rela.debug_aranges")
			elfstrdbg[ElfStrRelDebugLine] = Addstring(shstrtab, ".rela.debug_line")
			elfstrdbg[ElfStrRelDebugFrame] = Addstring(shstrtab, ".rela.debug_frame")
		default:
			elfstrdbg[ElfStrRelDebugInfo] = Addstring(shstrtab, ".rel.debug_info")
			elfstrdbg[ElfStrRelDebugAranges] = Addstring(shstrtab, ".rel.debug_aranges")
			elfstrdbg[ElfStrRelDebugLine] = Addstring(shstrtab, ".rel.debug_line")
			elfstrdbg[ElfStrRelDebugFrame] = Addstring(shstrtab, ".rel.debug_frame")
		}

		infosym = Linklookup(Ctxt, ".debug_info", 0)
		infosym.Hide = 1

		abbrevsym = Linklookup(Ctxt, ".debug_abbrev", 0)
		abbrevsym.Hide = 1

		linesym = Linklookup(Ctxt, ".debug_line", 0)
		linesym.Hide = 1

		framesym = Linklookup(Ctxt, ".debug_frame", 0)
		framesym.Hide = 1
	}
}

// Add section symbols for DWARF debug info.  This is called before
// dwarfaddelfheaders.
func dwarfaddelfsectionsyms() {
	if infosym != nil {
		infosympos = Cpos()
		putelfsectionsym(infosym, 0)
	}

	if abbrevsym != nil {
		abbrevsympos = Cpos()
		putelfsectionsym(abbrevsym, 0)
	}

	if linesym != nil {
		linesympos = Cpos()
		putelfsectionsym(linesym, 0)
	}

	if framesym != nil {
		framesympos = Cpos()
		putelfsectionsym(framesym, 0)
	}
}

func dwarfaddelfrelocheader(elfstr int, shdata *ElfShdr, off int64, size int64) {
	sh := newElfShdr(elfstrdbg[elfstr])
	switch Thearch.Thechar {
	case '6', '7', '9':
		sh.type_ = SHT_RELA
	default:
		sh.type_ = SHT_REL
	}

	sh.entsize = uint64(Thearch.Ptrsize) * 2
	if sh.type_ == SHT_RELA {
		sh.entsize += uint64(Thearch.Ptrsize)
	}
	sh.link = uint32(elfshname(".symtab").shnum)
	sh.info = uint32(shdata.shnum)
	sh.off = uint64(off)
	sh.size = uint64(size)
	sh.addralign = uint64(Thearch.Ptrsize)
}

func dwarfaddelfheaders() {
	if Debug['w'] != 0 { // disable dwarf
		return
	}

	sh := newElfShdr(elfstrdbg[ElfStrDebugAbbrev])
	sh.type_ = SHT_PROGBITS
	sh.off = uint64(abbrevo)
	sh.size = uint64(abbrevsize)
	sh.addralign = 1
	if abbrevsympos > 0 {
		putelfsymshndx(abbrevsympos, sh.shnum)
	}

	sh = newElfShdr(elfstrdbg[ElfStrDebugLine])
	sh.type_ = SHT_PROGBITS
	sh.off = uint64(lineo)
	sh.size = uint64(linesize)
	sh.addralign = 1
	if linesympos > 0 {
		putelfsymshndx(linesympos, sh.shnum)
	}
	shline := sh

	sh = newElfShdr(elfstrdbg[ElfStrDebugFrame])
	sh.type_ = SHT_PROGBITS
	sh.off = uint64(frameo)
	sh.size = uint64(framesize)
	sh.addralign = 1
	if framesympos > 0 {
		putelfsymshndx(framesympos, sh.shnum)
	}
	shframe := sh

	sh = newElfShdr(elfstrdbg[ElfStrDebugInfo])
	sh.type_ = SHT_PROGBITS
	sh.off = uint64(infoo)
	sh.size = uint64(infosize)
	sh.addralign = 1
	if infosympos > 0 {
		putelfsymshndx(infosympos, sh.shnum)
	}
	shinfo := sh

	if pubnamessize > 0 {
		sh := newElfShdr(elfstrdbg[ElfStrDebugPubNames])
		sh.type_ = SHT_PROGBITS
		sh.off = uint64(pubnameso)
		sh.size = uint64(pubnamessize)
		sh.addralign = 1
	}

	if pubtypessize > 0 {
		sh := newElfShdr(elfstrdbg[ElfStrDebugPubTypes])
		sh.type_ = SHT_PROGBITS
		sh.off = uint64(pubtypeso)
		sh.size = uint64(pubtypessize)
		sh.addralign = 1
	}

	var sharanges *ElfShdr
	if arangessize != 0 {
		sh := newElfShdr(elfstrdbg[ElfStrDebugAranges])
		sh.type_ = SHT_PROGBITS
		sh.off = uint64(arangeso)
		sh.size = uint64(arangessize)
		sh.addralign = 1
		sharanges = sh
	}

	if gdbscriptsize != 0 {
		sh := newElfShdr(elfstrdbg[ElfStrGDBScripts])
		sh.type_ = SHT_PROGBITS
		sh.off = uint64(gdbscripto)
		sh.size = uint64(gdbscriptsize)
		sh.addralign = 1
	}

	if inforelocsize != 0 {
		dwarfaddelfrelocheader(ElfStrRelDebugInfo, shinfo, inforeloco, inforelocsize)
	}

	if arangesrelocsize != 0 {
		dwarfaddelfrelocheader(ElfStrRelDebugAranges, sharanges, arangesreloco, arangesrelocsize)
	}

	if linerelocsize != 0 {
		dwarfaddelfrelocheader(ElfStrRelDebugLine, shline, linereloco, linerelocsize)
	}

	if framerelocsize != 0 {
		dwarfaddelfrelocheader(ElfStrRelDebugFrame, shframe, framereloco, framerelocsize)
	}
}

/*
 * Macho
 */
func dwarfaddmachoheaders(ms *MachoSeg) {
	if Debug['w'] != 0 { // disable dwarf
		return
	}

	// Zero vsize segments won't be loaded in memory, even so they
	// have to be page aligned in the file.
	fakestart := Rnd(int64(Segdwarf.Fileoff), 0x1000)
	addr := Segdata.Vaddr + Segdata.Length

	nsect := 4
	if pubnamessize > 0 {
		nsect++
	}
	if pubtypessize > 0 {
		nsect++
	}
	if arangessize > 0 {
		nsect++
	}
	if gdbscriptsize > 0 {
		nsect++
	}

	if Linkmode != LinkExternal {
		ms = newMachoSeg("__DWARF", nsect)
		ms.fileoffset = uint64(fakestart)
		ms.filesize = Segdwarf.Filelen
		ms.vaddr = addr
	}

	msect := newMachoSect(ms, "__debug_abbrev", "__DWARF")
	msect.off = uint32(abbrevo)
	msect.size = uint64(abbrevsize)
	msect.addr = addr
	addr += msect.size
	msect.flag = 0x02000000
	if abbrevsym != nil {
		abbrevsym.Value = int64(msect.addr)
	}

	msect = newMachoSect(ms, "__debug_line", "__DWARF")
	msect.off = uint32(lineo)
	msect.size = uint64(linesize)
	msect.addr = addr
	addr += msect.size
	msect.flag = 0x02000000
	if linesym != nil {
		linesym.Value = int64(msect.addr)
	}
	if linerelocsize > 0 {
		msect.nreloc = uint32(len(linesec.R))
		msect.reloc = uint32(linereloco)
	}

	msect = newMachoSect(ms, "__debug_frame", "__DWARF")
	msect.off = uint32(frameo)
	msect.size = uint64(framesize)
	msect.addr = addr
	addr += msect.size
	msect.flag = 0x02000000
	if framesym != nil {
		framesym.Value = int64(msect.addr)
	}
	if framerelocsize > 0 {
		msect.nreloc = uint32(len(framesec.R))
		msect.reloc = uint32(framereloco)
	}

	msect = newMachoSect(ms, "__debug_info", "__DWARF")
	msect.off = uint32(infoo)
	msect.size = uint64(infosize)
	msect.addr = addr
	addr += msect.size
	msect.flag = 0x02000000
	if infosym != nil {
		infosym.Value = int64(msect.addr)
	}
	if inforelocsize > 0 {
		msect.nreloc = uint32(len(infosec.R))
		msect.reloc = uint32(inforeloco)
	}

	if pubnamessize > 0 {
		msect := newMachoSect(ms, "__debug_pubnames", "__DWARF")
		msect.off = uint32(pubnameso)
		msect.size = uint64(pubnamessize)
		msect.addr = addr
		addr += msect.size
		msect.flag = 0x02000000
	}

	if pubtypessize > 0 {
		msect := newMachoSect(ms, "__debug_pubtypes", "__DWARF")
		msect.off = uint32(pubtypeso)
		msect.size = uint64(pubtypessize)
		msect.addr = addr
		addr += msect.size
		msect.flag = 0x02000000
	}

	if arangessize > 0 {
		msect := newMachoSect(ms, "__debug_aranges", "__DWARF")
		msect.off = uint32(arangeso)
		msect.size = uint64(arangessize)
		msect.addr = addr
		addr += msect.size
		msect.flag = 0x02000000
		if arangesrelocsize > 0 {
			msect.nreloc = uint32(len(arangessec.R))
			msect.reloc = uint32(arangesreloco)
		}
	}

	// TODO(lvd) fix gdb/python to load MachO (16 char section name limit)
	if gdbscriptsize > 0 {
		msect := newMachoSect(ms, "__debug_gdb_scripts", "__DWARF")
		msect.off = uint32(gdbscripto)
		msect.size = uint64(gdbscriptsize)
		msect.addr = addr
		addr += msect.size
		msect.flag = 0x02000000
	}
}

/*
 * Windows PE
 */
func dwarfaddpeheaders() {
	if Debug['w'] != 0 { // disable dwarf
		return
	}

	newPEDWARFSection(".debug_abbrev", abbrevsize)
	newPEDWARFSection(".debug_line", linesize)
	newPEDWARFSection(".debug_frame", framesize)
	newPEDWARFSection(".debug_info", infosize)
	newPEDWARFSection(".debug_pubnames", pubnamessize)
	newPEDWARFSection(".debug_pubtypes", pubtypessize)
	newPEDWARFSection(".debug_aranges", arangessize)
	newPEDWARFSection(".debug_gdb_scripts", gdbscriptsize)
}
