mirror of https://code.videolan.org/videolan/vlc
vcdx: remove unmaintained module
This commit is contained in:
parent
6297968fe7
commit
933424d7ed
1
NEWS
1
NEWS
|
@ -192,6 +192,7 @@ Removed modules
|
|||
* QuartText text renderer module (use Freetype instead)
|
||||
* Win32 GDI text renderer module (use Freetype instead)
|
||||
* Growl notification (replaced by osx_notifications)
|
||||
* VCDX "extended" Video CD access module (use the normal VCD module)
|
||||
|
||||
|
||||
Changes between 2.2.0 and 2.2.1:
|
||||
|
|
|
@ -1803,11 +1803,6 @@ fi
|
|||
AM_CONDITIONAL(HAVE_DECKLINK, [ test "${have_decklink}" != "no" ])
|
||||
|
||||
|
||||
dnl
|
||||
dnl VCDX modules
|
||||
dnl
|
||||
PKG_ENABLE_MODULES_VLC([VCDX], [vcdx], [libcdio >= 0.78.2 libiso9660 >= 0.72 libvcdinfo >= 0.7.22], [navigate VCD with libvcdinfo], [no])
|
||||
|
||||
dnl
|
||||
dnl Built-in CD-DA and VCD module
|
||||
dnl
|
||||
|
|
|
@ -16,7 +16,6 @@ nobase_doc_DATA = $(LIBVLC_SAMPLES)
|
|||
|
||||
doc_DATA = \
|
||||
fortunes.txt \
|
||||
intf-vcd.txt \
|
||||
$(NULL)
|
||||
|
||||
CHANGELOGS = \
|
||||
|
@ -49,7 +48,6 @@ EXTRA_DIST = \
|
|||
$(man1_MANS) \
|
||||
$(LIBVLC_SAMPLES) \
|
||||
fortunes.txt \
|
||||
intf-vcd.txt \
|
||||
release-howto.txt \
|
||||
Doxyfile.in \
|
||||
lirc/example.lircrc \
|
||||
|
|
547
doc/intf-vcd.txt
547
doc/intf-vcd.txt
|
@ -1,547 +0,0 @@
|
|||
This file documents the ``Extended'' VLC Video CD Plugin
|
||||
|
||||
Copyright (C) 2003, 2004 Rocky Bernstein (rocky@panix.com)
|
||||
|
||||
Permission is granted to copy, distribute and/or modify this document
|
||||
under the terms of the GNU Free Documentation License, Version 1.1 or
|
||||
any later version published by the Free Software Foundation; with the
|
||||
Invariant Sections being ``Free Software'' and ``Free Software Needs
|
||||
Free Documentation'', with the Front-Cover Texts being ``A GNU Manual,''
|
||||
and with the Back-Cover Texts as in (a) below.
|
||||
|
||||
(a) The Free Software Foundation's Back-Cover Text is: ``You have
|
||||
freedom to copy and modify this GNU Manual, like GNU software. Copies
|
||||
published by the Free Software Foundation raise funds for GNU
|
||||
development.''
|
||||
|
||||
-----------------------------------------------------------------
|
||||
Quick start
|
||||
-----------------------------------------------------------------
|
||||
|
||||
The newer Video CD plugin (using libcdio and vcdimager) has some
|
||||
navigation and playback capabilities. However full integration with
|
||||
into vlc is a bit lacking and will probably take some a bit of work
|
||||
and time.
|
||||
|
||||
Although, this plugin replaces the older VCD plugin, the old plugin is
|
||||
still built and installed and used when the newer plugin is not found.
|
||||
|
||||
This document describes only the newer VCD plugin.
|
||||
|
||||
The next section is a general overview of Video CD's in general. If
|
||||
you are in a hurry to find out how to use this plugin or know this
|
||||
already, this section can be skipped.
|
||||
|
||||
After that we describe the terms and concepts used in the remainder
|
||||
Again, in a hurry, this section can be skipped or skimmed. If you come
|
||||
across a term like "segment," or "lid" that confuses you, look in
|
||||
this section.
|
||||
|
||||
The next section describes the MRL format that this plugin uses. If
|
||||
you want to know how to control where to start playing, read this.
|
||||
Even if you are familiar with vlc MRL's, you probably want to look
|
||||
at this section. Some of the units in a VCD are a little different
|
||||
than those in a DVD or audio CD.
|
||||
|
||||
The next section gives key bindings that are used by this
|
||||
plugin. Again to be able to control the plugin, especially for
|
||||
playback control, you may need to read this section.
|
||||
|
||||
The next section describes the configuration parameters you can set
|
||||
for the plugin. Most of the default values I hope are what most
|
||||
people will want to start out with. But for fine control of the
|
||||
defaults, read this section.
|
||||
|
||||
One configuration variable is the debug output. The next section
|
||||
describes the meaning of debug flags and how to troubleshoot the
|
||||
plugin.
|
||||
|
||||
-----------------------------------------------------------------
|
||||
About VCDs, SVCDs, and XVCDs.
|
||||
-----------------------------------------------------------------
|
||||
From: http://www.vcdhelp.com/vcd
|
||||
|
||||
VCD stands for 'Video Compact Disc' and basically it is a CD that
|
||||
contains moving pictures and sound. If you're familiar with regular
|
||||
audio/music CDs, then you will know what a Video CD looks like. A VCD
|
||||
has the capacity to hold up to 74/80 minutes on 650MB/700MB CDs
|
||||
respectively of full-motion video along with quality stereo
|
||||
sound. VCDs use a compression standard called MPEG to store the video
|
||||
and audio. A VCD can be played on almost all standalone DVD Players
|
||||
and of course on all computers with a DVD-ROM or CD-ROM drive with
|
||||
the help of a software based decoder / player. It is also possible to
|
||||
use menus and chapters, similar to DVDs, on a VCD and also simple
|
||||
photo album/slide shows with background audio. The quality of a very
|
||||
good VCD is about the same as a VHS tape based movie but VCD is
|
||||
usually a bit more blurry. If you want better quality checkout
|
||||
SVCD,CVD or DVD.
|
||||
|
||||
From: http://www.vcdhelp.com/svcd.htm
|
||||
|
||||
SVCD stands for "Super VideoCD". A SVCD is very similar to a VCD, it
|
||||
has the capacity to hold about 35-60 minutes on 74/80 min CDs of very
|
||||
good quality full-motion video along with up to 2 stereo audio tracks
|
||||
and also 4 selectable subtitles. A SVCD can be played on many
|
||||
standalone DVD Players and of course on all computers with a DVD-ROM
|
||||
or CD-ROM drive with the help of a software based decoder / player. It
|
||||
is also possible to use menus and chapters, similar to DVDs, on a
|
||||
SVCD and also simple photo album/slide shows with background
|
||||
audio. The quality of a SVCD is much better than a VCD, especially
|
||||
much more sharpen picture than a VCD because of the higher
|
||||
resolution. But the quality depends how many minutes you choose to
|
||||
store on a CD, less minutes/CD generally means higher quality.
|
||||
|
||||
From: http://www.vcdhelp.com/xvcd.htm
|
||||
|
||||
XVCD stands for eXtendedVCD. XVCD has same features as VCD but it is
|
||||
possible to use higher bitrates and higher resolution to get higher
|
||||
video quality. XVCD is basicly everything that uses MPEG1 video, is
|
||||
not within the VCD standard and burnt in "VCD"-Mode.
|
||||
|
||||
XSVCD stands for eXtendedSVCD. XSVCD has same features as SVCD but it
|
||||
is possible to use higher bitrates and higher resolution to get
|
||||
higher video quality. XSVCD is basicly everything that uses MPEG2
|
||||
video, is not within the SVCD standard and burnt in "SVCD"-Mode.
|
||||
|
||||
|
||||
-----------------------------------------------------------------
|
||||
Concepts used by this plugin.
|
||||
-----------------------------------------------------------------
|
||||
|
||||
The remote control of a Video CD players (or the front panel)
|
||||
generally has special keys or buttons. The author of a Video CD can
|
||||
assign what action to use when these buttons are pressed. They buttons
|
||||
are:
|
||||
|
||||
RETURN: Often used to return to the previous menu or previouly
|
||||
interruped video segment.
|
||||
|
||||
DEFAULT: Possibly take the default selection value. This function can
|
||||
only be assigned when the LID refers to in a "Program Selection List"
|
||||
or "Extended Program Selection List"
|
||||
|
||||
NEXT: Possibly the next entry, chapter, track, or menu.
|
||||
|
||||
PREVIOUS: Possibly the previous entry, chapter, track, or menu.
|
||||
|
||||
Contiguous non-overlapping regions of a Compact Disc are called
|
||||
"Tracks". The sum of the tracks forms the entire CD. The CD
|
||||
specifications standards say that between tracks there is to be a
|
||||
150-sector gap.
|
||||
|
||||
In the MRL list described below, we generally don't list the first
|
||||
track which we would call call "Track 0", but other tools like
|
||||
VCDimager, cdinfo, and the CD-reading world in the general call this
|
||||
"Track 1". This first track usually contains an ISO 9660-format
|
||||
filesystem with metadata describing what's on the CD. It may also
|
||||
contain "segments" or small MPEGs that generally make up still frames
|
||||
and menus. Aside from the segments which are merely only parts of
|
||||
track 0, it doesn't make sense to try to "play" track 0 (or track 1
|
||||
depending on how you want to count), which is why we don't list it.
|
||||
It seems natural to call the first thing you would want to play "track
|
||||
1" (which in fact is track 2 to everyone else).
|
||||
|
||||
There are two other units that this plugin lists and are used
|
||||
internally. One we call an "entry". This is a starting point of a
|
||||
track which can include the beginning of the track, and when an entry
|
||||
points to the beginning of a track, it is equivalent to listing the
|
||||
track. However Video CD's often have multiple entry points into a
|
||||
track. Logically this corresponds to a "Chapter" or "Scene" of a
|
||||
larger uninterruptable unit. One might think a CD "track" could serve
|
||||
this purpose with a collection of tracks making up a work or
|
||||
movie. Alas, there is "track pregap" space between tracks which appear
|
||||
as a time gaps when hardware players go between tracks - something
|
||||
that doesn't have to happen switching between entries because there in
|
||||
fact is no gap.
|
||||
|
||||
Another unit we use is a called a "segment." These are just the
|
||||
playable units in track 0. Segments come in fixed-length units so
|
||||
several may be combined to form a single logical playable unit. Still
|
||||
frames for menus are segments. A menu doesn't have to have a
|
||||
still-frame associated with it; a menu might be implemented as a short
|
||||
looped movie clip. But all still frames are segments. Also, Video CD
|
||||
specifications allow still frames to have higher resolution than
|
||||
motion clips. All segments reside in track 0.
|
||||
|
||||
A "list ID" (also called a LID and and is one greater than a Play
|
||||
Sequence descripter or "PSD" number) combines "entries" and "segments"
|
||||
and "tracks" together with some navigation logic. "Playback Control"
|
||||
(acronym PBC) is simply starting playback at a particular LID, and
|
||||
unless otherwise specified you'd start with the first playback item
|
||||
which we call P1.
|
||||
|
||||
Below we will refer to an "item" as combination of a unit name (track,
|
||||
entry, segment, playback) and a whole number.
|
||||
|
||||
-----------------------------------------------------------------
|
||||
MRLS:
|
||||
-----------------------------------------------------------------
|
||||
|
||||
This vlc Video CD plugin, identifies itself in the vlc GUI preferences
|
||||
vcdx. It also registers itelf to handle a class of MRL's that start
|
||||
with vcdx://.
|
||||
|
||||
The VCDX MRL takes the following form:
|
||||
|
||||
vcdx://[path to file or vcd device][@[letter]number]]
|
||||
|
||||
(Note: eventually the trailing "x" will be dropped. In MRL's "vcd"
|
||||
works as well as "vcdx".
|
||||
|
||||
A simple vcdx:// runs the default item (e.g. perhaps track 1 or the
|
||||
playback control) the default VCD device (perhaps /dev/cdrom). Whether
|
||||
to use playback control and the default device are user-configurable.
|
||||
|
||||
It is however also possible to specify both Video CD device/filename
|
||||
and the kind of item explicitly in the MRL.
|
||||
|
||||
For example vcdx:/dev/dvd specifies the default entry using device
|
||||
/dev/dvd which might useful if this is your DVD which is different
|
||||
than your CD-ROM device and your DVD drive can play CD's. And
|
||||
vcdx://test_svcd_ntsc.cue specifies the cue file for CD image on disk.
|
||||
(test_svcd_ntsc.bin is the corresponding bin file, but using that
|
||||
won't work.)
|
||||
|
||||
After the optional device name or file name, you can name the kind of
|
||||
unit which preceded by an '@'. An MRL which ends in an @ is like
|
||||
not adding it at all: the default entry type and number is used. Items
|
||||
come in 4 flavors: "Track," "Entry," "Playback," and "Segment." See
|
||||
the preceding section for an explaination of these terms. These units
|
||||
are indicated with the capital first letter of each type: T, E, P, S,
|
||||
s.
|
||||
|
||||
--- In the future when we are able to control MRL display:
|
||||
An uppercase S in the MRL display indicates a NTS segment while a
|
||||
lowercase S indicates a PAL segment.
|
||||
----
|
||||
|
||||
However when you enter a MRL, the case of these letters is
|
||||
insignificant.
|
||||
|
||||
You can configure various things that affect MRLs are selected when
|
||||
there is some ambiguity in the MRL name. vcdx-PBC sets whether to
|
||||
to use PBC in a MRL is none is given. Another configuration
|
||||
setting, vcdx-device, determines what device to use if that part is
|
||||
not given.
|
||||
|
||||
Some examples of MRLS are given below. In the examples, we assume the
|
||||
following configuration settings:
|
||||
|
||||
vcdx-PBC=1
|
||||
vcdx-device=/dev/cdrom
|
||||
|
||||
vcdx:// - Play (navigate) default item (in this
|
||||
case Entry ID 0) from the default device (in this
|
||||
case set to /dev/cdrom)
|
||||
vcdx://@ - same as above
|
||||
vcdx:///dev/cdrom@ - same effect as above since the default device
|
||||
is set to /dev/cdrom.
|
||||
vcdx:///dev/cdrom@E0 - same as above. But note that this is
|
||||
because we have autoplay:entry which is
|
||||
no longer the default value
|
||||
vcdx:///dev/cdrom2@ - Play (navigate) the default item of /dev/cdrom2
|
||||
vcdx:///dev/cdrom2 - should be same as above but is currently broken?
|
||||
vcdx:///dev/cdrom2@T1 - Play Track 1 from /dev/cdrom2
|
||||
vcdx:///dev/cdrom@S1 - Play segment 1 from /dev/cdrom. This
|
||||
assumes there *is* a segment 1. Check
|
||||
the MRL list to see if that is the case.
|
||||
vcdx://@P1 - Play LID item 1 from default device
|
||||
If there is no playback control, MRL will
|
||||
get converted into vcdx://@E0. Again
|
||||
check the MRL list to see if there is a P1.
|
||||
vcdx://@P1* - probably same as above.
|
||||
vcdx:///dev/cdrom@E1 - Play Entry id 1 from default device
|
||||
vcdx://@S0 - Play segment 0 from default device
|
||||
vcdx://@3 - Play track 3 from default device
|
||||
vcdx:///dev/cdrom2:1 - Play track 1 from /dev/cdrom2
|
||||
vcdx:///tmp/ntsc.cue@ - Play default item (E0) of /tmp/ntsc.bin. Note
|
||||
trailing @
|
||||
vcdx://ntsc.cue/@E0 - Play entry 0 of ntsc.bin
|
||||
vcdx:///tmp/ntsc.nrg/@E0 - Play entry 0 of /tmp/ntsc.nrg (Nero
|
||||
file) Works for some simple Nero images.
|
||||
|
||||
-----------------------------------------------------------------
|
||||
Key bindings and non-PBC navigation.
|
||||
-----------------------------------------------------------------
|
||||
|
||||
At present vlc doesn't have special hot-keys for "NEXT", "PREVIOUS",
|
||||
"RETURN" or "DEFAULT". So we use some of other hot-key names that
|
||||
don't seem to correspond to anything for a VCD. The key mapping names
|
||||
are:
|
||||
|
||||
VLC NAME VCD NAME
|
||||
--------------------------
|
||||
NAVIGATE UP RETURN
|
||||
NAVIGATE DOWN DEFAULT
|
||||
NAVIGATE LEFT PREVIOUS
|
||||
NAVIGATE RIGHT NEXT
|
||||
|
||||
Also this plugin understand numeric input. Since the hot-keys don't
|
||||
have assignments for numbers, the digits on the keyboard (also
|
||||
available from the keypad if num-lock is on) are hard-coded. Even
|
||||
though this isn't customizable, it's probably what most people would
|
||||
expect and want.
|
||||
|
||||
The enter a number just type the digits of the number. To finish
|
||||
specifying a number use the whatever key is bound to vlc's
|
||||
"ACTIVATE" hot key - the default value is the "Enter" key.
|
||||
|
||||
However the next/previous/return buttons can be prefaced with a number
|
||||
and that has the effect of hitting that button that many times. So
|
||||
let's say you want to go forward 5 "Chapters" and hitting the "Next"
|
||||
key 5 times would do that Instead, you could just enter the digit 5
|
||||
followed by the key that is assigned to "NAVIGATE RIGHT", probably the
|
||||
right-arrow key.
|
||||
|
||||
If you have better suggestions as to what functions the VCD buttons
|
||||
would be better bound to how what fixed algorithm to use when not in
|
||||
PBC, let me know.
|
||||
|
||||
-----------------------------------------------------------------
|
||||
Configuration settings:
|
||||
-----------------------------------------------------------------
|
||||
|
||||
Configuration settings in xine are generally put in ~/.vlc/vlcrc, but
|
||||
can be configured via a vlc GUI. A description of the ones specific to
|
||||
VCDX are listed below.
|
||||
|
||||
- -
|
||||
|
||||
vcdx-device
|
||||
|
||||
This specifies the name of the video device that will be used by default.
|
||||
If you don't specify anything, the plugin scan for a suitable CD-ROM
|
||||
device containing a Video CD in it.
|
||||
|
||||
The default device in a MRL when none is listed. The default is
|
||||
determined by the appropriate name for the OS that you are running.
|
||||
|
||||
- -
|
||||
|
||||
vcd-debug
|
||||
|
||||
An integer (interpreted as a bit mask) which shows additional
|
||||
debugging information see the Debugging Section below for more
|
||||
information about the bits that can be set.
|
||||
|
||||
-----------------------------------------------------------------
|
||||
Troubleshooting Guide
|
||||
-----------------------------------------------------------------
|
||||
|
||||
The VCD plugin leaves a bit to be desired and has many bugs. I expect
|
||||
that there will not be covered below. But the below is a start.
|
||||
|
||||
This gives higher-level troubleshooting. More detailed and
|
||||
lower-level information is given in the next section DEBUGGING.
|
||||
|
||||
Problem: something doesn't work. Start at step -1.
|
||||
|
||||
Problem: The program gets a SEGFAULT or gives core dump. Start at step
|
||||
0.
|
||||
|
||||
Problem: I don't get anything playing. I can't even get information
|
||||
listed in "Media and Stream Information" or the playlist.
|
||||
Determination: start at step 1.
|
||||
|
||||
Problem: Okay, I something plays menu now. But I don't see information
|
||||
about the CD in the playlist.
|
||||
Determination: start at step 5.
|
||||
|
||||
|
||||
-1. (Something doesn't work.)
|
||||
|
||||
A lot of what is put here really is applicable to reporting
|
||||
problems and troubleshooting in vlc and the concepts really
|
||||
apply to any sort of bug reporting.
|
||||
|
||||
When reporting a problem it's helpful to have facts:
|
||||
|
||||
a) the version of vlc) you are using
|
||||
|
||||
b) the OS you are running on
|
||||
|
||||
c) the version of libcdio and/or libcddb you are using
|
||||
versions of libcdio and libcddb can be obtained by running
|
||||
pkg-config --modversion libcdio
|
||||
pkg-config --modversion libvcdinfo
|
||||
|
||||
d) what you input or requested (e.g. the full command line entered -
|
||||
if it is possible to reproduce the problem by giving a
|
||||
commandline that is desirable since it is probably the simplest
|
||||
way to convey exactly what was requested)
|
||||
|
||||
People often give (some part) of an error message neglecting
|
||||
to also include what was requested or entered that led to the
|
||||
output.
|
||||
|
||||
e) The setting for this plugin. That is the values of the
|
||||
variables that start cddax- listed above. On Unix this can
|
||||
generally be found in ~/.vlc/vlcrc
|
||||
|
||||
|
||||
f) Exactly the messages that were what given. You can turn
|
||||
increase the verbosity level by setting "verbosity=2" in the
|
||||
vlc preferences files. On Unix the preferences file is
|
||||
generally in ~/vlc/.vlcrc but there are GUI ways to set this
|
||||
too. Give everything that is in the message log.
|
||||
|
||||
0. (The program gets a SEGFAULT or gives core dump.)
|
||||
|
||||
Get and send a stack trace.
|
||||
|
||||
In addition to -1. Make sure the program has been compiled with
|
||||
debugging symbols put into the code. This is usually done by having
|
||||
the "-g" flag set when compiling the program.
|
||||
|
||||
You can get a strack trace the GNU debugger using the "where"
|
||||
command. For example on this might work:
|
||||
|
||||
gdb vlc *name-of-corefile*
|
||||
where
|
||||
|
||||
|
||||
1. (I don't get anything playing. I can't even get information
|
||||
listed in "Media and Stream Information" or the playlist)
|
||||
|
||||
Do you even have the plugin loaded?
|
||||
|
||||
When you run the vlc GUI, under Settings/Preferences you should see
|
||||
a "plugins" expandable list and under that another "access" list do
|
||||
you see a expandalbe entry under "access" labeled "vcdx"? If so,
|
||||
skip on to step 2.
|
||||
|
||||
a) If no "vcdx" expandable list, thent the VCDX plugin isn't
|
||||
loaded. Does a shared object exist? The plugin shared object is
|
||||
called "libvcdx_plugin.so" It should be in the directory that has
|
||||
...vlc/access. If this isn't around you need to build and install
|
||||
the VCDX plugin.
|
||||
|
||||
b) if libvcdx_plugin.so is in the fileystem, there might be a
|
||||
loader error; perhaps libcdio or libvcdinfo are not installed or
|
||||
are the wrong version. Use ldd on the file to see that it has all
|
||||
of the libraries dependencies satisfied. Also you might be able
|
||||
check if there was an attempt to load it by tracking system
|
||||
calls. On Linux and other OS's) "strace" can be used to see if the
|
||||
file gets accessed. On Solaris use "truss".
|
||||
|
||||
For example on Linux, amonst the many line of output when I run
|
||||
"strace -e trace=file vlc" I see this amongst lots of other
|
||||
output:
|
||||
|
||||
...
|
||||
stat64("/usr/local/lib/vlc/access/libvcdx_plugin.so", {st_mode=S_IFREG|0755, st_size=302990, ...}) = 0
|
||||
open("/usr/local/lib/vlc/access/libvcdx_plugin.so", O_RDONLY) = 5
|
||||
|
||||
The parameters inside the calls may be different depending on where
|
||||
vlc is installed and what release is installed. If the the file is
|
||||
found and "opened",
|
||||
|
||||
There may also be a message may under "setup/logs".
|
||||
|
||||
2. (There plugin was loaded and preferences found). In the "vcdx" tab
|
||||
of preference. An important selection is "vcdx-device." If this is
|
||||
set to the empty string, VCDX will try to scan your drives for a
|
||||
suitable device if the driver has the capability to scan for
|
||||
drives. However you can set the device to something of your
|
||||
choosing. On GNU/Linux, this may be "/dev/cdrom" and on Solaris it
|
||||
may be "/vol/dev/aliases/cdrom0". If you set this field, make sure
|
||||
these are correct for your particular setup. For example, I
|
||||
generally play out of the DVD device and this is called /dev/dvd
|
||||
rather than /dev/cdrom.
|
||||
|
||||
3. (Video CD Setup devices seems correct and there is a CD in the
|
||||
drive).
|
||||
|
||||
when you run
|
||||
vlc vcdx://
|
||||
|
||||
you should see your CD disk light go on if you have one. And the CD
|
||||
should be read.
|
||||
|
||||
a. If not something's wrong like step 2. Another tack may be to try
|
||||
to read a disk image of a Video CD and thus elimate any problems
|
||||
with hardware. You can get a test Video CD disk image to test here:
|
||||
|
||||
http://www.vcdimager.org/pub/vcdimager/examples/test_svcd/test_svcd_pal.zip
|
||||
|
||||
After unzipping this run there should be files test_svcd_pal.cue
|
||||
and test_svcd_pal.bin. Get out of xine and run from the directory
|
||||
that contains those files:
|
||||
vcdx://test_svcd_pal.cue@E0
|
||||
|
||||
If you see something playing then this is a hardware problem.
|
||||
|
||||
-----------------------------------------------------------------
|
||||
Debugging
|
||||
-----------------------------------------------------------------
|
||||
|
||||
**General vlc debugging...
|
||||
|
||||
Before delving to things specific to this plugin, some preparation may
|
||||
be in order. You'll probably want to configure vlc with "--enable-debug".
|
||||
plugin with debug information. Instead of "make'ing" with "make", use
|
||||
"make debug" and instead of installing using "make install" use "make
|
||||
install-debug".
|
||||
|
||||
I use gdb to debug. Debugging vlc with the entire suite of plugins
|
||||
under gdb is slow because it has to read in symbol tables from all the
|
||||
plugins. There are two ways to make loading faster when debugging. The
|
||||
simplest is just to go to the plugin directory and remove unused
|
||||
plugins. Another approach is create a new directory and make
|
||||
(symbolic) links into the complete plugin directory. Another way to
|
||||
speed up gdb loading is to attach the debugger after vlc has started up
|
||||
via a command like:
|
||||
|
||||
gdb -p *pid-of-vlc-process*
|
||||
|
||||
|
||||
**vcdx debugging...
|
||||
|
||||
It's a fact of life that this plugin is in an incomplete state and has
|
||||
bugs. So to facilitate tracking down problems we let you see what's
|
||||
going on dynamically. Various debugging settings will cause output to
|
||||
appear on vlc plugin log and/or "standard error" (assuming you've run
|
||||
xine in a way that you can capture this).
|
||||
|
||||
You think of debug switches as a bit mask, that you specifiy as an
|
||||
integers the various "bit" values (given in decimal) are listed below.
|
||||
|
||||
name value description
|
||||
------ ---------- -----------
|
||||
meta info 1 Trace Meta information
|
||||
event info 2 Trace keyboard events
|
||||
MRL 4 Things involved getting lists of what's in the VCD
|
||||
ext call 8 Trace vlc calls to the plugin routines
|
||||
all calls (10) 16 Trace all calls
|
||||
LSN (20) 32 Trace updates to the Logical sector number
|
||||
(basically reads)
|
||||
PBC (40) 64 Trace things involved with playback control
|
||||
libcdio (80) 128 Turn on CDIO debugging
|
||||
seek-set (100) 256 Trace "seek set" calls
|
||||
seek-cur (200) 512 Trace "seek cur" calls
|
||||
still (400) 1024 Trace Still-frames
|
||||
vcdinfo (800) 2048 Turn on VCDINFO debugging
|
||||
|
||||
|
||||
**Video CD debugging...
|
||||
|
||||
The tool vcd-info from the cdio branch of vcdimager can be used to
|
||||
show the entire contents of a Video CD or selected portions of
|
||||
that. Until the cdio branch of vcdimager is completely merged with
|
||||
vcdimager, the cd-info branch vresion has a few more
|
||||
features. (However consult vcdimager for complete of the program).
|
||||
|
||||
vcdxrip can be used to extract portions of a Video CD and or create an
|
||||
XML description file of the Video CD. This XML file and the extracted
|
||||
files can be used by vcdxbuild to recreate another Video CD.
|
||||
|
||||
And finally see also tools cd-info an cd-read from libcdio.
|
||||
|
||||
-----------------------------------------------------------------
|
||||
Other references
|
||||
-----------------------------------------------------------------
|
||||
http://www.vcdhelp.com/
|
||||
http://www.vcdimager.org/
|
||||
http://www.vcdimager.org/guides/#guides
|
||||
|
||||
$Id$
|
|
@ -411,7 +411,6 @@ $Id$
|
|||
* vaapi_x11: VAAPI hardware-accelerated decoding with x11 backend
|
||||
* vc1: VC-1 Video demuxer
|
||||
* vcd: input module for accessing Video CDs
|
||||
* vcdx: input module for accessing Video CDs with navigation & stills
|
||||
* vda: VDADecoder hardware-accelerated decoding
|
||||
* vdpau_adjust: VDPAU color adjust video filter
|
||||
* vdpau_avcodec: VDPAU hardware-accelerated decoding
|
||||
|
|
|
@ -272,23 +272,6 @@ endif
|
|||
EXTRA_LTLIBRARIES += libvcd_plugin.la
|
||||
access_LTLIBRARIES += $(LTLIBvcd)
|
||||
|
||||
libvcdx_plugin_la_SOURCES = \
|
||||
access/vcdx/access.h access/vcdx/access.c \
|
||||
access/vcdx/vcd.c access/vcdx/vcd.h \
|
||||
access/vcdx/vcdplayer.h access/vcdx/vcdplayer.c \
|
||||
access/vcdx/info.c access/vcdx/info.h
|
||||
libvcdx_plugin_la_CPPFLAGS = $(AM_CPPFLAGS)
|
||||
libvcdx_plugin_la_LIBADD = $(VCDX_LIBS)
|
||||
if HAVE_WIN32
|
||||
libvcdx_plugin_la_LIBADD += -lwinmm
|
||||
endif
|
||||
libvcdx_plugin_la_LDFLAGS = $(AM_LDFLAGS) -rpath '$(accessdir)'
|
||||
if HAVE_DARWIN
|
||||
libvcdx_plugin_la_LDFLAGS += -Wl,-framework,IOKit,-framework,CoreFoundation
|
||||
endif
|
||||
EXTRA_LTLIBRARIES += libvcdx_plugin.la
|
||||
access_LTLIBRARIES += $(LTLIBvcdx)
|
||||
|
||||
libdvdnav_plugin_la_SOURCES = access/dvdnav.c demux/mpeg/ps.h demux/mpeg/pes.h
|
||||
libdvdnav_plugin_la_CFLAGS = $(AM_CFLAGS) $(DVDNAV_CFLAGS)
|
||||
libdvdnav_plugin_la_LIBADD = $(DVDNAV_LIBS)
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -1,31 +0,0 @@
|
|||
/*****************************************************************************
|
||||
* access.h : VCD access.c routine headers
|
||||
*****************************************************************************
|
||||
* Copyright (C) 2004 VLC authors and VideoLAN
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation; either version 2.1 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
|
||||
*****************************************************************************/
|
||||
#ifndef VCD_ACCESS_H
|
||||
#define VCD_ACCESS_H
|
||||
|
||||
void VCDSetOrigin( access_t *p_access, lsn_t i_lsn, track_t i_track,
|
||||
const vcdinfo_itemid_t *p_itemid );
|
||||
|
||||
int VCDOpen ( vlc_object_t * );
|
||||
void VCDClose ( vlc_object_t * );
|
||||
|
||||
|
||||
#endif /* VCD_ACCESS_H */
|
||||
|
|
@ -1,326 +0,0 @@
|
|||
/*****************************************************************************
|
||||
* info.c : CD digital audio input information routines
|
||||
*****************************************************************************
|
||||
* Copyright (C) 2004 VLC authors and VideoLAN
|
||||
* $Id$
|
||||
*
|
||||
* Authors: Rocky Bernstein <rocky@panix.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation; either version 2.1 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
|
||||
*****************************************************************************/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#include <vlc_common.h>
|
||||
#include <vlc_input.h>
|
||||
#include <vlc_access.h>
|
||||
#include "vcd.h"
|
||||
#include "info.h"
|
||||
|
||||
#include <cdio/cdio.h>
|
||||
#include <cdio/cd_types.h>
|
||||
#include <cdio/logging.h>
|
||||
#include <cdio/util.h>
|
||||
#include <libvcd/info.h>
|
||||
#include <libvcd/logging.h>
|
||||
|
||||
static char *
|
||||
VCDFormatStr(vcdplayer_t *p_vcdplayer,
|
||||
const char *format_str, const char *mrl,
|
||||
const vcdinfo_itemid_t *itemid);
|
||||
void
|
||||
VCDMetaInfo( access_t *p_access, /*const*/ char *psz_mrl )
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer = (vcdplayer_t *) p_access->p_sys;
|
||||
input_thread_t *p_input = p_vcdplayer->p_input;
|
||||
vcdinfo_obj_t *p_vcdev = p_vcdplayer->vcd;
|
||||
|
||||
size_t i_entries = vcdinfo_get_num_entries(p_vcdev);
|
||||
size_t last_entry = 0;
|
||||
char *psz_cat = _("Disc");
|
||||
|
||||
track_t i_track;
|
||||
|
||||
# define addstr(t,v) input_Control(p_input,INPUT_ADD_INFO,psz_cat,t,"%s",v)
|
||||
# define addnum(t,v) input_Control(p_input,INPUT_ADD_INFO,psz_cat,t,"%d",v)
|
||||
# define addhex(t,v) input_Control(p_input,INPUT_ADD_INFO,psz_cat,t,"%x",v)
|
||||
|
||||
addstr(_("VCD Format"), vcdinfo_get_format_version_str(p_vcdev));
|
||||
addstr(_("Album"), vcdinfo_get_album_id (p_vcdev));
|
||||
addstr(_("Application"), vcdinfo_get_application_id (p_vcdev));
|
||||
addstr(_("Preparer"), vcdinfo_get_preparer_id (p_vcdev));
|
||||
addnum(_("Vol #"), vcdinfo_get_volume_num (p_vcdev));
|
||||
addnum(_("Vol max #"), vcdinfo_get_volume_count (p_vcdev));
|
||||
addstr(_("Volume Set"), vcdinfo_get_volumeset_id (p_vcdev));
|
||||
addstr(_("Volume"), vcdinfo_get_volume_id (p_vcdev));
|
||||
addstr(_("Publisher"), vcdinfo_get_publisher_id (p_vcdev));
|
||||
addstr(_("System Id"), vcdinfo_get_system_id (p_vcdev));
|
||||
addnum("LIDs", vcdinfo_get_num_LIDs (p_vcdev));
|
||||
addnum(_("Entries"), vcdinfo_get_num_entries (p_vcdev));
|
||||
addnum(_("Segments"), vcdinfo_get_num_segments (p_vcdev));
|
||||
addnum(_("Tracks"), vcdinfo_get_num_tracks (p_vcdev));
|
||||
|
||||
/* Spit out track information. Could also include MSF info.
|
||||
Also build title table.
|
||||
*/
|
||||
|
||||
for( i_track = 1 ; i_track < p_vcdplayer->i_tracks ; i_track++ ) {
|
||||
unsigned int audio_type = vcdinfo_get_track_audio_type(p_vcdev, i_track);
|
||||
uint32_t i_secsize = vcdinfo_get_track_sect_count(p_vcdev, i_track);
|
||||
|
||||
if (p_vcdplayer->b_svd) {
|
||||
addnum(_("Audio Channels"),
|
||||
vcdinfo_audio_type_num_channels(p_vcdev, audio_type) );
|
||||
}
|
||||
|
||||
addnum(_("First Entry Point"), 0 );
|
||||
|
||||
for ( last_entry = 0 ; last_entry < i_entries
|
||||
&& vcdinfo_get_track(p_vcdev, last_entry) == i_track; last_entry++ ) ;
|
||||
|
||||
addnum(_("Last Entry Point"), last_entry-1 );
|
||||
addnum(_("Track size (in sectors)"), i_secsize );
|
||||
}
|
||||
|
||||
{
|
||||
lid_t i_lid;
|
||||
for( i_lid = 1 ; i_lid <= p_vcdplayer->i_lids ; i_lid++ ) {
|
||||
PsdListDescriptor_t pxd;
|
||||
if (vcdinfo_lid_get_pxd(p_vcdev, &pxd, i_lid)) {
|
||||
switch (pxd.descriptor_type) {
|
||||
case PSD_TYPE_END_LIST:
|
||||
addstr(_("type"), _("end"));
|
||||
break;
|
||||
case PSD_TYPE_PLAY_LIST:
|
||||
addstr(_("type"), _("play list"));
|
||||
addnum("items", vcdinf_pld_get_noi(pxd.pld));
|
||||
addhex("next", vcdinf_pld_get_next_offset(pxd.pld));
|
||||
addhex("previous", vcdinf_pld_get_prev_offset(pxd.pld));
|
||||
addhex("return", vcdinf_pld_get_return_offset(pxd.pld));
|
||||
addnum("wait time", vcdinf_get_wait_time(pxd.pld));
|
||||
break;
|
||||
case PSD_TYPE_SELECTION_LIST:
|
||||
case PSD_TYPE_EXT_SELECTION_LIST:
|
||||
addstr(_("type"), PSD_TYPE_SELECTION_LIST == pxd.descriptor_type
|
||||
? _("extended selection list") : _("selection list") );
|
||||
addhex("default", vcdinf_psd_get_default_offset(pxd.psd));
|
||||
addhex("loop count", vcdinf_get_loop_count(pxd.psd));
|
||||
addhex("next", vcdinf_psd_get_next_offset(pxd.psd));
|
||||
addhex("previous", vcdinf_psd_get_prev_offset(pxd.psd));
|
||||
addhex("return", vcdinf_psd_get_return_offset(pxd.psd));
|
||||
addhex("rejected", vcdinf_psd_get_lid_rejected(pxd.psd));
|
||||
addhex("time-out offset", vcdinf_get_timeout_offset(pxd.psd));
|
||||
addnum("time-out time", vcdinf_get_timeout_time(pxd.psd));
|
||||
break;
|
||||
default:
|
||||
addstr(_("type"), _("unknown type"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
# undef addstr
|
||||
# undef addnum
|
||||
# undef addhex
|
||||
|
||||
if ( CDIO_INVALID_TRACK != i_track )
|
||||
{
|
||||
char *psz_tfmt = var_InheritString( p_access, MODULE_STRING "-title-format" );
|
||||
char *psz_name = VCDFormatStr( p_vcdplayer, psz_tfmt, psz_mrl,
|
||||
&(p_vcdplayer->play_item) );
|
||||
free( psz_tfmt );
|
||||
|
||||
input_Control( p_input, INPUT_SET_NAME, psz_name );
|
||||
free( psz_name );
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/*!
|
||||
Take a format string and expand escape sequences, that is sequences that
|
||||
begin with %, with information from the current VCD.
|
||||
The expanded string is returned. Here is a list of escape sequences:
|
||||
|
||||
%A : The album information
|
||||
%C : The VCD volume count - the number of CD's in the collection.
|
||||
%c : The VCD volume num - the number of the CD in the collection.
|
||||
%F : The VCD Format, e.g. VCD 1.0, VCD 1.1, VCD 2.0, or SVCD
|
||||
%I : The current entry/segment/playback type, e.g. ENTRY, TRACK, SEGMENT...
|
||||
%L : The playlist ID prefixed with " LID" if it exists
|
||||
%M : MRL
|
||||
%N : The current number of the %I - a decimal number
|
||||
%P : The publisher ID
|
||||
%p : The preparer ID
|
||||
%S : If we are in a segment (menu), the kind of segment
|
||||
%T : The track number
|
||||
%V : The volume set ID
|
||||
%v : The volume ID
|
||||
A number between 1 and the volume count.
|
||||
%% : a %
|
||||
*/
|
||||
static char *
|
||||
VCDFormatStr(vcdplayer_t *p_vcdplayer,
|
||||
const char *format_str, const char *mrl,
|
||||
const vcdinfo_itemid_t *itemid)
|
||||
{
|
||||
#define TEMP_STR_SIZE 256
|
||||
char temp_str[TEMP_STR_SIZE];
|
||||
char *tp = temp_str;
|
||||
const char *te = tp+TEMP_STR_SIZE-1;
|
||||
bool saw_control_prefix = false;
|
||||
|
||||
memset(temp_str, 0, TEMP_STR_SIZE);
|
||||
|
||||
for (; *format_str && tp<te; ++format_str) {
|
||||
|
||||
if (!saw_control_prefix && *format_str != '%') {
|
||||
*tp++ = *format_str;
|
||||
saw_control_prefix = false;
|
||||
continue;
|
||||
}
|
||||
|
||||
switch(*format_str) {
|
||||
case '%':
|
||||
if (saw_control_prefix) {
|
||||
*tp++ = '%';
|
||||
}
|
||||
saw_control_prefix = !saw_control_prefix;
|
||||
break;
|
||||
case 'A':
|
||||
tp += snprintf(tp,te-tp,"%s",
|
||||
vcdinfo_strip_trail(vcdinfo_get_album_id(p_vcdplayer->vcd),
|
||||
MAX_ALBUM_LEN));
|
||||
break;
|
||||
|
||||
case 'c':
|
||||
tp += snprintf(tp,te-tp,"%d",vcdinfo_get_volume_num(p_vcdplayer->vcd));
|
||||
break;
|
||||
|
||||
case 'C':
|
||||
tp += snprintf(tp,te-tp,"%d",vcdinfo_get_volume_count(p_vcdplayer->vcd));
|
||||
break;
|
||||
|
||||
case 'F':
|
||||
tp += snprintf(tp,te-tp,"%s",
|
||||
vcdinfo_get_format_version_str(p_vcdplayer->vcd));
|
||||
break;
|
||||
|
||||
case 'I':
|
||||
{
|
||||
switch (itemid->type) {
|
||||
case VCDINFO_ITEM_TYPE_TRACK:
|
||||
tp += snprintf(tp,te-tp,"%s",_("Track"));
|
||||
break;
|
||||
case VCDINFO_ITEM_TYPE_ENTRY:
|
||||
tp += snprintf(tp,te-tp,"%s",_("Entry"));
|
||||
break;
|
||||
case VCDINFO_ITEM_TYPE_SEGMENT:
|
||||
tp += snprintf(tp,te-tp,"%s",_("Segment"));
|
||||
break;
|
||||
case VCDINFO_ITEM_TYPE_LID:
|
||||
tp += snprintf(tp,te-tp,"%s",_("List ID"));
|
||||
break;
|
||||
case VCDINFO_ITEM_TYPE_SPAREID2:
|
||||
tp += snprintf(tp,te-tp,"%s",_("Navigation"));
|
||||
break;
|
||||
default:
|
||||
/* What to do? */
|
||||
;
|
||||
}
|
||||
saw_control_prefix = false;
|
||||
}
|
||||
break;
|
||||
|
||||
case 'L':
|
||||
if (vcdplayer_pbc_is_on(p_vcdplayer))
|
||||
tp += snprintf(tp,te-tp,"%s %d",_("List ID"),p_vcdplayer->i_lid);
|
||||
saw_control_prefix = false;
|
||||
break;
|
||||
|
||||
case 'M':
|
||||
tp += snprintf(tp,te-tp,"%s",mrl);
|
||||
break;
|
||||
|
||||
case 'N':
|
||||
tp += snprintf(tp,te-tp,"%d",itemid->num);
|
||||
break;
|
||||
|
||||
case 'p':
|
||||
tp += snprintf(tp,te-tp,"%s",vcdinfo_get_preparer_id(p_vcdplayer->vcd));
|
||||
break;
|
||||
|
||||
case 'P':
|
||||
tp += snprintf(tp,te-tp,"%s",vcdinfo_get_publisher_id(p_vcdplayer->vcd));
|
||||
break;
|
||||
|
||||
case 'S':
|
||||
if ( VCDINFO_ITEM_TYPE_SEGMENT==itemid->type ) {
|
||||
tp += snprintf(tp,te-tp," %s",
|
||||
vcdinfo_video_type2str(p_vcdplayer->vcd, itemid->num));
|
||||
}
|
||||
saw_control_prefix = false;
|
||||
break;
|
||||
|
||||
case 'T':
|
||||
tp += snprintf(tp,te-tp,"%d",p_vcdplayer->i_track);
|
||||
break;
|
||||
|
||||
case 'V':
|
||||
tp += snprintf(tp,te-tp,"%s",vcdinfo_get_volumeset_id(p_vcdplayer->vcd));
|
||||
break;
|
||||
|
||||
case 'v':
|
||||
tp += snprintf(tp,te-tp,"%s",vcdinfo_get_volume_id(p_vcdplayer->vcd));
|
||||
break;
|
||||
|
||||
default:
|
||||
*tp++ = '%';
|
||||
if(tp<te)
|
||||
*tp++ = *format_str;
|
||||
saw_control_prefix = false;
|
||||
}
|
||||
}
|
||||
return strdup(temp_str);
|
||||
}
|
||||
|
||||
void
|
||||
VCDUpdateTitle( access_t *p_access )
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer= (vcdplayer_t *)p_access->p_sys;
|
||||
|
||||
size_t psz_mrl_max = strlen(VCD_MRL_PREFIX)
|
||||
+ strlen(p_vcdplayer->psz_source) + sizeof("@E999")+3;
|
||||
char *psz_mrl = malloc( psz_mrl_max );
|
||||
|
||||
if( psz_mrl )
|
||||
{
|
||||
char *psz_name;
|
||||
char *psz_tfmt = var_InheritString( p_access, MODULE_STRING "-title-format" );
|
||||
snprintf( psz_mrl, psz_mrl_max, "%s%s",
|
||||
VCD_MRL_PREFIX, p_vcdplayer->psz_source );
|
||||
if( psz_tfmt )
|
||||
{
|
||||
psz_name = VCDFormatStr( p_vcdplayer, psz_tfmt, psz_mrl,
|
||||
&(p_vcdplayer->play_item) );
|
||||
free(psz_tfmt);
|
||||
input_Control( p_vcdplayer->p_input, INPUT_SET_NAME, psz_name );
|
||||
free(psz_name);
|
||||
}
|
||||
free(psz_mrl);
|
||||
}
|
||||
}
|
||||
|
|
@ -1,44 +0,0 @@
|
|||
/*****************************************************************************
|
||||
* info.h : VCD information routine headers
|
||||
*****************************************************************************
|
||||
* Copyright (C) 2004 VLC authors and VideoLAN
|
||||
* $Id$
|
||||
*
|
||||
* Authors: Rocky Bernstein <rocky@panix.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation; either version 2.1 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
|
||||
*****************************************************************************/
|
||||
|
||||
#ifndef VCD_INFO_H
|
||||
#define VCD_INFO_H
|
||||
|
||||
#include "vcdplayer.h"
|
||||
|
||||
/*
|
||||
Sets VCD meta information and navigation/playlist entries.
|
||||
*/
|
||||
void VCDMetaInfo( access_t *p_access, /*const*/ char *psz_mrl );
|
||||
|
||||
|
||||
#if 0
|
||||
char * VCDFormatStr(vcdplayer_t *p_vcdplayer,
|
||||
const char *format_str, const char *mrl,
|
||||
const vcdinfo_itemid_t *itemid);
|
||||
#endif
|
||||
|
||||
|
||||
void VCDUpdateTitle( access_t *p_access );
|
||||
|
||||
#endif /* VCD_INFO_H */
|
|
@ -1,127 +0,0 @@
|
|||
/*****************************************************************************
|
||||
* vcd.c : VCD input module for vlc
|
||||
*****************************************************************************
|
||||
* Copyright (C) 2000, 2003, 2004, 2005 VLC authors and VideoLAN
|
||||
* $Id$
|
||||
*
|
||||
* Authors: Rocky Bernstein <rocky@panix.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation; either version 2.1 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
|
||||
*****************************************************************************/
|
||||
|
||||
/*****************************************************************************
|
||||
* top-level module code - handles options, shortcuts, loads sub-modules.
|
||||
*****************************************************************************/
|
||||
|
||||
/*****************************************************************************
|
||||
* Preamble
|
||||
*****************************************************************************/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#include <vlc_common.h>
|
||||
#include <vlc_plugin.h>
|
||||
|
||||
#include "vcd.h"
|
||||
#include "access.h"
|
||||
|
||||
/*****************************************************************************
|
||||
* Option help text
|
||||
*****************************************************************************/
|
||||
|
||||
#define DEBUG_LONGTEXT \
|
||||
"This integer when viewed in binary is a debugging mask\n" \
|
||||
"meta info 1\n" \
|
||||
"event info 2\n" \
|
||||
"MRL 4\n" \
|
||||
"external call 8\n" \
|
||||
"all calls (10) 16\n" \
|
||||
"LSN (20) 32\n" \
|
||||
"PBC (40) 64\n" \
|
||||
"libcdio (80) 128\n" \
|
||||
"seek-set (100) 256\n" \
|
||||
"seek-cur (200) 512\n" \
|
||||
"still (400) 1024\n" \
|
||||
"vcdinfo (800) 2048\n"
|
||||
|
||||
#define VCD_TITLE_FMT_LONGTEXT \
|
||||
"Format used in the GUI Playlist Title. Similar to the Unix date \n" \
|
||||
"Format specifiers that start with a percent sign. Specifiers are: \n" \
|
||||
" %A : The album information\n" \
|
||||
" %C : The VCD volume count - the number of CDs in the collection\n" \
|
||||
" %c : The VCD volume num - the number of the CD in the collection.\n" \
|
||||
" %F : The VCD Format, e.g. VCD 1.0, VCD 1.1, VCD 2.0, or SVCD\n" \
|
||||
" %I : The current entry/segment/playback type, e.g. ENTRY, TRACK, SEGMENT...\n" \
|
||||
" %L : The playlist ID prefixed with \" LID\" if it exists\n" \
|
||||
" %N : The current number of the %I - a decimal number\n" \
|
||||
" %P : The publisher ID\n" \
|
||||
" %p : The preparer ID\n" \
|
||||
" %S : If we are in a segment (menu), the kind of segment\n" \
|
||||
" %T : The MPEG track number (starts at 1)\n" \
|
||||
" %V : The volume set ID\n" \
|
||||
" %v : The volume ID\n" \
|
||||
" A number between 1 and the volume count.\n" \
|
||||
" %% : a % \n"
|
||||
|
||||
/*****************************************************************************
|
||||
* Module descriptor
|
||||
*****************************************************************************/
|
||||
|
||||
vlc_module_begin ()
|
||||
set_shortname( N_("(Super) Video CD"))
|
||||
set_description( N_("Video CD (VCD 1.0, 1.1, 2.0, SVCD, HQVCD) input") )
|
||||
add_usage_hint( N_("vcdx://[device-or-file][@{P,S,T}num]") )
|
||||
add_shortcut( "vcdx" )
|
||||
set_category( CAT_INPUT )
|
||||
set_subcategory( SUBCAT_INPUT_ACCESS )
|
||||
set_capability( "access", 55 /* slightly lower than vcd */ )
|
||||
set_callbacks( VCDOpen, VCDClose )
|
||||
|
||||
/* Configuration options */
|
||||
add_integer ( MODULE_STRING "-debug", 0,
|
||||
N_("If nonzero, this gives additional debug information."),
|
||||
DEBUG_LONGTEXT, true )
|
||||
|
||||
add_integer ( MODULE_STRING "-blocks-per-read", 20,
|
||||
N_("Number of CD blocks to get in a single read."),
|
||||
N_("Number of CD blocks to get in a single read."),
|
||||
true )
|
||||
|
||||
add_bool( MODULE_STRING "-PBC", false,
|
||||
N_("Use playback control?"),
|
||||
N_("If VCD is authored with playback control, use it. "
|
||||
"Otherwise we play by tracks."),
|
||||
false )
|
||||
|
||||
add_obsolete_bool( MODULE_STRING "-track-length" )
|
||||
|
||||
add_bool( MODULE_STRING "-extended-info", false,
|
||||
N_("Show extended VCD info?"),
|
||||
N_("Show the maximum amount of information under Stream and "
|
||||
"Media Info. Shows for example playback control navigation."),
|
||||
false )
|
||||
|
||||
add_string( MODULE_STRING "-author-format", "%v - %F disc %c of %C",
|
||||
N_("Format to use in the playlist's \"author\" field."),
|
||||
VCD_TITLE_FMT_LONGTEXT, true )
|
||||
|
||||
add_string( MODULE_STRING "-title-format", "%I %N %L%S - %M %A %v - disc %c of %C %F",
|
||||
N_("Format to use in the playlist's \"title\" field."),
|
||||
VCD_TITLE_FMT_LONGTEXT, false )
|
||||
|
||||
vlc_module_end ()
|
||||
|
|
@ -1,55 +0,0 @@
|
|||
/*****************************************************************************
|
||||
* vcd.h : VCD input module header for vlc
|
||||
* using libcdio, libvcd and libvcdinfo
|
||||
*****************************************************************************
|
||||
* Copyright (C) 2003, 2004 VLC authors and VideoLAN
|
||||
* $Id$
|
||||
*
|
||||
* Authors: Rocky Bernstein <rocky@panix.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation; either version 2.1 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
|
||||
*****************************************************************************/
|
||||
|
||||
#include <libvcd/info.h>
|
||||
#include <vlc_interface.h>
|
||||
|
||||
#define VCD_MRL_PREFIX "vcdx://"
|
||||
|
||||
/*****************************************************************************
|
||||
* vcd_data_t: structure for communication between access and intf.
|
||||
*****************************************************************************/
|
||||
typedef struct {
|
||||
#ifdef FINISHED
|
||||
vcdplay_ptr vmg;
|
||||
#endif
|
||||
|
||||
#ifdef DEMUX_FINISHED
|
||||
int i_audio_nb;
|
||||
int i_spu_nb;
|
||||
#endif
|
||||
|
||||
int i_still_time;
|
||||
bool b_end_of_cell;
|
||||
|
||||
#ifdef FINISHED
|
||||
vcdplay_event_t event;
|
||||
vcdplay_ctrl_t control;
|
||||
vcdplay_highlight_t hli;
|
||||
#endif
|
||||
|
||||
} vcd_data_t;
|
||||
|
||||
int VCDSetArea ( access_t * );
|
||||
int VCDSeek ( access_t *, uint64_t );
|
|
@ -1,952 +0,0 @@
|
|||
/*****************************************************************************
|
||||
* vcdplayer.c : VCD input module for vlc
|
||||
* using libcdio, libvcd and libvcdinfo
|
||||
*****************************************************************************
|
||||
* Copyright (C) 2003, 2004 Rocky Bernstein <rocky@panix.com>
|
||||
* $Id$
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation; either version 2.1 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
|
||||
*****************************************************************************/
|
||||
|
||||
/*
|
||||
This contains more of the vlc-independent parts that might be used
|
||||
in any VCD input module for a media player. However at present there
|
||||
are vlc-specific structures. See also vcdplayer.c of the xine plugin.
|
||||
*/
|
||||
/*****************************************************************************
|
||||
* Preamble
|
||||
*****************************************************************************/
|
||||
|
||||
#ifdef HAVE_CONFIG_H
|
||||
# include "config.h"
|
||||
#endif
|
||||
|
||||
#include <vlc_common.h>
|
||||
#include <vlc_input.h>
|
||||
#include <vlc_interface.h>
|
||||
#include <vlc_rand.h>
|
||||
|
||||
#include "vcd.h"
|
||||
#include "vcdplayer.h"
|
||||
#include "access.h"
|
||||
|
||||
#include <cdio/cdio.h>
|
||||
#include <cdio/util.h>
|
||||
#include <libvcd/info.h>
|
||||
|
||||
/*!
|
||||
Return true if playback control (PBC) is on
|
||||
*/
|
||||
bool
|
||||
vcdplayer_pbc_is_on( const vcdplayer_t *p_vcdplayer )
|
||||
{
|
||||
return VCDINFO_INVALID_ENTRY != p_vcdplayer->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_vcdplayer= (vcdplayer_t *)p_access->p_sys;
|
||||
|
||||
switch (itemid.type) {
|
||||
case VCDINFO_ITEM_TYPE_ENTRY:
|
||||
return p_vcdplayer->entry[itemid.num].size;
|
||||
break;
|
||||
case VCDINFO_ITEM_TYPE_SEGMENT:
|
||||
return p_vcdplayer->segment[itemid.num].size;
|
||||
break;
|
||||
case VCDINFO_ITEM_TYPE_TRACK:
|
||||
return p_vcdplayer->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", "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)
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer= (vcdplayer_t *)p_access->p_sys;
|
||||
|
||||
if ( ofs == VCDINFO_INVALID_OFFSET ) {
|
||||
*entry = VCDINFO_INVALID_ENTRY;
|
||||
} else {
|
||||
vcdinfo_offset_t *off = vcdinfo_get_offset_t(p_vcdplayer->vcd, ofs);
|
||||
if (off != NULL) {
|
||||
*entry = off->lid;
|
||||
dbg_print(INPUT_DBG_PBC, "%s: LID %d", label, off->lid);
|
||||
} else
|
||||
*entry = VCDINFO_INVALID_ENTRY;
|
||||
}
|
||||
}
|
||||
|
||||
/* Handles navigation when NOT in PBC reaching the end of a play item.
|
||||
|
||||
The navigations rules here may be sort of made up, but the intent
|
||||
is to do something that's probably right or helpful.
|
||||
|
||||
return true if the caller should return.
|
||||
*/
|
||||
static vcdplayer_read_status_t
|
||||
vcdplayer_non_pbc_nav ( access_t *p_access, uint8_t *wait_time )
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer= (vcdplayer_t *)p_access->p_sys;
|
||||
|
||||
/* Not in playback control. Do we advance automatically or stop? */
|
||||
switch (p_vcdplayer->play_item.type) {
|
||||
case VCDINFO_ITEM_TYPE_TRACK:
|
||||
case VCDINFO_ITEM_TYPE_ENTRY: {
|
||||
if ( ! vcdplayer_play_next( p_access ) )
|
||||
return READ_END;
|
||||
break;
|
||||
}
|
||||
case VCDINFO_ITEM_TYPE_SPAREID2:
|
||||
dbg_print( (INPUT_DBG_STILL|INPUT_DBG_LSN),
|
||||
"SPAREID2" );
|
||||
if (p_vcdplayer->in_still)
|
||||
{
|
||||
dbg_print( (INPUT_DBG_STILL|INPUT_DBG_LSN),
|
||||
"End of still spareid2" );
|
||||
*wait_time = 255;
|
||||
return READ_STILL_FRAME ;
|
||||
}
|
||||
return READ_END;
|
||||
case VCDINFO_ITEM_TYPE_NOTFOUND:
|
||||
LOG_ERR ("NOTFOUND outside PBC -- not supposed to happen");
|
||||
return READ_ERROR;
|
||||
case VCDINFO_ITEM_TYPE_LID:
|
||||
LOG_ERR ("LID outside PBC -- not supposed to happen");
|
||||
return READ_ERROR;
|
||||
case VCDINFO_ITEM_TYPE_SEGMENT:
|
||||
/* Hack: Just go back and do still again */
|
||||
/* FIXME */
|
||||
if (p_vcdplayer->in_still)
|
||||
{
|
||||
dbg_print( (INPUT_DBG_STILL|INPUT_DBG_LSN),
|
||||
"End of still Segment" );
|
||||
*wait_time = 10;
|
||||
return READ_STILL_FRAME;
|
||||
}
|
||||
return READ_END;
|
||||
}
|
||||
return READ_BLOCK;
|
||||
}
|
||||
|
||||
/*!
|
||||
Set reading to play an entire track.
|
||||
*/
|
||||
static void
|
||||
_vcdplayer_set_track(access_t * p_access, track_t i_track)
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer = (vcdplayer_t *)p_access->p_sys;
|
||||
if (i_track < 1 || i_track > p_vcdplayer->i_tracks)
|
||||
return;
|
||||
else {
|
||||
const vcdinfo_obj_t *p_vcdinfo = p_vcdplayer->vcd;
|
||||
vcdinfo_itemid_t itemid;
|
||||
|
||||
itemid.num = i_track;
|
||||
itemid.type = VCDINFO_ITEM_TYPE_TRACK;
|
||||
p_vcdplayer->in_still = 0;
|
||||
|
||||
VCDSetOrigin(p_access, vcdinfo_get_track_lsn(p_vcdinfo, i_track),
|
||||
i_track, &itemid);
|
||||
|
||||
dbg_print(INPUT_DBG_LSN, "LSN: %u", p_vcdplayer->i_lsn);
|
||||
}
|
||||
}
|
||||
|
||||
/*!
|
||||
Set reading to play an entry
|
||||
*/
|
||||
static void
|
||||
_vcdplayer_set_entry(access_t * p_access, unsigned int num)
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer = (vcdplayer_t *)p_access->p_sys;
|
||||
vcdinfo_obj_t *p_vcdinfo = p_vcdplayer->vcd;
|
||||
const unsigned int i_entries = vcdinfo_get_num_entries(p_vcdinfo);
|
||||
|
||||
if (num >= i_entries) {
|
||||
LOG_ERR("%s %d", "bad entry number", num);
|
||||
return;
|
||||
} else {
|
||||
vcdinfo_itemid_t itemid;
|
||||
|
||||
itemid.num = num;
|
||||
itemid.type = VCDINFO_ITEM_TYPE_ENTRY;
|
||||
p_vcdplayer->i_still = 0;
|
||||
|
||||
VCDSetOrigin(p_access, vcdinfo_get_entry_lsn(p_vcdinfo, num),
|
||||
vcdinfo_get_track(p_vcdinfo, num), &itemid);
|
||||
|
||||
dbg_print(INPUT_DBG_LSN, "LSN: %u, track_end LSN: %u",
|
||||
p_vcdplayer->i_lsn, p_vcdplayer->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_vcdplayer = (vcdplayer_t *)p_access->p_sys;
|
||||
vcdinfo_obj_t *p_vcdinfo = p_vcdplayer->vcd;
|
||||
segnum_t i_segs = vcdinfo_get_num_segments(p_vcdinfo);
|
||||
|
||||
if (num >= i_segs) {
|
||||
LOG_ERR("%s %d", "bad segment number", num);
|
||||
return;
|
||||
} else {
|
||||
vcdinfo_itemid_t itemid;
|
||||
|
||||
if (VCDINFO_NULL_LSN==p_vcdplayer->i_lsn) {
|
||||
LOG_ERR("%s %d",
|
||||
"Error in getting current segment number", num);
|
||||
return;
|
||||
}
|
||||
|
||||
itemid.num = num;
|
||||
itemid.type = VCDINFO_ITEM_TYPE_SEGMENT;
|
||||
|
||||
VCDSetOrigin(p_access, vcdinfo_get_seg_lsn(p_vcdinfo, num), 0, &itemid);
|
||||
|
||||
dbg_print(INPUT_DBG_LSN, "LSN: %u", p_vcdplayer->i_lsn);
|
||||
}
|
||||
}
|
||||
|
||||
/* Play entry. */
|
||||
/* Play a single item. */
|
||||
static bool
|
||||
vcdplayer_play_single_item( access_t * p_access, vcdinfo_itemid_t itemid)
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer = (vcdplayer_t *)p_access->p_sys;
|
||||
vcdinfo_obj_t *p_vcdinfo = p_vcdplayer->vcd;
|
||||
|
||||
dbg_print(INPUT_DBG_CALL, "called itemid.num: %d, itemid.type: %d",
|
||||
itemid.num, itemid.type);
|
||||
|
||||
p_vcdplayer->i_still = 0;
|
||||
|
||||
switch (itemid.type) {
|
||||
case VCDINFO_ITEM_TYPE_SEGMENT:
|
||||
{
|
||||
vcdinfo_video_segment_type_t segtype
|
||||
= vcdinfo_get_video_type(p_vcdinfo, itemid.num);
|
||||
segnum_t i_segs = vcdinfo_get_num_segments(p_vcdinfo);
|
||||
|
||||
dbg_print(INPUT_DBG_PBC, "%s (%d), itemid.num: %d",
|
||||
vcdinfo_video_type2str(p_vcdinfo, itemid.num),
|
||||
(int) segtype, itemid.num);
|
||||
|
||||
if (itemid.num >= i_segs) return false;
|
||||
_vcdplayer_set_segment(p_access, itemid.num);
|
||||
|
||||
switch (segtype)
|
||||
{
|
||||
case VCDINFO_FILES_VIDEO_NTSC_STILL:
|
||||
case VCDINFO_FILES_VIDEO_NTSC_STILL2:
|
||||
case VCDINFO_FILES_VIDEO_PAL_STILL:
|
||||
case VCDINFO_FILES_VIDEO_PAL_STILL2:
|
||||
p_vcdplayer->i_still = STILL_READING;
|
||||
break;
|
||||
default:
|
||||
p_vcdplayer->i_still = 0;
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
case VCDINFO_ITEM_TYPE_TRACK:
|
||||
dbg_print(INPUT_DBG_PBC, "track %d", itemid.num);
|
||||
if (itemid.num < 1 || itemid.num > p_vcdplayer->i_tracks) return false;
|
||||
_vcdplayer_set_track(p_access, itemid.num);
|
||||
break;
|
||||
|
||||
case VCDINFO_ITEM_TYPE_ENTRY:
|
||||
{
|
||||
unsigned int i_entries = vcdinfo_get_num_entries(p_vcdinfo);
|
||||
dbg_print(INPUT_DBG_PBC, "entry %d", itemid.num);
|
||||
if (itemid.num >= i_entries) return false;
|
||||
_vcdplayer_set_entry(p_access, itemid.num);
|
||||
break;
|
||||
}
|
||||
|
||||
case VCDINFO_ITEM_TYPE_LID:
|
||||
LOG_ERR("%s", "Should have converted p_vcdplayer above");
|
||||
return false;
|
||||
break;
|
||||
|
||||
case VCDINFO_ITEM_TYPE_NOTFOUND:
|
||||
dbg_print(INPUT_DBG_PBC, "play nothing");
|
||||
p_vcdplayer->i_lsn = p_vcdplayer->end_lsn;
|
||||
return false;
|
||||
|
||||
default:
|
||||
LOG_ERR("item type %d not implemented.", itemid.type);
|
||||
return false;
|
||||
}
|
||||
|
||||
p_vcdplayer->play_item = itemid;
|
||||
|
||||
/* Some players like xine, have a fifo queue of audio and video buffers
|
||||
that need to be flushed when playing a new selection. */
|
||||
/* if (p_vcdplayer->flush_buffers)
|
||||
p_vcdplayer->flush_buffers(); */
|
||||
return true;
|
||||
}
|
||||
|
||||
/*
|
||||
Set's start origin and size for subsequent seeks.
|
||||
input: p_vcdplayer->i_lsn, p_vcdplayer->play_item
|
||||
changed: p_vcdplayer->origin_lsn, p_vcdplayer->end_lsn
|
||||
*/
|
||||
|
||||
void
|
||||
vcdplayer_set_origin(access_t *p_access, lsn_t i_lsn, track_t i_track,
|
||||
const vcdinfo_itemid_t *p_itemid)
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer = (vcdplayer_t *)p_access->p_sys;
|
||||
const size_t i_size= vcdplayer_get_item_size(p_access, *p_itemid);
|
||||
|
||||
if( VCDINFO_NULL_LSN == i_lsn )
|
||||
{
|
||||
LOG_ERR("%s %d", "Invalid LSN for track", i_track);
|
||||
return;
|
||||
}
|
||||
|
||||
p_vcdplayer->play_item.num = p_itemid->num;
|
||||
p_vcdplayer->play_item.type = p_itemid->type;
|
||||
p_vcdplayer->i_lsn = i_lsn;
|
||||
p_vcdplayer->end_lsn = p_vcdplayer->i_lsn + i_size;
|
||||
p_vcdplayer->origin_lsn = p_vcdplayer->i_lsn;
|
||||
p_vcdplayer->i_track = i_track;
|
||||
p_vcdplayer->track_lsn = vcdinfo_get_track_lsn(p_vcdplayer->vcd,
|
||||
i_track);
|
||||
p_vcdplayer->track_end_lsn = p_vcdplayer->track_lsn +
|
||||
vcdinfo_get_track_sect_count(p_vcdplayer->vcd, i_track);
|
||||
|
||||
dbg_print((INPUT_DBG_CALL|INPUT_DBG_LSN),
|
||||
"lsn %u, end LSN: %u item.num %d, item.type %d",
|
||||
p_vcdplayer->i_lsn, p_vcdplayer->end_lsn,
|
||||
p_vcdplayer->play_item.num, p_vcdplayer->play_item.type);
|
||||
}
|
||||
|
||||
/*!
|
||||
Get the next play-item in the list given in the LIDs. Note play-item
|
||||
here refers to list of play-items for a single LID It shouldn't be
|
||||
confused with a user's list of favorite things to play or the
|
||||
"next" field of a LID which moves us to a different LID.
|
||||
*/
|
||||
static bool
|
||||
vcdplayer_inc_play_item(access_t *p_access)
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer = (vcdplayer_t *)p_access->p_sys;
|
||||
int noi;
|
||||
|
||||
dbg_print(INPUT_DBG_CALL, "called pli: %d", p_vcdplayer->pdi);
|
||||
|
||||
if ( NULL == p_vcdplayer || NULL == p_vcdplayer->pxd.pld )
|
||||
return false;
|
||||
|
||||
noi = vcdinf_pld_get_noi(p_vcdplayer->pxd.pld);
|
||||
if ( noi <= 0 )
|
||||
return false;
|
||||
|
||||
/* Handle delays like autowait or wait here? */
|
||||
|
||||
p_vcdplayer->pdi++;
|
||||
|
||||
if ( p_vcdplayer->pdi < 0 || p_vcdplayer->pdi >= noi )
|
||||
return false;
|
||||
|
||||
uint16_t trans_itemid_num=vcdinf_pld_get_play_item(p_vcdplayer->pxd.pld,
|
||||
p_vcdplayer->pdi);
|
||||
vcdinfo_itemid_t trans_itemid;
|
||||
|
||||
if (VCDINFO_INVALID_ITEMID == trans_itemid_num) return false;
|
||||
|
||||
vcdinfo_classify_itemid(trans_itemid_num, &trans_itemid);
|
||||
dbg_print(INPUT_DBG_PBC, " play-item[%d]: %s",
|
||||
p_vcdplayer->pdi, vcdinfo_pin2str (trans_itemid_num));
|
||||
return vcdplayer_play_single_item(p_access, trans_itemid);
|
||||
}
|
||||
|
||||
void
|
||||
vcdplayer_play(access_t *p_access, vcdinfo_itemid_t itemid)
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer = (vcdplayer_t *)p_access->p_sys;
|
||||
|
||||
dbg_print(INPUT_DBG_CALL, "called itemid.num: %d itemid.type: %d",
|
||||
itemid.num, itemid.type);
|
||||
|
||||
if (!vcdplayer_pbc_is_on(p_vcdplayer)) {
|
||||
vcdplayer_play_single_item(p_access, itemid);
|
||||
} else {
|
||||
/* PBC on - Itemid.num is LID. */
|
||||
|
||||
vcdinfo_obj_t *p_vcdinfo = p_vcdplayer->vcd;
|
||||
|
||||
if (p_vcdinfo == NULL)
|
||||
return;
|
||||
|
||||
p_vcdplayer->i_lid = itemid.num;
|
||||
vcdinfo_lid_get_pxd(p_vcdinfo, &(p_vcdplayer->pxd), itemid.num);
|
||||
|
||||
switch (p_vcdplayer->pxd.descriptor_type) {
|
||||
|
||||
case PSD_TYPE_SELECTION_LIST:
|
||||
case PSD_TYPE_EXT_SELECTION_LIST: {
|
||||
vcdinfo_itemid_t trans_itemid;
|
||||
uint16_t trans_itemid_num;
|
||||
|
||||
if (p_vcdplayer->pxd.psd == NULL) return;
|
||||
trans_itemid_num = vcdinf_psd_get_itemid(p_vcdplayer->pxd.psd);
|
||||
vcdinfo_classify_itemid(trans_itemid_num, &trans_itemid);
|
||||
p_vcdplayer->i_loop = 1;
|
||||
p_vcdplayer->loop_item = trans_itemid;
|
||||
vcdplayer_play_single_item(p_access, trans_itemid);
|
||||
break;
|
||||
}
|
||||
|
||||
case PSD_TYPE_PLAY_LIST: {
|
||||
if (p_vcdplayer->pxd.pld == NULL) return;
|
||||
p_vcdplayer->pdi = -1;
|
||||
vcdplayer_inc_play_item(p_access);
|
||||
break;
|
||||
}
|
||||
|
||||
case PSD_TYPE_END_LIST:
|
||||
case PSD_TYPE_COMMAND_LIST:
|
||||
|
||||
default:
|
||||
;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* Handles PBC navigation when reaching the end of a play item. */
|
||||
static vcdplayer_read_status_t
|
||||
vcdplayer_pbc_nav ( access_t * p_access, uint8_t *wait_time )
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer= (vcdplayer_t *)p_access->p_sys;
|
||||
|
||||
/* We are in playback control. */
|
||||
vcdinfo_itemid_t itemid;
|
||||
|
||||
/* The end of an entry is really the end of the associated
|
||||
sequence (or track). */
|
||||
|
||||
if ( (VCDINFO_ITEM_TYPE_ENTRY == p_vcdplayer->play_item.type) &&
|
||||
(p_vcdplayer->i_lsn < p_vcdplayer->end_lsn) ) {
|
||||
/* Set up to just continue to the next entry */
|
||||
p_vcdplayer->play_item.num++;
|
||||
dbg_print( (INPUT_DBG_LSN|INPUT_DBG_PBC),
|
||||
"continuing into next entry: %u", p_vcdplayer->play_item.num);
|
||||
vcdplayer_play_single_item( p_access, p_vcdplayer->play_item );
|
||||
/* p_vcdplayer->update_title(); */
|
||||
return READ_BLOCK;
|
||||
}
|
||||
|
||||
switch (p_vcdplayer->pxd.descriptor_type) {
|
||||
case PSD_TYPE_END_LIST:
|
||||
return READ_END;
|
||||
break;
|
||||
case PSD_TYPE_PLAY_LIST: {
|
||||
if (vcdplayer_inc_play_item(p_access))
|
||||
return READ_BLOCK;
|
||||
|
||||
/* Set up for caller process wait time given. */
|
||||
if (p_vcdplayer->i_still) {
|
||||
*wait_time = vcdinf_get_wait_time(p_vcdplayer->pxd.pld);
|
||||
dbg_print((INPUT_DBG_PBC|INPUT_DBG_STILL),
|
||||
"playlist wait time: %d", *wait_time);
|
||||
return READ_STILL_FRAME;
|
||||
}
|
||||
|
||||
/* Wait time has been processed; continue with next entry. */
|
||||
vcdplayer_update_entry( p_access,
|
||||
vcdinf_pld_get_next_offset(p_vcdplayer->pxd.pld),
|
||||
&itemid.num, "next" );
|
||||
itemid.type = VCDINFO_ITEM_TYPE_LID;
|
||||
vcdplayer_play( p_access, itemid );
|
||||
break;
|
||||
}
|
||||
case PSD_TYPE_SELECTION_LIST: /* Selection List (+Ext. for SVCD) */
|
||||
case PSD_TYPE_EXT_SELECTION_LIST: /* Extended Selection List (VCD2.0) */
|
||||
{
|
||||
uint16_t timeout_offs = vcdinf_get_timeout_offset(p_vcdplayer->pxd.psd);
|
||||
uint16_t max_loop = vcdinf_get_loop_count(p_vcdplayer->pxd.psd);
|
||||
vcdinfo_offset_t *offset_timeout_LID =
|
||||
vcdinfo_get_offset_t(p_vcdplayer->vcd, timeout_offs);
|
||||
|
||||
dbg_print(INPUT_DBG_PBC, "looped: %d, max_loop %d",
|
||||
p_vcdplayer->i_loop, max_loop);
|
||||
|
||||
/* Set up for caller process wait time given. */
|
||||
if (p_vcdplayer->i_still) {
|
||||
*wait_time = vcdinf_get_timeout_time(p_vcdplayer->pxd.psd);
|
||||
dbg_print((INPUT_DBG_PBC|INPUT_DBG_STILL),
|
||||
"playlist wait_time: %d", *wait_time);
|
||||
return READ_STILL_FRAME;
|
||||
}
|
||||
|
||||
/* Wait time has been processed; continue with next entry. */
|
||||
/* Handle any looping given. */
|
||||
if ( max_loop == 0 || p_vcdplayer->i_loop < max_loop ) {
|
||||
p_vcdplayer->i_loop++;
|
||||
if (p_vcdplayer->i_loop == 0x7f) p_vcdplayer->i_loop = 0;
|
||||
vcdplayer_play_single_item(p_access, p_vcdplayer->loop_item);
|
||||
/* if (p_vcdplayer->i_still) p_vcdplayer->force_redisplay();*/
|
||||
return READ_BLOCK;
|
||||
}
|
||||
|
||||
/* Looping finished and wait finished. Move to timeout
|
||||
entry or next entry, or handle still. */
|
||||
|
||||
if (NULL != offset_timeout_LID) {
|
||||
/* Handle timeout_LID */
|
||||
itemid.num = offset_timeout_LID->lid;
|
||||
itemid.type = VCDINFO_ITEM_TYPE_LID;
|
||||
dbg_print(INPUT_DBG_PBC, "timeout to: %d", itemid.num);
|
||||
vcdplayer_play( p_access, itemid );
|
||||
return READ_BLOCK;
|
||||
} else {
|
||||
int i_selections = vcdinf_get_num_selections(p_vcdplayer->pxd.psd);
|
||||
if (i_selections > 0) {
|
||||
/* Pick a random selection. */
|
||||
unsigned int bsn=vcdinf_get_bsn(p_vcdplayer->pxd.psd);
|
||||
int rand_selection=bsn +
|
||||
((unsigned)vlc_lrand48() % (unsigned)i_selections);
|
||||
lid_t rand_lid=vcdinfo_selection_get_lid (p_vcdplayer->vcd,
|
||||
p_vcdplayer->i_lid,
|
||||
rand_selection);
|
||||
itemid.num = rand_lid;
|
||||
itemid.type = VCDINFO_ITEM_TYPE_LID;
|
||||
dbg_print(INPUT_DBG_PBC, "random selection %d, lid: %d",
|
||||
rand_selection - bsn, rand_lid);
|
||||
vcdplayer_play( p_access, itemid );
|
||||
return READ_BLOCK;
|
||||
} else if (p_vcdplayer->i_still) {
|
||||
/* Hack: Just go back and do still again */
|
||||
msleep(10000);
|
||||
return READ_STILL_FRAME;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
;
|
||||
}
|
||||
/* FIXME: Should handle autowait ... */
|
||||
|
||||
return READ_ERROR;
|
||||
}
|
||||
|
||||
/*!
|
||||
Read block into p_buf and return the status back.
|
||||
|
||||
This routine is a bit complicated because on reaching the end of
|
||||
a track or entry we may automatically advance to the item, or
|
||||
interpret the next item in the playback-control list.
|
||||
*/
|
||||
vcdplayer_read_status_t
|
||||
vcdplayer_read (access_t * p_access, uint8_t *p_buf)
|
||||
{
|
||||
|
||||
/* p_access->handle_events (); */
|
||||
uint8_t wait_time=0;
|
||||
|
||||
vcdplayer_t *p_vcdplayer= (vcdplayer_t *)p_access->p_sys;
|
||||
if ( p_vcdplayer->i_lsn > p_vcdplayer->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: %u, end: %u\n",
|
||||
p_vcdplayer->i_lsn, p_vcdplayer->end_lsn);
|
||||
|
||||
handle_item_continuation:
|
||||
read_status = vcdplayer_pbc_is_on( p_vcdplayer )
|
||||
? vcdplayer_pbc_nav( p_access, &wait_time )
|
||||
: vcdplayer_non_pbc_nav( p_access, &wait_time );
|
||||
|
||||
if (READ_STILL_FRAME == read_status) {
|
||||
*p_buf = wait_time;
|
||||
return READ_STILL_FRAME;
|
||||
}
|
||||
|
||||
if (READ_BLOCK != read_status) return read_status;
|
||||
}
|
||||
|
||||
/* Read the next block.
|
||||
|
||||
Important note: we probably speed things up by removing "data"
|
||||
and the memcpy to it by extending vcd_image_source_read_mode2
|
||||
to allow a mode to do what's below in addition to its
|
||||
"raw" and "block" mode. It also would probably improve the modularity
|
||||
a little bit as well.
|
||||
*/
|
||||
|
||||
{
|
||||
CdIo *p_img = vcdinfo_get_cd_image(p_vcdplayer->vcd);
|
||||
typedef struct {
|
||||
uint8_t subheader [CDIO_CD_SUBHEADER_SIZE];
|
||||
uint8_t data [M2F2_SECTOR_SIZE];
|
||||
uint8_t spare [4];
|
||||
} vcdsector_t;
|
||||
vcdsector_t vcd_sector;
|
||||
|
||||
do {
|
||||
if (cdio_read_mode2_sector(p_img, &vcd_sector,
|
||||
p_vcdplayer->i_lsn, true)!=0) {
|
||||
dbg_print(INPUT_DBG_LSN, "read error\n");
|
||||
p_vcdplayer->i_lsn++;
|
||||
return READ_ERROR;
|
||||
}
|
||||
p_vcdplayer->i_lsn++;
|
||||
|
||||
if ( p_vcdplayer->i_lsn >= p_vcdplayer->end_lsn ) {
|
||||
/* 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 in reading, cur: %u, end: %u\n",
|
||||
p_vcdplayer->i_lsn, p_vcdplayer->end_lsn);
|
||||
break;
|
||||
}
|
||||
|
||||
/* Check header ID for a padding sector and simply discard
|
||||
these. It is alleged that VCD's put these in to keep the
|
||||
bitrate constant.
|
||||
*/
|
||||
} while((vcd_sector.subheader[2]&~0x01)==0x60);
|
||||
|
||||
if ( p_vcdplayer->i_lsn >= p_vcdplayer->end_lsn )
|
||||
/* We've run off of the end of this entry. Do we continue or stop? */
|
||||
goto handle_item_continuation;
|
||||
|
||||
memcpy (p_buf, vcd_sector.data, M2F2_SECTOR_SIZE);
|
||||
return READ_BLOCK;
|
||||
}
|
||||
}
|
||||
|
||||
/*!
|
||||
Play item assocated with the "default" selection.
|
||||
|
||||
Return false if there was some problem.
|
||||
*/
|
||||
bool
|
||||
vcdplayer_play_default( access_t * p_access )
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer= (vcdplayer_t *)p_access->p_sys;
|
||||
|
||||
vcdinfo_itemid_t itemid;
|
||||
|
||||
if (!p_vcdplayer) {
|
||||
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_PBC),
|
||||
"null p_vcdplayer" );
|
||||
return VLC_EGENERIC;
|
||||
}
|
||||
|
||||
|
||||
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_PBC),
|
||||
"current: %d" , p_vcdplayer->play_item.num);
|
||||
|
||||
itemid.type = p_vcdplayer->play_item.type;
|
||||
|
||||
if (vcdplayer_pbc_is_on(p_vcdplayer)) {
|
||||
|
||||
#if defined(LIBVCD_VERSION)
|
||||
lid_t lid=vcdinfo_get_multi_default_lid(p_vcdplayer->vcd, p_vcdplayer->i_lid,
|
||||
p_vcdplayer->i_lsn);
|
||||
|
||||
if (VCDINFO_INVALID_LID != lid) {
|
||||
itemid.num = lid;
|
||||
itemid.type = VCDINFO_ITEM_TYPE_LID;
|
||||
dbg_print(INPUT_DBG_PBC, "DEFAULT to %d", itemid.num);
|
||||
} else {
|
||||
dbg_print(INPUT_DBG_PBC, "no DEFAULT for LID %d", p_vcdplayer->i_lid);
|
||||
return VLC_EGENERIC;
|
||||
}
|
||||
|
||||
#else
|
||||
vcdinfo_lid_get_pxd(p_vcdplayer->vcd, &(p_vcdplayer->pxd),
|
||||
p_vcdplayer->i_lid);
|
||||
|
||||
switch (p_vcdplayer->pxd.descriptor_type) {
|
||||
case PSD_TYPE_SELECTION_LIST:
|
||||
case PSD_TYPE_EXT_SELECTION_LIST:
|
||||
if (p_vcdplayer->pxd.psd == NULL) return false;
|
||||
vcdplayer_update_entry(p_access,
|
||||
vcdinfo_get_default_offset(p_vcdplayer->vcd,
|
||||
p_vcdplayer->i_lid),
|
||||
&itemid.num, "default");
|
||||
break;
|
||||
|
||||
case PSD_TYPE_PLAY_LIST:
|
||||
case PSD_TYPE_END_LIST:
|
||||
case PSD_TYPE_COMMAND_LIST:
|
||||
LOG_WARN( "There is no PBC 'default' selection here" );
|
||||
return false;
|
||||
}
|
||||
#endif /* LIBVCD_VERSION (< 0.7.21) */
|
||||
|
||||
|
||||
} else {
|
||||
|
||||
/* PBC is not on. "default" selection beginning of current
|
||||
selection . */
|
||||
|
||||
itemid.num = p_vcdplayer->play_item.num;
|
||||
|
||||
}
|
||||
|
||||
/** ??? p_vcdplayer->update_title(); ***/
|
||||
vcdplayer_play( p_access, itemid );
|
||||
return VLC_SUCCESS;
|
||||
|
||||
}
|
||||
|
||||
/*!
|
||||
Play item assocated with the "next" selection.
|
||||
|
||||
Return false if there was some problem.
|
||||
*/
|
||||
bool
|
||||
vcdplayer_play_next( access_t * p_access )
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer= (vcdplayer_t *)p_access->p_sys;
|
||||
|
||||
vcdinfo_obj_t *p_vcdinfo;
|
||||
vcdinfo_itemid_t itemid;
|
||||
|
||||
if (!p_vcdplayer) return false;
|
||||
|
||||
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_PBC),
|
||||
"current: %d" , p_vcdplayer->play_item.num);
|
||||
|
||||
p_vcdinfo = p_vcdplayer->vcd;
|
||||
|
||||
itemid = p_vcdplayer->play_item;
|
||||
|
||||
if (vcdplayer_pbc_is_on(p_vcdplayer)) {
|
||||
|
||||
vcdinfo_lid_get_pxd(p_vcdinfo, &(p_vcdplayer->pxd), p_vcdplayer->i_lid);
|
||||
|
||||
switch (p_vcdplayer->pxd.descriptor_type) {
|
||||
case PSD_TYPE_SELECTION_LIST:
|
||||
case PSD_TYPE_EXT_SELECTION_LIST:
|
||||
if (p_vcdplayer->pxd.psd == NULL) return false;
|
||||
vcdplayer_update_entry(p_access,
|
||||
vcdinf_psd_get_next_offset(p_vcdplayer->pxd.psd),
|
||||
&itemid.num, "next");
|
||||
itemid.type = VCDINFO_ITEM_TYPE_LID;
|
||||
break;
|
||||
|
||||
case PSD_TYPE_PLAY_LIST:
|
||||
if (p_vcdplayer->pxd.pld == NULL) return false;
|
||||
vcdplayer_update_entry(p_access,
|
||||
vcdinf_pld_get_next_offset(p_vcdplayer->pxd.pld),
|
||||
&itemid.num, "next");
|
||||
itemid.type = VCDINFO_ITEM_TYPE_LID;
|
||||
break;
|
||||
|
||||
case PSD_TYPE_END_LIST:
|
||||
case PSD_TYPE_COMMAND_LIST:
|
||||
LOG_WARN( "There is no PBC 'next' selection here" );
|
||||
return false;
|
||||
}
|
||||
} else {
|
||||
|
||||
/* PBC is not on. "Next" selection is play_item.num+1 if possible. */
|
||||
|
||||
int max_entry = 0;
|
||||
|
||||
switch (p_vcdplayer->play_item.type) {
|
||||
case VCDINFO_ITEM_TYPE_ENTRY:
|
||||
case VCDINFO_ITEM_TYPE_SEGMENT:
|
||||
case VCDINFO_ITEM_TYPE_TRACK:
|
||||
|
||||
switch (p_vcdplayer->play_item.type) {
|
||||
case VCDINFO_ITEM_TYPE_ENTRY:
|
||||
max_entry = p_vcdplayer->i_entries;
|
||||
break;
|
||||
case VCDINFO_ITEM_TYPE_SEGMENT:
|
||||
max_entry = p_vcdplayer->i_segments;
|
||||
break;
|
||||
case VCDINFO_ITEM_TYPE_TRACK:
|
||||
max_entry = p_vcdplayer->i_tracks;
|
||||
break;
|
||||
default: ; /* Handle exceptional cases below */
|
||||
}
|
||||
|
||||
if (p_vcdplayer->play_item.num+1 < max_entry) {
|
||||
itemid.num = p_vcdplayer->play_item.num+1;
|
||||
} else {
|
||||
LOG_WARN( "At the end - non-PBC 'next' not possible here" );
|
||||
return false;
|
||||
}
|
||||
|
||||
break;
|
||||
|
||||
case VCDINFO_ITEM_TYPE_LID:
|
||||
/* Should have handled above. */
|
||||
LOG_WARN( "Internal inconsistency - should not have gotten here." );
|
||||
return false;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/** ??? p_vcdplayer->update_title(); ***/
|
||||
vcdplayer_play( p_access, itemid );
|
||||
return VLC_SUCCESS;
|
||||
|
||||
}
|
||||
|
||||
/*!
|
||||
Play item assocated with the "prev" selection.
|
||||
|
||||
Return false if there was some problem.
|
||||
*/
|
||||
bool
|
||||
vcdplayer_play_prev( access_t * p_access )
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer= (vcdplayer_t *)p_access->p_sys;
|
||||
vcdinfo_obj_t *p_vcdinfo = p_vcdplayer->vcd;
|
||||
vcdinfo_itemid_t itemid;
|
||||
|
||||
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_PBC),
|
||||
"current: %d" , p_vcdplayer->play_item.num);
|
||||
|
||||
itemid = p_vcdplayer->play_item;
|
||||
|
||||
if (vcdplayer_pbc_is_on(p_vcdplayer)) {
|
||||
|
||||
vcdinfo_lid_get_pxd(p_vcdinfo, &(p_vcdplayer->pxd), p_vcdplayer->i_lid);
|
||||
|
||||
switch (p_vcdplayer->pxd.descriptor_type) {
|
||||
case PSD_TYPE_SELECTION_LIST:
|
||||
case PSD_TYPE_EXT_SELECTION_LIST:
|
||||
if (p_vcdplayer->pxd.psd == NULL) return false;
|
||||
vcdplayer_update_entry(p_access,
|
||||
vcdinf_psd_get_prev_offset(p_vcdplayer->pxd.psd),
|
||||
&itemid.num, "prev");
|
||||
itemid.type = VCDINFO_ITEM_TYPE_LID;
|
||||
break;
|
||||
|
||||
case PSD_TYPE_PLAY_LIST:
|
||||
if (p_vcdplayer->pxd.pld == NULL) return false;
|
||||
vcdplayer_update_entry(p_access,
|
||||
vcdinf_pld_get_prev_offset(p_vcdplayer->pxd.pld),
|
||||
&itemid.num, "prev");
|
||||
itemid.type = VCDINFO_ITEM_TYPE_LID;
|
||||
break;
|
||||
|
||||
case PSD_TYPE_END_LIST:
|
||||
case PSD_TYPE_COMMAND_LIST:
|
||||
LOG_WARN( "There is no PBC 'prev' selection here" );
|
||||
return false;
|
||||
}
|
||||
} else {
|
||||
|
||||
/* PBC is not on. "Prev" selection is play_item.num-1 if possible. */
|
||||
|
||||
int min_entry = (VCDINFO_ITEM_TYPE_ENTRY == p_vcdplayer->play_item.type)
|
||||
? 0 : 1;
|
||||
|
||||
if (p_vcdplayer->play_item.num > min_entry) {
|
||||
itemid.num = p_vcdplayer->play_item.num-1;
|
||||
} else {
|
||||
LOG_WARN( "At the beginning - non-PBC 'prev' not possible here" );
|
||||
return false;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/** ??? p_vcdplayer->update_title(); ***/
|
||||
vcdplayer_play( p_access, itemid );
|
||||
return VLC_SUCCESS;
|
||||
|
||||
}
|
||||
|
||||
/*!
|
||||
Play item assocated with the "return" selection.
|
||||
|
||||
Return false if there was some problem.
|
||||
*/
|
||||
bool
|
||||
vcdplayer_play_return( access_t * p_access )
|
||||
{
|
||||
vcdplayer_t *p_vcdplayer= (vcdplayer_t *)p_access->p_sys;
|
||||
vcdinfo_obj_t *p_vcdinfo = p_vcdplayer->vcd;
|
||||
vcdinfo_itemid_t itemid;
|
||||
|
||||
dbg_print( (INPUT_DBG_CALL|INPUT_DBG_PBC),
|
||||
"current: %d" , p_vcdplayer->play_item.num);
|
||||
|
||||
itemid = p_vcdplayer->play_item;
|
||||
|
||||
if (vcdplayer_pbc_is_on(p_vcdplayer)) {
|
||||
|
||||
vcdinfo_lid_get_pxd(p_vcdinfo, &(p_vcdplayer->pxd), p_vcdplayer->i_lid);
|
||||
|
||||
switch (p_vcdplayer->pxd.descriptor_type) {
|
||||
case PSD_TYPE_SELECTION_LIST:
|
||||
case PSD_TYPE_EXT_SELECTION_LIST:
|
||||
if (p_vcdplayer->pxd.psd == NULL) return false;
|
||||
vcdplayer_update_entry(p_access,
|
||||
vcdinf_psd_get_return_offset(p_vcdplayer->pxd.psd),
|
||||
&itemid.num, "return");
|
||||
itemid.type = VCDINFO_ITEM_TYPE_LID;
|
||||
break;
|
||||
|
||||
case PSD_TYPE_PLAY_LIST:
|
||||
if (p_vcdplayer->pxd.pld == NULL) return false;
|
||||
vcdplayer_update_entry(p_access,
|
||||
vcdinf_pld_get_return_offset(p_vcdplayer->pxd.pld),
|
||||
&itemid.num, "return");
|
||||
itemid.type = VCDINFO_ITEM_TYPE_LID;
|
||||
break;
|
||||
|
||||
case PSD_TYPE_END_LIST:
|
||||
case PSD_TYPE_COMMAND_LIST:
|
||||
LOG_WARN( "There is no PBC 'return' selection here" );
|
||||
return false;
|
||||
}
|
||||
} else {
|
||||
|
||||
/* PBC is not on. "Return" selection is min_entry if possible. */
|
||||
|
||||
p_vcdplayer->play_item.num =
|
||||
(VCDINFO_ITEM_TYPE_ENTRY == p_vcdplayer->play_item.type)
|
||||
? 0 : 1;
|
||||
|
||||
}
|
||||
|
||||
/** ??? p_vcdplayer->update_title(); ***/
|
||||
vcdplayer_play( p_access, itemid );
|
||||
return VLC_SUCCESS;
|
||||
|
||||
}
|
|
@ -1,232 +0,0 @@
|
|||
/*****************************************************************************
|
||||
* Copyright (C) 2003, 2004 Rocky Bernstein (for VLC authors and VideoLAN)
|
||||
* $Id$
|
||||
*
|
||||
* Authors: Rocky Bernstein <rocky@panix.com>
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms of the GNU Lesser General Public License as published by
|
||||
* the Free Software Foundation; either version 2.1 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Lesser General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Lesser General Public License
|
||||
* along with this program; if not, write to the Free Software Foundation,
|
||||
* Inc., 51 Franklin Street, Fifth Floor, Boston MA 02110-1301, USA.
|
||||
*****************************************************************************/
|
||||
|
||||
/* VCD Player header. More or less media-player independent. Or at least
|
||||
that is the goal. So we prefer bool to vlc_bool.
|
||||
*/
|
||||
|
||||
#ifndef _VCDPLAYER_H_
|
||||
#define _VCDPLAYER_H_
|
||||
|
||||
#include <libvcd/info.h>
|
||||
#include <vlc_meta.h>
|
||||
#include <vlc_input.h>
|
||||
#include <vlc_access.h>
|
||||
|
||||
#define INPUT_DBG_META 1 /* Meta information */
|
||||
#define INPUT_DBG_EVENT 2 /* input (keyboard/mouse) events */
|
||||
#define INPUT_DBG_MRL 4 /* MRL parsing */
|
||||
#define INPUT_DBG_EXT 8 /* Calls from external routines */
|
||||
#define INPUT_DBG_CALL 16 /* routine calls */
|
||||
#define INPUT_DBG_LSN 32 /* LSN changes */
|
||||
#define INPUT_DBG_PBC 64 /* Playback control */
|
||||
#define INPUT_DBG_CDIO 128 /* Debugging from CDIO */
|
||||
#define INPUT_DBG_SEEK 256 /* Seeks to set location */
|
||||
#define INPUT_DBG_SEEK_CUR 512 /* Seeks to find current location */
|
||||
#define INPUT_DBG_STILL 1024 /* Still-frame */
|
||||
#define INPUT_DBG_VCDINFO 2048 /* Debugging from VCDINFO */
|
||||
|
||||
#define INPUT_DEBUG 1
|
||||
#if INPUT_DEBUG
|
||||
#define dbg_print(mask, s, args...) \
|
||||
if (p_vcdplayer && p_vcdplayer->i_debug & mask) \
|
||||
msg_Dbg(p_access, "%s: "s, __func__ , ##args)
|
||||
#else
|
||||
#define dbg_print(mask, s, args...)
|
||||
#endif
|
||||
|
||||
#define LOG_ERR(...) msg_Err( p_access, __VA_ARGS__ )
|
||||
#define LOG_WARN(...) msg_Warn( p_access, __VA_ARGS__ )
|
||||
|
||||
/*------------------------------------------------------------------
|
||||
General definitions and structures.
|
||||
---------------------------------------------------------------------*/
|
||||
|
||||
/* Value for indefinite wait period on a still frame */
|
||||
#define STILL_INDEFINITE_WAIT 255
|
||||
/* Value when we have yet to finish reading blocks of a frame. */
|
||||
#define STILL_READING -5
|
||||
|
||||
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_t: VCD information
|
||||
*****************************************************************************/
|
||||
typedef struct vcdplayer_input_s
|
||||
{
|
||||
vcdinfo_obj_t *vcd; /* CD device descriptor */
|
||||
|
||||
/*------------------------------------------------------------------
|
||||
User-settable options
|
||||
--------------------------------------------------------------*/
|
||||
unsigned int i_debug; /* Debugging mask */
|
||||
unsigned int i_blocks_per_read; /* number of blocks per read */
|
||||
|
||||
/*-------------------------------------------------------------
|
||||
Playback control fields
|
||||
--------------------------------------------------------------*/
|
||||
bool in_still; /* true if in still */
|
||||
int i_lid; /* LID that play item is in. Implies
|
||||
PBC is on. VCDPLAYER_BAD_ENTRY if
|
||||
not none or not in PBC */
|
||||
PsdListDescriptor_t pxd; /* If PBC is on, the relevant
|
||||
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 */
|
||||
int i_loop; /* # of times play-item has been
|
||||
played. Meaningful only in a
|
||||
selection list. */
|
||||
track_t i_track; /* current track number */
|
||||
|
||||
/*-----------------------------------
|
||||
location fields
|
||||
------------------------------------*/
|
||||
lsn_t i_lsn; /* LSN of where we are right now */
|
||||
lsn_t end_lsn; /* LSN of end of current
|
||||
entry/segment/track. This block
|
||||
can be read (and is not one after
|
||||
the "end").
|
||||
*/
|
||||
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 */
|
||||
bool b_valid_ep; /* Valid entry points flag */
|
||||
bool b_end_of_track; /* If the end of track was reached */
|
||||
|
||||
/*--------------------------------------------------------------
|
||||
(S)VCD Medium information
|
||||
---------------------------------------------------------------*/
|
||||
|
||||
char *psz_source; /* (S)VCD drive or image filename */
|
||||
bool b_svd; /* true if we have SVD info */
|
||||
vlc_meta_t *p_meta;
|
||||
track_t i_tracks; /* # of playable MPEG tracks. This is
|
||||
generally one less than the number
|
||||
of CD tracks as the first CD track
|
||||
is an ISO-9660 track and is not
|
||||
playable.
|
||||
*/
|
||||
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 i_* 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. */
|
||||
unsigned int i_cur_title;
|
||||
unsigned int i_cur_chapter;
|
||||
|
||||
/*
|
||||
# tracks + menu for segments + menu for LIDs
|
||||
*/
|
||||
input_title_t *p_title[CDIO_CD_MAX_TRACKS+2];
|
||||
|
||||
/* Probably gets moved into another structure...*/
|
||||
int i_audio_nb;
|
||||
int i_still;
|
||||
bool b_end_of_cell;
|
||||
input_thread_t *p_input;
|
||||
access_t *p_access;
|
||||
|
||||
} vcdplayer_t;
|
||||
|
||||
/* vcdplayer_read return status */
|
||||
typedef enum {
|
||||
READ_BLOCK,
|
||||
READ_STILL_FRAME,
|
||||
READ_ERROR,
|
||||
READ_END,
|
||||
} vcdplayer_read_status_t;
|
||||
|
||||
|
||||
/* ----------------------------------------------------------------------
|
||||
Function Prototypes
|
||||
-----------------------------------------------------------------------*/
|
||||
|
||||
/*!
|
||||
Return true if playback control (PBC) is on
|
||||
*/
|
||||
bool vcdplayer_pbc_is_on(const vcdplayer_t *p_vcdplayer);
|
||||
|
||||
/*!
|
||||
Play item assocated with the "default" selection.
|
||||
|
||||
Return false if there was some problem.
|
||||
*/
|
||||
bool vcdplayer_play_default( access_t * p_access );
|
||||
|
||||
/*!
|
||||
Play item assocated with the "next" selection.
|
||||
|
||||
Return false if there was some problem.
|
||||
*/
|
||||
bool vcdplayer_play_next( access_t * p_access );
|
||||
|
||||
/*!
|
||||
Play item assocated with the "prev" selection.
|
||||
|
||||
Return false if there was some problem.
|
||||
*/
|
||||
bool vcdplayer_play_prev( access_t * p_access );
|
||||
|
||||
/*!
|
||||
Play item assocated with the "return" selection.
|
||||
|
||||
Return false if there was some problem.
|
||||
*/
|
||||
bool 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, lsn_t i_lsn, track_t i_track,
|
||||
const vcdinfo_itemid_t *p_itemid);
|
||||
|
||||
void vcdplayer_play(access_t *p_access, vcdinfo_itemid_t itemid);
|
||||
|
||||
vcdplayer_read_status_t vcdplayer_read (access_t * p_access_t, uint8_t *p_buf);
|
||||
|
||||
#endif /* _VCDPLAYER_H_ */
|
||||
/*
|
||||
* Local variables:
|
||||
* c-file-style: "gnu"
|
||||
* tab-width: 8
|
||||
* indent-tabs-mode: nil
|
||||
* End:
|
||||
*/
|
|
@ -46,7 +46,7 @@
|
|||
static const char ppsz_supported_uri_schemes[][9] = {
|
||||
"file", "http", "https", "rtsp", "realrtsp", "pnm", "ftp", "mtp", "smb",
|
||||
"mms", "mmsu", "mmst", "mmsh", "unsv", "itpc", "icyx", "rtmp", "rtp",
|
||||
"dccp", "dvd", "vcd", "vcdx"
|
||||
"dccp", "dvd", "vcd"
|
||||
};
|
||||
|
||||
static const char ppsz_supported_mime_types[][26] = {
|
||||
|
|
|
@ -268,13 +268,6 @@ modules/access/vcd/cdrom.c
|
|||
modules/access/vcd/cdrom.h
|
||||
modules/access/vcd/cdrom_internals.h
|
||||
modules/access/vcd/vcd.c
|
||||
modules/access/vcdx/access.c
|
||||
modules/access/vcdx/info.c
|
||||
modules/access/vcdx/info.h
|
||||
modules/access/vcdx/vcd.c
|
||||
modules/access/vcdx/vcd.h
|
||||
modules/access/vcdx/vcdplayer.c
|
||||
modules/access/vcdx/vcdplayer.h
|
||||
modules/access/vdr.c
|
||||
modules/access/vnc.c
|
||||
modules/access/wasapi.c
|
||||
|
|
Loading…
Reference in New Issue