Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse code

Merge branch 'master' of https://github.com/i-maravic/xorp.ct

  • Loading branch information...
commit 277de9cc102fad981d161a104a3531c28d437532 2 parents 3e39c91 + 8ce7308
Ben Greear authored

Showing 48 changed files with 1,913 additions and 2,050 deletions. Show diff stats Hide diff stats

  1. 16  xorp/SConstruct
  2. 58  xorp/libxorp/ipnet.hh
  3. 26  xorp/libxorp/ipv4.cc
  4. 42  xorp/libxorp/ipv4.hh
  5. 65  xorp/libxorp/ipv6.cc
  6. 74  xorp/libxorp/ipv6.hh
  7. 100  xorp/libxorp/memory_pool.hh
  8. 46  xorp/libxorp/nexthop.cc
  9. 26  xorp/libxorp/nexthop.hh
  10. 115  xorp/libxorp/tests/test_trie.cc
  11. 47  xorp/libxorp/trie.hh
  12. 6  xorp/libxorp/xlog.h
  13. 3  xorp/policy/backend/policy_redist_map.cc
  14. 2  xorp/rib/SConscript
  15. 6  xorp/rib/parser.cc
  16. 2  xorp/rib/parser_direct_cmds.hh
  17. 5  xorp/rib/protocol.cc
  18. 2  xorp/rib/protocol.hh
  19. 581  xorp/rib/rib.cc
  20. 136  xorp/rib/rib.hh
  21. 107  xorp/rib/route.cc
  22. 101  xorp/rib/route.hh
  23. 6  xorp/rib/rt_tab_base.cc
  24. 29  xorp/rib/rt_tab_base.hh
  25. 169  xorp/rib/rt_tab_deletion.cc
  26. 116  xorp/rib/rt_tab_deletion.hh
  27. 913  xorp/rib/rt_tab_extint.cc
  28. 78  xorp/rib/rt_tab_extint.hh
  29. 46  xorp/rib/rt_tab_log.cc
  30. 23  xorp/rib/rt_tab_log.hh
  31. 124  xorp/rib/rt_tab_origin.cc
  32. 118  xorp/rib/rt_tab_origin.hh
  33. 155  xorp/rib/rt_tab_pol_conn.cc
  34. 18  xorp/rib/rt_tab_pol_conn.hh
  35. 93  xorp/rib/rt_tab_pol_redist.cc
  36. 18  xorp/rib/rt_tab_pol_redist.hh
  37. 105  xorp/rib/rt_tab_redist.cc
  38. 26  xorp/rib/rt_tab_redist.hh
  39. 91  xorp/rib/rt_tab_register.cc
  40. 86  xorp/rib/rt_tab_register.hh
  41. 22  xorp/rib/tests/commands
  42. 28  xorp/rib/tests/rt_tab_expect.cc
  43. 18  xorp/rib/tests/rt_tab_expect.hh
  44. 28  xorp/rib/tests/test_deletion.cc
  45. 47  xorp/rib/tests/test_redist.cc
  46. 18  xorp/rib/tests/test_register.cc
  47. 20  xorp/rtrmgr/template.ll
  48. 2  xorp/site_scons/config/allconfig.py
16  xorp/SConstruct
@@ -83,6 +83,7 @@ vars.AddVariables(
83 83
     BoolVariable('disable_otherlogs',  'Force disable other logs', False),
84 84
     BoolVariable('disable_profile',  'Disable Xorp Profiler feature', False),
85 85
     BoolVariable('disable_werror',  'Disable -Werror compiler flag', False),
  86
+    BoolVariable('disable_assert',  'Force disabling assertions - use with caution', False),
86 87
     BoolVariable('enable_lex_hack',  'Works around lex/yacc issues on FreeBSD', False),
87 88
     BoolVariable('enable_builddirrun',  'Enable Xorp to run from BUILD_DIR', False),
88 89
     BoolVariable('enable_boost',  'Use BOOST', False),
@@ -298,6 +299,7 @@ print 'Disable fatal logs : ', env['disable_fatallogs']
298 299
 print 'Disable info logs : ', env['disable_infologs']
299 300
 print 'Disable assert logs : ', env['disable_assertlogs']
300 301
 print 'Disable other logs : ', env['disable_otherlogs']
  302
+print 'Disable assert: ', env['disable_assert']
301 303
 
302 304
 
303 305
 env['CONFIGURELOG'] = str(builddir) + os.sep + 'config.log'
@@ -604,6 +606,20 @@ if tst and not ((tst == "no") or (tst == "false")):
604 606
 else:
605 607
     env['disable_otherlogs'] = False
606 608
 
  609
+tst = ARGUMENTS.get('disable_assert', False)
  610
+if tst and not ((tst == "no") or (tst == "false")):
  611
+    env['disable_assert'] = True
  612
+    env['disable_werror'] = True
  613
+    env['disable_otherlogs'] = True
  614
+    env['disable_assertlogs'] = True
  615
+    env['disable_infologs'] = True
  616
+    env['disable_fatallogs'] = True
  617
+    env['disable_tracelogs'] = True
  618
+    env['disable_errorlogs'] = True
  619
+    env['disable_warninglogs'] = True
  620
+else:
  621
+    env['disable_assert'] = False
  622
+
607 623
 ########## start configure magic
608 624
 
609 625
 if env.has_key('LIBS'):
58  xorp/libxorp/ipnet.hh
@@ -9,13 +9,13 @@
9 9
 // Redistribution and/or modification of this program under the terms of
10 10
 // any other version of the GNU Lesser General Public License is not
11 11
 // permitted.
12  
-// 
  12
+//
13 13
 // This program is distributed in the hope that it will be useful, but
14 14
 // WITHOUT ANY WARRANTY; without even the implied warranty of
15 15
 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. For more details,
16 16
 // see the GNU Lesser General Public License, Version 2.1, a copy of
17 17
 // which can be found in the XORP LICENSE.lgpl file.
18  
-// 
  18
+//
19 19
 // XORP, Inc, 2953 Bunker Hill Lane, Suite 204, Santa Clara, CA 95054, USA;
20 20
 // http://xorp.net
21 21
 
@@ -104,8 +104,8 @@ public:
104 104
      * right-hand operand.
105 105
      */
106 106
     bool operator==(const IPNet& other) const {
107  
-	return ((prefix_len() == other.prefix_len()) &&
108  
-		(masked_addr() == other.masked_addr()));
  107
+	return ((_prefix_len == other._prefix_len) &&
  108
+		(_masked_addr == other._masked_addr));
109 109
     }
110 110
 
111 111
     /**
@@ -456,7 +456,8 @@ private:
456 456
 /* ------------------------------------------------------------------------- */
457 457
 /* Deferred method definitions */
458 458
 
459  
-template <class A> bool
  459
+template <class A>
  460
+inline bool
460 461
 IPNet<A>::operator<(const IPNet& other) const
461 462
 {
462 463
 #if 1
@@ -548,23 +549,38 @@ IPNet<A>::is_overlap(const IPNet<A>& other) const
548 549
     return (other.masked_addr() == masked_addr());
549 550
 }
550 551
 
551  
-template <class A> bool
552  
-IPNet<A>::contains(const IPNet<A>& other) const
  552
+template <>
  553
+inline bool
  554
+IPNet<IPv4>::contains(const IPv4& addr) const
553 555
 {
554  
-    if (masked_addr().af() != other.masked_addr().af())
555  
-	return (false);
  556
+    return addr.mask_by_prefix_len_uint(_prefix_len) == _masked_addr.addr();
  557
+}
556 558
 
557  
-    if (prefix_len() > other.prefix_len()) {
  559
+template <>
  560
+inline bool
  561
+IPNet<IPv6>::contains(const IPv6& addr) const
  562
+{
  563
+    uint32_t prefixed_addr[4];
  564
+    addr.mask_by_prefix_len_uint(_prefix_len, prefixed_addr);
  565
+    return ((prefixed_addr[0] == _masked_addr.addr()[0])
  566
+	    && (prefixed_addr[1] == _masked_addr.addr()[1])
  567
+	    && (prefixed_addr[2] == _masked_addr.addr()[2])
  568
+	    && (prefixed_addr[3] == _masked_addr.addr()[3]));
  569
+}
  570
+
  571
+template <class A>
  572
+inline bool
  573
+IPNet<A>::contains(const IPNet<A>& other) const
  574
+{
  575
+    if (_prefix_len > other._prefix_len)
558 576
 	// I have smaller prefix size, hence I don't contain other.
559 577
 	return (false);
560  
-    }
561  
-    if (prefix_len() < other.prefix_len()) {
562  
-	// I have bigger prefix size
563  
-	IPNet other_masked(other.masked_addr(), prefix_len());
564  
-	return (other_masked.masked_addr() == masked_addr());
565  
-    }
566  
-    // Same prefix size
567  
-    return (other.masked_addr() == masked_addr());
  578
+
  579
+    if (_prefix_len == other._prefix_len)
  580
+	return (other._masked_addr == _masked_addr);
  581
+
  582
+    // I have bigger prefix size
  583
+    return (contains(other._masked_addr));
568 584
 }
569 585
 
570 586
 template <class A> void
@@ -591,7 +607,8 @@ IPNet<A>::initialize_from_string(const char *cp)
591 607
     _masked_addr = A(addr.c_str()).mask_by_prefix_len(_prefix_len);
592 608
 }
593 609
 
594  
-template <class A> IPNet<A>&
  610
+template <class A>
  611
+inline IPNet<A>&
595 612
 IPNet<A>::operator--()
596 613
 {
597 614
     _masked_addr = _masked_addr >> (_masked_addr.addr_bitlen() - _prefix_len);
@@ -600,7 +617,8 @@ IPNet<A>::operator--()
600 617
     return (*this);
601 618
 }
602 619
 
603  
-template <class A> IPNet<A>&
  620
+template <class A>
  621
+inline IPNet<A>&
604 622
 IPNet<A>::operator++()
605 623
 {
606 624
     _masked_addr = _masked_addr >> (_masked_addr.addr_bitlen() - _prefix_len);
26  xorp/libxorp/ipv4.cc
@@ -8,13 +8,13 @@
8 8
 // Redistribution and/or modification of this program under the terms of
9 9
 // any other version of the GNU Lesser General Public License is not
10 10
 // permitted.
11  
-// 
  11
+//
12 12
 // This program is distributed in the hope that it will be useful, but
13 13
 // WITHOUT ANY WARRANTY; without even the implied warranty of
14 14
 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. For more details,
15 15
 // see the GNU Lesser General Public License, Version 2.1, a copy of
16 16
 // which can be found in the XORP LICENSE.lgpl file.
17  
-// 
  17
+//
18 18
 // XORP, Inc, 2953 Bunker Hill Lane, Suite 204, Santa Clara, CA 95054, USA;
19 19
 // http://xorp.net
20 20
 
@@ -219,12 +219,6 @@ IPv4::operator>>(uint32_t right_shift) const
219 219
     return IPv4(htonl(tmp_addr));
220 220
 }
221 221
 
222  
-bool
223  
-IPv4::operator<(const IPv4& other) const
224  
-{
225  
-    return ntohl(_addr) < ntohl(other._addr);
226  
-}
227  
-
228 222
 IPv4
229 223
 IPv4::make_prefix(uint32_t mask_len) throw (InvalidNetmaskLength)
230 224
 {
@@ -251,22 +245,6 @@ IPv4::mask_len() const
251 245
     return ctr;
252 246
 }
253 247
 
254  
-IPv4&
255  
-IPv4::operator--()
256  
-{
257  
-    uint32_t tmp_addr = ntohl(_addr) - 1;
258  
-    _addr = htonl(tmp_addr);
259  
-    return *this;
260  
-}
261  
-
262  
-IPv4&
263  
-IPv4::operator++()
264  
-{
265  
-    uint32_t tmp_addr = ntohl(_addr) + 1;
266  
-    _addr = htonl(tmp_addr);
267  
-    return *this;
268  
-}
269  
-
270 248
 string
271 249
 IPv4::str() const
272 250
 {
42  xorp/libxorp/ipv4.hh
@@ -9,13 +9,13 @@
9 9
 // Redistribution and/or modification of this program under the terms of
10 10
 // any other version of the GNU Lesser General Public License is not
11 11
 // permitted.
12  
-// 
  12
+//
13 13
 // This program is distributed in the hope that it will be useful, but
14 14
 // WITHOUT ANY WARRANTY; without even the implied warranty of
15 15
 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. For more details,
16 16
 // see the GNU Lesser General Public License, Version 2.1, a copy of
17 17
 // which can be found in the XORP LICENSE.lgpl file.
18  
-// 
  18
+//
19 19
 // XORP, Inc, 2953 Bunker Hill Lane, Suite 204, Santa Clara, CA 95054, USA;
20 20
 // http://xorp.net
21 21
 
@@ -612,6 +612,8 @@ public:
612 612
      */
613 613
     static IPv4 make_prefix(uint32_t mask_len) throw (InvalidNetmaskLength);
614 614
 
  615
+    static uint32_t make_prefix_uint(uint32_t mask_len) throw (InvalidNetmaskLength);
  616
+
615 617
     /**
616 618
      * Make an IPv4 address prefix.
617 619
      *
@@ -624,6 +626,11 @@ public:
624 626
 	return (*this) & make_prefix(mask_len);
625 627
     }
626 628
 
  629
+    uint32_t mask_by_prefix_len_uint(uint32_t mask_len) const
  630
+	throw (InvalidNetmaskLength) {
  631
+	return this->_addr & make_prefix_uint(mask_len);
  632
+    }
  633
+
627 634
     /**
628 635
      * Get the mask length.
629 636
      *
@@ -748,6 +755,31 @@ IPv4::bits(uint32_t lsb, uint32_t len) const
748 755
 }
749 756
 
750 757
 inline uint32_t
  758
+IPv4::make_prefix_uint(uint32_t mask_len) throw (InvalidNetmaskLength)
  759
+{
  760
+    if (mask_len > 32)
  761
+	xorp_throw(InvalidNetmaskLength, mask_len);
  762
+    uint32_t m = (mask_len == 0) ? 0 : ((~0U) << (32 - mask_len));
  763
+    return htonl(m);
  764
+}
  765
+
  766
+inline IPv4&
  767
+IPv4::operator--()
  768
+{
  769
+    uint32_t tmp_addr = ntohl(_addr) - 1;
  770
+    _addr = htonl(tmp_addr);
  771
+    return *this;
  772
+}
  773
+
  774
+inline IPv4&
  775
+IPv4::operator++()
  776
+{
  777
+    uint32_t tmp_addr = ntohl(_addr) + 1;
  778
+    _addr = htonl(tmp_addr);
  779
+    return *this;
  780
+}
  781
+
  782
+inline uint32_t
751 783
 IPv4::bit_count() const
752 784
 {
753 785
     // XXX: no need for ntohl()
@@ -760,6 +792,12 @@ IPv4::leading_zero_count() const
760 792
     return (xorp_leading_zero_count_uint32(ntohl(_addr)));
761 793
 }
762 794
 
  795
+inline bool
  796
+IPv4::operator<(const IPv4& other) const
  797
+{
  798
+    return ntohl(_addr) < ntohl(other._addr);
  799
+}
  800
+
763 801
 struct IPv4Constants {
764 802
     static const IPv4 zero,
765 803
 	any,
65  xorp/libxorp/ipv6.cc
@@ -8,13 +8,13 @@
8 8
 // Redistribution and/or modification of this program under the terms of
9 9
 // any other version of the GNU Lesser General Public License is not
10 10
 // permitted.
11  
-// 
  11
+//
12 12
 // This program is distributed in the hope that it will be useful, but
13 13
 // WITHOUT ANY WARRANTY; without even the implied warranty of
14 14
 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. For more details,
15 15
 // see the GNU Lesser General Public License, Version 2.1, a copy of
16 16
 // which can be found in the XORP LICENSE.lgpl file.
17  
-// 
  17
+//
18 18
 // XORP, Inc, 2953 Bunker Hill Lane, Suite 204, Santa Clara, CA 95054, USA;
19 19
 // http://xorp.net
20 20
 
@@ -329,67 +329,6 @@ IPv6::operator>>(uint32_t rs) const
329 329
     return IPv6(tmp_addr);
330 330
 }
331 331
 
332  
-bool
333  
-IPv6::operator<(const IPv6& other) const
334  
-{
335  
-    int i;
336  
-    x_static_assert(sizeof(_addr) == 16);
337  
-
338  
-    for (i = 0; i < 3; i++) {	// XXX: Loop ends intentionally at 3 not 4
339  
-	if (_addr[i] != other._addr[i])
340  
-	    break;
341  
-    }
342  
-    return ntohl(_addr[i]) < ntohl(other._addr[i]);
343  
-}
344  
-
345  
-bool
346  
-IPv6::operator==(const IPv6& other) const
347  
-{
348  
-    return ((_addr[0] == other._addr[0])
349  
-	    && (_addr[1] == other._addr[1])
350  
-	    && (_addr[2] == other._addr[2])
351  
-	    && (_addr[3] == other._addr[3]));
352  
-}
353  
-
354  
-bool
355  
-IPv6::operator!=(const IPv6& other) const
356  
-{
357  
-    return ((_addr[0] != other._addr[0])
358  
-	    || (_addr[1] != other._addr[1])
359  
-	    || (_addr[2] != other._addr[2])
360  
-	    || (_addr[3] != other._addr[3]));
361  
-}
362  
-
363  
-IPv6&
364  
-IPv6::operator--()
365  
-{
366  
-    for (int i = 3; i >= 0; i--) {
367  
-	if (_addr[i] == 0) {
368  
-	    _addr[i] = 0xffffffffU;
369  
-	} else {
370  
-	    uint32_t tmp_addr = ntohl(_addr[i]) - 1;
371  
-	    _addr[i] = htonl(tmp_addr);
372  
-	    return *this;
373  
-	}
374  
-    }
375  
-    return *this;
376  
-}
377  
-
378  
-IPv6&
379  
-IPv6::operator++()
380  
-{
381  
-    for (int i = 3; i >= 0; i--) {
382  
-	if (_addr[i] == 0xffffffffU) {
383  
-	    _addr[i] = 0;
384  
-	} else {
385  
-	    uint32_t tmp_addr = ntohl(_addr[i]) + 1;
386  
-	    _addr[i] = htonl(tmp_addr);
387  
-	    return *this;
388  
-	}
389  
-    }
390  
-    return *this;
391  
-}
392  
-
393 332
 static uint32_t
394 333
 init_prefixes(IPv6* v6prefix)
395 334
 {
74  xorp/libxorp/ipv6.hh
@@ -9,13 +9,13 @@
9 9
 // Redistribution and/or modification of this program under the terms of
10 10
 // any other version of the GNU Lesser General Public License is not
11 11
 // permitted.
12  
-// 
  12
+//
13 13
 // This program is distributed in the hope that it will be useful, but
14 14
 // WITHOUT ANY WARRANTY; without even the implied warranty of
15 15
 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. For more details,
16 16
 // see the GNU Lesser General Public License, Version 2.1, a copy of
17 17
 // which can be found in the XORP LICENSE.lgpl file.
18  
-// 
  18
+//
19 19
 // XORP, Inc, 2953 Bunker Hill Lane, Suite 204, Santa Clara, CA 95054, USA;
20 20
 // http://xorp.net
21 21
 
@@ -514,6 +514,15 @@ public:
514 514
 	return (*this) & make_prefix(prefix_len);
515 515
     }
516 516
 
  517
+    void mask_by_prefix_len_uint(uint32_t prefix_len, uint32_t* masked_addr) const
  518
+	throw (InvalidNetmaskLength) {
  519
+	const IPv6& other = make_prefix(prefix_len);
  520
+	masked_addr[0] = _addr[0] & other._addr[0];
  521
+	masked_addr[1] = _addr[1] & other._addr[1];
  522
+	masked_addr[2] = _addr[2] & other._addr[2];
  523
+	masked_addr[3] = _addr[3] & other._addr[3];
  524
+    }
  525
+
517 526
     /**
518 527
      * Get the mask length.
519 528
      *
@@ -661,6 +670,67 @@ IPv6::leading_zero_count() const
661 670
     return (r);
662 671
 }
663 672
 
  673
+inline bool
  674
+IPv6::operator<(const IPv6& other) const
  675
+{
  676
+    int i;
  677
+    x_static_assert(sizeof(_addr) == 16);
  678
+
  679
+    for (i = 0; i < 3; i++) {	// XXX: Loop ends intentionally at 3 not 4
  680
+	if (_addr[i] != other._addr[i])
  681
+	    break;
  682
+    }
  683
+    return ntohl(_addr[i]) < ntohl(other._addr[i]);
  684
+}
  685
+
  686
+inline bool
  687
+IPv6::operator==(const IPv6& other) const
  688
+{
  689
+    return ((_addr[0] == other._addr[0])
  690
+	    && (_addr[1] == other._addr[1])
  691
+	    && (_addr[2] == other._addr[2])
  692
+	    && (_addr[3] == other._addr[3]));
  693
+}
  694
+
  695
+inline bool
  696
+IPv6::operator!=(const IPv6& other) const
  697
+{
  698
+    return ((_addr[0] != other._addr[0])
  699
+	    || (_addr[1] != other._addr[1])
  700
+	    || (_addr[2] != other._addr[2])
  701
+	    || (_addr[3] != other._addr[3]));
  702
+}
  703
+
  704
+inline IPv6&
  705
+IPv6::operator--()
  706
+{
  707
+    for (int i = 3; i >= 0; i--) {
  708
+	if (_addr[i] == 0) {
  709
+	    _addr[i] = 0xffffffffU;
  710
+	} else {
  711
+	    uint32_t tmp_addr = ntohl(_addr[i]) - 1;
  712
+	    _addr[i] = htonl(tmp_addr);
  713
+	    return *this;
  714
+	}
  715
+    }
  716
+    return *this;
  717
+}
  718
+
  719
+inline IPv6&
  720
+IPv6::operator++()
  721
+{
  722
+    for (int i = 3; i >= 0; i--) {
  723
+	if (_addr[i] == 0xffffffffU) {
  724
+	    _addr[i] = 0;
  725
+	} else {
  726
+	    uint32_t tmp_addr = ntohl(_addr[i]) + 1;
  727
+	    _addr[i] = htonl(tmp_addr);
  728
+	    return *this;
  729
+	}
  730
+    }
  731
+    return *this;
  732
+}
  733
+
664 734
 struct IPv6Constants {
665 735
     static const IPv6 zero,
666 736
 	any,
100  xorp/libxorp/memory_pool.hh
... ...
@@ -0,0 +1,100 @@
  1
+// -*- c-basic-offset: 4; tab-width: 8; indent-tabs-mode: t -*-
  2
+// vim:set sts=4 ts=8:
  3
+
  4
+// Copyright (c) 2012 XORP, Inc and Others
  5
+//
  6
+// This program is free software; you can redistribute it and/or modify
  7
+// it under the terms of the GNU General Public License, Version 2, June
  8
+// 1991 as published by the Free Software Foundation. Redistribution
  9
+// and/or modification of this program under the terms of any other
  10
+// version of the GNU General Public License is not permitted.
  11
+//
  12
+// This program is distributed in the hope that it will be useful, but
  13
+// WITHOUT ANY WARRANTY; without even the implied warranty of
  14
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. For more details,
  15
+// see the GNU General Public License, Version 2, a copy of which can be
  16
+// found in the XORP LICENSE.gpl file.
  17
+//
  18
+// XORP Inc, 2953 Bunker Hill Lane, Suite 204, Santa Clara, CA 95054, USA;
  19
+// http://xorp.net
  20
+
  21
+#ifndef _LIBXORP_MEMORY_POOL_HH_
  22
+#define _LIBXORP_MEMORY_POOL_HH_
  23
+
  24
+#include "xorp.h"
  25
+
  26
+template <class T, size_t EXPANSION_SIZE = 100>
  27
+class MemoryPool : public NONCOPYABLE {
  28
+public:
  29
+    MemoryPool();
  30
+    ~MemoryPool();
  31
+
  32
+    //Allocate element of type T from free list
  33
+    void* alloc();
  34
+
  35
+    // Return element to the free list
  36
+    void free(void* doomed);
  37
+private:
  38
+    // next element on the free list
  39
+    MemoryPool<T, EXPANSION_SIZE>* _next;
  40
+
  41
+    // Add free elements to the list
  42
+    void expand_free_list();
  43
+
  44
+    size_t _size;
  45
+};
  46
+
  47
+template <class T, size_t EXPANSION_SIZE>
  48
+MemoryPool<T, EXPANSION_SIZE>::MemoryPool() :
  49
+    _size((sizeof(T) > sizeof(MemoryPool<T, EXPANSION_SIZE>)) ? sizeof(T) :sizeof(MemoryPool<T, EXPANSION_SIZE>))
  50
+{
  51
+    expand_free_list();
  52
+}
  53
+
  54
+template <class T, size_t EXPANSION_SIZE>
  55
+MemoryPool<T, EXPANSION_SIZE>::~MemoryPool()
  56
+{
  57
+    for (MemoryPool<T, EXPANSION_SIZE> *nextPtr = _next; nextPtr != NULL; nextPtr = _next) {
  58
+	_next = _next->_next;
  59
+	delete [] reinterpret_cast<char* >(nextPtr);
  60
+    }
  61
+}
  62
+
  63
+template <class T, size_t EXPANSION_SIZE>
  64
+inline void*
  65
+MemoryPool<T, EXPANSION_SIZE>::alloc()
  66
+{
  67
+    if (!_next)
  68
+	expand_free_list();
  69
+
  70
+    MemoryPool<T, EXPANSION_SIZE>* head = _next;
  71
+    _next = head->_next;
  72
+    return head;
  73
+}
  74
+
  75
+template <class T, size_t EXPANSION_SIZE>
  76
+inline void
  77
+MemoryPool<T, EXPANSION_SIZE>::free(void* doomed)
  78
+{
  79
+    MemoryPool<T, EXPANSION_SIZE>* head = reinterpret_cast<MemoryPool<T, EXPANSION_SIZE>* >(doomed);
  80
+
  81
+    head->_next = _next;
  82
+    _next = head;
  83
+}
  84
+
  85
+template <class T, size_t EXPANSION_SIZE>
  86
+inline void
  87
+MemoryPool<T, EXPANSION_SIZE>::expand_free_list()
  88
+{
  89
+    // We must allocate object large enough to contain the next pointer
  90
+    MemoryPool<T, EXPANSION_SIZE>* runner = reinterpret_cast<MemoryPool<T, EXPANSION_SIZE>* >(new char[_size]);
  91
+
  92
+    _next = runner;
  93
+    for (size_t i = 0; i < EXPANSION_SIZE; ++i) {
  94
+	runner->_next = reinterpret_cast<MemoryPool<T, EXPANSION_SIZE>* >(new char[_size]);
  95
+	runner = runner->_next;
  96
+    }
  97
+    runner->_next = NULL;
  98
+}
  99
+
  100
+#endif /* MEMORY_POOL_HH_ */
46  xorp/libxorp/nexthop.cc
@@ -70,6 +70,29 @@ IPPeerNextHop<A>::IPPeerNextHop(const A& from_ipaddr)
70 70
 }
71 71
 
72 72
 template<class A>
  73
+void*
  74
+IPPeerNextHop<A>::operator new(size_t/* size*/)
  75
+{
  76
+    return memory_pool().alloc();
  77
+}
  78
+
  79
+template<class A>
  80
+void
  81
+IPPeerNextHop<A>::operator delete(void* ptr)
  82
+{
  83
+    memory_pool().free(ptr);
  84
+}
  85
+
  86
+template<class A>
  87
+inline
  88
+MemoryPool<IPPeerNextHop<A> >&
  89
+IPPeerNextHop<A>::memory_pool()
  90
+{
  91
+    static MemoryPool<IPPeerNextHop<A> > mp;
  92
+    return mp;
  93
+}
  94
+
  95
+template<class A>
73 96
 IPEncapsNextHop<A>::IPEncapsNextHop(const A& from_ipaddr)
74 97
     : IPNextHop<A>(from_ipaddr)
75 98
 {
@@ -81,6 +104,29 @@ IPExternalNextHop<A>::IPExternalNextHop(const A& from_ipaddr)
81 104
 {
82 105
 }
83 106
 
  107
+template<class A>
  108
+void*
  109
+IPExternalNextHop<A>::operator new(size_t/* size*/)
  110
+{
  111
+    return memory_pool().alloc();
  112
+}
  113
+
  114
+template<class A>
  115
+void
  116
+IPExternalNextHop<A>::operator delete(void* ptr)
  117
+{
  118
+    memory_pool().free(ptr);
  119
+}
  120
+
  121
+template<class A>
  122
+inline
  123
+MemoryPool<IPExternalNextHop<A> >&
  124
+IPExternalNextHop<A>::memory_pool()
  125
+{
  126
+    static MemoryPool<IPExternalNextHop<A> > mp;
  127
+    return mp;
  128
+}
  129
+
84 130
 template <class A>
85 131
 DiscardNextHop<A>::DiscardNextHop()
86 132
     : IPNextHop<A>(A::ZERO())
26  xorp/libxorp/nexthop.hh
@@ -28,6 +28,7 @@
28 28
 #include "ipv4.hh"
29 29
 #include "ipv6.hh"
30 30
 #include "ipvx.hh"
  31
+#include "memory_pool.hh"
31 32
 
32 33
 // NextHop is a generic next hop object.
33 34
 // PeerNextHop is for next hops that are local peers.
@@ -115,6 +116,8 @@ public:
115 116
      */
116 117
     IPNextHop(const A &from_ipaddr);
117 118
 
  119
+    virtual ~IPNextHop() { }
  120
+
118 121
 #ifdef XORP_USE_USTL
119 122
     IPNextHop() { }
120 123
 #endif
@@ -134,6 +137,12 @@ public:
134 137
      */
135 138
     string str() const;
136 139
 
  140
+    /**
  141
+     * Returns pointer to copy of IPNextHop
  142
+     *
  143
+     * Callers ARE RESPONSIBLE for freeing the memory
  144
+     */
  145
+
137 146
 protected:
138 147
     const A _addr;
139 148
 };
@@ -171,8 +180,13 @@ public:
171 180
      */
172 181
     int type() const { return PEER_NEXTHOP; }
173 182
 
174  
-private:
  183
+    IPPeerNextHop* get_copy() { return new IPPeerNextHop<A>(*this); }
  184
+
  185
+    void* operator new(size_t size);
  186
+    void operator delete(void* ptr);
175 187
 
  188
+private:
  189
+    static MemoryPool<IPPeerNextHop<A> >& memory_pool();
176 190
 };
177 191
 
178 192
 typedef IPPeerNextHop<IPv4> IPv4PeerNextHop;
@@ -204,6 +218,7 @@ public:
204 218
      */
205 219
     int type() const { return ENCAPS_NEXTHOP; }
206 220
 
  221
+
207 222
 private:
208 223
     //_cached_peer is the cached copy of the local peer we send the
209 224
     //encapsulated packet to.
@@ -248,8 +263,13 @@ public:
248 263
      */
249 264
     int type() const { return EXTERNAL_NEXTHOP; }
250 265
 
251  
-private:
  266
+    IPExternalNextHop* get_copy() { return new IPExternalNextHop<A>(*this); }
  267
+
  268
+    void* operator new(size_t size);
  269
+    void operator delete(void* ptr);
252 270
 
  271
+private:
  272
+    static MemoryPool<IPExternalNextHop<A> >& memory_pool();
253 273
 };
254 274
 
255 275
 typedef IPExternalNextHop<IPv4> IPv4ExternalNextHop;
@@ -277,6 +297,7 @@ public:
277 297
      */
278 298
     int type() const { return DISCARD_NEXTHOP; }
279 299
 
  300
+
280 301
 private:
281 302
 
282 303
 };
@@ -302,6 +323,7 @@ public:
302 323
      */
303 324
     int type() const { return UNREACHABLE_NEXTHOP; }
304 325
 
  326
+
305 327
 private:
306 328
 
307 329
 };
115  xorp/libxorp/tests/test_trie.cc
@@ -9,13 +9,13 @@
9 9
 // Redistribution and/or modification of this program under the terms of
10 10
 // any other version of the GNU Lesser General Public License is not
11 11
 // permitted.
12  
-// 
  12
+//
13 13
 // This program is distributed in the hope that it will be useful, but
14 14
 // WITHOUT ANY WARRANTY; without even the implied warranty of
15 15
 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. For more details,
16 16
 // see the GNU Lesser General Public License, Version 2.1, a copy of
17 17
 // which can be found in the XORP LICENSE.lgpl file.
18  
-// 
  18
+//
19 19
 // XORP, Inc, 2953 Bunker Hill Lane, Suite 204, Santa Clara, CA 95054, USA;
20 20
 // http://xorp.net
21 21
 
@@ -124,7 +124,7 @@ void test_upper_bound(IPv4 test_addr, IPv4 test_answer) {
124 124
 	print_passed(result.str());
125 125
     } else {
126 126
 	print_failed("");
127  
-	printf("answer should be %s, result was %s\n", 
  127
+	printf("answer should be %s, result was %s\n",
128 128
 	       test_answer.str().c_str(), result.str().c_str());
129 129
 	trie.print();
130 130
 	abort();
@@ -142,7 +142,7 @@ void test_lower_bound(IPv4 test_addr, IPv4 test_answer) {
142 142
 	print_passed(result.str());
143 143
     } else {
144 144
 	print_failed("");
145  
-	printf("Fail: answer should be %s, result was %s\n", 
  145
+	printf("Fail: answer should be %s, result was %s\n",
146 146
 	       test_answer.str().c_str(), result.str().c_str());
147 147
 	trie.print();
148 148
 	abort();
@@ -202,7 +202,7 @@ void test_upper_bound6(IPv6 test_addr, IPv6 test_answer) {
202 202
 	print_passed(result.str());
203 203
     } else {
204 204
 	print_failed("");
205  
-	printf("Fail: answer should be %s, result was %s\n", 
  205
+	printf("Fail: answer should be %s, result was %s\n",
206 206
 	       test_answer.str().c_str(), result.str().c_str());
207 207
 	trie.print();
208 208
 	abort();
@@ -216,19 +216,22 @@ test_find_subtree()
216 216
     printf("Find subtree\n");
217 217
 
218 218
     Trie<IPv4, string> trie_subtree;
219  
-    
  219
+
220 220
     IPv4Net n1(IPv4("169.229.0.136"), 29);
221 221
     trie_subtree.insert(n1, "169.229.0.136/29");
222 222
 
223 223
     IPv4Net n2(IPv4("192.150.187.0"), 25);
224 224
     trie_subtree.insert(n2, "192.150.187.0/25");
225  
- 
  225
+
226 226
     IPv4Net n3(IPv4("192.168.254.2"), 32);
227 227
     trie_subtree.insert(n3, "192.168.254.2/32");
228 228
 
229 229
     IPv4Net n4(IPv4("192.168.254.3"), 32);
230 230
     trie_subtree.insert(n4, "192.168.254.3/32");
231 231
 
  232
+    IPv4Net n5(IPv4("192.168.254.4"), 32);
  233
+    trie_subtree.insert(n5, "192.168.254.4/32");
  234
+
232 235
     trie_subtree.print();
233 236
 
234 237
     IPv4Net nsearch1(IPv4("192.150.187.248"), 29);
@@ -241,8 +244,8 @@ test_find_subtree()
241 244
 	abort();
242 245
     }
243 246
 
244  
-    IPv4Net n5(IPv4("192.150.187.248"), 29);
245  
-    trie_subtree.insert(n5, "192.150.187.248/29");
  247
+    IPv4Net n6(IPv4("192.150.187.248"), 29);
  248
+    trie_subtree.insert(n6, "192.150.187.248/29");
246 249
 
247 250
     IPv4Net nsearch2(IPv4("192.150.187.0"), 25);
248 251
     trie_subtree.erase(n2);
@@ -256,6 +259,70 @@ test_find_subtree()
256 259
 	abort();
257 260
     }
258 261
 
  262
+    IPv4Net nsearchReally(IPv4("192.168.254.0"), 24);
  263
+    iter = trie_subtree.search_subtree(nsearchReally);
  264
+    int i = 0;
  265
+    printf("--- Results for %s\n", nsearchReally.str().c_str());
  266
+    for( ; iter != trie_subtree.end(); iter++) {
  267
+	i++;
  268
+	printf("subtree = %s\n", iter.payload().c_str());
  269
+    }
  270
+    printf("---\n");
  271
+
  272
+    if (i != 3) {
  273
+	print_failed("");
  274
+	printf("We expected three entries to be found and we found %d", i);
  275
+	abort();
  276
+    }
  277
+
  278
+    IPv4Net nsearchReally2(IPv4("192.0.0.0"), 8);
  279
+    iter = trie_subtree.search_subtree(nsearchReally2);
  280
+
  281
+    printf("--- Results for %s\n", nsearchReally2.str().c_str());
  282
+    for(i = 0; iter != trie_subtree.end(); iter++) {
  283
+	i++;
  284
+	printf("subtree = %s\n", iter.payload().c_str());
  285
+    }
  286
+    printf("---\n");
  287
+
  288
+    if (i != 4) {
  289
+	print_failed("");
  290
+	printf("We expected four entries to be found and we found %d", i);
  291
+	abort();
  292
+    }
  293
+
  294
+    IPv4Net nsearchReally3(IPv4("192.168.254.0"), 30);
  295
+    iter = trie_subtree.search_subtree(nsearchReally3);
  296
+
  297
+    printf("--- Results for %s\n", nsearchReally3.str().c_str());
  298
+    for(i = 0; iter != trie_subtree.end(); iter++) {
  299
+	i++;
  300
+	printf("subtree = %s\n", iter.payload().c_str());
  301
+    }
  302
+    printf("---\n");
  303
+
  304
+    if (i != 2) {
  305
+	print_failed("");
  306
+	printf("We expected two entries to be found and we found %d", i);
  307
+	abort();
  308
+    }
  309
+
  310
+    IPv4Net nsearchReally4(IPv4("192.168.254.4"), 31);
  311
+    iter = trie_subtree.search_subtree(nsearchReally4);
  312
+
  313
+    printf("--- Results for %s\n", nsearchReally4.str().c_str());
  314
+    for(i = 0; iter != trie_subtree.end(); iter++) {
  315
+	i++;
  316
+	printf("subtree = %s\n", iter.payload().c_str());
  317
+    }
  318
+    printf("---\n");
  319
+
  320
+    if (i != 1) {
  321
+	print_failed("");
  322
+	printf("We expected one entrie to be found and we found %d", i);
  323
+	abort();
  324
+    }
  325
+
259 326
     print_passed("");
260 327
 }
261 328
 
@@ -407,7 +474,7 @@ int main() {
407 474
     IPv4Net n9(IPv4("1.2.2.0"), 24);
408 475
     trie.insert(n9, &d9);
409 476
     trie.print();
410  
-    
  477
+
411 478
     trie.erase(n9);
412 479
 
413 480
     trie.erase(n2);
@@ -460,7 +527,7 @@ int main() {
460 527
     test_lower_bound(IPv4("1.0.0.1"), IPv4("0.0.0.0"));
461 528
     test_upper_bound(IPv4("1.3.128.1"), IPv4("255.255.255.255"));
462 529
     test_upper_bound(IPv4("1.2.2.1"), IPv4("1.2.2.255"));
463  
-    
  530
+
464 531
     trie.print();
465 532
     Trie<IPv4, IPv4RouteEntry*>::iterator iter;
466 533
     IPv4Net subroot(IPv4("1.2.0.0"), 21);
@@ -498,7 +565,7 @@ int main() {
498 565
 	iter++;
499 566
     }
500 567
 
501  
-    
  568
+
502 569
     trie.insert(n10, &d10);
503 570
     trie.insert(n1, &d1);
504 571
     trie.insert(n9, &d9);
@@ -516,7 +583,7 @@ int main() {
516 583
 	iter++;
517 584
     }
518 585
 
519  
-    //-------------------------------------------------------    
  586
+    //-------------------------------------------------------
520 587
 
521 588
     printf("Test replacement of interior node\n");
522 589
 
@@ -525,13 +592,13 @@ int main() {
525 592
     trie.insert(n13, &d13);
526 593
     trie.print();
527 594
 
528  
-    //-------------------------------------------------------    
  595
+    //-------------------------------------------------------
529 596
     printf("==================\nTest of begin()\n");
530 597
     trie.erase(n11);
531 598
     trie.erase(n10);
532 599
     trie.print();
533 600
 
534  
-    //-------------------------------------------------------    
  601
+    //-------------------------------------------------------
535 602
     printf("==================\nTest of lower_bound()\n");
536 603
     trie.print();
537 604
     iter = trie.lower_bound(n1); /*1.2.1.0/24*/
@@ -543,23 +610,23 @@ int main() {
543 610
     iter = trie.lower_bound(n13); /*1.2.2.0/23*/
544 611
     assert(iter.key() == n13);
545 612
 
546  
-    iter = trie.lower_bound(IPNet<IPv4>("1.2.1.128/25")); 
  613
+    iter = trie.lower_bound(IPNet<IPv4>("1.2.1.128/25"));
547 614
     assert(iter.key() == n1); /*1.2.1.0/24*/
548 615
 
549  
-    iter = trie.lower_bound(IPNet<IPv4>("1.2.4.128/25")); 
  616
+    iter = trie.lower_bound(IPNet<IPv4>("1.2.4.128/25"));
550 617
     assert(iter == trie.end());
551 618
 
552  
-    iter = trie.lower_bound(IPNet<IPv4>("1.2.1.0/23")); 
  619
+    iter = trie.lower_bound(IPNet<IPv4>("1.2.1.0/23"));
553 620
     assert(iter.key() == n9); /*1.2.2.0/24*/
554 621
 
555  
-    iter = trie.lower_bound(IPNet<IPv4>("1.0.0.0/24")); 
  622
+    iter = trie.lower_bound(IPNet<IPv4>("1.0.0.0/24"));
556 623
     if (iter != trie.end())
557 624
 	printf("iter.key = %s\n", iter.key().str().c_str());
558 625
     else
559 626
 	printf("iter = end\n");
560 627
     assert(iter.key() == n1); /*1.2.1.0/24*/
561 628
 
562  
-    //-------------------------------------------------------    
  629
+    //-------------------------------------------------------
563 630
 
564 631
     printf("Test /32 prefix works\n");
565 632
 
@@ -579,7 +646,7 @@ int main() {
579 646
     // inserting a list of unsorted subnets and check that the iterator
580 647
     // retrieves them in the proper order.
581 648
 
582  
-    Trie<IPv4, IPv4RouteEntry*, TriePreOrderIterator<IPv4, IPv4RouteEntry*> > 
  649
+    Trie<IPv4, IPv4RouteEntry*, TriePreOrderIterator<IPv4, IPv4RouteEntry*> >
583 650
 	preotrie;
584 651
     const char * subnets[] = {  "1.2.0.0/16",
585 652
 				"1.2.0.0/20",
@@ -611,7 +678,7 @@ int main() {
611 678
     printf("adding n20: %s route: %p\n", n20.str().c_str(), &d20);
612 679
     preotrie.insert(n20, &d20);
613 680
 
614  
-    //-------------------------------------------------------    
  681
+    //-------------------------------------------------------
615 682
     printf("-----------\n");
616 683
     printf("Test of prefix increment (++ti)\n");
617 684
     printf("-----------\n");
@@ -636,11 +703,11 @@ int main() {
636 703
     }
637 704
     print_passed("");
638 705
 
639  
-    //-------------------------------------------------------    
  706
+    //-------------------------------------------------------
640 707
     printf("-----------\n");
641 708
     printf("Test of postfix increment (ti++)\n");
642 709
     printf("-----------\n");
643  
-    subnetidx = 0;     
  710
+    subnetidx = 0;
644 711
     for (ti = preotrie.begin() ; ti != preotrie.end() ; ++ti) {
645 712
         printf("*** node: %-26s %s\n",
646 713
                ti.cur()->k().str().c_str(),
47  xorp/libxorp/trie.hh
@@ -244,6 +244,8 @@ public:
244 244
 		lo = x->high(); ++lo;
245 245
 		hi = n->_right->low(); --hi;
246 246
 	    } else if (a <= n->_right->_k.top_addr()) {	// case 4:
  247
+		if (n->_left && a > n->_left->_k.top_addr())
  248
+		    lo = n->_left->high(); ++lo;
247 249
 		n = n->_right; // and continue
248 250
 	    } else {					// case 5:
249 251
 		lo = n->_right->high(); ++lo;
@@ -384,6 +386,10 @@ public:
384 386
 	return (_cur == x._cur);
385 387
     }
386 388
 
  389
+    bool operator!=(const TriePostOrderIterator & x) const {
  390
+	return (_cur != x._cur);
  391
+    }
  392
+
387 393
     bool has_payload() const		{ return _cur->has_payload(); }
388 394
     Payload & payload()			{ return _cur->p(); };
389 395
     const Payload & payload() const	{ return _cur->p(); };
@@ -483,6 +489,10 @@ public:
483 489
 	return (_cur == x._cur);
484 490
     }
485 491
 
  492
+    bool operator!=(const TriePreOrderIterator & x) const {
  493
+	return (_cur != x._cur);
  494
+    }
  495
+
486 496
     bool has_payload() const		{ return _cur->has_payload(); }
487 497
     Payload & payload()			{ return _cur->p(); };
488 498
     const Payload & payload() const	{ return _cur->p(); };
@@ -532,11 +542,14 @@ public:
532 542
     iterator insert(const Key & net, const Payload& p) {
533 543
 	bool replaced = false;
534 544
 	Node *out = Node::insert(&_root, net, p, replaced);
535  
-	if (replaced) {
536  
-	    fprintf(stderr, "overwriting a full node"); //XXX
537  
-	} else {
  545
+	if (!replaced) {
538 546
 	    _payload_count++;
539 547
 	}
  548
+#ifdef DEBUG_LOGGING
  549
+	else {
  550
+	    fprintf(stderr, "overwriting a full node"); //XXX
  551
+	}
  552
+#endif
540 553
 	return iterator(out);
541 554
     }
542 555
 
@@ -661,7 +674,8 @@ public:
661 674
     }
662 675
 
663 676
 #endif // compatibility
664  
-    int route_count() const			{ return _payload_count; }
  677
+    int route_count() const			{ return static_cast<int>(_payload_count); }
  678
+    size_t size() const				{ return _payload_count; }
665 679
 
666 680
     bool empty() const				{ return (_payload_count == 0); }
667 681
 
@@ -674,7 +688,7 @@ private:
674 688
     }
675 689
 
676 690
     Node	*_root;
677  
-    int		_payload_count;
  691
+    size_t	_payload_count;
678 692
 };
679 693
 
680 694
 
@@ -853,13 +867,13 @@ TrieNode<A, Payload>::erase()
853 867
  * that contains the desired key and has a Payload
854 868
  */
855 869
 template <class A, class Payload>
856  
-TrieNode<A, Payload> *
  870
+inline TrieNode<A, Payload> *
857 871
 TrieNode<A,Payload>::find(const Key &key)
858 872
 {
859 873
     TrieNode * cand = NULL;
860 874
     TrieNode * r = this;
861 875
 
862  
-    for ( ; r && r->_k.contains(key) ; ) {
  876
+    while(r && r->_k.contains(key)) {
863 877
 	if (r->_p)
864 878
 	    cand = r;		// we have a candidate.
865 879
 	if (r->_left && r->_left->_k.contains(key))
@@ -930,13 +944,24 @@ TrieNode<A,Payload>::find_subtree(const Key &key)
930 944
     TrieNode *cand = r && key.contains(r->_k) ? r : NULL;
931 945
 
932 946
     for ( ; r && r->_k.contains(key) ; ) {
933  
-	if (key.contains(r->_k))
934  
-	    cand = r;		// we have a candidate.
  947
+	if (key.contains(r->_k)) {
  948
+	    cand = r;			// we have a candidate.
  949
+	    break;			// and we don't need to search any more!
  950
+	}
935 951
 	if (r->_left && r->_left->_k.contains(key))
936 952
 	    r = r->_left;
937  
-	else			// should check that right contains(key), but
938  
-	    r = r->_right;	// the loop condition will do it for us.
  953
+	else if (r->_right && r->_right->_k.contains(key))
  954
+	    r = r->_right;
  955
+	else if (r->_left && key.contains(r->_left->_k)) {
  956
+	    cand = r->_left;
  957
+	    break;
  958
+	} else if (r->_right && key.contains(r->_right->_k)) {
  959
+	    cand = r->_right;
  960
+	    break;
  961
+	} else
  962
+	    break;
939 963
     }
  964
+
940 965
     return cand;
941 966
 }
942 967
 
6  xorp/libxorp/xlog.h
@@ -345,6 +345,9 @@ void _xlog_with_level(int log_level,
345 345
  #define XLOG_RTRMGR_ONLY_NO_PREAMBLE(fmt...)	do{}while(0)
346 346
 #endif    
347 347
 
  348
+#ifdef NO_ASSERT
  349
+#define XLOG_ASSERT(assertion) do {} while(0)
  350
+#else
348 351
 #ifdef L_ASSERT
349 352
 /**
350 353
  * XORP replacement for assert(3).
@@ -362,7 +365,8 @@ void _xlog_with_level(int log_level,
362 365
  } while (0)
363 366
 #else
364 367
 # define XLOG_ASSERT(assertion)	assert(assertion)
365  
-#endif
  368
+#endif /* L_ASSERT */
  369
+#endif /* NO_ASSERT */
366 370
 
367 371
 /**
368 372
  * A marker that can be used to indicate code that should never be executed.
3  xorp/policy/backend/policy_redist_map.cc
@@ -35,6 +35,9 @@ PolicyRedistMap::~PolicyRedistMap() {
35 35
 void
36 36
 PolicyRedistMap::remove(const string& protocol)
37 37
 {
  38
+    Map::iterator i = _map.find(protocol);
  39
+    if (i != _map.end())
  40
+	delete i->second;
38 41
     _map.erase(protocol);
39 42
 }
40 43
 
2  xorp/rib/SConscript
@@ -110,8 +110,6 @@ libxorp_rib_srcs = [
110 110
 	     'rt_tab_base.cc',
111 111
 	     'rt_tab_deletion.cc',
112 112
 	     'rt_tab_extint.cc',
113  
-	     'rt_tab_log.cc',
114  
-	     'rt_tab_merged.cc',
115 113
 	     'rt_tab_origin.cc',
116 114
 	     'rt_tab_pol_conn.cc',
117 115
 	     'rt_tab_pol_redist.cc',