linux-surface / iptsd

Userspace daemon for Intel Precise Touch & Stylus
GNU General Public License v2.0
86 stars 39 forks source link

iptsd@.service unit file loses access to the ipts device unit service after a while #163

Open samvde opened 3 weeks ago

samvde commented 3 weeks ago

I could not get the stylus to work on my surface book 2 anymore, and after some troubleshooting it appeared -at least on my configuration using arch, haven't tried on other OS- that some config parameters in the iptsd@service unit flle might be wrong (https://raw.githubusercontent.com/linux-surface/iptsd/78bfa6958ba25831cb5b47e6ee32f2cf6a460afd/etc/systemd/iptsd%40.service.in):

[Unit]
Description=Intel Precise Touch & Stylus Daemon
Documentation=https://github.com/linux-surface/iptsd
StopWhenUnneeded=yes
BindsTo=%i.device

[Service]
Type=simple
ExecStart=@bindir@/iptsd /%I

This is my working version:

[Unit]
Description=Intel Precise Touch & Stylus Daemon
Documentation=https://github.com/linux-surface/iptsd
BindsTo=/%I

[Service]
Type=simple
ExecStart=/usr/bin/iptsd /%I
StollD commented 3 weeks ago
  • The BindsTo directive translates to "dev-hidraw1.device", which does not exist, so iptsd does not start. Simply changing it to /%I which translates to /dev/hidraw1 works fine.

If one exists, the other will exist as well. Please post the output of systemctl status dev-hidraw1.device.

  • The StopWhenUnneeded directive makes the device disappear when udev gets reloaded on my system. I removed it.

That's exactly what you want. When the device that the service is reading from disappears, you want the service to stop. Otherwise it just crashes.

samvde commented 3 weeks ago
  • The BindsTo directive translates to "dev-hidraw1.device", which does not exist, so iptsd does not start. Simply changing it to /%I which translates to /dev/hidraw1 works fine.

If one exists, the other will exist as well. Please post the output of systemctl status dev-hidraw1.device.

Here you go:

systemctl status dev-hidraw1.device ○ dev-hidraw1.device - /dev/hidraw1 Loaded: loaded Active: inactive (dead)

I can't explain it then, it does not work for me with this reference in the unit file, only the device path works. I do suspect others here might have the same issue reading some of the iptsd issues and manual fixes. Is it an issue to just use the device path if it ends up being the same result?

  • The StopWhenUnneeded directive makes the device disappear when udev gets reloaded on my system. I removed it.

That's exactly what you want. When the device that the service is reading from disappears, you want the service to stop. Otherwise it just crashes.

I think I understand the goal, but as a user I just need the daemon to be there when the device is, and it never seems to recover from this until a reboot. Not sure how that should work.

Happy to test whatever you want. I have no developer experience unfortunately.

StollD commented 3 weeks ago

Here you go:

systemctl status dev-hidraw1.device ○ dev-hidraw1.device - /dev/hidraw1 Loaded: loaded Active: inactive (dead)

So that is exactly what it should say.

I can't explain it then, it does not work for me with this reference in the unit file, only the device path works. I do suspect others here might have the same issue reading some of the iptsd issues and manual fixes. Is it an issue to just use the device path if it ends up being the same result?

What is the output of systemctl status $(iptsd-find-service) when booting with the default service file?

I think I understand the goal, but as a user I just need the daemon to be there when the device is, and it never seems to recover from this until a reboot. Not sure how that should work.

I am not sure what is going on on your system. What do you mean by udev getting reloaded? Are you reloading it yourself?

Can you post the output of dmesg when it breaks?

samvde commented 3 weeks ago

Here you go: systemctl status dev-hidraw1.device ○ dev-hidraw1.device - /dev/hidraw1 Loaded: loaded Active: inactive (dead)

So that is exactly what it should say.

I can't explain it then, it does not work for me with this reference in the unit file, only the device path works. I do suspect others here might have the same issue reading some of the iptsd issues and manual fixes. Is it an issue to just use the device path if it ends up being the same result?

What is the output of systemctl status $(iptsd-find-service) when booting with the default service file?

It looks pretty normal and stylus is working:

systemctl status $(iptsd-find-service) ● iptsd@dev-hidraw2.service - Intel Precise Touch & Stylus Daemon Loaded: loaded (/usr/lib/systemd/system/iptsd@.service; static) Active: active (running) since Mon 2024-06-03 22:08:36 CEST; 29s ago Docs: https://github.com/linux-surface/iptsd Main PID: 1166 (iptsd) Tasks: 1 (limit: 18924) Memory: 908.0K (peak: 1.6M) CPU: 735ms CGroup: /system.slice/system-iptsd.slice/iptsd@dev-hidraw2.service └─1166 /usr/bin/iptsd /dev/hidraw2

jun 03 22:08:36 lenny systemd[1]: Started Intel Precise Touch & Stylus Daemon. jun 03 22:08:36 lenny iptsd[1166]: [22:08:36.756] [info] Connected to device 045E:0021

I think I understand the goal, but as a user I just need the daemon to be there when the device is, and it never seems to recover from this until a reboot. Not sure how that should work.

I am not sure what is going on on your system. What do you mean by udev getting reloaded? Are you reloading it yourself?

Can you post the output of dmesg when it breaks?

So it stops working after a while when not rebooting the system, and I noticed during troubleshooting it consistently stopped working when I do "sudo udevadm control --reload-rules && sudo udevadm trigger" which is what I use to reproduce it.

The dmesg output when it breaks using that udevadm command:

[ma jun 3 22:11:12 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: Stopping IPTS [ma jun 3 22:11:12 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: Failed to wait for flush: -11 [ma jun 3 22:11:13 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: Starting IPTS [ma jun 3 22:11:13 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: IPTS EDS Version: 1 [ma jun 3 22:11:13 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: IPTS running in event mode

And:

systemctl status $(iptsd-find-service) ○ iptsd@dev-hidraw2.service - Intel Precise Touch & Stylus Daemon Loaded: loaded (/usr/lib/systemd/system/iptsd@.service; static) Active: inactive (dead) Docs: https://github.com/linux-surface/iptsd

jun 03 22:08:36 lenny systemd[1]: Started Intel Precise Touch & Stylus Daemon. jun 03 22:08:36 lenny iptsd[1166]: [22:08:36.756] [info] Connected to device 045E:0021 jun 03 22:11:12 lenny systemd[1]: Stopping Intel Precise Touch & Stylus Daemon... jun 03 22:11:12 lenny iptsd[1166]: [22:11:12.129] [warning] Interrupted system call jun 03 22:11:12 lenny iptsd[1166]: [22:11:12.229] [info] Stopping jun 03 22:11:13 lenny systemd[1]: iptsd@dev-hidraw2.service: Deactivated successfully. jun 03 22:11:13 lenny systemd[1]: Stopped Intel Precise Touch & Stylus Daemon. jun 03 22:11:13 lenny systemd[1]: iptsd@dev-hidraw2.service: Consumed 3.141s CPU time, 1.6M memory peak, 0B memory swap peak.

I have just rebooted with the service file using /dev/hidraw1, and doing that I can't get it to break using the udevadm command. The dmesg output doesn't show the "Failed to wait for flush: -11" error though:

[ma jun 3 22:15:31 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: Starting IPTS [ma jun 3 22:15:31 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: IPTS EDS Version: 1 [ma jun 3 22:15:31 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: IPTS running in event mode [ma jun 3 22:15:34 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: Stopping IPTS [ma jun 3 22:15:35 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: Starting IPTS [ma jun 3 22:15:35 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: IPTS EDS Version: 1 [ma jun 3 22:15:35 2024] ipts 0000:00:16.4-3e8d0870-271a-4208-8eb5-9acb9402ae04: IPTS running in poll mode

And it changed to "poll mode" apparently.

So I am not sure this udevadm command is a good test to be honest. It can confirm it does stop working when leaving the laptop on for an extended periode of time (days).

StollD commented 3 weeks ago

So I am not sure this udevadm command is a good test to be honest.

It certainly seems interesting. Looks almost like a systemd bug to me ... the device node is kept around but the device unit vanishes?

I'll check if I can reproduce this on my machine.