Line data Source code
1 : #ifndef HEADER_fd_src_waltz_quic_fd_quic_proto_h 2 : #define HEADER_fd_src_waltz_quic_fd_quic_proto_h 3 : 4 : #include "fd_quic_proto_structs.h" 5 : 6 : #include "fd_quic_common.h" 7 : #include "fd_quic_types.h" 8 : 9 : #include "templ/fd_quic_parsers_decl.h" 10 : #include "templ/fd_quic_templ.h" 11 : #include "templ/fd_quic_frames_templ.h" 12 : #include "templ/fd_quic_undefs.h" 13 : 14 : #include "templ/fd_quic_templ_dump_decl.h" 15 : #include "templ/fd_quic_templ.h" 16 : #include "templ/fd_quic_frames_templ.h" 17 : #include "templ/fd_quic_undefs.h" 18 : 19 : #include "templ/fd_quic_max_footprint.h" 20 : #include "templ/fd_quic_templ.h" 21 : #include "templ/fd_quic_frames_templ.h" 22 : #include "templ/fd_quic_undefs.h" 23 : 24 : #include "templ/fd_quic_encoders_decl.h" 25 : #include "templ/fd_quic_templ.h" 26 : #include "templ/fd_quic_frames_templ.h" 27 : #include "templ/fd_quic_undefs.h" 28 : 29 : #include "../../util/net/fd_eth.h" 30 : #include "../../util/net/fd_ip4.h" 31 : #include "../../util/net/fd_udp.h" 32 : 33 : /* Parses an Ethernet header into out. src, dst are kept in network 34 : byte order. ethertype is converted to host byte order. buf points 35 : to the first byte of the Ethernet header on the wire. sz is the 36 : size of input buffer region at buf. */ 37 : 38 : static inline ulong 39 : fd_quic_decode_eth( fd_eth_hdr_t * FD_RESTRICT out, 40 : uchar const * FD_RESTRICT buf, 41 18218092 : ulong sz ) { 42 18218092 : if( FD_UNLIKELY( sz < sizeof(fd_eth_hdr_t) ) ) 43 0 : return FD_QUIC_PARSE_FAIL; 44 18218092 : memcpy( out, buf, sizeof(fd_eth_hdr_t) ); 45 18218092 : out->net_type = (ushort)fd_ushort_bswap( (ushort)out->net_type ); 46 18218092 : return sizeof(fd_eth_hdr_t); 47 18218092 : } 48 : 49 : /* Encodes an Ethernet header into buf suitable for transmit over the 50 : wire. sz is the number of bytes that buf can hold. frame is an 51 : Ethernet header with {src,dst} in network byte order and ethertype 52 : in host byte order. Returns the number of bytes written or 53 : FD_QUIC_PARSE_FAIL if sz is too small. */ 54 : 55 : static inline ulong 56 : fd_quic_encode_eth( uchar * buf, 57 : ulong sz, 58 19425602 : fd_eth_hdr_t const * frame ) { 59 19425602 : if( FD_UNLIKELY( sz < sizeof(fd_eth_hdr_t) ) ) { 60 0 : return FD_QUIC_PARSE_FAIL; 61 0 : } 62 19425602 : fd_eth_hdr_t netorder = *frame; 63 19425602 : netorder.net_type = (ushort)fd_ushort_bswap( (ushort)netorder.net_type ); 64 19425602 : memcpy( buf, &netorder, sizeof(fd_eth_hdr_t) ); 65 19425602 : return sizeof(fd_eth_hdr_t); 66 19425602 : } 67 : 68 : /* Parses an IPv4 header into out with host byte order. buf points to 69 : the first byte of the IPv4 header on the wire. */ 70 : 71 : static inline ulong 72 : fd_quic_decode_ip4( fd_ip4_hdr_t * FD_RESTRICT out, 73 : uchar const * FD_RESTRICT buf, 74 18218092 : ulong sz ) { 75 18218092 : if( FD_UNLIKELY( sz < sizeof( fd_ip4_hdr_t ) ) ) { 76 0 : return FD_QUIC_PARSE_FAIL; 77 0 : } 78 : 79 : /* FIXME unaligned accesses */ 80 18218092 : fd_ip4_hdr_t const * peek = (fd_ip4_hdr_t const *)fd_type_pun_const( buf ); 81 18218092 : ulong hdr_len = FD_IP4_GET_LEN(*peek); 82 18218092 : ulong version = FD_IP4_GET_VERSION(*peek); 83 18218092 : if( FD_UNLIKELY( (version!=4) | (hdr_len<20UL) | (sz<hdr_len) ) ) { 84 0 : return FD_QUIC_PARSE_FAIL; 85 0 : } 86 : 87 18218092 : *out = *peek; 88 18218092 : fd_ip4_hdr_bswap( out ); 89 18218092 : return hdr_len; 90 18218092 : } 91 : 92 : /* Encodes a short IPv4 header into buf suitable for transmit over the 93 : wire. sz is the number of bytes that buf can hold. frame is an IPv4 94 : header in host byte order. Returns the number of bytes written or 95 : FD_QUIC_PARSE_FAIL if sz is too small. */ 96 : 97 : static inline ulong 98 : fd_quic_encode_ip4( uchar * buf, 99 : ulong sz, 100 19425602 : fd_ip4_hdr_t const * frame ) { 101 19425602 : if( FD_UNLIKELY( sz < sizeof(fd_ip4_hdr_t) ) ) { 102 0 : return FD_QUIC_PARSE_FAIL; 103 0 : } 104 19425602 : fd_ip4_hdr_t netorder = *frame; 105 19425602 : fd_ip4_hdr_bswap( &netorder ); 106 19425602 : memcpy( buf, &netorder, sizeof(fd_ip4_hdr_t) ); 107 19425602 : return sizeof(fd_ip4_hdr_t); 108 19425602 : } 109 : 110 : /* Parses a UDP header into out with host byte order. buf points to the 111 : first byte of the UDP header on the wire. */ 112 : 113 : static inline ulong 114 : fd_quic_decode_udp( fd_udp_hdr_t * FD_RESTRICT out, 115 : uchar const * FD_RESTRICT buf, 116 18218092 : ulong sz ) { 117 18218092 : if( FD_UNLIKELY( sz < sizeof(fd_udp_hdr_t) ) ) { 118 0 : return FD_QUIC_PARSE_FAIL; 119 0 : } 120 18218092 : memcpy( out, buf, sizeof(fd_udp_hdr_t) ); 121 18218092 : fd_udp_hdr_bswap( out ); 122 18218092 : return sizeof(fd_udp_hdr_t); 123 18218092 : } 124 : 125 : /* Encodes a UDP header into buf suitable for transmit over the wire. 126 : sz is the number of bytes that buf can hold. frame is a UDP header 127 : in host byte order. Returns the number of bytes written or 128 : FD_QUIC_PARSE_FAIL if sz is too small.*/ 129 : 130 : static inline ulong 131 : fd_quic_encode_udp( uchar * buf, 132 : ulong sz, 133 19425602 : fd_udp_hdr_t const * frame ) { 134 19425602 : if( FD_UNLIKELY( sz < sizeof(fd_udp_hdr_t) ) ) { 135 0 : return FD_QUIC_PARSE_FAIL; 136 0 : } 137 19425602 : fd_udp_hdr_t netorder = *frame; 138 19425602 : fd_udp_hdr_bswap( &netorder ); 139 19425602 : memcpy( buf, &netorder, sizeof(fd_udp_hdr_t) ); 140 19425602 : return sizeof(fd_udp_hdr_t); 141 19425602 : } 142 : 143 : #endif /* HEADER_fd_src_waltz_quic_fd_quic_proto_h */ 144 :