M480 BSP V3.05.006
The Board Support Package for M480 Series
msc_xfer.c
Go to the documentation of this file.
1/**************************************************************************/
10#include <stdio.h>
11#include <stdlib.h>
12#include <string.h>
13
14#include "NuMicro.h"
15#include "diskio.h" // FATFS header
16#include "usb.h"
17#include "msc.h"
18
19
20static int __tag = 0x10e24388;
21
22
23static void bulk_xfer_done(UTR_T *utr)
24{
25 // msc_debug_msg("BULK XFER done - %d\n", utr->status);
26}
27
28int msc_bulk_transfer(MSC_T *msc, EP_INFO_T *ep, uint8_t *data_buff, int data_len, int timeout_ticks)
29{
30 UTR_T *utr;
31 uint32_t t0;
32 int ret;
33
34 utr = alloc_utr(msc->iface->udev);
35 if (!utr)
37
38 utr->ep = ep;
39 utr->buff = data_buff;
40 utr->data_len = data_len;
41 utr->xfer_len = 0;
42 utr->func = bulk_xfer_done;
43 utr->bIsTransferDone = 0;
44
45 ret = usbh_bulk_xfer(utr);
46 if (ret < 0)
47 return ret;
48
49 t0 = get_ticks();
50 while (utr->bIsTransferDone == 0)
51 {
52 if (get_ticks() - t0 > timeout_ticks)
53 {
54 usbh_quit_utr(utr);
55 free_utr(utr);
56 return USBH_ERR_TIMEOUT;
57 }
58 }
59 ret = utr->status;
60 free_utr(utr);
61 msc_debug_msg(" <BULK> status: %d, xfer_len: %d\n", utr->status, utr->xfer_len);
62
63 return ret;
64}
65
66
67static int do_scsi_command(MSC_T *msc, uint8_t *buff, uint32_t data_len, int bIsDataIn, int timeout_ticks)
68{
69 int ret;
70 struct bulk_cb_wrap *cmd_blk = &msc->cmd_blk; /* MSC Bulk-only command block */
71 struct bulk_cs_wrap *cmd_status = &msc->cmd_status;; /* MSC Bulk-only command status */
72
73 cmd_blk->Signature = MSC_CB_SIGN;
74 cmd_blk->Tag = __tag++;
75 cmd_blk->DataTransferLength = data_len;
76 cmd_blk->Lun = msc->lun;
77
78 ret = msc_bulk_transfer(msc, msc->ep_bulk_out, (uint8_t *)cmd_blk, 31, timeout_ticks);
79 if (ret < 0)
80 return ret;
81
82 msc_debug_msg(" [XFER] MSC CMD OK.\n");
83
84 if (data_len > 0)
85 {
86 if (bIsDataIn)
87 ret = msc_bulk_transfer(msc, msc->ep_bulk_in, buff, data_len, 500);
88 else
89 ret = msc_bulk_transfer(msc, msc->ep_bulk_out, buff, data_len, 500);
90 if (ret < 0)
91 return ret;
92 msc_debug_msg(" [XFER] MSC DATA OK.\n");
93 }
94
95 ret = msc_bulk_transfer(msc, msc->ep_bulk_in, (uint8_t *)cmd_status, 13, timeout_ticks);
96 if (ret < 0)
97 return ret;
98
99 msc_debug_msg(" [XFER] MSC STATUS OK.\n");
100
101 if (cmd_status->Status != 0)
102 {
103 msc_debug_msg(" !! CSW status error.\n");
104 return UMAS_ERR_CMD_STATUS;
105 }
106 msc_debug_msg(" [CSW] status OK.\n");
107
108 msc_debug_msg("SCSI command 0x%0x done.\n", cmd_blk->CDB[0]);
109 return 0;
110}
111
112
113int run_scsi_command(MSC_T *msc, uint8_t *buff, uint32_t data_len, int bIsDataIn, int timeout_ticks)
114{
115 return do_scsi_command(msc, buff, data_len, bIsDataIn, timeout_ticks);
116}
117
118/*** (C) COPYRIGHT 2017 Nuvoton Technology Corp. ***/
119
120
NuMicro peripheral access layer header file.
#define USBH_ERR_TIMEOUT
Definition: usbh_lib.h:46
#define UMAS_ERR_CMD_STATUS
Definition: usbh_lib.h:81
#define USBH_ERR_MEMORY_OUT
Definition: usbh_lib.h:32
uint32_t get_ticks(void)
A function return current tick count.
M480 MCU USB Host mass storage class header.
static int __tag
Definition: msc_xfer.c:20
static void bulk_xfer_done(UTR_T *utr)
Definition: msc_xfer.c:23
static int do_scsi_command(MSC_T *msc, uint8_t *buff, uint32_t data_len, int bIsDataIn, int timeout_ticks)
Definition: msc_xfer.c:67
int msc_bulk_transfer(MSC_T *msc, EP_INFO_T *ep, uint8_t *data_buff, int data_len, int timeout_ticks)
Definition: msc_xfer.c:28
int run_scsi_command(MSC_T *msc, uint8_t *buff, uint32_t data_len, int bIsDataIn, int timeout_ticks)
Definition: msc_xfer.c:113
USB Host library header file.