Lines Matching full:hs_ep
111 * @hs_ep: The endpoint
116 static inline void dwc2_gadget_incr_frame_num(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_incr_frame_num() argument
118 hs_ep->target_frame += hs_ep->interval; in dwc2_gadget_incr_frame_num()
119 if (hs_ep->target_frame > DSTS_SOFFN_LIMIT) { in dwc2_gadget_incr_frame_num()
120 hs_ep->frame_overrun = true; in dwc2_gadget_incr_frame_num()
121 hs_ep->target_frame &= DSTS_SOFFN_LIMIT; in dwc2_gadget_incr_frame_num()
123 hs_ep->frame_overrun = false; in dwc2_gadget_incr_frame_num()
130 * @hs_ep: The endpoint.
137 static inline void dwc2_gadget_dec_frame_num_by_one(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_dec_frame_num_by_one() argument
139 if (hs_ep->target_frame) in dwc2_gadget_dec_frame_num_by_one()
140 hs_ep->target_frame -= 1; in dwc2_gadget_dec_frame_num_by_one()
142 hs_ep->target_frame = DSTS_SOFFN_LIMIT; in dwc2_gadget_dec_frame_num_by_one()
400 * @hs_ep: The endpoint to query.
405 static inline int is_ep_periodic(struct dwc2_hsotg_ep *hs_ep) in is_ep_periodic() argument
407 return hs_ep->periodic; in is_ep_periodic()
413 * @hs_ep: The endpoint for the request
420 struct dwc2_hsotg_ep *hs_ep, in dwc2_hsotg_unmap_dma() argument
425 usb_gadget_unmap_request(&hsotg->gadget, req, hs_ep->dir_in); in dwc2_hsotg_unmap_dma()
479 * @hs_ep: The endpoint we're going to write for.
493 struct dwc2_hsotg_ep *hs_ep, in dwc2_hsotg_write_fifo() argument
496 bool periodic = is_ep_periodic(hs_ep); in dwc2_hsotg_write_fifo()
499 int to_write = hs_ep->size_loaded; in dwc2_hsotg_write_fifo()
505 to_write -= (buf_pos - hs_ep->last_load); in dwc2_hsotg_write_fifo()
512 u32 epsize = dwc2_readl(hsotg, DIEPTSIZ(hs_ep->index)); in dwc2_hsotg_write_fifo()
527 if (hs_ep->fifo_load != 0) { in dwc2_hsotg_write_fifo()
534 hs_ep->size_loaded, hs_ep->fifo_load, hs_ep->fifo_size); in dwc2_hsotg_write_fifo()
537 size_done = hs_ep->size_loaded - size_left; in dwc2_hsotg_write_fifo()
540 can_write = hs_ep->fifo_load - size_done; in dwc2_hsotg_write_fifo()
544 can_write = hs_ep->fifo_size - can_write; in dwc2_hsotg_write_fifo()
552 } else if (hsotg->dedicated_fifos && hs_ep->index != 0) { in dwc2_hsotg_write_fifo()
554 DTXFSTS(hs_ep->fifo_index)); in dwc2_hsotg_write_fifo()
572 max_transfer = hs_ep->ep.maxpacket * hs_ep->mc; in dwc2_hsotg_write_fifo()
636 hs_ep->total_data += to_write; in dwc2_hsotg_write_fifo()
639 hs_ep->fifo_load += to_write; in dwc2_hsotg_write_fifo()
644 dwc2_writel_rep(hsotg, EPFIFO(hs_ep->index), data, to_write); in dwc2_hsotg_write_fifo()
651 * @hs_ep: The endpoint
656 static unsigned int get_ep_limit(struct dwc2_hsotg_ep *hs_ep) in get_ep_limit() argument
658 int index = hs_ep->index; in get_ep_limit()
667 if (hs_ep->dir_in) in get_ep_limit()
682 if ((maxpkt * hs_ep->ep.maxpacket) < maxsize) in get_ep_limit()
683 maxsize = maxpkt * hs_ep->ep.maxpacket; in get_ep_limit()
708 * @hs_ep: The endpoint
714 static unsigned int dwc2_gadget_get_chain_limit(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_get_chain_limit() argument
716 const struct usb_endpoint_descriptor *ep_desc = hs_ep->ep.desc; in dwc2_gadget_get_chain_limit()
717 int is_isoc = hs_ep->isochronous; in dwc2_gadget_get_chain_limit()
719 u32 mps = hs_ep->ep.maxpacket; in dwc2_gadget_get_chain_limit()
720 int dir_in = hs_ep->dir_in; in dwc2_gadget_get_chain_limit()
723 maxsize = (hs_ep->dir_in ? DEV_DMA_ISOC_TX_NBYTES_LIMIT : in dwc2_gadget_get_chain_limit()
730 if (hs_ep->index) in dwc2_gadget_get_chain_limit()
739 * @hs_ep: The endpoint
754 static u32 dwc2_gadget_get_desc_params(struct dwc2_hsotg_ep *hs_ep, u32 *mask) in dwc2_gadget_get_desc_params() argument
756 const struct usb_endpoint_descriptor *ep_desc = hs_ep->ep.desc; in dwc2_gadget_get_desc_params()
757 u32 mps = hs_ep->ep.maxpacket; in dwc2_gadget_get_desc_params()
758 int dir_in = hs_ep->dir_in; in dwc2_gadget_get_desc_params()
761 if (!hs_ep->index && !dir_in) { in dwc2_gadget_get_desc_params()
764 } else if (hs_ep->isochronous) { in dwc2_gadget_get_desc_params()
781 if (hs_ep->index) in dwc2_gadget_get_desc_params()
790 static void dwc2_gadget_fill_nonisoc_xfer_ddma_one(struct dwc2_hsotg_ep *hs_ep, in dwc2_gadget_fill_nonisoc_xfer_ddma_one() argument
796 int dir_in = hs_ep->dir_in; in dwc2_gadget_fill_nonisoc_xfer_ddma_one()
797 u32 mps = hs_ep->ep.maxpacket; in dwc2_gadget_fill_nonisoc_xfer_ddma_one()
803 maxsize = dwc2_gadget_get_desc_params(hs_ep, &mask); in dwc2_gadget_fill_nonisoc_xfer_ddma_one()
805 hs_ep->desc_count = (len / maxsize) + in dwc2_gadget_fill_nonisoc_xfer_ddma_one()
808 hs_ep->desc_count = 1; in dwc2_gadget_fill_nonisoc_xfer_ddma_one()
810 for (i = 0; i < hs_ep->desc_count; ++i) { in dwc2_gadget_fill_nonisoc_xfer_ddma_one()
816 if (!hs_ep->index && !dir_in) in dwc2_gadget_fill_nonisoc_xfer_ddma_one()
831 ((hs_ep->send_zlp && true_last) ? in dwc2_gadget_fill_nonisoc_xfer_ddma_one()
848 * @hs_ep: The endpoint
856 static void dwc2_gadget_config_nonisoc_xfer_ddma(struct dwc2_hsotg_ep *hs_ep, in dwc2_gadget_config_nonisoc_xfer_ddma() argument
861 struct dwc2_dma_desc *desc = hs_ep->desc_list; in dwc2_gadget_config_nonisoc_xfer_ddma()
866 if (hs_ep->req) in dwc2_gadget_config_nonisoc_xfer_ddma()
867 ureq = &hs_ep->req->req; in dwc2_gadget_config_nonisoc_xfer_ddma()
871 dwc2_gadget_fill_nonisoc_xfer_ddma_one(hs_ep, &desc, in dwc2_gadget_config_nonisoc_xfer_ddma()
878 dwc2_gadget_fill_nonisoc_xfer_ddma_one(hs_ep, &desc, in dwc2_gadget_config_nonisoc_xfer_ddma()
881 desc_count += hs_ep->desc_count; in dwc2_gadget_config_nonisoc_xfer_ddma()
884 hs_ep->desc_count = desc_count; in dwc2_gadget_config_nonisoc_xfer_ddma()
889 * @hs_ep: The isochronous endpoint.
898 static int dwc2_gadget_fill_isoc_desc(struct dwc2_hsotg_ep *hs_ep, in dwc2_gadget_fill_isoc_desc() argument
902 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_gadget_fill_isoc_desc()
907 dwc2_gadget_get_desc_params(hs_ep, &mask); in dwc2_gadget_fill_isoc_desc()
909 index = hs_ep->next_desc; in dwc2_gadget_fill_isoc_desc()
910 desc = &hs_ep->desc_list[index]; in dwc2_gadget_fill_isoc_desc()
920 if (hs_ep->next_desc) in dwc2_gadget_fill_isoc_desc()
921 hs_ep->desc_list[index - 1].status &= ~DEV_DMA_L; in dwc2_gadget_fill_isoc_desc()
924 __func__, hs_ep->index, hs_ep->dir_in ? "in" : "out", index); in dwc2_gadget_fill_isoc_desc()
933 if (hs_ep->dir_in) { in dwc2_gadget_fill_isoc_desc()
935 pid = DIV_ROUND_UP(len, hs_ep->ep.maxpacket); in dwc2_gadget_fill_isoc_desc()
940 ((len % hs_ep->ep.maxpacket) ? in dwc2_gadget_fill_isoc_desc()
942 ((hs_ep->target_frame << in dwc2_gadget_fill_isoc_desc()
951 if (hs_ep->dir_in) in dwc2_gadget_fill_isoc_desc()
952 dwc2_gadget_incr_frame_num(hs_ep); in dwc2_gadget_fill_isoc_desc()
955 hs_ep->next_desc++; in dwc2_gadget_fill_isoc_desc()
956 if (hs_ep->next_desc >= MAX_DMA_DESC_NUM_HS_ISOC) in dwc2_gadget_fill_isoc_desc()
957 hs_ep->next_desc = 0; in dwc2_gadget_fill_isoc_desc()
964 * @hs_ep: The isochronous endpoint.
969 static void dwc2_gadget_start_isoc_ddma(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_start_isoc_ddma() argument
971 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_gadget_start_isoc_ddma()
973 int index = hs_ep->index; in dwc2_gadget_start_isoc_ddma()
981 if (list_empty(&hs_ep->queue)) { in dwc2_gadget_start_isoc_ddma()
982 hs_ep->target_frame = TARGET_FRAME_INITIAL; in dwc2_gadget_start_isoc_ddma()
989 desc = &hs_ep->desc_list[i]; in dwc2_gadget_start_isoc_ddma()
995 hs_ep->next_desc = 0; in dwc2_gadget_start_isoc_ddma()
996 list_for_each_entry_safe(hs_req, treq, &hs_ep->queue, queue) { in dwc2_gadget_start_isoc_ddma()
1003 ret = dwc2_gadget_fill_isoc_desc(hs_ep, dma_addr, in dwc2_gadget_start_isoc_ddma()
1009 hs_ep->compl_desc = 0; in dwc2_gadget_start_isoc_ddma()
1010 depctl = hs_ep->dir_in ? DIEPCTL(index) : DOEPCTL(index); in dwc2_gadget_start_isoc_ddma()
1011 dma_reg = hs_ep->dir_in ? DIEPDMA(index) : DOEPDMA(index); in dwc2_gadget_start_isoc_ddma()
1014 dwc2_writel(hsotg, hs_ep->desc_list_dma, dma_reg); in dwc2_gadget_start_isoc_ddma()
1024 * @hs_ep: The endpoint to process a request for
1032 struct dwc2_hsotg_ep *hs_ep, in dwc2_hsotg_start_req() argument
1037 int index = hs_ep->index; in dwc2_hsotg_start_req()
1038 int dir_in = hs_ep->dir_in; in dwc2_hsotg_start_req()
1049 if (hs_ep->req && !continuing) { in dwc2_hsotg_start_req()
1053 } else if (hs_ep->req != hs_req && continuing) { in dwc2_hsotg_start_req()
1067 hs_ep->dir_in ? "in" : "out"); in dwc2_hsotg_start_req()
1082 maxreq = get_ep_limit(hs_ep); in dwc2_hsotg_start_req()
1084 maxreq = dwc2_gadget_get_chain_limit(hs_ep); in dwc2_hsotg_start_req()
1087 int round = maxreq % hs_ep->ep.maxpacket; in dwc2_hsotg_start_req()
1100 packets = DIV_ROUND_UP(length, hs_ep->ep.maxpacket); in dwc2_hsotg_start_req()
1105 if (hs_ep->isochronous) in dwc2_hsotg_start_req()
1118 if ((ureq->length >= hs_ep->ep.maxpacket) && in dwc2_hsotg_start_req()
1119 !(ureq->length % hs_ep->ep.maxpacket)) in dwc2_hsotg_start_req()
1120 hs_ep->send_zlp = 1; in dwc2_hsotg_start_req()
1130 hs_ep->req = hs_req; in dwc2_hsotg_start_req()
1134 u32 mps = hs_ep->ep.maxpacket; in dwc2_hsotg_start_req()
1148 dwc2_gadget_config_nonisoc_xfer_ddma(hs_ep, ureq->dma + offset, in dwc2_hsotg_start_req()
1152 dwc2_writel(hsotg, hs_ep->desc_list_dma, dma_reg); in dwc2_hsotg_start_req()
1155 __func__, (u32)hs_ep->desc_list_dma, dma_reg); in dwc2_hsotg_start_req()
1173 if (hs_ep->isochronous && hs_ep->interval == 1) { in dwc2_hsotg_start_req()
1174 hs_ep->target_frame = dwc2_hsotg_read_frameno(hsotg); in dwc2_hsotg_start_req()
1175 dwc2_gadget_incr_frame_num(hs_ep); in dwc2_hsotg_start_req()
1177 if (hs_ep->target_frame & 0x1) in dwc2_hsotg_start_req()
1199 hs_ep->size_loaded = length; in dwc2_hsotg_start_req()
1200 hs_ep->last_load = ureq->actual; in dwc2_hsotg_start_req()
1204 hs_ep->fifo_load = 0; in dwc2_hsotg_start_req()
1206 dwc2_hsotg_write_fifo(hsotg, hs_ep, hs_req); in dwc2_hsotg_start_req()
1224 dwc2_hsotg_ctrl_epint(hsotg, hs_ep->index, hs_ep->dir_in, 1); in dwc2_hsotg_start_req()
1230 * @hs_ep: The endpoint the request is on.
1240 struct dwc2_hsotg_ep *hs_ep, in dwc2_hsotg_map_dma() argument
1245 ret = usb_gadget_map_request(&hsotg->gadget, req, hs_ep->dir_in); in dwc2_hsotg_map_dma()
1259 struct dwc2_hsotg_ep *hs_ep, in dwc2_hsotg_handle_unaligned_buf_start() argument
1271 hs_ep->ep.name, req_buf, hs_req->req.length); in dwc2_hsotg_handle_unaligned_buf_start()
1285 if (hs_ep->dir_in) in dwc2_hsotg_handle_unaligned_buf_start()
1292 struct dwc2_hsotg_ep *hs_ep, in dwc2_hsotg_handle_unaligned_buf_complete() argument
1300 hs_ep->ep.name, hs_req->req.status, hs_req->req.actual); in dwc2_hsotg_handle_unaligned_buf_complete()
1303 if (!hs_ep->dir_in && !hs_req->req.status) in dwc2_hsotg_handle_unaligned_buf_complete()
1316 * @hs_ep: The driver endpoint to check
1321 static bool dwc2_gadget_target_frame_elapsed(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_target_frame_elapsed() argument
1323 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_gadget_target_frame_elapsed()
1324 u32 target_frame = hs_ep->target_frame; in dwc2_gadget_target_frame_elapsed()
1326 bool frame_overrun = hs_ep->frame_overrun; in dwc2_gadget_target_frame_elapsed()
1341 * @hs_ep: the ep descriptor chain is for
1347 struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_set_ep0_desc_chain() argument
1352 hs_ep->desc_list = hsotg->setup_desc[0]; in dwc2_gadget_set_ep0_desc_chain()
1353 hs_ep->desc_list_dma = hsotg->setup_desc_dma[0]; in dwc2_gadget_set_ep0_desc_chain()
1357 hs_ep->desc_list = hsotg->ctrl_in_desc; in dwc2_gadget_set_ep0_desc_chain()
1358 hs_ep->desc_list_dma = hsotg->ctrl_in_desc_dma; in dwc2_gadget_set_ep0_desc_chain()
1361 hs_ep->desc_list = hsotg->ctrl_out_desc; in dwc2_gadget_set_ep0_desc_chain()
1362 hs_ep->desc_list_dma = hsotg->ctrl_out_desc_dma; in dwc2_gadget_set_ep0_desc_chain()
1377 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); in dwc2_hsotg_ep_queue() local
1378 struct dwc2_hsotg *hs = hs_ep->parent; in dwc2_hsotg_ep_queue()
1402 if (hs_ep->isochronous && in dwc2_hsotg_ep_queue()
1403 req->length > (hs_ep->mc * hs_ep->ep.maxpacket)) { in dwc2_hsotg_ep_queue()
1411 if (using_desc_dma(hs) && hs_ep->isochronous) { in dwc2_hsotg_ep_queue()
1412 maxsize = dwc2_gadget_get_desc_params(hs_ep, &mask); in dwc2_hsotg_ep_queue()
1413 if (hs_ep->dir_in && req->length > maxsize) { in dwc2_hsotg_ep_queue()
1419 if (!hs_ep->dir_in && req->length > hs_ep->ep.maxpacket) { in dwc2_hsotg_ep_queue()
1421 req->length, hs_ep->ep.maxpacket); in dwc2_hsotg_ep_queue()
1426 ret = dwc2_hsotg_handle_unaligned_buf_start(hs, hs_ep, hs_req); in dwc2_hsotg_ep_queue()
1432 ret = dwc2_hsotg_map_dma(hs, hs_ep, req); in dwc2_hsotg_ep_queue()
1437 if (using_desc_dma(hs) && !hs_ep->index) { in dwc2_hsotg_ep_queue()
1438 ret = dwc2_gadget_set_ep0_desc_chain(hs, hs_ep); in dwc2_hsotg_ep_queue()
1443 first = list_empty(&hs_ep->queue); in dwc2_hsotg_ep_queue()
1444 list_add_tail(&hs_req->queue, &hs_ep->queue); in dwc2_hsotg_ep_queue()
1452 if (using_desc_dma(hs) && hs_ep->isochronous) { in dwc2_hsotg_ep_queue()
1453 if (hs_ep->target_frame != TARGET_FRAME_INITIAL) { in dwc2_hsotg_ep_queue()
1460 dwc2_gadget_fill_isoc_desc(hs_ep, dma_addr, in dwc2_hsotg_ep_queue()
1467 if (!hs_ep->index && !req->length && !hs_ep->dir_in && in dwc2_hsotg_ep_queue()
1469 hs_ep->dir_in = 1; in dwc2_hsotg_ep_queue()
1472 if (!hs_ep->isochronous) { in dwc2_hsotg_ep_queue()
1473 dwc2_hsotg_start_req(hs, hs_ep, hs_req, false); in dwc2_hsotg_ep_queue()
1479 while (dwc2_gadget_target_frame_elapsed(hs_ep)) { in dwc2_hsotg_ep_queue()
1480 dwc2_gadget_incr_frame_num(hs_ep); in dwc2_hsotg_ep_queue()
1487 if (hs_ep->target_frame != TARGET_FRAME_INITIAL) in dwc2_hsotg_ep_queue()
1488 dwc2_hsotg_start_req(hs, hs_ep, hs_req, false); in dwc2_hsotg_ep_queue()
1496 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); in dwc2_hsotg_ep_queue_lock() local
1497 struct dwc2_hsotg *hs = hs_ep->parent; in dwc2_hsotg_ep_queue_lock()
1527 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); in dwc2_hsotg_complete_oursetup() local
1528 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_hsotg_complete_oursetup()
1701 * @hs_ep: The controller endpoint to get
1705 static struct dwc2_hsotg_req *get_ep_head(struct dwc2_hsotg_ep *hs_ep) in get_ep_head() argument
1707 return list_first_entry_or_null(&hs_ep->queue, struct dwc2_hsotg_req, in get_ep_head()
1713 * @hs_ep: Endpoint structure
1719 static void dwc2_gadget_start_next_request(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_start_next_request() argument
1722 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_gadget_start_next_request()
1723 int dir_in = hs_ep->dir_in; in dwc2_gadget_start_next_request()
1727 if (!list_empty(&hs_ep->queue)) { in dwc2_gadget_start_next_request()
1728 hs_req = get_ep_head(hs_ep); in dwc2_gadget_start_next_request()
1729 dwc2_hsotg_start_req(hsotg, hs_ep, hs_req, false); in dwc2_gadget_start_next_request()
1732 if (!hs_ep->isochronous) in dwc2_gadget_start_next_request()
1992 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); in dwc2_hsotg_complete_setup() local
1993 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_hsotg_complete_setup()
2048 struct dwc2_hsotg_ep *hs_ep) in dwc2_hsotg_program_zlp() argument
2051 u8 index = hs_ep->index; in dwc2_hsotg_program_zlp()
2052 u32 epctl_reg = hs_ep->dir_in ? DIEPCTL(index) : DOEPCTL(index); in dwc2_hsotg_program_zlp()
2053 u32 epsiz_reg = hs_ep->dir_in ? DIEPTSIZ(index) : DOEPTSIZ(index); in dwc2_hsotg_program_zlp()
2055 if (hs_ep->dir_in) in dwc2_hsotg_program_zlp()
2063 dma_addr_t dma = hs_ep->desc_list_dma; in dwc2_hsotg_program_zlp()
2066 dwc2_gadget_set_ep0_desc_chain(hsotg, hs_ep); in dwc2_hsotg_program_zlp()
2068 dwc2_gadget_config_nonisoc_xfer_ddma(hs_ep, dma, 0); in dwc2_hsotg_program_zlp()
2085 * @hs_ep: The endpoint the request was on.
2096 struct dwc2_hsotg_ep *hs_ep, in dwc2_hsotg_complete_request() argument
2106 hs_ep, hs_ep->ep.name, hs_req, result, hs_req->req.complete); in dwc2_hsotg_complete_request()
2117 dwc2_hsotg_unmap_dma(hsotg, hs_ep, hs_req); in dwc2_hsotg_complete_request()
2119 dwc2_hsotg_handle_unaligned_buf_complete(hsotg, hs_ep, hs_req); in dwc2_hsotg_complete_request()
2121 hs_ep->req = NULL; in dwc2_hsotg_complete_request()
2131 usb_gadget_giveback_request(&hs_ep->ep, &hs_req->req); in dwc2_hsotg_complete_request()
2136 if (using_desc_dma(hsotg) && hs_ep->isochronous) in dwc2_hsotg_complete_request()
2145 if (!hs_ep->req && result >= 0) in dwc2_hsotg_complete_request()
2146 dwc2_gadget_start_next_request(hs_ep); in dwc2_hsotg_complete_request()
2151 * @hs_ep: The endpoint the request was on.
2158 static void dwc2_gadget_complete_isoc_request_ddma(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_complete_isoc_request_ddma() argument
2160 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_gadget_complete_isoc_request_ddma()
2166 desc_sts = hs_ep->desc_list[hs_ep->compl_desc].status; in dwc2_gadget_complete_isoc_request_ddma()
2172 hs_req = get_ep_head(hs_ep); in dwc2_gadget_complete_isoc_request_ddma()
2182 mask = hs_ep->dir_in ? DEV_DMA_ISOC_TX_NBYTES_MASK : in dwc2_gadget_complete_isoc_request_ddma()
2190 if (!hs_ep->dir_in && ureq->length & 0x3) in dwc2_gadget_complete_isoc_request_ddma()
2199 dwc2_hsotg_complete_request(hsotg, hs_ep, hs_req, 0); in dwc2_gadget_complete_isoc_request_ddma()
2201 hs_ep->compl_desc++; in dwc2_gadget_complete_isoc_request_ddma()
2202 if (hs_ep->compl_desc > (MAX_DMA_DESC_NUM_HS_ISOC - 1)) in dwc2_gadget_complete_isoc_request_ddma()
2203 hs_ep->compl_desc = 0; in dwc2_gadget_complete_isoc_request_ddma()
2204 desc_sts = hs_ep->desc_list[hs_ep->compl_desc].status; in dwc2_gadget_complete_isoc_request_ddma()
2210 * @hs_ep: The isochronous endpoint.
2217 static void dwc2_gadget_handle_isoc_bna(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_handle_isoc_bna() argument
2219 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_gadget_handle_isoc_bna()
2221 if (!hs_ep->dir_in) in dwc2_gadget_handle_isoc_bna()
2223 dwc2_hsotg_complete_request(hsotg, hs_ep, get_ep_head(hs_ep), 0); in dwc2_gadget_handle_isoc_bna()
2225 hs_ep->target_frame = TARGET_FRAME_INITIAL; in dwc2_gadget_handle_isoc_bna()
2226 hs_ep->next_desc = 0; in dwc2_gadget_handle_isoc_bna()
2227 hs_ep->compl_desc = 0; in dwc2_gadget_handle_isoc_bna()
2242 struct dwc2_hsotg_ep *hs_ep = hsotg->eps_out[ep_idx]; in dwc2_hsotg_rx_data() local
2243 struct dwc2_hsotg_req *hs_req = hs_ep->req; in dwc2_hsotg_rx_data()
2280 hs_ep->total_data += to_read; in dwc2_hsotg_rx_data()
2328 * @hs_ep - The endpoint on which transfer went
2333 static unsigned int dwc2_gadget_get_xfersize_ddma(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_get_xfersize_ddma() argument
2335 const struct usb_endpoint_descriptor *ep_desc = hs_ep->ep.desc; in dwc2_gadget_get_xfersize_ddma()
2336 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_gadget_get_xfersize_ddma()
2339 struct dwc2_dma_desc *desc = hs_ep->desc_list; in dwc2_gadget_get_xfersize_ddma()
2342 u32 mps = hs_ep->ep.maxpacket; in dwc2_gadget_get_xfersize_ddma()
2343 int dir_in = hs_ep->dir_in; in dwc2_gadget_get_xfersize_ddma()
2349 if (hs_ep->index) in dwc2_gadget_get_xfersize_ddma()
2353 for (i = 0; i < hs_ep->desc_count; ++i) { in dwc2_gadget_get_xfersize_ddma()
2383 struct dwc2_hsotg_ep *hs_ep = hsotg->eps_out[epnum]; in dwc2_hsotg_handle_outdone() local
2384 struct dwc2_hsotg_req *hs_req = hs_ep->req; in dwc2_hsotg_handle_outdone()
2396 dwc2_hsotg_complete_request(hsotg, hs_ep, hs_req, 0); in dwc2_hsotg_handle_outdone()
2402 size_left = dwc2_gadget_get_xfersize_ddma(hs_ep); in dwc2_hsotg_handle_outdone()
2416 size_done = hs_ep->size_loaded - size_left; in dwc2_hsotg_handle_outdone()
2417 size_done += hs_ep->last_load; in dwc2_hsotg_handle_outdone()
2424 dwc2_hsotg_start_req(hsotg, hs_ep, hs_req, true); in dwc2_hsotg_handle_outdone()
2451 if (hs_ep->isochronous && hs_ep->interval == 1) in dwc2_hsotg_handle_outdone()
2453 else if (hs_ep->isochronous && hs_ep->interval > 1) in dwc2_hsotg_handle_outdone()
2454 dwc2_gadget_incr_frame_num(hs_ep); in dwc2_hsotg_handle_outdone()
2458 if (!using_desc_dma(hsotg) && hs_ep->isochronous) in dwc2_hsotg_handle_outdone()
2461 dwc2_hsotg_complete_request(hsotg, hs_ep, hs_req, result); in dwc2_hsotg_handle_outdone()
2584 struct dwc2_hsotg_ep *hs_ep; in dwc2_hsotg_set_ep_maxpacket() local
2587 hs_ep = index_to_ep(hsotg, ep, dir_in); in dwc2_hsotg_set_ep_maxpacket()
2588 if (!hs_ep) in dwc2_hsotg_set_ep_maxpacket()
2598 hs_ep->ep.maxpacket = mps_bytes; in dwc2_hsotg_set_ep_maxpacket()
2599 hs_ep->mc = 1; in dwc2_hsotg_set_ep_maxpacket()
2603 hs_ep->mc = mc; in dwc2_hsotg_set_ep_maxpacket()
2606 hs_ep->ep.maxpacket = mps; in dwc2_hsotg_set_ep_maxpacket()
2646 * @hs_ep: The driver endpoint to check.
2652 struct dwc2_hsotg_ep *hs_ep) in dwc2_hsotg_trytx() argument
2654 struct dwc2_hsotg_req *hs_req = hs_ep->req; in dwc2_hsotg_trytx()
2656 if (!hs_ep->dir_in || !hs_req) { in dwc2_hsotg_trytx()
2661 if (hs_ep->index != 0) in dwc2_hsotg_trytx()
2662 dwc2_hsotg_ctrl_epint(hsotg, hs_ep->index, in dwc2_hsotg_trytx()
2663 hs_ep->dir_in, 0); in dwc2_hsotg_trytx()
2669 hs_ep->index); in dwc2_hsotg_trytx()
2670 return dwc2_hsotg_write_fifo(hsotg, hs_ep, hs_req); in dwc2_hsotg_trytx()
2679 * @hs_ep: The endpoint that has just completed.
2685 struct dwc2_hsotg_ep *hs_ep) in dwc2_hsotg_complete_in() argument
2687 struct dwc2_hsotg_req *hs_req = hs_ep->req; in dwc2_hsotg_complete_in()
2688 u32 epsize = dwc2_readl(hsotg, DIEPTSIZ(hs_ep->index)); in dwc2_hsotg_complete_in()
2697 if (hs_ep->index == 0 && hsotg->ep0_state == DWC2_EP0_STATUS_IN) { in dwc2_hsotg_complete_in()
2704 hs_ep->dir_in = 0; in dwc2_hsotg_complete_in()
2706 dwc2_hsotg_complete_request(hsotg, hs_ep, hs_req, 0); in dwc2_hsotg_complete_in()
2732 size_left = dwc2_gadget_get_xfersize_ddma(hs_ep); in dwc2_hsotg_complete_in()
2740 size_done = hs_ep->size_loaded - size_left; in dwc2_hsotg_complete_in()
2741 size_done += hs_ep->last_load; in dwc2_hsotg_complete_in()
2753 dwc2_hsotg_start_req(hsotg, hs_ep, hs_req, true); in dwc2_hsotg_complete_in()
2758 if (hs_ep->send_zlp) { in dwc2_hsotg_complete_in()
2759 dwc2_hsotg_program_zlp(hsotg, hs_ep); in dwc2_hsotg_complete_in()
2760 hs_ep->send_zlp = 0; in dwc2_hsotg_complete_in()
2765 if (hs_ep->index == 0 && hsotg->ep0_state == DWC2_EP0_DATA_IN) { in dwc2_hsotg_complete_in()
2771 dwc2_hsotg_complete_request(hsotg, hs_ep, hs_req, 0); in dwc2_hsotg_complete_in()
2804 * @hs_ep: The endpoint on which interrupt is asserted.
2815 static void dwc2_gadget_handle_ep_disabled(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_handle_ep_disabled() argument
2817 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_gadget_handle_ep_disabled()
2819 unsigned char idx = hs_ep->index; in dwc2_gadget_handle_ep_disabled()
2820 int dir_in = hs_ep->dir_in; in dwc2_gadget_handle_ep_disabled()
2829 dwc2_hsotg_txfifo_flush(hsotg, hs_ep->fifo_index); in dwc2_gadget_handle_ep_disabled()
2831 if (hs_ep->isochronous) { in dwc2_gadget_handle_ep_disabled()
2832 dwc2_hsotg_complete_in(hsotg, hs_ep); in dwc2_gadget_handle_ep_disabled()
2850 if (!hs_ep->isochronous) in dwc2_gadget_handle_ep_disabled()
2853 if (list_empty(&hs_ep->queue)) { in dwc2_gadget_handle_ep_disabled()
2855 __func__, hs_ep); in dwc2_gadget_handle_ep_disabled()
2860 hs_req = get_ep_head(hs_ep); in dwc2_gadget_handle_ep_disabled()
2862 dwc2_hsotg_complete_request(hsotg, hs_ep, hs_req, in dwc2_gadget_handle_ep_disabled()
2864 dwc2_gadget_incr_frame_num(hs_ep); in dwc2_gadget_handle_ep_disabled()
2867 } while (dwc2_gadget_target_frame_elapsed(hs_ep)); in dwc2_gadget_handle_ep_disabled()
2869 dwc2_gadget_start_next_request(hs_ep); in dwc2_gadget_handle_ep_disabled()
2925 * @hs_ep: The endpoint on which interrupt is asserted.
2937 static void dwc2_gadget_handle_nak(struct dwc2_hsotg_ep *hs_ep) in dwc2_gadget_handle_nak() argument
2939 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_gadget_handle_nak()
2940 int dir_in = hs_ep->dir_in; in dwc2_gadget_handle_nak()
2942 if (!dir_in || !hs_ep->isochronous) in dwc2_gadget_handle_nak()
2945 if (hs_ep->target_frame == TARGET_FRAME_INITIAL) { in dwc2_gadget_handle_nak()
2948 hs_ep->target_frame = hsotg->frame_number; in dwc2_gadget_handle_nak()
2949 dwc2_gadget_incr_frame_num(hs_ep); in dwc2_gadget_handle_nak()
2958 hs_ep->target_frame &= ~hs_ep->interval + 1; in dwc2_gadget_handle_nak()
2963 dwc2_gadget_incr_frame_num(hs_ep); in dwc2_gadget_handle_nak()
2964 dwc2_gadget_dec_frame_num_by_one(hs_ep); in dwc2_gadget_handle_nak()
2967 dwc2_gadget_start_isoc_ddma(hs_ep); in dwc2_gadget_handle_nak()
2971 hs_ep->target_frame = hsotg->frame_number; in dwc2_gadget_handle_nak()
2972 if (hs_ep->interval > 1) { in dwc2_gadget_handle_nak()
2974 DIEPCTL(hs_ep->index)); in dwc2_gadget_handle_nak()
2975 if (hs_ep->target_frame & 0x1) in dwc2_gadget_handle_nak()
2980 dwc2_writel(hsotg, ctrl, DIEPCTL(hs_ep->index)); in dwc2_gadget_handle_nak()
2983 dwc2_hsotg_complete_request(hsotg, hs_ep, in dwc2_gadget_handle_nak()
2984 get_ep_head(hs_ep), 0); in dwc2_gadget_handle_nak()
2988 dwc2_gadget_incr_frame_num(hs_ep); in dwc2_gadget_handle_nak()
3002 struct dwc2_hsotg_ep *hs_ep = index_to_ep(hsotg, idx, dir_in); in dwc2_hsotg_epint() local
3013 if (!hs_ep) { in dwc2_hsotg_epint()
3032 if (using_desc_dma(hsotg) && idx == 0 && !hs_ep->dir_in && in dwc2_hsotg_epint()
3043 if (using_desc_dma(hsotg) && hs_ep->isochronous) { in dwc2_hsotg_epint()
3046 dwc2_gadget_complete_isoc_request_ddma(hs_ep); in dwc2_hsotg_epint()
3053 if (hs_ep->isochronous && hs_ep->interval > 1) in dwc2_hsotg_epint()
3054 dwc2_gadget_incr_frame_num(hs_ep); in dwc2_hsotg_epint()
3056 dwc2_hsotg_complete_in(hsotg, hs_ep); in dwc2_hsotg_epint()
3060 if (idx == 0 && !hs_ep->req) in dwc2_hsotg_epint()
3067 if (hs_ep->isochronous && hs_ep->interval > 1) in dwc2_hsotg_epint()
3068 dwc2_gadget_incr_frame_num(hs_ep); in dwc2_hsotg_epint()
3075 dwc2_gadget_handle_ep_disabled(hs_ep); in dwc2_hsotg_epint()
3078 dwc2_gadget_handle_out_token_ep_disabled(hs_ep); in dwc2_hsotg_epint()
3081 dwc2_gadget_handle_nak(hs_ep); in dwc2_hsotg_epint()
3133 if (hs_ep->isochronous) in dwc2_hsotg_epint()
3134 dwc2_gadget_handle_isoc_bna(hs_ep); in dwc2_hsotg_epint()
3137 if (dir_in && !hs_ep->isochronous) { in dwc2_hsotg_epint()
3156 dwc2_hsotg_trytx(hsotg, hs_ep); in dwc2_hsotg_epint()
3586 struct dwc2_hsotg_ep *hs_ep; in dwc2_gadget_handle_incomplete_isoc_in() local
3596 hs_ep = hsotg->eps_in[idx]; in dwc2_gadget_handle_incomplete_isoc_in()
3598 if ((BIT(idx) & ~daintmsk) || !hs_ep->isochronous) in dwc2_gadget_handle_incomplete_isoc_in()
3603 dwc2_gadget_target_frame_elapsed(hs_ep)) { in dwc2_gadget_handle_incomplete_isoc_in()
3633 struct dwc2_hsotg_ep *hs_ep; in dwc2_gadget_handle_incomplete_isoc_out() local
3642 hs_ep = hsotg->eps_out[idx]; in dwc2_gadget_handle_incomplete_isoc_out()
3644 if ((BIT(idx) & ~daintmsk) || !hs_ep->isochronous) in dwc2_gadget_handle_incomplete_isoc_out()
3649 dwc2_gadget_target_frame_elapsed(hs_ep)) { in dwc2_gadget_handle_incomplete_isoc_out()
3805 struct dwc2_hsotg_ep *hs_ep; in dwc2_hsotg_irq() local
3816 hs_ep = hsotg->eps_out[idx]; in dwc2_hsotg_irq()
3824 if ((epctrl & DXEPCTL_EPENA) && hs_ep->isochronous) { in dwc2_hsotg_irq()
3832 if (hs_ep->halted) { in dwc2_hsotg_irq()
3876 struct dwc2_hsotg_ep *hs_ep) in dwc2_hsotg_ep_stop_xfr() argument
3881 epctrl_reg = hs_ep->dir_in ? DIEPCTL(hs_ep->index) : in dwc2_hsotg_ep_stop_xfr()
3882 DOEPCTL(hs_ep->index); in dwc2_hsotg_ep_stop_xfr()
3883 epint_reg = hs_ep->dir_in ? DIEPINT(hs_ep->index) : in dwc2_hsotg_ep_stop_xfr()
3884 DOEPINT(hs_ep->index); in dwc2_hsotg_ep_stop_xfr()
3887 hs_ep->name); in dwc2_hsotg_ep_stop_xfr()
3889 if (hs_ep->dir_in) { in dwc2_hsotg_ep_stop_xfr()
3890 if (hsotg->dedicated_fifos || hs_ep->periodic) { in dwc2_hsotg_ep_stop_xfr()
3929 if (hs_ep->dir_in) { in dwc2_hsotg_ep_stop_xfr()
3932 if (hsotg->dedicated_fifos || hs_ep->periodic) in dwc2_hsotg_ep_stop_xfr()
3933 fifo_index = hs_ep->fifo_index; in dwc2_hsotg_ep_stop_xfr()
3941 if (!hsotg->dedicated_fifos && !hs_ep->periodic) in dwc2_hsotg_ep_stop_xfr()
3960 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); in dwc2_hsotg_ep_enable() local
3961 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_hsotg_ep_enable()
3963 unsigned int index = hs_ep->index; in dwc2_hsotg_ep_enable()
3987 if (dir_in != hs_ep->dir_in) { in dwc2_hsotg_ep_enable()
4026 if (using_desc_dma(hsotg) && !hs_ep->desc_list) { in dwc2_hsotg_ep_enable()
4027 hs_ep->desc_list = dmam_alloc_coherent(hsotg->dev, in dwc2_hsotg_ep_enable()
4029 &hs_ep->desc_list_dma, GFP_ATOMIC); in dwc2_hsotg_ep_enable()
4030 if (!hs_ep->desc_list) { in dwc2_hsotg_ep_enable()
4048 dwc2_hsotg_set_ep_maxpacket(hsotg, hs_ep->index, mps, mc, dir_in); in dwc2_hsotg_ep_enable()
4051 hs_ep->isochronous = 0; in dwc2_hsotg_ep_enable()
4052 hs_ep->periodic = 0; in dwc2_hsotg_ep_enable()
4053 hs_ep->halted = 0; in dwc2_hsotg_ep_enable()
4054 hs_ep->interval = desc->bInterval; in dwc2_hsotg_ep_enable()
4060 hs_ep->isochronous = 1; in dwc2_hsotg_ep_enable()
4061 hs_ep->interval = 1 << (desc->bInterval - 1); in dwc2_hsotg_ep_enable()
4062 hs_ep->target_frame = TARGET_FRAME_INITIAL; in dwc2_hsotg_ep_enable()
4063 hs_ep->next_desc = 0; in dwc2_hsotg_ep_enable()
4064 hs_ep->compl_desc = 0; in dwc2_hsotg_ep_enable()
4066 hs_ep->periodic = 1; in dwc2_hsotg_ep_enable()
4083 hs_ep->periodic = 1; in dwc2_hsotg_ep_enable()
4086 hs_ep->interval = 1 << (desc->bInterval - 1); in dwc2_hsotg_ep_enable()
4105 size = hs_ep->ep.maxpacket * hs_ep->mc; in dwc2_hsotg_ep_enable()
4128 hs_ep->fifo_index = fifo_index; in dwc2_hsotg_ep_enable()
4129 hs_ep->fifo_size = fifo_size; in dwc2_hsotg_ep_enable()
4133 if (index && !hs_ep->isochronous) in dwc2_hsotg_ep_enable()
4143 hs_ep->isochronous && dir_in) { in dwc2_hsotg_ep_enable()
4171 if (ret && using_desc_dma(hsotg) && hs_ep->desc_list) { in dwc2_hsotg_ep_enable()
4174 hs_ep->desc_list, hs_ep->desc_list_dma); in dwc2_hsotg_ep_enable()
4175 hs_ep->desc_list = NULL; in dwc2_hsotg_ep_enable()
4187 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); in dwc2_hsotg_ep_disable() local
4188 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_hsotg_ep_disable()
4189 int dir_in = hs_ep->dir_in; in dwc2_hsotg_ep_disable()
4190 int index = hs_ep->index; in dwc2_hsotg_ep_disable()
4211 dwc2_hsotg_ep_stop_xfr(hsotg, hs_ep); in dwc2_hsotg_ep_disable()
4221 dwc2_hsotg_ctrl_epint(hsotg, hs_ep->index, hs_ep->dir_in, 0); in dwc2_hsotg_ep_disable()
4224 kill_all_requests(hsotg, hs_ep, -ESHUTDOWN); in dwc2_hsotg_ep_disable()
4226 hsotg->fifo_map &= ~(1 << hs_ep->fifo_index); in dwc2_hsotg_ep_disable()
4227 hs_ep->fifo_index = 0; in dwc2_hsotg_ep_disable()
4228 hs_ep->fifo_size = 0; in dwc2_hsotg_ep_disable()
4235 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); in dwc2_hsotg_ep_disable_lock() local
4236 struct dwc2_hsotg *hsotg = hs_ep->parent; in dwc2_hsotg_ep_disable_lock()
4271 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); in dwc2_hsotg_ep_dequeue() local
4272 struct dwc2_hsotg *hs = hs_ep->parent; in dwc2_hsotg_ep_dequeue()
4279 if (!on_list(hs_ep, hs_req)) { in dwc2_hsotg_ep_dequeue()
4285 if (req == &hs_ep->req->req) in dwc2_hsotg_ep_dequeue()
4286 dwc2_hsotg_ep_stop_xfr(hs, hs_ep); in dwc2_hsotg_ep_dequeue()
4288 dwc2_hsotg_complete_request(hs, hs_ep, hs_req, -ECONNRESET); in dwc2_hsotg_ep_dequeue()
4306 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); in dwc2_hsotg_ep_sethalt() local
4307 struct dwc2_hsotg *hs = hs_ep->parent; in dwc2_hsotg_ep_sethalt()
4308 int index = hs_ep->index; in dwc2_hsotg_ep_sethalt()
4324 if (hs_ep->isochronous) { in dwc2_hsotg_ep_sethalt()
4329 if (!now && value && !list_empty(&hs_ep->queue)) { in dwc2_hsotg_ep_sethalt()
4335 if (hs_ep->dir_in) { in dwc2_hsotg_ep_sethalt()
4369 hs_ep->halted = value; in dwc2_hsotg_ep_sethalt()
4380 struct dwc2_hsotg_ep *hs_ep = our_ep(ep); in dwc2_hsotg_ep_sethalt_lock() local
4381 struct dwc2_hsotg *hs = hs_ep->parent; in dwc2_hsotg_ep_sethalt_lock()
4677 * @hs_ep: The endpoint to be initialised.
4686 struct dwc2_hsotg_ep *hs_ep, in dwc2_hsotg_initep() argument
4699 hs_ep->dir_in = dir_in; in dwc2_hsotg_initep()
4700 hs_ep->index = epnum; in dwc2_hsotg_initep()
4702 snprintf(hs_ep->name, sizeof(hs_ep->name), "ep%d%s", epnum, dir); in dwc2_hsotg_initep()
4704 INIT_LIST_HEAD(&hs_ep->queue); in dwc2_hsotg_initep()
4705 INIT_LIST_HEAD(&hs_ep->ep.ep_list); in dwc2_hsotg_initep()
4709 list_add_tail(&hs_ep->ep.ep_list, &hsotg->gadget.ep_list); in dwc2_hsotg_initep()
4711 hs_ep->parent = hsotg; in dwc2_hsotg_initep()
4712 hs_ep->ep.name = hs_ep->name; in dwc2_hsotg_initep()
4715 usb_ep_set_maxpacket_limit(&hs_ep->ep, 8); in dwc2_hsotg_initep()
4717 usb_ep_set_maxpacket_limit(&hs_ep->ep, in dwc2_hsotg_initep()
4719 hs_ep->ep.ops = &dwc2_hsotg_ep_ops; in dwc2_hsotg_initep()
4722 hs_ep->ep.caps.type_control = true; in dwc2_hsotg_initep()
4725 hs_ep->ep.caps.type_iso = true; in dwc2_hsotg_initep()
4726 hs_ep->ep.caps.type_bulk = true; in dwc2_hsotg_initep()
4728 hs_ep->ep.caps.type_int = true; in dwc2_hsotg_initep()
4732 hs_ep->ep.caps.dir_in = true; in dwc2_hsotg_initep()
4734 hs_ep->ep.caps.dir_out = true; in dwc2_hsotg_initep()