10Sstevel@tonic-gate /* 20Sstevel@tonic-gate * CDDL HEADER START 30Sstevel@tonic-gate * 40Sstevel@tonic-gate * The contents of this file are subject to the terms of the 5*2830Sdjl * Common Development and Distribution License (the "License"). 6*2830Sdjl * You may not use this file except in compliance with the License. 70Sstevel@tonic-gate * 80Sstevel@tonic-gate * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 90Sstevel@tonic-gate * or http://www.opensolaris.org/os/licensing. 100Sstevel@tonic-gate * See the License for the specific language governing permissions 110Sstevel@tonic-gate * and limitations under the License. 120Sstevel@tonic-gate * 130Sstevel@tonic-gate * When distributing Covered Code, include this CDDL HEADER in each 140Sstevel@tonic-gate * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 150Sstevel@tonic-gate * If applicable, add the following below this CDDL HEADER, with the 160Sstevel@tonic-gate * fields enclosed by brackets "[]" replaced with your own identifying 170Sstevel@tonic-gate * information: Portions Copyright [yyyy] [name of copyright owner] 180Sstevel@tonic-gate * 190Sstevel@tonic-gate * CDDL HEADER END 200Sstevel@tonic-gate */ 210Sstevel@tonic-gate /* 22*2830Sdjl * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 230Sstevel@tonic-gate * Use is subject to license terms. 240Sstevel@tonic-gate */ 250Sstevel@tonic-gate 260Sstevel@tonic-gate #pragma ident "%Z%%M% %I% %E% SMI" 270Sstevel@tonic-gate 280Sstevel@tonic-gate #include "ldap_common.h" 290Sstevel@tonic-gate 300Sstevel@tonic-gate /* bootparams attributes filters */ 310Sstevel@tonic-gate #define _B_HOSTNAME "cn" 320Sstevel@tonic-gate #define _B_PARAMETER "bootparameter" 330Sstevel@tonic-gate #define _F_GETBOOTPARAMBYNAME "(&(objectClass=bootableDevice)(cn=%s))" 340Sstevel@tonic-gate #define _F_GETBOOTPARAMBYNAME_SSD "(&(%%s)(cn=%s))" 350Sstevel@tonic-gate 360Sstevel@tonic-gate static const char *bootparams_attrs[] = { 370Sstevel@tonic-gate _B_HOSTNAME, 380Sstevel@tonic-gate _B_PARAMETER, 390Sstevel@tonic-gate (char *)NULL 400Sstevel@tonic-gate }; 410Sstevel@tonic-gate 420Sstevel@tonic-gate /* 43*2830Sdjl * _nss_ldap_bootparams2str is the data marshaling method for the 44*2830Sdjl * bootparams bootparams_getbyname backend processes. 45*2830Sdjl * This method is called after a successful ldap search has been performed. 46*2830Sdjl * This method will parse the ldap search values into the file format. 470Sstevel@tonic-gate * 480Sstevel@tonic-gate * A host's bootparameters are returned on one line separated by white 49*2830Sdjl * space. The LDAP server stores each boot parameter as a separate entry. 50*2830Sdjl * If more than one bootparameter is available, a white space separated buffer 510Sstevel@tonic-gate * must be constructed and returned. 52*2830Sdjl * 530Sstevel@tonic-gate */ 540Sstevel@tonic-gate 550Sstevel@tonic-gate static int 56*2830Sdjl _nss_ldap_bootparams2str(ldap_backend_ptr be, nss_XbyY_args_t *argp) 570Sstevel@tonic-gate { 58*2830Sdjl uint_t i; 59*2830Sdjl int buflen = 0, len = 0; 60*2830Sdjl int nss_result, firsttime; 61*2830Sdjl ns_ldap_attr_t *bparams; 62*2830Sdjl char *buffer, **names; 630Sstevel@tonic-gate ns_ldap_result_t *result = be->result; 640Sstevel@tonic-gate 65*2830Sdjl if (result == NULL) 66*2830Sdjl return (NSS_STR_PARSE_PARSE); 67*2830Sdjl buflen = argp->buf.buflen; 68*2830Sdjl if (argp->buf.result != NULL) { 69*2830Sdjl if ((be->buffer = calloc(1, buflen)) == NULL) { 70*2830Sdjl nss_result = NSS_STR_PARSE_PARSE; 71*2830Sdjl goto result_bp2str; 72*2830Sdjl } 73*2830Sdjl buffer = be->buffer; 74*2830Sdjl } else 75*2830Sdjl buffer = argp->buf.buffer; 760Sstevel@tonic-gate 77*2830Sdjl nss_result = NSS_STR_PARSE_SUCCESS; 78*2830Sdjl (void) memset(argp->buf.buffer, 0, buflen); 790Sstevel@tonic-gate 80*2830Sdjl names = __ns_ldap_getAttr(result->entry, _B_HOSTNAME); 81*2830Sdjl if (names == NULL || names[0] == NULL || 82*2830Sdjl (strlen(names[0]) < 1)) { 83*2830Sdjl nss_result = NSS_STR_PARSE_PARSE; 84*2830Sdjl goto result_bp2str; 85*2830Sdjl } 86*2830Sdjl bparams = __ns_ldap_getAttrStruct(result->entry, _B_PARAMETER); 87*2830Sdjl if (bparams == NULL || bparams->attrvalue == NULL) { 88*2830Sdjl nss_result = NSS_STR_PARSE_PARSE; 89*2830Sdjl goto result_bp2str; 90*2830Sdjl } 91*2830Sdjl firsttime = 1; 92*2830Sdjl for (i = 0; i < bparams->value_count; i++) { 93*2830Sdjl if (bparams->attrvalue[i] == NULL) { 94*2830Sdjl nss_result = NSS_STR_PARSE_PARSE; 95*2830Sdjl goto result_bp2str; 960Sstevel@tonic-gate } 97*2830Sdjl /* 98*2830Sdjl * Skip client host name. The early version of ldapaddent 99*2830Sdjl * adds hostname as a boot param and it should be filtered. 100*2830Sdjl */ 101*2830Sdjl if (strcasecmp(names[0], bparams->attrvalue[i]) != 0) { 102*2830Sdjl if (firsttime) { 103*2830Sdjl firsttime = 0; 104*2830Sdjl len = snprintf(buffer, buflen, "%s", 105*2830Sdjl bparams->attrvalue[i]); 106*2830Sdjl } else 107*2830Sdjl len = snprintf(buffer, buflen, " %s", 108*2830Sdjl bparams->attrvalue[i]); 109*2830Sdjl TEST_AND_ADJUST(len, buffer, buflen, result_bp2str); 1100Sstevel@tonic-gate } 1110Sstevel@tonic-gate } 112*2830Sdjl /* The front end marshaller doesn't need to copy trailing nulls */ 113*2830Sdjl if (argp->buf.result != NULL) 114*2830Sdjl be->buflen = strlen(be->buffer); 1150Sstevel@tonic-gate 116*2830Sdjl result_bp2str: 1170Sstevel@tonic-gate 1180Sstevel@tonic-gate (void) __ns_ldap_freeResult(&be->result); 119*2830Sdjl return (nss_result); 1200Sstevel@tonic-gate } 1210Sstevel@tonic-gate 1220Sstevel@tonic-gate /* 1230Sstevel@tonic-gate * getbyname gets bootparameters by host name. This function constructs an 1240Sstevel@tonic-gate * ldap search filter using the host name invocation parameter and the 1250Sstevel@tonic-gate * getbootparambyname search filter defined. Once the filter is 1260Sstevel@tonic-gate * constructed, we search for matching entries and marshal the data 1270Sstevel@tonic-gate * results into argp->buf.buffer for the frontend process. The function 1280Sstevel@tonic-gate * _nss_ldap_bootparams2ent performs the data marshaling. 1290Sstevel@tonic-gate * 1300Sstevel@tonic-gate * RFC 2307, An Approach for Using LDAP as a Network Information Service, 1310Sstevel@tonic-gate * indicates that dn's be fully qualified. Host name searches will be on 1320Sstevel@tonic-gate * fully qualified host names (e.g., foo.bar.sun.com). 1330Sstevel@tonic-gate */ 1340Sstevel@tonic-gate 1350Sstevel@tonic-gate static nss_status_t 1360Sstevel@tonic-gate getbyname(ldap_backend_ptr be, void *a) 1370Sstevel@tonic-gate { 1380Sstevel@tonic-gate char hostname[3 * MAXHOSTNAMELEN]; 1390Sstevel@tonic-gate nss_XbyY_args_t *argp = (nss_XbyY_args_t *)a; 1400Sstevel@tonic-gate char searchfilter[SEARCHFILTERLEN]; 1410Sstevel@tonic-gate char userdata[SEARCHFILTERLEN]; 1420Sstevel@tonic-gate int ret; 1430Sstevel@tonic-gate 1440Sstevel@tonic-gate if (_ldap_filter_name(hostname, argp->key.name, sizeof (hostname)) != 0) 1450Sstevel@tonic-gate return ((nss_status_t)NSS_NOTFOUND); 1460Sstevel@tonic-gate 1470Sstevel@tonic-gate ret = snprintf(searchfilter, sizeof (searchfilter), 1480Sstevel@tonic-gate _F_GETBOOTPARAMBYNAME, hostname); 1490Sstevel@tonic-gate if (ret >= sizeof (searchfilter) || ret < 0) 1500Sstevel@tonic-gate return ((nss_status_t)NSS_NOTFOUND); 1510Sstevel@tonic-gate 1520Sstevel@tonic-gate ret = snprintf(userdata, sizeof (userdata), 1530Sstevel@tonic-gate _F_GETBOOTPARAMBYNAME_SSD, hostname); 1540Sstevel@tonic-gate if (ret >= sizeof (userdata) || ret < 0) 1550Sstevel@tonic-gate return ((nss_status_t)NSS_NOTFOUND); 1560Sstevel@tonic-gate return ((nss_status_t)_nss_ldap_lookup(be, argp, 1570Sstevel@tonic-gate _BOOTPARAMS, searchfilter, NULL, 1580Sstevel@tonic-gate _merge_SSD_filter, userdata)); 1590Sstevel@tonic-gate } 1600Sstevel@tonic-gate 1610Sstevel@tonic-gate 1620Sstevel@tonic-gate static ldap_backend_op_t bootparams_ops[] = { 1630Sstevel@tonic-gate _nss_ldap_destr, 1640Sstevel@tonic-gate getbyname 1650Sstevel@tonic-gate }; 1660Sstevel@tonic-gate 1670Sstevel@tonic-gate 1680Sstevel@tonic-gate /* 1690Sstevel@tonic-gate * _nss_ldap_bootparams_constr is where life begins. This function calls 1700Sstevel@tonic-gate * the generic ldap constructor function to define and build the abstract 1710Sstevel@tonic-gate * data types required to support ldap operations. 1720Sstevel@tonic-gate */ 1730Sstevel@tonic-gate 1740Sstevel@tonic-gate /*ARGSUSED0*/ 1750Sstevel@tonic-gate nss_backend_t * 1760Sstevel@tonic-gate _nss_ldap_bootparams_constr(const char *dummy1, const char *dummy2, 1770Sstevel@tonic-gate const char *dummy3) 1780Sstevel@tonic-gate { 1790Sstevel@tonic-gate 1800Sstevel@tonic-gate return ((nss_backend_t *)_nss_ldap_constr(bootparams_ops, 1810Sstevel@tonic-gate sizeof (bootparams_ops)/sizeof (bootparams_ops[0]), 182*2830Sdjl _BOOTPARAMS, bootparams_attrs, _nss_ldap_bootparams2str)); 1830Sstevel@tonic-gate } 184