Sfoglia il codice sorgente

http2: fix memory leak issue.

Nick Peng 1 settimana fa
parent
commit
960480ee09

+ 8 - 1
src/dns_client/client_http2.c

@@ -182,6 +182,13 @@ static int _dns_client_http2_pending_data(struct dns_conn_stream *stream, struct
 										  struct dns_query_struct *query, void *packet, int len)
 {
 	struct epoll_event event;
+	
+	/* Validate input parameters */
+	if (len <= 0 || len > DNS_IN_PACKSIZE - 128) {
+		errno = EINVAL;
+		return -1;
+	}
+	
 	if (DNS_TCP_BUFFER - stream->send_buff.len < len) {
 		errno = ENOMEM;
 		return -1;
@@ -450,7 +457,7 @@ static int _dns_client_http2_process_read(struct dns_server_info *server_info)
 	struct http2_poll_item poll_items[128];
 	int poll_count = 0;
 	int loop_count = 0;
-	const int MAX_LOOP_COUNT = 128;
+	const int MAX_LOOP_COUNT = 512;
 	struct dns_conn_stream *conn_stream = NULL;
 	int ret = 0;
 	int i = 0;

+ 5 - 0
src/dns_server/connection.c

@@ -62,6 +62,11 @@ void _dns_server_conn_release(struct dns_server_conn_head *conn)
 			SSL_free(tls_client->ssl);
 			tls_client->ssl = NULL;
 		}
+
+		if (tls_client->http2_ctx != NULL) {
+			http2_ctx_put(tls_client->http2_ctx);
+			tls_client->http2_ctx = NULL;
+		}
 		pthread_mutex_destroy(&tls_client->ssl_lock);
 	} else if (conn->type == DNS_CONN_TYPE_TLS_SERVER || conn->type == DNS_CONN_TYPE_HTTPS_SERVER) {
 		struct dns_server_conn_tls_server *tls_server = (struct dns_server_conn_tls_server *)conn;

+ 5 - 5
src/dns_server/server_http2.c

@@ -21,6 +21,7 @@
 #include "connection.h"
 #include "dns_server.h"
 #include "server_tls.h"
+#include "smartdns/dns_conf.h"
 #include "smartdns/http2.h"
 #include "smartdns/tlog.h"
 #include "smartdns/util.h"
@@ -216,10 +217,6 @@ int _dns_server_process_http2(struct dns_server_conn_tls_client *tls_client, str
 			tlog(TLOG_ERROR, "init http2 context failed.");
 			return -1;
 		}
-		if (tls_client->http2_ctx != NULL) {
-			http2_ctx_close(tls_client->http2_ctx);
-		}
-		tls_client->http2_ctx = ctx;
 
 		/* Perform initial handshake */
 		ret = http2_ctx_handshake(ctx);
@@ -230,8 +227,11 @@ int _dns_server_process_http2(struct dns_server_conn_tls_client *tls_client, str
 				log_level = TLOG_DEBUG; /* Less noisy for clients that disconnect early or misbehave */
 			}
 			tlog(log_level, "http2 handshake failed, ret=%d (%s), alpn=%s.", ret, err_msg, tls_client->alpn_selected);
+			http2_ctx_close(ctx);
 			return -1;
 		}
+		
+		tls_client->http2_ctx = ctx;
 	}
 
 	/* Handle EPOLLOUT - flush pending writes */
@@ -252,7 +252,7 @@ int _dns_server_process_http2(struct dns_server_conn_tls_client *tls_client, str
 		struct http2_poll_item poll_items[10];
 		int poll_count = 0;
 		int loop_count = 0;
-		const int MAX_LOOP_COUNT = 128;
+		const int MAX_LOOP_COUNT = 512;
 
 		/* Ensure handshake is complete */
 		ret = http2_ctx_handshake(ctx);

+ 4 - 3
src/http_parse/http2.c

@@ -624,7 +624,7 @@ static struct http2_stream *_http2_create_stream(struct http2_ctx *ctx, uint32_t
 	}
 
 	stream->ctx = ctx;
-	stream->refcount = 1; /* Initial reference count */
+	stream->refcount = 0; /* Initial reference count */
 	stream->stream_id = stream_id;
 	stream->state = HTTP2_STREAM_IDLE;
 
@@ -649,10 +649,12 @@ static struct http2_stream *_http2_create_stream(struct http2_ctx *ctx, uint32_t
 	INIT_LIST_HEAD(&stream->header_list.list);
 	hash_init(stream->header_map);
 
+	http2_stream_get(stream); /* Hold ownership for ctx */
+	pthread_mutex_lock(&ctx->mutex);
 	hash_add(ctx->stream_map, &stream->hash_node, stream->stream_id);
 	list_add(&stream->node, &ctx->streams);
 	ctx->active_streams++;
-	http2_ctx_get(ctx);
+	pthread_mutex_unlock(&ctx->mutex);
 
 	return stream;
 }
@@ -1623,7 +1625,6 @@ void http2_stream_close(struct http2_stream *stream)
 		pthread_mutex_unlock(&ctx->mutex);
 
 		_http2_remove_stream(stream);
-		http2_ctx_put(ctx);
 	}
 	/* Mark stream as closed */
 	stream->state = HTTP2_STREAM_CLOSED;

+ 1 - 1
src/include/smartdns/http2.h

@@ -32,7 +32,7 @@ struct http2_stream;
 
 /* HTTP/2 Settings structure */
 struct http2_settings {
-	int max_concurrent_streams; /* -1 = use default (4096), 0 = unlimited */
+	int max_concurrent_streams; /* -1 = use default (8192), 0 = unlimited */
 };
 
 /* Error codes */