start	end	text
1510	7620	All right, folks. Welcome today to All Aboard the Can Bus or Motorcycle.
7620	11680	Two wires, two wheels, bikes can do, can too.
14520	21800	In today's talk, we will cover who am I, a little bit about myself,
22650	29520	the bike and brand. I feel to completely understand the essence of this project.
29520	35220	The bike's a little bit on the rarer side, so we'll cover a little bit about that.
35420	41680	Why the project inspiration and purpose. Some of the hurdles that came into play when
42900	49400	working with the motorcycle as opposed to a car. And then the project begins, what I used,
49400	56160	what I built, the hardware involved with the project. I built an engine simulation
56940	64420	and I did quite a bit of CSV parsing and data analyzing with a Python script I made.
64440	69320	And then we'll talk a little bit about what's the future of the project.
71930	77670	So who am I? I'm Derek. I've been riding motorcycles for about 10 years.
78550	83650	I've been a developer and InfoSec hobbyist for about 15 years.
83650	91150	I currently work as director of IT for a food and beverage automation company.
91410	97150	If you're interested in continuing to follow this project after this talk, you can follow me on
97150	102730	Twitter, CanBusDutch. If you have any questions that aren't answered or you don't get a chance
102730	110330	to ask them at the end of the talk, you could email me at CanBusDutch, gmail.com. And all the
110330	118630	code talked about can be found at my github, github.com slash CircuitWorks1.
119930	132790	So this is my bike, an EBR 1190 RX. Those of you not familiar with EBR or the Buell brand,
132790	137550	Eric Buell, the founder, was a Harley engineer who liked racing motorcycles.
138230	143910	They make the only, or they, yeah, they're the only production sport bike made and designed in
143910	151410	the USA. They're the only American-made motorcycle to ever score points in World Superbike. And they
151410	157870	won the 2009 Daytona Superbike Championship without a single DNF. Those not into power sports,
157870	163470	it stands for did not finish, which means no engine failures, and more importantly,
163470	172770	no accidents. They manufactured nearly 140,000 motorcycles in 15 years when acting as a Harley
172770	181270	subsidiary. And in 2009, after Harley-Davidson axed Buell, they came back as Eric Buell Racing
181270	190430	and sold 65 bikes in 18 months, garnering $3 million in revenue as a startup. And sadly,
190430	195330	now it's a company teetering on the edge of existence.
197150	205350	So here's a few Buells and EBRs, some a face only a mom could love. But that top bike there in the
205350	213230	top left is the bike that helped them fund EBR. It's the EBR 1190 RS. And then you'll see the
213230	222350	same bike I have, the EBR 1190 RX. And then the EBR 1190 SX, which is the same as the RX,
222350	232450	just in a different trim. And then down here, we take a look at the Buell XB9S, which utilizes a
232450	242690	Harley-Davidson Sportster power plant. And then the EBR XB9R, or sorry, the Buell XB9R. And then
242690	255690	finally, the Buell 1125R. And we can't forget, that is the 2010 Buell Blast, which is kind of
255690	265830	an inside joke amongst the Buell community. So now let's get into it. So after about six months of
265830	273890	owning my EBR 1190 RX, I was on a large group ride where I did about 100 miles in a day.
275250	282890	And on my way back home, my dash fell apart. Luckily, I didn't lose anything.
282890	291990	My screen there held on by the ribbon to the rest of the display. And when I got back home,
291990	302690	I reassembled it. But sadly, I started receiving a comm error. And after about a few months of
303890	310370	you know, surfing around the Buell Facebook groups and forums, I started to realize I wasn't the only
310370	320510	one. There was this guy, and this guy, and this guy, and this guy. Well, you get the point.
321690	329250	So sadly, apart from these comm errors, there was also individuals who
330150	338270	had their dash rattle to pieces, just as mine did. And at the time, the future of EBR was being
338270	344350	decided by the courts as they had filed for receivership, which is a similar process to
344350	354190	bankruptcy. And there was zero parts availability. So because I'm not only stupid, but also ambitious,
354190	362970	I decided to look into designing an aftermarket dash. And that's when I realized it probably
362970	371690	wouldn't be as easy as I thought. The main issue I ran into is that there is no diagnostics
371690	380390	standard in the motorcycle industry. OBD2 is kind of a large plug, hard to fit on a small vehicle,
380390	388850	and not really ideal for motorcycles. Although we will see the OBD2 standard is used on a few
388850	397050	manufacturers. And from what I've been told, that it is becoming a standard in Europe.
398890	408870	So there are universal diagnostic tools, although the bite offset, scaling factor,
408870	414290	all of that good stuff is different for every manufacturer. And in order for these universal
414290	420250	tools to obtain that information, the manufacturers charge a lot of money. So these tools
420930	430650	are very expensive. Not only that, but the likelihood of finding a universal diagnostics tool
430650	438470	that works with a bike with only about a thousand of them manufactured in the world
439330	446710	is slim to none. You aren't going to find. So let's take a look at the...
448410	455130	we'll take a peek into the motorcycle diagnostics port world. In this slide alone,
455130	464730	we have two Kawasaki, two Hondas, two Suzuki connectors. And there we go. There we have a
464730	472470	four pin Harley diagnostics cable. And we could see there that Piaggio, Triumph, and Victory
472790	484310	all use the vehicle standard OBD2. And then here we see another Kawasaki connector.
485790	496690	And here we have the Buell diagnostics port. And then we have another Kawasaki cable.
498190	505310	And this is one of my favorites. So this MV Agusta four pin cable down here
505310	513970	is actually the same connector used on Hondas, but it has a separate pinout. So if you accidentally
513970	525340	use the MV Agusta connector on your Honda, you will fry your ECM. And then here's another one
525340	529500	that kind of grabs my attention. Down in the left hand corner there, we have the Harley Davidson
529500	535400	CAN six pin cable. If you remember, I just mentioned they had a four pin diagnostics cable
535400	545200	and a six pin CAN cable. And as we all know, CAN is a two wire signal. So why couldn't they
545200	553560	have just jammed the diagnostics and CAN into one cable? Who knows? And last but not least,
553560	562160	we have the Benelli cable there. But overall, that's 37 different connectors for about 25
562160	571660	different manufacturers. Kind of a headache. But luckily, we have CAN.
572640	579260	Most European and Japanese manufacturers began implementing a CAN bus system on
579260	587380	their bikes around 2003. This includes Ducati, BMW, Honda, Kawasaki. And the American manufacturers,
587380	592200	as with most things when it comes to automotive, were a little bit late to the CAN party.
592300	600320	Buell first implemented a CAN system on the 2008 release of their 1125. And Harley's first
600320	608740	CAN based bike wasn't until 2011. And it wasn't until 2014, that all Harleys were equipped with
609220	615840	CAN bus. Information was a little bit lacking when it came to the Polaris brands Indian and
615840	626380	the now defunct Victory. But I believe they started using CAN around 2013. So let's hop
626380	634540	into what exactly my ECM comprises of. The microcontroller is a microtechnology PIC device.
635400	646040	The diagnostics protocol is a single wire variable pulse width, J1850. And the CAN protocol
646040	654600	is 500 kilobits a second, 11-bit IDs, 20-ohm termination, and least significant bit first.
657310	663070	When it came to hardware for my project, I started out with this Seed Studio device.
663070	670270	But after the second one failed me, I navigated over to using the the Cannibal device, which
670270	680570	was much more reliable. And software-wise, I started off using the Seed Studio software, but
681570	686430	ended up converting over to Busmaster after I purchased the Cannibal device.
689330	698250	So, after doing quite a few CAN capture sessions and figuring out some of the CAN definitions from
698250	704290	reading CAN packets directly from the bike, I was kind of over the idea of spending hours in
704290	711010	the hot garage huffing exhaust fumes. So I thought, why not try some engine simulation?
711610	716410	The most important part for my bike when simulating the engine sensor data is the
716410	726370	crankshaft sensor output. The ECM won't really acknowledge some of the other data if the crankshaft
726370	734690	sensor output is not reading correctly. On my bike, the crankshaft sensor produces two waves,
734690	742010	180 degrees at a phase with each other. The wave is generated using a Hall sensor and a stepped
742010	749750	rotor tone ring surrounding the stator magneto. There are 34 steps and a timing gap the equivalent
749750	755870	to two wavelengths, or two steps. So, it's essentially 36 steps. And there we have a
755870	763530	picture of it. You can see the timing gap there, pretty common. And now let's take a look at it.
763530	770790	There we go. A few oscilloscope readings of the output, so I know exactly what I'm recreating.
772950	780930	And so, how do we simulate it? There's 36 steps, one full step every 10 degrees, 360 degrees in a
780930	790270	circle. We pick an RPM. For math's sake, we'll do 6,000 RPMs. And then, since we all know RPM is a
790270	796510	measurement of minutes and Hertz is a measurement by seconds, we'll have a math equation that looks
796510	805930	something like the following. RPM divided by 60 seconds times 36 steps. And we get a wavelength
805930	819330	of 3.6 kilohertz to simulate the 6,000 RPMs. So, the code. What we do is we take the frequency
819330	827930	input by the user through the serial monitor. I did all this using an Arduino Teensy. And
830110	837890	we calculate the time to execute both a 34-wave cycle and a 36-wave cycle in microseconds.
838170	847550	So, we set our variables there, RPM time and RPM restart. And then, our code logic
847550	855930	looks something like this. If the wave start time is greater than RPM time,
856710	864670	then we stop the wave. And if wave start time greater than RPM restart, we restart the wave.
864810	872370	So, basically, what's happening here is we produce a wave for 34 seconds.
873010	878010	And then, once the time hits greater than 34 seconds, we stop it.
878550	883990	And then, we turn it back on once the time hits greater than 36 seconds. So,
883990	894890	we have those 34 steps with a two-step pause. And now, let's take a look at what we got. And
894890	901370	there's our oscilloscope output. We got the 34 steps and then the blank spot, the equivalent
901370	912810	two steps. Now, we'll look into doing the mile per hour, the speed. The speed sensor simulation
912810	921090	is a bit more basic because there's no timing gap. So, simulate our speed sensor. We
923370	930050	will take a given frequency that was input by the user, again, through the serial monitor.
930310	936450	And we'll turn on and off one of the pins rapidly to generate a square wave. So,
936450	942530	we first calculate the period to complete one wave cycle in microseconds.
943070	950110	And then, we divide that by two to find out how long the pin needs to stay in each state
950110	959690	to complete the entire waveform. And we control it with a non-blocking delay here.
959810	967270	So, you can see there, if the delay timer is less than the speed time divided by two,
967270	976870	pin off. And if it's greater, then pin on. And if it's greater than... and once we created two,
977770	984670	a full waveform there, then we restart the timer and go to town again. So,
986030	994670	there we have it. And again, this code for the TNC can all be found in my
995590	1003910	GitHub repository that I gave at the beginning of the talk. So, now that we got our two waves
1003910	1013590	looking good, we'll play with it a little bit. So, aside from the speed and RPM, I also programmed
1013590	1023350	in a few switches so that I could pop back forth the things such as the neutral switch and
1024290	1032650	the gas light and a few other things. So, we'll watch it and give it a try here.
1038060	1043240	So, oil pressure true. And you could see up there, sorry, I forgot to point it out,
1043240	1049560	but the oil pressure light went there. And now we'll change our neutral switch to false. Boom.
1052460	1056840	And then low fuel set to true.
1060040	1066060	And one thing about the low fuel, as it says right here, it has to remain true for 20 seconds
1066060	1074920	before the ECM flips the low fuel bit to true. So, it'll pop on any second there.
1079380	1083600	And there we go. Low fuel. You see the fuel trip flipped over there.
1087120	1091280	And here's the fun part. RPM frequency 1001.
1095840	1100440	And we got a little bit of RPM going there and speed frequency 300.
1102000	1106240	And now we got a little bit of speed going there. And if you'll notice in a second,
1106240	1121260	the fuel trip odometer goes up to one, the end. So, success. What the heck happened here?
1122360	1133320	Okay. So, let me switch back into presentation mode. So, I...
1134220	1142060	once I did that, I started capturing sessions like crazy. I was capturing everything to a CSV.
1143080	1153960	And, you know, clearly, they, you know, all this data in only one set of eyes.
1153960	1161640	You know, you don't want to go through all that without some software analyzing it. So,
1161640	1168400	I created a Python script that compares two CSVs that were created using the CAN software.
1169340	1179380	In the example I'm about to show, I have two CSVs. One is where I set the oil pressure to true.
1179380	1193610	And the second is where I set the oil pressure to false. So, oops. So, a little bit about
1193610	1209150	my parser here, my Python script. Out of the 15 populated columns used by my software,
1209750	1218390	we only use nine of them. It's the frame ID and then the eight bytes. So,
1222820	1229440	basically, what the Python script does is it looks at the number of times each ID appears and
1229440	1235880	the number of times a hex value appears in each given ID. And then compares that to allow us to
1235880	1242240	have in our outputs the difference in hex value appearances, the increase and decrease percentage
1242240	1249840	of hex value appearances, and appearance of a new hex value in a given ID. And I also programmed it
1249840	1258580	to convert the hex value to binary. So, if we take a look here,
1258580	1264540	this output shows the number of times a hex value appears in a given ID. If its appearance
1264540	1270980	account was zero in either of the CAN capture session, the line will be highlighted in red.
1276100	1282200	The line will be highlighted in red if the number of hex value appearances is equal to
1282200	1293980	the number of appearances of its given ID. So, meaning that in one CAN capture session,
1293980	1299960	the hex value appeared zero times and in the other one it appeared 100% of the time. So,
1299960	1306960	if we take a look here, we have that happen four times in this one. There is hex value 19
1307920	1318800	and 99 which appeared in ID 202 100% of the time while appearing in one CAN capture session while
1318800	1327160	appearing zero times in the other one. And then we have down here hex value 20 and hex value 60
1327160	1336560	which appeared in ID 451 100% of the time in one file and zero percent of the time in the other.
1336840	1347500	And I can confirm that after figuring this out, I was able to verify that
1348060	1360580	an ID 202 byte A bit 7 is the low oil warning light and ID 451 byte H bit 6 is an oil pressure
1360580	1375160	True, false, bit. So, we can see... so, let's go on. Again, this, which we'll call it, this
1375160	1388400	Python script is available at my GitHub account to take a look at and analyze your own CSVs.
1388960	1396340	And now we'll look. Now that I have the... now that I've reversed a whole bunch using the Python script
1396960	1404140	and, you know, I was able to trigger all types of ECM settings to reverse,
1404140	1416040	I developed my first prototype here. This project was used with a... I'll wait and let it go.
1470920	1487200	All right. So, that was developed using a Nextion display and a ESP32 with some... with a CAN input on it.
1487460	1496480	And, you know, originally I was going to make this from the ground up, but, I don't know, I just
1496480	1501960	decided when everything's exposed to the elements, like on a motorcycle, it probably wasn't the
1502460	1514320	best route to go. So, I ended up purchasing an AIM MXS 1.2 Strata, which so far I've loved
1514320	1521780	and highly recommend. I haven't actually put it on the bike yet, but here's a little video of
1521780	1529260	what I got going. We're going to let the bike warm up. You'll see the light over here
1529260	1532500	for the engine temperature. We'll go from blue to green
1533740	1539740	when the engine is warm, and then I'll give it a few revs to show off.
1596200	1604120	All right, there we go. So, what's next for the project? Aside from finishing the development of
1604120	1611520	the dash, you know, I'd really like to stretch my Python script a little bit further. Right now,
1611520	1619640	all the IDs to my bike are hard programmed into the Python script. Ideally, you know,
1619640	1625300	this Python script would be able to look at the ID column, grab all the individual IDs that are in
1625300	1632360	it, and then start analyzing then. You know, I spend a lot of time as a front-end developer,
1632360	1639160	and I'd also like to make the Python script output a little bit prettier. I think some
1639160	1645640	data visualization that I've started playing with, you know, would really spice things up a bit and
1645640	1654920	kind of make things easier to point out. Some byte annotation. Right now, the Python script
1654920	1663500	only parses data based on the hex values and the IDs. So, you could end up with some confusion on,
1663500	1671260	you know, if you're getting hex value changes in different bytes in the same ID and stuff like
1671260	1676600	that. And then, I'd also like to implement some bit flip search, which, you know, would help
1676600	1685160	things with, like, the ground triggers or ground switches and stuff like that that are in the
1689150	1703330	dash and stuff. So, you know, so anyways, that's about it. You know, I want to give some shout-outs
1703330	1710430	and some thanks. Thanks to the Buell community. There's really nothing like it. Thanks to the
1710430	1716550	man, the myth, the legend himself, Eric Buell, and those involved with Buell Motorcycles and EBR.
1716810	1722350	And, you know, even though you guys probably hate me, I want to say thanks to Tim Blumenberg at IDS,
1722350	1730430	who is the company that developed the ECM, and Bill Melvin, who currently owns EBR. And then,
1730430	1737010	some of my gearhead friends that I wouldn't have been able to do this without. Jacob,
1737010	1744990	Zach, Rob Weaver, Leland. You know, it couldn't have been done without everyone. Thanks.
1746810	1747250	you
