Add the 'next' and 'prev' commands (aliased to '+' and '-') which skip
forward or backward by a specified number of tracks (defaulting to 1). Use strvisx() to display the media catalog in case it contains unprintable characters. Sort includes. Based on two patches submitted by PR, plus style fixes and other changes of my own. Submitted by: Seth Kingsley <sethk@osd.bsdi.com>, Maxime Henrion <mux@qualys.com> PR: bin/22672, bin/26962 MFC After: 1 week
This commit is contained in:
parent
48c35f87be
commit
4dbed42f75
@ -44,9 +44,17 @@ Suffix `c' is added to the device name if needed.
|
||||
The available commands are listed below. Only as many
|
||||
characters as are required to uniquely identify a command
|
||||
need be specified.
|
||||
Word
|
||||
.Em play
|
||||
can be omitted.
|
||||
The word
|
||||
.Cm play
|
||||
can be omitted or the characters
|
||||
.Dq +
|
||||
and
|
||||
.Dq -
|
||||
can be used in the
|
||||
place of
|
||||
.Cm next
|
||||
and
|
||||
.Cm prev .
|
||||
.Bl -tag -width Cm
|
||||
.It Cm play Ar first_track Op Ar last_track
|
||||
Play from track
|
||||
@ -82,6 +90,10 @@ Play starting from the logical block
|
||||
using
|
||||
.Ar length
|
||||
logical blocks.
|
||||
.It Cm next Op Ar tracks
|
||||
Skip forward a number of tracks (default 1).
|
||||
.It Cm prev Op Ar tracks
|
||||
Skip backward a number of tracks (default 1).
|
||||
.It Cm pause
|
||||
Stop playing.
|
||||
Do not stop the disc.
|
||||
|
@ -23,19 +23,20 @@ static const char rcsid[] =
|
||||
"$FreeBSD$";
|
||||
#endif /* not lint */
|
||||
|
||||
#include <sys/cdio.h>
|
||||
#include <sys/file.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/param.h>
|
||||
#include <ctype.h>
|
||||
#include <err.h>
|
||||
#include <errno.h>
|
||||
#include <histedit.h>
|
||||
#include <paths.h>
|
||||
#include <stdio.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <unistd.h>
|
||||
#include <sys/file.h>
|
||||
#include <sys/cdio.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/param.h>
|
||||
#include <histedit.h>
|
||||
#include <vis.h>
|
||||
|
||||
#define VERSION "2.0"
|
||||
|
||||
@ -69,6 +70,8 @@ static const char rcsid[] =
|
||||
#define CMD_SET 13
|
||||
#define CMD_STATUS 14
|
||||
#define CMD_CDID 15
|
||||
#define CMD_NEXT 16
|
||||
#define CMD_PREVIOUS 17
|
||||
#define STATUS_AUDIO 0x1
|
||||
#define STATUS_MEDIA 0x2
|
||||
#define STATUS_VOLUME 0x4
|
||||
@ -85,11 +88,13 @@ struct cmdtab {
|
||||
{ CMD_HELP, "?", 1, 0 },
|
||||
{ CMD_HELP, "help", 1, "" },
|
||||
{ CMD_INFO, "info", 1, "" },
|
||||
{ CMD_NEXT, "next", 1, "" },
|
||||
{ CMD_PAUSE, "pause", 2, "" },
|
||||
{ CMD_PLAY, "play", 1, "min1:sec1[.fram1] [min2:sec2[.fram2]]" },
|
||||
{ CMD_PLAY, "play", 1, "track1[.index1] [track2[.index2]]" },
|
||||
{ CMD_PLAY, "play", 1, "tr1 m1:s1[.f1] [[tr2] [m2:s2[.f2]]]" },
|
||||
{ CMD_PLAY, "play", 1, "[#block [len]]" },
|
||||
{ CMD_PREVIOUS, "previous", 2, "" },
|
||||
{ CMD_QUIT, "quit", 1, "" },
|
||||
{ CMD_RESET, "reset", 4, "" },
|
||||
{ CMD_RESUME, "resume", 1, "" },
|
||||
@ -115,6 +120,7 @@ int play_track __P((int, int, int, int));
|
||||
int get_vol __P((int *, int *));
|
||||
int status __P((int *, int *, int *, int *));
|
||||
int open_cd __P((void));
|
||||
int next_prev __P((char *arg, int));
|
||||
int play __P((char *arg));
|
||||
int info __P((char *arg));
|
||||
int cdid __P((void));
|
||||
@ -287,6 +293,16 @@ int run (int cmd, char *arg)
|
||||
|
||||
return pstatus (arg);
|
||||
|
||||
case CMD_NEXT:
|
||||
case CMD_PREVIOUS:
|
||||
if (fd < 0 && ! open_cd ())
|
||||
return (0);
|
||||
|
||||
while (isspace (*arg))
|
||||
arg++;
|
||||
|
||||
return next_prev (arg, cmd);
|
||||
|
||||
case CMD_PAUSE:
|
||||
if (fd < 0 && ! open_cd ())
|
||||
return (0);
|
||||
@ -690,6 +706,36 @@ int play (char *arg)
|
||||
return (0);
|
||||
}
|
||||
|
||||
int next_prev (char *arg, int cmd)
|
||||
{
|
||||
struct ioc_toc_header h;
|
||||
int dir, junk, n, off, rc, trk;
|
||||
|
||||
dir = (cmd == CMD_NEXT) ? 1 : -1;
|
||||
rc = ioctl (fd, CDIOREADTOCHEADER, &h);
|
||||
if (rc < 0)
|
||||
return (rc);
|
||||
|
||||
n = h.ending_track - h.starting_track + 1;
|
||||
rc = status (&trk, &junk, &junk, &junk);
|
||||
if (rc < 0)
|
||||
return (-1);
|
||||
|
||||
if (arg && *arg) {
|
||||
if (sscanf (arg, "%u", &off) != 1) {
|
||||
warnx("invalid command argument");
|
||||
return (0);
|
||||
} else
|
||||
trk += off * dir;
|
||||
} else
|
||||
trk += dir;
|
||||
|
||||
if (trk > h.ending_track)
|
||||
trk = 1;
|
||||
|
||||
return (play_track (trk, 1, n, 1));
|
||||
}
|
||||
|
||||
char *strstatus (int sts)
|
||||
{
|
||||
switch (sts) {
|
||||
@ -710,7 +756,7 @@ int pstatus (char *arg)
|
||||
struct cd_sub_channel_info data;
|
||||
int rc, trk, m, s, f;
|
||||
int what = 0;
|
||||
char *p;
|
||||
char *p, vmcn[(4 * 15) + 1];
|
||||
|
||||
while ((p = strtok(arg, " \t"))) {
|
||||
arg = 0;
|
||||
@ -750,8 +796,11 @@ int pstatus (char *arg)
|
||||
ss.data->what.media_catalog.mc_valid ? "": "in");
|
||||
if (ss.data->what.media_catalog.mc_valid &&
|
||||
ss.data->what.media_catalog.mc_number[0])
|
||||
printf(", number \"%.15s\"",
|
||||
ss.data->what.media_catalog.mc_number);
|
||||
{
|
||||
strvisx (vmcn, ss.data->what.media_catalog.mc_number,
|
||||
(sizeof (vmcn) - 1) / 4, VIS_OCTAL | VIS_NL);
|
||||
printf(", number \"%.*s\"", (int)sizeof (vmcn), vmcn);
|
||||
}
|
||||
putchar('\n');
|
||||
} else
|
||||
printf("No media catalog info available\n");
|
||||
@ -1103,6 +1152,12 @@ char *parse (char *buf, int *cmd)
|
||||
if (isdigit (*p) || (p[0] == '#' && isdigit (p[1]))) {
|
||||
*cmd = CMD_PLAY;
|
||||
return (p);
|
||||
} else if (*p == '+') {
|
||||
*cmd = CMD_NEXT;
|
||||
return (p + 1);
|
||||
} else if (*p == '-') {
|
||||
*cmd = CMD_PREVIOUS;
|
||||
return (p + 1);
|
||||
}
|
||||
|
||||
for (buf = p; *p && ! isspace (*p); p++)
|
||||
|
Loading…
Reference in New Issue
Block a user