diff --git a/dhcp-4.2.3-P2-ldap-filter-value-escape.patch b/dhcp-4.2.3-P2-ldap-filter-value-escape.patch new file mode 100644 index 0000000..5d6b5ba --- /dev/null +++ b/dhcp-4.2.3-P2-ldap-filter-value-escape.patch @@ -0,0 +1,200 @@ +From e8ad30e0ed9dcb77cb1a87e5e676f4dc56a36afa Mon Sep 17 00:00:00 2001 +From: Marius Tomaschewski +Date: Tue, 31 Jan 2012 17:38:25 +0100 +Subject: [PATCH] Fixed to escape values used in ldap filters + +Use ldap_bv2escaped_filter_value to escape all values used in +constructed ldap filters, e.g. "o=*Test" in DN (bnc#721829). + +Signed-off-by: Marius Tomaschewski +--- + server/ldap.c | 116 +++++++++++++++++++++++++++++++++++++++++++++++--------- + 1 files changed, 97 insertions(+), 19 deletions(-) + +diff --git a/server/ldap.c b/server/ldap.c +index 68acbbb..274e934 100644 +--- a/server/ldap.c ++++ b/server/ldap.c +@@ -1024,6 +1024,17 @@ _do_ldap_retry(int ret, const char *server, int port) + return 0; + } + ++static struct berval * ++_do_ldap_str2esc_filter_bv(const char *str, ber_len_t len, struct berval *bv_o) ++{ ++ struct berval bv_i; ++ ++ if (!str || !bv_o || (ber_str2bv(str, len, 0, &bv_i) == NULL) || ++ (ldap_bv2escaped_filter_value(&bv_i, bv_o) != 0)) ++ return NULL; ++ return bv_o; ++} ++ + static void + ldap_start (void) + { +@@ -1801,6 +1812,7 @@ ldap_read_config (void) + size_t length; + int ret, cnt; + struct berval **tempbv = NULL; ++ struct berval bv_o[2]; + + if (local_family != AF_INET) + return (ISC_R_SUCCESS); +@@ -1825,24 +1837,49 @@ ldap_read_config (void) + uname (&unme); + if (ldap_dhcp_server_cn != NULL) + { ++ if (_do_ldap_str2esc_filter_bv(ldap_dhcp_server_cn, 0, &bv_o[0]) == NULL) ++ { ++ log_error ("Cannot escape ldap filter value %s: %m", ldap_dhcp_server_cn); ++ return (ISC_R_FAILURE); ++ } ++ + snprintf (hfilter, sizeof (hfilter), +- "(&(objectClass=dhcpServer)(cn=%s))", ldap_dhcp_server_cn); +- } +- else +- { +- if(0 == get_host_entry(fqdn, sizeof(fqdn), NULL, 0)) +- { +- snprintf (hfilter, sizeof (hfilter), +- "(&(objectClass=dhcpServer)(|(cn=%s)(cn=%s)))", +- unme.nodename, fqdn); ++ "(&(objectClass=dhcpServer)(cn=%s))", bv_o[0].bv_val); ++ ++ ber_memfree(bv_o[0].bv_val); + } + else + { +- snprintf (hfilter, sizeof (hfilter), +- "(&(objectClass=dhcpServer)(cn=%s))", unme.nodename); +- } ++ if (_do_ldap_str2esc_filter_bv(unme.nodename, 0, &bv_o[0]) == NULL) ++ { ++ log_error ("Cannot escape ldap filter value %s: %m", unme.nodename); ++ return (ISC_R_FAILURE); ++ } ++ ++ if(0 == get_host_entry(fqdn, sizeof(fqdn), NULL, 0)) ++ { ++ if (_do_ldap_str2esc_filter_bv(fqdn, 0, &bv_o[1]) == NULL) ++ { ++ log_error ("Cannot escape ldap filter value %s: %m", fqdn); ++ ber_memfree(bv_o[0].bv_val); ++ return (ISC_R_FAILURE); ++ } + +- } ++ snprintf (hfilter, sizeof (hfilter), ++ "(&(objectClass=dhcpServer)(|(cn=%s)(cn=%s)))", ++ bv_o[0].bv_val, bv_o[1].bv_val); ++ ++ ber_memfree(bv_o[1].bv_val); ++ } ++ else ++ { ++ snprintf (hfilter, sizeof (hfilter), ++ "(&(objectClass=dhcpServer)(cn=%s))", ++ bv_o[0].bv_val); ++ } ++ ++ ber_memfree(bv_o[0].bv_val); ++ } + + ldap_enable_retry = 1; + do +@@ -1929,9 +1966,20 @@ ldap_read_config (void) + res = ISC_R_SUCCESS; + for (cnt=0; tempbv[cnt] != NULL; cnt++) + { ++ ++ if (_do_ldap_str2esc_filter_bv(hostdn, 0, &bv_o[0]) == NULL) ++ { ++ log_error ("Cannot escape ldap filter value %s: %m", hostdn); ++ res = ISC_R_FAILURE; ++ break; ++ } ++ + snprintf(sfilter, sizeof(sfilter), "(&(objectClass=dhcpService)" + "(|(|(dhcpPrimaryDN=%s)(dhcpSecondaryDN=%s))(dhcpServerDN=%s)))", +- hostdn, hostdn, hostdn); ++ bv_o[0].bv_val, bv_o[0].bv_val, bv_o[0].bv_val); ++ ++ ber_memfree(bv_o[0].bv_val); ++ + ldres = NULL; + if ((ret = ldap_search_ext_s (ld, tempbv[cnt]->bv_val, LDAP_SCOPE_BASE, + sfilter, NULL, 0, NULL, NULL, NULL, +@@ -2082,16 +2130,29 @@ ldap_parse_options (LDAPMessage * ent, struct group *group, + + if (temp2 != NULL) + { +- snprintf (filter, sizeof(filter), +- "(&(cn=%.*s)(objectClass=dhcpGroup))", +- (int)(temp2 - temp1), temp1); ++ struct berval bv_o; ++ ++ if (_do_ldap_str2esc_filter_bv(temp1, (temp2 - temp1), &bv_o) == NULL) ++ { ++ log_error ("Cannot escape ldap filter value %.*s: %m", ++ (int)(temp2 - temp1), temp1); ++ filter[0] = '\0'; ++ } ++ else ++ { ++ snprintf (filter, sizeof(filter), ++ "(&(cn=%s)(objectClass=dhcpGroup))", ++ bv_o.bv_val); ++ ++ ber_memfree(bv_o.bv_val); ++ } + + basedn = strchr (temp1, ','); + if (basedn != NULL) + ++basedn; + } + +- if (basedn != NULL && *basedn != '\0') ++ if (basedn != NULL && *basedn != '\0' && filter[0] != '\0') + { + ret = ldap_search_ext_s (ld, basedn, LDAP_SCOPE_SUBTREE, filter, + NULL, 0, NULL, NULL, NULL, 0, &groupdn); +@@ -2163,6 +2224,8 @@ find_haddr_in_ldap (struct host_decl **hp, int htype, unsigned hlen, + char up_hwaddr[20]; + char lo_hwaddr[20]; + int ret; ++ struct berval bv_o[2]; ++ + + if (local_family != AF_INET) + return (0); +@@ -2199,9 +2262,24 @@ find_haddr_in_ldap (struct host_decl **hp, int htype, unsigned hlen, + print_hw_addr (htype, hlen, haddr)); + x_strxform(up_hwaddr, lo_hwaddr, sizeof(up_hwaddr), toupper); + ++ if (_do_ldap_str2esc_filter_bv(lo_hwaddr, 0, &bv_o[0]) == NULL) ++ { ++ log_error ("Cannot escape ldap filter value %s: %m", lo_hwaddr); ++ return (0); ++ } ++ if (_do_ldap_str2esc_filter_bv(up_hwaddr, 0, &bv_o[1]) == NULL) ++ { ++ log_error ("Cannot escape ldap filter value %s: %m", up_hwaddr); ++ ber_memfree(bv_o[0].bv_val); ++ return (0); ++ } ++ + snprintf (buf, sizeof (buf), + "(&(objectClass=dhcpHost)(|(dhcpHWAddress=%s %s)(dhcpHWAddress=%s %s)))", +- type_str, lo_hwaddr, type_str, up_hwaddr); ++ type_str, bv_o[0].bv_val, type_str, bv_o[1].bv_val); ++ ++ ber_memfree(bv_o[0].bv_val); ++ ber_memfree(bv_o[1].bv_val); + + res = ent = NULL; + for (curr = ldap_service_dn_head; +-- +1.7.7 + diff --git a/dhcp.changes b/dhcp.changes index 14db6d1..22fea1a 100644 --- a/dhcp.changes +++ b/dhcp.changes @@ -1,3 +1,10 @@ +------------------------------------------------------------------- +Mon Mar 19 09:37:52 UTC 2012 - mt@suse.com + +- dhcp-server: fixed to escape all values used in constructed + ldap filters as a DN may contain e.g. asterisks (bnc#721829, + [ISC-Bugs #28545]). + ------------------------------------------------------------------- Fri Jan 13 15:26:43 UTC 2012 - mt@suse.com diff --git a/dhcp.spec b/dhcp.spec index 2a1b05c..5b308f5 100644 --- a/dhcp.spec +++ b/dhcp.spec @@ -83,6 +83,7 @@ Patch20: dhcp-4.1.1-dhclient-exec-filedes.diff Patch21: dhcp-4.2.2-dhclient-send-hostname-rml.diff ## patch repo lives here: http://www.suse.de/~mt/git/dhcp-ldap.git/ Patch30: dhcp-4.2.3-P1-ldap-patch-mt01.diff.bz2 +Patch31: dhcp-4.2.3-P2-ldap-filter-value-escape.patch Patch40: dhcp-4.1.1-P1-lpf-bind-msg-fix.diff Patch44: dhcp-4.2.2-xen-checksum.diff Patch45: dhcp-4.2.2-dhclient-option-checks.bnc675052.diff @@ -213,6 +214,7 @@ Authors: %patch21 -p1 %if %{with_ldap} %patch30 -p1 +%patch31 -p1 %endif %patch40 -p1 %patch44 -p1