17c478bd9Sstevel@tonic-gate /* 27c478bd9Sstevel@tonic-gate * CDDL HEADER START 37c478bd9Sstevel@tonic-gate * 47c478bd9Sstevel@tonic-gate * The contents of this file are subject to the terms of the 5*45916cd2Sjpk * Common Development and Distribution License (the "License"). 6*45916cd2Sjpk * You may not use this file except in compliance with the License. 77c478bd9Sstevel@tonic-gate * 87c478bd9Sstevel@tonic-gate * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 97c478bd9Sstevel@tonic-gate * or http://www.opensolaris.org/os/licensing. 107c478bd9Sstevel@tonic-gate * See the License for the specific language governing permissions 117c478bd9Sstevel@tonic-gate * and limitations under the License. 127c478bd9Sstevel@tonic-gate * 137c478bd9Sstevel@tonic-gate * When distributing Covered Code, include this CDDL HEADER in each 147c478bd9Sstevel@tonic-gate * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 157c478bd9Sstevel@tonic-gate * If applicable, add the following below this CDDL HEADER, with the 167c478bd9Sstevel@tonic-gate * fields enclosed by brackets "[]" replaced with your own identifying 177c478bd9Sstevel@tonic-gate * information: Portions Copyright [yyyy] [name of copyright owner] 187c478bd9Sstevel@tonic-gate * 197c478bd9Sstevel@tonic-gate * CDDL HEADER END 207c478bd9Sstevel@tonic-gate */ 217c478bd9Sstevel@tonic-gate /* 22*45916cd2Sjpk * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 237c478bd9Sstevel@tonic-gate * Use is subject to license terms. 247c478bd9Sstevel@tonic-gate */ 257c478bd9Sstevel@tonic-gate 267c478bd9Sstevel@tonic-gate #pragma ident "%Z%%M% %I% %E% SMI" 277c478bd9Sstevel@tonic-gate 28*45916cd2Sjpk #ifndef lint 29*45916cd2Sjpk static char sccsid[] = "%Z%%M% %I% %E% SMI"; 307c478bd9Sstevel@tonic-gate #endif 317c478bd9Sstevel@tonic-gate 32*45916cd2Sjpk #include <ctype.h> 33*45916cd2Sjpk #include <string.h> 34*45916cd2Sjpk #include <stdlib.h> 35*45916cd2Sjpk #include <tsol/label.h> 36*45916cd2Sjpk #include <bsm/devices.h> 37*45916cd2Sjpk #include <bsm/devalloc.h> 38*45916cd2Sjpk 39*45916cd2Sjpk extern char *_strdup_null(char *); 40*45916cd2Sjpk 417c478bd9Sstevel@tonic-gate static struct _dabuff { 427c478bd9Sstevel@tonic-gate FILE *_daf; /* pointer into /etc/security/device_allocate */ 437c478bd9Sstevel@tonic-gate devalloc_t _interpdevalloc; 44*45916cd2Sjpk char _interpdaline[DA_BUFSIZE + 1]; 457c478bd9Sstevel@tonic-gate char *_DEVALLOC; 467c478bd9Sstevel@tonic-gate } *__dabuff; 477c478bd9Sstevel@tonic-gate 487c478bd9Sstevel@tonic-gate #define daf (_da->_daf) 497c478bd9Sstevel@tonic-gate #define interpdevalloc (_da->_interpdevalloc) 50*45916cd2Sjpk #define interpdaline (_da->_interpdaline) 51*45916cd2Sjpk #define DEVALLOC_FILE (_da->_DEVALLOC) 52*45916cd2Sjpk static devalloc_t *da_interpret(char *); 53*45916cd2Sjpk 54*45916cd2Sjpk int da_matchname(devalloc_t *, char *); 55*45916cd2Sjpk int da_matchtype(devalloc_t *, char *); 56*45916cd2Sjpk 57*45916cd2Sjpk static int system_labeled = 0; 587c478bd9Sstevel@tonic-gate 597c478bd9Sstevel@tonic-gate /* 60*45916cd2Sjpk * trim_white - 61*45916cd2Sjpk * trims off leading and trailing white space from input string. 62*45916cd2Sjpk * The leading white space is skipped by moving the pointer forward. 63*45916cd2Sjpk * The trailing white space is removed by nulling the white space 64*45916cd2Sjpk * characters. 65*45916cd2Sjpk * returns pointer to non-white string, else returns NULL if input string 66*45916cd2Sjpk * is null or if the resulting string has zero length. 677c478bd9Sstevel@tonic-gate */ 68*45916cd2Sjpk char * 69*45916cd2Sjpk trim_white(char *ptr) 707c478bd9Sstevel@tonic-gate { 71*45916cd2Sjpk char *tptr; 72*45916cd2Sjpk 737c478bd9Sstevel@tonic-gate if (ptr == NULL) 747c478bd9Sstevel@tonic-gate return (NULL); 75*45916cd2Sjpk while (isspace(*ptr)) 767c478bd9Sstevel@tonic-gate ptr++; 77*45916cd2Sjpk tptr = ptr + strlen(ptr); 78*45916cd2Sjpk while (tptr != ptr && isspace(tptr[-1])) 79*45916cd2Sjpk --tptr; 807c478bd9Sstevel@tonic-gate *tptr = '\0'; 81*45916cd2Sjpk if (*ptr == '\0') 827c478bd9Sstevel@tonic-gate return (NULL); 83*45916cd2Sjpk 847c478bd9Sstevel@tonic-gate return (ptr); 857c478bd9Sstevel@tonic-gate } 867c478bd9Sstevel@tonic-gate 877c478bd9Sstevel@tonic-gate /* 88*45916cd2Sjpk * pack_white - 89*45916cd2Sjpk * trims off multiple occurrences of white space from input string. 90*45916cd2Sjpk * returns the number of spaces retained 917c478bd9Sstevel@tonic-gate */ 92*45916cd2Sjpk int 93*45916cd2Sjpk pack_white(char *ptr) 947c478bd9Sstevel@tonic-gate { 95*45916cd2Sjpk int cnt = 0; 96*45916cd2Sjpk char *tptr, ch; 977c478bd9Sstevel@tonic-gate 98*45916cd2Sjpk if (ptr == NULL) 997c478bd9Sstevel@tonic-gate return (0); 100*45916cd2Sjpk tptr = ptr; 101*45916cd2Sjpk while (isspace(*tptr)) 102*45916cd2Sjpk tptr++; 103*45916cd2Sjpk for (;;) { 104*45916cd2Sjpk while ((ch = *tptr) != '\0' && !isspace(ch)) { 105*45916cd2Sjpk *ptr++ = ch; 106*45916cd2Sjpk tptr++; 1077c478bd9Sstevel@tonic-gate } 108*45916cd2Sjpk while (isspace(*tptr)) 109*45916cd2Sjpk tptr++; 110*45916cd2Sjpk if (*tptr == '\0') 111*45916cd2Sjpk break; 112*45916cd2Sjpk *ptr++ = ' '; 113*45916cd2Sjpk cnt++; 1147c478bd9Sstevel@tonic-gate } 115*45916cd2Sjpk *ptr = '\0'; 1167c478bd9Sstevel@tonic-gate 117*45916cd2Sjpk return (cnt); 118*45916cd2Sjpk } 1197c478bd9Sstevel@tonic-gate 1207c478bd9Sstevel@tonic-gate /* 121*45916cd2Sjpk * getdadmline - 122*45916cd2Sjpk * reads one device_alloc/device_maps line from stream into buff of len 123*45916cd2Sjpk * bytes. Continued lines from stream are concatenated into one line in 124*45916cd2Sjpk * buff. Comments are removed from buff. 125*45916cd2Sjpk * returns the number of characters in buff, else returns 0 if no 126*45916cd2Sjpk * characters are read or an error occurred. 1277c478bd9Sstevel@tonic-gate */ 128*45916cd2Sjpk int 129*45916cd2Sjpk getdadmline(char *buff, int len, FILE *stream) 1307c478bd9Sstevel@tonic-gate { 1317c478bd9Sstevel@tonic-gate int tmpcnt; 1327c478bd9Sstevel@tonic-gate int charcnt = 0; 1337c478bd9Sstevel@tonic-gate int fileerr = 0; 134*45916cd2Sjpk int contline = 0; 135*45916cd2Sjpk char *cp; 136*45916cd2Sjpk char *ccp; 137*45916cd2Sjpk 1387c478bd9Sstevel@tonic-gate do { 1397c478bd9Sstevel@tonic-gate cp = buff; 1407c478bd9Sstevel@tonic-gate *cp = NULL; 1417c478bd9Sstevel@tonic-gate do { 142*45916cd2Sjpk contline = 0; 1437c478bd9Sstevel@tonic-gate if (fgets(cp, len - charcnt, stream) == NULL) { 1447c478bd9Sstevel@tonic-gate fileerr = 1; 1457c478bd9Sstevel@tonic-gate break; 1467c478bd9Sstevel@tonic-gate } 147*45916cd2Sjpk ccp = strchr(cp, '\n'); 1487c478bd9Sstevel@tonic-gate if (ccp != NULL) { 149*45916cd2Sjpk if (ccp != cp && ccp[-1] == '\\') { 150*45916cd2Sjpk ccp--; 1517c478bd9Sstevel@tonic-gate contline = 1; 152*45916cd2Sjpk } 1537c478bd9Sstevel@tonic-gate else 1547c478bd9Sstevel@tonic-gate contline = 0; 1557c478bd9Sstevel@tonic-gate *ccp = NULL; 1567c478bd9Sstevel@tonic-gate } 1577c478bd9Sstevel@tonic-gate tmpcnt = strlen(cp); 1587c478bd9Sstevel@tonic-gate cp += tmpcnt; 1597c478bd9Sstevel@tonic-gate charcnt += tmpcnt; 1607c478bd9Sstevel@tonic-gate } while ((contline) || (charcnt == 0)); 1617c478bd9Sstevel@tonic-gate ccp = strpbrk(buff, "#"); 1627c478bd9Sstevel@tonic-gate if (ccp != NULL) 1637c478bd9Sstevel@tonic-gate *ccp = NULL; 1647c478bd9Sstevel@tonic-gate charcnt = strlen(buff); 1657c478bd9Sstevel@tonic-gate } while ((fileerr == 0) && (charcnt == 0)); 166*45916cd2Sjpk 167*45916cd2Sjpk if (fileerr && !charcnt) 1687c478bd9Sstevel@tonic-gate return (0); 1697c478bd9Sstevel@tonic-gate else 1707c478bd9Sstevel@tonic-gate return (charcnt); 1717c478bd9Sstevel@tonic-gate } 1727c478bd9Sstevel@tonic-gate 173*45916cd2Sjpk /* 174*45916cd2Sjpk * _daalloc - 175*45916cd2Sjpk * allocates common buffers and structures. 176*45916cd2Sjpk * returns pointer to the new structure, else returns NULL on error. 177*45916cd2Sjpk */ 178*45916cd2Sjpk static struct _dabuff * 179*45916cd2Sjpk _daalloc(void) 1807c478bd9Sstevel@tonic-gate { 181*45916cd2Sjpk struct _dabuff *_da = __dabuff; 182*45916cd2Sjpk 183*45916cd2Sjpk if (_da == NULL) { 184*45916cd2Sjpk _da = (struct _dabuff *)calloc((unsigned)1, 185*45916cd2Sjpk (unsigned)sizeof (*__dabuff)); 186*45916cd2Sjpk if (_da == NULL) 187*45916cd2Sjpk return (NULL); 188*45916cd2Sjpk DEVALLOC_FILE = "/etc/security/device_allocate"; 189*45916cd2Sjpk daf = NULL; 190*45916cd2Sjpk __dabuff = _da; 191*45916cd2Sjpk system_labeled = is_system_labeled(); 192*45916cd2Sjpk } 193*45916cd2Sjpk 194*45916cd2Sjpk return (__dabuff); 195*45916cd2Sjpk } 196*45916cd2Sjpk 197*45916cd2Sjpk /* 198*45916cd2Sjpk * getdadmfield - 199*45916cd2Sjpk * gets individual fields separated by skip in ptr. 200*45916cd2Sjpk */ 201*45916cd2Sjpk char * 202*45916cd2Sjpk getdadmfield(char *ptr, char *skip) 203*45916cd2Sjpk { 204*45916cd2Sjpk static char *tptr = NULL; 205*45916cd2Sjpk char *pend; 206*45916cd2Sjpk 207*45916cd2Sjpk /* check for a continuing search */ 2087c478bd9Sstevel@tonic-gate if (ptr == NULL) 2097c478bd9Sstevel@tonic-gate ptr = tptr; 210*45916cd2Sjpk /* check for source end */ 211*45916cd2Sjpk if (ptr == NULL || *ptr == '\0') 2127c478bd9Sstevel@tonic-gate return (NULL); 213*45916cd2Sjpk /* find terminator */ 214*45916cd2Sjpk pend = strpbrk(ptr, skip); 215*45916cd2Sjpk /* terminate and set continuation pointer */ 216*45916cd2Sjpk if (pend != NULL) { 217*45916cd2Sjpk *pend++ = '\0'; 218*45916cd2Sjpk tptr = pend; 219*45916cd2Sjpk } else 220*45916cd2Sjpk tptr = NULL; 2217c478bd9Sstevel@tonic-gate /* 222*45916cd2Sjpk * trim off any surrounding white space, return what's left 2237c478bd9Sstevel@tonic-gate */ 2247c478bd9Sstevel@tonic-gate 225*45916cd2Sjpk return (trim_white(ptr)); 2267c478bd9Sstevel@tonic-gate } 2277c478bd9Sstevel@tonic-gate 2287c478bd9Sstevel@tonic-gate /* 229*45916cd2Sjpk * setdaent - 230*45916cd2Sjpk * rewinds the device_allocate file to the begining. 2317c478bd9Sstevel@tonic-gate */ 2327c478bd9Sstevel@tonic-gate 2337c478bd9Sstevel@tonic-gate void 234*45916cd2Sjpk setdaent(void) 2357c478bd9Sstevel@tonic-gate { 236*45916cd2Sjpk struct _dabuff *_da = _daalloc(); 2377c478bd9Sstevel@tonic-gate 238*45916cd2Sjpk if (_da == NULL) 2397c478bd9Sstevel@tonic-gate return; 240*45916cd2Sjpk if (daf == NULL) 241*45916cd2Sjpk daf = fopen(DEVALLOC_FILE, "r"); 242*45916cd2Sjpk else 2437c478bd9Sstevel@tonic-gate rewind(daf); 2447c478bd9Sstevel@tonic-gate } 2457c478bd9Sstevel@tonic-gate 2467c478bd9Sstevel@tonic-gate /* 247*45916cd2Sjpk * enddaent - 248*45916cd2Sjpk * closes device_allocate file. 2497c478bd9Sstevel@tonic-gate */ 2507c478bd9Sstevel@tonic-gate 2517c478bd9Sstevel@tonic-gate void 252*45916cd2Sjpk enddaent(void) 2537c478bd9Sstevel@tonic-gate { 254*45916cd2Sjpk struct _dabuff *_da = _daalloc(); 2557c478bd9Sstevel@tonic-gate 256*45916cd2Sjpk if (_da == NULL) 2577c478bd9Sstevel@tonic-gate return; 2587c478bd9Sstevel@tonic-gate if (daf != NULL) { 2597c478bd9Sstevel@tonic-gate (void) fclose(daf); 2607c478bd9Sstevel@tonic-gate daf = NULL; 2617c478bd9Sstevel@tonic-gate } 2627c478bd9Sstevel@tonic-gate } 2637c478bd9Sstevel@tonic-gate 2647c478bd9Sstevel@tonic-gate /* 265*45916cd2Sjpk * setdafile - 266*45916cd2Sjpk * changes the default device_allocate file to the one specified. 267*45916cd2Sjpk * It does not close the previous file. If this is desired, enddaent 268*45916cd2Sjpk * should be called prior to setdafile. 2697c478bd9Sstevel@tonic-gate */ 2707c478bd9Sstevel@tonic-gate void 271*45916cd2Sjpk setdafile(char *file) 2727c478bd9Sstevel@tonic-gate { 273*45916cd2Sjpk struct _dabuff *_da = _daalloc(); 2747c478bd9Sstevel@tonic-gate 275*45916cd2Sjpk if (_da == NULL) 2767c478bd9Sstevel@tonic-gate return; 2777c478bd9Sstevel@tonic-gate if (daf != NULL) { 2787c478bd9Sstevel@tonic-gate (void) fclose(daf); 2797c478bd9Sstevel@tonic-gate daf = NULL; 2807c478bd9Sstevel@tonic-gate } 281*45916cd2Sjpk DEVALLOC_FILE = file; 2827c478bd9Sstevel@tonic-gate } 2837c478bd9Sstevel@tonic-gate 284*45916cd2Sjpk void 285*45916cd2Sjpk freedaent(devalloc_t *dap) 286*45916cd2Sjpk { 287*45916cd2Sjpk if (dap == NULL) 288*45916cd2Sjpk return; 289*45916cd2Sjpk _kva_free(dap->da_devopts); 290*45916cd2Sjpk dap->da_devopts = NULL; 291*45916cd2Sjpk } 2927c478bd9Sstevel@tonic-gate 2937c478bd9Sstevel@tonic-gate /* 294*45916cd2Sjpk * getdaon - 295*45916cd2Sjpk * checks if device_allocate has string DEVICE_ALLOCATION=ON or 296*45916cd2Sjpk * DEVICE_ALLOCATION=OFF string in it. 297*45916cd2Sjpk * returns 1 if the string is DEVICE_ALLOCATION=ON, 0 if it is 298*45916cd2Sjpk * DEVICE_ALLOCATION=OFF, -1 if neither string present. 299*45916cd2Sjpk */ 300*45916cd2Sjpk int 301*45916cd2Sjpk getdaon() 302*45916cd2Sjpk { 303*45916cd2Sjpk int is_on = -1; 304*45916cd2Sjpk char line1[DA_BUFSIZE + 1]; 305*45916cd2Sjpk struct _dabuff *_da = _daalloc(); 306*45916cd2Sjpk 307*45916cd2Sjpk setdaent(); 308*45916cd2Sjpk if ((_da == NULL) || (daf == NULL)) { 309*45916cd2Sjpk enddaent(); 310*45916cd2Sjpk return (is_on); 311*45916cd2Sjpk } 312*45916cd2Sjpk while (getdadmline(line1, (int)sizeof (line1), daf) != 0) { 313*45916cd2Sjpk if (strncmp(line1, DA_ON_STR, (strlen(DA_ON_STR) - 1)) == 0) { 314*45916cd2Sjpk is_on = 1; 315*45916cd2Sjpk break; 316*45916cd2Sjpk } else if (strncmp(line1, DA_OFF_STR, 317*45916cd2Sjpk (strlen(DA_OFF_STR) - 1)) == 0) { 318*45916cd2Sjpk is_on = 0; 319*45916cd2Sjpk break; 320*45916cd2Sjpk } 321*45916cd2Sjpk } 322*45916cd2Sjpk enddaent(); 323*45916cd2Sjpk 324*45916cd2Sjpk return (is_on); 325*45916cd2Sjpk } 326*45916cd2Sjpk 327*45916cd2Sjpk /* 328*45916cd2Sjpk * getdaent - 329*45916cd2Sjpk * When first called, returns a pointer to the first devalloc_t 330*45916cd2Sjpk * structure in device_allocate; thereafter, it returns a pointer to the 331*45916cd2Sjpk * next devalloc_t structure in the file. Thus, successive calls can be 332*45916cd2Sjpk * used to search the entire file. 333*45916cd2Sjpk * call to getdaent should be bracketed by setdaent and enddaent. 334*45916cd2Sjpk * returns NULL on error. 3357c478bd9Sstevel@tonic-gate */ 3367c478bd9Sstevel@tonic-gate devalloc_t * 337*45916cd2Sjpk getdaent(void) 3387c478bd9Sstevel@tonic-gate { 339*45916cd2Sjpk char line1[DA_BUFSIZE + 1]; 3407c478bd9Sstevel@tonic-gate devalloc_t *da; 341*45916cd2Sjpk struct _dabuff *_da = _daalloc(); 3427c478bd9Sstevel@tonic-gate 343*45916cd2Sjpk if ((_da == 0) || (daf == NULL)) 3447c478bd9Sstevel@tonic-gate return (NULL); 3457c478bd9Sstevel@tonic-gate 346*45916cd2Sjpk while (getdadmline(line1, (int)sizeof (line1), daf) != 0) { 347*45916cd2Sjpk if ((strncmp(line1, DA_ON_STR, (strlen(DA_ON_STR) - 1)) == 0) || 348*45916cd2Sjpk (strncmp(line1, DA_OFF_STR, (strlen(DA_OFF_STR) - 1)) == 0)) 3497c478bd9Sstevel@tonic-gate continue; 350*45916cd2Sjpk if ((da = da_interpret(line1)) == NULL) 351*45916cd2Sjpk continue; 352*45916cd2Sjpk return (da); 3537c478bd9Sstevel@tonic-gate } 3547c478bd9Sstevel@tonic-gate 355*45916cd2Sjpk return (NULL); 356*45916cd2Sjpk } 357*45916cd2Sjpk 3587c478bd9Sstevel@tonic-gate /* 359*45916cd2Sjpk * getdanam 360*45916cd2Sjpk * searches from the beginning of device_allocate for the device specified 361*45916cd2Sjpk * by its name. 362*45916cd2Sjpk * call to getdanam should be bracketed by setdaent and enddaent. 363*45916cd2Sjpk * returns pointer to devalloc_t for the device if it is found, else 364*45916cd2Sjpk * returns NULL if device not found or in case of error. 3657c478bd9Sstevel@tonic-gate */ 366*45916cd2Sjpk devalloc_t * 367*45916cd2Sjpk getdanam(char *name) 3687c478bd9Sstevel@tonic-gate { 369*45916cd2Sjpk char line[DA_BUFSIZE + 1]; 370*45916cd2Sjpk devalloc_t *da; 371*45916cd2Sjpk struct _dabuff *_da = _daalloc(); 3727c478bd9Sstevel@tonic-gate 373*45916cd2Sjpk if ((name == NULL) || (_da == 0) || (daf == NULL)) 374*45916cd2Sjpk return (NULL); 375*45916cd2Sjpk 376*45916cd2Sjpk while (getdadmline(line, (int)sizeof (line), daf) != 0) { 377*45916cd2Sjpk if (strstr(line, name) == NULL) 378*45916cd2Sjpk continue; 379*45916cd2Sjpk if ((da = da_interpret(line)) == NULL) 380*45916cd2Sjpk continue; 381*45916cd2Sjpk if (da_matchname(da, name)) { 382*45916cd2Sjpk enddaent(); 383*45916cd2Sjpk return (da); 384*45916cd2Sjpk } 385*45916cd2Sjpk freedaent(da); 386*45916cd2Sjpk } 387*45916cd2Sjpk 388*45916cd2Sjpk return (NULL); 389*45916cd2Sjpk } 390*45916cd2Sjpk 391*45916cd2Sjpk /* 392*45916cd2Sjpk * getdatype - 393*45916cd2Sjpk * searches from the beginning of device_allocate for the device specified 394*45916cd2Sjpk * by its type. 395*45916cd2Sjpk * call to getdatype should be bracketed by setdaent and enddaent. 396*45916cd2Sjpk * returns pointer to devalloc_t for the device if it is found, else 397*45916cd2Sjpk * returns NULL if device not found or in case of error. 398*45916cd2Sjpk */ 399*45916cd2Sjpk devalloc_t * 400*45916cd2Sjpk getdatype(char *type) 401*45916cd2Sjpk { 402*45916cd2Sjpk char line1[DA_BUFSIZE + 1]; 403*45916cd2Sjpk devalloc_t *da; 404*45916cd2Sjpk struct _dabuff *_da = _daalloc(); 405*45916cd2Sjpk 406*45916cd2Sjpk if ((type == NULL) || (_da == NULL) || (daf == NULL)) 407*45916cd2Sjpk return (NULL); 408*45916cd2Sjpk 409*45916cd2Sjpk while (getdadmline(line1, (int)sizeof (line1), daf) != 0) { 410*45916cd2Sjpk if (strstr(line1, type) == NULL) 411*45916cd2Sjpk continue; 412*45916cd2Sjpk if ((da = da_interpret(line1)) == NULL) 413*45916cd2Sjpk continue; 414*45916cd2Sjpk if (da_matchtype(da, type)) 415*45916cd2Sjpk return (da); 416*45916cd2Sjpk freedaent(da); 417*45916cd2Sjpk } 418*45916cd2Sjpk 419*45916cd2Sjpk return (NULL); 420*45916cd2Sjpk } 421*45916cd2Sjpk 422*45916cd2Sjpk /* 423*45916cd2Sjpk * da_matchname - 424*45916cd2Sjpk * checks if the specified devalloc_t is for the device specified. 425*45916cd2Sjpk * returns 1 if it is, else returns 0. 426*45916cd2Sjpk */ 427*45916cd2Sjpk int 428*45916cd2Sjpk da_matchname(devalloc_t *dap, char *name) 429*45916cd2Sjpk { 430*45916cd2Sjpk if (dap->da_devname == NULL) 4317c478bd9Sstevel@tonic-gate return (0); 432*45916cd2Sjpk 433*45916cd2Sjpk return ((strcmp(dap->da_devname, name) == 0)); 434*45916cd2Sjpk } 435*45916cd2Sjpk 436*45916cd2Sjpk /* 437*45916cd2Sjpk * da_matchtype - 438*45916cd2Sjpk * checks if the specified devalloc_t is for the device type specified. 439*45916cd2Sjpk * returns 1 if match found, else, returns 0. 440*45916cd2Sjpk */ 441*45916cd2Sjpk int 442*45916cd2Sjpk da_matchtype(devalloc_t *da, char *type) 443*45916cd2Sjpk { 444*45916cd2Sjpk if (da->da_devtype == NULL) 4457c478bd9Sstevel@tonic-gate return (0); 446*45916cd2Sjpk 447*45916cd2Sjpk return ((strcmp(da->da_devtype, type) == 0)); 448*45916cd2Sjpk } 449*45916cd2Sjpk 450*45916cd2Sjpk /* 451*45916cd2Sjpk * da_match - 452*45916cd2Sjpk * calls da_matchname or da_matchdev as appropriate. 453*45916cd2Sjpk */ 454*45916cd2Sjpk int 455*45916cd2Sjpk da_match(devalloc_t *dap, da_args *dargs) 456*45916cd2Sjpk { 457*45916cd2Sjpk if (dargs->devinfo->devname) 458*45916cd2Sjpk return (da_matchname(dap, dargs->devinfo->devname)); 459*45916cd2Sjpk else if (dargs->devinfo->devtype) 460*45916cd2Sjpk return (da_matchtype(dap, dargs->devinfo->devtype)); 461*45916cd2Sjpk 4627c478bd9Sstevel@tonic-gate return (0); 4637c478bd9Sstevel@tonic-gate } 4647c478bd9Sstevel@tonic-gate 4657c478bd9Sstevel@tonic-gate /* 466*45916cd2Sjpk * da_interpret - 467*45916cd2Sjpk * parses val and initializes pointers in devalloc_t. 468*45916cd2Sjpk * returns pointer to parsed devalloc_t entry, else returns NULL on error. 4697c478bd9Sstevel@tonic-gate */ 4707c478bd9Sstevel@tonic-gate static devalloc_t * 471*45916cd2Sjpk da_interpret(char *val) 4727c478bd9Sstevel@tonic-gate { 473*45916cd2Sjpk struct _dabuff *_da = _daalloc(); 474*45916cd2Sjpk char *opts; 475*45916cd2Sjpk int i; 476*45916cd2Sjpk kva_t *kvap; 477*45916cd2Sjpk kv_t *kvp; 4787c478bd9Sstevel@tonic-gate 479*45916cd2Sjpk if (_da == NULL) 480*45916cd2Sjpk return (NULL); 4817c478bd9Sstevel@tonic-gate 482*45916cd2Sjpk (void) strcpy(interpdaline, val); 483*45916cd2Sjpk interpdevalloc.da_devname = getdadmfield(interpdaline, KV_DELIMITER); 484*45916cd2Sjpk interpdevalloc.da_devtype = getdadmfield(NULL, KV_DELIMITER); 485*45916cd2Sjpk opts = getdadmfield(NULL, KV_DELIMITER); 486*45916cd2Sjpk (void) getdadmfield(NULL, KV_DELIMITER); /* reserved field */ 487*45916cd2Sjpk interpdevalloc.da_devauth = getdadmfield(NULL, KV_DELIMITER); 488*45916cd2Sjpk interpdevalloc.da_devexec = getdadmfield(NULL, KV_DELIMITER); 489*45916cd2Sjpk interpdevalloc.da_devopts = NULL; 490*45916cd2Sjpk if (interpdevalloc.da_devname == NULL || 491*45916cd2Sjpk interpdevalloc.da_devtype == NULL) 492*45916cd2Sjpk return (NULL); 493*45916cd2Sjpk if ((opts != NULL) && 494*45916cd2Sjpk (strncmp(opts, DA_RESERVED, strlen(DA_RESERVED)) != 0)) { 495*45916cd2Sjpk interpdevalloc.da_devopts = 496*45916cd2Sjpk _str2kva(opts, KV_ASSIGN, KV_TOKEN_DELIMIT); 497*45916cd2Sjpk } 498*45916cd2Sjpk /* remove any extraneous whitespace in the options */ 499*45916cd2Sjpk if ((kvap = interpdevalloc.da_devopts) != NULL) { 500*45916cd2Sjpk for (i = 0, kvp = kvap->data; i < kvap->length; i++, kvp++) { 501*45916cd2Sjpk (void) pack_white(kvp->key); 502*45916cd2Sjpk (void) pack_white(kvp->value); 503*45916cd2Sjpk } 504*45916cd2Sjpk } 505*45916cd2Sjpk 506*45916cd2Sjpk if (system_labeled) { 507*45916cd2Sjpk /* if label range is not defined, use the default range. */ 508*45916cd2Sjpk int i = 0, nlen = 0; 509*45916cd2Sjpk char *minstr = NULL, *maxstr = NULL; 510*45916cd2Sjpk kva_t *nkvap = NULL; 511*45916cd2Sjpk kv_t *ndata = NULL, *odata = NULL; 512*45916cd2Sjpk 513*45916cd2Sjpk if (kvap == NULL) { 514*45916cd2Sjpk nlen = 2; /* minlabel, maxlabel */ 515*45916cd2Sjpk } else { 516*45916cd2Sjpk nlen += kvap->length; 517*45916cd2Sjpk if ((minstr = kva_match(kvap, DAOPT_MINLABEL)) == NULL) 518*45916cd2Sjpk nlen++; 519*45916cd2Sjpk if ((maxstr = kva_match(kvap, DAOPT_MAXLABEL)) == NULL) 520*45916cd2Sjpk nlen++; 521*45916cd2Sjpk } 522*45916cd2Sjpk if ((minstr != NULL) && (maxstr != NULL)) 523*45916cd2Sjpk /* 524*45916cd2Sjpk * label range provided; we don't need to construct 525*45916cd2Sjpk * default range. 526*45916cd2Sjpk */ 527*45916cd2Sjpk goto out; 528*45916cd2Sjpk nkvap = _new_kva(nlen); 529*45916cd2Sjpk ndata = nkvap->data; 530*45916cd2Sjpk if (kvap != NULL) { 531*45916cd2Sjpk for (i = 0; i < kvap->length; i++) { 532*45916cd2Sjpk odata = kvap->data; 533*45916cd2Sjpk ndata[i].key = _strdup_null(odata[i].key); 534*45916cd2Sjpk ndata[i].value = _strdup_null(odata[i].value); 535*45916cd2Sjpk nkvap->length++; 536*45916cd2Sjpk } 537*45916cd2Sjpk } 538*45916cd2Sjpk if (minstr == NULL) { 539*45916cd2Sjpk ndata[i].key = strdup(DAOPT_MINLABEL); 540*45916cd2Sjpk ndata[i].value = strdup(DA_DEFAULT_MIN); 541*45916cd2Sjpk nkvap->length++; 542*45916cd2Sjpk i++; 543*45916cd2Sjpk } 544*45916cd2Sjpk if (maxstr == NULL) { 545*45916cd2Sjpk ndata[i].key = strdup(DAOPT_MAXLABEL); 546*45916cd2Sjpk ndata[i].value = strdup(DA_DEFAULT_MAX); 547*45916cd2Sjpk nkvap->length++; 548*45916cd2Sjpk } 549*45916cd2Sjpk interpdevalloc.da_devopts = nkvap; 550*45916cd2Sjpk } 551*45916cd2Sjpk 552*45916cd2Sjpk out: 5537c478bd9Sstevel@tonic-gate return (&interpdevalloc); 5547c478bd9Sstevel@tonic-gate } 555