//////////////////////////////////////////////////////////// //~ Command buff types Struct(NET_W32_Cmd) { NET_W32_Cmd *next; NET_Key key; String data; b32 burst; }; Struct(NET_W32_CmdList) { i64 count; NET_W32_Cmd *first; NET_W32_Cmd *last; }; Struct(NET_W32_CmdBuff) { Arena *arena; NET_W32_CmdList cmds; }; //////////////////////////////////////////////////////////// //~ Message buff types Struct(NET_W32_MsgBuff) { Arena *arena; NET_MsgList msgs; }; //////////////////////////////////////////////////////////// //~ Packet types Enum(NET_W32_PacketFlag) { NET_W32_PacketFlag_None = 0, NET_W32_PacketFlag_EndMsg = (1 << 0), NET_W32_PacketFlag_Heartbeat = (1 << 2), // NET_W32_PacketFlag_Burst = (1 << 3), }; Struct(NET_W32_PacketHeader) { u32 magic; NET_W32_PacketFlag flags; i64 seq; i64 msg_seq; i64 bottom_ack; u64 ack_bits; }; Struct(NET_W32_Packet) { NET_W32_Packet *next; NET_W32_Packet *prev; NET_W32_PacketFlag flags; i64 seq; i64 msg_seq; String data; i64 last_sent_ns; }; //////////////////////////////////////////////////////////// //~ Peer types Struct(NET_W32_Peer) { NET_W32_Peer *next; NET_W32_Peer *prev; NET_W32_Peer *next_in_bin; NET_W32_Peer *prev_in_bin; u64 hash; NET_Key key; i64 remote_bottom_ack; u64 remote_ack_bits; i64 bottom_ack; u64 ack_bits; NET_W32_Packet *first_remote_packet; NET_W32_Packet *last_remote_packet; NET_W32_Packet *first_fragmented_packet; NET_W32_Packet *last_fragmented_packet; NET_W32_Packet *first_contiguous_packet; NET_W32_Packet *last_contiguous_packet; i64 seq; i64 msg_seq; String fragment; i64 last_packet_received_ns; i64 last_packet_sent_ns; i64 num_msg_packets_received_this_frame; }; Struct(NET_W32_PeerBin) { NET_W32_Peer *first; NET_W32_Peer *last; }; //////////////////////////////////////////////////////////// //~ Pipe types Struct(NET_W32_Pipe) { //- Shared data NET_W32_Pipe *next; NET_W32_Pipe *prev; Atomic64 desired_port; // >64k means ephemeral TicketMutex back_cmd_buff_seq_tm; i64 back_cmd_buff_seq; NET_W32_CmdBuff cmd_buffs[2]; TicketMutex back_msg_buff_seq_tm; i64 back_msg_buff_seq; NET_W32_MsgBuff msg_buffs[2]; //- Worker data NET_W32_Peer *first_peer; NET_W32_Peer *last_peer; i64 peer_bins_count; NET_W32_PeerBin *peer_bins; u64 bound_port; SOCKET udp; }; //////////////////////////////////////////////////////////// //~ State types Struct(NET_W32_DummySocket) { SOCKET sock; i32 addr_size; struct sockaddr_storage addr; }; Struct(NET_W32_Ctx) { TicketMutex pipes_tm; i64 pipes_count; NET_W32_Pipe *first_pipe; NET_W32_Pipe *last_pipe; NET_W32_Peer *first_free_peer; NET_W32_Packet *first_free_packet; NET_W32_DummySocket wake_send_sock; NET_W32_DummySocket wake_recv_sock; }; extern NET_W32_Ctx NET_W32; //////////////////////////////////////////////////////////// //~ Helpers NET_W32_DummySocket NET_W32_CreateDummySocket(void); NET_W32_Pipe *NET_W32_PipeFromHandle(NET_PipeHandle pipe_handle); NET_Key NET_W32_KeyFromAddress(struct sockaddr_in6 addr); struct sockaddr_in6 NET_W32_AddressFromKey(NET_Key key); u64 NET_W32_HashFromKey(NET_Key key); void NET_W32_SignalWorker(void); NET_W32_Peer *NET_W32_TouchPeerFromKey(NET_W32_Pipe *pipe, NET_Key key); //////////////////////////////////////////////////////////// //~ Worker void NET_W32_TickForever(WaveLaneCtx *lane);