Unverified Commit e0c4a3ea authored by Mouse's avatar Mouse Committed by GitHub

Merge pull request #177 from v0-e/integer-2-int64

INTEGER to 64-bit native integer methods
parents ce10a57a 665a2278
......@@ -414,6 +414,33 @@ asn_ulong2INTEGER(INTEGER_t *st, unsigned long value) {
return asn_imax2INTEGER(st, value);
}
int asn_INTEGER2int64(const INTEGER_t *st, int64_t *value) {
intmax_t v;
if(asn_INTEGER2imax(st, &v) == 0) {
if(v < INT64_MIN || v > INT64_MAX) {
errno = ERANGE;
return -1;
}
*value = v;
return 0;
} else {
return -1;
}
}
int asn_INTEGER2uint64(const INTEGER_t *st, uint64_t *value) {
uintmax_t v;
if(asn_INTEGER2umax(st, &v) == 0) {
if(v > UINT64_MAX) {
errno = ERANGE;
return -1;
}
*value = v;
return 0;
} else {
return -1;
}
}
int
asn_uint642INTEGER(INTEGER_t *st, uint64_t value) {
......
......@@ -108,6 +108,8 @@ int asn_INTEGER2long(const INTEGER_t *i, long *l);
int asn_INTEGER2ulong(const INTEGER_t *i, unsigned long *l);
int asn_long2INTEGER(INTEGER_t *i, long l);
int asn_ulong2INTEGER(INTEGER_t *i, unsigned long l);
int asn_INTEGER2int64(const INTEGER_t *i, int64_t *l);
int asn_INTEGER2uint64(const INTEGER_t *i, uint64_t *l);
int asn_int642INTEGER(INTEGER_t *i, int64_t l);
int asn_uint642INTEGER(INTEGER_t *i, uint64_t l);
......
......@@ -147,6 +147,136 @@ check_unsigned(uint8_t *buf, int size, unsigned long check_long, int check_ret)
}
}
static void
check_64(uint8_t *buf, size_t size, int64_t check_i64, int check_ret) {
char scratch[128];
char verify[32];
INTEGER_t val;
uint8_t *buf_end = buf + size;
int ret;
int64_t rint64 = 123;
assert(buf);
assert(size > 0);
val.buf = buf;
val.size = size;
printf("Testing: [");
for(; buf < buf_end; buf++) {
if(buf != val.buf) printf(":");
printf("%02x", *buf);
}
printf("]: ");
ret = asn_INTEGER2int64(&val, &rint64);
printf(" (%ld, %d) vs (%ld, %d)\n",
rint64, ret, check_i64, check_ret);
assert(ret == check_ret);
printf("%ld %ld\n", rint64, check_i64);
assert(rint64 == check_i64);
if(check_ret == 0) {
INTEGER_t val2;
int64_t rint642;
val2.buf = 0;
val2.size = 0;
ret = asn_int642INTEGER(&val2, rint64);
assert(ret == 0);
assert(val2.buf);
assert(val2.size <= val.size); /* At least as compact */
ret = asn_INTEGER2int64(&val, &rint642);
assert(ret == 0);
assert(rint64 == rint642);
ASN_STRUCT_RESET(asn_DEF_INTEGER, &val2);
}
shared_scratch_start = scratch;
ret = INTEGER_print(&asn_DEF_INTEGER, &val, 0, _print2buf, scratch);
assert(shared_scratch_start < scratch + sizeof(scratch));
assert(ret == 0);
ret = snprintf(verify, sizeof(verify), "%ld", check_i64);
assert(ret < 0 || (size_t)ret < sizeof(verify));
ret = strcmp(scratch, verify);
printf(" [%s] vs [%s]: %d%s\n",
scratch, verify, ret,
(check_ret == -1)?" (expected to fail)":""
);
if(check_ret == -1) {
assert(strcmp(scratch, verify));
} else {
assert(strcmp(scratch, verify) == 0);
}
}
static void
check_unsigned_64(uint8_t *buf, int size, uint64_t check_u64, int check_ret) {
char scratch[128];
char verify[32];
INTEGER_t val;
uint8_t *buf_end = buf + size;
int ret;
uint64_t ruint64 = 123;
assert(buf);
assert(size >= 0);
val.buf = buf;
val.size = size;
printf("Testing: [");
for(; buf < buf_end; buf++) {
if(buf != val.buf) printf(":");
printf("%02x", *buf);
}
printf("]: ");
ret = asn_INTEGER2uint64(&val, &ruint64);
printf(" (%lu, %d) vs (%lu, %d)\n",
ruint64, ret, check_u64, check_ret);
assert(ret == check_ret);
assert(ruint64 == check_u64);
if(check_ret == 0) {
INTEGER_t val2;
uint64_t ruint642;
val2.buf = 0;
val2.size = 0;
ret = asn_uint642INTEGER(&val2, ruint64);
assert(ret == 0);
assert(val2.buf);
if(val2.size > val.size) {
/* At least as compact */
printf("val2.size=%d, val.size=%d\n",
(int)val2.size, (int)val.size);
assert(val2.size <= val.size);
}
ret = asn_INTEGER2uint64(&val, &ruint642);
assert(ret == 0);
assert(ruint64 == ruint642);
ASN_STRUCT_RESET(asn_DEF_INTEGER, &val2);
}
return;
shared_scratch_start = scratch;
ret = INTEGER_print(&asn_DEF_INTEGER, &val, 0, _print2buf, scratch);
assert(shared_scratch_start < scratch + sizeof(scratch));
assert(ret == 0);
ret = snprintf(verify, sizeof(verify), "%lu", check_u64);
assert(ret < (int)sizeof(verify));
ret = strcmp(scratch, verify);
printf(" [%s] vs [%s]: %d%s\n",
scratch, verify, ret,
(check_ret == -1)?" (expected to fail)":""
);
if(check_ret == -1) {
assert(strcmp(scratch, verify));
} else {
assert(strcmp(scratch, verify) == 0);
}
}
static void
check_xer(int lineno, int tofail, char *xmldata, long orig_value) {
INTEGER_t *st = 0;
......@@ -353,10 +483,15 @@ main() {
uint8_t buf14[] = { 0x00, 0x80, 0x00, 0x00 };
uint8_t buf15[] = { 0x00, 0x80, 0x00, 0x00, 0x00 };
uint8_t buf16[] = { 0x00, 0xff, 0xff, 0x00, 0x00 };
uint8_t buf17[] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
uint8_t buf18[] = { 0x00, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
uint8_t buf19[] = { 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
uint8_t buf20[] = { 0x00, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff };
#define UCHECK(buf, val, ret) check_unsigned(buf, sizeof(buf), val, ret)
#define CHECK(buf, val, ret) check(buf, sizeof(buf), val, ret)
#define UCHECK64(buf, val, ret) check_unsigned_64(buf, sizeof(buf), val, ret)
#define CHECK64(buf, val, ret) check_64(buf, sizeof(buf), val, ret)
CHECK(buf1, 1, 0);
CHECK(buf2, -1, 0);
......@@ -376,6 +511,28 @@ main() {
UCHECK(buf15, 0x80000000UL, 0);
UCHECK(buf16, 0xffff0000UL, 0);
CHECK64(buf1, 1, 0);
CHECK64(buf2, -1, 0);
CHECK64(buf3, -1, 0);
CHECK64(buf4, -16, 0);
CHECK64(buf5, 257, 0);
CHECK64(buf6, 123, -1);
CHECK64(buf7, 123, -1);
CHECK64(buf8, 0x7F7E7D7C, 0);
CHECK64(buf9, 0x7F7E7D7C, 0);
CHECK64(buf10, 0x7F7E7D7C, 0);
UCHECK64(buf10, 0x7F7E7D7C, 0);
CHECK64(buf11, -2147483647-1, 0); /* 0x80000000 */
CHECK64(buf12, -32768, 0);
CHECK64(buf13, -128, 0);
UCHECK64(buf14, 0x800000, 0);
UCHECK64(buf15, 0x80000000UL, 0);
UCHECK64(buf16, 0xffff0000UL, 0);
CHECK64(buf17, 0xffffffffffffffffLL, 0);
UCHECK64(buf18, 0xffffffffffffffffULL, 0);
CHECK64(buf19, 0x7fffffffffffffffLL, 0);
UCHECK64(buf20, 0x7fffffffffffffffULL, 0);
CHECK_XER(-1, "", 0);
CHECK_XER(-1, "<INTEGER></INTEGER>", 0);
CHECK_XER(-1, "<INTEGER> </INTEGER>", 0);
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment