size -= n;
}
}
+
+bool
+str_to_int(const char *s, int base, int *i)
+{
+ long long ll;
+ bool ok = str_to_llong(s, base, &ll);
+ *i = ll;
+ return ok;
+}
+
+bool
+str_to_long(const char *s, int base, long *li)
+{
+ long long ll;
+ bool ok = str_to_llong(s, base, &ll);
+ *li = ll;
+ return ok;
+}
+
+bool
+str_to_llong(const char *s, int base, long long *x)
+{
+ int save_errno = errno;
+ char *tail;
+ errno = 0;
+ *x = strtoll(s, &tail, base);
+ if (errno == EINVAL || errno == ERANGE || tail == s || *tail != '\0') {
+ errno = save_errno;
+ *x = 0;
+ return false;
+ } else {
+ errno = save_errno;
+ return true;
+ }
+}
+
+bool
+str_to_uint(const char *s, int base, unsigned int *u)
+{
+ return str_to_int(s, base, (int *) u);
+}
+
+bool str_to_ulong(const char *s, int base, unsigned long *ul)
+{
+ return str_to_long(s, base, (long *) ul);
+}
+
+bool str_to_ullong(const char *s, int base, unsigned long long *ull)
+{
+ return str_to_llong(s, base, (long long *) ull);
+}
void ofp_error(int err_no, const char *format, ...) PRINTF_FORMAT(2, 3);
void ofp_hex_dump(FILE *, const void *, size_t, uintptr_t offset, bool ascii);
+bool str_to_int(const char *, int base, int *);
+bool str_to_long(const char *, int base, long *);
+bool str_to_llong(const char *, int base, long long *);
+bool str_to_uint(const char *, int base, unsigned int *);
+bool str_to_ulong(const char *, int base, unsigned long *);
+bool str_to_ullong(const char *, int base, unsigned long long *);
+
#ifdef __cplusplus
}
#endif
static uint32_t
-str_to_int(const char *str)
+str_to_u32(const char *str)
{
char *tail;
uint32_t value;
act_len = sizeof *va;
va->type = htons(OFPAT_SET_VLAN_VID);
- va->vlan_vid = htons(str_to_int(arg));
+ va->vlan_vid = htons(str_to_u32(arg));
} else if (!strcasecmp(act, "mod_vlan_pcp")) {
struct ofp_action_vlan_pcp *va = (struct ofp_action_vlan_pcp *)ah;
act_len = sizeof *va;
va->type = htons(OFPAT_SET_VLAN_PCP);
- va->vlan_pcp = str_to_int(arg);
+ va->vlan_pcp = str_to_u32(arg);
} else if (!strcasecmp(act, "strip_vlan")) {
ah->type = htons(OFPAT_STRIP_VLAN);
} else if (!strcasecmp(act, "output")) {
- port = str_to_int(arg);
+ port = str_to_u32(arg);
#ifdef SUPPORT_SNAT
} else if (!strcasecmp(act, "nat")) {
struct nx_action_snat *sa = (struct nx_action_snat *)ah;
ofp_fatal(0, "Insufficient room for SNAT action\n");
}
- if (str_to_int(arg) > OFPP_MAX) {
+ if (str_to_u32(arg) > OFPP_MAX) {
ofp_fatal(0, "Invalid nat port: %s\n", arg);
}
sa->type = htons(OFPAT_VENDOR);
sa->vendor = htonl(NX_VENDOR_ID);
sa->subtype = htons(NXAST_SNAT);
- sa->port = htons(str_to_int(arg));
+ sa->port = htons(str_to_u32(arg));
#endif
} else if (!strcasecmp(act, "TABLE")) {
port = OFPP_TABLE;
/* Unless a numeric argument is specified, we send the whole
* packet to the controller. */
if (arg && (strspn(act, "0123456789") == strlen(act))) {
- ca->max_len= htons(str_to_int(arg));
+ ca->max_len= htons(str_to_u32(arg));
}
} else if (!strcasecmp(act, "LOCAL")) {
port = OFPP_LOCAL;
} else if (strspn(act, "0123456789") == strlen(act)) {
- port = str_to_int(act);
+ port = str_to_u32(act);
} else {
ofp_fatal(0, "Unknown action: %s", act);
}
} else {
wildcards &= ~f->wildcard;
if (f->type == F_U8) {
- *(uint8_t *) data = str_to_int(value);
+ *(uint8_t *) data = str_to_u32(value);
} else if (f->type == F_U16) {
- *(uint16_t *) data = htons(str_to_int(value));
+ *(uint16_t *) data = htons(str_to_u32(value));
} else if (f->type == F_MAC) {
str_to_mac(value, data);
} else if (f->type == F_IP) {
nac->type = htons(NXAST_SNAT);
nac->snat[0].command = NXSC_ADD;
- nac->snat[0].port = htons(str_to_int(argv[2]));
+ nac->snat[0].port = htons(str_to_u32(argv[2]));
nac->snat[0].mac_timeout = htons(0);
str_to_ip(argv[3], &nac->snat[0].ip_addr_start);
str_to_ip(argv[3], &nac->snat[0].ip_addr_end);
nac->type = htons(NXAST_SNAT);
nac->snat[0].command = NXSC_DELETE;
- nac->snat[0].port = htons(str_to_int(argv[2]));
+ nac->snat[0].port = htons(str_to_u32(argv[2]));
nac->snat[0].mac_timeout = htons(0);
open_vconn(argv[1], &vconn);