revision 493:c8183f888b14
summary |
tree |
shortlog |
changelog |
graph |
changeset |
raw | bz2 | zip | gz changeset | 493:c8183f888b14 |
parent | 492:84e33e4dda1c |
child | 494:67c133a17400 |
author | nkeynes |
date | Tue Nov 06 08:35:33 2007 +0000 (16 years ago) |
Implement mode select command
src/dreamcast.h | view | annotate | diff | log | ||
src/gdrom/ide.c | view | annotate | diff | log | ||
src/gdrom/ide.h | view | annotate | diff | log | ||
src/gdrom/packet.h | view | annotate | diff | log |
1.1 --- a/src/dreamcast.h Tue Nov 06 08:35:16 2007 +00001.2 +++ b/src/dreamcast.h Tue Nov 06 08:35:33 2007 +00001.3 @@ -1,5 +1,5 @@1.4 /**1.5 - * $Id: dreamcast.h,v 1.21 2007-10-31 09:10:23 nkeynes Exp $1.6 + * $Id: dreamcast.h,v 1.22 2007-11-06 08:35:33 nkeynes Exp $1.7 *1.8 * Public interface for dreamcast.c -1.9 * Central switchboard for the system. This pulls all the individual modules1.10 @@ -47,7 +47,7 @@1.11 gboolean dreamcast_is_running(void);1.13 #define DREAMCAST_SAVE_MAGIC "%!-lxDream!Save\0"1.14 -#define DREAMCAST_SAVE_VERSION 0x000100011.15 +#define DREAMCAST_SAVE_VERSION 0x000100021.17 int dreamcast_save_state( const gchar *filename );1.18 int dreamcast_load_state( const gchar *filename );
2.1 --- a/src/gdrom/ide.c Tue Nov 06 08:35:16 2007 +00002.2 +++ b/src/gdrom/ide.c Tue Nov 06 08:35:33 2007 +00002.3 @@ -1,5 +1,5 @@2.4 /**2.5 - * $Id: ide.c,v 1.26 2007-10-08 12:06:01 nkeynes Exp $2.6 + * $Id: ide.c,v 1.27 2007-11-06 08:35:33 nkeynes Exp $2.7 *2.8 * IDE interface implementation2.9 *2.10 @@ -56,12 +56,12 @@2.11 #define WRITE_BUFFER(x16) *((uint16_t *)(data_buffer + idereg.data_offset)) = x162.12 #define READ_BUFFER() *((uint16_t *)(data_buffer + idereg.data_offset))2.14 -/* "\0\0\0\0\xb4\x19\0\0\x08SE REV 6.42990316" */2.15 -unsigned char gdrom_ident[] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0xb4, 0x19, 0x00,2.16 - 0x00, 0x08, 0x53, 0x45, 0x20, 0x20, 0x20, 0x20,2.17 - 0x20, 0x20, 0x52, 0x65, 0x76, 0x20, 0x36, 0x2e,2.18 - 0x34, 0x32, 0x39, 0x39, 0x30, 0x33, 0x31, 0x36 };2.19 -2.20 +/* 10 bytes followed by "SE REV 6.42990316" */2.21 +unsigned char default_gdrom_mode[GDROM_MODE_LENGTH] =2.22 + { 0x00, 0x00, 0x00, 0x00, 0x00, 0xb4, 0x19, 0x00, 0x00, 0x08,2.23 + 0x53, 0x45, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,2.24 + 0x52, 0x65, 0x76, 0x20, 0x36, 0x2e, 0x34, 0x32, 0x39, 0x39, 0x30, 0x33, 0x31, 0x36 };2.25 +2.26 unsigned char gdrom_71[] = { 0x3E, 0x0F, 0x90, 0xBE, 0x1D, 0xD9, 0x89, 0x04, 0x28, 0x3A, 0x8E, 0x26, 0x5C, 0x95, 0x10, 0x5A,2.27 0x0A, 0x99, 0xEE, 0xFB, 0x69, 0xCE, 0xD9, 0x63, 0x00, 0xF5, 0x0A, 0xBC, 0x2C, 0x0D, 0xF8, 0xE2,2.28 0x05, 0x02, 0x00, 0x7C, 0x03, 0x00, 0x3D, 0x08, 0xD8, 0x8D, 0x08, 0x7A, 0x6D, 0x00, 0x35, 0x06,2.29 @@ -148,11 +148,12 @@2.30 idereg.device = 0x00;2.31 idereg.state = IDE_STATE_IDLE;2.32 memset( idereg.gdrom_sense, '\0', 10 );2.33 + memcpy( idereg.gdrom_mode, default_gdrom_mode, GDROM_MODE_LENGTH );2.34 idereg.data_offset = -1;2.35 idereg.data_length = -1;2.36 idereg.last_read_track = 1;2.37 - idereg.read_lba = 150;2.38 - idereg.read_mode = 0x28;2.39 + idereg.current_lba = 150;2.40 + idereg.current_mode = 0x28;2.41 idereg.sectors_left = 0;2.42 idereg.was_reset = TRUE;2.43 }2.44 @@ -209,7 +210,7 @@2.45 }2.47 /**2.48 - * Begin PIO read from the device. The data is assumed to already be2.49 + * Begin PIO/DMA read from the device. The data is assumed to already be2.50 * in the buffer at this point.2.51 */2.52 static void ide_start_read( int length, gboolean dma )2.53 @@ -229,6 +230,23 @@2.54 }2.55 }2.57 +static void ide_start_write( int length, gboolean dma )2.58 +{2.59 + idereg.count = 0;2.60 + idereg.data_length = length;2.61 + idereg.data_offset = 0;2.62 + if( dma ) {2.63 + idereg.state = IDE_STATE_DMA_WRITE;2.64 + idereg.status = 0xD0;2.65 + } else {2.66 + idereg.state = IDE_STATE_PIO_WRITE;2.67 + idereg.status = 0x58;2.68 + idereg.lba1 = length & 0xFF;2.69 + idereg.lba2 = length >> 8;2.70 + ide_raise_interrupt( );2.71 + }2.72 +}2.73 +2.74 static void ide_start_packet_read( int length, int sector_count )2.75 {2.76 idereg.sectors_left = sector_count;2.77 @@ -236,6 +254,13 @@2.78 ide_start_read( length, (idereg.feature & IDE_FEAT_DMA) ? TRUE : FALSE );2.79 }2.81 +static void ide_start_packet_write( int length, int sector_count )2.82 +{2.83 + idereg.sectors_left = sector_count;2.84 + ide_set_packet_result( PKT_ERR_OK );2.85 + ide_start_write( length, (idereg.feature & IDE_FEAT_DMA) ? TRUE : FALSE );2.86 +}2.87 +2.88 static void ide_raise_interrupt( void )2.89 {2.90 if( idereg.intrq_pending == 0 ) {2.91 @@ -341,11 +366,14 @@2.92 }2.93 } else if( idereg.state == IDE_STATE_PIO_WRITE ) {2.94 WRITE_BUFFER(val);2.95 + idereg.data_offset +=2;2.96 if( idereg.data_offset >= idereg.data_length ) {2.97 - idereg.state = IDE_STATE_BUSY;2.98 + idereg.state = IDE_STATE_IDLE;2.99 + idereg.status &= ~IDE_STATUS_DRQ;2.100 idereg.data_offset = -1;2.101 - idereg.status = (idereg.status & ~IDE_STATUS_DRQ) | IDE_STATUS_BSY;2.102 - /* ??? - no data writes yet anyway */2.103 + idereg.count = 3; /* complete */2.104 + ide_raise_interrupt();2.105 + ide_write_buffer( data_buffer, idereg.data_length );2.106 }2.107 }2.108 }2.109 @@ -432,16 +460,16 @@2.110 uint32_t sector_size;2.111 REQUIRE_DISC();2.112 gdrom_error_t status =2.113 - gdrom_disc->read_sector( gdrom_disc, idereg.read_lba, idereg.read_mode,2.114 + gdrom_disc->read_sector( gdrom_disc, idereg.current_lba, idereg.current_mode,2.115 data_buffer, §or_size );2.116 if( status != PKT_ERR_OK ) {2.117 ide_set_packet_result( status );2.118 - idereg.gdrom_sense[5] = (idereg.read_lba >> 16) & 0xFF;2.119 - idereg.gdrom_sense[6] = (idereg.read_lba >> 8) & 0xFF;2.120 - idereg.gdrom_sense[7] = idereg.read_lba & 0xFF;2.121 + idereg.gdrom_sense[5] = (idereg.current_lba >> 16) & 0xFF;2.122 + idereg.gdrom_sense[6] = (idereg.current_lba >> 8) & 0xFF;2.123 + idereg.gdrom_sense[7] = idereg.current_lba & 0xFF;2.124 WARN( " => Read CD returned sense key %02X, %02X", status & 0xFF, status >> 8 );2.125 } else {2.126 - idereg.read_lba++;2.127 + idereg.current_lba++;2.128 idereg.sectors_left--;2.129 ide_start_read( sector_size, (idereg.feature & IDE_FEAT_DMA) ? TRUE : FALSE );2.130 }2.131 @@ -475,18 +503,30 @@2.132 ide_raise_interrupt();2.133 idereg.status = 0x50;2.134 break;2.135 - case PKT_CMD_IDENTIFY:2.136 + case PKT_CMD_MODE_SENSE:2.137 lba = cmd[2];2.138 - if( lba >= sizeof(gdrom_ident) ) {2.139 + if( lba >= GDROM_MODE_LENGTH ) {2.140 ide_set_error(PKT_ERR_BADFIELD);2.141 } else {2.142 length = cmd[4];2.143 - if( lba+length > sizeof(gdrom_ident) )2.144 - length = sizeof(gdrom_ident) - lba;2.145 - memcpy( data_buffer, gdrom_ident + lba, length );2.146 + if( lba+length > GDROM_MODE_LENGTH )2.147 + length = GDROM_MODE_LENGTH - lba;2.148 + memcpy( data_buffer, idereg.gdrom_mode + lba, length );2.149 ide_start_packet_read( length, 0 );2.150 }2.151 break;2.152 + case PKT_CMD_MODE_SELECT:2.153 + lba = cmd[2];2.154 + if( lba >= GDROM_MODE_LENGTH ) {2.155 + ide_set_error(PKT_ERR_BADFIELD);2.156 + } else {2.157 + length = cmd[4];2.158 + if( lba+length > GDROM_MODE_LENGTH )2.159 + length = GDROM_MODE_LENGTH - lba;2.160 + idereg.current_lba = lba;2.161 + ide_start_packet_write( length, 0 );2.162 + }2.163 + break;2.164 case PKT_CMD_SENSE:2.165 length = cmd[4];2.166 if( length > 10 )2.167 @@ -527,9 +567,9 @@2.168 break;2.169 case PKT_CMD_READ_SECTOR:2.170 REQUIRE_DISC();2.171 - idereg.read_lba = cmd[2] << 16 | cmd[3] << 8 | cmd[4];2.172 + idereg.current_lba = cmd[2] << 16 | cmd[3] << 8 | cmd[4];2.173 idereg.sectors_left = cmd[8] << 16 | cmd[9] << 8 | cmd[10]; /* blocks */2.174 - idereg.read_mode = cmd[1];2.175 + idereg.current_mode = cmd[1];2.176 ide_read_next_sector();2.177 break;2.178 case PKT_CMD_SPIN_UP:2.179 @@ -553,7 +593,7 @@2.180 if( length > 14 ) {2.181 length = 14;2.182 }2.183 - gdrom_disc->read_position( gdrom_disc, idereg.read_lba, data_buffer );2.184 + gdrom_disc->read_position( gdrom_disc, idereg.current_lba, data_buffer );2.185 data_buffer[0] = 0x00;2.186 data_buffer[1] = 0x15; /* audio status ? */2.187 data_buffer[2] = 0x00;2.188 @@ -575,4 +615,21 @@2.189 ide_set_packet_result( PKT_ERR_BADCMD ); /* Invalid command */2.190 return;2.191 }2.192 + idereg.last_packet_command = cmd[0];2.193 }2.194 +2.195 +void ide_write_buffer( unsigned char *data, uint32_t length )2.196 +{2.197 + switch( idereg.last_packet_command ) {2.198 + case PKT_CMD_MODE_SELECT:2.199 + if( idereg.current_lba < 10 ) {2.200 + if( idereg.current_lba + length > 10 ) {2.201 + length = 10 - idereg.current_lba;2.202 + }2.203 + memcpy( idereg.gdrom_mode + idereg.current_lba, data, length );2.204 + }2.205 + break;2.206 + default:2.207 + WARN( "Don't know what to do with received data buffer for command %02X", idereg.last_packet_command );2.208 + }2.209 +}
3.1 --- a/src/gdrom/ide.h Tue Nov 06 08:35:16 2007 +00003.2 +++ b/src/gdrom/ide.h Tue Nov 06 08:35:33 2007 +00003.3 @@ -1,5 +1,5 @@3.4 /**3.5 - * $Id: ide.h,v 1.13 2007-01-31 10:58:42 nkeynes Exp $3.6 + * $Id: ide.h,v 1.14 2007-11-06 08:35:33 nkeynes Exp $3.7 *3.8 * This file defines the interface and structures of the dreamcast's IDE3.9 * port. Note that the register definitions are in asic.h, as the registers3.10 @@ -25,6 +25,9 @@3.12 #include "dream.h"3.14 +#define GDROM_SENSE_LENGTH 103.15 +#define GDROM_MODE_LENGTH 323.16 +3.17 struct ide_registers {3.18 /* IDE interface registers */3.19 uint8_t status; /* A05F709C + A05F7018 Read-only */3.20 @@ -43,22 +46,23 @@3.21 uint8_t intrq_pending; /* Flag to indicate if the INTRQ line is active */3.22 gboolean interface_enabled;3.23 gboolean was_reset; /* Flag indicating that the device has just been reset */3.24 - int state;3.25 + uint32_t state;3.26 + uint32_t last_packet_command; /* Identifies the command executing during a r/w cycle */3.28 /* Sense response for the last executed packet command */3.29 - unsigned char gdrom_sense[10];3.30 -3.31 + unsigned char gdrom_sense[GDROM_SENSE_LENGTH];3.32 + unsigned char gdrom_mode[GDROM_MODE_LENGTH];3.34 /* offset in the buffer of the next word to read/write, or -13.35 * if inactive.3.36 */3.37 - int data_offset;3.38 - int data_length;3.39 + int32_t data_offset;3.40 + int32_t data_length;3.42 /* Status reporting information */3.43 uint8_t last_read_track;3.44 - uint32_t read_lba;3.45 - uint32_t read_mode;3.46 + uint32_t current_lba;3.47 + uint32_t current_mode;3.48 uint32_t sectors_left; /* sectors left after current read */3.49 };3.51 @@ -116,7 +120,7 @@3.52 uint32_t ide_read_data_dma( uint32_t addr, uint32_t length );3.53 uint8_t ide_read_status(void);3.54 uint8_t ide_get_drive_status(void);3.55 -void ide_write_buffer( unsigned char *data, int length );3.56 +void ide_write_buffer( unsigned char *data, uint32_t length );3.58 void ide_write_command( uint8_t command );3.59 void ide_write_control( uint8_t value );
4.1 --- a/src/gdrom/packet.h Tue Nov 06 08:35:16 2007 +00004.2 +++ b/src/gdrom/packet.h Tue Nov 06 08:35:33 2007 +00004.3 @@ -1,5 +1,5 @@4.4 /**4.5 - * $Id: packet.h,v 1.7 2007-01-31 10:58:42 nkeynes Exp $4.6 + * $Id: packet.h,v 1.8 2007-11-06 08:35:33 nkeynes Exp $4.7 *4.8 * This file defines the command codes and any other flags used by the4.9 * GD-Rom ATAPI packet commands.4.10 @@ -47,7 +47,8 @@4.11 */4.13 #define PKT_CMD_TEST_READY 0x004.14 -#define PKT_CMD_IDENTIFY 0x114.15 +#define PKT_CMD_MODE_SENSE 0x114.16 +#define PKT_CMD_MODE_SELECT 0x124.17 #define PKT_CMD_SENSE 0x134.18 #define PKT_CMD_READ_TOC 0x144.19 #define PKT_CMD_SESSION_INFO 0x15
.