Changeset: 031e14da4e02 for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB/rev/031e14da4e02
Modified Files:
clients/Tests/MAL-signatures-hge.test
clients/Tests/MAL-signatures.test
gdk/gdk_atoms.c
gdk/gdk_calc_convert.c
monetdb5/modules/atoms/inet-46.c
Branch: default
Log Message:
Implemented conversion between inet4 and inet6 (both ways) in BATconvert.
diffs (truncated from 385 to 300 lines):
diff --git a/clients/Tests/MAL-signatures-hge.test
b/clients/Tests/MAL-signatures-hge.test
--- a/clients/Tests/MAL-signatures-hge.test
+++ b/clients/Tests/MAL-signatures-hge.test
@@ -29160,6 +29160,11 @@ INETinet42inet4_bulk
(empty)
batcalc
inet4
+command batcalc.inet4(X_0:bat[:inet6], X_1:bat[:oid]):bat[:inet4]
+INETinet62inet4_bulk
+Coerce an inet6 to an inet4
+batcalc
+inet4
command batcalc.inet4(X_0:bat[:str], X_1:bat[:oid]):bat[:inet4]
INETstr2inet4_bulk
Coerce a string to an inet4, validating its format
@@ -44150,6 +44155,11 @@ INETinet42inet4
(empty)
calc
inet4
+command calc.inet4(X_0:inet6):inet4
+INETinet62inet4
+Coerce an inet6 to an inet4
+calc
+inet4
command calc.inet4(X_0:str):inet4
INETstr2inet4
Coerce a string to an inet4, validating its format
diff --git a/clients/Tests/MAL-signatures.test
b/clients/Tests/MAL-signatures.test
--- a/clients/Tests/MAL-signatures.test
+++ b/clients/Tests/MAL-signatures.test
@@ -20585,6 +20585,11 @@ INETinet42inet4_bulk
(empty)
batcalc
inet4
+command batcalc.inet4(X_0:bat[:inet6], X_1:bat[:oid]):bat[:inet4]
+INETinet62inet4_bulk
+Coerce an inet6 to an inet4
+batcalc
+inet4
command batcalc.inet4(X_0:bat[:str], X_1:bat[:oid]):bat[:inet4]
INETstr2inet4_bulk
Coerce a string to an inet4, validating its format
@@ -32810,6 +32815,11 @@ INETinet42inet4
(empty)
calc
inet4
+command calc.inet4(X_0:inet6):inet4
+INETinet62inet4
+Coerce an inet6 to an inet4
+calc
+inet4
command calc.inet4(X_0:str):inet4
INETstr2inet4
Coerce a string to an inet4, validating its format
diff --git a/gdk/gdk_atoms.c b/gdk/gdk_atoms.c
--- a/gdk/gdk_atoms.c
+++ b/gdk/gdk_atoms.c
@@ -1674,19 +1674,19 @@ INET6toString(str *retval, size_t *len,
*len = 40;
}
/* find longest stretch of zeroes */
- int rl = 0;
- int rl1 = -1;
- int mrl = 0;
- int mrl1 = -1;
+ int rl = 0; /* length of current stretch of zeros */
+ int rl1 = -1; /* start of current stretch of zeros */
+ int mrl = 0; /* length of longest stretch of zeros */
+ int mrl1 = -1; /* start of longest stretch of zeros */
for (int i = 0; i < 8; i++) {
if (value->oct[i] == 0) {
if (rl++ == 0)
rl1 = i;
- } else if (rl > 1 && rl > mrl) {
- mrl = rl;
- mrl1 = rl1;
- rl = 0;
} else {
+ if (rl > 1 && rl > mrl) {
+ mrl = rl;
+ mrl1 = rl1;
+ }
rl = 0;
}
}
@@ -1698,6 +1698,7 @@ INET6toString(str *retval, size_t *len,
mrl1 = 8;
int pos = 0;
if (mrl1 == 0 && mrl == 5 && value->oct[5] == 0xFFFF) {
+ /* IPv4 address disguised as IPv6 */
pos += snprintf(*retval + pos, *len - pos,
"::%x:%d.%d.%d.%d",
value->oct[5], value->oct[6] >> 8,
diff --git a/gdk/gdk_calc_convert.c b/gdk/gdk_calc_convert.c
--- a/gdk/gdk_calc_convert.c
+++ b/gdk/gdk_calc_convert.c
@@ -978,6 +978,120 @@ convert_void_any(oid seq, BAT *bn,
}
static BUN
+convert_inet6_inet4(const inet6 *src, inet4 *restrict dst,
+ struct canditer *restrict ci,
+ oid candoff)
+{
+ BUN i, nils = 0;
+ oid x;
+ QryCtx *qry_ctx = MT_thread_get_qry_ctx();
+
+ if (ci->tpe == cand_dense) {
+ TIMEOUT_LOOP_IDX(i, ci->ncand, qry_ctx) {
+ x = canditer_next_dense(ci) - candoff;
+ if (is_inet6_nil(src[x])) {
+ dst[i] = inet4_nil;
+ nils++;
+ } else if (src[x].oct[0] == 0 &&
+ src[x].oct[1] == 0 &&
+ src[x].oct[2] == 0 &&
+ src[x].oct[3] == 0 &&
+ src[x].oct[4] == 0 &&
+ src[x].oct[5] == 0xFFFF &&
+ (src[x].oct[6] != 0 || src[x].oct[7] != 0)) {
+ dst[i] = (inet4) {
+ .quad[0] = src[x].oct[6] >> 8,
+ .quad[1] = src[x].oct[6] & 0xFF,
+ .quad[2] = src[x].oct[7] >> 8,
+ .quad[3] = src[x].oct[7] & 0xFF,
+ };
+ } else {
+ char buf[40], *s = buf;
+ size_t l = sizeof(buf);
+ BATatoms[TYPE_inet6].atomToStr(&s, &l, &src[x],
false);
+ assert(buf == s);
+ GDKerror("22003!overflow in conversion of %s to
inet4.\n", buf);
+ return BUN_NONE;
+ }
+ }
+ TIMEOUT_CHECK(qry_ctx, TIMEOUT_HANDLER(BUN_NONE, qry_ctx));
+ } else {
+ TIMEOUT_LOOP_IDX(i, ci->ncand, qry_ctx) {
+ x = canditer_next(ci) - candoff;
+ if (is_inet6_nil(src[x])) {
+ dst[i] = inet4_nil;
+ nils++;
+ } else if (src[x].oct[0] == 0 &&
+ src[x].oct[1] == 0 &&
+ src[x].oct[2] == 0 &&
+ src[x].oct[3] == 0 &&
+ src[x].oct[4] == 0 &&
+ src[x].oct[5] == 0xFFFF &&
+ (src[x].oct[6] != 0 || src[x].oct[7] != 0)) {
+ dst[i] = (inet4) {
+ .quad[0] = src[x].oct[6] >> 8,
+ .quad[1] = src[x].oct[6] & 0xFF,
+ .quad[2] = src[x].oct[7] >> 8,
+ .quad[3] = src[x].oct[7] & 0xFF,
+ };
+ } else {
+ char buf[40], *s = buf;
+ size_t l = sizeof(buf);
+ BATatoms[TYPE_inet6].atomToStr(&s, &l, &src[x],
false);
+ assert(buf == s);
+ GDKerror("22003!overflow in conversion of %s to
inet4.\n", buf);
+ return BUN_NONE;
+ }
+ }
+ TIMEOUT_CHECK(qry_ctx, TIMEOUT_HANDLER(BUN_NONE, qry_ctx));
+ }
+ return nils;
+}
+
+static BUN
+convert_inet4_inet6(const inet4 *src, inet6 *restrict dst,
+ struct canditer *restrict ci,
+ oid candoff)
+{
+ BUN i, nils = 0;
+ oid x;
+ QryCtx *qry_ctx = MT_thread_get_qry_ctx();
+
+ if (ci->tpe == cand_dense) {
+ TIMEOUT_LOOP_IDX(i, ci->ncand, qry_ctx) {
+ x = canditer_next_dense(ci) - candoff;
+ if (is_inet4_nil(src[x])) {
+ dst[i] = inet6_nil;
+ nils++;
+ } else {
+ dst[i] = (inet6) {
+ .oct[5] = 0xffff,
+ .oct[6] = (src[x].quad[0] << 8) |
src[x].quad[1],
+ .oct[7] = (src[x].quad[2] << 8) |
src[x].quad[3],
+ };
+ }
+ }
+ TIMEOUT_CHECK(qry_ctx, TIMEOUT_HANDLER(BUN_NONE, qry_ctx));
+ } else {
+ TIMEOUT_LOOP_IDX(i, ci->ncand, qry_ctx) {
+ x = canditer_next(ci) - candoff;
+ if (is_inet4_nil(src[x])) {
+ dst[i] = inet6_nil;
+ nils++;
+ } else {
+ dst[i] = (inet6) {
+ .oct[5] = 0xffff,
+ .oct[6] = (src[x].quad[0] << 8) |
src[x].quad[1],
+ .oct[7] = (src[x].quad[2] << 8) |
src[x].quad[3],
+ };
+ }
+ }
+ TIMEOUT_CHECK(qry_ctx, TIMEOUT_HANDLER(BUN_NONE, qry_ctx));
+ }
+ return nils;
+}
+
+static BUN
convert_typeswitchloop(const void *src, int stp, void *restrict dst, int dtp,
struct canditer *restrict ci,
oid candoff, bool *reduce,
@@ -1406,6 +1520,22 @@ convert_typeswitchloop(const void *src,
default:
return BUN_NONE + 1;
}
+ case TYPE_inet4:
+ switch (ATOMbasetype(dtp)) {
+ case TYPE_inet6:
+ *reduce = false;
+ return convert_inet4_inet6(src, dst, ci, candoff);
+ default:
+ return BUN_NONE + 1;
+ }
+ case TYPE_inet6:
+ switch (ATOMbasetype(dtp)) {
+ case TYPE_inet4:
+ *reduce = false;
+ return convert_inet6_inet4(src, dst, ci, candoff);
+ default:
+ return BUN_NONE + 1;
+ }
default:
return BUN_NONE + 1;
}
diff --git a/monetdb5/modules/atoms/inet-46.c b/monetdb5/modules/atoms/inet-46.c
--- a/monetdb5/modules/atoms/inet-46.c
+++ b/monetdb5/modules/atoms/inet-46.c
@@ -563,6 +563,8 @@ INETinet62str(char **ret, const inet6 *v
static str
INETinet42inet6(inet6 *ret, const inet4 *s)
{
+ /* could use VALconvert like the function below, but this has less
+ * overhead */
if (is_inet4_nil(*s))
*ret = inet6_nil;
else
@@ -574,6 +576,18 @@ INETinet42inet6(inet6 *ret, const inet4
return MAL_SUCCEED;
}
+static str
+INETinet62inet4(inet4 *ret, const inet6 *s)
+{
+ ValRecord val;
+ VALinit(&val, TYPE_inet6, s);
+ if (VALconvert(TYPE_inet4, &val) == NULL)
+ throw(MAL, "inet46.inet4",
+ SQLSTATE(22003) "overflow in conversion to inet4");
+ *ret = val.val.ip4val;
+ return MAL_SUCCEED;
+}
+
static bte
inet6containsinet6(const inet6 *ip1, const sht *msk1, const inet6 *ip2, const
sht *msk2, bool strict, bool symmetric)
{
@@ -672,13 +686,7 @@ static str
INETinet42inet6_bulk(bat *ret, const bat *bid, const bat *sid)
{
BAT *b = NULL, *s = NULL, *dst = NULL;
- inet4 *restrict bv;
- inet6 *restrict dv;
str msg = NULL;
- struct canditer ci;
- oid off;
- bool nils = false;
- BATiter bi;
if (sid && !is_bat_nil(*sid)) {
if ((s = BATdescriptor(*sid)) == NULL) {
@@ -695,55 +703,48 @@ INETinet42inet6_bulk(bat *ret, const bat
SQLSTATE(HY002)
RUNTIME_OBJECT_MISSING);
goto bailout;
}
- off = b->hseqbase;
- canditer_init(&ci, b, s);
- if (!(dst = COLnew(ci.hseq, TYPE_inet6, ci.ncand, TRANSIENT))) {
+ if ((dst = BATconvert(b, s, TYPE_inet6, 0, 0, 0)) == NULL) {
msg = createException(SQL, "batcalc.inet6",
SQLSTATE(HY013)
MAL_MALLOC_FAIL);
goto bailout;
}
+ *ret = dst->batCacheid;
+ BBPkeepref(dst);
_______________________________________________
checkin-list mailing list -- [email protected]
To unsubscribe send an email to [email protected]