Search
lxdream.org :: lxdream/src/bios.c :: diff
lxdream 0.9.1
released Jun 29
Download Now
filename src/bios.c
changeset 1101:78e762cec843
prev1100:50e702af9373
next1102:957b76b312cc
author nkeynes
date Tue Feb 16 09:29:39 2010 +1000 (10 years ago)
permissions -rw-r--r--
last change Implement BIOS read cd + read toc2 functions
file annotate diff log raw
1.1 --- a/src/bios.c Mon Feb 15 17:27:14 2010 +1000
1.2 +++ b/src/bios.c Tue Feb 16 09:29:39 2010 +1000
1.3 @@ -56,24 +56,28 @@
1.4 #define GD_ERROR_DISC_CHANGE 6
1.5 #define GD_ERROR_SYSTEM 1
1.6
1.7 +struct gdrom_toc2_params {
1.8 + uint32_t session;
1.9 + sh4addr_t buffer;
1.10 +};
1.11 +
1.12 +struct gdrom_readcd_params {
1.13 + cdrom_lba_t lba;
1.14 + cdrom_count_t count;
1.15 + sh4addr_t buffer;
1.16 + uint32_t unknown;
1.17 +};
1.18 +
1.19 +struct gdrom_playcd_params {
1.20 + cdrom_lba_t start;
1.21 + cdrom_lba_t end;
1.22 + uint32_t repeat;
1.23 +};
1.24 +
1.25 typedef union gdrom_cmd_params {
1.26 - struct gdrom_toc2_params {
1.27 - uint32_t session;
1.28 - sh4addr_t buffer;
1.29 - } toc2;
1.30 -
1.31 - struct gdrom_readcd_params {
1.32 - cdrom_lba_t sector;
1.33 - cdrom_count_t count;
1.34 - sh4addr_t buffer;
1.35 - uint32_t unknown;
1.36 - } readcd;
1.37 -
1.38 - struct gdrom_playcd_params {
1.39 - cdrom_lba_t start;
1.40 - cdrom_lba_t end;
1.41 - uint32_t repeat;
1.42 - } playcd;
1.43 + struct gdrom_toc2_params toc2;
1.44 + struct gdrom_readcd_params readcd;
1.45 + struct gdrom_playcd_params playcd;
1.46 } *gdrom_cmd_params_t;
1.47
1.48
1.49 @@ -82,7 +86,7 @@
1.50 typedef struct gdrom_queue_entry {
1.51 int status;
1.52 uint32_t cmd_code;
1.53 - sh4ptr_t data;
1.54 + union gdrom_cmd_params params;
1.55 uint32_t result[4];
1.56 } *gdrom_queue_entry_t;
1.57
1.58 @@ -93,34 +97,83 @@
1.59 uint32_t disk_type;
1.60 } bios_gdrom_status;
1.61
1.62 +void bios_gdrom_init( void )
1.63 +{
1.64 + memset( &gdrom_cmd_queue, 0, sizeof(gdrom_cmd_queue) );
1.65 +}
1.66 +
1.67 void bios_gdrom_run_command( gdrom_queue_entry_t cmd )
1.68 {
1.69 DEBUG( "BIOS GD command %d", cmd->cmd_code );
1.70 + cdrom_error_t status = CDROM_ERROR_OK;
1.71 + sh4ptr_t ptr;
1.72 switch( cmd->cmd_code ) {
1.73 case GD_CMD_INIT:
1.74 /* *shrug* */
1.75 cmd->status = GD_CMD_STATUS_DONE;
1.76 break;
1.77 + case GD_CMD_GETTOC2:
1.78 + ptr = mem_get_region( cmd->params.toc2.buffer );
1.79 + status = gdrom_read_toc( ptr );
1.80 + if( status == CDROM_ERROR_OK ) {
1.81 + /* Convert data to little-endian */
1.82 + struct gdrom_toc *toc = (struct gdrom_toc *)ptr;
1.83 + for( unsigned i=0; i<99; i++ ) {
1.84 + toc->track[i] = ntohl(toc->track[i]);
1.85 + }
1.86 + toc->first = ntohl(toc->first);
1.87 + toc->last = ntohl(toc->last);
1.88 + toc->leadout = ntohl(toc->leadout);
1.89 + }
1.90 + break;
1.91 + case GD_CMD_PIOREAD:
1.92 + case GD_CMD_DMAREAD:
1.93 + ptr = mem_get_region( cmd->params.readcd.buffer );
1.94 + status = gdrom_read_cd( cmd->params.readcd.lba,
1.95 + cmd->params.readcd.count, 0x28, ptr, NULL );
1.96 + break;
1.97 + default:
1.98 + WARN( "Unknown BIOS GD command %d\n", cmd->cmd_code );
1.99 + cmd->status = GD_CMD_STATUS_ERROR;
1.100 + cmd->result[0] = GD_ERROR_SYSTEM;
1.101 + return;
1.102 + }
1.103 +
1.104 + switch( status ) {
1.105 + case CDROM_ERROR_OK:
1.106 + cmd->status = GD_CMD_STATUS_DONE;
1.107 + cmd->result[0] = GD_ERROR_OK;
1.108 + break;
1.109 + case CDROM_ERROR_NODISC:
1.110 + cmd->status = GD_CMD_STATUS_ERROR;
1.111 + cmd->result[0] = GD_ERROR_NO_DISC;
1.112 + break;
1.113 default:
1.114 cmd->status = GD_CMD_STATUS_ERROR;
1.115 cmd->result[0] = GD_ERROR_SYSTEM;
1.116 - break;
1.117 }
1.118 }
1.119
1.120 -void bios_gdrom_init( void )
1.121 -{
1.122 - memset( &gdrom_cmd_queue, 0, sizeof(gdrom_cmd_queue) );
1.123 -}
1.124 -
1.125 -uint32_t bios_gdrom_enqueue( uint32_t cmd, sh4ptr_t ptr )
1.126 +uint32_t bios_gdrom_enqueue( uint32_t cmd, sh4addr_t data )
1.127 {
1.128 int i;
1.129 for( i=0; i<COMMAND_QUEUE_LENGTH; i++ ) {
1.130 if( gdrom_cmd_queue[i].status != GD_CMD_STATUS_ACTIVE ) {
1.131 gdrom_cmd_queue[i].status = GD_CMD_STATUS_ACTIVE;
1.132 gdrom_cmd_queue[i].cmd_code = cmd;
1.133 - gdrom_cmd_queue[i].data = ptr;
1.134 + switch( cmd ) {
1.135 + case GD_CMD_PIOREAD:
1.136 + case GD_CMD_DMAREAD:
1.137 + mem_copy_from_sh4( (unsigned char *)&gdrom_cmd_queue[i].params.readcd, data, sizeof(struct gdrom_readcd_params) );
1.138 + break;
1.139 + case GD_CMD_GETTOC2:
1.140 + mem_copy_from_sh4( (unsigned char *)&gdrom_cmd_queue[i].params.toc2, data, sizeof(struct gdrom_toc2_params) );
1.141 + break;
1.142 + case GD_CMD_PLAY:
1.143 + case GD_CMD_PLAY2:
1.144 + mem_copy_from_sh4( (unsigned char *)&gdrom_cmd_queue[i].params.playcd, data, sizeof(struct gdrom_playcd_params) );
1.145 + break;
1.146 + }
1.147 return i;
1.148 }
1.149 }
1.150 @@ -165,10 +218,7 @@
1.151 case 0: /* GD-Rom */
1.152 switch( sh4r.r[7] ) {
1.153 case 0: /* Send command */
1.154 - if( sh4r.r[5] == 0 )
1.155 - sh4r.r[0] = bios_gdrom_enqueue( sh4r.r[4], NULL );
1.156 - else
1.157 - sh4r.r[0] = bios_gdrom_enqueue( sh4r.r[4], mem_get_region(sh4r.r[5]) );
1.158 + sh4r.r[0] = bios_gdrom_enqueue( sh4r.r[4], sh4r.r[5] );
1.159 break;
1.160 case 1: /* Check command */
1.161 cmd = bios_gdrom_get_command( sh4r.r[4] );
.