![]() |
OpenStint laptiming decoder
I'm proud to announce OpenStint, an open-source, RC3-compatible laptiming decoder project. Instead of custom hardware builds, it relies on inexpensive, ready-made software-defined radios. The primairly audience are small clubs and friendly gatherings, who either like thinkering or have no budget for a ready-made solution. It is also useful for tracks where RC3 compatibility is required, but compatible decoders are not available any more.
PROJECT URL: github.com /zsellera/openstint The project is accompanied by a reference design of a transponder, and a low-noise balun & preamplifier side-project, custom-designed for RC timing loops. HIGHLIGHTS
To start using it, the necessary steps are detailed in the project's README. In short, you'll need:
PICKUP ANTENNA The detector antenna uses a similar design as other commercial solutions: it is a parallel wire transmission line, with a balun on one end, and a 330/470 ohm termination on the other end. The wires should be ideally 2 mm^2, and separated by 25 cm from each other. Use the 330 ohm termination for in-the-ground installations, and the 470 ohm termination for overhead wires. The inexpensive NoElec 1:9 HF balun gives a very good impedance match for the overhead installations, and is also usable for in-the-ground setups. Note: I use the term "antenna" and not "loop". From a geometrical standpoint, it is a loop for sure. From electrical perspective, this is a parallel-wire transmission line, an unshielded arrangement to pick up external disturbances. There is no need for "resonance matching" or other similar magic. TRANSPONDERS While the project can decode RC3-compatible transponders, the preferred protocol is the OpenStint transponder protocol. The protocol is well documented, it makes sense (no deliberate obfuscation) and has pretty good SNR characteristics. A reference implementation is available (schematics, pcb and firmware). At club level, one can manufacture 40 pcs of these transponders for $130 (a cost less than a single RC4 hybrid). The reference design is available at: github.com /zsellera/openstint-transponder/ The reference design produce comparable signal levels to the commercial offerings when running from 7.2 V (servo port of the receiver). It requires 4.5 V minimum to function properly, and testing was done up to 8.5 V (2s). The output level depends on the input voltage. Note: this is a "v2" design shared, I just submitted an order at JLCPCB for it. I'll update this thread when I could properly test them. PREAMPLIFIER The project comes with an optional, low noise preamp + filter, that does the differential to single-ended conversion as well. It fits into a Hammond 1590L die-cast aluminium case. It is useful at overhead antenna installations and in noisy environments. The design offers a good +13 dB power gain. The onboard filters get rid of out-of-band interferring radio signals, which may get downconverted to baseband due to non-idealities in the inexpensive radio receivers. Project url: github.com /zsellera/openstint-preamp WHAT'S NEXT? On the short run, I'd like to focus on:
HOW CAN YOU HELP OR CONTRIBUTE? First off, this project converts a hardware problem into a software one, which is usually more likely to get solved.
|
|
Yesterday we could test the system at our club. It ran the whole day, and counted 3170 laps in total. Out of these, 801 were made with OpenStint transponders, and the rest with RC3/RC4Hybrid/clone ones. I received no complaints about missed laps from people participating in the test.
As it was an indoor event and the pickup antenna was placed under the carpet. I used a lightly coated 26 AWG (0.14 mm2) wire. The wire separation was 30 cm, and a 330 Ohm termination resistor was soldered onto the remote end. At the business end, I added an openstint-preamp (see github for shematics), which was connected to the HackRF One. The HackRF was connected to a raspberry pi, which streamed the laptimes to a makeshift dashboard people could access with their phone. I set the amplifier gains of the HackRF with the help of SDRAngel. It's a great tool to do all sort of RF magic with SDRs. To figure out the gains, we only need its' spectroscope though. Open the HackRF device with it, tune to 5 MHZ, set sample rate to 5 MSPS and IF filter bandwidth to 1.75 MHz. Park a car with a well-placed, strong transponder over the loop. Then, start from low values, and increase the LNA gains until you see sidelobes on the spectroscope. It indicates clipping. If seen, back off by 8 dB. Then do the same with the VGA gains (2 dB steps). I ended up starting the decoder with the following parameters: ./openstint -l 24 -v 22 -b The antenna was placed to a slow section of the track. During passings, a typical RC4-hybid registered 55-60 hits, while an OpenStint transponder did 170-180. This is in-line with the expectations, as the openstint transponders produce ~3x more decodable messages as an RC4-hybrid does. Unfortunately, the decoder also reported (probably) RC3 status messages as passings. I added a patch, so next time (hopefully) this will be not a problem. Unfortunately I'm just guessing though. The real solution would be a monitor mode, similar to what RCHourGlass has, to aid solving these mysteries. |
Hello,
your work is incredible. I have a question, i want to detect when the car pass on the loop of our track (mylaps decoder) and send a telemetry signal to my radio (MT12 with elrs and csrf telemetry) It seems i can do it with your transponder modifying the code to not emit and only a signal high on a pin when the car pass on the loop. (now i use a gps inside the car to detect the pass of my car for my lap timing on the MT12) By using your transponder as a a loop detector ? Do you know how to do this ? |
You can absolutely achieve this. Chatgpt can even produce simple integrations. This was my prompt:
Write a python program which connects as a subscriber to a zeromq publisher, and toggles pins on a raspberry pi model 3 b+ based in the text messages received. The zeromq publisher implements openstint decoder protocol (URL REDACTED). The interresting messages are "Passings", which start with a letter "P" and has the following charactersistics: ``` P <decoder_timestamp:uint64> <transponder_type:string> <transponder_id:uint32_t> <rssi:float> <hit_count:uint32_t> <evm:float> [other future parameters] ``` Example messages: ``` P 1618706341 OPN 1615544 3.50 64 0.30 P 1618714251 OPN 1615544 3.08 40 0.25 ``` Write a program that identifies transponders ids specified in a python dictionary, and sets the specified pin TRUE for 1 second whenever the transponder is detected, then resets the pin to FALSE: ``` TRANSPONDER_PINS = { '1615544': 4 # transponder_id, GPIO pin } ``` Use BCM pin numbering on the raspberry pi. gist.github.com zsellera/5b5b2cb178dd1cdd0c35bc6f06a974b8 |
now I'm interested and getting this system going. seems like a fairly cheap way for a local low budget club to get lap counting going.
|
This is fantastic. I'm ordering some SDR tools and hopefully I can start working and contributing to this project. Thank you so much for all your hard work.
|
I have put in a few hours of getting a STL-SDR to work. I am detecting the R3/R4 Hybrid, the issue is that i am only getting it 1 out of 25 times. My issues now is that i just don't know enough about SDR in general so my learning curve is steep. I am relying on AI alot right now. fun project though. my family is very confused with all the wires on dinner table. :)
Lowered the threshold and now getting better detection, but the EVM is not good and not getting transponder code detection. YET. might be my antenna build From AI: You're getting excellent frame detection (EVM as low as 0.45-0.46) but the demodulation still needs the preamp to reliably decode transponder IDs. The software side is working well - it's purely a signal/noise ratio limitation now." [DEBUG] Max correlation: 0.7760 (threshold: 0.67), DC offset: (-1, 0) F OPN T:24743 RSSI:-4.41127 EVM:0.619048 [0, 223, 0, 0, 1, 255, 255, 255, 255, 64, 246, 3, 0, 222, 176, 82, 220, 0, 255, 0, 0, 22, 114, 182, 0, 0, 226, 0, 255, 0, 0, 0, 255, 6, 0, 255, 30, 0, 3, 95, 45, 36, 0, 20, 230, 94, 226, 97, 62, 151, 3, 0, 0, 210, 0, 166, 79, 250, 4, 0, 242, 106, 249, 0, 0, 255, 17, 0, 24, 255, 0, 0, 0, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 255, 247, 104, 80, 119, 136, 133, 129, 128, 128, 128, 128, 128, 129, 129, 127, 128, 127, 129, 129, 127, ] |
Nice, thanks for working on this. I tested your fork, and it works for me as well.
This is a typical passing: [DEBUG] Max correlation: 0.9223 (threshold: 0.70), DC offset: (0, 0) S 9346 -44.558327 0 451 426 P 9169 OPN 6551418 -14.75 3721 0.53 Detection threshold: the lower you set the correlation threshold, the more likely it recognises random noise as valid preamble. On very low settings, it will recognise practically anything as valid frame. On the other hand, I indeed see worse correlation with the rtl-sdr implementation. You can get it into shape by not tweaking the resampling's filter bandwidth (just use resamp_crcf_create_default). EVM: yep, it's far from being nice, but for a different reason (it's bad with HackRF as well, I think the symbol synchronizer is used with an incorrect filter). Amplifiers: The "RSSI:-4.41127" means you're using practically the full scale of the radio's input. |
Hi,
There is a writeup with expected images in the repository on how to test a given setup with SDRAngel: github.com/zsellera/openstint/blob/master/docs/setup-tutorial.md#testing-the-system-so-far If you can receive signal using SDRAngel, you should be able to do so with the openstint software as well. If there is no signal visible with sdrangel, try: 1. Can you receive any other signals with your hackrf, like fm-stations? 2. What balun/preamp do you use? It might need power from the built-in bias tee. Verify the voltage requirements, as the HackRF supplies 3.3 V 50 mA max. 3. Verify the transponders transmit. The transponders need 4.5 V minimum to transmit (this is a limitation of the mosfet driver used). The blinking is a good sign btw. 4. If you have access to rc3 or rc4 hybrids, you can give a try to those as well.
Originally Posted by pikwas
(Post 16237228)
Hello everyone. Project is great but I`m having some troubles to get it working. I ordered transponders from JLCPCB, did compile of hex file under ubuntu next I programmed transponder with stm32 cube programmer via st-link v2. After powering up transponder blinks every second so it`s probably working properly. Next I compiled openstint under ubuntu. Nex I`m putting hackrf one to usb under ubuntu with openstint, connecting balut to hackrf and wire loop with resistor to balun as antenna. One thing which I changed is openstint is "float noise_floor = 10.0f * std::log10(noise_power) - 20.0f * std::log10(ADC_FULL_SCALE);" from log10f to log10 because problems with compiling. Could it be a reason ? I`m running openstint but I`m not getting any passes. How can I debug ? Where to search for problem ? I tried with -a -m -b -l -v parameters but with no success. Here is my output:
:~/openstint/build/src$ ./openstint Listening on tcp://*:5556 HackRF RX: freq=5000000 Hz, sample_rate=5000000 Hz, LNA=24, VGA=24 HackRF SerNo.: 0000000000000000919068dc35943b1f Streaming... stop with Ctrl-C S 5019 -38.499035 2 0 0 S 10029 -38.502296 2 0 0 S 15041 -38.422245 2 0 0 S 20050 -38.551464 2 0 0 S 25060 -38.39564 2 0 0 S 30068 -38.534252 2 0 0 S 35078 -38.495895 2 0 0 S 40089 -38.576733 2 0 0 S 45099 -38.52184 2 0 0 S 50109 -38.53396 2 0 0 S 55118 -38.50404 2 0 0 S 60128 -38.711315 2 0 0 S 65139 -38.455574 2 0 0 |
It's exciting to see this project coming along, thanks for all your effort. I see you have support for windows using Zround. Registered for it a few days ago but can't download the software until "an admin" approves my account. Next Level Timing also supports Zround protocol among several others. Also seems responsive to adding hardware to their compatibility list. https://nextleveltiming.com/
I'm getting ready to buy the parts for the decoder. Banggood has the Hack RFOne for under $100. I have a couple mrt and rc3 transponders to test it out with. I'm unsure of some things. My plan is: antenna> active SDR loop amp or 1:9 balun (both similar priced ~$12)> RFOne> - from there could I use an HP thin client running linux (i have one already collecting dust) instead of a RPi? Keep this all in a pelican case and connected to wifi. I would then be able to run timing software on a windows PC connected to the same lan ? Regarding the OpenStint transponders, I plan on ordering them once I get the decoder working. I'll gladly share any .stls I create for 3d printed cases. Do you have any recommendations for flashing them? I figure it wouldn't be too hard to make a jig with pogo pins. |
HP thin client
I expect it to work; make sure you compile with optimalizations (-O2 or -O3), and it will perform nicely on older / less-capable CPUs (I'll update docs on how to do it). Note: you can run the whole stack on a single windows laptop, the rbpi/minipc is a nice-to-have. Active SDR loop amp or 1:9 balun I'd prefer the active solution; the antenna *might* pick up disturbances (ie. sparking of motor commutation), and having an active device provides some additional safety. I haven't had issues with the 1:9 baluns neither so far (note though, I'm using the "clifford version" hackrfs, which have additional frontend protections). Timing software You can download ZRound Suite without admin approval or registration. NextLevelTiming: unfortunately (last time I checked) it supports only serial port / usb based decoders, the TCP-based ZRound protocol is not supported. Programming JIG for transponders: Any contribution is welcome, and a programming JIG is a nice idea. If you share yours, I'll to link to it from project readme; or send a PR to the project having the files inside. For now, I use pogo pins soldered to 2 mm pitch row header glued together. |
Timing software You can download ZRound Suite without admin approval or registration. NextLevelTiming: unfortunately (last time I checked) it supports only serial port / usb based decoders, the TCP-based ZRound protocol is not supported. It hadn't really occurred to me the difference in implementation of your decoder vs something like Hourglass until you spelled it out for me. I do ok following instructions but regarding hardware and software creation and implementation I'm fairly ignorant. Having now messed around with Zround, Next Level does seem rather simple in comparison. Still, I'll submit a request through their website and link your github. Maybe it'll encourage them to give your decoder a look. I expect to have a Hackrf by mid February. I'm sure I'll have more questions. While I wait I'll try to get familiar with SDR. I'll probably order some OpenStint transponders in the next few days as well. I'm sure I'm not alone in appreciating how the affordability of this whole setup, especially sub $5 transponders, has the potential to benefit this expensive hobby. |
Open practice lap counter application - FYI
https://github.com/zsellera/openstint-lapcounter/ | live cloud instance Features:
On our last practice day, this was my transponder. I set up a demo track so you can see how it works live. The source code is available, so you can set up your own local & cloud instances as well. Although it uses the "openstint" naming, I have no long-term plans with this project. I just wanted to share it, as an alternative to ZRound practice mode. |
I have successfully installed OrangePI 3b+RTL_SDR V4, but I'm having trouble connecting to ZRount. When I connect to the ZRount device, I select ZRount and set the IP and PORT. Although the connection is established, no vehicles pass by (-ID), and the connection drops after a while.
root@orangepi3b:~/openstint/build/src# ./openstint -r -g 40 -t 0.67 -p 5556 Detection threshold: 0.67 Listening on tcp://*:5556 Found Rafael Micro R828D tuner RTL-SDR Blog V4 Detected Device: Generic RTL2832U OEM (SN: 00000001) RTL-SDR Blog V4 detected: using upconverter for HF (direct sampling disabled) [DEBUG] Offset tuning ENABLED. Hardware freq: 4750000 Hz (target: 5000000 Hz) RTL-SDR optimization: Using 2.5 MSPS hardware rate with 2:1 upsampler to reach 5.0 MSPS Exact sample rate is: 2500000.107620 Hz [DEBUG] Software mixer ENABLED. Phase step: -0.628319 rad/sample RTL-SDR gain set to 19.7 dB RTL-SDR RX: freq=5000000 Hz, sample_rate=5000000 Hz Streaming... stop with Ctrl-C S 1080 -inf 0 115 101 [DEBUG] Max correlation: 0.9408 (threshold: 0.67), DC offset: (0, 0) S 2082 -45.361607 0 433 399 [DEBUG] Max correlation: 0.9440 (threshold: 0.67), DC offset: (0, 0) S 3084 -45.361607 0 411 373 [DEBUG] Max correlation: 0.9312 (threshold: 0.67), DC offset: (0, 0) S 4086 -45.361607 0 402 370 P 3153 AMB 4747720 -4.34 1312 0.55 [DEBUG] Max correlation: 0.9272 (threshold: 0.67), DC offset: (0, 0) S 5088 -46.39358 0 81 69 [DEBUG] Max correlation: 0.9299 (threshold: 0.67), DC offset: (0, 0) S 6090 -45.639183 0 326 297 [DEBUG] Max correlation: 0.9264 (threshold: 0.67), DC offset: (0, 0) S 7092 -45.639183 0 400 371 [DEBUG] Max correlation: 0.9269 (threshold: 0.67), DC offset: (0, 0) S 8094 -45.639183 0 402 366 [DEBUG] Max correlation: 0.9273 (threshold: 0.67), DC offset: (0, 0) S 9096 -45.639183 0 402 362 [DEBUG] Max correlation: 0.9334 (threshold: 0.67), DC offset: (0, 0) S 10098 -45.639183 0 403 365 [DEBUG] Max correlation: 0.9361 (threshold: 0.67), DC offset: (0, 0) S 11100 -45.639183 0 400 374 [DEBUG] Max correlation: 0.9369 (threshold: 0.67), DC offset: (0, 0) S 12102 -45.639183 0 407 369 |
Do you run the `integrations/bridge-zround.py`?
The OpenStint project defines its own protocol, but it's currently not supported by any other laptimers. By default, it listens on port 5556. The ZRound is compatible with many laptimer protocols, but also defines its' own. By default, it connects to port 5001. There is a python-based integration to convert between the two. It has to run as well, meaning there are 3 things you have to start: openstint, zround-bridge and zround manager. OpenStint:5556 <---> zround-bridge:5001 <---> ZRound Once I - or someone else - manages to build a P3/MyLaps bridge, we can use this decoder with LiveTime/RC-timing as well. |
I haven't run `integrations/bridge-zround.py` because my English is terrible, and I relied entirely on translation software, so I missed many important points.
It's already evening here, so I'll test it tomorrow. |
I placed an order for the transponders this past weekend from JLC. The total for 5 boards came out to a bit over $210 USD ($60 in tariff+$50 in shipping) with a $10 new user coupon for five panels on github. It appears production won't be effected by the February holidays and they'll be finished and shipped out by the end of the week.
I did get a warning the 20mhz crystal used on the board was in low supply, preventing me from ordering 10 boards. The suggested alternatives use a different footprint, HC-49S-SMD. If you broaden the search there are SMD3225-4P alternatives but the capacitance is different from the 15pf in the bom. |
Originally Posted by durtman
(Post 16242107)
I placed an order for the transponders this past weekend from JLC. The total for 5 boards came out to a bit over $210 USD ($60 in tariff) with a $10 new user coupon for five panels on github. It appears production won't be effected by the February holidays and they'll be finished and shipped out by the end of the week.
2025 October (first design) - 5 panel, 40 pcs @ $130 2025 December - 5 panel, 40 pcs @ $160 (extra components were added though) 2026 February - 5 panel, 40 pcs @ $195 The price increase is quite visible. The MCU's price went up considerably for sure (~$.4x -> $.62), but I don't know what else...
Originally Posted by durtman
(Post 16242107)
I did get a warning the 20mhz crystal used on the board was in low supply, preventing me from ordering 10 boards. The suggested alternatives use a different footprint, HC-49S-SMD. If you broaden the search there are SMD3225-4P alternatives but the capacitance is different from the 15pf in the bom.
|
I'm pleased that the Windows version supports RTL-SDR V4, but during testing, I encountered a very low accuracy issue when using an RCHourglass transponder.
However, dpereda doesn't have this problem (https://github.com/dpereda/openstint...rtlsdr-support). The following information suggests that heating the ceramic oscillating crystal with a soldering iron improves the accuracy after frequency shifting. I also experienced very low accuracy with an RCHourglass transponder using a quartz oscillating crystal, but the frequency shift rate after heating was too low to cause any change. P 245427 AMB 9054415 0.07 3 0 P 245987 AMB 6170831 0.36 3 0 P 246169 AMB 9054415 -0.33 2 0 S 248093 -13.887955 0.6209385 1619 13 P 249921 AMB 5122255 -0.41 2 0 S 253196 -15.625666 0.671906 1571 11 P 252910 AMB 5122255 -0.70 2 0 P 255110 AMB 6170831 -0.80 2 0 S 258264 -14.165384 1.0111554 1549 14 S 263317 -15.54817 0.9497359 1557 11 S 268373 -13.748856 1.1199342 1550 5 P 269396 AMB 6170831 -0.71 3 0 S 273436 -15.75556 1.2064183 1565 10 S 278498 -13.823208 1.0250344 1549 3 S 283561 -15.9267235 0.998238 1555 3 S 288621 -15.964384 0.8444875 1532 2 S 293671 -13.885162 0.93904746 1554 2 S 298726 -15.904615 0.88216096 1575 170 P 298683 AMB 6170831 0.56 305 0 S 303781 -14.011459 1.0007908 1788 139 S 308843 -15.81168 1.163349 1791 704 S 313904 -15.6712 0.694628 1742 1735 S 318978 -14.380028 1.0818797 1687 1682 P 316675 AMB 6170831 0.72 4096 0 S 324032 -15.515686 0.9550401 1673 1264 S 329115 -15.628176 1.1601095 1620 0 S 334154 -15.179371 0.8359169 1610 2 P 334046 AMB 9054415 -0.20 2 0 P 334478 AMB 9054415 0.35 3 0 S 339216 -15.827322 1.096461 1580 11 S 344285 -16.06084 0.9382957 1624 565 P 343604 AMB 6170831 0.67 676 0 S 349338 -15.746948 1.0568093 1733 1396 S 354397 -15.477932 0.5965904 1703 1699 S 359450 -15.817425 1.3155696 1699 1693 S 364531 -13.960957 0.39396092 1725 1720 P 359908 AMB 6170831 0.77 4096 0 S 369607 -13.999393 0.7691634 1669 431 S 374668 -15.633345 0.9228952 1613 4 P 375896 AMB 6170831 -0.04 2 0 P 376513 AMB 9054415 -0.39 3 0 P 378627 AMB 6170831 -0.54 2 0 P 378867 AMB 9054415 -0.28 2 0 |
I have multiple good news about this project.
RTL-SDR v4 SUPPORT Our forum member, @danny325is, added support for RTL-SDR some weeks ago, and is now merged with the rest of the improvements. As RTL-SDR v4 is an inexpensive, ~$40 device, the barrier of entry was lowered significantly. For purchasing options, see their official site, there are multiple options (Amazon/Ebay/AliExpress). Make sure you buy the v4 version, as the decoder was not tested with earlier versions (I just ordered an older one, weeks to arrive). WINDOWS BUILD The project is built for Windows semi-automatically, meaning you can download a .zip, containing the whole project (no installer is needed). You no longer have to install python to use the core integrations, as the zround and p3 bridges are compiled to their own .exe files (each of such file contain the whole python runtime and dependencies, hence the 10 MB+ filesize). As such, once you have the SDR drivers installed: 1. plug in the radio to an USB port 2. double-click on openstint_hackrf.exe or openstint_rtlsdr.exe (and ignore the "untrusted code" warnings - it's not signed, hence the error) 3. double-click on bridge-zround.exe 4. start your ZRound, and set 127.0.0.1 as decoder ip address You might have to allow the firewall exceptions meanwhile. INCREASED RECEPTION QUALITY Firstly, the symbol synchronizer was fixed. Previously about 8-10% of all frames were dropped. With the fixed version, I was able to lower the preamble-detection threshold while still maintaining a very high detection ratio. Long story short, we can detect and decode weaker signals more reliably now. Secondly, a feature called "adaptive equalisation" was added. For super-nerds only: the transmit coils, the antenna and the whole transmit-receive chain has non-idealities, resulting in bit errors. An adaptive equaliser learns these errors and corrects for them. A few cars have to pass, and the system tunes itself. The result of these two improvements, more frames are decoded even in non-ideal radio environments. In ideal ones, EVM figures lower that 0.05 are often observable (rssi > -10 dB; hackrf one). RELIABLE PASSING TIME DETECTION The "point of passing" was determined previously as "point of highest signal strength". Now there is a more sophisticated algorithm implemented. I placed two transponders ~15 mm distance from each other. The new algorithm is reliably able to distinguish if the car passes the loop forward or reverse, based on which transponder passes first (tested at low speeds). EDIT: the p3-bridge feature was removed; contact in private message if you really need it. |
Originally Posted by Oldfan
(Post 16242155)
I'm pleased that the Windows version supports RTL-SDR V4, but during testing, I encountered a very low accuracy issue when using an RCHourglass transponder.
However, dpereda doesn't have this problem (https://github.com/dpereda/openstint...rtlsdr-support). The following information suggests that heating the ceramic oscillating crystal with a soldering iron improves the accuracy after frequency shifting. I also experienced very low accuracy with an RCHourglass transponder using a quartz oscillating crystal, but the frequency shift rate after heating was too low to cause any change. P 245987 AMB 6170831 0.36 3 0 P 246169 AMB 9054415 -0.33 2 0 S 248093 -13.887955 0.6209385 1619 13 However, I'd look for the problem elsewhere in your case. 1. Too much noise or amplifications The "-13.88 dBFS" noise floor measurement is really off. it should be lower than -39.0 ideally. It can be caused by too much gain. During testing, I settled around "-g 20" for rtl-sdr; "-g 30" max. The "0.36 dBFS" and "-0.33 dBFS" indicates the signal you received is clipping. "0 dBFS" means the signal is using the full range of the ADC. As the signal is sinusoid, there is a difference between "peak" and "rms", this value can be over 0.0 - but it shouldn't. It should be max "-3.0" imho. 2. Crystal fails to start / MCU falls back to internal oscillator The initial symbol sync happens on the first 12 bits of the preamble, and there are about 100 bits in total. For a 90* phase shift (so decoding fails), the frequency has to differ by more than 600 ppm. My first Casio hand watch - a used from the '80s - was advertised as "max 1 second per day", which is 12 ppm. While 40+ years passed, I'd expect this level accuracy from a cheap XO today. There are orders of magnitude in difference... I guess the MCU failed to start the crystal, and fall back to some internal oscillator: when you heat the crystal, the microcontroller's temperature is changing as well. 3. You are also right I indeed did removed a makeshift costas loop when I fixed the symbol synchronizer. There is no good reason for the removal, I'll add it back in the coming weekend or so (I simply did not take into account the "failed crystal" case above). It can compensate for 1000+ ppm of clock differences. |
Hi guys, I'm developing a timing software to learn Python. I have implemented the AMB Mylaps protocol, is it difficult to implement this protocol?
|
Originally Posted by Reboot
(Post 16243394)
Hi guys, I'm developing a timing software to learn Python. I have implemented the AMB Mylaps protocol, is it difficult to implement this protocol?
https://github.com/zsellera/openstin...er-protocol.md |
https://cimg2.ibsrv.net/gimg/www.rct...87dd5ca704.jpg
I've had success with the Thin client running OpenStint and detecting my MRT ptx with the Hackrf one and near field probe connected. I'm able to connect it to Zround on my win10 pc, still need to build a loop. Similar success with the windows executables. I got a bit distracted for the last couple weeks using the Hackrf on my windows PC to mess around with tuning into radio stations during my free time. Unfortunately with linux and command line I'm way over my head. I did a new install of ubuntu. I was initially not able to get the openstint.service to work, after a few hours of shots in the dark, I finally used nano to view "openstint.service" and realized I needed to edit it to point to openstint_hackrf and got the service to start up on boot with the hackrf connected. I have bridge-zround.service starting on boot as well. After looking through the process to flash the transponders, I'm lost. So far, I've copied the transponder git, and ran cmake in the firmware directory.
Originally Posted by Openstint-Transponder
cmake -DCMAKE_BUILD_TYPE=Release .
make
Originally Posted by UbuntuThinClient
pi@ostc:~/osptx$
... -- Build files have been written to: /home/pi/osptx/firmware pi@ostc:~/osptx/firmware$ make [ 9%] Generating C011F4.ld [ 9%] Built target CMSIS_LD_C011F4 [ 18%] Building C object CMakeFiles/transponder.dir/main.c.obj cc: warning: ‘-mcpu=’ is deprecated; use ‘-mtune=’ or ‘-march=’ instead cc: fatal error: cannot read spec file ‘nosys.specs’: No such file or directory compilation terminated. make[2]: *** [CMakeFiles/transponder.dir/build.make:76: CMakeFiles/transponder.dir/main.c.obj] Error 1 make[1]: *** [CMakeFiles/Makefile2:436: CMakeFiles/transponder.dir/all] Error 2 make: *** [Makefile:91: all] Error 2 pi@ostc:~/osptx/firmware$
Originally Posted by UbuntuThinClient
pi@ostc:~/osptx/firmware$ st-flash --connect-under-reset --format ihex write transponder.hex
st-flash 1.8.0 2026-03-02T06:46:57 WARN common.c: NRST is not connected 2026-03-02T06:46:57 ERROR common.c: Soft reset failed: error write to AIRCR Failed to enter SWD mode Failed to connect to target Failed to parse flash type or unrecognized flash type |
This is the DIY programming header I use, and the reason there is no "programming JIG" yet:
https://cimg9.ibsrv.net/gimg/www.rct...6c8fec09c5.jpg Aliexpress links: pogo pins: [1] [2] [3] pin header: [4] (2 mm pitch is a less common item, but I had no space on board for 2.54 mm spacing) UV curable resin: local model shop, beauty shop or [5] cables: [6] (female-female both ends; remove plastic socket on one end to fit the pogo pins inside) An en-mass programming requires the pogo pins. The rest is optional. I use the UV-curable resin to secure the cables to the transponder as well (put some over the solder joints). PROGRAMMING Try tools with GUI, like Stm32CubeProg. Here is a precompiled hex, so you don't have to compile it. The programming points are labeled on the silkscreen, note "CLK" is "SWCLK" and "DIO" is "SWDIO". SIMPLEST DECODER SETUP You can use everything from a single Windows machine (decoder + bridge + zround), no need for Raspberry or thin-client: https://github.com/zsellera/openstin...ial-windows.md CLOSING THOUGHTS I know you have more questions than answers here; I'll answer them later when I have more time. I hope this helps already. |
With your help I was able to narrow down the CC error. I had to install the Arm embedded toolchain.
Code:
sudo apt install gcc-arm-none-eabi binutils-arm-none-eabi
Originally Posted by CMakeCache.txt
cd to the firmware directory
nano CMakeCache.txt and search for CMAKE_C_COMPILER:FILEPATH=/usr/bin/cc changed to CMAKE_C_COMPILER:FILEPATH=/usr/bin/arm-none-eabi-gcc-ar
Originally Posted by OpenStintThinClient
Generating ihex file transponder.hex
[ 90%] Built target transponder [100%] Target Sizes: text data bss dec hex filename 5984 312 2500 8796 225c /home/pi/osptx/firmware/transponder.elf [100%] Built target transponder_always_display_size pi@ostc:~/osptx/firmware$ ls build cmake CMakeFiles CMakeLists.txt main.c transponder.elf C011F4.ld CMakeCache.txt cmake_install.cmake _deps Makefile transponder.hex |
Here's a 3d printable jig to hold your transponder securely while programming it. I've got enough spare pogo pins to mail a few out for anyone whose thinking of getting some transponders. If you don't have access to a 3d printer, I'll be happy to send a print as well to those who have bought transponders.
https://cimg0.ibsrv.net/gimg/www.rct...bcb4677340.jpg Available at https://www.thingiverse.com/thing:7310937 .. I got a pair of OS transponders showing up in OpenStint with the firmware you provided. I initially flashed the hex I created but despite getting flashing light when powering it up, don't get any hits with the hackrf. I'll need to spend some time to figure out my mistake, but I have an idea. |
Thanks, it looks cool!
I got a pair of OS transponders showing up in OpenStint with the firmware you provided. I initially flashed the hex I created but despite getting flashing light when powering it up, don't get any hits with the hackrf. I'll need to spend some time to figure out my mistake, but I have an idea. It's a known phenomena. The transmission is timing-critical, and the firmware is using the SPI bus to do it. The next bit has to be available right when the transmit buffer goes empty. You have to compile with optimalization, otherwise the compiler keeps extra operations in the loop (to help debugging). |
RC4 support, help needed
RC4 SUPPORT - HELP NEEDED
@Oldfan suggested and implemented a scheme to learn RC4 messages, similarly to how RCHourGlass does this. Before committing to further work, I'd like to verify that the scheme indeed works. First off, RC4 was designed to make reverse-engineering hard, and we do not pursue it neither. It sends many different unique messages, probably sending a random sequence (IV) in each message, then obfuscated with a block-cipher (I would have implemented it in a similar way myself). I have access to a single RC4-hybrid transponder. Based on that, the RC4 messages are 3-modal (3 distinct types and repetition rates):
Histogram: https://cimg6.ibsrv.net/gimg/www.rct...a395c91a37.jpg HELP VERIFY THE UNIQENESS OF THESE MESSAGES The best doing it on a Windows laptop, there is a special build for it.
https://cimg8.ibsrv.net/gimg/www.rct...5c117c9b56.jpg PLEASE COLLECT DATA FROM AS MANY TRANSPONDERS AS YOU CAN, AND EMAIL THE FILES TO ME My email address: [email protected] The files are a few kB in size, and contain the repeating messages of a 8196 sample, in a human-readable way. This experiment is important, as it dictates how future support around this feature is done. I'd like to collect data from at least 30 transponders.
|
Great project, thank you for sharing it!
I have two questions regarding an indoor carpet track setup, where I plan to use MyLaps Hybrid transponders. Is the preamplifier necessary for an indoor carpet track, or is the balun alone sufficient? Is the preamplifier a replacement for the HF balun, or do they serve different purposes and should be used together? |
Originally Posted by cmrhun
(Post 16250402)
Great news. Does it currently work with the Hybrid transponder? It supports both RC3 and RC4 protocols, so I'm wondering if it's compatible.
This call-for-help is about RC4 support. The next time I have a chance to visit a local club will be mid-April, and I expect to collect data from max. ~10 pcs. RC4 transponders, which is not enough to draw significant conclusions. Is the preamplifier necessary for an indoor carpet track, or is the balun alone sufficient? A balun is sufficient, I tried with this one: https://www.aliexpress.com/item/1005006281437909.html https://www.aliexpress.com/item/1005006243992995.html You might find even cheaper alternatives if you look hard enough. There is an important trick: make sure both ends of the wire sit perfectly in the connector (especially with thicker cables). If one end is not connected properly, you get a different type of antenna, which is more sensitive to external radio signals and less sensitive to the transponders. The band the transponders use is full of other both legit and non-intentional signals. Not connecting one end result in at least +10 dB higher noise floor, and -10 dB lower signal level. Is the preamplifier a replacement for the HF balun, or do they serve different purposes and should be used together? 1. esd protection 2. 1:8 balun (better fit than 1:9, but much more expensive than the Chinese part) 3. impedance matching circuit 4. low-noise preamplifier 5. band-pass filter None of them is strictly needed, but the balun. |
As written somewhere in the thread, RCHourglass will keep the top 12 packets received from a RC4 transponder and use that to match the ID. I ran with ESC powered transponder, so probably voltage is quite stable. But those packet seem to repeat always. One packet every 4 is totally 'random', the other seem to repeat with a non uniform distribution. 12 is of course a tradeoff between reception vs number of max learnt transponders (given the memory constraint in the PSOC EEPROM).
|
This is how to use the RCHourglass decoder to complete the number mapping for the RC4 transponder.Since there is no memory limit, each RC4 transponder records the top 30 numbers with the highest repetition rate. Adding an RC4 transponder will generate a corresponding number starting with 1000000 if the transponder is placed in the loop for more than ten seconds. |
RC4 native packets use a [65,77] linear block code over GF(2). Each 96-bit payload contains 18 forced-transition bits for RF clock recovery (one per 5-bit group), leaving 77 information bits. Of those, bits 0–64 are data and bits 65–76 are 12 parity check bits — each is a XOR of a specific subset of the data bits. The parity equations have been verified against 22K+ packets from three different transponders (two pure RC4, one RC4 Hybrid) with zero failures. This makes a solid packet validator for catching demodulation errors.
|
Originally Posted by disq
(Post 16250839)
RC4 native packets use a [65,77] linear block code over GF(2). Each 96-bit payload contains 18 forced-transition bits for RF clock recovery (one per 5-bit group), leaving 77 information bits. Of those, bits 0–64 are data and bits 65–76 are 12 parity check bits — each is a XOR of a specific subset of the data bits. The parity equations have been verified against 22K+ packets from three different transponders (two pure RC4, one RC4 Hybrid) with zero failures. This makes a solid packet validator for catching demodulation errors.
TOPIC 1: I'm somewhat able to verify your results. When using a 20-bit preamble (0x54066 non-differential-encoded), I see 111 active symbols. - the last 7 symbols are always 0 (possibly there to feed digital filters) - after differential-decoding the remaining 104 symbols, the last 4 bits are always 0 - in the remaining 100 symbols, I recognise the pattern you describe, but I see (4+1)*20, total 80 information bits. If I'm correct, you're might missing the last 3 bits. Would you share the 12 generator polynoms known to you? TOPIC 2: Your results beg the question even louder: why do we see repeating messages?!? The transponder id fits into 24 bits; if I generously allocate 2x12 bits for BEC voltage and bumper temperature, there are still 16 bits left to randomise things. Yet, we're seeing repeating messages, likely encoding something else than the than just the transponder id. While I'm suspecting these are transponderId-dependent anti-counterfeit messages, I'd like to be certain that these are unique enough to a transponder. To verify, I'd still like to collect the repeating messages from at least 30 RC4 transponders to draw a meaningful conclusion. My personal reach is about 10 transponders, so community help is needed. So far I received only a single transponder file, so I might close the experiment and take a different route though. |
Good catch on the 3 missing bits, that lines up. The decoder extracts 96 bits (12 bytes) after a 24-bit preamble, giving 19 groups. If the real payload is 20 groups (100 bits after DBPSK) with 4 trailing zeros, that accounts for the difference. Will look into extending the extraction.
Here are the 12 parity equations over the 77-bit reduced codeword c[0..76]. Each equation specifies which c indices to XOR, plus a constant term (0 or 1). Parity bit c[N] should equal the XOR of the listed indices ⊕ constant:
Spoiler
The reduced codeword c[0..76] is extracted as: c[0] = payload bit 0 (always 1), c[1..3] = group 0 data bits (b2,b3,b4), then for groups 1–18: 4 bits each (b0,b2,b3,b4), and c[76] = payload bit 95. Again, this was verified on 22K+ packets from three transponders (two pure RC4, one RC4 Hybrid) with zero failures. |
Originally Posted by zsellera
(Post 16250897)
TOPIC 2:
Your results beg the question even louder: why do we see repeating messages?!? The transponder id fits into 24 bits; if I generously allocate 2x12 bits for BEC voltage and bumper temperature, there are still 16 bits left to randomise things. Yet, we're seeing repeating messages, likely encoding something else than the than just the transponder id. While I'm suspecting these are transponderId-dependent anti-counterfeit messages, I'd like to be certain that these are unique enough to a transponder. To verify, I'd still like to collect the repeating messages from at least 30 RC4 transponders to draw a meaningful conclusion. My personal reach is about 10 transponders, so community help is needed. So far I received only a single transponder file, so I might close the experiment and take a different route though. The codes are completely transponder-unique: Zero overlap between two transponders' code tables was observed across 40K+ packets each. The crypto analysis shows full GF(2) rank, no LFSR structure, and no derivable relationship between the codes and the printed transponder ID. The transponder ID is NOT embedded in the payload in any obvious way, the decoder needs a per-transponder key/lookup to map codes back to an ID. So yes, they are transponder-dependent anti-counterfeit codes, but it's more of a challenge-response lookup table than a simple encrypted ID broadcast. But I'm still working on it, need some new hardware which is on the way. The v4.5/v4.7 decoder firmware updates are distributed as per-unit overlay files (one per decoder MAC address). Each overlay contains three packets: the ARM9 MCU firmware (encrypted), a second data blob (encrypted, could be uBlox related, or FPGA init tables, or both), and the FPGA bitstream. The FPGA bitstream is in plaintext, which means the full transponder cipher/decode logic implemented in the Spartan-3 can be extracted and analyzed, which led to some findings... I was able to get 100% of LUT truth tables and routing mux decoded, but still need more data (such as initial values/data tables and so on). I couldn't get the `openstint_rtlsdr` to give me meaningful output (Rafael Micro R820T - RTL2832U) but I'm also missing the balun and a proper MCX connector, and it's a fairly old device (my last contribution about rtlsdr was to the dump1090 project in 2013) so I'll get a modern RTLSDR v4 soon. |
(edit didn't work, new message)
UPDATE: Extended the extraction to 104 bits (13 bytes). The full frame is confirmed at 104 bits- tried 108 and 112 but got zero valid packets, so 104 is the end. Bits 96-101 are 6 additional GF(2) parity bits over the raw 96 input bits. Bits 102-103 are always zero (frame tail). These 6 equations operate on raw bit positions (0-95), not the reduced codeword:
Spoiler
|
Not sure if this will help but github.com/datagutten/amb-p3-parser - decodes mylaps signals. I thru it at claude to convert to a python script and it decodes fairly well.
|
| All times are GMT -7. It is currently 08:41 AM. |
Powered By: vBulletin v3.9.3.9 Patch Level 3
Copyright © 2026 MH Sub I, LLC dba Internet Brands. All rights reserved. Use of this site indicates your consent to the Terms of Use.