Files
ViperOS/VKernel/Kernel/drivers/usb/hid/usb_mouse.py
2026-07-19 12:38:20 +08:00

78 lines
2.7 KiB
Python

import t, c
import drivers.usb.usb as usb
import drivers.usb.hid.hid as hid
import drivers.usb.uhci as uhci
import drivers.serial.uart.serial as serial
MOUSE_BUF_SIZE: t.CDefine = 1024
class usb_mouse_packet(t.CStruct):
buttons: t.CUInt8T
dx: t.CInt16T
dy: t.CInt16T
wheel: t.CInt8T
mse_buf: t.CArray[usb_mouse_packet, MOUSE_BUF_SIZE]
mse_buf_head: t.CInt = 0
mse_buf_tail: t.CInt = 0
mse_buf_count: t.CInt = 0
mse_dev: usb.usb_device | t.CPtr = None
mse_report: hid.hid_mouse_report
mse_initialized: t.CInt = 0
mse_slot_id: t.CInt = -1
def init() -> t.CInt:
global mse_dev, mse_initialized, mse_slot_id
dev: usb.usb_device | t.CPtr = usb.find_hid_device(0x02)
if dev is None:
serial.puts("[usb_mse] no USB mouse found\n")
return -1
mse_dev = dev
if hid.init_mouse(dev) != 0:
serial.puts("[usb_mse] init failed\n")
return -2
mse_initialized = 1
serial.puts("[usb_mse] initialized\n")
mse_slot_id = uhci.register_int_callback(c.Addr(_on_int_complete))
if mse_slot_id < 0:
serial.puts("[usb_mse] register callback failed\n")
mse_initialized = 0
return -3
uhci.schedule_int_transfer(mse_slot_id, dev.addr, dev.ep_in, dev.ls, t.CUInt8T(dev.ep_in_max), dev.ep_in_toggle, c.Addr(mse_report))
return 0
def _on_int_complete() -> t.CInt:
global mse_buf_head, mse_buf_tail, mse_buf_count
if mse_initialized == 0: return 0
if mse_report.dx != 0 or mse_report.dy != 0 or mse_report.buttons != 0:
if mse_buf_count < MOUSE_BUF_SIZE:
mse_buf[mse_buf_tail].buttons = mse_report.buttons
mse_buf[mse_buf_tail].dx = t.CInt16T(mse_report.dx)
mse_buf[mse_buf_tail].dy = t.CInt16T(mse_report.dy)
mse_buf[mse_buf_tail].wheel = mse_report.wheel
mse_buf_tail = mse_buf_tail + 1
if mse_buf_tail >= MOUSE_BUF_SIZE:
mse_buf_tail = 0
mse_buf_count += 1
dev: usb.usb_device | t.CPtr = mse_dev
if dev is not None and mse_slot_id >= 0:
uhci.schedule_int_transfer(mse_slot_id, dev.addr, dev.ep_in, dev.ls, t.CUInt8T(dev.ep_in_max), dev.ep_in_toggle, c.Addr(mse_report))
return 0
def has_data() -> t.CInt:
if mse_buf_count > 0: return 1
return 0
def read_packet(out: usb_mouse_packet | t.CPtr) -> t.CInt:
global mse_buf_head, mse_buf_count
if mse_buf_count == 0: return -1
out.buttons = mse_buf[mse_buf_head].buttons
out.dx = mse_buf[mse_buf_head].dx
out.dy = mse_buf[mse_buf_head].dy
out.wheel = mse_buf[mse_buf_head].wheel
mse_buf_head = mse_buf_head + 1
if mse_buf_head >= MOUSE_BUF_SIZE:
mse_buf_head = 0
mse_buf_count -= 1
return 0