Line data Source code
1 : #ifndef HEADER_fd_src_app_fddev_rpc_client_h 2 : #define HEADER_fd_src_app_fddev_rpc_client_h 3 : 4 : #include "../../../util/fd_util.h" 5 : 6 : #include <poll.h> 7 : 8 : /* This is a poor RPC client implementation to retrieve information from 9 : the Agave validator. It is not a Firedancer RPC implementation 10 : and should not be used in that way. It is just here to provide code 11 : interoperability. It is not fuzzed or hardened, and should not be 12 : used in any code that matters. */ 13 : 14 12 : #define FD_RPC_CLIENT_SUCCESS (0) 15 6 : #define FD_RPC_CLIENT_PENDING (-1) 16 : #define FD_RPC_CLIENT_ERR_NOT_FOUND (-2) 17 0 : #define FD_RPC_CLIENT_ERR_TOO_LARGE (-3) 18 0 : #define FD_RPC_CLIENT_ERR_TOO_MANY (-4) 19 0 : #define FD_RPC_CLIENT_ERR_MALFORMED (-5) 20 0 : #define FD_RPC_CLIENT_ERR_NETWORK (-6) 21 : 22 0 : #define FD_RPC_CLIENT_ALIGN (8UL) 23 0 : #define FD_RPC_CLIENT_FOOTPRINT (273424UL) 24 : 25 390 : #define FD_RPC_CLIENT_STATE_NONE (0UL) 26 6 : #define FD_RPC_CLIENT_STATE_CONNECTED (1UL) 27 6 : #define FD_RPC_CLIENT_STATE_SENT (2UL) 28 : #define FD_RPC_CLIENT_STATE_RECEIVED (3UL) 29 6 : #define FD_RPC_CLIENT_STATE_FINISHED (4UL) 30 : 31 4454075 : #define FD_RPC_CLIENT_REQUEST_CNT (128UL) 32 : 33 6 : #define FD_RPC_CLIENT_METHOD_LATEST_BLOCK_HASH (0UL) 34 6 : #define FD_RPC_CLIENT_METHOD_TRANSACTION_COUNT (1UL) 35 : 36 : typedef struct { 37 : long request_id; 38 : ulong method; 39 : 40 : long status; 41 : 42 : union { 43 : struct { 44 : uchar block_hash[ 32 ]; 45 : } latest_block_hash; 46 : 47 : struct { 48 : ulong transaction_count; 49 : } transaction_count; 50 : } result; 51 : } fd_rpc_client_response_t; 52 : 53 : struct fd_rpc_client_private; 54 : typedef struct fd_rpc_client_private fd_rpc_client_t; 55 : 56 : FD_PROTOTYPES_BEGIN 57 : 58 0 : FD_FN_CONST static inline ulong fd_rpc_client_align ( void ) { return FD_RPC_CLIENT_ALIGN; } 59 0 : FD_FN_CONST static inline ulong fd_rpc_client_footprint( void ) { return FD_RPC_CLIENT_FOOTPRINT; } 60 : 61 : void * 62 : fd_rpc_client_new( void * mem, 63 : uint rpc_addr, 64 : ushort rpc_port ); 65 : 66 3 : static inline fd_rpc_client_t * fd_rpc_client_join ( void * _rpc ) { return (fd_rpc_client_t *)_rpc; } 67 3 : static inline void * fd_rpc_client_leave ( fd_rpc_client_t * rpc ) { return (void *) rpc; } 68 3 : static inline void * fd_rpc_client_delete( void * _rpc ) { return (void *)_rpc; } 69 : 70 : /* Wait until the RPC server is ready to receive requests. This is a 71 : blocking call. If timeout_ns is -1 it will wait forever, otherwise 72 : it will wait at most this amount of nanoseconds before returning 73 : FD_RPC_CLIENT_ERR_NETWORK. 74 : 75 : Returns FD_RPC_CLIENT_SUCCESS once the server is ready. */ 76 : 77 : long 78 : fd_rpc_client_wait_ready( fd_rpc_client_t * rpc, 79 : long timeout_ns ); 80 : 81 : /* Make an RPC request to get the latest block hash. 82 : 83 : On success returns a non-negative request ID. On failure, returns a 84 : negative value, one of FD_RPC_ERR_*. In particular, if there are too 85 : many requests in flight already FD_RPC_ERR_TOO_MANY is returned. */ 86 : 87 : long 88 : fd_rpc_client_request_latest_block_hash( fd_rpc_client_t * rpc ); 89 : 90 : /* Make an RPC request to the current transaction count. 91 : 92 : On success returns a non-negative request ID. On failure, returns a 93 : negative value, one of FD_RPC_ERR_*. In particular, if there are too 94 : many requests in flight already FD_RPC_ERR_TOO_MANY is returned. */ 95 : 96 : long 97 : fd_rpc_client_request_transaction_count( fd_rpc_client_t * rpc ); 98 : 99 : /* Service all the RPC connections. This sends, receives, parses and 100 : otherwise does all the work required to poll and make forward 101 : progress on receiving responses for RPC requests that have been made. 102 : 103 : This is non-blocking and will always return immediately after sending 104 : and receiving data. To operate in blocking mode, where the function 105 : will not return unless some forward progress has been made, set wait 106 : to true. The function may still return without a response available 107 : when wait is true. 108 : 109 : Returns 1 if the RPC client did any work to progress a connection, 110 : otherwise returns 0. */ 111 : 112 : int 113 : fd_rpc_client_service( fd_rpc_client_t * rpc, 114 : int wait ); 115 : 116 : /* Get the response of the RPC request with a given ID. If the response 117 : is not yet available, the status will be FD_RPC_PENDING, otherwise it 118 : is one of FD_RPC_SUCCESS or FD_RPC_ERR_*. 119 : 120 : If wait is true, the function will block until an error occurs or the 121 : response is available, and it will not return FD_RPC_PENDING. 122 : 123 : If the request_id does not exist or has already been closed, 124 : NULL is returned. */ 125 : 126 : fd_rpc_client_response_t * 127 : fd_rpc_client_status( fd_rpc_client_t * rpc, 128 : long request_id, 129 : int wait ); 130 : 131 : /* Close the request with the given ID. If the request is still pending, 132 : it will be abandoned. If the request has already been closed or does 133 : not exist the function will silently return. 134 : 135 : All RPC requests need to be closed once you are done inspecting the 136 : results, otherwise the RPC client will run out of resources and 137 : subsequent requests will fail with FD_RPC_ERR_TOO_MANY. */ 138 : 139 : void 140 : fd_rpc_client_close( fd_rpc_client_t * rpc, 141 : long request_id ); 142 : 143 : FD_PROTOTYPES_END 144 : 145 : #endif /* HEADER_fd_src_app_fddev_rpc_client_h */