summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJoel Stålnacke <joel@saker.fi>2024-10-13 14:32:14 +0300
committerJoel Stålnacke <joel@saker.fi>2024-10-13 14:32:14 +0300
commit11b2cfa087f5de09b97eb42fb219f563886f6d40 (patch)
tree215a8e65edc0b74a47da63a0c8230b8eadba060f
parent53a1cdf5bee2955995dfbf441f5354d1dcfc1e0c (diff)
Add libdjup logging
-rw-r--r--Djup.Native/LibDjup.cs6
-rw-r--r--Djup.Native/Types.cs12
-rw-r--r--client/Root.cs14
-rwxr-xr-xlib/build.sh2
-rw-r--r--lib/log.c56
-rw-r--r--lib/log.h23
-rw-r--r--lib/world.c1
7 files changed, 112 insertions, 2 deletions
diff --git a/Djup.Native/LibDjup.cs b/Djup.Native/LibDjup.cs
index fece18a..0ecf7a8 100644
--- a/Djup.Native/LibDjup.cs
+++ b/Djup.Native/LibDjup.cs
@@ -16,6 +16,12 @@ public static partial class LibDjup
[LibraryImport(LibraryName, EntryPoint = Prefix + nameof(get_vec2))]
public static partial Vec2 get_vec2();
+ [LibraryImport(LibraryName, EntryPoint = Prefix + nameof(log_set_output))]
+ public static partial Vec2 log_set_output([MarshalAs(UnmanagedType.FunctionPtr)] LoggerDelegate logger);
+
+ [LibraryImport(LibraryName, EntryPoint = Prefix + nameof(log_set_level))]
+ public static partial Vec2 log_set_level(LogLevel minLevel);
+
[LibraryImport(LibraryName, EntryPoint = Prefix + nameof(world_create))]
public static partial IntPtr world_create();
diff --git a/Djup.Native/Types.cs b/Djup.Native/Types.cs
index c930bd6..572277f 100644
--- a/Djup.Native/Types.cs
+++ b/Djup.Native/Types.cs
@@ -39,3 +39,15 @@ public struct Ball
public Vec2 Position { get; set; }
public Vec2 Velocity { get; set; }
}
+
+public enum LogLevel
+{
+ Trace,
+ Debug,
+ Info,
+ Warn,
+ Error,
+ Fatal
+}
+
+public delegate void LoggerDelegate(LogLevel level, string source, int line, string message);
diff --git a/client/Root.cs b/client/Root.cs
index e39a485..b565083 100644
--- a/client/Root.cs
+++ b/client/Root.cs
@@ -13,7 +13,19 @@ public partial class Root : Node2D
public unsafe override void _Ready()
{
RenderingServer.SetDefaultClearColor(Colors.LightGray);
-
+ LibDjup.log_set_output((level, source, line, msg) => {
+ string level_name = level switch
+ {
+ LogLevel.Trace => "trace",
+ LogLevel.Debug => "debug",
+ LogLevel.Info => "info",
+ LogLevel.Warn => "warn",
+ LogLevel.Error => "error",
+ LogLevel.Fatal => "fatal"
+ };
+ GD.Print($"libdjup {source}:{line} {level_name.PadLeft(5, ' ')}: {msg}");
+ });
+
native_world = LibDjup.world_create();
for (int i = 0; i < balls.Length; i++)
{
diff --git a/lib/build.sh b/lib/build.sh
index 8cf9d11..725c237 100755
--- a/lib/build.sh
+++ b/lib/build.sh
@@ -8,7 +8,7 @@ fail() {
CC=cc
CFLAGS="-std=c99 -Wall -Wextra -Wpedantic -D_POSIX_C_SOURCE=200809L"
LDFLAGS="-fPIC"
-SOURCES="test.c vec2.c world.c"
+SOURCES="test.c vec2.c world.c log.c"
output="build"
for arg ; do
diff --git a/lib/log.c b/lib/log.c
new file mode 100644
index 0000000..51ab107
--- /dev/null
+++ b/lib/log.c
@@ -0,0 +1,56 @@
+#include <stdarg.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <time.h>
+
+#include "log.h"
+
+/* Message buffer */
+#define MBUF_SIZE 512
+
+static void (*log_output)(int level, const char *source, int line, const char *msg) = NULL;
+static int min_level = LOGL_INFO;
+
+void
+dp_log_set_output(void (*output)(int, const char *, int, const char *))
+{
+ log_output = output;
+}
+
+void
+dp_log_set_level(int level)
+{
+ min_level = level;
+}
+
+void
+dp_log_write(int level, const char *source, int line, const char *fmt, ...)
+{
+ char mbuf[MBUF_SIZE];
+ char *msg;
+ va_list va;
+ int len;
+
+ if (level < min_level)
+ return;
+ if (!log_output)
+ return;
+
+ msg = mbuf;
+ va_start(va, fmt);
+ len = vsnprintf(msg, MBUF_SIZE, fmt, va);
+ va_end(va);
+
+ if (len >= MBUF_SIZE)
+ {
+ msg = (char *)malloc(len + 1);
+ va_start(va, fmt);
+ len = vsnprintf(msg, len + 1, fmt, va);
+ va_end(va);
+ }
+
+ log_output(level, source, line, msg);
+
+ if (msg != mbuf)
+ free(msg);
+}
diff --git a/lib/log.h b/lib/log.h
new file mode 100644
index 0000000..e1cdcb8
--- /dev/null
+++ b/lib/log.h
@@ -0,0 +1,23 @@
+#include <stdio.h>
+
+enum { LOGL_TRACE, LOGL_DEBUG, LOGL_INFO, LOGL_WARN, LOGL_ERROR, LOGL_FATAL };
+
+/*
+ * log_info("Hello %s!", "World");
+ * log_warn("warning");
+ */
+#define log_trace(...) dp_log_write(LOGL_TRACE, __FILE__, __LINE__, __VA_ARGS__)
+#define log_debug(...) dp_log_write(LOGL_DEBUG, __FILE__, __LINE__, __VA_ARGS__)
+#define log_info(...) dp_log_write(LOGL_INFO, __FILE__, __LINE__, __VA_ARGS__)
+#define log_warn(...) dp_log_write(LOGL_WARN, __FILE__, __LINE__, __VA_ARGS__)
+#define log_error(...) dp_log_write(LOGL_ERROR, __FILE__, __LINE__, __VA_ARGS__)
+#define log_fatal(...) dp_log_write(LOGL_FATAL, __FILE__, __LINE__, __VA_ARGS__)
+
+void dp_log_set_output(void (*)(int level, const char *source, int line, const char *msg));
+
+/*
+ * Sets the minimum log level. Level is inclusive.
+ */
+void dp_log_set_level(int level);
+
+void dp_log_write(int level, const char *source, int line, const char *fmt, ...);
diff --git a/lib/world.c b/lib/world.c
index 954aa94..34d7489 100644
--- a/lib/world.c
+++ b/lib/world.c
@@ -3,6 +3,7 @@
#include "types.h"
#include "world.h"
+#include "log.h"
struct world {
struct entity entities[WORLD_MAX_ENTITIES];