/***************************************************************************
*	NAME:  VOCSTART.C
**	COPYRIGHT:
**	"Copyright (c) 1992, by FORTE
**
**       "This software is furnished under a license and may be used,
**       copied, or disclosed only in accordance with the terms of such
**       license and with the inclusion of the above copyright notice.
**       This software or any other copies thereof may not be provided or
**       otherwise made available to any other person. No title to and
**       ownership of the software is hereby transfered."
****************************************************************************
*  CREATION DATE: 11/18/92
*--------------------------------------------------------------------------*
*     VERSION	DATE	   NAME		DESCRIPTION
*>	1.0	11/18/92		Original
***************************************************************************/

#include <dos.h>
#include <conio.h>

#include "forte.h"
#include "gf1proto.h"
#include "osproto.h"
#include "gf1hware.h"
#include "gf1os.h"
#include "extern.h"

extern ULTRA_DATA _gf1_data;

unsigned char
UltraPrimeVoice(int voice,unsigned long begin,unsigned long start,unsigned long end,unsigned char mode)
// int voice;					/* voice to start */
// unsigned long begin;		/* start location in ultra DRAM */
// unsigned long start;		/* start loop location in ultra DRAM */
// unsigned long end;			/* end location in ultra DRAM */
// unsigned char mode;			/* mode to run the voice (loop etc) */
{
unsigned long phys_start,phys_end;
unsigned long phys_begin;
unsigned long temp;
unsigned char vmode;

	/* if start is greater than end, flip 'em and turn on */
	/* decrementing addresses */
	if (start > end)
		{
		temp = start;
		start = end;
		end = temp;
		mode |= VC_DIRECT;
		}

	/* if 16 bit data, must convert addresses */
	if (mode & VC_DATA_TYPE)
		{
		phys_begin = convert_to_16bit(begin);
		phys_start = convert_to_16bit(start);
		phys_end   = convert_to_16bit(end);
		}
	else
		{
		phys_begin = begin;
		phys_start = start;
		phys_end = end;
		}

	ENTER_CRITICAL;

	/* Make sure we are talking to proper voice */
	outp(_gf1_data.voice_select,voice);

	/* set/reset the rollover bit as per user request */
	outp(_gf1_data.reg_select,GET_VOLUME_CONTROL);
	vmode = inp (_gf1_data.data_hi);

	if (mode & USE_ROLLOVER)
		{
		vmode |= VC_ROLLOVER;
		}
	else
		{
		vmode &= ~VC_ROLLOVER;
		}
	outp(_gf1_data.reg_select,SET_VOLUME_CONTROL);
	outp(_gf1_data.data_hi,vmode);
	gf1_delay();

	outp(_gf1_data.data_hi,vmode);

	/* First set accumulator to beginning of data */
	outp(_gf1_data.reg_select,SET_ACC_LOW);
	outpw(_gf1_data.data_low,ADDR_LOW(phys_begin));
	outp(_gf1_data.reg_select,SET_ACC_HIGH);
	outpw(_gf1_data.data_low,ADDR_HIGH(phys_begin));

	/* Set start loop address of buffer */
	outp(_gf1_data.reg_select,SET_START_HIGH);
	outpw(_gf1_data.data_low,ADDR_HIGH(phys_start));
	outp(_gf1_data.reg_select,SET_START_LOW);
	outpw(_gf1_data.data_low,ADDR_LOW(phys_start));

	/* Set end address of buffer */
	outp(_gf1_data.reg_select,SET_END_HIGH);
	outpw(_gf1_data.data_low,ADDR_HIGH(phys_end));
	outp(_gf1_data.reg_select,SET_END_LOW);
	outpw(_gf1_data.data_low,ADDR_LOW(phys_end));

	LEAVE_CRITICAL;

return(mode);
}

void
UltraGoVoice(int voice,unsigned char mode)
{
	ENTER_CRITICAL;

	/* Make sure we are talking to proper voice */
	outp(_gf1_data.voice_select,voice);

	mode &= ~(VOICE_STOPPED|STOP_VOICE);	/* turn 'stop' bits off ... */

	/* NOTE: no irq's from the voice ... */
	outp(_gf1_data.reg_select,SET_CONTROL);
	outp(_gf1_data.data_hi,mode);

	gf1_delay();

	outp(_gf1_data.data_hi,mode);

	LEAVE_CRITICAL;

}

/**********************************************************************
 *
 * This function will start playing a wave out of DRAM. It assumes
 * the playback rate, volume & balance have been set up before ...
 *
 *********************************************************************/

void
UltraStartVoice(int voice,unsigned long begin,unsigned long start,unsigned long end,unsigned char mode)
// int voice;					/* voice to start */
// unsigned long begin;		/* start location in ultra DRAM */
// unsigned long start;		/* start loop location in ultra DRAM */
// unsigned long end;			/* end location in ultra DRAM */
// unsigned char mode;			/* mode to run the voice (loop etc) */
{
mode = UltraPrimeVoice(voice,begin,start,end,mode);
UltraGoVoice(voice,mode);
}

