ReactOS 0.4.15-dev-8339-g4028de8
rdpsnd_sun.c File Reference
#include "rdesktop.h"
#include <unistd.h>
#include <fcntl.h>
#include <errno.h>
#include <sys/ioctl.h>
#include <sys/audioio.h>
Include dependency graph for rdpsnd_sun.c:

Go to the source code of this file.

Classes

struct  audio_packet
 

Macros

#define MAX_QUEUE   10
 

Functions

BOOL wave_out_open (void)
 
void wave_out_close (void)
 
BOOL wave_out_format_supported (WAVEFORMATEX *pwfx)
 
BOOL wave_out_set_format (WAVEFORMATEX *pwfx)
 
void wave_out_volume (uint16 left, uint16 right)
 
void wave_out_write (STREAM s, uint16 tick, uint8 index)
 
void wave_out_play (void)
 

Variables

int This dsp_
 
BOOL This dsp_bu = False
 
static BOOL g_reopened
 
static BOOL g_swapaudio
 
static short g_samplewidth
 
static struct audio_packet packet_queue [MAX_QUEUE]
 
static unsigned int queue_hi
 
static unsigned int queue_lo
 

Macro Definition Documentation

◆ MAX_QUEUE

#define MAX_QUEUE   10

Definition at line 34 of file rdpsnd_sun.c.

Function Documentation

◆ wave_out_close()

void wave_out_close ( void  )

Definition at line 76 of file rdpsnd_sun.c.

77{
78 /* Ack all remaining packets */
79 while (queue_lo != queue_hi)
80 {
83 queue_lo = (queue_lo + 1) % MAX_QUEUE;
84 }
85
86#if defined I_FLUSH && defined FLUSHW
87 /* Flush the audiobuffer */
88 ioctl(This->dsp_, I_FLUSH, FLUSHW);
89#endif
90#if defined AUDIO_FLUSH
91 ioctl(This->dsp_, AUDIO_FLUSH, NULL);
92#endif
93 close(This->dsp_);
94}
#define close
Definition: acwin.h:98
#define free
Definition: debug_ros.c:5
#define NULL
Definition: types.h:112
GLdouble s
Definition: gl.h:2039
GLuint index
Definition: glext.h:6031
void rdpsnd_send_completion(RDPCLIENT *This, uint16 tick, uint8 packet_index)
Definition: rdpsnd.c:55
static unsigned int queue_lo
Definition: rdpsnd_sun.c:48
static unsigned int queue_hi
Definition: rdpsnd_sun.c:48
#define MAX_QUEUE
Definition: rdpsnd_sun.c:34
static struct audio_packet packet_queue[MAX_QUEUE]
#define ioctl
Definition: wintirpc.h:60

◆ wave_out_format_supported()

BOOL wave_out_format_supported ( WAVEFORMATEX pwfx)

Definition at line 97 of file rdpsnd_sun.c.

98{
99 if (pwfx->wFormatTag != WAVE_FORMAT_PCM)
100 return False;
101 if ((pwfx->nChannels != 1) && (pwfx->nChannels != 2))
102 return False;
103 if ((pwfx->wBitsPerSample != 8) && (pwfx->wBitsPerSample != 16))
104 return False;
105
106 return True;
107}
#define WAVE_FORMAT_PCM
Definition: constants.h:425
#define False
Definition: types.h:25
#define True
Definition: types.h:24
WORD wBitsPerSample
Definition: audioclient.idl:45

◆ wave_out_open()

BOOL wave_out_open ( void  )

Definition at line 51 of file rdpsnd_sun.c.

52{
53 char *dsp_dev = getenv("AUDIODEV");
54
55 if (dsp_dev == NULL)
56 {
57 dsp_dev = xstrdup("/dev/audio");
58 }
59
60 if ((This->dsp_ = open(dsp_dev, O_WRONLY | O_NONBLOCK)) == -1)
61 {
62 perror(dsp_dev);
63 return False;
64 }
65
66 /* Non-blocking so that user interface is responsive */
67 fcntl(This->dsp_, F_SETFL, fcntl(This->dsp_, F_GETFL) | O_NONBLOCK);
68
69 queue_lo = queue_hi = 0;
71
72 return True;
73}
#define O_WRONLY
Definition: acwin.h:111
#define open
Definition: acwin.h:95
char * xstrdup(const char *s)
Definition: uimain.c:768
_CRTIMP void __cdecl perror(_In_opt_z_ const char *_ErrMsg)
_Check_return_ char *__cdecl getenv(_In_z_ const char *_VarName)
#define O_NONBLOCK
Definition: port.h:158
static BOOL g_reopened
Definition: rdpsnd_sun.c:38

◆ wave_out_play()

void wave_out_play ( void  )

Definition at line 222 of file rdpsnd_sun.c.

223{
224 struct audio_packet *packet;
225 audio_info_t info;
226 ssize_t len;
227 unsigned int i;
228 uint8 swap;
229 STREAM out;
230 static BOOL swapped = False;
231 static BOOL sentcompletion = True;
232 static uint32 samplecnt = 0;
233 static uint32 numsamples;
234
235 while (1)
236 {
237 if (g_reopened)
238 {
239 /* Device was just (re)openend */
240 samplecnt = 0;
241 swapped = False;
242 sentcompletion = True;
244 }
245
246 if (queue_lo == queue_hi)
247 {
248 This->dsp_bu = 0;
249 return;
250 }
251
253 out = &packet->s;
254
255 /* Swap the current packet, but only once */
256 if (g_swapaudio && !swapped)
257 {
258 for (i = 0; i < out->end - out->p; i += 2)
259 {
260 swap = *(out->p + i);
261 *(out->p + i) = *(out->p + i + 1);
262 *(out->p + i + 1) = swap;
263 }
264 swapped = True;
265 }
266
267 if (sentcompletion)
268 {
269 sentcompletion = False;
270 numsamples = (out->end - out->p) / g_samplewidth;
271 }
272
273 len = 0;
274
275 if (out->end != out->p)
276 {
277 len = write(This->dsp_, out->p, out->end - out->p);
278 if (len == -1)
279 {
280 if (errno != EWOULDBLOCK)
281 perror("write audio");
282 This->dsp_bu = 1;
283 return;
284 }
285 }
286
287 out->p += len;
288 if (out->p == out->end)
289 {
290 if (ioctl(This->dsp_, AUDIO_GETINFO, &info) == -1)
291 {
292 perror("AUDIO_GETINFO");
293 return;
294 }
295
296 /* Ack the packet, if we have played at least 70% */
297 if (info.play.samples >= samplecnt + ((numsamples * 7) / 10))
298 {
299 samplecnt += numsamples;
300 rdpsnd_send_completion(packet->tick, packet->index);
301 free(out->data);
302 queue_lo = (queue_lo + 1) % MAX_QUEUE;
303 swapped = False;
304 sentcompletion = True;
305 }
306 else
307 {
308 This->dsp_bu = 1;
309 return;
310 }
311 }
312 }
313}
#define write
Definition: acwin.h:97
unsigned int uint32
Definition: types.h:32
unsigned char uint8
Definition: types.h:28
#define EWOULDBLOCK
Definition: errno.h:42
unsigned int BOOL
Definition: ntddk_ex.h:94
GLenum GLsizei len
Definition: glext.h:6722
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
#define swap(a, b)
Definition: qsort.c:63
static short g_samplewidth
Definition: rdpsnd_sun.c:40
static BOOL g_swapaudio
Definition: rdpsnd_sun.c:39
static FILE * out
Definition: regtests2xml.c:44
int ssize_t
Definition: rosdhcp.h:48
#define errno
Definition: errno.h:18
Definition: dhcpd.h:135
Definition: parse.h:23

Referenced by wave_out_write().

◆ wave_out_set_format()

BOOL wave_out_set_format ( WAVEFORMATEX pwfx)

Definition at line 110 of file rdpsnd_sun.c.

111{
112 audio_info_t info;
113
114 ioctl(This->dsp_, AUDIO_DRAIN, 0);
116 AUDIO_INITINFO(&info);
117
118
119 if (pwfx->wBitsPerSample == 8)
120 {
121 info.play.encoding = AUDIO_ENCODING_LINEAR8;
122 }
123 else if (pwfx->wBitsPerSample == 16)
124 {
125 info.play.encoding = AUDIO_ENCODING_LINEAR;
126 /* Do we need to swap the 16bit values? (Are we BigEndian) */
127#ifdef B_ENDIAN
128 g_swapaudio = 1;
129#else
130 g_swapaudio = 0;
131#endif
132 }
133
134 g_samplewidth = pwfx->wBitsPerSample / 8;
135
136 if (pwfx->nChannels == 1)
137 {
138 info.play.channels = 1;
139 }
140 else if (pwfx->nChannels == 2)
141 {
142 info.play.channels = 2;
143 g_samplewidth *= 2;
144 }
145
146 info.play.sample_rate = pwfx->nSamplesPerSec;
147 info.play.precision = pwfx->wBitsPerSample;
148 info.play.samples = 0;
149 info.play.eof = 0;
150 info.play.error = 0;
152
153 if (ioctl(This->dsp_, AUDIO_SETINFO, &info) == -1)
154 {
155 perror("AUDIO_SETINFO");
156 close(This->dsp_);
157 return False;
158 }
159
160 return True;
161}
DWORD nSamplesPerSec
Definition: audioclient.idl:42

◆ wave_out_volume()

void wave_out_volume ( uint16  left,
uint16  right 
)

Definition at line 164 of file rdpsnd_sun.c.

165{
166 audio_info_t info;
167 uint balance;
168 uint volume;
169
170 AUDIO_INITINFO(&info);
171
172 volume = (left > right) ? left : right;
173
174 if (volume / AUDIO_MID_BALANCE != 0)
175 {
176 balance =
177 AUDIO_MID_BALANCE - (left / (volume / AUDIO_MID_BALANCE)) +
178 (right / (volume / AUDIO_MID_BALANCE));
179 }
180 else
181 {
182 balance = AUDIO_MID_BALANCE;
183 }
184
185 info.play.gain = volume / (65536 / AUDIO_MAX_GAIN);
186 info.play.balance = balance;
187
188 if (ioctl(This->dsp_, AUDIO_SETINFO, &info) == -1)
189 {
190 perror("AUDIO_SETINFO");
191 return;
192 }
193}
UINT32 uint
Definition: types.h:83
GLdouble GLdouble right
Definition: glext.h:10859
GLint left
Definition: glext.h:7726

◆ wave_out_write()

void wave_out_write ( STREAM  s,
uint16  tick,
uint8  index 
)

Definition at line 196 of file rdpsnd_sun.c.

197{
199 unsigned int next_hi = (queue_hi + 1) % MAX_QUEUE;
200
201 if (next_hi == queue_lo)
202 {
203 error("No space to queue audio packet\n");
204 return;
205 }
206
207 queue_hi = next_hi;
208
209 packet->s = *s;
210 packet->tick = tick;
211 packet->index = index;
212 packet->s.p += 4;
213
214 /* we steal the data buffer from s, give it a new one */
215 s->data = malloc(s->size);
216
217 if (!This->dsp_bu)
219}
#define index(s, c)
Definition: various.h:29
#define malloc
Definition: debug_ros.c:4
#define error(str)
Definition: mkdosfs.c:1605
void wave_out_play(void)
Definition: rdpsnd_sun.c:222

Variable Documentation

◆ dsp_

int This dsp_

Definition at line 36 of file rdpsnd_sun.c.

◆ dsp_bu

BOOL This dsp_bu = False

Definition at line 37 of file rdpsnd_sun.c.

◆ g_reopened

BOOL g_reopened
static

Definition at line 38 of file rdpsnd_sun.c.

Referenced by wave_out_open(), wave_out_play(), and wave_out_set_format().

◆ g_samplewidth

short g_samplewidth
static

Definition at line 40 of file rdpsnd_sun.c.

Referenced by wave_out_play(), and wave_out_set_format().

◆ g_swapaudio

BOOL g_swapaudio
static

Definition at line 39 of file rdpsnd_sun.c.

Referenced by wave_out_play(), and wave_out_set_format().

◆ packet_queue

◆ queue_hi

unsigned int queue_hi
static

Definition at line 48 of file rdpsnd_sun.c.

Referenced by wave_out_close(), wave_out_open(), wave_out_play(), and wave_out_write().

◆ queue_lo

unsigned int queue_lo
static

Definition at line 48 of file rdpsnd_sun.c.

Referenced by wave_out_close(), wave_out_open(), wave_out_play(), and wave_out_write().