Wyatt Hepler | f9fb90f | 2020-09-30 18:59:33 -0700 | [diff] [blame] | 1 | .. _module-pw_protobuf_compiler: |
Alexei Frolov | 4a257c1 | 2020-03-02 14:09:42 -0800 | [diff] [blame] | 2 | |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 3 | -------------------- |
| 4 | pw_protobuf_compiler |
| 5 | -------------------- |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 6 | The Protobuf compiler module provides build system integration and wrapper |
| 7 | scripts for generating source code for Protobuf definitions. |
| 8 | |
Alexei Frolov | f39cd8b | 2020-04-13 17:59:20 -0700 | [diff] [blame] | 9 | Generator support |
| 10 | ================= |
Alexei Frolov | f39cd8b | 2020-04-13 17:59:20 -0700 | [diff] [blame] | 11 | Protobuf code generation is currently supported for the following generators: |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 12 | |
Alexei Frolov | 79b7cb0 | 2020-07-06 13:51:43 -0700 | [diff] [blame] | 13 | +-------------+----------------+-----------------------------------------------+ |
| 14 | | Generator | Code | Notes | |
| 15 | +-------------+----------------+-----------------------------------------------+ |
| 16 | | pw_protobuf | ``pwpb`` | Compiles using ``pw_protobuf``. | |
| 17 | +-------------+----------------+-----------------------------------------------+ |
Alexei Frolov | 79b7cb0 | 2020-07-06 13:51:43 -0700 | [diff] [blame] | 18 | | Nanopb | ``nanopb`` | Compiles using Nanopb. The build argument | |
| 19 | | | | ``dir_pw_third_party_nanopb`` must be set to | |
| 20 | | | | point to a local nanopb installation. | |
| 21 | +-------------+----------------+-----------------------------------------------+ |
Alexei Frolov | c912ea7 | 2020-10-26 08:43:27 -0700 | [diff] [blame] | 22 | | Nanopb RPC | ``nanopb_rpc`` | Compiles pw_rpc service and client code for | |
| 23 | | | | nanopb. Requires a nanopb installation. | |
| 24 | +-------------+----------------+-----------------------------------------------+ |
| 25 | | Raw RPC | ``raw_rpc`` | Compiles raw binary pw_rpc service code. | |
Alexei Frolov | 79b7cb0 | 2020-07-06 13:51:43 -0700 | [diff] [blame] | 26 | +-------------+----------------+-----------------------------------------------+ |
Alexei Frolov | a4c0aee | 2020-12-01 13:48:48 -0800 | [diff] [blame] | 27 | | Go | ``go`` | Compiles using the standard Go protobuf | |
| 28 | | | | plugin with gRPC service support. | |
| 29 | +-------------+----------------+-----------------------------------------------+ |
| 30 | | Python | ``python`` | Compiles using the standard Python protobuf | |
| 31 | | | | plugin, creating a ``pw_python_package``. | |
| 32 | +-------------+----------------+-----------------------------------------------+ |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 33 | |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 34 | GN template |
| 35 | =========== |
Armando Montanez | 377a68c | 2021-05-13 15:53:13 -0700 | [diff] [blame] | 36 | This module provides a ``pw_proto_library`` GN template that defines a |
| 37 | collection of protobuf files that should be compiled together. The template |
| 38 | creates a sub-target for each supported generator, named |
Alexei Frolov | b499d3f | 2020-10-28 13:00:08 -0700 | [diff] [blame] | 39 | ``<target_name>.<generator>``. These sub-targets generate their respective |
| 40 | protobuf code, and expose it to the build system appropriately (e.g. a |
| 41 | ``pw_source_set`` for C/C++). |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 42 | |
Alexei Frolov | b499d3f | 2020-10-28 13:00:08 -0700 | [diff] [blame] | 43 | For example, given the following target: |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 44 | |
Alexei Frolov | b499d3f | 2020-10-28 13:00:08 -0700 | [diff] [blame] | 45 | .. code-block:: |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 46 | |
| 47 | pw_proto_library("test_protos") { |
Wyatt Hepler | d517afc | 2021-02-03 19:40:08 -0800 | [diff] [blame] | 48 | sources = [ "my_test_protos/test.proto" ] |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 49 | } |
| 50 | |
Alexei Frolov | b499d3f | 2020-10-28 13:00:08 -0700 | [diff] [blame] | 51 | ``test_protos.pwpb`` compiles code for pw_protobuf, and ``test_protos.nanopb`` |
| 52 | compiles using Nanopb (if it's installed). |
| 53 | |
| 54 | Protobuf code is only generated when a generator sub-target is listed as a |
| 55 | dependency of another GN target. |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 56 | |
Wyatt Hepler | 4cdc3e7 | 2021-03-24 08:41:08 -0700 | [diff] [blame] | 57 | GN permits using abbreviated labels when the target name matches the directory |
| 58 | name (e.g. ``//foo`` for ``//foo:foo``). For consistency with this, the |
| 59 | sub-targets for each generator are aliased to the directory when the target name |
| 60 | is the same. For example, these two labels are equivalent: |
| 61 | |
| 62 | .. code-block:: |
| 63 | |
| 64 | //path/to/my_protos:my_protos.pwpb |
| 65 | //path/to/my_protos:pwpb |
| 66 | |
Wyatt Hepler | 2c6c0ba | 2021-04-07 09:50:23 -0700 | [diff] [blame] | 67 | ``pw_python_package`` subtargets are also available on the ``python`` subtarget: |
| 68 | |
| 69 | .. code-block:: |
| 70 | |
| 71 | //path/to/my_protos:my_protos.python.lint |
| 72 | //path/to/my_protos:python.lint |
| 73 | |
Armando Montanez | 377a68c | 2021-05-13 15:53:13 -0700 | [diff] [blame] | 74 | **Supported Codegen** |
| 75 | |
| 76 | GN supports the following compiled proto libraries via the specified |
| 77 | sub-targets generated by a ``pw_proto_library``. |
| 78 | |
| 79 | * ``${target_name}.pwpb`` - Generated C++ pw_protobuf code |
| 80 | * ``${target_name}.nanopb`` - Generated C++ nanopb code (requires Nanopb) |
| 81 | * ``${target_name}.nanopb_rpc`` - Generated C++ Nanopb pw_rpc code (requires |
| 82 | Nanopb) |
| 83 | * ``${target_name}.raw_rpc`` - Generated C++ raw pw_rpc code (no protobuf |
| 84 | library) |
| 85 | * ``${target_name}.go`` - Generated GO protobuf libraries |
| 86 | * ``${target_name}.python`` - Generated Python protobuf libraries |
| 87 | |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 88 | **Arguments** |
| 89 | |
Wyatt Hepler | 752d7d3 | 2021-03-02 09:02:23 -0800 | [diff] [blame] | 90 | * ``sources``: List of input .proto files. |
| 91 | * ``deps``: List of other pw_proto_library dependencies. |
| 92 | * ``inputs``: Other files on which the protos depend (e.g. nanopb ``.options`` |
| 93 | files). |
| 94 | * ``prefix``: A prefix to add to the source protos prior to compilation. For |
| 95 | example, a source called ``"foo.proto"`` with ``prefix = "nested"`` will be |
| 96 | compiled with protoc as ``"nested/foo.proto"``. |
| 97 | * ``strip_prefix``: Remove this prefix from the source protos. All source and |
| 98 | input files must be nested under this path. |
Wyatt Hepler | 4cdc3e7 | 2021-03-24 08:41:08 -0700 | [diff] [blame] | 99 | * ``python_package``: Label of Python package to which to add the proto modules. |
Wyatt Hepler | b2062fd | 2021-06-01 21:33:07 -0700 | [diff] [blame] | 100 | The .python subtarget will redirect to this package. |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 101 | |
| 102 | **Example** |
| 103 | |
Wyatt Hepler | 752d7d3 | 2021-03-02 09:02:23 -0800 | [diff] [blame] | 104 | .. code-block:: |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 105 | |
| 106 | import("$dir_pw_protobuf_compiler/proto.gni") |
| 107 | |
| 108 | pw_proto_library("my_protos") { |
| 109 | sources = [ |
Wyatt Hepler | d517afc | 2021-02-03 19:40:08 -0800 | [diff] [blame] | 110 | "my_protos/foo.proto", |
| 111 | "my_protos/bar.proto", |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 112 | ] |
| 113 | } |
| 114 | |
| 115 | pw_proto_library("my_other_protos") { |
Wyatt Hepler | 752d7d3 | 2021-03-02 09:02:23 -0800 | [diff] [blame] | 116 | sources = [ "some/other/path/baz.proto" ] # imports foo.proto |
| 117 | |
| 118 | # This removes the "some/other/path" prefix from the proto files. |
| 119 | strip_prefix = "some/other/path" |
| 120 | |
| 121 | # This adds the "my_other_protos/" prefix to the proto files. |
| 122 | prefix = "my_other_protos" |
Alexei Frolov | 8e30d46 | 2020-10-22 13:54:36 -0700 | [diff] [blame] | 123 | |
| 124 | # Proto libraries depend on other proto libraries directly. |
| 125 | deps = [ ":my_protos" ] |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 126 | } |
| 127 | |
| 128 | source_set("my_cc_code") { |
| 129 | sources = [ |
| 130 | "foo.cc", |
| 131 | "bar.cc", |
| 132 | "baz.cc", |
| 133 | ] |
Alexei Frolov | 8e30d46 | 2020-10-22 13:54:36 -0700 | [diff] [blame] | 134 | |
| 135 | # When depending on protos in a source_set, specify the generator suffix. |
| 136 | deps = [ ":my_other_protos.pwpb" ] |
Alexei Frolov | 942adf0 | 2019-12-11 17:07:28 -0800 | [diff] [blame] | 137 | } |
Wyatt Hepler | d517afc | 2021-02-03 19:40:08 -0800 | [diff] [blame] | 138 | |
Wyatt Hepler | 752d7d3 | 2021-03-02 09:02:23 -0800 | [diff] [blame] | 139 | From C++, ``baz.proto`` included as follows: |
| 140 | |
| 141 | .. code-block:: cpp |
| 142 | |
| 143 | #include "my_other_protos/baz.pwpb.h" |
| 144 | |
| 145 | From Python, ``baz.proto`` is imported as follows: |
| 146 | |
| 147 | .. code-block:: python |
| 148 | |
| 149 | from my_other_protos import baz_pb2 |
| 150 | |
Wyatt Hepler | d517afc | 2021-02-03 19:40:08 -0800 | [diff] [blame] | 151 | Proto file structure |
| 152 | -------------------- |
| 153 | Protobuf source files must be nested under another directory when they are |
Wyatt Hepler | 752d7d3 | 2021-03-02 09:02:23 -0800 | [diff] [blame] | 154 | compiled. This ensures that they can be packaged properly in Python. The first |
| 155 | directory is used as the Python package name, so must be unique across the |
| 156 | build. The ``prefix`` option may be used to set this directory. |
Wyatt Hepler | d517afc | 2021-02-03 19:40:08 -0800 | [diff] [blame] | 157 | |
Wyatt Hepler | 752d7d3 | 2021-03-02 09:02:23 -0800 | [diff] [blame] | 158 | Using ``prefix`` and ``strip_prefix`` together allows remapping proto files to |
| 159 | a completely different path. This can be useful when working with protos defined |
| 160 | in external libraries. For example, consider this proto library: |
| 161 | |
| 162 | .. code-block:: |
| 163 | |
| 164 | pw_proto_library("external_protos") { |
| 165 | sources = [ |
| 166 | "//other/external/some_library/src/protos/alpha.proto", |
| 167 | "//other/external/some_library/src/protos/beta.proto, |
| 168 | "//other/external/some_library/src/protos/internal/gamma.proto", |
| 169 | ] |
| 170 | strip_prefix = "//other/external/some_library/src/protos" |
| 171 | prefix = "some_library" |
| 172 | } |
| 173 | |
| 174 | These protos will be compiled by protoc as if they were in this file structure: |
| 175 | |
| 176 | .. code-block:: |
| 177 | |
| 178 | some_library/ |
| 179 | ├── alpha.proto |
| 180 | ├── beta.proto |
| 181 | └── internal |
| 182 | └── gamma.proto |
Wyatt Hepler | d517afc | 2021-02-03 19:40:08 -0800 | [diff] [blame] | 183 | |
Wyatt Hepler | dcfcecf | 2021-03-01 08:36:19 -0800 | [diff] [blame] | 184 | .. _module-pw_protobuf_compiler-add-to-python-package: |
| 185 | |
| 186 | Adding Python proto modules to an existing package |
| 187 | -------------------------------------------------- |
| 188 | By default, generated Python proto modules are organized into their own Python |
| 189 | package. These proto modules can instead be added to an existing Python package |
Wyatt Hepler | b847615 | 2021-04-06 15:28:32 -0700 | [diff] [blame] | 190 | declared with ``pw_python_package``. This is done by setting the |
Wyatt Hepler | dcfcecf | 2021-03-01 08:36:19 -0800 | [diff] [blame] | 191 | ``python_package`` argument on the ``pw_proto_library`` and the |
| 192 | ``proto_library`` argument on the ``pw_python_package``. |
| 193 | |
| 194 | For example, the protos declared in ``my_protos`` will be nested in the Python |
| 195 | package declared by ``my_package``. |
| 196 | |
| 197 | .. code-block:: |
| 198 | |
| 199 | pw_proto_library("my_protos") { |
| 200 | sources = [ "hello.proto ] |
| 201 | prefix = "foo" |
| 202 | python_package = ":my_package" |
| 203 | } |
| 204 | |
| 205 | pw_python_pacakge("my_package") { |
| 206 | generate_setup = { |
| 207 | name = "foo" |
| 208 | version = "1.0" |
| 209 | } |
| 210 | sources = [ "foo/cool_module.py" ] |
| 211 | proto_library = ":my_protos" |
| 212 | } |
| 213 | |
| 214 | The ``hello_pb2.py`` proto module can be used alongside other files in the |
| 215 | ``foo`` package. |
| 216 | |
| 217 | .. code-block:: python |
| 218 | |
| 219 | from foo import cool_module, hello_pb2 |
| 220 | |
Wyatt Hepler | d517afc | 2021-02-03 19:40:08 -0800 | [diff] [blame] | 221 | Working with externally defined protos |
| 222 | -------------------------------------- |
| 223 | ``pw_proto_library`` targets may be used to build ``.proto`` sources from |
| 224 | existing projects. In these cases, it may be necessary to supply the |
Wyatt Hepler | 752d7d3 | 2021-03-02 09:02:23 -0800 | [diff] [blame] | 225 | ``strip_prefix`` argument, which specifies the protobuf include path to use for |
Wyatt Hepler | d517afc | 2021-02-03 19:40:08 -0800 | [diff] [blame] | 226 | ``protoc``. If only a single external protobuf is being compiled, the |
Wyatt Hepler | 752d7d3 | 2021-03-02 09:02:23 -0800 | [diff] [blame] | 227 | ``python_module_as_package`` option can be used to override the requirement that |
| 228 | the protobuf be nested under a directory. This option generates a Python package |
| 229 | with the same name as the proto file, so that the generated proto can be |
| 230 | imported as if it were a standalone Python module. |
| 231 | |
| 232 | For example, the ``pw_proto_library`` target for Nanopb sets |
| 233 | ``python_module_as_package`` to ``nanopb_pb2``. |
| 234 | |
| 235 | .. code-block:: |
| 236 | |
| 237 | pw_proto_library("proto") { |
| 238 | strip_prefix = "$dir_pw_third_party_nanopb/generator/proto" |
| 239 | sources = [ "$dir_pw_third_party_nanopb/generator/proto/nanopb.proto" ] |
| 240 | python_module_as_package = "nanopb_pb2" |
| 241 | } |
| 242 | |
| 243 | In Python, this makes ``nanopb.proto`` available as ``import nanopb_pb2`` via |
| 244 | the ``nanopb_pb2`` Python package. In C++, ``nanopb.proto`` is accessed as |
| 245 | ``#include "nanopb.pwpb.h"``. |
| 246 | |
| 247 | The ``python_module_as_package`` feature should only be used when absolutely |
| 248 | necessary --- for example, to support proto files that include |
| 249 | ``import "nanopb.proto"``. |
| 250 | |
| 251 | CMake |
| 252 | ===== |
| 253 | CMake provides a ``pw_proto_library`` function with similar features as the |
| 254 | GN template. The CMake build only supports building firmware code, so |
| 255 | ``pw_proto_library`` does not generate a Python package. |
| 256 | |
| 257 | **Arguments** |
| 258 | |
| 259 | * ``NAME``: the base name of the libraries to create |
| 260 | * ``SOURCES``: .proto source files |
| 261 | * ``DEPS``: dependencies on other ``pw_proto_library`` targets |
| 262 | * ``PREFIX``: prefix add to the proto files |
| 263 | * ``STRIP_PREFIX``: prefix to remove from the proto files |
| 264 | * ``INPUTS``: files to include along with the .proto files (such as Nanopb |
| 265 | .options files) |
| 266 | |
| 267 | **Example** |
| 268 | |
| 269 | .. code-block:: cmake |
| 270 | |
| 271 | include($ENV{PW_ROOT}/pw_build/pigweed.cmake) |
| 272 | include($ENV{PW_ROOT}/pw_protobuf_compiler/proto.cmake) |
| 273 | |
| 274 | pw_proto_library(my_module.my_protos |
| 275 | SOURCES |
| 276 | my_protos/foo.proto |
| 277 | my_protos/bar.proto |
| 278 | ) |
| 279 | |
| 280 | pw_proto_library(my_module.my_protos |
| 281 | SOURCES |
| 282 | my_protos/foo.proto |
| 283 | my_protos/bar.proto |
| 284 | ) |
| 285 | |
| 286 | pw_proto_library(my_module.my_other_protos |
| 287 | SOURCES |
| 288 | some/other/path/baz.proto # imports foo.proto |
| 289 | |
| 290 | # This removes the "some/other/path" prefix from the proto files. |
| 291 | STRIP_PREFIX |
| 292 | some/other/path |
| 293 | |
| 294 | # This adds the "my_other_protos/" prefix to the proto files. |
| 295 | PREFIX |
| 296 | my_other_protos |
| 297 | |
| 298 | # Proto libraries depend on other proto libraries directly. |
| 299 | DEPS |
| 300 | my_module.my_protos |
| 301 | ) |
| 302 | |
| 303 | add_library(my_module.my_cc_code |
| 304 | foo.cc |
| 305 | bar.cc |
| 306 | baz.cc |
| 307 | ) |
| 308 | |
| 309 | # When depending on protos in a source_set, specify the generator suffix. |
| 310 | target_link_libraries(my_module.my_cc_code PUBLIC |
| 311 | my_module.my_other_protos.pwpb |
| 312 | ) |
| 313 | |
| 314 | These proto files are accessed in C++ the same as in the GN build: |
| 315 | |
| 316 | .. code-block:: cpp |
| 317 | |
Wyatt Hepler | 4cdc3e7 | 2021-03-24 08:41:08 -0700 | [diff] [blame] | 318 | #include "my_other_protos/baz.pwpb.h" |
Nathaniel Brough | 9d9a20d | 2020-08-04 16:46:56 +0800 | [diff] [blame] | 319 | |
Armando Montanez | 377a68c | 2021-05-13 15:53:13 -0700 | [diff] [blame] | 320 | **Supported Codegen** |
| 321 | |
| 322 | CMake supports the following compiled proto libraries via the specified |
| 323 | sub-targets generated by a ``pw_proto_library``. |
| 324 | |
| 325 | * ``${NAME}.pwpb`` - Generated C++ pw_protobuf code |
| 326 | * ``${NAME}.nanopb`` - Generated C++ nanopb code (requires Nanopb) |
| 327 | * ``${NAME}.nanopb_rpc`` - Generated C++ Nanopb pw_rpc code (requires Nanopb) |
| 328 | * ``${NAME}.raw_rpc`` - Generated C++ raw pw_rpc code (no protobuf library) |
| 329 | |
Nathaniel Brough | 9d9a20d | 2020-08-04 16:46:56 +0800 | [diff] [blame] | 330 | Bazel |
| 331 | ===== |
| 332 | Bazel provides a ``pw_proto_library`` rule with similar features as the |
| 333 | GN template. The Bazel build only supports building firmware code, so |
| 334 | ``pw_proto_library`` does not generate a Python package. The Bazel rules differ |
| 335 | slightly compared to the GN build to be more in line with what would be |
| 336 | considered idiomatic in Bazel. |
| 337 | |
| 338 | To use Pigweeds Protobuf rules you must first pull in the required dependencies |
| 339 | into your Bazel WORKSPACE file. e.g. |
| 340 | |
| 341 | .. code-block:: python |
| 342 | |
| 343 | # WORKSPACE ... |
| 344 | load("@pigweed//pw_protobuf_compiler:deps.bzl", "pw_protobuf_dependencies") |
| 345 | pw_protobuf_dependencies() |
| 346 | |
| 347 | Bazel uses a different set of rules to manage proto files than it does to |
| 348 | compile them. e.g. |
| 349 | |
| 350 | .. code-block:: python |
| 351 | |
| 352 | # BUILD ... |
| 353 | load("@rules_proto//proto:defs.bzl", "proto_library") |
| 354 | load("@pigweed//pw_protobuf_compiler:proto.bzl", "pw_proto_library") |
| 355 | |
| 356 | # Manages proto sources and dependencies. |
| 357 | proto_library( |
| 358 | name = "my_proto", |
| 359 | srcs = [ |
| 360 | "my_protos/foo.proto", |
| 361 | "my_protos/bar.proto", |
| 362 | ] |
| 363 | ) |
| 364 | |
| 365 | # Compiles dependant protos to C++. |
| 366 | pw_proto_library( |
| 367 | name = "my_cc_proto", |
| 368 | deps = [":my_proto"], |
| 369 | ) |
| 370 | |
| 371 | # Library that depends on generated proto targets. |
| 372 | pw_cc_library( |
| 373 | name = "my_lib", |
| 374 | srcs = ["my/lib.cc"], |
| 375 | deps = [":my_cc_proto"], |
| 376 | ) |
| 377 | |
| 378 | From ``my/lib.cc`` you can now include the generated headers. |
| 379 | e.g. |
| 380 | |
| 381 | .. code:: cpp |
| 382 | |
Armando Montanez | 377a68c | 2021-05-13 15:53:13 -0700 | [diff] [blame] | 383 | #include "my_protos/bar.pwpb.h" |
Nathaniel Brough | b4f4e7a | 2021-05-06 14:49:55 +0800 | [diff] [blame] | 384 | // and/or RPC headers |
| 385 | #include "my_protos/bar.raw_rpc.pb.h |
| 386 | |
| 387 | .. note:: |
| 388 | |
| 389 | Currently only raw RPC is supported by the Bazel build. |
Armando Montanez | 377a68c | 2021-05-13 15:53:13 -0700 | [diff] [blame] | 390 | |
| 391 | **Supported Codegen** |
| 392 | |
| 393 | Bazel supports the following compiled proto libraries via the specified |
| 394 | sub-targets generated by a ``pw_proto_library``. |
| 395 | |
| 396 | * ``${NAME}.pwpb`` - Generated C++ pw_protobuf code |
Armando Montanez | 377a68c | 2021-05-13 15:53:13 -0700 | [diff] [blame] | 397 | * ``${NAME}.raw_rpc`` - Generated C++ raw pw_rpc code (no protobuf library) |
Nathaniel Brough | b4f4e7a | 2021-05-06 14:49:55 +0800 | [diff] [blame] | 398 | |