#include <libvcd/info.h>
#include <libvcd/logging.h>
+#define FREE_AND_NULL(ptr) if (NULL != ptr) free(ptr); ptr = NULL;
+
/* how many blocks VCDRead will read in each loop */
#define VCD_BLOCKS_ONCE 20
va_list args );
/* Now those which are strictly internal */
-static void VCDSetOrigin ( access_t *p_access,
- lsn_t origin_lsn,
- lsn_t i_lsn, lsn_t end_lsn,
- track_t track,
+static void VCDSetOrigin ( access_t *p_access, lsn_t i_lsn,
+ track_t track,
const vcdinfo_itemid_t * p_itemid );
static int VCDEntryPoints ( access_t * );
static int VCDLIDs ( access_t * );
static void
cdio_log_handler (cdio_log_level_t level, const char message[])
{
- const access_vcd_data_t *p_vcd = (access_vcd_data_t *)p_vcd_access->p_sys;
+ const vcdplayer_t *p_vcd = (vcdplayer_t *)p_vcd_access->p_sys;
switch (level) {
case CDIO_LOG_DEBUG:
case CDIO_LOG_INFO:
static void
vcd_log_handler (vcd_log_level_t level, const char message[])
{
- access_vcd_data_t *p_vcd = (access_vcd_data_t *)p_vcd_access->p_sys;
+ vcdplayer_t *p_vcd = (vcdplayer_t *)p_vcd_access->p_sys;
switch (level) {
case VCD_LOG_DEBUG:
case VCD_LOG_INFO:
static block_t *
VCDReadBlock( access_t * p_access )
{
- access_vcd_data_t * p_vcd= (access_vcd_data_t *)p_access->p_sys;
- block_t *p_block;
- int i_blocks = VCD_BLOCKS_ONCE;
- int i_read;
- byte_t p_last_sector[ M2F2_SECTOR_SIZE ];
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
+ block_t *p_block;
+ int i_blocks = VCD_BLOCKS_ONCE;
+ int i_read;
+ byte_t p_last_sector[ M2F2_SECTOR_SIZE ];
i_read = 0;
+#if 0
dbg_print( (INPUT_DBG_CALL), "lsn: %lu",
(long unsigned int) p_vcd->i_lsn );
+#endif
/* Compute the number of blocks we have to read */
for ( i_read = 0 ; i_read < i_blocks ; i_read++ )
{
- if ( p_vcd->i_lsn == p_vcd->end_lsn ) {
+ if ( p_vcd->i_lsn >= p_vcd->end_lsn ) {
vcdplayer_read_status_t read_status;
/* We've run off of the end of this entry. Do we continue or stop? */
dbg_print( (INPUT_DBG_LSN|INPUT_DBG_PBC),
- "end reached, cur: %lu",
- (long unsigned int) p_vcd->i_lsn );
+ "end reached, cur: %lu, end: %u",
+ (long unsigned int) p_vcd->i_lsn,
+ p_vcd->end_lsn);
read_status = vcdplayer_pbc_is_on( p_vcd )
? vcdplayer_pbc_nav( p_access )
p_vcd->play_item.num = i_entry;
dbg_print( (INPUT_DBG_LSN|INPUT_DBG_PBC), "entry change" );
VCDSetOrigin( p_access,
- vcdinfo_get_track_lba(p_vcd->vcd, i_track),
vcdinfo_get_entry_lba(p_vcd->vcd, i_entry),
- vcdinfo_get_track_lba(p_vcd->vcd, i_track+1),
i_track, &(p_vcd->play_item) );
}
}
if (!p_access || !p_access->p_sys) return VLC_EGENERIC;
{
- access_vcd_data_t *p_vcd =
- (access_vcd_data_t *)p_vcd_access->p_sys;
+ vcdplayer_t *p_vcd = (vcdplayer_t *)p_vcd_access->p_sys;
const input_title_t *t = p_vcd->p_title[p_access->info.i_title];
int i_seekpoint;
unsigned int i_entry=VCDINFO_INVALID_ENTRY;
/* Next sector to read */
p_access->info.i_pos = i_pos;
p_vcd->i_lsn = (i_pos / (int64_t)M2F2_SECTOR_SIZE) +
- p_vcd->origin_lsn;
+ p_vcd->track_lsn;
/* Find entry */
if( p_vcd->b_valid_ep )
}
p_vcd->play_item.num = i_entry;
p_vcd->play_item.type = VCDINFO_ITEM_TYPE_ENTRY;
+ vcdplayer_set_origin(p_access);
+ VCDUpdateTitle(p_access);
}
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_EXT|INPUT_DBG_SEEK),
{
- access_vcd_data_t *p_vcd= (access_vcd_data_t *)p_access->p_sys;
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
#if 0
const vlc_bool_t b_was_still = p_vcd->in_still;
#endif
}
p_vcd->in_still = VLC_FALSE;
VCDSetOrigin( p_access,
- vcdinfo_get_track_lba(p_vcd->vcd, i_track),
vcdinfo_get_entry_lba(p_vcd->vcd, i_entry),
- vcdinfo_get_track_lba(p_vcd->vcd, i_track+1),
i_track, &itemid );
break;
}
default:
p_vcd->in_still = VLC_FALSE;
}
- VCDSetOrigin( p_access, p_vcd->p_segments[i_seg],
- p_vcd->p_segments[i_seg],
- p_vcd->p_segments[i_seg+1],
+ VCDSetOrigin( p_access, p_vcd->p_segments[i_seg],
0, &itemid );
}
track_t i_track = vcdinfo_get_track(p_vcd->vcd, i_entry);
p_vcd->in_still = VLC_FALSE;
VCDSetOrigin( p_access,
- vcdinfo_get_entry_lba(p_vcd->vcd, i_track),
vcdinfo_get_entry_lba(p_vcd->vcd, i_entry),
- vcdinfo_get_entry_lba(p_vcd->vcd, i_track+1),
i_track, &itemid );
}
break;
if (!p_access || !p_access->p_sys) return VLC_EGENERIC;
{
- access_vcd_data_t *p_vcd = (access_vcd_data_t *) p_access->p_sys;
+ vcdplayer_t *p_vcd = (vcdplayer_t *) p_access->p_sys;
const unsigned int i_entries = vcdinfo_get_num_entries(p_vcd->vcd);
const track_t i_last_track
= cdio_get_num_tracks(vcdinfo_get_cd_image(p_vcd->vcd))
static int
VCDSegments( access_t * p_access )
{
- access_vcd_data_t * p_vcd;
- unsigned int i;
- unsigned int i_segments;
+ vcdplayer_t *p_vcd;
+ unsigned int i;
+ unsigned int i_segments;
- p_vcd = (access_vcd_data_t *) p_access->p_sys;
+ p_vcd = (vcdplayer_t *) p_access->p_sys;
i_segments = p_vcd->num_segments = vcdinfo_get_num_segments(p_vcd->vcd);
#define area p_access->stream.pp_areas
if (!p_access || !p_access->p_sys) return VLC_EGENERIC;
{
- access_vcd_data_t *p_vcd = (access_vcd_data_t *) p_access->p_sys;
+ vcdplayer_t *p_vcd = (vcdplayer_t *) p_access->p_sys;
track_t i;
p_vcd->i_titles = 0;
static int
VCDLIDs( access_t * p_access )
{
- access_vcd_data_t *p_vcd = (access_vcd_data_t *) p_access->p_sys;
+ vcdplayer_t *p_vcd = (vcdplayer_t *) p_access->p_sys;
p_vcd->i_lids = vcdinfo_get_num_LIDs(p_vcd->vcd);
p_vcd->i_lid = VCDINFO_INVALID_ENTRY;
VCDParse( access_t * p_access, /*out*/ vcdinfo_itemid_t * p_itemid,
/*out*/ vlc_bool_t *play_single_item )
{
- access_vcd_data_t *p_vcd = (access_vcd_data_t *)p_access->p_sys;
- char * psz_parser;
- char * psz_source;
- char * psz_next;
+ vcdplayer_t *p_vcd = (vcdplayer_t *)p_access->p_sys;
+ char *psz_parser;
+ char *psz_source;
+ char *psz_next;
if( config_GetInt( p_access, MODULE_STRING "-PBC" ) ) {
p_itemid->type = VCDINFO_ITEM_TYPE_LID;
Set's start origin subsequent seeks/reads
*/
static void
-VCDSetOrigin( access_t *p_access, lsn_t origin_lsn,
- lsn_t i_lsn, lsn_t end_lsn, track_t i_track,
+VCDSetOrigin( access_t *p_access, lsn_t i_lsn, track_t i_track,
const vcdinfo_itemid_t *p_itemid )
{
- access_vcd_data_t *p_vcd= (access_vcd_data_t *)p_access->p_sys;
-
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
+
unsigned int i_title = i_track - 1; /* For now */
- p_vcd->origin_lsn = origin_lsn;
p_vcd->i_lsn = i_lsn;
- p_vcd->end_lsn = end_lsn;
p_vcd->i_track = i_track;
+ p_vcd->track_lsn = vcdinfo_get_track_lsn(p_vcd->vcd, i_track);
+
p_vcd->play_item.num = p_itemid->num;
p_vcd->play_item.type = p_itemid->type;
+ vcdplayer_set_origin(p_access);
+
p_access->info.i_title = i_track-1;
p_access->info.i_size = p_vcd->p_title[i_title]->i_size;
- p_access->info.i_pos = ( i_lsn - origin_lsn ) * M2F2_SECTOR_SIZE;
+ p_access->info.i_pos = ( i_lsn - p_vcd->track_lsn )
+ * M2F2_SECTOR_SIZE;
p_access->info.i_update |= INPUT_UPDATE_TITLE|INPUT_UPDATE_SIZE
| INPUT_UPDATE_SEEKPOINT;
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_LSN),
- "origin: %lu, cur_lsn: %lu, end_lsn: %lu, track: %d",
- (long unsigned int) origin_lsn,
- (long unsigned int) i_lsn,
- (long unsigned int) end_lsn, i_track );
+ "i_lsn: %lu, track: %d", (long unsigned int) i_lsn,
+ i_track );
if (p_itemid->type == VCDINFO_ITEM_TYPE_ENTRY) {
VCDUpdateVar( p_access, p_itemid->num, VLC_VAR_SETVALUE,
"chapter", _("Segment"), "Setting entry/segment");
/* seekpoint is what? ??? */
}
-
- {
- unsigned int psz_mrl_max = strlen(VCD_MRL_PREFIX)
- + strlen(p_vcd->psz_source) + sizeof("@E999")+3;
- char *psz_mrl = malloc( psz_mrl_max );
-
- if( psz_mrl )
- {
- char *psz_name;
- snprintf(psz_mrl, psz_mrl_max, "%s%s",
- VCD_MRL_PREFIX, p_vcd->psz_source);
- psz_name = VCDFormatStr( p_access, p_vcd,
- config_GetPsz( p_access, MODULE_STRING
- "-title-format" ),
- psz_mrl, &(p_vcd->play_item) );
- input_Control( p_vcd->p_input, INPUT_SET_NAME, psz_name );
- free(psz_mrl);
- }
- }
+ VCDUpdateTitle( p_access );
+
}
/*****************************************************************************
- * vcd_Open: Opens a VCD device or file and returns an opaque handle
+ * vcd_Open: Opens a VCD device or file initializes, a list of
+ tracks, segements and entry lsns and sizes and returns an opaque handle.
*****************************************************************************/
static vcdinfo_obj_t *
vcd_Open( vlc_object_t *p_this, const char *psz_dev )
{
+ access_t *p_access = (access_t *)p_this;
+ vcdplayer_t *p_vcd = (vcdplayer_t *) p_access->p_sys;
vcdinfo_obj_t *p_vcdobj;
char *actual_dev;
+ unsigned int i;
+
+ dbg_print(INPUT_DBG_CALL, "called with %s\n", psz_dev);
if( !psz_dev ) return NULL;
}
free(actual_dev);
+ /*
+ Save summary info on tracks, segments and entries...
+ */
+
+ if ( 0 < (p_vcd->i_tracks = vcdinfo_get_num_tracks(p_vcdobj)) ) {
+ p_vcd->track = (vcdplayer_play_item_info_t *)
+ calloc(p_vcd->i_tracks, sizeof(vcdplayer_play_item_info_t));
+
+ for (i=0; i<p_vcd->i_tracks; i++) {
+ unsigned int track_num=i+1;
+ p_vcd->track[i].size =
+ vcdinfo_get_track_sect_count(p_vcdobj, track_num);
+ p_vcd->track[i].start_LSN =
+ vcdinfo_get_track_lsn(p_vcdobj, track_num);
+ }
+ } else
+ p_vcd->track = NULL;
+
+ if ( 0 < (p_vcd->i_entries = vcdinfo_get_num_entries(p_vcdobj)) ) {
+ p_vcd->entry = (vcdplayer_play_item_info_t *)
+ calloc(p_vcd->i_entries, sizeof(vcdplayer_play_item_info_t));
+
+ for (i=0; i<p_vcd->i_entries; i++) {
+ p_vcd->entry[i].size = vcdinfo_get_entry_sect_count(p_vcdobj, i);
+ p_vcd->entry[i].start_LSN = vcdinfo_get_entry_lba(p_vcdobj, i);
+ }
+ } else
+ p_vcd->entry = NULL;
+
+ if ( 0 < (p_vcd->i_segments = vcdinfo_get_num_segments(p_vcdobj)) ) {
+ p_vcd->segment = (vcdplayer_play_item_info_t *)
+ calloc(p_vcd->i_segments, sizeof(vcdplayer_play_item_info_t));
+
+ for (i=0; i<p_vcd->i_segments; i++) {
+ p_vcd->segment[i].size = vcdinfo_get_seg_sector_count(p_vcdobj, i);
+ p_vcd->segment[i].start_LSN = vcdinfo_get_seg_lba(p_vcdobj, i);
+ }
+ } else
+ p_vcd->segment = NULL;
+
+
return p_vcdobj;
}
vlc_value_t val;
val.i_int = i_num;
if (p_access) {
- const access_vcd_data_t *p_vcd = (access_vcd_data_t *)p_vcd_access->p_sys;
+ const vcdplayer_t *p_vcd = (vcdplayer_t *)p_vcd_access->p_sys;
dbg_print( INPUT_DBG_PBC, "%s %d", p_debug_label, i_num );
}
if (p_label) {
E_(DebugCallback) ( vlc_object_t *p_this, const char *psz_name,
vlc_value_t oldval, vlc_value_t val, void *p_data )
{
- access_vcd_data_t *p_vcd;
+ vcdplayer_t *p_vcd;
if (NULL == p_vcd_access) return VLC_EGENERIC;
- p_vcd = (access_vcd_data_t *)p_vcd_access->p_sys;
+ p_vcd = (vcdplayer_t *)p_vcd_access->p_sys;
if (p_vcd->i_debug & (INPUT_DBG_CALL|INPUT_DBG_EXT)) {
msg_Dbg( p_vcd_access, "Old debug (x%0x) %d, new debug (x%0x) %d",
int
E_(VCDOpen) ( vlc_object_t *p_this )
{
- access_t * p_access = (access_t *)p_this;
- access_vcd_data_t * p_vcd;
- char * psz_source;
- vcdinfo_itemid_t itemid;
- vlc_bool_t b_play_ok;
- vlc_bool_t play_single_item = VLC_FALSE;
+ access_t *p_access = (access_t *)p_this;
+ vcdplayer_t *p_vcd;
+ char *psz_source;
+ vcdinfo_itemid_t itemid;
+ vlc_bool_t b_play_ok;
+ vlc_bool_t play_single_item = VLC_FALSE;
p_access->pf_read = NULL;
p_access->pf_block = VCDReadBlock;
p_access->info.i_title = 0;
p_access->info.i_seekpoint = 0;
- p_vcd = malloc( sizeof(access_vcd_data_t) );
+ p_vcd = malloc( sizeof(vcdplayer_t) );
if( p_vcd == NULL )
{
void
E_(VCDClose) ( vlc_object_t *p_this )
{
- access_t *p_access = (access_t *)p_this;
- access_vcd_data_t *p_vcd = (access_vcd_data_t *)p_access->p_sys;
+ access_t *p_access = (access_t *)p_this;
+ vcdplayer_t *p_vcd = (vcdplayer_t *)p_access->p_sys;
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_EXT), "VCDClose" );
vcdinfo_close( p_vcd->vcd );
- free( p_vcd->p_entries );
- free( p_vcd->p_segments );
- free( p_vcd->psz_source );
-
- /* For reasons that are a mystery to me we don't have to deal with
- stopping, and destroying the p_vcd->p_intf thread. And if we do
- it causes problems upstream.
- */
- if( p_vcd->p_intf != NULL )
- {
- p_vcd->p_intf = NULL;
- }
+ FREE_AND_NULL( p_vcd->p_entries );
+ FREE_AND_NULL( p_vcd->p_segments );
+ FREE_AND_NULL( p_vcd->psz_source );
+ FREE_AND_NULL( p_vcd->track );
+ FREE_AND_NULL( p_vcd->segment );
+ FREE_AND_NULL( p_vcd->entry );
free( p_vcd );
p_access->p_sys = NULL;
*****************************************************************************/
static int VCDControl( access_t *p_access, int i_query, va_list args )
{
- access_vcd_data_t * p_vcd= (access_vcd_data_t *)p_access->p_sys;
- int *pi_int;
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
+ int *pi_int;
int i;
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_EXT|INPUT_DBG_EVENT),
itemid.type = VCDINFO_ITEM_TYPE_TRACK;
VCDSetOrigin(p_access,
- vcdinfo_get_track_lba(p_vcd->vcd, i_track),
vcdinfo_get_entry_lba(p_vcd->vcd, i_entry),
- vcdinfo_get_track_lba(p_vcd->vcd, i_track+1),
i_track, &itemid );
}
break;
p_vcd->play_item.type = VCDINFO_ITEM_TYPE_ENTRY;
VCDSetOrigin( p_access,
- vcdinfo_get_track_lba(p_vcd->vcd, i_track),
vcdinfo_get_entry_lba(p_vcd->vcd, i),
- vcdinfo_get_track_lba(p_vcd->vcd, i_track+1),
i_track, &(p_vcd->play_item) );
}
return VLC_SUCCESS;
MetaInfoAddStr(access_t *p_access, char *p_cat,
char *title, const char *str)
{
- access_vcd_data_t *p_vcd = (access_vcd_data_t *) p_access->p_sys;
+ vcdplayer_t *p_vcd = (vcdplayer_t *) p_access->p_sys;
if ( str ) {
dbg_print( INPUT_DBG_META, "field: %s: %s", title, str);
input_Control( p_vcd->p_input, INPUT_ADD_INFO, p_cat, title, "%s", str);
static inline void
MetaInfoAddNum(access_t *p_access, char *psz_cat, char *title, int num)
{
- access_vcd_data_t *p_vcd = (access_vcd_data_t *) p_access->p_sys;
+ vcdplayer_t *p_vcd = (vcdplayer_t *) p_access->p_sys;
dbg_print( INPUT_DBG_META, "field %s: %d", title, num);
input_Control( p_vcd->p_input, INPUT_ADD_INFO, psz_cat, title, "%d", num );
}
void
VCDMetaInfo( access_t *p_access, /*const*/ char *psz_mrl )
{
- access_vcd_data_t *p_vcd = (access_vcd_data_t *) p_access->p_sys;
+ vcdplayer_t *p_vcd = (vcdplayer_t *) p_access->p_sys;
unsigned int i_entries = vcdinfo_get_num_entries(p_vcd->vcd);
unsigned int last_entry = 0;
char *psz_cat;
%% : a %
*/
char *
-VCDFormatStr(const access_t *p_access, access_vcd_data_t *p_vcd,
+VCDFormatStr(const access_t *p_access, vcdplayer_t *p_vcd,
const char format_str[], const char *mrl,
const vcdinfo_itemid_t *itemid)
{
static void
VCDCreatePlayListItem(const access_t *p_access,
- access_vcd_data_t *p_vcd,
+ vcdplayer_t *p_vcd,
playlist_t *p_playlist,
const vcdinfo_itemid_t *itemid,
char *psz_mrl, int psz_mrl_max,
}
int
-VCDFixupPlayList( access_t *p_access, access_vcd_data_t *p_vcd,
+VCDFixupPlayList( access_t *p_access, vcdplayer_t *p_vcd,
const char *psz_source, vcdinfo_itemid_t *itemid,
vlc_bool_t b_single_item )
{
return 0;
}
+void
+VCDUpdateTitle( access_t *p_access )
+{
+
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
+
+ unsigned int psz_mrl_max = strlen(VCD_MRL_PREFIX)
+ + strlen(p_vcd->psz_source) + sizeof("@E999")+3;
+ char *psz_mrl = malloc( psz_mrl_max );
+
+ if( psz_mrl )
+ {
+ char *psz_name;
+ snprintf(psz_mrl, psz_mrl_max, "%s%s",
+ VCD_MRL_PREFIX, p_vcd->psz_source);
+ psz_name = VCDFormatStr( p_access, p_vcd,
+ config_GetPsz( p_access, MODULE_STRING
+ "-title-format" ),
+ psz_mrl, &(p_vcd->play_item) );
+ input_Control( p_vcd->p_input, INPUT_SET_NAME, psz_name );
+ free(psz_mrl);
+ }
+}
+
/*
Fills out playlist information.
*/
-int VCDFixupPlayList( access_t *p_access, access_vcd_data_t *p_vcd,
+int VCDFixupPlayList( access_t *p_access, vcdplayer_t *p_vcd,
const char *psz_source, vcdinfo_itemid_t *itemid,
vlc_bool_t b_single_track );
void VCDMetaInfo( access_t *p_access, /*const*/ char *psz_mrl );
-char * VCDFormatStr(const access_t *p_access, access_vcd_data_t *p_vcd,
+char * VCDFormatStr(const access_t *p_access, vcdplayer_t *p_vcd,
const char format_str[], const char *mrl,
const vcdinfo_itemid_t *itemid);
+void VCDUpdateTitle( access_t *p_access );
+
#endif /* VCD_INFO_H */
*****************************************************************************/
struct intf_sys_t
{
- input_thread_t * p_input;
- access_vcd_data_t * p_vcd;
+ input_thread_t *p_input;
+ vcdplayer_t *p_vcd;
- vlc_bool_t b_still; /* True if we are in a still frame */
- vlc_bool_t b_inf_still; /* True if still wait time is infinite */
- mtime_t m_still_time; /* Time in microseconds remaining
+ vlc_bool_t b_still; /* True if we are in a still frame */
+ vlc_bool_t b_inf_still; /* True if still wait time is infinite */
+ mtime_t m_still_time; /* Time in microseconds remaining
to wait in still frame.
*/
#if FINISHED
Return VLC_TRUE if playback control (PBC) is on
*/
vlc_bool_t
-vcdplayer_pbc_is_on( const access_vcd_data_t *p_vcd )
+vcdplayer_pbc_is_on( const vcdplayer_t *p_vcd )
{
return VCDINFO_INVALID_ENTRY != p_vcd->i_lid;
}
+/* Given an itemid, return the size for the object (via information
+ previously stored when opening the vcd). */
+static size_t
+vcdplayer_get_item_size(access_t * p_access, vcdinfo_itemid_t itemid)
+{
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
+
+ switch (itemid.type) {
+ case VCDINFO_ITEM_TYPE_ENTRY:
+ return p_vcd->entry[itemid.num].size;
+ break;
+ case VCDINFO_ITEM_TYPE_SEGMENT:
+ return p_vcd->segment[itemid.num].size;
+ break;
+ case VCDINFO_ITEM_TYPE_TRACK:
+ return p_vcd->track[itemid.num-1].size;
+ break;
+ case VCDINFO_ITEM_TYPE_LID:
+ /* Play list number (LID) */
+ return 0;
+ break;
+ case VCDINFO_ITEM_TYPE_NOTFOUND:
+ case VCDINFO_ITEM_TYPE_SPAREID2:
+ default:
+ LOG_ERR("%s %d\n", _("bad item type"), itemid.type);
+ return 0;
+ }
+}
+
static void
vcdplayer_update_entry( access_t * p_access, uint16_t ofs,
uint16_t *entry, const char *label)
{
- access_vcd_data_t * p_vcd= (access_vcd_data_t *)p_access->p_sys;
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
if ( ofs == VCDINFO_INVALID_OFFSET ) {
*entry = VCDINFO_INVALID_ENTRY;
vcdplayer_read_status_t
vcdplayer_non_pbc_nav ( access_t * p_access )
{
- access_vcd_data_t * p_vcd= (access_vcd_data_t *)p_access->p_sys;
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
/* Not in playback control. Do we advance automatically or stop? */
switch (p_vcd->play_item.type) {
return READ_BLOCK;
}
+#if FINISHED
+/*!
+ Set reading to play an entire track.
+*/
+static void
+_vcdplayer_set_track(access_t * p_access, track_t i_track)
+{
+ vcdplayer_t *p_vcd = (vcdplayer_t *)p_access->p_sys;
+ if (i_track < 1 || i_track > p_vcd->i_tracks)
+ return;
+ else {
+ vcdinfo_obj_t *p_obj = p_vcd->vcd;
+ vcdinfo_itemid_t itemid;
+
+ itemid.num = i_track;
+ itemid.type = VCDINFO_ITEM_TYPE_TRACK;
+ p_vcd->in_still = 0;
+ p_vcd->i_lsn = vcdinfo_get_track_lsn(p_obj, i_track);
+ p_vcd->play_item = itemid;
+ p_vcd->i_track = i_track;
+ p_vcd->track_lsn = p_vcd->i_lsn;
+
+ vcdplayer_set_origin(p_access);
+
+ dbg_print(INPUT_DBG_LSN, "LSN: %u\n", p_vcd->i_lsn);
+ }
+}
+
+/*!
+ Set reading to play an entry
+*/
+static void
+_vcdplayer_set_entry(access_t * p_access, unsigned int num)
+{
+ vcdplayer_t *p_vcd = (vcdplayer_t *)p_access->p_sys;
+ vcdinfo_obj_t *p_obj = p_vcd->vcd;
+ unsigned int num_entries = vcdinfo_get_num_entries(p_obj);
+
+ if (num >= num_entries) {
+ LOG_ERR("%s %d\n", _("bad entry number"), num);
+ return;
+ } else {
+ vcdinfo_itemid_t itemid;
+
+ itemid.num = num;
+ itemid.type = VCDINFO_ITEM_TYPE_ENTRY;
+ p_vcd->in_still = 0;
+ p_vcd->i_lsn = vcdinfo_get_entry_lsn(p_obj, num);
+ p_vcd->play_item = itemid;
+ p_vcd->i_track = vcdinfo_get_track(p_obj, num);
+ p_vcd->track_lsn = vcdinfo_get_track_lsn(p_obj, p_vcd->i_track);
+ p_vcd->track_end_lsn = p_vcd->track_lsn +
+ p_vcd->track[p_vcd->i_track-1].size;
+
+ vcdplayer_set_origin(p_access);
+
+ dbg_print(INPUT_DBG_LSN, "LSN: %u, track_end LSN: %u\n",
+ p_vcd->i_lsn, p_vcd->track_end_lsn);
+ }
+}
+
+/*!
+ Set reading to play an segment (e.g. still frame)
+*/
+static void
+_vcdplayer_set_segment(access_t * p_access, unsigned int num)
+{
+ vcdplayer_t *p_vcd = (vcdplayer_t *)p_access->p_sys;
+ vcdinfo_obj_t *p_obj = p_vcd->vcd;
+ segnum_t num_segs = vcdinfo_get_num_segments(p_obj);
+
+ if (num >= num_segs) {
+ LOG_ERR("%s %d\n", _("bad segment number"), num);
+ return;
+ } else {
+ vcdinfo_itemid_t itemid;
+
+ p_vcd->i_lsn = vcdinfo_get_seg_lsn(p_obj, num);
+ p_vcd->i_track = 0;
+
+ if (VCDINFO_NULL_LSN==p_vcd->i_lsn) {
+ LOG_ERR("%s %d\n",
+ _("Error in getting current segment number"), num);
+ return;
+ }
+
+ itemid.num = num;
+ itemid.type = VCDINFO_ITEM_TYPE_SEGMENT;
+ p_vcd->play_item = itemid;
+
+ vcdplayer_set_origin(p_access);
+
+ dbg_print(INPUT_DBG_LSN, "LSN: %u\n", p_vcd->i_lsn);
+ }
+}
+#endif /* FINISHED */
+
+/*
+ Set's start origin and size for subsequent seeks.
+ input: p_vcd->i_lsn, p_vcd->play_item
+ changed: p_vcd->origin_lsn, p_vcd->end_lsn
+*/
+void
+vcdplayer_set_origin(access_t *p_access)
+{
+ vcdplayer_t *p_vcd = (vcdplayer_t *)p_access->p_sys;
+ size_t i_size= vcdplayer_get_item_size(p_access, p_vcd->play_item);
+
+ p_vcd->end_lsn = p_vcd->i_lsn + i_size;
+ p_vcd->origin_lsn = p_vcd->i_lsn;
+
+ dbg_print((INPUT_DBG_CALL|INPUT_DBG_LSN), "end LSN: %u\n", p_vcd->end_lsn);
+}
+
/* Handles PBC navigation when reaching the end of a play item. */
vcdplayer_read_status_t
vcdplayer_pbc_nav ( access_t * p_access )
{
- access_vcd_data_t * p_vcd= (access_vcd_data_t *)p_access->p_sys;
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
/* We are in playback control. */
vcdinfo_itemid_t itemid;
vlc_bool_t
vcdplayer_inc_play_item( access_t *p_access )
{
- access_vcd_data_t * p_vcd= (access_vcd_data_t *)p_access->p_sys;
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
int noi;
vlc_bool_t
vcdplayer_play_default( access_t * p_access )
{
- access_vcd_data_t *p_vcd= (access_vcd_data_t *)p_access->p_sys;
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
vcdinfo_itemid_t itemid;
vlc_bool_t
vcdplayer_play_next( access_t * p_access )
{
- access_vcd_data_t *p_vcd= (access_vcd_data_t *)p_access->p_sys;
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
- vcdinfo_obj_t *obj;
+ vcdinfo_obj_t *p_obj;
vcdinfo_itemid_t itemid;
if (!p_vcd) return VLC_FALSE;
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_PBC),
"current: %d" , p_vcd->play_item.num);
- obj = p_vcd->vcd;
+ p_obj = p_vcd->vcd;
itemid.type = p_vcd->play_item.type;
if (vcdplayer_pbc_is_on(p_vcd)) {
- vcdinfo_lid_get_pxd(obj, &(p_vcd->pxd), p_vcd->i_lid);
+ vcdinfo_lid_get_pxd(p_obj, &(p_vcd->pxd), p_vcd->i_lid);
switch (p_vcd->pxd.descriptor_type) {
case PSD_TYPE_SELECTION_LIST:
vlc_bool_t
vcdplayer_play_prev( access_t * p_access )
{
- access_vcd_data_t *p_vcd= (access_vcd_data_t *)p_access->p_sys;
-
- vcdinfo_obj_t *obj = p_vcd->vcd;
- vcdinfo_itemid_t itemid;
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
+ vcdinfo_obj_t *p_obj = p_vcd->vcd;
+ vcdinfo_itemid_t itemid;
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_PBC),
"current: %d" , p_vcd->play_item.num);
if (vcdplayer_pbc_is_on(p_vcd)) {
- vcdinfo_lid_get_pxd(obj, &(p_vcd->pxd), p_vcd->i_lid);
+ vcdinfo_lid_get_pxd(p_obj, &(p_vcd->pxd), p_vcd->i_lid);
switch (p_vcd->pxd.descriptor_type) {
case PSD_TYPE_SELECTION_LIST:
vlc_bool_t
vcdplayer_play_return( access_t * p_access )
{
- access_vcd_data_t *p_vcd= (access_vcd_data_t *)p_access->p_sys;
-
- vcdinfo_obj_t *obj = p_vcd->vcd;
- vcdinfo_itemid_t itemid;
+ vcdplayer_t *p_vcd= (vcdplayer_t *)p_access->p_sys;
+ vcdinfo_obj_t *p_obj = p_vcd->vcd;
+ vcdinfo_itemid_t itemid;
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_PBC),
"current: %d" , p_vcd->play_item.num);
if (vcdplayer_pbc_is_on(p_vcd)) {
- vcdinfo_lid_get_pxd(obj, &(p_vcd->pxd), p_vcd->i_lid);
+ vcdinfo_lid_get_pxd(p_obj, &(p_vcd->pxd), p_vcd->i_lid);
switch (p_vcd->pxd.descriptor_type) {
case PSD_TYPE_SELECTION_LIST:
#define LOG_ERR(args...) msg_Err( p_access, args )
#define LOG_WARN(args...) msg_Warn( p_access, args )
+/*------------------------------------------------------------------
+ General definitions and structures.
+---------------------------------------------------------------------*/
+
+#define VCDPLAYER_IN_STILL 65535
+
+typedef struct {
+ lsn_t start_LSN; /* LSN where play item starts */
+ size_t size; /* size in sector units of play item. */
+} vcdplayer_play_item_info_t;
+
/* vcdplayer_read return status */
typedef enum {
READ_BLOCK,
} vcdplayer_read_status_t;
/*****************************************************************************
- * access_vcd_data_t: VCD information
+ * vcdplayer_t: VCD information
*****************************************************************************/
typedef struct thread_vcd_data_s
{
/* Current State: position */
int i_debug; /* Debugging mask */
vlc_bool_t in_still; /* true if in still */
- vcdinfo_itemid_t play_item; /* play-item, VCDPLAYER_BAD_ENTRY
- if none */
int i_lid; /* LID that play item is in. Implies
PBC is on. VCDPLAYER_BAD_ENTRY if
not none or not in PBC */
PSD/PLD */
int pdi; /* current pld index of pxd. -1 if
no index*/
+ vcdinfo_itemid_t play_item; /* play-item, VCDPLAYER_BAD_ENTRY
+ if none */
vcdinfo_itemid_t loop_item; /* Where do we loop back to?
Meaningful only in a selection
list */
lsn_t end_lsn; /* LSN of end of current
entry/segment/track. */
lsn_t origin_lsn; /* LSN of start of seek/slider */
-
+ lsn_t track_lsn; /* LSN of start track origin of track
+ we are in. */
+ lsn_t track_end_lsn; /* LSN of end of current track (if
+ entry). */
lsn_t * p_entries; /* Entry points */
lsn_t * p_segments; /* Segments */
vlc_bool_t b_valid_ep; /* Valid entry points flag */
unsigned int i_segments; /* # of segments */
unsigned int i_entries; /* # of entries */
unsigned int i_lids; /* # of List IDs */
+
+ /* Tracks, segment, and entry information. The number of entries for
+ each is given by the corresponding num_* field above. */
+ vcdplayer_play_item_info_t *track;
+ vcdplayer_play_item_info_t *segment;
+ vcdplayer_play_item_info_t *entry;
+
unsigned int i_titles; /* # of navigatable titles. */
input_title_t *p_title[CDIO_CD_MAX_TRACKS];
vlc_bool_t b_end_of_cell;
input_thread_t *p_input;
-} access_vcd_data_t;
+} vcdplayer_t;
/*!
Get the next play-item in the list given in the LIDs. Note play-item
/*!
Return true if playback control (PBC) is on
*/
-vlc_bool_t vcdplayer_pbc_is_on(const access_vcd_data_t *p_this);
+vlc_bool_t vcdplayer_pbc_is_on(const vcdplayer_t *p_this);
/*!
Play item assocated with the "default" selection.
vlc_bool_t
vcdplayer_play_return( access_t * p_access );
+/*
+ Set's start origin and size for subsequent seeks.
+ input: p_vcd->i_lsn, p_vcd->play_item
+ changed: p_vcd->origin_lsn, p_vcd->end_lsn
+*/
+void vcdplayer_set_origin(access_t * p_access);
+
vcdplayer_read_status_t vcdplayer_pbc_nav ( access_t * p_access );
vcdplayer_read_status_t vcdplayer_non_pbc_nav ( access_t * p_access );