// 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, "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)
}
