// Emacs style mode select   -*- C++ -*-
//-----------------------------------------------------------------------------
//
// $Id
//
//  Copyright (C) 2004 Carlos Guariglia
//
//  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., 59 Temple Place - Suite 330, Boston, MA 
//  02111-1307, USA.
//
//
// DESCRIPTION:
//      System interface for sound.
//
//-----------------------------------------------------------------------------

#include <stdio.h>
#include "doomstat.h"
#include "w_wad.h"
#include "d_main.h"
#include "sounds.h"

typedef struct
{
int freq;
unsigned long len;
void *data;
} SAMPLE;

static SAMPLE *raw2SAMPLE(unsigned char *rawdata, int len)
{
 SAMPLE *spl = (SAMPLE*)malloc(sizeof(SAMPLE));
 spl->freq = (rawdata[3]<<8)+rawdata[2];
 spl->len = len;
 spl->data = rawdata + 8;
 _go32_dpmi_lock_data(rawdata+8, len);
 return spl;
}

static void *getsfx(char *sfxname, int *len)
{
 unsigned char *sfx, *paddedsfx;
 int i, size, paddedsize, sfxlump;
 char name[20];

 sprintf(name, "ds%s", sfxname);
 if ( W_CheckNumForName(name) == -1 )
 sfxlump = W_GetNumForName("dspistol");
 else
 sfxlump = W_GetNumForName(name);
 size = W_LumpLength(sfxlump);
 sfx = W_CacheLumpNum(sfxlump, 1);
 paddedsize = size + 503;
 paddedsfx = (unsigned char*) Z_Malloc(paddedsize+8, 1, 0);
 memcpy(paddedsfx, sfx, size);
 for (i=size; i<paddedsize+8; i++)
 paddedsfx[i] = 128;
 Z_Free(sfx);
 *len = paddedsize;
 return raw2SAMPLE(paddedsfx,paddedsize);
}

void I_SetSfxVolume(int volume)
{
 snd_SfxVolume = volume;
}

int I_GetSfxLumpNum(sfxinfo_t* sfx)
{
 char namebuf[9];
 sprintf(namebuf, "ds%s", sfx->name);
 return W_CheckNumForName(namebuf);
}
static SAMPLE channel[128];
int I_StartSound(int sfx, int vol, int sep, int pitch, int pri)
{
 static int handle;
 if (++handle >= 128)
 handle = 0;
 stop_sample(&channel[handle]);
 memcpy(&channel[handle], S_sfx[sfx].data, sizeof(SAMPLE));
 play_sample(&channel[handle],vol*16+15);
 return handle;
}

void I_StopSound (int handle)
{
 stop_sample(channel+handle);
}

void I_ShutdownSound(void)
{
 remove_sound();
}
boolean nosfxparm,nomusicparm;
void I_InitSound(void)
{
 int lengths[NUMSFX], i;
 fputs("I_InitSound: ", stdout);
 if (install_sound()==-1)
 {
 puts("ausent\n");
 nosfxparm = 1;
 }
 else
 {
 puts("ok\n");
 _go32_dpmi_lock_data(channel,sizeof channel);
 atexit(I_ShutdownSound);
 }

 for (i=1; i<NUMSFX; i++)
 if (!S_sfx[i].link)
 S_sfx[i].data = getsfx(S_sfx[i].name, &lengths[i]);
 else
 {
 S_sfx[i].data = S_sfx[i].link->data;
 lengths[i] = lengths[(S_sfx[i].link - S_sfx)/sizeof(sfxinfo_t)];
 }
}
