1*6ba597c5SAnurag S. Maskey /* 2*6ba597c5SAnurag S. Maskey * CDDL HEADER START 3*6ba597c5SAnurag S. Maskey * 4*6ba597c5SAnurag S. Maskey * The contents of this file are subject to the terms of the 5*6ba597c5SAnurag S. Maskey * Common Development and Distribution License (the "License"). 6*6ba597c5SAnurag S. Maskey * You may not use this file except in compliance with the License. 7*6ba597c5SAnurag S. Maskey * 8*6ba597c5SAnurag S. Maskey * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9*6ba597c5SAnurag S. Maskey * or http://www.opensolaris.org/os/licensing. 10*6ba597c5SAnurag S. Maskey * See the License for the specific language governing permissions 11*6ba597c5SAnurag S. Maskey * and limitations under the License. 12*6ba597c5SAnurag S. Maskey * 13*6ba597c5SAnurag S. Maskey * When distributing Covered Code, include this CDDL HEADER in each 14*6ba597c5SAnurag S. Maskey * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15*6ba597c5SAnurag S. Maskey * If applicable, add the following below this CDDL HEADER, with the 16*6ba597c5SAnurag S. Maskey * fields enclosed by brackets "[]" replaced with your own identifying 17*6ba597c5SAnurag S. Maskey * information: Portions Copyright [yyyy] [name of copyright owner] 18*6ba597c5SAnurag S. Maskey * 19*6ba597c5SAnurag S. Maskey * CDDL HEADER END 20*6ba597c5SAnurag S. Maskey */ 21*6ba597c5SAnurag S. Maskey 22*6ba597c5SAnurag S. Maskey /* 23*6ba597c5SAnurag S. Maskey * Copyright 2010 Sun Microsystems, Inc. All rights reserved. 24*6ba597c5SAnurag S. Maskey * Use is subject to license terms. 25*6ba597c5SAnurag S. Maskey */ 26*6ba597c5SAnurag S. Maskey 27*6ba597c5SAnurag S. Maskey #include <assert.h> 28*6ba597c5SAnurag S. Maskey #include <stdlib.h> 29*6ba597c5SAnurag S. Maskey #include <strings.h> 30*6ba597c5SAnurag S. Maskey #include <string.h> 31*6ba597c5SAnurag S. Maskey 32*6ba597c5SAnurag S. Maskey #include "libnwam_impl.h" 33*6ba597c5SAnurag S. Maskey #include <libintl.h> 34*6ba597c5SAnurag S. Maskey #include <libnwam.h> 35*6ba597c5SAnurag S. Maskey 36*6ba597c5SAnurag S. Maskey /* 37*6ba597c5SAnurag S. Maskey * Generic object manipulation functions. Given an object handle and 38*6ba597c5SAnurag S. Maskey * other parameters, create/destroy objects, walk them, walk their 39*6ba597c5SAnurag S. Maskey * properties, modify/retrieve/delete properties, enable/disable them, 40*6ba597c5SAnurag S. Maskey * etc. All object handles are "struct nwam_handle *" objects, sharing 41*6ba597c5SAnurag S. Maskey * the same description based on the object type, name, original name 42*6ba597c5SAnurag S. Maskey * (used in renaming) and associated data representing properties. 43*6ba597c5SAnurag S. Maskey */ 44*6ba597c5SAnurag S. Maskey 45*6ba597c5SAnurag S. Maskey nwam_error_t 46*6ba597c5SAnurag S. Maskey nwam_handle_create(nwam_object_type_t type, const char *name, 47*6ba597c5SAnurag S. Maskey struct nwam_handle **hpp) 48*6ba597c5SAnurag S. Maskey { 49*6ba597c5SAnurag S. Maskey 50*6ba597c5SAnurag S. Maskey assert(name != NULL && hpp != NULL); 51*6ba597c5SAnurag S. Maskey 52*6ba597c5SAnurag S. Maskey if (strnlen(name, NWAM_MAX_NAME_LEN) > NWAM_MAX_NAME_LEN) { 53*6ba597c5SAnurag S. Maskey *hpp = NULL; 54*6ba597c5SAnurag S. Maskey return (NWAM_INVALID_ARG); 55*6ba597c5SAnurag S. Maskey } 56*6ba597c5SAnurag S. Maskey 57*6ba597c5SAnurag S. Maskey if ((*hpp = calloc(1, sizeof (struct nwam_handle))) == NULL) 58*6ba597c5SAnurag S. Maskey return (NWAM_NO_MEMORY); 59*6ba597c5SAnurag S. Maskey 60*6ba597c5SAnurag S. Maskey (*hpp)->nwh_object_type = type; 61*6ba597c5SAnurag S. Maskey (void) strlcpy((*hpp)->nwh_name, name, strlen(name) + 1); 62*6ba597c5SAnurag S. Maskey (*hpp)->nwh_committed = B_FALSE; 63*6ba597c5SAnurag S. Maskey (*hpp)->nwh_data = NULL; 64*6ba597c5SAnurag S. Maskey 65*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 66*6ba597c5SAnurag S. Maskey } 67*6ba597c5SAnurag S. Maskey 68*6ba597c5SAnurag S. Maskey /* 69*6ba597c5SAnurag S. Maskey * Read object of specified type from dbname. 70*6ba597c5SAnurag S. Maskey */ 71*6ba597c5SAnurag S. Maskey nwam_error_t 72*6ba597c5SAnurag S. Maskey nwam_read(nwam_object_type_t type, const char *dbname, const char *name, 73*6ba597c5SAnurag S. Maskey uint64_t flags, struct nwam_handle **hpp) 74*6ba597c5SAnurag S. Maskey { 75*6ba597c5SAnurag S. Maskey nwam_error_t err; 76*6ba597c5SAnurag S. Maskey char dbname_copy[MAXPATHLEN]; 77*6ba597c5SAnurag S. Maskey 78*6ba597c5SAnurag S. Maskey assert(name != NULL && hpp != NULL); 79*6ba597c5SAnurag S. Maskey 80*6ba597c5SAnurag S. Maskey if (dbname != NULL) 81*6ba597c5SAnurag S. Maskey (void) strlcpy(dbname_copy, dbname, sizeof (dbname_copy)); 82*6ba597c5SAnurag S. Maskey 83*6ba597c5SAnurag S. Maskey if ((err = nwam_valid_flags(flags, NWAM_FLAG_BLOCKING)) != NWAM_SUCCESS) 84*6ba597c5SAnurag S. Maskey return (err); 85*6ba597c5SAnurag S. Maskey if ((err = nwam_handle_create(type, name, hpp)) != NWAM_SUCCESS) 86*6ba597c5SAnurag S. Maskey return (err); 87*6ba597c5SAnurag S. Maskey 88*6ba597c5SAnurag S. Maskey if ((err = nwam_read_object_from_backend 89*6ba597c5SAnurag S. Maskey (dbname != NULL ? dbname_copy : NULL, 90*6ba597c5SAnurag S. Maskey type == NWAM_OBJECT_TYPE_NCP ? NULL : (*hpp)->nwh_name, flags, 91*6ba597c5SAnurag S. Maskey &(*hpp)->nwh_data)) != NWAM_SUCCESS) { 92*6ba597c5SAnurag S. Maskey free(*hpp); 93*6ba597c5SAnurag S. Maskey *hpp = NULL; 94*6ba597c5SAnurag S. Maskey return (err); 95*6ba597c5SAnurag S. Maskey } 96*6ba597c5SAnurag S. Maskey if (type == NWAM_OBJECT_TYPE_NCP && dbname != NULL) { 97*6ba597c5SAnurag S. Maskey char *ncpname; 98*6ba597c5SAnurag S. Maskey 99*6ba597c5SAnurag S. Maskey /* 100*6ba597c5SAnurag S. Maskey * dbname_copy may have been changed due to case-insensitive 101*6ba597c5SAnurag S. Maskey * match against the actual NCP configuration file. 102*6ba597c5SAnurag S. Maskey */ 103*6ba597c5SAnurag S. Maskey if (nwam_ncp_file_to_name(dbname_copy, &ncpname) 104*6ba597c5SAnurag S. Maskey == NWAM_SUCCESS) { 105*6ba597c5SAnurag S. Maskey (void) strlcpy((*hpp)->nwh_name, ncpname, 106*6ba597c5SAnurag S. Maskey sizeof ((*hpp)->nwh_name)); 107*6ba597c5SAnurag S. Maskey free(ncpname); 108*6ba597c5SAnurag S. Maskey } 109*6ba597c5SAnurag S. Maskey } 110*6ba597c5SAnurag S. Maskey 111*6ba597c5SAnurag S. Maskey (*hpp)->nwh_committed = B_TRUE; 112*6ba597c5SAnurag S. Maskey 113*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 114*6ba597c5SAnurag S. Maskey } 115*6ba597c5SAnurag S. Maskey 116*6ba597c5SAnurag S. Maskey /* 117*6ba597c5SAnurag S. Maskey * Create simply creates the handle - the object-specific function must 118*6ba597c5SAnurag S. Maskey * then fill in property values. 119*6ba597c5SAnurag S. Maskey */ 120*6ba597c5SAnurag S. Maskey nwam_error_t 121*6ba597c5SAnurag S. Maskey nwam_create(nwam_object_type_t type, const char *dbname, const char *name, 122*6ba597c5SAnurag S. Maskey struct nwam_handle **hpp) 123*6ba597c5SAnurag S. Maskey { 124*6ba597c5SAnurag S. Maskey struct nwam_handle *hp; 125*6ba597c5SAnurag S. Maskey 126*6ba597c5SAnurag S. Maskey assert(hpp != NULL && name != NULL); 127*6ba597c5SAnurag S. Maskey 128*6ba597c5SAnurag S. Maskey if (nwam_read(type, dbname, name, 0, &hp) == NWAM_SUCCESS) { 129*6ba597c5SAnurag S. Maskey nwam_free(hp); 130*6ba597c5SAnurag S. Maskey return (NWAM_ENTITY_EXISTS); 131*6ba597c5SAnurag S. Maskey } 132*6ba597c5SAnurag S. Maskey /* Create handle */ 133*6ba597c5SAnurag S. Maskey return (nwam_handle_create(type, name, hpp)); 134*6ba597c5SAnurag S. Maskey } 135*6ba597c5SAnurag S. Maskey 136*6ba597c5SAnurag S. Maskey nwam_error_t 137*6ba597c5SAnurag S. Maskey nwam_get_name(struct nwam_handle *hp, char **namep) 138*6ba597c5SAnurag S. Maskey { 139*6ba597c5SAnurag S. Maskey assert(hp != NULL && namep != NULL); 140*6ba597c5SAnurag S. Maskey 141*6ba597c5SAnurag S. Maskey if ((*namep = strdup(hp->nwh_name)) == NULL) { 142*6ba597c5SAnurag S. Maskey *namep = NULL; 143*6ba597c5SAnurag S. Maskey return (NWAM_NO_MEMORY); 144*6ba597c5SAnurag S. Maskey } 145*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 146*6ba597c5SAnurag S. Maskey } 147*6ba597c5SAnurag S. Maskey 148*6ba597c5SAnurag S. Maskey nwam_error_t 149*6ba597c5SAnurag S. Maskey nwam_set_name(struct nwam_handle *hp, const char *name) 150*6ba597c5SAnurag S. Maskey { 151*6ba597c5SAnurag S. Maskey assert(hp != NULL && name != NULL); 152*6ba597c5SAnurag S. Maskey 153*6ba597c5SAnurag S. Maskey if (hp->nwh_committed) 154*6ba597c5SAnurag S. Maskey return (NWAM_ENTITY_READ_ONLY); 155*6ba597c5SAnurag S. Maskey 156*6ba597c5SAnurag S. Maskey if (strlen(name) >= sizeof (hp->nwh_name)) 157*6ba597c5SAnurag S. Maskey return (NWAM_INVALID_ARG); 158*6ba597c5SAnurag S. Maskey 159*6ba597c5SAnurag S. Maskey (void) strcpy(hp->nwh_name, name); 160*6ba597c5SAnurag S. Maskey 161*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 162*6ba597c5SAnurag S. Maskey } 163*6ba597c5SAnurag S. Maskey 164*6ba597c5SAnurag S. Maskey /* Compare object names c1 and c2 using strcasecmp() */ 165*6ba597c5SAnurag S. Maskey static int 166*6ba597c5SAnurag S. Maskey name_cmp(const void *c1, const void *c2) 167*6ba597c5SAnurag S. Maskey { 168*6ba597c5SAnurag S. Maskey nwam_ncu_type_t t1, t2; 169*6ba597c5SAnurag S. Maskey char *n1, *n2; 170*6ba597c5SAnurag S. Maskey 171*6ba597c5SAnurag S. Maskey /* If c1 and c2 are typed NCU names, compare names without the types */ 172*6ba597c5SAnurag S. Maskey if (nwam_ncu_typed_name_to_name(*(const char **)c1, &t1, &n1) 173*6ba597c5SAnurag S. Maskey == NWAM_SUCCESS && 174*6ba597c5SAnurag S. Maskey nwam_ncu_typed_name_to_name(*(const char **)c2, &t2, &n2) 175*6ba597c5SAnurag S. Maskey == NWAM_SUCCESS) { 176*6ba597c5SAnurag S. Maskey int ret = strcasecmp(n1, n2); 177*6ba597c5SAnurag S. Maskey free(n1); 178*6ba597c5SAnurag S. Maskey free(n2); 179*6ba597c5SAnurag S. Maskey 180*6ba597c5SAnurag S. Maskey /* For NCUs with the same name, compare their types */ 181*6ba597c5SAnurag S. Maskey if (ret == 0) { 182*6ba597c5SAnurag S. Maskey if (t1 < t2) 183*6ba597c5SAnurag S. Maskey ret = -1; 184*6ba597c5SAnurag S. Maskey else if (t1 > t2) 185*6ba597c5SAnurag S. Maskey ret = 1; 186*6ba597c5SAnurag S. Maskey } 187*6ba597c5SAnurag S. Maskey return (ret); 188*6ba597c5SAnurag S. Maskey } 189*6ba597c5SAnurag S. Maskey 190*6ba597c5SAnurag S. Maskey return (strcasecmp(*(const char **)c1, *(const char **)c2)); 191*6ba597c5SAnurag S. Maskey } 192*6ba597c5SAnurag S. Maskey 193*6ba597c5SAnurag S. Maskey /* 194*6ba597c5SAnurag S. Maskey * Generic walk function takes the standard walk arguments, and in addition 195*6ba597c5SAnurag S. Maskey * takes a selection callback that is object-specific. If this returns 196*6ba597c5SAnurag S. Maskey * 0, the object is a valid selection for the walk and the callback is called. 197*6ba597c5SAnurag S. Maskey * Otherwise, it is skipped. 198*6ba597c5SAnurag S. Maskey */ 199*6ba597c5SAnurag S. Maskey nwam_error_t 200*6ba597c5SAnurag S. Maskey nwam_walk(nwam_object_type_t type, const char *dbname, 201*6ba597c5SAnurag S. Maskey int(*cb)(struct nwam_handle *, void *), 202*6ba597c5SAnurag S. Maskey void *data, uint64_t flags, int *retp, 203*6ba597c5SAnurag S. Maskey int(*selectcb)(struct nwam_handle *, uint64_t, void *)) 204*6ba597c5SAnurag S. Maskey { 205*6ba597c5SAnurag S. Maskey void *objlist; 206*6ba597c5SAnurag S. Maskey nwam_value_t value; 207*6ba597c5SAnurag S. Maskey char **object_names; 208*6ba597c5SAnurag S. Maskey uint_t i, num_objects = 0; 209*6ba597c5SAnurag S. Maskey struct nwam_handle *hp; 210*6ba597c5SAnurag S. Maskey nwam_error_t err; 211*6ba597c5SAnurag S. Maskey int ret = 0; 212*6ba597c5SAnurag S. Maskey 213*6ba597c5SAnurag S. Maskey assert(cb != NULL); 214*6ba597c5SAnurag S. Maskey 215*6ba597c5SAnurag S. Maskey /* 216*6ba597c5SAnurag S. Maskey * To walk a set of objects, call nwam_read_object_from_backend() 217*6ba597c5SAnurag S. Maskey * with a "dbname" argument set to the container db name and 218*6ba597c5SAnurag S. Maskey * the object name set to NULL. This returns an nvlist with one 219*6ba597c5SAnurag S. Maskey * member - the NWAM_OBJECT_NAMES_STRING - and the values it contains 220*6ba597c5SAnurag S. Maskey * represent the names of the objects. Read each in turn, calling 221*6ba597c5SAnurag S. Maskey * the callback function. 222*6ba597c5SAnurag S. Maskey */ 223*6ba597c5SAnurag S. Maskey if ((err = nwam_read_object_from_backend((char *)dbname, NULL, flags, 224*6ba597c5SAnurag S. Maskey &objlist)) != NWAM_SUCCESS) { 225*6ba597c5SAnurag S. Maskey if (err == NWAM_ENTITY_NOT_FOUND) { 226*6ba597c5SAnurag S. Maskey /* 227*6ba597c5SAnurag S. Maskey * This indicates the dbname container is not present. 228*6ba597c5SAnurag S. Maskey * Do not pass back an error in this case, since it is 229*6ba597c5SAnurag S. Maskey * valid for a container not to exist. 230*6ba597c5SAnurag S. Maskey */ 231*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 232*6ba597c5SAnurag S. Maskey } 233*6ba597c5SAnurag S. Maskey return (err); 234*6ba597c5SAnurag S. Maskey } 235*6ba597c5SAnurag S. Maskey 236*6ba597c5SAnurag S. Maskey if ((err = nwam_get_prop_value(objlist, NWAM_OBJECT_NAMES_STRING, 237*6ba597c5SAnurag S. Maskey &value)) != NWAM_SUCCESS) { 238*6ba597c5SAnurag S. Maskey nwam_free_object_list(objlist); 239*6ba597c5SAnurag S. Maskey return (err); 240*6ba597c5SAnurag S. Maskey } 241*6ba597c5SAnurag S. Maskey err = nwam_value_get_string_array(value, &object_names, &num_objects); 242*6ba597c5SAnurag S. Maskey nwam_free_object_list(objlist); 243*6ba597c5SAnurag S. Maskey if (err != NWAM_SUCCESS) { 244*6ba597c5SAnurag S. Maskey nwam_value_free(value); 245*6ba597c5SAnurag S. Maskey return (err); 246*6ba597c5SAnurag S. Maskey } 247*6ba597c5SAnurag S. Maskey 248*6ba597c5SAnurag S. Maskey /* sort the object names alphabetically */ 249*6ba597c5SAnurag S. Maskey qsort(object_names, num_objects, sizeof (char *), name_cmp); 250*6ba597c5SAnurag S. Maskey 251*6ba597c5SAnurag S. Maskey for (i = 0; i < num_objects; i++) { 252*6ba597c5SAnurag S. Maskey err = nwam_read(type, dbname, object_names[i], 253*6ba597c5SAnurag S. Maskey flags & NWAM_FLAG_GLOBAL_MASK, &hp); 254*6ba597c5SAnurag S. Maskey /* An object may have disappeared. If so, skip it. */ 255*6ba597c5SAnurag S. Maskey if (err == NWAM_ENTITY_NOT_FOUND) 256*6ba597c5SAnurag S. Maskey continue; 257*6ba597c5SAnurag S. Maskey if (err != NWAM_SUCCESS) { 258*6ba597c5SAnurag S. Maskey nwam_value_free(value); 259*6ba597c5SAnurag S. Maskey return (err); 260*6ba597c5SAnurag S. Maskey } 261*6ba597c5SAnurag S. Maskey if ((selectcb == NULL) || (selectcb(hp, flags, data) == 0)) { 262*6ba597c5SAnurag S. Maskey ret = cb(hp, data); 263*6ba597c5SAnurag S. Maskey if (ret != 0) { 264*6ba597c5SAnurag S. Maskey nwam_free(hp); 265*6ba597c5SAnurag S. Maskey nwam_value_free(value); 266*6ba597c5SAnurag S. Maskey if (retp != NULL) 267*6ba597c5SAnurag S. Maskey *retp = ret; 268*6ba597c5SAnurag S. Maskey return (NWAM_WALK_HALTED); 269*6ba597c5SAnurag S. Maskey } 270*6ba597c5SAnurag S. Maskey } 271*6ba597c5SAnurag S. Maskey nwam_free(hp); 272*6ba597c5SAnurag S. Maskey } 273*6ba597c5SAnurag S. Maskey nwam_value_free(value); 274*6ba597c5SAnurag S. Maskey 275*6ba597c5SAnurag S. Maskey if (retp != NULL) 276*6ba597c5SAnurag S. Maskey *retp = ret; 277*6ba597c5SAnurag S. Maskey return (err); 278*6ba597c5SAnurag S. Maskey } 279*6ba597c5SAnurag S. Maskey 280*6ba597c5SAnurag S. Maskey void 281*6ba597c5SAnurag S. Maskey nwam_free(struct nwam_handle *hp) 282*6ba597c5SAnurag S. Maskey { 283*6ba597c5SAnurag S. Maskey if (hp != NULL) { 284*6ba597c5SAnurag S. Maskey if (hp->nwh_data != NULL) 285*6ba597c5SAnurag S. Maskey nwam_free_object_list(hp->nwh_data); 286*6ba597c5SAnurag S. Maskey free(hp); 287*6ba597c5SAnurag S. Maskey } 288*6ba597c5SAnurag S. Maskey } 289*6ba597c5SAnurag S. Maskey 290*6ba597c5SAnurag S. Maskey /* 291*6ba597c5SAnurag S. Maskey * Copy object represented by oldhp to an object newname, all in container 292*6ba597c5SAnurag S. Maskey * dbname. 293*6ba597c5SAnurag S. Maskey */ 294*6ba597c5SAnurag S. Maskey nwam_error_t 295*6ba597c5SAnurag S. Maskey nwam_copy(const char *dbname, struct nwam_handle *oldhp, const char *newname, 296*6ba597c5SAnurag S. Maskey struct nwam_handle **newhpp) 297*6ba597c5SAnurag S. Maskey { 298*6ba597c5SAnurag S. Maskey nwam_error_t err; 299*6ba597c5SAnurag S. Maskey struct nwam_handle *hp; 300*6ba597c5SAnurag S. Maskey 301*6ba597c5SAnurag S. Maskey assert(oldhp != NULL && newname != NULL && newhpp != NULL); 302*6ba597c5SAnurag S. Maskey 303*6ba597c5SAnurag S. Maskey if (nwam_read(oldhp->nwh_object_type, dbname, newname, 0, &hp) 304*6ba597c5SAnurag S. Maskey == NWAM_SUCCESS) { 305*6ba597c5SAnurag S. Maskey nwam_free(hp); 306*6ba597c5SAnurag S. Maskey return (NWAM_ENTITY_EXISTS); 307*6ba597c5SAnurag S. Maskey } 308*6ba597c5SAnurag S. Maskey 309*6ba597c5SAnurag S. Maskey if ((err = nwam_handle_create(oldhp->nwh_object_type, newname, newhpp)) 310*6ba597c5SAnurag S. Maskey != NWAM_SUCCESS) 311*6ba597c5SAnurag S. Maskey return (err); 312*6ba597c5SAnurag S. Maskey if ((err = nwam_dup_object_list(oldhp->nwh_data, 313*6ba597c5SAnurag S. Maskey &((*newhpp)->nwh_data))) != NWAM_SUCCESS) { 314*6ba597c5SAnurag S. Maskey nwam_free(*newhpp); 315*6ba597c5SAnurag S. Maskey *newhpp = NULL; 316*6ba597c5SAnurag S. Maskey return (err); 317*6ba597c5SAnurag S. Maskey } 318*6ba597c5SAnurag S. Maskey 319*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 320*6ba597c5SAnurag S. Maskey } 321*6ba597c5SAnurag S. Maskey 322*6ba597c5SAnurag S. Maskey /* ARGSUSED3 */ 323*6ba597c5SAnurag S. Maskey nwam_error_t 324*6ba597c5SAnurag S. Maskey nwam_walk_props(struct nwam_handle *hp, 325*6ba597c5SAnurag S. Maskey int (*cb)(const char *, nwam_value_t, void *), 326*6ba597c5SAnurag S. Maskey void *data, uint64_t flags, int *retp) 327*6ba597c5SAnurag S. Maskey { 328*6ba597c5SAnurag S. Maskey char *lastpropname = NULL, *propname; 329*6ba597c5SAnurag S. Maskey nwam_value_t value; 330*6ba597c5SAnurag S. Maskey nwam_error_t err; 331*6ba597c5SAnurag S. Maskey int ret = 0; 332*6ba597c5SAnurag S. Maskey 333*6ba597c5SAnurag S. Maskey assert(hp != NULL && hp->nwh_data != NULL && cb != NULL); 334*6ba597c5SAnurag S. Maskey 335*6ba597c5SAnurag S. Maskey if ((err = nwam_valid_flags(flags, 0)) != NWAM_SUCCESS) 336*6ba597c5SAnurag S. Maskey return (err); 337*6ba597c5SAnurag S. Maskey while ((err = nwam_next_object_prop(hp->nwh_data, lastpropname, 338*6ba597c5SAnurag S. Maskey &propname, &value)) == NWAM_SUCCESS) { 339*6ba597c5SAnurag S. Maskey 340*6ba597c5SAnurag S. Maskey ret = cb(propname, value, data); 341*6ba597c5SAnurag S. Maskey if (ret != 0) 342*6ba597c5SAnurag S. Maskey err = NWAM_WALK_HALTED; 343*6ba597c5SAnurag S. Maskey 344*6ba597c5SAnurag S. Maskey /* Free value */ 345*6ba597c5SAnurag S. Maskey nwam_value_free(value); 346*6ba597c5SAnurag S. Maskey 347*6ba597c5SAnurag S. Maskey if (err != NWAM_SUCCESS) 348*6ba597c5SAnurag S. Maskey break; 349*6ba597c5SAnurag S. Maskey 350*6ba597c5SAnurag S. Maskey lastpropname = propname; 351*6ba597c5SAnurag S. Maskey } 352*6ba597c5SAnurag S. Maskey 353*6ba597c5SAnurag S. Maskey if (retp != NULL) 354*6ba597c5SAnurag S. Maskey *retp = ret; 355*6ba597c5SAnurag S. Maskey if (err == NWAM_SUCCESS || err == NWAM_LIST_END) 356*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 357*6ba597c5SAnurag S. Maskey return (err); 358*6ba597c5SAnurag S. Maskey } 359*6ba597c5SAnurag S. Maskey 360*6ba597c5SAnurag S. Maskey /* 361*6ba597c5SAnurag S. Maskey * Note that prior to calling the generic commit function, object-specific 362*6ba597c5SAnurag S. Maskey * validation should be carried out. 363*6ba597c5SAnurag S. Maskey */ 364*6ba597c5SAnurag S. Maskey nwam_error_t 365*6ba597c5SAnurag S. Maskey nwam_commit(const char *dbname, struct nwam_handle *hp, uint64_t flags) 366*6ba597c5SAnurag S. Maskey { 367*6ba597c5SAnurag S. Maskey nwam_error_t err; 368*6ba597c5SAnurag S. Maskey uint64_t iflags = flags; 369*6ba597c5SAnurag S. Maskey boolean_t is_ncu; 370*6ba597c5SAnurag S. Maskey struct nwam_handle *testhp; 371*6ba597c5SAnurag S. Maskey nwam_action_t action; 372*6ba597c5SAnurag S. Maskey 373*6ba597c5SAnurag S. Maskey assert(hp != NULL); 374*6ba597c5SAnurag S. Maskey 375*6ba597c5SAnurag S. Maskey /* 376*6ba597c5SAnurag S. Maskey * NWAM_FLAG_ENTITY_KNOWN_WLAN is only used for Known WLANs and 377*6ba597c5SAnurag S. Maskey * NWAM_FLAG_ENTITY_ENABLE is used for other objects (during enable 378*6ba597c5SAnurag S. Maskey * and disable). 379*6ba597c5SAnurag S. Maskey */ 380*6ba597c5SAnurag S. Maskey if ((err = nwam_valid_flags(flags, 381*6ba597c5SAnurag S. Maskey NWAM_FLAG_BLOCKING | NWAM_FLAG_CREATE | 382*6ba597c5SAnurag S. Maskey (hp->nwh_object_type == NWAM_OBJECT_TYPE_KNOWN_WLAN ? 383*6ba597c5SAnurag S. Maskey NWAM_FLAG_ENTITY_KNOWN_WLAN : NWAM_FLAG_ENTITY_ENABLE))) 384*6ba597c5SAnurag S. Maskey != NWAM_SUCCESS) 385*6ba597c5SAnurag S. Maskey return (err); 386*6ba597c5SAnurag S. Maskey 387*6ba597c5SAnurag S. Maskey is_ncu = (hp->nwh_object_type == NWAM_OBJECT_TYPE_NCU); 388*6ba597c5SAnurag S. Maskey 389*6ba597c5SAnurag S. Maskey /* 390*6ba597c5SAnurag S. Maskey * Does object already exist? If not, action is ADD, otherwise REFRESH. 391*6ba597c5SAnurag S. Maskey */ 392*6ba597c5SAnurag S. Maskey switch (nwam_read(hp->nwh_object_type, (char *)dbname, hp->nwh_name, 0, 393*6ba597c5SAnurag S. Maskey &testhp)) { 394*6ba597c5SAnurag S. Maskey case NWAM_ENTITY_NOT_FOUND: 395*6ba597c5SAnurag S. Maskey action = NWAM_ACTION_ADD; 396*6ba597c5SAnurag S. Maskey break; 397*6ba597c5SAnurag S. Maskey case NWAM_SUCCESS: 398*6ba597c5SAnurag S. Maskey nwam_free(testhp); 399*6ba597c5SAnurag S. Maskey if (hp->nwh_object_type == NWAM_OBJECT_TYPE_NCP) 400*6ba597c5SAnurag S. Maskey return (NWAM_ENTITY_EXISTS); 401*6ba597c5SAnurag S. Maskey /* FALLTHRU */ 402*6ba597c5SAnurag S. Maskey default: 403*6ba597c5SAnurag S. Maskey action = NWAM_ACTION_REFRESH; 404*6ba597c5SAnurag S. Maskey break; 405*6ba597c5SAnurag S. Maskey } 406*6ba597c5SAnurag S. Maskey 407*6ba597c5SAnurag S. Maskey err = nwam_update_object_in_backend((char *)dbname, 408*6ba597c5SAnurag S. Maskey hp->nwh_object_type == NWAM_OBJECT_TYPE_NCP ? NULL : hp->nwh_name, 409*6ba597c5SAnurag S. Maskey iflags, hp->nwh_data); 410*6ba597c5SAnurag S. Maskey if (err != NWAM_SUCCESS) 411*6ba597c5SAnurag S. Maskey return (err); 412*6ba597c5SAnurag S. Maskey 413*6ba597c5SAnurag S. Maskey hp->nwh_committed = B_TRUE; 414*6ba597c5SAnurag S. Maskey 415*6ba597c5SAnurag S. Maskey /* 416*6ba597c5SAnurag S. Maskey * Tell nwamd to reread this object. For NCUs, we need to convert 417*6ba597c5SAnurag S. Maskey * the dbname to the NCP name in order to pass it to nwamd. 418*6ba597c5SAnurag S. Maskey */ 419*6ba597c5SAnurag S. Maskey if (is_ncu) { 420*6ba597c5SAnurag S. Maskey char *ncpname; 421*6ba597c5SAnurag S. Maskey 422*6ba597c5SAnurag S. Maskey if (nwam_ncp_file_to_name(dbname, &ncpname) == NWAM_SUCCESS) { 423*6ba597c5SAnurag S. Maskey (void) nwam_request_action(hp->nwh_object_type, 424*6ba597c5SAnurag S. Maskey hp->nwh_name, ncpname, action); 425*6ba597c5SAnurag S. Maskey free(ncpname); 426*6ba597c5SAnurag S. Maskey } 427*6ba597c5SAnurag S. Maskey } else { 428*6ba597c5SAnurag S. Maskey (void) nwam_request_action(hp->nwh_object_type, hp->nwh_name, 429*6ba597c5SAnurag S. Maskey NULL, action); 430*6ba597c5SAnurag S. Maskey } 431*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 432*6ba597c5SAnurag S. Maskey } 433*6ba597c5SAnurag S. Maskey 434*6ba597c5SAnurag S. Maskey static boolean_t 435*6ba597c5SAnurag S. Maskey nwam_is_active(struct nwam_handle *hp) 436*6ba597c5SAnurag S. Maskey { 437*6ba597c5SAnurag S. Maskey nwam_state_t state; 438*6ba597c5SAnurag S. Maskey nwam_aux_state_t aux; 439*6ba597c5SAnurag S. Maskey 440*6ba597c5SAnurag S. Maskey return ((nwam_get_state(NULL, hp, &state, &aux) == NWAM_SUCCESS && 441*6ba597c5SAnurag S. Maskey state == NWAM_STATE_ONLINE)); 442*6ba597c5SAnurag S. Maskey } 443*6ba597c5SAnurag S. Maskey 444*6ba597c5SAnurag S. Maskey nwam_error_t 445*6ba597c5SAnurag S. Maskey nwam_destroy(const char *dbname, struct nwam_handle *hp, uint64_t flags) 446*6ba597c5SAnurag S. Maskey { 447*6ba597c5SAnurag S. Maskey nwam_error_t err; 448*6ba597c5SAnurag S. Maskey char *name; 449*6ba597c5SAnurag S. Maskey boolean_t is_ncp, is_ncu; 450*6ba597c5SAnurag S. Maskey 451*6ba597c5SAnurag S. Maskey assert(hp != NULL); 452*6ba597c5SAnurag S. Maskey 453*6ba597c5SAnurag S. Maskey /* NWAM_FLAG_ENTITY_KNOWN_WLAN is only used for Known WLANs */ 454*6ba597c5SAnurag S. Maskey if ((err = nwam_valid_flags(flags, 455*6ba597c5SAnurag S. Maskey NWAM_FLAG_BLOCKING | NWAM_FLAG_DO_NOT_FREE | 456*6ba597c5SAnurag S. Maskey (hp->nwh_object_type == NWAM_OBJECT_TYPE_KNOWN_WLAN ? 457*6ba597c5SAnurag S. Maskey NWAM_FLAG_ENTITY_KNOWN_WLAN : 0))) != NWAM_SUCCESS) 458*6ba597c5SAnurag S. Maskey return (err); 459*6ba597c5SAnurag S. Maskey 460*6ba597c5SAnurag S. Maskey is_ncp = hp->nwh_object_type == NWAM_OBJECT_TYPE_NCP; 461*6ba597c5SAnurag S. Maskey is_ncu = hp->nwh_object_type == NWAM_OBJECT_TYPE_NCU; 462*6ba597c5SAnurag S. Maskey name = hp->nwh_name; 463*6ba597c5SAnurag S. Maskey 464*6ba597c5SAnurag S. Maskey /* Check if object is active */ 465*6ba597c5SAnurag S. Maskey if (!is_ncp && !is_ncu && nwam_is_active(hp)) 466*6ba597c5SAnurag S. Maskey return (NWAM_ENTITY_IN_USE); 467*6ba597c5SAnurag S. Maskey 468*6ba597c5SAnurag S. Maskey /* For NCPs, just remove the dbname file, otherwise remove the object */ 469*6ba597c5SAnurag S. Maskey err = nwam_remove_object_from_backend((char *)dbname, 470*6ba597c5SAnurag S. Maskey is_ncp ? NULL : name, flags); 471*6ba597c5SAnurag S. Maskey 472*6ba597c5SAnurag S. Maskey /* 473*6ba597c5SAnurag S. Maskey * Tell nwamd to remove this object. For NCUs, we need to convert the 474*6ba597c5SAnurag S. Maskey * dbname filename to the NCP name to pass it to nwamd. 475*6ba597c5SAnurag S. Maskey */ 476*6ba597c5SAnurag S. Maskey if (is_ncu) { 477*6ba597c5SAnurag S. Maskey char *ncpname; 478*6ba597c5SAnurag S. Maskey 479*6ba597c5SAnurag S. Maskey if (nwam_ncp_file_to_name(dbname, &ncpname) == NWAM_SUCCESS) { 480*6ba597c5SAnurag S. Maskey (void) nwam_request_action(hp->nwh_object_type, name, 481*6ba597c5SAnurag S. Maskey ncpname, NWAM_ACTION_DESTROY); 482*6ba597c5SAnurag S. Maskey free(ncpname); 483*6ba597c5SAnurag S. Maskey } 484*6ba597c5SAnurag S. Maskey } else { 485*6ba597c5SAnurag S. Maskey (void) nwam_request_action(hp->nwh_object_type, name, NULL, 486*6ba597c5SAnurag S. Maskey NWAM_ACTION_DESTROY); 487*6ba597c5SAnurag S. Maskey } 488*6ba597c5SAnurag S. Maskey 489*6ba597c5SAnurag S. Maskey if ((err == NWAM_SUCCESS) && !(flags & NWAM_FLAG_DO_NOT_FREE)) 490*6ba597c5SAnurag S. Maskey nwam_free(hp); 491*6ba597c5SAnurag S. Maskey 492*6ba597c5SAnurag S. Maskey return (err); 493*6ba597c5SAnurag S. Maskey } 494*6ba597c5SAnurag S. Maskey 495*6ba597c5SAnurag S. Maskey /* 496*6ba597c5SAnurag S. Maskey * Enable/disable functions assume prior checking of activation mode 497*6ba597c5SAnurag S. Maskey * to ensure an enable/disable action is valid for the object. "parent" in these 498*6ba597c5SAnurag S. Maskey * functions specifies the NCP for NCUs. 499*6ba597c5SAnurag S. Maskey */ 500*6ba597c5SAnurag S. Maskey nwam_error_t 501*6ba597c5SAnurag S. Maskey nwam_enable(const char *parent, struct nwam_handle *hp) 502*6ba597c5SAnurag S. Maskey { 503*6ba597c5SAnurag S. Maskey return (nwam_request_action(hp->nwh_object_type, hp->nwh_name, 504*6ba597c5SAnurag S. Maskey parent, NWAM_ACTION_ENABLE)); 505*6ba597c5SAnurag S. Maskey } 506*6ba597c5SAnurag S. Maskey 507*6ba597c5SAnurag S. Maskey nwam_error_t 508*6ba597c5SAnurag S. Maskey nwam_disable(const char *parent, struct nwam_handle *hp) 509*6ba597c5SAnurag S. Maskey { 510*6ba597c5SAnurag S. Maskey return (nwam_request_action(hp->nwh_object_type, hp->nwh_name, 511*6ba597c5SAnurag S. Maskey parent, NWAM_ACTION_DISABLE)); 512*6ba597c5SAnurag S. Maskey } 513*6ba597c5SAnurag S. Maskey 514*6ba597c5SAnurag S. Maskey nwam_error_t 515*6ba597c5SAnurag S. Maskey nwam_get_state(const char *parent, struct nwam_handle *hp, nwam_state_t *statep, 516*6ba597c5SAnurag S. Maskey nwam_aux_state_t *auxp) 517*6ba597c5SAnurag S. Maskey { 518*6ba597c5SAnurag S. Maskey return (nwam_request_state(hp->nwh_object_type, hp->nwh_name, parent, 519*6ba597c5SAnurag S. Maskey statep, auxp)); 520*6ba597c5SAnurag S. Maskey } 521*6ba597c5SAnurag S. Maskey 522*6ba597c5SAnurag S. Maskey struct nwam_prop_table_entry * 523*6ba597c5SAnurag S. Maskey nwam_get_prop_table_entry(struct nwam_prop_table table, const char *propname) 524*6ba597c5SAnurag S. Maskey { 525*6ba597c5SAnurag S. Maskey struct nwam_prop_table_entry *cur = table.entries; 526*6ba597c5SAnurag S. Maskey struct nwam_prop_table_entry *end = cur + table.num_entries; 527*6ba597c5SAnurag S. Maskey 528*6ba597c5SAnurag S. Maskey assert(propname != NULL); 529*6ba597c5SAnurag S. Maskey 530*6ba597c5SAnurag S. Maskey for (; cur < end; cur++) { 531*6ba597c5SAnurag S. Maskey if (strcmp(propname, cur->prop_name) == 0) 532*6ba597c5SAnurag S. Maskey return (cur); 533*6ba597c5SAnurag S. Maskey } 534*6ba597c5SAnurag S. Maskey return (NULL); 535*6ba597c5SAnurag S. Maskey } 536*6ba597c5SAnurag S. Maskey 537*6ba597c5SAnurag S. Maskey nwam_error_t 538*6ba597c5SAnurag S. Maskey nwam_get_prop_description(struct nwam_prop_table table, const char *propname, 539*6ba597c5SAnurag S. Maskey const char **descriptionp) 540*6ba597c5SAnurag S. Maskey { 541*6ba597c5SAnurag S. Maskey struct nwam_prop_table_entry *pte; 542*6ba597c5SAnurag S. Maskey 543*6ba597c5SAnurag S. Maskey assert(propname != NULL && descriptionp != NULL); 544*6ba597c5SAnurag S. Maskey 545*6ba597c5SAnurag S. Maskey if ((pte = nwam_get_prop_table_entry(table, propname)) == NULL) { 546*6ba597c5SAnurag S. Maskey *descriptionp = NULL; 547*6ba597c5SAnurag S. Maskey return (NWAM_INVALID_ARG); 548*6ba597c5SAnurag S. Maskey } 549*6ba597c5SAnurag S. Maskey 550*6ba597c5SAnurag S. Maskey *descriptionp = dgettext(TEXT_DOMAIN, pte->prop_description); 551*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 552*6ba597c5SAnurag S. Maskey } 553*6ba597c5SAnurag S. Maskey 554*6ba597c5SAnurag S. Maskey nwam_error_t 555*6ba597c5SAnurag S. Maskey nwam_get_prop_type(struct nwam_prop_table table, const char *propname, 556*6ba597c5SAnurag S. Maskey nwam_value_type_t *typep) 557*6ba597c5SAnurag S. Maskey { 558*6ba597c5SAnurag S. Maskey struct nwam_prop_table_entry *pte; 559*6ba597c5SAnurag S. Maskey 560*6ba597c5SAnurag S. Maskey assert(propname != NULL && typep != NULL); 561*6ba597c5SAnurag S. Maskey 562*6ba597c5SAnurag S. Maskey if ((pte = nwam_get_prop_table_entry(table, propname)) == NULL) 563*6ba597c5SAnurag S. Maskey return (NWAM_INVALID_ARG); 564*6ba597c5SAnurag S. Maskey 565*6ba597c5SAnurag S. Maskey *typep = pte->prop_type; 566*6ba597c5SAnurag S. Maskey 567*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 568*6ba597c5SAnurag S. Maskey } 569*6ba597c5SAnurag S. Maskey 570*6ba597c5SAnurag S. Maskey nwam_error_t 571*6ba597c5SAnurag S. Maskey nwam_prop_multivalued(struct nwam_prop_table table, const char *propname, 572*6ba597c5SAnurag S. Maskey boolean_t *multip) 573*6ba597c5SAnurag S. Maskey { 574*6ba597c5SAnurag S. Maskey struct nwam_prop_table_entry *pte; 575*6ba597c5SAnurag S. Maskey 576*6ba597c5SAnurag S. Maskey assert(propname != NULL && multip != NULL); 577*6ba597c5SAnurag S. Maskey 578*6ba597c5SAnurag S. Maskey if ((pte = nwam_get_prop_table_entry(table, propname)) == NULL) 579*6ba597c5SAnurag S. Maskey return (NWAM_INVALID_ARG); 580*6ba597c5SAnurag S. Maskey 581*6ba597c5SAnurag S. Maskey if (pte->prop_max_numvalues > 1) 582*6ba597c5SAnurag S. Maskey *multip = B_TRUE; 583*6ba597c5SAnurag S. Maskey else 584*6ba597c5SAnurag S. Maskey *multip = B_FALSE; 585*6ba597c5SAnurag S. Maskey 586*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 587*6ba597c5SAnurag S. Maskey } 588*6ba597c5SAnurag S. Maskey 589*6ba597c5SAnurag S. Maskey nwam_error_t 590*6ba597c5SAnurag S. Maskey nwam_prop_read_only(struct nwam_prop_table table, const char *propname, 591*6ba597c5SAnurag S. Maskey boolean_t *readp) 592*6ba597c5SAnurag S. Maskey { 593*6ba597c5SAnurag S. Maskey struct nwam_prop_table_entry *pte; 594*6ba597c5SAnurag S. Maskey 595*6ba597c5SAnurag S. Maskey assert(propname != NULL && readp != NULL); 596*6ba597c5SAnurag S. Maskey 597*6ba597c5SAnurag S. Maskey if ((pte = nwam_get_prop_table_entry(table, propname)) == NULL) 598*6ba597c5SAnurag S. Maskey return (NWAM_INVALID_ARG); 599*6ba597c5SAnurag S. Maskey 600*6ba597c5SAnurag S. Maskey *readp = (pte->prop_is_readonly && !nwam_uid_is_netadm()); 601*6ba597c5SAnurag S. Maskey 602*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 603*6ba597c5SAnurag S. Maskey } 604*6ba597c5SAnurag S. Maskey 605*6ba597c5SAnurag S. Maskey /* 606*6ba597c5SAnurag S. Maskey * Structure used to pass in prop table and errprop string pointer to internal 607*6ba597c5SAnurag S. Maskey * validate function. 608*6ba597c5SAnurag S. Maskey */ 609*6ba597c5SAnurag S. Maskey struct validate_internal_arg { 610*6ba597c5SAnurag S. Maskey struct nwam_prop_table table; 611*6ba597c5SAnurag S. Maskey const char **errpropp; 612*6ba597c5SAnurag S. Maskey }; 613*6ba597c5SAnurag S. Maskey 614*6ba597c5SAnurag S. Maskey /* 615*6ba597c5SAnurag S. Maskey * Callback used by nwam_walk_props() in nwam_validate(), and 616*6ba597c5SAnurag S. Maskey * by nwam_validate_prop() to determine that the number, type and 617*6ba597c5SAnurag S. Maskey * range of values are correct, and that validation function (if present) 618*6ba597c5SAnurag S. Maskey * succeeds. 619*6ba597c5SAnurag S. Maskey */ 620*6ba597c5SAnurag S. Maskey static int 621*6ba597c5SAnurag S. Maskey nwam_validate_prop_internal(const char *propname, nwam_value_t value, 622*6ba597c5SAnurag S. Maskey void *arg) 623*6ba597c5SAnurag S. Maskey { 624*6ba597c5SAnurag S. Maskey struct validate_internal_arg *via = arg; 625*6ba597c5SAnurag S. Maskey struct nwam_prop_table table = via->table; 626*6ba597c5SAnurag S. Maskey const char **errpropp = via->errpropp; 627*6ba597c5SAnurag S. Maskey struct nwam_prop_table_entry *pte; 628*6ba597c5SAnurag S. Maskey nwam_error_t err; 629*6ba597c5SAnurag S. Maskey nwam_value_type_t type; 630*6ba597c5SAnurag S. Maskey uint_t numvalues; 631*6ba597c5SAnurag S. Maskey int i; 632*6ba597c5SAnurag S. Maskey 633*6ba597c5SAnurag S. Maskey if ((err = nwam_value_get_numvalues(value, &numvalues)) 634*6ba597c5SAnurag S. Maskey != NWAM_SUCCESS || 635*6ba597c5SAnurag S. Maskey (err = nwam_value_get_type(value, &type)) != NWAM_SUCCESS) { 636*6ba597c5SAnurag S. Maskey if (errpropp != NULL) 637*6ba597c5SAnurag S. Maskey *errpropp = propname; 638*6ba597c5SAnurag S. Maskey return (err); 639*6ba597c5SAnurag S. Maskey } 640*6ba597c5SAnurag S. Maskey if ((pte = nwam_get_prop_table_entry(table, propname)) == NULL) 641*6ba597c5SAnurag S. Maskey return (NWAM_INVALID_ARG); 642*6ba597c5SAnurag S. Maskey 643*6ba597c5SAnurag S. Maskey /* have we get expected number of values? */ 644*6ba597c5SAnurag S. Maskey if (numvalues < pte->prop_min_numvalues || 645*6ba597c5SAnurag S. Maskey numvalues > pte->prop_max_numvalues) { 646*6ba597c5SAnurag S. Maskey if (errpropp != NULL) 647*6ba597c5SAnurag S. Maskey *errpropp = propname; 648*6ba597c5SAnurag S. Maskey if (numvalues < 1) 649*6ba597c5SAnurag S. Maskey return (NWAM_ENTITY_NO_VALUE); 650*6ba597c5SAnurag S. Maskey else 651*6ba597c5SAnurag S. Maskey return (NWAM_ENTITY_INVALID_VALUE); 652*6ba597c5SAnurag S. Maskey } 653*6ba597c5SAnurag S. Maskey /* Ensure type matches */ 654*6ba597c5SAnurag S. Maskey if (numvalues > 0) { 655*6ba597c5SAnurag S. Maskey for (i = 0; i < numvalues; i++) { 656*6ba597c5SAnurag S. Maskey if (pte->prop_type != type) { 657*6ba597c5SAnurag S. Maskey if (errpropp != NULL) 658*6ba597c5SAnurag S. Maskey *errpropp = propname; 659*6ba597c5SAnurag S. Maskey return (NWAM_ENTITY_TYPE_MISMATCH); 660*6ba597c5SAnurag S. Maskey 661*6ba597c5SAnurag S. Maskey } 662*6ba597c5SAnurag S. Maskey } 663*6ba597c5SAnurag S. Maskey } 664*6ba597c5SAnurag S. Maskey /* Call property-specific validation function */ 665*6ba597c5SAnurag S. Maskey if (pte->prop_validate != NULL) { 666*6ba597c5SAnurag S. Maskey err = pte->prop_validate(value); 667*6ba597c5SAnurag S. Maskey if (err != NWAM_SUCCESS && errpropp != NULL) 668*6ba597c5SAnurag S. Maskey *errpropp = propname; 669*6ba597c5SAnurag S. Maskey return (err); 670*6ba597c5SAnurag S. Maskey } 671*6ba597c5SAnurag S. Maskey 672*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 673*6ba597c5SAnurag S. Maskey } 674*6ba597c5SAnurag S. Maskey 675*6ba597c5SAnurag S. Maskey nwam_error_t 676*6ba597c5SAnurag S. Maskey nwam_validate_prop(struct nwam_prop_table table, struct nwam_handle *hp, 677*6ba597c5SAnurag S. Maskey const char *propname, nwam_value_t value) 678*6ba597c5SAnurag S. Maskey { 679*6ba597c5SAnurag S. Maskey struct validate_internal_arg via; 680*6ba597c5SAnurag S. Maskey 681*6ba597c5SAnurag S. Maskey assert(hp != NULL && propname != NULL); 682*6ba597c5SAnurag S. Maskey 683*6ba597c5SAnurag S. Maskey via.table = table; 684*6ba597c5SAnurag S. Maskey via.errpropp = NULL; 685*6ba597c5SAnurag S. Maskey 686*6ba597c5SAnurag S. Maskey return ((nwam_error_t)nwam_validate_prop_internal(propname, 687*6ba597c5SAnurag S. Maskey value, &via)); 688*6ba597c5SAnurag S. Maskey } 689*6ba597c5SAnurag S. Maskey 690*6ba597c5SAnurag S. Maskey nwam_error_t 691*6ba597c5SAnurag S. Maskey nwam_validate(struct nwam_prop_table table, struct nwam_handle *hp, 692*6ba597c5SAnurag S. Maskey const char **errpropp) 693*6ba597c5SAnurag S. Maskey { 694*6ba597c5SAnurag S. Maskey struct validate_internal_arg via; 695*6ba597c5SAnurag S. Maskey nwam_error_t err1, err2; 696*6ba597c5SAnurag S. Maskey 697*6ba597c5SAnurag S. Maskey assert(hp != NULL); 698*6ba597c5SAnurag S. Maskey 699*6ba597c5SAnurag S. Maskey via.table = table; 700*6ba597c5SAnurag S. Maskey via.errpropp = errpropp; 701*6ba597c5SAnurag S. Maskey 702*6ba597c5SAnurag S. Maskey err1 = nwam_walk_props(hp, nwam_validate_prop_internal, &via, 703*6ba597c5SAnurag S. Maskey 0, (int *)&err2); 704*6ba597c5SAnurag S. Maskey if (err1 != NWAM_SUCCESS) 705*6ba597c5SAnurag S. Maskey return (err2); 706*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 707*6ba597c5SAnurag S. Maskey } 708*6ba597c5SAnurag S. Maskey 709*6ba597c5SAnurag S. Maskey /* 710*6ba597c5SAnurag S. Maskey * Given the type and class flag representations, return the list of properties 711*6ba597c5SAnurag S. Maskey * that can be set for that type/class combination. Note this list is a complete 712*6ba597c5SAnurag S. Maskey * property list that includes both the required and the optional properties. 713*6ba597c5SAnurag S. Maskey * The type and class flags are only used for NCU objects at present. 714*6ba597c5SAnurag S. Maskey * 715*6ba597c5SAnurag S. Maskey * Caller needs to free prop_list. 716*6ba597c5SAnurag S. Maskey */ 717*6ba597c5SAnurag S. Maskey nwam_error_t 718*6ba597c5SAnurag S. Maskey nwam_get_default_proplist(struct nwam_prop_table table, 719*6ba597c5SAnurag S. Maskey uint64_t type, uint64_t class, const char ***prop_list, uint_t *numvalues) 720*6ba597c5SAnurag S. Maskey { 721*6ba597c5SAnurag S. Maskey struct nwam_prop_table_entry *cur = table.entries; 722*6ba597c5SAnurag S. Maskey struct nwam_prop_table_entry *end = cur + table.num_entries; 723*6ba597c5SAnurag S. Maskey int i = 0; 724*6ba597c5SAnurag S. Maskey const char **list = NULL; 725*6ba597c5SAnurag S. Maskey 726*6ba597c5SAnurag S. Maskey assert(prop_list != NULL && numvalues != NULL); 727*6ba597c5SAnurag S. Maskey 728*6ba597c5SAnurag S. Maskey /* Construct a list of all properties for required type/class */ 729*6ba597c5SAnurag S. Maskey list = calloc(table.num_entries, sizeof (char *)); 730*6ba597c5SAnurag S. Maskey if (list == NULL) { 731*6ba597c5SAnurag S. Maskey *prop_list = NULL; 732*6ba597c5SAnurag S. Maskey *numvalues = 0; 733*6ba597c5SAnurag S. Maskey return (NWAM_NO_MEMORY); 734*6ba597c5SAnurag S. Maskey } 735*6ba597c5SAnurag S. Maskey for (; cur < end; cur++) { 736*6ba597c5SAnurag S. Maskey if (((type & cur->prop_type_membership) == 0) || 737*6ba597c5SAnurag S. Maskey ((class & cur->prop_class_membership) == 0)) 738*6ba597c5SAnurag S. Maskey continue; 739*6ba597c5SAnurag S. Maskey list[i++] = cur->prop_name; 740*6ba597c5SAnurag S. Maskey } 741*6ba597c5SAnurag S. Maskey *numvalues = i; 742*6ba597c5SAnurag S. Maskey *prop_list = list; 743*6ba597c5SAnurag S. Maskey return (NWAM_SUCCESS); 744*6ba597c5SAnurag S. Maskey } 745