quickjs-tart

quickjs-based runtime for wallet-core logic
Log | Files | Refs | README | LICENSE

curl_ws_recv.md (4381B)


      1 ---
      2 c: Copyright (C) Daniel Stenberg, <daniel@haxx.se>, et al.
      3 SPDX-License-Identifier: curl
      4 Title: curl_ws_recv
      5 Section: 3
      6 Source: libcurl
      7 See-also:
      8   - curl_easy_getinfo (3)
      9   - curl_easy_perform (3)
     10   - curl_easy_setopt (3)
     11   - curl_ws_send (3)
     12   - libcurl-ws (3)
     13 Protocol:
     14   - WS
     15 Added-in: 7.86.0
     16 ---
     17 
     18 # NAME
     19 
     20 curl_ws_recv - receive WebSocket data
     21 
     22 # SYNOPSIS
     23 
     24 ~~~c
     25 #include <curl/curl.h>
     26 
     27 CURLcode curl_ws_recv(CURL *curl, void *buffer, size_t buflen,
     28                       size_t *recv, const struct curl_ws_frame **meta);
     29 ~~~
     30 
     31 # DESCRIPTION
     32 
     33 Retrieves as much as possible of a received WebSocket frame into the *buffer*,
     34 but not more than *buflen* bytes. *recv* is set to the number of bytes
     35 actually stored.
     36 
     37 If the function call is successful, the *meta* pointer gets set to point to a
     38 *const struct curl_ws_frame* that contains information about the received
     39 data. That struct must not be freed and its contents must not be relied upon
     40 anymore once another WebSocket function is called. See curl_ws_meta(3) for
     41 more details on that struct.
     42 
     43 The application must check `meta->bytesleft` to determine whether the complete
     44 frame has been received. If more payload is pending, the application must call
     45 this function again with an updated *buffer* and *buflen* to resume receiving.
     46 This may for example happen when the data does not fit into the provided
     47 buffer or when not all frame data has been delivered over the network yet.
     48 
     49 If the application wants to read the metadata without consuming any payload,
     50 it may call this function with a *buflen* of zero. Setting *buffer* to a NULL
     51 pointer is permitted in this case. Note that frames without payload are
     52 consumed by this action.
     53 
     54 If the received message consists of multiple fragments, the *CURLWS_CONT* bit
     55 is set in all frames except the final one. The appropriate *CURLWS_TEXT* or
     56 *CURLWS_BINARY* flag is set in every frame, regardless whether it is the first
     57 fragment, an intermediate fragment or the final fragment. The application is
     58 responsible for reassembling fragmented messages. Special care must be taken
     59 to correctly handle control frames (i.e. CLOSE, PING and PONG) arriving in
     60 between consecutive fragments of a fragmented TEXT or BINARY message. See
     61 curl_ws_meta(3) for more details on *CURLWS_CONT*.
     62 
     63 The WebSocket protocol consists of *messages* that can be delivered over the
     64 wire as one or more *frames* - but since a frame can be too large to buffer in
     65 memory, libcurl may need to deliver partial frames to the application.
     66 Fragments, or chunks, of frames.
     67 
     68 # %PROTOCOLS%
     69 
     70 # EXAMPLE
     71 
     72 ~~~c
     73 int main(void)
     74 {
     75   char buffer[256];
     76   size_t offset = 0;
     77   CURLcode res = CURLE_OK;
     78   CURL *curl = curl_easy_init();
     79 
     80   curl_easy_setopt(curl, CURLOPT_URL, "wss://example.com/");
     81   curl_easy_setopt(curl, CURLOPT_CONNECT_ONLY, 2L);
     82   /* start HTTPS connection and upgrade to WSS, then return control */
     83   curl_easy_perform(curl);
     84 
     85   /* Note: This example neglects fragmented messages. (CURLWS_CONT bit)
     86            A real application must handle them appropriately. */
     87 
     88   while(!res) {
     89     size_t recv;
     90     const struct curl_ws_frame *meta;
     91     res = curl_ws_recv(curl, buffer + offset, sizeof(buffer) - offset, &recv,
     92                        &meta);
     93     offset += recv;
     94 
     95     if(res == CURLE_OK) {
     96       if(meta->bytesleft == 0)
     97         break; /* finished receiving */
     98       if(meta->bytesleft > sizeof(buffer) - offset)
     99         res = CURLE_TOO_LARGE;
    100     }
    101 
    102     if(res == CURLE_AGAIN)
    103       /* in real application: wait for socket here, e.g. using select() */
    104       res = CURLE_OK;
    105   }
    106 
    107   curl_easy_cleanup(curl);
    108   return (int)res;
    109 }
    110 ~~~
    111 
    112 # %AVAILABILITY%
    113 
    114 # RETURN VALUE
    115 
    116 This function returns a CURLcode indicating success or error.
    117 
    118 CURLE_OK (0) means everything was OK, non-zero means an error occurred, see
    119 libcurl-errors(3). If CURLOPT_ERRORBUFFER(3) was set with curl_easy_setopt(3)
    120 there can be an error message stored in the error buffer when non-zero is
    121 returned.
    122 
    123 Returns **CURLE_GOT_NOTHING** if the associated connection is closed.
    124 
    125 Instead of blocking, the function returns **CURLE_AGAIN**. The correct
    126 behavior is then to wait for the socket to signal readability before calling
    127 this function again.
    128 
    129 Any other non-zero return value indicates an error. See the libcurl-errors(3)
    130 man page for the full list with descriptions.
    131 
    132 Returns **CURLE_GOT_NOTHING** if the associated connection is closed.