Search
lxdream.org :: lxdream/src/gdrom/cdi.c :: diff
lxdream 0.9.1
released Jun 29
Download Now
filename src/gdrom/cdi.c
changeset 1:eea311cfd33e
next31:495e480360d7
author nkeynes
date Thu Dec 08 13:38:00 2005 +0000 (18 years ago)
permissions -rw-r--r--
last change Generalise the core debug window to allow multiple instances.
Add cpu description structure to define different cpus for use by the
debug window, in preparation for ARM implementation
file annotate diff log raw
1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000
1.2 +++ b/src/gdrom/cdi.c Thu Dec 08 13:38:00 2005 +0000
1.3 @@ -0,0 +1,154 @@
1.4 +
1.5 +#include <stdlib.h>
1.6 +#include <stdio.h>
1.7 +#include <stdint.h>
1.8 +#include <fcntl.h>
1.9 +#include <errno.h>
1.10 +#include <sys/stat.h>
1.11 +#include "cdi.h"
1.12 +
1.13 +#define CDI_V2 0x80000004
1.14 +#define CDI_V3 0x80000005
1.15 +
1.16 +static char track_start_marker[20] = { 0,0,1,0,0,0,255,255,255,255,
1.17 + 0,0,1,0,0,0,255,255,255,255 };
1.18 +
1.19 +struct cdi_trailer {
1.20 + uint32_t cdi_version;
1.21 + uint32_t header_offset;
1.22 +};
1.23 +
1.24 +struct cdi_track {
1.25 + int file_posn;
1.26 + int length; /* bytes */
1.27 + int pregap; /* sectors */
1.28 + int mode;
1.29 + int sector_size;
1.30 + int session;
1.31 + struct cdi_track *next;
1.32 +};
1.33 +
1.34 +struct cdi_handle {
1.35 + int fd;
1.36 + uint16_t num_sessions;
1.37 + struct cdi_track *tracks;
1.38 +};
1.39 +
1.40 +
1.41 +
1.42 +struct cdi_track_data {
1.43 + char unknown[0x19];
1.44 + uint32_t pregap_length;
1.45 + uint32_t length;
1.46 + char unknown2[6];
1.47 + uint32_t mode;
1.48 + char unknown3[0x0c];
1.49 + uint32_t start_lba;
1.50 + uint32_t total_length;
1.51 + char unknown4[0x10];
1.52 + uint32_t sector_size;
1.53 + char unknown5[0x1D];
1.54 +} __attribute__((packed));
1.55 +
1.56 +cdi_t cdi_open( char *filename )
1.57 +{
1.58 +#define BAIL( x, ... ) { fprintf( stderr, x, __VA_ARGS__ ); if( fd != -1 ) close(fd); return NULL; }
1.59 +
1.60 + struct stat st;
1.61 + int fd = -1, i,j, tmp;
1.62 + int posn = 0, hdr;
1.63 + long len;
1.64 + struct cdi_trailer trail;
1.65 + struct cdi_handle cdi;
1.66 + uint16_t tracks;
1.67 + uint32_t new_fmt;
1.68 + char tmpc;
1.69 + char marker[20];
1.70 +
1.71 + fd = open( filename, O_RDONLY );
1.72 + if( fd == -1 )
1.73 + BAIL( "Unable to open file: %s (%s)\n", filename, strerror(errno) );
1.74 + fstat( fd, &st );
1.75 + if( st.st_size < 8 )
1.76 + BAIL( "File is too small to be a valid CDI image: %s\n", filename );
1.77 + len = lseek( fd, -8, SEEK_END );
1.78 + read( fd, &trail, sizeof(trail) );
1.79 + if( trail.header_offset > st.st_size ||
1.80 + trail.header_offset == 0 )
1.81 + BAIL( "Not a valid CDI image: %s\n", filename );
1.82 +
1.83 + if( trail.cdi_version == CDI_V2 ) trail.cdi_version = 2;
1.84 + else if( trail.cdi_version == CDI_V3 ) trail.cdi_version = 3;
1.85 + else BAIL( "Unknown CDI version code %08x in %s\n", trail.cdi_version,
1.86 + filename );
1.87 +
1.88 + lseek( fd, trail.header_offset, SEEK_SET );
1.89 + read( fd, &cdi.num_sessions, 2 );
1.90 +
1.91 +
1.92 + printf( "CDI version: %d\n", trail.cdi_version );
1.93 + printf( "Sessions: %d\n\n", cdi.num_sessions );
1.94 + for( i=0; i< cdi.num_sessions; i++ ) {
1.95 + read( fd, &tracks, 2 );
1.96 + printf( "Session %d - %d tracks:\n", i+1, tracks );
1.97 + for( j=0; j<tracks; j++ ) {
1.98 + struct cdi_track_data trk;
1.99 +
1.100 + read( fd, &new_fmt, 4 );
1.101 + if( new_fmt != 0 ) { /* Additional data 3.00.780+ ?? */
1.102 + printf( "Note: CDI image has 3.00.780+ flag set\n" );
1.103 + lseek( fd, 8, SEEK_CUR );
1.104 + }
1.105 + read( fd, marker, 20 );
1.106 + if( memcmp( marker, track_start_marker, 20) != 0 )
1.107 + BAIL( "Track start marker not found, error reading cdi\n",NULL );
1.108 + read( fd, &tmp, 4 );
1.109 + printf( "Unknown 4 bytes: %08x\n", tmp );
1.110 + read( fd, &tmpc, 1 );
1.111 + lseek( fd, (int)tmpc, SEEK_CUR ); /* skip over the filename */
1.112 + read( fd, &trk, sizeof(trk) );
1.113 + switch( trk.sector_size ) {
1.114 + case 0: trk.sector_size = 2048; hdr=0; break;
1.115 + case 1: trk.sector_size = 2336; hdr=8; break;
1.116 + case 2:
1.117 + trk.sector_size = 2352;
1.118 + if( trk.mode == 2 ) hdr=24;
1.119 + else hdr=16;
1.120 + break;
1.121 + default: BAIL( "Unknown sector size: %d\n", trk.sector_size );
1.122 + }
1.123 + posn += hdr;
1.124 + len = trk.length*trk.sector_size;
1.125 + printf( " Track %d\n", j+1 );
1.126 + printf( " Pregap: %08x\n", trk.pregap_length );
1.127 + printf( " Length: %08x\n", trk.length );
1.128 + printf( " Mode: %d\n", trk.mode );
1.129 + printf( " Sector size: %d\n", trk.sector_size );
1.130 + printf( " Start LBA: %08x\n", trk.start_lba );
1.131 + printf( " Total length: %08x\n", trk.total_length );
1.132 + printf( " ---\n" );
1.133 + printf( " File position: %08x\n", posn+trk.pregap_length*trk.sector_size );
1.134 + printf( " File length: %d\n", len );
1.135 + posn += trk.total_length*trk.sector_size;
1.136 + lseek( fd, 12, SEEK_CUR );
1.137 + if( new_fmt )
1.138 + lseek( fd, 78, SEEK_CUR );
1.139 + tmp = lseek( fd, 0, SEEK_CUR );
1.140 + printf( "(Header offset: %x)\n", tmp - trail.header_offset );
1.141 + }
1.142 + }
1.143 +
1.144 + return NULL;
1.145 +#undef BAIL(x, ...)
1.146 +}
1.147 +
1.148 +int main(int argc, char *argv[] )
1.149 +{
1.150 + int i;
1.151 +
1.152 + for( i=1; i<argc; i++ ) {
1.153 + cdi_open(argv[i]);
1.154 + }
1.155 + return 0;
1.156 +}
1.157 +
.