ng_operand

package
v0.0.0-...-d5e0ede Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jun 26, 2025 License: GPL-3.0 Imports: 18 Imported by: 0

Documentation

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Parse

func Parse(filename string, b []byte, opts ...Option) (any, error)

Parse parses the data from b using filename as information in the error messages.

func ParseFile

func ParseFile(filename string, opts ...Option) (i any, err error)

ParseFile parses the file identified by filename.

func ParseReader

func ParseReader(filename string, r io.Reader, opts ...Option) (any, error)

ParseReader parses the data from r using filename as information in the error messages.

Types

type Cloner

type Cloner interface {
	Clone() any
}

Cloner is implemented by any value that has a Clone method, which returns a copy of the value. This is mainly used for types which are not passed by value (e.g map, slice, chan) or structs that contain such types.

This is used in conjunction with the global state feature to create proper copies of the state to allow the parser to properly restore the state in the case of backtracking.

type MemoryInfo

type MemoryInfo struct {
	BaseReg      string // ベースレジスタ (例: "EAX", "BX")
	IndexReg     string // インデックスレジスタ (例: "ESI", "DI")
	Scale        int    // スケールファクタ (1, 2, 4, 8) - インデックスレジスタに適用
	Displacement int64  // ディスプレースメント (オフセット値)
	IsHexDisp    bool   // ディスプレースメントが16進数表記だったか
	DispLabel    string // ディスプレースメントがラベルの場合のラベル名
	Segment      string // セグメントオーバーライドプレフィックス (例: "ES", "CS:")
}

MemoryInfo は、メモリオペランドのアドレッシングに関する詳細情報を格納します。

type OperandPegImpl

type OperandPegImpl struct {
	// contains filtered or unexported fields
}

OperandPegImpl は PEG パーサーを使用して Operands インターフェースを実装します。 複数のパース済みオペランドを保持します。

func NewOperandPegImpl

func NewOperandPegImpl(parsedOperands []*ParsedOperandPeg) *OperandPegImpl

NewOperandPegImpl は、パース済みオペランドのスライスから新しい OperandPegImpl を作成します。

func (*OperandPegImpl) CalcOffsetByteSize

func (o *OperandPegImpl) CalcOffsetByteSize() int

CalcOffsetByteSize はメモリオペランドのオフセットサイズを計算します。 TODO: 複数のオペランドを処理する。現在は最初のメモリオペランドをチェックしています。 TODO: ディスプレースメント値 (1, 2, 4) に基づいてサイズを計算する。

func (*OperandPegImpl) CalcSibByteSize

func (o *OperandPegImpl) CalcSibByteSize() int

CalcSibByteSize は、SIB バイトが必要な場合に 1 を、不要な場合に 0 を返します。

func (*OperandPegImpl) DetectImmediateSize

func (o *OperandPegImpl) DetectImmediateSize() int

DetectImmediateSize は即値オペランドのサイズ (バイト単位) を検出します。 実際の即値が収まる最小サイズ (1, 2, 4, 8) を返します。

func (*OperandPegImpl) DisplacementBytes

func (o *OperandPegImpl) DisplacementBytes() []byte

DisplacementBytes は、最初のメモリオペランドのディスプレースメント部分をバイト列として返します。 ModRMがない直接アドレス指定 (moffs) の場合に利用することを想定しています。 メモリオペランドがない場合や、ディスプレースメントがない場合は nil を返します。 バイト列のサイズは BitMode に基づいて決定されます。

func (*OperandPegImpl) FromString

func (o *OperandPegImpl) FromString(text string) Operands

FromString はインターフェースを満たすためのダミー実装です。 代わりにパッケージレベルの FromString を使用してください。

func (*OperandPegImpl) GetBitMode

func (o *OperandPegImpl) GetBitMode() cpu.BitMode

func (*OperandPegImpl) GetMemoryInfo

func (o *OperandPegImpl) GetMemoryInfo() (*MemoryInfo, bool)

GetMemoryInfo は、最初のメモリオペランドの詳細情報を返します。見つからない場合は nil と false を返します。

func (*OperandPegImpl) ImmediateValueFitsIn8Bits

func (o *OperandPegImpl) ImmediateValueFitsIn8Bits() bool

ヘルパー関数 (isR32Type, isR16Type, isRegisterType, needsResolution) は operand_util.go に移動しました。 ImmediateValueFitsIn8Bits は、即値オペランドの値が8ビットに収まるかどうかを返します。 複数の即値がある場合は、最初の即値オペランドをチェックします。

func (*OperandPegImpl) ImmediateValueFitsInSigned8Bits

func (o *OperandPegImpl) ImmediateValueFitsInSigned8Bits() bool

ImmediateValueFitsInSigned8Bits は、即値オペランドの値が符号付き8ビット (-128 から 127) に収まるかどうかを返します。

func (*OperandPegImpl) InternalString

func (o *OperandPegImpl) InternalString() string

InternalString は最初のオペランドの文字列表現を返します。 互換性のために保持されていますが、複数のオペランドには InternalStrings を使用すべきです。

func (*OperandPegImpl) InternalStrings

func (o *OperandPegImpl) InternalStrings() []string

InternalStrings は各オペランドの文字列表現をスライスとして返します。

func (*OperandPegImpl) IsControlRegisterOperation

func (o *OperandPegImpl) IsControlRegisterOperation() bool

IsControlRegisterOperation は、オペランドに制御レジスタが含まれるかどうかを返します。

func (*OperandPegImpl) IsDirectMemory

func (o *OperandPegImpl) IsDirectMemory() bool

IsDirectMemory は、オペランドに直接メモリアドレスが含まれるかどうかを返します。 直接アドレスは [displacement] の形式と判断します。

func (*OperandPegImpl) IsIndirectMemory

func (o *OperandPegImpl) IsIndirectMemory() bool

IsIndirectMemory は、オペランドに間接メモリアドレスが含まれるかどうかを返します。 間接アドレスはレジスタを含む形式 (例: [EAX], [ESI+4]) と判断します。

func (*OperandPegImpl) IsType

func (o *OperandPegImpl) IsType(index int, targetType OperandType) bool

IsType は、指定されたインデックスのオペランドが指定されたタイプと一致するかどうかを返します。

func (*OperandPegImpl) OperandTypes

func (o *OperandPegImpl) OperandTypes() []OperandType

OperandTypes は各オペランドの型をスライスとして返します。サイズ解決ロジックを含みます。

func (*OperandPegImpl) Require66h

func (o *OperandPegImpl) Require66h() bool

Require66h はオペランドサイズプレフィックス (66h) が必要か判定します。 ビットモードとオペランドの *本来の* サイズ (依存関係解決前) の不一致をチェックします。

func (*OperandPegImpl) Require67h

func (o *OperandPegImpl) Require67h() bool

Require67h はアドレスサイズプレフィックス (67h) が必要か判定します。 ビットモードとメモリオペランドのアドレス指定の不一致をチェックします。

func (*OperandPegImpl) Serialize

func (o *OperandPegImpl) Serialize() string

Serialize はオペランドをシリアライズ可能な文字列 (カンマ区切り) として返します。

func (*OperandPegImpl) WithBitMode

func (o *OperandPegImpl) WithBitMode(mode cpu.BitMode) Operands

func (*OperandPegImpl) WithForceRelAsImm

func (o *OperandPegImpl) WithForceRelAsImm(force bool) Operands

type OperandType

type OperandType string

OperandType はオペランドの種類を表す型 (既存のものを流用または再定義) pkg/operand/operand.go からコピー&修正

const (
	CodeM    OperandType = "m"    // メモリアドレス
	CodeM8   OperandType = "m8"   // 8ビットメモリ
	CodeM16  OperandType = "m16"  // 16ビットメモリ
	CodeM32  OperandType = "m32"  // 32ビットメモリ
	CodeM64  OperandType = "m64"  // 64ビットメモリ (FPU, MMX, SSE用)
	CodeM128 OperandType = "m128" // 128ビットメモリ (SSE用)
	CodeM256 OperandType = "m256" // 256ビットメモリ (AVX用)
	CodeM512 OperandType = "m512" // 512ビットメモリ (AVX-512用)
	CodeMEM  OperandType = "mem"  // メモリアドレス (サイズは他のオペランドによって決定)

	CodeR8   OperandType = "r8"    // 8ビットレジスタ
	CodeR16  OperandType = "r16"   // 16ビットレジスタ
	CodeR32  OperandType = "r32"   // 32ビットレジスタ
	CodeR64  OperandType = "r64"   // 64ビットレジスタ
	CodeRM8  OperandType = "r/m8"  // 8ビットレジスタまたはメモリ
	CodeRM16 OperandType = "r/m16" // 16ビットレジスタまたはメモリ
	CodeRM32 OperandType = "r/m32" // 32ビットレジスタまたはメモリ
	CodeRM64 OperandType = "r/m64" // 64ビットレジスタまたはメモリ

	CodeIMM   OperandType = "imm"   // 即値 (サイズは他のオペランドによって決定)
	CodeIMM8  OperandType = "imm8"  // 8ビット即値
	CodeIMM16 OperandType = "imm16" // 16ビット即値
	CodeIMM32 OperandType = "imm32" // 32ビット即値
	CodeIMM64 OperandType = "imm64" // 64ビット即値 (MOV r64, imm64 で使用)

	CodeREL8  OperandType = "rel8"  // 8ビット相対オフセット
	CodeREL16 OperandType = "rel16" // 16ビット相対オフセット
	CodeREL32 OperandType = "rel32" // 32ビット相対オフセット

	CodePTR1616 OperandType = "ptr16:16" // 16:16 ファーポインタ
	CodePTR1632 OperandType = "ptr16:32" // 16:32 ファーポインタ

	CodeSREG OperandType = "sreg" // セグメントレジスタ (CS, DS, ES, FS, GS, SS) - 小文字に変更
	CodeCREG OperandType = "creg" // コントロールレジスタ (CR0-CR8) - 小文字に変更
	CodeDREG OperandType = "dreg" // デバッグレジスタ (DR0-DR7) - 小文字に変更
	CodeTREG OperandType = "treg" // テストレジスタ (TR3-TR7) - 小文字に変更

	CodeAL OperandType = "AL" // AL レジスタ
	CodeCL OperandType = "CL" // CL レジスタ
	CodeDL OperandType = "DL" // DL レジスタ
	CodeBL OperandType = "BL" // BL レジスタ
	CodeAH OperandType = "AH" // AH レジスタ
	CodeCH OperandType = "CH" // CH レジスタ
	CodeDH OperandType = "DH" // DH レジスタ
	CodeBH OperandType = "BH" // BH レジスタ

	CodeAX OperandType = "AX" // AX レジスタ
	CodeCX OperandType = "CX" // CX レジスタ
	CodeDX OperandType = "DX" // DX レジスタ
	CodeBX OperandType = "BX" // BX レジスタ
	CodeSP OperandType = "SP" // SP レジスタ
	CodeBP OperandType = "BP" // BP レジスタ
	CodeSI OperandType = "SI" // SI レジスタ
	CodeDI OperandType = "DI" // DI レジスタ

	CodeEAX OperandType = "EAX" // EAX レジスタ
	CodeECX OperandType = "ECX" // ECX レジスタ
	CodeEDX OperandType = "EDX" // EDX レジスタ
	CodeEBX OperandType = "EBX" // EBX レジスタ
	CodeESP OperandType = "ESP" // ESP レジスタ
	CodeEBP OperandType = "EBP" // EBP レジスタ
	CodeESI OperandType = "ESI" // ESI レジスタ
	CodeEDI OperandType = "EDI" // EDI レジスタ

	CodeRAX OperandType = "RAX" // RAX レジスタ (64ビットモード)

	CodeES OperandType = "ES" // ES セグメントレジスタ
	CodeCS OperandType = "CS" // CS セグメントレジスタ
	CodeSS OperandType = "SS" // SS セグメントレジスタ
	CodeDS OperandType = "DS" // DS セグメントレジスタ
	CodeFS OperandType = "FS" // FS セグメントレジスタ
	CodeGS OperandType = "GS" // GS セグメントレジスタ

	CodeST0 OperandType = "ST(0)" // FPU レジスタ ST(0)
	CodeSTI OperandType = "ST(i)" // FPU レジスタ ST(i)

	CodeMM   OperandType = "mm"     // MMX レジスタ
	CodeMMRM OperandType = "mm/m64" // MMX レジスタまたは64ビットメモリ

	CodeXMM   OperandType = "xmm"      // XMM レジスタ
	CodeXMMRM OperandType = "xmm/m128" // XMM レジスタまたは128ビットメモリ

	CodeYMM   OperandType = "ymm"      // YMM レジスタ
	CodeYMMRM OperandType = "ymm/m256" // YMM レジスタまたは256ビットメモリ

	CodeZMM   OperandType = "zmm"      // ZMM レジスタ
	CodeZMMRM OperandType = "zmm/m512" // ZMM レジスタまたは512ビットメモリ

	CodeBND OperandType = "bnd" // バウンドレジスタ (BND0-BND3)

	CodeKREG OperandType = "k" // マスクレジスタ (k0-k7)

	CodeMOFFS8  OperandType = "moffs8"  // メモリオフセット (8ビット)
	CodeMOFFS16 OperandType = "moffs16" // メモリオフセット (16ビット)
	CodeMOFFS32 OperandType = "moffs32" // メモリオフセット (32ビット)
	CodeMOFFS64 OperandType = "moffs64" // メモリオフセット (64ビット)

	CodeCONST1 OperandType = "1" // 定数 1

	CodeLABEL OperandType = "label" // ラベル (プレースホルダー型)

	CodeUNKNOWN OperandType = "unknown" // 不明
)

func (OperandType) IsR16Type

func (ot OperandType) IsR16Type() bool

IsR16Type は OperandType が 16 ビットレジスタを表すか判定します。

func (OperandType) IsR32Type

func (ot OperandType) IsR32Type() bool

IsR32Type は OperandType が 32 ビットレジスタを表すか判定します。

type Operands

type Operands interface {
	// InternalString は、内部表現の単一文字列を返します(主にデバッグ用)。
	InternalString() string
	// InternalStrings は、各オペランドの内部表現文字列のスライスを返します。
	InternalStrings() []string
	// OperandTypes は、各オペランドの型 (`OperandType`) のスライスを返します。
	OperandTypes() []OperandType
	// Serialize は、オペランドをシリアライズ可能な形式(通常は元の文字列)で返します。
	Serialize() string
	// FromString は、与えられた文字列から新しい Operands オブジェクトを生成します。
	FromString(text string) Operands
	// CalcOffsetByteSize は、メモリオペランドのオフセット部分のバイトサイズを計算します。
	CalcOffsetByteSize() int
	// DetectImmediateSize は、即値オペランドのサイズ(バイト単位)を検出します。
	DetectImmediateSize() int
	// WithBitMode は、指定されたビットモード (`cpu.BitMode`) を持つ新しい Operands オブジェクトを返します。
	WithBitMode(mode cpu.BitMode) Operands // 再追加
	// WithForceImm8 メソッド削除
	// WithForceRelAsImm は、相対アドレスを即値として強制的に扱うかどうかを設定した新しい Operands オブジェクトを返します。
	WithForceRelAsImm(force bool) Operands
	// GetBitMode は、現在のビットモードを返します。
	GetBitMode() cpu.BitMode // 再追加
	// Require66h は、オペランドサイズプレフィックス (0x66) が必要かどうかを返します。
	Require66h() bool // オペランドサイズプレフィックスが必要かどうか
	// Require67h は、アドレスサイズプレフィックス (0x67) が必要かどうかを返します。
	Require67h() bool // アドレスサイズプレフィックスが必要かどうか
	// IsDirectMemory は、オペランドに直接メモリアドレスが含まれるかどうかを返します。
	IsDirectMemory() bool
	// IsIndirectMemory は、オペランドに間接メモリアドレスが含まれるかどうかを返します。
	IsIndirectMemory() bool
	// GetMemoryInfo は、最初のメモリオペランドの詳細情報を返します。見つからない場合は nil と false を返します。
	GetMemoryInfo() (*MemoryInfo, bool)
	// DisplacementBytes は、最初のメモリオペランドのディスプレースメント部分をバイト列として返します。
	// ModRMがない直接アドレス指定 (moffs) の場合に利用することを想定しています。
	// メモリオペランドがない場合や、ディスプレースメントがない場合は nil を返します。
	// バイト列のサイズは BitMode に基づいて決定されます。
	DisplacementBytes() []byte
	// ImmediateValueFitsIn8Bits は、即値オペランドの値が符号なし8ビット (0-255) に収まるかどうかを返します。
	ImmediateValueFitsIn8Bits() bool
	// ImmediateValueFitsInSigned8Bits は、即値オペランドの値が符号付き8ビット (-128 から 127) に収まるかどうかを返します。
	ImmediateValueFitsInSigned8Bits() bool
	// IsControlRegisterOperation は、オペランドに制御レジスタが含まれるかどうかを返します。
	IsControlRegisterOperation() bool
	// IsType は、指定されたインデックスのオペランドが指定されたタイプと一致するかどうかを返します。
	// 汎用的なタイプチェック (例: R32, IMM, M8) に使用できます。
	IsType(index int, targetType OperandType) bool
	// CalcSibByteSize は、SIB バイトが必要な場合に 1 を、不要な場合に 0 を返します。
	CalcSibByteSize() int
}

Operands インターフェース (pkg/operand/operand.go からコピー) このインターフェースは、オペランドのセットを表します。 元のparticipleベースのパーサーから移行中のため、一部のメソッドは 新しいpigeonベースのパーサーの実装 (`OperandPegImpl`) で提供されます。

func FromString

func FromString(text string) (Operands, error)

FromString はオペランド文字列をパースし、Operands インターフェースを返します。 これは外部から呼び出される主要なコンストラクタです。 内部的に ParseOperands を呼び出します。

type Option

type Option func(*parser) Option

Option is a function that can set an option on the parser. It returns the previous setting as an Option.

func AllowInvalidUTF8

func AllowInvalidUTF8(b bool) Option

AllowInvalidUTF8 creates an Option to allow invalid UTF-8 bytes. Every invalid UTF-8 byte is treated as a utf8.RuneError (U+FFFD) by character class matchers and is matched by the any matcher. The returned matched value, c.text and c.offset are NOT affected.

The default is false.

func Debug

func Debug(b bool) Option

Debug creates an Option to set the debug flag to b. When set to true, debugging information is printed to stdout while parsing.

The default is false.

func Entrypoint

func Entrypoint(ruleName string) Option

Entrypoint creates an Option to set the rule name to use as entrypoint. The rule name must have been specified in the -alternate-entrypoints if generating the parser with the -optimize-grammar flag, otherwise it may have been optimized out. Passing an empty string sets the entrypoint to the first rule in the grammar.

The default is to start parsing at the first rule in the grammar.

func GlobalStore

func GlobalStore(key string, value any) Option

GlobalStore creates an Option to set a key to a certain value in the globalStore.

func InitState

func InitState(key string, value any) Option

InitState creates an Option to set a key to a certain value in the global "state" store.

func MaxExpressions

func MaxExpressions(maxExprCnt uint64) Option

MaxExpressions creates an Option to stop parsing after the provided number of expressions have been parsed, if the value is 0 then the parser will parse for as many steps as needed (possibly an infinite number).

The default for maxExprCnt is 0.

func Memoize

func Memoize(b bool) Option

Memoize creates an Option to set the memoize flag to b. When set to true, the parser will cache all results so each expression is evaluated only once. This guarantees linear parsing time even for pathological cases, at the expense of more memory and slower times for typical cases.

The default is false.

func Recover

func Recover(b bool) Option

Recover creates an Option to set the recover flag to b. When set to true, this causes the parser to recover from panics and convert it to an error. Setting it to false can be useful while debugging to access the full stack trace.

The default is true.

func Statistics

func Statistics(stats *Stats, choiceNoMatch string) Option

Statistics adds a user provided Stats struct to the parser to allow the user to process the results after the parsing has finished. Also the key for the "no match" counter is set.

Example usage:

input := "input"
stats := Stats{}
_, err := Parse("input-file", []byte(input), Statistics(&stats, "no match"))
if err != nil {
    log.Panicln(err)
}
b, err := json.MarshalIndent(stats.ChoiceAltCnt, "", "  ")
if err != nil {
    log.Panicln(err)
}
fmt.Println(string(b))

type ParsedOperandPeg

type ParsedOperandPeg struct {
	Type      OperandType  // オペランドの種類 (例: CodeR32, CodeM, CodeIMM8)
	Register  string       // レジスタ名 (Typeがレジスタの場合)
	Immediate int64        // 即値 (Typeが即値の場合)
	IsHex     bool         // 即値が16進数表記だったか
	Memory    *MemoryInfo  // メモリアドレス情報 (Typeがメモリの場合)
	Segment   string       // セグメントレジスタ名 (TypeがSREGの場合、またはセグメントオーバーライドがある場合)
	Label     string       // ラベル名 (TypeがLABELの場合)
	DataType  ast.DataType // データ型 (BYTE, WORD, DWORD など) - ast.DataType に変更
	JumpType  string       // ジャンプタイプ (SHORT, NEAR, FAR) - ラベルオペランド用
	PtrPrefix string       // PTR または FAR PTR プレフィックス (例: "WORD PTR")
	RawString string       // パース前の元のオペランド文字列
}

ParsedOperandPeg は、PEGパーサーによってパースされた単一のオペランド情報を格納する構造体です。

func ParseOperandString

func ParseOperandString(text string) (*ParsedOperandPeg, error)

ParseOperandString は単一のオペランド文字列をパースします。 例: "EAX", "[EBX+100]", "BYTE [ESI]", "123", "0xFF", "'A'", "my_label"

func ParseOperands

func ParseOperands(text string, bitMode cpu.BitMode, forceRelAsImm bool) ([]*ParsedOperandPeg, error)

ParseOperands はカンマ区切りのオペランド文字列全体をパースします。 例: "EAX, EBX", "AL, [SI]", "label, 0x10" TODO: BitMode, ForceRelAsImm をパース処理に反映させる必要があります (現在は引数で受け取るのみ)。 戻り値を []*ParsedOperandPeg に変更しました。

type Stats

type Stats struct {
	// ExprCnt counts the number of expressions processed during parsing
	// This value is compared to the maximum number of expressions allowed
	// (set by the MaxExpressions option).
	ExprCnt uint64

	// ChoiceAltCnt is used to count for each ordered choice expression,
	// which alternative is used how may times.
	// These numbers allow to optimize the order of the ordered choice expression
	// to increase the performance of the parser
	//
	// The outer key of ChoiceAltCnt is composed of the name of the rule as well
	// as the line and the column of the ordered choice.
	// The inner key of ChoiceAltCnt is the number (one-based) of the matching alternative.
	// For each alternative the number of matches are counted. If an ordered choice does not
	// match, a special counter is incremented. The name of this counter is set with
	// the parser option Statistics.
	// For an alternative to be included in ChoiceAltCnt, it has to match at least once.
	ChoiceAltCnt map[string]map[string]int
}

Stats stores some statistics, gathered during parsing

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL