From: Radek Matějka Date: Tue, 18 Dec 2012 04:19:10 +0000 (-0600) Subject: cegw cleanup and refactor, new test t7 X-Git-Url: http://rtime.felk.cvut.cz/gitweb/can-eth-gw.git/commitdiff_plain/b727e37db5c673c2e0fd7ca46d9bd25101800272 cegw cleanup and refactor, new test t7 Configuration utility cegw was cleansed and improved. A new test (t7) was introduced. t7 is running 3 gateway jobs and testing if it works correctly. --- diff --git a/distro/customroot/sbin/t0 b/distro/customroot/sbin/t0 index 0eda8d5..01f9738 120000 --- a/distro/customroot/sbin/t0 +++ b/distro/customroot/sbin/t0 @@ -1 +1 @@ -../../../test/test \ No newline at end of file +../../../test/t0 \ No newline at end of file diff --git a/test/t0 b/test/t0 new file mode 100755 index 0000000..26026d7 --- /dev/null +++ b/test/t0 @@ -0,0 +1,36 @@ +#!/bin/sh +N=10 +MODE=oneattime +CAN=vcan0 +UDP_SRC=127.0.0.1:10501 +UDP_DST=127.0.0.1:10502 + +evalmsg() +{ + if test $1 -eq 0; then + echo -e "\033[32mOK" + else + echo -e "\033[31mFAIL" + fi; + echo -ne "\033[0m" +} + +if test $# -eq 1; then + N=$1; +fi + +if test $# -eq 4; then + CAN=$1 + UDP_SRC=$2 + UDP_DST=$3 + N=$4 +fi + +echo -n "Testing eth->can: " +cegwbench -s udp@$UDP_SRC -d can@$CAN -n $N -m $MODE -t 1 &> /dev/zero +evalmsg $? + +echo -n "Testing can->eth: " +cegwbench -s can@vcan0 -d udp@$UDP_DST -n $N -m $MODE -t 1 &> /dev/zero +evalmsg $? + diff --git a/test/t7 b/test/t7 new file mode 100755 index 0000000..4782adc --- /dev/null +++ b/test/t7 @@ -0,0 +1,11 @@ +cegw vcan0 0.0.0.0:10501 127.0.0.1:10502 127.0.0.1:10503& +JOBA=$! +cegw vcan0 0.0.0.0:10601 127.0.0.1:10602 127.0.0.1:10503& +JOBB=$! +cegw vcan0 0.0.0.0:10701 127.0.0.1:10702 127.0.0.1:10503& +JOBC=$! + +t0 vcan0 127.0.0.1:10501 127.0.0.1:10502 10 && kill $JOBA & +t0 vcan0 127.0.0.1:10601 127.0.0.1:10602 10 && kill $JOBB & +t0 vcan0 127.0.0.1:10701 127.0.0.1:10702 10 && kill $JOBC & + diff --git a/test/test b/test/test deleted file mode 100755 index 1e18187..0000000 --- a/test/test +++ /dev/null @@ -1,26 +0,0 @@ -#!/bin/sh -N=10 -MODE=oneattime - -evalmsg() -{ - if test $1 -eq 0; then - echo -e "\033[32mOK" - else - echo -e "\033[31mFAIL" - fi; - echo -ne "\033[0m" -} - -if test $# -ne 0; then - N=$1; -fi - -echo -n "Testing eth->can: " -cegwbench -s udp@127.0.0.1:10501 -d can@vcan0 -n $N -m $MODE -t 1 &> /dev/zero -evalmsg $? - -echo -n "Testing can->eth: " -cegwbench -s can@vcan0 -d udp@127.0.0.1:10502 -n $N -m $MODE -t 1 &> /dev/zero -evalmsg $? - diff --git a/utils/cegw/Makefile b/utils/cegw/Makefile index 5fe6d86..ac24cbb 100644 --- a/utils/cegw/Makefile +++ b/utils/cegw/Makefile @@ -1,3 +1,5 @@ all: - gcc -Wall -ggdb -ocegw -D_DEBUG -I../../kernel cegw.c -lnetlink + gcc -Wall -ocegw -I../../kernel cegw.c +debug: + gcc -Wall -ggdb -D_DEBUG -ocegw -I../../kernel cegw.c diff --git a/utils/cegw/cegw.c b/utils/cegw/cegw.c index 566a09f..c0cb885 100644 --- a/utils/cegw/cegw.c +++ b/utils/cegw/cegw.c @@ -6,9 +6,6 @@ #include #include #include -#include -#include -#include #include #include #include @@ -20,61 +17,11 @@ #include #include "canethgw.h" -/** - * ToDo: - * [ ] print usage, on -h and plain execution - * [ ] start/stop listening - * [ ] split to files - */ - -#define CEGW_CMD_ADD 1 -#define CEGW_CMD_LIST 2 -#define CEGW_CMD_FLUSH 4 -#define CEGW_CMD_LISTEN 8 - -enum -{ - IF_UNDEF, - IF_CAN, - IF_ETH_UDP -}; - -struct cegw_data -{ - int content; - int src_if, dst_if; - int can_ifidx; - struct in_addr eth_addr; - unsigned short eth_port; - struct in_addr eth_listen_addr; - unsigned short eth_listen_port; -}; - -struct cegw_nlmsg -{ - struct nlmsghdr nh; - struct rtmsg rt; - char buf[768]; /* enough? */ -}; - -struct list_item -{ - int type; - int can; - struct in_addr ip; - unsigned short port; -}; - unsigned int cegw_errno = 0; enum { CEGW_ERR_UNKNOWN, - CEGW_ERR_IF_UNSPEC, - CEGW_ERR_IF_SAME, - CEGW_ERR_IF_TYPE, - CEGW_ERR_IF_CAN, - CEGW_ERR_IF_ETH, CEGW_ERR_COLON, CEGW_ERR_ATON, CEGW_ERR_PORT @@ -82,34 +29,30 @@ enum char* cegw_errlist[] = { - [ CEGW_ERR_UNKNOWN ] = "", - [ CEGW_ERR_IF_UNSPEC ] = "source or destination not specified", - [ CEGW_ERR_IF_SAME ] = "source and destination have same interface type", - [ CEGW_ERR_IF_TYPE ] = "unknown interface type", - [ CEGW_ERR_IF_CAN ] = "invalid can interface", - [ CEGW_ERR_IF_ETH ] = "invalid eth interface", - [ CEGW_ERR_COLON ] = "expected ':' (:)", - [ CEGW_ERR_ATON ] = "ip address mismatch", - [ CEGW_ERR_PORT ] = "port number" + [CEGW_ERR_UNKNOWN] = "", + [CEGW_ERR_COLON ] = "expected ':' (:)", + [CEGW_ERR_ATON ] = "ip address mismatch", + [CEGW_ERR_PORT ] = "port number" }; -static void perr( char* s ) +static const char help_msg[] = "usage:\n\ + %s : N x (:)\n\ +example:\n\ + %s can0 192.168.0.1:10501 192.168.0.4:980 192.168.0.7:1160\n"; + +static void perr(char* s) { - if( s ) - { - if( cegw_errno == 0 ) - { - fprintf( stderr, "error: %s\n", s ); + if (s) { + if (cegw_errno == 0) { + fprintf(stderr, "error: %s\n", s); - } else - { - fprintf( stderr, "error: %s, %s\n", s, - cegw_errlist[ cegw_errno ] ); + } else { + fprintf(stderr, "error: %s, %s\n", s, cegw_errlist[cegw_errno]); } return; } - fprintf( stderr, "error: %s\n", cegw_errlist[ cegw_errno ] ); + fprintf(stderr, "error: %s\n", cegw_errlist[cegw_errno]); } /** @@ -121,222 +64,127 @@ static void perr( char* s ) * @param[out] port transport layer port * @return 0 on success, -1 otherwise */ -int read_addrport( char* in, struct in_addr* addr, unsigned short* port ) +int read_addrport(char* in, struct in_addr* addr, unsigned short* port) { char* delim = NULL; char addrstr[16]; int addrlen; - if( (delim = strchr( in, ':' )) == NULL ) - { + if ((delim = strchr(in, ':')) == NULL) { cegw_errno = CEGW_ERR_COLON; return -1; } /* get address */ addrlen = delim - in; - memcpy( addrstr, in, addrlen ); + memcpy(addrstr, in, addrlen); addrstr[addrlen] = '\0'; - if( inet_aton( addrstr, addr ) == 0 ) - { + if (inet_aton(addrstr, addr) == 0) { cegw_errno = CEGW_ERR_ATON; return -1; } /* get port */ - if( sscanf( delim, ":%hu", port ) != 1 ) /* ToDo: handle overflow */ - { - cegw_errno = CEGW_ERR_PORT; - return -1; - } + /* ToDo: handle overflow */ - return 0; -} - -/** - * read_iftype - reads @in for iftype - * Iftype type is e.g. "can@" or "udp@". - * - * @param[in] in string to search in - * @param[out] iftype iftype detected - * @return pointer to @in after iftype on success, NULL otherwise - */ -char* read_iftype( char* in, int* iftype ) -{ - char* ret = in+4; - - if( strncmp( "udp@", optarg, 4 ) == 0 ) - { - *iftype = IF_ETH_UDP; - return ret; - } - /* - if( strncmp( "tcp@", optarg, 4 ) == 0 ) - { - return NULL; - } - */ - if( strncmp( "can@", optarg, 4 ) == 0 ) - { - *iftype = IF_CAN; - return ret; - } - - cegw_errno = CEGW_ERR_IF_TYPE; - return NULL; -} - -/* ToDo: move to common */ - -/** - * read_if - reads interface from @in - * Function analyzes @in for interface specification in format - * @:, where is can or udp, is address in dotted - * format - * - * @param[in] in string to search in - * @param[out] iftype interface type (IF_CAN or IF_ETH_UDP) - * @param[out] d ip and port is stored to @d - */ -int read_if( char* in, int* iftype, struct cegw_data* d ) -{ - char* optstr = NULL; - - if( (optstr = read_iftype( in, iftype )) == NULL ) - { + if (sscanf(delim, ":%hu", port) != 1) { + cegw_errno = CEGW_ERR_PORT; return -1; } - switch( *iftype ) - { - case IF_CAN: - d->can_ifidx = if_nametoindex( optstr ); - if( d->can_ifidx == 0 ) - { - cegw_errno = CEGW_ERR_IF_CAN; - return -1; - } - break; - case IF_ETH_UDP: - if( read_addrport( optstr, &d->eth_addr, &d->eth_port ) != 0 ) - { - return -1; - } - break; - default: - return -1; - break; - } - return 0; } -int main( int argc, char* argv[] ) +int main(int argc, char* argv[]) { - int s; - int tmp = 0; - int cmd = 0; - char* optstr; - char opt; - struct sockaddr_nl nladdr; - int err = 0; - struct cegw_nlmsg req; - struct cegw_data d; - char rxbuf[8192]; /* ToDo: /linux/netlink.h? */ - int rsize = 0; - struct nlmsghdr* nlh; - struct nlmsgerr* rte; - struct rtattr* rta; - int len; - struct list_item li; + int i; + int fd; + int tmpi; + int dstcnt; + unsigned short port; int udp_sock, can_sock; struct sockaddr_in udp_addr; struct sockaddr_can can_addr; - struct in_addr ipaddr; - unsigned short port; - int i; struct sockaddr_in* dst = NULL; + struct cegw_ioctl* gwctl = NULL; - if( argc < 3 ) - { - perr( "not enought arguments" ); + if (argc < 3) { + perr("not enought arguments"); + printf(help_msg, argv[0], argv[0]); /* ToDo: print usage */ - return; + return -1; } - int dstcnt = argc-3; -#ifdef _DEBUG - printf( "dstcnt=%i\n", dstcnt ); -#endif - struct cegw_ioctl* gwctl = (struct cegw_ioctl*)malloc( sizeof(*gwctl) + (dstcnt)*sizeof(struct sockaddr_in) ); + dstcnt = argc-3; + gwctl = (struct cegw_ioctl*)malloc(sizeof(*gwctl) + (dstcnt)*sizeof(struct sockaddr_in)); - for( i=1; iudp_dst[i-3]; dst->sin_family = AF_INET; - if( read_addrport(argv[i], &dst->sin_addr, &port) != 0 ) - { + if (read_addrport(argv[i], &dst->sin_addr, &port) != 0) { perr( "udp destination mismatch" ); + free( gwctl ); + return -1; } dst->sin_port = htons(port); break; } } - /* udp socket */ - udp_sock = socket( PF_INET, SOCK_DGRAM, IPPROTO_UDP ); - if( udp_sock == -1 ) - { - fprintf( stderr, "error: udp socket(..) failed\n" ); + /* prepare udp socket */ + udp_sock = socket(PF_INET, SOCK_DGRAM, IPPROTO_UDP); + if (udp_sock == -1) { + fprintf(stderr, "error: udp socket(..) failed\n"); + free(gwctl); return -1; } - printf( "port:%x\n", udp_addr.sin_port ); - if(bind( udp_sock, (struct sockaddr *)&udp_addr, sizeof(struct sockaddr_in) ) != 0) - { - fprintf( stderr, "error: udp bind(..) failed\n" ); + if (bind(udp_sock, (struct sockaddr *)&udp_addr, sizeof(struct sockaddr_in)) != 0) { + fprintf(stderr, "error: udp bind(..) failed\n"); + free(gwctl); return -1; } - /* can socket */ - /* ToDo: name lookup error */ - can_sock = socket( PF_CAN, SOCK_RAW, CAN_RAW ); - if( can_sock == -1 ) - { - fprintf( stderr, "error: can socket(..) failed\n" ); + /* prepare can socket */ + can_sock = socket(PF_CAN, SOCK_RAW, CAN_RAW); + if (can_sock == -1) { + fprintf(stderr, "error: can socket(..) failed\n"); + free(gwctl); return -1; } - if( bind(can_sock, (struct sockaddr *)&can_addr, sizeof(struct sockaddr_can)) != 0 ) - { - fprintf( stderr, "error: can bind(..) failed\n" ); + if (bind(can_sock, (struct sockaddr *)&can_addr, sizeof(struct sockaddr_can)) != 0) { + fprintf(stderr, "error: can bind(..) failed\n"); + free(gwctl); return -1; } /* send it to kernel gateway */ - int fd; - - fd = open( "/dev/cegw", O_RDONLY ); - if( fd == -1 ) - { - fprintf( stderr, "error: could not open device file\n" ); + fd = open("/dev/cegw", O_RDONLY); + if (fd == -1) { + fprintf(stderr, "error: could not open device file\n"); + free(gwctl); return -1; } @@ -345,16 +193,17 @@ int main( int argc, char* argv[] ) gwctl->udp_dstcnt = dstcnt; gwctl->udp_addrlen = sizeof(struct sockaddr_in); - if( ioctl( fd, CEGW_IOCTL_START, gwctl ) != 0 ) - { - perror( NULL ); + if (ioctl(fd, CEGW_IOCTL_START, gwctl) != 0) { + perror(NULL); + free(gwctl); + return -1; } + printf("gateway sucessfully set-up and running\n"); + free(gwctl); - //close( fd ); - - while(1) - { - sleep( UINT_MAX ); + /* sleep until someone kills me */ + while (1) { + sleep(UINT_MAX); } return 0;