Ptv_t* ptvunion(Ptv_t* a, Ptv_t* b) { Ptvprefix_t* bp; if (!(a = ptvcopy(a))) return 0; for (bp = (Ptvprefix_t*)dtfirst(b->dict); bp; bp = (Ptvprefix_t*)dtnext(b->dict, bp)) if (!ptvinsert(a, bp->min, bp->max)) break; return a; }
Ptv_t* ptvcover(Ptv_t* a, Ptv_t* b) { Ptv_t* t; Ptvprefix_t* ap; Ptvprefix_t* bp; if (!(t = ptvopen(a->disc, a->size))) return 0; ap = (Ptvprefix_t*)dtfirst(a->dict); bp = (Ptvprefix_t*)dtfirst(b->dict); while (ap && bp) { if (fvcmp(a->size, ap->min, bp->max) > 0) bp = (Ptvprefix_t*)dtnext(b->dict, bp); else { if (fvcmp(a->size, ap->max, bp->min) >= 0 && !ptvinsert(t, ap->min, ap->max)) break; ap = (Ptvprefix_t*)dtnext(a->dict, ap); } } return t; }
int main(int argc, char** argv) { char* file; char* s; Ptv_t* ptv; Ptvprefix_t* pp; Sfio_t* sp; unsigned char prefix[IP6PREFIX]; unsigned char addr[IP6ADDR]; Ptvdisc_t ptvdisc; int dump = 0; error_info.id = "testptv"; ptvinit(&ptvdisc); ptvdisc.errorf = errorf; for (;;) { switch (optget(argv, usage)) { case 'd': dump = 1; continue; case '?': error(ERROR_USAGE|4, "%s", opt_info.arg); continue; case ':': error(2, "%s", opt_info.arg); continue; } break; } argv += opt_info.index; if (!(file = *argv++)) error(ERROR_USAGE|4, "%s", optusage(0)); if (!(sp = sfopen(0, file, "r"))) error(ERROR_SYSTEM|3, "%s: cannot read prefix file", file); if (!(ptv = ptvopen(&ptvdisc, 16))) error(3, "cannot open ptv table"); while (s = sfgetr(sp, '\n', 1)) if (strtoip6(s, 0, prefix, prefix + IP6BITS)) error(1, "%s: invalid prefix", s); else { if (dump) sfprintf(sfstderr, "insert %s %s\n", fmtip6(ptvmin(ptv->size, ptv->r[0], prefix, prefix[IP6BITS]), prefix[IP6BITS]), fmtip6(ptvmax(ptv->size, ptv->r[1], prefix, prefix[IP6BITS]), prefix[IP6BITS])); if (!ptvinsert(ptv, ptvmin(ptv->size, ptv->r[0], prefix, prefix[IP6BITS]), ptvmax(ptv->size, ptv->r[1], prefix, prefix[IP6BITS]))) { error(2, "%s: ptv insertion error", s); break; } } sfclose(sp); if (dump) ptvdump(ptv, sfstdout); file = *argv++; do { if (!file || streq(file, "-")) sp = sfstdin; else if (!(sp = sfopen(0, file, "r"))) error(ERROR_SYSTEM|3, "%s: cannot read address file", file); while (s = sfgetr(sp, '\n', 1)) if (strtoip6(s, 0, addr, 0)) error(1, "%s: invalid address", s); else if (pp = ptvmatch(ptv, addr)) sfprintf(sfstdout, "%-38s %-38s %-38s\n", fmtip6(addr, -1), fmtip6(pp->min, -1), fmtip6(pp->max, -1)); else sfprintf(sfstdout, "%-38s -\n", fmtip6(addr, -1)); if (sp != sfstdin) sfclose(sp); } while (file && (file = *argv++)); ptvclose(ptv); return 0; }