7 v4parseip(uchar *to, char *from)
13 for(i = 0; i < 4 && *p; i++){
14 to[i] = strtoul(p, &p, 0);
19 case 0: /* class A - 1 uchar net */
30 case 2: /* class B - 2 uchar net */
43 return c == '.' || c == ':' || isascii(c) && isxdigit(c);
51 if(c == '.' || c == ':' || isascii(c) && isalnum(c))
57 * `from' may contain an address followed by other characters,
58 * at least in /boot, so we permit whitespace (and more) after the address.
59 * we do ensure that "delete" cannot be parsed as "de::".
61 * some callers don't check the return value for errors, so
62 * set `to' to something distinctive in the case of a parse error.
65 parseip(uchar *to, char *from)
67 int i, elipsis = 0, v4 = 1;
71 memset(to, 0, IPaddrlen);
73 for(i = 0; i < IPaddrlen && ipcharok(*p); i+=2){
75 x = strtoul(p, &p, 16);
76 if(*p == '.' || (*p == 0 && i == 0)){ /* ends with v4? */
78 memset(to, 0, IPaddrlen);
79 return -1; /* parse error */
81 p = v4parseip(to+i, op);
85 /* v6: at most 4 hex digits, followed by colon or delim */
86 if(x != (ushort)x || *p != ':' && !delimchar(*p)) {
87 memset(to, 0, IPaddrlen);
88 return -1; /* parse error */
94 if(*++p == ':'){ /* :: is elided zero short(s) */
96 memset(to, 0, IPaddrlen);
97 return -1; /* second :: */
102 } else if (p == op) /* strtoul made no progress? */
105 if (p == from || !delimchar(*p)) {
106 memset(to, 0, IPaddrlen);
107 return -1; /* parse error */
110 memmove(&to[elipsis+IPaddrlen-i], &to[elipsis], i-elipsis);
111 memset(&to[elipsis], 0, IPaddrlen-i);
114 to[10] = to[11] = 0xff;
115 return nhgetl(to + IPv4off);
121 * hack to allow ip v4 masks to be entered in the old
125 parseipmask(uchar *to, char *from)
132 /* as a number of prefix bits */
139 memset(to, 0, IPaddrlen);
140 for(p = to; i >= 8; i -= 8)
143 *p = ~((1<<(8-i))-1);
144 x = nhgetl(to+IPv4off);
146 * identify as ipv6 if the mask is inexpressible as a v4 mask
147 * (because it has too few mask bits). Arguably, we could
148 * always return 6 here.
150 if (w < 8*(IPaddrlen-IPv4addrlen))
153 /* as a straight v4 bit mask */
154 x = parseip(to, from);
156 x = (ulong)nhgetl(to + IPv4off);
157 if(memcmp(to, v4prefix, IPv4off) == 0)
158 memset(to, 0xff, IPv4off);
164 * parse a v4 ip address/mask in cidr format
167 v4parsecidr(uchar *addr, uchar *mask, char *from)
173 p = v4parseip(addr, from);
176 /* as a number of prefix bits */
177 i = strtoul(p+1, &p, 0);
180 memset(mask, 0, IPv4addrlen);
181 for(a = mask; i >= 8; i -= 8)
184 *a = ~((1<<(8-i))-1);
186 memcpy(mask, defmask(addr), IPv4addrlen);