2 * PROJECT: ReactOS USB Port Driver
3 * LICENSE: GPL-2.0+ (https://spdx.org/licenses/GPL-2.0+)
4 * PURPOSE: USBPort USB 2.0 functions
5 * COPYRIGHT: Copyright 2017 Vadim Galyant <vgal@rambler.ru>
15 USB2_AllocateCheck(IN OUT PULONG OutTimeUsed
,
17 IN ULONG LimitAllocation
)
20 BOOLEAN Result
= TRUE
;
22 BusTime
= *OutTimeUsed
+ CalcBusTime
;
23 *OutTimeUsed
+= CalcBusTime
;
25 if (BusTime
> LimitAllocation
)
27 DPRINT("USB2_AllocateCheck: BusTime > LimitAllocation\n");
36 USB2_AddDataBitStuff(IN USHORT DataTime
)
38 return (DataTime
+ (DataTime
/ 16));
43 USB2_IncMicroFrame(OUT PUCHAR frame
,
48 if (*uframe
> (USB2_MICROFRAMES
- 1))
51 *frame
= (*frame
+ 1) & (USB2_FRAMES
- 1);
57 USB2_GetPrevMicroFrame(OUT PUCHAR frame
,
60 *uframe
= USB2_MICROFRAMES
- 1;
65 *frame
= USB2_FRAMES
- 1;
70 USB2_CheckTtEndpointInsert(IN PUSB2_TT_ENDPOINT nextTtEndpoint
,
71 IN PUSB2_TT_ENDPOINT TtEndpoint
)
75 DPRINT("USB2_CheckTtEndpointInsert: nextTtEndpoint - %p, TtEndpoint - %p\n",
81 if (TtEndpoint
->CalcBusTime
>= (USB2_FS_MAX_PERIODIC_ALLOCATION
/ 2))
83 DPRINT1("USB2_CheckTtEndpointInsert: Result - FALSE\n");
89 DPRINT("USB2_CheckTtEndpointInsert: Result - TRUE\n");
93 TransferType
= TtEndpoint
->TtEndpointParams
.TransferType
;
95 if (nextTtEndpoint
->ActualPeriod
< TtEndpoint
->ActualPeriod
&&
96 TransferType
== USBPORT_TRANSFER_TYPE_INTERRUPT
)
98 DPRINT("USB2_CheckTtEndpointInsert: Result - TRUE\n");
102 if ((nextTtEndpoint
->ActualPeriod
<= TtEndpoint
->ActualPeriod
&&
103 TransferType
== USBPORT_TRANSFER_TYPE_ISOCHRONOUS
) ||
104 nextTtEndpoint
== TtEndpoint
)
106 DPRINT("USB2_CheckTtEndpointInsert: Result - TRUE\n");
110 DPRINT("USB2_CheckTtEndpointInsert: Result - FALSE\n");
116 USB2_GetOverhead(IN PUSB2_TT_ENDPOINT TtEndpoint
)
124 TransferType
= TtEndpoint
->TtEndpointParams
.TransferType
;
125 Direction
= TtEndpoint
->TtEndpointParams
.Direction
;
126 DeviceSpeed
= TtEndpoint
->TtEndpointParams
.Direction
;
128 HostDelay
= TtEndpoint
->Tt
->HcExtension
->HcDelayTime
;
130 if (DeviceSpeed
== UsbHighSpeed
)
132 if (Direction
== USBPORT_TRANSFER_DIRECTION_OUT
)
134 if (TransferType
== USBPORT_TRANSFER_TYPE_ISOCHRONOUS
)
135 Overhead
= HostDelay
+ USB2_HS_ISOCHRONOUS_OUT_OVERHEAD
;
137 Overhead
= HostDelay
+ USB2_HS_INTERRUPT_OUT_OVERHEAD
;
141 if (TransferType
== USBPORT_TRANSFER_TYPE_ISOCHRONOUS
)
142 Overhead
= HostDelay
+ USB2_HS_ISOCHRONOUS_IN_OVERHEAD
;
144 Overhead
= HostDelay
+ USB2_HS_ISOCHRONOUS_OUT_OVERHEAD
;
147 else if (DeviceSpeed
== UsbFullSpeed
)
149 if (TransferType
== USBPORT_TRANSFER_TYPE_ISOCHRONOUS
)
150 Overhead
= HostDelay
+ USB2_FS_ISOCHRONOUS_OVERHEAD
;
152 Overhead
= HostDelay
+ USB2_FS_INTERRUPT_OVERHEAD
;
156 Overhead
= HostDelay
+ USB2_LS_INTERRUPT_OVERHEAD
;
164 USB2_GetHsOverhead(IN PUSB2_TT_ENDPOINT TtEndpoint
,
165 IN PULONG OverheadSS
,
166 IN PULONG OverheadCS
)
172 TransferType
= TtEndpoint
->TtEndpointParams
.TransferType
;
173 Direction
= TtEndpoint
->TtEndpointParams
.Direction
;
175 HostDelay
= TtEndpoint
->Tt
->HcExtension
->HcDelayTime
;
177 if (Direction
== USBPORT_TRANSFER_DIRECTION_OUT
)
179 if (TransferType
== USBPORT_TRANSFER_TYPE_ISOCHRONOUS
)
181 *OverheadSS
= HostDelay
+ USB2_HS_SS_ISOCHRONOUS_OUT_OVERHEAD
;
186 *OverheadSS
= HostDelay
+ USB2_HS_SS_INTERRUPT_OUT_OVERHEAD
;
187 *OverheadCS
= HostDelay
+ USB2_HS_CS_INTERRUPT_OUT_OVERHEAD
;
192 if (TransferType
== USBPORT_TRANSFER_TYPE_ISOCHRONOUS
)
194 *OverheadSS
= HostDelay
+ USB2_HS_SS_ISOCHRONOUS_IN_OVERHEAD
;
195 *OverheadCS
= HostDelay
+ USB2_HS_CS_ISOCHRONOUS_IN_OVERHEAD
;
199 *OverheadSS
= HostDelay
+ USB2_HS_SS_INTERRUPT_IN_OVERHEAD
;
200 *OverheadCS
= HostDelay
+ USB2_HS_CS_INTERRUPT_IN_OVERHEAD
;
203 DPRINT("USB2_GetHsOverhead: *OverheadSS - %X, *OverheadCS - %X\n",
211 USB2_GetLastIsoTime(IN PUSB2_TT_ENDPOINT TtEndpoint
,
214 PUSB2_TT_ENDPOINT nextTtEndpoint
;
217 DPRINT("USB2_GetLastIsoTime: TtEndpoint - %p, Frame - %X\n",
221 nextTtEndpoint
= TtEndpoint
->Tt
->FrameBudget
[Frame
].IsoEndpoint
->NextTtEndpoint
;
223 if (nextTtEndpoint
||
224 (nextTtEndpoint
= TtEndpoint
->Tt
->FrameBudget
[Frame
].AltEndpoint
) != NULL
)
226 Result
= nextTtEndpoint
->StartTime
+ nextTtEndpoint
->CalcBusTime
;
230 Result
= USB2_FS_SOF_TIME
;
238 USB2_GetStartTime(IN PUSB2_TT_ENDPOINT nextTtEndpoint
,
239 IN PUSB2_TT_ENDPOINT TtEndpoint
,
240 IN PUSB2_TT_ENDPOINT prevTtEndpoint
,
243 PUSB2_TT_ENDPOINT ttEndpoint
;
246 DPRINT("USB2_GetStartTime: nextTtEndpoint - %p, TtEndpoint - %p, prevTtEndpoint - %p, Frame - %X\n",
252 TransferType
= TtEndpoint
->TtEndpointParams
.TransferType
;
254 if (TransferType
== USBPORT_TRANSFER_TYPE_ISOCHRONOUS
)
257 return nextTtEndpoint
->StartTime
+ nextTtEndpoint
->CalcBusTime
;
259 ttEndpoint
= TtEndpoint
->Tt
->FrameBudget
[Frame
].AltEndpoint
;
262 return ttEndpoint
->StartTime
+ ttEndpoint
->CalcBusTime
;
264 return USB2_FS_SOF_TIME
;
268 ttEndpoint
= prevTtEndpoint
;
270 if (ttEndpoint
== TtEndpoint
->Tt
->FrameBudget
[Frame
].IntEndpoint
)
271 return USB2_GetLastIsoTime(TtEndpoint
, Frame
);
273 return ttEndpoint
->StartTime
+ ttEndpoint
->CalcBusTime
;
279 USB2_InitTtEndpoint(IN PUSB2_TT_ENDPOINT TtEndpoint
,
280 IN UCHAR TransferType
,
282 IN UCHAR DeviceSpeed
,
284 IN USHORT MaxPacketSize
,
287 TtEndpoint
->TtEndpointParams
.TransferType
= TransferType
;
288 TtEndpoint
->TtEndpointParams
.Direction
= Direction
;
289 TtEndpoint
->TtEndpointParams
.DeviceSpeed
= DeviceSpeed
;
291 TtEndpoint
->Period
= Period
;
292 TtEndpoint
->MaxPacketSize
= MaxPacketSize
;
295 TtEndpoint
->CalcBusTime
= 0;
296 TtEndpoint
->StartTime
= 0;
297 TtEndpoint
->ActualPeriod
= 0;
298 TtEndpoint
->StartFrame
= 0;
299 TtEndpoint
->StartMicroframe
= 0;
301 TtEndpoint
->Nums
.AsULONG
= 0;
302 TtEndpoint
->NextTtEndpoint
= NULL
;
303 TtEndpoint
->Reserved2
= 0;
304 TtEndpoint
->PreviosPeriod
= 0;
305 TtEndpoint
->IsPromoted
= FALSE
;
310 USB2_AllocateHS(IN PUSB2_TT_ENDPOINT TtEndpoint
,
313 PUSB2_HC_EXTENSION HcExtension
;
318 ULONG RemainDataTime
;
327 DPRINT("USB2_AllocateHS: TtEndpoint - %p, Frame - %X, TtEndpoint->StartFrame - %X\n",
330 TtEndpoint
->StartFrame
);
333 HcExtension
= Tt
->HcExtension
;
335 TransferType
= TtEndpoint
->TtEndpointParams
.TransferType
;
336 Direction
= TtEndpoint
->TtEndpointParams
.Direction
;
340 TtEndpoint
->StartMicroframe
=
341 TtEndpoint
->StartTime
/ USB2_FS_RAW_BYTES_IN_MICROFRAME
- 1;
343 DPRINT("USB2_AllocateHS: TtEndpoint->StartMicroframe - %X\n",
344 TtEndpoint
->StartMicroframe
);
347 USB2_GetHsOverhead(TtEndpoint
, &OverheadSS
, &OverheadCS
);
349 if (TransferType
== USBPORT_TRANSFER_TYPE_INTERRUPT
)
353 TtEndpoint
->Nums
.NumStarts
= 1;
355 if ((CHAR
)TtEndpoint
->StartMicroframe
< 5)
357 TtEndpoint
->Nums
.NumCompletes
= 3;
361 TtEndpoint
->Nums
.NumCompletes
= 2;
367 if (Direction
== USBPORT_TRANSFER_DIRECTION_OUT
)
369 DPRINT("USB2_AllocateHS: ISO UNIMPLEMENTED\n");
374 DPRINT("USB2_AllocateHS: ISO UNIMPLEMENTED\n");
379 frame
= TtEndpoint
->StartFrame
+ Frame
;
380 uframe
= TtEndpoint
->StartMicroframe
;
382 if (TtEndpoint
->StartMicroframe
== 0xFF)
383 USB2_GetPrevMicroFrame(&frame
, &uframe
);
385 for (ix
= 0; ix
< TtEndpoint
->Nums
.NumStarts
; ix
++)
387 if (!USB2_AllocateCheck(&HcExtension
->TimeUsed
[frame
][uframe
],
389 USB2_MAX_MICROFRAME_ALLOCATION
))
394 if (Tt
->NumStartSplits
[frame
][uframe
] > (USB2_MAX_FS_LS_TRANSACTIONS_IN_UFRAME
- 1))
396 DPRINT1("USB2_AllocateHS: Num Start Splits - %X\n",
397 Tt
->NumStartSplits
[frame
][uframe
] + 1);
403 ++Tt
->NumStartSplits
[frame
][uframe
];
404 USB2_IncMicroFrame(&frame
, &uframe
);
407 frame
= TtEndpoint
->StartFrame
+ Frame
;
408 uframe
= TtEndpoint
->StartMicroframe
+ TtEndpoint
->Nums
.NumStarts
+ 1;
410 for (ix
= 0; ix
< TtEndpoint
->Nums
.NumCompletes
; ix
++)
412 if (!USB2_AllocateCheck(&HcExtension
->TimeUsed
[frame
][uframe
],
414 USB2_MAX_MICROFRAME_ALLOCATION
))
419 USB2_IncMicroFrame(&frame
, &uframe
);
422 if (Direction
== USBPORT_TRANSFER_DIRECTION_OUT
)
424 DPRINT("USB2_AllocateHS: DIRECTION OUT UNIMPLEMENTED\n");
429 frame
= TtEndpoint
->StartFrame
+ Frame
;
430 uframe
= TtEndpoint
->StartMicroframe
+ TtEndpoint
->Nums
.NumStarts
+ 1;
432 for (ix
= 0; ix
< TtEndpoint
->Nums
.NumCompletes
; ix
++)
434 if (Tt
->TimeCS
[frame
][uframe
] < USB2_FS_RAW_BYTES_IN_MICROFRAME
)
436 if (Tt
->TimeCS
[frame
][uframe
] < USB2_FS_RAW_BYTES_IN_MICROFRAME
)
438 RemainDataTime
= USB2_FS_RAW_BYTES_IN_MICROFRAME
-
439 Tt
->TimeCS
[frame
][uframe
];
446 PktSize
= TtEndpoint
->MaxPacketSize
;
448 if (RemainDataTime
>= USB2_AddDataBitStuff(PktSize
))
450 DataTime
= USB2_AddDataBitStuff(PktSize
);
454 DataTime
= RemainDataTime
;
457 if (!USB2_AllocateCheck(&HcExtension
->TimeUsed
[frame
][uframe
],
459 USB2_MAX_MICROFRAME_ALLOCATION
))
465 PktSize
= TtEndpoint
->MaxPacketSize
;
467 if (USB2_AddDataBitStuff(PktSize
) < USB2_FS_RAW_BYTES_IN_MICROFRAME
)
469 Tt
->TimeCS
[frame
][uframe
] += USB2_AddDataBitStuff(PktSize
);
473 Tt
->TimeCS
[frame
][uframe
] += USB2_FS_RAW_BYTES_IN_MICROFRAME
;
476 USB2_IncMicroFrame(&frame
, &uframe
);
480 DPRINT("USB2_AllocateHS: Result - %X\n", Result
);
486 USB2_DeallocateHS(IN PUSB2_TT_ENDPOINT TtEndpoint
,
489 DPRINT("USB2_DeallocateHS: UNIMPLEMENTED FIXME\n");
495 USB2_MoveTtEndpoint(IN PUSB2_TT_ENDPOINT TtEndpoint
,
497 IN PUSB2_REBALANCE Rebalance
,
498 IN ULONG RebalanceListEntries
,
499 OUT BOOLEAN
* OutResult
)
501 DPRINT("USB2_MoveTtEndpoint: UNIMPLEMENTED FIXME\n");
508 USB2_ConvertFrame(IN UCHAR Frame
,
511 OUT PUCHAR HcMicroframe
)
513 DPRINT("USB2_ConvertFrame: Frame - %x, Microframe - %x\n",
517 if (Microframe
== 0xFF)
523 if (Microframe
>= 0 &&
524 Microframe
<= (USB2_MICROFRAMES
- 2))
527 *HcMicroframe
= Microframe
+ 1;
530 if (Microframe
== (USB2_MICROFRAMES
- 1))
532 *HcFrame
= Frame
+ 1;
539 USB2_GetSMASK(IN PUSB2_TT_ENDPOINT TtEndpoint
)
546 if (TtEndpoint
->TtEndpointParams
.DeviceSpeed
== UsbHighSpeed
)
548 SMask
= (1 << TtEndpoint
->StartMicroframe
);
552 USB2_ConvertFrame(TtEndpoint
->StartFrame
,
553 TtEndpoint
->StartMicroframe
,
557 for (ix
= 0; ix
< TtEndpoint
->Nums
.NumStarts
; ix
++)
559 SMask
|= (1 << HcMicroFrame
);
569 USB2_DeallocateEndpointBudget(IN PUSB2_TT_ENDPOINT TtEndpoint
,
570 IN PUSB2_REBALANCE Rebalance
,
571 IN PULONG RebalanceListEntries
,
574 DPRINT("USB2_DeallocateEndpointBudget: UNIMPLEMENTED FIXME\n");
581 USB2_AllocateTimeForEndpoint(IN PUSB2_TT_ENDPOINT TtEndpoint
,
582 IN PUSB2_REBALANCE Rebalance
,
583 IN PULONG RebalanceListEntries
)
586 PUSB2_HC_EXTENSION HcExtension
;
597 PUSB2_TT_ENDPOINT prevTtEndpoint
;
598 PUSB2_TT_ENDPOINT nextTtEndpoint
;
599 PUSB2_TT_ENDPOINT IntEndpoint
;
602 BOOLEAN Result
= TRUE
;
604 DPRINT("USB2_AllocateTimeForEndpoint: TtEndpoint - %p\n", TtEndpoint
);
607 HcExtension
= Tt
->HcExtension
;
609 TtEndpoint
->Nums
.NumStarts
= 0;
610 TtEndpoint
->Nums
.NumCompletes
= 0;
612 TtEndpoint
->StartFrame
= 0;
613 TtEndpoint
->StartMicroframe
= 0;
615 if (TtEndpoint
->CalcBusTime
)
617 DPRINT("USB2_AllocateTimeForEndpoint: TtEndpoint already allocated!\n");
621 Speed
= TtEndpoint
->TtEndpointParams
.DeviceSpeed
;
623 if (Speed
== UsbHighSpeed
)
625 if (TtEndpoint
->Period
> USB2_MAX_MICROFRAMES
)
626 TtEndpoint
->ActualPeriod
= USB2_MAX_MICROFRAMES
;
628 TtEndpoint
->ActualPeriod
= TtEndpoint
->Period
;
630 MinTimeUsed
= HcExtension
->TimeUsed
[0][0];
632 for (ix
= 1; ix
< TtEndpoint
->ActualPeriod
; ix
++)
634 frame
= ix
/ USB2_MICROFRAMES
;
635 uframe
= ix
% (USB2_MICROFRAMES
- 1);
637 TimeUsed
= HcExtension
->TimeUsed
[frame
][uframe
];
639 if (TimeUsed
< MinTimeUsed
)
641 MinTimeUsed
= TimeUsed
;
642 TtEndpoint
->StartFrame
= frame
;
643 TtEndpoint
->StartMicroframe
= uframe
;
647 TtEndpoint
->CalcBusTime
= USB2_GetOverhead(TtEndpoint
) +
648 USB2_AddDataBitStuff(TtEndpoint
->MaxPacketSize
);
650 DPRINT("USB2_AllocateTimeForEndpoint: StartFrame - %X, StartMicroframe - %X, CalcBusTime - %X\n",
651 TtEndpoint
->StartFrame
,
652 TtEndpoint
->StartMicroframe
,
653 TtEndpoint
->CalcBusTime
);
655 Microframe
= TtEndpoint
->StartFrame
* USB2_MICROFRAMES
+
656 TtEndpoint
->StartMicroframe
;
658 if (Microframe
>= USB2_MAX_MICROFRAMES
)
660 DPRINT("USB2_AllocateTimeForEndpoint: Microframe >= 256. Result - TRUE\n");
664 for (ix
= Microframe
;
665 ix
< USB2_MAX_MICROFRAMES
;
666 ix
+= TtEndpoint
->ActualPeriod
)
668 frame
= ix
/ USB2_MICROFRAMES
;
669 uframe
= ix
% (USB2_MICROFRAMES
- 1);
671 DPRINT("USB2_AllocateTimeForEndpoint: frame - %X, uframe - %X, TimeUsed[f][uf] - %X\n",
674 HcExtension
->TimeUsed
[frame
][uframe
]);
676 if (!USB2_AllocateCheck(&HcExtension
->TimeUsed
[frame
][uframe
],
677 TtEndpoint
->CalcBusTime
,
678 USB2_MAX_MICROFRAME_ALLOCATION
))
680 DPRINT("USB2_AllocateTimeForEndpoint: Result = FALSE\n");
687 for (ix
= Microframe
;
688 ix
< USB2_MAX_MICROFRAMES
;
689 ix
+= TtEndpoint
->ActualPeriod
)
691 frame
= ix
/ USB2_MICROFRAMES
;
692 uframe
= ix
% (USB2_MICROFRAMES
- 1);
694 HcExtension
->TimeUsed
[frame
][uframe
] -= TtEndpoint
->CalcBusTime
;
698 DPRINT("USB2_AllocateTimeForEndpoint: Result - TRUE\n");
702 /* Speed != UsbHighSpeed (FS/LS) */
704 if (TtEndpoint
->Period
> USB2_FRAMES
)
705 TtEndpoint
->ActualPeriod
= USB2_FRAMES
;
707 TtEndpoint
->ActualPeriod
= TtEndpoint
->Period
;
709 MinTimeUsed
= Tt
->FrameBudget
[0].TimeUsed
;
711 for (ix
= 1; ix
< TtEndpoint
->ActualPeriod
; ix
++)
713 if ((Tt
->FrameBudget
[ix
].TimeUsed
) < MinTimeUsed
)
715 MinTimeUsed
= Tt
->FrameBudget
[ix
].TimeUsed
;
716 TtEndpoint
->StartFrame
= ix
;
720 TransferType
= TtEndpoint
->TtEndpointParams
.TransferType
;
722 if (TransferType
== USBPORT_TRANSFER_TYPE_ISOCHRONOUS
)
724 if (Speed
== UsbFullSpeed
)
726 Overhead
= USB2_FS_ISOCHRONOUS_OVERHEAD
+ Tt
->DelayTime
;
730 DPRINT("USB2_AllocateTimeForEndpoint: ISO can not be on a LS bus!\n");
736 if (Speed
== UsbFullSpeed
)
737 Overhead
= USB2_FS_INTERRUPT_OVERHEAD
+ Tt
->DelayTime
;
739 Overhead
= USB2_LS_INTERRUPT_OVERHEAD
+ Tt
->DelayTime
;
742 if (Speed
== UsbLowSpeed
)
744 TtEndpoint
->CalcBusTime
= TtEndpoint
->MaxPacketSize
* 8 + Overhead
;
748 TtEndpoint
->CalcBusTime
= TtEndpoint
->MaxPacketSize
+ Overhead
;
751 LatestStart
= USB2_HUB_DELAY
+ USB2_FS_SOF_TIME
;
754 (TtEndpoint
->StartFrame
+ ix
) < USB2_FRAMES
;
755 ix
+= TtEndpoint
->ActualPeriod
)
757 frame
= TtEndpoint
->StartFrame
+ ix
;
759 if (Tt
->FrameBudget
[frame
].AltEndpoint
&&
760 TtEndpoint
->CalcBusTime
>= (USB2_FS_MAX_PERIODIC_ALLOCATION
/ 2))
762 DPRINT("USB2_AllocateTimeForEndpoint: return FALSE\n");
766 if (TransferType
== USBPORT_TRANSFER_TYPE_ISOCHRONOUS
)
767 prevTtEndpoint
= Tt
->FrameBudget
[frame
].IsoEndpoint
;
769 prevTtEndpoint
= Tt
->FrameBudget
[frame
].IntEndpoint
;
771 for (nextTtEndpoint
= prevTtEndpoint
->NextTtEndpoint
;
773 nextTtEndpoint
= nextTtEndpoint
->NextTtEndpoint
)
775 if (USB2_CheckTtEndpointInsert(nextTtEndpoint
, TtEndpoint
))
780 prevTtEndpoint
= nextTtEndpoint
;
783 StartTime
= USB2_GetStartTime(nextTtEndpoint
,
788 if (StartTime
> LatestStart
)
789 LatestStart
= StartTime
;
792 TtEndpoint
->StartTime
= LatestStart
;
794 if ((LatestStart
+ TtEndpoint
->CalcBusTime
) > USB2_FS_MAX_PERIODIC_ALLOCATION
)
796 TtEndpoint
->CalcBusTime
= 0;
797 DPRINT("USB2_AllocateTimeForEndpoint: return FALSE\n");
801 for (ix
= 0, frame
= -TtEndpoint
->StartFrame
;
805 DPRINT("USB2_AllocateTimeForEndpoint: ix - %X, frame - %X, StartFrame - %X\n",
808 TtEndpoint
->StartFrame
);
810 if (TransferType
== USBPORT_TRANSFER_TYPE_ISOCHRONOUS
)
812 DPRINT1("USB2_AllocateTimeForEndpoint: Iso Ep UNIMPLEMENTED. FIXME\n");
817 IntEndpoint
= Tt
->FrameBudget
[ix
].IntEndpoint
;
818 nextTtEndpoint
= IntEndpoint
->NextTtEndpoint
;
820 for (nextTtEndpoint
= IntEndpoint
->NextTtEndpoint
;
822 nextTtEndpoint
= nextTtEndpoint
->NextTtEndpoint
)
824 if (USB2_CheckTtEndpointInsert(nextTtEndpoint
, TtEndpoint
))
826 IntEndpoint
= nextTtEndpoint
;
829 if ((frame
% TtEndpoint
->ActualPeriod
) == 0)
837 calcBusTime
= LatestStart
+ TtEndpoint
->CalcBusTime
-
838 nextTtEndpoint
->StartTime
;
842 calcBusTime
= TtEndpoint
->CalcBusTime
;
847 TimeUsed
= Tt
->FrameBudget
[ix
].TimeUsed
;
849 if (!USB2_AllocateCheck(&TimeUsed
,
851 USB2_FS_MAX_PERIODIC_ALLOCATION
))
853 DPRINT("USB2_AllocateTimeForEndpoint: Result = FALSE\n");
859 if (nextTtEndpoint
!= TtEndpoint
)
861 if ((frame
% TtEndpoint
->ActualPeriod
) == 0)
865 DPRINT("USB2_AllocateTimeForEndpoint: frame == 0\n");
866 TtEndpoint
->NextTtEndpoint
= nextTtEndpoint
;
869 IntEndpoint
->NextTtEndpoint
= TtEndpoint
;
871 DPRINT("USB2_AllocateTimeForEndpoint: TtEndpoint - %p, nextTtEndpoint - %p\n",
881 DPRINT("USB2_AllocateTimeForEndpoint: nextTtEndpoint - %p, calcBusTime - %X\n",
887 nextTtEndpoint
= nextTtEndpoint
->NextTtEndpoint
)
889 MoveResult
= USB2_MoveTtEndpoint(nextTtEndpoint
,
892 *RebalanceListEntries
,
897 DPRINT("USB2_AllocateTimeForEndpoint: Result = FALSE\n");
908 if ((frame
% TtEndpoint
->ActualPeriod
) == 0)
910 if (!USB2_AllocateHS(TtEndpoint
, frame
))
912 DPRINT1("USB2_AllocateTimeForEndpoint: USB2_AllocateHS return FALSE\n");
916 Tt
->FrameBudget
[ix
].TimeUsed
+= TtEndpoint
->CalcBusTime
;
921 USB2_DeallocateEndpointBudget(TtEndpoint
,
923 RebalanceListEntries
,
926 DPRINT("USB2_AllocateTimeForEndpoint: return FALSE\n");
931 DPRINT("USB2_AllocateTimeForEndpoint: Result - %X\n", Result
);
937 USB2_PromotePeriods(IN PUSB2_TT_ENDPOINT TtEndpoint
,
938 IN PUSB2_REBALANCE Rebalance
,
939 IN PULONG RebalanceListEntries
)
941 DPRINT1("USB2_PromotePeriods: UNIMPLEMENTED. FIXME\n");
948 USBPORT_UpdateAllocatedBwTt(IN PUSB2_TT_EXTENSION TtExtension
)
951 ULONG NewBusBandwidth
;
952 ULONG MaxBusBandwidth
= 0;
953 ULONG MinBusBandwidth
;
956 DPRINT("USBPORT_UpdateAllocatedBwTt: TtExtension - %p\n", TtExtension
);
958 BusBandwidth
= TtExtension
->BusBandwidth
;
959 MinBusBandwidth
= BusBandwidth
;
961 for (ix
= 0; ix
< USB2_FRAMES
; ix
++)
963 NewBusBandwidth
= BusBandwidth
- TtExtension
->Bandwidth
[ix
];
965 if (NewBusBandwidth
> MaxBusBandwidth
)
966 MaxBusBandwidth
= NewBusBandwidth
;
968 if (NewBusBandwidth
< MinBusBandwidth
)
969 MinBusBandwidth
= NewBusBandwidth
;
972 TtExtension
->MaxBandwidth
= MaxBusBandwidth
;
974 if (MinBusBandwidth
== BusBandwidth
)
975 TtExtension
->MinBandwidth
= 0;
977 TtExtension
->MinBandwidth
= MinBusBandwidth
;
982 USBPORT_AllocateBandwidthUSB2(IN PDEVICE_OBJECT FdoDevice
,
983 IN PUSBPORT_ENDPOINT Endpoint
)
985 PUSBPORT_DEVICE_EXTENSION FdoExtension
;
986 PUSBPORT_ENDPOINT_PROPERTIES EndpointProperties
;
987 PUSB2_TT_EXTENSION TtExtension
;
989 PUSB2_REBALANCE Rebalance
;
990 LIST_ENTRY RebalanceList
;
991 ULONG RebalanceListEntries
;
992 PUSB2_TT_ENDPOINT TtEndpoint
;
993 PUSB2_TT_ENDPOINT RebalanceTtEndpoint
;
995 USB_DEVICE_SPEED DeviceSpeed
;
997 ULONG AllocedBusTime
;
998 ULONG EndpointBandwidth
;
999 ULONG ScheduleOffset
;
1009 DPRINT("USBPORT_AllocateBandwidthUSB2: FdoDevice - %p, Endpoint - %p\n",
1013 EndpointProperties
= &Endpoint
->EndpointProperties
;
1014 EndpointProperties
->ScheduleOffset
= 0;
1016 if (Endpoint
->Flags
& ENDPOINT_FLAG_ROOTHUB_EP0
)
1018 DPRINT("USBPORT_AllocateBandwidthUSB2: ENDPOINT_FLAG_ROOTHUB_EP0\n");
1022 FdoExtension
= FdoDevice
->DeviceExtension
;
1024 TransferType
= EndpointProperties
->TransferType
;
1025 DPRINT("USBPORT_AllocateBandwidthUSB2: TransferType - %X\n", TransferType
);
1027 if (TransferType
== USBPORT_TRANSFER_TYPE_CONTROL
||
1028 TransferType
== USBPORT_TRANSFER_TYPE_BULK
)
1033 if (Endpoint
->TtExtension
)
1034 TtExtension
= Endpoint
->TtExtension
;
1038 InitializeListHead(&RebalanceList
);
1040 Rebalance
= ExAllocatePoolWithTag(NonPagedPool
,
1041 sizeof(USB2_REBALANCE
),
1044 DPRINT("USBPORT_AllocateBandwidthUSB2: Rebalance - %p, TtExtension - %p\n",
1050 RtlZeroMemory(Rebalance
, sizeof(USB2_REBALANCE
));
1052 TtEndpoint
= Endpoint
->TtEndpoint
;
1053 TtEndpoint
->Endpoint
= Endpoint
;
1055 Direction
= EndpointProperties
->Direction
== USBPORT_TRANSFER_DIRECTION_OUT
;
1056 DeviceSpeed
= EndpointProperties
->DeviceSpeed
;
1058 switch (DeviceSpeed
)
1063 Tt
= &TtExtension
->Tt
;
1065 Period
= USB2_FRAMES
;
1067 while (Period
> 0 && Period
> EndpointProperties
->Period
)
1072 DPRINT("USBPORT_AllocateBandwidthUSB2: Period - %X\n", Period
);
1078 Tt
= &FdoExtension
->Usb2Extension
->HcTt
;
1080 if (EndpointProperties
->Period
> USB2_MAX_MICROFRAMES
)
1081 Period
= USB2_MAX_MICROFRAMES
;
1083 Period
= EndpointProperties
->Period
;
1090 DPRINT1("USBPORT_AllocateBandwidthUSB2: DeviceSpeed - %X!\n",
1095 Tt
= &TtExtension
->Tt
;
1100 USB2_InitTtEndpoint(TtEndpoint
,
1105 EndpointProperties
->MaxPacketSize
,
1108 RebalanceListEntries
= USB2_FRAMES
- 2;
1110 Result
= USB2_AllocateTimeForEndpoint(TtEndpoint
,
1112 &RebalanceListEntries
);
1116 Result
= USB2_PromotePeriods(TtEndpoint
,
1118 &RebalanceListEntries
);
1121 RebalanceListEntries
= 0;
1123 for (ix
= 0; Rebalance
->RebalanceEndpoint
[ix
]; ix
++)
1125 RebalanceListEntries
= ix
+ 1;
1130 RebalanceListEntries
= 0;
1134 DPRINT("USBPORT_AllocateBandwidthUSB2: RebalanceListEntries - %X, Result - %X\n",
1135 RebalanceListEntries
,
1138 for (ix
= 0; ix
< RebalanceListEntries
; ix
++)
1140 RebalanceTtEndpoint
= Rebalance
->RebalanceEndpoint
[ix
];
1142 DPRINT("USBPORT_AllocateBandwidthUSB2: RebalanceTtEndpoint[%X] - %p, RebalanceTtEndpoint - %p, RebalanceLink - %p\n",
1144 RebalanceTtEndpoint
,
1145 &RebalanceTtEndpoint
->Endpoint
->RebalanceLink
);
1147 InsertTailList(&RebalanceList
,
1148 &RebalanceTtEndpoint
->Endpoint
->RebalanceLink
);
1152 ExFreePoolWithTag(Rebalance
, USB_PORT_TAG
);
1156 SMask
= USB2_GetSMASK(Endpoint
->TtEndpoint
);
1157 EndpointProperties
->InterruptScheduleMask
= SMask
;
1159 CMask
= USB2_GetCMASK(Endpoint
->TtEndpoint
);
1160 EndpointProperties
->SplitCompletionMask
= CMask
;
1162 AllocedBusTime
= TtEndpoint
->CalcBusTime
;
1164 EndpointBandwidth
= USB2_MICROFRAMES
* AllocedBusTime
;
1165 EndpointProperties
->UsbBandwidth
= EndpointBandwidth
;
1167 ActualPeriod
= Endpoint
->TtEndpoint
->ActualPeriod
;
1168 EndpointProperties
->Period
= ActualPeriod
;
1170 ScheduleOffset
= Endpoint
->TtEndpoint
->StartFrame
;
1171 EndpointProperties
->ScheduleOffset
= ScheduleOffset
;
1173 Factor
= USB2_FRAMES
/ ActualPeriod
;
1176 n
= ScheduleOffset
* Factor
;
1180 for (ix
= 0; ix
< Factor
; ix
++)
1182 TtExtension
->Bandwidth
[n
+ ix
] -= EndpointBandwidth
;
1187 for (ix
= 1; ix
< Factor
; ix
++)
1189 FdoExtension
->Bandwidth
[n
+ ix
] -= EndpointBandwidth
;
1193 USBPORT_DumpingEndpointProperties(EndpointProperties
);
1194 USBPORT_DumpingTtEndpoint(Endpoint
->TtEndpoint
);
1196 if (AllocedBusTime
>= (USB2_FS_MAX_PERIODIC_ALLOCATION
/ 2))
1198 DPRINT1("USBPORT_AllocateBandwidthUSB2: AllocedBusTime >= 0.5 * MAX_ALLOCATION \n");
1202 //USB2_Rebalance(FdoDevice, &RebalanceList);
1206 DPRINT("USBPORT_AllocateBandwidthUSB2: Result - %X\n", Result
);
1210 for (ix
= 0; ix
< USB2_FRAMES
; ix
++)
1212 FdoExtension
->Bandwidth
[ix
] += TtExtension
->MaxBandwidth
;
1215 USBPORT_UpdateAllocatedBwTt(TtExtension
);
1217 for (ix
= 0; ix
< USB2_FRAMES
; ix
++)
1219 FdoExtension
->Bandwidth
[ix
] -= TtExtension
->MaxBandwidth
;
1222 DPRINT("USBPORT_AllocateBandwidthUSB2: Result - %X\n", Result
);
1229 USBPORT_FreeBandwidthUSB2(IN PDEVICE_OBJECT FdoDevice
,
1230 IN PUSBPORT_ENDPOINT Endpoint
)
1232 DPRINT1("USBPORT_FreeBandwidthUSB2: UNIMPLEMENTED. FIXME. \n");
1237 USB2_InitTT(IN PUSB2_HC_EXTENSION HcExtension
,
1243 DPRINT("USB2_InitTT: HcExtension - %p, Tt - %p\n", HcExtension
, Tt
);
1245 Tt
->HcExtension
= HcExtension
;
1247 Tt
->MaxTime
= USB2_FS_MAX_PERIODIC_ALLOCATION
;
1249 for (ix
= 0; ix
< USB2_FRAMES
; ix
++)
1251 Tt
->FrameBudget
[ix
].TimeUsed
= USB2_MAX_MICROFRAMES
;
1252 Tt
->FrameBudget
[ix
].AltEndpoint
= NULL
;
1254 for (jx
= 0; jx
< USB2_MICROFRAMES
; jx
++)
1256 Tt
->TimeCS
[ix
][jx
] = 0;
1257 Tt
->NumStartSplits
[ix
][jx
] = 0;
1260 Tt
->FrameBudget
[ix
].IsoEndpoint
= &Tt
->IsoEndpoint
[ix
];
1262 USB2_InitTtEndpoint(&Tt
->IsoEndpoint
[ix
],
1263 USBPORT_TRANSFER_TYPE_ISOCHRONOUS
,
1264 USBPORT_TRANSFER_DIRECTION_OUT
,
1270 Tt
->IsoEndpoint
[ix
].ActualPeriod
= USB2_FRAMES
;
1271 Tt
->IsoEndpoint
[ix
].CalcBusTime
= USB2_FS_SOF_TIME
+ USB2_HUB_DELAY
;
1272 Tt
->IsoEndpoint
[ix
].StartFrame
= ix
;
1273 Tt
->IsoEndpoint
[ix
].StartMicroframe
= 0xFF;
1275 Tt
->FrameBudget
[ix
].IntEndpoint
= &Tt
->IntEndpoint
[ix
];
1277 USB2_InitTtEndpoint(&Tt
->IntEndpoint
[ix
],
1278 USBPORT_TRANSFER_TYPE_INTERRUPT
,
1279 USBPORT_TRANSFER_DIRECTION_OUT
,
1285 Tt
->IntEndpoint
[ix
].ActualPeriod
= USB2_FRAMES
;
1286 Tt
->IntEndpoint
[ix
].CalcBusTime
= USB2_FS_SOF_TIME
+ USB2_HUB_DELAY
;
1287 Tt
->IntEndpoint
[ix
].StartFrame
= ix
;
1288 Tt
->IntEndpoint
[ix
].StartMicroframe
= 0xFF;
1294 USB2_InitController(IN PUSB2_HC_EXTENSION HcExtension
)
1299 DPRINT("USB2_InitController: HcExtension - %p\n", HcExtension
);
1301 HcExtension
->MaxHsBusAllocation
= USB2_MAX_MICROFRAME_ALLOCATION
;
1303 for (ix
= 0; ix
< USB2_FRAMES
; ix
++)
1305 for (jx
= 0; jx
< USB2_MICROFRAMES
; jx
++)
1307 HcExtension
->TimeUsed
[ix
][jx
] = 0;
1311 HcExtension
->HcDelayTime
= USB2_CONTROLLER_DELAY
;
1313 USB2_InitTT(HcExtension
, &HcExtension
->HcTt
);