From 8296df8b3dc6f2cd3d8f23411f6948e712f19175 Mon Sep 17 00:00:00 2001 From: rocky Date: Thu, 10 Feb 2005 01:59:05 +0000 Subject: [PATCH] Add generic mode_sense(), add cdio_have_atapi() and use these. API number bumped Add bool_3way_t (yes, nope, dunno) --- include/cdio/cdio.h | 4 +- include/cdio/device.h | 5 ++- include/cdio/mmc.h | 38 +++++++++++----- include/cdio/types.h | 8 +++- lib/cdda_interface/interface.c | 6 +-- lib/driver/device.c | 80 +++++++++++++++++++++++++++++++++- lib/driver/libcdio.sym | 5 +++ lib/driver/mmc.c | 54 +++++++++++++++++------ lib/iso9660/iso9660_fs.c | 11 +---- 9 files changed, 168 insertions(+), 43 deletions(-) diff --git a/include/cdio/cdio.h b/include/cdio/cdio.h index 5424f1cb..97243f3a 100644 --- a/include/cdio/cdio.h +++ b/include/cdio/cdio.h @@ -1,5 +1,5 @@ /* -*- c -*- - $Id: cdio.h,v 1.79 2005/02/05 14:42:28 rocky Exp $ + $Id: cdio.h,v 1.80 2005/02/10 01:59:05 rocky Exp $ Copyright (C) 2001 Herbert Valerio Riedel Copyright (C) 2003, 2004, 2005 Rocky Bernstein @@ -32,7 +32,7 @@ /** Application Interface or Protocol version number. If the public * interface changes, we increase this number. */ -#define CDIO_API_VERSION 4 +#define CDIO_API_VERSION 5 #include diff --git a/include/cdio/device.h b/include/cdio/device.h index 8780851a..87dfeb6f 100644 --- a/include/cdio/device.h +++ b/include/cdio/device.h @@ -1,5 +1,5 @@ /* -*- c -*- - $Id: device.h,v 1.12 2005/02/06 11:13:37 rocky Exp $ + $Id: device.h,v 1.13 2005/02/10 01:59:06 rocky Exp $ Copyright (C) 2005 Rocky Bernstein @@ -282,6 +282,9 @@ extern "C" { */ int cdio_get_media_changed(CdIo_t *p_cdio); + /*! True if CD-ROM understand ATAPI commands. */ + bool_3way_t cdio_have_atapi (CdIo_t *p_cdio); + /*! True if AIX driver is available. */ bool cdio_have_aix (void); diff --git a/include/cdio/mmc.h b/include/cdio/mmc.h index 4108e6c8..f8069357 100644 --- a/include/cdio/mmc.h +++ b/include/cdio/mmc.h @@ -1,5 +1,5 @@ /* - $Id: mmc.h,v 1.5 2005/02/09 02:50:47 rocky Exp $ + $Id: mmc.h,v 1.6 2005/02/10 01:59:06 rocky Exp $ Copyright (C) 2003, 2004, 2005 Rocky Bernstein @@ -391,7 +391,7 @@ uint8_t mmc_get_cmd_len(uint8_t scsi_cmd); Set the block size for subsequest read requests, via an MMC MODE_SENSE 6 command. */ -int mmc_get_blocksize ( const CdIo_t *p_cdio ); +int mmc_get_blocksize ( CdIo_t *p_cdio ); /*! Get the lsn of the end of the CD @@ -416,10 +416,10 @@ discmode_t mmc_get_discmode( const CdIo_t *p_cdio ); Get drive capabilities for a device. @return the drive capabilities. */ -void mmc_get_drive_cap (const CdIo_t *p_cdio, - /*out*/ cdio_drive_read_cap_t *p_read_cap, - /*out*/ cdio_drive_write_cap_t *p_write_cap, - /*out*/ cdio_drive_misc_cap_t *p_misc_cap); +void mmc_get_drive_cap ( CdIo_t *p_cdio, + /*out*/ cdio_drive_read_cap_t *p_read_cap, + /*out*/ cdio_drive_write_cap_t *p_write_cap, + /*out*/ cdio_drive_misc_cap_t *p_misc_cap); /*! Get the DVD type associated with cd object. @@ -465,15 +465,29 @@ char * mmc_get_mcn ( const CdIo_t *p_cdio ); routine could probably return the sincle mmc_feature_interface_t. @return true if we have the interface and false if not. */ -bool mmc_have_interface( const CdIo_t *p_cdio, - mmc_feature_interface_t e_interface ); +bool_3way_t mmc_have_interface( CdIo_t *p_cdio, + mmc_feature_interface_t e_interface ); -/*! Run a MODE_SENSE_10 and put the results in p_buf */ -int mmc_mode_sense_10( const CdIo_t *p_cdio, void *p_buf, int i_size, +/*! Run a MODE_SENSE command (6- or 10-byte version) + and put the results in p_buf + @return DRIVER_OP_SUCCESS if we ran the command ok. +*/ +int mmc_mode_sense( CdIo_t *p_cdio, /*out*/ void *p_buf, int i_size, + int page); + + +/*! Run a MODE_SENSE command (10-byte version) + and put the results in p_buf + @return DRIVER_OP_SUCCESS if we ran the command ok. +*/ +int mmc_mode_sense_10( CdIo_t *p_cdio, /*out*/ void *p_buf, int i_size, int page); -/*! Run a MODE_SENSE_6 and put the results in p_buf */ -int mmc_mode_sense_6( const CdIo_t *p_cdio, void *p_buf, int i_size, +/*! Run a MODE_SENSE command (6-byte version) + and put the results in p_buf + @return DRIVER_OP_SUCCESS if we ran the command ok. +*/ +int mmc_mode_sense_6( CdIo_t *p_cdio, /*out*/ void *p_buf, int i_size, int page); diff --git a/include/cdio/types.h b/include/cdio/types.h index 128ded9f..02451b25 100644 --- a/include/cdio/types.h +++ b/include/cdio/types.h @@ -1,5 +1,5 @@ /* - $Id: types.h,v 1.25 2005/01/04 04:33:36 rocky Exp $ + $Id: types.h,v 1.26 2005/02/10 01:59:06 rocky Exp $ Copyright (C) 2000 Herbert Valerio Riedel Copyright (C) 2002, 2003, 2004 Rocky Bernstein @@ -192,6 +192,12 @@ extern "C" { #define msf_t_SIZEOF 3 + typedef enum { + nope = 0, + yep = 1, + dunno = 2 + } bool_3way_t; + /* type used for bit-fields in structs (1 <= bits <= 8) */ #if defined(__GNUC__) /* this is strict ISO C99 which allows only 'unsigned int', 'signed diff --git a/lib/cdda_interface/interface.c b/lib/cdda_interface/interface.c index b7e63cff..c852be25 100644 --- a/lib/cdda_interface/interface.c +++ b/lib/cdda_interface/interface.c @@ -1,5 +1,5 @@ /* - $Id: interface.c,v 1.21 2005/02/07 03:36:02 rocky Exp $ + $Id: interface.c,v 1.22 2005/02/10 01:59:06 rocky Exp $ Copyright (C) 2005 Rocky Bernstein Copyright (C) 1998 Monty xiphmont@mit.edu @@ -121,8 +121,8 @@ cdio_cddap_open(cdrom_drive_t *d) /* d->select_speed(d,d->maxspeed); most drives are full speed by default */ if ( -1 == d->bigendianp ) { - if (mmc_have_interface(d->p_cdio, CDIO_MMC_FEATURE_INTERFACE_ATAPI)) - /* Is this right? */ + if (yep == cdio_have_atapi(d->p_cdio)) + /* Is this right? Might we also have to check for SCSI ATAPI? */ d->bigendianp = 1; else d->bigendianp = data_bigendianp(d); diff --git a/lib/driver/device.c b/lib/driver/device.c index 291bcada..96d50fbc 100644 --- a/lib/driver/device.c +++ b/lib/driver/device.c @@ -1,5 +1,5 @@ /* - $Id: device.c,v 1.9 2005/02/06 11:13:37 rocky Exp $ + $Id: device.c,v 1.10 2005/02/10 01:59:06 rocky Exp $ Copyright (C) 2005 Rocky Bernstein @@ -37,6 +37,14 @@ #include #endif +/* This probably will get moved to driver code, i.e _cdio_linux.c */ +#ifdef HAVE_LINUX_MAJOR_H +#include +#endif +#ifdef HAVE_SYS_STAT_H +#include +#endif + /* The below array gives of the drivers that are currently available for on a particular host. */ @@ -583,6 +591,76 @@ cdio_get_media_changed(CdIo_t *p_cdio) return DRIVER_OP_UNSUPPORTED; } +bool_3way_t +cdio_have_atapi(CdIo_t *p_cdio) +{ + bool_3way_t i_status; + + if (!p_cdio) return nope; + i_status = mmc_have_interface(p_cdio, CDIO_MMC_FEATURE_INTERFACE_ATAPI); + if (dunno != i_status) return i_status; + + { + /* cdparanoia seems to think that if we have a mode sense command + we have an atapi drive or is atapi compatible. + */ + uint8_t buf[22]; + if (DRIVER_OP_SUCCESS == mmc_mode_sense(p_cdio, buf, sizeof(buf), + CDIO_MMC_CAPABILITIES_PAGE) ) { + uint8_t *b = buf; + b+=b[3]+4; + if( CDIO_MMC_CAPABILITIES_PAGE == (b[0]&0x3F) ) { + /* MMC style drive! */ + return yep; + } + } + } + + /* Put these in the various drivers? If we get more, yes! + */ +#ifdef HAVE_LINUX_MAJOR_H + { + /* This too is from cdparanoia. */ + struct stat st; + generic_img_private_t *p_env = p_cdio->env; + if ( 0 == lstat(p_env->source_name, &st) ) { + if (S_ISCHR(st.st_mode) || S_ISBLK(st.st_mode)) { + int drive_type=(int)(st.st_rdev>>8); + switch (drive_type) { + case IDE0_MAJOR: + case IDE1_MAJOR: + case IDE2_MAJOR: + case IDE3_MAJOR: + /* Yay, ATAPI... */ + return yep; + break; + case CDU31A_CDROM_MAJOR: + case CDU535_CDROM_MAJOR: + case MATSUSHITA_CDROM_MAJOR: + case MATSUSHITA_CDROM2_MAJOR: + case MATSUSHITA_CDROM3_MAJOR: + case MATSUSHITA_CDROM4_MAJOR: + case SANYO_CDROM_MAJOR: + case MITSUMI_CDROM_MAJOR: + case MITSUMI_X_CDROM_MAJOR: + case OPTICS_CDROM_MAJOR: + case AZTECH_CDROM_MAJOR: + case GOLDSTAR_CDROM_MAJOR: + case CM206_CDROM_MAJOR: + case SCSI_CDROM_MAJOR: + case SCSI_GENERIC_MAJOR: + return nope; + break; + default: + return dunno; + } + } + } + } +#endif /*HAVE_LINUX_MAJOR_H*/ + return dunno; +} + bool cdio_have_driver(driver_id_t driver_id) { diff --git a/lib/driver/libcdio.sym b/lib/driver/libcdio.sym index 3d27063d..49452310 100644 --- a/lib/driver/libcdio.sym +++ b/lib/driver/libcdio.sym @@ -55,6 +55,7 @@ cdio_get_first_track_num cdio_get_hwinfo cdio_get_joliet_level cdio_get_last_track_num +cdio_get_media_changed cdio_get_mcn cdio_get_num_tracks cdio_get_track @@ -69,6 +70,7 @@ cdio_get_track_msf cdio_get_track_preemphasis cdio_get_track_sec_count cdio_guess_cd_type +cdio_have_atapi cdio_have_bincue cdio_have_bsdi cdio_have_cdrdao @@ -159,6 +161,9 @@ mmc_get_last_lsn mmc_feature2str mmc_feature_profile2str mmc_have_interface +mmc_mode_sense +mmc_mode_sense_10 +mmc_mode_sense_6 mmc_read_sectors mmc_run_cmd mmc_set_blocksize diff --git a/lib/driver/mmc.c b/lib/driver/mmc.c index 8b873ec4..8b1f128e 100644 --- a/lib/driver/mmc.c +++ b/lib/driver/mmc.c @@ -1,6 +1,6 @@ /* Common Multimedia Command (MMC) routines. - $Id: mmc.c,v 1.6 2005/02/09 02:50:47 rocky Exp $ + $Id: mmc.c,v 1.7 2005/02/10 01:59:06 rocky Exp $ Copyright (C) 2004, 2005 Rocky Bernstein @@ -249,8 +249,29 @@ mmc_get_mcn_private ( void *p_env, return NULL; } +/* Run a MODE SENSE command (either the 6- or 10-byte version + @return DRIVER_OP_SUCCESS if we ran the command ok. + */ int -mmc_mode_sense_6( const CdIo_t *p_cdio, void *p_buf, int i_size, int page) +mmc_mode_sense( CdIo_t *p_cdio, /*out*/ void *p_buf, int i_size, + int page) +{ + if ( cdio_have_atapi(p_cdio) ) { + if ( DRIVER_OP_SUCCESS == mmc_mode_sense_6(p_cdio, p_buf, i_size, page) ) + return DRIVER_OP_SUCCESS; + return mmc_mode_sense_10(p_cdio, p_buf, i_size, page); + } + if ( DRIVER_OP_SUCCESS == mmc_mode_sense_10(p_cdio, p_buf, i_size, page) ) + return DRIVER_OP_SUCCESS; + return mmc_mode_sense_6(p_cdio, p_buf, i_size, page); +} + +/*! Run a MODE_SENSE command (6-byte version) + and put the results in p_buf + @return DRIVER_OP_SUCCESS if we ran the command ok. +*/ +int +mmc_mode_sense_6( CdIo_t *p_cdio, void *p_buf, int i_size, int page) { scsi_mmc_cdb_t cdb = {{0, }}; @@ -271,8 +292,12 @@ mmc_mode_sense_6( const CdIo_t *p_cdio, void *p_buf, int i_size, int page) } +/*! Run a MODE_SENSE command (10-byte version) + and put the results in p_buf + @return DRIVER_OP_SUCCESS if we ran the command ok. +*/ int -mmc_mode_sense_10( const CdIo_t *p_cdio, void *p_buf, int i_size, int page) +mmc_mode_sense_10( CdIo_t *p_cdio, void *p_buf, int i_size, int page) { scsi_mmc_cdb_t cdb = {{0, }}; @@ -500,10 +525,10 @@ mmc_get_discmode( const CdIo_t *p_cdio ) } void -mmc_get_drive_cap (const CdIo_t *p_cdio, - /*out*/ cdio_drive_read_cap_t *p_read_cap, - /*out*/ cdio_drive_write_cap_t *p_write_cap, - /*out*/ cdio_drive_misc_cap_t *p_misc_cap) +mmc_get_drive_cap (CdIo_t *p_cdio, + /*out*/ cdio_drive_read_cap_t *p_read_cap, + /*out*/ cdio_drive_write_cap_t *p_write_cap, + /*out*/ cdio_drive_misc_cap_t *p_misc_cap) { if ( ! p_cdio ) return; /* Largest buffer size we use. */ @@ -688,7 +713,7 @@ mmc_run_cmd( const CdIo_t *p_cdio, unsigned int i_timeout_ms, } int -mmc_get_blocksize ( const CdIo_t *p_cdio) +mmc_get_blocksize ( CdIo_t *p_cdio) { int i_status; @@ -915,8 +940,8 @@ const char *mmc_feature_profile2str( int i_feature_profile ) * See if CD-ROM has feature with value value * @return true if we have the feature and false if not. */ -bool -mmc_have_interface( const CdIo_t *p_cdio, mmc_feature_interface_t interface ) +bool_3way_t +mmc_have_interface( CdIo_t *p_cdio, mmc_feature_interface_t e_interface ) { int i_status; /* Result of MMC command */ uint8_t buf[500] = { 0, }; /* Place to hold returned data */ @@ -929,7 +954,7 @@ mmc_have_interface( const CdIo_t *p_cdio, mmc_feature_interface_t interface ) i_status = mmc_run_cmd(p_cdio, 0, &cdb, SCSI_MMC_DATA_READ, sizeof(buf), &buf); - if (i_status == 0) { + if (DRIVER_OP_SUCCESS == i_status) { uint8_t *p; uint32_t i_data; uint8_t *p_max = buf + 65530; @@ -945,12 +970,13 @@ mmc_have_interface( const CdIo_t *p_cdio, mmc_feature_interface_t interface ) if (CDIO_MMC_FEATURE_CORE == i_feature) { uint8_t *q = p+4; uint32_t i_interface_standard = CDIO_MMC_GET_LEN32(q); - if (interface == i_interface_standard) return true; + if (e_interface == i_interface_standard) return yep; } p += i_feature_additional + 4; } - } - return false; + return nope; + } else + return dunno; } /*! Read sectors using SCSI-MMC GPCMD_READ_CD. diff --git a/lib/iso9660/iso9660_fs.c b/lib/iso9660/iso9660_fs.c index 393b6624..6c3d195f 100644 --- a/lib/iso9660/iso9660_fs.c +++ b/lib/iso9660/iso9660_fs.c @@ -1,5 +1,5 @@ /* - $Id: iso9660_fs.c,v 1.10 2005/02/06 11:32:22 rocky Exp $ + $Id: iso9660_fs.c,v 1.11 2005/02/10 01:59:06 rocky Exp $ Copyright (C) 2001 Herbert Valerio Riedel Copyright (C) 2003, 2004, 2005 Rocky Bernstein @@ -51,14 +51,7 @@ #include -typedef enum { - nope = 0, - yep = 1, - dunno = 2 -} bool_3way_t; - - -static const char _rcsid[] = "$Id: iso9660_fs.c,v 1.10 2005/02/06 11:32:22 rocky Exp $"; +static const char _rcsid[] = "$Id: iso9660_fs.c,v 1.11 2005/02/10 01:59:06 rocky Exp $"; /* Implementation of iso9660_t type */ struct _iso9660 {