pw_log_string: Add backend
pw_log_string is similar to pw_log_basic in that it simply takes raw
data at logging callsites and pipes it to an extern C symbol. The
difference is that pw_log_string does NOT provide an implementation of
said C symbol. This allows string-based log handling to be dictated by
the project.
Change-Id: Id40262a090a1c17db25425389fe52dce3c546c39
Reviewed-on: https://pigweed-review.googlesource.com/c/pigweed/pigweed/+/77182
Reviewed-by: Carlos Chinchilla <cachinchilla@google.com>
Reviewed-by: Keir Mierle <keir@google.com>
Commit-Queue: Armando Montanez <amontanez@google.com>
diff --git a/docs/BUILD.gn b/docs/BUILD.gn
index 67ee306..84366b4 100644
--- a/docs/BUILD.gn
+++ b/docs/BUILD.gn
@@ -112,6 +112,7 @@
"$dir_pw_log_basic:docs",
"$dir_pw_log_null:docs",
"$dir_pw_log_rpc:docs",
+ "$dir_pw_log_string:docs",
"$dir_pw_log_tokenized:docs",
"$dir_pw_malloc:docs",
"$dir_pw_malloc_freelist:docs",
diff --git a/modules.gni b/modules.gni
index 8b9dc58..42a8e5a 100644
--- a/modules.gni
+++ b/modules.gni
@@ -68,6 +68,7 @@
dir_pw_log_basic = get_path_info("pw_log_basic", "abspath")
dir_pw_log_null = get_path_info("pw_log_null", "abspath")
dir_pw_log_rpc = get_path_info("pw_log_rpc", "abspath")
+ dir_pw_log_string = get_path_info("pw_log_string", "abspath")
dir_pw_log_tokenized = get_path_info("pw_log_tokenized", "abspath")
dir_pw_malloc = get_path_info("pw_malloc", "abspath")
dir_pw_malloc_freelist = get_path_info("pw_malloc_freelist", "abspath")
diff --git a/pw_log_string/BUILD.bazel b/pw_log_string/BUILD.bazel
new file mode 100644
index 0000000..933e3b9
--- /dev/null
+++ b/pw_log_string/BUILD.bazel
@@ -0,0 +1,37 @@
+# Copyright 2022 The Pigweed Authors
+#
+# Licensed under the Apache License, Version 2.0 (the "License"); you may not
+# use this file except in compliance with the License. You may obtain a copy of
+# the License at
+#
+# https://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+# License for the specific language governing permissions and limitations under
+# the License.
+
+load(
+ "//pw_build:pigweed.bzl",
+ "pw_cc_library",
+)
+
+package(default_visibility = ["//visibility:public"])
+
+licenses(["notice"])
+
+pw_cc_library(
+ name = "pw_log_string",
+ hdrs = [
+ "public/pw_log_string/log_string.h",
+ "public_overrides/pw_log_backend/log_backend.h",
+ ],
+ includes = [
+ "public",
+ "public_overrides",
+ ],
+ deps = [
+ "//pw_preprocessor",
+ ],
+)
diff --git a/pw_log_string/BUILD.gn b/pw_log_string/BUILD.gn
new file mode 100644
index 0000000..67ab903
--- /dev/null
+++ b/pw_log_string/BUILD.gn
@@ -0,0 +1,64 @@
+# Copyright 2022 The Pigweed Authors
+#
+# Licensed under the Apache License, Version 2.0 (the "License"); you may not
+# use this file except in compliance with the License. You may obtain a copy of
+# the License at
+#
+# https://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+# License for the specific language governing permissions and limitations under
+# the License.
+
+import("//build_overrides/pigweed.gni")
+
+import("$dir_pw_build/error.gni")
+import("$dir_pw_build/target_types.gni")
+import("$dir_pw_docgen/docs.gni")
+import("backend.gni")
+
+config("public_include_path") {
+ include_dirs = [ "public" ]
+}
+
+config("backend_config") {
+ include_dirs = [ "public_overrides" ]
+}
+
+# This source set only provides pw_log_string's backend interface. The implementation is
+# pulled in through pw_build_LINK_DEPS.
+pw_source_set("pw_log_string") {
+ public_configs = [
+ ":backend_config",
+ ":public_include_path",
+ ]
+ public = [
+ "public/pw_log_string/log_string.h",
+ "public_overrides/pw_log_backend/log_backend.h",
+ ]
+ public_deps = [ dir_pw_preprocessor ]
+}
+
+# The log backend deps that might cause circular dependencies, since
+# pw_log is so ubiquitous. These deps are kept separate so they can be
+# depended on from elsewhere.
+if (pw_log_string_BACKEND != "") {
+ pw_source_set("pw_log_string.impl") {
+ deps = [ pw_log_string_BACKEND ]
+ }
+} else {
+ pw_error("pw_log_string.impl") {
+ message = string_join(
+ " ",
+ [
+ "To use pw_log_string, please direct pw_log_string_BACKEND",
+ "to the source set that implements the C API.",
+ ])
+ }
+}
+
+pw_doc_group("docs") {
+ sources = [ "docs.rst" ]
+}
diff --git a/pw_log_string/CMakeLists.txt b/pw_log_string/CMakeLists.txt
new file mode 100644
index 0000000..dfb1810
--- /dev/null
+++ b/pw_log_string/CMakeLists.txt
@@ -0,0 +1,22 @@
+# Copyright 2022 The Pigweed Authors
+#
+# Licensed under the Apache License, Version 2.0 (the "License"); you may not
+# use this file except in compliance with the License. You may obtain a copy of
+# the License at
+#
+# https://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+# License for the specific language governing permissions and limitations under
+# the License.
+
+include($ENV{PW_ROOT}/pw_build/pigweed.cmake)
+
+pw_add_module_library(pw_log_string
+ IMPLEMENTS_FACADES
+ pw_log
+ PUBLIC_DEPS
+ pw_preprocessor
+)
diff --git a/pw_log_string/backend.gni b/pw_log_string/backend.gni
new file mode 100644
index 0000000..b6dd80e
--- /dev/null
+++ b/pw_log_string/backend.gni
@@ -0,0 +1,21 @@
+# Copyright 2022 The Pigweed Authors
+#
+# Licensed under the Apache License, Version 2.0 (the "License"); you may not
+# use this file except in compliance with the License. You may obtain a copy of
+# the License at
+#
+# https://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+# License for the specific language governing permissions and limitations under
+# the License.
+
+import("//build_overrides/pigweed.gni")
+
+declare_args() {
+ # The pw_log_string backend implements the pw_Log C API laid out by the
+ # pw_log_string module's implementation of the pw_log facade.
+ pw_log_string_BACKEND = ""
+}
diff --git a/pw_log_string/docs.rst b/pw_log_string/docs.rst
new file mode 100644
index 0000000..63d7fad
--- /dev/null
+++ b/pw_log_string/docs.rst
@@ -0,0 +1,30 @@
+.. _module-pw_log_string:
+
+=============
+pw_log_string
+=============
+``pw_log_string`` is a partial backend for ``pw_log``. This backend defines a
+C API that the ``PW_LOG_*`` macros will call out to. ``pw_log_string`` does not
+implement the C API, leaving projects to provide their own implementation.
+See ``pw_log_basic`` for a similar ``pw_log`` backend that also provides an
+implementation.
+
+As this module passes the log message, file name, and module name as a string to
+the handler function, it's relatively expensive and not well suited for
+space-constrained devices. This module is oriented towards usage on a host
+(e.g. a simulated device).
+
+---------------
+Getting started
+---------------
+This module is extremely minimal to set up:
+
+1. Implement ``pw_log_string_HandleMessage()``
+2. Set ``pw_log_BACKEND`` to ``"$dir_pw_log_string"``
+3. Set ``pw_log_string_BACKEND`` to point to the source set that implements
+ ``pw_log_string_HandleMessage()``
+
+What exactly ``pw_log_string_HandleMessage()`` should do is entirely up to the
+implementation. ``pw_log_basic``'s log handler is one example, but it's also
+possible to encode as protobuf and send over a TCP port, write to a file, or
+blink an LED to log as morse code.
diff --git a/pw_log_string/public/pw_log_string/log_string.h b/pw_log_string/public/pw_log_string/log_string.h
new file mode 100644
index 0000000..7200d8a
--- /dev/null
+++ b/pw_log_string/public/pw_log_string/log_string.h
@@ -0,0 +1,47 @@
+// Copyright 2022 The Pigweed Authors
+//
+// Licensed under the Apache License, Version 2.0 (the "License"); you may not
+// use this file except in compliance with the License. You may obtain a copy of
+// the License at
+//
+// https://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+// License for the specific language governing permissions and limitations under
+// the License.
+#pragma once
+
+#include "pw_preprocessor/arguments.h"
+#include "pw_preprocessor/compiler.h"
+#include "pw_preprocessor/util.h"
+
+PW_EXTERN_C_START
+
+// Log a message with the listed attributes.
+void pw_log_string_HandleMessage(int level,
+ unsigned int flags,
+ const char* module_name,
+ const char* file_name,
+ int line_number,
+ const char* message,
+ ...) PW_PRINTF_FORMAT(6, 7);
+
+PW_EXTERN_C_END
+
+// Log a message with many attributes included. This is a backend implementation
+// for the logging facade in pw_log/log.h.
+//
+// This is the log macro frontend that funnels everything into the C handler
+// above, pw_log_string_HandleMessage. It's not efficient at the callsite, since
+// it passes many arguments.
+#define PW_HANDLE_LOG(level, flags, message, ...) \
+ do { \
+ pw_log_string_HandleMessage((level), \
+ (flags), \
+ PW_LOG_MODULE_NAME, \
+ __FILE__, \
+ __LINE__, \
+ message PW_COMMA_ARGS(__VA_ARGS__)); \
+ } while (0)
diff --git a/pw_log_string/public_overrides/pw_log_backend/log_backend.h b/pw_log_string/public_overrides/pw_log_backend/log_backend.h
new file mode 100644
index 0000000..6bc92fe
--- /dev/null
+++ b/pw_log_string/public_overrides/pw_log_backend/log_backend.h
@@ -0,0 +1,16 @@
+// Copyright 2022 The Pigweed Authors
+//
+// Licensed under the Apache License, Version 2.0 (the "License"); you may not
+// use this file except in compliance with the License. You may obtain a copy of
+// the License at
+//
+// https://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+// License for the specific language governing permissions and limitations under
+// the License.
+#pragma once
+
+#include "pw_log_string/log_string.h"