LCOV - code coverage report
Current view: top level - app/fddev - dump.c (source / functions) Hit Total Coverage
Test: cov.lcov Lines: 0 61 0.0 %
Date: 2024-11-13 11:58:15 Functions: 0 3 0.0 %

          Line data    Source code
       1             : #include "fddev.h"
       2             : #include "../../util/net/fd_pcap.h"
       3             : #include <stdio.h>
       4             : 
       5             : void
       6             : dump_cmd_args( int      * argc,
       7             :                char * * * argv,
       8           0 :                args_t   * args ) {
       9           0 :   char const * out_file = fd_env_strip_cmdline_cstr( argc, argv, "--out-file", NULL, "dump.pcap" );
      10           0 :   char const * link     = fd_env_strip_cmdline_cstr( argc, argv, "--link",     NULL, ""          );
      11           0 :   fd_cstr_fini( fd_cstr_append_cstr_safe( fd_cstr_init( args->dump.pcap_path ), out_file, sizeof(args->dump.pcap_path)-1UL ) );
      12           0 :   fd_cstr_fini( fd_cstr_append_cstr_safe( fd_cstr_init( args->dump.link_name ), link,     sizeof(args->dump.link_name)-1UL ) );
      13           0 : }
      14             : 
      15             : static void
      16             : dump_link( void           * out_file,
      17             :            fd_topo_link_t * link,
      18           0 :            void           * mem ) {
      19           0 :   fd_frag_meta_t const * mcache = link->mcache;
      20           0 :   ulong seq0 = fd_mcache_seq0( mcache );
      21           0 :   ulong seq_init = fd_mcache_seq_query( fd_mcache_seq_laddr_const( mcache ) );
      22           0 :   ulong depth = fd_mcache_depth( mcache );
      23             : 
      24           0 :   ulong dumped_count = 0UL;
      25             : 
      26           0 :   uint link_hash = (uint)((fd_hash( 17UL, link->name, strlen( link->name ) ) << 8) | link->kind_id);
      27             :   /* For links that are published reliably, we can trust the value of
      28             :      seq_init.  For unreliable links, we'll just publish one whole
      29             :      depth. */
      30             : 
      31             :   /* We know at this point [seq0, seq_init) were published, but they may
      32             :      be long overwritten, and there may be more published than that. */
      33             : 
      34           0 :   ulong min_seq_seen = seq_init; /* What we actually dumped is [min_seq_seen, seq_init) */
      35           0 :   for( ulong seq=fd_seq_dec( seq_init, 1UL ); fd_seq_ge( seq, seq0 ); seq=fd_seq_dec( seq, 1UL ) ) {
      36             :     /* It's not necessary for this to be atomic, since this is a
      37             :        post-mortem tool. */
      38           0 :     fd_frag_meta_t const * line = mcache+fd_mcache_line_idx( seq, depth );
      39           0 :     ulong read_seq = fd_frag_meta_seq_query( line );
      40           0 :     if( FD_UNLIKELY( read_seq!=seq ) ) break;
      41             : 
      42           0 :     min_seq_seen = seq;
      43             : 
      44           0 :     ulong chunk = line->chunk;
      45           0 :     ulong sz    = line->sz;
      46             : 
      47           0 :     void const * buffer = fd_chunk_to_laddr_const( mem, chunk );
      48             : 
      49           0 :     fd_pcap_fwrite_pkt( (long)seq, line, sizeof(fd_frag_meta_t), buffer, sz, link_hash, out_file );
      50           0 :     dumped_count++;
      51           0 :   }
      52             : 
      53             :   /* Now check everything after seq_init.  This could potentially loop
      54             :      forever if the producer is still going, so we cap it at one depth. */
      55           0 :   for( ulong off=0UL; off<depth; off++ ) {
      56           0 :     ulong seq = fd_seq_inc( seq_init, off );
      57             : 
      58           0 :     fd_frag_meta_t const * line = mcache+fd_mcache_line_idx( seq, depth );
      59           0 :     ulong read_seq = fd_frag_meta_seq_query( line );
      60             : 
      61             :     /* Skip anything we processed in the first loop, also skipping any
      62             :        with the err control bit set.  When an mcache is initialized, all
      63             :        the frags have err set to true, so this will skip those in
      64             :        particular as well. */
      65           0 :     if( FD_UNLIKELY( (fd_seq_le( min_seq_seen, read_seq ) & fd_seq_lt( read_seq, seq_init )) | (line->ctl & (1<<2)) ) ) continue;
      66             : 
      67           0 :     ulong chunk = line->chunk;
      68           0 :     ulong sz    = line->sz;
      69             : 
      70           0 :     void const * buffer = fd_chunk_to_laddr_const( mem, chunk );
      71             : 
      72           0 :     fd_pcap_fwrite_pkt( (long)seq, line, sizeof(fd_frag_meta_t), buffer, sz, link_hash, out_file );
      73           0 :     dumped_count++;
      74           0 :   }
      75           0 :   FD_LOG_NOTICE(( "Dumped %lu frags from %s %lu. Link hash: 0x%x", dumped_count, link->name, link->kind_id, link_hash ));
      76           0 : }
      77             : 
      78             : void
      79             : dump_cmd_fn( args_t *         args,
      80           0 :              config_t * const config ) {
      81             : 
      82           0 :   FILE * out = fopen( args->dump.pcap_path, "w" );
      83           0 :   FD_TEST( fd_pcap_fwrite_hdr( out, FD_PCAP_LINK_LAYER_USER0 ) );
      84             : 
      85           0 :   fd_topo_join_workspaces( &config->topo, FD_SHMEM_JOIN_MODE_READ_ONLY );
      86           0 :   fd_topo_fill( &config->topo );
      87             : 
      88           0 :   char * tokens[ 16 ];
      89           0 :   ulong token_count = fd_cstr_tokenize( tokens, 16UL, args->dump.link_name, ',' );
      90             : 
      91           0 :   for( ulong i=0UL; i<config->topo.link_cnt; i++ ) {
      92           0 :     int found = (token_count==0UL);
      93           0 :     for( ulong k=0UL; k<token_count; k++ ) found |= !strcmp( tokens[ k ], config->topo.links[ i ].name );
      94           0 :     if( found ) {
      95             : 
      96           0 :       fd_topo_link_t * link = &(config->topo.links[ i ]);
      97           0 :       if( (link->mcache==NULL) | (link->dcache==NULL) ) {
      98           0 :         FD_LOG_NOTICE(( "Skipping %s %lu", link->name, link->kind_id ));
      99           0 :         continue;
     100           0 :       }
     101           0 :       void * mem = config->topo.workspaces[ config->topo.objs[ link->dcache_obj_id ].wksp_id ].wksp;
     102             : 
     103           0 :       dump_link( out, link, mem );
     104           0 :     }
     105           0 :   }
     106             : 
     107           0 :   fclose( out );
     108           0 :   fd_topo_leave_workspaces( &config->topo );
     109           0 : }

Generated by: LCOV version 1.14