summaryrefslogtreecommitdiff
path: root/usr/src/lib/nsswitch/ldap/common/getnetent.c
diff options
context:
space:
mode:
Diffstat (limited to 'usr/src/lib/nsswitch/ldap/common/getnetent.c')
-rw-r--r--usr/src/lib/nsswitch/ldap/common/getnetent.c248
1 files changed, 91 insertions, 157 deletions
diff --git a/usr/src/lib/nsswitch/ldap/common/getnetent.c b/usr/src/lib/nsswitch/ldap/common/getnetent.c
index a5afb360ce..d042e0fe2b 100644
--- a/usr/src/lib/nsswitch/ldap/common/getnetent.c
+++ b/usr/src/lib/nsswitch/ldap/common/getnetent.c
@@ -2,9 +2,8 @@
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
- * Common Development and Distribution License, Version 1.0 only
- * (the "License"). You may not use this file except in compliance
- * with the License.
+ * Common Development and Distribution License (the "License").
+ * You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* or http://www.opensolaris.org/os/licensing.
@@ -20,7 +19,7 @@
* CDDL HEADER END
*/
/*
- * Copyright 2003 Sun Microsystems, Inc. All rights reserved.
+ * Copyright 2006 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
@@ -38,8 +37,10 @@
#define _N_NETWORK "ipnetworknumber"
#define _F_GETNETBYNAME "(&(objectClass=ipNetwork)(cn=%s))"
#define _F_GETNETBYNAME_SSD "(&(%%s)(cn=%s))"
-#define _F_GETNETBYADDR "(&(objectClass=ipNetwork)(ipNetworkNumber=%s))"
-#define _F_GETNETBYADDR_SSD "(&(%%s)(ipNetworkNumber=%s))"
+#define _F_GETNETBYADDR "(&(objectClass=ipNetwork)(|(ipNetworkNumber=%s)" \
+ "(ipNetworkNumber=%s)))"
+#define _F_GETNETBYADDR_SSD "(&(%%s)(|(ipNetworkNumber=%s)" \
+ "(ipNetworkNumber=%s)))"
static const char *networks_attrs[] = {
_N_NAME,
@@ -48,187 +49,119 @@ static const char *networks_attrs[] = {
};
/*
- * _nss_ldap_networks2ent is the data marshaling method for the networks
+ * _nss_ldap_networks2str is the data marshaling method for the networks
* getXbyY * (e.g., getbyname(), getbyaddr(), getnetent() backend processes.
* This method is called after a successful ldap search has been performed.
- * This method will parse the ldap search values into struct netent =
- * argp->buf.buffer which the frontend process expects. Three error conditions
- * are expected and returned to nsswitch.
+ * This method will parse the ldap search values into the file format.
+ * e.g.
+ *
+ * SunRay-ce2 10.34.96.0 SunRay
+ *
*/
-
static int
-_nss_ldap_networks2ent(ldap_backend_ptr be, nss_XbyY_args_t *argp)
+_nss_ldap_networks2str(ldap_backend_ptr be, nss_XbyY_args_t *argp)
{
- int i, j;
+ uint_t i;
int nss_result;
- int buflen = (int)0;
- int firstime = (int)1;
- unsigned long len = 0L;
- char **mp, *cname = NULL;
-#ifdef DEBUG
- char addrstr[16];
-#endif /* DEBUG */
- char *buffer = (char *)NULL;
- char *ceiling = (char *)NULL;
- struct netent *ntk = (struct netent *)NULL;
+ int buflen = 0, len;
+ char **network, *cname = NULL;
+ char *buffer = NULL;
ns_ldap_result_t *result = be->result;
- ns_ldap_attr_t *attrptr;
+ ns_ldap_attr_t *names;
- buffer = argp->buf.buffer;
- buflen = (size_t)argp->buf.buflen;
- if (!argp->buf.result) {
- nss_result = (int)NSS_STR_PARSE_ERANGE;
- goto result_net2ent;
- }
- ntk = (struct netent *)argp->buf.result;
- ceiling = buffer + buflen;
+ if (result == NULL)
+ return (NSS_STR_PARSE_PARSE);
+ buflen = argp->buf.buflen;
- nss_result = (int)NSS_STR_PARSE_SUCCESS;
+ if (argp->buf.result != NULL) {
+ if ((be->buffer = calloc(1, buflen)) == NULL) {
+ nss_result = NSS_STR_PARSE_PARSE;
+ goto result_net2str;
+ }
+ buffer = be->buffer;
+ } else
+ buffer = argp->buf.buffer;
+
+ nss_result = NSS_STR_PARSE_SUCCESS;
(void) memset(argp->buf.buffer, 0, buflen);
- attrptr = getattr(result, 0);
- if (attrptr == NULL) {
- nss_result = (int)NSS_STR_PARSE_PARSE;
- goto result_net2ent;
+ names = __ns_ldap_getAttrStruct(result->entry, _N_NAME);
+ if (names == NULL || names->attrvalue == NULL) {
+ nss_result = NSS_STR_PARSE_PARSE;
+ goto result_net2str;
}
-
- for (i = 0; i < result->entry->attr_count; i++) {
- attrptr = getattr(result, i);
- if (attrptr == NULL) {
- nss_result = (int)NSS_STR_PARSE_PARSE;
- goto result_net2ent;
- }
- if (strcasecmp(attrptr->attrname, _N_NAME) == 0) {
- for (j = 0; j < attrptr->value_count; j++) {
- if (firstime) {
- /*
- * The definition of the object class
- * "ipNetwork" has a descripency between
- * RFC 2307 and 2307bis.
- * In 2307, "cn" is a MUST attribute.
- * In 2307bis, "cn" is a MAY attribute.
- * If "cn" is a MAY attribute,
- * it does not appear in RDN and can't
- * be derived from RDN as a canonical
- * "cn" name. In that case, use 1st
- * "cn" value as the official name.
- */
- cname = __s_api_get_canonical_name(
- result->entry, attrptr, 1);
- if (cname == NULL)
- /* 2307bis case */
- cname = attrptr->attrvalue[j];
-
- if (cname == NULL ||
- (len = strlen(cname)) < 1) {
- nss_result =
- NSS_STR_PARSE_PARSE;
- goto result_net2ent;
- }
- ntk->n_name = buffer;
- buffer += len + 1;
- if (buffer >= ceiling) {
- nss_result =
- (int)NSS_STR_PARSE_ERANGE;
- goto result_net2ent;
- }
- (void) strcpy(ntk->n_name, cname);
- /* alias list */
- mp = ntk->n_aliases =
- (char **)ROUND_UP(buffer,
- sizeof (char **));
- buffer = (char *)ntk->n_aliases +
- sizeof (char *) *
- (attrptr->value_count + 1);
- buffer = (char *)ROUND_UP(buffer,
- sizeof (char **));
- if (buffer >= ceiling) {
- nss_result =
- (int)NSS_STR_PARSE_ERANGE;
- goto result_net2ent;
- }
- firstime = (int)0;
- }
- /* alias list */
- if ((attrptr->attrvalue[j] == NULL) ||
- (len = strlen(attrptr->attrvalue[j])) < 1) {
- nss_result = (int)NSS_STR_PARSE_PARSE;
- goto result_net2ent;
- }
- /* skip canonical name(official name) */
- if (strcmp(attrptr->attrvalue[j], cname) == 0)
- continue;
- *mp = buffer;
- buffer += len + 1;
- if (buffer >= ceiling) {
- nss_result = (int)NSS_STR_PARSE_ERANGE;
- goto result_net2ent;
- }
- (void) strcpy(*mp++, attrptr->attrvalue[j]);
- continue;
- }
+ /* Get the canonical name */
+ cname = __s_api_get_canonical_name(result->entry, names, 1);
+ /*
+ * The definition of the object class "ipNetwork" has a
+ * discrepency between RFC 2307 and 2307bis.
+ * In 2307, "cn" is a MUST attribute. In 2307bis, "cn" is a
+ * MAY attribute.
+ * If "cn" is a MAY attribute, it does not appear in RDN and can't
+ * be derived from RDN as a canonical "cn" name. In that case, use 1st
+ * "cn" value as the official name.
+ */
+ if (cname == NULL)
+ /* 2307bis case */
+ cname = names->attrvalue[0];
+ if (cname == NULL || (len = strlen(cname)) < 1) {
+ nss_result = NSS_STR_PARSE_PARSE;
+ goto result_net2str;
+ }
+ network = __ns_ldap_getAttr(result->entry, _N_NETWORK);
+ if (network == NULL || network[0] == NULL ||
+ (len = strlen(network[0])) < 1) {
+ nss_result = NSS_STR_PARSE_PARSE;
+ goto result_net2str;
+ }
+ len = snprintf(buffer, buflen, "%s %s", cname, network[0]);
+ TEST_AND_ADJUST(len, buffer, buflen, result_net2str);
+ /* Append aliases */
+ for (i = 0; i < names->value_count; i++) {
+ if (names->attrvalue[i] == NULL) {
+ nss_result = NSS_STR_PARSE_PARSE;
+ goto result_net2str;
}
- if (strcasecmp(attrptr->attrname, _N_NETWORK) == 0) {
- if ((attrptr->attrvalue[0] == NULL) ||
- (len = strlen(attrptr->attrvalue[0])) < 1) {
- nss_result = (int)NSS_STR_PARSE_PARSE;
- goto result_net2ent;
- }
- if ((ntk->n_net = (in_addr_t)
- inet_network(attrptr->attrvalue[0])) ==
- (in_addr_t)-1) {
- nss_result = (int)NSS_STR_PARSE_PARSE;
- goto result_net2ent;
- }
-#ifdef DEBUG
- strlcpy(addrstr, attrptr->attrvalue[0],
- sizeof (addrstr));
-#endif /* DEBUG */
- continue;
+ /* Skip the canonical name */
+ if (strcasecmp(names->attrvalue[i], cname) != 0) {
+ len = snprintf(buffer, buflen, " %s",
+ names->attrvalue[i]);
+ TEST_AND_ADJUST(len, buffer, buflen, result_net2str);
}
}
- ntk->n_addrtype = AF_INET;
-
-#ifdef DEBUG
- (void) fprintf(stdout, "\n[getnetent.c: _nss_ldap_networks2ent]\n");
- (void) fprintf(stdout, " n_name: [%s]\n", ntk->n_name);
- if (mp != NULL) {
- for (mp = ntk->n_aliases; *mp != NULL; mp++)
- (void) fprintf(stdout, " n_aliases: [%s]\n", *mp);
- }
- if (ntk->n_addrtype == AF_INET)
- (void) fprintf(stdout, " n_addrtype: [AF_INET]\n");
- else
- (void) fprintf(stdout, " n_addrtype: [%d]\n",
- ntk->n_addrtype);
- (void) fprintf(stdout, " n_net: [%s]\n", addrstr);
-#endif /* DEBUG */
-result_net2ent:
+ /* The front end marshaller doesn't need to copy trailing nulls */
+ if (argp->buf.result != NULL)
+ be->buflen = strlen(be->buffer);
+
+result_net2str:
(void) __ns_ldap_freeResult(&be->result);
- return ((int)nss_result);
+ return (nss_result);
}
-
/*
* Takes an unsigned integer in host order, and returns a printable
* string for it as a network number. To allow for the possibility of
* naming subnets, only trailing dot-zeros are truncated.
+ * buf2 is untruncated version.
*/
-static int nettoa(int anet, char *buf, int buflen)
+static int nettoa(int anet, char *buf, char *buf2, int buflen)
{
int addr;
char *p;
struct in_addr in;
- if (buf == 0)
+ if (buf == NULL || buf2 == NULL)
return ((int)1);
in = inet_makeaddr(anet, INADDR_ANY);
addr = in.s_addr;
- if (strlcpy(buf, inet_ntoa(in), buflen) >= buflen)
+ if (inet_ntop(AF_INET, (const void *)&in, buf2, INET_ADDRSTRLEN)
+ == NULL)
+ return ((int)1);
+ if (strlcpy(buf, buf2, buflen) >= buflen)
return ((int)1);
if ((IN_CLASSA_HOST & htonl(addr)) == 0) {
p = strchr(buf, '.');
@@ -304,21 +237,22 @@ static nss_status_t
getbyaddr(ldap_backend_ptr be, void *a)
{
nss_XbyY_args_t *argp = (nss_XbyY_args_t *)a;
- char addrstr[16];
+ char addrstr[INET_ADDRSTRLEN], addrstr2[INET_ADDRSTRLEN];
char searchfilter[SEARCHFILTERLEN];
char userdata[SEARCHFILTERLEN];
int ret;
- if (nettoa((int)argp->key.netaddr.net, addrstr, 16) != 0)
+ if (nettoa((int)argp->key.netaddr.net, addrstr, addrstr2,
+ INET_ADDRSTRLEN) != 0)
return ((nss_status_t)NSS_UNAVAIL);
ret = snprintf(searchfilter, sizeof (searchfilter),
- _F_GETNETBYADDR, addrstr);
+ _F_GETNETBYADDR, addrstr, addrstr2);
if (ret >= sizeof (searchfilter) || ret < 0)
return ((nss_status_t)NSS_NOTFOUND);
ret = snprintf(userdata, sizeof (userdata),
- _F_GETNETBYADDR_SSD, addrstr);
+ _F_GETNETBYADDR_SSD, addrstr, addrstr2);
if (ret >= sizeof (userdata) || ret < 0)
return ((nss_status_t)NSS_NOTFOUND);
@@ -351,5 +285,5 @@ _nss_ldap_networks_constr(const char *dummy1, const char *dummy2,
return ((nss_backend_t *)_nss_ldap_constr(net_ops,
sizeof (net_ops)/sizeof (net_ops[0]), _NETWORKS,
- networks_attrs, _nss_ldap_networks2ent));
+ networks_attrs, _nss_ldap_networks2str));
}