1 /******************************************************************************
3 Copyright (c) 2012, Intel Corporation
6 Redistribution and use in source and binary forms, with or without
7 modification, are permitted provided that the following conditions are met:
9 1. Redistributions of source code must retain the above copyright notice,
10 this list of conditions and the following disclaimer.
12 2. Redistributions in binary form must reproduce the above copyright
13 notice, this list of conditions and the following disclaimer in the
14 documentation and/or other materials provided with the distribution.
16 3. Neither the name of the Intel Corporation nor the names of its
17 contributors may be used to endorse or promote products derived from
18 this software without specific prior written permission.
20 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
21 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
23 ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
24 LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
25 CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
26 SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
27 INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
28 CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
29 ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
30 POSSIBILITY OF SUCH DAMAGE.
32 ******************************************************************************/
42 #include <sys/ioctl.h>
44 #include <sys/resource.h>
47 #include <sys/socket.h>
49 #include <netpacket/packet.h>
50 #include <netinet/in.h>
51 #include <arpa/inet.h>
52 #include <net/ethernet.h>
57 /* global variables */
58 int control_socket = -1;
60 #define VERSION_STR "0.0"
62 static const char *version_str =
63 "mrpctl v" VERSION_STR "\n"
64 "Copyright (c) 2012, Intel Corporation\n";
67 init_local_ctl( void ) {
68 struct sockaddr_in addr;
73 sock_fd = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP);
74 if (sock_fd < 0) goto out;
75 sock_flags = fcntl(sock_fd, F_GETFL, 0);
76 fcntl(sock_fd, F_SETFL, sock_flags | O_NONBLOCK);
78 memset(&addr, 0, sizeof(addr));
79 addr.sin_family = AF_INET;
80 addr.sin_port = htons(MRPD_PORT_DEFAULT);
81 inet_aton("127.0.0.1", &addr.sin_addr);
82 addr_len = sizeof(addr);
84 /* rc = bind(sock_fd, (struct sockaddr *)&addr, addr_len); */
86 /* if (rc < 0) goto out; */
88 memset(&addr, 0, sizeof(addr));
90 * use an abstract socket address with a leading null character
91 * note this is non-portable
94 printf("connected!\n");
95 control_socket = sock_fd;
99 if (sock_fd != -1) close(sock_fd);
105 process_ctl_msg(char *buf, int buflen, struct sockaddr_in *client) {
108 * M?? - query MMRP Registrar MAC Address database
109 * M+? - JOIN_MT a MAC address
110 * -- note M++ doesn't exist apparently- MMRP doesn't use 'New' --
111 * M-- - LV a MAC address
112 * V?? - query MVRP Registrar VID database
113 * V++ - JOIN_IN a VID (VLAN ID)
114 * V+? - JOIN_MT a VID (VLAN ID)
115 * V-- - LV a VID (VLAN ID)
119 printf("RESP:%s from SRV %d (bytes=%d)\n", buf, client->sin_port, buflen);
127 struct sockaddr_in client_addr;
132 msgbuf = (char *)malloc (MAX_MRPD_CMDSZ);
135 memset(&msg, 0, sizeof(msg));
136 memset(&client_addr, 0, sizeof(client_addr));
137 memset(msgbuf, 0, MAX_MRPD_CMDSZ);
139 iov.iov_len = MAX_MRPD_CMDSZ;
140 iov.iov_base = msgbuf;
141 msg.msg_name = &client_addr;
142 msg.msg_namelen = sizeof(client_addr);
145 printf("recv msg ... \n");
146 bytes = recvmsg(control_socket, &msg, 0); if (bytes < 0) goto out;
148 return(process_ctl_msg(msgbuf, bytes, &client_addr) );
150 printf("recv'd bad msg ... \n");
157 send_control_msg( char *notify_data, int notify_len) {
158 struct sockaddr_in addr;
161 memset(&addr, 0, sizeof(addr));
162 addr.sin_family = AF_INET;
163 addr.sin_port = htons(MRPD_PORT_DEFAULT);
164 inet_aton("127.0.0.1", &addr.sin_addr);
165 addr_len = sizeof(addr);
167 printf("sending message\n");
169 if (control_socket != -1)
170 return(sendto(control_socket, notify_data, notify_len, 0, (struct sockaddr *)&addr, addr_len));
176 process_events( void ) {
178 /* wait for events, demux the received packets, process packets */
185 "usage: mrpd [-hdlmvs] -i interface-name"
188 " -h show this message\n"
189 " -d run daemon in the background\n"
190 " -l enable logging (ignored in daemon mode)\n"
191 " -m enable MMRP Registrar and Participant\n"
192 " -v enable MVRP Registrar and Participant\n"
193 " -s enable MSRP Registrar and Participant\n"
194 " -i specify interface to monitor\n"
203 main(int argc, char *argv[]) {
209 c = getopt(argc, argv, "hdlmvsi:");
223 rc = init_local_ctl(); if (rc) { printf("init failed\n"); goto out; }
225 msgbuf = malloc(1500);
226 if (NULL == msgbuf) {
227 printf("memory allocation error - exiting\n");
231 memset(msgbuf,0,1500);
232 sprintf(msgbuf,"M++:M=010203040506");
233 rc = send_control_msg(msgbuf, 1500 );
236 memset(msgbuf,0,1500);
237 sprintf(msgbuf,"M++:M=ffffffffffff");
238 rc = send_control_msg(msgbuf, 1500 );
241 memset(msgbuf,0,1500);
242 sprintf(msgbuf,"V++:I=0002");
243 rc = send_control_msg(msgbuf, 1500 );
246 memset(msgbuf,0,1500);
247 sprintf(msgbuf,"M++:M=060504030201");
248 rc = send_control_msg(msgbuf, 1500 );
250 memset(msgbuf,0,1500);
251 sprintf(msgbuf,"M++:S=1");
252 rc = send_control_msg(msgbuf, 1500 );
254 memset(msgbuf,0,1500);
255 sprintf(msgbuf,"M--:M=060504030201");
256 rc = send_control_msg(msgbuf, 1500 );
258 memset(msgbuf,0,1500);
259 sprintf(msgbuf,"M--:S=1");
260 rc = send_control_msg(msgbuf, 1500 );
263 memset(msgbuf,0,1500);
264 sprintf(msgbuf,"V++:I=0002");
265 rc = send_control_msg(msgbuf, 1500 );
267 sprintf(msgbuf,"V--:I=0002");
268 rc = send_control_msg(msgbuf, 1500 );
271 memset(msgbuf,0,1500);
272 sprintf(msgbuf,"S++:S=DEADBEEFBADFCA11,A=112233445566,V=0002,Z=576,I=8000,P=96,L=1000");
273 rc = send_control_msg(msgbuf, 1500);
275 memset(msgbuf,0,1500);
276 sprintf(msgbuf,"S--:S=DEADBEEFBADFCA11");
277 rc = send_control_msg(msgbuf, 1500);
280 memset(msgbuf,0,1500);
281 sprintf(msgbuf,"S++:S=FFEEDDCCBBAA9988,A=112233445567,V=0002,Z=576,I=8000,P=96,L=1000");
282 rc = send_control_msg(msgbuf, 1500);
284 memset(msgbuf,0,1500);
285 sprintf(msgbuf,"S+L:L=DEADBEEFBADFCA11,D=2");
286 rc = send_control_msg(msgbuf, 1500);
288 memset(msgbuf,0,1500);
289 sprintf(msgbuf,"S+L:L=F00F00F00F00F000,D=2");
290 rc = send_control_msg(msgbuf, 1500);
292 memset(msgbuf,0,1500);
293 sprintf(msgbuf, "S+D:C=6,P=3,V=0002");
294 rc = send_control_msg(msgbuf, 1500);
296 memset(msgbuf,0,1500);
297 sprintf(msgbuf, "S-D:C=6,P=3,V=0002");
298 rc = send_control_msg(msgbuf, 1500);
300 memset(msgbuf,0,1500);
301 sprintf(msgbuf,"S-L:L=F00F00F00F00F000");
302 rc = send_control_msg(msgbuf, 1500);
306 memset(msgbuf,0,1500);
307 sprintf(msgbuf,"M??");
308 rc = send_control_msg(msgbuf, 1500);
309 memset(msgbuf,0,1500);
310 sprintf(msgbuf,"V??");
311 rc = send_control_msg(msgbuf, 1500 );
312 memset(msgbuf,0,1500);
313 sprintf(msgbuf,"S??");
314 rc = send_control_msg(msgbuf, 1500 );
319 printf("exiting (rc=%d)\n", rc);