You are not logged in.
I am trying to get my touch pad to work but no luck so far. It appears there are other people many other people with this problem, but I haven't got anything to work yet. I have tried several distros other then Arch and I am getting the same problem on each except linux mint 30.3 "una" live boot with a pretty old kernel. My touch pad is detected and left and right click works, but I cannot move the cursor. This post is very similar but that solution isn't working for me: https://bbs.archlinux.org/viewtopic.php?id=228686/. I also found this which indicates someone has got it working semi-recently on my exact machine: https://linux-hardware.org/?probe=cbea798725.
I can see my touch pad with libinput list-devices
Device: ELAN1206:00 04F3:30F1 Touchpad
Kernel: /dev/input/event5
Group: 8
Seat: seat0, default
Size: 125x63mm
Capabilities: pointer gesture
Tap-to-click: disabled
Tap-and-drag: enabled
Tap drag lock: disabled
Left-handed: disabled
Nat.scrolling: disabled
Middle emulation: disabled
Calibration: n/a
Scroll methods: *two-finger edge
Click methods: *button-areas clickfinger
Disable-w-typing: enabled
Disable-w-trackpointing: enabled
Accel profiles: flat *adaptive custom
Rotation: n/a
using evtest on event5 I get this which looks reasonable to me. Note that it even includes positions.
Event: time 1738819278.422243, type 3 (EV_ABS), code 57 (ABS_MT_TRACKING_ID), value 73
Event: time 1738819278.422243, type 3 (EV_ABS), code 53 (ABS_MT_POSITION_X), value 1264
Event: time 1738819278.422243, type 3 (EV_ABS), code 54 (ABS_MT_POSITION_Y), value 860
Event: time 1738819278.422243, type 1 (EV_KEY), code 330 (BTN_TOUCH), value 1
Event: time 1738819278.422243, type 1 (EV_KEY), code 325 (BTN_TOOL_FINGER), value 1
Event: time 1738819278.422243, type 3 (EV_ABS), code 0 (ABS_X), value 1264
Event: time 1738819278.422243, type 3 (EV_ABS), code 1 (ABS_Y), value 860
Event: time 1738819278.422243, type 4 (EV_MSC), code 5 (MSC_TIMESTAMP), value 0
Event: time 1738819278.422243, -------------- SYN_REPORT ------------
Event: time 1738819278.526021, type 3 (EV_ABS), code 57 (ABS_MT_TRACKING_ID), value -1
Event: time 1738819278.526021, type 1 (EV_KEY), code 330 (BTN_TOUCH), value 0
Event: time 1738819278.526021, type 1 (EV_KEY), code 325 (BTN_TOOL_FINGER), value 0
Event: time 1738819278.526021, -------------- SYN_REPORT ------------
Event: time 1738819278.630874, type 3 (EV_ABS), code 57 (ABS_MT_TRACKING_ID), value 74
Event: time 1738819278.630874, type 3 (EV_ABS), code 53 (ABS_MT_POSITION_X), value 1415
Event: time 1738819278.630874, type 3 (EV_ABS), code 54 (ABS_MT_POSITION_Y), value 799
Event: time 1738819278.630874, type 1 (EV_KEY), code 330 (BTN_TOUCH), value 1
Event: time 1738819278.630874, type 1 (EV_KEY), code 325 (BTN_TOOL_FINGER), value 1
Event: time 1738819278.630874, type 3 (EV_ABS), code 0 (ABS_X), value 1415
Event: time 1738819278.630874, type 3 (EV_ABS), code 1 (ABS_Y), value 799
Event: time 1738819278.630874, type 4 (EV_MSC), code 5 (MSC_TIMESTAMP), value 273000
Event: time 1738819278.630874, -------------- SYN_REPORT ------------
Event: time 1738819278.734036, type 3 (EV_ABS), code 57 (ABS_MT_TRACKING_ID), value -1
Event: time 1738819278.734036, type 1 (EV_KEY), code 330 (BTN_TOUCH), value 0
Event: time 1738819278.734036, type 1 (EV_KEY), code 325 (BTN_TOOL_FINGER), value 0
Event: time 1738819278.734036, -------------- SYN_REPORT ------------
Event: time 1738819278.837978, type 3 (EV_ABS), code 57 (ABS_MT_TRACKING_ID), value 75
Event: time 1738819278.837978, type 3 (EV_ABS), code 53 (ABS_MT_POSITION_X), value 1728
Event: time 1738819278.837978, type 3 (EV_ABS), code 54 (ABS_MT_POSITION_Y), value 843
Event: time 1738819278.837978, type 1 (EV_KEY), code 330 (BTN_TOUCH), value 1
Event: time 1738819278.837978, type 1 (EV_KEY), code 325 (BTN_TOOL_FINGER), value 1
Event: time 1738819278.837978, type 3 (EV_ABS), code 0 (ABS_X), value 1728
Event: time 1738819278.837978, type 3 (EV_ABS), code 1 (ABS_Y), value 843
Event: time 1738819278.837978, type 4 (EV_MSC), code 5 (MSC_TIMESTAMP), value 487000
Event: time 1738819278.837978, -------------- SYN_REPORT ------------
Event: time 1738819278.941844, type 3 (EV_ABS), code 57 (ABS_MT_TRACKING_ID), value -1
Event: time 1738819278.941844, type 1 (EV_KEY), code 330 (BTN_TOUCH), value 0
Event: time 1738819278.941844, type 1 (EV_KEY), code 325 (BTN_TOOL_FINGER), value 0
Event: time 1738819278.941844, -------------- SYN_REPORT ------------
Event: time 1738819279.045889, type 4 (EV_MSC), code 5 (MSC_TIMESTAMP), value 705000
Event: time 1738819279.045889, -------------- SYN_REPORT ------------
Using libinput debug-events I only see events related to tapping not movement which is consistent with behavior.
-event5 DEVICE_ADDED ELAN1206:00 04F3:30F1 Touchpad seat0 default group1 cap:pg size 125x63mm tap(dl off) left scroll-nat scroll-2fg-edge click-buttonareas-clickfinger dwt-on dwtp-on
event5 GESTURE_HOLD_BEGIN +0.040s 1
event5 GESTURE_HOLD_END +0.104s 1
event5 GESTURE_HOLD_BEGIN +0.248s 1
event5 GESTURE_HOLD_END +0.312s 1
event5 GESTURE_HOLD_BEGIN +0.456s 1
event5 GESTURE_HOLD_END +0.520s 1
event5 GESTURE_HOLD_BEGIN +1.496s 1
event5 GESTURE_HOLD_END +1.560s 1
event5 POINTER_BUTTON +1.664s BTN_LEFT (272) pressed, seat count: 1
event5 POINTER_BUTTON +1.872s BTN_LEFT (272) released, seat count: 0
event5 POINTER_BUTTON +2.704s BTN_LEFT (272) pressed, seat count: 1
event5 POINTER_BUTTON +2.912s BTN_LEFT (272) released, seat count: 0
event5 GESTURE_HOLD_BEGIN +4.616s 1
event5 GESTURE_HOLD_END +4.680s 1
event5 GESTURE_HOLD_BEGIN +4.824s 1
event5 GESTURE_HOLD_END +4.888s 1
event5 POINTER_BUTTON +5.616s BTN_RIGHT (273) pressed, seat count: 1
event5 POINTER_BUTTON +5.824s BTN_RIGHT (273) released, seat count: 0
This may also be relevant:
cat /var/log/Xorg.0.log | grep -i Elan
...
[ 8.554] (II) Using input driver 'libinput' for 'ELAN1206:00 04F3:30F1 Touchpad'
[ 8.554] (**) ELAN1206:00 04F3:30F1 Touchpad: always reports core events
[ 8.583] (EE) libinput: ELAN1206:00 04F3:30F1 Touchpad: Failed to create a device for /dev/input/mouse1
[ 8.583] (EE) PreInit returned 2 for "ELAN1206:00 04F3:30F1 Touchpad"
If anyone has any suggestions help would be appreciated. It feels like its close to working since clicks are going through and the OS is (sort of) picking up on movement, but I'm a bit of a beginner and at a loss for where to go.
Last edited by nunibye (2025-02-06 07:24:26)
Offline
Update:
I was reading this https://bbs.archlinux.org/viewtopic.php?id=244535
If I run rmmod hid_multitouch the touchpad begins to scroll the page and can't click. modprobe hid_multitouch reverts the touchpad back to previous behavior.
Offline
Been working on it some more. After looking at evtest I realized the problem is that it is registering touch up very frequently. I wrote a quick C program to fix this by just filtering out some data and pushing events to a virtual touchpad. That worked and touch pad moves/clicks, but the events just don't come in fast enough and to filter the events you kinda have to remove gesture support. I'm guessing there is some problem with the i2c_hid_acpi driver not following precision touch protocol. I'm going to give up on this because I don't have the skills to fix i2c_hid_acpi especially since there is no documentation on how PTP works.
Offline
I fixed this by changing to kernel 6.1. It appears there was a bug introduced into the i2c stack at some point. Bug is referenced here: https://bugzilla.kernel.org/show_bug.cgi?id=217701. I still can't get the touchpad working on latest kernel.
Offline
I bisected the Kernel and identified this commit at around kernel 6.9: https://github.com/torvalds/linux/commi … a51d20c2bc. I confirmed that removing the conditional added in this commit does restore touchpad support in latest kernel. I created this bug report https://bugzilla.kernel.org/show_bug.cgi?id=219799. I created this pull request: https://github.com/torvalds/linux/pull/1153. I emailed something similar, but I likely got the format wrong. If anyone could help out by creating a better solution then simply removing the old commit and submitting a proper PR anything is appreciated.
Offline
I would suggest replying to https://lore.kernel.org/all/20240321120 … intel.com/ if you have not already contacted the author the commit that introduced the issue.
Offline
I would suggest replying to https://lore.kernel.org/all/20240321120 … intel.com/ if you have not already contacted the author the commit that introduced the issue.
Thank you for the reply, I will reach out to him. My "fix" causes very excessive interrupts so its not quite as simple as I hoped. I'm working on a workaround, but it would be great if this could get resolved properly.
Offline
If anyone else is having this problem in the future I fixed it by compiling and running this C program as a system d service. No need to modify kernel.
https://github.com/eliahreeves/.dotfile … tor/main.c
#include <dirent.h>
#include <fcntl.h>
#include <linux/input.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/epoll.h>
#include <time.h>
#include <unistd.h>
#define TOUCHPAD_NAME "ELAN1206"
#define MAX_PATH_LEN 256
#define MAX_LINE_LEN 256
int find_touchpad_event() {
DIR *dir;
struct dirent *entry;
char device_path[MAX_PATH_LEN];
int event_num;
dir = opendir("/sys/class/input");
if (dir == NULL) {
perror("Error opening /sys/class/input directory");
return -1;
}
while ((entry = readdir(dir)) != NULL) {
if (strncmp(entry->d_name, "event", 5) == 0) {
snprintf(device_path, MAX_PATH_LEN, "/sys/class/input/%s/device/name",
entry->d_name);
if (access(device_path, F_OK) != -1) {
FILE *device_file = fopen(device_path, "r");
if (device_file != NULL) {
char name_content[MAX_LINE_LEN];
if (fgets(name_content, MAX_LINE_LEN, device_file) != NULL) {
size_t len = strlen(name_content);
if (len > 0 && name_content[len - 1] == '\n') {
name_content[len - 1] = '\0';
}
if (strstr(name_content, TOUCHPAD_NAME) != NULL &&
strstr(name_content, "Touchpad") != NULL) {
sscanf(entry->d_name, "event%d", &event_num);
fclose(device_file);
break;
}
}
fclose(device_file);
}
}
}
}
closedir(dir);
return event_num;
}
int stop_touch_pad() {
FILE *fp = fopen("/sys/bus/platform/drivers/idma64/unbind", "w");
if (fp == NULL) {
perror("Failed to open file");
return 1;
}
if (fprintf(fp, "idma64.1") < 0) {
perror("Failed to write to file");
fclose(fp);
return 1;
}
fclose(fp);
return 0;
}
int start_touch_pad() {
FILE *fp = fopen("/sys/bus/platform/drivers/idma64/bind", "w");
if (fp == NULL) {
perror("Failed to open file");
return 1;
}
if (fprintf(fp, "idma64.1") < 0) {
perror("Failed to write to file");
fclose(fp);
return 1;
}
fclose(fp);
return 0;
}
int main() {
int touchpad_event = find_touchpad_event();
char touchpad_event_path[MAX_PATH_LEN];
if (touchpad_event != -1) {
snprintf(touchpad_event_path, MAX_PATH_LEN, "/dev/input/event%d",
touchpad_event);
int fd = open(touchpad_event_path, O_RDONLY | O_NONBLOCK);
if (fd < 0) {
perror("Failed to open device");
return 1;
}
int epfd = epoll_create1(0);
if (epfd < 0) {
perror("epoll_create1 failed");
close(fd);
return 1;
}
struct epoll_event ev;
ev.events = EPOLLIN;
ev.data.fd = fd;
if (epoll_ctl(epfd, EPOLL_CTL_ADD, fd, &ev) < 0) {
perror("epoll_ctl failed");
close(epfd);
close(fd);
return 1;
}
struct input_event event;
time_t last_event_time = time(NULL);
int is_sleeping = 0;
while (1) {
struct epoll_event events[1];
int nfds = epoll_wait(epfd, events, 1, 1000);
time_t current_time = time(NULL);
if (!is_sleeping && difftime(current_time, last_event_time) >= 1.0 &&
nfds == 0) {
is_sleeping = 1;
stop_touch_pad();
}
if (nfds > 0) {
if (read(fd, &event, sizeof(event)) == sizeof(event)) {
last_event_time = current_time;
if (is_sleeping) {
is_sleeping = 0;
start_touch_pad();
}
}
}
}
close(epfd);
close(fd);
return 0;
} else {
fprintf(stderr, "Touchpad device %s not found\n", TOUCHPAD_NAME);
return 1;
}
}
Offline
I'm on Mint and not Arch (for now...) but it worked for me, thanks for sharing! I've been searching everywhere for this for weeks now. I had the exact same symptoms and behavior as you on an ASUS UX564EI. If I didn't need secure boot for something on my windows partition I would have switched to arch just to try this already.
Last edited by Crazy88 (2025-03-20 02:09:47)
Offline
Thank you nunibye! I have been trying to get this working for a long time. It works on Arch, but also for Ubuntu. The link to your github for the code is broken, here is the updated with the updated code. https://github.com/eliahreeves/.dotfile … ad_monitor
Offline
Here is the idiots guide i had to make for myself using Brave Leo AI and nunibye's code:
To compile and run the `touchpad_monitor.sh` script as a system service, follow these steps:
1.Install `evtest` if you don't have it.
bash
sudo apt-get install evtest
2. **Save the script**: Create a file named `touchpad_monitor.sh` on your system in the file path of your choice, or use this one. You can use a text editor like `nano` or `vim` for this.
bash
sudo nano /etc/init.d/touchpad_monitor.sh
Copy this into the file, then save and exit:
#!/bin/bash
TOUCHPAD_NAME="ELAN1206"
find_touchpad_event() {
for device in /sys/class/input/event*/device/name; do
if [ -f "$device" ]; then
if grep -q "$TOUCHPAD_NAME" "$device"; then
event_path=$(dirname "$device")
event_num=$(basename "$(dirname "$event_path")" | sed 's/event//')
if [[ $(cat "$device") == *"Touchpad"* ]]; then
echo "/dev/input/event$event_num"
return 0
fi
fi
fi
done
return 1
}
TOUCHPAD_EVENT=$(find_touchpad_event)
if [ -z "$TOUCHPAD_EVENT" ]; then
exit 1
fi
LAST_EVENT_TIME=$(date +%s)
IS_SLEEPING=false
exec 3< <(evtest "$TOUCHPAD_EVENT")
while true; do
if IFS= read -r -t 1 line <&3; then
CURRENT_TIME=$(date +%s)
LAST_EVENT_TIME=$CURRENT_TIME
if [ "$IS_SLEEPING" = true ]; then
# wake
echo 'idma64.1' | sudo tee /sys/bus/platform/drivers/idma64/bind
IS_SLEEPING=false
fi
else
CURRENT_TIME=$(date +%s)
DIFF=$((CURRENT_TIME - LAST_EVENT_TIME))
if [ "$DIFF" -ge 1 ] && [ "$IS_SLEEPING" = false ]; then
# sleep
echo 'idma64.1' | sudo tee /sys/bus/platform/drivers/idma64/unbind
IS_SLEEPING=true
fi
fi
done
3. **Make the script executable**: Change the permissions of the script to make it executable.
bash
sudo chmod +x /etc/init.d/touchpad_monitor.sh
4. **Create a systemd service file**: Create a new file in the `/etc/systemd/system` directory to define the service.
bash
sudo nano /etc/systemd/system/touchpad_monitor.service
Add the following contents to the file, then save and exit:
[Unit]
Description=Touchpad Monitor Service
After=network.target
[Service]
ExecStart=/etc/init.d/touchpad_monitor.sh
Restart=always
[Install]
WantedBy=multi-user.target
5. **Reload the systemd daemon**: Reload the systemd daemon to pick up the new service file.
bash
sudo systemctl daemon-reload
6. **Enable the service**: Enable the service to start automatically on boot.
bash
sudo systemctl enable touchpad_monitor.service
7. **Start the service**: Start the service manually.
bash
sudo systemctl start touchpad_monitor.service
8. **Verify the service**: Check the status of the service to ensure it's running.
bash
sudo systemctl status touchpad_monitor.service
You may need to restart the OS to ensure everything is working correctly.
This code is from nunibye from https://github.com/eliahreeves/.dotfile … or.service, and the instructions from Brave Leo AI (Llama 3.1 8B)
Last edited by juanfibo (2025-04-07 05:08:54)
Offline
Here is the idiots guide i had to make for myself using Brave Leo AI and nunibye's code:
To compile and run the `touchpad_monitor.sh` script as a system service, follow these steps:
1.Install `evtest` if you don't have it.
bash
sudo apt-get install evtest2. **Save the script**: Create a file named `touchpad_monitor.sh` on your system in the file path of your choice, or use this one. You can use a text editor like `nano` or `vim` for this.
bash
sudo nano /etc/init.d/touchpad_monitor.shCopy this into the file, then save and exit:
#!/bin/bash
TOUCHPAD_NAME="ELAN1206"
find_touchpad_event() {
for device in /sys/class/input/event*/device/name; do
if [ -f "$device" ]; then
if grep -q "$TOUCHPAD_NAME" "$device"; then
event_path=$(dirname "$device")
event_num=$(basename "$(dirname "$event_path")" | sed 's/event//')
if [[ $(cat "$device") == *"Touchpad"* ]]; then
echo "/dev/input/event$event_num"
return 0
fi
fi
fi
done
return 1
}TOUCHPAD_EVENT=$(find_touchpad_event)
if [ -z "$TOUCHPAD_EVENT" ]; then
exit 1
fiLAST_EVENT_TIME=$(date +%s)
IS_SLEEPING=falseexec 3< <(evtest "$TOUCHPAD_EVENT")
while true; do
if IFS= read -r -t 1 line <&3; then
CURRENT_TIME=$(date +%s)
LAST_EVENT_TIME=$CURRENT_TIMEif [ "$IS_SLEEPING" = true ]; then
# wake
echo 'idma64.1' | sudo tee /sys/bus/platform/drivers/idma64/bind
IS_SLEEPING=false
fielse
CURRENT_TIME=$(date +%s)
DIFF=$((CURRENT_TIME - LAST_EVENT_TIME))
if [ "$DIFF" -ge 1 ] && [ "$IS_SLEEPING" = false ]; then
# sleep
echo 'idma64.1' | sudo tee /sys/bus/platform/drivers/idma64/unbind
IS_SLEEPING=true
fi
fi
done3. **Make the script executable**: Change the permissions of the script to make it executable.
bash
sudo chmod +x /etc/init.d/touchpad_monitor.sh4. **Create a systemd service file**: Create a new file in the `/etc/systemd/system` directory to define the service.
bash
sudo nano /etc/systemd/system/touchpad_monitor.serviceAdd the following contents to the file, then save and exit:
[Unit]
Description=Touchpad Monitor Service
After=network.target[Service]
ExecStart=/etc/init.d/touchpad_monitor.sh
Restart=always[Install]
WantedBy=multi-user.target
5. **Reload the systemd daemon**: Reload the systemd daemon to pick up the new service file.bash
sudo systemctl daemon-reload6. **Enable the service**: Enable the service to start automatically on boot.
bash
sudo systemctl enable touchpad_monitor.service7. **Start the service**: Start the service manually.
bash
sudo systemctl start touchpad_monitor.service8. **Verify the service**: Check the status of the service to ensure it's running.
bash
sudo systemctl status touchpad_monitor.serviceYou may need to restart the OS to ensure everything is working correctly.
This code is from nunibye from https://github.com/eliahreeves/.dotfile … or.service, and the instructions from Brave Leo AI (Llama 3.1 8B)
Gald this is helping other people, I kinda thought I was the only one going through this. I do highly recommend switching to my C program. It has no dependency on evtest and uses a fraction of the resources. I only actually used the bash script for a couple hours since it is inefficient. https://github.com/eliahreeves/.dotfile … tor/main.c
Offline
If anyone needs I can write a tutorial, but its pretty much the same as what juanfibo wrote up, but you need to compile the program first and then use the executable in place of the bash script.
Offline