xref: /illumos-gate/usr/src/lib/libbsm/common/getdevicerange.c (revision 581cede61ac9c14d8d4ea452562a567189eead78)
1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License (the "License").
6  * You may not use this file except in compliance with the License.
7  *
8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9  * or http://www.opensolaris.org/os/licensing.
10  * See the License for the specific language governing permissions
11  * and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL HEADER in each
14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15  * If applicable, add the following below this CDDL HEADER, with the
16  * fields enclosed by brackets "[]" replaced with your own identifying
17  * information: Portions Copyright [yyyy] [name of copyright owner]
18  *
19  * CDDL HEADER END
20  */
21 
22 /*
23  * Copyright 2006 Sun Microsystems, Inc.  All rights reserved.
24  * Use is subject to license terms.
25  */
26 
27 #pragma ident	"%Z%%M%	%I%	%E% SMI"
28 
29 #include <stdlib.h>
30 #include <errno.h>
31 #include <tsol/label.h>
32 #include <bsm/devices.h>
33 
34 
35 /*
36  * getdevicerange
37  *	Gets the minimum and maximum labels within which the device can
38  *	be used. If label range is not specified for the device in
39  *	device_allocate, defaults to admin_low and admin_high.
40  *	Returns malloc'ed blrange pointer, or NULL on any error.
41  */
42 blrange_t *
43 getdevicerange(const char *dev)
44 {
45 	int		err;
46 	char		*lstr;
47 	devalloc_t	*da;
48 	devmap_t	*dm;
49 	blrange_t	*range;
50 
51 	errno = 0;
52 	if ((range = malloc(sizeof (blrange_t))) == NULL)
53 		return (NULL);
54 	if ((range->lower_bound = blabel_alloc()) == NULL) {
55 		free(range);
56 		return (NULL);
57 	}
58 	if ((range->upper_bound = blabel_alloc()) == NULL) {
59 		blabel_free(range->lower_bound);
60 		free(range);
61 		return (NULL);
62 	}
63 
64 	/*
65 	 * If an entry is found for the named device,
66 	 * return its label range.
67 	 */
68 	setdaent();
69 	if ((da = getdanam((char *)dev)) == NULL) {
70 		setdmapent();
71 		/* check for an actual device file */
72 		if ((dm = getdmapdev((char *)dev)) != NULL) {
73 			da = getdanam(dm->dmap_devname);
74 			freedmapent(dm);
75 		}
76 		enddmapent();
77 	}
78 	enddaent();
79 	if (da == NULL) {
80 		bsllow(range->lower_bound);
81 		bslhigh(range->upper_bound);
82 	} else {
83 		lstr = kva_match(da->da_devopts, DAOPT_MINLABEL);
84 		if (lstr == NULL) {
85 			bsllow(range->lower_bound);
86 		} else if (stobsl(lstr, range->lower_bound, NO_CORRECTION,
87 		    &err) == 0) {
88 			blabel_free(range->lower_bound);
89 			blabel_free(range->upper_bound);
90 			free(range);
91 			errno = ENOTSUP;
92 			return (NULL);
93 		}
94 		lstr = kva_match(da->da_devopts, DAOPT_MAXLABEL);
95 		if (lstr == NULL) {
96 			bslhigh(range->upper_bound);
97 		} else if (stobsl(lstr, range->upper_bound, NO_CORRECTION,
98 		    &err) == 0) {
99 			blabel_free(range->lower_bound);
100 			blabel_free(range->upper_bound);
101 			free(range);
102 			errno = ENOTSUP;
103 			return (NULL);
104 		}
105 		freedaent(da);
106 	}
107 
108 	return (range);
109 }
110