rasteri / HIDman

Adapting USB devices to work on old computers
282 stars 21 forks source link

PS/2 and mouse incompatibilities #44

Open pdaderko opened 3 weeks ago

pdaderko commented 3 weeks ago

I recently built a couple HIDman AXP (Rev C) boards and loaded them with FW v1.1.3, and I've encountered some PS/2 and mouse functionality/incompatibility issues. I'm hoping you can either help me resolve them, or tell me how I can best help improve HIDman.

First, I have no PS/2 mouse functionality at all when using a cheap PS/2 to USB adapter or connected to an older HP EliteBook 6930p docking station. Both of those work with a true PS/2 mouse. The USB adapter is pictured at the bottom... I don't remember where I got it, but it shows up as VID: 0x13BA PID: 0x0018. Keyboard functionality seems to work on both of those. I have the mouse PS/2 cable plugged into the side w/ the USB connectors, and KB PS/2 cable plugged into the side w/ the RS232 connector, which I think is correct.

I have a KVM cable with a built-in PS/2 to USB adapter (VID: 0x0557 PID: 0x2221), which does work with HIDman, so I'm pretty sure my HIDman builds are working correctly, and is compatible with the USB mouse I was using. I've got a few other systems with PS/2 ports that I'll be testing with shortly.

I also have a wireless keyboard and mouse combo (also pictured at the bottom): https://www.amazon.com/gp/product/B078G77FK8/ (Miritz 2.4GHz Wireless Mini Keyboard with Mouse Touchpad) that seems to have a working keyboard, but the mouse has weird behavior. Left/right on the mouse moves the cursor up/down, and if I hold a mouse button, any mouse movement will also move to the right. If I change the mouse settings to "Advanced USB - Yes", then it seems to function correctly, though has very choppy movement. It isn't choppy when natively connected to a PC, and a regular USB mouse isn't choppy through HIDman with the same settings.

And while the keyboard seems to generally work, I've had quite a few issues with the menu, which seems like it'd be PS/2 keyboard related. I have never gotten the menu to work with the "good" PS/2 to USB adapter (0x0557/0x2221) - I usually get something like below, which looks like it's trying, but has a bunch of dropped characters:

Ha.
.e2 Mo3  d
mu

With the "bad" adapter (0x13BA/0x0018) I usually get just a partial menu (sometimes ending with a bunch of repeated characters), though occasionally get a full menu. Something like below is pretty typical:

HIgame

4. Adv.

ESC to exit menu

Gooddddddddddddddddd

I'm happy to dig into these issues - I've got a logic analyzer, oscilloscope, Cynthion (USB analyzer), etc... and plenty of other devices to compare with. Just looking to help in the most efficient way - if these are known issues that you're working on, I'll just wait... or if log dumps will tell you everything, I can send those your way. Or if I should start probing lines and looking at timing, voltage levels, etc... I can do that too.

And a couple quick notes on the build - overall, it went smoothly, but I noticed the gerbers posted don't have a solder paste mask layer, and are slightly out of date vs. the latest KiCAD files. I was able to revert the KiCAD PCB file to the commit matching the gerbers and export it, but having everything matched may make the build easier for others. And a note about shorting C5 for the initial firmware load on factory fresh CH559L chips (found that on a forum post) would have also saved a few minutes.

IMG_6390

Thanks

rasteri commented 3 weeks ago

All PS/2 to USB adapters that I've tried are pretty buggy.

For a start they don't send the necessary command to enable PS/2 mice. In an older revision of hidman we used to ignore that anyway, but that caused problems with certain BIOSes on real PCs, so the decision was made to support them rather than the PS/2 adapters. Perhaps we could make it an option in the menu.

Regarding the menu issues, if you check with a logic analyzer you'll see that HIDman is sending the correct codes but the adapter is missing half of them. I'd like to get HIDman working with them but even inserting a huge delay between each code doesn't help. I'd ideally like to get these adapters working but obviously they're not really a high priority.

Your PS/2 keyboard/touchpad combo should work though - if you could send me a HID dump that would be great - make sure to move the mouse after it dumps the descriptors, and try it in both advanced and normal USB mode. In fact if you could install USBtreeview and get me all the information there too that would be great :

usbtreeview

Good shout on the paste layer - PCBway didn't complain so I guess they generated one themselves, but if you fancy posting the paste layer you generated you'd save me some time.

pdaderko commented 3 weeks ago

Thanks for the info... makes sense that real PS/2 compatibility is more important than USB PS/2 adapters.

Attached is the dump of the dongle from USB UsbTreeView: wireless_kb_mouse.txt

The paste layer corresponding to the Rev C gerbers posted is attached: ps2usb-F_Paste.zip

I'll post back here shortly with the HID dumps... I need to reboot this PC for it to (hopefully) detect HIDman on the native PS/2 port so I can capture the dumped outputs.

pdaderko commented 3 weeks ago

Here's the log in regular mode: HID_log.txt

Here's the log in advanced mode: HID_log_adv.txt

For both of these, I was moving my finger around in a figure-eight pattern. Then at the end I alternated clicking the two mouse buttons a bunch of times.

Some good news is that I can confirm HIDman works with my modern motherboard (MSI PRO Z690-A WIFI).

rasteri commented 3 weeks ago

Hi, the usbtreeview stuff is great, but those HIDman logs don't include the report descriptors - if you could make sure you unplug/replug your wireless dongle into hidman while the HID is logging that would be great, as it only dumps the report descriptors when you plug something in.

pdaderko commented 3 weeks ago

I was wondering about that... you mentioned descriptors, but I didn't see them.

Here they are - regular mode: HID_log.txt

Advanced mode: HID_log_adv.txt

And I did some quick testing/debugging with the scope last night - the 0x13BA/0x0018 USB adapter looks to hold the clock low to throttle the data until its buffer is clear, so it makes sense that it usually gets long bursts of legible data, and sometimes full menus. The other USB adapter (0x0557/0x2221) looks like it doesn't do anything to the clock, so HIDman writes at full speed, causing it to drop most of the characters. Though when powered up the 0x0557/0x2221 adapter looks to enable the mouse, while the 0x13BA/0x0018 adapter doesn't (causing the dead mouse on that one). If I "initialize" the HIDman mouse with 0x0557/0x2221, then swap the mouse plug to 0x13BA/0x0018, it works. So yeah, if you could add an option to force enable the mouse, I think that'd be helpful.

I also tried this on my HP 16702B Logic Analyzer, and it doesn't seem to work at all. But that's not totally surprising, since I've tried 5 or 6 PS/2 devices on it, and only one has actually worked (IIRC an HP PS/2 rack mounted console). So I'll try to figure out what the difference between the good/bad is.

pdaderko commented 3 weeks ago

I built a PS/2 passthrough so I could easily probe the lines to see what the 16702B was doing. And it looks like the problem is that they don't (always?) follow the PS/2 protocol of pulling the clock low before data low to request a host to device transfer.

During boot, on both the keyboard and the mouse, there's a point where the data line goes low and stays low forever (presumably waiting for a response): Keyboard: 16702b_kb Mouse: 16702b_mouse

The blue trace is clock, yellow is data, magenta is the "extra" data line from the other connector (I probed that to make sure it wasn't HIDman holding the data low).

With HIDman, if I press a key on the keyboard, it sends clocks for the key press data, and the data line goes high again, but the keyboard still doesn't work... so I assume it's actually looking for the response data, or maybe just timely response. If I boot with the good keyboard, then hot swap to HIDman, the keyboard does work, so it must be generally compatible... just missing something at startup.

The same applies for the mouse as well. If I boot with the good mouse, and "initialize" the mouse on HIDman, then hot swap, the mouse works fine.

I also tested a couple more PS/2 mice on the 16702B, and both worked. One is an Intellimouse Optical, and the other an old/cheap "Mini Optical Mouse". So I guess some devices are OK with how it does host to data transfer.

Is it possible to only check for data being held low instead of ensuring clock went low first? Or will that break something else, or require reworking a bunch of code?

rasteri commented 3 weeks ago

I'll get more into it later, but looks like your keyboard isn't going into boot mode properly.

I've tweaked the boot mode logic a bit, could you try this firmware and see if that makes any difference? hidman_v1.1.4beta2.zip

I'll have a think about the clock/data thing later today.

pdaderko commented 3 weeks ago

I just tried that firmware, and I don't notice any difference (cursor still goes up/down when I move my finger left/right). I'm no expert on HID stuff, but is it possible that this doesn't support boot mode (and is there an easy way I could check)?

From a quick search, I came across this reddit thread: https://old.reddit.com/r/osdev/comments/unhe5x/about_usb_hid_keyboards/ ... not sure if that applies here.

BTW, to make the USB HID implementation simple you should use Boot protocol mode. Otherwise you would have to implement a quite involved parser. DON'T assume that all keyboards always use the same packet format in Boot mode and Report mode. DO check that the interface is capable of Boot mode, and ignore it otherwise. DO send the Set Protocol request with the Boot value to the keyboard to initialise the keyboard to Boot mode. When your OS starts talking to it, the mode could be either Report or Boot mode, so just don't assume one or the other.

BTW 2, DON'T assume that the first interface is the keyboard interface. (I've seen that error in host implementations)

rasteri commented 3 weeks ago

It CLAIMS to support Boot mode (bInterfaceSubClass is 0x01) but the packets it's giving out aren't in boot mode format.

I already do everything in that reddit post.

I've been meaning to get one of those tiny keyboards anyway so I ordered a very similar unit to yours, hopefully it behaves in the same way.

rasteri commented 3 weeks ago

I got one of those tiny keyboards and it fails in the exact same way. Interesting

pdaderko commented 3 weeks ago

Great! Er, well at least it's reproducible and not something weird on my end. Though let me know if there's anything I can do to help (as I mentioned, I do have a Cynthion, so I can log all the USB traffic if that's helpful).

rasteri commented 3 weeks ago

So yeah as we thought it isn't going into boot mode properly. It claims to be but the reports it's sending aren't in boot mode format. So I guess it'll have to run in advanced USB mode.

I've made some changes, does this get it working in Advanced mode for you? hidman_v1.1.4beta3.zip

pdaderko commented 2 weeks ago

That seems to work the same as before. As I noted in my original post, if I have mouse set to "Advanced USB - Yes" then it works, though the movement is noticeably choppy. With "Advanced USB - No" it only moves vertically.

It sounds like you're suggesting this only supports Advanced mode, in which case, do you see the same choppiness, and is that expected for advanced mode?

rasteri commented 2 weeks ago

Movement seems fine with advanced USB on. Weird.

rasteri commented 2 weeks ago

Is there any way you could get me a video of the choppiness

pdaderko commented 2 weeks ago

The best way I can describe it is the Wireless KB/Mouse through HIDman in Advanced Mode feels like I'm connected to my computer through a VNC connection, while the wired mouse doesn't feel any different than plugged straight into the host.

I tried a video, but it's hard to capture the choppiness/lag. So instead I tried coming up with a way to objectively measure it. In the console of Firefox (Ctrl+Shift+K), I ran: onmousemove = function(e){console.log(Date.now(),e.clientX, e.clientY)}

This logs the current time in milliseconds, as well as the X and Y coordinate of the mouse cursor on every move. So I did figure-eights with the cursor and plotted the X and Y, as well as measured the average time delta between points. The cursor was updated on average every ~17ms (60 Hz) for every case except the Wireless KB/Mouse in Advanced Mode, which updated on average every ~40ms (25 Hz). This only captured the choppiness, though it also feels a bit laggy (but that's harder to definitively measure).

mouse_comparison

From those plots, you can see that the curves are much less smooth on the Wireless KB/Mouse in Advanced Mode, and also the "sensitivity" is noticeably reduced (a figure-eight only goes 200-300 pixels rather than 500-600 when natively plugged in). Maybe it's throwing away over half of the reported X/Y delta values?

I also ran it in boot mode, which obviously doesn't work correctly, but feels smooth. I held the button so it'd drift right while moving, and corresponding to the feel, I confirmed that it updated at 60 Hz.

Anyway, I'm not sure if that's helpful, but I appreciate you looking into it! (and the other things I mentioned)