Repository: pwr-Solaar/Solaar

Issue:
Logitech G613 keyboard G-keys stopped working
**Information**
- Solaar version (solaar --version` or `git describe --tags` if cloned from this repository): 1.1.3
- Distribution: OpenSUSE Tumbleweed
- Kernel version (ex. `uname -srmo`): Linux 5.17.7-1-default x86_64 GNU/Linux
- Output of `solaar show`: 

<details>

```
Solaar version 1.1.3

Lightspeed Receiver
  Device path  : /dev/hidraw2
  USB id       : 046d:C53D
  Serial       : C271A999
    Firmware   : 43.01.B0009
    Bootloader : 02.10
    Other      : AA.D2
  Has 1 paired device(s) out of a maximum of 1.
  Notifications: wireless, software present (0x000900)
  Device activity counters: (empty)

  1: G613 Wireless Mechanical Gaming Keyboard
     Device path  : None
     WPID         : 4065
     Codename     : G613
     Kind         : keyboard
     Protocol     : HID++ 4.2
     Polling rate : 1 ms (1000Hz)
     Serial number: 0DBC5FF6
     Model ID:      B34F40650000
     Unit ID:       9AAB3225
        Bootloader: BOT 46.00.B0006
          Firmware: MPK 05.02.B0021
             Other: 
     Supports 32 HID++ 2.0 features:
         0: ROOT                   {0000}   
         1: FEATURE SET            {0001}   
         2: DEVICE FW VERSION      {0003}   
            Firmware: Bootloader BOT 46.00.B0006 00006E86A7BD
            Firmware: Firmware MPK 05.02.B0021 40656E86A7BD
            Firmware: Other   
            Unit ID: 9AAB3225  Model ID: B34F40650000  Transport IDs: {'btleid': 'B34F', 'wpid': '4065'}
         3: DEVICE NAME            {0005}   
            Name: G613 Wireless Mechanical Gaming Keyboard
            Kind: keyboard
         4: WIRELESS DEVICE STATUS {1D4B}   
         5: RESET                  {0020}   
         6: DEVICE FRIENDLY NAME   {0007}   
            Friendly Name: G613
         7: BATTERY STATUS         {1000}   
            Battery: 50%, discharging, next level 20%.
         8: CHANGE HOST            {1814}   
            Change Host        : 1:video2
         9: HOSTS INFO             {1815}   
            Host 0 (paired): video2
            Host 1 (paired): CB73CG2
        10: REPROG CONTROLS V4     {1B04}   
            Key/Button Diversion (saved): {Host Switch Channel 1:Regular, Host Switch Channel 2:Regular}
            Key/Button Diversion        : {Host Switch Channel 1:Regular, Host Switch Channel 2:Regular}
        11: REPORT HID USAGE       {1BC0}   
        12: ENCRYPTION             {4100}   
        13: KEYBOARD DISABLE BY USAGE {4522}   
        14: KEYBOARD LAYOUT 2      {4540}   
        15: GKEY                   {8010}   
            Divert G Keys (saved): True
            Divert G Keys        : False
        16: REPORT RATE            {8060}   
            Polling Rate (ms): 1
            Polling Rate (ms) (saved): 1
            Polling Rate (ms)        : 1
        17: DFUCONTROL SIGNED      {00C2}   
        18: DEVICE RESET           {1802}   internal, hidden
        19: unknown:1803           {1803}   internal, hidden
        20: CONFIG DEVICE PROPS    {1806}   internal, hidden
        21: unknown:1813           {1813}   internal, hidden
        22: OOBSTATE               {1805}   internal, hidden
        23: unknown:1830           {1830}   internal, hidden
        24: unknown:1890           {1890}   internal, hidden
        25: unknown:1891           {1891}   internal, hidden
        26: unknown:18A1           {18A1}   internal, hidden
        27: unknown:1DF3           {1DF3}   internal, hidden
        28: unknown:1E00           {1E00}   hidden
        29: unknown:1EB0           {1EB0}   internal, hidden
        30: unknown:1861           {1861}   internal, hidden
        31: unknown:18B1           {18B1}   internal, hidden
     Has 2 reprogrammable keys:
         0: Host Switch Channel 1     , default: HostSwitch Channel 1        => HostSwitch Channel 1      
             divertable, persistently divertable, pos:1, group:0, group mask:empty
             reporting: default
         1: Host Switch Channel 2     , default: HostSwitch Channel 2        => HostSwitch Channel 2      
             divertable, persistently divertable, pos:2, group:0, group mask:empty
             reporting: default
     Battery: 50%, discharging, next level 20%.

<mouse stuff omitted as it is connected to different controller.

```
</details>

- Contents of `~/.config/solaar/config.yaml` (or `~/.config/solaar/config.json` if `~/.config/solaar/config.yaml` not present):

<details>

```
$ cat config.json
{
  "400A:5A5DE8E9": {
    "_modelId": "400A00000000",
    "_name": "Wireless Mouse M325",
    "_sensitive": {
      "hi-res-scroll": false
    },
    "_serial": "5A5DE8E9",
    "_unitId": "5A5DE8E9"
  },
  "4065:0DBC5FF6": {
    "_modelId": "B34F40650000",
    "_name": "G613 Wireless Mechanical Gaming Keyboard",
    "_sensitive": {
      "change-host": true,
      "divert-gkeys": true,
      "divert-keys": true,
      "report_rate": true
    },
    "_serial": "0DBC5FF6",
    "_unitId": "9AAB3225",
    "divert-gkeys": true,
    "divert-keys": {
      "209": 0,
      "210": 0
    },
    "report_rate": 1
  },
  "_version": "1.0.6"
}$ cat config.yaml 
- 1.1.3
- _NAME: Wireless Mouse M325
  _absent: [lowres-scroll-mode, hires-smooth-invert, hires-smooth-resolution, hires-scroll-mode, smart-shift, thumb-scroll-mode, thumb-scroll-invert, onboard_profiles,
    report_rate, pointer_speed, dpi, dpi-sliding, speed-change, mouse-gestures, backlight, backlight-timed, fn-swap, reprogrammable-keys, persistent-remappable-keys,
    divert-keys, disable-keyboard-keys, divert-crown, crown-smooth, divert-gkeys, m-key-leds, mr-key-led, multiplatform, change-host, gesture2-gestures,
    gesture2-divert, gesture2-params, hi-res-scroll]
  _modelId: 400A00000000
  _sensitive: {hi-res-scroll: false}
  _serial: 5A5DE8E9
  _unitId: 5A5DE8E9
  _wpid: 400A
  hi-res-scroll: null
- _NAME: G613 Wireless Mechanical Gaming Keyboard
  _absent: [hi-res-scroll, lowres-scroll-mode, hires-smooth-invert, hires-smooth-resolution, hires-scroll-mode, smart-shift, thumb-scroll-mode, thumb-scroll-invert,
    onboard_profiles, pointer_speed, dpi, dpi-sliding, speed-change, mouse-gestures, backlight, backlight-timed, fn-swap, reprogrammable-keys, persistent-remappable-keys,
    disable-keyboard-keys, divert-crown, crown-smooth, m-key-leds, mr-key-led, multiplatform, gesture2-gestures, gesture2-divert, gesture2-params]
  _modelId: B34F40650000
  _sensitive: {change-host: true, divert-gkeys: true, divert-keys: true, report_rate: true}
  _serial: 0DBC5FF6
  _unitId: 9AAB3225
  _wpid: '4065'
  divert-gkeys: true
  divert-keys: {209: 0, 210: 0}
  report_rate: 1
$ cat rules.yaml
%YAML 1.3
---
- Feature: GKEY
- Rule:
  - Modifiers: Control
  - Rule:
    - Key: G1
    - KeyPress: [Control_L, F7]
  - Rule:
    - Key: G2
    - KeyPress: [Control_L, F8]
  - Rule:
    - Key: G3
    - KeyPress: ''
  - Rule:
    - Key: G4
    - KeyPress: ''
  - Rule:
    - Key: G5
    - KeyPress: ''
  - Rule:
    - Key: G6
    - KeyPress: ''
- Rule:
  - Key: G1
  - KeyPress: [Control_L, F1]
- Rule:
  - Key: G2
  - KeyPress: [Control_L, F2]
- Rule:
  - Key: G3
  - KeyPress: [Control_L, F3]
- Rule:
  - Key: G4
  - KeyPress: [Control_L, F4]
- Rule:
  - Key: G5
  - KeyPress: [Control_L, F5]
- Rule:
  - Key: G6
  - KeyPress: [Control_L, F6]
...


```
</details>


- Errors or warrnings from Solaar:
<!-- Run Solaar as `solaar -dd`, after killing any running Solaar processes.  If any warnings or errors show up, include the output here. -->

```
$ solaar -dd
22:41:04,265     INFO [MainThread] root: language en_GB (UTF-8), translations path None
22:41:04,456     INFO [MainThread] logitech_receiver.diversion: GDK Keymap set up
22:41:04,464  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress not sequence of key names ['']
22:41:04,464  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress not sequence of key names ['']
22:41:04,464  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress not sequence of key names ['']
22:41:04,464  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress not sequence of key names ['']
22:41:04,464     INFO [MainThread] logitech_receiver.diversion: loaded 1 rules from /home/jiivee/.config/solaar/rules.yaml
22:41:04,485     INFO [MainThread] solaar.upower: connected to system dbus, watching for suspend/resume events
22:41:04,492     INFO [MainThread] solaar.ui.notify: starting desktop notifications
22:41:04,726     INFO [MainThread] solaar.listener: starting receiver listening threads
22:41:04,739     INFO [MainThread] solaar.listener: receiver event add DeviceInfo(path='/dev/hidraw2', vendor_id='046D', product_id='C53D', serial='', release=None, manufacturer=None, product=None, interface=2, driver='hid-generic', bus_id=3, isDevice=None)
22:41:04,802     INFO [MainThread] logitech_receiver.base: New lock 13
22:41:04,805     INFO [ReceiverListener:hidraw2] logitech_receiver.listener: started with <LightspeedReceiver(/dev/hidraw2,13)> (13)
22:41:04,805     INFO [ReceiverListener:hidraw2] solaar.listener: <LightspeedReceiver(/dev/hidraw2,13)>: notifications listener has started (13)
22:41:04,805     INFO [ReceiverListener:hidraw2] logitech_receiver.base: New lock <_ThreadedHandle(/dev/hidraw2)>
22:41:04,806     INFO [MainThread] solaar.listener: receiver event add DeviceInfo(path='/dev/hidraw3', vendor_id='046D', product_id='C52B', serial='', release=None, manufacturer=None, product=None, interface=2, driver='logitech-djreceiver', bus_id=3, isDevice=None)
22:41:04,806     INFO [MainThread] logitech_receiver.base: New lock 14
22:41:04,807     INFO [ReceiverListener:hidraw2] logitech_receiver.receiver: <LightspeedReceiver(/dev/hidraw2,13)>: receiver notifications enabled => ('wireless', 'software present')
22:41:04,810     INFO [ReceiverListener:hidraw2] solaar.listener: status_changed <LightspeedReceiver(/dev/hidraw2,13)>: present, No paired devices. (0) 
22:41:04,815     INFO [ReceiverListener:hidraw3] logitech_receiver.listener: started with <UnifyingReceiver(/dev/hidraw3,14)> (14)
22:41:04,816     INFO [ReceiverListener:hidraw3] solaar.listener: <UnifyingReceiver(/dev/hidraw3,14)>: notifications listener has started (14)
22:41:04,816     INFO [ReceiverListener:hidraw3] logitech_receiver.base: New lock <_ThreadedHandle(/dev/hidraw3)>
22:41:04,822     INFO [ReceiverListener:hidraw3] logitech_receiver.receiver: <UnifyingReceiver(/dev/hidraw3,14)>: receiver notifications enabled => ('wireless', 'software present')
22:41:04,826     INFO [ReceiverListener:hidraw3] solaar.listener: status_changed <UnifyingReceiver(/dev/hidraw3,14)>: present, No paired devices. (0) 
22:41:04,842     INFO [ReceiverListener:hidraw3] logitech_receiver.receiver: <UnifyingReceiver(/dev/hidraw3,14)>: found new device 1 (400A)
22:41:04,842     INFO [ReceiverListener:hidraw3] solaar.listener: connection Notification(10,1,41,04,120A40) for <Device(1,400A,Wireless Mouse M325,5A5DE8E9)> (mouse)
22:41:04,844     INFO [ReceiverListener:hidraw3] solaar.listener: status_changed <UnifyingReceiver(/dev/hidraw3,14)>: present, 1 paired device. (0) 
22:41:04,845     INFO [ReceiverListener:hidraw3] logitech_receiver.base: New lock 16
22:41:05,038  WARNING [ReceiverListener:hidraw3] logitech_receiver.status: <Device(1,400A,Wireless Mouse M325,5A5DE8E9)>: battery 5%, ALERT discharging
22:41:05,039     INFO [ReceiverListener:hidraw3] solaar.listener: status_changed <Device(1,400A,Wireless Mouse M325,5A5DE8E9)>: paired online, {'LINK ENCRYPTED': False, 'BATTERY LEVEL': 5, 'BATTERY STATUS': NamedInt(0, 'discharging'), 'BATTERY NEXT LEVEL': 0, 'BATTERY VOLTAGE': None, 'BATTERY CHARGING': False, 'ERROR': NamedInt(0, 'discharging')} (5) Battery: 5% (discharging)
22:41:05,227     INFO [ReceiverListener:hidraw3] logitech_receiver.status: <Device(1,400A,Wireless Mouse M325,5A5DE8E9)> pushing device settings [<Setting([feature:toggle] M325:hi-res-scroll=None)>]
22:41:05,298     INFO [ReceiverListener:hidraw3] solaar.listener: status_changed <Device(1,400A,Wireless Mouse M325,5A5DE8E9)>: paired online, {'LINK ENCRYPTED': False, 'BATTERY LEVEL': 5, 'BATTERY STATUS': NamedInt(0, 'discharging'), 'BATTERY NEXT LEVEL': 0, 'BATTERY VOLTAGE': None, 'BATTERY CHARGING': False, 'ERROR': NamedInt(0, 'discharging')} (0) 
22:41:05,299  WARNING [ReceiverListener:hidraw3] logitech_receiver.status: <Device(1,400A,Wireless Mouse M325,5A5DE8E9)>: battery 5%, ALERT discharging
22:41:05,299     INFO [ReceiverListener:hidraw3] solaar.listener: status_changed <Device(1,400A,Wireless Mouse M325,5A5DE8E9)>: paired online, {'LINK ENCRYPTED': False, 'BATTERY LEVEL': 5, 'BATTERY STATUS': NamedInt(0, 'discharging'), 'BATTERY NEXT LEVEL': 0, 'BATTERY VOLTAGE': None, 'BATTERY CHARGING': False, 'ERROR': NamedInt(0, 'discharging')} (0) Battery: 5% (discharging)
22:41:05,300     INFO [ReceiverListener:hidraw3] logitech_receiver.notifications: <Device(1,400A,Wireless Mouse M325,5A5DE8E9)>: spurious BATTERY status Notification(11,1,05,10,0200C21C020000000000000000000000)
22:41:05,825     INFO [ReceiverListener:hidraw2] logitech_receiver.receiver: <LightspeedReceiver(/dev/hidraw2,13)>: found new device 1 (4065)
22:41:05,825     INFO [ReceiverListener:hidraw2] solaar.listener: connection Notification(10,1,41,0D,316540) for <Device(1,4065,G613 Wireless Mechanical Gaming Keyboard,0DBC5FF6)> (keyboard)
22:41:06,835     INFO [ReceiverListener:hidraw2] solaar.listener: status_changed <LightspeedReceiver(/dev/hidraw2,13)>: present, 1 paired device. (0) 
22:41:06,995     INFO [ReceiverListener:hidraw2] solaar.listener: status_changed <Device(1,4065,G613 Wireless Mechanical Gaming Keyboard,0DBC5FF6)>: paired online, {'LINK ENCRYPTED': True, 'BATTERY LEVEL': 50, 'BATTERY STATUS': NamedInt(0, 'discharging'), 'BATTERY NEXT LEVEL': 20, 'BATTERY VOLTAGE': None, 'BATTERY CHARGING': False, 'ERROR': None} (0) 
22:41:07,157     INFO [ReceiverListener:hidraw2] logitech_receiver.device: <Device(1,4065,G613 Wireless Mechanical Gaming Keyboard,0DBC5FF6)>: unitId 9AAB3225 does not match serial 0DBC5FF6
22:41:08,456     INFO [ReceiverListener:hidraw2] logitech_receiver.status: <Device(1,4065,G613 Wireless Mechanical Gaming Keyboard,0DBC5FF6)> pushing device settings [<Setting([feature:choice] G613:report_rate=None)>, <Setting([feature:map choice] G613:divert-keys=None)>, <Setting([feature:toggle] G613:divert-gkeys=None)>, <Setting([feature:choice] G613:change-host=None)>]
22:41:08,862     INFO [ReceiverListener:hidraw2] solaar.listener: status_changed <Device(1,4065,G613 Wireless Mechanical Gaming Keyboard,0DBC5FF6)>: paired online, {'LINK ENCRYPTED': True, 'BATTERY LEVEL': 50, 'BATTERY STATUS': NamedInt(0, 'discharging'), 'BATTERY NEXT LEVEL': 20, 'BATTERY VOLTAGE': None, 'BATTERY CHARGING': False, 'ERROR': None} (0) 
22:41:19,567     INFO [MainThread] logitech_receiver.diversion: KeyPress action: ['Control_L', 'F1'], modifiers 16 ['0xffe3', '0xffbe']
22:41:19,568     INFO [MainThread] logitech_receiver.diversion: XKB display set up
22:41:19,625     INFO [MainThread] logitech_receiver.diversion: X11 library loaded and display set up
22:41:19,631  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress key symbol not currently available KeyPress: Control_L F1
22:41:19,631  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress key symbol not currently available KeyPress: Control_L F1
22:41:25,305     INFO [MainThread] logitech_receiver.diversion: KeyPress action: ['Control_L', 'F2'], modifiers 16 ['0xffe3', '0xffbf']
22:41:25,306  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress key symbol not currently available KeyPress: Control_L F2
22:41:25,306  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress key symbol not currently available KeyPress: Control_L F2
22:41:38,035     INFO [MainThread] solaar.listener: stopping receiver listening threads [<ReceiverListener(ReceiverListener:hidraw2, started daemon 139811990009408)>, <ReceiverListener(ReceiverListener:hidraw3, started daemon 139811973224000)>]
22:41:38,044     INFO [MainThread] solaar.configuration: saved ['1.1.3', {'_NAME': 'Wireless Mouse M325', '_absent': ['lowres-scroll-mode', 'hires-smooth-invert', 'hires-smooth-resolution', 'hires-scroll-mode', 'smart-shift', 'thumb-scroll-mode', 'thumb-scroll-invert', 'onboard_profiles', 'report_rate', 'pointer_speed', 'dpi', 'dpi-sliding', 'speed-change', 'mouse-gestures', 'backlight', 'backlight-timed', 'fn-swap', 'reprogrammable-keys', 'persistent-remappable-keys', 'divert-keys', 'disable-keyboard-keys', 'divert-crown', 'crown-smooth', 'divert-gkeys', 'm-key-leds', 'mr-key-led', 'multiplatform', 'change-host', 'gesture2-gestures', 'gesture2-divert', 'gesture2-params', 'hi-res-scroll'], '_modelId': '400A00000000', '_sensitive': {'hi-res-scroll': False}, '_serial': '5A5DE8E9', '_unitId': '5A5DE8E9', '_wpid': '400A', 'hi-res-scroll': None}, {'_NAME': 'G613 Wireless Mechanical Gaming Keyboard', '_absent': ['hi-res-scroll', 'lowres-scroll-mode', 'hires-smooth-invert', 'hires-smooth-resolution', 'hires-scroll-mode', 'smart-shift', 'thumb-scroll-mode', 'thumb-scroll-invert', 'onboard_profiles', 'pointer_speed', 'dpi', 'dpi-sliding', 'speed-change', 'mouse-gestures', 'backlight', 'backlight-timed', 'fn-swap', 'reprogrammable-keys', 'persistent-remappable-keys', 'disable-keyboard-keys', 'divert-crown', 'crown-smooth', 'm-key-leds', 'mr-key-led', 'multiplatform', 'gesture2-gestures', 'gesture2-divert', 'gesture2-params'], '_modelId': 'B34F40650000', '_sensitive': {'change-host': True, 'divert-gkeys': True, 'divert-keys': True, 'report_rate': True}, '_serial': '0DBC5FF6', '_unitId': '9AAB3225', '_wpid': '4065', 'divert-gkeys': True, 'divert-keys': {209: 0, 210: 0}, 'report_rate': 1}] to /home/jiivee/.config/solaar/config.yaml
22:41:38,426     INFO [ReceiverListener:hidraw2] solaar.listener: <LightspeedReceiver(/dev/hidraw2,13)>: notifications listener has stopped
22:41:38,587     INFO [ReceiverListener:hidraw3] solaar.listener: <UnifyingReceiver(/dev/hidraw3,14)>: notifications listener has stopped
22:41:38,589     INFO [MainThread] solaar.ui.notify: stopping desktop notifications
```


**Describe the bug**
G-keys of Logitech G613 keyboard stopped working when I upgraded from solaar 1.1.1 to 1.1.2 or to 1.1.3. 


**To Reproduce**
Steps to reproduce the behavior:
1. Start solaar
2. Click on G1 and G2. Expected behaviour is to switch to desktop 0 and desktop 1, respectively.
3. Quit solaar and start solaar -dd
4. Click on G1 and G2
5. See solaar error below

22:41:19,631  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress key symbol not currently available KeyPress: Control_L F1
22:41:19,631  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress key symbol not currently available KeyPress: Control_L F1
22:41:25,305     INFO [MainThread] logitech_receiver.diversion: KeyPress action: ['Control_L', 'F2'], modifiers 16 ['0xffe3', '0xffbf']
22:41:25,306  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress key symbol not currently available KeyPress: Control_L F2
22:41:25,306  WARNING [MainThread] logitech_receiver.diversion: rule KeyPress key symbol not currently available KeyPress: Control_L F2




Discussion:
[I was confused.  You are not running Wayland.]
Ooh, the early warnings are from the four rules that have '' as their keypress.  You should fix these rules.
The interesting warnings arise because Solaar is unable to find a key on the simulated keyboard it is trying to use for some key symbol in the KeyPress action.   The question is why.  That will probably require some debugging of the code and the data structures that Solaar creates.
Before null keypress config has not caused any issues. Nevertheless, I assigned keypresses to ctrl+G3 - ctrl+G6. Below are used rules, solaar -dd output and xev output. During solaar and xev sessions I pressed keys G1, G2, ctrl+G1 and ctrl+G2. If I interpret xev output correctly, only control key press is seen by xev (although it is not acting as control key).

[rules.yaml.txt](https://github.com/pwr-Solaar/Solaar/files/8736226/rules.yaml.txt)
[solaar.log](https://github.com/pwr-Solaar/Solaar/files/8736229/solaar.log)
[xev.log](https://github.com/pwr-Solaar/Solaar/files/8736230/xev.log)

As far I see, Xwayland is installed, but it is not used. Xorg is in use. Running X binary is /usr/bin/Xorg,bin.
What appears to be happening is that Solaar can't find an F1 key on the keyboard that GDK thinks you are using.   The question is why.  To find out clone Solaar and add the following lines 
```
for kc in range(0,256):
    (a, m, vs) = gkeymap.get_entries_for_keycode(kc)
    if a:
        print("XK ", kc, vs, [(next((key for key, value in XK_KEYS.items() if value == v), None)) for v in vs],
              [(k.group, k.level) for k in m])
```
to lib/logitech_receiver/diversion.py after 
```
if _log.isEnabledFor(_INFO):
    _log.info('GDK Keymap %sset up', '' if gkeymap else 'not ')
```
This will dump the contents of the keymap.  Run solaar from the clone directory as `bin/solaar` and run one of the problematic rules.

Post the resulting output.
Please, find attached
bin/solaar -dd
output when run after adding for loop.

Just a moment ago I remembered that I have configured three different keyboard layouts. In one of them Solaar works, i.e. G-keys do what I want them to do. In two of them they don't work. The layout I usually use is "kotoistus" and it is now broken. Also layout "Finnish" is broken regarding Solaar. Layout "Finninsh (classic)" works with Solaar, but it is otherwise broken for daily use.

So, it seems Solaar is not broken, but somebody has messed with keyboard layouts or how they are interpreted. I opened thread regarding these issues: https://forums.opensuse.org/showthread.php/570284-Xorg-keymaps-and-Solaar-interoperability-issues.

[solaar.log](https://github.com/pwr-Solaar/Solaar/files/8750059/solaar.log)

It actually might be a Sollaar bug.  It appears that you have set up multiple keyboard layouts.  Solaar might not be sophisticated enough to figure out that keycodes with only layout 0 can be used in other layouts.

It appears that whatever keyboard layout is first on the layout list, works with Solaar. Kotoistus as first layout → G1 delivers ctrl+F1 and so forth. Finnish as first layout → G1 delivers ctrl+F1 and so forth. Any of the two other layouts active → G1 doesn't work.

Resolving patch:
diff --git a/lib/logitech_receiver/diversion.py b/lib/logitech_receiver/diversion.py
--- a/lib/logitech_receiver/diversion.py
+++ b/lib/logitech_receiver/diversion.py
@@ -133,7 +133,7 @@ def x11_setup():
         if _log.isEnabledFor(_INFO):
             _log.info('X11 library loaded and display set up')
     except Exception:
-        _log.warn('X11 not available - some rule capabilities inoperable: %s', exc_info=_sys.exc_info())
+        _log.warn('X11 not available - some rule capabilities inoperable', exc_info=_sys.exc_info())
         _x11 = False
         xtest_available = False
     return _x11
@@ -191,6 +191,7 @@ def setup_uinput():
         udevice = evdev.uinput.UInput(events=devicecap, name='solaar-keyboard')
         if _log.isEnabledFor(_INFO):
             _log.info('uinput device set up')
+        return True
     except Exception as e:
         _log.warn('cannot create uinput device: %s', e)
 
@@ -833,14 +834,23 @@ def __init__(self, keys):
             _log.warn('rule KeyPress not sequence of key names %s', keys)
             self.key_symbols = []
 
+    # WARNING:  This is an attempt to reverse the keycode to keysym mappping in XKB.  It may not be completely general.
     def keysym_to_keycode(self, keysym, modifiers):  # maybe should take shift into account
         group = kbdgroup() or 0
         keycodes = gkeymap.get_entries_for_keyval(keysym)
         (keycode, level) = (None, None)
-        for k in keycodes.keys:
-            if (group == k.group or len(keycodes.keys) == 1) and k.keycode < 256 and (level is None or k.level < level):
+        for k in keycodes.keys:  # mappings that have the correct group
+            if group == k.group and k.keycode < 256 and (level is None or k.level < level):
                 keycode = k.keycode
                 level = k.level
+        if keycode or group == 0:
+            return (keycode, level)
+        for k in keycodes.keys:  # mappings for group 0 where keycode only has group 0 mappings
+            if 0 == k.group and k.keycode < 256 and (level is None or k.level < level):
+                (a, m, vs) = gkeymap.get_entries_for_keycode(k.keycode)
+                if a and all(mk.group == 0 for mk in m):
+                    keycode = k.keycode
+                    level = k.level
         return (keycode, level)
 
     def __str__(self):
@@ -880,7 +890,7 @@ def evaluate(self, feature, notification, device, status, last_result):
         if gkeymap:
             current = gkeymap.get_modifier_state()
             if _log.isEnabledFor(_INFO):
-                _log.info('KeyPress action: %s, modifiers %s %s', self.key_names, current, [hex(k) for k in self.key_symbols])
+                _log.info('KeyPress action: %s, group %s, modifiers %s', self.key_names, kbdgroup(), current)
             self.keyDown(self.key_symbols, current)
             self.keyUp(reversed(self.key_symbols), current)
             _time.sleep(0.01)


Test patch: