complete msc device demo with 8KB ram disk

This commit is contained in:
hathach 2013-11-05 14:55:58 +07:00
parent 83d9ececfb
commit 024858a605
1 changed files with 92 additions and 6 deletions

View File

@ -48,7 +48,7 @@
//--------------------------------------------------------------------+
enum
{
DISK_BLOCK_NUM = 16,
DISK_BLOCK_NUM = 16, // 8KB is the smallest size that windows allow to mount
DISK_BLOCK_SIZE = 512
};
@ -78,9 +78,35 @@ typedef ATTR_PACKED_STRUCT(struct) {
uint8_t filesystem_type[8] ; ///< File system type label in ASCII, padded with blank (0x20). Standard values include "FAT," "FAT12," and "FAT16," but nothing is required.
uint8_t reserved2[448] ;
uint16_t fat_signature ; ///< Signature value (0xAA55).
}fat16_boot_sector_t;
}fat12_boot_sector_t;
STATIC_ASSERT(sizeof(fat16_boot_sector_t) == 512, "size is not correct");
STATIC_ASSERT(sizeof(fat12_boot_sector_t) == 512, "size is not correct");
typedef ATTR_PACKED_STRUCT(struct) {
uint8_t name[11];
ATTR_PACKED_STRUCT(struct){
uint8_t readonly : 1;
uint8_t hidden : 1;
uint8_t system : 1;
uint8_t volume_label : 1;
uint8_t directory : 1;
uint8_t archive : 1;
} attr; // Long File Name = 0x0f
uint8_t reserved;
uint8_t created_time_tenths_of_seconds;
uint16_t created_time;
uint16_t created_date;
uint16_t accessed_date;
uint16_t cluster_high;
uint16_t written_time;
uint16_t written_date;
uint16_t cluster_low;
uint32_t file_size;
}fat_directory_t;
STATIC_ASSERT(sizeof(fat_directory_t) == 32, "size is not correct");
static scsi_inquiry_data_t mscd_inquiry_data TUSB_CFG_ATTR_USBRAM =
{
@ -133,7 +159,15 @@ static uint16_t read10(uint8_t coreid, uint8_t lun, scsi_read10_t* p_read10, voi
{
uint8_t block_count = __be2h_16(p_read10->block_count);
(*pp_buffer) = &mscd_app_ramdisk[ __be2le(p_read10->lba)];
(*pp_buffer) = mscd_app_ramdisk[ __be2le(p_read10->lba)];
return block_count*DISK_BLOCK_SIZE;
}
static uint16_t write10(uint8_t coreid, uint8_t lun, scsi_read10_t* p_read10, void** pp_buffer)
{
uint8_t block_count = __be2h_16(p_read10->block_count);
(*pp_buffer) = mscd_app_ramdisk[ __be2le(p_read10->lba)];
return block_count*DISK_BLOCK_SIZE;
}
@ -182,6 +216,7 @@ msc_csw_status_t tusbd_msc_scsi_received_isr (uint8_t coreid, uint8_t lun, uint8
break;
case SCSI_CMD_WRITE_10:
(*p_length) = write10(coreid, lun, (scsi_read10_t*) scsi_cmd, pp_buffer);
break;
default: return MSC_CSW_STATUS_FAILED;
@ -193,10 +228,26 @@ msc_csw_status_t tusbd_msc_scsi_received_isr (uint8_t coreid, uint8_t lun, uint8
//--------------------------------------------------------------------+
// IMPLEMENTATION
//--------------------------------------------------------------------+
void fat12_fs_init(uint8_t mscd_app_ramdisk[DISK_BLOCK_NUM][DISK_BLOCK_SIZE]);
void msc_dev_app_init (void)
{
fat16_boot_sector_t* p_boot_fat = (fat16_boot_sector_t* ) &mscd_app_ramdisk[0];
memclr_(p_boot_fat, sizeof(fat16_boot_sector_t));
fat12_fs_init(mscd_app_ramdisk);
}
//--------------------------------------------------------------------+
// HELPER
//--------------------------------------------------------------------+
void fat12_fs_init(uint8_t mscd_app_ramdisk[DISK_BLOCK_NUM][DISK_BLOCK_SIZE])
{
uint8_t const readme_contents[] =
"This is tinyusb's MassStorage Class demo.\r\n\r\n\
If you find any bugs or get any questions, feel free to file an\r\n\
issue at https://github.com/hathach/tinyusb";
//------------- Boot Sector -------------//
fat12_boot_sector_t* p_boot_fat = (fat12_boot_sector_t* ) mscd_app_ramdisk[0];
memclr_(p_boot_fat, sizeof(fat12_boot_sector_t));
memcpy(p_boot_fat->jump_code, "\xEB\x3C\x90", 3);
memcpy(p_boot_fat->oem_name, "MSDOS5.0", 8);
@ -218,5 +269,40 @@ void msc_dev_app_init (void)
memcpy(p_boot_fat->volume_label , "tinyusb msc", 11);
memcpy(p_boot_fat->filesystem_type, "FAT12 ", 8);
p_boot_fat->fat_signature = 0xAA55;
//------------- FAT12 Table (first 2 entries are F8FF, third entry is cluster end of readme file-------------//
memcpy(mscd_app_ramdisk[1], "\xF8\xFF\xFF\xFF\x0F", 5);
//------------- Root Directory -------------//
fat_directory_t* p_entry = (fat_directory_t*) mscd_app_ramdisk[2];
// first entry is volume label
(*p_entry) = (fat_directory_t)
{
.name = "TINYUSB MSC",
.attr.volume_label = 1,
};
p_entry += 1; // advance to second entry, second entry is readme file
(*p_entry) = (fat_directory_t)
{
.name = "README TXT",
.created_time = 0x6D52,
.written_time = 0x6D52,
.created_date = 0x4365,
.accessed_date = 0x4365,
.written_date = 0x4365,
.cluster_high = 0,
.cluster_low = 2,
.file_size = sizeof(readme_contents)-1 // exculde NULL
}; // first entry is volume label
//------------- Readme Content -------------//
memcpy(mscd_app_ramdisk[3], readme_contents, sizeof(readme_contents)-1);
}
#endif