Browse code

Add source code of the firmware for the IO Board

Pawel Jablonski authored on 05/06/2023 17:01:27
Showing 1 changed files
1 1
new file mode 100644
... ...
@@ -0,0 +1,478 @@
1
+/**
2
+  ******************************************************************************
3
+  * @file    usbd_msc_bot.c
4
+  * @author  MCD Application Team
5
+  * @brief   This file provides all the BOT protocol core functions.
6
+  ******************************************************************************
7
+  * @attention
8
+  *
9
+  * Copyright (c) 2015 STMicroelectronics.
10
+  * All rights reserved.
11
+  *
12
+  * This software is licensed under terms that can be found in the LICENSE file
13
+  * in the root directory of this software component.
14
+  * If no LICENSE file comes with this software, it is provided AS-IS.
15
+  *
16
+  ******************************************************************************
17
+  */
18
+
19
+/* BSPDependencies
20
+- "stm32xxxxx_{eval}{discovery}{nucleo_144}.c"
21
+- "stm32xxxxx_{eval}{discovery}_io.c"
22
+- "stm32xxxxx_{eval}{discovery}{adafruit}_sd.c"
23
+EndBSPDependencies */
24
+
25
+/* Includes ------------------------------------------------------------------*/
26
+#include "usbd_msc_bot.h"
27
+#include "usbd_msc.h"
28
+#include "usbd_msc_scsi.h"
29
+#include "usbd_ioreq.h"
30
+
31
+/** @addtogroup STM32_USB_DEVICE_LIBRARY
32
+  * @{
33
+  */
34
+
35
+
36
+/** @defgroup MSC_BOT
37
+  * @brief BOT protocol module
38
+  * @{
39
+  */
40
+
41
+/** @defgroup MSC_BOT_Private_TypesDefinitions
42
+  * @{
43
+  */
44
+/**
45
+  * @}
46
+  */
47
+
48
+
49
+/** @defgroup MSC_BOT_Private_Defines
50
+  * @{
51
+  */
52
+
53
+/**
54
+  * @}
55
+  */
56
+
57
+
58
+/** @defgroup MSC_BOT_Private_Macros
59
+  * @{
60
+  */
61
+/**
62
+  * @}
63
+  */
64
+
65
+
66
+/** @defgroup MSC_BOT_Private_Variables
67
+  * @{
68
+  */
69
+extern uint8_t MSCInEpAdd;
70
+extern uint8_t MSCOutEpAdd;
71
+/**
72
+  * @}
73
+  */
74
+
75
+
76
+/** @defgroup MSC_BOT_Private_FunctionPrototypes
77
+  * @{
78
+  */
79
+static void MSC_BOT_SendData(USBD_HandleTypeDef *pdev, uint8_t *pbuf, uint32_t len);
80
+static void MSC_BOT_CBW_Decode(USBD_HandleTypeDef *pdev);
81
+static void MSC_BOT_Abort(USBD_HandleTypeDef *pdev);
82
+/**
83
+  * @}
84
+  */
85
+
86
+
87
+/** @defgroup MSC_BOT_Private_Functions
88
+  * @{
89
+  */
90
+
91
+
92
+/**
93
+  * @brief  MSC_BOT_Init
94
+  *         Initialize the BOT Process
95
+  * @param  pdev: device instance
96
+  * @retval None
97
+  */
98
+void MSC_BOT_Init(USBD_HandleTypeDef *pdev)
99
+{
100
+  USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassDataCmsit[pdev->classId];
101
+
102
+#ifdef USE_USBD_COMPOSITE
103
+  /* Get the Endpoints addresses allocated for this class instance */
104
+  MSCInEpAdd  = USBD_CoreGetEPAdd(pdev, USBD_EP_IN, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
105
+  MSCOutEpAdd = USBD_CoreGetEPAdd(pdev, USBD_EP_OUT, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
106
+#endif /* USE_USBD_COMPOSITE */
107
+
108
+  if (hmsc == NULL)
109
+  {
110
+    return;
111
+  }
112
+
113
+  hmsc->bot_state = USBD_BOT_IDLE;
114
+  hmsc->bot_status = USBD_BOT_STATUS_NORMAL;
115
+
116
+  hmsc->scsi_sense_tail = 0U;
117
+  hmsc->scsi_sense_head = 0U;
118
+  hmsc->scsi_medium_state = SCSI_MEDIUM_UNLOCKED;
119
+
120
+  ((USBD_StorageTypeDef *)pdev->pUserData[pdev->classId])->Init(0U);
121
+
122
+  (void)USBD_LL_FlushEP(pdev, MSCOutEpAdd);
123
+  (void)USBD_LL_FlushEP(pdev, MSCInEpAdd);
124
+
125
+  /* Prepare EP to Receive First BOT Cmd */
126
+  (void)USBD_LL_PrepareReceive(pdev, MSCOutEpAdd, (uint8_t *)&hmsc->cbw,
127
+                               USBD_BOT_CBW_LENGTH);
128
+}
129
+
130
+/**
131
+  * @brief  MSC_BOT_Reset
132
+  *         Reset the BOT Machine
133
+  * @param  pdev: device instance
134
+  * @retval  None
135
+  */
136
+void MSC_BOT_Reset(USBD_HandleTypeDef *pdev)
137
+{
138
+  USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassDataCmsit[pdev->classId];
139
+
140
+#ifdef USE_USBD_COMPOSITE
141
+  /* Get the Endpoints addresses allocated for this class instance */
142
+  MSCInEpAdd  = USBD_CoreGetEPAdd(pdev, USBD_EP_IN, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
143
+  MSCOutEpAdd = USBD_CoreGetEPAdd(pdev, USBD_EP_OUT, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
144
+#endif /* USE_USBD_COMPOSITE */
145
+
146
+  if (hmsc == NULL)
147
+  {
148
+    return;
149
+  }
150
+
151
+  hmsc->bot_state  = USBD_BOT_IDLE;
152
+  hmsc->bot_status = USBD_BOT_STATUS_RECOVERY;
153
+
154
+  (void)USBD_LL_ClearStallEP(pdev, MSCInEpAdd);
155
+  (void)USBD_LL_ClearStallEP(pdev, MSCOutEpAdd);
156
+
157
+  /* Prepare EP to Receive First BOT Cmd */
158
+  (void)USBD_LL_PrepareReceive(pdev, MSCOutEpAdd, (uint8_t *)&hmsc->cbw,
159
+                               USBD_BOT_CBW_LENGTH);
160
+}
161
+
162
+/**
163
+  * @brief  MSC_BOT_DeInit
164
+  *         DeInitialize the BOT Machine
165
+  * @param  pdev: device instance
166
+  * @retval None
167
+  */
168
+void MSC_BOT_DeInit(USBD_HandleTypeDef  *pdev)
169
+{
170
+  USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassDataCmsit[pdev->classId];
171
+
172
+  if (hmsc != NULL)
173
+  {
174
+    hmsc->bot_state = USBD_BOT_IDLE;
175
+  }
176
+}
177
+
178
+/**
179
+  * @brief  MSC_BOT_DataIn
180
+  *         Handle BOT IN data stage
181
+  * @param  pdev: device instance
182
+  * @param  epnum: endpoint index
183
+  * @retval None
184
+  */
185
+void MSC_BOT_DataIn(USBD_HandleTypeDef *pdev, uint8_t epnum)
186
+{
187
+  UNUSED(epnum);
188
+
189
+  USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassDataCmsit[pdev->classId];
190
+
191
+  if (hmsc == NULL)
192
+  {
193
+    return;
194
+  }
195
+
196
+  switch (hmsc->bot_state)
197
+  {
198
+    case USBD_BOT_DATA_IN:
199
+      if (SCSI_ProcessCmd(pdev, hmsc->cbw.bLUN, &hmsc->cbw.CB[0]) < 0)
200
+      {
201
+        MSC_BOT_SendCSW(pdev, USBD_CSW_CMD_FAILED);
202
+      }
203
+      break;
204
+
205
+    case USBD_BOT_SEND_DATA:
206
+    case USBD_BOT_LAST_DATA_IN:
207
+      MSC_BOT_SendCSW(pdev, USBD_CSW_CMD_PASSED);
208
+      break;
209
+
210
+    default:
211
+      break;
212
+  }
213
+}
214
+/**
215
+  * @brief  MSC_BOT_DataOut
216
+  *         Process MSC OUT data
217
+  * @param  pdev: device instance
218
+  * @param  epnum: endpoint index
219
+  * @retval None
220
+  */
221
+void MSC_BOT_DataOut(USBD_HandleTypeDef *pdev, uint8_t epnum)
222
+{
223
+  UNUSED(epnum);
224
+
225
+  USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassDataCmsit[pdev->classId];
226
+
227
+  if (hmsc == NULL)
228
+  {
229
+    return;
230
+  }
231
+
232
+  switch (hmsc->bot_state)
233
+  {
234
+    case USBD_BOT_IDLE:
235
+      MSC_BOT_CBW_Decode(pdev);
236
+      break;
237
+
238
+    case USBD_BOT_DATA_OUT:
239
+      if (SCSI_ProcessCmd(pdev, hmsc->cbw.bLUN, &hmsc->cbw.CB[0]) < 0)
240
+      {
241
+        MSC_BOT_SendCSW(pdev, USBD_CSW_CMD_FAILED);
242
+      }
243
+      break;
244
+
245
+    default:
246
+      break;
247
+  }
248
+}
249
+
250
+/**
251
+  * @brief  MSC_BOT_CBW_Decode
252
+  *         Decode the CBW command and set the BOT state machine accordingly
253
+  * @param  pdev: device instance
254
+  * @retval None
255
+  */
256
+static void  MSC_BOT_CBW_Decode(USBD_HandleTypeDef *pdev)
257
+{
258
+  USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassDataCmsit[pdev->classId];
259
+
260
+#ifdef USE_USBD_COMPOSITE
261
+  /* Get the Endpoints addresses allocated for this class instance */
262
+  MSCInEpAdd  = USBD_CoreGetEPAdd(pdev, USBD_EP_IN, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
263
+  MSCOutEpAdd = USBD_CoreGetEPAdd(pdev, USBD_EP_OUT, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
264
+#endif /* USE_USBD_COMPOSITE */
265
+
266
+  if (hmsc == NULL)
267
+  {
268
+    return;
269
+  }
270
+
271
+  hmsc->csw.dTag = hmsc->cbw.dTag;
272
+  hmsc->csw.dDataResidue = hmsc->cbw.dDataLength;
273
+
274
+  if ((USBD_LL_GetRxDataSize(pdev, MSCOutEpAdd) != USBD_BOT_CBW_LENGTH) ||
275
+      (hmsc->cbw.dSignature != USBD_BOT_CBW_SIGNATURE) ||
276
+      (hmsc->cbw.bLUN > 1U) || (hmsc->cbw.bCBLength < 1U) ||
277
+      (hmsc->cbw.bCBLength > 16U))
278
+  {
279
+    SCSI_SenseCode(pdev, hmsc->cbw.bLUN, ILLEGAL_REQUEST, INVALID_CDB);
280
+
281
+    hmsc->bot_status = USBD_BOT_STATUS_ERROR;
282
+    MSC_BOT_Abort(pdev);
283
+  }
284
+  else
285
+  {
286
+    if (SCSI_ProcessCmd(pdev, hmsc->cbw.bLUN, &hmsc->cbw.CB[0]) < 0)
287
+    {
288
+      if (hmsc->bot_state == USBD_BOT_NO_DATA)
289
+      {
290
+        MSC_BOT_SendCSW(pdev, USBD_CSW_CMD_FAILED);
291
+      }
292
+      else
293
+      {
294
+        MSC_BOT_Abort(pdev);
295
+      }
296
+    }
297
+    /* Burst xfer handled internally */
298
+    else if ((hmsc->bot_state != USBD_BOT_DATA_IN) &&
299
+             (hmsc->bot_state != USBD_BOT_DATA_OUT) &&
300
+             (hmsc->bot_state != USBD_BOT_LAST_DATA_IN))
301
+    {
302
+      if (hmsc->bot_data_length > 0U)
303
+      {
304
+        MSC_BOT_SendData(pdev, hmsc->bot_data, hmsc->bot_data_length);
305
+      }
306
+      else if (hmsc->bot_data_length == 0U)
307
+      {
308
+        MSC_BOT_SendCSW(pdev, USBD_CSW_CMD_PASSED);
309
+      }
310
+      else
311
+      {
312
+        MSC_BOT_Abort(pdev);
313
+      }
314
+    }
315
+    else
316
+    {
317
+      return;
318
+    }
319
+  }
320
+}
321
+
322
+/**
323
+  * @brief  MSC_BOT_SendData
324
+  *         Send the requested data
325
+  * @param  pdev: device instance
326
+  * @param  buf: pointer to data buffer
327
+  * @param  len: Data Length
328
+  * @retval None
329
+  */
330
+static void  MSC_BOT_SendData(USBD_HandleTypeDef *pdev, uint8_t *pbuf, uint32_t len)
331
+{
332
+  USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassDataCmsit[pdev->classId];
333
+
334
+  uint32_t length;
335
+
336
+#ifdef USE_USBD_COMPOSITE
337
+  /* Get the Endpoints addresses allocated for this class instance */
338
+  MSCInEpAdd  = USBD_CoreGetEPAdd(pdev, USBD_EP_IN, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
339
+  MSCOutEpAdd = USBD_CoreGetEPAdd(pdev, USBD_EP_OUT, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
340
+#endif /* USE_USBD_COMPOSITE */
341
+
342
+  if (hmsc == NULL)
343
+  {
344
+    return;
345
+  }
346
+
347
+  length = MIN(hmsc->cbw.dDataLength, len);
348
+
349
+  hmsc->csw.dDataResidue -= len;
350
+  hmsc->csw.bStatus = USBD_CSW_CMD_PASSED;
351
+  hmsc->bot_state = USBD_BOT_SEND_DATA;
352
+
353
+  (void)USBD_LL_Transmit(pdev, MSCInEpAdd, pbuf, length);
354
+}
355
+
356
+/**
357
+  * @brief  MSC_BOT_SendCSW
358
+  *         Send the Command Status Wrapper
359
+  * @param  pdev: device instance
360
+  * @param  status : CSW status
361
+  * @retval None
362
+  */
363
+void  MSC_BOT_SendCSW(USBD_HandleTypeDef *pdev, uint8_t CSW_Status)
364
+{
365
+  USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassDataCmsit[pdev->classId];
366
+
367
+#ifdef USE_USBD_COMPOSITE
368
+  /* Get the Endpoints addresses allocated for this class instance */
369
+  MSCInEpAdd  = USBD_CoreGetEPAdd(pdev, USBD_EP_IN, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
370
+  MSCOutEpAdd = USBD_CoreGetEPAdd(pdev, USBD_EP_OUT, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
371
+#endif /* USE_USBD_COMPOSITE */
372
+
373
+  if (hmsc == NULL)
374
+  {
375
+    return;
376
+  }
377
+
378
+  hmsc->csw.dSignature = USBD_BOT_CSW_SIGNATURE;
379
+  hmsc->csw.bStatus = CSW_Status;
380
+  hmsc->bot_state = USBD_BOT_IDLE;
381
+
382
+  (void)USBD_LL_Transmit(pdev, MSCInEpAdd, (uint8_t *)&hmsc->csw,
383
+                         USBD_BOT_CSW_LENGTH);
384
+
385
+  /* Prepare EP to Receive next Cmd */
386
+  (void)USBD_LL_PrepareReceive(pdev, MSCOutEpAdd, (uint8_t *)&hmsc->cbw,
387
+                               USBD_BOT_CBW_LENGTH);
388
+}
389
+
390
+/**
391
+  * @brief  MSC_BOT_Abort
392
+  *         Abort the current transfer
393
+  * @param  pdev: device instance
394
+  * @retval status
395
+  */
396
+
397
+static void  MSC_BOT_Abort(USBD_HandleTypeDef *pdev)
398
+{
399
+  USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassDataCmsit[pdev->classId];
400
+
401
+#ifdef USE_USBD_COMPOSITE
402
+  /* Get the Endpoints addresses allocated for this class instance */
403
+  MSCInEpAdd  = USBD_CoreGetEPAdd(pdev, USBD_EP_IN, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
404
+  MSCOutEpAdd = USBD_CoreGetEPAdd(pdev, USBD_EP_OUT, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
405
+#endif /* USE_USBD_COMPOSITE */
406
+
407
+  if (hmsc == NULL)
408
+  {
409
+    return;
410
+  }
411
+
412
+  if ((hmsc->cbw.bmFlags == 0U) &&
413
+      (hmsc->cbw.dDataLength != 0U) &&
414
+      (hmsc->bot_status == USBD_BOT_STATUS_NORMAL))
415
+  {
416
+    (void)USBD_LL_StallEP(pdev, MSCOutEpAdd);
417
+  }
418
+
419
+  (void)USBD_LL_StallEP(pdev, MSCInEpAdd);
420
+
421
+  if (hmsc->bot_status == USBD_BOT_STATUS_ERROR)
422
+  {
423
+    (void)USBD_LL_StallEP(pdev, MSCInEpAdd);
424
+    (void)USBD_LL_StallEP(pdev, MSCOutEpAdd);
425
+  }
426
+}
427
+
428
+/**
429
+  * @brief  MSC_BOT_CplClrFeature
430
+  *         Complete the clear feature request
431
+  * @param  pdev: device instance
432
+  * @param  epnum: endpoint index
433
+  * @retval None
434
+  */
435
+
436
+void  MSC_BOT_CplClrFeature(USBD_HandleTypeDef *pdev, uint8_t epnum)
437
+{
438
+  USBD_MSC_BOT_HandleTypeDef *hmsc = (USBD_MSC_BOT_HandleTypeDef *)pdev->pClassDataCmsit[pdev->classId];
439
+
440
+#ifdef USE_USBD_COMPOSITE
441
+  /* Get the Endpoints addresses allocated for this class instance */
442
+  MSCInEpAdd  = USBD_CoreGetEPAdd(pdev, USBD_EP_IN, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
443
+  MSCOutEpAdd = USBD_CoreGetEPAdd(pdev, USBD_EP_OUT, USBD_EP_TYPE_BULK, (uint8_t)pdev->classId);
444
+#endif /* USE_USBD_COMPOSITE */
445
+
446
+  if (hmsc == NULL)
447
+  {
448
+    return;
449
+  }
450
+
451
+  if (hmsc->bot_status == USBD_BOT_STATUS_ERROR) /* Bad CBW Signature */
452
+  {
453
+    (void)USBD_LL_StallEP(pdev, MSCInEpAdd);
454
+    (void)USBD_LL_StallEP(pdev, MSCOutEpAdd);
455
+  }
456
+  else if (((epnum & 0x80U) == 0x80U) && (hmsc->bot_status != USBD_BOT_STATUS_RECOVERY))
457
+  {
458
+    MSC_BOT_SendCSW(pdev, USBD_CSW_CMD_FAILED);
459
+  }
460
+  else
461
+  {
462
+    return;
463
+  }
464
+}
465
+/**
466
+  * @}
467
+  */
468
+
469
+
470
+/**
471
+  * @}
472
+  */
473
+
474
+
475
+/**
476
+  * @}
477
+  */
478
+