Difference between revisions of "Lua:AOBScan"
m |
Mr millchick (talk | contribs) m (fixed formatting, restored accidentally deleted references) |
||
| (One intermediate revision by the same user not shown) | |||
| Line 4: | Line 4: | ||
'''function''' AOBScan(''AOBString'', ''ProtectionFlags'' OPTIONAL, ''AlignmentType'' OPTIONAL, ''AlignmentParam'' HALFOPTIONAL) | '''function''' AOBScan(''AOBString'', ''ProtectionFlags'' OPTIONAL, ''AlignmentType'' OPTIONAL, ''AlignmentParam'' HALFOPTIONAL) | ||
| − | Scans the currently opened process and returns a [[Lua:Class:Stringlist|StringList]] object containing all the | + | Scans the currently opened process memory for a byte pattern (Array of Bytes) and returns a [[Lua:Class:Stringlist|StringList]] object containing all matching addresses as hexadecimal strings. |
| − | + | ||
| − | + | * '''Returns:''' A [[Lua:Class:Stringlist|StringList]] containing the addresses found, or '''nil''' if no matches are found. | |
| + | * '''Important:''' Always call '''list.destroy()''' when done to free memory and prevent leaks. | ||
| + | |||
| + | === Two Calling Modes === | ||
| + | |||
| + | '''Mode 1: Pattern String''' - Provide an AOB pattern as a hex string with optional wildcards | ||
| + | AOBScan(AOBString, ProtectionFlags, AlignmentType, AlignmentParam) | ||
| + | |||
| + | '''Mode 2: Varargs Bytes''' - Pass individual byte values as separate arguments | ||
| + | AOBScan(byte1, byte2, byte3, ...) | ||
| + | |||
| + | In varargs mode: | ||
| + | * Values 0-255 are treated as literal bytes | ||
| + | * '''nil''', non-numeric values, or values > 255 become wildcards | ||
| + | * Zero (0) is written as "00" if it's a number, or as a wildcard if nil/non-numeric | ||
=== Function Parameters === | === Function Parameters === | ||
| − | + | ==== Mode 1: Pattern String ==== | |
| − | |||
| − | |||
| − | |||
| − | |||
| − | |||
| − | |||
| − | |||
| − | |||
| − | |||
{|width="85%" cellpadding="10%" cellpadding="5%" cellspacing="0" border="0" | {|width="85%" cellpadding="10%" cellpadding="5%" cellspacing="0" border="0" | ||
| Line 29: | Line 34: | ||
|AOBString | |AOBString | ||
|string | |string | ||
| − | |A | + | |A hex byte pattern with space/comma/dash separators. Use '''??''' or '''*''' for full-byte wildcards. Supports nibble wildcards like '''7?''' or '''?A''' |
|- | |- | ||
|ProtectionFlags | |ProtectionFlags | ||
|string | |string | ||
| − | | | + | |'''Optional.''' Memory protection filter (see below). Default: "" (scan all memory) |
|- | |- | ||
|AlignmentType | |AlignmentType | ||
|integer | |integer | ||
| − | | | + | |'''Optional.''' Alignment mode: 0=None, 1=Divisible, 2=Last digits. Default: 0 |
|- | |- | ||
|AlignmentParam | |AlignmentParam | ||
|string | |string | ||
| − | | | + | |'''Optional.''' Hex value for alignment checking. Default: "1" |
| + | |} | ||
| + | |||
| + | ==== Mode 2: Varargs Bytes ==== | ||
| + | |||
| + | {|width="85%" cellpadding="10%" cellpadding="5%" cellspacing="0" border="0" | ||
| + | !align="left"|Parameter | ||
| + | !align="left"|Type | ||
| + | !style="width: 80%;" align="left"|Description | ||
| + | |- | ||
| + | |... | ||
| + | |'''varargs''' | ||
| + | |Individual byte values (0-255). Use '''nil''' or values > 255 for wildcards | ||
|} | |} | ||
| − | + | === Protection Flags === | |
| − | * | + | |
| − | * | + | The '''''ProtectionFlags''''' parameter is a string that filters which memory regions to scan based on their protection attributes: |
| − | * | + | |
| − | * | + | '''Syntax:''' Prefix each flag with: |
| − | Examples: | + | * '''+''' = Region MUST have this flag set |
| − | +W-C | + | * '''-''' = Region MUST NOT have this flag set |
| − | +X-C | + | * '''*''' = Don't care (default) |
| − | +W | + | |
| − | "" = | + | '''Flags:''' |
| + | * '''X''' = Executable | ||
| + | * '''W''' = Writable | ||
| + | * '''C''' = Copy On Write | ||
| + | * '''D''' = Dirty (macOS only) | ||
| + | |||
| + | '''Examples:''' | ||
| + | "+W-C" Writable memory excluding copy-on-write (don't care about executable) | ||
| + | "+X-W-C" Readonly executable memory (code sections) | ||
| + | "+X" All executable memory (typical for code scanning) | ||
| + | "-W" Non-writable memory only | ||
| + | "" Scan everything (equivalent to "*X*W*C") | ||
| + | "*X*W*C" Explicitly scan everything (don't care about any flags) | ||
| + | |||
| + | |||
| + | === Alignment Parameters === | ||
| + | |||
| + | Use '''''AlignmentType''''' and '''''AlignmentParam''''' to constrain addresses and improve scan performance: | ||
| + | |||
| + | '''AlignmentType values:''' | ||
| + | * '''0''' = fsmNotAligned - No alignment check (default) | ||
| + | * '''1''' = fsmAligned - Address must be divisible by AlignmentParam | ||
| + | * '''2''' = fsmLastDigits - Address must end with specific hex digits | ||
| + | |||
| + | '''AlignmentParam:''' | ||
| + | * Interpreted as a '''hexadecimal''' value | ||
| + | * For '''AlignmentType=1''': Alignment boundary (e.g., "10" = 16-byte aligned, "4" = 4-byte aligned) | ||
| + | * For '''AlignmentType=2''': Required ending hex digits (e.g., "00" = addresses ending in ...00, "F0" = ending in ...F0) | ||
| + | |||
| + | '''Examples:''' | ||
| + | AlignmentType=1, AlignmentParam="10" Only 16-byte aligned addresses (0x...0, 0x...10, 0x...20, etc.) | ||
| + | AlignmentType=1, AlignmentParam="4" Only 4-byte aligned addresses | ||
| + | AlignmentType=2, AlignmentParam="00" Only addresses ending with 00 (0x...00) | ||
| + | AlignmentType=2, AlignmentParam="F0" Only addresses ending with F0 (0x...F0) | ||
| + | |||
| + | |||
| + | === Wildcard Syntax === | ||
| + | |||
| + | '''Full-byte wildcards:''' Match any byte value | ||
| + | * '''??''' - Most common notation | ||
| + | * '''*''' - Alternative notation | ||
| + | * Any non-hex characters in a byte position | ||
| + | |||
| + | '''Nibble wildcards:''' Match specific half-byte (4 bits) | ||
| + | * '''7?''' - High nibble is 7, low nibble can be anything (matches 70-7F) | ||
| + | * '''?A''' - High nibble can be anything, low nibble is A (matches 0A, 1A, 2A, ..., FA) | ||
| + | |||
| + | '''Examples:''' | ||
| + | "48 8B ?? ?? ?? 89" Full wildcards for bytes 3-5 | ||
| + | "DE AD ?? EF" Wildcard for byte 3 | ||
| + | "7? A? ?3" Nibble wildcards: 7x, Ax, x3 | ||
| + | |||
| + | |||
| + | === Usage Examples === | ||
| + | |||
| + | '''Basic scan - find all matches:''' | ||
| + | local results = AOBScan("48 8B 05 ?? ?? ?? 89") | ||
| + | if results then | ||
| + | print("Found " .. results.Count .. " matches") | ||
| + | for i = 0, results.Count - 1 do | ||
| + | print(string.format("%X", results[i])) | ||
| + | end | ||
| + | results.destroy() | ||
| + | else | ||
| + | print("Pattern not found") | ||
| + | end | ||
| + | |||
| + | '''Scan executable memory only (faster for code patterns):''' | ||
| + | local results = AOBScan("55 8B EC", "+X") | ||
| + | if results then | ||
| + | print("First match: " .. results[0]) | ||
| + | results.destroy() | ||
| + | end | ||
| + | |||
| + | '''Scan with alignment (16-byte aligned addresses):''' | ||
| + | local results = AOBScan("FF 15 ?? ?? ?? ??", "+X", 1, "10") | ||
| + | if results then | ||
| + | results.destroy() | ||
| + | end | ||
| + | |||
| + | '''Scan for addresses ending in 00:''' | ||
| + | local results = AOBScan("DE AD BE EF", "", 2, "00") | ||
| + | if results then | ||
| + | results.destroy() | ||
| + | end | ||
| + | '''Varargs mode with wildcards:''' | ||
| + | local results = AOBScan(0x48, 0x8B, nil, nil, nil, 0x89) -- nil = wildcard | ||
| + | if results then | ||
| + | results.destroy() | ||
| + | end | ||
| − | + | '''Helper function to get first match:''' | |
| − | * | + | function findAOB(pattern, flags) |
| − | ** | + | local results = AOBScan(pattern, flags or "+X") |
| − | ** | + | if results and results.Count > 0 then |
| + | local addr = results[0] | ||
| + | results.destroy() | ||
| + | return addr | ||
| + | end | ||
| + | return nil | ||
| + | end | ||
| + | |||
| + | local address = findAOB("48 8B ?? ?? ?? 89") | ||
| + | if address then | ||
| + | print("Found at: " .. address) | ||
| + | end | ||
| + | |||
| + | |||
| + | === Performance Tips === | ||
| + | |||
| + | * Use '''+X''' protection flag when scanning for code to dramatically reduce scan time | ||
| + | * Use alignment when you know the address characteristics (e.g., function pointers are often aligned) | ||
| + | * Keep patterns as specific as possible - avoid excessive wildcards | ||
| + | * For single-result scans, consider using '''AOBScanUnique''' or module-specific variants | ||
| + | * Always destroy the StringList after use to prevent memory leaks | ||
| + | |||
| + | |||
| + | === Return Value === | ||
| + | |||
| + | * '''Success:''' Returns a [[Lua:Class:Stringlist|StringList]] object containing hex address strings | ||
| + | * '''Failure:''' Returns '''nil''' (no matches found or invalid pattern) | ||
| + | |||
| + | '''Note:''' The returned addresses are strings in hexadecimal format (e.g., "7FF12340"). Convert with tonumber(addr, 16) if you need numeric values. | ||
| Line 66: | Line 200: | ||
=== Related Functions === | === Related Functions === | ||
| + | |||
| + | * [[Lua:AOBScanUnique|AOBScanUnique]] - Returns a single address or nil (no cleanup needed) | ||
| + | * [[Lua:AOBScanModuleUnique|AOBScanModuleUnique]] - Find unique pattern in a module | ||
| + | |||
* [[Lua:autoAssemble|autoAssemble]] | * [[Lua:autoAssemble|autoAssemble]] | ||
* [[Lua:disassemble|disassemble]] | * [[Lua:disassemble|disassemble]] | ||
| Line 93: | Line 231: | ||
* [[Lua:byteTableToString|byteTableToString]] | * [[Lua:byteTableToString|byteTableToString]] | ||
* [[Lua:byteTableToWideString|byteTableToWideString]] | * [[Lua:byteTableToWideString|byteTableToWideString]] | ||
| + | |||
| + | === Readonly Classes === | ||
| + | * [[Lua:Class:Stringlist|StringList]] - String list object documentation | ||
Latest revision as of 04:12, 21 October 2025
function AOBScan(...)
function AOBScan(AOBString, ProtectionFlags OPTIONAL, AlignmentType OPTIONAL, AlignmentParam HALFOPTIONAL)
Scans the currently opened process memory for a byte pattern (Array of Bytes) and returns a StringList object containing all matching addresses as hexadecimal strings.
- Returns: A StringList containing the addresses found, or nil if no matches are found.
- Important: Always call list.destroy() when done to free memory and prevent leaks.
Contents
Two Calling Modes[edit]
Mode 1: Pattern String - Provide an AOB pattern as a hex string with optional wildcards
AOBScan(AOBString, ProtectionFlags, AlignmentType, AlignmentParam)
Mode 2: Varargs Bytes - Pass individual byte values as separate arguments
AOBScan(byte1, byte2, byte3, ...)
In varargs mode:
- Values 0-255 are treated as literal bytes
- nil, non-numeric values, or values > 255 become wildcards
- Zero (0) is written as "00" if it's a number, or as a wildcard if nil/non-numeric
Function Parameters[edit]
Mode 1: Pattern String[edit]
| Parameter | Type | Description |
|---|---|---|
| AOBString | string | A hex byte pattern with space/comma/dash separators. Use ?? or * for full-byte wildcards. Supports nibble wildcards like 7? or ?A |
| ProtectionFlags | string | Optional. Memory protection filter (see below). Default: "" (scan all memory) |
| AlignmentType | integer | Optional. Alignment mode: 0=None, 1=Divisible, 2=Last digits. Default: 0 |
| AlignmentParam | string | Optional. Hex value for alignment checking. Default: "1" |
Mode 2: Varargs Bytes[edit]
| Parameter | Type | Description |
|---|---|---|
| ... | varargs | Individual byte values (0-255). Use nil or values > 255 for wildcards |
Protection Flags[edit]
The ProtectionFlags parameter is a string that filters which memory regions to scan based on their protection attributes:
Syntax: Prefix each flag with:
- + = Region MUST have this flag set
- - = Region MUST NOT have this flag set
- * = Don't care (default)
Flags:
- X = Executable
- W = Writable
- C = Copy On Write
- D = Dirty (macOS only)
Examples:
"+W-C" Writable memory excluding copy-on-write (don't care about executable) "+X-W-C" Readonly executable memory (code sections) "+X" All executable memory (typical for code scanning) "-W" Non-writable memory only "" Scan everything (equivalent to "*X*W*C") "*X*W*C" Explicitly scan everything (don't care about any flags)
Alignment Parameters[edit]
Use AlignmentType and AlignmentParam to constrain addresses and improve scan performance:
AlignmentType values:
- 0 = fsmNotAligned - No alignment check (default)
- 1 = fsmAligned - Address must be divisible by AlignmentParam
- 2 = fsmLastDigits - Address must end with specific hex digits
AlignmentParam:
- Interpreted as a hexadecimal value
- For AlignmentType=1: Alignment boundary (e.g., "10" = 16-byte aligned, "4" = 4-byte aligned)
- For AlignmentType=2: Required ending hex digits (e.g., "00" = addresses ending in ...00, "F0" = ending in ...F0)
Examples:
AlignmentType=1, AlignmentParam="10" Only 16-byte aligned addresses (0x...0, 0x...10, 0x...20, etc.) AlignmentType=1, AlignmentParam="4" Only 4-byte aligned addresses AlignmentType=2, AlignmentParam="00" Only addresses ending with 00 (0x...00) AlignmentType=2, AlignmentParam="F0" Only addresses ending with F0 (0x...F0)
Wildcard Syntax[edit]
Full-byte wildcards: Match any byte value
- ?? - Most common notation
- * - Alternative notation
- Any non-hex characters in a byte position
Nibble wildcards: Match specific half-byte (4 bits)
- 7? - High nibble is 7, low nibble can be anything (matches 70-7F)
- ?A - High nibble can be anything, low nibble is A (matches 0A, 1A, 2A, ..., FA)
Examples:
"48 8B ?? ?? ?? 89" Full wildcards for bytes 3-5 "DE AD ?? EF" Wildcard for byte 3 "7? A? ?3" Nibble wildcards: 7x, Ax, x3
Usage Examples[edit]
Basic scan - find all matches:
local results = AOBScan("48 8B 05 ?? ?? ?? 89")
if results then
print("Found " .. results.Count .. " matches")
for i = 0, results.Count - 1 do
print(string.format("%X", results[i]))
end
results.destroy()
else
print("Pattern not found")
end
Scan executable memory only (faster for code patterns):
local results = AOBScan("55 8B EC", "+X")
if results then
print("First match: " .. results[0])
results.destroy()
end
Scan with alignment (16-byte aligned addresses):
local results = AOBScan("FF 15 ?? ?? ?? ??", "+X", 1, "10")
if results then
results.destroy()
end
Scan for addresses ending in 00:
local results = AOBScan("DE AD BE EF", "", 2, "00")
if results then
results.destroy()
end
Varargs mode with wildcards:
local results = AOBScan(0x48, 0x8B, nil, nil, nil, 0x89) -- nil = wildcard if results then results.destroy() end
Helper function to get first match:
function findAOB(pattern, flags)
local results = AOBScan(pattern, flags or "+X")
if results and results.Count > 0 then
local addr = results[0]
results.destroy()
return addr
end
return nil
end
local address = findAOB("48 8B ?? ?? ?? 89")
if address then
print("Found at: " .. address)
end
Performance Tips[edit]
- Use +X protection flag when scanning for code to dramatically reduce scan time
- Use alignment when you know the address characteristics (e.g., function pointers are often aligned)
- Keep patterns as specific as possible - avoid excessive wildcards
- For single-result scans, consider using AOBScanUnique or module-specific variants
- Always destroy the StringList after use to prevent memory leaks
Return Value[edit]
- Success: Returns a StringList object containing hex address strings
- Failure: Returns nil (no matches found or invalid pattern)
Note: The returned addresses are strings in hexadecimal format (e.g., "7FF12340"). Convert with tonumber(addr, 16) if you need numeric values.
See also[edit]
Related Functions[edit]
- AOBScanUnique - Returns a single address or nil (no cleanup needed)
- AOBScanModuleUnique - Find unique pattern in a module
- autoAssemble
- disassemble
- getInstructionSize
- getPreviousOpcode
- allocateSharedMemory
- mapMemory
- unmapMemory
- readBytes
- readPointer
- writeBytes
- readBytesLocal
- readPointerLocal
- writeBytesLocal
- wordToByteTable
- dwordToByteTable
- qwordToByteTable
- floatToByteTable
- doubleToByteTable
- stringToByteTable
- wideStringToByteTable
- byteTableToWord
- byteTableToDword
- byteTableToQword
- byteTableToFloat
- byteTableToDouble
- byteTableToString
- byteTableToWideString
Readonly Classes[edit]
- StringList - String list object documentation