| 105 | } |
| 106 | |
| 107 | static int websocket_protocol_callback(lws *wsi, enum lws_callback_reasons reason, void *user, void *in, size_t len) |
| 108 | { |
| 109 | per_session_data *pss = (per_session_data *)user; |
| 110 | lws_context *context = lws_get_context(wsi); |
| 111 | context_data *ctx_data = contexts_map[context]; |
| 112 | switch(reason) |
| 113 | { |
| 114 | case LWS_CALLBACK_WSI_CREATE: |
| 115 | if(pss == nullptr) |
| 116 | { |
| 117 | return 0; |
| 118 | } |
| 119 | [[fallthrough]]; |
| 120 | case LWS_CALLBACK_ESTABLISHED: |
| 121 | { |
| 122 | sockaddr_storage peersockaddr; |
| 123 | socklen_t peersockaddr_size = sizeof(peersockaddr); |
| 124 | getpeername(lws_get_socket_fd(wsi), (sockaddr *)&peersockaddr, &peersockaddr_size); |
| 125 | NETADDR addr; |
| 126 | sockaddr_to_netaddr_websocket((sockaddr *)&peersockaddr, peersockaddr_size, &addr); |
| 127 | if(addr.type == NETTYPE_INVALID) |
| 128 | { |
| 129 | return 0; |
| 130 | } |
| 131 | |
| 132 | pss->wsi = wsi; |
| 133 | pss->addr = addr; |
| 134 | pss->send_buffer.Init(); |
| 135 | ctx_data->port_map[addr] = pss; |
| 136 | |
| 137 | char addr_str[NETADDR_MAXSTRSIZE]; |
| 138 | net_addr_str(&addr, addr_str, sizeof(addr_str), true); |
| 139 | log_trace("websockets", "Connection established with '%s'", addr_str); |
| 140 | return 0; |
| 141 | } |
| 142 | |
| 143 | case LWS_CALLBACK_CLOSED: |
| 144 | { |
| 145 | char addr_str[NETADDR_MAXSTRSIZE]; |
| 146 | net_addr_str(&pss->addr, addr_str, sizeof(addr_str), true); |
| 147 | log_trace("websockets", "Connection closed with '%s'", addr_str); |
| 148 | |
| 149 | static const unsigned char CLOSE_PACKET[] = {0x10, 0x0e, 0x00, 0x04}; |
| 150 | receive_chunk(ctx_data, pss, &CLOSE_PACKET, sizeof(CLOSE_PACKET)); |
| 151 | pss->wsi = nullptr; |
| 152 | ctx_data->port_map.erase(pss->addr); |
| 153 | return 0; |
| 154 | } |
| 155 | |
| 156 | case LWS_CALLBACK_CLIENT_WRITEABLE: |
| 157 | [[fallthrough]]; |
| 158 | case LWS_CALLBACK_SERVER_WRITEABLE: |
| 159 | { |
| 160 | websocket_chunk *chunk = pss->send_buffer.First(); |
| 161 | if(chunk == nullptr) |
| 162 | { |
| 163 | return 0; |
| 164 | } |
nothing calls this directly
no test coverage detected