Article View: es.comp.os.linux.programacion
Article #13627Re: reproductor de CD "pofessional"
From: Manuel López Moreno
Date: Mon, 12 Feb 2001 11:20
Date: Mon, 12 Feb 2001 11:20
316 lines
8580 bytes
8580 bytes
Tal d�a Fri, 9 Feb 2001 18:17:18 -0000,
Francisco Cuenya Folgar <francisco.cuenya@wanadoo.es> nos relat�:
> Lo de capturar la salida del CD deber�a conocer las llamadas a sistema o
> librer�as que controlen el CD para implementarlo no? Alguien sabe cu�les son
> estas librer�as o llamadas y d�nde puedo encontrar info sobre ellas? Gracias
Est� todo en <linux/cdrom.h>
Ah� va un programilla que escrib� para probar las ioctl's. No te
f�es demasiado del control de errores. Hay cosas que no acaban de
funcionar.
Para compilar: $ gcc -Wall -Wstrict-prototypes cdr.c -o cdr
- cdr.c --8<----------------------------------------
/*
* Utilidad: Diversas funciones del CD-ROM.
* Fecha: Martes, 16 de Julio de 1996
* Revisi�n: Jueves, 9 de Julio de 1998
* Autor: Manuel L�pez Moreno <luname@mx2.redestb.es>
*
* Sintaxis: cdr [e|s|p|r] [argumentos]
*
* Argumentos: Eject: e
* Stop: s
* Play: p <lba0> <lba1>
* Read: r <lba> <nfr>
*/
#include <fcntl.h> // open()
#include <unistd.h> // write()
#include <sys/ioctl.h> // ioctl()
#include <stdio.h> // printf()
#include <stdlib.h> // atoi()
#include <sys/types.h> // u_char, linux/cdrom.h
#include <linux/cdrom.h> // CDROM...
//----- Constantes
#define DEVICE "/dev/cdrom"
#define MAXTOCENT 96
enum
{
EJECT = 1, STOP, TOCHDR, TOCENT, PLAY, PAUSE, RESUME,
MEM, READ, SUBCHNL, FADE, CLOSE
};
static char* Msj[] =
{
"Fallo al abrir",
"Fallo al expulsar bandeja",
"Fallo al parar el motor",
"Fallo al leer TOC Header",
"Fallo al leer TOC Entry",
"Fallo al reproducir",
"Fallo al parar (pause)",
"Fallo al continuar (resume)",
"Error de obtenci�n de memoria",
"Fallo al leer audio",
"Fallo al leer status",
"Fallo al modificar volumen",
"Fallo al cerrar bandeja"
};
//----- Prototipos
static int GetTOC (int drive);
static void DisplayTOC (void);
static int Play (int drive, int lba0, int lba1);
static int Read (int drive, int lba, int nfr);
static int SubChannel (int drive);
static int Fade (int drive, int sw);
static void lba2msf (int lba, unsigned char msf[]);
//----- Variables Globales
static struct cdrom_tocentry TocEntry[MAXTOCENT];
static u_char NTracks;
//------------------------------------------------------------
int main (int argc, char* argv[])
{
int drive;
int io = -1;
int com;
int lba0, lba1;
int trk = (argc > 2 ? atoi(argv[2]) : 1);
int ind = (argc > 3 ? atoi(argv[3]) : 0);
int nfr = (argc > 3 ? atoi(argv[3]) : CD_FRAMES);
int sw = (argc > 2 ? atoi(argv[2]) : 0);
if ((drive = open(DEVICE, 0)) < 0)
{
perror(Msj[0]);
return 1;
}
if ((com = GetTOC(drive)) != 0)
puts(Msj[com]);
lba0 = (argc > 2 ? atoi(argv[2]) : TocEntry[0].cdte_addr.lba);
lba1 = (argc > 3 ? atoi(argv[3]) : TocEntry[NTracks].cdte_addr.lba);
if (argc == 1)
DisplayTOC();
else if (argc > 1)
{
switch (*argv[1])
{
case 'e': io = ioctl(drive, CDROMEJECT); com = EJECT;
break;
case 't': io = ioctl(drive, CDROMCLOSETRAY); com = CLOSE;
break;
case 's': io = ioctl(drive, CDROMSTOP); com = STOP;
break;
case 'p': io = com = Play(drive, lba0, lba1);
break;
case 'P': io = ioctl(drive, CDROMPAUSE); com = PAUSE;
break;
case 'S': io = ioctl(drive, CDROMRESUME); com = RESUME;
break;
case 'r': io = com = Read(drive, lba0, nfr);
break;
case 'c': io = com = SubChannel(drive);
break;
case 'f': io = com = Fade(drive, sw);
}
if (io != 0)
{
perror(Msj[com]);
return 1;
}
}
return 0;
}
//------------------------------------------------------------
int GetTOC (int drive)
{
struct cdrom_tochdr TocHdr;
struct cdrom_tocentry* pTE;
int i;
if (ioctl(drive, CDROMREADTOCHDR, &TocHdr) < 0)
return TOCHDR;
NTracks = TocHdr.cdth_trk1;
for (i = 1, pTE = TocEntry; i <= NTracks; i++, pTE++)
{
pTE->cdte_track = i;
pTE->cdte_format = CDROM_LBA;
if (ioctl(drive, CDROMREADTOCENTRY, pTE) < 0)
return TOCENT;
}
pTE->cdte_track = CDROM_LEADOUT;
pTE->cdte_format = CDROM_MSF;
if (ioctl(drive, CDROMREADTOCENTRY, pTE) < 0)
return TOCENT;
return 0;
}
//------------------------------------------------------------
void DisplayTOC (void)
{
struct cdrom_tocentry* pTE;
int i;
u_char msf[3];
printf("\nDuraci�n Total: %02d:%02d:%02d (%d pista%c)\n\n",
TocEntry[NTracks].cdte_addr.msf.minute,
TocEntry[NTracks].cdte_addr.msf.second,
TocEntry[NTracks].cdte_addr.msf.frame,
NTracks, (NTracks == 1 ? 0 : 's'));
printf("Pista adr ctrl mode mm:ss:ff LBA\n"
"----- --- ---- ---- -------- --------\n" );
for (i = 0, pTE = TocEntry; i < NTracks; i++, pTE++)
{
lba2msf(pTE->cdte_addr.lba, msf);
printf("%5d %3d %4d %4d %02d:%02d:%02d %8d\n",
pTE->cdte_track,
pTE->cdte_adr,
pTE->cdte_ctrl,
pTE->cdte_datamode,
msf[0], msf[1], msf[2],
pTE->cdte_addr.lba);
}
}
//------------------------------------------------------------
int Play (int drive, int lba0, int lba1)
{
struct cdrom_msf msf;
lba2msf(lba0, (u_char*) &msf.cdmsf_min0);
lba2msf(lba1, (u_char*) &msf.cdmsf_min1);
if (ioctl(drive, CDROMPLAYMSF, &msf) < 0)
return PLAY;
return 0;
}
//------------------------------------------------------------
int Read (int drive, int lba, int nfr)
{
struct cdrom_read_audio RA;
int nbytes = nfr * CD_FRAMESIZE_RAW;
RA.addr_format = CDROM_LBA;
RA.addr.lba = lba;
RA.nframes = nfr;
if ((RA.buf = (u_char*) malloc(nbytes)) == NULL)
return MEM;
if (ioctl(drive, CDROMREADAUDIO, &RA) < 0)
return READ;
write(1, &RA.buf, nbytes);
return 0;
}
//------------------------------------------------------------
int SubChannel (int drive)
{
struct cdrom_subchnl subc;
subc.cdsc_format = CDROM_MSF;
if (ioctl(drive, CDROMSUBCHNL, &subc) < 0)
return SUBCHNL;
printf("Status %02X, Pista %03d, "
"Indice %03d MSF %02d:%02d:%02d (%1X %1X)\n",
subc.cdsc_audiostatus,
subc.cdsc_trk,
subc.cdsc_ind,
subc.cdsc_reladdr.msf.minute,
subc.cdsc_reladdr.msf.second,
subc.cdsc_reladdr.msf.frame,
subc.cdsc_adr,
subc.cdsc_ctrl);
return 0;
}
//------------------------------------------------------------
int Fade (int drive, int sw)
{
// Habr� que inicializar v, digo yo :-/
int v;
struct cdrom_volctrl vol = { 0 };
if (sw > 0)
{
vol.channel0 = vol.channel1 = 0;
sw = +1;
}
else if (sw < 0)
{
vol.channel0 = vol.channel1 = 255;
sw = -1;
}
printf("Volumen inicial: %d\n", v);
while (v += sw)
{
vol.channel0 = vol.channel1 = v;
if (ioctl(drive, CDROMVOLCTRL, &vol) < 0)
return FADE;
}
printf("Volumen final: %d\n", v);
return 0;
}
//------------------------------------------------------------
void lba2msf (int lba, unsigned char msf[])
{
lba += CD_MSF_OFFSET;
msf[0] = lba / (CD_SECS * CD_FRAMES);
lba %= CD_SECS * CD_FRAMES;
msf[1] = lba / CD_FRAMES;
msf[2] = lba % CD_FRAMES;
}
----------8<----------------------------------------
--
Manuel L�pez Moreno PGP key ID: 0xC6C9455E
Visita: Web de es.comp.os.linux.* <http://www.escomposlinux.org>
Technical Details
Message-ID:
<slrn98fhdl.lr.luname@mantium.luname.net>Path:
arc1-ca.pugleaf.net!supernews.google.com!sn-xit-03!supernews.com!nntp.cs.ubc.ca!skynet.be!fr.clara.net!heighliner.fr.clara.net!opentransit.net!newsfeed.comtenidos.com!m2newsfeed.uni2.es!m2newsread.uni2.es.POSTED!not-for-mailReferences:
<95k2uu$kh6$1@m2newsreader01.wanadoo.es> <95nddf$n8c$1@m2wpersoisp01.wanadoo.es> <G7gg6.4027$T9.51249236@news.jazztel.es> <slrn983lh6.1og.gorka@conan.hondarribia.penguinpowered.com> <961834$jfv$1@m2wpersoisp01.wanadoo.es>Show Full Headers
Complete Article Headers
X-Google-Language: SPANISH,ASCII X-Google-Thread: f86c8,b79667b5118ecabf X-Google-Attributes: gidf86c8,public X-Google-ArrivalTime: 2001-02-12 03:22:06 PST Path: arc1-ca.pugleaf.net!supernews.google.com!sn-xit-03!supernews.com!nntp.cs.ubc.ca!skynet.be!fr.clara.net!heighliner.fr.clara.net!opentransit.net!newsfeed.comtenidos.com!m2newsfeed.uni2.es!m2newsread.uni2.es.POSTED!not-for-mail From: luname@linuxfan.com (Manuel López Moreno) Newsgroups: es.comp.os.linux.programacion Subject: Re: reproductor de CD "pofessional" References: <95k2uu$kh6$1@m2newsreader01.wanadoo.es> <95nddf$n8c$1@m2wpersoisp01.wanadoo.es> <G7gg6.4027$T9.51249236@news.jazztel.es> <slrn983lh6.1og.gorka@conan.hondarribia.penguinpowered.com> <961834$jfv$1@m2wpersoisp01.wanadoo.es> Message-ID: <slrn98fhdl.lr.luname@mantium.luname.net> Mime-Version: 1.0 Content-Type: text/plain; charset=iso-8859-1 Content-Transfer-Encoding: 8bit User-Agent: slrn/0.9.6.2 (Linux) Lines: 316 Date: Mon, 12 Feb 2001 11:20:29 GMT NNTP-Posting-Host: 62.36.169.113 X-Complaints-To: abuse@wanadoo.es X-Trace: m2newsread.uni2.es 981976829 62.36.169.113 (Mon, 12 Feb 2001 12:20:29 MET) NNTP-Posting-Date: Mon, 12 Feb 2001 12:20:29 MET Organization: Servidor Usenet News de Uni2/Wanadoo