]> git.puffer.fish Git - mirror/frr.git/commitdiff
bgpd: Replace peer->ibuf_scratch 14077/head
authorDonald Sharp <sharpd@nvidia.com>
Fri, 21 Jul 2023 17:10:03 +0000 (13:10 -0400)
committerMergify <37929162+mergify[bot]@users.noreply.github.com>
Fri, 21 Jul 2023 20:15:19 +0000 (20:15 +0000)
The peer->ibuf_scratch was allocating 65535 * 10 bytes
for scratch space to hold data incoming from a read
from a peer.  When you have 4k peers this is 262,1400,000
or 262 mb of data.  Which is crazy large.  Especially
since the i/o pthread is reading per peer without
any chance of having the data interfere with other reads.

Signed-off-by: Donald Sharp <sharpd@nvidia.com>
(cherry picked from commit bdc17624059c1722e5208523cb06fe9b0ed7acb2)

bgpd/bgp_io.c
bgpd/bgpd.h

index e9178fd8fccda37974f6fb002c086854e478dec6..215554af3ead0245cfd95be2930cdddf26750387 100644 (file)
@@ -480,6 +480,7 @@ done : {
        return status;
 }
 
+uint8_t ibuf_scratch[BGP_EXTENDED_MESSAGE_MAX_PACKET_SIZE * BGP_READ_PACKET_MAX];
 /*
  * Reads a chunk of data from peer->fd into peer->ibuf_work.
  *
@@ -487,6 +488,10 @@ done : {
  *    Pointer to location to store FSM event code in case of fatal error.
  *
  * @return status flag (see top-of-file)
+ *
+ * PLEASE NOTE:  If we ever transform the bgp_read to be a pthread
+ * per peer then we need to rethink the global ibuf_scratch
+ * data structure above.
  */
 static uint16_t bgp_read(struct peer *peer, int *code_p)
 {
@@ -502,9 +507,9 @@ static uint16_t bgp_read(struct peer *peer, int *code_p)
                return status;
        }
 
-       readsize = MIN(ibuf_work_space, sizeof(peer->ibuf_scratch));
+       readsize = MIN(ibuf_work_space, sizeof(ibuf_scratch));
 
-       nbytes = read(peer->fd, peer->ibuf_scratch, readsize);
+       nbytes = read(peer->fd, ibuf_scratch, readsize);
 
        /* EAGAIN or EWOULDBLOCK; come back later */
        if (nbytes < 0 && ERRNO_IO_RETRY(errno)) {
@@ -533,8 +538,8 @@ static uint16_t bgp_read(struct peer *peer, int *code_p)
 
                SET_FLAG(status, BGP_IO_FATAL_ERR);
        } else {
-               assert(ringbuf_put(peer->ibuf_work, peer->ibuf_scratch, nbytes)
-                      == (size_t)nbytes);
+               assert(ringbuf_put(peer->ibuf_work, ibuf_scratch, nbytes) ==
+                      (size_t)nbytes);
        }
 
        return status;
index c3b806c6dc5921aa278ba66b75ca8d495a17850d..5e443ca5c970bc60aa2786d95621a0a51ce2a957 100644 (file)
@@ -1150,9 +1150,6 @@ struct peer {
        struct stream_fifo *ibuf; // packets waiting to be processed
        struct stream_fifo *obuf; // packets waiting to be written
 
-       /* used as a block to deposit raw wire data to */
-       uint8_t ibuf_scratch[BGP_EXTENDED_MESSAGE_MAX_PACKET_SIZE
-                            * BGP_READ_PACKET_MAX];
        struct ringbuf *ibuf_work; // WiP buffer used by bgp_read() only
 
        struct stream *curr; // the current packet being parsed