From 3dad671ef310b8b98b82b40d55ff91482a69769b Mon Sep 17 00:00:00 2001 From: Frank Gevaerts Date: Thu, 21 Aug 2008 10:10:58 +0000 Subject: [PATCH] Use cached memory for ata_write_sectors(). This seems to finally fix FS#8663 Thanks to Martin Ritter for finding out that the uncached accesses were somehow causing this SERIALIZE_WRITES can probably be removed, but this requires a bit more testing first git-svn-id: svn://svn.rockbox.org/rockbox/trunk@18327 a1c6a512-1295-4272-9138-f99709370657 --- firmware/usbstack/usb_storage.c | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-) diff --git a/firmware/usbstack/usb_storage.c b/firmware/usbstack/usb_storage.c index 17b8bb7168..e6fd7a70ac 100644 --- a/firmware/usbstack/usb_storage.c +++ b/firmware/usbstack/usb_storage.c @@ -235,6 +235,7 @@ static union { struct command_status_wrapper* csw; char *max_lun; } tb; +unsigned char* cached_transfer_buffer; static struct { unsigned int sector; @@ -242,6 +243,7 @@ static struct { unsigned int tag; unsigned int lun; unsigned char *data[2]; + unsigned char *cached_data[2]; unsigned char data_select; unsigned int last_result; } cur_cmd; @@ -386,8 +388,10 @@ void usb_storage_init_connection(void) unsigned char * audio_buffer; audio_buffer = audio_get_buffer(false,&bufsize); + cached_transfer_buffer = + (void *)((unsigned int)(audio_buffer + 31) & 0xffffffe0); tb.transfer_buffer = - (void *)UNCACHED_ADDR((unsigned int)(audio_buffer + 31) & 0xffffffe0); + (void *)UNCACHED_ADDR(cached_transfer_buffer); invalidate_icache(); #endif usb_drv_recv(usb_endpoint, tb.transfer_buffer, 1024); @@ -428,11 +432,12 @@ void usb_storage_transfer_complete(int ep,bool in,int status,int length) /* Now write the data that just came in, while the host is sending the next bit */ + invalidate_icache(); int result = ata_write_sectors(IF_MV2(cur_cmd.lun,) cur_cmd.sector, MIN(BUFFER_SIZE/SECTOR_SIZE, cur_cmd.count), - cur_cmd.data[cur_cmd.data_select]); + cur_cmd.cached_data[cur_cmd.data_select]); if(result != 0) { send_csw(UMS_STATUS_FAIL); cur_sense_data.sense_key=SENSE_MEDIUM_ERROR; @@ -650,6 +655,10 @@ static void handle_scsi(struct command_block_wrapper* cbw) cur_cmd.tag = cbw->tag; cur_cmd.lun = lun; + cur_cmd.cached_data[0] = cached_transfer_buffer; + cur_cmd.cached_data[1] = &cached_transfer_buffer[BUFFER_SIZE]; + cur_cmd.data[0] = tb.transfer_buffer; + cur_cmd.data[1] = &tb.transfer_buffer[BUFFER_SIZE]; switch (cbw->command_block[0]) { case SCSI_TEST_UNIT_READY: @@ -905,8 +914,6 @@ static void handle_scsi(struct command_block_wrapper* cbw) cur_sense_data.ascq=0; break; } - cur_cmd.data[0] = tb.transfer_buffer; - cur_cmd.data[1] = &tb.transfer_buffer[BUFFER_SIZE]; cur_cmd.data_select=0; cur_cmd.sector = block_size_mult * (cbw->command_block[2] << 24 | @@ -944,8 +951,6 @@ static void handle_scsi(struct command_block_wrapper* cbw) cur_sense_data.ascq=0; break; } - cur_cmd.data[0] = tb.transfer_buffer; - cur_cmd.data[1] = &tb.transfer_buffer[BUFFER_SIZE]; cur_cmd.data_select=0; cur_cmd.sector = block_size_mult * (cbw->command_block[2] << 24 |