Metropoli BBS
VIEWER: ultradev.c MODE: TEXT (ASCII)
#define INCL_DOSDEVICES
#include <os2.h>
#include <string.h>
#include "struct.h"

// IOCTL commands
#define GUS_COMMANDS			0x0F
#define UltraDevSetNVoices		0x50
#define UltraDevEnableOutput		0x51
#define UltraDevDisableOutput		0x52
#define UltraDevPokeData		0x53
#define UltraDevPeekData		0x54
#define UltraDevMemAlloc		0x55
#define UltraDevMemFree			0x56
#define UltraDevMemInit			0x57
#define UltraDevStartTimer		0x58
#define UltraDevStopTimer		0x59
#define UltraDevBlockTimerHandler1	0x5A
#define UltraDevBlockTimerHandler2	0x5B
#define UltraDevStartVoice		0x5C
#define UltraDevStopVoice		0x5D
#define UltraDevSetBalance		0x5E
#define UltraDevSetFrequency		0x5F
#define UltraDevVectorLinearVolume	0x60
#define UltraDevPrepare4DMAXfer		0x61
#define UltraDevUnblockAll		0x62
#define UltraDevSetAll			0x63
#define UltraDevGetAccess   	        0x6A
#define UltraDevReleaseAccess  	        0x6B
#define UltraDevSizeDRAM		0x6D
#define UltraDevGetDriverVersion	0x6E

#define UltraDevMODMemAlloc  		0x70
#define UltraDevMODMemFree		0x71
#define UltraDevMODBigMemAlloc		0x72
#define UltraDevSetLoopMode		0x73
#define UltraDevVoiceStopped		0x74

extern HFILE GUSHandle;

/******************************************************************************/
/******************************************************************************/
APIRET UltraSetNVoices(numvoices)
int numvoices;
{
ULONG ParmLength=0, DataLength=4;

return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevSetNVoices, NULL, 0, &ParmLength,
		 &numvoices, 4, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraGetAccess()
{
ULONG DataLength = 0, ParmLength = 0;

return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevGetAccess, NULL, 0,
		 &ParmLength, NULL, 0, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraReleaseAccess()
{
ULONG DataLength = 0, ParmLength = 0;

return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevReleaseAccess, NULL, 0,
		 &ParmLength, NULL, 0, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraEnableOutput()
{
ULONG DataLength = 0, ParmLength = 0;

return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevEnableOutput, NULL, 0,
		 &ParmLength, NULL, 0, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraDisableOutput()
{
ULONG DataLength = 0, ParmLength = 0;

return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevDisableOutput, NULL, 0,
		 &ParmLength, NULL, 0, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraBlockTimerHandler1()
{
ULONG ParmLength = 0, DataLength = 0;
// block until timer interrupt
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevBlockTimerHandler1, NULL, 0, &ParmLength,
        	    NULL, 0, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraBlockTimerHandler2()
{
ULONG ParmLength = 0, DataLength = 0;
// block until timer interrupt
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevBlockTimerHandler2, NULL, 0, &ParmLength,
         	    NULL, 0, &DataLength));
} 
/******************************************************************************/
/******************************************************************************/
APIRET UltraStartTimer(timer, time)
int timer;
int time;
{
TimerStruct tbuffer;
ULONG ParmLength, DataLength;

ParmLength = 0;
DataLength = sizeof(TimerStruct);
tbuffer.timer = (short int)timer;
tbuffer.time = (unsigned char)time;
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevStartTimer, NULL, 0, &ParmLength,
	    &tbuffer, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraStopTimer(timer)
int timer;
{
ULONG ParmLength, DataLength;

ParmLength = 0;
DataLength = 4; 
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevStopTimer, NULL, 0, &ParmLength,
		 &timer, 4, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraSetBalance(voice, data)
int voice;
int data;
{
ULONG ParmLength = 0, DataLength;
BalanceStruct bbuffer;

DataLength = sizeof(BalanceStruct);
bbuffer.voice = (short int)voice;
bbuffer.data = (unsigned char)data;
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevSetBalance, NULL, 0,
	    &ParmLength, &bbuffer, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraSetFrequency(voice, freq)
int voice;
int freq;
{
ULONG ParmLength = 0, DataLength;
FreqStruct fbuffer;

DataLength = sizeof(FreqStruct);
fbuffer.voice = (short int)voice;
fbuffer.speed_khz = freq;
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevSetFrequency, NULL, 0,
	    &ParmLength, &fbuffer, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltiMODMemFree()
{
ULONG ParmLength = 0, DataLength = 0;
//just free it all
  return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevMODMemFree, NULL,
	  	      0, &ParmLength, NULL, 0, &DataLength)) ;
}
/******************************************************************************/
/******************************************************************************/
APIRET UltiMODMemAlloc(size, location)
unsigned long size;
unsigned long *location;
{
ULONG ParmLength = 0, DataLength;
AllocStruct abuffer;
APIRET rc;

DataLength = sizeof(AllocStruct);
abuffer.size = size;
abuffer.location = *location;

if(size >= 256*1024) 
//alloc more than 256 kb (xm) NO 16 BIT SAMPLES!
	rc = DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevMODBigMemAlloc, NULL,
			 0, &ParmLength, &abuffer, DataLength, &DataLength);	
else	rc = DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevMODMemAlloc, NULL,
		         0, &ParmLength, &abuffer, DataLength, &DataLength);

*location = abuffer.location; /* location in DRAM GUS */
return(rc);
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraMemFree(int size, int location)
{
ULONG ParmLength = 0, DataLength = sizeof(AllocStruct);
AllocStruct abuffer;

 abuffer.size = size;
 abuffer.location = location;
 return(DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevMemFree, NULL,
	    0, &ParmLength, &abuffer, DataLength, &DataLength)) ;
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraMemAlloc(size, location)
unsigned long size;
unsigned long *location;
{
ULONG ParmLength = 0, DataLength;
AllocStruct abuffer;
APIRET rc;

DataLength = sizeof(AllocStruct);
abuffer.size = size;
abuffer.location = *location;

rc = DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevMemAlloc, NULL,
	       0, &ParmLength, &abuffer, DataLength, &DataLength);

*location = abuffer.location; /* location in DRAM GUS */
return(rc);
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraMemInit()
{
ULONG ParmLength = 0, DataLength = 0;

 return(DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevMemAlloc, NULL,
	            0, &ParmLength, NULL, 0, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
/******************************************************************************/
/******************************************************************************/
APIRET UltraDownload(dataptr, control, dram_loc, size, wait)
char *dataptr;
unsigned char control;
unsigned long dram_loc;
unsigned int size;
int wait;
{
ULONG ParmLength = 0, DataLength;
APIRET rc;
ULONG written;
XferStruct xbuffer;
char *Buffer64k;

 /* structure voor UltraPrepare4DMAXfer IOCtl call */
 DataLength = sizeof(XferStruct);
 xbuffer.control = control;	 //control byte (data width, signed/unsigned)
 xbuffer.dram_loc = dram_loc;

 // NEED to allocate a buffer to transfer samples > 64 kb !!!
 rc = DosAllocMem(&Buffer64k, 64*1024, PAG_COMMIT | PAG_WRITE);
 if(rc) return(TRUE);

 while(TRUE) {
 	if(size > 64000) {//16 bit segments in a 32 bit world 8(
		memcpy(Buffer64k, dataptr, 64000);

	 	rc = DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevPrepare4DMAXfer, NULL,
			       0, &ParmLength, &xbuffer, DataLength, &DataLength);
		if(rc != 0) 	    goto download_err;

		rc = DosWrite(GUSHandle, Buffer64k, 64000, &written);
		if(rc != 0)	    goto download_err;

		dram_loc += 64000;
		xbuffer.dram_loc = dram_loc;
		xbuffer.control = control;
		dataptr += 64000;
		size -= 64000;
	 }
	 else 	break;
 }
 if(size > 0) {
 	 memcpy(Buffer64k, dataptr, size);
	 rc = DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevPrepare4DMAXfer, NULL,
	 	       0, &ParmLength, &xbuffer, DataLength, &DataLength);
	 if(rc != 0) 	    goto download_err;

	 rc =  DosWrite(GUSHandle, Buffer64k, size, &written); //last transfer
	 if(rc) goto download_err;
 }

 DosFreeMem(Buffer64k); 
 return(0);

download_err:
 DosFreeMem(Buffer64k); 
 return(rc);
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraPokeData(address, data)
long address;
int data;
{
ULONG ParmLength = 0, DataLength;
PokeStruct pbuffer;

pbuffer.address = address;
pbuffer.data = (unsigned char)data;
DataLength = sizeof(pbuffer);
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevPokeData, NULL, 0,
	    &ParmLength, &pbuffer, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraPeekData(int *address)
{
ULONG ParmLength = 0, DataLength;

DataLength = sizeof(int);
return(DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevPeekData, NULL, 0, &ParmLength,
                   address, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraUnblockAll()
{
ULONG ParmLength = 0, DataLength = 0;

return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevUnblockAll, NULL, 0, &ParmLength,
		  NULL, 0, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraStopVoice(int c)
{
ULONG ParmLength = 0, DataLength = 2;
short int voice;

voice = (short int)c;
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevStopVoice, NULL, 0, &ParmLength,
		    &voice, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraVectorLinearVolume(voice, end_idx, rate, mode)
int voice;
unsigned int end_idx;		/* end location in ultra DRAM */
unsigned char rate;			/* 0 to 63 */
unsigned char mode;			/* mode to run the volume ramp in ... */
{
ULONG ParmLength, DataLength;
VolumeStruct vbuffer;

vbuffer.voice = (short int)voice;
vbuffer.end_idx = (short int)end_idx;
vbuffer.rate = rate;
vbuffer.mode = mode;
DataLength = sizeof(VolumeStruct);
ParmLength = 0;
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevVectorLinearVolume,
		 NULL, 0, &ParmLength, &vbuffer, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraSetAll(voice, balance, freq, volume, rate, mode)
int voice;
char balance;
int freq, volume;
unsigned char rate;			/* 0 to 63 */
unsigned char mode;			/* mode to run the volume ramp in ... */
{
ULONG ParmLength = 0, DataLength;
AllStruct abuffer;

DataLength = sizeof(AllStruct);
abuffer.voice = (short int)voice;
abuffer.balance = (unsigned char)balance;
abuffer.freq = freq;
abuffer.volume = (unsigned short int)volume;
abuffer.rate = rate;
abuffer.mode = mode;
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevSetAll, NULL, 0,
		    &ParmLength, &abuffer, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraStartVoice(gusvoice, begin, start, end, mode)
int gusvoice;		 /* voice to start */
unsigned int begin;	 /* start location in ultra DRAM */
unsigned int start;	 /* start loop location in ultra DRAM */
unsigned int end;	 /* end location in ultra DRAM */
unsigned char mode;	 /* mode to run the voice (loop etc) */
{
ULONG ParmLength = 0, DataLength;
VoiceStruct voice;

voice.voice = (short int)gusvoice;
voice.begin = begin; // start in DRAM
voice.start = start; //start loop
voice.end = end;
voice.mode = mode;
DataLength = sizeof(VoiceStruct);
return(	DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevStartVoice, NULL, 0,
		    &ParmLength, &voice, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraSizeDram(int *size)
{
ULONG ParmLength = 0, DataLength;

  DataLength = sizeof(int);
  return(DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevSizeDRAM, NULL, 0, &ParmLength,
                     size, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraGetDriverVersion(int *version)
{
ULONG ParmLength = 0, DataLength;
//High word contains major version, low word minor version

  DataLength = sizeof(int);
  return(DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevGetDriverVersion, NULL, 0, &ParmLength,
                     version, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraSetLoopMode(int voice, int mode)
{
ULONG ParmLength = 0, DataLength;
BalanceStruct bbuffer;

DataLength = sizeof(BalanceStruct);
bbuffer.voice = (short int)voice;
bbuffer.data = (unsigned char)mode;
return( DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevSetLoopMode, NULL, 0,
	    &ParmLength, &bbuffer, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
APIRET UltraVoiceStopped(int *voice)
{
ULONG ParmLength = 0, DataLength;

  DataLength = sizeof(int);
  return(DosDevIOCtl(GUSHandle, GUS_COMMANDS, UltraDevVoiceStopped, NULL, 0, &ParmLength,
                     voice, DataLength, &DataLength));
}
/******************************************************************************/
/******************************************************************************/
[ RETURN TO DIRECTORY ]