From 5d3f8073b26c77302c275126af4f26cf4db9d592 Mon Sep 17 00:00:00 2001 From: Oleksij Rempel Date: Fri, 29 Nov 2019 12:41:52 +0100 Subject: [PATCH 1/3] testj1939: add optional promiscuous mode and boradcast support Upstream version of J1939 stack has different UAPI. To make documented testj1939 examples work again we need at least boradcast flag. Signed-off-by: Oleksij Rempel --- testj1939.c | 31 ++++++++++++++++++++++++++++++- 1 file changed, 30 insertions(+), 1 deletion(-) diff --git a/testj1939.c b/testj1939.c index 82d3266..c8fff13 100644 --- a/testj1939.c +++ b/testj1939.c @@ -39,7 +39,9 @@ static const char help_msg[] = " This atually receives packets\n" " -c Issue connect()\n" " -p=PRIO Set priority to PRIO\n" + " -P Promiscuous mode. Allow to receive all packets\n" " -b Do normal bind with SA+1 and rebind with actual SA\n" + " -B Allow to send and receive broadcast packets.\n" " -o Omit bind\n" " -n Emit 64bit NAMEs in output\n" " -w[TIME] Return after TIME (default 1) seconds\n" @@ -49,7 +51,7 @@ static const char help_msg[] = "\n" ; -static const char optstring[] = "?vbos::rep:cnw::"; +static const char optstring[] = "?vbBPos::rep:cnw::"; static void onsigalrm(int sig) { @@ -92,6 +94,7 @@ int main(int argc, char *argv[]) int valid_peername = 0; int todo_send = 0, todo_recv = 0, todo_echo = 0, todo_prio = -1; int todo_connect = 0, todo_names = 0, todo_wait = 0, todo_rebind = 0; + int todo_broadcast = 0, todo_promisc = 0; int no_bind = 0; /* argument parsing */ @@ -114,6 +117,9 @@ int main(int argc, char *argv[]) case 'p': todo_prio = strtoul(optarg, NULL, 0); break; + case 'P': + todo_promisc = 1; + break; case 'c': todo_connect = 1; break; @@ -123,6 +129,9 @@ int main(int argc, char *argv[]) case 'b': todo_rebind = 1; break; + case 'B': + todo_broadcast = 1; + break; case 'o': no_bind = 1; break; @@ -161,6 +170,26 @@ int main(int argc, char *argv[]) if (ret < 0) err(1, "socket(j1939)"); + if (todo_promisc) { + if (verbose) + fprintf(stderr, "- setsockopt(, SOL_SOCKET, SO_J1939_PROMISC, %d, %zd);\n", + todo_promisc, sizeof(todo_promisc)); + ret = setsockopt(sock, SOL_CAN_J1939, SO_J1939_PROMISC, + &todo_promisc, sizeof(todo_promisc)); + if (ret < 0) + err(1, "setsockopt: filed to set promiscuous mode"); + } + + if (todo_broadcast) { + if (verbose) + fprintf(stderr, "- setsockopt(, SOL_SOCKET, SO_BROADCAST, %d, %zd);\n", + todo_broadcast, sizeof(todo_broadcast)); + ret = setsockopt(sock, SOL_SOCKET, SO_BROADCAST, + &todo_broadcast, sizeof(todo_broadcast)); + if (ret < 0) + err(1, "setsockopt: filed to set broadcast"); + } + if (todo_prio >= 0) { if (verbose) fprintf(stderr, "- setsockopt(, SOL_CAN_J1939, SO_J1939_SEND_PRIO, &%i);\n", todo_prio); From 8cf63530395560311ff07fc94a49c05f308b19ac Mon Sep 17 00:00:00 2001 From: Oleksij Rempel Date: Fri, 29 Nov 2019 13:22:58 +0100 Subject: [PATCH 2/3] can-j1939-kickstart: update documentation for testj1939 testj1939 need to use -B (broadcast) flag to be able to send or receive broadcast packages. Signed-off-by: Oleksij Rempel --- can-j1939-kickstart.md | 53 ++++++++++++++++++------------------------ 1 file changed, 22 insertions(+), 31 deletions(-) diff --git a/can-j1939-kickstart.md b/can-j1939-kickstart.md index 8f338e1..f195b67 100644 --- a/can-j1939-kickstart.md +++ b/can-j1939-kickstart.md @@ -33,7 +33,7 @@ testj1939 can be told to print the used API calls by adding **-v** program argum Do in terminal 1 - ./testj1939 -r can0: + testj1939 -B -r can0 Send raw CAN in terminal 2 @@ -59,7 +59,7 @@ is not meant for us and *testj1939* does not receive it. Binding a can-j1939 socket to a source address will register allow you to send packets. - ./testj1939 can0:0x80 + testj1939 can0:0x80 Your system had, for a small moment, source address 0x80 assigned. @@ -67,7 +67,7 @@ Your system had, for a small moment, source address 0x80 assigned. Terminal 1: - ./testj1939 -r can0:0x80 + testj1939 -r can0:0x80 Terminal 2: @@ -87,37 +87,42 @@ Open in terminal 1: And to these test in another terminal - ./testj1939 -s can0:0x80,0x3ffff + testj1939 -B -s can0:0x80 can0:,0x3ffff This produces **1BFFFF80#0123456789ABCDEF** on CAN. +Note: To be able to send a broadcast we need to use, we need to use "-B" flag. + ### Multiple source addresses on 1 CAN device - ./testj1939 -s can0:0x90,0x3ffff + testj1939 -B -s can0:0x90 can0:,0x3ffff produces **1BFFFF90#0123456789ABCDEF** , ### Use PDU1 PGN - ./testj1939 -s can0:0x80,0x12345 + testj1939 -B -s can0:0x80 can0:,0x12300 emits **1923FF80#0123456789ABCDEF** . -Note that the real PGN is **0x12300**, and destination address is **0xff**. +Note that the PGN is **0x12300**, and destination address is **0xff**. ### Use destination address info +Since in this example we use unicast source and destination addresses, we do +not need to use "-B" (broadcast) flag. + The destination field may be set during sendto(). *testj1939* implements that like this - ./testj1939 -s can0:0x80,0x12345 can0:0x40 + testj1939 -s can0:0x80 can0:0x40,0x12300 emits **19234080#0123456789ABCDEF** . The destination CAN iface __must__ always match the source CAN iface. Specifying one during bind is therefore sufficient. - ./testj1939 -s can0:,0x12300 :0x40 + testj1939 -s can0:0x80 :0x40,0x12300 emits the very same. @@ -129,13 +134,13 @@ __sendto( *peername* )__ , and only one is used. For broadcasted transmissions - ./testj1939 -s can0:0x80,0x12300 :,0x32100 + testj1939 -B -s can0:0x80 :,0x32100 -emits **1B21FF80#0123456789ABCDEF** rather than 1923FF80#012345678ABCDEF +emits **1B21FF80#0123456789ABCDEF** Destination specific transmissions - ./testj1939 -s can0:0x80,0x12300 :0x40,0x32100 + testj1939 -s can0:0x80,0x12300 :0x40,0x32100 emits **1B214080#0123456789ABCDEF** . @@ -146,21 +151,7 @@ It makes sometimes sense to omit the PGN in __bind( *sockname* )__ . J1939 transparently switches to *Transport Protocol* when packets do not fit into single CAN packets. - ./testj1939 -s20 can0:0x80 :,0x12300 - -emits: - - 18ECFF80#20140003FF002301 - -This is the first fragment for broadcasted *Transport Protocol*. -_testj1939_ returns before the subsequent packets can leave, and -as the last socket on the system closes, can-j1939 effectively -cleans up all resources. Real-world applications will run like forever, -and will not encounter this side-effect. - -Try again, and instruct _testj1939_ to keep the socket open for 1 second. - - ./testj1939 -w1.0 -s20 can0:0x80 :,0x12300 + testj1939 -B -s20 can0:0x80 :,0x12300 emits: @@ -178,11 +169,11 @@ First assign 0x90 to the local system. This becomes important because the kernel must interact in the transport protocol sessions before the complete packet is delivered. - ./testj1939 can0:0x90 -r & + testj1939 can0:0x90 -r & Now test: - ./testj1939 -s20 can0:0x80 :0x90,0x12300 + testj1939 -s20 can0:0x80 :0x90,0x12300 emits: @@ -200,8 +191,8 @@ This overhead scales very good for larger J1939 packets. ### Change priority of J1939 packets - ./testj1939 -s can0:0x80,0x0100 - ./testj1939 -s -p3 can0:0x80,0x0200 + testj1939 -B -s can0:0x80 :,0x0100 + testj1939 -B -s -p3 can0:0x80 :,0x0200 emits From 153501c0ab383e3a2ec2cee86d232f7cf3889a33 Mon Sep 17 00:00:00 2001 From: Oleksij Rempel Date: Mon, 2 Dec 2019 08:29:45 +0100 Subject: [PATCH 3/3] can-j1939-kickstart: remove "Use source address" example This example do not really demonstrate UAPI or testj1939 functionality. So, remove it. Signed-off-by: Oleksij Rempel --- can-j1939-kickstart.md | 9 --------- 1 file changed, 9 deletions(-) diff --git a/can-j1939-kickstart.md b/can-j1939-kickstart.md index f195b67..bc8f9de 100644 --- a/can-j1939-kickstart.md +++ b/can-j1939-kickstart.md @@ -54,15 +54,6 @@ In J1939, this means that ECU 0x40 sends directly to ECU 0x41 Since we did not bind to address 0x41, this traffic is not meant for us and *testj1939* does not receive it. -### Use source address - -Binding a can-j1939 socket to a source address will register -allow you to send packets. - - testj1939 can0:0x80 - -Your system had, for a small moment, source address 0x80 assigned. - ### receive with source address Terminal 1: