LCOV - code coverage report
Current view: top level - flamenco/runtime/tests - fd_elf_harness.c (source / functions) Hit Total Coverage
Test: cov.lcov Lines: 67 69 97.1 %
Date: 2026-10-22 18:10:43 Functions: 1 1 100.0 %

          Line data    Source code
       1             : #include "fd_solfuzz.h"
       2             : #include "fd_solfuzz_private.h"
       3             : #include "../../../ballet/sbpf/fd_sbpf_loader.h"
       4             : #include "../program/fd_bpf_loader_program.h"
       5             : #include "../../vm/fd_vm_base.h"
       6             : #include "../../progcache/fd_prog_load.h"
       7             : #include "generated/elf.pb.h"
       8             : 
       9             : #define SORT_NAME        sort_ulong
      10      817398 : #define SORT_KEY_T       ulong
      11     1108705 : #define SORT_BEFORE(a,b) (a)<(b)
      12             : #include "../../../util/tmpl/fd_sort.c"
      13             : 
      14             : ulong
      15             : fd_solfuzz_pb_elf_loader_run( fd_solfuzz_runner_t * runner,
      16             :                               void const *          input_,
      17             :                               void **               output_,
      18             :                               void *                output_buf,
      19        1946 :                               ulong                 output_bufsz ) {
      20        1946 :   fd_exec_test_elf_loader_ctx_t const * input  = fd_type_pun_const( input_ );
      21        1946 :   fd_exec_test_elf_loader_effects_t **  output = fd_type_pun( output_ );
      22             : 
      23        1946 :   fd_spad_t *   spad    = runner->spad;
      24        1946 :   uchar const * elf_bin = input->elf_data ? input->elf_data->bytes : NULL;
      25        1946 :   ulong         elf_sz  = input->elf_data ? input->elf_data->size  : 0UL;
      26             : 
      27             :   /* Allocate effects struct out of the caller's output buffer */
      28        1946 :   ulong output_end = (ulong)output_buf + output_bufsz;
      29        1946 :   FD_SCRATCH_ALLOC_INIT( l, output_buf );
      30        1946 :   fd_exec_test_elf_loader_effects_t * effects =
      31        1946 :     FD_SCRATCH_ALLOC_APPEND( l, alignof(fd_exec_test_elf_loader_effects_t),
      32        1946 :                                 sizeof (fd_exec_test_elf_loader_effects_t) );
      33        1946 :   if( FD_UNLIKELY( _l > output_end ) ) return 0UL;
      34        1946 :   fd_memset( effects, 0, sizeof(fd_exec_test_elf_loader_effects_t) );
      35             : 
      36             :   /* Restore feature set */
      37        1946 :   fd_features_t feature_set = {0};
      38        1946 :   if( FD_UNLIKELY( input->has_features &&
      39        1946 :                    !fd_solfuzz_pb_restore_features( &feature_set, &input->features ) ) ) {
      40           0 :     return 0UL;
      41           0 :   }
      42             : 
      43        1946 :   fd_sbpf_loader_config_t config = {
      44        1946 :     .elf_deploy_checks = input->deploy_checks,
      45        1946 :   };
      46             : 
      47        1946 :   fd_prog_versions_t versions = fd_prog_versions( &feature_set, UINT_MAX );
      48        1946 :   config.sbpf_min_version = versions.min_sbpf_version;
      49        1946 :   config.sbpf_max_version = versions.max_sbpf_version;
      50             : 
      51             :   /* Peek */
      52        1946 :   fd_sbpf_elf_info_t info;
      53        1946 :   int err = fd_sbpf_elf_peek( &info, elf_bin, elf_sz, &config );
      54        1946 :   if( err ) {
      55         399 :     effects->err_code = (uint)(-err);
      56         399 :     *output = effects;
      57         399 :     return FD_SCRATCH_ALLOC_FINI( l, 1UL ) - (ulong)output_buf;
      58         399 :   }
      59             : 
      60             :   /* Set up loading context */
      61        1547 :   void *               rodata         = fd_spad_alloc_check( spad, FD_SBPF_PROG_RODATA_ALIGN, info.bin_sz );
      62        1547 :   fd_sbpf_program_t *  prog           = fd_sbpf_program_new( fd_spad_alloc_check( spad, fd_sbpf_program_align(), fd_sbpf_program_footprint( &info ) ), &info, rodata );
      63        1547 :   fd_sbpf_syscalls_t * syscalls       = fd_sbpf_syscalls_new( fd_spad_alloc_check( spad, fd_sbpf_syscalls_align(), fd_sbpf_syscalls_footprint() ));
      64        1547 :   void *               rodata_scratch = fd_spad_alloc_check( spad, 1UL, elf_sz );
      65             : 
      66             :   /* Register syscalls given the active feature set. We can pass in an
      67             :      arbitrary slot as its just used to check if features should be
      68             :      active or not. */
      69        1547 :   FD_TEST( !fd_vm_syscall_register_slot( syscalls, UINT_MAX, &feature_set, !!config.elf_deploy_checks ) );
      70             : 
      71             :   /* Load */
      72        1547 :   err = fd_sbpf_program_load( prog, elf_bin, elf_sz, syscalls, &config, rodata_scratch, elf_sz );
      73        1547 :   if( err ) {
      74         156 :     effects->err_code = (uint)(-err);
      75         156 :     *output = effects;
      76         156 :     return FD_SCRATCH_ALLOC_FINI( l, 1UL ) - (ulong)output_buf;
      77         156 :   }
      78             : 
      79             :   /**** Capture effects ****/
      80             : 
      81        1391 :   effects->err_code    = FD_SBPF_ELF_SUCCESS;
      82        1391 :   effects->rodata_hash = fd_hash( 0UL, prog->rodata, prog->rodata_sz );
      83        1391 :   effects->text_cnt    = prog->info.text_cnt;
      84        1391 :   effects->text_off    = fd_sbpf_enable_stricter_elf_headers_enabled( prog->info.sbpf_version ) ? 0UL : prog->info.text_off;
      85        1391 :   effects->entry_pc    = prog->entry_pc;
      86             : 
      87             :   /* Calldests */
      88        1391 :   ulong   max_out_calldests_cnt = 1UL + ( prog->calldests ? fd_sbpf_calldests_cnt( prog->calldests ) : 0UL );
      89        1391 :   ulong * tmp_out_calldests     = fd_spad_alloc_check( spad, alignof(ulong), sizeof(ulong)*max_out_calldests_cnt );
      90        1391 :   ulong   out_calldests_cnt     = 0UL;
      91             : 
      92        1391 :   if( !fd_sbpf_enable_stricter_elf_headers_enabled( prog->info.sbpf_version ) ) {
      93             :     /* Add the entrypoint to the calldests */
      94        1222 :     tmp_out_calldests[out_calldests_cnt++] = prog->entry_pc;
      95             : 
      96             :     /* Add the rest of the calldests */
      97        1222 :     if( FD_LIKELY( prog->calldests ) ) {
      98        1222 :       for( ulong target_pc=fd_sbpf_calldests_const_iter_init( prog->calldests );
      99      130647 :                           !fd_sbpf_calldests_const_iter_done( target_pc );
     100      129425 :                  target_pc=fd_sbpf_calldests_const_iter_next( prog->calldests, target_pc ) ) {
     101      129465 :         if( FD_LIKELY( target_pc!=prog->entry_pc ) ) {
     102      129465 :           tmp_out_calldests[out_calldests_cnt++] = target_pc;
     103      129465 :         }
     104      129425 :       }
     105        1222 :     }
     106        1222 :   }
     107             : 
     108             :   /* Sort the calldests in ascending order */
     109        1391 :   sort_ulong_inplace( tmp_out_calldests, out_calldests_cnt );
     110             : 
     111             :   /* Compute calldests hash */
     112        1391 :   effects->calldests_hash = fd_hash( 0UL, tmp_out_calldests, sizeof(ulong) * out_calldests_cnt );
     113             : 
     114        1391 :   *output = effects;
     115        1391 :   return FD_SCRATCH_ALLOC_FINI( l, 1UL ) - (ulong)output_buf;
     116        1547 : }

Generated by: LCOV version 1.14