Subversion Repositories Kolibri OS

Rev

Rev 4530 | Go to most recent revision | Only display areas with differences | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 4530 Rev 4592
1
; HID mouse driver, part of USBHID driver.
1
; HID mouse driver, part of USBHID driver.
2
 
2
 
3
; Global constants.
3
; Global constants.
4
; They are assembled in a macro to separate code and data;
4
; They are assembled in a macro to separate code and data;
5
; the code is located at the point of "include 'mouse.inc'",
5
; the code is located at the point of "include 'mouse.inc'",
6
; the data are collected when workers_globals is instantiated.
6
; the data are collected when workers_globals is instantiated.
7
macro workers_globals
7
macro workers_globals
8
{
8
{
9
; include global constants from previous workers
9
; include global constants from previous workers
10
        workers_globals
10
        workers_globals
11
align 4
11
align 4
12
; Callbacks for HID layer.
12
; Callbacks for HID layer.
13
mouse_driver:
13
mouse_driver:
14
        dd      mouse_driver_add_device
14
        dd      mouse_driver_add_device
15
        dd      mouse_driver_disconnect
15
        dd      mouse_driver_disconnect
16
        dd      mouse_driver_begin_packet
16
        dd      mouse_driver_begin_packet
17
        dd      mouse_driver_array_overflow?
17
        dd      mouse_driver_array_overflow?
18
        dd      mouse_driver_input_field
18
        dd      mouse_driver_input_field
19
        dd      mouse_driver_end_packet
19
        dd      mouse_driver_end_packet
20
}
20
}
21
 
21
 
22
; Data that are specific for one mouse device.
22
; Data that are specific for one mouse device.
23
struct mouse_device_data
23
struct mouse_device_data
24
buttons         dd      ?       ; buttons that are currently pressed
24
buttons         dd      ?       ; buttons that are currently pressed
25
dx              dd      ?       ; current x moving
25
dx              dd      ?       ; current x moving
26
dy              dd      ?       ; current y moving
26
dy              dd      ?       ; current y moving
27
wheel           dd      ?       ; current wheel moving
27
wheel           dd      ?       ; current wheel moving
28
hwheel          dd      ?
28
hwheel          dd      ?
29
ends
29
ends
30
 
30
 
31
; This procedure is called when HID layer detects a new mouse.
31
; This procedure is called when HID layer detects a new mouse.
32
; in: ebx -> device_data from USB layer, edi -> collection
32
; in: ebx -> device_data from USB layer, edi -> collection
33
; out: eax = device-specific data or NULL on error
33
; out: eax = device-specific data or NULL on error
34
proc mouse_driver_add_device
34
proc mouse_driver_add_device
35
; Get screen resolution so we can calculate absolute coordinates.
-
 
36
        mov     eax, 14
-
 
37
        int     0x40
-
 
38
        mov     [screen_y], eax
-
 
39
        and     [screen_y], 0xffff
-
 
40
        shr     eax, 16
-
 
41
        mov     [screen_x], eax
-
 
42
; Just allocate memory; no initialization needed.
35
; Just allocate memory; no initialization needed.
43
        movi    eax, sizeof.mouse_device_data
36
        movi    eax, sizeof.mouse_device_data
44
        call    Kmalloc
37
        call    Kmalloc
45
        ret
38
        ret
46
endp
39
endp
47
 
40
 
48
; This procedure is called when HID layer detects disconnect of a previously
41
; This procedure is called when HID layer detects disconnect of a previously
49
; connected mouse.
42
; connected mouse.
50
; in: edi -> mouse_device_data (pointer returned from mouse_driver_add_device)
43
; in: edi -> mouse_device_data (pointer returned from mouse_driver_add_device)
51
proc mouse_driver_disconnect
44
proc mouse_driver_disconnect
52
; Free the allocated memory.
45
; Free the allocated memory.
53
        mov     eax, edi
46
        mov     eax, edi
54
        call    Kfree
47
        call    Kfree
55
        ret
48
        ret
56
endp
49
endp
57
 
50
 
58
; This procedure is called when HID layer starts processing a new input packet
51
; This procedure is called when HID layer starts processing a new input packet
59
; from a mouse.
52
; from a mouse.
60
; in: edi -> mouse_device_data (pointer returned from mouse_driver_add_device)
53
; in: edi -> mouse_device_data (pointer returned from mouse_driver_add_device)
61
proc mouse_driver_begin_packet
54
proc mouse_driver_begin_packet
62
; Zero all variables describing the current state.
55
; Zero all variables describing the current state.
63
        mov     [edi+mouse_device_data.buttons], 0
56
        mov     [edi+mouse_device_data.buttons], 0
64
        mov     [edi+mouse_device_data.dx], 0
57
        mov     [edi+mouse_device_data.dx], 0
65
        mov     [edi+mouse_device_data.dy], 0
58
        mov     [edi+mouse_device_data.dy], 0
66
        mov     [edi+mouse_device_data.wheel], 0
59
        mov     [edi+mouse_device_data.wheel], 0
67
        mov     [edi+mouse_device_data.hwheel], 0
60
        mov     [edi+mouse_device_data.hwheel], 0
68
        ret
61
        ret
69
endp
62
endp
70
 
63
 
71
; This procedure is called when HID layer processes every non-empty array field group.
64
; This procedure is called when HID layer processes every non-empty array field group.
72
; in: edi -> mouse_device_data (pointer returned from mouse_driver_add_device)
65
; in: edi -> mouse_device_data (pointer returned from mouse_driver_add_device)
73
; in: ecx = fields count (always nonzero), edx = pointer to fields values
66
; in: ecx = fields count (always nonzero), edx = pointer to fields values
74
; in: esi -> report_field_group
67
; in: esi -> report_field_group
75
; out: CF set => array is ok, CF cleared => array should be ignored
68
; out: CF set => array is ok, CF cleared => array should be ignored
76
proc mouse_driver_array_overflow?
69
proc mouse_driver_array_overflow?
77
; no array fields, no overflows
70
; no array fields, no overflows
78
        stc
71
        stc
79
        ret
72
        ret
80
endp
73
endp
81
 
74
 
82
; This procedure is called from HID layer for every field.
75
; This procedure is called from HID layer for every field.
83
; in: edi -> mouse_device_data (pointer returned from mouse_driver_add_device)
76
; in: edi -> mouse_device_data (pointer returned from mouse_driver_add_device)
84
; in: ecx = field usage, edx = value, esi -> report_field_group
77
; in: ecx = field usage, edx = value, esi -> report_field_group
85
proc mouse_driver_input_field
78
proc mouse_driver_input_field
86
; 1. Determine the handler. We process x/y moving, wheel and up to 32 buttons.
79
; 1. Determine the handler. We process x/y moving, wheel and up to 32 buttons.
87
; Pass other fields to the default handler - default_driver_input_field if
80
; Pass other fields to the default handler - default_driver_input_field if
88
; HID_DUMP_UNCLAIMED is enabled, just ignore otherwise.
81
; HID_DUMP_UNCLAIMED is enabled, just ignore otherwise.
89
        cmp     ecx, USAGE_GD_X
82
        cmp     ecx, USAGE_GD_X
90
        jz      .x
83
        jz      .x
91
        cmp     ecx, USAGE_GD_Y
84
        cmp     ecx, USAGE_GD_Y
92
        jz      .y
85
        jz      .y
93
        cmp     ecx, USAGE_GD_WHEEL
86
        cmp     ecx, USAGE_GD_WHEEL
94
        jz      .wheel
87
        jz      .wheel
95
        cmp     ecx, 0xC0238
88
        cmp     ecx, 0xC0238
96
        jz      .hwheel
89
        jz      .hwheel
97
        sub     ecx, USAGE_BUTTON_PAGE + 1
90
        sub     ecx, USAGE_BUTTON_PAGE + 1
98
        jb      .unclaimed
91
        jb      .unclaimed
99
        cmp     ecx, 32
92
        cmp     ecx, 32
100
        jae     .unclaimed
93
        jae     .unclaimed
101
; 2. This is a button.
94
; 2. This is a button.
102
; If a button is pressed, set the corresponding bit in the state.
95
; If a button is pressed, set the corresponding bit in the state.
103
; If a button is not pressed, do nothing.
96
; If a button is not pressed, do nothing.
104
        test    edx, edx
97
        test    edx, edx
105
        jz      @f
98
        jz      @f
106
        bts     [edi+mouse_device_data.buttons], ecx
99
        bts     [edi+mouse_device_data.buttons], ecx
107
@@:
100
@@:
108
if ~HID_DUMP_UNCLAIMED
101
if ~HID_DUMP_UNCLAIMED
109
.unclaimed:
102
.unclaimed:
110
end if
103
end if
111
        ret
104
        ret
112
if HID_DUMP_UNCLAIMED
105
if HID_DUMP_UNCLAIMED
113
.unclaimed:
106
.unclaimed:
114
        add     ecx, USAGE_BUTTON_PAGE + 1
107
        add     ecx, USAGE_BUTTON_PAGE + 1
115
        jmp     default_driver_input_field
108
        jmp     default_driver_input_field
116
end if
109
end if
117
.x:
110
.x:
118
; 3. This is x moving. For relative fields, store the value in the state.
111
; 3. This is x moving. For relative fields, store the value in the state.
119
; Pass absolute field to the default handler.
112
; Pass absolute field to the default handler.
120
        test    byte [esi+report_field_group.flags], HID_FIELD_RELATIVE
113
        test    byte [esi+report_field_group.flags], HID_FIELD_RELATIVE
121
        jz      .absolute_x
114
        jz      .absolute_x
122
        mov     [edi+mouse_device_data.dx], edx
115
        mov     [edi+mouse_device_data.dx], edx
123
        ret
116
        ret
124
.y:
117
.y:
125
; 4. This is y moving. For relative fields, store the value in the state,
118
; 4. This is y moving. For relative fields, store the value in the state,
126
; changing the sign: HID uses "mathematics" scheme with Y axis increasing from
119
; changing the sign: HID uses "mathematics" scheme with Y axis increasing from
127
; bottom to top, the kernel expects "programming" PS/2-style with Y axis
120
; bottom to top, the kernel expects "programming" PS/2-style with Y axis
128
; increasing from top to bottom.
121
; increasing from top to bottom.
129
; Pass absolute fields to the default handler.
122
; Pass absolute fields to the default handler.
130
        test    byte [esi+report_field_group.flags], HID_FIELD_RELATIVE
123
        test    byte [esi+report_field_group.flags], HID_FIELD_RELATIVE
131
        jz      .absolute_y
124
        jz      .absolute_y
132
        neg     edx
125
        neg     edx
133
        mov     [edi+mouse_device_data.dy], edx
126
        mov     [edi+mouse_device_data.dy], edx
134
        ret
127
        ret
135
.wheel:
128
.wheel:
136
; 5. This is wheel event. For relative fields, store the value in the state,
129
; 5. This is wheel event. For relative fields, store the value in the state,
137
; changing the sign. Pass absolute fields to the default handler.
130
; changing the sign. Pass absolute fields to the default handler.
138
        test    byte [esi+report_field_group.flags], HID_FIELD_RELATIVE
131
        test    byte [esi+report_field_group.flags], HID_FIELD_RELATIVE
139
        jz      .unclaimed
132
        jz      .unclaimed
140
        neg     edx
133
        neg     edx
141
        mov     [edi+mouse_device_data.wheel], edx
134
        mov     [edi+mouse_device_data.wheel], edx
142
        ret
135
        ret
143
.hwheel:
136
.hwheel:
144
        test    byte [esi+report_field_group.flags], HID_FIELD_RELATIVE
137
        test    byte [esi+report_field_group.flags], HID_FIELD_RELATIVE
145
        jz      .unclaimed
138
        jz      .unclaimed
146
        mov     [edi+mouse_device_data.hwheel], edx
139
        mov     [edi+mouse_device_data.hwheel], edx
147
        ret
140
        ret
148
.absolute_x:
141
.absolute_x:
149
        push    ebx
-
 
150
        mov     eax, [screen_x]
-
 
151
        mul     edx
-
 
152
        mov     ebx, 0x8000
-
 
153
        div     ebx
-
 
154
        mov     [edi+mouse_device_data.dx], eax
142
        mov     [edi+mouse_device_data.dx], edx
155
        or      [edi+mouse_device_data.buttons], 0x80000000
143
        or      [edi+mouse_device_data.buttons], 0x80000000
156
        pop     ebx
-
 
157
        ret
144
        ret
158
.absolute_y:
145
.absolute_y:
159
        push    ebx
-
 
160
        mov     eax, [screen_y]
-
 
161
        mul     edx
-
 
162
        mov     ebx, 0x8000
-
 
163
        div     ebx
-
 
164
        mov     [edi+mouse_device_data.dy], eax
146
        mov     [edi+mouse_device_data.dy], edx
165
        or      [edi+mouse_device_data.buttons], 0x40000000
147
        or      [edi+mouse_device_data.buttons], 0x40000000
166
        pop     ebx
-
 
167
        ret
148
        ret
168
endp
149
endp
169
 
150
 
170
; This procedure is called when HID layer ends processing a new input packet
151
; This procedure is called when HID layer ends processing a new input packet
171
; from a mouse.
152
; from a mouse.
172
; in: edi -> mouse_device_data (pointer returned from mouse_driver_add_device)
153
; in: edi -> mouse_device_data (pointer returned from mouse_driver_add_device)
173
proc mouse_driver_end_packet
154
proc mouse_driver_end_packet
174
; Call the kernel, passing collected state.
155
; Call the kernel, passing collected state.
175
        stdcall SetMouseData, \
156
        stdcall SetMouseData, \
176
                [edi+mouse_device_data.buttons], \
157
                [edi+mouse_device_data.buttons], \
177
                [edi+mouse_device_data.dx], \
158
                [edi+mouse_device_data.dx], \
178
                [edi+mouse_device_data.dy], \
159
                [edi+mouse_device_data.dy], \
179
                [edi+mouse_device_data.wheel], \
160
                [edi+mouse_device_data.wheel], \
180
                [edi+mouse_device_data.hwheel]
161
                [edi+mouse_device_data.hwheel]
181
        ret
162
        ret
182
endp
163
endp