edgetx icon indicating copy to clipboard operation
edgetx copied to clipboard

Some changes not written to Radio from Companion

Open msun12000 opened this issue 4 months ago • 17 comments

Is there an existing issue for this problem?

  • [x] I have searched the existing issues

What part of EdgeTX is the focus of this bug?

Companion

Current Behavior

Models and setting are written to radio successfully but some changes are ignored. Specifically, any deletions of "Global Functions" in "Radio settings" are ignored and remin on the Transmitter/Controller.

Expected Behavior

All settings including deletion of Global Functions should be saved to the TX.

Steps To Reproduce

  1. Select to "Edit Radio Settings"
  2. Select Global functions
  3. Highlight GFn where GFn is an entry such as "Play Track" based on a switch
  4. Righ-click to select to Delete or clear that entry
  5. Write Models and settings to radio
  6. The deleted entry remains on the radio.

Version

2.11.2

Transmitter

FrSky X9 Lite / Lite S

Operating System (OS)

Windows

OS Version

11 Home

Anything else?

This was tested on two identical transmitters.

msun12000 avatar Aug 26 '25 10:08 msun12000

How are you connecting the radio when this happens? Is it at the bootloader (thus firmware is not running), or do you plug in and use USB storage mode (thus firmware is running)? I'm just wondering if somehow some of the radio settings persist if the firmware is running. Otherwise, maybe the bug is in Companion.

pfeerick avatar Aug 26 '25 10:08 pfeerick

I am connecting via USB storage mode. PS - I'm not aware of the option to write Models and Settings in bootloader mode. PPS - I see that 11.2.3 has just been released. I can test again with that new release?

msun12000 avatar Aug 26 '25 10:08 msun12000

When you plug the USB in with the radio in bootloader mode, it will just appear as a USB drive, which is the same as USB Storage mode.

Generally no harm in trying, but there is no specific fix for a problem of that description there. The best way to diagnose where the problem is by only changing one variable at a time. So if you do update, only do the update, and then try again, exactly how you did before. And make sure you update both the bootloader and the firmware when updating (i.e. by using DFU mode to update both at once, or updating the bootloader from the firmware, and the firmware from the bootloader).

pfeerick avatar Aug 26 '25 11:08 pfeerick

I've just upgraded to the latest 11.2.3 by updating the bootloader from the firmware, and the firmware from the bootloader . I can confirm that the issue remains - thanks.

msun12000 avatar Aug 26 '25 11:08 msun12000

PS - I'm wondering if this issue requires closure?

msun12000 avatar Sep 07 '25 16:09 msun12000

I'll take a swing at seeing if I can reproduce the issue on my Zorro tonight. As I understand it, I need to confirm if deleting a global function in Companion will properly transfer that change to the radio.

I assume you verified that the other model changes transferred okay? What was the last version that this worked on?

J-Sorenson avatar Sep 08 '25 16:09 J-Sorenson

Thanks, you do understand correctly.

Other model changes do transfer to my TX accurately, though I cannot confirm the last version when this worked, as I haven't deleted any global functions in the past.

msun12000 avatar Sep 08 '25 17:09 msun12000

Okay, here we go. I'm using EdgeTX 2.11.3 (of course) on a RM Zorro with internal 4-in-1. I'm used USB Storage mode with my Zorro in order to match you.

First off, the TX settings are stored in your SD card under /RADIO/radio.yml. The nice thing about using USB storage is that I can look at the changes to radio.yml as soon as I upload them from Companion.

I already had a global function (display brightness), so I added a couple other random functions. My global functions look like this.

customFn:
  0:
    swtch: ON
    func: BACKLIGHT
    def: P2,0
  1:
    swtch: "!TELEMETRY_STREAMING"
    func: BACKLIGHT
    def: P1,1
  2:
    swtch: SG2
    func: PLAY_SOUND
    def: Rata,1,1x

Okay, I ejected the Zorro drive and tested the functions to make sure they worked. I then reconnected the Zorro, re-imported the models and settings, then deleted the middle global function (I don't know which you deleted). I didn't even bother saving the document1.etx file, as I just uploaded the settings to the transmitter. I confirmed that I saw this in radio.yml:

customFn:
  0:
    swtch: ON
    func: BACKLIGHT
    def: P2,0
  1:
    swtch: SG2
    func: PLAY_SOUND
    def: Rata,1,1x

So far, so good. Eject and tested and verified that the telemetry-trigger backlight no longer worked. End of story, right?

Nope! We have a bug, but not what you think. I still had the "SG2" global function in slot 2...and in slot 1. I rebooted the Zorro, but the duplicate remained. When I plugged it back in, the radio.yaml updated with: customFn:

   0:
      swtch: "ON"
      func: BACKLIGHT
      def: "P2,0"
   1:
      swtch: "SG2"
      func: PLAY_SOUND
      def: "Rata,1,1x"
   2:
      swtch: "SG2"
      func: PLAY_SOUND
      def: "Rata,1,1x"

By any chance, were you deleting the last global function? It deleted the global function, but It appears it did not update the length of the global list, so it pulled something from the cached memory when I unplugged.

Gonna play with this a little to get more details, but I believe we've reproduced this.

J-Sorenson avatar Sep 09 '25 04:09 J-Sorenson

Okay, this is not a Companion issue. The radio.yml file is getting updated correctly, but something happens when the radio reads the updated file upon getting unplugged from USB. This time I loaded up 5 global functions:

customFn:
  0:
    swtch: ON
    func: BACKLIGHT
    def: P2,0
  1:
    swtch: SH2
    func: PLAY_SOUND
    def: Wrn1,1,1x
  2:
    swtch: SG2
    func: PLAY_SOUND
    def: Rata,1,1x
  3:
    swtch: TrimRudRight
    func: PLAY_SOUND
    def: Bp1,1,1x
  4:
    swtch: TrimEleUp
    func: PLAY_SOUND
    def: Bp3,1,1x

I then deleted 0, 1, and 3 from Companion. The updated YAML looked good:

customFn:
  0:
    swtch: SG2
    func: PLAY_SOUND
    def: Rata,1,1x
  1:
    swtch: TrimEleUp
    func: PLAY_SOUND
    def: Bp3,1,1x

I ejected and unplugged and immediately saw that I still had 4 special functions. Functions 0 and 1 were updated, but 2,3,4 were from the previous load:

customFn: 
   0:
      swtch: "SG2"
      func: PLAY_SOUND
      def: "Rata,1,1x"
   1:
      swtch: "TrimEleUp"
      func: PLAY_SOUND
      def: "Bp3,1,1x"
   2:
      swtch: "SG2"
      func: PLAY_SOUND
      def: "Rata,1,1x"
   3:
      swtch: "TrimRudRight"
      func: PLAY_SOUND
      def: "Bp1,1,1x"
   4:
      swtch: "TrimEleUp"
      func: PLAY_SOUND
      def: "Bp3,1,1x"

Final test. I reset the special functions to be the 5 shown on the top and made sure they loaded properly in the Zorro. I then powered down and used bootloader to load the models/settings into companion, deleted the same 3 functions, then load back. Just like before, I saw the radio.yml file get updated properly. However, when I exited the bootloader, the updates had taken effect!

Conclusion: when using USB Storage mode, the special functions are not getting updated properly. The functions defined in the yaml are getting updated correctly, but the list does not get truncated to the new length, so anything still in memory will still exist. These then get written back to the yaml when powered down or when USB storage is activated again.

Workaround: use bootloader method to update your models and settings. It always works.

Side note: when the Zorro updates the radio.yml file, it uses 3-space indexing. When Companion updates, it uses 2-space indexing. I don't think it's related, but I failed to notice this when I tried to manually re-apply the global functions to the yml file and the Zorro rejected and dumped my settings. Companion backups are a blessed thing.

J-Sorenson avatar Sep 09 '25 04:09 J-Sorenson

Thanks for testing with the resultant insight. I was indeed deleting the last (several) global functions so that ties in with your test results. Now I'm wondering if Companion could or should somehow delete that cached data prior to writing to TX in USB storage mode?

msun12000 avatar Sep 09 '25 08:09 msun12000

It's not something Companion can do, as it's already doing the right things. This is in the firmware, where the file gets reloaded after the USB is disconnected. It's no issue if you update using bootloader: the file is loaded into a fresh system on startup. This used to be the only way to update models, but EdgeTX added the ability to connect and update while the firmware is already running. It's more convenient to test the settings without having to reboot the transmitter each time.

However, that means reloading settings while the firmware is already running. It's not a big deal for models: just dump the model and reload. Radio settings are a different matter, since the firmware is already running with the previous settings and can't be stopped: there is a bit of a swap-dance when the settings are changed. The "dance" currently does not truncate the array of global custom functions to the new length on reload.

J-Sorenson avatar Sep 09 '25 15:09 J-Sorenson

The "dance" currently does not truncate the array of global custom functions to the new length on reload.

Interesting, IMHO that should still deserve a fix.

raphaelcoeffic avatar Sep 10 '25 08:09 raphaelcoeffic

Of course. I'm new to this, so I don't have a dev environment setup. Anyhow, the code appears to use a fixed array of custom functions as "g_eeGeneral.customFn[MAX_SPECIAL_FCN]." What we need to do upon settings reload is init/disable all functions in the fixed array so that "swtch=0" (usually a memset to the whole thing), then read in the new functions. I can see where special functions are exported to YAML, but I'm having a more difficult time tracing where the YAML gets pulled into the array. When I get some spare time, I'll check into Discord and see if anyone wants to lend a hand. Nobody is assigned yet.

J-Sorenson avatar Sep 10 '25 18:09 J-Sorenson

On Companion, I am able to read from SD Path and make changes. But write to SD Path is not active, always grey out. How to write changes back to SD Path?

hiarmen avatar Oct 15 '25 13:10 hiarmen

Is the models status indicator green?

Image

If it isn't, you can't write until you fix the models with invalid settings... look for model names in the list that are in red, select it, and then use this icon on the toolbar to find out what is wrong so you can fix it.

Image

pfeerick avatar Oct 16 '25 02:10 pfeerick

Is the models status indicator green?

Image If it isn't, you can't write until you fix the models with invalid settings... look for model names in the list that are in red, select it, and then use this icon on the toolbar to find out what is wrong so you can fix it. Image

Thanks Peter, it worked!

hiarmen avatar Oct 16 '25 03:10 hiarmen

Just to note that hiarmen's issue is a separate thing. We still have the issue that the EdgeTX firmware does not truncate the list of special functions after a user deletes one or more functions in Companion. The yaml file is updated. But, once the USB cable is disconnected, it just overwrites the current list with the contents of the YAML file. The leftover special functions at the end of the list should be removed, but instead continue to exist. When the user shuts down the radio or switches models, the active list is written back to the YAML file, thereby putting that function back into the list.

Current work-around is to either update only while in boot-loader, or to just disable the functions in companion(instead of delete) with the intent of deleting those functions directly within EdgeTX.

I've dug through the code a bit, but I'm more of a Linux C++ dev than a low-level C dev. It's taking me some time to trace the logic.

J-Sorenson avatar Dec 10 '25 22:12 J-Sorenson

Bonus! I get to see how he fixed it. Thanks!

J-Sorenson avatar Dec 13 '25 05:12 J-Sorenson

Many thanks for fixing this issue in version 2.11.4

msun12000 avatar Dec 17 '25 18:12 msun12000