/*
   XMMS-SID - SIDPlay input plugin for X MultiMedia System (XMMS)

   libSIDPlay skeleton functions used both by v1 and 2 of the backends

   Programmed and designed by Matti 'ccr' Hamalainen <ccr@tnsp.org>
   (C) Copyright 2005-2007 Tecnic Software productions (TNSP)

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 2 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 General Public License for more details.

   You should have received a copy of the GNU 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 function gets most of the information, though we do miss some
 * (those variables that are only set by libSIDPlay when tune is initialized).
 * Rest of the information is acquired in TFUNCTION2()
 */
t_xs_tuneinfo *TFUNCTION(const gchar *sidFilename)
{
	t_xs_tuneinfo *pResult;
	TTUNEINFO myInfo;
	TTUNE *myTune;
	guint8 *buf = NULL;
	size_t bufSize = 0;

	/* Load file */
	if (!sidFilename) return NULL;

	if (xs_fload_buffer(sidFilename, &buf, &bufSize) != 0)
		return NULL;
	
	/* Check if the tune exists and is readable */
	if ((myTune = new TTUNE(buf, bufSize)) == NULL) {
		g_free(buf);
		return NULL;
	}
	g_free(buf);

	if (!myTune->getStatus()) {
		delete myTune;
		return NULL;
	}

	/* Get general tune information */
#ifdef XS_SIDPLAY1_H
	myTune->getInfo(myInfo);
#endif
#ifdef XS_SIDPLAY2_H
	myInfo = myTune->getInfo();
#endif

	/* Allocate tuneinfo structure and set information */
	pResult = xs_tuneinfo_new(sidFilename,
		myInfo.songs, myInfo.startSong,
		myInfo.infoString[0], myInfo.infoString[1], myInfo.infoString[2],
		myInfo.loadAddr, myInfo.initAddr, myInfo.playAddr,
		myInfo.dataFileLen, myInfo.formatString, myInfo.sidModel);
	
	/* NOTICE! libSIDPlay[12] headers specifically state that sidModel,
	 * songSpeed and clockSpeed are "undefined" before song initialization,
	 * but in practice sidModel is known after getInfo() invocation...
	 * This of course does not take the sub-tune specific changes into account,
	 * but at least we have a reasonable guesstimate.
	 */

	delete myTune;

	return pResult;
}


/* Updates the information of currently playing tune
 */
gboolean TFUNCTION2(t_xs_status *myStatus)
{
	TTUNEINFO myInfo;
	TTUNE *myTune;
	TENGINE *myEngine;
	t_xs_tuneinfo *i;
	
	/* Check if we have required structures initialized */
	if (!myStatus || !myStatus->tuneInfo || !myStatus->sidEngine)
		return FALSE;

	myEngine = (TENGINE *) myStatus->sidEngine;
	myTune = myEngine->currTune;
	if (!myTune)
		return FALSE;

	/* Get currently playing tune information */
#ifdef XS_SIDPLAY1_H
	myTune->getInfo(myInfo);
#endif
#ifdef XS_SIDPLAY2_H
	myInfo = myTune->getInfo();
#endif

	/* NOTICE! Here we assume that libSIDPlay[12] headers define
	 * SIDTUNE_SIDMODEL_* similarly to our enums in xs_config.h ...
	 */
	i = myStatus->tuneInfo;
	i->sidModel = myInfo.sidModel;

	if ((myStatus->currSong > 0) && (myStatus->currSong <= i->nsubTunes)) {
		gint tmpSpeed = -1;
		
		switch (myInfo.clockSpeed) {
		case SIDTUNE_CLOCK_PAL:
			tmpSpeed = XS_CLOCK_PAL;
			break;
		case SIDTUNE_CLOCK_NTSC:
			tmpSpeed = XS_CLOCK_NTSC;
			break;
		case SIDTUNE_CLOCK_ANY:
			tmpSpeed = XS_CLOCK_ANY;
			break;
		case SIDTUNE_CLOCK_UNKNOWN:
			switch (myInfo.songSpeed) {
			case SIDTUNE_SPEED_VBI:
				tmpSpeed = XS_CLOCK_VBI;
				break;
			case SIDTUNE_SPEED_CIA_1A:
				tmpSpeed = XS_CLOCK_CIA;
				break;
			default:
				tmpSpeed = myInfo.songSpeed;
				break;
			}
		default:
			tmpSpeed = myInfo.clockSpeed;
			break;
		}
			
		i->subTunes[myStatus->currSong - 1].tuneSpeed = tmpSpeed;
	}

	return TRUE;
}

/* Undefine these */
#undef TFUNCTION
#undef TFUNCTION2
#undef TTUNEINFO
#undef TTUNE
