@@ -2,57 +2,127 @@ use flatbuffers::FlatBufferBuilder;
22use prost:: Message ;
33use solfuzz_agave:: context_generated as fbs_ctx;
44use solfuzz_agave:: elf_generated as fbs_elf;
5+ use solfuzz_agave:: metadata_generated as fbs_meta;
56use solfuzz_agave:: proto as pb;
7+ use solfuzz_agave:: utils:: fd_hash:: { fd_hash_u64_without_seed, fd_hash_without_seed} ;
68use std:: env;
79use std:: fs;
810use std:: io;
911use std:: path:: PathBuf ;
1012
11- fn convert_ctx_proto_to_flatbuf ( input : & pb:: ElfLoaderCtx ) -> Vec < u8 > {
12- let mut fbb = FlatBufferBuilder :: new ( ) ;
13+ fn convert_fixture_proto_to_flatbuf ( input : & pb:: ElfLoaderFixture ) -> Vec < u8 > {
14+ let mut fbb: FlatBufferBuilder < ' _ > = FlatBufferBuilder :: new ( ) ;
15+
16+ // metadata
17+ let fn_entrypoint = input
18+ . metadata
19+ . as_ref ( )
20+ . map ( |m| m. fn_entrypoint . as_str ( ) )
21+ . unwrap_or ( "" ) ;
22+ let fn_entrypoint_off = fbb. create_string ( fn_entrypoint) ;
23+ let metadata_off = fbs_meta:: FixtureMetadata :: create (
24+ & mut fbb,
25+ & fbs_meta:: FixtureMetadataArgs {
26+ fn_entrypoint : Some ( fn_entrypoint_off) ,
27+ } ,
28+ ) ;
1329
1430 // input ctx
15- let features_off = input. features . as_ref ( ) . map ( |features| {
16- let vec_off = fbb. create_vector ( & features. features ) ;
17- fbs_ctx:: FeatureSet :: create (
18- & mut fbb,
19- & fbs_ctx:: FeatureSetArgs {
20- features : Some ( vec_off) ,
21- } ,
22- )
23- } ) ;
31+ let ctx = input. input . as_ref ( ) ;
32+ let feature_values: & [ u64 ] = ctx
33+ . and_then ( |c| c. features . as_ref ( ) )
34+ . map ( |features| features. features . as_slice ( ) )
35+ . unwrap_or ( & [ ] ) ;
36+ let features_vec = fbb. create_vector ( feature_values) ;
37+ let features_off = Some ( fbs_ctx:: FeatureSet :: create (
38+ & mut fbb,
39+ & fbs_ctx:: FeatureSetArgs {
40+ features : Some ( features_vec) ,
41+ } ,
42+ ) ) ;
2443
25- let elf_off = input
26- . elf
27- . as_ref ( )
28- . map ( |elf| fbb. create_vector ( elf. data . as_slice ( ) ) ) ;
44+ let elf_bytes: & [ u8 ] = ctx
45+ . and_then ( |c| c. elf . as_ref ( ) )
46+ . map ( |elf| elf. data . as_slice ( ) )
47+ . unwrap_or ( & [ ] ) ;
48+ let elf_off = Some ( fbb. create_vector ( elf_bytes) ) ;
2949
50+ let deploy_checks = ctx. map ( |c| c. deploy_checks ) . unwrap_or ( false ) ;
3051 let ctx_off = fbs_elf:: ELFLoaderCtx :: create (
3152 & mut fbb,
3253 & fbs_elf:: ELFLoaderCtxArgs {
3354 elf_data : elf_off,
3455 features : features_off,
35- deploy_checks : input. deploy_checks ,
56+ deploy_checks,
57+ } ,
58+ ) ;
59+
60+ // output effects
61+ let output = input. output . as_ref ( ) ;
62+ let error = output. map ( |o| o. error ) . unwrap_or ( 0 ) as u8 ;
63+ let text_cnt = output. map ( |o| o. text_cnt ) . unwrap_or ( 0 ) ;
64+ let text_off = output. map ( |o| o. text_off ) . unwrap_or ( 0 ) ;
65+ let entry_pc = output. map ( |o| o. entry_pc ) . unwrap_or ( 0 ) ;
66+
67+ // Compute rodata hash
68+ let rodata_hash = output. and_then ( |o| {
69+ if !o. rodata . is_empty ( ) {
70+ let hash_u64 = fd_hash_without_seed ( & o. rodata ) ;
71+ Some ( fbs_ctx:: XXHash :: new ( & hash_u64. to_le_bytes ( ) ) )
72+ } else {
73+ None
74+ }
75+ } ) ;
76+
77+ // Compute calldests hash
78+ let calldests_hash = output. and_then ( |o| {
79+ if !o. calldests . is_empty ( ) {
80+ let hash_u64 = unsafe { fd_hash_u64_without_seed ( o. calldests . as_slice ( ) ) } ;
81+ Some ( fbs_ctx:: XXHash :: new ( & hash_u64. to_le_bytes ( ) ) )
82+ } else {
83+ None
84+ }
85+ } ) ;
86+
87+ let effects_off = fbs_elf:: ELFLoaderEffects :: create (
88+ & mut fbb,
89+ & fbs_elf:: ELFLoaderEffectsArgs {
90+ err_code : error,
91+ rodata_hash : rodata_hash. as_ref ( ) ,
92+ text_cnt,
93+ text_off,
94+ entry_pc,
95+ calldests_hash : calldests_hash. as_ref ( ) ,
96+ } ,
97+ ) ;
98+
99+ // fixture
100+ let fixture_off = fbs_elf:: ELFLoaderFixture :: create (
101+ & mut fbb,
102+ & fbs_elf:: ELFLoaderFixtureArgs {
103+ metadata : Some ( metadata_off) ,
104+ input : Some ( ctx_off) ,
105+ output : Some ( effects_off) ,
36106 } ,
37107 ) ;
38108
39- fbb. finish ( ctx_off , None ) ;
109+ fbb. finish ( fixture_off , None ) ;
40110 fbb. finished_data ( ) . to_vec ( )
41111}
42112
43113fn read_file ( path : & PathBuf ) -> io:: Result < Vec < u8 > > {
44114 fs:: read ( path)
45115}
46116
47- fn decode_ctx ( bytes : & [ u8 ] ) -> Result < pb:: ElfLoaderCtx , prost:: DecodeError > {
48- pb:: ElfLoaderCtx :: decode ( bytes)
117+ fn decode_fixture ( bytes : & [ u8 ] ) -> Result < pb:: ElfLoaderFixture , prost:: DecodeError > {
118+ pb:: ElfLoaderFixture :: decode ( bytes)
49119}
50120
51121fn process_file ( path : & PathBuf , out_dir : & PathBuf ) -> i32 {
52122 match read_file ( path) {
53- Ok ( bytes) => match decode_ctx ( & bytes) {
54- Ok ( ctx ) => {
55- let out = convert_ctx_proto_to_flatbuf ( & ctx ) ;
123+ Ok ( bytes) => match decode_fixture ( & bytes) {
124+ Ok ( fixture ) => {
125+ let out = convert_fixture_proto_to_flatbuf ( & fixture ) ;
56126 // Write to output directory with same filename
57127 if let Err ( e) = fs:: create_dir_all ( out_dir) {
58128 eprintln ! (
@@ -83,7 +153,7 @@ fn process_file(path: &PathBuf, out_dir: &PathBuf) -> i32 {
83153 }
84154 Err ( e) => {
85155 eprintln ! (
86- "{}: failed to decode protobuf ElfLoaderCtx : {}" ,
156+ "{}: failed to decode protobuf ElfLoaderFixture : {}" ,
87157 path. display( ) ,
88158 e
89159 ) ;
0 commit comments