⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dvd_reader.c

📁 python的多媒体包,可以实现很多漂亮的功能哦
💻 C
📖 第 1 页 / 共 2 页
字号:
										 int encrypted )
{
	int ret;
	
	ret = dvdcss_seek( device->fd, (int) lb_number, DVDCSS_SEEK_KEY );
	if( ret != (int) lb_number ) {
		//fprintf( stderr, "libdvdread: Can't seek to block %u\n", lb_number );
		return 0;
	}
	
	return dvdcss_read( device->fd, (char *) data, (int) block_count, encrypted ); 
}

/* It's required to either fail or deliver all the blocks asked for. */
int DVDReadLBUDF( dvd_reader_t *device, uint32_t lb_number,
								 size_t block_count, unsigned char *data, 
								 int encrypted )
{
  int ret;
  size_t count = block_count;
  
  while(count > 0) {
    
    ret = UDFReadBlocksRaw(device, lb_number, count, data, encrypted);
		
    if(ret <= 0) {
		/* One of the reads failed or nothing more to read, too bad.
			* We won't even bother returning the reads that went ok. */
      return ret;
    }
    
    count -= (size_t)ret;
    lb_number += (uint32_t)ret;
  }
	
  return block_count;
}

/* Reopen file by it's location */
void DVDReopen( const char *location, dvd_file_t *file )
{
	file->dvd= DVDOpen( location );
}

/* Open file by it's domain type */
dvd_file_t *DVDOpenFile( dvd_reader_t *dvd, int titlenum, dvd_read_domain_t domain )
{
	char filename[ MAX_UDF_FILE_NAME_LEN ];
	
	/* Check arguments. */
	if( dvd == NULL || titlenum < 0 )
		return NULL;
	
	switch( domain ) {
	case DVD_READ_INFO_FILE:
		if( titlenum == 0 ) {
			sprintf( filename, "/VIDEO_TS/VIDEO_TS.IFO" );
		} else {
			sprintf( filename, "/VIDEO_TS/VTS_%02i_0.IFO", titlenum );
		}
		break;
	case DVD_READ_INFO_BACKUP_FILE:
		if( titlenum == 0 ) {
			sprintf( filename, "/VIDEO_TS/VIDEO_TS.BUP" );
		} else {
			sprintf( filename, "/VIDEO_TS/VTS_%02i_0.BUP", titlenum );
		}
		break;
	case DVD_READ_MENU_VOBS:
		return DVDOpenVOBUDF( dvd, titlenum, 1 );
	case DVD_READ_TITLE_VOBS:
		if( titlenum == 0 ) return 0;
		return DVDOpenVOBUDF( dvd, titlenum, 0 );
	default:
		//fprintf( stderr, "libdvdread: Invalid domain for file open.\n" );
		return NULL;
	}
	
	return DVDOpenFileUDF( dvd, filename );
}

void DVDCloseFile( dvd_file_t *dvd_file )
{
	free( dvd_file );
}

/* This is using a single input and starting from 'dvd_file->lb_start' offset.
*
* Reads 'block_count' blocks from 'dvd_file' at block offset 'offset'
* into the buffer located at 'data' and if 'encrypted' is set
* descramble the data if it's encrypted.  Returning either an
* negative error or the number of blocks read. */
static int DVDReadBlocksUDF( dvd_file_t *dvd_file, uint32_t offset,
														size_t block_count, unsigned char *data,
														int encrypted )
{
	return UDFReadBlocksRaw( dvd_file->dvd, dvd_file->lb_start + offset,
		block_count, data, encrypted );
}

/* This is broken reading more than 2Gb at a time is ssize_t is 32-bit. */
int DVDReadBlocks( dvd_file_t *dvd_file, int offset, 
									size_t block_count, unsigned char *data )
{
	/* Check arguments. */
	if( dvd_file == NULL || offset < 0 || data == NULL )
		return -1;
	
	/* Hack, and it will still fail for multiple opens in a threaded app ! */
	if( dvd_file->dvd->css_title != dvd_file->css_title ) {
		dvd_file->dvd->css_title = dvd_file->css_title;
		/* Here each vobu has it's own dvdcss handle, so no need to update 
		else {
		dvdinput_title( dvd_file->title_devs[ 0 ], (int)dvd_file->lb_start );
	}*/
	}
	
	return DVDReadBlocksUDF( dvd_file, (unsigned int)offset, block_count, data, 1 );
}

int32_t DVDFileSeek( dvd_file_t *dvd_file, int32_t offset )
{
	/* Check arguments. */
	if( dvd_file == NULL || offset < 0 )
		return -1;
	
	dvd_file->seek_pos = (uint32_t) offset;
	return offset;
}

int DVDReadBytes( dvd_file_t *dvd_file, void *data, int byte_size )
{
	unsigned char *secbuf;
	unsigned int numsec, seek_sector, seek_byte;
	int ret;
	
	/* Check arguments. */
	if( dvd_file == NULL || data == NULL )
		return -1;
	
	seek_sector = dvd_file->seek_pos / DVD_VIDEO_LB_LEN;
	seek_byte   = dvd_file->seek_pos % DVD_VIDEO_LB_LEN;
	
	numsec = ( ( seek_byte + byte_size ) / DVD_VIDEO_LB_LEN ) +
		( ( ( seek_byte + byte_size ) % DVD_VIDEO_LB_LEN ) ? 1 : 0 );
	
	secbuf = (unsigned char *) malloc( numsec * DVD_VIDEO_LB_LEN );
	if( !secbuf ) {
		//fprintf( stderr, "libdvdread: Can't allocate memory " 
		//	"for file read!\n" );
		return 0;
	}
	
	ret = DVDReadBlocksUDF( dvd_file, seek_sector, numsec, secbuf, 0 );
	if( ret != (int) numsec ) {
		free( secbuf );
		return ret < 0 ? ret : 0;
	}
	
	memcpy( data, &(secbuf[ seek_byte ]), byte_size );
	free( secbuf );
	
	dvd_file->seek_pos += byte_size;
	return byte_size;
}

int DVDFileSize( dvd_file_t *dvd_file )
{
	/* Check arguments. */
	if( dvd_file == NULL )
		return -1;
	
	return dvd_file->filesize;
}

int DVDDiscID( dvd_reader_t *dvd, unsigned char *discid )
{
	struct md5_ctx ctx;
	int title;
	
	/* Check arguments. */
	if( dvd == NULL || discid == NULL )
		return 0;
	
    /* Go through the first 10 IFO:s, in order, 
	* and md5sum them, i.e  VIDEO_TS.IFO and VTS_0?_0.IFO */
	md5_init_ctx( &ctx );
	for( title = 0; title < 10; title++ ) {
		dvd_file_t *dvd_file = DVDOpenFile( dvd, title, DVD_READ_INFO_FILE );
		if( dvd_file != NULL ) {
			int bytes_read;
			int file_size = dvd_file->filesize * DVD_VIDEO_LB_LEN;
			char *buffer = malloc( file_size );
			
			if( buffer == NULL ) {
				//fprintf( stderr, "libdvdread: DVDDiscId, failed to "
				//	"allocate memory for file read!\n" );
				return -1;
			}
			bytes_read = DVDReadBytes( dvd_file, buffer, file_size );
			if( bytes_read != file_size ) {
				//fprintf( stderr, "libdvdread: DVDDiscId read returned %d bytes"
				//	", wanted %d\n", bytes_read, file_size );
				DVDCloseFile( dvd_file );
				return -1;
			}
			
			md5_process_bytes( buffer, file_size,  &ctx );
			
			DVDCloseFile( dvd_file );
			free( buffer );
		}
	}
	md5_finish_ctx( &ctx, discid );
	
	return 0;
}


int DVDISOVolumeInfo( dvd_reader_t *dvd,
										 char *volid, unsigned int volid_size,
										 unsigned char *volsetid, unsigned int volsetid_size )
{
  unsigned char *buffer;
  int ret;
	
  /* Check arguments. */
  if( dvd == NULL )
    return 0;
  
  if( dvd->fd == NULL ) {
    /* No block access, so no ISO... */
    return -1;
  }
  
  buffer = malloc( DVD_VIDEO_LB_LEN );
  if( buffer == NULL ) {
    fprintf( stderr, "libdvdread: DVDISOVolumeInfo, failed to "
	     "allocate memory for file read!\n" );
    return -1;
  }
	
  ret = UDFReadBlocksRaw( dvd, 16, 1, buffer, 0 );
  if( ret != 1 ) {
    fprintf( stderr, "libdvdread: DVDISOVolumeInfo, failed to "
	     "read ISO9660 Primary Volume Descriptor!\n" );
    return -1;
  }
  
  if( (volid != NULL) && (volid_size > 0) ) {
    unsigned int n;
    for(n = 0; n < 32; n++) {
      if(buffer[40+n] == 0x20) {
				break;
      }
    }
    
    if(volid_size > n+1) {
      volid_size = n+1;
    }
		
    memcpy(volid, &buffer[40], volid_size-1);
    volid[volid_size-1] = '\0';
  }
  
  if( (volsetid != NULL) && (volsetid_size > 0) ) {
    if(volsetid_size > 128) {
      volsetid_size = 128;
    }
    memcpy(volsetid, &buffer[190], volsetid_size);
  }
  return 0;
}


int DVDUDFVolumeInfo( dvd_reader_t *dvd,
										 char *volid, unsigned int volid_size,
										 unsigned char *volsetid, unsigned int volsetid_size )
{
  int ret;
  /* Check arguments. */
  if( dvd == NULL )
    return -1;
  
  if( dvd->fd == NULL ) {
    /* No block access, so no UDF VolumeSet Identifier */
    return -1;
  }
  
  if( (volid != NULL) && (volid_size > 0) ) {
    ret = UDFGetVolumeIdentifier(dvd, volid, volid_size);
    if(!ret) {
      return -1;
    }
  }
  if( (volsetid != NULL) && (volsetid_size > 0) ) {
    ret =  UDFGetVolumeSetIdentifier(dvd, volsetid, volsetid_size);
    if(!ret) {
      return -1;
    }
  }
	
  return 0;  
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -