// Copyright 2019 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.

package goobj

import (
	"bytes"
	"cmd/internal/objabi"
	"encoding/binary"
)

// CUFileIndex is used to index the filenames that are stored in the
// per-package/per-CU FileList.
type CUFileIndex uint32

// FuncInfo is serialized as a symbol (aux symbol). The symbol data is
// the binary encoding of the struct below.
//
// TODO: make each pcdata a separate symbol?
type FuncInfo struct {
	Args     uint32
	Locals   uint32
	FuncID   objabi.FuncID
	FuncFlag objabi.FuncFlag

	Pcsp        SymRef
	Pcfile      SymRef
	Pcline      SymRef
	Pcinline    SymRef
	Pcdata      []SymRef
	Funcdataoff []uint32
	File        []CUFileIndex

	InlTree []InlTreeNode
}

func (a *FuncInfo) Write(w *bytes.Buffer) {
	writeUint8 := func(x uint8) {
		w.WriteByte(x)
	}
	var b [4]byte
	writeUint32 := func(x uint32) {
		binary.LittleEndian.PutUint32(b[:], x)
		w.Write(b[:])
	}
	writeSymRef := func(s SymRef) {
		writeUint32(s.PkgIdx)
		writeUint32(s.SymIdx)
	}

	writeUint32(a.Args)
	writeUint32(a.Locals)
	writeUint8(uint8(a.FuncID))
	writeUint8(uint8(a.FuncFlag))
	writeUint8(0) // pad to uint32 boundary
	writeUint8(0)
	writeSymRef(a.Pcsp)
	writeSymRef(a.Pcfile)
	writeSymRef(a.Pcline)
	writeSymRef(a.Pcinline)
	writeUint32(uint32(len(a.Pcdata)))
	for _, sym := range a.Pcdata {
		writeSymRef(sym)
	}

	writeUint32(uint32(len(a.Funcdataoff)))
	for _, x := range a.Funcdataoff {
		writeUint32(x)
	}
	writeUint32(uint32(len(a.File)))
	for _, f := range a.File {
		writeUint32(uint32(f))
	}
	writeUint32(uint32(len(a.InlTree)))
	for i := range a.InlTree {
		a.InlTree[i].Write(w)
	}
}

// FuncInfoLengths is a cache containing a roadmap of offsets and
// lengths for things within a serialized FuncInfo. Each length field
// stores the number of items (e.g. files, inltree nodes, etc), and the
// corresponding "off" field stores the byte offset of the start of
// the items in question.
type FuncInfoLengths struct {
	NumPcdata      uint32
	PcdataOff      uint32
	NumFuncdataoff uint32
	FuncdataoffOff uint32
	NumFile        uint32
	FileOff        uint32
	NumInlTree     uint32
	InlTreeOff     uint32
	Initialized    bool
}

func (*FuncInfo) ReadFuncInfoLengths(b []byte) FuncInfoLengths {
	var result FuncInfoLengths

	// Offset to the number of pcdata values. This value is determined by counting
	// the number of bytes until we write pcdata to the file.
	const numpcdataOff = 44
	result.NumPcdata = binary.LittleEndian.Uint32(b[numpcdataOff:])
	result.PcdataOff = numpcdataOff + 4

	numfuncdataoffOff := result.PcdataOff + 8*result.NumPcdata
	result.NumFuncdataoff = binary.LittleEndian.Uint32(b[numfuncdataoffOff:])
	result.FuncdataoffOff = numfuncdataoffOff + 4

	numfileOff := result.FuncdataoffOff + 4*result.NumFuncdataoff
	result.NumFile = binary.LittleEndian.Uint32(b[numfileOff:])
	result.FileOff = numfileOff + 4

	numinltreeOff := result.FileOff + 4*result.NumFile
	result.NumInlTree = binary.LittleEndian.Uint32(b[numinltreeOff:])
	result.InlTreeOff = numinltreeOff + 4

	result.Initialized = true

	return result
}

func (*FuncInfo) ReadArgs(b []byte) uint32 { return binary.LittleEndian.Uint32(b) }

func (*FuncInfo) ReadLocals(b []byte) uint32 { return binary.LittleEndian.Uint32(b[4:]) }

func (*FuncInfo) ReadFuncID(b []byte) objabi.FuncID { return objabi.FuncID(b[8]) }

func (*FuncInfo) ReadFuncFlag(b []byte) objabi.FuncFlag { return objabi.FuncFlag(b[9]) }

func (*FuncInfo) ReadPcsp(b []byte) SymRef {
	return SymRef{binary.LittleEndian.Uint32(b[12:]), binary.LittleEndian.Uint32(b[16:])}
}

func (*FuncInfo) ReadPcfile(b []byte) SymRef {
	return SymRef{binary.LittleEndian.Uint32(b[20:]), binary.LittleEndian.Uint32(b[24:])}
}

func (*FuncInfo) ReadPcline(b []byte) SymRef {
	return SymRef{binary.LittleEndian.Uint32(b[28:]), binary.LittleEndian.Uint32(b[32:])}
}

func (*FuncInfo) ReadPcinline(b []byte) SymRef {
	return SymRef{binary.LittleEndian.Uint32(b[36:]), binary.LittleEndian.Uint32(b[40:])}
}

func (*FuncInfo) ReadPcdata(b []byte) []SymRef {
	syms := make([]SymRef, binary.LittleEndian.Uint32(b[44:]))
	for i := range syms {
		syms[i] = SymRef{binary.LittleEndian.Uint32(b[48+i*8:]), binary.LittleEndian.Uint32(b[52+i*8:])}
	}
	return syms
}

func (*FuncInfo) ReadFuncdataoff(b []byte, funcdataofffoff uint32, k uint32) int64 {
	return int64(binary.LittleEndian.Uint32(b[funcdataofffoff+4*k:]))
}

func (*FuncInfo) ReadFile(b []byte, filesoff uint32, k uint32) CUFileIndex {
	return CUFileIndex(binary.LittleEndian.Uint32(b[filesoff+4*k:]))
}

func (*FuncInfo) ReadInlTree(b []byte, inltreeoff uint32, k uint32) InlTreeNode {
	const inlTreeNodeSize = 4 * 6
	var result InlTreeNode
	result.Read(b[inltreeoff+k*inlTreeNodeSize:])
	return result
}

// InlTreeNode is the serialized form of FileInfo.InlTree.
type InlTreeNode struct {
	Parent   int32
	File     CUFileIndex
	Line     int32
	Func     SymRef
	ParentPC int32
}

func (inl *InlTreeNode) Write(w *bytes.Buffer) {
	var b [4]byte
	writeUint32 := func(x uint32) {
		binary.LittleEndian.PutUint32(b[:], x)
		w.Write(b[:])
	}
	writeUint32(uint32(inl.Parent))
	writeUint32(uint32(inl.File))
	writeUint32(uint32(inl.Line))
	writeUint32(inl.Func.PkgIdx)
	writeUint32(inl.Func.SymIdx)
	writeUint32(uint32(inl.ParentPC))
}

// Read an InlTreeNode from b, return the remaining bytes.
func (inl *InlTreeNode) Read(b []byte) []byte {
	readUint32 := func() uint32 {
		x := binary.LittleEndian.Uint32(b)
		b = b[4:]
		return x
	}
	inl.Parent = int32(readUint32())
	inl.File = CUFileIndex(readUint32())
	inl.Line = int32(readUint32())
	inl.Func = SymRef{readUint32(), readUint32()}
	inl.ParentPC = int32(readUint32())
	return b
}
