Line data Source code
1 : #include "../dev.h"
2 : #include "../../../shared/commands/configure/configure.h" /* CONFIGURE_CMD_INIT */
3 : #include "../../../shared/commands/run/run.h" /* fdctl_check_configure */
4 : #include "../../../../disco/net/fd_net_tile.h"
5 : #include "../../../../disco/topo/fd_topob.h"
6 : #include "../../../../disco/topo/fd_cpu_topo.h"
7 : #include "../../../../util/net/fd_ip4.h"
8 :
9 : #include <unistd.h> /* pause */
10 :
11 : extern fd_topo_obj_callbacks_t * CALLBACKS[];
12 :
13 : fd_topo_run_tile_t
14 : fdctl_tile_run( fd_topo_tile_t const * tile );
15 :
16 : static void
17 0 : udpecho_topo( config_t * config ) {
18 0 : char const * affinity = config->development.udpecho.affinity;
19 0 : int is_auto_affinity = !strcmp( affinity, "auto" );
20 :
21 0 : ushort parsed_tile_to_cpu[ FD_TILE_MAX ];
22 0 : for( ulong i=0UL; i<FD_TILE_MAX; i++ ) parsed_tile_to_cpu[ i ] = USHORT_MAX;
23 :
24 0 : fd_topo_cpus_t cpus[1];
25 0 : fd_topo_cpus_init( cpus );
26 :
27 0 : ulong affinity_tile_cnt = 0UL;
28 0 : if( FD_LIKELY( !is_auto_affinity ) ) affinity_tile_cnt = fd_topob_parse_affinity_cstr( affinity, parsed_tile_to_cpu, 0, 1 );
29 :
30 0 : ulong tile_to_cpu[ FD_TILE_MAX ] = {0};
31 0 : for( ulong i=0UL; i<affinity_tile_cnt; i++ ) {
32 0 : ushort cpu_idx = (ushort)( parsed_tile_to_cpu[ i ] & ~FD_TOPOB_CPU_SHARED );
33 0 : if( FD_UNLIKELY( parsed_tile_to_cpu[ i ]!=USHORT_MAX && cpu_idx>=cpus->cpu_cnt ) )
34 0 : FD_LOG_ERR(( "The CPU affinity string in the configuration file under [development.udpecho.affinity] specifies a CPU index of %hu, but the system "
35 0 : "only has %lu CPUs. You should either change the CPU allocations in the affinity string, or increase the number of CPUs "
36 0 : "in the system.",
37 0 : cpu_idx, cpus->cpu_cnt ));
38 0 : tile_to_cpu[ i ] = fd_ulong_if( parsed_tile_to_cpu[ i ]==USHORT_MAX, ULONG_MAX, (ulong)parsed_tile_to_cpu[ i ] );
39 0 : }
40 0 : if( FD_LIKELY( !is_auto_affinity ) ) {
41 0 : if( FD_UNLIKELY( affinity_tile_cnt!=4UL ) )
42 0 : FD_LOG_ERR(( "Invalid [development.udpecho.affinity]: must include exactly three CPUs" ));
43 0 : }
44 :
45 : /* Reset topology from scratch */
46 0 : fd_topo_t * topo = &config->topo;
47 0 : fd_topob_new( &config->topo, config->name );
48 0 : topo->max_page_size = fd_cstr_to_shmem_page_sz( config->hugetlbfs.max_page_size );
49 :
50 0 : fd_topob_wksp( topo, "metric" );
51 0 : fd_topob_wksp( topo, "metric_in" );
52 0 : fd_topos_net_tiles( topo, config->layout.net_tile_count, &config->net, config->tiles.netlink.max_routes, config->tiles.netlink.max_peer_routes, config->tiles.netlink.max_neighbors, 0, tile_to_cpu );
53 0 : char const * net_tile_name = fd_net_tile_name( config->net.provider );
54 0 : fd_topob_tile( topo, "metric", "metric", "metric_in", tile_to_cpu[ topo->tile_cnt ], 0, 0, 0, 1 );
55 :
56 0 : fd_topob_wksp( topo, "l4swap" );
57 0 : fd_topob_tile( topo, "l4swap", "l4swap", "l4swap", tile_to_cpu[ topo->tile_cnt ], 0, 0, 0, 0 );
58 :
59 0 : fd_topob_link( topo, "quic_net", "l4swap", 2048UL, FD_NET_MTU, 1UL );
60 0 : fd_topob_tile_out( topo, "l4swap", 0UL, "quic_net", 0UL );
61 0 : fd_topob_tile_in( topo, net_tile_name, 0UL, "metric_in", "quic_net", 0UL, FD_TOPOB_UNRELIABLE, FD_TOPOB_POLLED );
62 :
63 0 : fd_topos_net_rx_link( topo, "net_quic", 0UL, config->net.ingress_buffer_size );
64 0 : fd_topob_tile_in( topo, "l4swap", 0UL, "metric_in", "net_quic", 0UL, FD_TOPOB_UNRELIABLE, FD_TOPOB_POLLED );
65 :
66 0 : fd_topos_net_tile_finish( topo, 0UL );
67 0 : if( FD_UNLIKELY( is_auto_affinity ) ) fd_topob_auto_layout( topo, 0 );
68 0 : topo->agave_affinity_cnt = 0;
69 0 : fd_topob_waker( topo );
70 0 : fd_topob_finish( topo, CALLBACKS );
71 0 : fd_topo_print_log( /* stdout */ 1, topo );
72 0 : }
73 :
74 : void
75 : udpecho_cmd_args( int * pargc,
76 : char *** pargv,
77 0 : args_t * args ) {
78 0 : ushort port_l = fd_env_strip_cmdline_ushort( pargc, pargv, "--port", NULL, 0 );
79 0 : ushort port_s = fd_env_strip_cmdline_ushort( pargc, pargv, "-p", NULL, 0 );
80 0 : ushort port = port_s ? port_s : port_l;
81 0 : if( FD_UNLIKELY( !port ) ) FD_LOG_ERR(( "Missing --port argument" ));
82 0 : args->udpecho.listen_port = port;
83 0 : }
84 :
85 : void
86 : udpecho_cmd_fn( args_t * args,
87 0 : config_t * config ) {
88 0 : udpecho_topo( config );
89 0 : fd_topo_t * topo = &config->topo;
90 0 : ulong net_tile_id = fd_topo_find_tile( topo, fd_net_tile_name( config->net.provider ), 0UL );
91 0 : if( FD_UNLIKELY( net_tile_id==ULONG_MAX ) ) FD_LOG_ERR(( "net tile not found" ));
92 0 : fd_topo_tile_t * net_tile = &topo->tiles[ net_tile_id ];
93 0 : fd_topo_tile_t * metric_tile = &topo->tiles[ fd_topo_find_tile( topo, "metric", 0UL ) ];
94 :
95 0 : net_tile->net.legacy_transaction_listen_port = args->udpecho.listen_port;
96 0 : config->tiles.quic.regular_transaction_listen_port = args->udpecho.listen_port;
97 :
98 0 : if( FD_UNLIKELY( !fd_cstr_to_ip4_addr( config->tiles.metric.prometheus_listen_address, &metric_tile->metric.prometheus_listen_addr ) ) )
99 0 : FD_LOG_ERR(( "failed to parse prometheus listen address `%s`", config->tiles.metric.prometheus_listen_address ));
100 0 : metric_tile->metric.prometheus_listen_port = config->tiles.metric.prometheus_listen_port;
101 :
102 0 : configure_stage( &fd_cfg_stage_sysctl, CONFIGURE_CMD_INIT, config );
103 0 : configure_stage( &fd_cfg_stage_hugetlbfs, CONFIGURE_CMD_INIT, config );
104 0 : configure_stage( &fd_cfg_stage_bonding, CONFIGURE_CMD_INIT, config );
105 0 : configure_stage( &fd_cfg_stage_ethtool_channels, CONFIGURE_CMD_INIT, config );
106 0 : configure_stage( &fd_cfg_stage_ethtool_offloads, CONFIGURE_CMD_INIT, config );
107 0 : configure_stage( &fd_cfg_stage_ethtool_loopback, CONFIGURE_CMD_INIT, config );
108 0 : configure_stage( &fd_cfg_stage_sysfs_poll, CONFIGURE_CMD_INIT, config );
109 :
110 0 : fdctl_check_configure( config );
111 : /* FIXME this allocates lots of memory unnecessarily */
112 0 : initialize_workspaces( config );
113 0 : initialize_stacks( config );
114 0 : if( 0==strcmp( config->net.provider, "xdp" ) ) {
115 0 : fd_topo_install_xdp_simple( &config->topo, config->net.bind_address_parsed );
116 0 : }
117 0 : fd_topo_join_workspaces( topo, FD_SHMEM_JOIN_MODE_READ_WRITE, FD_TOPO_CORE_DUMP_LEVEL_DISABLED );
118 0 : if( 0==strcmp( config->net.provider, "mlx5" ) ) {
119 0 : fd_topo_install_mlx5( topo, NULL );
120 0 : }
121 :
122 : /* FIXME allow running sandboxed/multiprocess */
123 0 : fd_topo_run_single_process( topo, 2, config->uid, config->gid, fdctl_tile_run );
124 0 : for(;;) pause();
125 0 : }
126 :
127 : action_t fd_action_udpecho = {
128 : .name = "udpecho",
129 : .args = udpecho_cmd_args,
130 : .fn = udpecho_cmd_fn,
131 : .perm = dev_cmd_perm,
132 : .description = "Run a UDP echo server"
133 : };
|