2 * valuepair.c Functions to handle VALUE_PAIRs
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
20 * Copyright 2000,2006 The FreeRADIUS server project
23 #include <freeradius-devel/ident.h>
26 #include <freeradius-devel/libradius.h>
34 #ifdef HAVE_PCREPOSIX_H
35 # include <pcreposix.h>
42 static const char *months[] = {
43 "jan", "feb", "mar", "apr", "may", "jun",
44 "jul", "aug", "sep", "oct", "nov", "dec" };
47 * This padding is necessary only for attributes that are NOT
48 * in the dictionary, and then only because the rest of the
49 * code accesses vp->name directly, rather than through an
52 * The name padding has to be large enough for:
54 * Attr-{3}.{8}.{3}.{3}.{3}.{3}
56 * i.e. 28 characters, plus a zero. We add some more bytes for
57 * padding, because the VALUE_PAIR structure may be un-aligned.
59 * The result is that for the normal case, the server uses a less
60 * memory (36 bytes * number of VALUE_PAIRs).
62 #define FR_VP_NAME_PAD (32)
63 #define FR_VP_NAME_LEN (30)
65 VALUE_PAIR *pairalloc(DICT_ATTR *da)
71 * Not in the dictionary: the name is allocated AFTER
72 * the VALUE_PAIR struct.
74 if (!da) name_len = FR_VP_NAME_PAD;
76 vp = malloc(sizeof(*vp) + name_len);
78 fr_strerror_printf("Out of memory");
81 memset(vp, 0, sizeof(*vp));
84 vp->attribute = da->attr;
85 vp->vendor = da->vendor;
88 vp->flags = da->flags;
92 vp->type = PW_TYPE_OCTETS;
94 memset(&vp->flags, 0, sizeof(vp->flags));
95 vp->flags.unknown_attr = 1;
97 vp->operator = T_OP_EQ;
108 case PW_TYPE_INTEGER:
115 case PW_TYPE_INTEGER64:
120 vp->length = sizeof(vp->vp_ifid);
123 case PW_TYPE_IPV6ADDR:
124 vp->length = sizeof(vp->vp_ipv6addr);
127 case PW_TYPE_IPV6PREFIX:
128 vp->length = sizeof(vp->vp_ipv6prefix);
131 case PW_TYPE_ETHERNET:
132 vp->length = sizeof(vp->vp_ether);
140 case PW_TYPE_COMBO_IP:
150 * Create a new valuepair.
152 VALUE_PAIR *paircreate_raw(int attr, int vendor, int type, VALUE_PAIR *vp)
154 char *p = (char *) (vp + 1);
156 if (!vp->flags.unknown_attr) {
162 vp->attribute = attr;
163 vp->operator = T_OP_EQ;
167 memset(&vp->flags, 0, sizeof(vp->flags));
168 vp->flags.unknown_attr = 1;
170 if (!vp_print_name(p, FR_VP_NAME_LEN, vp->attribute, vp->vendor)) {
179 * Create a new valuepair.
181 VALUE_PAIR *paircreate(int attr, int vendor, int type)
186 da = dict_attrbyvalue(attr, vendor);
187 if ((vp = pairalloc(da)) == NULL) {
192 * It isn't in the dictionary: update the name.
194 if (!da) return paircreate_raw(attr, vendor, type, vp);
200 * release the memory used by a single attribute-value pair
201 * just a wrapper around free() for now.
203 void pairbasicfree(VALUE_PAIR *pair)
205 if (pair->type == PW_TYPE_TLV) free(pair->vp_tlv);
206 /* clear the memory here */
207 memset(pair, 0, sizeof(*pair));
212 * Release the memory used by a list of attribute-value
213 * pairs, and sets the pair pointer to NULL.
215 void pairfree(VALUE_PAIR **pair_ptr)
217 VALUE_PAIR *next, *pair;
219 if (!pair_ptr) return;
222 while (pair != NULL) {
233 * Find the pair with the matching attribute
235 VALUE_PAIR * pairfind(VALUE_PAIR *first, unsigned int attr, unsigned int vendor)
238 if ((first->attribute == attr) && (first->vendor == vendor)) {
249 * Delete the pair(s) with the matching attribute
251 void pairdelete(VALUE_PAIR **first, unsigned int attr, unsigned int vendor)
253 VALUE_PAIR *i, *next;
254 VALUE_PAIR **last = first;
256 for(i = *first; i; i = next) {
258 if ((i->attribute == attr) && (i->vendor == vendor)) {
268 * Add a pair at the end of a VALUE_PAIR list.
270 void pairadd(VALUE_PAIR **first, VALUE_PAIR *add)
276 if (*first == NULL) {
280 for(i = *first; i->next; i = i->next)
286 * Add or replace a pair at the end of a VALUE_PAIR list.
288 void pairreplace(VALUE_PAIR **first, VALUE_PAIR *replace)
290 VALUE_PAIR *i, *next;
291 VALUE_PAIR **prev = first;
293 if (*first == NULL) {
299 * Not an empty list, so find item if it is there, and
300 * replace it. Note, we always replace the first one, and
301 * we ignore any others that might exist.
303 for(i = *first; i; i = next) {
307 * Found the first attribute, replace it,
310 if ((i->attribute == replace->attribute) &&
311 (i->vendor == replace->vendor)) {
315 * Should really assert that replace->next == NULL
317 replace->next = next;
323 * Point to where the attribute should go.
329 * If we got here, we didn't find anything to replace, so
330 * stopped at the last item, which we just append to.
339 VALUE_PAIR *paircopyvp(const VALUE_PAIR *vp)
344 if (!vp) return NULL;
346 if (!vp->flags.unknown_attr) {
349 name_len = FR_VP_NAME_PAD;
352 if ((n = malloc(sizeof(*n) + name_len)) == NULL) {
353 fr_strerror_printf("out of memory");
356 memcpy(n, vp, sizeof(*n) + name_len);
359 * Reset the name field to point to the NEW attribute,
360 * rather than to the OLD one.
362 if (vp->flags.unknown_attr) n->name = (char *) (n + 1);
366 if ((n->type == PW_TYPE_TLV) &&
367 (n->vp_tlv != NULL)) {
368 n->vp_tlv = malloc(n->length);
369 memcpy(n->vp_tlv, vp->vp_tlv, n->length);
377 * Copy just a certain type of pairs.
379 VALUE_PAIR *paircopy2(VALUE_PAIR *vp, unsigned int attr, unsigned int vendor)
381 VALUE_PAIR *first, *n, **last;
388 !((vp->attribute == attr) && (vp->vendor == vendor))) {
394 if (!n) return first;
406 VALUE_PAIR *paircopy(VALUE_PAIR *vp)
408 return paircopy2(vp, 0, 0);
413 * Move attributes from one list to the other
414 * if not already present.
416 void pairmove(VALUE_PAIR **to, VALUE_PAIR **from)
418 VALUE_PAIR **tailto, *i, *j, *next;
419 VALUE_PAIR *tailfrom = NULL;
421 int has_password = 0;
424 * First, see if there are any passwords here, and
425 * point "tailto" to the end of the "to" list.
428 for(i = *to; i; i = i->next) {
429 if (i->attribute == PW_USER_PASSWORD ||
430 i->attribute == PW_CRYPT_PASSWORD)
436 * Loop over the "from" list.
438 for(i = *from; i; i = next) {
442 * If there was a password in the "to" list,
443 * do not move any other password from the
444 * "from" to the "to" list.
447 (i->attribute == PW_USER_PASSWORD ||
448 i->attribute == PW_CRYPT_PASSWORD)) {
453 switch (i->operator) {
455 * These are COMPARISON attributes
456 * from a check list, and are not
457 * supposed to be copied!
475 * If the attribute is already present in "to",
476 * do not move it from "from" to "to". We make
477 * an exception for "Hint" which can appear multiple
478 * times, and we never move "Fall-Through".
480 if (i->attribute == PW_FALL_THROUGH ||
481 (i->attribute != PW_HINT && i->attribute != PW_FRAMED_ROUTE)) {
483 found = pairfind(*to, i->attribute, i->vendor);
484 switch (i->operator) {
487 * If matching attributes are found,
490 case T_OP_SUB: /* -= */
492 if (!i->vp_strvalue[0] ||
493 (strcmp((char *)found->vp_strvalue,
494 (char *)i->vp_strvalue) == 0)){
495 pairdelete(to, found->attribute, found->vendor);
498 * 'tailto' may have been
502 for(j = *to; j; j = j->next) {
511 /* really HAVE_REGEX_H */
514 * Attr-Name =~ "s/find/replace/"
516 * Very bad code. Barely working,
522 (i->vp_strvalue[0] == 's')) {
529 p = i->vp_strvalue + 1;
530 q = strchr(p + 1, *p);
531 if (!q || (q[strlen(q) - 1] != *p)) {
535 str = strdup(i->vp_strvalue + 2);
538 q[strlen(q) - 1] = '\0';
540 regcomp(®, str, 0);
541 if (regexec(®, found->vp_strvalue,
543 fprintf(stderr, "\"%s\" will have %d to %d replaced with %s\n",
544 found->vp_strvalue, match[0].rm_so,
551 tailfrom = i; /* don't copy it over */
555 case T_OP_EQ: /* = */
557 * FIXME: Tunnel attributes with
558 * different tags are different
563 continue; /* with the loop */
568 * If a similar attribute is found,
569 * replace it with the new one. Otherwise,
570 * add the new one to the list.
572 case T_OP_SET: /* := */
574 VALUE_PAIR *mynext = found->next;
577 * Do NOT call pairdelete()
578 * here, due to issues with
579 * re-writing "request->username".
581 * Everybody calls pairmove,
582 * and expects it to work.
583 * We can't update request->username
584 * here, so instead we over-write
585 * the vp that it's pointing to.
587 memcpy(found, i, sizeof(*found));
588 found->next = mynext;
590 pairdelete(&found->next, found->attribute, found->vendor);
593 * 'tailto' may have been
596 for(j = found; j; j = j->next) {
604 * Add the new element to the list, even
605 * if similar ones already exist.
608 case T_OP_ADD: /* += */
613 tailfrom->next = next;
618 * If ALL of the 'to' attributes have been deleted,
619 * then ensure that the 'tail' is updated to point
634 * Move one kind of attributes from one list to the other
636 void pairmove2(VALUE_PAIR **to, VALUE_PAIR **from, unsigned int attr, unsigned int vendor)
638 VALUE_PAIR *to_tail, *i, *next;
639 VALUE_PAIR *iprev = NULL;
642 * Find the last pair in the "to" list and put it in "to_tail".
646 for(i = *to; i; i = i->next)
651 for(i = *from; i; i = next) {
655 * vendor=0, attr = PW_VENDOR_SPECIFIC means
656 * "match any vendor attribute".
658 if ((vendor == 0) && (attr == PW_VENDOR_SPECIFIC)) {
660 * It's a VSA: move it over.
662 if (i->vendor != 0) goto move;
665 * It's Vendor-Specific: move it over.
667 if (i->attribute == attr) goto move;
670 * It's not a VSA: ignore it.
677 * If it isn't an exact match, ignore it.
679 if (!((i->vendor == vendor) && (i->attribute == attr))) {
686 * Remove the attribute from the "from" list.
694 * Add the attribute to the "to" list.
707 * Sort of strtok/strsep function.
709 static char *mystrtok(char **ptr, const char *sep)
715 while (**ptr && strchr(sep, **ptr))
720 while (**ptr && strchr(sep, **ptr) == NULL)
728 * Turn printable string into time_t
729 * Returns -1 on error, 0 on OK.
731 static int gettime(const char *valstr, time_t *date)
742 * Test for unix timestamp date
744 *date = strtoul(valstr, &tail, 10);
750 memset(tm, 0, sizeof(*tm));
751 tm->tm_isdst = -1; /* don't know, and don't care about DST */
753 strlcpy(buf, valstr, sizeof(buf));
756 f[0] = mystrtok(&p, " \t");
757 f[1] = mystrtok(&p, " \t");
758 f[2] = mystrtok(&p, " \t");
759 f[3] = mystrtok(&p, " \t"); /* may, or may not, be present */
760 if (!f[0] || !f[1] || !f[2]) return -1;
763 * The time has a colon, where nothing else does.
764 * So if we find it, bubble it to the back of the list.
767 for (i = 0; i < 3; i++) {
768 if (strchr(f[i], ':')) {
778 * The month is text, which allows us to find it easily.
781 for (i = 0; i < 3; i++) {
782 if (isalpha( (int) *f[i])) {
784 * Bubble the month to the front of the list
790 for (i = 0; i < 12; i++) {
791 if (strncasecmp(months[i], f[0], 3) == 0) {
799 /* month not found? */
800 if (tm->tm_mon == 12) return -1;
803 * The year may be in f[1], or in f[2]
805 tm->tm_year = atoi(f[1]);
806 tm->tm_mday = atoi(f[2]);
808 if (tm->tm_year >= 1900) {
813 * We can't use 2-digit years any more, they make it
814 * impossible to tell what's the day, and what's the year.
816 if (tm->tm_mday < 1900) return -1;
819 * Swap the year and the day.
822 tm->tm_year = tm->tm_mday - 1900;
827 * If the day is out of range, die.
829 if ((tm->tm_mday < 1) || (tm->tm_mday > 31)) {
834 * There may be %H:%M:%S. Parse it in a hacky way.
837 f[0] = f[3]; /* HH */
838 f[1] = strchr(f[0], ':'); /* find : separator */
839 if (!f[1]) return -1;
841 *(f[1]++) = '\0'; /* nuke it, and point to MM:SS */
843 f[2] = strchr(f[1], ':'); /* find : separator */
845 *(f[2]++) = '\0'; /* nuke it, and point to SS */
846 tm->tm_sec = atoi(f[2]);
847 } /* else leave it as zero */
849 tm->tm_hour = atoi(f[0]);
850 tm->tm_min = atoi(f[1]);
854 * Returns -1 on error.
857 if (t == (time_t) -1) return -1;
864 static const char *hextab = "0123456789abcdef";
867 * Parse a string value into a given VALUE_PAIR
869 * FIXME: we probably want to fix this function to accept
870 * octets as values for any type of attribute. We should then
871 * double-check the parsed value, to be sure it's legal for that
872 * type (length, etc.)
874 static uint32_t getint(const char *value, char **end)
876 if ((value[0] == '0') && (value[1] == 'x')) {
877 return strtoul(value, end, 16);
880 return strtoul(value, end, 10);
883 static int check_for_whitespace(const char *value)
886 if (!isspace((int) *value)) return 0;
895 VALUE_PAIR *pairparsevalue(VALUE_PAIR *vp, const char *value)
900 unsigned long long y;
904 if (!value) return NULL;
907 * Even for integers, dates and ip addresses we
908 * keep the original string in vp->vp_strvalue.
910 if (vp->type != PW_TYPE_TLV) {
911 strlcpy(vp->vp_strvalue, value, sizeof(vp->vp_strvalue));
912 vp->length = strlen(vp->vp_strvalue);
924 while (*cp && (length < (sizeof(vp->vp_strvalue) - 1))) {
958 c = '\\'; /* no cp++ */
961 if ((cp[0] >= '0') &&
967 (sscanf(cp, "%3o", &x) == 1)) {
970 } /* else just do '\\' */
976 vp->vp_strvalue[length] = '\0';
982 * It's a comparison, not a real IP.
984 if ((vp->operator == T_OP_REG_EQ) ||
985 (vp->operator == T_OP_REG_NE)) {
990 * FIXME: complain if hostname
991 * cannot be resolved, or resolve later!
1000 if (ip_hton(cs, AF_INET, &ipaddr) < 0) {
1002 fr_strerror_printf("Failed to find IP address for %s", cs);
1006 vp->vp_ipaddr = ipaddr.ipaddr.ip4addr.s_addr;
1016 * Note that ALL integers are unsigned!
1018 vp->vp_integer = getint(value, &p);
1020 if (vp->vp_integer > 255) {
1021 fr_strerror_printf("Byte value \"%s\" is larger than 255", value);
1026 if (check_for_whitespace(p)) break;
1027 goto check_for_value;
1031 * Note that ALL integers are unsigned!
1033 vp->vp_integer = getint(value, &p);
1036 if (vp->vp_integer > 65535) {
1037 fr_strerror_printf("Byte value \"%s\" is larger than 65535", value);
1042 if (check_for_whitespace(p)) break;
1043 goto check_for_value;
1045 case PW_TYPE_INTEGER:
1047 * Note that ALL integers are unsigned!
1049 vp->vp_integer = getint(value, &p);
1052 if (check_for_whitespace(p)) break;
1056 * Look for the named value for the given
1059 if ((dval = dict_valbyname(vp->attribute, vp->vendor, value)) == NULL) {
1060 fr_strerror_printf("Unknown value %s for attribute %s",
1064 vp->vp_integer = dval->value;
1067 case PW_TYPE_INTEGER64:
1069 * Note that ALL integers are unsigned!
1071 p = vp->vp_strvalue;
1072 if (sscanf(p, "%llu", &y) != 1) {
1073 fr_strerror_printf("Invalid value %s for attribute %s",
1077 vp->vp_integer64 = y;
1079 p += strspn(p, "0123456789");
1080 if (check_for_whitespace(p)) break;
1086 * time_t may be 64 bits, whule vp_date
1087 * MUST be 32-bits. We need an
1088 * intermediary variable to handle
1093 if (gettime(value, &date) < 0) {
1094 fr_strerror_printf("failed to parse time string "
1104 case PW_TYPE_ABINARY:
1105 #ifdef ASCEND_BINARY
1106 if (strncasecmp(value, "0x", 2) == 0) {
1107 vp->type = PW_TYPE_OCTETS;
1111 if (ascend_parse_filter(vp) < 0 ) {
1114 snprintf(buffer, sizeof(buffer), "failed to parse Ascend binary attribute: %s", fr_strerror());
1115 fr_strerror_printf("%s", buffer);
1121 * If Ascend binary is NOT defined,
1122 * then fall through to raw octets, so that
1123 * the user can at least make them by hand...
1127 /* raw octets: 0x01020304... */
1128 case PW_TYPE_OCTETS:
1129 if (strncasecmp(value, "0x", 2) == 0) {
1141 if ((size & 0x01) != 0) {
1142 fr_strerror_printf("Hex string is not an even length string.");
1146 vp->length = size >> 1;
1147 if (size > 2*sizeof(vp->vp_octets)) {
1148 vp->type |= PW_FLAG_LONG;
1149 us = vp->vp_tlv = malloc(vp->length);
1151 fr_strerror_printf("Out of memory.");
1156 if (fr_hex2bin(cp, us,
1157 vp->length) != vp->length) {
1158 fr_strerror_printf("Invalid hex data");
1165 if (ifid_aton(value, (void *) &vp->vp_ifid) == NULL) {
1166 fr_strerror_printf("failed to parse interface-id "
1167 "string \"%s\"", value);
1173 case PW_TYPE_IPV6ADDR:
1177 if (ip_hton(value, AF_INET6, &ipaddr) < 0) {
1180 strlcpy(buffer, fr_strerror(), sizeof(buffer));
1182 fr_strerror_printf("failed to parse IPv6 address "
1183 "string \"%s\": %s", value, buffer);
1186 vp->vp_ipv6addr = ipaddr.ipaddr.ip6addr;
1187 vp->length = 16; /* length of IPv6 address */
1191 case PW_TYPE_IPV6PREFIX:
1192 p = strchr(value, '/');
1193 if (!p || ((p - value) >= 256)) {
1194 fr_strerror_printf("invalid IPv6 prefix "
1195 "string \"%s\"", value);
1198 unsigned int prefix;
1199 char buffer[256], *eptr;
1201 memcpy(buffer, value, p - value);
1202 buffer[p - value] = '\0';
1204 if (inet_pton(AF_INET6, buffer, vp->vp_octets + 2) <= 0) {
1205 fr_strerror_printf("failed to parse IPv6 address "
1206 "string \"%s\"", value);
1210 prefix = strtoul(p + 1, &eptr, 10);
1211 if ((prefix > 128) || *eptr) {
1212 fr_strerror_printf("failed to parse IPv6 address "
1213 "string \"%s\"", value);
1216 vp->vp_octets[1] = prefix;
1218 vp->vp_octets[0] = '\0';
1219 vp->length = 16 + 2;
1222 case PW_TYPE_ETHERNET:
1224 const char *c1, *c2;
1231 c2 = memchr(hextab, tolower((int) cp[0]), 16);
1233 } else if ((cp[1] != '\0') &&
1236 c1 = memchr(hextab, tolower((int) cp[0]), 16);
1237 c2 = memchr(hextab, tolower((int) cp[1]), 16);
1239 if (*cp == ':') cp++;
1243 if (!c1 || !c2 || (length >= sizeof(vp->vp_ether))) {
1244 fr_strerror_printf("failed to parse Ethernet address \"%s\"", value);
1247 vp->vp_ether[length] = ((c1-hextab)<<4) + (c2-hextab);
1254 case PW_TYPE_COMBO_IP:
1255 if (inet_pton(AF_INET6, value, vp->vp_strvalue) > 0) {
1256 vp->type = PW_TYPE_IPV6ADDR;
1257 vp->length = 16; /* length of IPv6 address */
1258 vp->vp_strvalue[vp->length] = '\0';
1263 if (ip_hton(value, AF_INET, &ipaddr) < 0) {
1264 fr_strerror_printf("Failed to find IPv4 address for %s", value);
1268 vp->type = PW_TYPE_IPADDR;
1269 vp->vp_ipaddr = ipaddr.ipaddr.ip4addr.s_addr;
1274 case PW_TYPE_SIGNED: /* Damned code for 1 WiMAX attribute */
1275 vp->vp_signed = (int32_t) strtol(value, &p, 10);
1279 case PW_TYPE_TLV: /* don't use this! */
1280 if (strncasecmp(value, "0x", 2) != 0) {
1281 fr_strerror_printf("Invalid TLV specification");
1284 length = strlen(value + 2) / 2;
1285 if (vp->length < length) {
1289 vp->vp_tlv = malloc(length);
1291 fr_strerror_printf("No memory");
1294 if (fr_hex2bin(value + 2, vp->vp_tlv,
1295 length) != length) {
1296 fr_strerror_printf("Invalid hex data in TLV");
1299 vp->length = length;
1306 fr_strerror_printf("unknown attribute type %d", vp->type);
1314 * Create a VALUE_PAIR from an ASCII attribute and value,
1315 * where the attribute name is in the form:
1320 * VendorName-Attr-%d
1323 static VALUE_PAIR *pairmake_any(const char *attribute, const char *value,
1326 unsigned int attr, vendor;
1327 unsigned int dv_type = 1;
1329 const char *p = attribute;
1336 * Unknown attributes MUST be of type 'octets'
1338 if (value && (strncasecmp(value, "0x", 2) != 0)) {
1339 fr_strerror_printf("Unknown attribute \"%s\" requires a hex string, not \"%s\"", attribute, value);
1346 * Pull off vendor prefix first.
1348 if (strncasecmp(p, "Attr-", 5) != 0) {
1349 if (strncasecmp(p, "Vendor-", 7) == 0) {
1350 vendor = (int) strtol(p + 7, &q, 10);
1351 if ((vendor == 0) || (vendor > FR_MAX_VENDOR)) {
1352 fr_strerror_printf("Invalid vendor value in attribute name \"%s\"", attribute);
1358 } else { /* must be vendor name */
1364 fr_strerror_printf("Invalid vendor name in attribute name \"%s\"", attribute);
1368 if ((size_t) (q - p) >= sizeof(buffer)) {
1369 fr_strerror_printf("Vendor name too long in attribute name \"%s\"", attribute);
1373 memcpy(buffer, p, (q - p));
1374 buffer[q - p] = '\0';
1376 vendor = dict_vendorbyname(buffer);
1378 fr_strerror_printf("Unknown vendor name in attribute name \"%s\"", attribute);
1386 fr_strerror_printf("Invalid text following vendor definition in attribute name \"%s\"", attribute);
1395 if (strncasecmp(p, "Attr-", 5) != 0) {
1396 fr_strerror_printf("Invalid format in attribute name \"%s\"", attribute);
1400 attr = strtol(p + 5, &q, 10);
1403 * Invalid attribute.
1406 fr_strerror_printf("Invalid value in attribute name \"%s\"", attribute);
1414 * VendorName-Attr-%d
1418 * Anything else is invalid.
1420 if (((vendor != 0) && (*p != '\0')) ||
1421 ((vendor == 0) && *p && (*p != '.'))) {
1423 fr_strerror_printf("Invalid OID");
1428 * Look for OIDs. Require the "Attr-26.Vendor-Id.type"
1429 * format, and disallow "Vendor-%d-Attr-%d" and
1430 * "VendorName-Attr-%d"
1432 * This section parses the Vendor-Id portion of
1433 * Attr-%d.%d. where the first number is 26, *or* an
1434 * extended attribute of the "evs" data type.
1439 da = dict_attrbyvalue(attr, 0);
1441 fr_strerror_printf("Cannot parse attributes without dictionaries");
1445 if ((attr != PW_VENDOR_SPECIFIC) &&
1446 !(da->flags.extended || da->flags.extended_flags)) {
1447 fr_strerror_printf("Standard attributes cannot use OIDs");
1451 if ((attr == PW_VENDOR_SPECIFIC) || da->flags.evs) {
1452 vendor = strtol(p + 1, &q, 10);
1453 if ((vendor == 0) || (vendor > FR_MAX_VENDOR)) {
1454 fr_strerror_printf("Invalid vendor");
1458 if (*q != '.') goto invalid;
1462 if (da->flags.evs) {
1463 vendor |= attr * FR_MAX_VENDOR;
1466 } /* else the second number is a TLV number */
1470 * Get the expected maximum size of the attribute.
1473 dv = dict_vendorbyvalue(vendor & (FR_MAX_VENDOR - 1));
1476 if (dv_type > 3) dv_type = 3; /* hack */
1481 * Parse the next number. It could be a Vendor-Type
1482 * of 1..2^24, or it could be a TLV.
1485 attr = strtol(p + 1, &q, 10);
1487 fr_strerror_printf("Invalid attribute number");
1492 if (*q != '.') goto invalid;
1493 if (dv_type != 1) goto invalid;
1500 * Enforce a maximum value on the attribute number.
1502 if (attr >= (unsigned) (1 << (dv_type << 3))) goto invalid;
1505 if (!dict_str2oid(p + 1, &attr, vendor, 1)) {
1511 * We've now parsed the attribute properly, Let's create
1512 * it. This next stop also looks the attribute up in the
1513 * dictionary, and creates the appropriate type for it.
1515 if ((vp = paircreate(attr, vendor, PW_TYPE_OCTETS)) == NULL) {
1516 fr_strerror_printf("out of memory");
1520 vp->operator = (operator == 0) ? T_OP_EQ : operator;
1521 if (!value) return vp;
1523 size = strlen(value + 2);
1524 data = vp->vp_octets;
1527 * We may be reading something like Attr-5. i.e.
1528 * who-ever wrote the text didn't understand it, but we
1533 if (size == (vp->length * 2)) break;
1534 vp->type = PW_TYPE_OCTETS;
1537 case PW_TYPE_OCTETS:
1538 case PW_TYPE_ABINARY:
1539 vp->length = size >> 1;
1540 if (vp->length > sizeof(vp->vp_octets)) {
1541 vp->vp_tlv = malloc(vp->length);
1543 fr_strerror_printf("Out of memory");
1548 vp->type |= PW_FLAG_LONG;
1552 case PW_TYPE_STRING:
1553 vp->length = size >> 1;
1554 memset(&vp->vp_strvalue, 0, sizeof(vp->vp_strvalue));
1555 if (vp->length >= sizeof(vp->vp_strvalue)) {
1556 vp->vp_tlv = malloc(vp->length);
1558 fr_strerror_printf("Out of memory");
1563 vp->type |= PW_FLAG_LONG;
1568 if (fr_hex2bin(value + 2, data, size) != vp->length) {
1569 fr_strerror_printf("Invalid hex string");
1575 * Move contents around based on type. This is
1576 * to work around the historical use of "lvalue".
1580 case PW_TYPE_IPADDR:
1581 case PW_TYPE_INTEGER:
1582 memcpy(&vp->lvalue, vp->vp_octets, sizeof(vp->lvalue));
1583 vp->vp_strvalue[0] = '\0';
1595 * Create a VALUE_PAIR from an ASCII attribute and value.
1597 VALUE_PAIR *pairmake(const char *attribute, const char *value, int operator)
1605 const char *attrname = attribute;
1608 * Check for tags in 'Attribute:Tag' format.
1613 ts = strrchr(attribute, ':');
1615 fr_strerror_printf("Invalid tag for attribute %s", attribute);
1620 strlcpy(buffer, attribute, sizeof(buffer));
1622 ts = strrchr(attrname, ':');
1624 /* Colon found with something behind it */
1625 if (ts[1] == '*' && ts[2] == 0) {
1626 /* Wildcard tag for check items */
1629 } else if ((ts[1] >= '0') && (ts[1] <= '9')) {
1630 /* It's not a wild card tag */
1631 tag = strtol(ts + 1, &tc, 0);
1632 if (tc && !*tc && TAG_VALID_ZERO(tag))
1636 fr_strerror_printf("Invalid tag for attribute %s", attribute);
1643 * It's not found in the dictionary, so we use
1644 * another method to create the attribute.
1646 if ((da = dict_attrbyname(attrname)) == NULL) {
1647 return pairmake_any(attrname, value, operator);
1650 if ((vp = pairalloc(da)) == NULL) {
1654 vp->operator = (operator == 0) ? T_OP_EQ : operator;
1656 /* Check for a tag in the 'Merit' format of:
1657 * :Tag:Value. Print an error if we already found
1658 * a tag in the Attribute.
1661 if (value && (*value == ':' && da->flags.has_tag)) {
1662 /* If we already found a tag, this is invalid */
1664 fr_strerror_printf("Duplicate tag %s for attribute %s",
1666 DEBUG("Duplicate tag %s for attribute %s\n",
1671 /* Colon found and attribute allows a tag */
1672 if (value[1] == '*' && value[2] == ':') {
1673 /* Wildcard tag for check items */
1678 tag = strtol(value + 1, &tc, 0);
1679 if (tc && *tc==':' && TAG_VALID_ZERO(tag))
1687 vp->flags.tag = tag;
1690 switch (vp->operator) {
1695 * For =* and !* operators, the value is irrelevant
1699 case T_OP_CMP_FALSE:
1700 vp->vp_strvalue[0] = '\0';
1706 * Regular expression comparison of integer attributes
1707 * does a STRING comparison of the names of their
1708 * integer attributes.
1710 case T_OP_REG_EQ: /* =~ */
1711 case T_OP_REG_NE: /* !~ */
1713 fr_strerror_printf("No regular expression found in %s",
1719 strlcpy(vp->vp_strvalue, value, sizeof(vp->vp_strvalue));
1720 vp->length = strlen(vp->vp_strvalue);
1722 * If anything goes wrong, this is a run-time error,
1723 * not a compile-time error.
1730 * FIXME: if (strcasecmp(attribute, vp->name) != 0)
1731 * then the user MAY have typed in the attribute name
1732 * as Vendor-%d-Attr-%d, and the value MAY be octets.
1734 * We probably want to fix pairparsevalue to accept
1735 * octets as values for any attribute.
1737 if (value && (pairparsevalue(vp, value) == NULL)) {
1749 static const int valid_attr_name[256] = {
1750 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1751 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1752 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0,
1753 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0,
1754 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1755 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 1,
1756 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
1757 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 0, 0, 0, 0,
1758 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1759 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1760 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1761 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1762 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1763 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1764 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
1765 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
1769 * Read a valuepair from a buffer, and advance pointer.
1770 * Sets *eol to T_EOL if end of line was encountered.
1772 VALUE_PAIR *pairread(const char **ptr, FR_TOKEN *eol)
1776 char value[1024], *q;
1778 FR_TOKEN token, t, xlat;
1782 *eol = T_OP_INVALID;
1785 while ((*p == ' ') || (*p == '\t')) p++;
1788 *eol = T_OP_INVALID;
1789 fr_strerror_printf("No token read where we expected an attribute name");
1795 fr_strerror_printf("Read a comment instead of a token");
1800 for (len = 0; len < sizeof(attr); len++) {
1801 if (valid_attr_name[(int)*p]) {
1808 if (len == sizeof(attr)) {
1809 *eol = T_OP_INVALID;
1810 fr_strerror_printf("Attribute name is too long");
1815 * We may have Foo-Bar:= stuff, so back up.
1817 if ((len > 0) && (attr[len - 1] == ':')) {
1825 /* Now we should have an operator here. */
1826 token = gettoken(ptr, buf, sizeof(buf));
1827 if (token < T_EQSTART || token > T_EQEND) {
1828 fr_strerror_printf("expecting operator");
1832 /* Read value. Note that empty string values are allowed */
1833 xlat = gettoken(ptr, value, sizeof(value));
1834 if (xlat == T_EOL) {
1835 fr_strerror_printf("failed to get value");
1840 * Peek at the next token. Must be T_EOL, T_COMMA, or T_HASH
1843 t = gettoken(&p, buf, sizeof(buf));
1844 if (t != T_EOL && t != T_COMMA && t != T_HASH) {
1845 fr_strerror_printf("Expected end of line or comma");
1857 * Make the full pair now.
1860 vp = pairmake(attr, value, token);
1866 case T_DOUBLE_QUOTED_STRING:
1867 p = strchr(value, '%');
1868 if (p && (p[1] == '{')) {
1869 if (strlen(value) >= sizeof(vp->vp_strvalue)) {
1870 fr_strerror_printf("Value too long");
1873 vp = pairmake(attr, NULL, token);
1875 *eol = T_OP_INVALID;
1879 strlcpy(vp->vp_strvalue, value, sizeof(vp->vp_strvalue));
1880 vp->flags.do_xlat = 1;
1884 * Parse && escape it, as defined by the
1887 vp = pairmake(attr, value, token);
1889 *eol = T_OP_INVALID;
1895 case T_SINGLE_QUOTED_STRING:
1896 vp = pairmake(attr, NULL, token);
1898 *eol = T_OP_INVALID;
1903 * String and octet types get copied verbatim.
1905 if ((vp->type == PW_TYPE_STRING) ||
1906 (vp->type == PW_TYPE_OCTETS)) {
1907 strlcpy(vp->vp_strvalue, value,
1908 sizeof(vp->vp_strvalue));
1909 vp->length = strlen(vp->vp_strvalue);
1912 * Everything else gets parsed: it's
1913 * DATA, not a string!
1915 } else if (!pairparsevalue(vp, value)) {
1917 *eol = T_OP_INVALID;
1923 * Mark the pair to be allocated later.
1925 case T_BACK_QUOTED_STRING:
1926 if (strlen(value) >= sizeof(vp->vp_strvalue)) {
1927 fr_strerror_printf("Value too long");
1931 vp = pairmake(attr, NULL, token);
1933 *eol = T_OP_INVALID;
1937 vp->flags.do_xlat = 1;
1938 strlcpy(vp->vp_strvalue, value, sizeof(vp->vp_strvalue));
1944 * If we didn't make a pair, return an error.
1947 *eol = T_OP_INVALID;
1955 * Read one line of attribute/value pairs. This might contain
1956 * multiple pairs seperated by comma's.
1958 FR_TOKEN userparse(const char *buffer, VALUE_PAIR **first_pair)
1962 FR_TOKEN last_token = T_OP_INVALID;
1963 FR_TOKEN previous_token;
1966 * We allow an empty line.
1973 previous_token = last_token;
1974 if ((vp = pairread(&p, &last_token)) == NULL) {
1977 pairadd(first_pair, vp);
1978 } while (*p && (last_token == T_COMMA));
1981 * Don't tell the caller that there was a comment.
1983 if (last_token == T_HASH) {
1984 return previous_token;
1988 * And return the last token which we read.
1994 * Read valuepairs from the fp up to End-Of-File.
1996 * Hmm... this function is only used by radclient..
1998 VALUE_PAIR *readvp2(FILE *fp, int *pfiledone, const char *errprefix)
2001 FR_TOKEN last_token = T_EOL;
2008 while (!error && fgets(buf, sizeof(buf), fp) != NULL) {
2010 * If we get a '\n' by itself, we assume that's
2011 * the end of that VP
2013 if ((buf[0] == '\n') && (list)) {
2016 if ((buf[0] == '\n') && (!list)) {
2021 * Comments get ignored
2023 if (buf[0] == '#') continue;
2026 * Read all of the attributes on the current line.
2029 last_token = userparse(buf, &vp);
2031 if (last_token != T_EOL) {
2032 fr_perror("%s", errprefix);
2043 if (error) pairfree(&list);
2047 return error ? NULL: list;
2053 * Compare two pairs, using the operator from "one".
2055 * i.e. given two attributes, it does:
2057 * (two->data) (one->operator) (one->data)
2059 * e.g. "foo" != "bar"
2061 * Returns true (comparison is true), or false (comparison is not true);
2063 * FIXME: Ignores tags!
2065 int paircmp(VALUE_PAIR *one, VALUE_PAIR *two)
2069 switch (one->operator) {
2071 return (two != NULL);
2073 case T_OP_CMP_FALSE:
2074 return (two == NULL);
2077 * One is a regex, compile it, print two to a string,
2078 * and then do string comparisons.
2082 #ifndef HAVE_REGEX_H
2087 char buffer[MAX_STRING_LEN * 4 + 1];
2089 compare = regcomp(®, one->vp_strvalue,
2092 regerror(compare, ®, buffer, sizeof(buffer));
2093 fr_strerror_printf("Illegal regular expression in attribute: %s: %s",
2098 vp_prints_value(buffer, sizeof(buffer), two, 0);
2101 * Don't care about substring matches,
2104 compare = regexec(®, buffer, 0, NULL, 0);
2107 if (one->operator == T_OP_REG_EQ) return (compare == 0);
2108 return (compare != 0);
2112 default: /* we're OK */
2117 * After doing the previous check for special comparisons,
2118 * do the per-type comparison here.
2120 switch (one->type) {
2121 case PW_TYPE_ABINARY:
2122 case PW_TYPE_OCTETS:
2126 if (one->length < two->length) {
2127 length = one->length;
2129 length = two->length;
2133 compare = memcmp(two->vp_octets, one->vp_octets,
2135 if (compare != 0) break;
2139 * Contents are the same. The return code
2140 * is therefore the difference in lengths.
2142 * i.e. "0x00" is smaller than "0x0000"
2144 compare = two->length - one->length;
2148 case PW_TYPE_STRING:
2149 compare = strcmp(two->vp_strvalue, one->vp_strvalue);
2154 case PW_TYPE_INTEGER:
2156 compare = two->vp_integer - one->vp_integer;
2159 case PW_TYPE_INTEGER64:
2161 * Don't want integer overflow!
2163 if (two->vp_integer64 < one->vp_integer64) {
2165 } else if (two->vp_integer64 > one->vp_integer64) {
2171 case PW_TYPE_IPADDR:
2172 compare = ntohl(two->vp_ipaddr) - ntohl(one->vp_ipaddr);
2175 case PW_TYPE_IPV6ADDR:
2176 compare = memcmp(&two->vp_ipv6addr, &one->vp_ipv6addr,
2177 sizeof(two->vp_ipv6addr));
2180 case PW_TYPE_IPV6PREFIX:
2181 compare = memcmp(&two->vp_ipv6prefix, &one->vp_ipv6prefix,
2182 sizeof(two->vp_ipv6prefix));
2186 compare = memcmp(&two->vp_ifid, &one->vp_ifid,
2187 sizeof(two->vp_ifid));
2191 return 0; /* unknown type */
2195 * Now do the operator comparison.
2197 switch (one->operator) {
2199 return (compare == 0);
2202 return (compare != 0);
2205 return (compare < 0);
2208 return (compare > 0);
2211 return (compare <= 0);
2214 return (compare >= 0);