Tại sao xsetwacom không hoạt động từ udev?


8

Tôi đã tạo một kịch bản để xoay máy tính bảng Wacom Bamboo của mình 180 độ. Nó hoạt động tốt khi tôi thực thi nó như chính tôi (người dùng) hoặc root, nhưng khi bắt đầu từ udev(tức là khi cắm máy tính bảng vào một usbcổng) thì nó sẽ không hoạt động.

Quy tắc của Udev :

SUBSYSTEMS=="usb", ATTRS{idVendor}=="056a", ATTRS{idProduct}=="00d1", ATTRS{manufacturer}=="Wacom Co.,Ltd.", RUN+="/usr/local/bin/red-wacom-bamboo.sh"

Tập lệnh Wacom /usr/local/bin/red-wacom-blyn.sh :

#!/usr/bin/env bash

exec > /tmp/red-wacom.log
exec 2>&1

# I had to do this otherwise xsetwacom would say:
# "Failed to open Display ."
# Is there a way to do this without using my username?
export XAUTHORITY=/home/redsandro/.Xauthority
export DISPLAY=:0

/usr/bin/xsetwacom set "Wacom Bamboo 2FG 4x5 Pen stylus" Rotate half
/usr/bin/xsetwacom set "Wacom Bamboo 2FG 4x5 Finger touch" Rotate half

Kết quả trong /tmp/red-wacom.log :

Cannot find device 'Wacom Bamboo 2FG 4x5 Pen stylus'.
Cannot find device 'Wacom Bamboo 2FG 4x5 Finger touch'.

(Lưu ý rằng lỗi trong nhật ký có nghĩa là chính quy tắc udev không phải là vấn đề.)

Tôi đã thử thiết lập một sleeptrong kịch bản, có thể nó cần một vài ms. Nhưng điều đó không có ích.

  • Tại sao tập lệnh này không hoạt động khi được gọi trực tiếp từ udev?
    • Làm thế nào để tôi sửa lỗi này?
  • Tôi có thể gọi một tập lệnh từ udevmột người dùng cụ thể không? (ví dụ: đồng bộ hóa /homevới ổ đĩa sao lưu ngoài - / home / chỉ hiển thị cho người dùng của nó)

Câu trả lời:


3

Có một cách giải quyết khá dễ dàng, bạn có thể thêm một cái gì đó như thế này vào xorg.conf(hoặc một tệp trong xorg.conf.d, như tôi đã làm):

anthony@Watt:/etc/X11/xorg.conf.d$ cat 55-local-wacom.conf 
Section "InputClass"
       Identifier "Wacom Left Handed"
       MatchDriver "wacom"
       Option "Rotate" "half"
EndSection

Kiểm tra trang chủ wacom (4) để biết chi tiết về tất cả các tùy chọn bạn có thể đặt.

(Về lý thuyết, bạn có thể sử dụng MatchProductđể định cấu hình riêng lẻ bàn di chuột, bút, cục tẩy, v.v., nhưng khi tôi thử cách đó một thời gian, nó đã khiến Xorg bị phân tách. Tương tự nếu tôi cố gắng làm nổi chúng. Nhưng bạn không làm gì cả về điều đó ... và có thể lỗi đã được sửa.)


Wow, sau rất nhiều googling tôi không bao giờ đi qua điều này. Tôi nêu lên câu trả lời của bạn. Tôi sẽ thử nó khi tôi đang làm việc. Bất kỳ lý do cụ thể cho 55? Tôi luôn sử dụng ý tưởng rằng "vô số mục được xử lý sau cùng, vì vậy tốt nhất là bỏ qua số cho mục nhập tùy chỉnh."
Redsandro

@Redsandro /usr/share/X11/xorg.conf.d/50-wacom.conflà 50 trên hệ thống của tôi, vì vậy tôi đã chọn 55 để đến sau nó. Không chắc chắn rằng thậm chí có vấn đề.
derobert

Câu trả lời này cung cấp thông tin hữu ích nhưng không trả lời câu hỏi ban đầu. Nếu bạn cắm thiết bị USB Wacom của bạn sau khi máy chủ X đã khởi động thì sao?
Lqueryvg

1
@Lqueryvg InputClass áp dụng cho các thiết bị cắm nóng, do đó, nó cũng sẽ hoạt động.
derobert

@derobert, cảm ơn bạn đã phản hồi. Tôi đã không nhận ra InputClass cũng hoạt động cho hotplug. Tôi có một số sự kiện nút mà tôi ánh xạ bằng xsetwacom và tôi muốn kích hoạt chúng nếu tôi cắm nóng máy tính bảng của mình sau khi X bắt đầu. Tôi sẽ thử. Cảm ơn !
Lqueryvg

2

Khi bạn cắm thiết bị:

  1. Linux phát hiện thiết bị và tạo một mục thiết bị dựa trên các quy tắc udev.
  2. Máy chủ X phát hiện thiết bị.

Bạn không thể chạy xsetwacomtrước giai đoạn 2. Kịch bản của bạn bị lỗi vì bạn đang chạy nó ở giai đoạn 1, khi X chưa biết thiết bị.

Bạn có thể thiết lập một số cài đặt với gnome-settings-daemon. Tôi tin rằng nó nhận được thông báo về thiết bị mới thông qua D-Bus , nhưng tôi không biết sự kiện D-Bus sẽ như thế nào. Hãy thử gián điệp trên xe buýt với dbus-monitor.


Tôi nêu lên câu trả lời của bạn để biết chi tiết, nhưng tôi không chắc điều này đúng vì lý do sau: Tôi đã thử sử dụng sleepvới một loạt giây. Khi cắm điện, máy tính bảng hoạt động sau chưa đầy một giây, do đó, khi lệnh được thực thi, thiết bị đã được phát hiện và sử dụng X. Nhưng nó vẫn không hoạt động?
Redsandro

2

Nó hoạt động nếu bạn tạo hai tệp, một tập lệnh bao bọc được gọi bởi udev, lần lượt gọi tập lệnh cấu hình thực tế trong nền. Kịch bản cấu hình cần ngủ trong một thời gian ngắn, để X11 có thời gian thực hiện công việc của mình. Đây là thiết lập tôi sử dụng:

Tập lệnh Wrapper được gọi bởi udev (/usr/local/bin/setupwacom.sh):

#!/usr/bin/env bash
/usr/local/bin/setupwacom-post-X11.sh &

Tập lệnh cấu hình được gọi bởi tập lệnh bao bọc (/usr/local/bin/setupwacom-post-X11.sh):

#!/usr/bin/env bash
sleep 2
export XAUTHORITY=/home/adrian/.Xauthority
export DISPLAY=:0
# Put your xsetwacom commands here, for example: 
xsetwacom --set "Wacom Intuos S Pad pad" Button 1 "key +ctrl +shift e"

2

Không có câu trả lời nào ở đây phù hợp với tôi và các tùy chọn tôi muốn đặt không thể được chỉ định trong xorg.conf:

$ xsetwacom -x get 'Wacom Intuos PT S Pad pad' button 1 
Button: Actions are not supported by xorg.conf. Try shell format (-s) instead.

Cuối cùng tôi đã phải bắt đầu tập lệnh với một dịch vụ systemd được kích hoạt bởi quy tắc udev:

$ cat /etc/udev/rules.d/99-wacom.rules
SUBSYSTEM=="usb", ENV{ID_VENDOR_ID}=="056a", ENV{ID_MODEL_ID}=="0302", TAG+="systemd"

Nhà cung cấp và id model có thể được tìm thấy đang chạy lsusbvới thiết bị được cắm.

Để tải lại các quy tắc udev:

$ udevadm control --reload-rules
$ udevadm trigger

Việc TAG+="systemd"cho phép các dịch vụ systemd khác (hệ thống hoặc người dùng) phụ thuộc vào thiết bị (đăng ký nó dưới dạng một đơn vị thiết bị, xem man systemd.device). Để tìm tên của đơn vị thiết bị chạy udevadm monitorvà cắm vào máy tính bảng. tôi có

UDEV  [2918.098423] add      /devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.3 (usb)
...

Để kiểm tra systemd đang chọn nó, hãy làm

$ systemctl status /sys/devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.3/
● sys-devices-pci0000:00-0000:00:1d.0-usb2-2\x2d1-2\x2d1.3.device - CTH-480 [Intuos Pen & Touch (S)]
   Loaded: loaded
   Active: active (plugged) since Mon 2016-06-20 11:14:20 UYT; 29min ago
   Device: /sys/devices/pci0000:00/0000:00:1d.0/usb2/2-1/2-1.3

Vì vậy, đơn vị thiết bị là sys-devices-pci0000:00-0000:00:1d.0-usb2-2\x2d1-2\x2d1.3.devicevà nó có thể được sử dụng trong đơn vị dịch vụ systemd

 $ cat .config/systemd/user/wacom.service    
[Service]
Type=forking
Restart=no
ExecStart=/path/to/wacom-pad-button-setup

[Install]
WantedBy=default.target
WantedBy=sys-devices-pci0000:00-0000:00:1d.0-usb2-2\x2d1-2\x2d1.1.device
WantedBy=sys-devices-pci0000:00-0000:00:1d.0-usb2-2\x2d1-2\x2d1.2.device
WantedBy=sys-devices-pci0000:00-0000:00:1d.0-usb2-2\x2d1-2\x2d1.3.device

Có một đơn vị thiết bị trên mỗi cổng usb.

Sau đó kích hoạt và tải lại các đơn vị với systemctl --user enable wacom.servicesystemctl --user daemon-reload.

Tập lệnh vẫn cần ngủ một chút để xsetwacom tìm thiết bị và cài đặt $DISPLAY$XAUTHORITY. Type=oneshothoạt động tốt khi cắm thiết bị, nhưng nó không chạy nếu thiết bị đã được cắm khi khởi động máy tính. Đó là lý do tại sao tôi cần sử dụng dịch vụ người dùng thay vì hệ thống và tại sao đơn vị cũng có WantedBy=default.target. Vấn đề với oneshot là nó đã chặn startx. Type=forkingRestart=noyêu cầu systemd đừng đợi quá trình rẽ nhánh của tập lệnh thoát ra, do đó, tập lệnh có thể ngủ ở chế độ nền chờ Xorg bắt đầu.

$ cat bin/wacom-pad-button-setup
#!/bin/rc
{
    sleep 2

    if (~ $DISPLAY ()) {
        DISPLAY=:0
        XAUTHORITY=/home/spelufo/.Xauthority
    }

    xsetwacom set 'Wacom Intuos PT S Pad pad' button 9 'button +3 -3'
    xsetwacom set 'Wacom Intuos PT S Pad pad' button 8 'button +4 -4'
    xsetwacom set 'Wacom Intuos PT S Pad pad' button 3 'button +1 -1'
    xsetwacom set 'Wacom Intuos PT S Pad pad' button 1 'button +2 -2'
} &

Tôi không biết tại sao nó không phải là trường hợp trong tình huống của bạn, nhưng tôi đã phải chạy trốn ít nhất là \xđể \\xtrong file dịch vụ. WantedBy của tôi cuối cùng trông như thế này: WantedBy=sys-devices-pci0000\:00-0000\:00\:14.0-usb1-1\\x2d4.devicevà bây giờ chúng được kích hoạt ... trước khi chúng không hoạt động.
ngày

1

Cách giải quyết của derobert không phù hợp với mọi tình huống (nếu bạn không thể sử dụng xorg.conf).

Gói và sleepgiải pháp được đề xuất bởi Adrian bằng cách nào đó không hoạt động đối với tôi (ubfox 16.04).

Nếu bạn thêm phần này vào đầu tập lệnh xsetwacom của bạn:

exec > /tmp/debug-my-script.txt 2>&1
xinput --list

Bạn có thể thấy từ đầu ra rằng tập lệnh xsetwacom bằng cách nào đó vẫn được thực thi trước khi xinputbiết về wacom. Không có vấn đề bao lâu bạn làm cho giấc ngủ.

Những gì tôi đề xuất ở đây là một giải pháp khác / workaround sử dụng chương trình nhỏ đó là đơn giản hơn so với các giải pháp của spelufo (mà tôi đã không cố gắng) nhưng chỉ đòi hỏi phải cài đặt atchương trình. ( sudo apt install atđối với người dùng debian).

Bây giờ thay đổi tập lệnh trình bao bọc của bạn (câu trả lời của Adrian) thành một cái gì đó như thế này:

#!/usr/bin/env bash
at now -f /usr/local/bin/setupwacom-post-X11.sh

atthường được sử dụng để lên lịch một lệnh một lần, ví dụ bạn có thể lên lịch trước một giờ at now +1 hours -f yourscript.sh. Nhưng vì bạn chỉ có thể thêm phút / giờ / ngày / tuần mà tôi đã sử dụng nowmà không cần thêm mà chỉ dựa vào giấc ngủ bên trong tập lệnh xsetwacom.


Đối mặt với cùng một vấn đề với đề xuất của Adrian và điều này đã khắc phục nó cho tôi trên 16.04 Ubuntu. Tôi gây trở ngại cho tôi làm thế nào nó bắt đầu làm việc với at nowmà không có bất kỳ sự giả mạo nào. Bất kỳ lý do cho điều đó? Trên thực tế với atphương thức, nó thậm chí không cần tập lệnh bao bọc. Bạn có thể trực tiếp thêm nó dưới dạng .., RUN+="/usr/bin/at now -f script-path":)
Gaurav

Điều này thật điên rồ vì tôi thậm chí không có giấc ngủ trong kịch bản và nó hoạt động mà không có nó. Tôi ước tôi biết những gì đang xảy ra trong nền để nó hoạt động vớiat
BozanicJosip
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.