1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164
|
/*
* Sounder/Sndtool format handler: W V Neisius, February 1992
*
* June 28, 93: force output to mono.
*/
#include <math.h>
#include "st.h"
#ifdef VMS
#include <errno.h>
#include <perror.h>
#endif
/* Private data used by writer */
struct sndpriv {
ULONG nsamples;
};
#ifndef SEEK_CUR
#define SEEK_CUR 1
#endif
IMPORT sndtwriteheader(P2(ft_t ft,LONG nsamples));
/*======================================================================*/
/* SNDSTARTREAD */
/*======================================================================*/
sndtstartread(ft)
ft_t ft;
{
struct sndpriv *p = (struct sndpriv *) ft->priv;
char buf[97];
LONG rate;
rate = 0;
/* determine file type */
/* if first 5 bytes == SOUND then this is probably a sndtool sound */
/* if first word (16 bits) == 0
and second word is between 4000 & 25000 then this is sounder sound */
/* otherwise, its probably raw, not handled here */
if (fread(buf, 1, 2, ft->fp) != 2)
fail("SND: unexpected EOF");
if (strncmp(buf,"\0\0",2) == 0)
{
/* sounder */
rate = rlshort(ft);
if (rate < 4000 || rate > 25000 )
fail ("SND: sample rate out of range");
fseek(ft->fp,4,SEEK_CUR);
}
else
{
/* sndtool ? */
fread(&buf[2],1,6,ft->fp);
if (strncmp(buf,"SOUND",5))
fail ("SND: unrecognized SND format");
fseek(ft->fp,12,SEEK_CUR);
rate = rlshort(ft);
fseek(ft->fp,6,SEEK_CUR);
if (fread(buf,1,96,ft->fp) != 96)
fail ("SND: unexpected EOF in SND header");
report ("%s",buf);
}
ft->info.channels = 1;
ft->info.rate = rate;
ft->info.style = UNSIGNED;
ft->info.size = BYTE;
}
/*======================================================================*/
/* SNDTSTARTWRITE */
/*======================================================================*/
sndtstartwrite(ft)
ft_t ft;
{
struct sndpriv *p = (struct sndpriv *) ft->priv;
/* write header */
ft->info.channels = 1;
ft->info.style = UNSIGNED;
ft->info.size = BYTE;
p->nsamples = 0;
sndtwriteheader(ft, 0);
}
/*======================================================================*/
/* SNDRSTARTWRITE */
/*======================================================================*/
sndrstartwrite(ft)
ft_t ft;
{
/* write header */
ft->info.channels = 1;
ft->info.style = UNSIGNED;
ft->info.size = BYTE;
/* sounder header */
wlshort (ft,0); /* sample size code */
wlshort (ft,(int) ft->info.rate); /* sample rate */
wlshort (ft,10); /* volume */
wlshort (ft,4); /* shift */
}
/*======================================================================*/
/* SNDTWRITE */
/*======================================================================*/
sndtwrite(ft, buf, len)
ft_t ft;
LONG *buf, len;
{
struct sndpriv *p = (struct sndpriv *) ft->priv;
p->nsamples += len;
rawwrite(ft, buf, len);
}
/*======================================================================*/
/* SNDTSTOPWRITE */
/*======================================================================*/
sndtstopwrite(ft)
ft_t ft;
{
struct sndpriv *p = (struct sndpriv *) ft->priv;
/* fixup file sizes in header */
if (fseek(ft->fp, 0L, 0) != 0)
fail("can't rewind output file to rewrite SND header");
sndtwriteheader(ft, p->nsamples);
}
/*======================================================================*/
/* SNDTWRITEHEADER */
/*======================================================================*/
sndtwriteheader(ft,nsamples)
ft_t ft;
LONG nsamples;
{
char name_buf[97];
/* sndtool header */
fputs ("SOUND",ft->fp); /* magic */
fputc (0x1a,ft->fp);
wlshort (ft,(LONG)0); /* hGSound */
wllong (ft,nsamples);
wllong (ft,(LONG)0);
wllong (ft,nsamples);
wlshort (ft,(int) ft->info.rate);
wlshort (ft,0);
wlshort (ft,10);
wlshort (ft,4);
sprintf (name_buf,"%s - File created by Sound Exchange",ft->filename);
fwrite (name_buf, 1, 96, ft->fp);
}
|