44 * This source is part of "libxutils" project
55 * 2015-2023 Sun Dro (f4tb0y@protonmail.com)
66 *
7- * @brief Implementation of high performance event based non-blocking Web Socket server.
7+ * @brief Implementation of high performance event based non-blocking WS/WSS echo server.
88 * The library will use poll(), WSAPoll(), or epoll() depending on the operating system.
99 */
1010
@@ -106,6 +106,7 @@ int handshake_answer(xapi_ctx_t *pCtx, xapi_data_t *pData)
106106
107107int send_pong (xapi_data_t * pData )
108108{
109+ session_data_t * pSession = (session_data_t * )pData -> pSessionData ;
109110 xws_status_t status ;
110111 xws_frame_t frame ;
111112
@@ -124,16 +125,17 @@ int send_pong(xapi_data_t *pData)
124125 XAPI_PutTxBuff (pData , & frame .buffer );
125126 XWebFrame_Clear (& frame );
126127
128+ pSession -> nTxCount ++ ;
127129 return XAPI_EnableEvent (pData , XPOLLOUT );
128130}
129131
130- int send_response (xapi_data_t * pData , const char * pPayload , size_t nLength )
132+ int send_response (xapi_data_t * pData , const uint8_t * pPayload , size_t nLength )
131133{
132134 session_data_t * pSession = (session_data_t * )pData -> pSessionData ;
133135 xws_status_t status ;
134136 xws_frame_t frame ;
135137
136- status = XWebFrame_Create (& frame , ( uint8_t * ) pPayload , nLength , XWS_TEXT , XTRUE );
138+ status = XWebFrame_Create (& frame , pPayload , nLength , XWS_TEXT , XTRUE );
137139 if (status != XWS_ERR_NONE )
138140 {
139141 xloge ("Failed to create WS frame: %s" ,
@@ -145,8 +147,6 @@ int send_response(xapi_data_t *pData, const char *pPayload, size_t nLength)
145147 xlogn ("Sending response: fd(%d), buff(%zu)" ,
146148 (int )pData -> sock .nFD , frame .buffer .nUsed );
147149
148- xlogn ("Response payload: %s" , pPayload );
149-
150150 XAPI_PutTxBuff (pData , & frame .buffer );
151151 XWebFrame_Clear (& frame );
152152
@@ -158,50 +158,24 @@ int handle_frame(xapi_ctx_t *pCtx, xapi_data_t *pData)
158158{
159159 xws_frame_t * pFrame = (xws_frame_t * )pData -> pPacket ;
160160 session_data_t * pSession = (session_data_t * )pData -> pSessionData ;
161+ pSession -> nRxCount ++ ;
161162
162163 xlogn ("Received WS frame: fd(%d), type(%s), fin(%s), hdr(%zu), pl(%zu), buff(%zu)" ,
163164 (int )pData -> sock .nFD , XWS_FrameTypeStr (pFrame -> eType ), pFrame -> bFin ?"true" :"false" ,
164165 pFrame -> nHeaderSize , pFrame -> nPayloadLength , pFrame -> buffer .nUsed );
165166
166- if (pFrame -> eType == XWS_CLOSE )
167- {
168- xlogd ("Received CLOSE frame" );
169- return XSTDERR ;
170- }
171- else if (pFrame -> eType == XWS_PING )
172- {
173- pSession -> nRxCount ++ ;
174- pSession -> nTxCount ++ ;
175- return send_pong (pData );
176- }
177- else if (pFrame -> eType != XWS_TEXT )
178- {
179- char sPayload [XSTR_MIN ];
167+ if (pFrame -> eType == XWS_PING ) return send_pong (pData );
168+ else if (pFrame -> eType == XWS_CLOSE ) return XSTDERR ;
180169
181- size_t nLength = xstrncpyf (
182- sPayload , sizeof (sPayload ),
183- "{\"error\":\"unsupported type\"}" );
184-
185- return send_response (pData , sPayload , nLength );
186- }
187-
188- /* Received close request, we should destroy this session */
189- const char * pPayload = (const char * )XWebFrame_GetPayload (pFrame );
190- if (xstrused (pPayload )) xlogn ("WS frame payload: %s" , pPayload );
191-
192- pSession -> nRxCount ++ ;
193- return XAPI_EnableEvent (pData , XPOLLOUT );
194- }
195-
196- int send_answer (xapi_ctx_t * pCtx , xapi_data_t * pData )
197- {
198- char sPayload [XSTR_MIN ];
170+ const uint8_t * pPayload = XWebFrame_GetPayload (pFrame );
171+ size_t nLength = XWebFrame_GetPayloadLength (pFrame );
172+ XASSERT_RET ((pPayload != NULL && nLength ), XSTDOK );
199173
200- size_t nLength = xstrncpyf (
201- sPayload , sizeof (sPayload ),
202- "{\"message\":\"here is your response\"}" );
174+ if (pFrame -> eType == XWS_TEXT && xstrused ((const char * )pPayload ))
175+ xlogn ("Payload (%zu bytes): %s" , nLength , (const char * )pPayload );
203176
204- return send_response (pData , sPayload , nLength );
177+ /* Send payload back to the client (echo) */
178+ return send_response (pData , pPayload , nLength );
205179}
206180
207181int init_session (xapi_ctx_t * pCtx , xapi_data_t * pData )
@@ -243,8 +217,6 @@ int service_callback(xapi_ctx_t *pCtx, xapi_data_t *pData)
243217 return destroy_session (pCtx , pData );
244218 case XAPI_CB_READ :
245219 return handle_frame (pCtx , pData );
246- case XAPI_CB_WRITE :
247- return send_answer (pCtx , pData );
248220 case XAPI_CB_ERROR :
249221 return print_error (pCtx , pData );
250222 case XAPI_CB_STATUS :
@@ -272,11 +244,11 @@ void display_usage(const char *pName)
272244 printf ("============================================================\n" );
273245 printf ("Usage: %s [options]\n\n" , pName );
274246 printf ("Options are:\n" );
275- printf (" -a <path > # Listener address (%s*%s)\n" , XSTR_CLR_RED , XSTR_FMT_RESET );
276- printf (" -p <path > # Listener port (%s*%s)\n" , XSTR_CLR_RED , XSTR_FMT_RESET );
277- printf (" -c <format> # SSL Cert file path\n" );
278- printf (" -k <format> # SSL Key file path\n" );
279- printf (" -r <format> # SSL CA file path\n" );
247+ printf (" -a <addr > # Listener address (%s*%s)\n" , XSTR_CLR_RED , XSTR_FMT_RESET );
248+ printf (" -p <port > # Listener port (%s*%s)\n" , XSTR_CLR_RED , XSTR_FMT_RESET );
249+ printf (" -c <path> # SSL Cert file path\n" );
250+ printf (" -k <path> # SSL Key file path\n" );
251+ printf (" -r <path> # SSL CA file path\n" );
280252 printf (" -s # SSL (WSS) mode\n" );
281253 printf (" -h # Version and usage\n\n" );
282254}
@@ -377,7 +349,7 @@ int main(int argc, char* argv[])
377349 endpt .certs .pCaPath = args .sCaPath ;
378350 endpt .certs .pKeyPath = args .sKeyPath ;
379351 endpt .certs .pCertPath = args .sCertPath ;
380- endpt .certs .nVerifyFlags = SSL_VERIFY_NONE ;
352+ endpt .certs .nVerifyFlags = SSL_VERIFY_PEER ;
381353 }
382354
383355 if (XAPI_Listen (& api , & endpt ) < 0 )
0 commit comments