Browse Source

Merge branch 'feature/httpd_low_level_apis' into 'master'

esp_http_server: Expose low level socket send/recv APIs

Closes IDFGH-1910

See merge request espressif/esp-idf!9084
Mahavir Jain 5 years ago
parent
commit
d7e33d60fa

+ 47 - 0
components/esp_http_server/include/esp_http_server.h

@@ -1292,6 +1292,53 @@ static inline esp_err_t httpd_resp_send_500(httpd_req_t *r) {
  */
 int httpd_send(httpd_req_t *r, const char *buf, size_t buf_len);
 
+/**
+ * A low level API to send data on a given socket
+ *
+ * @note This API is not recommended to be used in any request handler.
+ * Use this only for advanced use cases, wherein some asynchronous
+ * data is to be sent over a socket.
+ *
+ * This internally calls the default send function, or the function registered by
+ * httpd_sess_set_send_override().
+ *
+ * @param[in] hd        server instance
+ * @param[in] sockfd    session socket file descriptor
+ * @param[in] buf       buffer with bytes to send
+ * @param[in] buf_len   data size
+ * @param[in] flags     flags for the send() function
+ * @return
+ *  - Bytes : The number of bytes sent successfully
+ *  - HTTPD_SOCK_ERR_INVALID  : Invalid arguments
+ *  - HTTPD_SOCK_ERR_TIMEOUT  : Timeout/interrupted while calling socket send()
+ *  - HTTPD_SOCK_ERR_FAIL     : Unrecoverable error while calling socket send()
+ */
+int httpd_socket_send(httpd_handle_t hd, int sockfd, const char *buf, size_t buf_len, int flags);
+
+/**
+ * A low level API to receive data from a given socket
+ *
+ * @note This API is not recommended to be used in any request handler.
+ * Use this only for advanced use cases, wherein some asynchronous
+ * communication is required.
+ *
+ * This internally calls the default recv function, or the function registered by
+ * httpd_sess_set_recv_override().
+ *
+ * @param[in] hd        server instance
+ * @param[in] sockfd    session socket file descriptor
+ * @param[in] buf       buffer with bytes to send
+ * @param[in] buf_len   data size
+ * @param[in] flags     flags for the send() function
+ * @return
+ *  - Bytes : The number of bytes received successfully
+ *  - 0     : Buffer length parameter is zero / connection closed by peer
+ *  - HTTPD_SOCK_ERR_INVALID  : Invalid arguments
+ *  - HTTPD_SOCK_ERR_TIMEOUT  : Timeout/interrupted while calling socket recv()
+ *  - HTTPD_SOCK_ERR_FAIL     : Unrecoverable error while calling socket recv()
+ */
+int httpd_socket_recv(httpd_handle_t hd, int sockfd, char *buf, size_t buf_len, int flags);
+
 /** End of Request / Response
  * @}
  */

+ 24 - 0
components/esp_http_server/src/httpd_txrx.c

@@ -599,3 +599,27 @@ int httpd_default_recv(httpd_handle_t hd, int sockfd, char *buf, size_t buf_len,
     }
     return ret;
 }
+
+int httpd_socket_send(httpd_handle_t hd, int sockfd, const char *buf, size_t buf_len, int flags)
+{
+    struct sock_db *sess = httpd_sess_get(hd, sockfd);
+    if (!sess) {
+        return ESP_ERR_INVALID_ARG;
+    }
+    if (!sess->send_fn) {
+        return ESP_ERR_INVALID_STATE;
+    }
+    return sess->send_fn(hd, sockfd, buf, buf_len, flags);
+}
+
+int httpd_socket_recv(httpd_handle_t hd, int sockfd, char *buf, size_t buf_len, int flags)
+{
+    struct sock_db *sess = httpd_sess_get(hd, sockfd);
+    if (!sess) {
+        return ESP_ERR_INVALID_ARG;
+    }
+    if (!sess->recv_fn) {
+        return ESP_ERR_INVALID_STATE;
+    }
+    return sess->recv_fn(hd, sockfd, buf, buf_len, flags);
+}

+ 3 - 5
examples/protocols/http_server/advanced_tests/main/tests.c

@@ -255,8 +255,6 @@ static esp_err_t leftover_data_post_handler(httpd_req_t *req)
     return ESP_OK;
 }
 
-extern int httpd_default_send(httpd_handle_t hd, int sockfd, const char *buf, unsigned buf_len, int flags);
-
 static void generate_async_resp(void *arg)
 {
     char buf[250];
@@ -272,10 +270,10 @@ static void generate_async_resp(void *arg)
 
     snprintf(buf, sizeof(buf), HTTPD_HDR_STR,
          strlen(STR));
-    httpd_default_send(hd, fd, buf, strlen(buf), 0);
+    httpd_socket_send(hd, fd, buf, strlen(buf), 0);
     /* Space for sending additional headers based on set_header */
-    httpd_default_send(hd, fd, "\r\n", strlen("\r\n"), 0);
-    httpd_default_send(hd, fd, STR, strlen(STR), 0);
+    httpd_socket_send(hd, fd, "\r\n", strlen("\r\n"), 0);
+    httpd_socket_send(hd, fd, STR, strlen(STR), 0);
 #undef STR
     free(arg);
 }