Subversion Repositories Kolibri OS

Rev

Rev 3520 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
3520 clevermous 1
; Code for OHCI controllers.
2
; Note: it should be moved to an external driver,
3
; it was convenient to have this code compiled into the kernel during initial
4
; development, but there are no reasons to keep it here.
5
 
6
; =============================================================================
7
; ================================= Constants =================================
8
; =============================================================================
9
; OHCI register declarations
10
; All of the registers should be read and written as Dwords.
11
; Partition 1. Control and Status registers.
12
OhciRevisionReg         = 0
13
OhciControlReg          = 4
14
OhciCommandStatusReg    = 8
15
OhciInterruptStatusReg  = 0Ch
16
OhciInterruptEnableReg  = 10h
17
OhciInterruptDisableReg = 14h
18
; Partition 2. Memory Pointer registers.
19
OhciHCCAReg             = 18h
20
OhciPeriodCurrentEDReg  = 1Ch
21
OhciControlHeadEDReg    = 20h
22
OhciControlCurrentEDReg = 24h
23
OhciBulkHeadEDReg       = 28h
24
OhciBulkCurrentEDReg    = 2Ch
25
OhciDoneHeadReg         = 30h
26
; Partition 3. Frame Counter registers.
27
OhciFmIntervalReg       = 34h
28
OhciFmRemainingReg      = 38h
29
OhciFmNumberReg         = 3Ch
30
OhciPeriodicStartReg    = 40h
31
OhciLSThresholdReg      = 44h
32
; Partition 4. Root Hub registers.
33
OhciRhDescriptorAReg    = 48h
34
OhciRhDescriptorBReg    = 4Ch
35
OhciRhStatusReg         = 50h
36
OhciRhPortStatusReg     = 54h
37
 
38
; =============================================================================
39
; ================================ Structures =================================
40
; =============================================================================
41
 
42
; OHCI-specific part of a pipe descriptor.
43
; * This structure corresponds to the Endpoint Descriptor aka ED from the OHCI
44
;   specification.
45
; * The hardware requires 16-bytes alignment of the hardware part.
46
;   Since the allocator (usb_allocate_common) allocates memory sequentially
47
;   from page start (aligned on 0x1000 bytes), size of the structure must be
48
;   divisible by 16.
49
struct ohci_pipe
50
; All addresses are physical.
51
Flags           dd      ?
52
; 1. Lower 7 bits (bits 0-6) are FunctionAddress. This is the USB address of
53
;    the function containing the endpoint that this ED controls.
54
; 2. Next 4 bits (bits 7-10) are EndpointNumber. This is the USB address of
55
;    the endpoint within the function.
56
; 3. Next 2 bits (bits 11-12) are Direction. This 2-bit field indicates the
57
;    direction of data flow: 1 = IN, 2 = OUT. If neither IN nor OUT is
58
;    specified, then the direction is determined from the PID field of the TD.
59
;    For CONTROL endpoints, the transfer direction is different
60
;    for different transfers, so the value of this field is 0
61
;    (3 would have the same effect) and the actual direction
62
;    of one transfer is encoded in the Transfer Descriptor.
63
; 4. Next bit (bit 13) is Speed bit. It indicates the speed of the endpoint:
64
;    full-speed (S = 0) or low-speed (S = 1).
65
; 5. Next bit (bit 14) is sKip bit. When this bit is set, the hardware
66
;    continues on to the next ED on the list without attempting access
67
;    to the TD queue or issuing any USB token for the endpoint.
68
;    Always cleared.
69
; 6. Next bit (bit 15) is Format bit. It must be 0 for Control, Bulk and
70
;    Interrupt endpoints and 1 for Isochronous endpoints.
71
; 7. Next 11 bits (bits 16-26) are MaximumPacketSize. This field indicates
72
;    the maximum number of bytes that can be sent to or received from the
73
;    endpoint in a single data packet.
74
TailP           dd      ?
75
; Physical address of the tail descriptor in the TD queue.
76
; The descriptor itself is not in the queue. See also HeadP.
77
HeadP           dd      ?
78
; 1. First bit (bit 0) is Halted bit. This bit is set by the hardware to
79
;    indicate that processing of the TD queue on the endpoint is halted.
80
; 2. Second bit (bit 1) is toggleCarry bit. Whenever a TD is retired, this
81
;    bit is written to contain the last data toggle value from the retired TD.
82
; 3. Next two bits (bits 2-3) are reserved and always zero.
83
; 4. With masked 4 lower bits, this is HeadP itself: physical address of the
84
;    head descriptor in the TD queue, that is, next TD to be processed for this
85
;    endpoint. Note that a TD must be 16-bytes aligned.
86
;    Empty queue is characterized by the condition HeadP == TailP.
87
NextED          dd      ?
88
; If nonzero, then this entry is a physical address of the next ED to be
89
; processed. See also the description before NextVirt field of the usb_pipe
90
; structure. Additionally to that description, the following is specific for
91
; the OHCI controller:
92
; * n=5, N=32, there are 32 "leaf" periodic lists.
93
; * The 1ms periodic list also serves Isochronous endpoints, which should be
94
;   in the end of the list.
95
; * There is no "next" list for Bulk and Control lists, they are processed
96
;   separately from others.
97
; * There is no "next" list for Periodic list for 1ms interval.
98
SoftwarePart    rd      sizeof.usb_pipe/4
99
; Software part, common for all controllers.
100
ends
101
 
102
if sizeof.ohci_pipe mod 16
103
.err ohci_pipe must be 16-bytes aligned
104
end if
105
 
106
; This structure describes the static head of every list of pipes.
107
; The hardware requires 16-bytes alignment of this structure.
108
; All instances of this structure are located sequentially in uhci_controller,
109
; uhci_controller is page-aligned, so it is sufficient to make this structure
110
; 16-bytes aligned and verify that the first instance is 16-bytes aligned
111
; inside uhci_controller.
112
struct ohci_static_ep
113
Flags           dd      ?
114
; Same as ohci_pipe.Flags.
115
; sKip bit is set, so the hardware ignores other fields except NextED.
116
                dd      ?
117
; Corresponds to ohci_pipe.TailP. Not used.
118
NextList        dd      ?
119
; Virtual address of the next list.
120
NextED          dd      ?
121
; Same as ohci_pipe.NextED.
122
SoftwarePart    rd      sizeof.usb_static_ep/4
123
; Software part, common for all controllers.
124
                dd      ?
125
; Padding for 16-bytes alignment.
126
ends
127
 
128
if sizeof.ohci_static_ep mod 16
129
.err ohci_static_ep must be 16-bytes aligned
130
end if
131
 
132
; OHCI-specific part of controller data.
133
; * The structure describes the memory area used for controller data,
134
;   additionally to the registers of the controller.
135
; * The structure includes two parts, the hardware part and the software part.
136
; * The hardware part consists of first 256 bytes and corresponds to
137
;   the HCCA from OHCI specification.
138
; * The hardware requires 256-bytes alignment of the hardware part, so
139
;   the entire descriptor must be 256-bytes aligned.
140
;   This structure is allocated with kernel_alloc (see usb_init_controller),
141
;   this gives page-aligned data.
142
; * The controller is described by both ohci_controller and usb_controller
143
;   structures, for each controller there is one ohci_controller and one
144
;   usb_controller structure. These structures are located sequentially
145
;   in the memory: beginning from some page start, there is ohci_controller
146
;   structure - this enforces hardware alignment requirements - and then
147
;   usb_controller structure.
148
; * The code keeps pointer to usb_controller structure. The ohci_controller
149
;   structure is addressed as [ptr + ohci_controller.field - sizeof.ohci_controller].
150
struct ohci_controller
151
; ------------------------------ hardware fields ------------------------------
152
InterruptTable  rd      32
153
; Pointers to interrupt EDs. The hardware starts processing of periodic lists
154
; within the frame N from the ED pointed to by [InterruptTable+(N and 31)*4].
155
; See also the description of periodic lists inside ohci_pipe structure.
156
FrameNumber     dw      ?
157
; The current frame number. This field is written by hardware only.
158
; This field is read by ohci_process_deferred and ohci_irq to
159
; communicate when control/bulk processing needs to be temporarily
160
; stopped/restarted.
161
                dw      ?
162
; Padding. Written as zero at every update of FrameNumber.
163
DoneHead        dd      ?
164
; Physical pointer to the start of Done Queue.
165
; When the hardware updates this field, it sets bit 0 to one if there is
166
; unmasked interrupt pending.
167
                rb      120
168
; Reserved for the hardware.
169
; ------------------------------ software fields ------------------------------
170
IntEDs          ohci_static_ep
171
                rb      62 * sizeof.ohci_static_ep
172
; Heads of 63 Periodic lists, see the description in usb_pipe.
173
ControlED       ohci_static_ep
174
; Head of Control list, see the description in usb_pipe.
175
BulkED          ohci_static_ep
176
; Head of Bulk list, see the description in usb_pipe.
177
MMIOBase        dd      ?
178
; Virtual address of memory-mapped area with OHCI registers OhciXxxReg.
179
PoweredUp       db      ?
180
; 1 in normal work, 0 during early phases of the initialization.
181
; This field is initialized to zero during memory allocation
182
; (see usb_init_controller), set to one by ohci_init when ports of the root hub
183
; are powered up, so connect/disconnect events can be handled.
184
                rb      3 ; alignment
185
DoneList        dd      ?
186
; List of descriptors which were processed by the controller and now need
187
; to be finalized.
188
DoneListEndPtr  dd      ?
189
; Pointer to dword which should receive a pointer to the next item in DoneList.
190
; If DoneList is empty, this is a pointer to DoneList itself;
191
; otherwise, this is a pointer to NextTD field of the last item in DoneList.
192
ends
193
 
194
if ohci_controller.IntEDs mod 16
195
.err Static endpoint descriptors must be 16-bytes aligned inside ohci_controller
196
end if
197
 
198
; OHCI general transfer descriptor.
199
; * The structure describes transfers to be performed on Control, Bulk or
200
;   Interrupt endpoints.
201
; * The structure includes two parts, the hardware part and the software part.
202
; * The hardware part consists of first 16 bytes and corresponds to
203
;   the General Transfer Descriptor aka general TD from OHCI specification.
204
; * The hardware requires 16-bytes alignment of the hardware part, so
205
;   the entire descriptor must be 16-bytes aligned. Since the allocator
206
;   (usb_allocate_common) allocates memory sequentially from page start
207
;   (aligned on 0x1000 bytes), size of the structure must be divisible by 16.
208
struct ohci_gtd
209
; ------------------------------ hardware fields ------------------------------
210
; All addresses in this part are physical.
211
Flags           dd      ?
212
; 1. Lower 18 bits (bits 0-17) are ignored and not modified by the hardware.
213
; 2. Next bit (bit 18) is bufferRounding bit. If this bit is 0, then the last
214
;    data packet must exactly fill the defined data buffer. If this bit is 1,
215
;    then the last data packet may be smaller than the defined buffer without
216
;    causing an error condition on the TD.
217
; 3. Next 2 bits (bits 19-20) are Direction field. This field indicates the
218
;    direction of data flow. If the Direction field in the ED is OUT or IN,
219
;    this field is ignored and the direction from the ED is used instead.
220
;    Otherwise, 0 = SETUP, 1 = OUT, 2 = IN, 3 is reserved.
221
; 4. Next 3 bits (bits 21-23) are DelayInterrupt field. This field contains
222
;    the interrupt delay count for this TD. When a TD is complete, the hardware
223
;    may wait up to DelayInterrupt frames before generating an interrupt.
224
;    If DelayInterrupt is 7 (maximum possible), then there is no interrupt
225
;    associated with completion of this TD.
226
; 5. Next 2 bits (bits 24-25) are DataToggle field. This field is used to
227
;    generate/compare the data PID value (DATA0 or DATA1). It is updated after
228
;    each successful transmission/reception of a data packet. The bit 25
229
;    is 0 when the data toggle value is acquired from the toggleCarry field in
230
;    the ED and 1 when the data toggle value is taken from the bit 24.
231
; 6. Next 2 bits (bits 26-27) are ErrorCount field. For each transmission
232
;    error, this value is incremented. If ErrorCount is 2 and another error
233
;    occurs, the TD is retired with error. When a transaction completes without
234
;    error, ErrorCount is reset to 0.
235
; 7. Upper 4 bits (bits 28-31) are ConditionCode field. This field contains
236
;    the status of the last attempted transaction, one of USB_STATUS_* values.
237
CurBufPtr       dd      ?
238
; Physical address of the next memory location that will be accessed for
239
; transfer to/from the endpoint. 0 means zero-length data packet or that all
240
; bytes have been transferred.
241
NextTD          dd      ?
242
; This field has different meanings depending on the status of the descriptor.
243
; When the descriptor is queued for processing, but not yet processed:
244
;   Physical address of the next TD for the endpoint.
245
; When the descriptor is processed by hardware, but not yet by software:
246
;   Physical address of the previous processed TD.
247
; When the descriptor is processed by the IRQ handler, but not yet completed:
248
;   Virtual pointer to the next processed TD.
249
BufEnd          dd      ?
250
; Physical address of the last byte in the buffer for this TD.
251
                dd      ?       ; padding for 16-bytes alignment
252
SoftwarePart    rd      sizeof.usb_gtd/4
253
; Common part for all controllers.
254
ends
255
 
256
if sizeof.ohci_gtd mod 16
257
.err ohci_gtd must be 16-bytes aligned
258
end if
259
 
260
; OHCI isochronous transfer descriptor.
261
; * The structure describes transfers to be performed on Isochronous endpoints.
262
; * The structure includes two parts, the hardware part and the software part.
263
; * The hardware part consists of first 32 bytes and corresponds to
264
;   the Isochronous Transfer Descriptor aka isochronous TD from OHCI
265
;   specification.
266
; * The hardware requires 32-bytes alignment of the hardware part, so
267
;   the entire descriptor must be 32-bytes aligned.
268
; * The isochronous endpoints are not supported yet, so only hardware part is
269
;   defined at the moment.
270
struct ohci_itd
271
StartingFrame   dw      ?
272
; This field contains the low order 16 bits of the frame number in which the
273
; first data packet of the Isochronous TD is to be sent.
274
Flags           dw      ?
275
; 1. Lower 5 bits (bits 0-4) are ignored and not modified by the hardware.
276
; 2. Next 3 bits (bits 5-7) are DelayInterrupt field.
277
; 3. Next 3 bits (bits 8-10) are FrameCount field. The TD describes
278
;    FrameCount+1 data packets.
279
; 4. Next bit (bit 11) is ignored and not modified by the hardware.
280
; 5. Upper 4 bits (bits 12-15) are ConditionCode field. This field contains
281
;    the completion code, one of USB_STATUS_* values, when the TD is moved to
282
;    the Done Queue.
283
BufPage0        dd      ?
284
; Lower 12 bits are ignored and not modified by the hardware.
285
; With masked 12 bits this field is the physical page containing all buffers.
286
NextTD          dd      ?
287
; Physical address of the next TD in the transfer queue.
288
BufEnd          dd      ?
289
; Physical address of the last byte in the buffer.
290
OffsetArray     rw      8
291
; Initialized by software, read by hardware: Offset for packet 0..7.
292
; Used to determine size and starting address of an isochronous data packet.
293
; Written by hardware, read by software: PacketStatusWord for packet 0..7.
294
; Contains completion code and, if applicable, size received for an isochronous
295
; data packet.
296
ends
297
 
298
; Description of OHCI-specific data and functions for
299
; controller-independent code.
300
; Implements the structure usb_hardware_func from hccommon.inc for OHCI.
301
iglobal
302
align 4
303
ohci_hardware_func:
304
        dd      'OHCI'
305
        dd      sizeof.ohci_controller
306
        dd      ohci_init
307
        dd      ohci_process_deferred
308
        dd      ohci_set_device_address
309
        dd      ohci_get_device_address
310
        dd      ohci_port_disable
311
        dd      ohci_new_port.reset
312
        dd      ohci_set_endpoint_packet_size
313
        dd      usb1_allocate_endpoint
314
        dd      usb1_free_endpoint
315
        dd      ohci_init_pipe
316
        dd      ohci_unlink_pipe
317
        dd      usb1_allocate_general_td
318
        dd      usb1_free_general_td
319
        dd      ohci_alloc_transfer
320
        dd      ohci_insert_transfer
321
        dd      ohci_new_device
322
endg
323
 
324
; =============================================================================
325
; =================================== Code ====================================
326
; =============================================================================
327
 
328
; Controller-specific initialization function.
329
; Called from usb_init_controller. Initializes the hardware and
330
; OHCI-specific parts of software structures.
331
; eax = pointer to ohci_controller to be initialized
332
; [ebp-4] = pcidevice
333
proc ohci_init
334
; inherit some variables from the parent (usb_init_controller)
335
.devfn   equ ebp - 4
336
.bus     equ ebp - 3
337
; 1. Store pointer to ohci_controller for further use.
338
        push    eax
339
        mov     edi, eax
340
; 2. Initialize hardware fields of ohci_controller.
341
; Namely, InterruptTable needs to be initialized with
342
; physical addresses of heads of first 32 Periodic lists.
343
; Note that all static heads fit in one page, so one call
344
; to get_pg_addr is sufficient.
345
if (ohci_controller.IntEDs / 0x1000) <> (ohci_controller.BulkED / 0x1000)
346
.err assertion failed
347
end if
348
if ohci_controller.IntEDs >= 0x1000
349
.err assertion failed
350
end if
351
        lea     esi, [eax+ohci_controller.IntEDs+32*sizeof.ohci_static_ep]
352
        call    get_pg_addr
353
        add     eax, ohci_controller.IntEDs
3598 clevermous 354
        movi    ecx, 32
3520 clevermous 355
        mov     edx, ecx
356
@@:
357
        stosd
358
        add     eax, sizeof.ohci_static_ep
359
        loop    @b
360
; 3. Initialize static heads ohci_controller.IntEDs, .ControlED, .BulkED.
361
; Use the loop over groups: first group consists of first 32 Periodic
362
; descriptors, next group consists of next 16 Periodic descriptors,
363
; ..., last group consists of the last Periodic descriptor.
364
; 3a. Prepare for the loop.
365
; make edi point to start of ohci_controller.IntEDs,
366
; other registers are already set.
367
; -128 fits in one byte, +128 does not fit.
368
        sub     edi, -128
369
; 3b. Loop over groups. On every iteration:
370
; edx = size of group, edi = pointer to the current group,
371
; esi = pointer to the next group, eax = physical address of the next group.
372
.init_static_eds:
373
; 3c. Get the size of the next group.
374
        shr     edx, 1
375
; 3d. Exit the loop if there is no next group.
376
        jz      .init_static_eds_done
377
; 3e. Initialize the first half of the current group.
378
; Advance edi to the second half.
379
        push    eax esi
380
        call    ohci_init_static_ep_group
381
        pop     esi eax
382
; 3f. Initialize the second half of the current group
383
; with the same values.
384
; Advance edi to the next group, esi/eax to the next of the next group.
385
        call    ohci_init_static_ep_group
386
        jmp     .init_static_eds
387
.init_static_eds_done:
388
; 3g. Initialize the head of the last Periodic list.
389
        xor     eax, eax
390
        xor     esi, esi
391
        call    ohci_init_static_endpoint
392
; 3i. Initialize the heads of Control and Bulk lists.
393
        call    ohci_init_static_endpoint
394
        call    ohci_init_static_endpoint
395
; 4. Create a virtual memory area to talk with the controller.
396
; 4a. Enable memory & bus master access.
397
        mov     ch, [.bus]
398
        mov     cl, 0
399
        mov     eax, ecx
400
        mov     bh, [.devfn]
401
        mov     bl, 4
402
        call    pci_read_reg
403
        or      al, 6
404
        xchg    eax, ecx
405
        call    pci_write_reg
406
; 4b. Read memory base address.
407
        mov     ah, [.bus]
408
        mov     al, 2
409
        mov     bl, 10h
410
        call    pci_read_reg
411
        and     al, not 0Fh
412
; 4c. Create mapping for physical memory. 256 bytes are sufficient.
413
        stdcall map_io_mem, eax, 100h, PG_SW+PG_NOCACHE
414
        test    eax, eax
415
        jz      .fail
416
        stosd   ; fill ohci_controller.MMIOBase
417
        xchg    eax, edi
418
; now edi = MMIOBase
419
; 5. Reset the controller if needed.
420
; 5a. Check operational state.
421
; 0 = reset, 1 = resume, 2 = operational, 3 = suspended
422
        mov     eax, [edi+OhciControlReg]
423
        and     al, 3 shl 6
424
        cmp     al, 2 shl 6
425
        jz      .operational
426
; 5b. State is not operational, reset is needed.
427
.reset:
428
; 5c. Save FmInterval register.
429
        pushd   [edi+OhciFmIntervalReg]
430
; 5d. Issue software reset and wait up to 10ms, checking status every 1 ms.
3598 clevermous 431
        movi    ecx, 1
432
        movi    edx, 10
3520 clevermous 433
        mov     [edi+OhciCommandStatusReg], ecx
434
@@:
435
        mov     esi, ecx
436
        call    delay_ms
437
        test    [edi+OhciCommandStatusReg], ecx
438
        jz      .resetdone
439
        dec     edx
440
        jnz     @b
441
        pop     eax
442
        dbgstr 'controller reset timeout'
443
        jmp     .fail_unmap
444
.resetdone:
445
; 5e. Restore FmInterval register.
446
        pop     eax
447
        mov     edx, eax
448
        and     edx, 3FFFh
449
        jz      .setfminterval
450
        cmp     dx, 2EDFh       ; default value?
451
        jnz     @f              ; assume that BIOS has configured the value
452
.setfminterval:
453
        mov     eax, 27792EDFh  ; default value
454
@@:
455
        mov     [edi+OhciFmIntervalReg], eax
456
; 5f. Set PeriodicStart to 90% of FmInterval.
457
        movzx   eax, ax
458
; Two following lines are equivalent to eax = floor(eax * 0.9)
459
; for any 0 <= eax < 1C71C71Dh, which of course is far from maximum 0FFFFh.
460
        mov     edx, 0E6666667h
461
        mul     edx
462
        mov     [edi+OhciPeriodicStartReg], edx
463
.operational:
464
; 6. Setup controller registers.
465
        pop     esi     ; restore pointer to ohci_controller saved in step 1
466
; 6a. Physical address of HCCA.
467
        mov     eax, esi
468
        call    get_pg_addr
469
        mov     [edi+OhciHCCAReg], eax
470
; 6b. Transition to operational state and clear all Enable bits.
471
        mov     cl, 2 shl 6
472
        mov     [edi+OhciControlReg], ecx
473
; 6c. Physical addresses of head of Control and Bulk lists.
474
if ohci_controller.BulkED >= 0x1000
475
.err assertion failed
476
end if
477
        add     eax, ohci_controller.ControlED
478
        mov     [edi+OhciControlHeadEDReg], eax
479
        add     eax, ohci_controller.BulkED - ohci_controller.ControlED
480
        mov     [edi+OhciBulkHeadEDReg], eax
481
; 6d. Zero Head registers: there are no active Control and Bulk descriptors yet.
482
        xor     eax, eax
483
;       mov     [edi+OhciPeriodCurrentEDReg], eax
484
        mov     [edi+OhciControlCurrentEDReg], eax
485
        mov     [edi+OhciBulkCurrentEDReg], eax
486
;       mov     [edi+OhciDoneHeadReg], eax
487
; 6e. Enable processing of all lists with control:bulk ratio = 1:1.
488
        mov     dword [edi+OhciControlReg], 10111100b
489
; 7. Get number of ports.
490
        add     esi, sizeof.ohci_controller
491
        mov     eax, [edi+OhciRhDescriptorAReg]
492
        and     eax, 0xF
493
        mov     [esi+usb_controller.NumPorts], eax
494
; 8. Initialize DoneListEndPtr to point to DoneList.
495
        lea     eax, [esi+ohci_controller.DoneList-sizeof.ohci_controller]
496
        mov     [esi+ohci_controller.DoneListEndPtr-sizeof.ohci_controller], eax
497
; 9. Hook interrupt.
498
        mov     ah, [.bus]
499
        mov     al, 0
500
        mov     bh, [.devfn]
501
        mov     bl, 3Ch
502
        call    pci_read_reg
503
; al = IRQ
504
        movzx   eax, al
505
        stdcall attach_int_handler, eax, ohci_irq, esi
506
; 10. Enable controller interrupt on HcDoneHead writeback and RootHubStatusChange.
507
        mov     dword [edi+OhciInterruptEnableReg], 80000042h
508
        DEBUGF 1,'K : OHCI controller at %x:%x with %d ports initialized\n',[.bus]:2,[.devfn]:2,[esi+usb_controller.NumPorts]
509
; 11. Initialize ports of the controller.
510
; 11a. Initiate power up, disable all ports, clear all "changed" bits.
511
        mov     dword [edi+OhciRhStatusReg], 10000h     ; SetGlobalPower
512
        xor     ecx, ecx
513
@@:
514
        mov     dword [edi+OhciRhPortStatusReg+ecx*4], 1F0101h  ; SetPortPower+ClearPortEnable+clear "changed" bits
515
        inc     ecx
516
        cmp     ecx, [esi+usb_controller.NumPorts]
517
        jb      @b
518
; 11b. Wait for power up.
519
; VirtualBox has AReg == 0, delay_ms doesn't like zero value; ignore zero delay
520
        push    esi
521
        mov     esi, [edi+OhciRhDescriptorAReg]
522
        shr     esi, 24
523
        add     esi, esi
524
        jz      @f
525
        call    delay_ms
526
@@:
527
        pop     esi
528
; 11c. Ports are powered up; now it is ok to process connect/disconnect events.
529
        mov     [esi+ohci_controller.PoweredUp-sizeof.ohci_controller], 1
530
                ; IRQ handler doesn't accept connect/disconnect events before this point
531
; 11d. We could miss some events while waiting for powering up;
532
; scan all ports manually and check for connected devices.
533
        xor     ecx, ecx
534
.port_loop:
535
        test    dword [edi+OhciRhPortStatusReg+ecx*4], 1
536
        jz      .next_port
537
; There is a connected device; mark the port as 'connected'
538
; and save the connected time.
539
; Note that ConnectedTime must be set before 'connected' mark,
540
; otherwise the code in ohci_process_deferred could use incorrect time.
541
        mov     eax, [timer_ticks]
542
        mov     [esi+usb_controller.ConnectedTime+ecx*4], eax
543
        lock bts [esi+usb_controller.NewConnected], ecx
544
.next_port:
545
        inc     ecx
546
        cmp     ecx, [esi+usb_controller.NumPorts]
547
        jb      .port_loop
548
; 12. Return pointer to usb_controller.
549
        xchg    eax, esi
550
        ret
551
.fail_unmap:
552
; On error after step 4, release the virtual memory area.
553
        stdcall free_kernel_space, edi
554
.fail:
555
; On error, free the ohci_controller structure and return zero.
556
; Note that the pointer was placed in the stack at step 1.
557
; Note also that there can be no errors after step 8,
558
; where that pointer is popped from the stack.
559
        pop     ecx
560
.nothing:
561
        xor     eax, eax
562
        ret
563
endp
564
 
565
; Helper procedure for step 3 of ohci_init.
566
; Initializes the static head of one list.
567
; eax = physical address of the "next" list, esi = pointer to the "next" list,
568
; edi = pointer to head to initialize.
569
; Advances edi to the next head, keeps eax/esi.
570
proc ohci_init_static_endpoint
571
        mov     byte [edi+ohci_static_ep.Flags+1], 1 shl (14 - 8)       ; sKip this endpoint
572
        mov     [edi+ohci_static_ep.NextED], eax
573
        mov     [edi+ohci_static_ep.NextList], esi
574
        add     edi, ohci_static_ep.SoftwarePart
575
        call    usb_init_static_endpoint
576
        add     edi, sizeof.ohci_static_ep - ohci_static_ep.SoftwarePart
577
        ret
578
endp
579
 
580
; Helper procedure for step 3 of ohci_init.
581
; Initializes one half of group of static heads.
582
; edx = size of the next group = half of size of the group,
583
; edi = pointer to the group, eax = physical address of the next group,
584
; esi = pointer to the next group.
585
; Advances eax, esi, edi to next group, keeps edx.
586
proc ohci_init_static_ep_group
587
        push    edx
588
@@:
589
        call    ohci_init_static_endpoint
590
        add     eax, sizeof.ohci_static_ep
591
        add     esi, sizeof.ohci_static_ep
592
        dec     edx
593
        jnz     @b
594
        pop     edx
595
        ret
596
endp
597
 
598
; Controller-specific pre-initialization function: take ownership from BIOS.
599
; Some BIOSes, although not all of them, provide legacy emulation
600
; for USB keyboard and/or mice as PS/2-devices. In this case,
601
; we must notify the BIOS that we don't need that emulation and know how to
602
; deal with USB devices.
603
proc ohci_kickoff_bios
604
; 1. Get the physical address of MMIO registers.
605
        mov     ah, [esi+PCIDEV.bus]
606
        mov     bh, [esi+PCIDEV.devfn]
607
        mov     al, 2
608
        mov     bl, 10h
609
        call    pci_read_reg
610
        and     al, not 0Fh
611
; 2. Create mapping for physical memory. 256 bytes are sufficient.
612
        stdcall map_io_mem, eax, 100h, PG_SW+PG_NOCACHE
613
        test    eax, eax
614
        jz      .nothing
615
; 3. Some BIOSes enable controller interrupts as a result of giving
616
; controller away. At this point the system knows nothing about how to serve
617
; OHCI interrupts, so such an interrupt will send the system into an infinite
618
; loop handling the same IRQ again and again. Thus, we need to block OHCI
619
; interrupts. We can't do this at the controller level until step 5,
620
; because the controller is currently owned by BIOS, so we block all hardware
621
; interrupts on this processor until step 5.
622
        pushf
623
        cli
624
; 4. Take the ownership over the controller.
625
; 4a. Check whether BIOS handles this controller at all.
626
        mov     edx, 100h
627
        test    dword [eax+OhciControlReg], edx
628
        jz      .has_ownership
629
; 4b. Send "take ownership" command to the BIOS.
630
; (This should generate SMI, BIOS should release its ownership in SMI handler.)
631
        mov     dword [eax+OhciCommandStatusReg], 8
632
; 4c. Wait for result no more than 50 ms, checking for status every 1 ms.
3598 clevermous 633
        movi    ecx, 50
3520 clevermous 634
@@:
635
        test    dword [eax+OhciControlReg], edx
636
        jz      .has_ownership
637
        push    esi
3598 clevermous 638
        movi    esi, 1
3520 clevermous 639
        call    delay_ms
640
        pop     esi
641
        loop    @b
642
        dbgstr 'warning: taking OHCI ownership from BIOS timeout'
643
.has_ownership:
644
; 5. Disable all controller interrupts until the system will be ready to
645
; process them.
646
        mov     dword [eax+OhciInterruptDisableReg], 0C000007Fh
647
; 6. Now we can unblock interrupts in the processor.
648
        popf
649
; 7. Release memory mapping created in step 2 and return.
650
        stdcall free_kernel_space, eax
651
.nothing:
652
        ret
653
endp
654
 
655
; IRQ handler for OHCI controllers.
656
ohci_irq.noint:
657
; Not our interrupt: restore registers and return zero.
658
        xor     eax, eax
659
        pop     edi esi ebx
660
        ret
661
 
662
proc ohci_irq
663
        push    ebx esi edi     ; save used registers to be cdecl
664
virtual at esp
665
                rd      3       ; saved registers
666
                dd      ?       ; return address
667
.controller     dd      ?
668
end virtual
669
; 1. ebx will hold whether some deferred processing is needed,
670
; that cannot be done from the interrupt handler. Initialize to zero.
671
        xor     ebx, ebx
672
; 2. Get the mask of events which should be processed.
673
        mov     esi, [.controller]
674
        mov     edi, [esi+ohci_controller.MMIOBase-sizeof.ohci_controller]
675
        mov     eax, [edi+OhciInterruptStatusReg]
676
; 3. Check whether that interrupt has been generated by our controller.
677
; (One IRQ can be shared by several devices.)
678
        and     eax, [edi+OhciInterruptEnableReg]
679
        jz      .noint
680
; 4. Get the physical pointer to the last processed descriptor.
681
; All processed descriptors form single-linked list from last to first
682
; with the help of NextTD field. The list is restarted every time when
683
; the controller writes to DoneHead, so grab the pointer now (before the next
684
; step) or it could be lost (the controller could write new value to DoneHead
685
; any time after WorkDone bit is cleared in OhciInterruptStatusReg).
686
        mov     ecx, [esi+ohci_controller.DoneHead-sizeof.ohci_controller]
687
        and     ecx, not 1
688
; 5. Clear the events we know of.
689
; Note that this should be done before processing of events:
690
; new events could arise while we are processing those, this way we won't lose
691
; them (the controller would generate another interrupt
692
; after completion of this one).
693
        mov     [edi+OhciInterruptStatusReg], eax
694
; 6. Save the mask of events for further reference.
695
        push    eax
696
; 7. Handle 'transfer is done' events.
697
; 7a. Test whether there are such events.
698
        test    al, 2
699
        jz      .skip_donehead
700
; There are some 'transfer is done' events, processed descriptors are linked
701
; through physical addresses in the reverse order.
702
; We can't do much in an interrupt handler, since callbacks could require
703
; waiting for locks and that can't be done in an interrupt handler.
704
; However, we can't also just defer all work to the USB thread, since
705
; it is possible that previous lists are not yet processed and it is hard
706
; to store unlimited number of list heads. Thus, we reverse the current list,
707
; append it to end of the previous list (if there is one) and defer other
708
; processing to the USB thread; this way there always is no more than one list
709
; (possibly joined from several controller-reported lists).
710
; The list traversal requires converting physical addresses to virtual pointers,
711
; so we may as well store pointers instead of physical addresses.
712
; 7b. Prepare for the reversing loop.
713
        push    ebx
714
        xor     ebx, ebx
715
        test    ecx, ecx
716
        jz      .tddone
717
        call    usb_td_to_virt
718
        test    eax, eax
719
        jz      .tddone
720
        lea     edx, [eax+ohci_gtd.NextTD]
721
; 7c. Reverse the list, converting physical to virtual. On every iteration:
722
; ecx = physical address of the current item
723
; eax = virtual pointer to the current item
724
; edx = virtual pointer to the last item.NextTD (first in the reverse list)
725
; ebx = virtual pointer to the next item (previous in the reverse list)
726
.tdloop:
727
        mov     ecx, [eax+ohci_gtd.NextTD]
728
        mov     [eax+ohci_gtd.NextTD], ebx
729
        lea     ebx, [eax+ohci_gtd.SoftwarePart]
730
        test    ecx, ecx
731
        jz      .tddone
732
        call    usb_td_to_virt
733
        test    eax, eax
734
        jnz     .tdloop
735
.tddone:
736
        mov     ecx, ebx
737
        pop     ebx
738
; 7d. The list is reversed,
739
; ecx = pointer to the first item, edx = pointer to the last item.NextTD.
740
; If the list is empty (unusual case), step 7 is done.
741
        test    ecx, ecx
742
        jz      .skip_donehead
743
; 7e. Otherwise, append this list to the end of previous one.
744
; Note that in theory the interrupt handler and the USB thread
745
; could execute in parallel.
746
.append_restart:
747
; Atomically get DoneListEndPtr in eax and set it to edx.
748
        mov     eax, [esi+ohci_controller.DoneListEndPtr-sizeof.ohci_controller]
749
        lock cmpxchg [esi+ohci_controller.DoneListEndPtr-sizeof.ohci_controller], edx
750
        jnz     .append_restart
751
; Store pointer to the new list.
752
; Note: we cannot perform any operations with [DoneListEndPtr]
753
; until we switch DoneListEndPtr to a new descriptor:
754
; it is possible that after first line of .append_restart loop
755
; ohci_process_deferred obtains the control, finishes processing
756
; of the old list, sets DoneListEndPtr to address of DoneList,
757
; frees all old descriptors, so eax would point to invalid location.
758
; This way, .append_restart loop would detect that DoneListEndPtr
759
; has changed, so eax needs to be re-read.
760
        mov     [eax], ecx
761
; 7f. Notify the USB thread that there is new work.
762
        inc     ebx
763
.skip_donehead:
764
; 8. Handle start-of-frame events.
765
; 8a. Test whether there are such events.
766
        test    byte [esp], 4
767
        jz      .skip_sof
768
; We enable SOF interrupt only when some pipes are waiting after changes.
769
        spin_lock_irqsave [esi+usb_controller.WaitSpinlock]
770
; 8b. Make sure that there was at least one frame update
771
; since the request. If not, wait for the next SOF.
772
        movzx   eax, [esi+ohci_controller.FrameNumber-sizeof.ohci_controller]
773
        cmp     eax, [esi+usb_controller.StartWaitFrame]
774
        jz      .sof_unlock
775
; 8c. Copy WaitPipeRequest* to ReadyPipeHead*.
776
        mov     eax, [esi+usb_controller.WaitPipeRequestAsync]
777
        mov     [esi+usb_controller.ReadyPipeHeadAsync], eax
778
        mov     eax, [esi+usb_controller.WaitPipeRequestPeriodic]
779
        mov     [esi+usb_controller.ReadyPipeHeadPeriodic], eax
780
; 8d. It is possible that pipe change is due to removal and
781
; Control/BulkCurrentED registers still point to one of pipes to be removed.
782
; The code responsible for disconnect events has temporarily stopped
783
; Control/Bulk processing, so it is safe to clear Control/BulkCurrentED.
784
; After that, restart processing.
785
        xor     edx, edx
786
        mov     [edi+OhciControlCurrentEDReg], edx
787
        mov     [edi+OhciBulkCurrentEDReg], edx
788
        mov     dword [edi+OhciCommandStatusReg], 6
789
        or      dword [edi+OhciControlReg], 30h
790
; 8e. Disable further interrupts on SOF.
791
; Note: OhciInterruptEnableReg/OhciInterruptDisableReg have unusual semantics.
792
        mov     dword [edi+OhciInterruptDisableReg], 4
793
; Notify the USB thread that there is new work (with pipes from ReadyPipeHead*).
794
        inc     ebx
795
.sof_unlock:
796
        spin_unlock_irqrestore [esi+usb_controller.RemoveSpinlock]
797
.skip_sof:
798
; Handle roothub events.
799
; 9. Test whether there are such events.
800
        test    byte [esp], 40h
801
        jz      .skip_roothub
802
; 10. Check the status of the roothub itself.
803
; 10a. Global overcurrent?
804
        test    dword [edi+OhciRhStatusReg], 2
805
        jz      @f
806
; Note: this needs work.
807
        dbgstr 'global overcurrent'
808
@@:
809
; 10b. Clear roothub events.
810
        mov     dword [edi+OhciRhStatusReg], 80020000h
811
; 11. Check the status of individual ports.
812
; Look for connect/disconnect and reset events.
813
; 11a. Prepare for the loop: start from port 0.
814
        xor     ecx, ecx
815
.portloop:
816
; 11b. Get the port status and changes of it.
817
; Accumulate change information.
818
; Look to "11.12.3 Port Change Information Processing" of the USB2 spec.
819
        xor     eax, eax
820
.accloop:
821
        mov     edx, [edi+OhciRhPortStatusReg+ecx*4]
822
        xor     ax, ax
823
        or      eax, edx
824
        test    edx, 1F0000h
825
        jz      .accdone
826
        mov     dword [edi+OhciRhPortStatusReg+ecx*4], 1F0000h
827
        jmp     .accloop
828
.accdone:
829
; debugging output, not needed for work
830
;       test    eax, 1F0000h
831
;       jz      @f
832
;       DEBUGF 1,'K : ohci irq [%d] status of port %d is %x\n',[timer_ticks],ecx,eax
833
;@@:
834
; 11c. Ignore any events until all ports are powered up.
835
; They will be processed by ohci_init.
836
        cmp     [esi+ohci_controller.PoweredUp-sizeof.ohci_controller], 0
837
        jz      .nextport
838
; Handle changing of connection status.
839
        test    eax, 10000h
840
        jz      .nocsc
841
; There was a connect or disconnect event at this port.
842
; 11d. Disconnect the old device on this port, if any.
843
; if the port was resetting, indicate fail and signal
844
        cmp     cl, [esi+usb_controller.ResettingPort]
845
        jnz     @f
846
        mov     [esi+usb_controller.ResettingStatus], -1
847
        inc     ebx
848
@@:
849
        lock bts [esi+usb_controller.NewDisconnected], ecx
850
; notify the USB thread that new work is waiting
851
        inc     ebx
852
; 11e. Change connected status. For the connection event, also
853
; store the connection time; any further processing is permitted only
854
; after USB_CONNECT_DELAY ticks.
855
        test    al, 1
856
        jz      .disconnect
857
; Note: ConnectedTime must be stored before setting the 'connected' bit,
858
; otherwise ohci_process_deferred could use an old time.
859
        mov     eax, [timer_ticks]
860
        mov     [esi+usb_controller.ConnectedTime+ecx*4], eax
861
        lock bts [esi+usb_controller.NewConnected], ecx
862
        jmp     .nextport
863
.disconnect:
864
        lock btr [esi+usb_controller.NewConnected], ecx
865
        jmp     .nextport
866
.nocsc:
867
; 11f. Process 'reset done' events.
868
        test    eax, 100000h
869
        jz      .nextport
870
        test    al, 10h
871
        jnz     .nextport
872
        mov     edx, [timer_ticks]
873
        mov     [esi+usb_controller.ResetTime], edx
874
        mov     [esi+usb_controller.ResettingStatus], 2
875
        inc     ebx
876
.nextport:
877
; 11g. Continue the loop for the next port.
878
        inc     ecx
879
        cmp     ecx, [esi+usb_controller.NumPorts]
880
        jb      .portloop
881
.skip_roothub:
882
; 12. Restore the stack after step 6.
883
        pop     eax
884
; 13. Notify the USB thread if some deferred processing is required.
885
        call    usb_wakeup_if_needed
886
; 14. Interrupt processed; return something non-zero.
887
        mov     al, 1
888
        pop     edi esi ebx     ; restore used registers to be stdcall
889
        ret
890
endp
891
 
892
; This procedure is called from usb_set_address_callback
893
; and stores USB device address in the ohci_pipe structure.
894
; in: esi -> usb_controller, ebx -> usb_pipe, cl = address
895
proc ohci_set_device_address
896
        mov     byte [ebx+ohci_pipe.Flags-ohci_pipe.SoftwarePart], cl
897
; Wait until the hardware will forget the old value.
898
        call    usb_subscribe_control
899
        ret
900
endp
901
 
902
; This procedure returns USB device address from the usb_pipe structure.
903
; in: esi -> usb_controller, ebx -> usb_pipe
904
; out: eax = endpoint address
905
proc ohci_get_device_address
906
        mov     eax, [ebx+ohci_pipe.Flags-ohci_pipe.SoftwarePart]
907
        and     eax, 7Fh
908
        ret
909
endp
910
 
911
; This procedure is called from usb_set_address_callback
912
; if the device does not accept SET_ADDRESS command and needs
913
; to be disabled at the port level.
914
; in: esi -> usb_controller, ecx = port
915
proc ohci_port_disable
916
        mov     edx, [esi+ohci_controller.MMIOBase-sizeof.ohci_controller]
917
        mov     dword [edx+OhciRhPortStatusReg+ecx*4], 1
918
        ret
919
endp
920
 
921
; This procedure is called from usb_get_descr8_callback when
922
; the packet size for zero endpoint becomes known and
923
; stores the packet size in ohci_pipe structure.
924
; in: esi -> usb_controller, ebx -> usb_pipe, ecx = packet size
925
proc ohci_set_endpoint_packet_size
926
        mov     byte [ebx+ohci_pipe.Flags+2-ohci_pipe.SoftwarePart], cl
927
; Wait until the hardware will forget the old value.
928
        call    usb_subscribe_control
929
        ret
930
endp
931
 
932
; This procedure is called from API usb_open_pipe and processes
933
; the controller-specific part of this API. See docs.
934
; in: edi -> usb_pipe for target, ecx -> usb_pipe for config pipe,
935
; esi -> usb_controller, eax -> usb_gtd for the first TD,
936
; [ebp+12] = endpoint, [ebp+16] = maxpacket, [ebp+20] = type
937
proc ohci_init_pipe
938
virtual at ebp+8
939
.config_pipe    dd      ?
940
.endpoint       dd      ?
941
.maxpacket      dd      ?
942
.type           dd      ?
943
.interval       dd      ?
944
end virtual
945
; 1. Initialize the queue of transfer descriptors: empty.
946
        sub     eax, ohci_gtd.SoftwarePart
947
        call    get_phys_addr
948
        mov     [edi+ohci_pipe.TailP-ohci_pipe.SoftwarePart], eax
949
        mov     [edi+ohci_pipe.HeadP-ohci_pipe.SoftwarePart], eax
950
; 2. Generate ohci_pipe.Flags, see the description in ohci_pipe.
951
        mov     eax, [ecx+ohci_pipe.Flags-ohci_pipe.SoftwarePart]
952
        and     eax, 0x207F     ; keep Speed bit and FunctionAddress
953
        mov     edx, [.endpoint]
954
        and     edx, 15
955
        shl     edx, 7
956
        or      eax, edx
957
        mov     [edi+ohci_pipe.Flags-ohci_pipe.SoftwarePart], eax
958
        mov     eax, [.maxpacket]
959
        mov     word [edi+ohci_pipe.Flags+2-ohci_pipe.SoftwarePart], ax
960
        cmp     [.type], CONTROL_PIPE
961
        jz      @f
962
        test    byte [.endpoint], 80h
963
        setnz   al
964
        inc     eax
965
        shl     al, 3
966
        or      byte [edi+ohci_pipe.Flags+1-ohci_pipe.SoftwarePart], al
967
@@:
968
; 3. Insert the new pipe to the corresponding list of endpoints.
969
; 3a. Use Control list for control pipes, Bulk list for bulk pipes.
970
        lea     edx, [esi+ohci_controller.ControlED.SoftwarePart-sizeof.ohci_controller]
971
        cmp     [.type], BULK_PIPE
972
        jb      .insert ; control pipe
973
        lea     edx, [esi+ohci_controller.BulkED.SoftwarePart-sizeof.ohci_controller]
974
        jz      .insert ; bulk pipe
975
.interrupt_pipe:
976
; 3b. For interrupt pipes, let the scheduler select the appropriate list
977
; based on the current bandwidth distribution and the requested bandwidth.
978
; This could fail if the requested bandwidth is not available;
979
; if so, return an error.
980
        lea     edx, [esi + ohci_controller.IntEDs - sizeof.ohci_controller]
981
        lea     eax, [esi + ohci_controller.IntEDs + 32*sizeof.ohci_static_ep - sizeof.ohci_controller]
3598 clevermous 982
        movi    ecx, 64
3520 clevermous 983
        call    usb1_select_interrupt_list
984
        test    edx, edx
985
        jz      .return0
986
; 3c. Insert endpoint at edi to the head of list in edx.
987
; Inserting to tail would work as well,
988
; but let's be consistent with other controllers.
989
.insert:
990
        mov     ecx, [edx+usb_pipe.NextVirt]
991
        mov     [edi+usb_pipe.NextVirt], ecx
992
        mov     [edi+usb_pipe.PrevVirt], edx
993
        mov     [ecx+usb_pipe.PrevVirt], edi
994
        mov     [edx+usb_pipe.NextVirt], edi
995
        mov     ecx, [edx+ohci_pipe.NextED-ohci_pipe.SoftwarePart]
996
        mov     [edi+ohci_pipe.NextED-ohci_pipe.SoftwarePart], ecx
997
        lea     eax, [edi-ohci_pipe.SoftwarePart]
998
        call    get_phys_addr
999
        mov     [edx+ohci_pipe.NextED-ohci_pipe.SoftwarePart], eax
1000
; 4. Return something non-zero.
1001
        ret
1002
.return0:
1003
        xor     eax, eax
1004
        ret
1005
endp
1006
 
1007
; This function is called from ohci_process_deferred when
1008
; a new device was connected at least USB_CONNECT_DELAY ticks
1009
; and therefore is ready to be configured.
1010
; ecx = port, esi -> usb_controller
1011
proc ohci_new_port
1012
; test whether we are configuring another port
1013
; if so, postpone configuring and return
1014
        bts     [esi+usb_controller.PendingPorts], ecx
1015
        cmp     [esi+usb_controller.ResettingPort], -1
1016
        jnz     .nothing
1017
        btr     [esi+usb_controller.PendingPorts], ecx
1018
; fall through to ohci_new_port.reset
1019
 
1020
; This function is called from usb_test_pending_port.
1021
; It starts reset signalling for the port. Note that in USB first stages
1022
; of configuration can not be done for several ports in parallel.
1023
.reset:
1024
; reset port
1025
        and     [esi+usb_controller.ResettingHub], 0
1026
        mov     [esi+usb_controller.ResettingPort], cl
1027
; Note: setting status must be the last action:
1028
; it is possible that the device has been disconnected
1029
; after timeout of USB_CONNECT_DELAY but before call to ohci_new_port.
1030
; In this case, ohci_irq would not set reset status to 'failed',
1031
; because ohci_irq would not know that this port is to be reset.
1032
; However, the hardware would generate another interrupt
1033
; in a response to reset a disconnected port, and this time
1034
; ohci_irq knows that it needs to generate 'reset failed' event
1035
; (because ResettingPort is now filled).
1036
        push    edi
1037
        mov     edi, [esi+ohci_controller.MMIOBase-sizeof.ohci_controller]
1038
        mov     dword [edi+OhciRhPortStatusReg+ecx*4], 10h
1039
        pop     edi
1040
.nothing:
1041
        ret
1042
endp
1043
 
1044
; This procedure is called from the several places in main USB code
1045
; and allocates required packets for the given transfer.
1046
; ebx = pipe, other parameters are passed through the stack:
1047
; buffer,size = data to transfer
1048
; flags = same as in usb_open_pipe: bit 0 = allow short transfer, other bits reserved
1049
; td = pointer to the current end-of-queue descriptor
1050
; direction =
1051
;   0000b for normal transfers,
1052
;   1000b for control SETUP transfer,
1053
;   1101b for control OUT transfer,
1054
;   1110b for control IN transfer
1055
; returns eax = pointer to the new end-of-queue descriptor
1056
; (not included in the queue itself) or 0 on error
1057
proc ohci_alloc_transfer stdcall uses edi, \
1058
        buffer:dword, size:dword, flags:dword, td:dword, direction:dword
1059
locals
1060
origTD          dd      ?
1061
packetSize      dd      ?       ; must be the last variable, see usb_init_transfer
1062
endl
1063
; 1. Save original value of td:
1064
; it will be useful for rollback if something would fail.
1065
        mov     eax, [td]
1066
        mov     [origTD], eax
1067
; One transfer descriptor can describe up to two pages.
1068
; In the worst case (when the buffer is something*1000h+0FFFh)
1069
; this corresponds to 1001h bytes. If the requested size is
1070
; greater, we should split the transfer into several descriptors.
1071
; Boundaries to split must be multiples of endpoint transfer size
1072
; to avoid short packets except in the end of the transfer,
1073
; 1000h is always a good value.
1074
; 2. While the remaining data cannot fit in one packet,
1075
; allocate page-sized descriptors.
1076
        mov     edi, 1000h
1077
        mov     [packetSize], edi
1078
.fullpackets:
1079
        cmp     [size], edi
1080
        jbe     .lastpacket
1081
        call    ohci_alloc_packet
1082
        test    eax, eax
1083
        jz      .fail
1084
        mov     [td], eax
1085
        add     [buffer], edi
1086
        sub     [size], edi
1087
        jmp     .fullpackets
1088
; 3. The remaining data can fit in one descriptor;
1089
; allocate the last descriptor with size = size of remaining data.
1090
.lastpacket:
1091
        mov     eax, [size]
1092
        mov     [packetSize], eax
1093
        call    ohci_alloc_packet
1094
        test    eax, eax
1095
        jz      .fail
1096
; 4. Enable an immediate interrupt on completion of the last packet.
1097
        and     byte [ecx+ohci_gtd.Flags+2-ohci_gtd.SoftwarePart], not (7 shl (21-16))
1098
; 5. If a short transfer is ok for a caller, set the corresponding bit in
1099
; the last descriptor, but not in others.
1100
; Note: even if the caller says that short transfers are ok,
1101
; all packets except the last one are marked as 'must be complete':
1102
; if one of them will be short, the software intervention is needed
1103
; to skip remaining packets; ohci_process_finalized_td will handle this
1104
; transparently to the caller.
1105
        test    [flags], 1
1106
        jz      @f
1107
        or      byte [ecx+ohci_gtd.Flags+2-ohci_gtd.SoftwarePart], 1 shl (18-16)
1108
@@:
1109
        ret
1110
.fail:
1111
        mov     edi, ohci_hardware_func
1112
        mov     eax, [td]
1113
        stdcall usb_undo_tds, [origTD]
1114
        xor     eax, eax
1115
        ret
1116
endp
1117
 
1118
; Helper procedure for ohci_alloc_transfer.
1119
; Allocates and initializes one transfer descriptor.
1120
; ebx = pipe, other parameters are passed through the stack;
1121
; fills the current last descriptor and
1122
; returns eax = next descriptor (not filled).
1123
proc ohci_alloc_packet
1124
; inherit some variables from the parent ohci_alloc_transfer
1125
virtual at ebp-8
1126
.origTD         dd      ?
1127
.packetSize     dd      ?
1128
                rd      2
1129
.buffer         dd      ?
1130
.transferSize   dd      ?
1131
.Flags          dd      ?
1132
.td             dd      ?
1133
.direction      dd      ?
1134
end virtual
1135
; 1. Allocate the next TD.
1136
        call    usb1_allocate_general_td
1137
        test    eax, eax
1138
        jz      .nothing
1139
; 2. Initialize controller-independent parts of both TDs.
1140
        push    eax
1141
        call    usb_init_transfer
1142
        pop     eax
1143
; 3. Save the returned value (next descriptor).
1144
        push    eax
1145
; 4. Store the physical address of the next descriptor.
1146
        sub     eax, ohci_gtd.SoftwarePart
1147
        call    get_phys_addr
1148
        mov     [ecx+ohci_gtd.NextTD-ohci_gtd.SoftwarePart], eax
1149
; 5. For zero-length transfers, store zero in both fields for buffer addresses.
1150
; Otherwise, fill them with real values.
1151
        xor     eax, eax
1152
        mov     [ecx+ohci_gtd.CurBufPtr-ohci_gtd.SoftwarePart], eax
1153
        mov     [ecx+ohci_gtd.BufEnd-ohci_gtd.SoftwarePart], eax
1154
        cmp     [.packetSize], eax
1155
        jz      @f
1156
        mov     eax, [.buffer]
1157
        call    get_phys_addr
1158
        mov     [ecx+ohci_gtd.CurBufPtr-ohci_gtd.SoftwarePart], eax
1159
        mov     eax, [.buffer]
1160
        add     eax, [.packetSize]
1161
        dec     eax
1162
        call    get_phys_addr
1163
        mov     [ecx+ohci_gtd.BufEnd-ohci_gtd.SoftwarePart], eax
1164
@@:
1165
; 6. Generate Flags field:
1166
; - set bufferRounding (bit 18) to zero = disallow short transfers;
1167
;   for the last transfer in a row, ohci_alloc_transfer would set the real value;
1168
; - set Direction (bits 19-20) to lower 2 bits of [.direction];
1169
; - set DelayInterrupt (bits 21-23) to 7 = do not generate interrupt;
1170
;   for the last transfer in a row, ohci_alloc_transfer would set the real value;
1171
; - set DataToggle (bits 24-25) to next 2 bits of [.direction];
1172
; - set ConditionCode (bits 28-31) to 1111b as a indicator that there was no
1173
;   attempts to perform this transfer yet;
1174
; - zero all other bits.
1175
        mov     eax, [.direction]
1176
        mov     edx, eax
1177
        and     eax, 3
1178
        shl     eax, 19
1179
        and     edx, (3 shl 2)
1180
        shl     edx, 24 - 2
1181
        lea     eax, [eax + edx + (7 shl 21) + (15 shl 28)]
1182
        mov     [ecx+ohci_gtd.Flags-ohci_gtd.SoftwarePart], eax
1183
; 7. Restore the returned value saved in step 3.
1184
        pop     eax
1185
.nothing:
1186
        ret
1187
endp
1188
 
1189
; This procedure is called from the several places in main USB code
1190
; and activates the transfer which was previously allocated by
1191
; ohci_alloc_transfer.
1192
; ecx -> last descriptor for the transfer, ebx -> usb_pipe
1193
proc ohci_insert_transfer
1194
; 1. Advance the queue of transfer descriptors.
1195
        mov     eax, [ecx+ohci_gtd.NextTD-ohci_gtd.SoftwarePart]
1196
        mov     [ebx+ohci_pipe.TailP-ohci_pipe.SoftwarePart], eax
1197
; 2. For control and bulk pipes, notify the controller that
1198
; there is new work in control/bulk queue respectively.
1199
ohci_notify_new_work:
1200
        mov     edx, [ebx+usb_pipe.Controller]
1201
        mov     edx, [edx+ohci_controller.MMIOBase-sizeof.ohci_controller]
1202
        cmp     [ebx+usb_pipe.Type], CONTROL_PIPE
1203
        jz      .control
1204
        cmp     [ebx+usb_pipe.Type], BULK_PIPE
1205
        jnz     .nothing
1206
.bulk:
1207
        mov     dword [edx+OhciCommandStatusReg], 4
1208
        jmp     .nothing
1209
.control:
1210
        mov     dword [edx+OhciCommandStatusReg], 2
1211
.nothing:
1212
        ret
1213
endp
1214
 
1215
; This function is called from ohci_process_deferred when
1216
; a new device has been reset and needs to be configured.
1217
proc ohci_port_after_reset
1218
; 1. Get the status.
1219
; If reset has been failed (device disconnected during reset),
1220
; continue to next device (if there is one).
1221
        xor     eax, eax
1222
        xchg    al, [esi+usb_controller.ResettingStatus]
1223
        test    al, al
1224
        js      usb_test_pending_port
1225
; If the controller has disabled the port (e.g. overcurrent),
1226
; continue to next device (if there is one).
1227
        movzx   ecx, [esi+usb_controller.ResettingPort]
1228
        mov     eax, [edi+OhciRhPortStatusReg+ecx*4]
1229
        test    al, 2
1230
        jnz     @f
1231
        DEBUGF 1,'K : USB port disabled after reset, status=%x\n',eax
1232
        jmp     usb_test_pending_port
1233
@@:
1234
        push    ecx
1235
; 2. Get LowSpeed bit to bit 0 of eax and call the worker procedure
1236
; to notify the protocol layer about new OHCI device.
1237
        mov     eax, [edi+OhciRhPortStatusReg+ecx*4]
1238
        DEBUGF 1,'K : port_after_reset [%d] status of port %d is %x\n',[timer_ticks],ecx,eax
1239
        shr     eax, 9
1240
        call    ohci_new_device
1241
        pop     ecx
1242
; 3. If something at the protocol layer has failed
1243
; (no memory, no bus address), disable the port and stop the initialization.
1244
        test    eax, eax
1245
        jnz     .nothing
1246
.disable_exit:
1247
        mov     dword [edi+OhciRhPortStatusReg+ecx*4], 1
1248
        jmp     usb_test_pending_port
1249
.nothing:
1250
        ret
1251
endp
1252
 
1253
; This procedure is called from uhci_port_init and from hub support code
1254
; when a new device is connected and has been reset.
1255
; It calls usb_new_device at the protocol layer with correct parameters.
1256
; in: esi -> usb_controller, eax = speed;
1257
; OHCI is USB1 device, so only low bit of eax (LowSpeed) is used.
1258
proc ohci_new_device
1259
; 1. Clear all bits of speed except bit 0.
1260
        and     eax, 1
1261
; 2. Store the speed for the protocol layer.
1262
        mov     [esi+usb_controller.ResettingSpeed], al
1263
; 3. Create pseudo-pipe in the stack.
1264
; See ohci_init_pipe: only .Controller and .Flags fields are used.
1265
        shl     eax, 13
1266
        push    esi     ; .Controller
1267
        mov     ecx, esp
1268
        sub     esp, 12 ; ignored fields
1269
        push    eax     ; .Flags
1270
; 4. Notify the protocol layer.
1271
        call    usb_new_device
1272
; 5. Cleanup the stack after step 3 and return.
1273
        add     esp, 20
1274
        ret
1275
endp
1276
 
1277
; This procedure is called in the USB thread from usb_thread_proc,
1278
; processes regular actions and those actions which can't be safely done
1279
; from interrupt handler.
1280
; Returns maximal time delta before the next call.
1281
proc ohci_process_deferred
1282
        push    ebx edi         ; save used registers to be stdcall
1283
; 1. Initialize the return value.
1284
        push    -1
1285
; 2. Process disconnect events.
1286
        call    usb_disconnect_stage2
1287
; 3. Check for connected devices.
1288
; If there is a connected device which was connected less than
1289
; USB_CONNECT_DELAY ticks ago, plan to wake up when the delay will be over.
1290
; Otherwise, call ohci_new_port.
1291
        mov     edi, [esi+ohci_controller.MMIOBase-sizeof.ohci_controller]
1292
        xor     ecx, ecx
1293
        cmp     [esi+usb_controller.NewConnected], ecx
1294
        jz      .skip_newconnected
1295
.portloop:
1296
        bt      [esi+usb_controller.NewConnected], ecx
1297
        jnc     .noconnect
1298
        mov     eax, [timer_ticks]
1299
        sub     eax, [esi+usb_controller.ConnectedTime+ecx*4]
1300
        sub     eax, USB_CONNECT_DELAY
1301
        jge     .connected
1302
        neg     eax
1303
        cmp     [esp], eax
1304
        jb      .nextport
1305
        mov     [esp], eax
1306
        jmp     .nextport
1307
.connected:
1308
        lock btr [esi+usb_controller.NewConnected], ecx
1309
        jnc     .nextport
1310
        call    ohci_new_port
1311
.noconnect:
1312
.nextport:
1313
        inc     ecx
1314
        cmp     ecx, [esi+usb_controller.NumPorts]
1315
        jb      .portloop
1316
.skip_newconnected:
1317
; 4. Check for end of reset signalling. If so, call ohci_port_after_reset.
1318
        cmp     [esi+usb_controller.ResettingStatus], 2
1319
        jnz     .no_reset_recovery
1320
        mov     eax, [timer_ticks]
1321
        sub     eax, [esi+usb_controller.ResetTime]
1322
        sub     eax, USB_RESET_RECOVERY_TIME
1323
        jge     .reset_done
1324
        neg     eax
1325
        cmp     [esp], eax
1326
        jb      .skip_roothub
1327
        mov     [esp], eax
1328
        jmp     .skip_roothub
1329
.no_reset_recovery:
1330
        cmp     [esi+usb_controller.ResettingStatus], 0
1331
        jz      .skip_roothub
1332
.reset_done:
1333
        call    ohci_port_after_reset
1334
.skip_roothub:
1335
; 5. Finalize transfers processed by hardware.
1336
; It is better to perform this step after processing disconnect events,
1337
; although not strictly obligatory. This way, an active transfer aborted
1338
; due to disconnect would be handled with more specific USB_STATUS_CLOSED,
1339
; not USB_STATUS_NORESPONSE.
1340
; Loop over all items in DoneList, call ohci_process_finalized_td for each.
1341
        xor     ebx, ebx
1342
        xchg    ebx, [esi+ohci_controller.DoneList-sizeof.ohci_controller]
1343
.tdloop:
1344
        test    ebx, ebx
1345
        jz      .tddone
1346
        call    ohci_process_finalized_td
1347
        jmp     .tdloop
1348
.tddone:
1349
; 6. Process wait-done notifications, test for new wait requests.
1350
; Note: that must be done after steps 2 and 5 which could create new requests.
1351
; 6a. Call the worker function from main USB code.
1352
        call    usb_process_wait_lists
1353
; 6b. If no new requests, skip the rest of this step.
1354
        test    eax, eax
1355
        jz      @f
1356
; 6c. OHCI is not allowed to cache anything; we don't know what is
1357
; processed right now, but we can be sure that the controller will not
1358
; use any removed structure starting from the next frame.
1359
; Schedule SOF event.
1360
        spin_lock_irq [esi+usb_controller.RemoveSpinlock]
1361
        mov     eax, [esi+usb_controller.WaitPipeListAsync]
1362
        mov     [esi+usb_controller.WaitPipeRequestAsync], eax
1363
        mov     eax, [esi+usb_controller.WaitPipeListPeriodic]
1364
        mov     [esi+usb_controller.WaitPipeRequestPeriodic], eax
1365
; temporarily stop bulk and interrupt processing;
1366
; this is required for handler of SOF event
1367
        and     dword [edi+OhciControlReg], not 30h
1368
; remember the frame number when processing has been stopped
1369
; (needs to be done after stopping)
1370
        movzx   eax, [esi+ohci_controller.FrameNumber-sizeof.ohci_controller]
1371
        mov     [esi+usb_controller.StartWaitFrame], eax
1372
; make sure that the next SOF will happen after the request
1373
        mov     dword [edi+OhciInterruptStatusReg], 4
1374
; enable interrupt on SOF
1375
; Note: OhciInterruptEnableReg/OhciInterruptDisableReg have unusual semantics,
1376
; so there should be 'mov' here, not 'or'
1377
        mov     dword [edi+OhciInterruptEnableReg], 4
1378
        spin_unlock_irq [esi+usb_controller.RemoveSpinlock]
1379
@@:
1380
; 7. Restore the return value and return.
1381
        pop     eax
1382
        pop     edi ebx         ; restore used registers to be stdcall
1383
        ret
1384
endp
1385
 
1386
; Helper procedure for ohci_process_deferred. Processes one completed TD.
1387
; in: esi -> usb_controller, ebx -> usb_gtd, out: ebx -> next usb_gtd.
1388
proc ohci_process_finalized_td
1389
;       DEBUGF 1,'K : processing %x\n',ebx
1390
; 1. Check whether the pipe has been closed, either due to API call or due to
1391
; disconnect; if so, the callback will be called by usb_pipe_closed with
1392
; correct status, so go to step 6 with ebx = 0 (do not free the TD).
1393
        mov     edx, [ebx+usb_gtd.Pipe]
1394
        test    [edx+usb_pipe.Flags], USB_FLAG_CLOSED
1395
        jz      @f
1396
        lea     eax, [ebx+ohci_gtd.NextTD-ohci_gtd.SoftwarePart]
1397
        xor     ebx, ebx
1398
        jmp     .next_td2
1399
@@:
1400
; 2. Remove the descriptor from the descriptors queue.
1401
        call    usb_unlink_td
1402
; 3. Get number of bytes that remain to be transferred.
1403
; If CurBufPtr is zero, everything was transferred.
1404
        xor     edx, edx
1405
        cmp     [ebx+ohci_gtd.CurBufPtr-ohci_gtd.SoftwarePart], edx
1406
        jz      .gotlen
1407
; Otherwise, the remaining length is
1408
; (BufEnd and 0xFFF) - (CurBufPtr and 0xFFF) + 1,
1409
; plus 0x1000 if BufEnd and CurBufPtr are in different pages.
1410
        mov     edx, [ebx+ohci_gtd.BufEnd-ohci_gtd.SoftwarePart]
1411
        mov     eax, [ebx+ohci_gtd.CurBufPtr-ohci_gtd.SoftwarePart]
1412
        mov     ecx, edx
1413
        and     edx, 0xFFF
1414
        inc     edx
1415
        xor     ecx, eax
1416
        and     ecx, -0x1000
1417
        jz      @f
1418
        add     edx, 0x1000
1419
@@:
1420
        and     eax, 0xFFF
1421
        sub     edx, eax
1422
.gotlen:
1423
; The actual length is Length - (remaining length).
1424
        sub     edx, [ebx+usb_gtd.Length]
1425
        neg     edx
1426
; 4. Check for error. If so, go to 7.
1427
        push    ebx
1428
        mov     eax, [ebx+ohci_gtd.Flags-ohci_gtd.SoftwarePart]
1429
        shr     eax, 28
1430
        jnz     .error
1431
.notify:
1432
; 5. Successful completion.
1433
; 5a. Check whether this descriptor has an associated callback.
1434
        mov     ecx, [ebx+usb_gtd.Callback]
1435
        test    ecx, ecx
1436
        jz      .ok_nocallback
1437
; 5b. If so, call the callback.
1438
        stdcall_verify ecx, [ebx+usb_gtd.Pipe], eax, \
1439
                [ebx+usb_gtd.Buffer], edx, [ebx+usb_gtd.UserData]
1440
        jmp     .next_td
1441
.ok_nocallback:
1442
; 5c. Otherwise, add length of the current descriptor to the next descriptor.
1443
        mov     eax, [ebx+usb_gtd.NextVirt]
1444
        add     [eax+usb_gtd.Length], edx
1445
.next_td:
1446
; 6. Free the current descriptor and advance to the next item.
1447
; If the current item is the last in the list,
1448
; set DoneListEndPtr to pointer to DoneList.
1449
        cmp     ebx, [esp]
1450
        jz      @f
1451
        stdcall usb1_free_general_td, ebx
1452
@@:
1453
        pop     ebx
1454
        lea     eax, [ebx+ohci_gtd.NextTD-ohci_gtd.SoftwarePart]
1455
.next_td2:
1456
        push    ebx
1457
        mov     ebx, eax
1458
        lea     edx, [esi+ohci_controller.DoneList-sizeof.ohci_controller]
1459
        xor     ecx, ecx        ; no next item
1460
        lock cmpxchg [esi+ohci_controller.DoneListEndPtr-sizeof.ohci_controller], edx
1461
        jz      .last
1462
; The current item is not the last.
1463
; It is possible, although very rare, that ohci_irq has already advanced
1464
; DoneListEndPtr, but not yet written NextTD. Wait until NextTD is nonzero.
1465
@@:
1466
        mov     ecx, [ebx]
1467
        test    ecx, ecx
1468
        jz      @b
1469
.last:
1470
        pop     ebx
1471
; ecx = the next item
1472
        push    ecx
1473
; Free the current item, set ebx to the next item, continue to 5a.
1474
        test    ebx, ebx
1475
        jz      @f
1476
        stdcall usb1_free_general_td, ebx
1477
@@:
1478
        pop     ebx
1479
        ret
1480
.error:
1481
; 7. There was an error while processing this descriptor.
1482
; The hardware has stopped processing the queue.
1483
; 7a. Save status and length.
1484
        push    eax
1485
        push    edx
1486
;       DEBUGF 1,'K : TD failed:\n'
1487
;       DEBUGF 1,'K : %x %x %x %x\n',[ebx-ohci_gtd.SoftwarePart],[ebx-ohci_gtd.SoftwarePart+4],[ebx-ohci_gtd.SoftwarePart+8],[ebx-ohci_gtd.SoftwarePart+12]
1488
;       DEBUGF 1,'K : %x %x %x %x\n',[ebx-ohci_gtd.SoftwarePart+16],[ebx-ohci_gtd.SoftwarePart+20],[ebx-ohci_gtd.SoftwarePart+24],[ebx-ohci_gtd.SoftwarePart+28]
1489
;       mov     eax, [ebx+usb_gtd.Pipe]
1490
;       DEBUGF 1,'K : pipe: %x %x %x %x\n',[eax-ohci_pipe.SoftwarePart],[eax-ohci_pipe.SoftwarePart+4],[eax-ohci_pipe.SoftwarePart+8],[eax-ohci_pipe.SoftwarePart+12]
1491
; 7b. Traverse the list of descriptors looking for the final packet
1492
; for this transfer.
1493
; Free and unlink non-final descriptors, except the current one.
1494
; Final descriptor will be freed in step 6.
1495
        call    usb_is_final_packet
1496
        jnc     .found_final
1497
        mov     ebx, [ebx+usb_gtd.NextVirt]
1498
virtual at esp
1499
.length         dd      ?
1500
.error_code     dd      ?
1501
.current_item   dd      ?
1502
end virtual
1503
.look_final:
1504
        call    usb_unlink_td
1505
        call    usb_is_final_packet
1506
        jnc     .found_final
1507
        push    [ebx+usb_gtd.NextVirt]
1508
        stdcall usb1_free_general_td, ebx
1509
        pop     ebx
1510
        jmp     .look_final
1511
.found_final:
1512
; 7c. If error code is USB_STATUS_UNDERRUN and the last TD allows short packets,
1513
; it is not an error.
1514
; Note: all TDs except the last one in any transfer stage are marked
1515
; as short-packet-is-error to stop controller from further processing
1516
; of that stage; we need to restart processing from a TD following the last.
1517
; After that, go to step 5 with eax = 0 (no error).
1518
        cmp     dword [.error_code], USB_STATUS_UNDERRUN
1519
        jnz     .no_underrun
1520
        test    byte [ebx+ohci_gtd.Flags+2-ohci_gtd.SoftwarePart], 1 shl (18-16)
1521
        jz      .no_underrun
1522
        and     dword [.error_code], 0
1523
        mov     ecx, [ebx+usb_gtd.Pipe]
1524
        mov     edx, [ecx+ohci_pipe.HeadP-ohci_pipe.SoftwarePart]
1525
        and     edx, 2
1526
.advance_queue:
1527
        mov     eax, [ebx+usb_gtd.NextVirt]
1528
        sub     eax, ohci_gtd.SoftwarePart
1529
        call    get_phys_addr
1530
        or      eax, edx
1531
        mov     [ecx+ohci_pipe.HeadP-ohci_pipe.SoftwarePart], eax
1532
        push    ebx
1533
        mov     ebx, ecx
1534
        call    ohci_notify_new_work
1535
        pop     ebx
1536
        pop     edx eax
1537
        jmp     .notify
1538
; 7d. Abort the entire transfer.
1539
; There are two cases: either there is only one transfer stage
1540
; (everything except control transfers), then ebx points to the last TD and
1541
; all previous TD were unlinked and dismissed (if possible),
1542
; or there are several stages (a control transfer) and ebx points to the last
1543
; TD of Data or Status stage (usb_is_final_packet does not stop in Setup stage,
1544
; because Setup stage can not produce short packets); for Data stage, we need
1545
; to unlink and free (if possible) one more TD and advance ebx to the next one.
1546
.no_underrun:
1547
        cmp     [ebx+usb_gtd.Callback], 0
1548
        jnz     .halted
1549
        cmp     ebx, [.current_item]
1550
        push    [ebx+usb_gtd.NextVirt]
1551
        jz      @f
1552
        stdcall usb1_free_general_td, ebx
1553
@@:
1554
        pop     ebx
1555
        call    usb_unlink_td
1556
.halted:
1557
; 7e. For bulk/interrupt transfers we have no choice but halt the queue,
1558
; the driver should intercede (through some API which is not written yet).
1559
; Control pipes normally recover at the next SETUP transaction (first stage
1560
; of any control transfer), so we hope on the best and just advance the queue
1561
; to the next transfer. (According to the standard, "A control pipe may also
1562
; support functional stall as well, but this is not recommended.").
1563
; Advance the transfer queue to the next descriptor.
1564
        mov     ecx, [ebx+usb_gtd.Pipe]
1565
        mov     edx, [ecx+ohci_pipe.HeadP-ohci_pipe.SoftwarePart]
1566
        and     edx, 2  ; keep toggleCarry bit
1567
        cmp     [ecx+usb_pipe.Type], CONTROL_PIPE
1568
        jnz     @f
1569
        inc     edx     ; set Halted bit
1570
@@:
1571
        jmp     .advance_queue
1572
endp
1573
 
1574
; This procedure is called when a pipe is closing (either due to API call
1575
; or due to disconnect); it unlinks the pipe from the corresponding list.
1576
; esi -> usb_controller, ebx -> usb_pipe
1577
proc ohci_unlink_pipe
1578
        cmp     [ebx+usb_pipe.Type], INTERRUPT_PIPE
1579
        jnz     @f
1580
        mov     eax, [ebx+ohci_pipe.Flags-ohci_pipe.SoftwarePart]
1581
        bt      eax, 13
1582
        setc    cl
1583
        bt      eax, 11
1584
        setc    ch
1585
        shr     eax, 16
1586
        stdcall usb1_interrupt_list_unlink, eax, ecx
1587
@@:
1588
        mov     edx, [ebx+usb_pipe.NextVirt]
1589
        mov     eax, [ebx+usb_pipe.PrevVirt]
1590
        mov     [edx+usb_pipe.PrevVirt], eax
1591
        mov     [eax+usb_pipe.NextVirt], edx
1592
        mov     edx, [ebx+ohci_pipe.NextED-ohci_pipe.SoftwarePart]
1593
        mov     [eax+ohci_pipe.NextED-ohci_pipe.SoftwarePart], edx
1594
        ret
1595
endp