/* * Open up a raw packet socket to catch all 802.2 packets. * and install a packet filter to only see STP (SAP 42) * * Since any bridged devices are already in promiscious mode * no need to add multicast address. */ int packet_sock_init(void) { int s; struct sock_fprog prog = { .len = sizeof(stp_filter) / sizeof(stp_filter[0]), .filter = stp_filter, }; s = socket(PF_PACKET, SOCK_RAW, htons(ETH_P_802_2)); if(s < 0) { ERROR("socket failed: %m"); return -1; } if(setsockopt(s, SOL_SOCKET, SO_ATTACH_FILTER, &prog, sizeof(prog)) < 0) ERROR("setsockopt packet filter failed: %m"); else if(fcntl(s, F_SETFL, O_NONBLOCK) < 0) ERROR("fcntl set nonblock failed: %m"); else { packet_event.fd = s; packet_event.handler = packet_rcv; if(0 == add_epoll(&packet_event)) return 0; } close(s); return -1; }
int ctl_socket_init(void) { int s = server_socket(); if (s < 0) return -1; ctl_handler.fd = s; ctl_handler.handler = ctl_rcv_handler; TST(add_epoll(&ctl_handler) == 0, -1); return 0; }
int init_bridge_ops(void) { if(rtnl_open(&rth, RTMGRP_LINK) < 0) { fprintf(stderr, "Couldn't open rtnl socket for monitoring\n"); return -1; } if(rtnl_open(&rth_state, 0) < 0) { fprintf(stderr, "Couldn't open rtnl socket for setting state\n"); return -1; } if(rtnl_wilddump_request(&rth, PF_BRIDGE, RTM_GETLINK) < 0) { //fprintf(stderr, "Cannot send dump request: %m\n"); fprintf(stderr, "Cannot send dump request: %s\n", strerror(errno)); return -1; } if(rtnl_dump_filter(&rth, dump_msg, stdout, NULL, NULL) < 0) { fprintf(stderr, "Dump terminated\n"); return -1; } if(fcntl(rth.fd, F_SETFL, O_NONBLOCK) < 0) { //fprintf(stderr, "Error setting O_NONBLOCK: %m\n"); fprintf(stderr, "Error setting O_NONBLOCK: %s\n", strerror(errno)); return -1; } br_handler.fd = rth.fd; br_handler.arg = NULL; br_handler.handler = br_ev_handler; if(add_epoll(&br_handler) < 0){ return -1; } return 0; }
/* * Open up a raw packet socket to catch all 802.2 packets. * and install a packet filter to only see STP (SAP 42) * * Since any bridged devices are already in promiscious mode * no need to add multicast address. */ int packet_sock_init(void) { int s; #ifdef KERNEL_BRIDGE_TURN_ON //内核开启Bridge 支持 struct sock_fprog prog = { .len = sizeof(stp_filter) / sizeof(stp_filter[0]), .filter = stp_filter, }; s = socket(PF_PACKET, SOCK_RAW, htons(ETH_P_802_2)); if(s < 0) { //ERROR("socket failed: %m"); ERROR("socket failed: %s", strerror(errno)); return -1; } if(setsockopt(s, SOL_SOCKET, SO_ATTACH_FILTER, &prog, sizeof(prog)) < 0) { //ERROR("setsockopt packet filter failed: %m"); ERROR("setsockopt packet filter failed: %s",strerror(errno)); } else if(fcntl(s, F_SETFL, O_NONBLOCK) < 0) { //ERROR("fcntl set nonblock failed: %m"); ERROR("fcntl set nonblock failed: %s", strerror(errno)); } else { packet_event.fd = s; packet_event.handler = packet_rcv; if(0 == add_epoll(&packet_event)) { return 0; } } #else s = socket(PF_PACKET, SOCK_RAW, htons(ETH_P_802_2)); if(s < 0) { //ERROR("socket failed: %m"); ERROR("socket failed: %s", strerror(errno)); return -1; } if(fcntl(s, F_SETFL, O_NONBLOCK) < 0) { //ERROR("fcntl set nonblock failed: %m"); ERROR("fcntl set nonblock failed: %s", strerror(errno)); } else { packet_event.fd = s; packet_event.handler = packet_rcv; if(0 == add_epoll(&packet_event)) { return 0; } } #endif close(s); return -1; }