commit b63d9f5515e037e4638a1c8b7e1d31b3da28f15a
parent 556f775124fa444d2d0f5992d2105b9fd26810f5
Author: Evgeny Grin (Karlson2k) <k2k@drgrin.dev>
Date: Mon, 20 Jul 2026 20:03:07 +0200
MHD_response_from_{fd,pipe}(): close FD on failure
Diffstat:
4 files changed, 35 insertions(+), 18 deletions(-)
diff --git a/src/examples2/demo.c b/src/examples2/demo.c
@@ -1169,11 +1169,7 @@ generate_page (void *cls,
0LLU /* offset */,
(uint_fast64_t)buf.st_size);
if (NULL == response)
- {
- /* internal error (i.e. out of memory) */
- (void)close (fd);
- return MHD_action_abort_request (request);
- }
+ return MHD_action_abort_request (request); /* internal error (i.e. out of memory) */
/* add mime type if we had one */
if (NULL != mime)
diff --git a/src/include/microhttpd2.h b/src/include/microhttpd2.h
@@ -6566,8 +6566,9 @@ MHD_response_from_iovec (
* @param size size of the data portion of the response;
* sizes larger than 2 GiB may be not supported by OS or
* MHD build; see #MHD_LIB_INFO_FIXED_HAS_LARGE_FILE
- * @return NULL on error (i.e. invalid arguments, out of memory)
- * FIXME: Close FD on error?
+ * @return new response object on success,
+ * NULL on failure (i.e. invalid arguments, out of memory),
+ * @p fd is closed automatically in case of failure
* @ingroup response
*/
MHD_EXTERN_ struct MHD_Response *
@@ -6592,8 +6593,9 @@ MHD_FN_PAR_FD_READ_ (2);
* @param fd file descriptor referring to a read-end of a pipe with the
* data; will be closed when response is destroyed;
* fd should be in 'blocking' mode
- * @return NULL on error (i.e. invalid arguments, out of memory)
- * FIXME: Close pipe FD on error?
+ * @return new response object on success,
+ * NULL on failure (i.e. invalid arguments, out of memory),
+ * @p fd is closed automatically in case of failure
* @ingroup response
*/
MHD_EXTERN_ struct MHD_Response *
diff --git a/src/include/microhttpd2_main.h.in b/src/include/microhttpd2_main.h.in
@@ -1649,8 +1649,9 @@ MHD_response_from_iovec (
* @param size size of the data portion of the response;
* sizes larger than 2 GiB may be not supported by OS or
* MHD build; see #MHD_LIB_INFO_FIXED_HAS_LARGE_FILE
- * @return NULL on error (i.e. invalid arguments, out of memory)
- * FIXME: Close FD on error?
+ * @return new response object on success,
+ * NULL on failure (i.e. invalid arguments, out of memory),
+ * @p fd is closed automatically in case of failure
* @ingroup response
*/
MHD_EXTERN_ struct MHD_Response *
@@ -1675,8 +1676,9 @@ MHD_FN_PAR_FD_READ_ (2);
* @param fd file descriptor referring to a read-end of a pipe with the
* data; will be closed when response is destroyed;
* fd should be in 'blocking' mode
- * @return NULL on error (i.e. invalid arguments, out of memory)
- * FIXME: Close pipe FD on error?
+ * @return new response object on success,
+ * NULL on failure (i.e. invalid arguments, out of memory),
+ * @p fd is closed automatically in case of failure
* @ingroup response
*/
MHD_EXTERN_ struct MHD_Response *
diff --git a/src/mhd2/response_from.c b/src/mhd2/response_from.c
@@ -369,12 +369,12 @@ MHD_response_from_iovec (
}
-MHD_EXTERN_
+static
MHD_FN_PAR_FD_READ_ (2) struct MHD_Response *
-MHD_response_from_fd (enum MHD_HTTP_StatusCode sc,
- int fd,
- uint_fast64_t offset,
- uint_fast64_t size)
+response_from_fd_inner (enum MHD_HTTP_StatusCode sc,
+ int fd,
+ uint_fast64_t offset,
+ uint_fast64_t size)
{
struct MHD_Response *restrict res;
if (offset == MHD_SIZE_UNKNOWN)
@@ -401,6 +401,21 @@ MHD_response_from_fd (enum MHD_HTTP_StatusCode sc,
MHD_EXTERN_
MHD_FN_PAR_FD_READ_ (2) struct MHD_Response *
+MHD_response_from_fd (enum MHD_HTTP_StatusCode sc,
+ int fd,
+ uint_fast64_t offset,
+ uint_fast64_t size)
+{
+ struct MHD_Response *res =
+ response_from_fd_inner (sc, fd, offset, size);
+ if (NULL == res)
+ close (fd);
+ return res;
+}
+
+
+MHD_EXTERN_
+MHD_FN_PAR_FD_READ_ (2) struct MHD_Response *
MHD_response_from_pipe (enum MHD_HTTP_StatusCode sc,
int fd)
{
@@ -419,6 +434,8 @@ MHD_response_from_pipe (enum MHD_HTTP_StatusCode sc,
#endif
res->cntn.file.is_pipe = true;
}
+ else
+ close (fd);
return res;
}