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

// Mapping from PC to SP offset (called CFA - Canonical Frame Address - in DWARF).
// This value is the offset from the stack pointer to the virtual frame pointer
// (address of zeroth argument) at each PC value in the program.

package dwarf

import "fmt"

// http://www.dwarfstd.org/doc/DWARF4.pdf Section 6.4 page 126
// We implement only the CFA column of the table, not the location
// information about other registers. In other words, we implement
// only what we need to understand Go programs compiled by gc.

// PCToSPOffset returns the offset, at the specified PC, to add to the
// SP to reach the virtual frame pointer, which corresponds to the
// address of the zeroth argument of the function, the word on the
// stack immediately above the return PC.
func (d *Data) PCToSPOffset(pc uint64) (offset int64, err error) {
	if len(d.frame) == 0 {
		return 0, fmt.Errorf("PCToSPOffset: no frame table")
	}
	var m frameMachine
	// Assume the first info unit is the same as us. Extremely likely. TODO?
	if len(d.unit) == 0 {
		return 0, fmt.Errorf("PCToSPOffset: no info section")
	}
	buf := makeBuf(d, &d.unit[0], "frame", 0, d.frame)
	for len(buf.data) > 0 {
		offset, err := m.evalCompilationUnit(&buf, pc)
		if err != nil {
			return 0, err
		}
		return offset, nil
	}
	return 0, fmt.Errorf("PCToSPOffset: no frame defined for PC %#x", pc)
}

// Call Frame instructions. Figure 40, page 181.
// Structure is high two bits plus low 6 bits specified by + in comment.
// Some take one or two operands.
const (
	frameNop              = 0<<6 + 0x00
	frameAdvanceLoc       = 1<<6 + 0x00 // + delta
	frameOffset           = 2<<6 + 0x00 // + register op: ULEB128 offset
	frameRestore          = 3<<6 + 0x00 // + register
	frameSetLoc           = 0<<6 + 0x01 // op: address
	frameAdvanceLoc1      = 0<<6 + 0x02 // op: 1-byte delta
	frameAdvanceLoc2      = 0<<6 + 0x03 // op: 2-byte delta
	frameAdvanceLoc4      = 0<<6 + 0x04 // op: 4-byte delta
	frameOffsetExtended   = 0<<6 + 0x05 // ops: ULEB128 register ULEB128 offset
	frameRestoreExtended  = 0<<6 + 0x06 // op: ULEB128 register
	frameUndefined        = 0<<6 + 0x07 // op: ULEB128 register
	frameSameValue        = 0<<6 + 0x08 // op: ULEB128 register
	frameRegister         = 0<<6 + 0x09 // op: ULEB128 register ULEB128 register
	frameRememberState    = 0<<6 + 0x0a
	frameRestoreState     = 0<<6 + 0x0b
	frameDefCFA           = 0<<6 + 0x0c // op: ULEB128 register ULEB128 offset
	frameDefCFARegister   = 0<<6 + 0x0d // op: ULEB128 register
	frameDefCFAOffset     = 0<<6 + 0x0e // op: ULEB128 offset
	frameDefCFAExpression = 0<<6 + 0x0f // op: BLOCK
	frameExpression       = 0<<6 + 0x10 // op: ULEB128 register BLOCK
	frameOffsetExtendedSf = 0<<6 + 0x11 // op: ULEB128 register SLEB128 offset
	frameDefCFASf         = 0<<6 + 0x12 // op: ULEB128 register SLEB128 offset
	frameDefCFAOffsetSf   = 0<<6 + 0x13 // op: SLEB128 offset
	frameValOffset        = 0<<6 + 0x14 // op: ULEB128 ULEB128
	frameValOffsetSf      = 0<<6 + 0x15 // op: ULEB128 SLEB128
	frameValExpression    = 0<<6 + 0x16 // op: ULEB128 BLOCK
	frameLoUser           = 0<<6 + 0x1c
	frameHiUser           = 0<<6 + 0x3f
)

// frameMachine represents the PC/SP engine.
// Section 6.4, page 129.
type frameMachine struct {
	// Initial values from CIE.
	version               uint8  // Version number, "independent of DWARF version"
	augmentation          string // Augmentation; treated as unexpected for now. TODO.
	addressSize           uint8  // In DWARF v4 and above. Size of a target address.
	segmentSize           uint8  // In DWARF v4 and above. Size of a segment selector.
	codeAlignmentFactor   uint64 // Unit of code size in advance instructions.
	dataAlignmentFactor   int64  // Unit of data size in certain offset instructions.
	returnAddressRegister int    // Pseudo-register (actually data column) representing return address.
	returnRegisterOffset  int64  // Offset to saved PC from CFA in bytes.
	// CFA definition.
	cfaRegister int   // Which register represents the SP.
	cfaOffset   int64 // CFA offset value.
	// Running machine.
	location uint64
}

// evalCompilationUnit scans the frame data for one compilation unit to retrieve
// the offset information for the specified pc.
func (m *frameMachine) evalCompilationUnit(b *buf, pc uint64) (int64, error) {
	err := m.parseCIE(b)
	if err != nil {
		return 0, err
	}
	for {
		offset, found, err := m.scanFDE(b, pc)
		if err != nil {
			return 0, err
		}
		if found {
			return offset, nil
		}
	}
}

// parseCIE assumes the incoming buffer starts with a CIE block and parses it
// to initialize a frameMachine.
func (m *frameMachine) parseCIE(allBuf *buf) error {
	length := int(allBuf.uint32())
	if len(allBuf.data) < length {
		return fmt.Errorf("CIE parse error: too short")
	}
	// Create buffer for just this section.
	b := allBuf.slice(length)
	cie := b.uint32()
	if cie != 0xFFFFFFFF {
		return fmt.Errorf("CIE parse error: not CIE: %x", cie)
	}
	m.version = b.uint8()
	if m.version != 3 && m.version != 4 {
		return fmt.Errorf("CIE parse error: unsupported version %d", m.version)
	}
	m.augmentation = b.string()
	if len(m.augmentation) > 0 {
		return fmt.Errorf("CIE: can't handled augmentation string %q", m.augmentation)
	}
	if m.version >= 4 {
		m.addressSize = b.uint8()
		m.segmentSize = b.uint8()
	} else {
		// Unused. Gc generates version 3, so these values will not be
		// set, but they are also not used so it's OK.
	}
	m.codeAlignmentFactor = b.uint()
	m.dataAlignmentFactor = b.int()
	m.returnAddressRegister = int(b.uint())

	// Initial instructions. At least for Go, establishes SP register number
	// and initial value of CFA offset at start of function.
	_, err := m.run(&b, ^uint64(0))
	if err != nil {
		return err
	}

	// There's padding, but we can ignore it.
	return nil
}

// scanFDE assumes the incoming buffer starts with a FDE block and parses it
// to run a frameMachine and, if the PC is represented in its range, return
// the CFA offset for that PC. The boolean returned reports whether the
// PC is in range for this FDE.
func (m *frameMachine) scanFDE(allBuf *buf, pc uint64) (int64, bool, error) {
	length := int(allBuf.uint32())
	if len(allBuf.data) < length {
		return 0, false, fmt.Errorf("FDE parse error: too short")
	}
	if length <= 0 {
		if length == 0 {
			// EOF.
			return 0, false, fmt.Errorf("PC not found in PC/SP table")
		}
		return 0, false, fmt.Errorf("bad FDE length %d", length)
	}
	// Create buffer for just this section.
	b := allBuf.slice(length)
	cieOffset := b.uint32() // TODO assumes 32 bits.
	// Expect 0: first CIE in this segment. TODO.
	if cieOffset != 0 {
		return 0, false, fmt.Errorf("FDE parse error: bad CIE offset: %.2x", cieOffset)
	}
	// Initial location.
	m.location = b.addr()
	addressRange := b.addr()
	// If the PC is not in this function, there's no point in executing the instructions.
	if pc < m.location || m.location+addressRange <= pc {
		return 0, false, nil
	}
	// The PC appears in this FDE. Scan to find the location.
	offset, err := m.run(&b, pc)
	if err != nil {
		return 0, false, err
	}

	// There's padding, but we can ignore it.
	return offset, true, nil
}

// run executes the instructions in the buffer, which has been sliced to contain
// only the data for this block. When we run out of data, we return.
// Since we are only called when we know the PC is in this block, reaching
// EOF is not an error, it just means the final CFA definition matches the
// tail of the block that holds the PC.
// The return value is the CFA at the end of the block or the PC, whichever
// comes first.
func (m *frameMachine) run(b *buf, pc uint64) (int64, error) {
	// We run the machine at location == PC because if the PC is at the first
	// instruction of a block, the definition of its offset arrives as an
	// offset-defining operand after the PC is set to that location.
	for m.location <= pc && len(b.data) > 0 {
		op := b.uint8()
		// Ops with embedded operands
		switch op & 0xC0 {
		case frameAdvanceLoc: // (6.4.2.1)
			// delta in low bits
			m.location += uint64(op & 0x3F)
			continue
		case frameOffset: // (6.4.2.3)
			// Register in low bits; ULEB128 offset.
			// For Go binaries we only see this in the CIE for the return address register.
			if int(op&0x3F) != m.returnAddressRegister {
				return 0, fmt.Errorf("invalid frameOffset register R%d should be R%d", op&0x3f, m.returnAddressRegister)
			}
			m.returnRegisterOffset = int64(b.uint()) * m.dataAlignmentFactor
			continue
		case frameRestore: // (6.4.2.3)
			// register in low bits
			return 0, fmt.Errorf("unimplemented frameRestore(R%d)\n", op&0x3F)
		}

		// The remaining ops do not have embedded operands.

		switch op {
		// Row creation instructions (6.4.2.1)
		case frameNop:
		case frameSetLoc: // op: address
			return 0, fmt.Errorf("unimplemented setloc") // what size is operand?
		case frameAdvanceLoc1: // op: 1-byte delta
			m.location += uint64(b.uint8())
		case frameAdvanceLoc2: // op: 2-byte delta
			m.location += uint64(b.uint16())
		case frameAdvanceLoc4: // op: 4-byte delta
			m.location += uint64(b.uint32())

		// CFA definition instructions (6.4.2.2)
		case frameDefCFA: // op: ULEB128 register ULEB128 offset
			m.cfaRegister = int(b.int())
			m.cfaOffset = int64(b.uint())
		case frameDefCFASf: // op: ULEB128 register SLEB128 offset
			return 0, fmt.Errorf("unimplemented frameDefCFASf")
		case frameDefCFARegister: // op: ULEB128 register
			return 0, fmt.Errorf("unimplemented frameDefCFARegister")
		case frameDefCFAOffset: // op: ULEB128 offset
			return 0, fmt.Errorf("unimplemented frameDefCFAOffset")
		case frameDefCFAOffsetSf: // op: SLEB128 offset
			offset := b.int()
			m.cfaOffset = offset * m.dataAlignmentFactor
			// TODO: Verify we are using a factored offset.
		case frameDefCFAExpression: // op: BLOCK
			return 0, fmt.Errorf("unimplemented frameDefCFAExpression")

		// Register Rule instructions (6.4.2.3)
		case frameOffsetExtended: // ops: ULEB128 register ULEB128 offset
			return 0, fmt.Errorf("unimplemented frameOffsetExtended")
		case frameRestoreExtended: // op: ULEB128 register
			return 0, fmt.Errorf("unimplemented frameRestoreExtended")
		case frameUndefined: // op: ULEB128 register; unimplemented
			return 0, fmt.Errorf("unimplemented frameUndefined")
		case frameSameValue: // op: ULEB128 register
			return 0, fmt.Errorf("unimplemented frameSameValue")
		case frameRegister: // op: ULEB128 register ULEB128 register
			return 0, fmt.Errorf("unimplemented frameRegister")
		case frameRememberState:
			return 0, fmt.Errorf("unimplemented frameRememberState")
		case frameRestoreState:
			return 0, fmt.Errorf("unimplemented frameRestoreState")
		case frameExpression: // op: ULEB128 register BLOCK
			return 0, fmt.Errorf("unimplemented frameExpression")
		case frameOffsetExtendedSf: // op: ULEB128 register SLEB128 offset
			return 0, fmt.Errorf("unimplemented frameOffsetExtended_sf")
		case frameValOffset: // op: ULEB128 ULEB128
			return 0, fmt.Errorf("unimplemented frameValOffset")
		case frameValOffsetSf: // op: ULEB128 SLEB128
			return 0, fmt.Errorf("unimplemented frameValOffsetSf")
		case frameValExpression: // op: ULEB128 BLOCK
			return 0, fmt.Errorf("unimplemented frameValExpression")

		default:
			if frameLoUser <= op && op <= frameHiUser {
				return 0, fmt.Errorf("unknown user-defined frame op %#x", op)
			}
			return 0, fmt.Errorf("unknown frame op %#x", op)
		}
	}
	return m.cfaOffset, nil
}
