LCOV - code coverage report
Current view: top level - flamenco/runtime/tests - fd_sol_compat.c (source / functions) Hit Total Coverage
Test: cov.lcov Lines: 0 239 0.0 %
Date: 2026-10-18 04:43:39 Functions: 0 15 0.0 %

          Line data    Source code
       1             : #include "fd_solfuzz.h"
       2             : #include "fd_solfuzz_private.h"
       3             : #include "fd_sol_compat.h"
       4             : #include "../../capture/fd_solcap_writer.h"
       5             : #include "fd_gossip_harness.h"
       6             : 
       7             : #include "generated/block.pb.h"
       8             : #include "generated/instr.pb.h"
       9             : #include "generated/vm.pb.h"
      10             : #include "generated/txn.pb.h"
      11             : #include "generated/bundle.pb.h"
      12             : #include "generated/cost.pb.h"
      13             : #include "generated/elf.pb.h"
      14             : #include "generated/vm_serialization.pb.h"
      15             : #include "generated/shred.pb.h"
      16             : 
      17             : #include <errno.h>
      18             : #include <fcntl.h>
      19             : #include <unistd.h>
      20             : 
      21             : static fd_wksp_t *           wksp   = NULL;
      22             : static fd_solfuzz_runner_t * runner = NULL;
      23             : 
      24             : static fd_solfuzz_runner_t *
      25           0 : sol_compat_setup_runner( fd_solfuzz_runner_options_t const * options ) {
      26           0 :   runner = fd_solfuzz_runner_new( wksp, 3UL, options );
      27           0 :   if( FD_UNLIKELY( !runner ) ) {
      28           0 :     FD_LOG_ERR(( "fd_solfuzz_runner_new() failed" ));
      29           0 :     return NULL;
      30           0 :   }
      31             : 
      32           0 :   char const * solcap_path = getenv( "FD_SOLCAP" );
      33           0 :   if( solcap_path ) {
      34           0 :     int fd = open( solcap_path, O_WRONLY | O_CREAT | O_TRUNC, 0644 );
      35           0 :     if( FD_UNLIKELY( fd == -1 ) ) {
      36           0 :       FD_LOG_ERR(( "open($FD_SOLCAP=%s) failed (%i-%s)", solcap_path, errno, fd_io_strerror( errno ) ));
      37           0 :     }
      38           0 :     runner->solcap_file = (void *)(ulong)fd;
      39           0 :     FD_LOG_NOTICE(( "Logging to solcap file %s", solcap_path ));
      40             : 
      41           0 :     void * solcap_mem = fd_wksp_alloc_laddr( runner->wksp, fd_solcap_writer_align(), fd_solcap_writer_footprint(), 1UL );
      42           0 :     runner->solcap = fd_solcap_writer_init( solcap_mem, fd );
      43           0 :     FD_TEST( runner->solcap );
      44           0 :   }
      45             : 
      46           0 :   return runner;
      47           0 : }
      48             : 
      49             : static void
      50           0 : sol_compat_cleanup_runner( fd_solfuzz_runner_t * runner ) {
      51             :   /* Cleanup test runner */
      52           0 :   if( runner->solcap ) {
      53           0 :     fd_wksp_free_laddr( ( runner->solcap ) );
      54           0 :     runner->solcap = NULL;
      55           0 :     if( runner->solcap_file ) {
      56           0 :       close( (int)(ulong)runner->solcap_file );
      57           0 :       runner->solcap_file = NULL;
      58           0 :     }
      59           0 :   }
      60           0 :   fd_solfuzz_runner_delete( runner );
      61           0 : }
      62             : 
      63             : void
      64           0 : sol_compat_init( int log_level ) {
      65           0 :   int argc = 1;
      66           0 :   char * argv[2] = { (char *)"fd_exec_sol_compat", NULL };
      67           0 :   char ** argv_ = argv;
      68           0 :   if( !getenv( "FD_LOG_PATH" ) ) {
      69           0 :     setenv( "FD_LOG_PATH", "", 1 );
      70           0 :   }
      71             : 
      72           0 :   char const * enable_vm_tracing_env  = getenv( "ENABLE_VM_TRACING");
      73           0 :   int enable_vm_tracing               = enable_vm_tracing_env!=NULL;
      74           0 :   fd_solfuzz_runner_options_t options = {
      75           0 :     .enable_vm_tracing = enable_vm_tracing
      76           0 :   };
      77             : 
      78           0 :   fd_log_enable_unclean_exit();
      79           0 :   fd_boot( &argc, &argv_ );
      80             : 
      81           0 :   if( FD_UNLIKELY( wksp || runner ) ) {
      82           0 :     FD_LOG_ERR(( "sol_compat_init() called multiple times" ));
      83           0 :   }
      84             : 
      85           0 :   ulong footprint = 22UL<<30;
      86           0 :   ulong part_max  = fd_wksp_part_max_est( footprint, 64UL<<10 );
      87           0 :   ulong data_max  = fd_wksp_data_max_est( footprint, part_max );
      88           0 :   wksp = fd_wksp_demand_paged_new( "sol_compat", 42U, part_max, data_max );
      89           0 :   if( FD_UNLIKELY( !wksp ) ) FD_LOG_ERR(( "fd_wksp_demand_paged_new() failed" ));
      90             : 
      91           0 :   runner = sol_compat_setup_runner( &options );
      92           0 :   if( FD_UNLIKELY( !runner ) ) FD_LOG_ERR(( "sol_compat_setup_runner() failed" ));
      93             : 
      94           0 :   fd_log_level_logfile_set( log_level );
      95           0 :   fd_log_level_core_set(4);  /* abort on FD_LOG_ERR */
      96           0 : }
      97             : 
      98             : void
      99           0 : sol_compat_fini( void ) {
     100           0 :   sol_compat_cleanup_runner( runner );
     101           0 :   fd_wksp_delete_anonymous( wksp );
     102           0 :   wksp   = NULL;
     103           0 :   runner = NULL;
     104           0 :   fd_halt();
     105           0 : }
     106             : 
     107             : sol_compat_features_t const *
     108           0 : sol_compat_get_features_v1( void ) {
     109           0 :   static sol_compat_features_t features;
     110           0 :   static ulong hardcoded_features[ FD_FEATURE_ID_CNT ];
     111           0 :   static ulong supported_features[ FD_FEATURE_ID_CNT ];
     112             : 
     113           0 :   FD_ONCE_BEGIN {
     114           0 :     features.struct_size = sizeof(sol_compat_features_t);
     115           0 :     features.hardcoded_features = hardcoded_features;
     116           0 :     features.supported_features = supported_features;
     117           0 :     for( fd_feature_id_t const * iter = fd_feature_iter_init();
     118           0 :          !fd_feature_iter_done( iter );
     119           0 :          iter = fd_feature_iter_next( iter ) ) {
     120           0 :       if( iter->reverted    ) continue; /* skip reverted features */
     121           0 :       if( !iter->implemented ) continue; /* skip features firedancer does not implement yet */
     122             : 
     123             :       /* Pretend that features activated on all clusters are hardcoded */
     124           0 :       if( iter->hardcode_for_fuzzing ) {
     125           0 :         hardcoded_features[ features.hardcoded_features_cnt++ ] = iter->id.ul[0];
     126           0 :       } else {
     127           0 :         supported_features[ features.supported_feature_cnt++  ] = iter->id.ul[0];
     128           0 :       }
     129           0 :     }
     130           0 :   }
     131           0 :   FD_ONCE_END;
     132             : 
     133           0 :   return &features;
     134           0 : }
     135             : 
     136             : /*
     137             :  * execute_v1
     138             :  */
     139             : 
     140             : int
     141             : sol_compat_instr_execute_v1( uchar *       out,
     142             :                              ulong *       out_sz,
     143             :                              uchar const * in,
     144           0 :                              ulong         in_sz ) {
     145           0 :   fd_exec_test_instr_context_t input[1] = {0};
     146           0 :   void * res = sol_compat_decode_lenient( &input, in, in_sz, &fd_exec_test_instr_context_t_msg );
     147           0 :   if( FD_UNLIKELY( !res ) ) return 0;
     148             : 
     149           0 :   int ok = 0;
     150           0 :   fd_spad_push( runner->spad );
     151           0 :   void * output = NULL;
     152           0 :   fd_solfuzz_pb_execute_wrapper( runner, input, &output, fd_solfuzz_pb_instr_run );
     153           0 :   if( output ) {
     154           0 :     ok = !!sol_compat_encode( out, out_sz, output, &fd_exec_test_instr_effects_t_msg );
     155           0 :   }
     156           0 :   fd_spad_pop( runner->spad );
     157             : 
     158           0 :   pb_release( &fd_exec_test_instr_context_t_msg, input );
     159           0 :   fd_solfuzz_runner_leak_check( runner );
     160           0 :   return ok;
     161           0 : }
     162             : 
     163             : int
     164             : sol_compat_txn_execute_v1( uchar *       out,
     165             :                            ulong *       out_sz,
     166             :                            uchar const * in,
     167           0 :                            ulong         in_sz ) {
     168           0 :   fd_exec_test_txn_context_t input[1] = {0};
     169           0 :   void * res = sol_compat_decode_lenient( &input, in, in_sz, &fd_exec_test_txn_context_t_msg );
     170           0 :   if( FD_UNLIKELY( !res ) ) return 0;
     171             : 
     172           0 :   int ok = 0;
     173           0 :   fd_spad_push( runner->spad );
     174           0 :   void * output = NULL;
     175           0 :   fd_solfuzz_pb_execute_wrapper( runner, input, &output, fd_solfuzz_pb_txn_run );
     176           0 :   if( output ) {
     177           0 :     ok = !!sol_compat_encode( out, out_sz, output, &fd_exec_test_txn_result_t_msg );
     178           0 :   }
     179           0 :   fd_spad_pop( runner->spad );
     180             : 
     181           0 :   pb_release( &fd_exec_test_txn_context_t_msg, input );
     182           0 :   fd_solfuzz_runner_leak_check( runner );
     183           0 :   return ok;
     184           0 : }
     185             : 
     186             : int
     187             : sol_compat_bundle_execute_v1( uchar *       out,
     188             :                               ulong *       out_sz,
     189             :                               uchar const * in,
     190           0 :                               ulong         in_sz ) {
     191           0 :   fd_exec_test_bundle_context_t input[1] = {0};
     192           0 :   void * res = sol_compat_decode_lenient( &input, in, in_sz, &fd_exec_test_bundle_context_t_msg );
     193           0 :   if( FD_UNLIKELY( !res ) ) return 0;
     194             : 
     195           0 :   int ok = 0;
     196           0 :   fd_spad_push( runner->spad );
     197           0 :   void * output = NULL;
     198           0 :   fd_solfuzz_pb_execute_wrapper( runner, input, &output, fd_solfuzz_pb_bundle_run );
     199           0 :   if( output ) {
     200           0 :     ok = !!sol_compat_encode( out, out_sz, output, &fd_exec_test_bundle_effects_t_msg );
     201           0 :   }
     202           0 :   fd_spad_pop( runner->spad );
     203             : 
     204           0 :   pb_release( &fd_exec_test_bundle_context_t_msg, input );
     205           0 :   fd_solfuzz_runner_leak_check( runner );
     206           0 :   return ok;
     207           0 : }
     208             : 
     209             : int
     210             : sol_compat_txn_cost_v1( uchar *       out,
     211             :                         ulong *       out_sz,
     212             :                         uchar const * in,
     213           0 :                         ulong         in_sz ) {
     214           0 :   fd_exec_test_cost_context_t input[1] = { FD_EXEC_TEST_COST_CONTEXT_INIT_ZERO };
     215           0 :   void * res = sol_compat_decode_lenient( &input, in, in_sz, &fd_exec_test_cost_context_t_msg );
     216           0 :   if( FD_UNLIKELY( !res ) ) return 0;
     217             : 
     218           0 :   int ok = 0;
     219           0 :   fd_spad_push( runner->spad );
     220           0 :   void * output = NULL;
     221           0 :   fd_solfuzz_pb_execute_wrapper( runner, input, &output, fd_solfuzz_pb_cost_run );
     222           0 :   if( output ) {
     223           0 :     ok = !!sol_compat_encode( out, out_sz, output, &fd_exec_test_cost_result_t_msg );
     224           0 :   }
     225           0 :   fd_spad_pop( runner->spad );
     226             : 
     227           0 :   pb_release( &fd_exec_test_cost_context_t_msg, input );
     228           0 :   fd_solfuzz_runner_leak_check( runner );
     229           0 :   return ok;
     230           0 : }
     231             : 
     232             : int
     233             : sol_compat_block_execute_v1( uchar *       out,
     234             :                              ulong *       out_sz,
     235             :                              uchar const * in,
     236           0 :                              ulong         in_sz ) {
     237           0 :   fd_exec_test_block_context_t input[1] = {0};
     238           0 :   void * res = sol_compat_decode_lenient( &input, in, in_sz, &fd_exec_test_block_context_t_msg );
     239           0 :   if( FD_UNLIKELY( !res ) ) return 0;
     240             : 
     241           0 :   fd_spad_push( runner->spad );
     242           0 :   int ok = 0;
     243           0 :   void * output = NULL;
     244           0 :   fd_solfuzz_pb_execute_wrapper( runner, input, &output, fd_solfuzz_pb_block_run );
     245           0 :   if( output ) {
     246           0 :     ok = !!sol_compat_encode( out, out_sz, output, &fd_exec_test_block_effects_t_msg );
     247           0 :   }
     248           0 :   fd_spad_pop( runner->spad );
     249             : 
     250           0 :   pb_release( &fd_exec_test_block_context_t_msg, input );
     251           0 :   fd_solfuzz_runner_leak_check( runner );
     252           0 :   return ok;
     253           0 : }
     254             : 
     255             : int
     256             : sol_compat_vm_syscall_execute_v1( uchar *       out,
     257             :                                   ulong *       out_sz,
     258             :                                   uchar const * in,
     259           0 :                                   ulong         in_sz ) {
     260           0 :   fd_exec_test_syscall_context_t input[1] = {0};
     261           0 :   void * res = sol_compat_decode_lenient( &input, in, in_sz, &fd_exec_test_syscall_context_t_msg );
     262           0 :   if( FD_UNLIKELY( !res ) ) return 0;
     263             : 
     264           0 :   fd_spad_push( runner->spad );
     265           0 :   int ok = 0;
     266           0 :   void * output = NULL;
     267           0 :   fd_solfuzz_pb_execute_wrapper( runner, input, &output, fd_solfuzz_pb_syscall_run );
     268           0 :   if( output ) {
     269           0 :     ok = !!sol_compat_encode( out, out_sz, output, &fd_exec_test_syscall_effects_t_msg );
     270           0 :   }
     271           0 :   fd_spad_pop( runner->spad );
     272             : 
     273           0 :   pb_release( &fd_exec_test_syscall_context_t_msg, input );
     274           0 :   fd_solfuzz_runner_leak_check( runner );
     275           0 :   return ok;
     276           0 : }
     277             : 
     278             : int
     279             : sol_compat_gossip_decode_v1( uchar *       out,
     280             :                              ulong *       out_sz,
     281             :                              uchar const * in,
     282           0 :                              ulong         in_sz ) {
     283           0 :   fd_spad_push( runner->spad );
     284           0 :   int ok = fd_solfuzz_gossip_decode( runner, out, out_sz, in, in_sz );
     285           0 :   fd_spad_pop( runner->spad );
     286           0 :   fd_solfuzz_runner_leak_check( runner );
     287           0 :   return ok;
     288           0 : }
     289             : 
     290             : int
     291             : sol_compat_elf_loader_v1( uchar *       out,
     292             :                           ulong *       out_sz,
     293             :                           uchar const * in,
     294           0 :                           ulong         in_sz ) {
     295           0 :   fd_exec_test_elf_loader_ctx_t input[1] = {0};
     296           0 :   void * res = sol_compat_decode_lenient( &input, in, in_sz, &fd_exec_test_elf_loader_ctx_t_msg );
     297           0 :   if( FD_UNLIKELY( !res ) ) return 0;
     298             : 
     299           0 :   int ok = 0;
     300           0 :   fd_spad_push( runner->spad );
     301           0 :   void * output = NULL;
     302           0 :   fd_solfuzz_pb_execute_wrapper( runner, input, &output, fd_solfuzz_pb_elf_loader_run );
     303           0 :   if( output ) {
     304           0 :     ok = !!sol_compat_encode( out, out_sz, output, &fd_exec_test_elf_loader_effects_t_msg );
     305           0 :   }
     306           0 :   fd_spad_pop( runner->spad );
     307             : 
     308           0 :   pb_release( &fd_exec_test_elf_loader_ctx_t_msg, input );
     309           0 :   fd_solfuzz_runner_leak_check( runner );
     310           0 :   return ok;
     311           0 : }
     312             : 
     313             : int
     314             : sol_compat_vm_serialize_execute_v1( uchar *       out,
     315             :                                     ulong *       out_sz,
     316             :                                     uchar const * in,
     317           0 :                                     ulong         in_sz ) {
     318           0 :   fd_exec_test_instr_context_t input[1] = {0};
     319           0 :   void * res = sol_compat_decode_lenient( &input, in, in_sz, &fd_exec_test_instr_context_t_msg );
     320           0 :   if( FD_UNLIKELY( !res ) ) return 0;
     321             : 
     322           0 :   int ok = 0;
     323           0 :   fd_spad_push( runner->spad );
     324           0 :   void * output = NULL;
     325           0 :   fd_solfuzz_pb_execute_wrapper( runner, input, &output, fd_solfuzz_pb_vm_serialize_run );
     326           0 :   if( output ) {
     327           0 :     ok = !!sol_compat_encode( out, out_sz, output, &fd_exec_test_vm_serialization_effects_t_msg );
     328           0 :   }
     329           0 :   fd_spad_pop( runner->spad );
     330             : 
     331           0 :   pb_release( &fd_exec_test_instr_context_t_msg, input );
     332           0 :   fd_solfuzz_runner_leak_check( runner );
     333           0 :   return ok;
     334           0 : }
     335             : 
     336             : int
     337             : sol_compat_shred_parse_v1( uchar *       out,
     338             :                            ulong *       out_sz,
     339             :                            uchar const * in,
     340           0 :                            ulong         in_sz ) {
     341           0 :   fd_exec_test_shred_parse_context_t input[1] = {0};
     342           0 :   void * res = sol_compat_decode_lenient( &input, in, in_sz, &fd_exec_test_shred_parse_context_t_msg );
     343           0 :   if( FD_UNLIKELY( !res ) ) return 0;
     344             : 
     345           0 :   int ok = 0;
     346           0 :   fd_spad_push( runner->spad );
     347           0 :   void * output = NULL;
     348           0 :   fd_solfuzz_pb_execute_wrapper( runner, input, &output, fd_solfuzz_pb_shred_run );
     349           0 :   if( output ) {
     350           0 :     ok = !!sol_compat_encode( out, out_sz, output, &fd_exec_test_shred_parse_effects_t_msg );
     351           0 :   }
     352           0 :   fd_spad_pop( runner->spad );
     353             : 
     354           0 :   pb_release( &fd_exec_test_shred_parse_context_t_msg, input );
     355           0 :   fd_solfuzz_runner_leak_check( runner );
     356           0 :   return ok;
     357           0 : }

Generated by: LCOV version 1.14