server: vfs: make sure handle freed if problems while setting up file transfer

https://github.com/warmcat/libwebsockets/issues/1765
diff --git a/lib/roles/http/server/server.c b/lib/roles/http/server/server.c
index 04d12fe..fa2c408 100644
--- a/lib/roles/http/server/server.c
+++ b/lib/roles/http/server/server.c
@@ -2369,6 +2369,11 @@
 			return !wsi->http2_substream;
 		}
 	}
+
+	/*
+	 * Caution... wsi->http.fop_fd is live from here
+	 */
+
 	wsi->http.filelen = lws_vfs_get_length(wsi->http.fop_fd);
 	total_content_length = wsi->http.filelen;
 
@@ -2388,7 +2393,7 @@
 		lws_return_http_status(wsi,
 				HTTP_STATUS_REQ_RANGE_NOT_SATISFIABLE, NULL);
 		if (lws_http_transaction_completed(wsi))
-			return -1; /* <0 means just hang up */
+			goto bail; /* <0 means just hang up */
 
 		lws_vfs_file_close(&wsi->http.fop_fd);
 
@@ -2399,7 +2404,7 @@
 #endif
 
 	if (lws_add_http_header_status(wsi, n, &p, end))
-		return -1;
+		goto bail;
 
 	if ((wsi->http.fop_fd->flags & (LWS_FOP_FLAG_COMPR_ACCEPTABLE_GZIP |
 		       LWS_FOP_FLAG_COMPR_IS_GZIP)) ==
@@ -2407,7 +2412,7 @@
 		if (lws_add_http_header_by_token(wsi,
 			WSI_TOKEN_HTTP_CONTENT_ENCODING,
 			(unsigned char *)"gzip", 4, &p, end))
-			return -1;
+			goto bail;
 		lwsl_info("file is being provided in gzip\n");
 	}
 #if defined(LWS_WITH_HTTP_STREAM_COMPRESSION)
@@ -2436,7 +2441,7 @@
 						 (unsigned char *)content_type,
 						 (int)strlen(content_type),
 						 &p, end))
-			return -1;
+			goto bail;
 
 #if defined(LWS_WITH_RANGES)
 	if (ranges >= 2) { /* multipart byteranges */
@@ -2449,7 +2454,7 @@
 						 "multipart/byteranges; "
 						 "boundary=_lws",
 			 	 	 	 20, &p, end))
-			return -1;
+			goto bail;
 
 		/*
 		 *  our overall content length has to include
@@ -2495,14 +2500,14 @@
 						 WSI_TOKEN_HTTP_CONTENT_RANGE,
 						 (unsigned char *)cache_control,
 						 n, &p, end))
-			return -1;
+			goto bail;
 	}
 
 	wsi->http.range.inside = 0;
 
 	if (lws_add_http_header_by_token(wsi, WSI_TOKEN_HTTP_ACCEPT_RANGES,
 					 (unsigned char *)"bytes", 5, &p, end))
-		return -1;
+		goto bail;
 #endif
 
 	if (!wsi->http2_substream) {
@@ -2518,7 +2523,7 @@
 			 */
 			if (lws_add_http_header_content_length(wsi,
 						total_content_length, &p, end))
-				return -1;
+				goto bail;
 		} else {
 
 #if defined(LWS_WITH_HTTP_STREAM_COMPRESSION)
@@ -2536,7 +2541,7 @@
 						WSI_TOKEN_HTTP_TRANSFER_ENCODING,
 						(unsigned char *)"chunked", 7,
 						&p, end))
-					return -1;
+					goto bail;
 
 				/*
 				 * ...this is fun, isn't it :-)  For h1 that is
@@ -2576,24 +2581,24 @@
 		if (lws_add_http_header_by_token(wsi,
 				WSI_TOKEN_HTTP_CACHE_CONTROL,
 				(unsigned char *)cc, cclen, &p, end))
-			return -1;
+			goto bail;
 	}
 
 	if (other_headers) {
 		if ((end - p) < other_headers_len)
-			return -1;
+			goto bail;
 		memcpy(p, other_headers, other_headers_len);
 		p += other_headers_len;
 	}
 
 	if (lws_finalize_http_header(wsi, &p, end))
-		return -1;
+		goto bail;
 
 	ret = lws_write(wsi, response, p - response, LWS_WRITE_HTTP_HEADERS);
 	if (ret != (p - response)) {
 		lwsl_err("_write returned %d from %ld\n", ret,
 			 (long)(p - response));
-		return -1;
+		goto bail;
 	}
 
 	wsi->http.filepos = 0;
@@ -2601,8 +2606,9 @@
 
 	if (lws_hdr_total_length(wsi, WSI_TOKEN_HEAD_URI)) {
 		/* we do not emit the body */
+		lws_vfs_file_close(&wsi->http.fop_fd);
 		if (lws_http_transaction_completed(wsi))
-			return -1;
+			goto bail;
 
 		return 0;
 	}
@@ -2610,6 +2616,11 @@
 	lws_callback_on_writable(wsi);
 
 	return 0;
+
+bail:
+	lws_vfs_file_close(&wsi->http.fop_fd);
+
+	return -1;
 }
 #endif