~clint-fewbar/ubuntu/precise/squid3/ignore-sighup-early

« back to all changes in this revision

Viewing changes to lib/radix.c

  • Committer: Bazaar Package Importer
  • Author(s): Luigi Gangitano
  • Date: 2010-05-04 11:15:49 UTC
  • mfrom: (1.3.1 upstream)
  • mto: (20.3.1 squeeze) (21.2.1 sid)
  • mto: This revision was merged to the branch mainline in revision 21.
  • Revision ID: james.westby@ubuntu.com-20100504111549-1apjh2g5sndki4te
Tags: upstream-3.1.3
ImportĀ upstreamĀ versionĀ 3.1.3

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
1
/*
2
 
 * $Id: radix.c,v 1.23 2007/04/25 11:30:16 adrian Exp $
 
2
 * $Id$
3
3
 *
4
4
 * DEBUG: section 53    Radix Tree data structure implementation
5
5
 * AUTHOR: NetBSD Derived
20
20
 *  it under the terms of the GNU General Public License as published by
21
21
 *  the Free Software Foundation; either version 2 of the License, or
22
22
 *  (at your option) any later version.
23
 
 *  
 
23
 *
24
24
 *  This program is distributed in the hope that it will be useful,
25
25
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
26
26
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
27
27
 *  GNU General Public License for more details.
28
 
 *  
 
28
 *
29
29
 *  You should have received a copy of the GNU General Public License
30
30
 *  along with this program; if not, write to the Free Software
31
31
 *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA.
113
113
struct squid_radix_mask *squid_rn_mkfreelist;
114
114
struct squid_radix_node_head *squid_mask_rnhead;
115
115
static char *addmask_key;
116
 
static unsigned char normal_chars[] =
117
 
{0, 0x80, 0xc0, 0xe0, 0xf0, 0xf8, 0xfc, 0xfe, 0xFF};
 
116
static unsigned char normal_chars[] = {0, 0x80, 0xc0, 0xe0, 0xf0, 0xf8, 0xfc, 0xfe, 0xFF};
118
117
static char *rn_zeros, *rn_ones;
119
118
 
120
119
/* aliases */
159
158
 * We define the index of a route to associated with the mask to be
160
159
 * the first bit number in the mask where 0 occurs (with bit number 0
161
160
 * representing the highest order bit).
162
 
 * 
 
161
 *
163
162
 * We say a mask is normal if every bit is 0, past the index of the mask.
164
163
 * If a node n has a descendant (k, m) with index(m) == index(n) == rn_b,
165
164
 * and m is a normal mask, then the route applies to every descendant of n.
166
165
 * If the index(m) < rn_b, this implies the trailing last few bits of k
167
166
 * before bit b are all 0, (and hence consequently true of every descendant
168
167
 * of n), so the route applies to all descendants of the node as well.
169
 
 * 
 
168
 *
170
169
 * Similar logic shows that a non-normal mask m such that
171
170
 * index(m) <= index(n) could potentially apply to many children of n.
172
171
 * Thus, for each non-host route, we attach its mask to a list at an internal
173
 
 * node as high in the tree as we can go. 
 
172
 * node as high in the tree as we can go.
174
173
 *
175
174
 * The present version of the code makes use of normal routes in short-
176
175
 * circuiting an explict mask and compare operation when testing whether
179
178
 */
180
179
 
181
180
struct squid_radix_node *
182
 
squid_rn_search(void *v_arg, struct squid_radix_node *head)
183
 
{
 
181
squid_rn_search(void *v_arg, struct squid_radix_node *head) {
184
182
    register struct squid_radix_node *x;
185
183
    register caddr_t v;
186
184
 
187
185
    for (x = head, v = v_arg; x->rn_b >= 0;) {
188
 
        if (x->rn_bmask & v[x->rn_off])
189
 
            x = x->rn_r;
190
 
        else
191
 
            x = x->rn_l;
 
186
        if (x->rn_bmask & v[x->rn_off])
 
187
            x = x->rn_r;
 
188
        else
 
189
            x = x->rn_l;
192
190
    }
193
191
    return (x);
194
192
}
195
193
 
196
194
struct squid_radix_node *
197
 
squid_rn_search_m(void *v_arg, struct squid_radix_node *head, void *m_arg)
198
 
{
 
195
squid_rn_search_m(void *v_arg, struct squid_radix_node *head, void *m_arg) {
199
196
    register struct squid_radix_node *x;
200
197
    register caddr_t v = v_arg, m = m_arg;
201
198
 
202
199
    for (x = head; x->rn_b >= 0;) {
203
 
        if ((x->rn_bmask & m[x->rn_off]) &&
204
 
            (x->rn_bmask & v[x->rn_off]))
205
 
            x = x->rn_r;
206
 
        else
207
 
            x = x->rn_l;
 
200
        if ((x->rn_bmask & m[x->rn_off]) &&
 
201
                (x->rn_bmask & v[x->rn_off]))
 
202
            x = x->rn_r;
 
203
        else
 
204
            x = x->rn_l;
208
205
    }
209
206
    return x;
210
207
}
218
215
    int masks_are_equal = 1;
219
216
 
220
217
    if (longer > 0)
221
 
        lim -= longer;
 
218
        lim -= longer;
222
219
    while (n < lim) {
223
 
        if (*n & ~(*m))
224
 
            return 0;
225
 
        if (*n++ != *m++)
226
 
            masks_are_equal = 0;
 
220
        if (*n & ~(*m))
 
221
            return 0;
 
222
        if (*n++ != *m++)
 
223
            masks_are_equal = 0;
227
224
    }
228
225
    while (n < lim2)
229
 
        if (*n++)
230
 
            return 0;
 
226
        if (*n++)
 
227
            return 0;
231
228
    if (masks_are_equal && (longer < 0))
232
 
        for (lim2 = m - longer; m < lim2;)
233
 
            if (*m++)
234
 
                return 1;
 
229
        for (lim2 = m - longer; m < lim2;)
 
230
            if (*m++)
 
231
                return 1;
235
232
    return (!masks_are_equal);
236
233
}
237
234
 
238
235
struct squid_radix_node *
239
 
squid_rn_lookup(void *v_arg, void *m_arg, struct squid_radix_node_head *head)
240
 
{
 
236
squid_rn_lookup(void *v_arg, void *m_arg, struct squid_radix_node_head *head) {
241
237
    register struct squid_radix_node *x;
242
238
    caddr_t netmask = 0;
243
239
 
244
240
    if (m_arg) {
245
 
        if ((x = squid_rn_addmask(m_arg, 1, head->rnh_treetop->rn_off)) == 0)
246
 
            return (0);
247
 
        netmask = x->rn_key;
 
241
        if ((x = squid_rn_addmask(m_arg, 1, head->rnh_treetop->rn_off)) == 0)
 
242
            return (0);
 
243
        netmask = x->rn_key;
248
244
    }
249
245
    x = squid_rn_match(v_arg, head);
250
246
    if (x && netmask) {
251
 
        while (x && x->rn_mask != netmask)
252
 
            x = x->rn_dupedkey;
 
247
        while (x && x->rn_mask != netmask)
 
248
            x = x->rn_dupedkey;
253
249
    }
254
250
    return x;
255
251
}
262
258
    int length = min(*(u_char *) cp, *(u_char *) cp2);
263
259
 
264
260
    if (cp3 == 0)
265
 
        cp3 = rn_ones;
 
261
        cp3 = rn_ones;
266
262
    else
267
 
        length = min(length, *(u_char *) cp3);
 
263
        length = min(length, *(u_char *) cp3);
268
264
    cplim = cp + length;
269
265
    cp3 += skip;
270
266
    cp2 += skip;
271
267
    for (cp += skip; cp < cplim; cp++, cp2++, cp3++)
272
 
        if ((*cp ^ *cp2) & *cp3)
273
 
            return 0;
 
268
        if ((*cp ^ *cp2) & *cp3)
 
269
            return 0;
274
270
    return 1;
275
271
}
276
272
 
277
273
struct squid_radix_node *
278
 
squid_rn_match(void *v_arg, struct squid_radix_node_head *head)
279
 
{
 
274
squid_rn_match(void *v_arg, struct squid_radix_node_head *head) {
280
275
    caddr_t v = v_arg;
281
276
    register struct squid_radix_node *t = head->rnh_treetop, *x;
282
277
    register caddr_t cp = v, cp2;
290
285
     * subroutine call.
291
286
     */
292
287
    for (; t->rn_b >= 0;) {
293
 
        if (t->rn_bmask & cp[t->rn_off])
294
 
            t = t->rn_r;
295
 
        else
296
 
            t = t->rn_l;
 
288
        if (t->rn_bmask & cp[t->rn_off])
 
289
            t = t->rn_r;
 
290
        else
 
291
            t = t->rn_l;
297
292
    }
298
293
    /*
299
294
     * See if we match exactly as a host destination
307
302
     * are probably the most common case...
308
303
     */
309
304
    if (t->rn_mask)
310
 
        vlen = *(u_char *) t->rn_mask;
 
305
        vlen = *(u_char *) t->rn_mask;
311
306
    cp += off;
312
307
    cp2 = t->rn_key + off;
313
308
    cplim = v + vlen;
314
309
    for (; cp < cplim; cp++, cp2++)
315
 
        if (*cp != *cp2)
316
 
            goto on1;
 
310
        if (*cp != *cp2)
 
311
            goto on1;
317
312
    /*
318
313
     * This extra grot is in case we are explicitly asked
319
314
     * to look up the default.  Ugh!
320
315
     */
321
316
    if ((t->rn_flags & RNF_ROOT) && t->rn_dupedkey)
322
 
        t = t->rn_dupedkey;
 
317
        t = t->rn_dupedkey;
323
318
    return t;
324
 
  on1:
 
319
on1:
325
320
    test = (*cp ^ *cp2) & 0xff; /* find first bit that differs */
326
321
    for (b = 7; (test >>= 1) > 0;)
327
 
        b--;
 
322
        b--;
328
323
    matched_off = cp - v;
329
324
    b += matched_off << 3;
330
325
    rn_b = -1 - b;
332
327
     * If there is a host route in a duped-key chain, it will be first.
333
328
     */
334
329
    if ((saved_t = t)->rn_mask == 0)
335
 
        t = t->rn_dupedkey;
 
330
        t = t->rn_dupedkey;
336
331
    for (; t; t = t->rn_dupedkey)
337
 
        /*
338
 
         * Even if we don't match exactly as a host,
339
 
         * we may match if the leaf we wound up at is
340
 
         * a route to a net.
341
 
         */
342
 
        if (t->rn_flags & RNF_NORMAL) {
343
 
            if (rn_b <= t->rn_b)
344
 
                return t;
345
 
        } else if (rn_satsifies_leaf(v, t, matched_off))
346
 
            return t;
 
332
        /*
 
333
         * Even if we don't match exactly as a host,
 
334
         * we may match if the leaf we wound up at is
 
335
         * a route to a net.
 
336
         */
 
337
        if (t->rn_flags & RNF_NORMAL) {
 
338
            if (rn_b <= t->rn_b)
 
339
                return t;
 
340
        } else if (rn_satsifies_leaf(v, t, matched_off))
 
341
            return t;
347
342
    t = saved_t;
348
343
    /* start searching up the tree */
349
344
    do {
350
 
        register struct squid_radix_mask *m;
351
 
        t = t->rn_p;
352
 
        if ((m = t->rn_mklist)) {
353
 
            /*
354
 
             * If non-contiguous masks ever become important
355
 
             * we can restore the masking and open coding of
356
 
             * the search and satisfaction test and put the
357
 
             * calculation of "off" back before the "do".
358
 
             */
359
 
            do {
360
 
                if (m->rm_flags & RNF_NORMAL) {
361
 
                    if (rn_b <= m->rm_b)
362
 
                        return (m->rm_leaf);
363
 
                } else {
364
 
                    off = min(t->rn_off, matched_off);
365
 
                    x = squid_rn_search_m(v, t, m->rm_mask);
366
 
                    while (x && x->rn_mask != m->rm_mask)
367
 
                        x = x->rn_dupedkey;
368
 
                    if (x && rn_satsifies_leaf(v, x, off))
369
 
                        return x;
370
 
                }
371
 
            } while ((m = m->rm_mklist));
372
 
        }
 
345
        register struct squid_radix_mask *m;
 
346
        t = t->rn_p;
 
347
        if ((m = t->rn_mklist)) {
 
348
            /*
 
349
             * If non-contiguous masks ever become important
 
350
             * we can restore the masking and open coding of
 
351
             * the search and satisfaction test and put the
 
352
             * calculation of "off" back before the "do".
 
353
             */
 
354
            do {
 
355
                if (m->rm_flags & RNF_NORMAL) {
 
356
                    if (rn_b <= m->rm_b)
 
357
                        return (m->rm_leaf);
 
358
                } else {
 
359
                    off = min(t->rn_off, matched_off);
 
360
                    x = squid_rn_search_m(v, t, m->rm_mask);
 
361
                    while (x && x->rn_mask != m->rm_mask)
 
362
                        x = x->rn_dupedkey;
 
363
                    if (x && rn_satsifies_leaf(v, x, off))
 
364
                        return x;
 
365
                }
 
366
            } while ((m = m->rm_mklist));
 
367
        }
373
368
    } while (t != top);
374
369
    return 0;
375
370
}
382
377
#endif
383
378
 
384
379
struct squid_radix_node *
385
 
squid_rn_newpair(void *v, int b, struct squid_radix_node nodes[2])
386
 
{
 
380
squid_rn_newpair(void *v, int b, struct squid_radix_node nodes[2]) {
387
381
    register struct squid_radix_node *tt = nodes, *t = tt + 1;
388
382
    t->rn_b = b;
389
383
    t->rn_bmask = 0x80 >> (b & 7);
404
398
}
405
399
 
406
400
struct squid_radix_node *
407
 
squid_rn_insert(void *v_arg, struct squid_radix_node_head *head, int *dupentry, struct squid_radix_node nodes[2])
408
 
{
 
401
squid_rn_insert(void *v_arg, struct squid_radix_node_head *head, int *dupentry, struct squid_radix_node nodes[2]) {
409
402
    caddr_t v = v_arg;
410
403
    struct squid_radix_node *top = head->rnh_treetop;
411
404
    int head_off = top->rn_off, vlen = (int) *((u_char *) v);
417
410
     * Find first bit at which v and t->rn_key differ
418
411
     */
419
412
    {
420
 
        register caddr_t cp2 = t->rn_key + head_off;
421
 
        register int cmp_res;
422
 
        caddr_t cplim = v + vlen;
 
413
        register caddr_t cp2 = t->rn_key + head_off;
 
414
        register int cmp_res;
 
415
        caddr_t cplim = v + vlen;
423
416
 
424
 
        while (cp < cplim)
425
 
            if (*cp2++ != *cp++)
426
 
                goto on1;
427
 
        *dupentry = 1;
428
 
        return t;
429
 
      on1:
430
 
        *dupentry = 0;
431
 
        cmp_res = (cp[-1] ^ cp2[-1]) & 0xff;
432
 
        for (b = (cp - v) << 3; cmp_res; b--)
433
 
            cmp_res >>= 1;
 
417
        while (cp < cplim)
 
418
            if (*cp2++ != *cp++)
 
419
                goto on1;
 
420
        *dupentry = 1;
 
421
        return t;
 
422
on1:
 
423
        *dupentry = 0;
 
424
        cmp_res = (cp[-1] ^ cp2[-1]) & 0xff;
 
425
        for (b = (cp - v) << 3; cmp_res; b--)
 
426
            cmp_res >>= 1;
434
427
    }
435
428
    {
436
 
        register struct squid_radix_node *p, *x = top;
437
 
        cp = v;
438
 
        do {
439
 
            p = x;
440
 
            if (cp[x->rn_off] & x->rn_bmask)
441
 
                x = x->rn_r;
442
 
            else
443
 
                x = x->rn_l;
444
 
        } while (b > (unsigned) x->rn_b);       /* x->rn_b < b && x->rn_b >= 0 */
 
429
        register struct squid_radix_node *p, *x = top;
 
430
        cp = v;
 
431
        do {
 
432
            p = x;
 
433
            if (cp[x->rn_off] & x->rn_bmask)
 
434
                x = x->rn_r;
 
435
            else
 
436
                x = x->rn_l;
 
437
        } while (b > (unsigned) x->rn_b);       /* x->rn_b < b && x->rn_b >= 0 */
445
438
#ifdef RN_DEBUG
446
 
        if (rn_debug)
447
 
            fprintf(stderr, "squid_rn_insert: Going In:\n");
448
 
        traverse(p);
 
439
        if (rn_debug)
 
440
            fprintf(stderr, "squid_rn_insert: Going In:\n");
 
441
        traverse(p);
449
442
#endif
450
 
        t = squid_rn_newpair(v_arg, b, nodes);
451
 
        tt = t->rn_l;
452
 
        if ((cp[p->rn_off] & p->rn_bmask) == 0)
453
 
            p->rn_l = t;
454
 
        else
455
 
            p->rn_r = t;
456
 
        x->rn_p = t;
457
 
        t->rn_p = p;            /* frees x, p as temp vars below */
458
 
        if ((cp[t->rn_off] & t->rn_bmask) == 0) {
459
 
            t->rn_r = x;
460
 
        } else {
461
 
            t->rn_r = tt;
462
 
            t->rn_l = x;
463
 
        }
 
443
        t = squid_rn_newpair(v_arg, b, nodes);
 
444
        tt = t->rn_l;
 
445
        if ((cp[p->rn_off] & p->rn_bmask) == 0)
 
446
            p->rn_l = t;
 
447
        else
 
448
            p->rn_r = t;
 
449
        x->rn_p = t;
 
450
        t->rn_p = p;            /* frees x, p as temp vars below */
 
451
        if ((cp[t->rn_off] & t->rn_bmask) == 0) {
 
452
            t->rn_r = x;
 
453
        } else {
 
454
            t->rn_r = tt;
 
455
            t->rn_l = x;
 
456
        }
464
457
#ifdef RN_DEBUG
465
 
        if (rn_debug)
466
 
            log(LOG_DEBUG, "squid_rn_insert: Coming Out:\n"), traverse(p);
 
458
        if (rn_debug)
 
459
            log(LOG_DEBUG, "squid_rn_insert: Coming Out:\n"), traverse(p);
467
460
#endif
468
461
    }
469
462
    return (tt);
470
463
}
471
464
 
472
465
struct squid_radix_node *
473
 
squid_rn_addmask(void *n_arg, int search, int skip)
474
 
{
 
466
squid_rn_addmask(void *n_arg, int search, int skip) {
475
467
    caddr_t netmask = (caddr_t) n_arg;
476
468
    register struct squid_radix_node *x;
477
469
    register caddr_t cp, cplim;
481
473
    static int last_zeroed = 0;
482
474
 
483
475
    if ((mlen = *(u_char *) netmask) > squid_max_keylen)
484
 
        mlen = squid_max_keylen;
 
476
        mlen = squid_max_keylen;
485
477
    if (skip == 0)
486
 
        skip = 1;
 
478
        skip = 1;
487
479
    if (mlen <= skip)
488
 
        return (squid_mask_rnhead->rnh_nodes);
 
480
        return (squid_mask_rnhead->rnh_nodes);
489
481
    if (skip > 1)
490
 
        memcpy(addmask_key + 1, rn_ones + 1, skip - 1);
 
482
        memcpy(addmask_key + 1, rn_ones + 1, skip - 1);
491
483
    if ((m0 = mlen) > skip)
492
 
        memcpy(addmask_key + skip, netmask + skip, mlen - skip);
 
484
        memcpy(addmask_key + skip, netmask + skip, mlen - skip);
493
485
    /*
494
486
     * Trim trailing zeroes.
495
487
     */
496
488
    for (cp = addmask_key + mlen; (cp > addmask_key) && cp[-1] == 0;)
497
 
        cp--;
 
489
        cp--;
498
490
    mlen = cp - addmask_key;
499
491
    if (mlen <= skip) {
500
 
        if (m0 >= last_zeroed)
501
 
            last_zeroed = mlen;
502
 
        return (squid_mask_rnhead->rnh_nodes);
 
492
        if (m0 >= last_zeroed)
 
493
            last_zeroed = mlen;
 
494
        return (squid_mask_rnhead->rnh_nodes);
503
495
    }
504
496
    if (m0 < last_zeroed)
505
 
        memset(addmask_key + m0, '\0', last_zeroed - m0);
 
497
        memset(addmask_key + m0, '\0', last_zeroed - m0);
506
498
    *addmask_key = last_zeroed = mlen;
507
499
    x = squid_rn_search(addmask_key, rn_masktop);
508
500
    if (memcmp(addmask_key, x->rn_key, mlen) != 0)
509
 
        x = 0;
 
501
        x = 0;
510
502
    if (x || search)
511
 
        return (x);
 
503
        return (x);
512
504
    squid_R_Malloc(x, struct squid_radix_node *, squid_max_keylen + 2 * sizeof(*x));
513
505
    if ((saved_x = x) == 0)
514
 
        return (0);
 
506
        return (0);
515
507
    memset(x, '\0', squid_max_keylen + 2 * sizeof(*x));
516
508
    netmask = cp = (caddr_t) (x + 2);
517
509
    memcpy(cp, addmask_key, mlen);
518
510
    x = squid_rn_insert(cp, squid_mask_rnhead, &maskduplicated, x);
519
511
    if (maskduplicated) {
520
 
        fprintf(stderr, "squid_rn_addmask: mask impossibly already in tree");
521
 
        squid_Free(saved_x);
522
 
        return (x);
 
512
        fprintf(stderr, "squid_rn_addmask: mask impossibly already in tree");
 
513
        squid_Free(saved_x);
 
514
        return (x);
523
515
    }
524
516
    /*
525
517
     * Calculate index of mask, and check for normalcy.
527
519
    cplim = netmask + mlen;
528
520
    isnormal = 1;
529
521
    for (cp = netmask + skip; (cp < cplim) && *(u_char *) cp == 0xff;)
530
 
        cp++;
 
522
        cp++;
531
523
    if (cp != cplim) {
532
 
        for (j = 0x80; (j & *cp) != 0; j >>= 1)
533
 
            b++;
534
 
        if (*cp != normal_chars[b] || cp != (cplim - 1))
535
 
            isnormal = 0;
 
524
        for (j = 0x80; (j & *cp) != 0; j >>= 1)
 
525
            b++;
 
526
        if (*cp != normal_chars[b] || cp != (cplim - 1))
 
527
            isnormal = 0;
536
528
    }
537
529
    b += (cp - netmask) << 3;
538
530
    x->rn_b = -1 - b;
539
531
    if (isnormal)
540
 
        x->rn_flags |= RNF_NORMAL;
 
532
        x->rn_flags |= RNF_NORMAL;
541
533
    return (x);
542
534
}
543
535
 
547
539
    register u_char *mp = m_arg, *np = n_arg, *lim;
548
540
 
549
541
    if (*mp > *np)
550
 
        return 1;               /* not really, but need to check longer one first */
 
542
        return 1;               /* not really, but need to check longer one first */
551
543
    if (*mp == *np)
552
 
        for (lim = mp + *mp; mp < lim;)
553
 
            if (*mp++ > *np++)
554
 
                return 1;
 
544
        for (lim = mp + *mp; mp < lim;)
 
545
            if (*mp++ > *np++)
 
546
                return 1;
555
547
    return 0;
556
548
}
557
549
 
558
550
static struct squid_radix_mask *
559
 
rn_new_radix_mask(struct squid_radix_node *tt, struct squid_radix_mask *next)
560
 
{
 
551
rn_new_radix_mask(struct squid_radix_node *tt, struct squid_radix_mask *next) {
561
552
    register struct squid_radix_mask *m;
562
553
 
563
554
    squid_MKGet(m);
564
555
    if (m == 0) {
565
 
        fprintf(stderr, "Mask for route not entered\n");
566
 
        return (0);
 
556
        fprintf(stderr, "Mask for route not entered\n");
 
557
        return (0);
567
558
    }
568
559
    memset(m, '\0', sizeof *m);
569
560
    m->rm_b = tt->rn_b;
570
561
    m->rm_flags = tt->rn_flags;
571
562
    if (tt->rn_flags & RNF_NORMAL)
572
 
        m->rm_leaf = tt;
 
563
        m->rm_leaf = tt;
573
564
    else
574
 
        m->rm_mask = tt->rn_mask;
 
565
        m->rm_mask = tt->rn_mask;
575
566
    m->rm_mklist = next;
576
567
    tt->rn_mklist = m;
577
568
    return m;
578
569
}
579
570
 
580
571
struct squid_radix_node *
581
 
squid_rn_addroute(void *v_arg, void *n_arg, struct squid_radix_node_head *head, struct squid_radix_node treenodes[2])
582
 
{
 
572
squid_rn_addroute(void *v_arg, void *n_arg, struct squid_radix_node_head *head, struct squid_radix_node treenodes[2]) {
583
573
    caddr_t v = (caddr_t) v_arg, netmask = (caddr_t) n_arg;
584
574
    register struct squid_radix_node *t, *x = NULL, *tt;
585
575
    struct squid_radix_node *saved_tt, *top = head->rnh_treetop;
596
586
     * nodes and possibly save time in calculating indices.
597
587
     */
598
588
    if (netmask) {
599
 
        if ((x = squid_rn_addmask(netmask, 0, top->rn_off)) == 0)
600
 
            return (0);
601
 
        b_leaf = x->rn_b;
602
 
        b = -1 - x->rn_b;
603
 
        netmask = x->rn_key;
 
589
        if ((x = squid_rn_addmask(netmask, 0, top->rn_off)) == 0)
 
590
            return (0);
 
591
        b_leaf = x->rn_b;
 
592
        b = -1 - x->rn_b;
 
593
        netmask = x->rn_key;
604
594
    }
605
595
    /*
606
596
     * Deal with duplicated keys: attach node to previous instance
607
597
     */
608
598
    saved_tt = tt = squid_rn_insert(v, head, &keyduplicated, treenodes);
609
599
    if (keyduplicated) {
610
 
        for (t = tt; tt; t = tt, tt = tt->rn_dupedkey) {
611
 
            if (tt->rn_mask == netmask)
612
 
                return (0);
613
 
            if (netmask == 0 ||
614
 
                (tt->rn_mask &&
615
 
                    ((b_leaf < tt->rn_b) ||     /* index(netmask) > node */
616
 
                        squid_rn_refines(netmask, tt->rn_mask) ||
617
 
                        rn_lexobetter(netmask, tt->rn_mask))))
618
 
                break;
619
 
        }
620
 
        /*
621
 
         * If the mask is not duplicated, we wouldn't
622
 
         * find it among possible duplicate key entries
623
 
         * anyway, so the above test doesn't hurt.
624
 
         *
625
 
         * We sort the masks for a duplicated key the same way as
626
 
         * in a masklist -- most specific to least specific.
627
 
         * This may require the unfortunate nuisance of relocating
628
 
         * the head of the list.
629
 
         */
630
 
        if (tt == saved_tt) {
631
 
            struct squid_radix_node *xx = x;
632
 
            /* link in at head of list */
633
 
            (tt = treenodes)->rn_dupedkey = t;
634
 
            tt->rn_flags = t->rn_flags;
635
 
            tt->rn_p = x = t->rn_p;
636
 
            if (x->rn_l == t)
637
 
                x->rn_l = tt;
638
 
            else
639
 
                x->rn_r = tt;
640
 
            saved_tt = tt;
641
 
            x = xx;
642
 
        } else {
643
 
            (tt = treenodes)->rn_dupedkey = t->rn_dupedkey;
644
 
            t->rn_dupedkey = tt;
645
 
        }
 
600
        for (t = tt; tt; t = tt, tt = tt->rn_dupedkey) {
 
601
            if (tt->rn_mask == netmask)
 
602
                return (0);
 
603
            if (netmask == 0 ||
 
604
                    (tt->rn_mask &&
 
605
                     ((b_leaf < tt->rn_b) ||    /* index(netmask) > node */
 
606
                      squid_rn_refines(netmask, tt->rn_mask) ||
 
607
                      rn_lexobetter(netmask, tt->rn_mask))))
 
608
                break;
 
609
        }
 
610
        /*
 
611
         * If the mask is not duplicated, we wouldn't
 
612
         * find it among possible duplicate key entries
 
613
         * anyway, so the above test doesn't hurt.
 
614
         *
 
615
         * We sort the masks for a duplicated key the same way as
 
616
         * in a masklist -- most specific to least specific.
 
617
         * This may require the unfortunate nuisance of relocating
 
618
         * the head of the list.
 
619
         */
 
620
        if (tt == saved_tt) {
 
621
            struct squid_radix_node *xx = x;
 
622
            /* link in at head of list */
 
623
            tt = treenodes;
 
624
            tt->rn_dupedkey = t;
 
625
            tt->rn_flags = t->rn_flags;
 
626
            tt->rn_p = x = t->rn_p;
 
627
            if (x->rn_l == t)
 
628
                x->rn_l = tt;
 
629
            else
 
630
                x->rn_r = tt;
 
631
            saved_tt = tt;
 
632
            x = xx;
 
633
        } else {
 
634
            tt = treenodes;
 
635
            tt->rn_dupedkey = t->rn_dupedkey;
 
636
            t->rn_dupedkey = tt;
 
637
        }
646
638
#ifdef RN_DEBUG
647
 
        t = tt + 1;
648
 
        tt->rn_info = rn_nodenum++;
649
 
        t->rn_info = rn_nodenum++;
650
 
        tt->rn_twin = t;
651
 
        tt->rn_ybro = rn_clist;
652
 
        rn_clist = tt;
 
639
        t = tt + 1;
 
640
        tt->rn_info = rn_nodenum++;
 
641
        t->rn_info = rn_nodenum++;
 
642
        tt->rn_twin = t;
 
643
        tt->rn_ybro = rn_clist;
 
644
        rn_clist = tt;
653
645
#endif
654
 
        tt->rn_key = (caddr_t) v;
655
 
        tt->rn_b = -1;
656
 
        tt->rn_flags = RNF_ACTIVE;
 
646
        tt->rn_key = (caddr_t) v;
 
647
        tt->rn_b = -1;
 
648
        tt->rn_flags = RNF_ACTIVE;
657
649
    }
658
650
    /*
659
651
     * Put mask in tree.
660
652
     */
661
653
    if (netmask) {
662
 
        tt->rn_mask = netmask;
663
 
        tt->rn_b = x->rn_b;
664
 
        tt->rn_flags |= x->rn_flags & RNF_NORMAL;
 
654
        tt->rn_mask = netmask;
 
655
        tt->rn_b = x->rn_b;
 
656
        tt->rn_flags |= x->rn_flags & RNF_NORMAL;
665
657
    }
666
658
    t = saved_tt->rn_p;
667
659
    if (keyduplicated)
668
 
        goto on2;
 
660
        goto on2;
669
661
    b_leaf = -1 - t->rn_b;
670
662
    if (t->rn_r == saved_tt)
671
 
        x = t->rn_l;
 
663
        x = t->rn_l;
672
664
    else
673
 
        x = t->rn_r;
 
665
        x = t->rn_r;
674
666
    /* Promote general routes from below */
675
667
    if (x->rn_b < 0) {
676
 
        for (mp = &t->rn_mklist; x; x = x->rn_dupedkey)
677
 
            if (x->rn_mask && (x->rn_b >= b_leaf) && x->rn_mklist == 0) {
678
 
                if ((*mp = m = rn_new_radix_mask(x, 0)))
679
 
                    mp = &m->rm_mklist;
680
 
            }
 
668
        for (mp = &t->rn_mklist; x; x = x->rn_dupedkey)
 
669
            if (x->rn_mask && (x->rn_b >= b_leaf) && x->rn_mklist == 0) {
 
670
                if ((*mp = m = rn_new_radix_mask(x, 0)))
 
671
                    mp = &m->rm_mklist;
 
672
            }
681
673
    } else if (x->rn_mklist) {
682
 
        /*
683
 
         * Skip over masks whose index is > that of new node
684
 
         */
685
 
        for (mp = &x->rn_mklist; (m = *mp); mp = &m->rm_mklist)
686
 
            if (m->rm_b >= b_leaf)
687
 
                break;
688
 
        t->rn_mklist = m;
689
 
        *mp = 0;
 
674
        /*
 
675
         * Skip over masks whose index is > that of new node
 
676
         */
 
677
        for (mp = &x->rn_mklist; (m = *mp); mp = &m->rm_mklist)
 
678
            if (m->rm_b >= b_leaf)
 
679
                break;
 
680
        t->rn_mklist = m;
 
681
        *mp = 0;
690
682
    }
691
 
  on2:
 
683
on2:
692
684
    /* Add new route to highest possible ancestor's list */
693
685
    if ((netmask == 0) || (b > t->rn_b))
694
 
        return tt;              /* can't lift at all */
 
686
        return tt;              /* can't lift at all */
695
687
    b_leaf = tt->rn_b;
696
688
    do {
697
 
        x = t;
698
 
        t = t->rn_p;
 
689
        x = t;
 
690
        t = t->rn_p;
699
691
    } while (b <= t->rn_b && x != top);
700
692
    /*
701
693
     * Search through routes associated with node to
704
696
     * double loop on deletion.
705
697
     */
706
698
    for (mp = &x->rn_mklist; (m = *mp); mp = &m->rm_mklist) {
707
 
        if (m->rm_b < b_leaf)
708
 
            continue;
709
 
        if (m->rm_b > b_leaf)
710
 
            break;
711
 
        if (m->rm_flags & RNF_NORMAL) {
712
 
            mmask = m->rm_leaf->rn_mask;
713
 
            if (tt->rn_flags & RNF_NORMAL) {
714
 
                fprintf(stderr,
715
 
                    "Non-unique normal route, mask not entered");
716
 
                return tt;
717
 
            }
718
 
        } else
719
 
            mmask = m->rm_mask;
720
 
        if (mmask == netmask) {
721
 
            m->rm_refs++;
722
 
            tt->rn_mklist = m;
723
 
            return tt;
724
 
        }
725
 
        if (squid_rn_refines(netmask, mmask) || rn_lexobetter(netmask, mmask))
726
 
            break;
 
699
        if (m->rm_b < b_leaf)
 
700
            continue;
 
701
        if (m->rm_b > b_leaf)
 
702
            break;
 
703
        if (m->rm_flags & RNF_NORMAL) {
 
704
            mmask = m->rm_leaf->rn_mask;
 
705
            if (tt->rn_flags & RNF_NORMAL) {
 
706
                fprintf(stderr,
 
707
                        "Non-unique normal route, mask not entered");
 
708
                return tt;
 
709
            }
 
710
        } else
 
711
            mmask = m->rm_mask;
 
712
        if (mmask == netmask) {
 
713
            m->rm_refs++;
 
714
            tt->rn_mklist = m;
 
715
            return tt;
 
716
        }
 
717
        if (squid_rn_refines(netmask, mmask) || rn_lexobetter(netmask, mmask))
 
718
            break;
727
719
    }
728
720
    *mp = rn_new_radix_mask(tt, *mp);
729
721
    return tt;
730
722
}
731
723
 
732
724
struct squid_radix_node *
733
 
squid_rn_delete(void *v_arg, void *netmask_arg, struct squid_radix_node_head *head)
734
 
{
 
725
squid_rn_delete(void *v_arg, void *netmask_arg, struct squid_radix_node_head *head) {
735
726
    register struct squid_radix_node *t, *p, *x, *tt;
736
727
    struct squid_radix_mask *m, *saved_m, **mp;
737
728
    struct squid_radix_node *dupedkey, *saved_tt, *top;
747
738
    saved_tt = tt;
748
739
    top = x;
749
740
    if (tt == 0 ||
750
 
        memcmp(v + head_off, tt->rn_key + head_off, vlen - head_off))
751
 
        return (0);
 
741
            memcmp(v + head_off, tt->rn_key + head_off, vlen - head_off))
 
742
        return (0);
752
743
    /*
753
744
     * Delete our route from mask lists.
754
745
     */
755
746
    if (netmask) {
756
 
        if ((x = squid_rn_addmask(netmask, 1, head_off)) == 0)
757
 
            return (0);
758
 
        netmask = x->rn_key;
759
 
        while (tt->rn_mask != netmask)
760
 
            if ((tt = tt->rn_dupedkey) == 0)
761
 
                return (0);
 
747
        if ((x = squid_rn_addmask(netmask, 1, head_off)) == 0)
 
748
            return (0);
 
749
        netmask = x->rn_key;
 
750
        while (tt->rn_mask != netmask)
 
751
            if ((tt = tt->rn_dupedkey) == 0)
 
752
                return (0);
762
753
    }
763
754
    if (tt->rn_mask == 0 || (saved_m = m = tt->rn_mklist) == 0)
764
 
        goto on1;
 
755
        goto on1;
765
756
    if (tt->rn_flags & RNF_NORMAL) {
766
 
        if (m->rm_leaf != tt || m->rm_refs > 0) {
767
 
            fprintf(stderr, "squid_rn_delete: inconsistent annotation\n");
768
 
            return 0;           /* dangling ref could cause disaster */
769
 
        }
 
757
        if (m->rm_leaf != tt || m->rm_refs > 0) {
 
758
            fprintf(stderr, "squid_rn_delete: inconsistent annotation\n");
 
759
            return 0;           /* dangling ref could cause disaster */
 
760
        }
770
761
    } else {
771
 
        if (m->rm_mask != tt->rn_mask) {
772
 
            fprintf(stderr, "squid_rn_delete: inconsistent annotation\n");
773
 
            goto on1;
774
 
        }
775
 
        if (--m->rm_refs >= 0)
776
 
            goto on1;
 
762
        if (m->rm_mask != tt->rn_mask) {
 
763
            fprintf(stderr, "squid_rn_delete: inconsistent annotation\n");
 
764
            goto on1;
 
765
        }
 
766
        if (--m->rm_refs >= 0)
 
767
            goto on1;
777
768
    }
778
769
    b = -1 - tt->rn_b;
779
770
    t = saved_tt->rn_p;
780
771
    if (b > t->rn_b)
781
 
        goto on1;               /* Wasn't lifted at all */
 
772
        goto on1;               /* Wasn't lifted at all */
782
773
    do {
783
 
        x = t;
784
 
        t = t->rn_p;
 
774
        x = t;
 
775
        t = t->rn_p;
785
776
    } while (b <= t->rn_b && x != top);
786
777
    for (mp = &x->rn_mklist; (m = *mp); mp = &m->rm_mklist)
787
 
        if (m == saved_m) {
788
 
            *mp = m->rm_mklist;
789
 
            squid_MKFree(m);
790
 
            break;
791
 
        }
 
778
        if (m == saved_m) {
 
779
            *mp = m->rm_mklist;
 
780
            squid_MKFree(m);
 
781
            break;
 
782
        }
792
783
    if (m == 0) {
793
 
        fprintf(stderr, "squid_rn_delete: couldn't find our annotation\n");
794
 
        if (tt->rn_flags & RNF_NORMAL)
795
 
            return (0);         /* Dangling ref to us */
 
784
        fprintf(stderr, "squid_rn_delete: couldn't find our annotation\n");
 
785
        if (tt->rn_flags & RNF_NORMAL)
 
786
            return (0);         /* Dangling ref to us */
796
787
    }
797
 
  on1:
 
788
on1:
798
789
    /*
799
790
     * Eliminate us from tree
800
791
     */
801
792
    if (tt->rn_flags & RNF_ROOT)
802
 
        return (0);
 
793
        return (0);
803
794
#ifdef RN_DEBUG
804
795
    /* Get us out of the creation list */
805
796
    for (t = rn_clist; t && t->rn_ybro != tt; t = t->rn_ybro) {
806
797
    }
807
798
    if (t)
808
 
        t->rn_ybro = tt->rn_ybro;
 
799
        t->rn_ybro = tt->rn_ybro;
809
800
#endif
810
801
    t = tt->rn_p;
811
802
    if ((dupedkey = saved_tt->rn_dupedkey)) {
812
 
        if (tt == saved_tt) {
813
 
            x = dupedkey;
814
 
            x->rn_p = t;
815
 
            if (t->rn_l == tt)
816
 
                t->rn_l = x;
817
 
            else
818
 
                t->rn_r = x;
819
 
        } else {
820
 
            for (x = p = saved_tt; p && p->rn_dupedkey != tt;)
821
 
                p = p->rn_dupedkey;
822
 
            if (p)
823
 
                p->rn_dupedkey = tt->rn_dupedkey;
824
 
            else
825
 
                fprintf(stderr, "squid_rn_delete: couldn't find us\n");
826
 
        }
827
 
        t = tt + 1;
828
 
        if (t->rn_flags & RNF_ACTIVE) {
 
803
        if (tt == saved_tt) {
 
804
            x = dupedkey;
 
805
            x->rn_p = t;
 
806
            if (t->rn_l == tt)
 
807
                t->rn_l = x;
 
808
            else
 
809
                t->rn_r = x;
 
810
        } else {
 
811
            for (x = p = saved_tt; p && p->rn_dupedkey != tt;)
 
812
                p = p->rn_dupedkey;
 
813
            if (p)
 
814
                p->rn_dupedkey = tt->rn_dupedkey;
 
815
            else
 
816
                fprintf(stderr, "squid_rn_delete: couldn't find us\n");
 
817
        }
 
818
        t = tt + 1;
 
819
        if (t->rn_flags & RNF_ACTIVE) {
829
820
#ifndef RN_DEBUG
830
 
            *++x = *t;
831
 
            p = t->rn_p;
 
821
            *++x = *t;
 
822
            p = t->rn_p;
832
823
#else
833
 
            b = t->rn_info;
834
 
            *++x = *t;
835
 
            t->rn_info = b;
836
 
            p = t->rn_p;
 
824
            b = t->rn_info;
 
825
            *++x = *t;
 
826
            t->rn_info = b;
 
827
            p = t->rn_p;
837
828
#endif
838
 
            if (p->rn_l == t)
839
 
                p->rn_l = x;
840
 
            else
841
 
                p->rn_r = x;
842
 
            x->rn_l->rn_p = x;
843
 
            x->rn_r->rn_p = x;
844
 
        }
845
 
        goto out;
 
829
            if (p->rn_l == t)
 
830
                p->rn_l = x;
 
831
            else
 
832
                p->rn_r = x;
 
833
            x->rn_l->rn_p = x;
 
834
            x->rn_r->rn_p = x;
 
835
        }
 
836
        goto out;
846
837
    }
847
838
    if (t->rn_l == tt)
848
 
        x = t->rn_r;
 
839
        x = t->rn_r;
849
840
    else
850
 
        x = t->rn_l;
 
841
        x = t->rn_l;
851
842
    p = t->rn_p;
852
843
    if (p->rn_r == t)
853
 
        p->rn_r = x;
 
844
        p->rn_r = x;
854
845
    else
855
 
        p->rn_l = x;
 
846
        p->rn_l = x;
856
847
    x->rn_p = p;
857
848
    /*
858
849
     * Demote routes attached to us.
859
850
     */
860
851
    if (t->rn_mklist) {
861
 
        if (x->rn_b >= 0) {
862
 
            for (mp = &x->rn_mklist; (m = *mp);)
863
 
                mp = &m->rm_mklist;
864
 
            *mp = t->rn_mklist;
865
 
        } else {
866
 
            /* If there are any key,mask pairs in a sibling
867
 
             * duped-key chain, some subset will appear sorted
868
 
             * in the same order attached to our mklist */
869
 
            for (m = t->rn_mklist; m && x; x = x->rn_dupedkey)
870
 
                if (m == x->rn_mklist) {
871
 
                    struct squid_radix_mask *mm = m->rm_mklist;
872
 
                    x->rn_mklist = 0;
873
 
                    if (--(m->rm_refs) < 0)
874
 
                        squid_MKFree(m);
875
 
                    m = mm;
876
 
                }
 
852
        if (x->rn_b >= 0) {
 
853
            for (mp = &x->rn_mklist; (m = *mp);)
 
854
                mp = &m->rm_mklist;
 
855
            *mp = t->rn_mklist;
 
856
        } else {
 
857
            /* If there are any key,mask pairs in a sibling
 
858
             * duped-key chain, some subset will appear sorted
 
859
             * in the same order attached to our mklist */
 
860
            for (m = t->rn_mklist; m && x; x = x->rn_dupedkey)
 
861
                if (m == x->rn_mklist) {
 
862
                    struct squid_radix_mask *mm = m->rm_mklist;
 
863
                    x->rn_mklist = 0;
 
864
                    if (--(m->rm_refs) < 0)
 
865
                        squid_MKFree(m);
 
866
                    m = mm;
 
867
                }
877
868
#if RN_DEBUG
878
 
            if (m)
879
 
                fprintf(stderr, "%s %x at %x\n",
880
 
                    "squid_rn_delete: Orphaned Mask", (int) m, (int) x);
 
869
            if (m)
 
870
                fprintf(stderr, "%s %x at %x\n",
 
871
                        "squid_rn_delete: Orphaned Mask", (int) m, (int) x);
881
872
#else
882
 
            assert(m == NULL);
 
873
            assert(m == NULL);
883
874
#endif
884
 
        }
 
875
        }
885
876
    }
886
877
    /*
887
878
     * We may be holding an active internal node in the tree.
889
880
    x = tt + 1;
890
881
    if (t != x) {
891
882
#ifndef RN_DEBUG
892
 
        *t = *x;
 
883
        *t = *x;
893
884
#else
894
 
        b = t->rn_info;
895
 
        *t = *x;
896
 
        t->rn_info = b;
 
885
        b = t->rn_info;
 
886
        *t = *x;
 
887
        t->rn_info = b;
897
888
#endif
898
 
        t->rn_l->rn_p = t;
899
 
        t->rn_r->rn_p = t;
900
 
        p = x->rn_p;
901
 
        if (p->rn_l == x)
902
 
            p->rn_l = t;
903
 
        else
904
 
            p->rn_r = t;
 
889
        t->rn_l->rn_p = t;
 
890
        t->rn_r->rn_p = t;
 
891
        p = x->rn_p;
 
892
        if (p->rn_l == x)
 
893
            p->rn_l = t;
 
894
        else
 
895
            p->rn_r = t;
905
896
    }
906
 
  out:
 
897
out:
907
898
    tt->rn_flags &= ~RNF_ACTIVE;
908
899
    tt[1].rn_flags &= ~RNF_ACTIVE;
909
900
    return (tt);
922
913
     */
923
914
    /* First time through node, go left */
924
915
    while (rn->rn_b >= 0)
925
 
        rn = rn->rn_l;
 
916
        rn = rn->rn_l;
926
917
    for (;;) {
927
 
        base = rn;
928
 
        /* If at right child go back up, otherwise, go right */
929
 
        while (rn->rn_p->rn_r == rn && (rn->rn_flags & RNF_ROOT) == 0)
930
 
            rn = rn->rn_p;
931
 
        /* Find the next *leaf* since next node might vanish, too */
932
 
        for (rn = rn->rn_p->rn_r; rn->rn_b >= 0;)
933
 
            rn = rn->rn_l;
934
 
        next = rn;
935
 
        /* Process leaves */
936
 
        while ((rn = base)) {
937
 
            base = rn->rn_dupedkey;
938
 
            if (!(rn->rn_flags & RNF_ROOT) && (error = (*f) (rn, w)))
939
 
                return (error);
940
 
        }
941
 
        rn = next;
942
 
        if (rn->rn_flags & RNF_ROOT)
943
 
            return (0);
 
918
        base = rn;
 
919
        /* If at right child go back up, otherwise, go right */
 
920
        while (rn->rn_p->rn_r == rn && (rn->rn_flags & RNF_ROOT) == 0)
 
921
            rn = rn->rn_p;
 
922
        /* Find the next *leaf* since next node might vanish, too */
 
923
        for (rn = rn->rn_p->rn_r; rn->rn_b >= 0;)
 
924
            rn = rn->rn_l;
 
925
        next = rn;
 
926
        /* Process leaves */
 
927
        while ((rn = base)) {
 
928
            base = rn->rn_dupedkey;
 
929
            if (!(rn->rn_flags & RNF_ROOT) && (error = (*f) (rn, w)))
 
930
                return (error);
 
931
        }
 
932
        rn = next;
 
933
        if (rn->rn_flags & RNF_ROOT)
 
934
            return (0);
944
935
    }
945
936
    /* NOTREACHED */
946
937
}
951
942
    register struct squid_radix_node_head *rnh;
952
943
    register struct squid_radix_node *t, *tt, *ttt;
953
944
    if (*head)
954
 
        return (1);
 
945
        return (1);
955
946
    squid_R_Malloc(rnh, struct squid_radix_node_head *, sizeof(*rnh));
956
947
    if (rnh == 0)
957
 
        return (0);
 
948
        return (0);
958
949
    memset(rnh, '\0', sizeof(*rnh));
959
950
    *head = rnh;
960
951
    t = squid_rn_newpair(rn_zeros, off, rnh->rnh_nodes);
983
974
    struct domain *dom;
984
975
 
985
976
    for (dom = domains; dom; dom = dom->dom_next)
986
 
        if (dom->dom_maxrtkey > squid_max_keylen)
987
 
            squid_max_keylen = dom->dom_maxrtkey;
 
977
        if (dom->dom_maxrtkey > squid_max_keylen)
 
978
            squid_max_keylen = dom->dom_maxrtkey;
988
979
#endif
989
980
    if (squid_max_keylen == 0) {
990
 
        fprintf(stderr,
991
 
            "squid_rn_init: radix functions require squid_max_keylen be set\n");
992
 
        return;
 
981
        fprintf(stderr,
 
982
                "squid_rn_init: radix functions require squid_max_keylen be set\n");
 
983
        return;
993
984
    }
994
985
    squid_R_Malloc(rn_zeros, char *, 3 * squid_max_keylen);
995
986
    if (rn_zeros == NULL) {
996
 
        fprintf(stderr, "squid_rn_init failed.\n");
997
 
        exit(-1);
 
987
        fprintf(stderr, "squid_rn_init failed.\n");
 
988
        exit(-1);
998
989
    }
999
990
    memset(rn_zeros, '\0', 3 * squid_max_keylen);
1000
991
    rn_ones = cp = rn_zeros + squid_max_keylen;
1001
992
    addmask_key = cplim = rn_ones + squid_max_keylen;
1002
993
    while (cp < cplim)
1003
 
        *cp++ = -1;
 
994
        *cp++ = -1;
1004
995
    if (squid_rn_inithead(&squid_mask_rnhead, 0) == 0) {
1005
 
        fprintf(stderr, "rn_init2 failed.\n");
1006
 
        exit(-1);
 
996
        fprintf(stderr, "rn_init2 failed.\n");
 
997
        exit(-1);
1007
998
    }
1008
999
}