Annotation of embedaddon/quagga/lib/zclient.c, revision 1.1.1.1

1.1       misho       1: /* Zebra's client library.
                      2:  * Copyright (C) 1999 Kunihiro Ishiguro
                      3:  * Copyright (C) 2005 Andrew J. Schorr
                      4:  *
                      5:  * This file is part of GNU Zebra.
                      6:  *
                      7:  * GNU Zebra is free software; you can redistribute it and/or modify
                      8:  * it under the terms of the GNU General Public License as published
                      9:  * by the Free Software Foundation; either version 2, or (at your
                     10:  * option) any later version.
                     11:  *
                     12:  * GNU Zebra 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.  See the GNU
                     15:  * General Public License for more details.
                     16:  *
                     17:  * You should have received a copy of the GNU General Public License
                     18:  * along with GNU Zebra; see the file COPYING.  If not, write to the
                     19:  * Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
                     20:  * MA 02111-1307, USA.
                     21:  */
                     22: 
                     23: #include <zebra.h>
                     24: 
                     25: #include "prefix.h"
                     26: #include "stream.h"
                     27: #include "buffer.h"
                     28: #include "network.h"
                     29: #include "if.h"
                     30: #include "log.h"
                     31: #include "thread.h"
                     32: #include "zclient.h"
                     33: #include "memory.h"
                     34: #include "table.h"
                     35: 
                     36: /* Zebra client events. */
                     37: enum event {ZCLIENT_SCHEDULE, ZCLIENT_READ, ZCLIENT_CONNECT};
                     38: 
                     39: /* Prototype for event manager. */
                     40: static void zclient_event (enum event, struct zclient *);
                     41: 
                     42: extern struct thread_master *master;
                     43: 
                     44: /* This file local debug flag. */
                     45: int zclient_debug = 0;
                     46: 
                     47: /* Allocate zclient structure. */
                     48: struct zclient *
                     49: zclient_new ()
                     50: {
                     51:   struct zclient *zclient;
                     52:   zclient = XCALLOC (MTYPE_ZCLIENT, sizeof (struct zclient));
                     53: 
                     54:   zclient->ibuf = stream_new (ZEBRA_MAX_PACKET_SIZ);
                     55:   zclient->obuf = stream_new (ZEBRA_MAX_PACKET_SIZ);
                     56:   zclient->wb = buffer_new(0);
                     57: 
                     58:   return zclient;
                     59: }
                     60: 
                     61: /* This function is only called when exiting, because
                     62:    many parts of the code do not check for I/O errors, so they could
                     63:    reference an invalid pointer if the structure was ever freed.
                     64: 
                     65:    Free zclient structure. */
                     66: void
                     67: zclient_free (struct zclient *zclient)
                     68: {
                     69:   if (zclient->ibuf)
                     70:     stream_free(zclient->ibuf);
                     71:   if (zclient->obuf)
                     72:     stream_free(zclient->obuf);
                     73:   if (zclient->wb)
                     74:     buffer_free(zclient->wb);
                     75: 
                     76:   XFREE (MTYPE_ZCLIENT, zclient);
                     77: }
                     78: 
                     79: /* Initialize zebra client.  Argument redist_default is unwanted
                     80:    redistribute route type. */
                     81: void
                     82: zclient_init (struct zclient *zclient, int redist_default)
                     83: {
                     84:   int i;
                     85:   
                     86:   /* Enable zebra client connection by default. */
                     87:   zclient->enable = 1;
                     88: 
                     89:   /* Set -1 to the default socket value. */
                     90:   zclient->sock = -1;
                     91: 
                     92:   /* Clear redistribution flags. */
                     93:   for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
                     94:     zclient->redist[i] = 0;
                     95: 
                     96:   /* Set unwanted redistribute route.  bgpd does not need BGP route
                     97:      redistribution. */
                     98:   zclient->redist_default = redist_default;
                     99:   zclient->redist[redist_default] = 1;
                    100: 
                    101:   /* Set default-information redistribute to zero. */
                    102:   zclient->default_information = 0;
                    103: 
                    104:   /* Schedule first zclient connection. */
                    105:   if (zclient_debug)
                    106:     zlog_debug ("zclient start scheduled");
                    107: 
                    108:   zclient_event (ZCLIENT_SCHEDULE, zclient);
                    109: }
                    110: 
                    111: /* Stop zebra client services. */
                    112: void
                    113: zclient_stop (struct zclient *zclient)
                    114: {
                    115:   if (zclient_debug)
                    116:     zlog_debug ("zclient stopped");
                    117: 
                    118:   /* Stop threads. */
                    119:   THREAD_OFF(zclient->t_read);
                    120:   THREAD_OFF(zclient->t_connect);
                    121:   THREAD_OFF(zclient->t_write);
                    122: 
                    123:   /* Reset streams. */
                    124:   stream_reset(zclient->ibuf);
                    125:   stream_reset(zclient->obuf);
                    126: 
                    127:   /* Empty the write buffer. */
                    128:   buffer_reset(zclient->wb);
                    129: 
                    130:   /* Close socket. */
                    131:   if (zclient->sock >= 0)
                    132:     {
                    133:       close (zclient->sock);
                    134:       zclient->sock = -1;
                    135:     }
                    136:   zclient->fail = 0;
                    137: }
                    138: 
                    139: void
                    140: zclient_reset (struct zclient *zclient)
                    141: {
                    142:   zclient_stop (zclient);
                    143:   zclient_init (zclient, zclient->redist_default);
                    144: }
                    145: 
                    146: /* Make socket to zebra daemon. Return zebra socket. */
                    147: int
                    148: zclient_socket(void)
                    149: {
                    150:   int sock;
                    151:   int ret;
                    152:   struct sockaddr_in serv;
                    153: 
                    154:   /* We should think about IPv6 connection. */
                    155:   sock = socket (AF_INET, SOCK_STREAM, 0);
                    156:   if (sock < 0)
                    157:     return -1;
                    158:   
                    159:   /* Make server socket. */ 
                    160:   memset (&serv, 0, sizeof (struct sockaddr_in));
                    161:   serv.sin_family = AF_INET;
                    162:   serv.sin_port = htons (ZEBRA_PORT);
                    163: #ifdef HAVE_STRUCT_SOCKADDR_IN_SIN_LEN
                    164:   serv.sin_len = sizeof (struct sockaddr_in);
                    165: #endif /* HAVE_STRUCT_SOCKADDR_IN_SIN_LEN */
                    166:   serv.sin_addr.s_addr = htonl (INADDR_LOOPBACK);
                    167: 
                    168:   /* Connect to zebra. */
                    169:   ret = connect (sock, (struct sockaddr *) &serv, sizeof (serv));
                    170:   if (ret < 0)
                    171:     {
                    172:       close (sock);
                    173:       return -1;
                    174:     }
                    175:   return sock;
                    176: }
                    177: 
                    178: /* For sockaddr_un. */
                    179: #include <sys/un.h>
                    180: 
                    181: int
                    182: zclient_socket_un (const char *path)
                    183: {
                    184:   int ret;
                    185:   int sock, len;
                    186:   struct sockaddr_un addr;
                    187: 
                    188:   sock = socket (AF_UNIX, SOCK_STREAM, 0);
                    189:   if (sock < 0)
                    190:     return -1;
                    191:   
                    192:   /* Make server socket. */ 
                    193:   memset (&addr, 0, sizeof (struct sockaddr_un));
                    194:   addr.sun_family = AF_UNIX;
                    195:   strncpy (addr.sun_path, path, strlen (path));
                    196: #ifdef HAVE_STRUCT_SOCKADDR_UN_SUN_LEN
                    197:   len = addr.sun_len = SUN_LEN(&addr);
                    198: #else
                    199:   len = sizeof (addr.sun_family) + strlen (addr.sun_path);
                    200: #endif /* HAVE_STRUCT_SOCKADDR_UN_SUN_LEN */
                    201: 
                    202:   ret = connect (sock, (struct sockaddr *) &addr, len);
                    203:   if (ret < 0)
                    204:     {
                    205:       close (sock);
                    206:       return -1;
                    207:     }
                    208:   return sock;
                    209: }
                    210: 
                    211: static int
                    212: zclient_failed(struct zclient *zclient)
                    213: {
                    214:   zclient->fail++;
                    215:   zclient_stop(zclient);
                    216:   zclient_event(ZCLIENT_CONNECT, zclient);
                    217:   return -1;
                    218: }
                    219: 
                    220: static int
                    221: zclient_flush_data(struct thread *thread)
                    222: {
                    223:   struct zclient *zclient = THREAD_ARG(thread);
                    224: 
                    225:   zclient->t_write = NULL;
                    226:   if (zclient->sock < 0)
                    227:     return -1;
                    228:   switch (buffer_flush_available(zclient->wb, zclient->sock))
                    229:     {
                    230:     case BUFFER_ERROR:
                    231:       zlog_warn("%s: buffer_flush_available failed on zclient fd %d, closing",
                    232:                __func__, zclient->sock);
                    233:       return zclient_failed(zclient);
                    234:       break;
                    235:     case BUFFER_PENDING:
                    236:       zclient->t_write = thread_add_write(master, zclient_flush_data,
                    237:                                          zclient, zclient->sock);
                    238:       break;
                    239:     case BUFFER_EMPTY:
                    240:       break;
                    241:     }
                    242:   return 0;
                    243: }
                    244: 
                    245: int
                    246: zclient_send_message(struct zclient *zclient)
                    247: {
                    248:   if (zclient->sock < 0)
                    249:     return -1;
                    250:   switch (buffer_write(zclient->wb, zclient->sock, STREAM_DATA(zclient->obuf),
                    251:                       stream_get_endp(zclient->obuf)))
                    252:     {
                    253:     case BUFFER_ERROR:
                    254:       zlog_warn("%s: buffer_write failed to zclient fd %d, closing",
                    255:                 __func__, zclient->sock);
                    256:       return zclient_failed(zclient);
                    257:       break;
                    258:     case BUFFER_EMPTY:
                    259:       THREAD_OFF(zclient->t_write);
                    260:       break;
                    261:     case BUFFER_PENDING:
                    262:       THREAD_WRITE_ON(master, zclient->t_write,
                    263:                      zclient_flush_data, zclient, zclient->sock);
                    264:       break;
                    265:     }
                    266:   return 0;
                    267: }
                    268: 
                    269: void
                    270: zclient_create_header (struct stream *s, uint16_t command)
                    271: {
                    272:   /* length placeholder, caller can update */
                    273:   stream_putw (s, ZEBRA_HEADER_SIZE);
                    274:   stream_putc (s, ZEBRA_HEADER_MARKER);
                    275:   stream_putc (s, ZSERV_VERSION);
                    276:   stream_putw (s, command);
                    277: }
                    278: 
                    279: /* Send simple Zebra message. */
                    280: static int
                    281: zebra_message_send (struct zclient *zclient, int command)
                    282: {
                    283:   struct stream *s;
                    284: 
                    285:   /* Get zclient output buffer. */
                    286:   s = zclient->obuf;
                    287:   stream_reset (s);
                    288: 
                    289:   /* Send very simple command only Zebra message. */
                    290:   zclient_create_header (s, command);
                    291:   
                    292:   return zclient_send_message(zclient);
                    293: }
                    294: 
                    295: /* Make connection to zebra daemon. */
                    296: int
                    297: zclient_start (struct zclient *zclient)
                    298: {
                    299:   int i;
                    300: 
                    301:   if (zclient_debug)
                    302:     zlog_debug ("zclient_start is called");
                    303: 
                    304:   /* zclient is disabled. */
                    305:   if (! zclient->enable)
                    306:     return 0;
                    307: 
                    308:   /* If already connected to the zebra. */
                    309:   if (zclient->sock >= 0)
                    310:     return 0;
                    311: 
                    312:   /* Check connect thread. */
                    313:   if (zclient->t_connect)
                    314:     return 0;
                    315: 
                    316:   /* Make socket. */
                    317: #ifdef HAVE_TCP_ZEBRA
                    318:   zclient->sock = zclient_socket ();
                    319: #else
                    320:   zclient->sock = zclient_socket_un (ZEBRA_SERV_PATH);
                    321: #endif /* HAVE_TCP_ZEBRA */
                    322:   if (zclient->sock < 0)
                    323:     {
                    324:       if (zclient_debug)
                    325:        zlog_debug ("zclient connection fail");
                    326:       zclient->fail++;
                    327:       zclient_event (ZCLIENT_CONNECT, zclient);
                    328:       return -1;
                    329:     }
                    330: 
                    331:   if (set_nonblocking(zclient->sock) < 0)
                    332:     zlog_warn("%s: set_nonblocking(%d) failed", __func__, zclient->sock);
                    333: 
                    334:   /* Clear fail count. */
                    335:   zclient->fail = 0;
                    336:   if (zclient_debug)
                    337:     zlog_debug ("zclient connect success with socket [%d]", zclient->sock);
                    338:       
                    339:   /* Create read thread. */
                    340:   zclient_event (ZCLIENT_READ, zclient);
                    341: 
                    342:   /* We need router-id information. */
                    343:   zebra_message_send (zclient, ZEBRA_ROUTER_ID_ADD);
                    344: 
                    345:   /* We need interface information. */
                    346:   zebra_message_send (zclient, ZEBRA_INTERFACE_ADD);
                    347: 
                    348:   /* Flush all redistribute request. */
                    349:   for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
                    350:     if (i != zclient->redist_default && zclient->redist[i])
                    351:       zebra_redistribute_send (ZEBRA_REDISTRIBUTE_ADD, zclient, i);
                    352: 
                    353:   /* If default information is needed. */
                    354:   if (zclient->default_information)
                    355:     zebra_message_send (zclient, ZEBRA_REDISTRIBUTE_DEFAULT_ADD);
                    356: 
                    357:   return 0;
                    358: }
                    359: 
                    360: /* This function is a wrapper function for calling zclient_start from
                    361:    timer or event thread. */
                    362: static int
                    363: zclient_connect (struct thread *t)
                    364: {
                    365:   struct zclient *zclient;
                    366: 
                    367:   zclient = THREAD_ARG (t);
                    368:   zclient->t_connect = NULL;
                    369: 
                    370:   if (zclient_debug)
                    371:     zlog_debug ("zclient_connect is called");
                    372: 
                    373:   return zclient_start (zclient);
                    374: }
                    375: 
                    376:  /* 
                    377:   * "xdr_encode"-like interface that allows daemon (client) to send
                    378:   * a message to zebra server for a route that needs to be
                    379:   * added/deleted to the kernel. Info about the route is specified
                    380:   * by the caller in a struct zapi_ipv4. zapi_ipv4_read() then writes
                    381:   * the info down the zclient socket using the stream_* functions.
                    382:   * 
                    383:   * The corresponding read ("xdr_decode") function on the server
                    384:   * side is zread_ipv4_add()/zread_ipv4_delete().
                    385:   *
                    386:   *  0 1 2 3 4 5 6 7 8 9 A B C D E F 0 1 2 3 4 5 6 7 8 9 A B C D E F
                    387:   * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    388:   * |            Length (2)         |    Command    | Route Type    |
                    389:   * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    390:   * | ZEBRA Flags   | Message Flags | Prefix length |
                    391:   * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    392:   * | Destination IPv4 Prefix for route                             |
                    393:   * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    394:   * | Nexthop count | 
                    395:   * +-+-+-+-+-+-+-+-+
                    396:   *
                    397:   * 
                    398:   * A number of IPv4 nexthop(s) or nexthop interface index(es) are then 
                    399:   * described, as per the Nexthop count. Each nexthop described as:
                    400:   *
                    401:   * +-+-+-+-+-+-+-+-+
                    402:   * | Nexthop Type  |  Set to one of ZEBRA_NEXTHOP_*
                    403:   * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    404:   * |       IPv4 Nexthop address or Interface Index number          |
                    405:   * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    406:   *
                    407:   * Alternatively, if the flags field has ZEBRA_FLAG_BLACKHOLE or
                    408:   * ZEBRA_FLAG_REJECT is set then Nexthop count is set to 1, then _no_ 
                    409:   * nexthop information is provided, and the message describes a prefix
                    410:   * to blackhole or reject route.
                    411:   *
                    412:   * If ZAPI_MESSAGE_DISTANCE is set, the distance value is written as a 1
                    413:   * byte value.
                    414:   * 
                    415:   * If ZAPI_MESSAGE_METRIC is set, the metric value is written as an 8
                    416:   * byte value.
                    417:   *
                    418:   * XXX: No attention paid to alignment.
                    419:   */ 
                    420: int
                    421: zapi_ipv4_route (u_char cmd, struct zclient *zclient, struct prefix_ipv4 *p,
                    422:                  struct zapi_ipv4 *api)
                    423: {
                    424:   int i;
                    425:   int psize;
                    426:   struct stream *s;
                    427: 
                    428:   /* Reset stream. */
                    429:   s = zclient->obuf;
                    430:   stream_reset (s);
                    431:   
                    432:   zclient_create_header (s, cmd);
                    433:   
                    434:   /* Put type and nexthop. */
                    435:   stream_putc (s, api->type);
                    436:   stream_putc (s, api->flags);
                    437:   stream_putc (s, api->message);
                    438: 
                    439:   /* Put prefix information. */
                    440:   psize = PSIZE (p->prefixlen);
                    441:   stream_putc (s, p->prefixlen);
                    442:   stream_write (s, (u_char *) & p->prefix, psize);
                    443: 
                    444:   /* Nexthop, ifindex, distance and metric information. */
                    445:   if (CHECK_FLAG (api->message, ZAPI_MESSAGE_NEXTHOP))
                    446:     {
                    447:       if (CHECK_FLAG (api->flags, ZEBRA_FLAG_BLACKHOLE))
                    448:         {
                    449:           stream_putc (s, 1);
                    450:           stream_putc (s, ZEBRA_NEXTHOP_BLACKHOLE);
                    451:           /* XXX assert(api->nexthop_num == 0); */
                    452:           /* XXX assert(api->ifindex_num == 0); */
                    453:         }
                    454:       else
                    455:         stream_putc (s, api->nexthop_num + api->ifindex_num);
                    456: 
                    457:       for (i = 0; i < api->nexthop_num; i++)
                    458:         {
                    459:           stream_putc (s, ZEBRA_NEXTHOP_IPV4);
                    460:           stream_put_in_addr (s, api->nexthop[i]);
                    461:         }
                    462:       for (i = 0; i < api->ifindex_num; i++)
                    463:         {
                    464:           stream_putc (s, ZEBRA_NEXTHOP_IFINDEX);
                    465:           stream_putl (s, api->ifindex[i]);
                    466:         }
                    467:     }
                    468: 
                    469:   if (CHECK_FLAG (api->message, ZAPI_MESSAGE_DISTANCE))
                    470:     stream_putc (s, api->distance);
                    471:   if (CHECK_FLAG (api->message, ZAPI_MESSAGE_METRIC))
                    472:     stream_putl (s, api->metric);
                    473: 
                    474:   /* Put length at the first point of the stream. */
                    475:   stream_putw_at (s, 0, stream_get_endp (s));
                    476: 
                    477:   return zclient_send_message(zclient);
                    478: }
                    479: 
                    480: #ifdef HAVE_IPV6
                    481: int
                    482: zapi_ipv6_route (u_char cmd, struct zclient *zclient, struct prefix_ipv6 *p,
                    483:               struct zapi_ipv6 *api)
                    484: {
                    485:   int i;
                    486:   int psize;
                    487:   struct stream *s;
                    488: 
                    489:   /* Reset stream. */
                    490:   s = zclient->obuf;
                    491:   stream_reset (s);
                    492: 
                    493:   zclient_create_header (s, cmd);
                    494: 
                    495:   /* Put type and nexthop. */
                    496:   stream_putc (s, api->type);
                    497:   stream_putc (s, api->flags);
                    498:   stream_putc (s, api->message);
                    499:   
                    500:   /* Put prefix information. */
                    501:   psize = PSIZE (p->prefixlen);
                    502:   stream_putc (s, p->prefixlen);
                    503:   stream_write (s, (u_char *)&p->prefix, psize);
                    504: 
                    505:   /* Nexthop, ifindex, distance and metric information. */
                    506:   if (CHECK_FLAG (api->message, ZAPI_MESSAGE_NEXTHOP))
                    507:     {
                    508:       stream_putc (s, api->nexthop_num + api->ifindex_num);
                    509: 
                    510:       for (i = 0; i < api->nexthop_num; i++)
                    511:        {
                    512:          stream_putc (s, ZEBRA_NEXTHOP_IPV6);
                    513:          stream_write (s, (u_char *)api->nexthop[i], 16);
                    514:        }
                    515:       for (i = 0; i < api->ifindex_num; i++)
                    516:        {
                    517:          stream_putc (s, ZEBRA_NEXTHOP_IFINDEX);
                    518:          stream_putl (s, api->ifindex[i]);
                    519:        }
                    520:     }
                    521: 
                    522:   if (CHECK_FLAG (api->message, ZAPI_MESSAGE_DISTANCE))
                    523:     stream_putc (s, api->distance);
                    524:   if (CHECK_FLAG (api->message, ZAPI_MESSAGE_METRIC))
                    525:     stream_putl (s, api->metric);
                    526: 
                    527:   /* Put length at the first point of the stream. */
                    528:   stream_putw_at (s, 0, stream_get_endp (s));
                    529: 
                    530:   return zclient_send_message(zclient);
                    531: }
                    532: #endif /* HAVE_IPV6 */
                    533: 
                    534: /* 
                    535:  * send a ZEBRA_REDISTRIBUTE_ADD or ZEBRA_REDISTRIBUTE_DELETE
                    536:  * for the route type (ZEBRA_ROUTE_KERNEL etc.). The zebra server will
                    537:  * then set/unset redist[type] in the client handle (a struct zserv) for the 
                    538:  * sending client
                    539:  */
                    540: int
                    541: zebra_redistribute_send (int command, struct zclient *zclient, int type)
                    542: {
                    543:   struct stream *s;
                    544: 
                    545:   s = zclient->obuf;
                    546:   stream_reset(s);
                    547:   
                    548:   zclient_create_header (s, command);
                    549:   stream_putc (s, type);
                    550:   
                    551:   stream_putw_at (s, 0, stream_get_endp (s));
                    552:   
                    553:   return zclient_send_message(zclient);
                    554: }
                    555: 
                    556: /* Router-id update from zebra daemon. */
                    557: void
                    558: zebra_router_id_update_read (struct stream *s, struct prefix *rid)
                    559: {
                    560:   int plen;
                    561: 
                    562:   /* Fetch interface address. */
                    563:   rid->family = stream_getc (s);
                    564: 
                    565:   plen = prefix_blen (rid);
                    566:   stream_get (&rid->u.prefix, s, plen);
                    567:   rid->prefixlen = stream_getc (s);
                    568: }
                    569: 
                    570: /* Interface addition from zebra daemon. */
                    571: /*  
                    572:  * The format of the message sent with type ZEBRA_INTERFACE_ADD or
                    573:  * ZEBRA_INTERFACE_DELETE from zebra to the client is:
                    574:  *     0                   1                   2                   3
                    575:  *  0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
                    576:  * +-+-+-+-+-+-+-+-+
                    577:  * |   type        |
                    578:  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    579:  * |  ifname                                                       |
                    580:  * |                                                               |
                    581:  * |                                                               |
                    582:  * |                                                               |
                    583:  * |                                                               |
                    584:  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    585:  * |         ifindex                                               |
                    586:  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    587:  * |         if_flags                                              |
                    588:  * |                                                               |
                    589:  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    590:  * |         metric                                                |
                    591:  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    592:  * |         ifmtu                                                 |
                    593:  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    594:  * |         ifmtu6                                                |
                    595:  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    596:  * |         bandwidth                                             |
                    597:  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    598:  * |         sockaddr_dl                                           |
                    599:  * +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
                    600:  */
                    601: 
                    602: struct interface *
                    603: zebra_interface_add_read (struct stream *s)
                    604: {
                    605:   struct interface *ifp;
                    606:   char ifname_tmp[INTERFACE_NAMSIZ];
                    607: 
                    608:   /* Read interface name. */
                    609:   stream_get (ifname_tmp, s, INTERFACE_NAMSIZ);
                    610: 
                    611:   /* Lookup/create interface by name. */
                    612:   ifp = if_get_by_name_len (ifname_tmp, strnlen(ifname_tmp, INTERFACE_NAMSIZ));
                    613: 
                    614:   /* Read interface's index. */
                    615:   ifp->ifindex = stream_getl (s);
                    616: 
                    617:   /* Read interface's value. */
                    618:   ifp->status = stream_getc (s);
                    619:   ifp->flags = stream_getq (s);
                    620:   ifp->metric = stream_getl (s);
                    621:   ifp->mtu = stream_getl (s);
                    622:   ifp->mtu6 = stream_getl (s);
                    623:   ifp->bandwidth = stream_getl (s);
                    624: #ifdef HAVE_STRUCT_SOCKADDR_DL
                    625:   stream_get (&ifp->sdl, s, sizeof (ifp->sdl));
                    626: #else
                    627:   ifp->hw_addr_len = stream_getl (s);
                    628:   if (ifp->hw_addr_len)
                    629:     stream_get (ifp->hw_addr, s, ifp->hw_addr_len);
                    630: #endif /* HAVE_STRUCT_SOCKADDR_DL */
                    631:   
                    632:   return ifp;
                    633: }
                    634: 
                    635: /* 
                    636:  * Read interface up/down msg (ZEBRA_INTERFACE_UP/ZEBRA_INTERFACE_DOWN)
                    637:  * from zebra server.  The format of this message is the same as
                    638:  * that sent for ZEBRA_INTERFACE_ADD/ZEBRA_INTERFACE_DELETE (see
                    639:  * comments for zebra_interface_add_read), except that no sockaddr_dl
                    640:  * is sent at the tail of the message.
                    641:  */
                    642: struct interface *
                    643: zebra_interface_state_read (struct stream *s)
                    644: {
                    645:   struct interface *ifp;
                    646:   char ifname_tmp[INTERFACE_NAMSIZ];
                    647: 
                    648:   /* Read interface name. */
                    649:   stream_get (ifname_tmp, s, INTERFACE_NAMSIZ);
                    650: 
                    651:   /* Lookup this by interface index. */
                    652:   ifp = if_lookup_by_name_len (ifname_tmp,
                    653:                               strnlen(ifname_tmp, INTERFACE_NAMSIZ));
                    654: 
                    655:   /* If such interface does not exist, indicate an error */
                    656:   if (! ifp)
                    657:      return NULL;
                    658: 
                    659:   /* Read interface's index. */
                    660:   ifp->ifindex = stream_getl (s);
                    661: 
                    662:   /* Read interface's value. */
                    663:   ifp->status = stream_getc (s);
                    664:   ifp->flags = stream_getq (s);
                    665:   ifp->metric = stream_getl (s);
                    666:   ifp->mtu = stream_getl (s);
                    667:   ifp->mtu6 = stream_getl (s);
                    668:   ifp->bandwidth = stream_getl (s);
                    669: 
                    670:   return ifp;
                    671: }
                    672: 
                    673: /* 
                    674:  * format of message for address additon is:
                    675:  *    0
                    676:  *  0 1 2 3 4 5 6 7
                    677:  * +-+-+-+-+-+-+-+-+
                    678:  * |   type        |  ZEBRA_INTERFACE_ADDRESS_ADD or
                    679:  * +-+-+-+-+-+-+-+-+  ZEBRA_INTERFACE_ADDRES_DELETE
                    680:  * |               |
                    681:  * +               +
                    682:  * |   ifindex     |
                    683:  * +               +
                    684:  * |               |
                    685:  * +               +
                    686:  * |               |
                    687:  * +-+-+-+-+-+-+-+-+
                    688:  * |   ifc_flags   |  flags for connected address
                    689:  * +-+-+-+-+-+-+-+-+
                    690:  * |  addr_family  |
                    691:  * +-+-+-+-+-+-+-+-+
                    692:  * |    addr...    |
                    693:  * :               :
                    694:  * |               |
                    695:  * +-+-+-+-+-+-+-+-+
                    696:  * |    addr_len   |  len of addr. E.g., addr_len = 4 for ipv4 addrs.
                    697:  * +-+-+-+-+-+-+-+-+
                    698:  * |     daddr..   |
                    699:  * :               :
                    700:  * |               |
                    701:  * +-+-+-+-+-+-+-+-+
                    702:  *
                    703:  */
                    704: 
                    705: void
                    706: zebra_interface_if_set_value (struct stream *s, struct interface *ifp)
                    707: {
                    708:   /* Read interface's index. */
                    709:   ifp->ifindex = stream_getl (s);
                    710:   ifp->status = stream_getc (s);
                    711: 
                    712:   /* Read interface's value. */
                    713:   ifp->flags = stream_getq (s);
                    714:   ifp->metric = stream_getl (s);
                    715:   ifp->mtu = stream_getl (s);
                    716:   ifp->mtu6 = stream_getl (s);
                    717:   ifp->bandwidth = stream_getl (s);
                    718: }
                    719: 
                    720: static int
                    721: memconstant(const void *s, int c, size_t n)
                    722: {
                    723:   const u_char *p = s;
                    724: 
                    725:   while (n-- > 0)
                    726:     if (*p++ != c)
                    727:       return 0;
                    728:   return 1;
                    729: }
                    730: 
                    731: struct connected *
                    732: zebra_interface_address_read (int type, struct stream *s)
                    733: {
                    734:   unsigned int ifindex;
                    735:   struct interface *ifp;
                    736:   struct connected *ifc;
                    737:   struct prefix p, d;
                    738:   int family;
                    739:   int plen;
                    740:   u_char ifc_flags;
                    741: 
                    742:   memset (&p, 0, sizeof(p));
                    743:   memset (&d, 0, sizeof(d));
                    744: 
                    745:   /* Get interface index. */
                    746:   ifindex = stream_getl (s);
                    747: 
                    748:   /* Lookup index. */
                    749:   ifp = if_lookup_by_index (ifindex);
                    750:   if (ifp == NULL)
                    751:     {
                    752:       zlog_warn ("zebra_interface_address_read(%s): "
                    753:                  "Can't find interface by ifindex: %d ",
                    754:                  (type == ZEBRA_INTERFACE_ADDRESS_ADD? "ADD" : "DELETE"),
                    755:                  ifindex);
                    756:       return NULL;
                    757:     }
                    758: 
                    759:   /* Fetch flag. */
                    760:   ifc_flags = stream_getc (s);
                    761: 
                    762:   /* Fetch interface address. */
                    763:   family = p.family = stream_getc (s);
                    764: 
                    765:   plen = prefix_blen (&p);
                    766:   stream_get (&p.u.prefix, s, plen);
                    767:   p.prefixlen = stream_getc (s);
                    768: 
                    769:   /* Fetch destination address. */
                    770:   stream_get (&d.u.prefix, s, plen);
                    771:   d.family = family;
                    772: 
                    773:   if (type == ZEBRA_INTERFACE_ADDRESS_ADD) 
                    774:     {
                    775:        /* N.B. NULL destination pointers are encoded as all zeroes */
                    776:        ifc = connected_add_by_prefix(ifp, &p,(memconstant(&d.u.prefix,0,plen) ?
                    777:                                              NULL : &d));
                    778:        if (ifc != NULL)
                    779:         {
                    780:           ifc->flags = ifc_flags;
                    781:           if (ifc->destination)
                    782:             ifc->destination->prefixlen = ifc->address->prefixlen;
                    783:         }
                    784:     }
                    785:   else
                    786:     {
                    787:       assert (type == ZEBRA_INTERFACE_ADDRESS_DELETE);
                    788:       ifc = connected_delete_by_prefix(ifp, &p);
                    789:     }
                    790: 
                    791:   return ifc;
                    792: }
                    793: 
                    794: 
                    795: /* Zebra client message read function. */
                    796: static int
                    797: zclient_read (struct thread *thread)
                    798: {
                    799:   int ret;
                    800:   size_t already;
                    801:   uint16_t length, command;
                    802:   uint8_t marker, version;
                    803:   struct zclient *zclient;
                    804: 
                    805:   /* Get socket to zebra. */
                    806:   zclient = THREAD_ARG (thread);
                    807:   zclient->t_read = NULL;
                    808: 
                    809:   /* Read zebra header (if we don't have it already). */
                    810:   if ((already = stream_get_endp(zclient->ibuf)) < ZEBRA_HEADER_SIZE)
                    811:     {
                    812:       ssize_t nbyte;
                    813:       if (((nbyte = stream_read_try(zclient->ibuf, zclient->sock,
                    814:                                     ZEBRA_HEADER_SIZE-already)) == 0) ||
                    815:          (nbyte == -1))
                    816:        {
                    817:          if (zclient_debug)
                    818:           zlog_debug ("zclient connection closed socket [%d].", zclient->sock);
                    819:          return zclient_failed(zclient);
                    820:        }
                    821:       if (nbyte != (ssize_t)(ZEBRA_HEADER_SIZE-already))
                    822:        {
                    823:          /* Try again later. */
                    824:          zclient_event (ZCLIENT_READ, zclient);
                    825:          return 0;
                    826:        }
                    827:       already = ZEBRA_HEADER_SIZE;
                    828:     }
                    829: 
                    830:   /* Reset to read from the beginning of the incoming packet. */
                    831:   stream_set_getp(zclient->ibuf, 0);
                    832: 
                    833:   /* Fetch header values. */
                    834:   length = stream_getw (zclient->ibuf);
                    835:   marker = stream_getc (zclient->ibuf);
                    836:   version = stream_getc (zclient->ibuf);
                    837:   command = stream_getw (zclient->ibuf);
                    838:   
                    839:   if (marker != ZEBRA_HEADER_MARKER || version != ZSERV_VERSION)
                    840:     {
                    841:       zlog_err("%s: socket %d version mismatch, marker %d, version %d",
                    842:                __func__, zclient->sock, marker, version);
                    843:       return zclient_failed(zclient);
                    844:     }
                    845:   
                    846:   if (length < ZEBRA_HEADER_SIZE) 
                    847:     {
                    848:       zlog_err("%s: socket %d message length %u is less than %d ",
                    849:               __func__, zclient->sock, length, ZEBRA_HEADER_SIZE);
                    850:       return zclient_failed(zclient);
                    851:     }
                    852: 
                    853:   /* Length check. */
                    854:   if (length > STREAM_SIZE(zclient->ibuf))
                    855:     {
                    856:       struct stream *ns;
                    857:       zlog_warn("%s: message size %u exceeds buffer size %lu, expanding...",
                    858:                __func__, length, (u_long)STREAM_SIZE(zclient->ibuf));
                    859:       ns = stream_new(length);
                    860:       stream_copy(ns, zclient->ibuf);
                    861:       stream_free (zclient->ibuf);
                    862:       zclient->ibuf = ns;
                    863:     }
                    864: 
                    865:   /* Read rest of zebra packet. */
                    866:   if (already < length)
                    867:     {
                    868:       ssize_t nbyte;
                    869:       if (((nbyte = stream_read_try(zclient->ibuf, zclient->sock,
                    870:                                     length-already)) == 0) ||
                    871:          (nbyte == -1))
                    872:        {
                    873:          if (zclient_debug)
                    874:            zlog_debug("zclient connection closed socket [%d].", zclient->sock);
                    875:          return zclient_failed(zclient);
                    876:        }
                    877:       if (nbyte != (ssize_t)(length-already))
                    878:        {
                    879:          /* Try again later. */
                    880:          zclient_event (ZCLIENT_READ, zclient);
                    881:          return 0;
                    882:        }
                    883:     }
                    884: 
                    885:   length -= ZEBRA_HEADER_SIZE;
                    886: 
                    887:   if (zclient_debug)
                    888:     zlog_debug("zclient 0x%p command 0x%x \n", zclient, command);
                    889: 
                    890:   switch (command)
                    891:     {
                    892:     case ZEBRA_ROUTER_ID_UPDATE:
                    893:       if (zclient->router_id_update)
                    894:        ret = (*zclient->router_id_update) (command, zclient, length);
                    895:       break;
                    896:     case ZEBRA_INTERFACE_ADD:
                    897:       if (zclient->interface_add)
                    898:        ret = (*zclient->interface_add) (command, zclient, length);
                    899:       break;
                    900:     case ZEBRA_INTERFACE_DELETE:
                    901:       if (zclient->interface_delete)
                    902:        ret = (*zclient->interface_delete) (command, zclient, length);
                    903:       break;
                    904:     case ZEBRA_INTERFACE_ADDRESS_ADD:
                    905:       if (zclient->interface_address_add)
                    906:        ret = (*zclient->interface_address_add) (command, zclient, length);
                    907:       break;
                    908:     case ZEBRA_INTERFACE_ADDRESS_DELETE:
                    909:       if (zclient->interface_address_delete)
                    910:        ret = (*zclient->interface_address_delete) (command, zclient, length);
                    911:       break;
                    912:     case ZEBRA_INTERFACE_UP:
                    913:       if (zclient->interface_up)
                    914:        ret = (*zclient->interface_up) (command, zclient, length);
                    915:       break;
                    916:     case ZEBRA_INTERFACE_DOWN:
                    917:       if (zclient->interface_down)
                    918:        ret = (*zclient->interface_down) (command, zclient, length);
                    919:       break;
                    920:     case ZEBRA_IPV4_ROUTE_ADD:
                    921:       if (zclient->ipv4_route_add)
                    922:        ret = (*zclient->ipv4_route_add) (command, zclient, length);
                    923:       break;
                    924:     case ZEBRA_IPV4_ROUTE_DELETE:
                    925:       if (zclient->ipv4_route_delete)
                    926:        ret = (*zclient->ipv4_route_delete) (command, zclient, length);
                    927:       break;
                    928:     case ZEBRA_IPV6_ROUTE_ADD:
                    929:       if (zclient->ipv6_route_add)
                    930:        ret = (*zclient->ipv6_route_add) (command, zclient, length);
                    931:       break;
                    932:     case ZEBRA_IPV6_ROUTE_DELETE:
                    933:       if (zclient->ipv6_route_delete)
                    934:        ret = (*zclient->ipv6_route_delete) (command, zclient, length);
                    935:       break;
                    936:     default:
                    937:       break;
                    938:     }
                    939: 
                    940:   if (zclient->sock < 0)
                    941:     /* Connection was closed during packet processing. */
                    942:     return -1;
                    943: 
                    944:   /* Register read thread. */
                    945:   stream_reset(zclient->ibuf);
                    946:   zclient_event (ZCLIENT_READ, zclient);
                    947: 
                    948:   return 0;
                    949: }
                    950: 
                    951: void
                    952: zclient_redistribute (int command, struct zclient *zclient, int type)
                    953: {
                    954: 
                    955:   if (command == ZEBRA_REDISTRIBUTE_ADD) 
                    956:     {
                    957:       if (zclient->redist[type])
                    958:          return;
                    959:       zclient->redist[type] = 1;
                    960:     }
                    961:   else
                    962:     {
                    963:       if (!zclient->redist[type])
                    964:          return;
                    965:       zclient->redist[type] = 0;
                    966:     }
                    967: 
                    968:   if (zclient->sock > 0)
                    969:     zebra_redistribute_send (command, zclient, type);
                    970: }
                    971: 
                    972: 
                    973: void
                    974: zclient_redistribute_default (int command, struct zclient *zclient)
                    975: {
                    976: 
                    977:   if (command == ZEBRA_REDISTRIBUTE_DEFAULT_ADD)
                    978:     {
                    979:       if (zclient->default_information)
                    980:         return;
                    981:       zclient->default_information = 1;
                    982:     }
                    983:   else 
                    984:     {
                    985:       if (!zclient->default_information)
                    986:         return;
                    987:       zclient->default_information = 0;
                    988:     }
                    989: 
                    990:   if (zclient->sock > 0)
                    991:     zebra_message_send (zclient, command);
                    992: }
                    993: 
                    994: static void
                    995: zclient_event (enum event event, struct zclient *zclient)
                    996: {
                    997:   switch (event)
                    998:     {
                    999:     case ZCLIENT_SCHEDULE:
                   1000:       if (! zclient->t_connect)
                   1001:        zclient->t_connect =
                   1002:          thread_add_event (master, zclient_connect, zclient, 0);
                   1003:       break;
                   1004:     case ZCLIENT_CONNECT:
                   1005:       if (zclient->fail >= 10)
                   1006:        return;
                   1007:       if (zclient_debug)
                   1008:        zlog_debug ("zclient connect schedule interval is %d", 
                   1009:                   zclient->fail < 3 ? 10 : 60);
                   1010:       if (! zclient->t_connect)
                   1011:        zclient->t_connect = 
                   1012:          thread_add_timer (master, zclient_connect, zclient,
                   1013:                            zclient->fail < 3 ? 10 : 60);
                   1014:       break;
                   1015:     case ZCLIENT_READ:
                   1016:       zclient->t_read = 
                   1017:        thread_add_read (master, zclient_read, zclient, zclient->sock);
                   1018:       break;
                   1019:     }
                   1020: }

FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>