Command to dump the metadata cache again
[lttng-modules.git] / lttng-abi.c
index 40f96eb5d76dc6992dd6e6a311742593ed3b87c1..d202b728451209526e02bc8dae0a984570521bc5 100644 (file)
@@ -51,6 +51,7 @@
 #include <wrapper/poll.h>
 #include <wrapper/file.h>
 #include <wrapper/kref.h>
+#include <lttng-string-utils.h>
 #include <lttng-abi.h>
 #include <lttng-abi-old.h>
 #include <lttng-events.h>
@@ -653,6 +654,38 @@ void lttng_metadata_ring_buffer_ioctl_put_next_subbuf(struct file *filp,
        stream->metadata_out = stream->metadata_in;
 }
 
+/*
+ * Reset the counter of how much metadata has been consumed to 0. That way,
+ * the consumer receives the content of the metadata cache unchanged. This is
+ * different from the metadata_regenerate where the offset from epoch is
+ * resampled, here we want the exact same content as the last time the metadata
+ * was generated. This command is only possible if all the metadata written
+ * in the cache has been output to the metadata stream to avoid corrupting the
+ * metadata file.
+ *
+ * Return 0 on success, a negative value on error.
+ */
+static
+int lttng_metadata_cache_dump(struct lttng_metadata_stream *stream)
+{
+       int ret;
+       struct lttng_metadata_cache *cache = stream->metadata_cache;
+
+       mutex_lock(&cache->lock);
+       if (stream->metadata_out != cache->metadata_written) {
+               ret = -EBUSY;
+               goto end;
+       }
+       stream->metadata_out = 0;
+       stream->metadata_in = 0;
+       wake_up_interruptible(&stream->read_wait);
+       ret = 0;
+
+end:
+       mutex_unlock(&cache->lock);
+       return ret;
+}
+
 static
 long lttng_metadata_ring_buffer_ioctl(struct file *filp,
                unsigned int cmd, unsigned long arg)
@@ -683,6 +716,7 @@ long lttng_metadata_ring_buffer_ioctl(struct file *filp,
                 */
                return -ENOSYS;
        }
+       case RING_BUFFER_FLUSH_EMPTY:   /* Fall-through. */
        case RING_BUFFER_FLUSH:
        {
                struct lttng_metadata_stream *stream = filp->private_data;
@@ -704,17 +738,11 @@ long lttng_metadata_ring_buffer_ioctl(struct file *filp,
 
                return put_u64(stream->version, arg);
        }
-       case RING_BUFFER_SNAPSHOT:
+       case RING_BUFFER_METADATA_CACHE_DUMP:
        {
-               /*
-                * Force the buffer to quiescent so the ring buffer
-                * don't attempt to perform a SWITCH_FLUSH, which would
-                * desynchronize the client accounting of the amount of
-                * data available in the buffer from the ring buffer
-                * view.
-                */
-               buf->quiescent = true;
-               break;
+               struct lttng_metadata_stream *stream = filp->private_data;
+
+               return lttng_metadata_cache_dump(stream);
        }
        default:
                break;
@@ -771,6 +799,7 @@ long lttng_metadata_ring_buffer_compat_ioctl(struct file *filp,
                 */
                return -ENOSYS;
        }
+       case RING_BUFFER_FLUSH_EMPTY:   /* Fall-through. */
        case RING_BUFFER_FLUSH:
        {
                struct lttng_metadata_stream *stream = filp->private_data;
@@ -792,17 +821,11 @@ long lttng_metadata_ring_buffer_compat_ioctl(struct file *filp,
 
                return put_u64(stream->version, arg);
        }
-       case RING_BUFFER_SNAPSHOT:
+       case RING_BUFFER_METADATA_CACHE_DUMP:
        {
-               /*
-                * Force the buffer to quiescent so the ring buffer
-                * don't attempt to perform a SWITCH_FLUSH, which would
-                * desynchronize the client accounting of the amount of
-                * data available in the buffer from the ring buffer
-                * view.
-                */
-               buf->quiescent = true;
-               break;
+               struct lttng_metadata_stream *stream = filp->private_data;
+
+               return lttng_metadata_cache_dump(stream);
        }
        default:
                break;
@@ -1068,8 +1091,12 @@ int lttng_abi_create_event(struct file *channel_file,
                        || event_param->instrumentation == LTTNG_KERNEL_SYSCALL) {
                struct lttng_enabler *enabler;
 
-               if (event_param->name[strlen(event_param->name) - 1] == '*') {
-                       enabler = lttng_enabler_create(LTTNG_ENABLER_WILDCARD,
+               if (strutils_is_star_glob_pattern(event_param->name)) {
+                       /*
+                        * If the event name is a star globbing pattern,
+                        * we create the special star globbing enabler.
+                        */
+                       enabler = lttng_enabler_create(LTTNG_ENABLER_STAR_GLOB,
                                event_param, channel);
                } else {
                        enabler = lttng_enabler_create(LTTNG_ENABLER_NAME,
This page took 0.024459 seconds and 4 git commands to generate.