mirror of
https://github.com/alsa-project/alsa-utils
synced 2024-11-08 23:05:42 +01:00
aplay/arecord: change the interrupt handling using snd_pcm_abort()
It is required (exclude the fatal SIGABRT) to call snd_pcm_close() and the end of work (outside of the interrupt handler). Use new snd_pcm_abort() function to inform alsa-lib to not ignore EINTR and move the in_aborting variable to the global scope to be checked in the i/o loops. Signed-off-by: Jaroslav Kysela <perex@perex.cz>
This commit is contained in:
parent
ffaff06849
commit
1d0042d7e9
1 changed files with 15 additions and 24 deletions
|
@ -107,6 +107,7 @@ static snd_pcm_stream_t stream = SND_PCM_STREAM_PLAYBACK;
|
|||
static int mmap_flag = 0;
|
||||
static int interleaved = 1;
|
||||
static int nonblock = 0;
|
||||
static int in_aborting = 0;
|
||||
static u_char *audiobuf = NULL;
|
||||
static snd_pcm_uframes_t chunk_size = 0;
|
||||
static unsigned period_time = 0;
|
||||
|
@ -383,8 +384,6 @@ static void prg_exit(int code)
|
|||
|
||||
static void signal_handler(int sig)
|
||||
{
|
||||
static int in_aborting;
|
||||
|
||||
if (in_aborting)
|
||||
return;
|
||||
|
||||
|
@ -393,22 +392,14 @@ static void signal_handler(int sig)
|
|||
putchar('\n');
|
||||
if (!quiet_mode)
|
||||
fprintf(stderr, _("Aborted by signal %s...\n"), strsignal(sig));
|
||||
if (stream == SND_PCM_STREAM_CAPTURE) {
|
||||
if (fmt_rec_table[file_type].end) {
|
||||
fmt_rec_table[file_type].end(fd);
|
||||
fd = -1;
|
||||
}
|
||||
stream = -1;
|
||||
}
|
||||
if (fd > 1) {
|
||||
close(fd);
|
||||
fd = -1;
|
||||
}
|
||||
if (handle && sig != SIGABRT) {
|
||||
snd_pcm_close(handle);
|
||||
if (handle)
|
||||
snd_pcm_abort(handle);
|
||||
if (sig == SIGABRT) {
|
||||
/* do not call snd_pcm_close() and abort immediately */
|
||||
handle = NULL;
|
||||
prg_exit(EXIT_FAILURE);
|
||||
}
|
||||
prg_exit(EXIT_FAILURE);
|
||||
signal(sig, signal_handler);
|
||||
}
|
||||
|
||||
/* call on SIGUSR1 signal. */
|
||||
|
@ -825,7 +816,7 @@ static ssize_t safe_read(int fd, void *buf, size_t count)
|
|||
{
|
||||
ssize_t result = 0, res;
|
||||
|
||||
while (count > 0) {
|
||||
while (count > 0 && !in_aborting) {
|
||||
if ((res = read(fd, buf, count)) == 0)
|
||||
break;
|
||||
if (res < 0)
|
||||
|
@ -2133,7 +2124,7 @@ static void voc_write_silence(unsigned x)
|
|||
return; /* not fatal error */
|
||||
}
|
||||
snd_pcm_format_set_silence(hwparams.format, buf, chunk_size * hwparams.channels);
|
||||
while (x > 0) {
|
||||
while (x > 0 && !in_aborting) {
|
||||
l = x;
|
||||
if (l > chunk_size)
|
||||
l = chunk_size;
|
||||
|
@ -2205,7 +2196,7 @@ static void voc_play(int fd, int ofs, char *name)
|
|||
set_params();
|
||||
|
||||
in_buffer = nextblock = 0;
|
||||
while (1) {
|
||||
while (!in_aborting) {
|
||||
Fill_the_buffer: /* need this for repeat */
|
||||
if (in_buffer < 32) {
|
||||
/* move the rest of buffer to pos 0 and fill the buf up */
|
||||
|
@ -2653,7 +2644,7 @@ static void playback_go(int fd, size_t loaded, off64_t count, int rtype, char *n
|
|||
header(rtype, name);
|
||||
set_params();
|
||||
|
||||
while (loaded > chunk_bytes && written < count) {
|
||||
while (loaded > chunk_bytes && written < count && !in_aborting) {
|
||||
if (pcm_write(audiobuf + written, chunk_size) <= 0)
|
||||
return;
|
||||
written += chunk_bytes;
|
||||
|
@ -2663,7 +2654,7 @@ static void playback_go(int fd, size_t loaded, off64_t count, int rtype, char *n
|
|||
memmove(audiobuf, audiobuf + written, loaded);
|
||||
|
||||
l = loaded;
|
||||
while (written < count) {
|
||||
while (written < count && !in_aborting) {
|
||||
do {
|
||||
c = count - written;
|
||||
if (c > chunk_bytes)
|
||||
|
@ -3003,7 +2994,7 @@ static void capture(char *orig_name)
|
|||
|
||||
/* capture */
|
||||
fdcount = 0;
|
||||
while (rest > 0 && recycle_capture_file == 0) {
|
||||
while (rest > 0 && recycle_capture_file == 0 && !in_aborting) {
|
||||
size_t c = (rest <= (off64_t)chunk_bytes) ?
|
||||
(size_t)rest : chunk_bytes;
|
||||
size_t f = c * 8 / bits_per_frame;
|
||||
|
@ -3055,7 +3046,7 @@ static void playbackv_go(int* fds, unsigned int channels, size_t loaded, off64_t
|
|||
for (channel = 0; channel < channels; ++channel)
|
||||
bufs[channel] = audiobuf + vsize * channel;
|
||||
|
||||
while (count > 0) {
|
||||
while (count > 0 && !in_aborting) {
|
||||
size_t c = 0;
|
||||
size_t expected = count / channels;
|
||||
if (expected > vsize)
|
||||
|
@ -3104,7 +3095,7 @@ static void capturev_go(int* fds, unsigned int channels, off64_t count, int rtyp
|
|||
for (channel = 0; channel < channels; ++channel)
|
||||
bufs[channel] = audiobuf + vsize * channel;
|
||||
|
||||
while (count > 0) {
|
||||
while (count > 0 && !in_aborting) {
|
||||
size_t rv;
|
||||
c = count;
|
||||
if (c > chunk_bytes)
|
||||
|
|
Loading…
Reference in a new issue