More diagnostics. Fixed shm use.

This commit is contained in:
Abramo Bagnara 2000-10-14 19:43:14 +00:00
parent a380edd64f
commit 03f9565ef8
8 changed files with 157 additions and 130 deletions

View file

@ -53,7 +53,7 @@ char *command;
} while (0) } while (0)
#endif #endif
#define SYSERR(string) ERROR(string ": %s", strerror(errno)) #define SYSERROR(string) ERROR(string ": %s", strerror(errno))
int make_local_socket(const char *filename) int make_local_socket(const char *filename)
{ {
@ -65,7 +65,7 @@ int make_local_socket(const char *filename)
sock = socket(PF_LOCAL, SOCK_STREAM, 0); sock = socket(PF_LOCAL, SOCK_STREAM, 0);
if (sock < 0) { if (sock < 0) {
int result = -errno; int result = -errno;
SYSERR("socket"); SYSERROR("socket failed");
return result; return result;
} }
@ -76,7 +76,7 @@ int make_local_socket(const char *filename)
if (bind(sock, (struct sockaddr *) addr, size) < 0) { if (bind(sock, (struct sockaddr *) addr, size) < 0) {
int result = -errno; int result = -errno;
SYSERR("bind"); SYSERROR("bind failed");
return result; return result;
} }
@ -91,7 +91,7 @@ int make_inet_socket(int port)
sock = socket(PF_INET, SOCK_STREAM, 0); sock = socket(PF_INET, SOCK_STREAM, 0);
if (sock < 0) { if (sock < 0) {
int result = -errno; int result = -errno;
SYSERR("socket"); SYSERROR("socket failed");
return result; return result;
} }
@ -101,7 +101,7 @@ int make_inet_socket(int port)
if (bind(sock, (struct sockaddr *) &addr, sizeof(addr)) < 0) { if (bind(sock, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
int result = -errno; int result = -errno;
SYSERR("bind"); SYSERROR("bind failed");
return result; return result;
} }
@ -135,7 +135,7 @@ int send_fd(int socket, void *data, size_t len, int fd)
ret = sendmsg(socket, &msghdr, 0 ); ret = sendmsg(socket, &msghdr, 0 );
if (ret < 0) { if (ret < 0) {
SYSERR("sendmsg"); SYSERROR("sendmsg failed");
return -errno; return -errno;
} }
return ret; return ret;
@ -253,13 +253,13 @@ int pcm_handler(waiter_t *waiter, unsigned short events)
if (events & POLLIN) { if (events & POLLIN) {
n = write(client->poll_fd, buf, 1); n = write(client->poll_fd, buf, 1);
if (n != 1) { if (n != 1) {
SYSERR("write"); SYSERROR("write failed");
return -errno; return -errno;
} }
} else if (events & POLLOUT) { } else if (events & POLLOUT) {
n = read(client->poll_fd, buf, 1); n = read(client->poll_fd, buf, 1);
if (n != 1) { if (n != 1) {
SYSERR("read"); SYSERROR("read failed");
return -errno; return -errno;
} }
} }
@ -283,7 +283,7 @@ int pcm_shm_open(client_t *client, int *cookie)
shmid = shmget(IPC_PRIVATE, PCM_SHM_SIZE, 0666); shmid = shmget(IPC_PRIVATE, PCM_SHM_SIZE, 0666);
if (shmid < 0) { if (shmid < 0) {
result = -errno; result = -errno;
SYSERR("shmget"); SYSERROR("shmget failed");
goto _err; goto _err;
} }
client->transport.shm.ctrl_id = shmid; client->transport.shm.ctrl_id = shmid;
@ -291,7 +291,7 @@ int pcm_shm_open(client_t *client, int *cookie)
if (client->transport.shm.ctrl == (void*) -1) { if (client->transport.shm.ctrl == (void*) -1) {
result = -errno; result = -errno;
shmctl(shmid, IPC_RMID, 0); shmctl(shmid, IPC_RMID, 0);
SYSERR("shmat"); SYSERROR("shmat failed");
goto _err; goto _err;
} }
*cookie = shmid; *cookie = shmid;
@ -314,14 +314,14 @@ int pcm_shm_close(client_t *client)
err = snd_pcm_close(client->device.pcm.handle); err = snd_pcm_close(client->device.pcm.handle);
ctrl->result = err; ctrl->result = err;
if (err < 0) if (err < 0)
SYSERR("snd_pcm_close"); ERROR("snd_pcm_close");
if (client->transport.shm.ctrl) { if (client->transport.shm.ctrl) {
err = shmdt((void *)client->transport.shm.ctrl); err = shmdt((void *)client->transport.shm.ctrl);
if (err < 0) if (err < 0)
SYSERR("shmdt"); SYSERROR("shmdt failed");
err = shmctl(client->transport.shm.ctrl_id, IPC_RMID, 0); err = shmctl(client->transport.shm.ctrl_id, IPC_RMID, 0);
if (err < 0) if (err < 0)
SYSERR("shmctl"); SYSERROR("shmctl IPC_RMID failed");
client->transport.shm.ctrl = 0; client->transport.shm.ctrl = 0;
} }
client->open = 0; client->open = 0;
@ -452,27 +452,12 @@ int pcm_shm_cmd(client_t *client)
} }
case SND_PCM_IOCTL_MMAP_INFO: case SND_PCM_IOCTL_MMAP_INFO:
{ {
snd_pcm_mmap_info_t *i;
unsigned int index = ctrl->u.mmap_info.index; unsigned int index = ctrl->u.mmap_info.index;
snd_pcm_mmap_info_t *i = &pcm->mmap_info[index];
if (index >= pcm->mmap_info_count) { if (index >= pcm->mmap_info_count) {
ctrl->result = -EINVAL; ctrl->result = -EINVAL;
break; break;
} }
i = &pcm->mmap_info[index];
if (i->type == SND_PCM_MMAP_USER) {
void *ptr;
int shmid = shmget(IPC_PRIVATE, i->size, 0666);
if (shmid < 0) {
SYSERR("shmget");
return -EINVAL;
}
ptr = shmat(shmid, i->addr, 0);
if (ptr != i->addr) {
SYSERR("shmat");
return -EINVAL;
}
i->u.user.shmid = shmid;
}
ctrl->u.mmap_info = *i; ctrl->u.mmap_info = *i;
ctrl->u.mmap_info.index = index; ctrl->u.mmap_info.index = index;
ctrl->result = 0; ctrl->result = 0;
@ -526,7 +511,7 @@ int ctl_handler(waiter_t *waiter, unsigned short events)
if (events & POLLIN) { if (events & POLLIN) {
n = write(client->poll_fd, buf, 1); n = write(client->poll_fd, buf, 1);
if (n != 1) { if (n != 1) {
SYSERR("write"); SYSERROR("write failed");
return -errno; return -errno;
} }
} }
@ -550,7 +535,7 @@ int ctl_shm_open(client_t *client, int *cookie)
shmid = shmget(IPC_PRIVATE, CTL_SHM_SIZE, 0666); shmid = shmget(IPC_PRIVATE, CTL_SHM_SIZE, 0666);
if (shmid < 0) { if (shmid < 0) {
result = -errno; result = -errno;
SYSERR("shmget"); SYSERROR("shmget failed");
goto _err; goto _err;
} }
client->transport.shm.ctrl_id = shmid; client->transport.shm.ctrl_id = shmid;
@ -558,7 +543,7 @@ int ctl_shm_open(client_t *client, int *cookie)
if (!client->transport.shm.ctrl) { if (!client->transport.shm.ctrl) {
result = -errno; result = -errno;
shmctl(shmid, IPC_RMID, 0); shmctl(shmid, IPC_RMID, 0);
SYSERR("shmat"); SYSERROR("shmat failed");
goto _err; goto _err;
} }
*cookie = shmid; *cookie = shmid;
@ -583,14 +568,14 @@ int ctl_shm_close(client_t *client)
err = snd_ctl_close(client->device.control.handle); err = snd_ctl_close(client->device.control.handle);
ctrl->result = err; ctrl->result = err;
if (err < 0) if (err < 0)
SYSERR("snd_ctl_close"); ERROR("snd_ctl_close");
if (client->transport.shm.ctrl) { if (client->transport.shm.ctrl) {
err = shmdt((void *)client->transport.shm.ctrl); err = shmdt((void *)client->transport.shm.ctrl);
if (err < 0) if (err < 0)
SYSERR("shmdt"); SYSERROR("shmdt failed");
err = shmctl(client->transport.shm.ctrl_id, IPC_RMID, 0); err = shmctl(client->transport.shm.ctrl_id, IPC_RMID, 0);
if (err < 0) if (err < 0)
SYSERR("shmctl"); SYSERROR("shmctl failed");
client->transport.shm.ctrl = 0; client->transport.shm.ctrl = 0;
} }
client->open = 0; client->open = 0;
@ -679,7 +664,7 @@ int snd_client_open(client_t *client)
memset(&ans, 0, sizeof(ans)); memset(&ans, 0, sizeof(ans));
err = read(client->ctrl_fd, &req, sizeof(req)); err = read(client->ctrl_fd, &req, sizeof(req));
if (err < 0) { if (err < 0) {
SYSERR("read"); SYSERROR("read failed");
exit(1); exit(1);
} }
if (err != sizeof(req)) { if (err != sizeof(req)) {
@ -689,7 +674,7 @@ int snd_client_open(client_t *client)
name = alloca(req.namelen); name = alloca(req.namelen);
err = read(client->ctrl_fd, name, req.namelen); err = read(client->ctrl_fd, name, req.namelen);
if (err < 0) { if (err < 0) {
SYSERR("read"); SYSERROR("read failed");
exit(1); exit(1);
} }
if (err != req.namelen) { if (err != req.namelen) {
@ -738,7 +723,7 @@ int snd_client_open(client_t *client)
_answer: _answer:
err = write(client->ctrl_fd, &ans, sizeof(ans)); err = write(client->ctrl_fd, &ans, sizeof(ans));
if (err != sizeof(ans)) { if (err != sizeof(ans)) {
SYSERR("write"); SYSERROR("write failed");
exit(1); exit(1);
} }
return 0; return 0;
@ -834,7 +819,7 @@ int local_handler(waiter_t *waiter, unsigned short events ATTRIBUTE_UNUSED)
sock = accept(waiter->fd, 0, 0); sock = accept(waiter->fd, 0, 0);
if (sock < 0) { if (sock < 0) {
int result = -errno; int result = -errno;
SYSERR("accept"); SYSERROR("accept failed");
return result; return result;
} else { } else {
client_t *client = calloc(1, sizeof(*client)); client_t *client = calloc(1, sizeof(*client));
@ -853,7 +838,7 @@ int inet_handler(waiter_t *waiter, unsigned short events ATTRIBUTE_UNUSED)
sock = accept(waiter->fd, 0, 0); sock = accept(waiter->fd, 0, 0);
if (sock < 0) { if (sock < 0) {
int result = -errno; int result = -errno;
SYSERR("accept"); SYSERROR("accept failed");
return result; return result;
} else { } else {
inet_pending_t *pending = calloc(1, sizeof(*pending)); inet_pending_t *pending = calloc(1, sizeof(*pending));
@ -878,12 +863,12 @@ int server(char *sockname, int port)
return sock; return sock;
if (fcntl(sock, F_SETFL, O_NONBLOCK) < 0) { if (fcntl(sock, F_SETFL, O_NONBLOCK) < 0) {
int result = -errno; int result = -errno;
SYSERR("fcntl"); SYSERROR("fcntl O_NONBLOCK failed");
return result; return result;
} }
if (listen(sock, 4) < 0) { if (listen(sock, 4) < 0) {
int result = -errno; int result = -errno;
SYSERR("listen"); SYSERROR("listen failed");
return result; return result;
} }
add_waiter(sock, POLLIN, local_handler, NULL); add_waiter(sock, POLLIN, local_handler, NULL);
@ -894,12 +879,12 @@ int server(char *sockname, int port)
return sock; return sock;
if (fcntl(sock, F_SETFL, O_NONBLOCK) < 0) { if (fcntl(sock, F_SETFL, O_NONBLOCK) < 0) {
int result = -errno; int result = -errno;
SYSERR("fcntl"); SYSERROR("fcntl failed");
return result; return result;
} }
if (listen(sock, 4) < 0) { if (listen(sock, 4) < 0) {
int result = -errno; int result = -errno;
SYSERR("listen"); SYSERROR("listen failed");
return result; return result;
} }
add_waiter(sock, POLLIN, inet_handler, NULL); add_waiter(sock, POLLIN, inet_handler, NULL);
@ -912,7 +897,7 @@ int server(char *sockname, int port)
err = poll(pollfds, pollfds_count, -1); err = poll(pollfds, pollfds_count, -1);
} while (err == 0); } while (err == 0);
if (err < 0) { if (err < 0) {
SYSERR("poll"); SYSERROR("poll failed");
continue; continue;
} }
@ -926,7 +911,7 @@ int server(char *sockname, int port)
continue; continue;
err = w->handler(w, pfd->revents); err = w->handler(w, pfd->revents);
if (err < 0) if (err < 0)
SYSERR("handler"); ERROR("waiter handler failed");
} }
} }
} }

View file

@ -119,7 +119,7 @@ typedef enum {
SND_PCM_TYPE_LBSERVER, SND_PCM_TYPE_LBSERVER,
} snd_pcm_type_t; } snd_pcm_type_t;
extern void snd_pcm_error(const char *file, int line, const char *function, const char *fmt, ...) __attribute__ ((weak, format (printf, 4, 5))); extern void snd_pcm_error(const char *file, int line, const char *function, int err, const char *fmt, ...) __attribute__ ((weak, format (printf, 5, 6)));
int snd_pcm_open(snd_pcm_t **pcm, char *name, int snd_pcm_open(snd_pcm_t **pcm, char *name,
int stream, int mode); int stream, int mode);

View file

@ -295,8 +295,10 @@ int snd_pcm_link(snd_pcm_t *pcm1, snd_pcm_t *pcm2)
int fd2 = snd_pcm_link_descriptor(pcm2); int fd2 = snd_pcm_link_descriptor(pcm2);
if (fd1 < 0 || fd2 < 0) if (fd1 < 0 || fd2 < 0)
return -ENOSYS; return -ENOSYS;
if (ioctl(fd1, SND_PCM_IOCTL_LINK, fd2) < 0) if (ioctl(fd1, SND_PCM_IOCTL_LINK, fd2) < 0) {
SYSERR("SND_PCM_IOCTL_LINK failed");
return -errno; return -errno;
}
return 0; return 0;
} }
@ -309,11 +311,12 @@ int snd_pcm_unlink(snd_pcm_t *pcm)
fd = snd_pcm_poll_descriptor(pcm); fd = snd_pcm_poll_descriptor(pcm);
break; break;
default: default:
errno = -ENOSYS; return -ENOSYS;
return -1;
} }
if (ioctl(fd, SND_PCM_IOCTL_UNLINK) < 0) if (ioctl(fd, SND_PCM_IOCTL_UNLINK) < 0) {
SYSERR("SND_PCM_IOCTL_UNLINK failed");
return -errno; return -errno;
}
return 0; return 0;
} }
@ -1047,12 +1050,14 @@ ssize_t snd_pcm_write_areas(snd_pcm_t *pcm, snd_pcm_channel_area_t *areas,
return err; return err;
} }
void snd_pcm_error(const char *file, int line, const char *function, const char *fmt, ...) void snd_pcm_error(const char *file, int line, const char *function, int err, const char *fmt, ...)
{ {
va_list arg; va_list arg;
va_start(arg, fmt); va_start(arg, fmt);
fprintf(stderr, "ALSA PCM lib %s:%i:(%s) ", file, line, function); fprintf(stderr, "ALSA PCM lib %s:%i:(%s) ", file, line, function);
vfprintf(stderr, fmt, arg); vfprintf(stderr, fmt, arg);
if (err)
fprintf(stderr, ": %s", snd_strerror(err));
putc('\n', stderr); putc('\n', stderr);
va_end(arg); va_end(arg);
} }

View file

@ -347,8 +347,10 @@ int snd_pcm_file_open(snd_pcm_t **pcmp, char *name, char *fname, int fd, snd_pcm
assert(pcmp && slave); assert(pcmp && slave);
if (fname) { if (fname) {
fd = open(fname, O_WRONLY|O_CREAT, 0666); fd = open(fname, O_WRONLY|O_CREAT, 0666);
if (fd < 0) if (fd < 0) {
SYSERR("open %s failed", fname);
return -errno; return -errno;
}
} }
file = calloc(1, sizeof(snd_pcm_file_t)); file = calloc(1, sizeof(snd_pcm_file_t));
if (!file) { if (!file) {

View file

@ -28,6 +28,7 @@
#include <fcntl.h> #include <fcntl.h>
#include <sys/ioctl.h> #include <sys/ioctl.h>
#include <sys/mman.h> #include <sys/mman.h>
#include <sys/shm.h>
#include "pcm_local.h" #include "pcm_local.h"
#ifndef F_SETSIG #ifndef F_SETSIG
@ -52,7 +53,7 @@ static int snd_pcm_hw_nonblock(snd_pcm_t *pcm, int nonblock)
int fd = hw->fd; int fd = hw->fd;
if ((flags = fcntl(fd, F_GETFL)) < 0) { if ((flags = fcntl(fd, F_GETFL)) < 0) {
ERR("F_GETFL failed"); SYSERR("F_GETFL failed");
return -errno; return -errno;
} }
if (nonblock) if (nonblock)
@ -60,7 +61,7 @@ static int snd_pcm_hw_nonblock(snd_pcm_t *pcm, int nonblock)
else else
flags &= ~O_NONBLOCK; flags &= ~O_NONBLOCK;
if (fcntl(fd, F_SETFL, flags) < 0) { if (fcntl(fd, F_SETFL, flags) < 0) {
ERR("F_SETFL for O_NONBLOCK failed"); SYSERR("F_SETFL for O_NONBLOCK failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -73,7 +74,7 @@ static int snd_pcm_hw_async(snd_pcm_t *pcm, int sig, pid_t pid)
int fd = hw->fd; int fd = hw->fd;
if ((flags = fcntl(fd, F_GETFL)) < 0) { if ((flags = fcntl(fd, F_GETFL)) < 0) {
ERR("F_GETFL failed"); SYSERR("F_GETFL failed");
return -errno; return -errno;
} }
if (sig >= 0) if (sig >= 0)
@ -81,7 +82,7 @@ static int snd_pcm_hw_async(snd_pcm_t *pcm, int sig, pid_t pid)
else else
flags &= ~O_ASYNC; flags &= ~O_ASYNC;
if (fcntl(fd, F_SETFL, flags) < 0) { if (fcntl(fd, F_SETFL, flags) < 0) {
ERR("F_SETFL for O_ASYNC failed"); SYSERR("F_SETFL for O_ASYNC failed");
return -errno; return -errno;
} }
if (sig < 0) if (sig < 0)
@ -89,13 +90,13 @@ static int snd_pcm_hw_async(snd_pcm_t *pcm, int sig, pid_t pid)
if (sig == 0) if (sig == 0)
sig = SIGIO; sig = SIGIO;
if (fcntl(fd, F_SETSIG, sig) < 0) { if (fcntl(fd, F_SETSIG, sig) < 0) {
ERR("F_SETSIG failed"); SYSERR("F_SETSIG failed");
return -errno; return -errno;
} }
if (pid == 0) if (pid == 0)
pid = getpid(); pid = getpid();
if (fcntl(fd, F_SETOWN, pid) < 0) { if (fcntl(fd, F_SETOWN, pid) < 0) {
ERR("F_SETOWN failed"); SYSERR("F_SETOWN failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -106,7 +107,7 @@ static int snd_pcm_hw_info(snd_pcm_t *pcm, snd_pcm_info_t * info)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_INFO, info) < 0) { if (ioctl(fd, SND_PCM_IOCTL_INFO, info) < 0) {
ERR("SND_PCM_IOCTL_INFO failed"); SYSERR("SND_PCM_IOCTL_INFO failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -117,7 +118,7 @@ static int snd_pcm_hw_params_info(snd_pcm_t *pcm, snd_pcm_params_info_t * info)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_PARAMS_INFO, info) < 0) { if (ioctl(fd, SND_PCM_IOCTL_PARAMS_INFO, info) < 0) {
ERR("SND_PCM_IOCTL_PARAMS_INFO failed"); SYSERR("SND_PCM_IOCTL_PARAMS_INFO failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -128,7 +129,7 @@ static int snd_pcm_hw_params(snd_pcm_t *pcm, snd_pcm_params_t * params)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_PARAMS, params) < 0) { if (ioctl(fd, SND_PCM_IOCTL_PARAMS, params) < 0) {
ERR("SND_PCM_IOCTL_PARAMS failed"); SYSERR("SND_PCM_IOCTL_PARAMS failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -139,7 +140,7 @@ static int snd_pcm_hw_setup(snd_pcm_t *pcm, snd_pcm_setup_t * setup)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_SETUP, setup) < 0) { if (ioctl(fd, SND_PCM_IOCTL_SETUP, setup) < 0) {
ERR("SND_PCM_IOCTL_SETUP failed"); SYSERR("SND_PCM_IOCTL_SETUP failed");
return -errno; return -errno;
} }
if (setup->mmap_shape == SND_PCM_MMAP_UNSPECIFIED) { if (setup->mmap_shape == SND_PCM_MMAP_UNSPECIFIED) {
@ -156,7 +157,7 @@ static int snd_pcm_hw_channel_info(snd_pcm_t *pcm, snd_pcm_channel_info_t * info
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_CHANNEL_INFO, info) < 0) { if (ioctl(fd, SND_PCM_IOCTL_CHANNEL_INFO, info) < 0) {
ERR("SND_PCM_IOCTL_CHANNEL_INFO failed"); SYSERR("SND_PCM_IOCTL_CHANNEL_INFO failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -167,7 +168,7 @@ static int snd_pcm_hw_channel_params(snd_pcm_t *pcm, snd_pcm_channel_params_t *
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_CHANNEL_PARAMS, params) < 0) { if (ioctl(fd, SND_PCM_IOCTL_CHANNEL_PARAMS, params) < 0) {
ERR("SND_PCM_IOCTL_CHANNEL_PARAMS failed"); SYSERR("SND_PCM_IOCTL_CHANNEL_PARAMS failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -178,7 +179,7 @@ static int snd_pcm_hw_channel_setup(snd_pcm_t *pcm, snd_pcm_channel_setup_t * se
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_CHANNEL_SETUP, setup) < 0) { if (ioctl(fd, SND_PCM_IOCTL_CHANNEL_SETUP, setup) < 0) {
ERR("SND_PCM_IOCTL_CHANNEL_SETUP failed"); SYSERR("SND_PCM_IOCTL_CHANNEL_SETUP failed");
return -errno; return -errno;
} }
if (!pcm->mmap_info) if (!pcm->mmap_info)
@ -206,7 +207,7 @@ static int snd_pcm_hw_status(snd_pcm_t *pcm, snd_pcm_status_t * status)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_STATUS, status) < 0) { if (ioctl(fd, SND_PCM_IOCTL_STATUS, status) < 0) {
ERR("SND_PCM_IOCTL_STATUS failed"); SYSERR("SND_PCM_IOCTL_STATUS failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -223,7 +224,7 @@ static int snd_pcm_hw_delay(snd_pcm_t *pcm, ssize_t *delayp)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_DELAY, delayp) < 0) { if (ioctl(fd, SND_PCM_IOCTL_DELAY, delayp) < 0) {
ERR("SND_PCM_IOCTL_DELAY failed"); SYSERR("SND_PCM_IOCTL_DELAY failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -234,7 +235,7 @@ static int snd_pcm_hw_prepare(snd_pcm_t *pcm)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_PREPARE) < 0) { if (ioctl(fd, SND_PCM_IOCTL_PREPARE) < 0) {
ERR("SND_PCM_IOCTL_PREPARE failed"); SYSERR("SND_PCM_IOCTL_PREPARE failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -245,7 +246,7 @@ static int snd_pcm_hw_start(snd_pcm_t *pcm)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_START) < 0) { if (ioctl(fd, SND_PCM_IOCTL_START) < 0) {
ERR("SND_PCM_IOCTL_START failed"); SYSERR("SND_PCM_IOCTL_START failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -256,7 +257,7 @@ static int snd_pcm_hw_drop(snd_pcm_t *pcm)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_DROP) < 0) { if (ioctl(fd, SND_PCM_IOCTL_DROP) < 0) {
ERR("SND_PCM_IOCTL_DROP failed"); SYSERR("SND_PCM_IOCTL_DROP failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -267,7 +268,7 @@ static int snd_pcm_hw_drain(snd_pcm_t *pcm)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_DRAIN) < 0) { if (ioctl(fd, SND_PCM_IOCTL_DRAIN) < 0) {
ERR("SND_PCM_IOCTL_DRAIN failed"); // SYSERR("SND_PCM_IOCTL_DRAIN failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -278,7 +279,7 @@ static int snd_pcm_hw_pause(snd_pcm_t *pcm, int enable)
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
int fd = hw->fd; int fd = hw->fd;
if (ioctl(fd, SND_PCM_IOCTL_PAUSE, enable) < 0) { if (ioctl(fd, SND_PCM_IOCTL_PAUSE, enable) < 0) {
ERR("SND_PCM_IOCTL_PAUSE failed"); SYSERR("SND_PCM_IOCTL_PAUSE failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -365,7 +366,7 @@ static int snd_pcm_hw_mmap_status(snd_pcm_t *pcm)
ptr = mmap(NULL, sizeof(snd_pcm_mmap_status_t), PROT_READ, MAP_FILE|MAP_SHARED, ptr = mmap(NULL, sizeof(snd_pcm_mmap_status_t), PROT_READ, MAP_FILE|MAP_SHARED,
hw->fd, SND_PCM_MMAP_OFFSET_STATUS); hw->fd, SND_PCM_MMAP_OFFSET_STATUS);
if (ptr == MAP_FAILED || ptr == NULL) { if (ptr == MAP_FAILED || ptr == NULL) {
ERR("status mmap failed"); SYSERR("status mmap failed");
return -errno; return -errno;
} }
hw->mmap_status = ptr; hw->mmap_status = ptr;
@ -380,7 +381,7 @@ static int snd_pcm_hw_mmap_control(snd_pcm_t *pcm)
ptr = mmap(NULL, sizeof(snd_pcm_mmap_control_t), PROT_READ|PROT_WRITE, MAP_FILE|MAP_SHARED, ptr = mmap(NULL, sizeof(snd_pcm_mmap_control_t), PROT_READ|PROT_WRITE, MAP_FILE|MAP_SHARED,
hw->fd, SND_PCM_MMAP_OFFSET_CONTROL); hw->fd, SND_PCM_MMAP_OFFSET_CONTROL);
if (ptr == MAP_FAILED || ptr == NULL) { if (ptr == MAP_FAILED || ptr == NULL) {
ERR("control mmap failed"); SYSERR("control mmap failed");
return -errno; return -errno;
} }
hw->mmap_control = ptr; hw->mmap_control = ptr;
@ -391,35 +392,41 @@ static int snd_pcm_hw_mmap_control(snd_pcm_t *pcm)
static int snd_pcm_hw_mmap(snd_pcm_t *pcm) static int snd_pcm_hw_mmap(snd_pcm_t *pcm)
{ {
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
pcm->mmap_info = calloc(1, sizeof(*pcm->mmap_info)); snd_pcm_mmap_info_t *i = calloc(1, sizeof(*i));
if (!pcm->mmap_info) if (!i)
return -ENOMEM; return -ENOMEM;
pcm->mmap_info_count = 1;
if (pcm->setup.mmap_shape == SND_PCM_MMAP_UNSPECIFIED) { if (pcm->setup.mmap_shape == SND_PCM_MMAP_UNSPECIFIED) {
pcm->mmap_info->type = SND_PCM_MMAP_USER; i->type = SND_PCM_MMAP_USER;
pcm->mmap_info->size = snd_pcm_frames_to_bytes(pcm, pcm->setup.buffer_size); i->size = snd_pcm_frames_to_bytes(pcm, pcm->setup.buffer_size);
pcm->mmap_info->addr = valloc(pcm->mmap_info->size); i->u.user.shmid = shmget(IPC_PRIVATE, i->size, 0666);
if (!pcm->mmap_info->addr) { if (i->u.user.shmid < 0) {
free(pcm->mmap_info); SYSERR("shmget failed");
pcm->mmap_info = 0; free(i);
return -ENOMEM; return -errno;
}
i->addr = shmat(i->u.user.shmid, 0, 0);
if (i->addr == (void*) -1) {
SYSERR("shmat failed");
free(i);
return -errno;
} }
} else { } else {
pcm->mmap_info->type = SND_PCM_MMAP_KERNEL; i->type = SND_PCM_MMAP_KERNEL;
pcm->mmap_info->size = pcm->setup.mmap_bytes; i->size = pcm->setup.mmap_bytes;
pcm->mmap_info->addr = mmap(NULL, pcm->setup.mmap_bytes, i->addr = mmap(NULL, pcm->setup.mmap_bytes,
PROT_WRITE | PROT_READ, PROT_WRITE | PROT_READ,
MAP_FILE|MAP_SHARED, MAP_FILE|MAP_SHARED,
hw->fd, SND_PCM_MMAP_OFFSET_DATA); hw->fd, SND_PCM_MMAP_OFFSET_DATA);
if (pcm->mmap_info->addr == MAP_FAILED || if (i->addr == MAP_FAILED ||
pcm->mmap_info->addr == NULL) { i->addr == NULL) {
ERR("data mmap failed"); SYSERR("data mmap failed");
free(pcm->mmap_info); free(i);
pcm->mmap_info = 0;
return -errno; return -errno;
} }
pcm->mmap_info->u.kernel.fd = hw->fd; i->u.kernel.fd = hw->fd;
} }
pcm->mmap_info = i;
pcm->mmap_info_count = 1;
return 0; return 0;
} }
@ -427,7 +434,7 @@ static int snd_pcm_hw_munmap_status(snd_pcm_t *pcm)
{ {
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
if (munmap((void*)hw->mmap_status, sizeof(*hw->mmap_status)) < 0) { if (munmap((void*)hw->mmap_status, sizeof(*hw->mmap_status)) < 0) {
ERR("status munmap failed"); SYSERR("status munmap failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -437,7 +444,7 @@ static int snd_pcm_hw_munmap_control(snd_pcm_t *pcm)
{ {
snd_pcm_hw_t *hw = pcm->private; snd_pcm_hw_t *hw = pcm->private;
if (munmap(hw->mmap_control, sizeof(*hw->mmap_control)) < 0) { if (munmap(hw->mmap_control, sizeof(*hw->mmap_control)) < 0) {
ERR("control munmap failed"); SYSERR("control munmap failed");
return -errno; return -errno;
} }
return 0; return 0;
@ -445,13 +452,21 @@ static int snd_pcm_hw_munmap_control(snd_pcm_t *pcm)
static int snd_pcm_hw_munmap(snd_pcm_t *pcm) static int snd_pcm_hw_munmap(snd_pcm_t *pcm)
{ {
if (pcm->setup.mmap_shape == SND_PCM_MMAP_UNSPECIFIED) if (pcm->setup.mmap_shape == SND_PCM_MMAP_UNSPECIFIED) {
free(pcm->mmap_info->addr); if (shmdt(pcm->mmap_info->addr) < 0) {
else SYSERR("shmdt failed");
if (munmap(pcm->mmap_info->addr, pcm->mmap_info->size) < 0) {
ERR("data munmap failed");
return -errno; return -errno;
} }
if (shmctl(pcm->mmap_info->u.user.shmid, IPC_RMID, 0) < 0) {
SYSERR("shmctl IPC_RMID failed");
return -errno;
}
} else {
if (munmap(pcm->mmap_info->addr, pcm->mmap_info->size) < 0) {
SYSERR("data munmap failed");
return -errno;
}
}
pcm->mmap_info_count = 0; pcm->mmap_info_count = 0;
free(pcm->mmap_info); free(pcm->mmap_info);
pcm->mmap_info = 0; pcm->mmap_info = 0;
@ -464,7 +479,7 @@ static int snd_pcm_hw_close(snd_pcm_t *pcm)
int fd = hw->fd; int fd = hw->fd;
free(hw); free(hw);
if (close(fd)) { if (close(fd)) {
ERR("close failed\n"); SYSERR("close failed\n");
return -errno; return -errno;
} }
snd_pcm_hw_munmap_status(pcm); snd_pcm_hw_munmap_status(pcm);
@ -608,6 +623,7 @@ int snd_pcm_hw_open_subdevice(snd_pcm_t **pcmp, int card, int device, int subdev
if ((fd = open(filename, fmode)) < 0) if ((fd = open(filename, fmode)) < 0)
return -errno; return -errno;
if (ioctl(fd, SND_PCM_IOCTL_PVERSION, &ver) < 0) { if (ioctl(fd, SND_PCM_IOCTL_PVERSION, &ver) < 0) {
SYSERR("SND_PCM_IOCTL_PVERSION failed");
ret = -errno; ret = -errno;
goto _err; goto _err;
} }
@ -618,6 +634,7 @@ int snd_pcm_hw_open_subdevice(snd_pcm_t **pcmp, int card, int device, int subdev
if (subdevice >= 0) { if (subdevice >= 0) {
memset(&info, 0, sizeof(info)); memset(&info, 0, sizeof(info));
if (ioctl(fd, SND_PCM_IOCTL_INFO, &info) < 0) { if (ioctl(fd, SND_PCM_IOCTL_INFO, &info) < 0) {
SYSERR("SND_PCM_IOCTL_INFO failed");
ret = -errno; ret = -errno;
goto _err; goto _err;
} }

View file

@ -27,9 +27,11 @@
#include "asoundlib.h" #include "asoundlib.h"
#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 95) #if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 95)
#define ERR(...) snd_pcm_error(__FILE__, __LINE__, __FUNCTION__, __VA_ARGS__) #define ERR(...) snd_pcm_error(__FILE__, __LINE__, __FUNCTION__, 0, __VA_ARGS__)
#define SYSERR(...) snd_pcm_error(__FILE__, __LINE__, __FUNCTION__, errno, __VA_ARGS__)
#else #else
#define ERR(args...) snd_pcm_error(__FILE__, __LINE__, __FUNCTION__, ##args) #define ERR(args...) snd_pcm_error(__FILE__, __LINE__, __FUNCTION__, 0, ##args)
#define SYSERR(args...) snd_pcm_error(__FILE__, __LINE__, __FUNCTION__, errno, ##args)
#endif #endif
typedef struct { typedef struct {

View file

@ -19,9 +19,10 @@
* *
*/ */
#include <sys/shm.h>
#include <limits.h>
#include "pcm_local.h" #include "pcm_local.h"
#include "pcm_plugin.h" #include "pcm_plugin.h"
#include <limits.h>
int snd_pcm_plugin_close(snd_pcm_t *pcm) int snd_pcm_plugin_close(snd_pcm_t *pcm)
{ {
@ -307,21 +308,29 @@ int snd_pcm_plugin_mmap(snd_pcm_t *pcm)
{ {
snd_pcm_plugin_t *plugin = pcm->private; snd_pcm_plugin_t *plugin = pcm->private;
snd_pcm_t *slave = plugin->slave; snd_pcm_t *slave = plugin->slave;
snd_pcm_mmap_info_t *i;
int err = snd_pcm_mmap(slave); int err = snd_pcm_mmap(slave);
if (err < 0) if (err < 0)
return err; return err;
pcm->mmap_info = calloc(1, sizeof(*pcm->mmap_info)); i = calloc(1, sizeof(*i));
if (!pcm->mmap_info) if (!i)
return -ENOMEM;
pcm->mmap_info_count = 1;
pcm->mmap_info->type = SND_PCM_MMAP_USER;
pcm->mmap_info->size = pcm->setup.buffer_size;
pcm->mmap_info->addr = valloc(snd_pcm_frames_to_bytes(pcm, pcm->setup.buffer_size));
if (!pcm->mmap_info->addr) {
free(pcm->mmap_info);
pcm->mmap_info = 0;
return -ENOMEM; return -ENOMEM;
i->type = SND_PCM_MMAP_USER;
i->size = snd_pcm_frames_to_bytes(pcm, pcm->setup.buffer_size);
i->u.user.shmid = shmget(IPC_PRIVATE, i->size, 0666);
if (i->u.user.shmid < 0) {
SYSERR("shmget failed");
free(i);
return -errno;
} }
i->addr = shmat(i->u.user.shmid, 0, 0);
if (i->addr == (void*) -1) {
SYSERR("shmat failed");
free(i);
return -errno;
}
pcm->mmap_info = i;
pcm->mmap_info_count = 1;
return 0; return 0;
} }
@ -332,7 +341,14 @@ int snd_pcm_plugin_munmap(snd_pcm_t *pcm)
int err = snd_pcm_munmap(slave); int err = snd_pcm_munmap(slave);
if (err < 0) if (err < 0)
return err; return err;
free(pcm->mmap_info->addr); if (shmdt(pcm->mmap_info->addr) < 0) {
SYSERR("shmdt failed");
return -errno;
}
if (shmctl(pcm->mmap_info->u.user.shmid, IPC_RMID, 0) < 0) {
SYSERR("shmctl IPC_RMID failed");
return -errno;
}
free(pcm->mmap_info); free(pcm->mmap_info);
pcm->mmap_info_count = 0; pcm->mmap_info_count = 0;
pcm->mmap_info = 0; pcm->mmap_info = 0;

View file

@ -71,7 +71,7 @@ int receive_fd(int socket, void *data, size_t len, int *fd)
ret = recvmsg(socket, &msghdr, 0); ret = recvmsg(socket, &msghdr, 0);
if (ret < 0) { if (ret < 0) {
ERR("recvmsg failed"); SYSERR("recvmsg failed");
return -errno; return -errno;
} }
*fd = *fds; *fd = *fds;
@ -385,14 +385,14 @@ static int snd_pcm_shm_mmap(snd_pcm_t *pcm)
fd, SND_PCM_MMAP_OFFSET_DATA); fd, SND_PCM_MMAP_OFFSET_DATA);
close(fd); close(fd);
if (ptr == MAP_FAILED || ptr == NULL) { if (ptr == MAP_FAILED || ptr == NULL) {
ERR("mmap failed"); SYSERR("mmap failed");
free(pcm->mmap_info); free(pcm->mmap_info);
return -errno; return -errno;
} }
} else { } else {
ptr = shmat(i->u.user.shmid, 0, 0); ptr = shmat(i->u.user.shmid, 0, 0);
if (ptr == (void*)-1) { if (ptr == (void*)-1) {
ERR("shmat failed"); SYSERR("shmat failed");
free(pcm->mmap_info); free(pcm->mmap_info);
return -errno; return -errno;
} }
@ -417,12 +417,12 @@ static int snd_pcm_shm_munmap(snd_pcm_t *pcm)
if (i->type == SND_PCM_MMAP_KERNEL) { if (i->type == SND_PCM_MMAP_KERNEL) {
err = munmap(i->addr, i->size); err = munmap(i->addr, i->size);
if (err < 0) if (err < 0)
ERR("munmap failed"); SYSERR("munmap failed");
return -errno; return -errno;
} else { } else {
err = shmdt(i->addr); err = shmdt(i->addr);
if (err < 0) if (err < 0)
ERR("shmdt failed"); SYSERR("shmdt failed");
return -errno; return -errno;
} }
} }
@ -531,7 +531,7 @@ static int make_local_socket(const char *filename)
sock = socket(PF_LOCAL, SOCK_STREAM, 0); sock = socket(PF_LOCAL, SOCK_STREAM, 0);
if (sock < 0) { if (sock < 0) {
ERR("socket failed"); SYSERR("socket failed");
return -errno; return -errno;
} }
@ -539,7 +539,7 @@ static int make_local_socket(const char *filename)
memcpy(addr->sun_path, filename, l); memcpy(addr->sun_path, filename, l);
if (connect(sock, (struct sockaddr *) addr, size) < 0) { if (connect(sock, (struct sockaddr *) addr, size) < 0) {
ERR("connect failed"); SYSERR("connect failed");
return -errno; return -errno;
} }
return sock; return sock;
@ -556,7 +556,7 @@ static int make_inet_socket(const char *host, int port)
sock = socket(PF_INET, SOCK_STREAM, 0); sock = socket(PF_INET, SOCK_STREAM, 0);
if (sock < 0) { if (sock < 0) {
ERR("socket failed"); SYSERR("socket failed");
return -errno; return -errno;
} }
@ -565,7 +565,7 @@ static int make_inet_socket(const char *host, int port)
memcpy(&addr.sin_addr, h->h_addr_list[0], sizeof(struct in_addr)); memcpy(&addr.sin_addr, h->h_addr_list[0], sizeof(struct in_addr));
if (connect(sock, (struct sockaddr *) &addr, sizeof(addr)) < 0) { if (connect(sock, (struct sockaddr *) &addr, sizeof(addr)) < 0) {
ERR("connect failed"); SYSERR("connect failed");
return -errno; return -errno;
} }
return sock; return sock;
@ -604,7 +604,7 @@ int snd_pcm_shm_open(snd_pcm_t **pcmp, char *name, char *socket, char *sname, in
req->namelen = snamelen; req->namelen = snamelen;
err = write(sock, req, reqlen); err = write(sock, req, reqlen);
if (err < 0) { if (err < 0) {
ERR("write error"); SYSERR("write error");
result = -errno; result = -errno;
goto _err; goto _err;
} }
@ -615,7 +615,7 @@ int snd_pcm_shm_open(snd_pcm_t **pcmp, char *name, char *socket, char *sname, in
} }
err = read(sock, &ans, sizeof(ans)); err = read(sock, &ans, sizeof(ans));
if (err < 0) { if (err < 0) {
ERR("read error"); SYSERR("read error");
result = -errno; result = -errno;
goto _err; goto _err;
} }
@ -630,7 +630,7 @@ int snd_pcm_shm_open(snd_pcm_t **pcmp, char *name, char *socket, char *sname, in
ctrl = shmat(ans.cookie, 0, 0); ctrl = shmat(ans.cookie, 0, 0);
if (!ctrl) { if (!ctrl) {
ERR("shmat error"); SYSERR("shmat error");
result = -errno; result = -errno;
goto _err; goto _err;
} }
@ -691,7 +691,7 @@ int is_local(struct hostent *hent)
s = socket(PF_INET, SOCK_STREAM, 0); s = socket(PF_INET, SOCK_STREAM, 0);
if (s < 0) { if (s < 0) {
ERR("socket failed"); SYSERR("socket failed");
return -errno; return -errno;
} }
@ -700,7 +700,7 @@ int is_local(struct hostent *hent)
while (1) { while (1) {
err = ioctl(s, SIOCGIFCONF, &conf); err = ioctl(s, SIOCGIFCONF, &conf);
if (err < 0) { if (err < 0) {
ERR("SIOCGIFCONF failed"); SYSERR("SIOCGIFCONF failed");
return -errno; return -errno;
} }
if ((size_t)conf.ifc_len < numreqs * sizeof(struct ifreq)) if ((size_t)conf.ifc_len < numreqs * sizeof(struct ifreq))