Skip to content

Commit

Permalink
Merge branch 'pe-symbols-have-no-type' into 'main'
Browse files Browse the repository at this point in the history
Fix symbol assignment for PE exported functions

See merge request rewriting/ddisasm!1174
  • Loading branch information
aeflores committed Dec 11, 2023
2 parents d9cbd1a + 3b025f1 commit 93ac51e
Show file tree
Hide file tree
Showing 4 changed files with 53 additions and 5 deletions.
2 changes: 2 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,8 @@
* `$t` symbols in ARM binaries now force creation of Thumb-mode code blocks.
* In PE binaries, duplicate imports no longer create duplicate symbols.
* Added pattern to match missed symbolic data in pointer arrays.
* Fix symbols associated to functions (Auxdata functionNames) for PE binaries
when Ddisasm is run with option `-F`.
* Requires gtirb >=1.12.1, gtirb-pprinter >=2.0.0

# 1.7.0
Expand Down
3 changes: 1 addition & 2 deletions examples/ex_ml_sym_mangling/Makefile.windows
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
CC=
CC=cl
CFLAGS=
EXEC=

Expand All @@ -16,7 +16,6 @@ clean:
rm -f ex *.dll out.txt *.s *.lib *.exp *.o *.err *.obj *.exe

check:
$(CC) ex.c foo.lib baz.lib
@ ex > check.txt
@ FC out.txt check.txt && echo TEST OK

Expand Down
19 changes: 16 additions & 3 deletions src/datalog/symbols.dl
Original file line number Diff line number Diff line change
Expand Up @@ -203,13 +203,26 @@ elf_avoid_symbols("__TMC_END__").
// and no pre-existing function symbols.

best_func_symbol(EA,SymbolName):-
symbol_score(EA,SymbolName,"FUNC","Beg",Score),
Score = max S: {symbol_score(EA,_,"FUNC","Beg",S)}.
binary_format("ELF"),
symbol_score(EA,SymbolName,"FUNC","Beg",Score),
Score = max S: {symbol_score(EA,_,"FUNC","Beg",S)}.

// For non-ELF (e.g. PE), symbols might not have a type
best_func_symbol(EA,SymbolName):-
!binary_format("ELF"),
symbol_score(EA,SymbolName,_,"Beg",Score),
Score = max S: {symbol_score(EA,_,_,"Beg",S)}.

inferred_symbol(EA,SymbolName,Scope,"DEFAULT","FUNC","Beg"),
best_func_symbol(EA,SymbolName):-
function_inference.function_entry(EA),
!symbol_score(EA,_,"FUNC","Beg",_),
(
binary_format("ELF"),
!symbol_score(EA,_,"FUNC","Beg",_)
;
!binary_format("ELF"),
!symbol_score(EA,_,_,"Beg",_)
),
SymbolName = cat("FUN_",@to_string_hex(EA)),
(
binary_isa("MIPS"), Scope = "GLOBAL";
Expand Down
34 changes: 34 additions & 0 deletions tests/misc_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -627,6 +627,40 @@ def test_symbol_selection(self):
self.assertIn("fun", fun_names)
self.assertNotIn("_fun", fun_names)

@unittest.skipUnless(
platform.system() == "Windows", "This test is Windows only"
)
def test_pe_function_symbol_selection(self):
"""
Test that function names are correctly selected
in PE binaries.
"""
library = "baz.dll"
with cd(ex_dir / "ex_ml_sym_mangling"):
proc = subprocess.run(make("clean"), stdout=subprocess.DEVNULL)
self.assertEqual(proc.returncode, 0)
proc = subprocess.run(make("all"), stdout=subprocess.DEVNULL)
self.assertEqual(proc.returncode, 0)
for extra_args in ([], ["-F"]):
with self.subTest(extra_args=extra_args):
self.assertTrue(
disassemble(
library, format="--ir", extra_args=extra_args
)[0]
)

ir_library = gtirb.IR.load_protobuf(library + ".gtirb")
m = ir_library.modules[0]

# check chosen function names
fun_names = {
sym.name
for sym in m.aux_data["functionNames"].data.values()
}
self.assertIn("Baz", fun_names)
self.assertIn("_Baz", fun_names)
self.assertIn("__Baz", fun_names)

@unittest.skipUnless(
platform.system() == "Linux", "This test is linux only."
)
Expand Down

0 comments on commit 93ac51e

Please sign in to comment.