]> git.saurik.com Git - apple/xnu.git/blob - pexpert/gen/bootargs.c
2d7f80b3f6f1026f5c0dceebee987e8644ec121e
[apple/xnu.git] / pexpert / gen / bootargs.c
1 /*
2 * Copyright (c) 2000-2004 Apple Computer, Inc. All rights reserved.
3 *
4 * @APPLE_OSREFERENCE_LICENSE_HEADER_START@
5 *
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. The rights granted to you under the License
10 * may not be used to create, or enable the creation or redistribution of,
11 * unlawful or unlicensed copies of an Apple operating system, or to
12 * circumvent, violate, or enable the circumvention or violation of, any
13 * terms of an Apple operating system software license agreement.
14 *
15 * Please obtain a copy of the License at
16 * http://www.opensource.apple.com/apsl/ and read it before using this file.
17 *
18 * The Original Code and all software distributed under the License are
19 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
20 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
21 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
22 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
23 * Please see the License for the specific language governing rights and
24 * limitations under the License.
25 *
26 * @APPLE_OSREFERENCE_LICENSE_HEADER_END@
27 */
28 #include <pexpert/pexpert.h>
29
30 extern boolean_t isargsep( char c);
31 extern int argstrcpy(char *from, char *to);
32 extern int getval(char *s, int *val);
33
34 #define NUM 0
35 #define STR 1
36
37 boolean_t
38 PE_parse_boot_arg(
39 const char *arg_string,
40 void *arg_ptr)
41 {
42 return PE_parse_boot_argn(arg_string, arg_ptr, -1);
43 }
44
45 boolean_t
46 PE_parse_boot_argn(
47 const char *arg_string,
48 void *arg_ptr,
49 int max_len)
50 {
51 char *args;
52 char *cp, c;
53 int i;
54 int val;
55 boolean_t arg_boolean;
56 boolean_t arg_found;
57
58 args = PE_boot_args();
59 if (*args == '\0') return FALSE;
60
61 arg_found = FALSE;
62
63 while(isargsep(*args)) args++;
64
65 while (*args)
66 {
67 if (*args == '-')
68 arg_boolean = TRUE;
69 else
70 arg_boolean = FALSE;
71
72 cp = args;
73 while (!isargsep (*cp) && *cp != '=')
74 cp++;
75 if (*cp != '=' && !arg_boolean)
76 goto gotit;
77
78 c = *cp;
79
80 i = cp-args;
81 if (strncmp(args, arg_string, i) ||
82 (i!=strlen(arg_string)))
83 goto gotit;
84 if (arg_boolean) {
85 *(unsigned int *)arg_ptr = TRUE;
86 arg_found = TRUE;
87 break;
88 } else {
89 while (isargsep (*cp))
90 cp++;
91 if (*cp == '=' && c != '=') {
92 args = cp+1;
93 goto gotit;
94 }
95 if ('_' == *arg_string) /* Force a string copy if the argument name begins with an underscore */
96 {
97 int hacklen = 16 > max_len ? 16 : max_len;
98 argstrcpy2 (++cp, (char *)arg_ptr, hacklen); /* Hack - terminate after 16 characters */
99 arg_found = TRUE;
100 break;
101 }
102 switch (getval(cp, &val))
103 {
104 case NUM:
105 *(unsigned int *)arg_ptr = val;
106 arg_found = TRUE;
107 break;
108 case STR:
109 if(max_len > 0) //max_len of 0 performs no copy at all
110 argstrcpy2(++cp, (char *)arg_ptr, max_len);
111 else if(max_len == -1)
112 argstrcpy(++cp, (char *)arg_ptr);
113 arg_found = TRUE;
114 break;
115 }
116 goto gotit;
117 }
118 gotit:
119 /* Skip over current arg */
120 while(!isargsep(*args)) args++;
121
122 /* Skip leading white space (catch end of args) */
123 while(*args && isargsep(*args)) args++;
124 }
125
126 return(arg_found);
127 }
128
129 boolean_t isargsep(
130 char c)
131 {
132 if (c == ' ' || c == '\0' || c == '\t')
133 return(TRUE);
134 else
135 return(FALSE);
136 }
137
138 int
139 argstrcpy(
140 char *from,
141 char *to)
142 {
143 int i = 0;
144
145 while (!isargsep(*from)) {
146 i++;
147 *to++ = *from++;
148 }
149 *to = 0;
150 return(i);
151 }
152
153 int
154 argstrcpy2(
155 char *from,
156 char *to,
157 unsigned maxlen)
158 {
159 int i = 0;
160
161 while (!isargsep(*from) && i < maxlen) {
162 i++;
163 *to++ = *from++;
164 }
165 *to = 0;
166 return(i);
167 }
168
169 int
170 getval(
171 char *s,
172 int *val)
173 {
174 unsigned int radix, intval;
175 char c;
176 int sign = 1;
177
178 if (*s == '=') {
179 s++;
180 if (*s == '-')
181 sign = -1, s++;
182 intval = *s++-'0';
183 radix = 10;
184 if (intval == 0) {
185 switch(*s) {
186
187 case 'x':
188 radix = 16;
189 s++;
190 break;
191
192 case 'b':
193 radix = 2;
194 s++;
195 break;
196
197 case '0': case '1': case '2': case '3':
198 case '4': case '5': case '6': case '7':
199 intval = *s-'0';
200 s++;
201 radix = 8;
202 break;
203
204 default:
205 if (!isargsep(*s))
206 return (STR);
207 }
208 } else if (intval >= radix) {
209 return (STR);
210 }
211 for(;;) {
212 c = *s++;
213 if (isargsep(c))
214 break;
215 if ((radix <= 10) &&
216 ((c >= '0') && (c <= ('9' - (10 - radix))))) {
217 c -= '0';
218 } else if ((radix == 16) &&
219 ((c >= '0') && (c <= '9'))) {
220 c -= '0';
221 } else if ((radix == 16) &&
222 ((c >= 'a') && (c <= 'f'))) {
223 c -= 'a' - 10;
224 } else if ((radix == 16) &&
225 ((c >= 'A') && (c <= 'F'))) {
226 c -= 'A' - 10;
227 } else if (c == 'k' || c == 'K') {
228 sign *= 1024;
229 break;
230 } else if (c == 'm' || c == 'M') {
231 sign *= 1024 * 1024;
232 break;
233 } else if (c == 'g' || c == 'G') {
234 sign *= 1024 * 1024 * 1024;
235 break;
236 } else {
237 return (STR);
238 }
239 if (c >= radix)
240 return (STR);
241 intval *= radix;
242 intval += c;
243 }
244 if (!isargsep(c) && !isargsep(*s))
245 return STR;
246 *val = intval * sign;
247 return (NUM);
248 }
249 *val = 1;
250 return (NUM);
251 }