diff options
author | Jay Sorg <jay.sorg@gmail.com> | 2013-05-12 18:03:32 -0700 |
---|---|---|
committer | Jay Sorg <jay.sorg@gmail.com> | 2013-05-12 18:03:32 -0700 |
commit | 21df0406d7e13bf85b5c5ca99f89edb2b9a55f15 (patch) | |
tree | ab6d925f21ea4f637ba40a96f0f9dd38c13f7f11 /sesman/chansrv/sound.c | |
parent | 8c9fe9452f822db29517c808e3607c19ca7847ba (diff) | |
download | xrdp-proprietary-21df0406d7e13bf85b5c5ca99f89edb2b9a55f15.tar.gz xrdp-proprietary-21df0406d7e13bf85b5c5ca99f89edb2b9a55f15.zip |
pulse work and cleanup
Diffstat (limited to 'sesman/chansrv/sound.c')
-rw-r--r-- | sesman/chansrv/sound.c | 217 |
1 files changed, 172 insertions, 45 deletions
diff --git a/sesman/chansrv/sound.c b/sesman/chansrv/sound.c index a4a94437..55f6f88d 100644 --- a/sesman/chansrv/sound.c +++ b/sesman/chansrv/sound.c @@ -23,43 +23,95 @@ extern int g_rdpsnd_chan_id; /* in chansrv.c */ extern int g_display_num; /* in chansrv.c */ -static struct trans *g_audio_l_trans = 0; // listener -static struct trans *g_audio_c_trans = 0; // connection +static struct trans *g_audio_l_trans = 0; /* listener */ +static struct trans *g_audio_c_trans = 0; /* connection */ static int g_training_sent_time = 0; static int g_cBlockNo = 0; #define BBUF_SIZE (1024 * 8) char g_buffer[BBUF_SIZE]; int g_buf_index = 0; +int g_sent_time[256]; #if defined(XRDP_SIMPLESOUND) static void *DEFAULT_CC read_raw_audio_data(void *arg); #endif +#define CHANSRV_PORT_STR "/tmp/.xrdp/xrdp_chansrv_audio_socket_%d" + +struct xr_wave_format_ex +{ + int wFormatTag; + int nChannels; + int nSamplesPerSec; + int nAvgBytesPerSec; + int nBlockAlign; + int wBitsPerSample; + int cbSize; + char *data; +}; + +static char g_pmc_22050_data[] = { 0 }; +static struct xr_wave_format_ex g_pmc_22050 = +{ + 1, /* wFormatTag - WAVE_FORMAT_PCM */ + 2, /* num of channels */ + 22050, /* samples per sec */ + 88200, /* avg bytes per sec */ + 4, /* block align */ + 16, /* bits per sample */ + 0, /* data size */ + g_pmc_22050_data /* data */ +}; + +static char g_pmc_44100_data[] = { 0 }; +static struct xr_wave_format_ex g_pmc_44100 = +{ + 1, /* wFormatTag - WAVE_FORMAT_PCM */ + 2, /* num of channels */ + 44100, /* samples per sec */ + 176400, /* avg bytes per sec */ + 4, /* block align */ + 16, /* bits per sample */ + 0, /* data size */ + g_pmc_44100_data /* data */ +}; + +#define NUM_BUILT_IN 2 +static struct xr_wave_format_ex *g_wave_formats[NUM_BUILT_IN] = +{ + &g_pmc_44100, + &g_pmc_22050 +}; + +/* index into list from client */ +static int g_current_client_format_index = 0; +/* index into list from server */ +static int g_current_server_format_index = 0; + /*****************************************************************************/ static int APP_CC sound_send_server_formats(void) { struct stream *s; int bytes; + int index; char *size_ptr; - print_got_here(); - make_stream(s); init_stream(s, 8182); out_uint16_le(s, SNDC_FORMATS); size_ptr = s->p; - out_uint16_le(s, 0); /* size, set later */ - out_uint32_le(s, 0); /* dwFlags */ - out_uint32_le(s, 0); /* dwVolume */ - out_uint32_le(s, 0); /* dwPitch */ - out_uint16_le(s, 0); /* wDGramPort */ - out_uint16_le(s, 1); /* wNumberOfFormats */ - out_uint8(s, g_cBlockNo); /* cLastBlockConfirmed */ - out_uint16_le(s, 2); /* wVersion */ - out_uint8(s, 0); /* bPad */ + out_uint16_le(s, 0); /* size, set later */ + out_uint32_le(s, 0); /* dwFlags */ + out_uint32_le(s, 0); /* dwVolume */ + out_uint32_le(s, 0); /* dwPitch */ + out_uint16_le(s, 0); /* wDGramPort */ + out_uint16_le(s, NUM_BUILT_IN); /* wNumberOfFormats */ + out_uint8(s, g_cBlockNo); /* cLastBlockConfirmed */ + out_uint16_le(s, 2); /* wVersion */ + out_uint8(s, 0); /* bPad */ /* sndFormats */ /* @@ -80,13 +132,21 @@ sound_send_server_formats(void) 00 00 */ - out_uint16_le(s, 1); // wFormatTag - WAVE_FORMAT_PCM - out_uint16_le(s, 2); // num of channels - out_uint32_le(s, 44100); // samples per sec - out_uint32_le(s, 176400); // avg bytes per sec - out_uint16_le(s, 4); // block align - out_uint16_le(s, 16); // bits per sample - out_uint16_le(s, 0); // size + for (index = 0; index < NUM_BUILT_IN; index++) + { + out_uint16_le(s, g_wave_formats[index]->wFormatTag); + out_uint16_le(s, g_wave_formats[index]->nChannels); + out_uint32_le(s, g_wave_formats[index]->nSamplesPerSec); + out_uint32_le(s, g_wave_formats[index]->nAvgBytesPerSec); + out_uint16_le(s, g_wave_formats[index]->nBlockAlign); + out_uint16_le(s, g_wave_formats[index]->wBitsPerSample); + bytes = g_wave_formats[index]->cbSize; + out_uint16_le(s, bytes); + if (bytes > 0) + { + out_uint8p(s, g_wave_formats[index]->data, bytes); + } + } s_mark_end(s); bytes = (int)((s->end - s->data) - 4); @@ -107,8 +167,6 @@ sound_send_training(void) int time; char *size_ptr; - print_got_here(); - make_stream(s); init_stream(s, 8182); out_uint16_le(s, SNDC_TRAINING); @@ -130,6 +188,52 @@ sound_send_training(void) } /*****************************************************************************/ +static int APP_CC +sound_process_format(int aindex, int wFormatTag, int nChannels, + int nSamplesPerSec, int nAvgBytesPerSec, + int nBlockAlign, int wBitsPerSample, + int cbSize, char *data) +{ + int lindex; + + LOG(0, ("sound_process_format:")); + LOG(0, (" wFormatTag %d", wFormatTag)); + LOG(0, (" nChannels %d", nChannels)); + LOG(0, (" nSamplesPerSec %d", nSamplesPerSec)); + LOG(0, (" nAvgBytesPerSec %d", nAvgBytesPerSec)); + LOG(0, (" nBlockAlign %d", nBlockAlign)); + LOG(0, (" wBitsPerSample %d", wBitsPerSample)); + LOG(0, (" cbSize %d", cbSize)); + g_hexdump(data, cbSize); + if (wFormatTag == g_pmc_44100.wFormatTag && + nChannels == g_pmc_44100.nChannels && + nSamplesPerSec == g_pmc_44100.nSamplesPerSec && + nAvgBytesPerSec == g_pmc_44100.nAvgBytesPerSec && + nBlockAlign == g_pmc_44100.nBlockAlign && + wBitsPerSample == g_pmc_44100.wBitsPerSample) + { + g_current_client_format_index = aindex; + g_current_server_format_index = 0; + } +#if 0 + for (lindex = 0; lindex < NUM_BUILT_IN; lindex++) + { + if (wFormatTag == g_wave_formats[lindex]->wFormatTag && + nChannels == g_wave_formats[lindex]->nChannels && + nSamplesPerSec == g_wave_formats[lindex]->nSamplesPerSec && + nAvgBytesPerSec == g_wave_formats[lindex]->nAvgBytesPerSec && + nBlockAlign == g_wave_formats[lindex]->nBlockAlign && + wBitsPerSample == g_wave_formats[lindex]->wBitsPerSample) + { + g_current_client_format_index = aindex; + g_current_server_format_index = lindex; + } + } +#endif + return 0; +} + +/*****************************************************************************/ /* 0000 07 02 26 00 03 00 80 00 ff ff ff ff 00 00 00 00 ..&............. 0010 00 00 01 00 00 02 00 00 01 00 02 00 44 ac 00 00 ............D... @@ -140,8 +244,15 @@ static int APP_CC sound_process_formats(struct stream *s, int size) { int num_formats; - - print_got_here(); + int index; + int wFormatTag; + int nChannels; + int nSamplesPerSec; + int nAvgBytesPerSec; + int nBlockAlign; + int wBitsPerSample; + int cbSize; + char *data; LOG(0, ("sound_process_formats:")); @@ -152,9 +263,24 @@ sound_process_formats(struct stream *s, int size) in_uint8s(s, 14); in_uint16_le(s, num_formats); + in_uint8s(s, 4); if (num_formats > 0) { + for (index = 0; index < num_formats; index++) + { + in_uint16_le(s, wFormatTag); + in_uint16_le(s, nChannels); + in_uint32_le(s, nSamplesPerSec); + in_uint32_le(s, nAvgBytesPerSec); + in_uint16_le(s, nBlockAlign); + in_uint16_le(s, wBitsPerSample); + in_uint16_le(s, cbSize); + in_uint8p(s, data, cbSize); + sound_process_format(index, wFormatTag, nChannels, nSamplesPerSec, + nAvgBytesPerSec, nBlockAlign, wBitsPerSample, + cbSize, data); + } sound_send_training(); } @@ -162,6 +288,7 @@ sound_process_formats(struct stream *s, int size) } /*****************************************************************************/ +/* send wave message to client */ static int sound_send_wave_data_chunk(char *data, int data_bytes) { @@ -170,7 +297,7 @@ sound_send_wave_data_chunk(char *data, int data_bytes) int time; char *size_ptr; - print_got_here(); + LOG(10, ("sound_send_wave_data_chunk: data_bytes %d", data_bytes)); if ((data_bytes < 4) || (data_bytes > 128 * 1024)) { @@ -188,9 +315,10 @@ sound_send_wave_data_chunk(char *data, int data_bytes) out_uint16_le(s, 0); /* size, set later */ time = g_time2(); out_uint16_le(s, time); - out_uint16_le(s, 0); /* wFormatNo */ + out_uint16_le(s, g_current_client_format_index); /* wFormatNo */ g_cBlockNo++; out_uint8(s, g_cBlockNo); + g_sent_time[g_cBlockNo & 0xff] = time; LOG(10, ("sound_send_wave_data_chunk: sending time %d, g_cBlockNo %d", time & 0xffff, g_cBlockNo & 0xff)); @@ -220,6 +348,7 @@ sound_send_wave_data_chunk(char *data, int data_bytes) } /*****************************************************************************/ +/* send wave message to client, buffer first */ static int sound_send_wave_data(char *data, int data_bytes) { @@ -252,6 +381,7 @@ sound_send_wave_data(char *data, int data_bytes) } /*****************************************************************************/ +/* send close message to client */ static int sound_send_close(void) { @@ -260,7 +390,6 @@ sound_send_close(void) char *size_ptr; LOG(10, ("sound_send_close:")); - print_got_here(); /* send any left over data */ sound_send_wave_data_chunk(g_buffer, g_buf_index); @@ -282,42 +411,45 @@ sound_send_close(void) } /*****************************************************************************/ +/* from client */ static int APP_CC sound_process_training(struct stream *s, int size) { int time_diff; - print_got_here(); - time_diff = g_time2() - g_training_sent_time; LOG(0, ("sound_process_training: round trip time %u", time_diff)); return 0; } /*****************************************************************************/ +/* from client */ static int APP_CC sound_process_wave_confirm(struct stream *s, int size) { int wTimeStamp; int cConfirmedBlockNo; + int time; + int time_diff; - print_got_here(); - + time = g_time2(); in_uint16_le(s, wTimeStamp); in_uint8(s, cConfirmedBlockNo); + time_diff = time - g_sent_time[cConfirmedBlockNo]; - LOG(10, ("sound_process_wave_confirm: wTimeStamp %d, cConfirmedBlockNo %d", - wTimeStamp, cConfirmedBlockNo)); + LOG(10, ("sound_process_wave_confirm: wTimeStamp %d, " + "cConfirmedBlockNo %d time diff %d", + wTimeStamp, cConfirmedBlockNo, time_diff)); return 0; } /*****************************************************************************/ +/* process message in from the audio source, eg pulse, alsa + on it's way to the client */ static int APP_CC process_pcm_message(int id, int size, struct stream *s) { - print_got_here(); - switch (id) { case 0: @@ -334,7 +466,7 @@ process_pcm_message(int id, int size, struct stream *s) } /*****************************************************************************/ -/* data coming in from audio source, eg pulse, alsa */ +/* data in from audio source, eg pulse, alsa */ static int DEFAULT_CC sound_trans_audio_data_in(struct trans *trans) { @@ -376,11 +508,11 @@ sound_trans_audio_data_in(struct trans *trans) } /*****************************************************************************/ +/* this is a connection in on the unix domain socket */ static int DEFAULT_CC sound_trans_audio_conn_in(struct trans *trans, struct trans *new_trans) { LOG(0, ("sound_trans_audio_conn_in:")); - print_got_here(); if (trans == 0) { @@ -410,8 +542,6 @@ sound_trans_audio_conn_in(struct trans *trans, struct trans *new_trans) return 0; } -#define CHANSRV_PORT_STR "/tmp/.xrdp/xrdp_chansrv_audio_socket_%d" - /*****************************************************************************/ int APP_CC sound_init(void) @@ -419,7 +549,6 @@ sound_init(void) char port[256]; int error; - print_got_here(); LOG(0, ("sound_init:")); sound_send_server_formats(); @@ -447,8 +576,6 @@ sound_init(void) int APP_CC sound_deinit(void) { - print_got_here(); - if (g_audio_l_trans != 0) { trans_delete(g_audio_l_trans); @@ -465,7 +592,7 @@ sound_deinit(void) } /*****************************************************************************/ -/* data in from client ( clinet -> xrdp -> chansrv ) */ +/* data in from client ( client -> xrdp -> chansrv ) */ int APP_CC sound_data_in(struct stream *s, int chan_id, int chan_flags, int length, int total_length) @@ -473,8 +600,6 @@ sound_data_in(struct stream *s, int chan_id, int chan_flags, int length, int code; int size; - print_got_here(); - in_uint8(s, code); in_uint8s(s, 1); in_uint16_le(s, size); @@ -544,6 +669,8 @@ sound_check_wait_objs(void) #if defined(XRDP_SIMPLESOUND) +#define AUDIO_BUF_SIZE 2048 + static int DEFAULT_CC sttrans_data_in(struct trans *self) { |