aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--include/serd/world.h10
-rw-r--r--src/world.c38
-rw-r--r--src/world.h4
-rw-r--r--test/meson.build1
-rw-r--r--test/test_world.c35
5 files changed, 86 insertions, 2 deletions
diff --git a/include/serd/world.h b/include/serd/world.h
index 22ae57ed..abf2999c 100644
--- a/include/serd/world.h
+++ b/include/serd/world.h
@@ -6,6 +6,7 @@
#include "serd/attributes.h"
#include "serd/error.h"
+#include "serd/node.h"
SERD_BEGIN_DECLS
@@ -32,6 +33,15 @@ SERD_API void
serd_world_free(SerdWorld* SERD_NULLABLE world);
/**
+ Return a unique blank node.
+
+ The returned node is valid only until the next time serd_world_get_blank()
+ is called or the world is destroyed.
+*/
+SERD_API const SerdNode* SERD_NONNULL
+serd_world_get_blank(SerdWorld* SERD_NONNULL world);
+
+/**
Set a function to be called when errors occur.
The `error_func` will be called with `handle` as its first argument. If
diff --git a/src/world.c b/src/world.c
index c3c3660f..ececd646 100644
--- a/src/world.c
+++ b/src/world.c
@@ -3,9 +3,12 @@
#include "world.h"
+#include "node.h"
#include "serd_config.h"
#include "system.h"
+#include "serd/string_view.h"
+
#if defined(USE_POSIX_FADVISE)
# include <fcntl.h>
#endif
@@ -14,6 +17,7 @@
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
+#include <string.h>
FILE*
serd_world_fopen(SerdWorld* world, const char* path, const char* mode)
@@ -83,13 +87,43 @@ serd_world_errorf(const SerdWorld* const world,
SerdWorld*
serd_world_new(void)
{
- return (SerdWorld*)calloc(1, sizeof(SerdWorld));
+ SerdWorld* world = (SerdWorld*)calloc(1, sizeof(SerdWorld));
+ SerdNode* blank_node = serd_new_blank(serd_string("b00000000000"));
+
+ if (!world || !blank_node) {
+ serd_node_free(blank_node);
+ free(world);
+ return NULL;
+ }
+
+ world->blank_node = blank_node;
+
+ return world;
}
void
serd_world_free(SerdWorld* const world)
{
- free(world);
+ if (world) {
+ serd_node_free(world->blank_node);
+ free(world);
+ }
+}
+
+const SerdNode*
+serd_world_get_blank(SerdWorld* const world)
+{
+#define BLANK_CHARS 12
+
+ char* buf = serd_node_buffer(world->blank_node);
+ memset(buf, 0, BLANK_CHARS + 1);
+
+ world->blank_node->length =
+ (size_t)snprintf(buf, BLANK_CHARS + 1, "b%u", ++world->next_blank_id);
+
+ return world->blank_node;
+
+#undef BLANK_CHARS
}
void
diff --git a/src/world.h b/src/world.h
index dd3d4043..b330d4e4 100644
--- a/src/world.h
+++ b/src/world.h
@@ -5,14 +5,18 @@
#define SERD_SRC_WORLD_H
#include "serd/error.h"
+#include "serd/node.h"
#include "serd/status.h"
#include "serd/world.h"
+#include <stdint.h>
#include <stdio.h>
struct SerdWorldImpl {
SerdErrorFunc error_func;
void* error_handle;
+ uint32_t next_blank_id;
+ SerdNode* blank_node;
};
/// Open a file configured for fast sequential reading
diff --git a/test/meson.build b/test/meson.build
index 0ee7cd23..efcb00f0 100644
--- a/test/meson.build
+++ b/test/meson.build
@@ -128,6 +128,7 @@ unit_tests = [
'string',
'syntax',
'uri',
+ 'world',
'writer',
]
diff --git a/test/test_world.c b/test/test_world.c
new file mode 100644
index 00000000..3f7f6ea6
--- /dev/null
+++ b/test/test_world.c
@@ -0,0 +1,35 @@
+// Copyright 2011-2020 David Robillard <d@drobilla.net>
+// SPDX-License-Identifier: ISC
+
+#undef NDEBUG
+
+#include "serd/node.h"
+#include "serd/world.h"
+
+#include <assert.h>
+#include <stdio.h>
+#include <string.h>
+
+static void
+test_get_blank(void)
+{
+ SerdWorld* world = serd_world_new();
+ char expected[12];
+
+ for (unsigned i = 0; i < 32; ++i) {
+ const SerdNode* blank = serd_world_get_blank(world);
+
+ snprintf(expected, sizeof(expected), "b%u", i + 1);
+ assert(!strcmp(serd_node_string(blank), expected));
+ }
+
+ serd_world_free(world);
+}
+
+int
+main(void)
+{
+ test_get_blank();
+
+ return 0;
+}