Ensure a crashing FDE still generates other FDEs
This commit is contained in:
parent
d7c1aaa6b5
commit
719fa27f99
5 changed files with 131 additions and 13 deletions
|
@ -1,7 +1,9 @@
|
|||
open Std
|
||||
|
||||
let main outfile proj =
|
||||
let pre_dwarf = Simplest.of_proj proj in
|
||||
let pre_dwarf = proj
|
||||
|> Simplest.of_proj
|
||||
|> Simplest.clean_lost_track_subs in
|
||||
Format.printf "%a" Frontend.pp_pre_dwarf_readelf pre_dwarf;
|
||||
let pre_c_dwarf = PreCBinding.convert_pre_c pre_dwarf in
|
||||
let fd = open_out_bin outfile in
|
||||
|
|
|
@ -1,6 +1,8 @@
|
|||
open Simplest
|
||||
open Std
|
||||
|
||||
exception InvalidPreDwarf of string
|
||||
|
||||
type pre_c_pre_dwarf_entry = {
|
||||
location: int64;
|
||||
cfa_offset: int64;
|
||||
|
@ -58,7 +60,9 @@ let convert_pre_c_entry loc entry : pre_c_pre_dwarf_entry =
|
|||
let offset, offset_reg = (match entry with
|
||||
| RspOffset off -> off, 7
|
||||
| RbpOffset off -> off, 6
|
||||
| CfaLostTrack -> assert false (* Should be filtered out beforehand *)
|
||||
| CfaLostTrack ->
|
||||
raise (InvalidPreDwarf
|
||||
("CfaLostTrack should be filtered out beforehand"))
|
||||
) in
|
||||
{
|
||||
location = loc;
|
||||
|
@ -72,22 +76,33 @@ let convert_pre_c_entries entries : pre_c_pre_dwarf_entry array =
|
|||
(fun loc entry _ -> convert_pre_c_entry loc entry)
|
||||
entries empty_entry
|
||||
|
||||
let convert_pre_c_fde name entry id : pre_c_pre_dwarf_fde =
|
||||
{
|
||||
num = AddrMap.cardinal entry.cfa_changes_fde;
|
||||
initial_location = entry.beg_pos;
|
||||
end_location = entry.end_pos;
|
||||
name = name;
|
||||
entries = convert_pre_c_entries entry.cfa_changes_fde
|
||||
}
|
||||
let convert_pre_c_fde name entry : pre_c_pre_dwarf_fde option =
|
||||
try
|
||||
Some {
|
||||
num = AddrMap.cardinal entry.cfa_changes_fde;
|
||||
initial_location = entry.beg_pos;
|
||||
end_location = entry.end_pos;
|
||||
name = name;
|
||||
entries = convert_pre_c_entries entry.cfa_changes_fde
|
||||
}
|
||||
with InvalidPreDwarf reason -> (
|
||||
Format.eprintf "FAILED subroutine %s: %s@." name reason ;
|
||||
None
|
||||
)
|
||||
|
||||
|
||||
module StrMapTool = MapTool(StrMap)
|
||||
let convert_pre_c (cfa_map: subroutine_cfa_map) : pre_c_pre_dwarf =
|
||||
(** Converts a `subroutine_cfa_map` to a `pre_c_pre_dwarf` type, in
|
||||
preparation for C coversion. *)
|
||||
let num_fde = StrMap.cardinal cfa_map in
|
||||
let fdes = StrMapTool.fold_map_to_array
|
||||
convert_pre_c_fde cfa_map empty_fde in
|
||||
let fdes_list_with_none = StrMap.fold (fun name entry folded ->
|
||||
(convert_pre_c_fde name entry) :: folded)
|
||||
cfa_map [] in
|
||||
let fdes_list = List.fold_left (fun folded elt -> match elt with
|
||||
| Some x -> x::folded
|
||||
| None -> folded) [] fdes_list_with_none in
|
||||
let fdes = Array.of_list fdes_list in
|
||||
{
|
||||
num_fde = num_fde ;
|
||||
fdes = fdes
|
||||
|
|
|
@ -458,3 +458,13 @@ let of_proj proj : subroutine_cfa_map =
|
|||
(** Extracts the `cfa_changes` of a project *)
|
||||
let prog = BStd.Project.program proj in
|
||||
of_prog prog
|
||||
|
||||
let clean_lost_track_subs pre_dwarf : subroutine_cfa_map =
|
||||
(** Removes the subroutines on which we lost track from [pre_dwarf] *)
|
||||
let sub_lost_track sub_name (sub: subroutine_cfa_data) =
|
||||
not @@ AddrMap.exists (fun addr pos -> (match pos with
|
||||
| RspOffset _ | RbpOffset _ -> false
|
||||
| CfaLostTrack -> true))
|
||||
sub.cfa_changes_fde
|
||||
in
|
||||
StrMap.filter sub_lost_track pre_dwarf
|
||||
|
|
91
csmith/csmith_test_generated.sh
Executable file
91
csmith/csmith_test_generated.sh
Executable file
|
@ -0,0 +1,91 @@
|
|||
#!/bin/bash
|
||||
|
||||
USAGE="$0 nb_tests kept_directory"
|
||||
|
||||
if [ "$#" -lt 1 ] ; then
|
||||
>&2 echo -e "Missing argument(s). Usage:\n$USAGE"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
NB_TESTS=$1
|
||||
KEPT_DIRECTORY=$2
|
||||
RUN_TIMEOUT=2
|
||||
|
||||
tmpdir="$(mktemp -d)"
|
||||
error_count=0
|
||||
|
||||
function statusline {
|
||||
echo -ne "\r\e[1m[\e[32m$(printf "%03d/%03d" "$1" "$NB_TESTS")\e[39m] >>>\e[0m $2 "
|
||||
}
|
||||
|
||||
function reporterror {
|
||||
echo -e "\n\e[1;31m[$(printf "%03d" $1)] Error: \e[0m $2"
|
||||
}
|
||||
|
||||
function mkpath {
|
||||
echo "$tmpdir/$1"
|
||||
}
|
||||
|
||||
function failed_test {
|
||||
path=$(mkpath $1)
|
||||
cp "$path."* "$KEPT_DIRECTORY"
|
||||
reporterror "$1" "$2"
|
||||
error_count=$((error_count + 1))
|
||||
}
|
||||
|
||||
function test_empty_dwarf {
|
||||
path="$2"
|
||||
statusline $1 "test DWARF emptyness"
|
||||
if [ -z "$(readelf -wF "$path.eh.bin")" ]; then
|
||||
return 1
|
||||
else
|
||||
return 0
|
||||
fi
|
||||
}
|
||||
|
||||
function test_run {
|
||||
path="$2"
|
||||
statusline $1 "running binaries"
|
||||
orig="$(timeout $RUN_TIMEOUT "$path.orig.bin")"
|
||||
orig_status=$?
|
||||
synth="$(timeout $RUN_TIMEOUT "$path.eh.bin")"
|
||||
synth_status=$?
|
||||
|
||||
if [ "$orig_status" -ne "$synth_status" ] || [ "$orig" != "$synth" ] ; then
|
||||
return 1
|
||||
else
|
||||
return 0
|
||||
fi
|
||||
}
|
||||
|
||||
mkdir -p "$KEPT_DIRECTORY"
|
||||
|
||||
statusline "" ""
|
||||
for num in $(seq 1 $NB_TESTS); do
|
||||
## Generation, compilation, synthesis
|
||||
statusline $num "csmith"
|
||||
path=$(mkpath $num)
|
||||
csmith > "$path.c"
|
||||
statusline $num "compiling"
|
||||
gcc -O2 -I/usr/include/csmith-2.3.0/ -w "$path.c" -o "$path.orig.bin"
|
||||
objcopy --remove-section '.eh_frame' --remove-section '.eh_frame_hdr' \
|
||||
"$path.orig.bin" "$path.bin"
|
||||
statusline $num "generating dwarf"
|
||||
../synthesize_dwarf.sh "$path.bin" "$path.eh.bin"
|
||||
|
||||
## Testing
|
||||
if ! test_empty_dwarf "$num" "$path"; then
|
||||
failed_test "$num" "empty generated DWARF"
|
||||
elif ! test_run "$num" "$path"; then
|
||||
failed_test "$num" "different execution behaviour"
|
||||
fi
|
||||
done
|
||||
|
||||
echo ""
|
||||
if [ "$error_count" -eq "0" ] ; then
|
||||
echo -e "\n== ALL TESTS PASSED =="
|
||||
else
|
||||
echo -e "\n== FAILED TESTS: $error_count/$NB_TESTS =="
|
||||
fi
|
||||
|
||||
rm -rf "$tmpdir"
|
|
@ -35,7 +35,7 @@ function find_ml_dwarf_write {
|
|||
}
|
||||
|
||||
function bap_synth {
|
||||
bap "$INPUT_FILE" -p dwarfsynth --dwarfsynth-output "$TMP_DIR/marshal" \
|
||||
bap "$INPUT_FILE" --no-byteweight -p dwarfsynth --dwarfsynth-output "$TMP_DIR/marshal" \
|
||||
> /dev/null
|
||||
return $?
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue