+
+/*
+====================
+Snd_CreateSndBuffer
+====================
+*/
+snd_buffer_t *Snd_CreateSndBuffer (const unsigned char *samples, unsigned int sampleframes, const snd_format_t* in_format, unsigned int sb_speed)
+{
+ size_t newsampleframes, memsize;
+ snd_buffer_t* sb;
+
+ newsampleframes = (size_t) ceil((double)sampleframes * (double)sb_speed / (double)in_format->speed);
+
+ memsize = newsampleframes * in_format->channels * in_format->width;
+ memsize += sizeof (*sb) - sizeof (sb->samples);
+
+ sb = (snd_buffer_t*)Mem_Alloc (snd_mempool, memsize);
+ sb->format.channels = in_format->channels;
+ sb->format.width = in_format->width;
+ sb->format.speed = sb_speed;
+ sb->maxframes = newsampleframes;
+ sb->nbframes = 0;
+
+ if (!Snd_AppendToSndBuffer (sb, samples, sampleframes, in_format))
+ {
+ Mem_Free (sb);
+ return NULL;
+ }
+
+ return sb;
+}
+
+
+/*
+====================
+Snd_AppendToSndBuffer
+====================
+*/
+qboolean Snd_AppendToSndBuffer (snd_buffer_t* sb, const unsigned char *samples, unsigned int sampleframes, const snd_format_t* format)
+{
+ size_t srclength, outcount;
+ unsigned char *out_data;
+
+ //Con_DPrintf("ResampleSfx: %d samples @ %dHz -> %d samples @ %dHz\n",
+ // sampleframes, format->speed, outcount, sb->format.speed);
+
+ // If the formats are incompatible
+ if (sb->format.channels != format->channels || sb->format.width != format->width)
+ {
+ Con_Print("AppendToSndBuffer: incompatible sound formats!\n");
+ return false;
+ }
+
+ outcount = (size_t) ((double)sampleframes * (double)sb->format.speed / (double)format->speed);
+
+ // If the sound buffer is too short
+ if (outcount > sb->maxframes - sb->nbframes)
+ {
+ Con_Print("AppendToSndBuffer: sound buffer too short!\n");
+ return false;
+ }
+
+ out_data = &sb->samples[sb->nbframes * sb->format.width * sb->format.channels];
+ srclength = sampleframes * format->channels;