atlas0fd00m / rfcat

RfCat - swiss-army knife of ISM band radio
Other
539 stars 115 forks source link

ESP32 and ESP 8266 #152

Open jpitz31 opened 5 months ago

jpitz31 commented 5 months ago

Just wondering if you have thought of porting rfcat to run on ESP32 and ESP8266, These processors are readily available and very inexpensive. Just add a CC1101 or a Nrf905.

Thanks Joe

atlas0fd00m commented 5 months ago

i haven't, actually. i'm not opposed. would you like to take the first swing at a hardware/firmware combination that could work? i'd be happy to help guide you through the process. any interest?

jpitz31 commented 5 months ago

I have been thinking about it. I am not familiar with the CC1111, but familiar with the ESP series. Let me take a look at the source. If I can get a grasp of what is involved I will let you know. Thanks for the offer.

Joe

jpitz31 commented 5 months ago

What platform are you developing with? Visual Studio Code with C/C++ plugins or Visual Studio Code with PlatformIO, Just wondering how much of the existing firmware code could be cross compiled as it is currently. I might try that first. Thanks Joe

atlas0fd00m commented 5 months ago

currently we build with SDCC, which is pretty nonspecific.

the firmware was written specifically for the CC1111, an SOC which incorporates an 8051 micro with a USB controller and the CC1101 radio (operating at 24MHz instead of 26MHz because that's in harmony with the 48MHz clock used by the USB controller and easier for TI to build).

the parts you'll be able to (or even want to) reuse have to do with the command-protocol. that's pretty simple. the rest of the firmware is basically just being a go-between for the Radio and the USB controller. honestly, the hardest part about RfCat firmware development was because i wrote the USB stack from scratch. i'm certain that the ESP* devkits will include whatever you need for USB and/or WiFi to make it easy :)

the CC1101 and the CC1111 are virtually identical from an interface perspective. you'll access the CC1101 differently, since it will be an external device. but once that tiny shim layer is done, the registers that control the radio are all the same. the 26/24MHz thing is just a calculation difference for the numbers that get put into certain RF control registers (and when using the Python code, it's already baked into the code to allow for either one). at one point i wanted to support the IMME dongle (which had a CC1101), but it's proprietary firmware/design and cypress chip were ultimately more than i had time or patience for.

i hope this helps. good luck! @

atlas0fd00m commented 5 months ago

oh, and i wrote it all in VIM. i'm pretty sure if VSCode is you thing, it will go well for you. i've considered it myself.

Crsarmv7l commented 5 months ago

i haven't, actually. i'm not opposed. would you like to take the first swing at a hardware/firmware combination that could work? i'd be happy to help guide you through the process. any interest?

Lol, I am actually working on such, slowly (work and kids mean I get to it only for an hour or so each weekend). Its an ugly combo, essentially reading serial input with RfCat style commands, which translate to the appropriate Elechouse lib for cc1101 control. Nice thing is I hopefully will incorporate a few decoders as well. rx on core 0, decode on core 1. Also cheap hardware plus the ability to automate with pyserial and it can work with any device.

Got the parsing done, need to modify the Elechouse lib though for quite a few issues.

Crsarmv7l commented 5 months ago

BTW @jpitz31 As atlas said the registers are very similar with cc1101 and cc1111 but there are differences (eg register addresses etc). By far the biggest difference is the cc1101 has a FIFO buffer which the cc1111 doesn't but there are a few other differences here and there with the registers.

My first whack with porting to esp/cc1101 I had hoped to use the chipcon_nic.py functions with modified registers/crystal at 26mhz etc along with the fifo buffer since python is slow with micropython. That didn't work out very well (although it did work) so now I am doing it appropriately with C++. My C++ isn't the best though and I am moving slow on it so feel free to attempt!

jpitz31 commented 5 months ago

Thanks @atlas0fd00m and @Crsarmv7l I will start looking over the firmware code.

jpitz31 commented 4 months ago

Yes, on linix firmware is loaded using esptool.py and is pretty easy to perform. On windows there is a Espressif app that allows users to flash the firmware. At first glance it appears that the firmware handles USB, bluetooth and wifi. To do anything, library functions or methods are used to communicate between the different devices. I have been playing around with RadioLib to communicate with CC1101 radios, pretty easy methods to call. Maybe RadioLib can be used as a model for radio communication. But I am still looking over the code. I also want to get familiar with how the client tools interact with the firmware, I want to try to leave all of the client stuff alone.

Thanks Joe

jpitz31 commented 4 months ago

Here is a link to ESP-IDF (Espressif IoT Development Framework), https://docs.espressif.com/projects/esp-idf/en/latest/esp32/get-started/ There is a Visual Studio plugin for this toolchain.

As I mentioned earlier, I am looking at Radiolib, several other RF projects use this lib, It supports 12 different radios and has an abstract layer to add other platforms. RFQuack uses Radiolib.

I am going to setup the toolchain and see how it works. Also trying to locate some docs on how the firmware communicates with the onboard devices ie: USB, BLE and Wifi. Will post my findings.

ALso looking at CMake and Ninja, it is cross platform, works on Windows, linux and Mac.

Thanks Joe

jpitz31 commented 4 months ago

Here is the tutorial I followed to setup the ESP-IDF https://www.espboards.dev/blog/use-esp-idf-with-vscode/

jpitz31 commented 4 months ago

Hey, Atlas, In the sample programs that came with the ESP-IDF tool chain, there is a CLI example program that allows you to query chip related info. This is sent directly through USB to the ESP32.
I have been going through the code for rfcat. I see there are several .c files that start with app*.c and one application.c file. Could you give me a quick run down on the program flow of files for the firmware for the C1111 radio. I also notice that sections of code are commented out, // not used by VCOM. Could you give me some background on this as well. What is the flow of how the firmware parses the in-comming python commands, appears to be stored in the ep5.OUTbuf.

Thanks

Joe

atlas0fd00m commented 4 months ago

sure!

so, the cc1111* files are mostly related to the RF part of the chip (all except the cc1111_vcom* files, which i apparently let slip through the pattern buffers unchecked).

the chipcon_* files are more about the details of making the microcontroller work. primarily chipcon_usb the the code that manages the USB controller, and subsequently has a lot of the core functionality in it. (the `cc1111_vcomfiles are somewhat out-of-date replacements forchipcon_usb*` written by someone way smarter than me, who decided using a more standard USB stack to make the dongle show up as a TTY/COM port was a better idea. but no! i had already spent so much time learning and making the USB stack from scratch, and i liked being able to twiddle the USB-bits to make hidden magic happen... so i continued to focus on my own code instead of the probably better vcom code)

the app* files are the glue that binds them together into one cohesive firmware. (notice, they're the only files with main() functions :)

and the imme* files are all completely different, but you can consider them a sort of app* set of files, intended to create awesome apps on the IMME girl-toys.

as far as the data getting to ep5.OUTbuf, the USB firmware initializes USB endpoint 5 (ep5, as defined in the USB docs for this chip). because of the standard verbology of USB, the buffers are named with regard to the Master (the computer), so it's an OUT buffer of data, and thus the name OUTbuf :) the characteristics of EP5 are initialized in ``

USB processing for EP5 starts with the Interrupt Handler usbIntHandler() which is initialized as the P2 Interrupt Vector handler, and basically just grabs the interrupt event flags and stores them in the usb_data.event field, does a little housekeeping, and returns.

you'll notice in usbProcessEvents(), after handling power state and EP0 stuff, it checks to see if usb_data.event has the USBD_OIF_OUTEP5IF flag set, indicating data is in the EP5 OUT buffer and needs to be handled. if so, it calls handleOUTEP5() and checks the results.

handleOUTEP5() basically grabs the message metadata and sticks it in ep5.*, then sets up DMA for copying the data from the USB buffer to the global memory buffer ep5.OUTbuf. when all that's done, it returns and usbProcessEvents() calls processOUTEP5() to actually process the data in the buffer.

processOUTEP5() is the first higher level function in the stack that actually deals with the data you're sending the RfCat over USB.

so you have this buffer, and you don't know what to do with it. so you make a simple protocol.
you think to yourself, "hey self. you might have multiple apps running on this thing at once, and each app probably wants to be able to have a bunch of commands (or "verbs"). so you make the first two bytes of every message <app> and <cmd>.
you later think "cool! i'm glad i did that cuz i can have this cool app called.... ahem..... let there be a SYSTEM app." and boom, there was a "SYSTEM" app, and it's app number was made 0xff. and you say to yourself, "self, this is good. now we shall be able to tell the god-like functionality from the mortal, errr. application level functionality." ok, so it was more that the SYSTEM app stuff was stuff i just always wanted to be wrapped into every app, a sort of "bonus" with functionality like printing log messages to the Python app, and allowing the Python app to peek and poke at raw memory locations, etc.... in fact, many of the RF settings in the Python side use peek/poke to work with the radio... so you may want to rewrite those to direct some chunk of memory to directly access the registers in the CC1101.

so, the protocol is pretty simple. the biggest thing i didn't tell you yet is that, whenever a command comes in, it should be acknowledged with a txdata() call, like this:

   txdata(ep5.OUTapp, ep5.OUTcmd, ep5.OUTbytesleft, ptr); 

the app/cmd have to match, or the Python side will keep waiting for it. it's a way to return some data as well. notice the clock and the ping responses:

            case CMD_GET_CLOCK:
                txdata(ep5.OUTapp, ep5.OUTcmd, 4, (__xdata u8*)clock);
                break;
            case CMD_PING:
                blink(2,2);
                txdata(ep5.OUTapp,ep5.OUTcmd,ep5.OUTlen,ptr);
                break;

txdata() takes 4 arguments: app, cmd, length, data)

here ends the lesson for the day. i hope it's been entertaining and useful. :)

jpitz31 commented 4 months ago

@atlas0fd00m Thanks for the run through. I have the toolchain working and have built the console cli using an example provided by ESP-IDF. To support many different radios. I have figured out a way to use a config.ini file to have cmake include different .c files and plan to write different .c files for each radio. So all you have to do is set the config.ini to the radio you want to use and then cmake the project. Radiolib supports 12 radios and different platforms.

The example uses a terminal console that uses serial communication. The ESP-IDF provides python code to launch the terminal console. This would be for the interactive CLI. Since the ESP32 is listening all of the time, I can write a python script to read a script as rfcat does.

I have tested radiolib with a CC1101 and can transmit and receive just fine.

The CLI example uses pointers to a function so it should be pretty easy to call the different functions to interface with the radios.

The menu options are dynamically built including argc and argv so custom commands can be built depending on each radio argument requirements. radiolib handles the communication between the processor and the radio using the SPI interface.

The example program registers functions that are called by function pointers and I am now looking at the code to model each radio function needed to call each radio.

Thanks

Joe

Crsarmv7l commented 4 months ago

The example uses a terminal console that uses serial communication. The ESP-IDF provides python code to launch the terminal console. This would be for the interactive CLI. Since the ESP32 is listening all of the time, I can write a python script to read a script as rfcat does.

Basically same thing I currently have done. ESP32 has a serial buffer which I am using to receive user entered commands (also keystop(), I love that function) and set the radio/rx/tx radio packets. Pyserial was also my plan to interact with serial input/output instead of pulling an @atlas0fd00m and writing the usb stack.

Also something I did that you might want to do is dedicate ESP32 core 0 to rx, then pass off the rxed packet to core 1 (Queueing) for print/decode etc freeing up core 0 to rx the next potential packet.

I need to do the actual radio and decode pieces with my project, been to busy the last few weeks to do anything.

Sounds like you are moving along. Keep at it

atlas0fd00m commented 4 months ago

@jpitz31 @Crsarmv7l , does it make sense for you two to work together on your project(s)?

it occurs to me that the python side will want to change to accommodate your new hardware. please let me know if you'd like some help matching that all together.

do you have a reference hardware combination yet? pictures or a link? :)

@

jpitz31 commented 4 months ago

Hi all, yes it does make sense to work together. My C/C++ skills are better than my python skills. I believe that @Crsarmv71 has better python skills.

I am still doing some research on if we need ESP32 with OTA or not. It appears that in some cases OTA will allow the use of two serial ports to echo responses back to the console, but then again this may be able to be done with a python console or python script echoing back to the terminal. Also having a python console will save esp32 processor resources than having the esp32 also doing console resources in addition to radio communications.

I am playing around with trying to get python to read a serial.write() message from the esp32. But again my python skills are not up to speed yet.

I am using UART and t-usb example code to do some testing. Feel free to take a stab at this. Since Flipperzero has become so popular I am also doing some reverse engineering on how .sub files are decoded and encoded to transmit those .sub files. .sub files are saved files either RAW or encoded and saved with an 0x00000988 key. This key is then encoded to play the radio signal back to the radio.

Thanks

On Fri, Feb 23, 2024 at 6:48 AM atlas0fd00m @.***> wrote:

@jpitz31 https://github.com/jpitz31 @Crsarmv7l https://github.com/Crsarmv7l , does it make sense for you two to work together on your project(s)?

it occurs to me that the python side will want to change to accommodate your new hardware. please let me know if you'd like some help matching that all together.

do you have a reference hardware combination yet? pictures or a link? :)

@

— Reply to this email directly, view it on GitHub https://github.com/atlas0fd00m/rfcat/issues/152#issuecomment-1961466030, or unsubscribe https://github.com/notifications/unsubscribe-auth/AAKE7TGSJAP3J2LMVT3IB6TYVCT33AVCNFSM6AAAAABCSKUA7SVHI2DSMVQWIX3LMV43OSLTON2WKQ3PNVWWK3TUHMYTSNRRGQ3DMMBTGA . You are receiving this because you were mentioned.Message ID: @.***>

-- http://joestechblog.com

// -------------------------------------------------------------------------------------- Old C programmers never die, they just get a new function pointer.

..."It began upon the following occasion: It is allowed on all hands, that the primitive way of breaking eggs before we eat them, was upon the larger end: but his present Majesty's grandfather, while he was a boy, going to eat an egg, and breaking it according to the ancient practice, happened to cut one of his fingers. Whereupon the Emperor his father published an edict, commanding all his subjects, upon great penalties, to break the smaller end of their eggs." Jonathan Swift

Crsarmv7l commented 4 months ago

Flipper Raw subs are encoded in pulse duration - gap format.

The keys formatted ones relate to the way they set up the protocols. Which it depends on the protocol.

I have keeloq decoding and tx working on the YS1 after dumping the flipper Manufacturer codes.

Provided I get a few hours this weekend, I should have a working prototype esp32/cc1101 outputting rx signals to serial console.

I have pcbs coming hopefully sometime this week too.

On Fri, Feb 23, 2024, 1:24 PM Joe Pitz @.***> wrote:

Hi all, yes it does make sense to work together. My C/C++ skills are better than my python skills. I believe that @Crsarmv71 has better python skills.

I am still doing some research on if we need ESP32 with OTA or not. It appears that in some cases OTA will allow the use of two serial ports to echo responses back to the console, but then again this may be able to be done with a python console or python script echoing back to the terminal. Also having a python console will save esp32 processor resources than having the esp32 also doing console resources in addition to radio communications.

I am playing around with trying to get python to read a serial.write() message from the esp32. But again my python skills are not up to speed yet.

I am using UART and t-usb example code to do some testing. Feel free to take a stab at this. Since Flipperzero has become so popular I am also doing some reverse engineering on how .sub files are decoded and encoded to transmit those .sub files. .sub files are saved files either RAW or encoded and saved with an 0x00000988 key. This key is then encoded to play the radio signal back to the radio.

Thanks

On Fri, Feb 23, 2024 at 6:48 AM atlas0fd00m @.***> wrote:

@jpitz31 https://github.com/jpitz31 @Crsarmv7l https://github.com/Crsarmv7l , does it make sense for you two to work together on your project(s)?

it occurs to me that the python side will want to change to accommodate your new hardware. please let me know if you'd like some help matching that all together.

do you have a reference hardware combination yet? pictures or a link? :)

@

— Reply to this email directly, view it on GitHub https://github.com/atlas0fd00m/rfcat/issues/152#issuecomment-1961466030,

or unsubscribe < https://github.com/notifications/unsubscribe-auth/AAKE7TGSJAP3J2LMVT3IB6TYVCT33AVCNFSM6AAAAABCSKUA7SVHI2DSMVQWIX3LMV43OSLTON2WKQ3PNVWWK3TUHMYTSNRRGQ3DMMBTGA>

. You are receiving this because you were mentioned.Message ID: @.***>

-- http://joestechblog.com

// --------------------------------------------------------------------------------------

Old C programmers never die, they just get a new function pointer.

..."It began upon the following occasion: It is allowed on all hands, that the primitive way of breaking eggs before we eat them, was upon the larger end: but his present Majesty's grandfather, while he was a boy, going to eat an egg, and breaking it according to the ancient practice, happened to cut one of his fingers. Whereupon the Emperor his father published an edict, commanding all his subjects, upon great penalties, to break the smaller end of their eggs." Jonathan Swift

— Reply to this email directly, view it on GitHub https://github.com/atlas0fd00m/rfcat/issues/152#issuecomment-1961795203, or unsubscribe https://github.com/notifications/unsubscribe-auth/AULD4G4BSEEBI5AHBLPPMQDYVDNF5AVCNFSM6AAAAABCSKUA7SVHI2DSMVQWIX3LMV43OSLTON2WKQ3PNVWWK3TUHMYTSNRRG44TKMRQGM . You are receiving this because you were mentioned.Message ID: @.***>

Crsarmv7l commented 4 months ago

@jpitz31

Elechouse lib didn't work for me (although I suppose it could also be an issue with my wiring/hw/noise, once my pcbs get here I can rule that out). I was hoping it was the easy button and while I have never used GFSK or MSK, ELECHOUSE supports that while radiolib doesn't. On the plus side, I can adapt my input/output to radiolib, so I am going that direction like you.

My current plan: Complete:

Pending:

I like the idea of keeping pure serial input/output as a possibility because that lends to a degree of being platform agnostic. I can open a Serial connection in a webbrowser, on my phone, on anything. As a scope creep goal, Serial over BLE would also provide an interesting way to interact with the cheap hardware.

Crsarmv7l commented 4 months ago

Hmm interesting. I am now getting something on rx by bitbanging gdo0 set as input and using the cc1101 in async mode. Not a very good way though because the polling rate is far too high for the given baud and I can't definitively say the actual signal is being captured.

I will need to think on this some more. I just needed to see something being received.

jpitz31 commented 4 months ago

Hello All, I put together a few radios and ESP32's cc1101

I did find some code on github that can play flipperzero raw .sub files. The lib they are using is Elechouse and this worked for me. I modified the ESP_IDF_UART_RxTx sample to read data from the serial port and then write the same text back to the serial port.

I then wrote a python program that allows users to enter a text string and send it to the esp32. The ESP32 then reads the string and writes it back to the serial port. The python reads the text and prints it to the console.

I am just using this sample program as a proof of concept. I like how the Advanced console sample app uses function pointers to execute functions. So when I get the everything working I can then write the custom code to use the more optimized code.

The radios use simple USB to UART bridge to the ESP32 chip, nothing special needed.

When I make a bit more progress I will put the code out on github.

When debugging the flipper code did you use a wifi dev board for debugging or a jtag board. When I try to debug subghz I have lots of issues with flipperzero crashing and not going directly to the subghz app. I have tried several suggestions on the flipper discord server, but still having issues.

I have tested my radio board with both Elechouse and radio and can transmit data to a doorbell I use for testing.

Crsarmv7l commented 4 months ago

@jpitz31

Sure the tx piece is easy. RX is fine too with ELECHOUSE provided you have a syncword high/low.

It is falling down when I want just raw. Think RfCat lowball(1). Likely because of the FIFO and because of the IOCFG0 pino Config (unless I directly poll GDO0).

See here for code examples and man page details regarding the configs ELECHOUSE is using. https://github.com/LSatan/SmartRC-CC1101-Driver-Lib/issues/146

@atlas0fd00m any thoughts On my observations there? I am fairly sure it is either the IOCFG0 config/the FIFO or both as I do get data when polling GDO directly. I have no problem doing that either, but I need to figure out a way to mitigate the speed I am polling at.

I have a way forward just not the time to test atm.

jpitz31 commented 4 months ago

@Crsarmv7l , Not sure if you have seen this, A windows program from Ti that helps you configure the registers of the CC line of chips. https://www.ti.com/tool/SMARTRFTM-STUDIO

Thanks

Crsarmv7l commented 4 months ago

More digging shows my assumption is correct, you cannot disable preamble/syncword and still use the FIFO. Makes sense though, and why I suspected it.

image

and another:

image

Sucks though, because I had 10 pcbs made from jlpcb, for drop in cc1101 and my esp32-S3 with the traces done....but I didn't run a trace for GDO2 🤣. So bodge wire it is

I need GDO2 for sync/async serial operations for the clock. Once this is dialed in I'll be set.

Handy Application Note for Continuous Data: https://www.ti.com/lit/an/swra359a/swra359a.pdf?ts=1709389401895&ref_url=https%253A%252F%252Fwww.ti.com%252Fproduct%252FCC1101

Atlasofdoom made it nice and simple for us with the YS1. This is a pain lol. I'll get there though. One problem at a time. Sucks though, I am doing full time automation coding at work so I don't want to touch my own projects even when I have a bit of time.

I do like the even further understanding of what is going on here. I was over polling before because I didn't have a clock (GDO2 wasn't wired),

Crsarmv7l commented 4 months ago

Looks like synchronous serial setup will do what I want, while maintaining most of the FIFO/hw functionality.

Async looks like it comes with some serious drawbacks to workaround.

jpitz31 commented 4 months ago

Hey guys, my schedule has gone crazy, I am going to have to back out of the project. It looks like @Crsarmv7l has a good handle on the getting the radio portion dialing in.

Good luck to you all.

Thanks

Crsarmv7l commented 3 months ago

Gdo2 wired. I'll get rid of the sockets so everything fits more flush, and put the code up once I get a chance to dial in rx reading from the pins directly. IMG_20240308_190517 IMG_20240308_190506

atlas0fd00m commented 3 months ago

Hello All, I put together a few radios and ESP32's cc1101

I did find some code on github that can play flipperzero raw .sub files. The lib they are using is Elechouse and this worked for me. I modified the ESP_IDF_UART_RxTx sample to read data from the serial port and then write the same text back to the serial port.

I then wrote a python program that allows users to enter a text string and send it to the esp32. The ESP32 then reads the string and writes it back to the serial port. The python reads the text and prints it to the console.

I am just using this sample program as a proof of concept. I like how the Advanced console sample app uses function pointers to execute functions. So when I get the everything working I can then write the custom code to use the more optimized code.

The radios use simple USB to UART bridge to the ESP32 chip, nothing special needed.

When I make a bit more progress I will put the code out on github.

When debugging the flipper code did you use a wifi dev board for debugging or a jtag board. When I try to debug subghz I have lots of issues with flipperzero crashing and not going directly to the subghz app. I have tried several suggestions on the flipper discord server, but still having issues.

I have tested my radio board with both Elechouse and radio and can transmit data to a doorbell I use for testing.

oooooooo pretty :)

atlas0fd00m commented 3 months ago

@jpitz31

Sure the tx piece is easy. RX is fine too with ELECHOUSE provided you have a syncword high/low.

It is falling down when I want just raw. Think RfCat lowball(1). Likely because of the FIFO and because of the IOCFG0 pino Config (unless I directly poll GDO0).

See here for code examples and man page details regarding the configs ELECHOUSE is using. LSatan/SmartRC-CC1101-Driver-Lib#146

@atlas0fd00m any thoughts On my observations there? I am fairly sure it is either the IOCFG0 config/the FIFO or both as I do get data when polling GDO directly. I have no problem doing that either, but I need to figure out a way to mitigate the speed I am polling at.

I have a way forward just not the time to test atm.

my apologies, i understand the "not enough time to test atm." i've been running hog-wild for the past several weeks. if you ever don't get a response from me and want one more quickly, hit me at atlas#AT#r4780y.com and hopefully i'll see it faster.

i'm not sure what to say here. i've only read about doing RX from a cc1101 chip, or used an existing library to do it... and all that was a while before i wrote lowBall. there should obviously be a trigger to indicate that there's a packet to pick up, which shouldn't have anything to do with the lowBall()-like settings (i wouldn't believe). you're still using the modem and packetizer, you're just clearing the path for it to identify packets constantly.

i would look for a race condition in the code (clearing an interrupt and missing that there's another packet), or possibly reviewing the settings you're doing in the RF CONFIG to cause a "lowball". i haven't had time to look at any code you may have shared, but it looks like you're polling the chip. is there no way for the cc1101 to let you know it's got a packet ready (like an interrupt line). sorry, been a long time since i looked at the 1101.

good work so far tho!

atlas0fd00m commented 3 months ago

@Crsarmv7l , Not sure if you have seen this, A windows program from Ti that helps you configure the registers of the CC line of chips. https://www.ti.com/tool/SMARTRFTM-STUDIO

Thanks

that's how i 'trued-in" the first initial configs, and learned about the way different settings have to work :) nice find!

atlas0fd00m commented 3 months ago

More digging shows my assumption is correct, you cannot disable preamble/syncword and still use the FIFO. Makes sense though, and why I suspected it.

image

and another:

image

Sucks though, because I had 10 pcbs made from jlpcb, for drop in cc1101 and my esp32-S3 with the traces done....but I didn't run a trace for GDO2 🤣. So bodge wire it is

I need GDO2 for sync/async serial operations for the clock. Once this is dialed in I'll be set.

Handy Application Note for Continuous Data: https://www.ti.com/lit/an/swra359a/swra359a.pdf?ts=1709389401895&ref_url=https%253A%252F%252Fwww.ti.com%252Fproduct%252FCC1101

Atlasofdoom made it nice and simple for us with the YS1. This is a pain lol. I'll get there though. One problem at a time. Sucks though, I am doing full time automation coding at work so I don't want to touch my own projects even when I have a bit of time.

I do like the even further understanding of what is going on here. I was over polling before because I didn't have a clock (GDO2 wasn't wired),

nice work. thank you for the kind words :) keep this in mind tho: i just took a dongle that was already on the market (albeit wildly undervalued) and dragged the functionality out to Python and played around with easier ways to reverse/hack RF.

you're reworking much of that, and generating new hardware, and overcoming/translating the differences! i'm really excited to see what you're doing and the outcome.

ok, so i wrote a USB stack. points for masochism! and the challenge, i guess, lol (debugging USB stack code by flashing an LED with error codes in binary was quite a trip). but you all probably would have been better served if i had used the VCOM USB stack provided by Gerard van den Bosch back in 2011 (code is still in there, although i haven't run it in a decade).

during this process, let's just say it's been a trip down memory lane... tracing me through ancient repo code stored locally... which spanned Github, BitBucket, GoogleCode... and traipsed through Git, Hg, and SVN. sadly, because the initial roots (a library called cc1111usb) was in SVN on GoogleCode, and those repos are long gone, so is the SVN log data :(

but i digress. i'm proud of the work you've done and where you're going with the project :)

hack fun! @

atlas0fd00m commented 3 months ago

Hey guys, my schedule has gone crazy, I am going to have to back out of the project. It looks like @Crsarmv7l has a good handle on the getting the radio portion dialing in.

Good luck to you all.

Thanks

understood. i'm sorry. i hope you get more time and can come back to it! thank you for your contributions so far, @jpitz31 . @

atlas0fd00m commented 3 months ago

Gdo2 wired. I'll get rid of the sockets so everything fits more flush, and put the code up once I get a chance to dial in rx reading from the pins directly. IMG_20240308_190517 IMG_20240308_190506

LOVING this. nice work :)

Crsarmv7l commented 3 months ago

my apologies, i understand the "not enough time to test atm." i've been running hog-wild for the past several weeks. if you ever don't get a response from me and want one more quickly, hit me at atlas#AT#r4780y.com and hopefully i'll see it faster.

Much appreciated with the POC info. I will use it sparingly.

Looks like I might have a chance to work on this some more this weekend. Wife and kiddo are taking off to Gran's house. I have been studying that application note thoroughly. Need to go back through the ELECHOUSE driver repo and figure out which GDO is clock when used with sync mode.

Nice thing with reading directly from the pins is I won't have to worry about the FIFO buffer overflow/underflow.

I already bought a whole load of adafruit QT boards for some miniaturization down the line with a new pcb. Will have to rework the code if (when) I get it working for the single core. One step at a time though.

Crsarmv7l commented 3 months ago

Been a bit since I posted here and whew.

ELECHOUSE was a bust. It doesn't put out the clock, at least that I could find. I have been looking into radiolib again as @jpitz31 was, and it will do what I want it to do (bypass the FIFO entirely), it puts out the clock on gdo0 and data on gdo2 for sync serial but it has some significant differences with ELECHOUSE with regards to the registers.

So now I am at a crossroads. I can try and get the registers correct in ELECHOUSE to output the clock in sync which I can use to trigger reads of gdo2 data at appropriate intervals. The downside is zero support or updates.

or

I can shift to radiolib which has sync serial, and outputs clock to trigger pin reading, it is regularly updated and JGromes is great about answering questions. HOWEVER, I will have to rework my entire serial command line, as radiolib groups carriersense register settings in with sync word setup among others, and FEC cant be modified (I might be able to with God mode, but that has the potential to break other things)

I need to setup and try a simple program with radiolib before I go further.

On a different note I saw this https://github.com/atlas0fd00m/rfcat/issues/155

That was one of the first things I asked Flipper devs for, which they denied and the current cli usage for flipper is not very useful.

TBH I mostly use my Flipper as a tester for decoders/encoders I wrote for the Yardstick One 🤣 (Flipper code is ref upon ref upon ref, at least to me its very convoluted)

Some issues they will run into: Flipper uses async serial which avoids the fifo buffer which is good, but there is no clock associated so they will have to figure out a way to modulate the pin reads (IIRC async is 8x the bitrate? Although if that is true they could decimate the bits after rx). Anyway that would be a cool feature for the flipper

Crsarmv7l commented 3 months ago

Hmm might be doable to modify ELECHOUSE

Radiolib registers for clock/data image

Setup like this: image

Elechouse registers image

Looks like Elechouse just jumps immediately to async serial and has data on both GDO0 and GDO2 (the else statement, CCMode(1) is setup for the FIFO). Famous last words, but it might be as simple as adding another case to the CCMode and just setting IOCFG0 and IOCFG2 like radiolib does and omit MDMCFG3 & 4 changes (don't want to mess with the drate/chanbw since sync serial and drate/chanbw is entered as part of the cli entries)

I want to leave the base functionality of the lib intact, because I may need to use the FIFO's to tx once I get to that part.

Crsarmv7l commented 3 months ago

Yep ELECHOUSE is out.

Radiolib does exactly what I want, at least for RX. Already forked and made a few changes to setPromiscuousMode to bring it more inline with lowball (1) with pulls pending for them.

Some of the things just make sense: for instance radiolib's promiscuous mode disables crc, syncword and preamble but doesn't set PQT=0. Upstream also currently doesn't allow you to set syncmode none/ syncmode carrier. So I changed it inline with radiolib's format to allow both of those and the pulls are pending.

Probably more changes required elsewhere, but I can actually use sync serial, and I will get to those as well.

Exciting Progress!

Crsarmv7l commented 3 months ago

Upstream changes accepted. setPromiscuous now behaves like either lowball(0) or lowball(1).

Found a few more things I need to modify that might make it upstream. Then I can start integrating radiolib into the framework I was using with ELECHOUSE.

Crsarmv7l commented 3 months ago

@atlas0fd00m ported your CalculatePktChanBw to Radiolib, ensured you were directly cited (maintainer wouldn't let me keep the OG name). Hope that's ok.

This, and my changes/merges with Promiscuous are part of getting my ducks in a row to use radiolib with my framework.

image

Crsarmv7l commented 2 months ago

Major progress. A few more tests/fixes, gotta test the new pcbs coming, design a case, maybe do a pyserial frontend, and/or bleserial and I'll release everything to the world with @atlas0fd00m blessing. Shot you an email with a function test video and a way to chat directly.

Crsarmv7l commented 1 month ago

adf5cb68-7149-46b6-93ba-9cea9e9e988a a3e747c6-6c5e-4879-9ed7-17b6f8b65cdf 738201bd-6a59-4bcb-925b-3808af99a182

We are getting there boys. Final case, final pcb, and final hardware complete.

Basic functionality including keystop(), complete (last piece is an RSSI filter eg ignore signals below threshold).

Upstreamed multiple things to radiolib. Forked radiolib to adjust the buffer methodsfor this application.

Also need to write protocol decoders for a variety of signals (performed on chip).

Yardstick One functionality on any device (phone, tablet, whatever) with no drivers, YS1 commands/syntax, scriptable on a computer (with pyserial). Decoders (sometime in the next few months) built in. Downsides: tx/rx not as clean as a YS1 and no amp. Cant directly mess with the cc1101 registers with whatever you are using it on. I have spent far more making it, but total cost to someone for parts/case/PCB is about $25 using AliExpress and jlcpcb for the pcb and case printing.

Crsarmv7l commented 3 weeks ago

Christ, I have been working on this for about 6 months so far.

Been on a bit of a tear recently:

Completed:

Current problems / In Progress:

Radiolib doesn't have a very well flushed out Sync TX, and the FIFO only holds 63 bytes. HOWEVER, Ti DN500 discusses refilling the FIFO buffer as it transmits to send upto 255 bytes! A massive improvement: https://www.ti.com/lit/an/swra109c/swra109c.pdf

I have been playing with refilling the buffer while txing, but due to my byte parsing issues above I couldn't verify it was performing as expected. Now that it is fixed, FIFO refill will be the next order of business.

Much later plans: Decoders. Gotta get basic functionality down first.

Crsarmv7l commented 3 weeks ago

Partial Success using the FIFO to send up to 255bytes.

I developed the simplest possible method and test, and attempted to send 100 bytes of data using only the FIFO. I Rxed with an rtlsdr on a different computer and received 97 bytes of data.

The issue is I am using SPI to hammer the TXBYTES register and refill as space is available. SPI is slow and wasn't able to keep up as evidenced by the missing 3 bytes (FIFO ran dry). The TXBYTEs Register has some reliability issues as (discussed in the TI DN500). These tests were all done at a very low bitrate as well. A mere 2 Kbaud.

So this is not a viable option, but it does let me know this is possible.

The path forward on this is via interrupts. Ti is using the FIFO_THR as the trigger on IOCFG2 (GDO2) to trigger a FIFO refill. I need to play with it and see how it all works.

Crsarmv7l commented 2 weeks ago

@atlas0fd00m You around?

I know the CC1111 doesn't have FIFO's so I was wondering how you are using the YS1 to send transmissions? Synchronous Serial? Async Serial? and if you could point me to the code where you do so.

I have made some progress using CC1101 FIFO's and still have more to test, but I am also looking for other alternatives.

Crsarmv7l commented 2 weeks ago

Belay my last. Think I found what I was looking for. DMA with interrupts to trigger the feed...whew, can't say I am surprised but hoping I can find a way to not use that.

Crsarmv7l commented 2 weeks ago

ISR's on my program working. Lets see how many bytes I can consistently get out the door with burst SPI transactions. Obviously the FIFO is pushing out faster than I can push in, but if a decent amount can go out.... I might just avoid trying DMA altogether.

This project can't and isn't supposed to replace well designed hardware and well written software like the YS1 and Rfcat. Just be a cheap and decently functional device that anyone who knows rfcat can pick up and get working.

Crsarmv7l commented 2 weeks ago

Been a rollercoaster with refilling FIFO. Was working terribly even with interrupts for FIFO_THR below threshold and FIFO full. Got a bit of a sanity check from the dev behind radiolib and instead wrote just a very simple sketch that only tx's and refills the FIFO. I used 100bytes of 0xAA to test.

It worked great! 99.5 bytes out of 100 Rxed on the first signal and 98 bytes out of 100 Rxed on the second signal. So it is something with my multiple loops that is killing the throughput (I was getting between 85-93 bytes throughput without much consistency).

Got a testing setup done last night in my program, bypassing Radiolib calls and doing the SPI transactions to fill the FIFO and run the interrupts directly. Lets see how that works tonight/tomrrow, then maybe I can wrap it in a func.

In theory it should work... key word "in theory". This is the last remaining piece for basic functionality (basic functionality is fine up to 64 bytes, I am shooting for at least 100 bytes tx capability. Probably not needed as 64 bytes=512 bits already. But for some reason I want it.)

I should probably also create a func to send bitstrings.

Crsarmv7l commented 1 week ago

Created a method for sending bitstrings....These FIFO refills are killing me though. Sometimes it works decently, sometimes it doesn't.

Drafting up some real test bitstrings... yeah I need the refills. Sigh this is probably gonna be really hard

Crsarmv7l commented 1 week ago

Getting much more consistent with byte throughput. New problem though. The signal sometimes gets inverted. I have no idea how that is happening as I am filling the FIFO and the FIFO should be emptying in accordance with the cc1101 clock...