struct squid_radix_node * squid_rn_lookup(void *v_arg, void *m_arg, struct squid_radix_node_head *head) { register struct squid_radix_node *x; caddr_t netmask = 0; if (m_arg) { if ((x = squid_rn_addmask(m_arg, 1, head->rnh_treetop->rn_off)) == 0) return (0); netmask = x->rn_key; } x = squid_rn_match(v_arg, head); if (x && netmask) { while (x && x->rn_mask != netmask) x = x->rn_dupedkey; } return x; }
int asnMatchIp(void *data, struct in_addr addr) { unsigned long lh; struct squid_radix_node *rn; as_info *e; m_int m_addr; intlist *a = NULL; intlist *b = NULL; lh = ntohl(addr.s_addr); debug(53, 3) ("asnMatchIp: Called for %s.\n", inet_ntoa(addr)); if (AS_tree_head == NULL) return 0; if (addr.s_addr == no_addr.s_addr) return 0; if (addr.s_addr == any_addr.s_addr) return 0; store_m_int(lh, m_addr); rn = squid_rn_match(m_addr, AS_tree_head); if (rn == NULL) { debug(53, 3) ("asnMatchIp: Address not in as db.\n"); return 0; } debug(53, 3) ("asnMatchIp: Found in db!\n"); e = ((rtentry *) rn)->e_info; assert(e); for (a = (intlist *) data; a; a = a->next) for (b = e->as_number; b; b = b->next) if (a->i == b->i) { debug(53, 5) ("asnMatchIp: Found a match!\n"); return 1; } debug(53, 5) ("asnMatchIp: AS not in as db.\n"); return 0; }
static int asnAddNet(char *as_string, int as_number) { rtentry *e; struct squid_radix_node *rn; char dbg1[32], dbg2[32]; intlist **Tail = NULL; intlist *q = NULL; as_info *asinfo = NULL; struct in_addr in_a, in_m; long mask, addr; char *t; int bitl; t = strchr(as_string, '/'); if (t == NULL) { debug(53, 3) ("asnAddNet: failed, invalid response from whois server.\n"); return 0; } *t = '\0'; addr = inet_addr(as_string); bitl = atoi(t + 1); if (bitl < 0) bitl = 0; if (bitl > 32) bitl = 32; mask = bitl ? 0xfffffffful << (32 - bitl) : 0; in_a.s_addr = addr; in_m.s_addr = mask; xstrncpy(dbg1, inet_ntoa(in_a), 32); xstrncpy(dbg2, inet_ntoa(in_m), 32); addr = ntohl(addr); /*mask = ntohl(mask); */ debug(53, 3) ("asnAddNet: called for %s/%s\n", dbg1, dbg2); e = xmalloc(sizeof(rtentry)); memset(e, '\0', sizeof(rtentry)); store_m_int(addr, e->e_addr); store_m_int(mask, e->e_mask); rn = squid_rn_lookup(e->e_addr, e->e_mask, AS_tree_head); if (rn != NULL) { asinfo = ((rtentry *) rn)->e_info; if (intlistFind(asinfo->as_number, as_number)) { debug(53, 3) ("asnAddNet: Ignoring repeated network '%s/%d' for AS %d\n", dbg1, bitl, as_number); } else { debug(53, 3) ("asnAddNet: Warning: Found a network with multiple AS numbers!\n"); for (Tail = &asinfo->as_number; *Tail; Tail = &(*Tail)->next); q = xcalloc(1, sizeof(intlist)); q->i = as_number; *(Tail) = q; e->e_info = asinfo; } } else { q = xcalloc(1, sizeof(intlist)); q->i = as_number; asinfo = xmalloc(sizeof(asinfo)); asinfo->as_number = q; rn = squid_rn_addroute(e->e_addr, e->e_mask, AS_tree_head, e->e_nodes); rn = squid_rn_match(e->e_addr, AS_tree_head); assert(rn != NULL); e->e_info = asinfo; if (rn == 0) { /* assert might expand to nothing */ xfree(asinfo); xfree(q); xfree(e); debug(53, 3) ("asnAddNet: Could not add entry.\n"); return 0; } } e->e_info = asinfo; return 1; }