2N/A * The contents of this file are subject to the terms of the 2N/A * Common Development and Distribution License (the "License"). 2N/A * You may not use this file except in compliance with the License. 2N/A * See the License for the specific language governing permissions 2N/A * and limitations under the License. 2N/A * When distributing Covered Code, include this CDDL HEADER in each 2N/A * If applicable, add the following below this CDDL HEADER, with the 2N/A * fields enclosed by brackets "[]" replaced with your own identifying 2N/A * information: Portions Copyright [yyyy] [name of copyright owner] 2N/A * Copyright (c) 2006, 2012, Oracle and/or its affiliates. All rights reserved. 2N/A * The following structure is for recording old entries to be retained. 2N/A * We read the entries from the database into a linked list in memory, 2N/A * then turn around and write them out again. 2N/A * check if the link should be included in device_maps 2N/A * return 1 if true, 0 if false. 2N/A * da_check_longindevperm - 2N/A *
ptr =
'\0';
/* handle comments */ 2N/A continue;
/* ignore blank lines */ 2N/A /* empty device list */ 2N/A * device and devname may be one of these types - 2N/A /* all wildcard types */ 2N/A * contents changed since the last time we read it. 2N/A * returns size of buffer read, or -1 on failure. 2N/A /* check the size and the time stamp on the file */ 2N/A * file has been modified since we last read it; or this 2N/A * read file into the buffer with rw lock. 2N/A * verify that the file did not change just after we read it. 2N/A * _update_zonename - 2N/A * put 'reserved' in the empty slot. 2N/A * converts a device_map entry into a printable string 2N/A * returns 0 on success, -1 on error. 2N/A * calls dmap2str to break given devmap_t into printable entry. 2N/A * returns pointer to decoded entry, NULL on error. 2N/A * converts a device_allocate entry into a printable string 2N/A * returns 0 on success, -1 on error. 2N/A * calls da2str to break given devalloc_t into printable entry. 2N/A * returns pointer to decoded entry, NULL on error. 2N/A * converts da_defs_t into a printable string. 2N/A * returns 0 on success, -1 on error. 2N/A * calls _def2str to break given da_defs_t into printable entry. 2N/A * returns pointer decoded entry, NULL on error. 2N/A * cycles through all defattr entries, stores them in memory. removes 2N/A * entries with the given search_key (device type). 2N/A * returns 0 if given entry not found, 1 if given entry removed, 2 on 2N/A * During DA_ADD, we keep an existing entry unless 2N/A * we have DA_FORCE set to override that entry. 2N/A /* retaining defattr entry: tmp_str->se_str */ 2N/A * Utility routine to make it easy to make type-based decisions in 2N/A * a switch statement. 2N/A * We have to handle the "standard" types in devlist differently than 2N/A * other devices, which are not covered by our auto-naming conventions. 2N/A * buf must be a buffer of size DA_MAX_NAME + 1 2N/A /* check safely for sizes */ 2N/A * allocatable: returns 2N/A * -1 if no auths field, 2N/A * 0 if not allocatable (marked '*') 2N/A * 1 if not marked '*' 2N/A * If dargs->optflag & DA_EVENT, does not assume the dargs list is 2N/A * complete or completely believable, since devfsadm caches 2N/A * ONLY what it has been exposed to via syseventd. 2N/A * Cycles through all the entries in the /etc files, stores them 2N/A * in memory, takes note of device->dname numbers (e.g. rmdisk0, 2N/A * Cycles through again, adds dargs entry 2N/A * with the name tname%d (lowest unused number for the device type) 2N/A * to the list of things for the caller to write out to a file, 2N/A * IFF it is a new entry. 2N/A * It is an error for it to already be there, if it is allocatable. 2N/A * Returns 0 if successful and 2 on error. 2N/A * Returns 0 if not found, 1 if found, 2 on error. 2N/A int suffix;
/* number at end of devname, i.e. rmdisk1 */ 2N/A /* read both files, maps first so we can compare actual devices */ 2N/A /* build device_maps */ 2N/A /* no need to track suffix on remove */ 2N/A /* if need to free and safe to free */ 2N/A continue;
/* don't retain */ 2N/A * Need to know which suffixes are in use 2N/A * Same type, different device. Record 2N/A * device suffix already in use, if 2N/A * Match allocatable on add is an error 2N/A * unless just looping through on a 2N/A * brainless loopy daemon. 2N/A * Or mapping attempt returned error. 2N/A "Cannot add %s on node %s",
2N/A /* add other transaction types as needed */ 2N/A * no dups w/o DA_FORCE, even if type differs, 2N/A * if there is a chance this operation is 2N/A * machine-driven. The 5 "standard types" 2N/A * can be machine-driven adds, and tend to 2N/A * Cut down on noise caused by busy daemon. 2N/A "Cannot add %s on node %s type %s",
2N/A /* retaining devmap entry: tmp_str->se_str */ 2N/A * No need to rewrite the files if the item to be removed is not 2N/A * in the files -- wait for another call on another darg. 2N/A * If we got here from an event, or from devfsadm, 2N/A * we know the passed-in devname is a useless guess, 2N/A * since the files had not been read when the name 2N/A * was chosen, and we don't keep them anywhere else 2N/A * that is sufficiently definitive. 2N/A * So, above, we've been setting bits in tmp_bitmap for each 2N/A * device of this type found as we loop through DEVMAPS_FILE, 2N/A * to make sure we don't change the entry for an existing 2N/A * allocatable device. 2N/A * Let the caller choose the name unless BOTH the name and 2N/A * device type one of: cdrom, floppy, audio, rmdisk, or tape. 2N/A * (or sr, fd for unlabeled) 2N/A * If the caller chooses a specialized name, then we 2N/A * trust the caller to keep track of the numbers 2N/A * (such as sraudio1, printer23) so we ignore the 2N/A * bitmap and therefore have no need for a limit on 2N/A * the number of devices. 2N/A * Future: support > 63 hotplug devices per type? 2N/A * DA_MAX_DEVNO was chosen as a handy number for 2N/A * a bitmap, and is much much higher than the number 2N/A * of hotpluggable devices we ever expect to see added 2N/A * by the devfsadmd daemon. 2N/A /* if need to free and safe to free */ 2N/A * Now adjust devalloc list to match devmaps 2N/A * Note we now have the correct devname for da_match to use. 2N/A "%s and %s out of sync," 2N/A /* make list w/o this entry */ 2N/A /* retaining devalloc entry: tmp_str->se_str */ 2N/A /* the caller needs to know if a remove needs to rewrite files */ 2N/A return (
1);
/* 0 and 2 cases returned earlier */ 2N/A return (0);
/* Successful DA_ADD */ 2N/A * Cycles through all the entries, stores them in memory. removes entries 2N/A * with the given search_key (device name or type). 2N/A * returns 0 if given entry not found, 1 if given entry removed, 2 on 2N/A /* build device_allocate */ 2N/A /* if in _build_lists and DA_ADD is set, so is DA_FORCE */ 2N/A /* retaining devalloc entry: tmp_str->se_str */ 2N/A /* build device_maps */ 2N/A /* retaining devmap entry: tmp_str->se_str */ 2N/A /* later code cleanup may cause the use of "found" in other cases */ 2N/A * writes current entries to devalloc_defaults. 2N/A * _write_device_allocate - 2N/A * writes current entries in the list to device_allocate. 2N/A * if the devalloc on/off string existed before, 2N/A * put it back before anything else. 2N/A * we need to check for the string only if the file 2N/A * _write_device_maps - 2N/A * writes current entries in the list to device_maps. 2N/A * and frees the strings 2N/A * _write_new_defattrs 2N/A * writes the new entry to devalloc_defaults. 2N/A * returns 0 on success, -1 on error. 2N/A * _write_new_entry - 2N/A * writes the new devalloc_t to device_allocate or the new devmap_t to 2N/A * returns 0 on success, -1 on error. 2N/A * locks the database files; lock can be either broken explicitly by 2N/A * closing the fd of the lock file, or it expires automatically at process 2N/A * returns fd of the lock file or -1 on error. 2N/A /* cannot open lock file */ 2N/A /* cannot position lock file */ 2N/A /* cannot set lock */ 2N/A * opens one or both database files - device_allocate, device_maps - in 2N/A * the specified mode. 2N/A * locks the database files; lock is either broken explicitly by the 2N/A * caller by closing the lock file fd, or it expires automatically at 2N/A * process termination. 2N/A * writes the file pointer of opened file in the input args - dafp, dmfp. 2N/A * returns fd of the lock file on success, -2 if database file does not 2N/A * exist, -1 on other errors. 2N/A * open the device allocation file 2N/A * open the device map file 2N/A * adds either DA_ON_STR or DA_OFF_STR to device_allocate 2N/A * returns 0 on success, -1 on error. 2N/A /* check the old device_allocate for on/off string */ 2N/A * the file never had either the on or the off string; 2N/A /* now put the first line that we read in fgets */ 2N/A /* now get the rest of the old file */ 2N/A /* write the on/off str + the old device_allocate to the temp file */ 2N/A * da_update_defattrs - 2N/A * writes default attributes to devalloc_defaults 2N/A * returns 0 on success, -1 on error. 2N/A * examine all entries, remove an old one if required, check 2N/A * if a new one needs to be added. 2N/A * write back any existing entries. 2N/A /* add new entries */ 2N/A * da_update_device - 2N/A * Writes existing entries and the SINGLE change requested by da_args, 2N/A * to device_allocate and device_maps. 2N/A * Returns 0 on success, -1 on error. 2N/A * device_allocate and device_maps. updates can be 2N/A * done in both or either of the files. 2N/A * name, type and list are required fields for adding a new 2N/A * Check if we are here just to record on/off status of 2N/A * device_allocation. 2N/A * We don't need to parse the file if we are here just to record 2N/A * If reacting to a hotplug, read the file entries, 2N/A * figure out what dname (tname + a new number) goes to the 2N/A * head_devmapp with everything good still in it (_rebuild_lists) 2N/A * Else examine all the entries, remove an old one if it is 2N/A * a duplicate with a device being added, returning the 2N/A * remaining list (_build_lists.) 2N/A * We need to do this only if the file exists already. 2N/A * Once we have built these lists, we need to free the strings 2N/A * in the head_* arrays before returning. 2N/A /* for device allocation, the /etc files are the "master" */ 2N/A * TODO: clean up the workings of DA_UPDATE. 2N/A * Due to da_match looking at fields that are missing 2N/A * in dargs for DA_UPDATE, the da_match call returns no match, 2N/A * but due to the way _da2str combines the devalloc_t info with 2N/A * the *dargs info, the DA_ADD_ZONE and DA_REMOVE_ZONE work. 2N/A * This would not scale if any type of update was ever needed 2N/A * Write out devallocp along with the devalloc on/off string. 2N/A * Write back any non-removed pre-existing entries. 2N/A * Add any new entries here. 2N/A /* add any new entries */ 2N/A * adds new /dev link name to the linked list of devices. 2N/A * returns 0 if link added successfully, -1 on error. 2N/A * Add the new link name to the list of links 2N/A * that the device 'dname' has. 2N/A * Either this is the first entry ever, or no matching entry 2N/A * was found. Create a new one and add to the list. 2N/A else /* no matching entry */ 2N/A * Look for default label range, authorizations and cleaning 2N/A * program in devalloc_defaults. If label range is not 2N/A * specified in devalloc_defaults, assume it to be admin_low 2N/A +
1;
/* +1 for terminator */ 2N/A * This is the first entry of this device type. 2N/A * removes a /dev link name from the linked list of devices. 2N/A * returns type of device if link for that device removed 2N/A * successfully, else returns -1 on error. 2N/A * if all links for a device are removed, stores that device 2N/A /* last name in the list */ 2N/A * what we removed above was the first entry 2N/A * in the list. make the next entry to be the 2N/A * the matching entry was the only entry in the list 2N/A * da_rm_list_entry - 2N/A * The adding of devnames to a devlist and the removal of a 2N/A * device are not symmetrical -- hot_cleanup gives a /devices 2N/A * name which is used to remove the dentry whose links all point to 2N/A * that /devices entry. 2N/A * The link argument is present if available to make debugging 2N/A * da_rm_list_entry removes an entry from the linked list of devices. 2N/A * Returns 1 if the devname was removed successfully, 2N/A * 0 if not found, -1 for error. 2N/A /* Presumably in daemon mode, no need to remove entry, list is empty */ 2N/A * checks if device allocation feature is turned on. 2N/A * returns 1 if on, 0 if off, -1 if status string not 2N/A * found in device_allocate. 2N/A * debug routine to print device entries.