662 changes: 662 additions & 0 deletions mythplugins/mythmusic/mythmusic/cddb.cpp

Large diffs are not rendered by default.

97 changes: 97 additions & 0 deletions mythplugins/mythmusic/mythmusic/cddb.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
#ifndef CDDB_H_
#define CDDB_H_

#include <QString>
#include <QStringList>
#include <QVector>

/*
* CDDB lookup
*/
struct Cddb
{
typedef unsigned long discid_t;
struct Album;

// A CDDB query match
struct Match
{
QString genre;
discid_t discID;
QString artist;
QString title;

Match() : discID(0) {}
Match(const char *g, discid_t d, const char *a, const char *t) :
genre(g), discID(d), artist(a), title(t)
{}
Match(const QString &g, discid_t d, const QString &a, const QString &t) :
genre(g), discID(d), artist(a), title(t)
{}
Match(const Album& a) : genre(a.genre), discID(a.discID),
artist(a.artist), title(a.title)
{}
};

// CDDB query results
struct Matches
{
discid_t discID; // discID of query
bool isExact;
typedef QVector< Match > match_t;
match_t matches;

Matches() : discID(0), isExact(false) {}
};

struct Msf
{
int min, sec, frame;
Msf(int m = 0, int s = 0, int f = 0) : min(m), sec(s), frame(f) {}
};
typedef QVector< Msf > Toc;

struct Track
{
QString artist;
QString title;
};

// CDDB detail result
struct Album
{
QString genre;
discid_t discID;
QString artist;
QString title;
int year;
QString submitter;
int rev;
bool isCompilation;
typedef QVector< Track > track_t;
track_t tracks;
QString extd;
typedef QVector< QString > ext_t;
ext_t ext;
Toc toc;

Album(discid_t d = 0, const char* g = 0) :
genre(g), discID(d), year(0), rev(1), isCompilation(false) {}

Album(const QString& s) { *this = s; }

Album& operator = (const QString&);
operator QString () const;
};

// Primary cddb access
static bool Query(Matches&, const Toc&);
static bool Read(Album&, const QString& genre, discid_t);
static bool Write(const Album&, bool bLocalOnly = true);

// Support
static discid_t Discid(unsigned& secs, const Msf [], unsigned tracks);
static void Alias(const Album&, discid_t);
};

#endif //ndef CDDB_H_
474 changes: 0 additions & 474 deletions mythplugins/mythmusic/mythmusic/cddecoder-darwin.cpp

This file was deleted.

141 changes: 0 additions & 141 deletions mythplugins/mythmusic/mythmusic/cddecoder-windows.cpp

This file was deleted.

926 changes: 588 additions & 338 deletions mythplugins/mythmusic/mythmusic/cddecoder.cpp

Large diffs are not rendered by default.

83 changes: 43 additions & 40 deletions mythplugins/mythmusic/mythmusic/cddecoder.h
Original file line number Diff line number Diff line change
Expand Up @@ -10,12 +10,9 @@
using std::vector;
#endif

#if defined(__linux__) || defined(__FreeBSD__)
#include <cdaudio.h>
extern "C" {
#include <cdda_interface.h>
#include <cdda_paranoia.h>
}
#ifdef HAVE_CDIO
# include <cdio/cdda.h>
# include <cdio/paranoia.h>
#endif

class Metadata;
Expand All @@ -24,36 +21,41 @@ class CdDecoder : public Decoder
{
public:
CdDecoder(const QString &file, DecoderFactory *, QIODevice *, AudioOutput *);
virtual ~CdDecoder(void);
virtual ~CdDecoder();

bool initialize();
double lengthInSeconds();
void seek(double);
void stop();
// Decoder implementation
virtual bool initialize();
virtual void seek(double);
virtual void stop();

int getNumTracks(void);
int getNumCDAudioTracks(void);
// Decoder overrides
virtual Metadata *getMetadata(void);
virtual void commitMetadata(Metadata *mdata);

// The following need to allocate a new Metadata object each time,
// because their callers (e.g. databasebox.cpp) free the returned value
Metadata *getMetadata(int track);
Metadata *getMetadata(void);
Metadata *getLastMetadata(void);
Metadata *getLastMetadata();

#if CONFIG_DARWIN
double lengthInSeconds();
#endif
int getNumTracks();
int getNumCDAudioTracks();

void commitMetadata(Metadata *mdata);
void setDevice(const QString &dev) { devicename = dev; }
void setDevice(const QString &dev);
void setCDSpeed(int speed);

private:
void run();

void writeBlock(void);
void writeBlock();
void deinit();

volatile bool inited;
volatile bool user_stop;
volatile bool m_inited;
volatile bool m_user_stop;

QString devicename;
QString m_devicename;

#if CONFIG_DARWIN
void lookupCDDB(const QString &hexID, uint tracks);
Expand All @@ -66,26 +68,27 @@ class CdDecoder : public Decoder
vector<int> m_tracks; ///< Start block offset of each track
vector<Metadata*> m_mData; ///< After lookup, details of each trk
#endif

int stat;
char *output_buf;
ulong output_at;

unsigned int bks, bksFrames, decodeBytes;
bool finish;
long freq, bitrate;
int chan;
double totalTime, seekTime;

int settracknum;
int tracknum;

#if defined(__linux__) || defined(__FreeBSD__)
cdrom_drive *device;
cdrom_paranoia *paranoia;
static QMutex& getCdioMutex();

DecoderEvent::Type m_stat;
char *m_output_buf;
std::size_t m_output_at;

std::size_t m_bks, m_bksFrames, m_decodeBytes;
bool m_finish;
long m_freq, m_bitrate;
int m_chan;
double m_totalTime, m_seekTime;

int m_settracknum;
int m_tracknum;

#ifdef HAVE_CDIO
CdIo_t *m_cdio;
cdrom_drive_t *m_device;
cdrom_paranoia_t *m_paranoia;
lsn_t m_start, m_end, m_curpos;
#endif

long int start, end, curpos;
};

#endif
Expand Down
83 changes: 50 additions & 33 deletions mythplugins/mythmusic/mythmusic/cdrip.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,15 +6,11 @@
#include <sys/types.h>
#include <fcntl.h>

// Linux C includes
#include "config.h"
#ifdef HAVE_CDAUDIO
#include <cdaudio.h>
extern "C" {
#include <cdda_interface.h>
#include <cdda_paranoia.h>
}
#endif
#ifdef HAVE_CDIO
# include <cdio/cdda.h>
# include <cdio/paranoia.h>
#endif //def HAVE_CDIO

// C++ includes
#include <iostream>
Expand Down Expand Up @@ -51,7 +47,9 @@ using namespace std;

// MythMusic includes
#include "cdrip.h"
#ifdef HAVE_CDIO
#include "cddecoder.h"
#endif
#include "encoder.h"
#include "vorbisencoder.h"
#include "lameencoder.h"
Expand All @@ -60,6 +58,17 @@ using namespace std;
#include "editmetadata.h"
#include "mythlogging.h"

#ifdef HAVE_CDIO
// libparanoia compatibility
#ifndef cdrom_paranoia
#define cdrom_paranoia cdrom_paranoia_t
#endif

#ifndef CD_FRAMESIZE_RAW
# define CD_FRAMESIZE_RAW CDIO_CD_FRAMESIZE_RAW
#endif
#endif

QEvent::Type RipStatusEvent::kTrackTextEvent =
(QEvent::Type) QEvent::registerEventType();
QEvent::Type RipStatusEvent::kOverallTextEvent =
Expand Down Expand Up @@ -113,15 +122,23 @@ void CDEjectorThread::run()

static long int getSectorCount (QString &cddevice, int tracknum)
{
#ifdef HAVE_CDAUDIO
#if defined HAVE_CDIO
QByteArray devname = cddevice.toAscii();
cdrom_drive *device = cdda_identify(devname.constData(), 0, NULL);

if (!device)
{
LOG(VB_GENERAL, LOG_ERR,
QString("Error: %1('%2',track=%3) failed at cdda_identify()").
arg(__func__).arg(cddevice).arg(tracknum));
return -1;
}

if (cdda_open(device))
{
LOG(VB_GENERAL, LOG_ERR,
QString("Error: %1('%2',track=%3) failed at cdda_open() - cdda not supported").
arg(__func__).arg(cddevice).arg(tracknum));
cdda_close(device);
return -1;
}
Expand All @@ -135,6 +152,8 @@ static long int getSectorCount (QString &cddevice, int tracknum)
cdda_close(device);
return end - start + 1;
}
LOG(VB_GENERAL, LOG_ERR,
QString("Error: cdrip - cdda_track_audiop(%1) returned 0").arg(cddevice));

cdda_close(device);
#else
Expand All @@ -143,9 +162,11 @@ static long int getSectorCount (QString &cddevice, int tracknum)
return 0;
}

static void paranoia_cb(long /*inpos*/, int /*function*/)
#ifdef HAVE_CDIO
static void paranoia_cb(long, paranoia_cb_mode_t)
{
}
#endif

CDRipperThread::CDRipperThread(RipStatus *parent, QString device,
QVector<RipTrack*> *tracks, int quality) :
Expand All @@ -156,6 +177,10 @@ CDRipperThread::CDRipperThread(RipStatus *parent, QString device,
m_totalSectorsDone(0), m_lastTrackPct(0),
m_lastOverallPct(0)
{
#ifdef WIN32 // libcdio needs the drive letter with no path
if (m_CDdevice.endsWith('\\'))
m_CDdevice.chop(1);
#endif
}

CDRipperThread::~CDRipperThread(void)
Expand Down Expand Up @@ -350,7 +375,7 @@ void CDRipperThread::run(void)

int CDRipperThread::ripTrack(QString &cddevice, Encoder *encoder, int tracknum)
{
#ifdef HAVE_CDAUDIO // && HAVE_CDPARANOIA
#if defined HAVE_CDIO
QByteArray devname = cddevice.toAscii();
cdrom_drive *device = cdda_identify(devname.constData(), 0, NULL);

Expand All @@ -365,13 +390,18 @@ int CDRipperThread::ripTrack(QString &cddevice, Encoder *encoder, int tracknum)

if (cdda_open(device))
{
LOG(VB_MEDIA, LOG_INFO,
QString("Error: %1('%2',track=%3) failed at cdda_open() - cdda not supported")
.arg(__func__).arg(cddevice).arg(tracknum));
cdda_close(device);
return -1;
}

cdda_verbose_set(device, CDDA_MESSAGE_FORGETIT, CDDA_MESSAGE_FORGETIT);
long int start = cdda_track_firstsector(device, tracknum);
long int end = cdda_track_lastsector(device, tracknum);
LOG(VB_MEDIA, LOG_INFO, QString("%1(%2,track=%3) start=%4 end=%5")
.arg(__func__).arg(cddevice).arg(tracknum).arg(start).arg(end));

cdrom_paranoia *paranoia = paranoia_init(device);
if (gCoreContext->GetSetting("ParanoiaLevel") == "full")
Expand Down Expand Up @@ -774,17 +804,12 @@ void Ripper::ScanFinished()

void Ripper::scanCD(void)
{
#ifdef HAVE_CDAUDIO
QByteArray devname = m_CDdevice.toAscii();
int cdrom_fd = cd_init_device(const_cast<char*>(devname.constData()));
LOG(VB_MEDIA, LOG_INFO, "Ripper::scanCD() - dev:" + m_CDdevice);
if (cdrom_fd == -1)
#ifdef HAVE_CDIO
{
LOG(VB_GENERAL, LOG_ERR, "Could not open cdrom_fd: " + ENO);
return;
LOG(VB_MEDIA, LOG_INFO, QString("Ripper::%1 CD='%2'").
arg(__func__).arg(m_CDdevice));
(void)cdio_close_tray(m_CDdevice.toAscii().constData(), NULL);
}
cd_close(cdrom_fd); //Close the CD tray
cd_finish(cdrom_fd);
#endif

if (m_decoder)
Expand Down Expand Up @@ -1230,22 +1255,14 @@ void Ripper::EjectFinished()

void Ripper::ejectCD()
{
LOG(VB_MEDIA, LOG_INFO, __PRETTY_FUNCTION__);
bool bEjectCD = gCoreContext->GetNumSetting("EjectCDAfterRipping",1);
if (bEjectCD)
{
#ifdef HAVE_CDAUDIO
QByteArray devname = m_CDdevice.toAscii();
int cdrom_fd = cd_init_device(const_cast<char*>(devname.constData()));
LOG(VB_MEDIA, LOG_INFO, "Ripper::ejectCD() - dev " + m_CDdevice);
if (cdrom_fd != -1)
{
if (cd_eject(cdrom_fd) == -1)
LOG(VB_GENERAL, LOG_ERR, "Failed on cd_eject: " + ENO);

cd_finish(cdrom_fd);
}
else
LOG(VB_GENERAL, LOG_ERR, "Failed on cd_init_device: " + ENO);
#ifdef HAVE_CDIO
LOG(VB_MEDIA, LOG_INFO, QString("Ripper::%1 '%2'").
arg(__func__).arg(m_CDdevice));
(void)cdio_eject_media_drive(m_CDdevice.toAscii().constData());
#else
MediaMonitor *mon = MediaMonitor::GetMediaMonitor();
if (mon)
Expand Down
4 changes: 2 additions & 2 deletions mythplugins/mythmusic/mythmusic/decoder.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -207,9 +207,9 @@ static void checkFactories()
{
factories = new QList<DecoderFactory*>;

#ifndef USING_MINGW
#ifdef HAVE_CDIO
Decoder::registerFactory(new CdDecoderFactory);
#endif // USING_MINGW
#endif
Decoder::registerFactory(new avfDecoderFactory);
}
}
Expand Down
53 changes: 4 additions & 49 deletions mythplugins/mythmusic/mythmusic/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -39,16 +39,12 @@
#include "visualizationsettings.h"
#include "importsettings.h"
#include "ratingsettings.h"
#include "importmusic.h"

#ifndef USING_MINGW
#ifdef HAVE_CDIO
#include "cdrip.h"
#include "importmusic.h"
#endif

// System header (relies on config.h define)
#ifdef HAVE_CDAUDIO
#include <cdaudio.h>
#endif

// This stores the last MythMediaDevice that was detected:
QString gCDdevice;
Expand All @@ -68,43 +64,6 @@ static QString chooseCD(void)
return MediaMonitor::defaultCDdevice();
}

static void CheckFreeDBServerFile(void)
{
QString homeDir = QDir::home().path();

if (homeDir.isEmpty())
{
LOG(VB_GENERAL, LOG_ERR, "main.o: You don't have a HOME environment "
"variable. CD lookup will almost certainly "
"not work.");
return;
}

QString filename = homeDir + "/.cdserverrc";
QFile file(filename);

if (!file.exists())
{
#ifdef HAVE_CDAUDIO
struct cddb_conf cddbconf;
struct cddb_serverlist list;
struct cddb_host proxy_host;

memset(&cddbconf, 0, sizeof(cddbconf));

cddbconf.conf_access = CDDB_ACCESS_REMOTE;
list.list_len = 1;
strncpy(list.list_host[0].host_server.server_name,
"freedb.freedb.org", 256);
strncpy(list.list_host[0].host_addressing, "~cddb/cddb.cgi", 256);
list.list_host[0].host_server.server_port = 80;
list.list_host[0].host_protocol = CDDB_MODE_HTTP;

cddb_write_serverlist(cddbconf, list, proxy_host.host_server);
#endif
}
}

static void SavePending(int pending)
{
// Temporary Hack until mythmusic
Expand Down Expand Up @@ -176,8 +135,6 @@ static void loadMusic()
if (gMusicData->initialized)
return;

CheckFreeDBServerFile();

MSqlQuery count_query(MSqlQuery::InitCon());

bool musicdata_exists = false;
Expand Down Expand Up @@ -279,7 +236,7 @@ static void startRipper(void)
{
loadMusic();

#ifndef USING_MINGW
#if defined HAVE_CDIO
MythScreenStack *mainStack = GetMythMainWindow()->GetMainStack();

Ripper *rip = new Ripper(mainStack, chooseCD());
Expand All @@ -300,7 +257,6 @@ static void startImport(void)
{
loadMusic();

#ifndef USING_MINGW
MythScreenStack *mainStack = GetMythMainWindow()->GetMainStack();

ImportMusicDialog *import = new ImportMusicDialog(mainStack);
Expand All @@ -314,7 +270,6 @@ static void startImport(void)
}
else
delete import;
#endif
}

static void MusicCallback(void *data, QString &selection)
Expand Down Expand Up @@ -448,7 +403,7 @@ static void runRipCD(void)
{
loadMusic();

#ifndef USING_MINGW
#if defined HAVE_CDIO
MythScreenStack *mainStack = GetMythMainWindow()->GetMainStack();

Ripper *rip = new Ripper(mainStack, chooseCD());
Expand Down
4 changes: 0 additions & 4 deletions mythplugins/mythmusic/mythmusic/musiccommon.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -35,10 +35,6 @@ using namespace std;
#include "editmetadata.h"
#include "playlist.h"

#ifndef USING_MINGW
#include "cddecoder.h"
#endif // USING_MINGW

#include "musiccommon.h"
#include "playlistview.h"
#include "playlisteditorview.h"
Expand Down
8 changes: 6 additions & 2 deletions mythplugins/mythmusic/mythmusic/musicplayer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,9 @@
#include "musicplayer.h"
#include "decoder.h"
#include "decoderhandler.h"
#ifdef HAVE_CDIO
#include "cddecoder.h"
#endif
#include "constants.h"
#include "mainvisual.h"
#include "miniplayer.h"
Expand Down Expand Up @@ -1253,9 +1255,11 @@ void MusicPlayer::decoderHandlerReady(void)
LOG(VB_PLAYBACK, LOG_INFO, QString ("decoder handler is ready, decoding %1")
.arg(getDecoder()->getFilename()));

#ifdef HAVE_CDIO
CdDecoder *cddecoder = dynamic_cast<CdDecoder*>(getDecoder());
if (cddecoder)
cddecoder->setDevice(m_CDdevice);
#endif

getDecoder()->setOutput(m_output);
//getDecoder()-> setBlockSize(2 * 1024);
Expand Down Expand Up @@ -1339,7 +1343,7 @@ CDWatcherThread::CDWatcherThread(const QString &dev)

void CDWatcherThread::run()
{
#ifndef USING_MINGW
#ifdef HAVE_CDIO
while (!m_stopped)
{
// lock all_music and cd_status_changed while running thread
Expand Down Expand Up @@ -1433,5 +1437,5 @@ void CDWatcherThread::run()

usleep(1000000);
}
#endif // USING_MINGW
#endif // HAVE_CDIO
}
29 changes: 11 additions & 18 deletions mythplugins/mythmusic/mythmusic/mythmusic.pro
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ QT += xml sql opengl network webkit
error(Missing config.pro: please run the configure script)
}

INCLUDEPATH *= $${SYSROOT}/usr/include/cdda
TEMPLATE = lib
CONFIG += plugin thread
TARGET = mythmusic
Expand All @@ -21,24 +20,21 @@ LIBS += -lmythavcodec
LIBS += -lmythavutil
LIBS += -ltag -logg -lvorbisfile -lvorbis -lvorbisenc -lFLAC -lmp3lame

cdaudio: LIBS += -lcdaudio
paranoia:LIBS += -lcdda_paranoia -lcdda_interface

# Input
HEADERS += cddecoder.h cdrip.h constants.h
HEADERS += constants.h
HEADERS += decoder.h flacencoder.h mainvisual.h
HEADERS += metadata.h playlist.h polygon.h
HEADERS += streaminput.h synaesthesia.h encoder.h visualize.h avfdecoder.h
HEADERS += vorbisencoder.h polygon.h
HEADERS += bumpscope.h lameencoder.h dbcheck.h
HEADERS += importmusic.h
HEADERS += metaio.h metaiotaglib.h
HEADERS += metaioflacvorbis.h metaioavfcomment.h metaiomp4.h
HEADERS += metaiowavpack.h metaioid3.h metaiooggvorbis.h
HEADERS += goom/filters.h goom/goomconfig.h goom/goom_core.h goom/graphic.h
HEADERS += goom/ifs.h goom/lines.h goom/mythgoom.h goom/drawmethods.h
HEADERS += goom/mmx.h goom/mathtools.h goom/tentacle3d.h goom/v3d.h
HEADERS += editmetadata.h smartplaylist.h genres.h
HEADERS += importmusic.h
HEADERS += filescanner.h musicplayer.h miniplayer.h
HEADERS += playlistcontainer.h
HEADERS += musiccommon.h decoderhandler.h pls.h shoutcast.h
Expand All @@ -47,21 +43,20 @@ HEADERS += visualizerview.h searchview.h musicutils.h
HEADERS += generalsettings.h visualizationsettings.h
HEADERS += importsettings.h playersettings.h ratingsettings.h

SOURCES += cddecoder.cpp cdrip.cpp decoder.cpp
SOURCES += decoder.cpp
SOURCES += flacencoder.cpp main.cpp
SOURCES += mainvisual.cpp metadata.cpp playlist.cpp
SOURCES += streaminput.cpp encoder.cpp dbcheck.cpp
SOURCES += synaesthesia.cpp lameencoder.cpp
SOURCES += vorbisencoder.cpp visualize.cpp bumpscope.cpp
SOURCES += genres.cpp
SOURCES += genres.cpp importmusic.cpp
SOURCES += metaio.cpp metaiotaglib.cpp
SOURCES += metaioflacvorbis.cpp metaioavfcomment.cpp metaiomp4.cpp
SOURCES += metaiowavpack.cpp metaioid3.cpp metaiooggvorbis.cpp
SOURCES += goom/filters.c goom/goom_core.c goom/graphic.c goom/tentacle3d.c
SOURCES += goom/ifs.c goom/ifs_display.c goom/lines.c goom/surf3d.c
SOURCES += goom/zoom_filter_mmx.c goom/zoom_filter_xmmx.c goom/mythgoom.cpp
SOURCES += avfdecoder.cpp editmetadata.cpp smartplaylist.cpp
SOURCES += importmusic.cpp
SOURCES += filescanner.cpp musicplayer.cpp miniplayer.cpp
SOURCES += playlistcontainer.cpp
SOURCES += musiccommon.cpp decoderhandler.cpp pls.cpp shoutcast.cpp
Expand All @@ -70,21 +65,19 @@ SOURCES += visualizerview.cpp searchview.cpp musicutils.cpp
SOURCES += generalsettings.cpp visualizationsettings.cpp
SOURCES += importsettings.cpp playersettings.cpp ratingsettings.cpp

macx {
SOURCES -= cddecoder.cpp
SOURCES += cddecoder-darwin.cpp

cdio {
INCLUDEPATH -= $${SYSROOT}/usr/include/cdda
INCLUDEPATH *= $${SYSROOT}/usr/include/cdio
HEADERS += cddecoder.h cdrip.h cddb.h
SOURCES += cddecoder.cpp cdrip.cpp cddb.cpp
QT += network
LIBS += -lcdio -lcdio_cdda -lcdio_paranoia
}

mingw {
HEADERS -= cdrip.h importmusic.h
SOURCES -= cdrip.cpp importmusic.cpp cddecoder.cpp
SOURCES += cddecoder-windows.cpp

LIBS += -logg

# libcdaudio needs ...
# flac needs ...
LIBS += -lwsock32
}

Expand Down