openafs-string-header-cleanup-20071030
[openafs.git] / src / util / volparse.c
1 /*
2  * Copyright 2000, International Business Machines Corporation and others.
3  * All Rights Reserved.
4  * 
5  * This software has been released under the terms of the IBM Public
6  * License.  For details, see the LICENSE file in the top-level source
7  * directory or online at http://www.openafs.org/dl/license10.html
8  */
9
10 #include <afsconfig.h>
11 #include <afs/param.h>
12
13 RCSID
14     ("$Header$");
15
16 #include <string.h>
17 #ifdef HAVE_STDLIB_H
18 #include <stdlib.h>
19 #endif
20
21 /* map a partition id from any partition-style name */
22 afs_int32
23 volutil_GetPartitionID(char *aname)
24 {
25     register char tc;
26     afs_int32 temp;
27     char ascii[3];
28
29     tc = *aname;
30     if (tc == 0)
31         return -1;              /* unknown */
32     /* numbers go straight through */
33     if (tc >= '0' && tc <= '9') {
34         temp = atoi(aname);
35         /* this next check is to make the syntax less ambiguous when discriminating
36          * between volume numbers and partition IDs.  This less things like
37          * bos salvage do some reasonability checks its input w/o checking
38          * to see if the partition is really on the server.
39          */
40         if (temp < 0 || temp > 25)
41             return -1;
42         else
43             return temp;
44     }
45     /* otherwise check for vicepa or /vicepa, or just plain "a" */
46     ascii[2] = 0;
47     if (strlen(aname) <= 2) {
48         strcpy(ascii, aname);
49     } else if (!strncmp(aname, "/vicep", 6)) {
50         strncpy(ascii, aname + 6, 2);
51     } else if (!strncmp(aname, "vicep", 5)) {
52         strncpy(ascii, aname + 5, 2);
53     } else
54         return -1;              /* bad partition name */
55     /* now partitions are named /vicepa ... /vicepz, /vicepaa, /vicepab, .../vicepzz,
56      * and are numbered from 0.  Do the appropriate conversion */
57     if (ascii[1] == 0) {
58         /* one char name, 0..25 */
59         if (ascii[0] < 'a' || ascii[0] > 'z')
60             return -1;          /* wrongo */
61         return ascii[0] - 'a';
62     } else {
63         /* two char name, 26 .. <whatever> */
64         if (ascii[0] < 'a' || ascii[0] > 'z')
65             return -1;          /* wrongo */
66         if (ascii[1] < 'a' || ascii[1] > 'z')
67             return -1;          /* just as bad */
68         return (ascii[0] - 'a') * 26 + (ascii[1] - 'a') + 26;
69     }
70 }
71
72 /* map a partition number back into a partition string */
73 #define BAD_VID "BAD VOLUME ID"
74 #define BAD_VID_LEN (sizeof(BAD_VID))
75 char *
76 volutil_PartitionName_r(int avalue, char *tbuffer, int buflen)
77 {
78     char tempString[3];
79     register int i;
80
81     if (buflen < BAD_VID_LEN) {
82         if (buflen > 3)
83             (void)strcpy(tbuffer, "SPC");
84         else
85             tbuffer[0] = '\0';
86         return tbuffer;
87     }
88     memset(tbuffer, 0, buflen);
89     tempString[1] = tempString[2] = 0;
90     strcpy(tbuffer, "/vicep");
91     if (avalue < 0 || avalue >= (26 * 26 + 26)) {
92         strcpy(tbuffer, "BAD VOLUME ID");
93     } else if (avalue <= 25) {
94         tempString[0] = 'a' + avalue;
95         strcat(tbuffer, tempString);
96     } else {
97         avalue -= 26;
98         i = (avalue / 26);
99         tempString[0] = i + 'a';
100         tempString[1] = (avalue % 26) + 'a';
101         strcat(tbuffer, tempString);
102     }
103     return tbuffer;
104 }
105
106 char *
107 volutil_PartitionName(int avalue)
108 {
109 #define VPN_TBUFLEN 64
110     static char tbuffer[VPN_TBUFLEN];
111     return volutil_PartitionName_r(avalue, tbuffer, VPN_TBUFLEN - 1);
112 }
113
114 /* is this a digit or a digit-like thing? */
115 static int
116 ismeta(register int ac, register int abase)
117 {
118 /*    if (ac == '-' || ac == 'x' || ac == 'X') return 1; */
119     if (ac >= '0' && ac <= '7')
120         return 1;
121     if (abase <= 8)
122         return 0;
123     if (ac >= '8' && ac <= '9')
124         return 1;
125     if (abase <= 10)
126         return 0;
127     if (ac >= 'a' && ac <= 'f')
128         return 1;
129     if (ac >= 'A' && ac <= 'F')
130         return 1;
131     return 0;
132 }
133
134 /* given that this is a digit or a digit-like thing, compute its value */
135 static int
136 getmeta(register int ac)
137 {
138     if (ac >= '0' && ac <= '9')
139         return ac - '0';
140     if (ac >= 'a' && ac <= 'f')
141         return ac - 'a' + 10;
142     if (ac >= 'A' && ac <= 'F')
143         return ac - 'A' + 10;
144     return 0;
145 }
146
147 afs_int32
148 util_GetInt32(register char *as, afs_int32 * aval)
149 {
150     register afs_int32 total;
151     register int tc;
152     int base;
153     int negative;
154
155     total = 0;                  /* initialize things */
156     negative = 0;
157
158     /* skip over leading spaces */
159     while ((tc = *as)) {
160         if (tc != ' ' && tc != '\t')
161             break;
162     }
163
164     /* compute sign */
165     if (*as == '-') {
166         negative = 1;
167         as++;                   /* skip over character */
168     }
169
170     /* compute the base */
171     if (*as == '0') {
172         as++;
173         if (*as == 'x' || *as == 'X') {
174             base = 16;
175             as++;
176         } else
177             base = 8;
178     } else
179         base = 10;
180
181     /* compute the # itself */
182     while ((tc = *as)) {
183         if (!ismeta(tc, base))
184             return -1;
185         total *= base;
186         total += getmeta(tc);
187         as++;
188     }
189
190     if (negative)
191         *aval = -total;
192     else
193         *aval = total;
194     return 0;
195 }
196
197 afs_uint32
198 util_GetUInt32(register char *as, afs_uint32 * aval)
199 {
200     register afs_uint32 total;
201     register int tc;
202     int base;
203
204     total = 0;                  /* initialize things */
205
206     /* skip over leading spaces */
207     while ((tc = *as)) {
208         if (tc != ' ' && tc != '\t')
209             break;
210     }
211
212     /* compute the base */
213     if (*as == '0') {
214         as++;
215         if (*as == 'x' || *as == 'X') {
216             base = 16;
217             as++;
218         } else
219             base = 8;
220     } else
221         base = 10;
222
223     /* compute the # itself */
224     while ((tc = *as)) {
225         if (!ismeta(tc, base))
226             return -1;
227         total *= base;
228         total += getmeta(tc);
229         as++;
230     }
231
232     *aval = total;
233     return 0;
234 }