From 254ec7bc4c72da11a4e3f2c90904b111a06a2c55 Mon Sep 17 00:00:00 2001 From: Mathieu Desnoyers Date: Thu, 9 Jun 2011 16:29:22 -0400 Subject: [PATCH] Return POLLERR if channel is disabled (error state) Signed-off-by: Mathieu Desnoyers --- lib/ringbuffer/frontend.h | 6 ++++++ lib/ringbuffer/ring_buffer_vfs.c | 13 ++++++++++++- ltt-debugfs-abi.c | 2 ++ ltt-events.h | 1 + ltt-ring-buffer-client.h | 7 +++++++ ltt-ring-buffer-metadata-client.h | 7 +++++++ 6 files changed, 35 insertions(+), 1 deletion(-) diff --git a/lib/ringbuffer/frontend.h b/lib/ringbuffer/frontend.h index 85858d93..01af77a2 100644 --- a/lib/ringbuffer/frontend.h +++ b/lib/ringbuffer/frontend.h @@ -163,6 +163,12 @@ int lib_ring_buffer_channel_is_finalized(const struct channel *chan) return chan->finalized; } +static inline +int lib_ring_buffer_channel_is_disabled(const struct channel *chan) +{ + return atomic_read(&chan->record_disabled); +} + static inline unsigned long lib_ring_buffer_get_read_data_size( const struct lib_ring_buffer_config *config, diff --git a/lib/ringbuffer/ring_buffer_vfs.c b/lib/ringbuffer/ring_buffer_vfs.c index 2558ab66..fecef217 100644 --- a/lib/ringbuffer/ring_buffer_vfs.c +++ b/lib/ringbuffer/ring_buffer_vfs.c @@ -86,19 +86,24 @@ unsigned int lib_ring_buffer_poll(struct file *filp, poll_table *wait) struct lib_ring_buffer *buf = filp->private_data; struct channel *chan = buf->backend.chan; const struct lib_ring_buffer_config *config = chan->backend.config; - int finalized; + int finalized, disabled; if (filp->f_mode & FMODE_READ) { init_poll_funcptr(wait, wrapper_pollwait_exclusive); poll_wait(filp, &buf->read_wait, wait); finalized = lib_ring_buffer_is_finalized(config, buf); + disabled = lib_ring_buffer_channel_is_disabled(chan); + /* * lib_ring_buffer_is_finalized() contains a smp_rmb() ordering * finalized load before offsets loads. */ WARN_ON(atomic_long_read(&buf->active_readers) != 1); retry: + if (disabled) + return POLLERR; + if (subbuf_trunc(lib_ring_buffer_get_offset(config, buf), chan) - subbuf_trunc(lib_ring_buffer_get_consumed(config, buf), chan) == 0) { @@ -159,6 +164,9 @@ long lib_ring_buffer_ioctl(struct file *filp, unsigned int cmd, unsigned long ar struct channel *chan = buf->backend.chan; const struct lib_ring_buffer_config *config = chan->backend.config; + if (lib_ring_buffer_channel_is_disabled(chan)) + return -EIO; + switch (cmd) { case RING_BUFFER_SNAPSHOT: return lib_ring_buffer_snapshot(buf, &buf->cons_snapshot, @@ -250,6 +258,9 @@ long lib_ring_buffer_compat_ioctl(struct file *filp, unsigned int cmd, struct channel *chan = buf->backend.chan; const struct lib_ring_buffer_config *config = chan->backend.config; + if (lib_ring_buffer_channel_is_disabled(chan)) + return -EIO; + switch (cmd) { case RING_BUFFER_SNAPSHOT: return lib_ring_buffer_snapshot(buf, &buf->cons_snapshot, diff --git a/ltt-debugfs-abi.c b/ltt-debugfs-abi.c index fb6c789f..f8bee492 100644 --- a/ltt-debugfs-abi.c +++ b/ltt-debugfs-abi.c @@ -568,6 +568,8 @@ unsigned int lttng_channel_poll(struct file *file, poll_table *wait) poll_wait(file, channel->ops->get_hp_wait_queue(channel->chan), wait); + if (channel->ops->is_disabled(channel->chan)) + return POLLERR; if (channel->ops->is_finalized(channel->chan)) return POLLHUP; else diff --git a/ltt-events.h b/ltt-events.h index 9c6fcac3..05eff540 100644 --- a/ltt-events.h +++ b/ltt-events.h @@ -205,6 +205,7 @@ struct ltt_channel_ops { wait_queue_head_t *(*get_reader_wait_queue)(struct channel *chan); wait_queue_head_t *(*get_hp_wait_queue)(struct channel *chan); int (*is_finalized)(struct channel *chan); + int (*is_disabled)(struct channel *chan); }; struct ltt_channel { diff --git a/ltt-ring-buffer-client.h b/ltt-ring-buffer-client.h index d1429785..0d8051ec 100644 --- a/ltt-ring-buffer-client.h +++ b/ltt-ring-buffer-client.h @@ -472,6 +472,12 @@ int ltt_is_finalized(struct channel *chan) return lib_ring_buffer_channel_is_finalized(chan); } +static +int ltt_is_disabled(struct channel *chan) +{ + return lib_ring_buffer_channel_is_disabled(chan); +} + static struct ltt_transport ltt_relay_transport = { .name = "relay-" RING_BUFFER_MODE_TEMPLATE_STRING, .owner = THIS_MODULE, @@ -487,6 +493,7 @@ static struct ltt_transport ltt_relay_transport = { .get_reader_wait_queue = ltt_get_reader_wait_queue, .get_hp_wait_queue = ltt_get_hp_wait_queue, .is_finalized = ltt_is_finalized, + .is_disabled = ltt_is_disabled, }, }; diff --git a/ltt-ring-buffer-metadata-client.h b/ltt-ring-buffer-metadata-client.h index a687b705..8b1079d9 100644 --- a/ltt-ring-buffer-metadata-client.h +++ b/ltt-ring-buffer-metadata-client.h @@ -237,6 +237,12 @@ int ltt_is_finalized(struct channel *chan) return lib_ring_buffer_channel_is_finalized(chan); } +static +int ltt_is_disabled(struct channel *chan) +{ + return lib_ring_buffer_channel_is_disabled(chan); +} + static struct ltt_transport ltt_relay_transport = { .name = "relay-" RING_BUFFER_MODE_TEMPLATE_STRING, .owner = THIS_MODULE, @@ -252,6 +258,7 @@ static struct ltt_transport ltt_relay_transport = { .get_reader_wait_queue = ltt_get_reader_wait_queue, .get_hp_wait_queue = ltt_get_hp_wait_queue, .is_finalized = ltt_is_finalized, + .is_disabled = ltt_is_disabled, }, }; -- 2.34.1