/* Update source selection. */ static int bgp_update_source(struct peer *peer) { struct interface *ifp; union sockunion addr; int ret = 0; sockunion_init(&addr); /* Source is specified with interface name. */ if (peer->update_if) { ifp = if_lookup_by_name(peer->update_if, peer->bgp->vrf_id); if (!ifp) return -1; if (bgp_update_address(ifp, &peer->su, &addr)) return -1; ret = sockunion_bind(peer->fd, &addr, 0, &addr); } /* Source is specified with IP address. */ if (peer->update_source) ret = sockunion_bind(peer->fd, peer->update_source, 0, peer->update_source); return ret; }
/* Update source selection. */ static void bgp_update_source (struct peer *peer) { struct interface *ifp; union sockunion addr; /* Source is specified with interface name. */ if (peer->update_if) { ifp = if_lookup_by_name (peer->update_if); if (! ifp) return; if (bgp_update_address (ifp, &peer->su, &addr)) return; sockunion_bind (peer->fd, &addr, 0, &addr); } /* Source is specified with IP address. */ if (peer->update_source) sockunion_bind (peer->fd, peer->update_source, 0, peer->update_source); }
/* Update source selection. */ static void bgp_update_source (struct peer *peer) { struct interface *ifp; struct in_addr *addr; /* Source is specified with interface name. */ if (peer->update_if) { ifp = if_lookup_by_name (peer->update_if); if (! ifp) return; addr = bgp_update_address (ifp); if (! addr) return; bgp_bind_address (peer->fd, addr); } /* Source is specified with IP address. */ if (peer->update_source) sockunion_bind (peer->fd, peer->update_source, 0, peer->update_source); }
/* Add thread to Listen Thread List */ tmp_lnode = XCALLOC (MTYPE_TMP, sizeof (struct bgp_listen_sock_lnode)); if (! tmp_lnode) { zlog_err (&BLG, "[NETWORK] Server Sock:" " Cannot allocate memory (%d) @ %s:%d", sizeof (struct bgp_peer_inconn_req), __FILE__, __LINE__); SSOCK_FD_CLOSE (&BLG, bgp_sock); BGP_READ_OFF (&BLG, t_accept); continue; } tmp_lnode->listen_sock = bgp_sock; tmp_lnode->t_accept = t_accept; if (bgp->listen_sock_lnode) tmp_lnode->next = bgp->listen_sock_lnode; bgp->listen_sock_lnode = tmp_lnode; } pal_sock_freeaddrinfo (ainfo_head); return ret; } #else /* HAVE_IPV6 && !NRL */ s_int32_t bpn_sock_listen (struct bgp *bgp, u_int16_t port) { struct bgp_listen_sock_lnode *tmp_lnode; struct thread *t_accept; union sockunion su; s_int32_t bgp_sock; fib_id_t fib_id; s_int32_t ret; pal_mem_set (&su, 0, sizeof (union sockunion)); t_accept = NULL; ret = 0; if (! bgp) { zlog_err (&BLG, "[NETWORK] Server Sock: Invalid 'bgp' instance"); ret = -1; goto EXIT; } fib_id = LIB_VRF_GET_FIB_ID (bgp->owning_ivrf); /* Specify address family. */ su.sa.sa_family = AF_INET; bgp_sock = pal_sock (&BLG, su.sa.sa_family, SOCK_STREAM, 0); if (bgp_sock < 0) { zlog_err (&BLG, "[NETWORK] Server Sock: socket() Failed, FIB-ID %d, " "Err:%d-%s", fib_id, errno, pal_strerror (errno)); ret = -1; goto EXIT; } pal_sock_set_reuseaddr (bgp_sock, PAL_TRUE); pal_sock_set_reuseport (bgp_sock, PAL_TRUE); /* Bind socket to FIB. */ ret = pal_sock_set_bindtofib (bgp_sock, fib_id); if (ret < 0) { zlog_err (&BLG, "[NETWORK] Server Sock: bindtofib() Failed, Sock %d" ", FIB-ID %d, Err:%d-%s", bgp_sock, fib_id, errno, pal_strerror (errno)); SSOCK_FD_CLOSE (&BLG, bgp_sock); /* Ignore platform error */ ret = 0; goto EXIT; } ret = sockunion_bind (&BLG, bgp_sock, &su, port, NULL); if (ret < 0) { zlog_err (&BLG, "[NETWORK] Server Sock: bind() Failed, Err: %d-%s", errno, pal_strerror (errno)); SSOCK_FD_CLOSE (&BLG, bgp_sock); /* Ignore platform error */ ret = 0; goto EXIT; } #ifdef HAVE_TCP_MD5SIG bgp_md5_set_server (bgp, bgp_sock); #endif /* TCP_MD5SIG */ ret = pal_sock_listen (bgp_sock, BGP_SOCK_LISTEN_BACKLOG); if (ret < 0) { zlog_err (&BLG, "[NETWORK] Server Sock: listen() Failed, Sock %d, " "FIB-ID %d, Err:%d-%s", bgp_sock, fib_id, errno, pal_strerror (errno)); SSOCK_FD_CLOSE (&BLG, bgp_sock); /* Ignore platform error */ ret = 0; goto EXIT; } /* Start a fresh Accept Thread */ BGP_READ_ON (&BLG, t_accept, bgp, bpn_sock_accept, bgp_sock); /* Add thread to Listen Thread List */ tmp_lnode = XCALLOC (MTYPE_TMP, sizeof (struct bgp_listen_sock_lnode)); if (! tmp_lnode) { zlog_err (&BLG, "[NETWORK] Server Sock:" " Cannot allocate memory (%d) @ %s:%d", sizeof (struct bgp_peer_inconn_req), __FILE__, __LINE__); SSOCK_FD_CLOSE (&BLG, bgp_sock); BGP_READ_OFF (&BLG, t_accept); ret = -1; goto EXIT; } tmp_lnode->listen_sock = bgp_sock; tmp_lnode->t_accept = t_accept; if (bgp->listen_sock_lnode) tmp_lnode->next = bgp->listen_sock_lnode; bgp->listen_sock_lnode = tmp_lnode; EXIT: return ret; }
/* active peer socket setup */ int pim_msdp_sock_connect(struct pim_msdp_peer *mp) { int rc; if (PIM_DEBUG_MSDP_INTERNAL) { zlog_debug("MSDP peer %s attempt connect%s", mp->key_str, mp->fd < 0 ? "" : "(dup)"); } /* if we have an existing connection we need to kill that one * with this one */ if (mp->fd >= 0) { if (PIM_DEBUG_MSDP_EVENTS) { zlog_notice( "msdp duplicate connect to %s nuke old connection", mp->key_str); } pim_msdp_peer_stop_tcp_conn(mp, false /* chg_state */); } /* Make socket for the peer. */ mp->fd = sockunion_socket(&mp->su_peer); if (mp->fd < 0) { flog_err_sys(LIB_ERR_SOCKET, "pim_msdp_socket socket failure: %s", safe_strerror(errno)); return -1; } if (mp->pim->vrf_id != VRF_DEFAULT) { struct interface *ifp = if_lookup_by_name(mp->pim->vrf->name, mp->pim->vrf_id); if (!ifp) { flog_err(LIB_ERR_INTERFACE, "%s: Unable to lookup vrf interface: %s", __PRETTY_FUNCTION__, mp->pim->vrf->name); return -1; } if (pim_socket_bind(mp->fd, ifp)) { flog_err_sys(LIB_ERR_SOCKET, "%s: Unable to bind to socket: %s", __PRETTY_FUNCTION__, safe_strerror(errno)); close(mp->fd); mp->fd = -1; return -1; } } set_nonblocking(mp->fd); /* Set socket send buffer size */ pim_msdp_update_sock_send_buffer_size(mp->fd); sockopt_reuseaddr(mp->fd); sockopt_reuseport(mp->fd); /* source bind */ rc = sockunion_bind(mp->fd, &mp->su_local, 0, &mp->su_local); if (rc < 0) { flog_err_sys(LIB_ERR_SOCKET, "pim_msdp_socket connect bind failure: %s", safe_strerror(errno)); close(mp->fd); mp->fd = -1; return rc; } /* Connect to the remote mp. */ return (sockunion_connect(mp->fd, &mp->su_peer, htons(PIM_MSDP_TCP_PORT), 0)); }