import { R2Shell } from "./shell.js"; import { R2PipeSync } from "./r2pipe.js"; export type InstructionType = "mov" | "jmp" | "cmp" | "nop" | "call" | "add" | "sub"; export type InstructionFamily = "cpu" | "fpu" | "priv"; export type GraphFormat = "dot" | "json" | "mermaid" | "ascii"; export type Permission = "---" | "r--" | "rw-" | "rwx" | "r-x" | "-wx" | "--x"; export type R2Papi = R2PapiSync; export interface SearchResult { offset: number; type: string; data: string; } export interface DebugModule { base: string; name: string; path: string; size: number; } export interface Flag { name: string; size: number; offset: number; } export type PluginFamily = "anal" | "arch" | "bin" | "core" | "crypto" | "debug" | "egg" | "esil" | "fs" | "io" | "lang"; export interface ThreadContext { context: any; id: number; state: string; selected: boolean; } export interface CallRef { addr: number; type: string; at: number; } export interface FunctionDetails { offset: number; name: string; size: number; noreturn: boolean; stackframe: number; ebbs: number; signature: string; nbbs: number; callrefs: CallRef[]; codexrefs: CallRef[]; } export interface BinFile { arch: string; static: boolean; va: boolean; stripped: boolean; pic: boolean; relocs: boolean; sanitize: boolean; baddr: number; binsz: number; bintype: string; bits: number; canary: boolean; class: string; compiler: string; endian: string; machine: string; nx: boolean; os: string; laddr: number; linenum: boolean; havecode: boolean; intrp: string; } export interface Reference { from: number; type: string; perm: string; opcode: string; fcn_addr: number; fcn_name: string; realname: string; refname: string; } export interface BasicBlock { addr: number; size: number; jump: number; fail: number; opaddr: number; inputs: number; outputs: number; ninstr: number; instrs: number[]; traced: boolean; } export declare class ThreadClass { api: any; constructor(r2: any); backtrace(): string; sleep(seconds: number): string; } export interface Instruction { type: InstructionType; addr: number; opcode: string; pseudo: string; mnemonic: string; sign: boolean; family: InstructionFamily; description: string; esil: string; opex: any; size: number; ptr: number; bytes: string; id: number; refptr: number; direction: "read" | "write"; stackptr: number; stack: string; } export declare class ModuleClass { api: any; constructor(r2: R2PipeSync); fileName(): string; name(): string; findBaseAddress(): string; getBaseAddress(name: string): string; getExportByName(name: string): NativePointer; findExportByName(name: string): NativePointer; enumerateExports(): any; enumerateImports(): any; enumerateSymbols(): any; enumerateEntrypoints(): any; enumerateRanges(): any; } export declare class ProcessClass { r2: any; constructor(r2: R2PipeSync); enumerateMallocRanges(): void; enumerateSystemRanges(): void; enumerateRanges(): void; enumerateThreads(): any; enumerateModules(): any; getModuleByAddress(addr: NativePointer | number | string): any; getModuleByName(moduleName: string): any; codeSigningPolicy(): string; getTmpDir(): any; getHomeDir(): any; platform(): any; getCurrentDir(): any; getCurrentThreadId(): number; pageSize(): number; isDebuggerAttached(): boolean; setExceptionHandler(): void; id(): any; pointerSize(): number; } /** * Assembler and disassembler facilities to decode and encode instructions * * @typedef Assembler */ export declare class Assembler { program: string; labels: any; endian: boolean; pc: NativePointer; r2: R2PipeSync; constructor(myr2?: R2PipeSync); /** * Change the address of the program counter, some instructions need to know where * are they located before being encoded or decoded. * * @param {NativePointerValue} */ setProgramCounter(pc: NativePointer): void; setEndian(big: boolean): void; toString(): string; append(x: string): void; label(s: string): NativePointer; /** * Encode (assemble) an instruction by taking the string representation. * * @param {string} the string representation of the instruction to assemble * @returns {string} the hexpairs that represent the assembled instruciton */ encode(s: string): string; /** * Decode (disassemble) an instruction by taking the hexpairs string as input. * TODO: should take an array of bytes too * * @param {string} the hexadecimal pairs of bytes to decode as an instruction * @returns {string} the mnemonic and operands of the resulting decoding */ decode(s: string): string; } /** * High level abstraction on top of the r2 command interface provided by r2pipe. * * @typedef R2Papi */ export declare class R2PapiSync { /** * Keep a reference r2pipe instance * * @type {R2PipeSync} */ r2: R2PipeSync; /** * Create a new instance of the R2Papi class, taking an r2pipe interface as reference. * * @param {R2PipeSync} the r2pipe instance to use as backend. * @returns {R2Papi} instance */ constructor(r2: R2PipeSync); toString(): string; toJSON(): string; /** * Get the base address used by the current loaded binary * * @returns {NativePointer} address of the base of the binary */ getBaseAddress(): NativePointer; jsonToTypescript(name: string, a: any): string; /** * Get the general purpose register size of the targize architecture in bits * * @returns {number} the regsize */ getBits(): number; /** * Get the name of the arch plugin selected, which tends to be the same target architecture. * Note that on some situations, this info will be stored protected bby the AirForce. * When using the r2ghidra arch plugin the underlying arch is in `asm.cpu`: * * @returns {string} the name of the target architecture. */ getArch(): string; callTrim(x: string): string; cmdTrim(x: string): string; /** * Get the name of the selected CPU for the current selected architecture. * * @returns {string} the value of asm.cpu */ getCpu(): string; setArch(arch: string, bits: number | undefined): void; setFlagSpace(name: string): void; demangleSymbol(lang: string, mangledName: string): string; setLogLevel(level: number): void; /** * should return the id for the new map using the given file descriptor */ newMap(fd: number, vaddr: NativePointer, size: number, paddr: NativePointer, perm: Permission, name?: string): void; at(a: string): NativePointer; getShell(): R2Shell; version(): string; platform(): string; arch(): string; bits(): string; id(): number; printAt(msg: string, x: number, y: number): void; clearScreen(): R2Papi; getConfig(key: string): Error | string; setConfig(key: string, val: string): R2Papi; getRegisterStateForEsil(): string; getRegisters(): any; resizeFile(newSize: number): R2Papi; insertNullBytes(newSize: number, at?: NativePointer | number | string): R2Papi; removeBytes(newSize: number, at?: NativePointer | number | string): R2Papi; seek(addr: number): R2Papi; currentSeek(): NativePointer; seekToRelativeOpcode(nth: number): NativePointer; getBlockSize(): number; setBlockSize(a: number): R2Papi; countFlags(): number; countFunctions(): number; analyzeFunctionsWithEsil(depth?: number): void; analyzeProgramWithEsil(depth?: number): void; analyzeProgram(depth?: number): this; enumerateThreads(): ThreadContext[]; currentThreadId(): number; setRegisters(obj: any): void; hex(s: number | string): string; step(): R2Papi; stepOver(): R2Papi; math(expr: number | string): number; stepUntil(dst: NativePointer | string | number): void; enumerateXrefsTo(s: string): string[]; findXrefsTo(s: string, use_esil: boolean): void; analyzeFunctionsFromCalls(): R2Papi; autonameAllFunctions(): R2Papi; analyzeFunctionsWithPreludes(): R2Papi; analyzeObjCReferences(): R2Papi; analyzeImports(): R2Papi; searchDisasm(s: string): SearchResult[]; searchString(s: string): SearchResult[]; searchBytes(data: number[]): SearchResult[]; binInfo(): BinFile; selectBinary(id: number): void; openFile(name: string): number | Error; openFileNomap(name: string): number | Error; currentFile(name: string): string; enumeratePlugins(type: PluginFamily): any; enumerateModules(): DebugModule[]; enumerateFiles(): any; enumerateBinaries(): any; enumerateMaps(): any; enumerateClasses(): any; enumerateSymbols(): any; enumerateExports(): any; enumerateImports(): any; enumerateLibraries(): string[]; enumerateSections(): any; enumerateSegments(): any; enumerateEntrypoints(): any; enumerateRelocations(): any; enumerateFunctions(): FunctionDetails[]; enumerateFlags(): Flag[]; skip(): void; ptr(s: string | number): NativePointer; call(s: string): string; callj(s: string): any; cmd(s: string): string; cmdj(s: string): any; log(s: string): void; clippy(msg: string): void; ascii(msg: string): void; } export declare class NativeFunction { constructor(); } export declare class NativeCallback { constructor(); } /** * Global function that returns a new instance of a NativePointer. * Saves some typing: `ptr(0)` is the same as `new NativePointer(0)` * * @type function */ export declare function ptr(v: NativePointerValue): NativePointer; /** * A NativePointer can be described using a string that contains a number in any base (hexadecimal and decimal are the most common formats used) * But it actually supports anything else that could be handled by radare2. You can use symbol names, math operations or special symbols like `$$`. * * @type NativePointerValue */ export type NativePointerValue = string | number | NativePointer; /** * Class providing a way to work with 64bit pointers from Javascript, this API mimics the same * well-known promitive available in Frida, but it's baked by the current session of r2. * * It is also possible to use this class via the global `ptr` function. * * @typedef NativePointer */ export declare class NativePointer { addr: string; api: R2Papi; constructor(s: NativePointerValue, api?: R2Papi); /** * Filter a string to be used as a valid flag name * * @param {string} name of the symbol name * @returns {string} filtered name to be used as a flag */ filterFlag(name: string): string; /** * Set a flag (name) at the offset pointed * * @param {string} name of the flag to set * @returns {string} base64 decoded string */ setFlag(name: string): void; /** * Remove the flag in the current offset * */ unsetFlag(): void; /** * Render an hexadecimal dump of the bytes contained in the range starting * in the current pointer and given length. * * @param {number} length optional amount of bytes to dump, using blocksize * @returns {string} string containing the hexadecimal dump of memory */ hexdump(length?: number): string; functionGraph(format?: GraphFormat): string; readByteArray(len: number): number[]; readHexString(len: number): string; and(a: number): NativePointer; or(a: number): NativePointer; add(a: number): NativePointer; sub(a: number): NativePointer; writeByteArray(data: number[]): NativePointer; writeAssembly(instruction: string): NativePointer; writeCString(s: string): NativePointer; writeWideString(s: string): NativePointer; /** * Check if it's a pointer to the address zero. Also known as null pointer. * * @returns {boolean} true if null */ isNull(): boolean; /** * Compare current pointer with the passed one, and return -1, 0 or 1. * * * if (this < arg) return -1; * * if (this > arg) return 1; * * if (this == arg) return 0; * * @returns {number} returns -1, 0 or 1 depending on the comparison of the pointers */ compare(a: NativePointerValue): number; /** * Check if it's a pointer to the address zero. Also known as null pointer. * * @returns {boolean} true if null */ pointsToNull(): boolean; toJSON(): string; toString(): string; toNumber(): number; writePointer(p: NativePointer): void; readRelativePointer(): NativePointer; readPointer(): NativePointer; readS8(): number; readU8(): number; readU16(): number; readU16le(): number; readU16be(): number; readS16(): number; readS16le(): number; readS16be(): number; readS32(): number; readU32(): number; readU32le(): number; readU32be(): number; readU64(): number; readU64le(): number; readU64be(): number; writeInt(n: number): boolean; /** * Write a byte in the current offset, the value must be between 0 and 255 * * @param {string} n number to write in the pointed byte in the current address * @returns {boolean} false if the operation failed */ writeU8(n: number): boolean; writeU16(n: number): boolean; writeU16be(n: number): boolean; writeU16le(n: number): boolean; writeU32(n: number): boolean; writeU32be(n: number): boolean; writeU32le(n: number): boolean; writeU64(n: number): boolean; writeU64be(n: number): boolean; writeU64le(n: number): boolean; readInt32(): number; readCString(): string; readWideString(): string; readPascalString(): string; instruction(): Instruction; disassemble(length?: number): string; analyzeFunction(): NativePointer; analyzeFunctionRecursively(): NativePointer; name(): string; methodName(): string; symbolName(): string; getFunction(): FunctionDetails; basicBlock(): BasicBlock; functionBasicBlocks(): BasicBlock[]; xrefs(): Reference[]; } /** * Global instance of R2Papi based on the current session of radare2. * Note that `r2` is the global instance of `r2pipe` used by `R`. * * @type R2Papi */ export declare const R: R2Papi; /** * Global instance of the Module class based on the current radare2 session. * This variable mimics the same APIs shipped by Frida. * * @type ModuleClass */ export declare const Module: ModuleClass; /** * Global instance of the Process class based on the current radare2 session. * This variable mimics the same APIs shipped by Frida. * * @type ProcessClass */ export declare const Process: ProcessClass; /** * Global instance of the Thread class based on the current radare2 session. * This variable mimics the same APIs shipped by Frida. * * @type ThreadClass */ export declare const Thread: ThreadClass;