1 /* All the code for dealing with OSS */
3 #include <linux/soundcard.h>
7 static int oss_fd_fakeopen
=0;
9 static int oss_fmt_translate(int format
){
12 if(format
==((1<<i
)>>1))return(i
);
16 static void oss_hook_init(void){
19 ossname
=nstrdup(getenv("SNATCH_OSS_DEVICE"));
23 "----env: SNATCH_OSS_DEVICE\n"
24 " not set. Using default (/dev/dsp*).\n");
25 ossname
=nstrdup("/dev/dsp*");
29 "----env: SNATCH_OSS_DEVICE\n"
30 " set (%s)\n",ossname
);
34 /* The OSS audio device is subverted through open(). If we didn't
35 care about allowing a fake audio open() to 'succeed' even when the
36 real device is busy, then we could just watch for the ioctl(), grab
37 the fd() then, and not need to bother with any silly string
38 matching. However, we *do* care, so we do this the more complex,
39 slightly more error prone way. */
41 static int oss_identify(const char *pathname
){
42 if( (ossname
[strlen(ossname
)-1]=='*' &&
43 !strncmp(pathname
,ossname
,strlen(ossname
)-1)) ||
44 (ossname
[strlen(ossname
)-1]!='*' &&
45 !strcmp(pathname
,ossname
)))return(1);
49 static int oss_open_hook(const char *pathname
){
52 /* umm... an oss fd is already open. report the problem and
56 "WARNING: RealPlayer is attempting to open more than one\n"
57 " OSS audio device (in this case, %s).\n"
58 " This behavior is unexpected; ignoring this open()\n"
59 " request.\n",pathname
);
63 /* are we faking the audio? */
65 ret
=(*libc_open
)("/dev/null",O_RDWR
,0);
68 ret
=(*libc_open
)(pathname
,O_RDWR
,0);
78 audio_timezero
=bigtime(NULL
,NULL
);
82 " ...: Caught RealPlayer opening OSS audio device "
85 if(debug
&& fake_audiop
)
87 " ...: Faking the audio open and writes as requested.\n");
92 static void oss_close_hook(int fd
){
93 if(fd
==oss_fd
)oss_fd
=-1;
96 /* watch OSS audio ioctl()s to track playback rate/channels/depth */
98 static int oss_ioctl_hook_p(int fd
){
99 if(fd
==oss_fd
)return(1);
103 static int oss_ioctl_hook(int fd
,int rq
,void *arg
){
105 if(!fake_audiop
&& !oss_fd_fakeopen
)
106 ret
=(*libc_ioctl
)(fd
,rq
,arg
);
109 case SNDCTL_DSP_RESET
:
113 case SNDCTL_DSP_SPEED
:
114 audio_rate
=*(int *)arg
;
117 " ...: Audio output sampling rate set to %dHz.\n",
121 case SNDCTL_DSP_CHANNELS
:
122 audio_channels
=*(int *)arg
;
125 " ...: Audio output set to %d channels.\n",
129 case SNDCTL_DSP_SETFMT
:
130 audio_format
=oss_fmt_translate(*(int *)arg
);
133 " ...: Audio output format set to %s.\n",
134 audio_fmts
[audio_format
]);
137 case SNDCTL_DSP_GETOSPACE
:
139 audio_buf_info
*temp
=arg
;
146 fprintf(stderr
," ...: OSS output buffer size requested; faking 64k\n");
150 case SNDCTL_DSP_GETODELAY
: /* Must reject the ODELAY if we're not going to
151 properly simulate it! */
155 " ...: Rejecting SNDCTL_DSP_GETODELAY ioctl()\n");