diff options
author | Thomas Markwalder <tmark@isc.org> | 2019-12-11 11:40:48 +0000 |
---|---|---|
committer | Thomas Markwalder <tmark@isc.org> | 2019-12-11 08:55:14 -0500 |
commit | 9bc0f5d1d227218efa5a8415e4e57c7304067d7d (patch) | |
tree | 4c5a75d6ea5c3e7f5959a53a1b536b160ed4a434 | |
parent | 2bf9c0e7f0594687be090478ddcdb4fe6f7cd377 (diff) | |
download | isc-dhcp-9bc0f5d1d227218efa5a8415e4e57c7304067d7d.tar.gz |
[#57] Fixed reference leaks.
Merges in !39, which applied changes from #57/master.
-rw-r--r-- | RELNOTES | 3 | ||||
-rw-r--r-- | client/dhc6.c | 19 | ||||
-rw-r--r-- | client/dhclient.c | 3 | ||||
-rw-r--r-- | common/dns.c | 9 | ||||
-rw-r--r-- | common/execute.c | 12 | ||||
-rw-r--r-- | common/options.c | 11 | ||||
-rw-r--r-- | relay/dhcrelay.c | 2 | ||||
-rw-r--r-- | server/class.c | 3 | ||||
-rw-r--r-- | server/confpars.c | 10 | ||||
-rw-r--r-- | server/dhcp.c | 7 | ||||
-rw-r--r-- | server/dhcpleasequery.c | 12 | ||||
-rw-r--r-- | server/dhcpv6.c | 20 | ||||
-rw-r--r-- | server/mdb6.c | 2 |
13 files changed, 62 insertions, 51 deletions
@@ -87,6 +87,9 @@ dhcp-users@lists.isc.org. for reporting this issue. [Gitlab #2] +- Corrected a number of reference counter and zero-length buffer leaks. + [Gitlab #57] + Changes since 4.1-ESV-R15 - Corrected dhclient command line parsing for --dad-wait-time that causes diff --git a/client/dhc6.c b/client/dhc6.c index f008ee17..4bbe2e74 100644 --- a/client/dhc6.c +++ b/client/dhc6.c @@ -867,8 +867,7 @@ dhc6_parse_ia_na(struct dhc6_ia **pia, struct packet *packet, } else { log_error("Invalid IA_NA option cache."); dfree(ia, MDL); - if (ds.len != 0) - data_string_forget(&ds, MDL); + data_string_forget(&ds, MDL); return ISC_R_UNEXPECTED; } } @@ -970,8 +969,7 @@ dhc6_parse_ia_ta(struct dhc6_ia **pia, struct packet *packet, } else { log_error("Invalid IA_TA option cache."); dfree(ia, MDL); - if (ds.len != 0) - data_string_forget(&ds, MDL); + data_string_forget(&ds, MDL); return ISC_R_UNEXPECTED; } } @@ -1093,8 +1091,7 @@ dhc6_parse_ia_pd(struct dhc6_ia **pia, struct packet *packet, } else { log_error("Invalid IA_PD option cache."); dfree(ia, MDL); - if (ds.len != 0) - data_string_forget(&ds, MDL); + data_string_forget(&ds, MDL); return ISC_R_UNEXPECTED; } } @@ -1209,8 +1206,7 @@ dhc6_parse_addrs(struct dhc6_addr **paddr, struct packet *packet, } else { log_error("Invalid IAADDR option cache."); dfree(addr, MDL); - if (ds.len != 0) - data_string_forget(&ds, MDL); + data_string_forget(&ds, MDL); return ISC_R_UNEXPECTED; } } @@ -1334,8 +1330,7 @@ dhc6_parse_prefixes(struct dhc6_addr **ppfx, struct packet *packet, } else { log_error("Invalid IAPREFIX option cache."); dfree(pfx, MDL); - if (ds.len != 0) - data_string_forget(&ds, MDL); + data_string_forget(&ds, MDL); return ISC_R_UNEXPECTED; } } @@ -1357,9 +1352,7 @@ dhc6_lease_destroy(struct dhc6_lease **src, const char *file, int line) } lease = *src; - if (lease->server_id.len != 0) - data_string_forget(&lease->server_id, file, line); - + data_string_forget(&lease->server_id, file, line); for (ia = lease->bindings ; ia != NULL ; ia = nia) { nia = ia->next; diff --git a/client/dhclient.c b/client/dhclient.c index 7d560d61..5015388c 100644 --- a/client/dhclient.c +++ b/client/dhclient.c @@ -3248,9 +3248,10 @@ void client_option_envadd (struct option_cache *oc, "option - discarded", name); } - data_string_forget (&data, MDL); } } + + data_string_forget (&data, MDL); } } diff --git a/common/dns.c b/common/dns.c index 51e9c75c..870eaa26 100644 --- a/common/dns.c +++ b/common/dns.c @@ -400,15 +400,19 @@ void cache_found_zone (ns_class class, /* See if there's already such a zone. */ if (dns_zone_lookup (&zone, zname) == ISC_R_SUCCESS) { /* If it's not a dynamic zone, leave it alone. */ - if (!zone -> timeout) + if (!zone -> timeout) { + dns_zone_dereference (&zone, MDL); return; + } + /* Address may have changed, so just blow it away. */ if (zone -> primary) option_cache_dereference (&zone -> primary, MDL); if (zone -> secondary) option_cache_dereference (&zone -> secondary, MDL); - } else if (!dns_zone_allocate (&zone, MDL)) + } else if (!dns_zone_allocate (&zone, MDL)) { return; + } if (!zone -> name) { zone -> name = @@ -445,6 +449,7 @@ void cache_found_zone (ns_class class, zone -> primary -> data.len = naddrs * sizeof *addrs; enter_dns_zone (zone); + dns_zone_dereference (&zone, MDL); } /* Have to use TXT records for now. */ diff --git a/common/execute.c b/common/execute.c index bd21fe04..bb8fd92d 100644 --- a/common/execute.c +++ b/common/execute.c @@ -71,8 +71,11 @@ int execute_statements (result, packet, lease, client_state, #if defined (DEBUG_EXPRESSIONS) log_debug ("exec: statements returns %d", status); #endif - if (!status) + if (!status) { + executable_statement_dereference (&r, MDL); return 0; + } + break; case on_statement: @@ -134,6 +137,8 @@ int execute_statements (result, packet, lease, client_state, in_options, out_options, scope, e))) { executable_statement_dereference (&e, MDL); + executable_statement_dereference + (&r, MDL); return 0; } executable_statement_dereference (&e, MDL); @@ -162,8 +167,10 @@ int execute_statements (result, packet, lease, client_state, if (!execute_statements (result, packet, lease, client_state, in_options, out_options, scope, - rc ? r -> data.ie.tc : r -> data.ie.fc)) + rc ? r -> data.ie.tc : r -> data.ie.fc)) { + executable_statement_dereference (&r, MDL); return 0; + } break; case eval_statement: @@ -285,6 +292,7 @@ int execute_statements (result, packet, lease, client_state, #if defined (DEBUG_EXPRESSIONS) log_debug ("exec: break"); #endif + executable_statement_dereference (&r, MDL); return 1; case supersede_option_statement: diff --git a/common/options.c b/common/options.c index 09723c60..b9a525c0 100644 --- a/common/options.c +++ b/common/options.c @@ -220,6 +220,7 @@ int parse_option_buffer (options, buffer, length, universe) log_error("parse_option_buffer: " "No memory."); buffer_dereference(&bp, MDL); + option_dereference(&option, MDL); return 0; } /* Copy old option to new data object. */ @@ -245,6 +246,7 @@ int parse_option_buffer (options, buffer, length, universe) log_error("parse_option_buffer: " "No memory."); buffer_dereference(&bp, MDL); + option_dereference(&option, MDL); return 0; } @@ -1382,8 +1384,9 @@ store_options(int *ocount, (option_space_encapsulate (&encapsulation, packet, lease, client_state, in_options, cfg_options, scope, &name)); - data_string_forget (&name, MDL); } + + data_string_forget (&name, MDL); } } @@ -3388,8 +3391,7 @@ int fqdn_option_space_encapsulate (result, packet, lease, client_state, } exit: for (i = 1; i <= FQDN_SUBOPTION_COUNT; i++) { - if (results [i].len) - data_string_forget (&results [i], MDL); + data_string_forget (&results[i], MDL); } buffer_dereference (&bp, MDL); if (!status) @@ -3548,8 +3550,7 @@ fqdn6_option_space_encapsulate(struct data_string *result, exit: for (i = 1 ; i <= FQDN_SUBOPTION_COUNT ; i++) { - if (results[i].len) - data_string_forget(&results[i], MDL); + data_string_forget(&results[i], MDL); } return rval; diff --git a/relay/dhcrelay.c b/relay/dhcrelay.c index 14f8230d..64238a30 100644 --- a/relay/dhcrelay.c +++ b/relay/dhcrelay.c @@ -1603,7 +1603,7 @@ process_down6(struct packet *packet) { &global_scope, oc, MDL) || (relay_msg.len < offsetof(struct dhcpv6_packet, options))) { log_error("Can't evaluate relay-msg."); - return; + goto cleanup; } msg = (const struct dhcpv6_packet *) relay_msg.data; diff --git a/server/class.c b/server/class.c index 971f3ab2..c19cdc18 100644 --- a/server/class.c +++ b/server/class.c @@ -177,7 +177,6 @@ int check_collection (packet, lease, collection) } data_string_copy (&nc -> hash_string, &data, MDL); - data_string_forget (&data, MDL); if (!class -> hash) class_new_hash(&class->hash, SCLASS_HASH_SIZE, MDL); @@ -189,6 +188,8 @@ int check_collection (packet, lease, collection) classify (packet, nc); class_dereference (&nc, MDL); } + + data_string_forget (&data, MDL); } } return matched; diff --git a/server/confpars.c b/server/confpars.c index ef411b6f..1841bd78 100644 --- a/server/confpars.c +++ b/server/confpars.c @@ -777,8 +777,11 @@ int parse_statement (cfile, group, type, host_decl, declaration) et = (struct executable_statement *)0; if (!parse_option_statement (&et, cfile, 1, option, - supersede_option_statement)) + supersede_option_statement)) { + option_dereference(&option, MDL); return declaration; + } + option_dereference(&option, MDL); goto insert_statement; } else @@ -2652,6 +2655,7 @@ void parse_subnet_declaration (cfile, share) if (token != NETMASK) { parse_warn (cfile, "Expecting netmask"); skip_to_semi (cfile); + subnet_dereference (&subnet, MDL); return; } @@ -2747,6 +2751,7 @@ parse_subnet6_declaration(struct parse *cfile, struct shared_network *share) { if (token != SLASH) { parse_warn(cfile, "Expecting a '/'."); skip_to_semi(cfile); + subnet_dereference(&subnet, MDL); return; } @@ -2754,6 +2759,7 @@ parse_subnet6_declaration(struct parse *cfile, struct shared_network *share) { if (token != NUMBER) { parse_warn(cfile, "Expecting a number."); skip_to_semi(cfile); + subnet_dereference(&subnet, MDL); return; } @@ -2763,12 +2769,14 @@ parse_subnet6_declaration(struct parse *cfile, struct shared_network *share) { (*endp != '\0')) { parse_warn(cfile, "Expecting a number between 0 and 128."); skip_to_semi(cfile); + subnet_dereference(&subnet, MDL); return; } if (!is_cidr_mask_valid(&subnet->net, subnet->prefix_len)) { parse_warn(cfile, "New subnet mask too short."); skip_to_semi(cfile); + subnet_dereference(&subnet, MDL); return; } diff --git a/server/dhcp.c b/server/dhcp.c index 9fd17e2d..a7693cda 100644 --- a/server/dhcp.c +++ b/server/dhcp.c @@ -1204,8 +1204,11 @@ void dhcpinform (packet, ms_nulltp) MDL)) { log_error ("unknown option space %s.", d1.data); option_state_dereference (&options, MDL); - if (subnet) + if (subnet) { subnet_dereference (&subnet, MDL); + } + + data_string_forget (&d1, MDL); return; } @@ -2856,6 +2859,7 @@ void ack_lease (packet, lease, offer, when, msg, ms_nulltp, hp) (const char *)d1.data, d1.len, MDL)) { log_error ("unknown option space %s.", d1.data); + data_string_forget (&d1, MDL); return; } @@ -4361,6 +4365,7 @@ int locate_network (packet) data_string_forget (&data, MDL); return 0; } + ia.len = 4; memcpy (ia.iabuf, data.data, 4); data_string_forget (&data, MDL); diff --git a/server/dhcpleasequery.c b/server/dhcpleasequery.c index 5ffd5c4f..5fc40276 100644 --- a/server/dhcpleasequery.c +++ b/server/dhcpleasequery.c @@ -868,15 +868,9 @@ valid_query_msg(struct lq6_state *lq) { exit: if (!ret_val) { - if (lq->client_id.len > 0) { - data_string_forget(&lq->client_id, MDL); - } - if (lq->server_id.len > 0) { - data_string_forget(&lq->server_id, MDL); - } - if (lq->lq_query.len > 0) { - data_string_forget(&lq->lq_query, MDL); - } + data_string_forget(&lq->client_id, MDL); + data_string_forget(&lq->server_id, MDL); + data_string_forget(&lq->lq_query, MDL); } return ret_val; } diff --git a/server/dhcpv6.c b/server/dhcpv6.c index 49b55c74..ffd5e845 100644 --- a/server/dhcpv6.c +++ b/server/dhcpv6.c @@ -488,13 +488,9 @@ valid_client_msg(struct packet *packet, struct data_string *client_id) { ret_val = 1; exit: - if (data.len > 0) { - data_string_forget(&data, MDL); - } + data_string_forget(&data, MDL); if (!ret_val) { - if (client_id->len > 0) { - data_string_forget(client_id, MDL); - } + data_string_forget(client_id, MDL); } return ret_val; } @@ -579,12 +575,8 @@ valid_client_resp(struct packet *packet, exit: if (!ret_val) { - if (server_id->len > 0) { - data_string_forget(server_id, MDL); - } - if (client_id->len > 0) { - data_string_forget(client_id, MDL); - } + data_string_forget(server_id, MDL); + data_string_forget(client_id, MDL); } return ret_val; } @@ -696,9 +688,7 @@ valid_client_info_req(struct packet *packet, struct data_string *server_id) { exit: if (!ret_val) { - if (server_id->len > 0) { - data_string_forget(server_id, MDL); - } + data_string_forget(server_id, MDL); } return ret_val; } diff --git a/server/mdb6.c b/server/mdb6.c index f96f7dd1..c914986c 100644 --- a/server/mdb6.c +++ b/server/mdb6.c @@ -864,9 +864,11 @@ create_lease6(struct ipv6_pool *pool, struct iasubopt **addr, case D6O_IA_PD: /* prefix */ log_error("create_lease6: prefix pool."); + data_string_forget(&ds, MDL); return ISC_R_INVALIDARG; default: log_error("create_lease6: untyped pool."); + data_string_forget(&ds, MDL); return ISC_R_INVALIDARG; } |