USB Component  Version 6.6
MDK-Professional Middleware for USB Device and Host
 All Data Structures Functions Variables Enumerations Enumerator Groups Pages
User API

User API reference of the Mass Storage Class. More...

Functions

void USBD_MSCn_Initialize (void)
 Called during USBD_Initialize to initialize the USB MSC class instance.
 
void USBD_MSCn_Uninitialize (void)
 Called during USBD_Uninitialize to de-initialize the USB MSC class instance.
 
bool USBD_MSCn_GetCacheInfo (uint32_t *buffer, uint32_t *size)
 Get cache information.
 
bool USBD_MSCn_GetMediaCapacity (uint32_t *block_count, uint32_t *block_size)
 Get media capacity.
 
bool USBD_MSCn_Read (uint32_t lba, uint32_t cnt, uint8_t *buf)
 Read data from media.
 
bool USBD_MSCn_Write (uint32_t lba, uint32_t cnt, const uint8_t *buf)
 Write data to media.
 
uint32_t USBD_MSCn_CheckMedia (void)
 Check media presence and write protect status.
 
int32_t USBD_MSCn_SetMediaOwnerUSB (void)
 Set USB as media owner.
 
int32_t USBD_MSCn_SetMediaOwnerFS (void)
 Set File System as media owner.
 

Description

User API reference of the Mass Storage Class.

Function Documentation

uint32_t USBD_MSCn_CheckMedia ( void  )

Check media presence and write protect status.

Returns
media presence and write protected status bit 1: write protect bit
  • value 1: media is write protected
  • value 0: media is not write protected bit 0: media presence bit
  • value 1: media is present
  • value 0: media is not present

The function USBD_MSCn_CheckMedia is called automatically upon specific USB Host requests (like Test Unit Ready) to check if media is ready for read/write operations. It needs no invocation in the user code. If media check is not available in hardware this function can be omitted.

Modify this function to the application's needs.

Code Example

#include "rl_usb.h"
uint32_t USBD_MSC0_CheckMedia (void) {
uint32_t param_status;
uint8_t media_state; // Bit 0. media ready, Bit 1. media write protect
static uint8_t media_ready_ex = 0U; // Previous media ready state
uint8_t own;
// Get current media status
media_state = 0U;
switch (fs_ioc_device_ctrl (drv_id, fsDevCtrlCodeCheckMedia, &param_status)) {
case fsOK:
if (param_status & FS_MEDIA_NOCHKMEDIA) {
// If check media not available on hardware layer
media_state = USBD_MSC_MEDIA_READY;
break;
}
if (param_status & FS_MEDIA_INSERTED) {
media_state = USBD_MSC_MEDIA_READY;
}
if (param_status & FS_MEDIA_PROTECTED) {
media_state |= USBD_MSC_MEDIA_PROTECTED;
}
break;
default:
break;
}
// Store current owner so no new request can interfere
own = usbd_msc0_media_own;
// De-initialize media according to previous owner
if (own & MEDIA_OWN_CHG) { // If owner change requested
if (own & MEDIA_OWN_USB) { // If new requested owner is USB (previous owner was File System)
funmount (MEDIA_DRIVE); // De-initialize media and dismount Drive
} else { // If new requested owner is File System (previous owner was USB)
fs_ioc_unlock (drv_id); // Un-lock media
}
}
// Initialize media according to current owner
if ((own & MEDIA_OWN_CHG) || // If owner change requested or
(media_state ^ media_ready_ex)) { // if media ready state has changed (disconnect(SD remove)/connect(SD insert))
if (media_state & USBD_MSC_MEDIA_READY) { // If media is ready
if (own & MEDIA_OWN_USB){ // If current owner is USB
media_ok = false; // Invalidate current media status (not initialized = not ok)
param_status = 0U; // Parameter for function call is 0
if (fs_ioc_device_ctrl (drv_id, fsDevCtrlCodeControlMedia, &param_status) == fsOK) {
// Initialization of media has succeeded
if (fs_ioc_lock (drv_id) == 0) { // If lock media for USB usage has succeeded
media_ok = true; // Media was initialized and is ok
}
}
} else { // If current owner is File System
if (fmount (MEDIA_DRIVE) == fsOK) { // Initialize media and Mount Drive for File System usage
media_ok = true; // Media was initialized and is ok
}
}
}
if (own & MEDIA_OWN_CHG) {
usbd_msc0_media_own &= ~MEDIA_OWN_CHG; // Clear request to change media owner if it was handled
}
media_ready_ex = media_state & USBD_MSC_MEDIA_READY;
}
// If media is not ok or owned by File System return that it is not ready for USB
if ((!media_ok) || (!(usbd_msc0_media_own & MEDIA_OWN_USB))) {
return 0U;
}
return media_state;
}
bool USBD_MSCn_GetCacheInfo ( uint32_t *  buffer,
uint32_t *  size 
)

Get cache information.

Parameters
[out]buffercache buffer address.
[out]sizecache buffer size.
Returns
true operation succeeded.
false operation failed.

The function USBD_MSCn_GetCacheInfo enables an MSC device to reuse RAM used by the File System for caching purposes as USB cache. This is required when a USB Host has control over the media so that it cannot be accessed by File System.

The argument buffer returns the cache buffer address, while the argument size returns the size of the cache buffer.

Code Example

#include "rl_usb.h"
bool USBD_MSC0_GetCacheInfo (uint32_t *buffer, uint32_t *size) {
fsIOC_Cache cache_info;
// Get cache settings of File System
if (fs_ioc_get_cache(drv_id, &cache_info) != fsOK) {
return false; // Exit if failed
}
// Use File Systems cache for MSC
*buffer = (uint32_t)cache_info.buffer;// Cache buffer from File System
*size = cache_info.size; // Cache size
return true;
}
bool USBD_MSCn_GetMediaCapacity ( uint32_t *  block_count,
uint32_t *  block_size 
)

Get media capacity.

Parameters
[out]block_counttotal number of blocks on media.
[out]block_sizemedia block size.
Returns
true operation succeeded.
false operation failed.

The function USBD_MSCn_GetMediaCapacity can be used to determine the geometry of the attached storage media.

The argument block_count returns the total number of blocks on the media, while the argument block_size returns the block size of the media.

Code Example

#include "rl_usb.h"
bool USBD_MSC0_GetMediaCapacity (uint32_t *block_count, uint32_t *block_size) {
fsMediaInfo media_info;
// Read media information of actual media
if (fs_ioc_read_info(drv_id, &media_info) != fsOK) {
return false; // Exit if failed
}
*block_count = media_info.block_cnt; // Total number of blocks on media
*block_size = media_info.read_blen; // Block size of blocks on media
return true;
}
void USBD_MSCn_Initialize ( void  )

Called during USBD_Initialize to initialize the USB MSC class instance.

Returns
none.

The function USBD_MSCn_Initialize is called automatically upon initialization of a Mass Storage Class Device and needs no invocation in the user code.

Modify this function to the application's needs to allocate resources and initialize additional peripherals.

Code Example

#include "rl_usb.h"
void USBD_MSC0_Initialize (void) {
uint32_t param_status;
usbd_mscn_media_own = MEDIA_OWN_USB; // Initially media is owned by USB
media_ok = false; // Current media status (not initialized = not ok)
if (finit (MEDIA_DRIVE) != fsOK) { // Initialize File System
return; // Exit if failed
}
param_status = 0U; // Parameter for function call is 0
// Initialize media
if (fs_ioc_device_ctrl (drv_id, fsDevCtrlCodeControlMedia, &param_status) != fsOK) {
return; // Exit if failed
}
drv_id = fs_ioc_get_id (MEDIA_DRIVE); // Get ID of media drive
if (drv_id < 0U) { return; } // If ID is invalid exit
if (fs_ioc_lock (drv_id)) { // Lock media for USB usage
return; // Exit if failed
}
media_ok = true; // Media was initialized and is ok
}
bool USBD_MSCn_Read ( uint32_t  lba,
uint32_t  cnt,
uint8_t *  buf 
)

Read data from media.

Parameters
[in]lbalogical address of first block to read.
[in]cntnumber of contiguous blocks to read from media.
[out]bufdata buffer for data read from media.
Returns
true read succeeded.
false read failed.

The function USBD_MSCn_Read reads the data that should be returned to the USB Host that requested it.

The argument lba specifies the logical address of the first block that is to be read.

The argument cnt specifies the number of contiguous blocks to be read from the media.

The argument buf is pointing to the buffer where the read data should be stored.

Modify this function to the application's needs.

Code Example

#include rl_usb.h
bool USBD_MSC0_Read (uint32_t lba, uint32_t cnt, uint8_t *buf) {
// Read data directly from media
if (fs_ioc_read_sector (drv_id, lba, buf, cnt) != fsOK) {
return false;
}
return true;
}
int32_t USBD_MSCn_SetMediaOwnerFS ( void  )

Set File System as media owner.

Returns
execution status
  • USBD_MSCn_OK = Media ownership changed successfully
  • USBD_MSCn_ERROR = Media ownership change has failed (due timeout)

The function USBD_MSCn_SetMediaOwnerFS sets the File System Component to the media owner of the attached media (drive). This will make the media unavailable to the USB Bus. Use USBD_MSCn_SetMediaOwnerUSB to enable ownership of the media for the USB Bus.

Code Example

int32_t USBD_MSC0_SetMediaOwnerFS (void) {
uint32_t timeout_cnt;
timeout_cnt = 300U; // 3 second timeout (300 * 10 ms)
usbd_msc0_media_own = USBD_MSC0_MEDIA_OWN_CHG;
while (usbd_msc0_media_own & USBD_MSC0_MEDIA_OWN_CHG) {
osDelay(10);
if ((--timeout_cnt) == 0) { return USBD_MSC0_ERROR; }
}
return USBD_MSC0_OK;
}

This function can be modified in the user code template file USBD_MSC_n.c.

int32_t USBD_MSCn_SetMediaOwnerUSB ( void  )

Set USB as media owner.

Returns
execution status
  • USBD_MSCn_OK = Media ownership changed successfully
  • USBD_MSCn_ERROR = Media ownership change has failed (due timeout)

The function USBD_MSCn_SetMediaOwnerUSB sets the USB Bus to the media owner of the attached media (drive). This will make the media unavailable to the File System Component. Use USBD_MSCn_SetMediaOwnerFS to enable ownership of the media for the File System Component.

Code Example

int32_t USBD_MSC0_SetMediaOwnerUSB (void) {
uint32_t timeout_cnt;
timeout_cnt = 300U; // 3 second timeout (300 * 10 ms)
usbd_msc0_media_own = USBD_MSC0_MEDIA_OWN_CHG | USBD_MSC0_MEDIA_OWN_USB;
while (usbd_msc0_media_own & USBD_MSC0_MEDIA_OWN_CHG) {
osDelay(10);
if ((--timeout_cnt) == 0) { return USBD_MSC0_ERROR; }
}
return USBD_MSC0_OK;
}

This function can be modified in the user code template file USBD_MSC_n.c.

void USBD_MSCn_Uninitialize ( void  )

Called during USBD_Uninitialize to de-initialize the USB MSC class instance.

Returns
none.

The function USBD_MSCn_Uninitialize is called automatically upon de-initialization of a Mass Storage Class Device and needs no invocation in the user code. If USBD_MSCn_Initialize has been adapted to the application, USBD_MSCn_Uninitialize should release resources and should de-initialize peripherals.

Code Example

#include "rl_usb.h"
int main (void) {
..
USBD_Initialize (0); // USB Device 0 Initialization
...
USBD_Uninitialize (0); // USB Device 0 De-Initialization
..
}
bool USBD_MSCn_Write ( uint32_t  lba,
uint32_t  cnt,
const uint8_t *  buf 
)

Write data to media.

Parameters
[in]lbalogical address of first block to write.
[in]cntnumber of contiguous blocks to write to media.
[out]bufdata buffer containing data to write to media.
Returns
true write succeeded.
false write failed.

The function USBD_MSCn_Write writes data received from the USB Host.

The argument lba specifies the logical address of the first block that is to be written.

The argument cnt specifies the number of contiguous blocks to be written to the media.

The argument buf is pointing to the buffer containing the data to be written.

Modify this function to the application's needs.

Code Example

#include rl_usb.h
bool USBD_MSC0_Write (uint32_t lba, uint32_t cnt, const uint8_t *buf) {
// Write data directly to media
if (fs_ioc_write_sector (drv_id, lba, buf, cnt) != fsOK) {
return false;
}
return true;
}