summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDan Halbert <halbert@halwitz.org>2017-11-09 17:19:33 -0500
committerGitHub <noreply@github.com>2017-11-09 17:19:33 -0500
commit9564f7b90edc6f73c3b5ffe914d903468ce99da4 (patch)
treee03e5ce0a9750aead6607cd2c05148103de56ddb
parent5e04780148e6cd486b02d8695ff5237f631e9d2d (diff)
parentef9a7f262a9272e0771cdec4981a54844462add8 (diff)
Merge pull request #425 from tannewt/align_usb
atmel-samd: USB mass storage tweaks.
-rw-r--r--ports/atmel-samd/asf4_conf/samd51/hpl_nvmctrl_config.h4
-rw-r--r--ports/atmel-samd/usb_mass_storage.c28
2 files changed, 21 insertions, 11 deletions
diff --git a/ports/atmel-samd/asf4_conf/samd51/hpl_nvmctrl_config.h b/ports/atmel-samd/asf4_conf/samd51/hpl_nvmctrl_config.h
index daaba85d4..53fcb593a 100644
--- a/ports/atmel-samd/asf4_conf/samd51/hpl_nvmctrl_config.h
+++ b/ports/atmel-samd/asf4_conf/samd51/hpl_nvmctrl_config.h
@@ -19,14 +19,14 @@
// <i> Indicate whether AHB0 cache is disable or not
// <id> nvm_arch_cache0
#ifndef CONF_NVM_CACHE0
-#define CONF_NVM_CACHE0 0
+#define CONF_NVM_CACHE0 1
#endif
// <q> AHB1 Cache Disable
// <i> Indicate whether AHB1 cache is disable or not
// <id> nvm_arch_cache1
#ifndef CONF_NVM_CACHE1
-#define CONF_NVM_CACHE1 0
+#define CONF_NVM_CACHE1 1
#endif
// </h>
diff --git a/ports/atmel-samd/usb_mass_storage.c b/ports/atmel-samd/usb_mass_storage.c
index d9d9d9f39..85c662e77 100644
--- a/ports/atmel-samd/usb_mass_storage.c
+++ b/ports/atmel-samd/usb_mass_storage.c
@@ -63,10 +63,10 @@ static fs_user_mount_t* get_vfs(int lun) {
/* Inquiry Information */
// This is designed to handle the common case where we have an internal file
// system and an optional SD card.
-static uint8_t inquiry_info[2][36];
+COMPILER_ALIGNED(4) static uint8_t inquiry_info[2][36];
/* Capacities of Disk */
-static uint8_t format_capa[2][8];
+COMPILER_ALIGNED(4) static uint8_t format_capa[2][8];
/**
* \brief Eject Disk
@@ -256,18 +256,17 @@ int32_t usb_msc_xfer_done(uint8_t lun) {
return ERR_DENIED;
}
+ CRITICAL_SECTION_ENTER();
if (active_read) {
active_addr += 1;
active_nblocks--;
- if (active_nblocks == 0) {
- active_read = false;
- }
}
if (active_write) {
sector_loaded = true;
}
usb_busy = false;
+ CRITICAL_SECTION_LEAVE();
return ERR_NONE;
}
@@ -275,11 +274,16 @@ int32_t usb_msc_xfer_done(uint8_t lun) {
// The start_read callback begins a read transaction which we accept but delay our response until the "main thread" calls usb_msc_background. Once it does, we read immediately from the drive into our cache and trigger the USB DMA to output the sector. Once the sector is transmitted, xfer_done will be called.
void usb_msc_background(void) {
if (active_read && !usb_busy) {
+ if (active_nblocks == 0) {
+ active_read = false;
+ return;
+ }
fs_user_mount_t * vfs = get_vfs(active_lun);
disk_read(vfs, sector_buffer, active_addr, 1);
- // TODO(tannewt): Check the read result.
- mscdf_xfer_blocks(true, sector_buffer, 1);
- usb_busy = true;
+ CRITICAL_SECTION_ENTER();
+ int32_t result = mscdf_xfer_blocks(true, sector_buffer, 1);
+ usb_busy = result == ERR_NONE;
+ CRITICAL_SECTION_LEAVE();
}
if (active_write && !usb_busy) {
if (sector_loaded) {
@@ -306,8 +310,14 @@ void usb_msc_background(void) {
}
// Load more blocks from USB if they are needed.
if (active_nblocks > 0) {
+ // Turn off interrupts because with them on,
+ // usb_msc_xfer_done could be called before we update
+ // usb_busy. If that happened, we'd overwrite the fact that
+ // the transfer actually already finished.
+ CRITICAL_SECTION_ENTER();
int32_t result = mscdf_xfer_blocks(false, sector_buffer, 1);
- usb_busy = result != ERR_NONE;
+ usb_busy = result == ERR_NONE;
+ CRITICAL_SECTION_LEAVE();
} else {
mscdf_xfer_blocks(false, NULL, 0);
active_write = false;