summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorPaul Buetow <pbuetow@mimecast.com>2018-03-30 10:21:02 +0100
committerPaul Buetow <pbuetow@mimecast.com>2018-03-30 10:21:02 +0100
commit712a25f115bf34dc73f81e5a4f1971b586fb524a (patch)
tree30a4620b9df7f72897d7bb0c4d587461cc748a61
parentfd779da9cfd81db6bf1d01404149235d7dd3e9df (diff)
add file hole support
-rw-r--r--.gitignore1
-rw-r--r--README.md1
-rw-r--r--ioriot/src/datas/btree.c180
-rw-r--r--ioriot/src/datas/btree.h21
-rw-r--r--ioriot/src/datas/list.c1
-rw-r--r--ioriot/src/defaults.h8
-rw-r--r--ioriot/src/generate/generate.c29
-rw-r--r--ioriot/src/generate/gioop.c21
-rw-r--r--ioriot/src/generate/gioop.h1
-rw-r--r--ioriot/src/generate/vsize.c97
-rw-r--r--ioriot/src/generate/vsize.h23
-rw-r--r--ioriot/src/init/init.c20
-rw-r--r--ioriot/src/init/itask.c6
-rw-r--r--ioriot/src/init/itask.h3
-rw-r--r--ioriot/src/init/ithread.c10
-rw-r--r--ioriot/src/opcodes.h1
-rw-r--r--ioriot/src/replay/rioop.c1
-rw-r--r--ioriot/src/utests.c4
-rw-r--r--ioriot/src/utils/futils.c24
-rw-r--r--ioriot/src/utils/futils.h9
-rw-r--r--ioriot/src/utils/utils.c56
-rw-r--r--ioriot/tags661
-rw-r--r--systemtap/src/ioriot.stp14
-rw-r--r--systemtap/src/javaioriot.stp14
-rw-r--r--systemtap/src/targetedioriot.stp14
25 files changed, 428 insertions, 792 deletions
diff --git a/.gitignore b/.gitignore
index ab4c720..07f2f4b 100644
--- a/.gitignore
+++ b/.gitignore
@@ -3,4 +3,5 @@
docs/html/
docs/latex/
ioriot/ioriot
+ioriot/tags
systemtap/downloads/
diff --git a/README.md b/README.md
index be6aa8f..0ab83cd 100644
--- a/README.md
+++ b/README.md
@@ -339,6 +339,7 @@ Currently, these file I/O related syscalls are supported (as of CentOS 7):
open
openat
lseek
+llseek
fcntl
creat
write
diff --git a/ioriot/src/datas/btree.c b/ioriot/src/datas/btree.c
index b150066..a70c442 100644
--- a/ioriot/src/datas/btree.c
+++ b/ioriot/src/datas/btree.c
@@ -37,7 +37,7 @@ void btree_destroy2(btree_s* b)
free(b);
}
-int btree_insert(btree_s* b, int key, void *data)
+int btree_insert(btree_s* b, long key, void *data)
{
int ret = 0;
@@ -48,13 +48,13 @@ int btree_insert(btree_s* b, int key, void *data)
ret = btreelem_insert_r(b->root, key, data);
}
- if (ret == 0)
+ if (ret == 1)
b->size++;
return ret;
}
-void* btree_get(btree_s* b, int key)
+void* btree_get(btree_s* b, long key)
{
if (b->root == NULL)
return NULL;
@@ -62,17 +62,45 @@ void* btree_get(btree_s* b, int key)
return btreelem_get_r(b->root, key);
}
+bool btree_has_range_l(btree_s* b, const long start, const long end)
+{
+ if (b->root == NULL)
+ return false;
+
+ return btreelem_has_range_lr(b->root, start, end);
+}
+
+long btree_get_l(btree_s* b, long key)
+{
+ void *data = btree_get(b, key);
+ if (data)
+ return (long)data;
+ else
+ return -1;
+}
+
+void btree_ensure_range_l(btree_s* b, const long start, const long end, const long threshold)
+{
+ if (b->root == NULL) {
+ btree_insert(b, start, (void*)end);
+ } else {
+ if (1 == btreelem_ensure_range_lr(b->root, start, end, threshold))
+ b->size++;
+ }
+}
+
void btree_print(btree_s* b)
{
- btreelem_print_r(b->root, 0);
+ Put("btree:%p size:%d", (void*)b, b->size);
+ btreelem_print_r(b->root, 1);
}
-void btree_run_cb2(btree_s* b, void (*cb)(void *data, void *data2))
+void btree_run_cb2(btree_s* b, void (*cb)(long key, void *data, void *data2), void *data2)
{
- btreelem_run_cb2_r(b->root, cb);
+ btreelem_run_cb2_r(b->root, cb, data2);
}
-btreelem_s* btreelem_new(int key, void *data)
+btreelem_s* btreelem_new(long key, void *data)
{
btreelem_s *e = Malloc(btreelem_s);
@@ -105,7 +133,7 @@ void btreelem_destroy_r2(btreelem_s* e)
free(e);
}
-int btreelem_insert_r(btreelem_s* e, int key, void *data)
+int btreelem_insert_r(btreelem_s* e, long key, void *data)
{
int ret = 1;
@@ -130,19 +158,65 @@ int btreelem_insert_r(btreelem_s* e, int key, void *data)
return ret;
}
-void* btreelem_get_r(btreelem_s* e, int key)
+int btreelem_ensure_range_lr(btreelem_s *e, const long start, const long end, const long threshold)
+{
+ int ret = 0;
+ long value = (long) e->data;
+
+ //Debug("%ld %ld %ld", start, end, threshold);
+
+ if (e->key == start) {
+ if (value < end) {
+ e->data = (void*) end;
+ } else {
+ // Nothing to do, range already present
+ }
+
+ } else if (e->key > start) {
+ if (e->left == NULL) {
+ if (value <= end) {
+ e->key = start;
+ e->data = (void*)end;
+ } else {
+ e->left = btreelem_new(start, (void*)end);
+ ret = 1;
+ }
+ } else {
+ ret = btreelem_ensure_range_lr(e->left, start, end, threshold);
+ }
+
+ } else { // if (e->key < start)
+ if (value >= start) {
+ if (value < end) {
+ e->data = (void*) end;
+ } else {
+ // Nothing to do, range already present
+ }
+ } else {
+ if (e->right == NULL) {
+ e->right = btreelem_new(start, (void*)end);
+ ret = 1;
+ } else {
+ ret = btreelem_ensure_range_lr(e->right, start, end, threshold);
+ }
+ }
+ }
+
+ return ret;
+}
+
+void* btreelem_get_r(btreelem_s* e, long key)
{
void *data = NULL;
- if (e->key == key)
+ if (e->key == key) {
data = e->data;
- else if (e->key > key) {
+ } else if (e->key > key) {
if (e->left)
data = btreelem_get_r(e->left, key);
- }
- else {
+ } else {
if (e->right)
data = btreelem_get_r(e->right, key);
}
@@ -150,6 +224,27 @@ void* btreelem_get_r(btreelem_s* e, int key)
return data;
}
+bool btreelem_has_range_lr(btreelem_s* e, const long start, const long end)
+{
+ long value = (long)e->data;
+
+ if (e->key <= start && value >= end) {
+ return true;
+
+ } else if (e->key > start) {
+ if (e->left)
+ return btreelem_has_range_lr(e->left, start, end);
+ else
+ return false;
+
+ } else {
+ if (e->right)
+ return btreelem_has_range_lr(e->right, start, end);
+ else
+ return false;
+ }
+}
+
void btreelem_print_r(btreelem_s* e, int depth)
{
if (!e)
@@ -157,7 +252,7 @@ void btreelem_print_r(btreelem_s* e, int depth)
for (int i = 0; i < depth; ++i)
Out(" ");
- Put("key:%d data:%ld\n", e->key, (long) e->data);
+ Put("key:%ld data:%ld", e->key, (long) e->data);
if (e->left)
btreelem_print_r(e->left, depth);
@@ -166,18 +261,18 @@ void btreelem_print_r(btreelem_s* e, int depth)
btreelem_print_r(e->right, depth+1);
}
-void btreelem_run_cb2_r(btreelem_s* e, void (*cb)(void *data, void *data2))
+void btreelem_run_cb2_r(btreelem_s* e, void (*cb)(long key, void *data, void *data2), void *data2)
{
if (!e)
return;
- cb((void*)(long)e->key, e->data);
+ cb(e->key, e->data, data2);
if (e->left)
- btreelem_run_cb2_r(e->left, cb);
+ btreelem_run_cb2_r(e->left, cb, data2);
if (e->right)
- btreelem_run_cb2_r(e->right, cb);
+ btreelem_run_cb2_r(e->right, cb, data2);
}
void btree_test(void)
@@ -186,23 +281,68 @@ void btree_test(void)
void* somedata = (void*)b;
assert(1 == btree_insert(b, 1, (void*)1));
+ assert(1 == b->size);
assert(1 == btree_insert(b, 2, (void*)2));
+ assert(2 == b->size);
assert(1 == btree_insert(b, 3, (void*)3));
- assert(1 == (long)btree_get(b, 1));
+ assert(3 == b->size);
+ assert(1 == btree_get_l(b, 1));
assert(1 == btree_insert(b, 1234, somedata));
+ assert(4 == b->size);
assert(1 == btree_insert(b, 13, somedata));
+ assert(5 == b->size);
assert(1 == btree_insert(b, 666, somedata));
+ assert(6 == b->size);
assert(0 == btree_insert(b, 13, somedata));
+ assert(6 == b->size);
assert(NULL != btree_get(b, 666));
assert(NULL == btree_get(b, 777));
assert(0 == btree_insert(b, 666, somedata));
assert(1 == btree_insert(b, 42, (void*)42));
- assert(42 == (long)btree_get(b, 42));
+ assert(42 == btree_get_l(b, 42));
btree_print(b);
+ btree_destroy(b);
+ b = btree_new();
+ assert(0 == b->size);
+
+ btree_ensure_range_l(b, 0, 23, 0);
+ assert(btree_get_l(b, 0) == (long) btree_get(b, 0));
+ assert(23 == btree_get_l(b, 0));
+ assert(btree_has_range_l(b, 2, 10));
+
+ assert(!btree_has_range_l(b, 300, 325));
+ btree_ensure_range_l(b, 300, 325, 0);
+ assert(2 == b->size);
+ assert(325 == btree_get_l(b, 300));
+ assert(btree_has_range_l(b, 300, 325));
+ assert(!btree_has_range_l(b, 300, 326));
+
+ btree_ensure_range_l(b, 200, 3321, 0);
+ assert(2 == b->size);
+
+ btree_ensure_range_l(b, 200, 1000, 0);
+ assert(2 == b->size);
+ assert(3321 == btree_get_l(b, 200));
+
+ btree_ensure_range_l(b, 0, 23, 0);
+ btree_ensure_range_l(b, 10, 10, 0);
+ btree_ensure_range_l(b, 22, 25, 0);
+ assert(25 == btree_get_l(b, 0));
+ assert(2 == b->size);
+
+ assert(!btree_has_range_l(b, 4000, 4000));
+ btree_ensure_range_l(b, 4000, 4000, 0);
+ assert(3 == b->size);
+ assert(btree_has_range_l(b, 4000, 4000));
+ assert(!btree_has_range_l(b, 4000, 4001));
+ assert(!btree_has_range_l(b, 3999, 4000));
+ btree_print(b);
+
+ btree_print(b);
btree_destroy(b);
}
diff --git a/ioriot/src/datas/btree.h b/ioriot/src/datas/btree.h
index acc5477..0a05cee 100644
--- a/ioriot/src/datas/btree.h
+++ b/ioriot/src/datas/btree.h
@@ -23,7 +23,7 @@
typedef struct btreelem_ {
struct btreelem_ *left; /**< The next element to the left */
struct btreelem_ *right; /**< The next element to the right */
- int key; /**< The key of the element */
+ long key; /**< The key of the element */
void *data; /**< A pointer to the data stored in this element */
} btreelem_s;
@@ -38,18 +38,23 @@ typedef struct btree_s_ {
btree_s* btree_new();
void btree_destroy(btree_s *b);
void btree_destroy2(btree_s *b);
-int btree_insert(btree_s *b, int key, void *data);
-void* btree_get(btree_s *b, int key);
+int btree_insert(btree_s *b, long key, void *data);
+void* btree_get(btree_s *b, long key);
+long btree_get_l(btree_s *b, long key);
+bool btree_has_range_l(btree_s *b, const long start, const long end);
+void btree_ensure_range_l(btree_s *b, const long start, const long end, const long threshold);
void btree_print(btree_s *b);
-void btree_run_cb2(btree_s* b, void (*cb)(void *data, void *data2));
+void btree_run_cb2(btree_s* b, void (*cb)(long key, void *data, void *data2), void *data2);
void btree_test(void);
-btreelem_s* btreelem_new(int key, void *data);
+btreelem_s* btreelem_new(long key, void *data);
void btreelem_destroy_r(btreelem_s *e);
void btreelem_destroy_r2(btreelem_s *e);
-int btreelem_insert_r(btreelem_s *e, int key, void *data);
-void* btreelem_get_r(btreelem_s *e, int key);
+int btreelem_insert_r(btreelem_s *e, long key, void *data);
+void* btreelem_get_r(btreelem_s *e, long key);
+bool btreelem_has_range_lr(btreelem_s *e, const long start, const long end);
+int btreelem_ensure_range_lr(btreelem_s *e, const long start, const long end, const long threshold);
void btreelem_print_r(btreelem_s *e, int depth);
-void btreelem_run_cb2_r(btreelem_s* e, void (*cb)(void *data, void *data2));
+void btreelem_run_cb2_r(btreelem_s* e, void (*cb)(long key, void *data, void *data2), void *data2);
#endif // BTREE_H
diff --git a/ioriot/src/datas/list.c b/ioriot/src/datas/list.c
index 9cc78db..81e3e57 100644
--- a/ioriot/src/datas/list.c
+++ b/ioriot/src/datas/list.c
@@ -14,7 +14,6 @@
#include "list.h"
-
list_s *list_new()
{
list_s *l = Malloc(list_s);
diff --git a/ioriot/src/defaults.h b/ioriot/src/defaults.h
index c0833c8..d822423 100644
--- a/ioriot/src/defaults.h
+++ b/ioriot/src/defaults.h
@@ -18,9 +18,9 @@
#include "utils/utils.h"
/** Version of the supported .capture format */
-#define CAPTURE_VERSION 1
+#define CAPTURE_VERSION 2
/** Version of the supported .replay format */
-#define REPLAY_VERSION 1
+#define REPLAY_VERSION 2
/** Max amount of tokens per line in the .capture file */
#define MAX_TOKENS 10
/** Max line length in either .capture or .replay file */
@@ -30,11 +30,13 @@
/** Version of I/O Riot */
#define IORIOT_VERSION "0.4-develop"
/** Copyright information */
-#define IORIOT_COPYRIGHT "Mimecast 2017, 2018 (c)"
+#define IORIOT_COPYRIGHT "(c) Mimecast 2018"
/** Max open files resource user limit */
#define SET_RLIMIT_NOFILE 369216
/** Max processes resource user limit */
#define SET_RLIMIT_NPROC 30768
+/** Ignore file hole size */
+#define IGNORE_FILE_HOLE_BYTES 1024*1024*10
// The following are for debugging purposes only
diff --git a/ioriot/src/generate/generate.c b/ioriot/src/generate/generate.c
index ee7178c..53751de 100644
--- a/ioriot/src/generate/generate.c
+++ b/ioriot/src/generate/generate.c
@@ -68,7 +68,6 @@ void generate_destroy(generate_s *g)
free(g);
}
-
status_e generate_run(options_s *opts)
{
generate_s *g = generate_new(opts);
@@ -189,14 +188,30 @@ status_e generate_run(options_s *opts)
return SUCCESS;
}
-void generate_write_init_cb(void *data)
+void _write_ranges_cb(long start, void *data, void *data2)
{
- vsize_s *l = data;
- generate_s *g = l->generate;
+ vsize_s *v = data2;
+ generate_s *g = v->generate;
+ long end = (long) data;
+ long bytes = end-start;
+ if (bytes > 0) {
+ fprintf(g->replay_fd, "%d|%d|%ld|%ld|%s|\n",
+ v->is_dir, v->is_file, start, bytes, v->path);
+ }
+}
- if (l->required && strlen(l->path) > 0) {
- fprintf(g->replay_fd, "%d|%d|%ld|%s|\n",
- l->is_dir, l->is_file, -l->vsize_deficit, l->path);
+void generate_write_init_cb(void *data)
+{
+ vsize_s *v = data;
+ generate_s *g = v->generate;
+
+ if (v->required && strlen(v->path) > 0) {
+ if (v->read_ranges) {
+ btree_run_cb2(v->read_ranges, _write_ranges_cb, data);
+ } else if (v->bytes >= 0) {
+ fprintf(g->replay_fd, "%d|%d|%ld|%ld|%s|\n",
+ v->is_dir, v->is_file, 0L, v->bytes, v->path);
+ }
}
}
diff --git a/ioriot/src/generate/gioop.c b/ioriot/src/generate/gioop.c
index 01701bc..d5b9a28 100644
--- a/ioriot/src/generate/gioop.c
+++ b/ioriot/src/generate/gioop.c
@@ -27,7 +27,7 @@ status_e gioop_run(gwriter_s *w, gtask_s *t)
generate_s *g = w->generate;
// Get the virtual process data object from the virtual PID space and store
- // a pointer to it to t->gprocess
+ // a pointer to it at t->gprocess
generate_gprocess_by_realpid(g, t);
// One of the open syscalls may openes a file handle succesfully
@@ -109,6 +109,9 @@ status_e gioop_run(gwriter_s *w, gtask_s *t)
} else if (Eq(t->op, "lseek")) {
Cleanup(gioop_lseek(w, t, g));
+ } else if (Eq(t->op, "llseek")) {
+ Cleanup(gioop_llseek(w, t, g));
+
} else if (Eq(t->op, "getdents")) {
Cleanup(gioop_getdents(w, t, g));
@@ -559,6 +562,22 @@ status_e gioop_lseek(gwriter_s *w, gtask_s *t, generate_s *g)
return SUCCESS;
}
+status_e gioop_llseek(gwriter_s *w, gtask_s *t, generate_s *g)
+{
+ if (!t->has_fd) {
+ return ERROR;
+ }
+
+ generate_vsize_by_path(g, t, t->vfd->path);
+ Gioop_write(LLSEEK, "%ld|%ld|%ld|%ld|llseek",
+ t->mapped_fd, t->offset, t->whence, t->bytes);
+
+ if (t->bytes >= 0)
+ vsize_seek(t->vsize, t->vfd, t->bytes);
+
+ return SUCCESS;
+}
+
status_e gioop_getdents(gwriter_s *w, gtask_s *t, generate_s *g)
{
if (!t->has_fd) {
diff --git a/ioriot/src/generate/gioop.h b/ioriot/src/generate/gioop.h
index ad49713..1df57c1 100644
--- a/ioriot/src/generate/gioop.h
+++ b/ioriot/src/generate/gioop.h
@@ -79,6 +79,7 @@ status_e gioop_readlinkat(gwriter_s *w, gtask_s *t, generate_s *g);
status_e gioop_write(gwriter_s *w, gtask_s *t, generate_s *g);
status_e gioop_writev(gwriter_s *w, gtask_s *t, generate_s *g);
status_e gioop_lseek(gwriter_s *w, gtask_s *t, generate_s *g);
+status_e gioop_llseek(gwriter_s *w, gtask_s *t, generate_s *g);
status_e gioop_getdents(gwriter_s *w, gtask_s *t, generate_s *g);
status_e gioop_mkdir(gwriter_s *w, gtask_s *t, generate_s *g);
status_e gioop_rmdir(gwriter_s *w, gtask_s *t, generate_s *g);
diff --git a/ioriot/src/generate/vsize.c b/ioriot/src/generate/vsize.c
index f2d56ba..4bf8433 100644
--- a/ioriot/src/generate/vsize.c
+++ b/ioriot/src/generate/vsize.c
@@ -17,7 +17,6 @@
#include "generate.h"
// Helper macros
-
#define _Set_file(v) v->is_file = true; v->unsure = v->is_dir = false
#define _Set_dir(v) v->is_dir = true; v->unsure = v->is_file = false
#define _Set_unsure(v) v->unsure = true
@@ -35,14 +34,14 @@ vsize_s* vsize_new(char *file_path, const unsigned long id,
v->inserted = false;
v->is_dir = false;
v->is_file = false;
- v->offset = -1;
v->path = Clone(file_path);
v->renamed = false;
v->required = false;
v->unsure = false;
v->updates = 0;
- v->vsize = 0;
- v->vsize_deficit = 0;
+ v->bytes = 0;
+ v->read_ranges = NULL;
+ v->write_ranges = NULL;
return v;
}
@@ -52,6 +51,11 @@ void vsize_destroy(vsize_s *v)
if (!v)
return;
+ if (v->read_ranges)
+ btree_destroy(v->read_ranges);
+ if (v->write_ranges)
+ btree_destroy(v->write_ranges);
+
free(v->path);
free(v);
}
@@ -91,9 +95,9 @@ void init_parent_dir(vsize_s *v, const char *path)
void vsize_open(vsize_s *v, void *vfd, const char *path, const int flags)
{
- // v->first_encounter == false means, that this is the first occurance of
+ // v->updates == 0 means, that this is the first occurance of
// this path and we didn't initialise it (means we didn't ensure that
- // we want to create all parent directories etc.
+ // we want to create all parent directories etc.)
if (v->updates == 0) {
// We may use a recycled vfd object! When opening a file we always
@@ -161,56 +165,87 @@ void vsize_rename(vsize_s *v, vsize_s *v2,
// We are not 100% sure that this is really a file,
// the path might be still a directory though!
_Set_unsure(v2);
+ v2->updates++;
// For debugging purposes only
_Set_renamed(v2);
- v2->updates++;
}
}
-void vsize_adjust(vsize_s *v, vfd_s* vfd)
+void vsize_ensure_data_range(vsize_s *v, btree_s **ranges, const long offset, const long bytes)
{
- if (v->vsize >= vfd->offset)
- return;
+ if (*ranges == NULL) {
+ if (offset == 0) {
+ if (v->bytes + IGNORE_FILE_HOLE_BYTES < bytes) {
+ // No file hole, just set the new (larger) vsize
+ v->bytes = bytes;
+ } else {
+ // Nothing to do, vsize is already sufficient
+ }
+
+ } else { // if (offset > 0)
+ if (offset <= v->bytes) {
+ // We won't add a hole to the file here either
+ if (v->bytes < bytes) {
+ // No file hole, just set the new (larger) bytes
+ v->bytes = bytes;
+ } else {
+ // Nothing to do, bytes is already sufficient
+ }
+ } else { // if (offset > v->bytes)
+ // From offset larger than bytes, we have a hole in the file!
+ *ranges = btree_new();
+
+ // Insert root data range
+ btree_insert(*ranges, 0, (void*)v->bytes);
+
+ // This value is not used anymore, we use the btree instead from now
+ // to store all used data ranges of a file.
+ v->bytes = -1;
+
+ // Rerun this function with a data range btree initialised
+ vsize_ensure_data_range(v, ranges, offset, bytes);
+ }
+ }
- long deficit = v->vsize - vfd->offset;
- if (deficit < v->vsize_deficit) {
- v->vsize_deficit = deficit;
- _Set_required(v);
- _Set_file(v);
+ } else { // if (*ranges != NULL)
+ btree_ensure_range_l(*ranges, offset, offset+bytes,
+ IGNORE_FILE_HOLE_BYTES);
}
}
void vsize_read(vsize_s *v, void *vfd, const char *path, const int bytes)
{
vfd_s *vfd_ = vfd;
+
+ if (v->write_ranges == NULL ||
+ !btree_has_range_l(v->write_ranges, vfd_->offset, vfd_->offset+bytes)) {
+ vsize_ensure_data_range(v, &v->read_ranges, vfd_->offset, bytes);
+ _Set_required(v);
+ _Set_file(v);
+ }
+
vfd_->offset += bytes;
- vsize_adjust(v, vfd_);
v->updates++;
}
-void vsize_seek(vsize_s *v, void *vfd, const long new_offset)
+void vsize_write(vsize_s *v, void *vfd, const char *path, const int bytes)
{
- //vfd_s *vfd_ = vfd;
-
- // The file's offset can be greater than the file's current size, in which
- // case the next write to the file will extend the file. This is referred
- // to as creating a hole in a file and is allowed. However, this behaviour
- // does not suit the estimation of the file size before we want to run the
- // test.
-
- // TODO: Implement file hole support!
- //v->updates++;
+ vfd_s *vfd_ = vfd;
+ vsize_ensure_data_range(v, &v->write_ranges, vfd_->offset, bytes);
+ vfd_->offset += bytes;
+ v->updates++;
}
-void vsize_write(vsize_s *v, void *vfd, const char *path, const int bytes)
+void vsize_seek(vsize_s *v, void *vfd, const long new_offset)
{
vfd_s *vfd_ = vfd;
- vfd_->offset += bytes;
- if (v->vsize < vfd_->offset)
- v->vsize = vfd_->offset;
+ // The file's offset can be greater than the file's current size, in which
+ // case the next write to the file will extend the file. This is referred
+ // to as creating a hole in a file.
+ vfd_->offset = new_offset;
v->updates++;
}
diff --git a/ioriot/src/generate/vsize.h b/ioriot/src/generate/vsize.h
index 8556ec0..ffda9e5 100644
--- a/ioriot/src/generate/vsize.h
+++ b/ioriot/src/generate/vsize.h
@@ -16,7 +16,7 @@
#define VSIZE_H
#include "../utils/utils.h"
-#include "../datas/hmap.h"
+#include "../datas/btree.h"
#include "../vfd.h"
/**
@@ -30,11 +30,11 @@
*/
typedef struct vsize_s_ {
char *path; /**< The path to the file/directory */
- off_t offset; /**< The current file offset */
+ long bytes; /**< The virtual size */
+ btree_s *read_ranges; /**< Used to store used data ranges in a file with holes */
+ btree_s *write_ranges; /**< Used to store used data ranges in a file with holes */
unsigned long id; /**< The vsize id */
void *generate; /**< A pointer to the generate object */
- long vsize; /**< The virtual size */
- long vsize_deficit; /**< Size to use for file creating during init mode */
bool renamed; /**< True if file/dir has been renamed */
bool required; /**< True if init mode will create this file/dir */
bool is_dir; /**< True if this file/dir is a directory */
@@ -72,19 +72,18 @@ void vsize_destroy(vsize_s *v);
void init_parent_dir(vsize_s *v, const char *path);
/**
- * @brief Adjusts the vsize
+ * @brief Ensure that we have a data range in the virtual file
*
* Compares the virtual file size of the file in the vsize
- * object to the the offset in the virtual file descriptor.
- * In case the offset is higher we have a size deficit and
- * we need to mark it. That way ioriot can ensure that
- * during init mode it will create a file with the correct
- * size prior of running the test!
+ * object to the the given offsets. This is required just in case
+ * we have holes in the file to be replayed.
*
* @param v The virtual size object
- * @param vfd The virtual file descriptor object
+ * @param ranges The ranges object to operaet on
+ * @param offset The start offset
+ * @param bytes The amount of bytes
*/
-void vsize_adjust(vsize_s *v, vfd_s* vfd);
+void vsize_ensure_data_range(vsize_s *v, btree_s **ranges, const long offset, const long bytes);
/**
* @brief Adjust vsize on open
diff --git a/ioriot/src/init/init.c b/ioriot/src/init/init.c
index e375379..3f9d8a0 100644
--- a/ioriot/src/init/init.c
+++ b/ioriot/src/init/init.c
@@ -21,7 +21,6 @@
#include "../mounts.h"
#include "../utils/futils.h"
-
init_s *init_new(options_s *opts)
{
init_s *i = Malloc(init_s);
@@ -118,7 +117,8 @@ status_e init_run(options_s *opts)
fseeko(i->replay_fd, init_offset, SEEK_SET);
bool is_file = false, is_dir = false;
- long vsize = 0;
+ long offset = 0;
+ long bytes = 0;
char *path;
// Stats
@@ -136,6 +136,7 @@ status_e init_run(options_s *opts)
// Process the INIT section of the .replay file line by line.
while ((read = getline(&line, &len, i->replay_fd)) != -1) {
+ Debug(line);
char *tok = strtok_r(line, "|", &saveptr);
for (int ntok = 0; tok; ntok++) {
@@ -147,12 +148,18 @@ status_e init_run(options_s *opts)
is_file = atoi(tok) == 1;
break;
case 2:
- vsize = atol(tok);
- if (vsize < 0) {
- Error("Size overflow");
+ offset = atol(tok);
+ if (offset < 0) {
+ Error("Offset overflow: '%ld'", offset);
}
break;
case 3:
+ bytes = atol(tok);
+ if (bytes < 0) {
+ Error("Size overflow: '%ld'", bytes);
+ }
+ break;
+ case 4:
path = tok;
break;
default:
@@ -178,7 +185,8 @@ status_e init_run(options_s *opts)
} else if (is_file) {
task->is_file = true;
- task->vsize = vsize;
+ task->bytes = bytes;
+ task->offset = offset;
}
task->path = Clone(path);
diff --git a/ioriot/src/init/itask.c b/ioriot/src/init/itask.c
index f04ce33..de7c551 100644
--- a/ioriot/src/init/itask.c
+++ b/ioriot/src/init/itask.c
@@ -35,7 +35,7 @@ void itask_destroy(itask_s *task)
void itask_reset_stats(itask_s *task)
{
task->is_dir = task->is_file = false;
- task->sizes_created = task->vsize = 0;
+ task->sizes_created = task->offset = task->bytes = 0;
task->dirs_created = task->files_created = 0;
if (task->path) {
@@ -60,7 +60,7 @@ void itask_extract_stats(itask_s *task, long* dirs_created, long *files_created,
void itask_print(itask_s *task)
{
- Put("itask(%p): is_dir:%d is_file:%d vsize:%ld path:%s",
+ Put("itask(%p): is_dir:%d is_file:%d offset:%ld bytes:%ld path:%s",
(void*)task, task->is_dir, task->is_file,
- task->vsize, task->path);
+ task->offset, task->bytes, task->path);
}
diff --git a/ioriot/src/init/itask.h b/ioriot/src/init/itask.h
index b10d515..21afba4 100644
--- a/ioriot/src/init/itask.h
+++ b/ioriot/src/init/itask.h
@@ -23,7 +23,8 @@
typedef struct itask_s_ {
bool is_dir;
bool is_file;
- long vsize;
+ long offset;
+ long bytes;
char *path;
long dirs_created;
long files_created;
diff --git a/ioriot/src/init/ithread.c b/ioriot/src/init/ithread.c
index a580e70..bcc31f3 100644
--- a/ioriot/src/init/ithread.c
+++ b/ioriot/src/init/ithread.c
@@ -90,9 +90,13 @@ void ithread_run_task(ithread_s *t, itask_s *task)
} else if (task->is_file) {
if (!ensure_file_exists(task->path, &task->dirs_created)) {
task->files_created++;
- if (task->vsize > 0) {
- append_random_to_file(task->path, task->vsize);
- task->sizes_created += task->vsize;
+ if (task->bytes > 0) {
+ if (task->offset > 0) {
+ write_random_to_file(task->path, task->bytes, task->offset);
+ } else {
+ append_random_to_file(task->path, task->bytes);
+ }
+ task->sizes_created += task->bytes;
}
}
}
diff --git a/ioriot/src/opcodes.h b/ioriot/src/opcodes.h
index 3d5c114..0dd060c 100644
--- a/ioriot/src/opcodes.h
+++ b/ioriot/src/opcodes.h
@@ -69,6 +69,7 @@ typedef enum {
FCNTL = 70,
GETDENTS,
LSEEK,
+ LLSEEK,
// mmap syscalls
MMAP2 = 80,
diff --git a/ioriot/src/replay/rioop.c b/ioriot/src/replay/rioop.c
index 2e16c94..0ce19c5 100644
--- a/ioriot/src/replay/rioop.c
+++ b/ioriot/src/replay/rioop.c
@@ -151,6 +151,7 @@ void rioop_run(rprocess_s *p, rthread_s *t, rtask_s *task)
rioop_getdents(p, t, task);
break;
case LSEEK:
+ case LLSEEK:
rioop_lseek(p, t, task);
break;
diff --git a/ioriot/src/utests.c b/ioriot/src/utests.c
index 0fc53c3..7cae7e8 100644
--- a/ioriot/src/utests.c
+++ b/ioriot/src/utests.c
@@ -18,7 +18,6 @@
#include "datas/btree.h"
#include "datas/hmap.h"
#include "datas/list.h"
-#include "datas/ranges.h"
#include "datas/rbuffer.h"
#include "utils/utils.h"
@@ -27,9 +26,6 @@ void utests_run()
fprintf(stderr, "Running btree_test()\n");
btree_test();
- fprintf(stderr, "Running ranges_test()\n");
- ranges_test();
-
fprintf(stderr, "Running amap_test()\n");
amap_test();
diff --git a/ioriot/src/utils/futils.c b/ioriot/src/utils/futils.c
index 5b35618..ccaf3e4 100644
--- a/ioriot/src/utils/futils.c
+++ b/ioriot/src/utils/futils.c
@@ -21,11 +21,9 @@
#include "../macros.h"
-void append_random_to_file(char *path, unsigned long bytes)
-{
+void _write_random_to_stream(FILE *fp, unsigned long bytes) {
char *buf = NULL;
int max_chunk = 50000000; // 50 mebibyetes
- FILE *fp = Fopen(path, "a");
for (;;) {
if (bytes > max_chunk) {
@@ -54,7 +52,25 @@ void append_random_to_file(char *path, unsigned long bytes)
if (buf)
free(buf);
- fclose(fp);
+}
+
+void append_random_to_file(char *path, unsigned long bytes)
+{
+ FILE *fp = Fopen(path, "a");
+ if (fp) {
+ _write_random_to_stream(fp, bytes);
+ fclose(fp);
+ }
+}
+
+void write_random_to_file(char *path, unsigned long bytes, off_t offset)
+{
+ FILE *fp = Fopen(path, "w");
+ if (fp) {
+ fseek(fp, offset, SEEK_SET);
+ _write_random_to_stream(fp, bytes);
+ fclose(fp);
+ }
}
long ensure_dir_exists(const char *path)
diff --git a/ioriot/src/utils/futils.h b/ioriot/src/utils/futils.h
index 9afde1a..e8cff97 100644
--- a/ioriot/src/utils/futils.h
+++ b/ioriot/src/utils/futils.h
@@ -77,6 +77,15 @@ int mkdir_p(const char *path, mode_t mode, long *num_dirs_created);
void append_random_to_file(char *path, unsigned long bytes);
/**
+ * @brief Writes random to a file at a given seek offset
+ *
+ * @param path The file path
+ * @param bytes The amount of bytes
+ * @param offset The seek offset in bytes
+ */
+void write_random_to_file(char *path, unsigned long bytes, off_t offset);
+
+/**
* @brief Ensures that a directory exists
*
* @param path The directory path
diff --git a/ioriot/src/utils/utils.c b/ioriot/src/utils/utils.c
index 4b41273..1ab995d 100644
--- a/ioriot/src/utils/utils.c
+++ b/ioriot/src/utils/utils.c
@@ -98,24 +98,26 @@ void set_limits_drop_root(const char *user)
(long long) SET_RLIMIT_NPROC)
}
- Put("Dropping root privileges to user '%s'", user);
- struct passwd *pw = getpwnam(user);
-
- /* process is running as root, drop privileges */
- if (setgid(pw->pw_gid) != 0) {
- Errno("Unable to drop group privileges!");
- }
- if (setuid(pw->pw_uid) != 0) {
- Errno("Unable to drop user privileges!");
+ if (!Eq("root", user)) {
+ Put("Dropping root privileges to user '%s'", user);
+ struct passwd *pw = getpwnam(user);
+
+ /* process is running as root, drop privileges */
+ if (setgid(pw->pw_gid) != 0) {
+ Errno("Unable to drop group privileges!");
+ }
+ if (setuid(pw->pw_uid) != 0) {
+ Errno("Unable to drop user privileges!");
+ }
}
}
/*
- getrlimit(RLIMIT_NOFILE, &rl);
- Put("Max open files: '%lld'", (long long) rl.rlim_cur);
- getrlimit(RLIMIT_NPROC, &rl);
- Put("Max open processes : '%lld'", (long long) rl.rlim_cur);
- */
+ getrlimit(RLIMIT_NOFILE, &rl);
+ Put("Max open files: '%lld'", (long long) rl.rlim_cur);
+ getrlimit(RLIMIT_NPROC, &rl);
+ Put("Max open processes : '%lld'", (long long) rl.rlim_cur);
+ */
}
void get_loadavg_s(char *readbuf)
@@ -153,19 +155,19 @@ void start_pthread(pthread_t *thread, void*(*cb)(void*), void *data)
int rc = pthread_create(thread, NULL, cb, data);
switch (rc) {
- case 0:
- break;
- case EAGAIN:
- Error("Out of resources while creating pthread (%d)", rc);
- break;
- case EINVAL:
- Error("Ivalid settings while creating pthread (%d)", rc);
- break;
- case EPERM:
- Error("No permissions to configure pthread (%d)", rc);
- default:
- Error("Unknown error while creating pthread (%d)", rc);
- break;
+ case 0:
+ break;
+ case EAGAIN:
+ Error("Out of resources while creating pthread (%d)", rc);
+ break;
+ case EINVAL:
+ Error("Ivalid settings while creating pthread (%d)", rc);
+ break;
+ case EPERM:
+ Error("No permissions to configure pthread (%d)", rc);
+ default:
+ Error("Unknown error while creating pthread (%d)", rc);
+ break;
}
}
diff --git a/ioriot/tags b/ioriot/tags
deleted file mode 100644
index 65fdc50..0000000
--- a/ioriot/tags
+++ /dev/null
@@ -1,661 +0,0 @@
-!_TAG_FILE_FORMAT 2 /extended format; --format=1 will not append ;" to lines/
-!_TAG_FILE_SORTED 1 /0=unsorted, 1=sorted, 2=foldcase/
-!_TAG_PROGRAM_AUTHOR Darren Hiebert /dhiebert@users.sourceforge.net/
-!_TAG_PROGRAM_NAME Exuberant Ctags //
-!_TAG_PROGRAM_URL http://ctags.sourceforge.net /official site/
-!_TAG_PROGRAM_VERSION 5.8 //
-AMAP_H ./src/datas/amap.h 2;" d
-AMAP_MAX_ARRAY_LENGTH ./src/datas/amap.h 6;" d
-Abs ./src/macros.h 13;" d
-BTREE_H ./src/datas/btree.h 2;" d
-CAPTURE_VERSION ./src/defaults.h 7;" d
-CHMOD ./src/opcodes.h /^ CHMOD = 100,$/;" e enum:__anon1
-CHOWN ./src/opcodes.h /^ CHOWN = 110,$/;" e enum:__anon1
-CHOWN16 ./src/opcodes.h /^ CHOWN16,$/;" e enum:__anon1
-CLEANUP_H ./src/cleanup/cleanup.h 2;" d
-CLOSE ./src/opcodes.h /^ CLOSE = 50,$/;" e enum:__anon1
-CREAT ./src/opcodes.h /^ CREAT,$/;" e enum:__anon1
-Calloc ./src/macros.h 23;" d
-Cleanup ./src/macros.h 4;" d
-Cleanup_unless ./src/macros.h 5;" d
-Clone ./src/macros.h 9;" d
-Cmapshared ./src/macros.h 36;" d
-DEFAULTS_H ./src/defaults.h 2;" d
-Debug ./src/macros.h 51;" d
-ERROR ./src/defaults.h /^ ERROR, \/**< An error happened :-( *\/$/;" e enum:status_e_
-Eq ./src/macros.h 10;" d
-Errno ./src/macros.h 68;" d
-Errno_if ./src/macros.h 77;" d
-Error ./src/macros.h 58;" d
-Error_if ./src/macros.h 66;" d
-F ./src/generate/gtask.h /^ int F; \/**< Arguments for fcntl syscall *\/$/;" m struct:gtask_s_
-FCHMOD ./src/opcodes.h /^ FCHMOD,$/;" e enum:__anon1
-FCHMODAT ./src/opcodes.h /^ FCHMODAT,$/;" e enum:__anon1
-FCHOWN ./src/opcodes.h /^ FCHOWN,$/;" e enum:__anon1
-FCHOWN16 ./src/opcodes.h /^ FCHOWN16,$/;" e enum:__anon1
-FCHOWNAT ./src/opcodes.h /^ FCHOWNAT,$/;" e enum:__anon1
-FCNTL ./src/opcodes.h /^ FCNTL = 70,$/;" e enum:__anon1
-FDATASYNC ./src/opcodes.h /^ FDATASYNC,$/;" e enum:__anon1
-FSTAT ./src/opcodes.h /^ FSTAT = 0,$/;" e enum:__anon1
-FSTATFS ./src/opcodes.h /^ FSTATFS,$/;" e enum:__anon1
-FSTATFS64 ./src/opcodes.h /^ FSTATFS64,$/;" e enum:__anon1
-FSTAT_AT ./src/opcodes.h /^ FSTAT_AT,$/;" e enum:__anon1
-FSYNC ./src/opcodes.h /^ FSYNC = 60,$/;" e enum:__anon1
-FUTILS_H ./src/utils/futils.h 2;" d
-Fill_with_stuff ./src/macros.h 98;" d
-Fopen ./src/macros.h 29;" d
-G ./src/generate/gtask.h /^ int G; \/**< Arguments for fcntl syscall *\/$/;" m struct:gtask_s_
-GENERATE_H ./src/generate/generate.h 2;" d
-GETDENTS ./src/opcodes.h /^ GETDENTS,$/;" e enum:__anon1
-GIOOP_H ./src/generate/gioop.h 2;" d
-GPARSER_H ./src/generate/gparser.h 2;" d
-GPROCESS_H ./src/generate/gprocess.h 2;" d
-GTASK_H ./src/generate/gtask.h 2;" d
-GWRITER_H ./src/generate/gwriter.h 2;" d
-Gioop_write ./src/generate/gioop.h 12;" d
-HMAP_H ./src/datas/hmap.h 2;" d
-Has ./src/macros.h 17;" d
-Hasnt ./src/macros.h 18;" d
-INIT_H ./src/init/init.h 2;" d
-IORIOT_COPYRIGHT ./src/defaults.h 19;" d
-IORIOT_VERSION ./src/defaults.h 17;" d
-ITASK_H ./src/init/itask.h 2;" d
-ITHREAD_H ./src/init/ithread.h 2;" d
-LCHOWN ./src/opcodes.h /^ LCHOWN,$/;" e enum:__anon1
-LCOWN16 ./src/opcodes.h /^ LCOWN16,$/;" e enum:__anon1
-LIST_H ./src/datas/list.h 2;" d
-LSEEK ./src/opcodes.h /^ LSEEK,$/;" e enum:__anon1
-LSTAT ./src/opcodes.h /^ LSTAT,$/;" e enum:__anon1
-MACROS_H ./src/macros.h 2;" d
-MAX_LINE_LEN ./src/defaults.h 13;" d
-MAX_MOUNTPOINTS ./src/mounts.h 8;" d
-MAX_TOKENS ./src/defaults.h 11;" d
-META_EXIT ./src/opcodes.h /^ META_EXIT = 900,$/;" e enum:__anon1
-META_EXIT_GROUP ./src/opcodes.h /^ META_EXIT_GROUP,$/;" e enum:__anon1
-META_H ./src/meta/meta.h 2;" d
-META_TIMELINE ./src/opcodes.h /^ META_TIMELINE$/;" e enum:__anon1
-MKDIR ./src/opcodes.h /^ MKDIR,$/;" e enum:__anon1
-MKDIR_AT ./src/opcodes.h /^ MKDIR_AT,$/;" e enum:__anon1
-MMAP2 ./src/opcodes.h /^ MMAP2 = 80,$/;" e enum:__anon1
-MOUNTPOINTS_H ./src/mounts.h 2;" d
-MSYNC ./src/opcodes.h /^ MSYNC,$/;" e enum:__anon1
-MUNMAP ./src/opcodes.h /^ MUNMAP,$/;" e enum:__anon1
-Malloc ./src/macros.h 21;" d
-Mmapshared ./src/macros.h 32;" d
-Mset ./src/macros.h 25;" d
-NAME_TO_HANDLE_AT ./src/opcodes.h /^ NAME_TO_HANDLE_AT,$/;" e enum:__anon1
-OPCODES_H ./src/opcodes.h 2;" d
-OPEN ./src/opcodes.h /^ OPEN = 30,$/;" e enum:__anon1
-OPEN_AT ./src/opcodes.h /^ OPEN_AT,$/;" e enum:__anon1
-OPEN_BY_HANDLE_AT ./src/opcodes.h /^ OPEN_BY_HANDLE_AT,$/;" e enum:__anon1
-OPTIONS_H ./src/options.h 2;" d
-Out ./src/macros.h 42;" d
-Put ./src/macros.h 45;" d
-RBUFFER_H ./src/datas/rbuffer.h 2;" d
-READ ./src/opcodes.h /^ READ = 10,$/;" e enum:__anon1
-READAHEAD ./src/opcodes.h /^ READAHEAD,$/;" e enum:__anon1
-READDIR ./src/opcodes.h /^ READDIR,$/;" e enum:__anon1
-READLINK ./src/opcodes.h /^ READLINK,$/;" e enum:__anon1
-READLINK_AT ./src/opcodes.h /^ READLINK_AT,$/;" e enum:__anon1
-READV ./src/opcodes.h /^ READV,$/;" e enum:__anon1
-REMAP ./src/opcodes.h /^ REMAP,$/;" e enum:__anon1
-RENAME ./src/opcodes.h /^ RENAME = 40,$/;" e enum:__anon1
-RENAME_AT ./src/opcodes.h /^ RENAME_AT,$/;" e enum:__anon1
-RENAME_AT2 ./src/opcodes.h /^ RENAME_AT2,$/;" e enum:__anon1
-REPLAY_H ./src/replay/replay.h 2;" d
-REPLAY_VERSION ./src/defaults.h 9;" d
-RIOOP_H ./src/replay/rioop.h 2;" d
-RMDIR ./src/opcodes.h /^ RMDIR,$/;" e enum:__anon1
-RPROCESS_H ./src/replay/rprocess.h 2;" d
-RTASK_H ./src/replay/rtask.h 2;" d
-RTHREAD_H ./src/replay/rthread.h 9;" d
-RWORKER_H ./src/replay/rworker.h 2;" d
-Readhex ./src/macros.h 14;" d
-STACK_H ./src/datas/stack.h 2;" d
-STAT ./src/opcodes.h /^ STAT,$/;" e enum:__anon1
-STATFS ./src/opcodes.h /^ STATFS,$/;" e enum:__anon1
-STATFS64 ./src/opcodes.h /^ STATFS64,$/;" e enum:__anon1
-SUCCESS ./src/defaults.h /^ SUCCESS, \/**< Great success! *\/$/;" e enum:status_e_
-SYNC ./src/opcodes.h /^ SYNC,$/;" e enum:__anon1
-SYNCFS ./src/opcodes.h /^ SYNCFS,$/;" e enum:__anon1
-SYNC_FILE_RANGE ./src/opcodes.h /^ SYNC_FILE_RANGE,$/;" e enum:__anon1
-Segfault ./src/macros.h 79;" d
-TASK_BUFFER_PER_THREAD ./src/defaults.h 15;" d
-UNKNOWN ./src/defaults.h /^ UNKNOWN, \/**< Unknown return status :-\/ *\/$/;" e enum:status_e_
-UNLINK ./src/opcodes.h /^ UNLINK,$/;" e enum:__anon1
-UNLINK_AT ./src/opcodes.h /^ UNLINK_AT,$/;" e enum:__anon1
-UTESTS_H ./src/utests.h 2;" d
-UTILS_H ./src/utils/utils.h 2;" d
-VFD_H ./src/vfd.h 2;" d
-VSIZE_H ./src/generate/vsize.h 2;" d
-WRITE ./src/opcodes.h /^ WRITE = 20,$/;" e enum:__anon1
-WRITEV ./src/opcodes.h /^ WRITEV,$/;" e enum:__anon1
-Warn ./src/macros.h 88;" d
-Warn_if ./src/macros.h 95;" d
-_Errno ./src/replay/rioop.c 15;" d file:
-_Error ./src/replay/rioop.c 7;" d file:
-_GNU_SOURCE ./src/utils/utils.h 5;" d
-_Init_arg ./src/replay/rioop.c 24;" d file:
-_Init_bytes ./src/replay/rioop.c 36;" d file:
-_Init_cmd ./src/replay/rioop.c 25;" d file:
-_Init_fd ./src/replay/rioop.c 26;" d file:
-_Init_flags ./src/replay/rioop.c 27;" d file:
-_Init_offset ./src/replay/rioop.c 29;" d file:
-_Init_op ./src/replay/rioop.c 30;" d file:
-_Init_path ./src/replay/rioop.c 32;" d file:
-_Init_path2 ./src/replay/rioop.c 31;" d file:
-_Init_rc ./src/replay/rioop.c 33;" d file:
-_Init_virtfd ./src/replay/rioop.c 40;" d file:
-_Init_whence ./src/replay/rioop.c 34;" d file:
-_MAX_META_LEN ./src/meta/meta.c 3;" d file:
-_MAX_PROCESSES ./src/generate/generate.c 10;" d file:
-_PATH_INSERT ./src/mounts.c 5;" d file:
-_PATH_INSERT_LEN ./src/mounts.c 6;" d file:
-_Perc_filtered ./src/generate/generate.c 12;" d file:
-_Set_dir ./src/generate/vsize.c 8;" d file:
-_Set_file ./src/generate/vsize.c 7;" d file:
-_Set_inserted ./src/generate/vsize.c 10;" d file:
-_Set_renamed ./src/generate/vsize.c 11;" d file:
-_Set_required ./src/generate/vsize.c 12;" d file:
-_Set_unsure ./src/generate/vsize.c 9;" d file:
-_Using_string_keys ./src/datas/hmap.c 3;" d file:
-_amap_new ./src/datas/amap.c /^static amap_s *_amap_new(long size, bool mmapped)$/;" f file:
-_amap_test ./src/datas/amap.c /^void _amap_test(amap_s *a)$/;" f
-_arch_check_atomic ./src/main.c /^static void _arch_check_atomic(void)$/;" f file:
-_gprocess_vfd_map_destroy_cb ./src/generate/gprocess.c /^void _gprocess_vfd_map_destroy_cb(void *data)$/;" f
-_hmap_new ./src/datas/hmap.c /^hmap_s *_hmap_new(unsigned int init_size)$/;" f
-_hmap_test ./src/datas/hmap.c /^static void _hmap_test(hmap_s *h)$/;" f file:
-_hmap_test_l ./src/datas/hmap.c /^static void _hmap_test_l(hmap_s *h)$/;" f file:
-_list_elem_remove ./src/datas/list.c /^void _list_elem_remove(list_s *l, list_elem_s *e)$/;" f
-_print_help ./src/main.c /^static void _print_help(void)$/;" f file:
-_print_synopsis ./src/main.c /^static void _print_synopsis(void)$/;" f file:
-_print_version ./src/main.c /^static void _print_version(void)$/;" f file:
-_rprocess_destroy_cb ./src/replay/rworker.c /^static void _rprocess_destroy_cb(void *data)$/;" f file:
-_rthread_init_log ./src/replay/rthread.c /^static void _rthread_init_log(rthread_s *t)$/;" f file:
-absolute_path ./src/utils/futils.c /^char *absolute_path(const char *path)$/;" f
-address ./src/generate/gtask.h /^ long address; \/**< An address (used by mmap related syscalls) *\/$/;" m struct:gtask_s_
-address2 ./src/generate/gtask.h /^ long address2; \/**< Another address (used by mmap related syscalls) *\/$/;" m struct:gtask_s_
-amap_destroy ./src/datas/amap.c /^void amap_destroy(amap_s* a)$/;" f
-amap_get ./src/datas/amap.c /^void* amap_get(amap_s *a, const long position)$/;" f
-amap_new ./src/datas/amap.c /^amap_s* amap_new(const long size)$/;" f
-amap_new_mmapped ./src/datas/amap.c /^amap_s* amap_new_mmapped(const long size)$/;" f
-amap_print ./src/datas/amap.c /^void amap_print(amap_s* a)$/;" f
-amap_reset ./src/datas/amap.c /^void amap_reset(amap_s* a)$/;" f
-amap_run_cb ./src/datas/amap.c /^void amap_run_cb(amap_s *a, void (*cb)(void *data))$/;" f
-amap_s ./src/datas/amap.h /^} amap_s;$/;" t typeref:struct:amap_s_
-amap_s_ ./src/datas/amap.h /^typedef struct amap_s_ {$/;" s
-amap_set ./src/datas/amap.c /^int amap_set(amap_s *a, const long position, void* value)$/;" f
-amap_test ./src/datas/amap.c /^void amap_test(void)$/;" f
-amap_unset ./src/datas/amap.c /^void* amap_unset(amap_s *a, const long position)$/;" f
-append_random_to_file ./src/utils/futils.c /^void append_random_to_file(char *path, unsigned long bytes)$/;" f
-arrays ./src/datas/amap.h /^ void*** arrays; \/**< The pointers to the amap arrays *\/$/;" m struct:amap_s_
-btree_destroy ./src/datas/btree.c /^void btree_destroy(btree_s* b)$/;" f
-btree_destroy2 ./src/datas/btree.c /^void btree_destroy2(btree_s* b)$/;" f
-btree_get ./src/datas/btree.c /^void* btree_get(btree_s* b, int key)$/;" f
-btree_insert ./src/datas/btree.c /^int btree_insert(btree_s* b, int key, void *data)$/;" f
-btree_new ./src/datas/btree.c /^btree_s* btree_new()$/;" f
-btree_print ./src/datas/btree.c /^void btree_print(btree_s* b)$/;" f
-btree_s ./src/datas/btree.h /^} btree_s;$/;" t typeref:struct:btree_s_
-btree_s_ ./src/datas/btree.h /^typedef struct btree_s_ {$/;" s
-btreelem_ ./src/datas/btree.h /^typedef struct btreelem_ {$/;" s
-btreelem_destroy_r ./src/datas/btree.c /^void btreelem_destroy_r(btreelem_s* e)$/;" f
-btreelem_destroy_r2 ./src/datas/btree.c /^void btreelem_destroy_r2(btreelem_s* e)$/;" f
-btreelem_get_r ./src/datas/btree.c /^void* btreelem_get_r(btreelem_s* e, int key)$/;" f
-btreelem_insert_r ./src/datas/btree.c /^int btreelem_insert_r(btreelem_s* e, int key, void *data)$/;" f
-btreelem_new ./src/datas/btree.c /^btreelem_s* btreelem_new(int key, void *data)$/;" f
-btreelem_print_r ./src/datas/btree.c /^void btreelem_print_r(btreelem_s* e, int depth)$/;" f
-btreelem_s ./src/datas/btree.h /^} btreelem_s;$/;" t typeref:struct:btreelem_
-bytes ./src/generate/gtask.h /^ long bytes; \/**< Amount of bytes *\/$/;" m struct:gtask_s_
-cache_file ./src/utils/futils.c /^void cache_file(const char *file)$/;" f
-capture_file ./src/options.h /^ char *capture_file; \/**< The name of the .capture file *\/$/;" m struct:options_s_
-chown_path ./src/utils/futils.c /^void chown_path(const char *user, const char *path)$/;" f
-chreplace ./src/utils/utils.c /^void chreplace(char *str, char replace, char with)$/;" f
-cleanup_run ./src/cleanup/cleanup.c /^status_e cleanup_run(options_s *opts)$/;" f
-clone ./src/replay/rtask.h /^ char *clone; \/**< Used for debug purposes only *\/$/;" m struct:rtask_s_
-count ./src/generate/gtask.h /^ long count; \/**< A count *\/$/;" m struct:gtask_s_
-count ./src/mounts.h /^ int count; \/**< The amount of mount points *\/$/;" m struct:mounts_s_
-data ./src/datas/btree.h /^ void *data; \/**< A pointer to the data stored in this element *\/$/;" m struct:btreelem_
-data ./src/datas/hmap.h /^ void **data; \/**< Pointers to the stored data, NULL if nothing there *\/$/;" m struct:hmap_s_
-data ./src/datas/list.h /^ void *data; \/**< Pointer to the stored data *\/$/;" m struct:list_elem_s_
-data ./src/datas/stack.h /^ void *data; \/**< Pointer to the stored data in the current element *\/$/;" m struct:stack_elem_s_
-data_destroy ./src/datas/amap.h /^ void (*data_destroy)(void *data); \/**< Callback to destroy all elements *\/$/;" m struct:amap_s_
-data_destroy ./src/datas/hmap.h /^ void (*data_destroy)(void *data); \/**< Callback to destroy all data *\/$/;" m struct:hmap_s_
-data_destroy ./src/datas/list.h /^ void (*data_destroy)(void *data); \/**< Callback to destroy all data *\/$/;" m struct:list_s_
-debug ./src/vfd.h /^ int debug; \/**< Used for debugging purposes only *\/$/;" m struct:vfd_s_
-dirfd ./src/vfd.h /^ DIR *dirfd; \/**< The real dirfd *\/$/;" m struct:vfd_s_
-dirname_r ./src/utils/futils.c /^char* dirname_r(char *path)$/;" f
-dirs_created ./src/init/itask.h /^ long dirs_created;$/;" m struct:itask_s_
-drop_caches ./src/options.h /^ bool drop_caches; \/**< True if ioriot should drop all Linux caches *\/$/;" m struct:options_s_
-drop_caches ./src/utils/futils.c /^void drop_caches(void)$/;" f
-drop_root ./src/utils/utils.c /^void drop_root(const char *user)$/;" f
-ensure_dir_empty ./src/utils/futils.c /^void ensure_dir_empty(const char *path)$/;" f
-ensure_dir_exists ./src/utils/futils.c /^long ensure_dir_exists(const char *path)$/;" f
-ensure_file_exists ./src/utils/futils.c /^int ensure_file_exists(char *path, long *num_dirs_created)$/;" f
-ensure_parent_dir_exists ./src/utils/futils.c /^void ensure_parent_dir_exists(const char *path)$/;" f
-exists ./src/utils/futils.c /^bool exists(const char *path)$/;" f
-fd ./src/generate/gtask.h /^ int fd; \/**< File descriptor number *\/$/;" m struct:gtask_s_
-fd ./src/vfd.h /^ int fd; \/**< the real fd *\/$/;" m struct:vfd_s_
-fd_map ./src/generate/gprocess.h /^ hmap_s *fd_map; \/**< All mappings from real fd to virtual fd *\/$/;" m struct:gprocess_s_
-fds_map ./src/replay/rprocess.h /^ amap_s *fds_map; \/**< Holding all file descriptors *\/$/;" m struct:rprocess_s_
-fds_map ./src/replay/rworker.h /^ amap_s* fds_map; \/**< Holding all file descriptors *\/$/;" m struct:__anon2
-files_created ./src/init/itask.h /^ long files_created;$/;" m struct:itask_s_
-filtered_where ./src/generate/gtask.h /^ char *filtered_where; \/**< Only used for debugging purposes *\/$/;" m struct:gtask_s_
-first ./src/datas/list.h /^ list_elem_s *first; \/**< The first element, NULL if list empty *\/$/;" m struct:list_s_
-flags ./src/generate/gtask.h /^ int flags; \/**< File open flags *\/$/;" m struct:gtask_s_
-fnotnull ./src/utils/utils.c /^FILE* fnotnull(FILE *fd, const char *path, char *file, int line)$/;" f
-free_path ./src/vfd.h /^ bool free_path; \/**< True if path has to be freed or not *\/$/;" m struct:vfd_s_
-generate ./src/generate/gparser.h /^ generate_s *generate; \/**< The generate object *\/$/;" m struct:gparser_s_
-generate ./src/generate/gtask.h /^ void *generate; \/**< A pointer to the generate object *\/$/;" m struct:gtask_s_
-generate ./src/generate/gwriter.h /^ struct generate_s_ *generate; \/**< The generate object *\/$/;" m struct:gwriter_s_ typeref:struct:gwriter_s_::generate_s_
-generate ./src/generate/vsize.h /^ void *generate; \/**< A pointer to the generate object *\/$/;" m struct:vsize_s_
-generate_destroy ./src/generate/generate.c /^void generate_destroy(generate_s *g)$/;" f
-generate_gprocess_by_realpid ./src/generate/generate.c /^void generate_gprocess_by_realpid(generate_s *g, gtask_s *t)$/;" f
-generate_new ./src/generate/generate.c /^generate_s* generate_new(options_s *opts)$/;" f
-generate_run ./src/generate/generate.c /^status_e generate_run(options_s *opts)$/;" f
-generate_s ./src/generate/generate.h /^} generate_s;$/;" t typeref:struct:generate_s_
-generate_s_ ./src/generate/generate.h /^typedef struct generate_s_ {$/;" s
-generate_vsize_by_path ./src/generate/generate.c /^vsize_s* generate_vsize_by_path(generate_s *g, gtask_s *t,$/;" f
-generate_write_init_cb ./src/generate/generate.c /^void generate_write_init_cb(void *data)$/;" f
-get_loadavg ./src/utils/utils.c /^void get_loadavg(char *readbuf)$/;" f
-gioop_chmod ./src/generate/gioop.c /^status_e gioop_chmod(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_chown ./src/generate/gioop.c /^status_e gioop_chown(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_close ./src/generate/gioop.c /^status_e gioop_close(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_close_all_vfd_cb ./src/generate/gioop.c /^void gioop_close_all_vfd_cb(void *data, void *data2)$/;" f
-gioop_creat ./src/generate/gioop.c /^status_e gioop_creat(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_exit_group ./src/generate/gioop.c /^status_e gioop_exit_group(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_fchmod ./src/generate/gioop.c /^status_e gioop_fchmod(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_fchown ./src/generate/gioop.c /^status_e gioop_fchown(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_fcntl ./src/generate/gioop.c /^status_e gioop_fcntl(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_fdatasync ./src/generate/gioop.c /^status_e gioop_fdatasync(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_fstat ./src/generate/gioop.c /^status_e gioop_fstat(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_fstatat ./src/generate/gioop.c /^status_e gioop_fstatat(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_fstatfs ./src/generate/gioop.c /^status_e gioop_fstatfs(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_fstatfs64 ./src/generate/gioop.c /^status_e gioop_fstatfs64(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_fsync ./src/generate/gioop.c /^status_e gioop_fsync(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_getdents ./src/generate/gioop.c /^status_e gioop_getdents(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_lchown ./src/generate/gioop.c /^status_e gioop_lchown(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_lseek ./src/generate/gioop.c /^status_e gioop_lseek(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_lstat ./src/generate/gioop.c /^status_e gioop_lstat(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_mkdir ./src/generate/gioop.c /^status_e gioop_mkdir(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_mkdirat ./src/generate/gioop.c /^status_e gioop_mkdirat(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_open ./src/generate/gioop.c /^status_e gioop_open(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_openat ./src/generate/gioop.c /^status_e gioop_openat(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_read ./src/generate/gioop.c /^status_e gioop_read(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_readahead ./src/generate/gioop.c /^status_e gioop_readahead(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_readdir ./src/generate/gioop.c /^status_e gioop_readdir(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_readlink ./src/generate/gioop.c /^status_e gioop_readlink(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_readlinkat ./src/generate/gioop.c /^status_e gioop_readlinkat(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_readv ./src/generate/gioop.c /^status_e gioop_readv(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_rename ./src/generate/gioop.c /^status_e gioop_rename(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_renameat ./src/generate/gioop.c /^status_e gioop_renameat(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_renameat2 ./src/generate/gioop.c /^status_e gioop_renameat2(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_rmdir ./src/generate/gioop.c /^status_e gioop_rmdir(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_run ./src/generate/gioop.c /^status_e gioop_run(gwriter_s *w, gtask_s *t)$/;" f
-gioop_stat ./src/generate/gioop.c /^status_e gioop_stat(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_statfs ./src/generate/gioop.c /^status_e gioop_statfs(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_statfs64 ./src/generate/gioop.c /^status_e gioop_statfs64(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_sync ./src/generate/gioop.c /^status_e gioop_sync(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_sync_file_range ./src/generate/gioop.c /^status_e gioop_sync_file_range(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_syncfs ./src/generate/gioop.c /^status_e gioop_syncfs(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_unlink ./src/generate/gioop.c /^status_e gioop_unlink(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_unlinkat ./src/generate/gioop.c /^status_e gioop_unlinkat(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_write ./src/generate/gioop.c /^status_e gioop_write(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gioop_writev ./src/generate/gioop.c /^status_e gioop_writev(gwriter_s *w, gtask_s *t, generate_s *g)$/;" f
-gparser_destroy ./src/generate/gparser.c /^void gparser_destroy(gparser_s *p)$/;" f
-gparser_extract ./src/generate/gparser.c /^void gparser_extract(gparser_s *p, gtask_s *t)$/;" f
-gparser_extract_tok ./src/generate/gparser.c /^status_e gparser_extract_tok(gparser_s *p, gtask_s *t, char *tok)$/;" f
-gparser_get_pidtid ./src/generate/gparser.c /^bool gparser_get_pidtid(gparser_s *p, char *pidtid, long *pid, long *tid)$/;" f
-gparser_new ./src/generate/gparser.c /^gparser_s* gparser_new(generate_s *g)$/;" f
-gparser_pthread_start ./src/generate/gparser.c /^void* gparser_pthread_start(void *data)$/;" f
-gparser_s ./src/generate/gparser.h /^} gparser_s;$/;" t typeref:struct:gparser_s_
-gparser_s_ ./src/generate/gparser.h /^typedef struct gparser_s_ {$/;" s
-gparser_start ./src/generate/gparser.c /^void gparser_start(gparser_s *p)$/;" f
-gparser_terminate ./src/generate/gparser.c /^void gparser_terminate(gparser_s *p)$/;" f
-gparser_token_not_ok ./src/generate/gparser.c /^bool gparser_token_not_ok(gparser_s *p, char *tok)$/;" f
-gprocess ./src/generate/gtask.h /^ struct gprocess_s_ *gprocess; \/**< A pointer to the process object *\/$/;" m struct:gtask_s_ typeref:struct:gtask_s_::gprocess_s_
-gprocess_create_vfd_by_realfd ./src/generate/gprocess.c /^void gprocess_create_vfd_by_realfd(gprocess_s *gp, gtask_s *t, generate_s *g)$/;" f
-gprocess_destroy ./src/generate/gprocess.c /^void gprocess_destroy(gprocess_s *gp)$/;" f
-gprocess_new ./src/generate/gprocess.c /^gprocess_s* gprocess_new(const long pid, const long mapped_pid)$/;" f
-gprocess_s ./src/generate/gprocess.h /^} gprocess_s;$/;" t typeref:struct:gprocess_s_
-gprocess_s_ ./src/generate/gprocess.h /^typedef struct gprocess_s_ {$/;" s
-gprocess_vfd_by_realfd ./src/generate/gprocess.c /^status_e gprocess_vfd_by_realfd(gprocess_s *gp, gtask_s *t)$/;" f
-gtask_destroy ./src/generate/gtask.c /^void gtask_destroy(gtask_s *t)$/;" f
-gtask_init ./src/generate/gtask.c /^void gtask_init(gtask_s *t, char *line, const unsigned long lineno)$/;" f
-gtask_new ./src/generate/gtask.c /^gtask_s* gtask_new(void *generate)$/;" f
-gtask_s ./src/generate/gtask.h /^} gtask_s;$/;" t typeref:struct:gtask_s_
-gtask_s_ ./src/generate/gtask.h /^typedef struct gtask_s_ {$/;" s
-gwriter_destroy ./src/generate/gwriter.c /^void gwriter_destroy(gwriter_s *w)$/;" f
-gwriter_new ./src/generate/gwriter.c /^gwriter_s* gwriter_new(generate_s *g)$/;" f
-gwriter_pthread_start ./src/generate/gwriter.c /^void* gwriter_pthread_start(void *data)$/;" f
-gwriter_s ./src/generate/gwriter.h /^} gwriter_s;$/;" t typeref:struct:gwriter_s_
-gwriter_s_ ./src/generate/gwriter.h /^typedef struct gwriter_s_ {$/;" s
-gwriter_start ./src/generate/gwriter.c /^void gwriter_start(gwriter_s *w)$/;" f
-gwriter_terminate ./src/generate/gwriter.c /^void gwriter_terminate(gwriter_s *w)$/;" f
-has_fd ./src/generate/gtask.h /^ bool has_fd; \/**< True if task has a file descriptor number *\/$/;" m struct:gtask_s_
-hmap_destroy ./src/datas/hmap.c /^void hmap_destroy(hmap_s *h)$/;" f
-hmap_get ./src/datas/hmap.c /^void* hmap_get(hmap_s *h, char *key)$/;" f
-hmap_get_addr ./src/datas/hmap.c /^unsigned int hmap_get_addr(hmap_s *h, char *key)$/;" f
-hmap_get_addr_l ./src/datas/hmap.c /^unsigned int hmap_get_addr_l(hmap_s *h, const long key)$/;" f
-hmap_get_l ./src/datas/hmap.c /^void* hmap_get_l(hmap_s *h, const long key)$/;" f
-hmap_insert ./src/datas/hmap.c /^int hmap_insert(hmap_s *h, char *key, void *data)$/;" f
-hmap_insert_l ./src/datas/hmap.c /^int hmap_insert_l(hmap_s *h, const long key, void *data)$/;" f
-hmap_new ./src/datas/hmap.c /^hmap_s *hmap_new(unsigned int init_size)$/;" f
-hmap_new_l ./src/datas/hmap.c /^hmap_s *hmap_new_l(unsigned int init_size)$/;" f
-hmap_print ./src/datas/hmap.c /^void hmap_print(hmap_s *h)$/;" f
-hmap_remove ./src/datas/hmap.c /^void* hmap_remove(hmap_s *h, char *key)$/;" f
-hmap_remove_l ./src/datas/hmap.c /^void* hmap_remove_l(hmap_s *h, const long key)$/;" f
-hmap_run_cb ./src/datas/hmap.c /^void hmap_run_cb(hmap_s* h, void (*cb)(void *data))$/;" f
-hmap_run_cb2 ./src/datas/hmap.c /^void hmap_run_cb2(hmap_s* h, void (*cb)(void *data, void *data2), void *data_)$/;" f
-hmap_s ./src/datas/hmap.h /^} hmap_s;$/;" t typeref:struct:hmap_s_
-hmap_s_ ./src/datas/hmap.h /^typedef struct hmap_s_ {$/;" s
-hmap_test ./src/datas/hmap.c /^void hmap_test(void)$/;" f
-id ./src/generate/vsize.h /^ unsigned long id; \/**< The vsize id *\/$/;" m struct:vsize_s_
-ignore_count ./src/mounts.h /^ int ignore_count; \/**< The amount of ignored mount points *\/$/;" m struct:mounts_s_
-ignore_mps ./src/mounts.h /^ char *ignore_mps[MAX_MOUNTPOINTS]; \/**< The ignored mp paths *\/$/;" m struct:mounts_s_
-init ./src/init/ithread.h /^ init_s *init; \/**< The responsible init object *\/$/;" m struct:ithread_s_
-init ./src/options.h /^ bool init; \/**< If set ioriot will initialise the environment *\/$/;" m struct:options_s_
-init_destroy ./src/init/init.c /^void init_destroy(init_s *i)$/;" f
-init_extract_header ./src/init/init.c /^void init_extract_header(init_s *i, off_t *init_offset)$/;" f
-init_new ./src/init/init.c /^init_s *init_new(options_s *opts)$/;" f
-init_parent_dir ./src/generate/vsize.c /^void init_parent_dir(vsize_s *v, const char *path)$/;" f
-init_run ./src/init/init.c /^status_e init_run(options_s *opts)$/;" f
-init_s ./src/init/init.h /^} init_s;$/;" t typeref:struct:init_s_
-init_s_ ./src/init/init.h /^typedef struct init_s_ {$/;" s
-initm ./src/replay/rprocess.h /^ bool initm; \/**< Indicates whether ioriot is in init mode or not *\/$/;" m struct:rprocess_s_
-inserted ./src/generate/vsize.h /^ bool inserted; \/**< For debugging purposes only *\/$/;" m struct:vsize_s_
-is_dir ./src/generate/vsize.h /^ bool is_dir; \/**< True if this file\/dir is a directory *\/$/;" m struct:vsize_s_
-is_dir ./src/init/itask.h /^ bool is_dir;$/;" m struct:itask_s_
-is_dir ./src/utils/futils.c /^bool is_dir(const char *path)$/;" f
-is_file ./src/generate/vsize.h /^ bool is_file; \/**< True if this file\/dir is a regular file *\/$/;" m struct:vsize_s_
-is_file ./src/init/itask.h /^ bool is_file;$/;" m struct:itask_s_
-is_number ./src/utils/utils.c /^bool is_number(char *str)$/;" f
-is_reg ./src/utils/futils.c /^bool is_reg(const char *path)$/;" f
-itask_destroy ./src/init/itask.c /^void itask_destroy(itask_s *task)$/;" f
-itask_extract_stats ./src/init/itask.c /^void itask_extract_stats(itask_s *task, long* dirs_created, long *files_created,$/;" f
-itask_new ./src/init/itask.c /^itask_s* itask_new()$/;" f
-itask_print ./src/init/itask.c /^void itask_print(itask_s *task)$/;" f
-itask_reset_stats ./src/init/itask.c /^void itask_reset_stats(itask_s *task)$/;" f
-itask_s ./src/init/itask.h /^} itask_s;$/;" t typeref:struct:itask_s_
-itask_s_ ./src/init/itask.h /^typedef struct itask_s_ {$/;" s
-ithread_destroy ./src/init/ithread.c /^void ithread_destroy(ithread_s *t)$/;" f
-ithread_new ./src/init/ithread.c /^ithread_s* ithread_new(init_s *i)$/;" f
-ithread_pthread_start ./src/init/ithread.c /^void* ithread_pthread_start(void *data)$/;" f
-ithread_run_task ./src/init/ithread.c /^void ithread_run_task(ithread_s *t, itask_s *task)$/;" f
-ithread_s ./src/init/ithread.h /^} ithread_s;$/;" t typeref:struct:ithread_s_
-ithread_s_ ./src/init/ithread.h /^typedef struct ithread_s_ {$/;" s
-ithread_start ./src/init/ithread.c /^void ithread_start(ithread_s *t)$/;" f
-ithread_terminate ./src/init/ithread.c /^void ithread_terminate(ithread_s *t)$/;" f
-key ./src/datas/btree.h /^ int key; \/**< The key of the element *\/$/;" m struct:btreelem_
-key ./src/datas/list.h /^ char *key; \/**< The key of the lemenet *\/$/;" m struct:list_elem_s_
-key_l ./src/datas/list.h /^ long key_l; \/**< The same as key, but for long keys *\/$/;" m struct:list_elem_s_
-keys ./src/datas/hmap.h /^ char **keys; \/**< List of all keys, NULL if nothing at a address *\/$/;" m struct:hmap_s_
-keys_l ./src/datas/hmap.h /^ int *keys_l; \/**< Same as keys, but for long keys *\/$/;" m struct:hmap_s_
-l ./src/datas/hmap.h /^ list_s **l; \/**< Pointers to the linked lists, used on hash collision *\/$/;" m struct:hmap_s_
-left ./src/datas/btree.h /^ struct btreelem_ *left; \/**< The next element to the left *\/$/;" m struct:btreelem_ typeref:struct:btreelem_::btreelem_
-lengths ./src/mounts.h /^ int lengths[MAX_MOUNTPOINTS]; \/**< The mp lenghts *\/$/;" m struct:mounts_s_
-line ./src/generate/gtask.h /^ char *line; \/**< A pointer to the remaining part of the .capture line *\/$/;" m struct:gtask_s_
-line ./src/replay/rtask.h /^ char line[MAX_LINE_LEN]; \/**< The remaining part of the .replay line *\/$/;" m struct:rtask_s_
-lineno ./src/generate/generate.h /^ long lineno; \/**< The current line number *\/$/;" m struct:generate_s_
-lineno ./src/generate/gtask.h /^ long lineno; \/**< The current line number *\/$/;" m struct:gtask_s_
-lineno ./src/replay/rprocess.h /^ unsigned long lineno; \/**< Holding the current .replay line number *\/$/;" m struct:rprocess_s_
-lineno ./src/replay/rtask.h /^ unsigned long lineno; \/**< The current line number *\/$/;" m struct:rtask_s_
-list_destroy ./src/datas/list.c /^void list_destroy(list_s *l)$/;" f
-list_elem_s ./src/datas/list.h /^} list_elem_s;$/;" t typeref:struct:list_elem_s_
-list_elem_s_ ./src/datas/list.h /^typedef struct list_elem_s_ {$/;" s
-list_key_get ./src/datas/list.c /^void* list_key_get(list_s *l, char *key)$/;" f
-list_key_get_l ./src/datas/list.c /^void* list_key_get_l(list_s *l, const long key)$/;" f
-list_key_insert ./src/datas/list.c /^int list_key_insert(list_s *l, char *key, void *data)$/;" f
-list_key_insert_l ./src/datas/list.c /^int list_key_insert_l(list_s *l, const long key, void *data)$/;" f
-list_key_remove ./src/datas/list.c /^void* list_key_remove(list_s *l, char *key)$/;" f
-list_key_remove_l ./src/datas/list.c /^void* list_key_remove_l(list_s *l, const long key)$/;" f
-list_new ./src/datas/list.c /^list_s *list_new()$/;" f
-list_new_l ./src/datas/list.c /^list_s *list_new_l()$/;" f
-list_print ./src/datas/list.c /^void list_print(list_s *l)$/;" f
-list_run_cb ./src/datas/list.c /^void list_run_cb(list_s* l, void (*cb)(void *data))$/;" f
-list_run_cb2 ./src/datas/list.c /^void list_run_cb2(list_s* l, void (*cb)(void *data, void *data2), void *data_)$/;" f
-list_s ./src/datas/list.h /^} list_s;$/;" t typeref:struct:list_s_
-list_s_ ./src/datas/list.h /^typedef struct list_s_ {$/;" s
-list_test ./src/datas/list.c /^void list_test(void)$/;" f
-main ./src/main.c /^int main(int argc, char **argv)$/;" f
-mapped_fd ./src/generate/gtask.h /^ long mapped_fd; \/**< The mapped file descriptor number *\/$/;" m struct:gtask_s_
-mapped_fd ./src/vfd.h /^ long mapped_fd; \/**< The mapped fd (virtual fd) *\/$/;" m struct:vfd_s_
-mapped_pid ./src/generate/gprocess.h /^ long mapped_pid; \/**< The mapped PID *\/$/;" m struct:gprocess_s_
-mapped_time ./src/generate/gtask.h /^ long mapped_time; \/**< The mapped time *\/$/;" m struct:gtask_s_
-max_mapped_fd ./src/generate/gprocess.h /^ long max_mapped_fd; \/**< The max mapped fd number *\/$/;" m struct:gprocess_s_
-meta_destroy ./src/meta/meta.c /^void meta_destroy(meta_s *m)$/;" f
-meta_new ./src/meta/meta.c /^meta_s* meta_new(FILE *replay_fd)$/;" f
-meta_read_l ./src/meta/meta.c /^bool meta_read_l(meta_s *m, char *key, long *val)$/;" f
-meta_read_s ./src/meta/meta.c /^bool meta_read_s(meta_s *m, char *key, char **val)$/;" f
-meta_read_start ./src/meta/meta.c /^void meta_read_start(meta_s *m)$/;" f
-meta_reserve ./src/meta/meta.c /^void meta_reserve(meta_s *m)$/;" f
-meta_s ./src/meta/meta.h /^} meta_s;$/;" t typeref:struct:meta_s_
-meta_s_ ./src/meta/meta.h /^typedef struct meta_s_ {$/;" s
-meta_write_l ./src/meta/meta.c /^void meta_write_l(meta_s *m, char *key, long val)$/;" f
-meta_write_s ./src/meta/meta.c /^void meta_write_s(meta_s *m, char *key, char *val)$/;" f
-meta_write_start ./src/meta/meta.c /^void meta_write_start(meta_s *m)$/;" f
-mkdir_p ./src/utils/futils.c /^int mkdir_p(const char *path, mode_t mode, long *num_dirs_created)$/;" f
-mmap_map ./src/generate/generate.h /^ hmap_s *mmap_map; \/**< mmap address mappings *\/$/;" m struct:generate_s_
-mmapok ./src/utils/utils.c /^void* mmapok(void *p, char *file, int line)$/;" f
-mmapped ./src/datas/amap.h /^ bool mmapped; \/**< True if amap is memory mapped *\/$/;" m struct:amap_s_
-mode ./src/generate/gtask.h /^ int mode; \/**< File open mode *\/$/;" m struct:gtask_s_
-mounts ./src/init/init.h /^ mounts_s *mounts;$/;" m struct:init_s_
-mounts_destroy ./src/mounts.c /^void mounts_destroy(mounts_s *m)$/;" f
-mounts_get_mountnumber ./src/mounts.c /^int mounts_get_mountnumber(mounts_s *m, const char *path)$/;" f
-mounts_ignore_path ./src/mounts.c /^bool mounts_ignore_path(mounts_s *m, const char *path)$/;" f
-mounts_init ./src/mounts.c /^void mounts_init(mounts_s *m)$/;" f
-mounts_new ./src/mounts.c /^mounts_s *mounts_new(options_s *opts)$/;" f
-mounts_purge ./src/mounts.c /^void mounts_purge(mounts_s *m)$/;" f
-mounts_read ./src/mounts.c /^void mounts_read(mounts_s *m)$/;" f
-mounts_s ./src/mounts.h /^} mounts_s;$/;" t typeref:struct:mounts_s_
-mounts_s_ ./src/mounts.h /^typedef struct mounts_s_ {$/;" s
-mounts_transform_path ./src/mounts.c /^bool mounts_transform_path(mounts_s *m, const char *name,$/;" f
-mounts_trash ./src/mounts.c /^void mounts_trash(mounts_s *m)$/;" f
-mps ./src/generate/generate.h /^ mounts_s *mps; \/**< The mounts object *\/$/;" m struct:generate_s_
-mps ./src/mounts.h /^ char *mps[MAX_MOUNTPOINTS]; \/**< The mp paths *\/$/;" m struct:mounts_s_
-name ./src/generate/generate.h /^ char *name; \/**< The name of the test specified by the user *\/$/;" m struct:generate_s_
-name ./src/options.h /^ char *name; \/**< The name of the test (found in .ioriot\/name sub-dirs) *\/$/;" m struct:options_s_
-next ./src/datas/list.h /^ struct list_elem_s_ *next; \/**< The next element *\/$/;" m struct:list_elem_s_ typeref:struct:list_elem_s_::list_elem_s_
-next ./src/datas/stack.h /^ struct stack_elem_s_ *next; \/**< The next element *\/$/;" m struct:stack_elem_s_ typeref:struct:stack_elem_s_::stack_elem_s_
-notnull ./src/utils/utils.c /^void* notnull(void *p, char *file, int line, int count)$/;" f
-num_arrays ./src/datas/amap.h /^ int num_arrays; \/**< The amount of arrays used in the amap *\/$/;" m struct:amap_s_
-num_lines_filtered ./src/generate/generate.h /^ long num_lines_filtered; \/**< The amount of lines filtered out *\/$/;" m struct:generate_s_
-num_mapped_fds ./src/generate/generate.h /^ unsigned long num_mapped_fds; \/**< The amount of mapped FDs *\/$/;" m struct:generate_s_
-num_mapped_pids ./src/generate/generate.h /^ unsigned long num_mapped_pids; \/**< The amount of mapped PIDs *\/$/;" m struct:generate_s_
-num_threads_per_worker ./src/options.h /^ int num_threads_per_worker; \/**< Max threads per worker processes *\/$/;" m struct:options_s_
-num_vsizes ./src/generate/generate.h /^ unsigned long num_vsizes; \/**< The amount of virtual sizes *\/$/;" m struct:generate_s_
-num_workers ./src/options.h /^ int num_workers; \/**< The amount of worker processes *\/$/;" m struct:options_s_
-offset ./src/generate/gtask.h /^ long offset; \/**< A offset *\/$/;" m struct:gtask_s_
-offset ./src/generate/vsize.h /^ off_t offset; \/**< The current file offset *\/$/;" m struct:vsize_s_
-offset ./src/meta/meta.h /^ off_t offset; \/**< The meta offset (usually 0) *\/$/;" m struct:meta_s_
-offset ./src/vfd.h /^ unsigned long offset; \/**< The current virtual file offset in bytes *\/$/;" m struct:vfd_s_
-op ./src/generate/gtask.h /^ char *op; \/**< Operation\/syscall name *\/$/;" m struct:gtask_s_
-opcode_e ./src/opcodes.h /^} opcode_e;$/;" t typeref:enum:__anon1
-options_destroy ./src/options.c /^void options_destroy(options_s *o)$/;" f
-options_new ./src/options.c /^options_s *options_new()$/;" f
-options_s ./src/options.h /^} options_s;$/;" t typeref:struct:options_s_
-options_s_ ./src/options.h /^typedef struct options_s_ {$/;" s
-opts ./src/generate/generate.h /^ options_s *opts; \/**< A pointer to the options object *\/$/;" m struct:generate_s_
-opts ./src/init/init.h /^ options_s *opts;$/;" m struct:init_s_
-opts ./src/mounts.h /^ options_s *opts; \/**< A pointer to the options object *\/$/;" m struct:mounts_s_
-opts ./src/replay/rworker.h /^ options_s *opts; \/**< To synchronise access to rthread_buffer *\/$/;" m struct:__anon2
-original_line ./src/generate/gtask.h /^ char *original_line; \/**< Only used for debugging purposes *\/$/;" m struct:gtask_s_
-path ./src/generate/gtask.h /^ char *path; \/**< Path name *\/$/;" m struct:gtask_s_
-path ./src/generate/vsize.h /^ char *path; \/**< The path to the file\/directory *\/$/;" m struct:vsize_s_
-path ./src/init/itask.h /^ char *path;$/;" m struct:itask_s_
-path ./src/vfd.h /^ char *path; \/**< The file path belonging to that fd *\/$/;" m struct:vfd_s_
-path2 ./src/generate/gtask.h /^ char *path2; \/**< A second path name (e.g. for rename) *\/$/;" m struct:gtask_s_
-path2_r ./src/generate/gtask.h /^ char *path2_r; \/**< Work around to track mallocs, so it can be freed *\/$/;" m struct:gtask_s_
-path_r ./src/generate/gtask.h /^ char *path_r; \/**< Work around to track mallocs, so it can be freed *\/$/;" m struct:gtask_s_
-pid ./src/generate/gprocess.h /^ long pid; \/**< The real PID *\/$/;" m struct:gprocess_s_
-pid ./src/generate/gtask.h /^ long pid; \/**< The process ID *\/$/;" m struct:gtask_s_
-pid ./src/replay/rprocess.h /^ int pid; \/**< The virtual process ID *\/$/;" m struct:rprocess_s_
-pid_map ./src/generate/generate.h /^ amap_s *pid_map; \/**< A map of all virtual process objects *\/$/;" m struct:generate_s_
-pidtid ./src/generate/gtask.h /^ char *pidtid; \/**< String representing pid:tid *\/$/;" m struct:gtask_s_
-prev ./src/datas/list.h /^ struct list_elem_s_ *prev; \/**< The previous element *\/$/;" m struct:list_elem_s_ typeref:struct:list_elem_s_::list_elem_s_
-process ./src/replay/rtask.h /^ void *process; \/* The responsible process object *\/$/;" m struct:rtask_s_
-pthread ./src/generate/gparser.h /^ pthread_t pthread; \/**< The posix thread *\/$/;" m struct:gparser_s_
-pthread ./src/generate/gwriter.h /^ pthread_t pthread; \/**< The posix thread *\/$/;" m struct:gwriter_s_
-pthread ./src/init/ithread.h /^ pthread_t pthread; \/**< We run the init tasks in concurrent pthreads *\/$/;" m struct:ithread_s_
-pthread ./src/replay/rthread.h /^ pthread_t pthread; \/**< We run the tasks in concurrent pthreads *\/$/;" m struct:rthread_s_
-purge ./src/options.h /^ bool purge; \/**< If set ioriot will purge the environment *\/$/;" m struct:options_s_
-queue ./src/generate/gparser.h /^ rbuffer_s *queue; \/**< A queue of task objects *\/$/;" m struct:gparser_s_
-queue ./src/generate/gwriter.h /^ rbuffer_s *queue; \/**< A queue of task objects *\/$/;" m struct:gwriter_s_
-queue ./src/init/ithread.h /^ rbuffer_s *queue; \/**< The thread's task queue *\/$/;" m struct:ithread_s_
-rbuffer_destroy ./src/datas/rbuffer.c /^void rbuffer_destroy(rbuffer_s *r)$/;" f
-rbuffer_get_next ./src/datas/rbuffer.c /^void* rbuffer_get_next(rbuffer_s* r)$/;" f
-rbuffer_has_next ./src/datas/rbuffer.c /^bool rbuffer_has_next(rbuffer_s* r)$/;" f
-rbuffer_insert ./src/datas/rbuffer.c /^bool rbuffer_insert(rbuffer_s* r, void *data)$/;" f
-rbuffer_new ./src/datas/rbuffer.c /^rbuffer_s *rbuffer_new(const int size)$/;" f
-rbuffer_print ./src/datas/rbuffer.c /^void rbuffer_print(rbuffer_s* r)$/;" f
-rbuffer_s ./src/datas/rbuffer.h /^} rbuffer_s;$/;" t typeref:struct:rbuffer_s_
-rbuffer_s_ ./src/datas/rbuffer.h /^typedef struct rbuffer_s_ {$/;" s
-rbuffer_test ./src/datas/rbuffer.c /^void rbuffer_test(void)$/;" f
-read_buf ./src/meta/meta.h /^ char* read_buf; \/**< Pointer to a read buffer *\/$/;" m struct:meta_s_
-read_pos ./src/datas/rbuffer.h /^ sig_atomic_t read_pos;$/;" m struct:rbuffer_s_
-renamed ./src/generate/vsize.h /^ bool renamed; \/**< True if file\/dir has been renamed *\/$/;" m struct:vsize_s_
-replay ./src/options.h /^ bool replay; \/**< If set ioriot will run\/replay the test *\/$/;" m struct:options_s_
-replay_extract_header ./src/replay/replay.c /^void replay_extract_header(options_s *opts, FILE *replay_fd, long *num_vsizes,$/;" f
-replay_fd ./src/generate/generate.h /^ FILE *replay_fd; \/**< The fd of the .replay file *\/$/;" m struct:generate_s_
-replay_fd ./src/init/init.h /^ FILE *replay_fd;$/;" m struct:init_s_
-replay_fd ./src/meta/meta.h /^ FILE* replay_fd; \/**< The FS of the .replay file *\/$/;" m struct:meta_s_
-replay_file ./src/options.h /^ char *replay_file; \/**< The name of the .replay file *\/$/;" m struct:options_s_
-replay_run ./src/replay/replay.c /^status_e replay_run(options_s *opts)$/;" f
-required ./src/generate/vsize.h /^ bool required; \/**< True if init mode will create this file\/dir *\/$/;" m struct:vsize_s_
-ret ./src/generate/gtask.h /^ int ret; \/**< ioriot process status, SUCCESS if everything is alright *\/$/;" m struct:gtask_s_
-reuse_queue ./src/generate/generate.h /^ rbuffer_s *reuse_queue; \/**< A task buffer, for reusing these *\/$/;" m struct:generate_s_
-reuse_queue ./src/init/init.h /^ rbuffer_s *reuse_queue;$/;" m struct:init_s_
-reuse_queue_mutex ./src/init/init.h /^ pthread_mutex_t reuse_queue_mutex;$/;" m struct:init_s_
-right ./src/datas/btree.h /^ struct btreelem_ *right; \/**< The next element to the right *\/$/;" m struct:btreelem_ typeref:struct:btreelem_::btreelem_
-ring ./src/datas/rbuffer.h /^ void **ring;$/;" m struct:rbuffer_s_
-rioop_chmod ./src/replay/rioop.c /^void rioop_chmod(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_chown ./src/replay/rioop.c /^void rioop_chown(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_close ./src/replay/rioop.c /^void rioop_close(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_fchmod ./src/replay/rioop.c /^void rioop_fchmod(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_fchown ./src/replay/rioop.c /^void rioop_fchown(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_fcntl ./src/replay/rioop.c /^void rioop_fcntl(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_fdatasync ./src/replay/rioop.c /^void rioop_fdatasync(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_fstat ./src/replay/rioop.c /^void rioop_fstat(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_fsync ./src/replay/rioop.c /^void rioop_fsync(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_getdents ./src/replay/rioop.c /^void rioop_getdents(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_lchown ./src/replay/rioop.c /^void rioop_lchown(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_lseek ./src/replay/rioop.c /^void rioop_lseek(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_mkdir ./src/replay/rioop.c /^void rioop_mkdir(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_open ./src/replay/rioop.c /^void rioop_open(rprocess_s *p, rthread_s *t, rtask_s *task, int flags_)$/;" f
-rioop_read ./src/replay/rioop.c /^void rioop_read(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_rename ./src/replay/rioop.c /^void rioop_rename(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_rmdir ./src/replay/rioop.c /^void rioop_rmdir(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_run ./src/replay/rioop.c /^void rioop_run(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_stat ./src/replay/rioop.c /^void rioop_stat(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_unlink ./src/replay/rioop.c /^void rioop_unlink(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-rioop_write ./src/replay/rioop.c /^void rioop_write(rprocess_s *p, rthread_s *t, rtask_s *task)$/;" f
-root ./src/datas/btree.h /^ btreelem_s *root; \/**< The root element *\/$/;" m struct:btree_s_
-rprocess_destroy ./src/replay/rprocess.c /^void rprocess_destroy(rprocess_s *p)$/;" f
-rprocess_map ./src/replay/rworker.h /^ amap_s* rprocess_map; \/**< Holding all processes handled by this worker *\/$/;" m struct:__anon2
-rprocess_new ./src/replay/rprocess.c /^rprocess_s* rprocess_new(const int pid, amap_s *fds_map)$/;" f
-rprocess_s ./src/replay/rprocess.h /^} rprocess_s;$/;" t typeref:struct:rprocess_s_
-rprocess_s_ ./src/replay/rprocess.h /^typedef struct rprocess_s_ {$/;" s
-rtask_destroy ./src/replay/rtask.c /^void rtask_destroy(rtask_s *task)$/;" f
-rtask_new ./src/replay/rtask.c /^rtask_s* rtask_new()$/;" f
-rtask_s ./src/replay/rtask.h /^} rtask_s;$/;" t typeref:struct:rtask_s_
-rtask_s_ ./src/replay/rtask.h /^typedef struct rtask_s_ {$/;" s
-rtask_update ./src/replay/rtask.c /^void rtask_update(rtask_s *task, void *worker, void *process, char *line,$/;" f
-rthread_buffer ./src/replay/rworker.h /^ rbuffer_s *rthread_buffer; \/**< Buffering idle threads to be reused *\/$/;" m struct:__anon2
-rthread_buffer_mutex ./src/replay/rworker.h /^ pthread_mutex_t rthread_buffer_mutex; \/**< Sync access to rthread_buffer *\/$/;" m struct:__anon2
-rthread_destroy ./src/replay/rthread.c /^void rthread_destroy(rthread_s *t)$/;" f
-rthread_fd ./src/replay/rthread.h /^ FILE *rthread_fd; \/**< Used for debugging purposes only *\/$/;" m struct:rthread_s_
-rthread_insert_task ./src/replay/rthread.c /^bool rthread_insert_task(rthread_s* t, rtask_s* task)$/;" f
-rthread_map ./src/replay/rworker.h /^ amap_s* rthread_map; \/**< Holding all threads handled by this worker *\/$/;" m struct:__anon2
-rthread_new ./src/replay/rthread.c /^rthread_s* rthread_new(const long tid, void *worker)$/;" f
-rthread_process_task ./src/replay/rthread.c /^void rthread_process_task(rthread_s* t, rtask_s *task,$/;" f
-rthread_pthread_start ./src/replay/rthread.c /^void *rthread_pthread_start(void *data)$/;" f
-rthread_s ./src/replay/rthread.h /^} rthread_s;$/;" t typeref:struct:rthread_s_
-rthread_s_ ./src/replay/rthread.h /^typedef struct rthread_s_ {$/;" s
-rthread_terminate ./src/replay/rthread.c /^void rthread_terminate(rthread_s* t)$/;" f
-rthread_update ./src/replay/rthread.c /^long rthread_update(rthread_s *t, const long tid)$/;" f
-rworker_destroy ./src/replay/rworker.c /^void rworker_destroy(rworker_s *w)$/;" f
-rworker_fd ./src/replay/rworker.h /^ FILE *rworker_fd; \/**< For debugging purposes only *\/$/;" m struct:__anon2
-rworker_new ./src/replay/rworker.c /^rworker_s* rworker_new(const int rworker_num, amap_s *fds_map,$/;" f
-rworker_num ./src/replay/rprocess.h /^ int rworker_num; \/**< The worker number of the responsible worker *\/$/;" m struct:rprocess_s_
-rworker_num ./src/replay/rworker.h /^ int rworker_num; \/**< The current worker ID *\/$/;" m struct:__anon2
-rworker_process_lines ./src/replay/rworker.c /^status_e rworker_process_lines(rworker_s* w, const long num_lines)$/;" f
-rworker_s ./src/replay/rworker.h /^} rworker_s;$/;" t typeref:struct:__anon2
-single_threaded ./src/replay/rthread.h /^ bool single_threaded; \/**< Worker is single threaded or not *\/$/;" m struct:rthread_s_
-size ./src/datas/amap.h /^ long size; \/**< The total size\/capacity of the amap *\/$/;" m struct:amap_s_
-size ./src/datas/btree.h /^ int size; \/**< The current size of the binary tree *\/$/;" m struct:btree_s_
-size ./src/datas/hmap.h /^ unsigned int size; \/**< Size of the hmap *\/$/;" m struct:hmap_s_
-size ./src/datas/rbuffer.h /^ int size;$/;" m struct:rbuffer_s_
-size ./src/datas/stack.h /^ unsigned long size; \/**< A count how many elements are in the stack *\/$/;" m struct:stack_s_
-sizes_created ./src/init/itask.h /^ long sizes_created;$/;" m struct:itask_s_
-speed_factor ./src/options.h /^ double speed_factor; \/**< Specifies how fast the test is replayed *\/$/;" m struct:options_s_
-stack_destroy ./src/datas/stack.c /^void stack_destroy(stack_s *s)$/;" f
-stack_elem_s ./src/datas/stack.h /^} stack_elem_s;$/;" t typeref:struct:stack_elem_s_
-stack_elem_s_ ./src/datas/stack.h /^typedef struct stack_elem_s_ {$/;" s
-stack_is_empty ./src/datas/stack.c /^int stack_is_empty(stack_s *s)$/;" f
-stack_new ./src/datas/stack.c /^stack_s *stack_new()$/;" f
-stack_new_reverse_from ./src/datas/stack.c /^stack_s* stack_new_reverse_from(stack_s *s)$/;" f
-stack_pop ./src/datas/stack.c /^void* stack_pop(stack_s *s)$/;" f
-stack_push ./src/datas/stack.c /^void stack_push(stack_s *s, void *data)$/;" f
-stack_s ./src/datas/stack.h /^} stack_s;$/;" t typeref:struct:stack_s_
-stack_s_ ./src/datas/stack.h /^typedef struct stack_s_ {$/;" s
-start_pthread ./src/utils/utils.c /^void start_pthread(pthread_t *thread, void*(*cb)(void*), void *data)$/;" f
-start_time ./src/generate/generate.h /^ long start_time; \/**< The start time from the .capture file *\/$/;" m struct:generate_s_
-status ./src/generate/gtask.h /^ int status; \/**< Operation\/syscall return status *\/$/;" m struct:gtask_s_
-status_e ./src/defaults.h /^} status_e;$/;" t typeref:enum:status_e_
-status_e_ ./src/defaults.h /^typedef enum status_e_ {$/;" g
-strtok2_r ./src/utils/utils.c /^char* strtok2_r(char *str, char *delim, char **saveptr)$/;" f
-strunquote ./src/utils/utils.c /^void strunquote(char *str)$/;" f
-task_buffer ./src/replay/rworker.h /^ rbuffer_s *task_buffer; \/**< Buffering thread tasks to be reused *\/$/;" m struct:__anon2
-task_buffer_mutex ./src/replay/rworker.h /^ pthread_mutex_t task_buffer_mutex; \/**< To sync access to task_buffer *\/$/;" m struct:__anon2
-tasks ./src/replay/rthread.h /^ rbuffer_s* tasks; \/**< Holds all outstanding tasks *\/$/;" m struct:rthread_s_
-terminate ./src/generate/gparser.h /^ bool terminate; \/**< The parser thread will terminate if set to true *\/$/;" m struct:gparser_s_
-terminate ./src/generate/gwriter.h /^ bool terminate; \/**< The writer thread will terminate if set to true *\/$/;" m struct:gwriter_s_
-terminate ./src/init/ithread.h /^ bool terminate; \/**< Indicates that thread can terminate *\/$/;" m struct:ithread_s_
-terminate ./src/replay/rprocess.h /^ int terminate; \/**< Indicates whether the worker is terminating or not *\/$/;" m struct:rprocess_s_
-terminate ./src/replay/rthread.h /^ bool terminate; \/**< True if thread shall terminate *\/$/;" m struct:rthread_s_
-threads_map ./src/init/init.h /^ amap_s *threads_map;$/;" m struct:init_s_
-tid ./src/generate/gtask.h /^ long tid; \/**< The thread ID *\/$/;" m struct:gtask_s_
-tid ./src/replay/rthread.h /^ long tid; \/**< The virtual thread id *\/$/;" m struct:rthread_s_
-toks ./src/replay/rtask.h /^ char *toks[MAX_TOKENS+1]; \/**< The tokens parsed from the .replay line *\/$/;" m struct:rtask_s_
-top ./src/datas/stack.h /^ stack_elem_s *top; \/**< The top element of the stack, NULL if empty *\/$/;" m struct:stack_s_
-trash ./src/options.h /^ bool trash; \/**< If set ioriot will trash the environment *\/$/;" m struct:options_s_
-unsure ./src/generate/vsize.h /^ bool unsure; \/**< True if the file type is not fully clear *\/$/;" m struct:vsize_s_
-updates ./src/generate/vsize.h /^ long updates; \/**< Amount of times this vsize has been updated *\/$/;" m struct:vsize_s_
-user ./src/options.h /^ char *user; \/**< The user name to run the test as *\/$/;" m struct:options_s_
-utests_run ./src/utests.c /^void utests_run()$/;" f
-vfd ./src/generate/gtask.h /^ vfd_s *vfd; \/**< A pointer to the virtual file descriptor *\/$/;" m struct:gtask_s_
-vfd_buffer ./src/generate/generate.h /^ rbuffer_s *vfd_buffer; \/**< A virtual fd buffer, for reusing these *\/$/;" m struct:generate_s_
-vfd_destroy ./src/vfd.c /^void vfd_destroy(vfd_s *vfd)$/;" f
-vfd_map ./src/generate/gprocess.h /^ hmap_s *vfd_map; \/**< All virtual file descriptors of that process *\/$/;" m struct:gprocess_s_
-vfd_new ./src/vfd.c /^vfd_s* vfd_new(const int fd, const long mapped_fd, char *path)$/;" f
-vfd_print ./src/vfd.c /^void vfd_print(vfd_s *vfd)$/;" f
-vfd_s ./src/vfd.h /^} vfd_s;$/;" t typeref:struct:vfd_s_
-vfd_s_ ./src/vfd.h /^typedef struct vfd_s_ {$/;" s
-vfd_update ./src/vfd.c /^void vfd_update(vfd_s *vfd, const int fd, const long mapped_fd, char *path)$/;" f
-vsize ./src/generate/gtask.h /^ vsize_s *vsize; \/**< Pointer to the virtual size object *\/$/;" m struct:gtask_s_
-vsize ./src/generate/vsize.h /^ long vsize; \/**< The virtual size *\/$/;" m struct:vsize_s_
-vsize ./src/init/itask.h /^ long vsize;$/;" m struct:itask_s_
-vsize ./src/replay/rtask.h /^ unsigned long vsize; \/**< The vsize *\/$/;" m struct:rtask_s_
-vsize2 ./src/generate/gtask.h /^ vsize_s *vsize2; \/**< Pointer to a second virtual size object *\/$/;" m struct:gtask_s_
-vsize_adjust ./src/generate/vsize.c /^void vsize_adjust(vsize_s *v, vfd_s* vfd)$/;" f
-vsize_close ./src/generate/vsize.c /^void vsize_close(vsize_s *v, void* vfd)$/;" f
-vsize_deficit ./src/generate/vsize.h /^ long vsize_deficit; \/**< Size to use for file creating during init mode *\/$/;" m struct:vsize_s_
-vsize_destroy ./src/generate/vsize.c /^void vsize_destroy(vsize_s *v)$/;" f
-vsize_map ./src/generate/generate.h /^ hmap_s *vsize_map; \/**< A hash map of all virtual size objects *\/$/;" m struct:generate_s_
-vsize_mkdir ./src/generate/vsize.c /^void vsize_mkdir(vsize_s *v, const char *path)$/;" f
-vsize_new ./src/generate/vsize.c /^vsize_s* vsize_new(char *file_path, const unsigned long id,$/;" f
-vsize_open ./src/generate/vsize.c /^void vsize_open(vsize_s *v, void *vfd, const char *path, const int flags)$/;" f
-vsize_read ./src/generate/vsize.c /^void vsize_read(vsize_s *v, void *vfd, const char *path, const int bytes)$/;" f
-vsize_rename ./src/generate/vsize.c /^void vsize_rename(vsize_s *v, vsize_s *v2,$/;" f
-vsize_rmdir ./src/generate/vsize.c /^void vsize_rmdir(vsize_s *v, const char *path)$/;" f
-vsize_s ./src/generate/vsize.h /^} vsize_s;$/;" t typeref:struct:vsize_s_
-vsize_s_ ./src/generate/vsize.h /^typedef struct vsize_s_ {$/;" s
-vsize_seek ./src/generate/vsize.c /^void vsize_seek(vsize_s *v, void *vfd, const long new_offset)$/;" f
-vsize_stat ./src/generate/vsize.c /^void vsize_stat(vsize_s *v, const char *path)$/;" f
-vsize_unlink ./src/generate/vsize.c /^void vsize_unlink(vsize_s *v, const char *path)$/;" f
-vsize_write ./src/generate/vsize.c /^void vsize_write(vsize_s *v, void *vfd, const char *path, const int bytes)$/;" f
-wd_base ./src/options.h /^ char *wd_base; \/**< The working directory base *\/$/;" m struct:options_s_
-whence ./src/generate/gtask.h /^ long whence; \/**< Whence *\/$/;" m struct:gtask_s_
-worker ./src/replay/rtask.h /^ void *worker; \/* The responsible worker object *\/$/;" m struct:rtask_s_
-worker ./src/replay/rthread.h /^ void *worker; \/**< The responsible worker object *\/$/;" m struct:rthread_s_
-write_pos ./src/datas/rbuffer.h /^ sig_atomic_t write_pos;$/;" m struct:rbuffer_s_
-writer ./src/generate/generate.h /^ struct gwriter_s_ *writer; \/**< A pointer to the writer object *\/$/;" m struct:generate_s_ typeref:struct:generate_s_::gwriter_s_
diff --git a/systemtap/src/ioriot.stp b/systemtap/src/ioriot.stp
index 9ea6a68..4029ebb 100644
--- a/systemtap/src/ioriot.stp
+++ b/systemtap/src/ioriot.stp
@@ -100,6 +100,20 @@ probe syscall.lseek.return {
}
}
+probe syscall.llseek.return {
+ if(execname() != "stapio") {
+ printf("t=%d;:,i=%d:%d;:,o=%s;:,d=%d;:,O=%d;:,W=%d;:,b=%d;:,\n",
+ gettimeofday_ms(),
+ pid(),
+ tid(),
+ name,
+ @entry($fd),
+ (@entry($offset_high) << 32 | @entry($offset_low)),
+ @entry($whence),
+ $return);
+ }
+}
+
probe syscall.fcntl.return {
if(execname() != "stapio") {
printf("t=%d;:,i=%d:%d;:,o=%s;:,d=%d;:,F=%d;:,G=%d;:,s=%d;:,\n",
diff --git a/systemtap/src/javaioriot.stp b/systemtap/src/javaioriot.stp
index 3943971..945ecf6 100644
--- a/systemtap/src/javaioriot.stp
+++ b/systemtap/src/javaioriot.stp
@@ -100,6 +100,20 @@ probe syscall.lseek.return {
}
}
+probe syscall.llseek.return {
+ if(execname() == "java") {
+ printf("t=%d;:,i=%d:%d;:,o=%s;:,d=%d;:,O=%d;:,W=%d;:,b=%d;:,\n",
+ gettimeofday_ms(),
+ pid(),
+ tid(),
+ name,
+ @entry($fd),
+ (@entry($offset_high) << 32 | @entry($offset_low)),
+ @entry($whence),
+ $return);
+ }
+}
+
probe syscall.fcntl.return {
if(execname() == "java") {
printf("t=%d;:,i=%d:%d;:,o=%s;:,d=%d;:,F=%d;:,G=%d;:,s=%d;:,\n",
diff --git a/systemtap/src/targetedioriot.stp b/systemtap/src/targetedioriot.stp
index f72dc66..ee3ee7a 100644
--- a/systemtap/src/targetedioriot.stp
+++ b/systemtap/src/targetedioriot.stp
@@ -100,6 +100,20 @@ probe syscall.lseek.return {
}
}
+probe syscall.llseek.return {
+ if(pid() == target()) {
+ printf("t=%d;:,i=%d:%d;:,o=%s;:,d=%d;:,O=%d;:,W=%d;:,b=%d;:,\n",
+ gettimeofday_ms(),
+ pid(),
+ tid(),
+ name,
+ @entry($fd),
+ (@entry($offset_high) << 32 | @entry($offset_low)),
+ @entry($whence),
+ $return);
+ }
+}
+
probe syscall.fcntl.return {
if(pid() == target()) {
printf("t=%d;:,i=%d:%d;:,o=%s;:,d=%d;:,F=%d;:,G=%d;:,s=%d;:,\n",