Merge branch 'pull/16'
This commit is contained in:
commit
7c819065e0
17 changed files with 801 additions and 99 deletions
2
.gitignore
vendored
2
.gitignore
vendored
|
|
@ -17,6 +17,8 @@ test-driver
|
|||
*.log
|
||||
*.trs
|
||||
|
||||
tests/*.out
|
||||
|
||||
*.o
|
||||
*.a
|
||||
*.so
|
||||
|
|
|
|||
36
Makefile.am
36
Makefile.am
|
|
@ -17,8 +17,9 @@ pkgconfig_DATA = c-capnproto.pc
|
|||
|
||||
EXTRA_DIST += compiler/c.capnp
|
||||
capnp_DATA = compiler/c.capnp
|
||||
|
||||
AM_CPPFLAGS = -I${srcdir}/lib
|
||||
AM_CPPFLAGS = \
|
||||
-I${srcdir}/compiler \
|
||||
-I${srcdir}/lib
|
||||
|
||||
lib_LTLIBRARIES += libcapnp_c.la
|
||||
libcapnp_c_la_LDFLAGS = -version-info 0:0:0
|
||||
|
|
@ -42,25 +43,52 @@ noinst_HEADERS += \
|
|||
lib/capnp_priv.h \
|
||||
compiler/str.h \
|
||||
compiler/schema.capnp.h \
|
||||
compiler/c++.capnp.h \
|
||||
compiler/test.capnp.h
|
||||
compiler/c.capnp.h \
|
||||
compiler/c++.capnp.h
|
||||
|
||||
# Don't try to generate any *.capnp files. Otherwise make wants to compile them
|
||||
# from *.capnp.c and fails.
|
||||
%.capnp: ;
|
||||
|
||||
# googletest
|
||||
GTEST_LDADD = gtest/googletest/lib/libgtest.la
|
||||
gtest/googletest/lib/libgtest.la:
|
||||
make -C gtest/googletest lib/libgtest.la
|
||||
GTEST_CPPFLAGS = -I${srcdir}/gtest/googletest/include
|
||||
DIST_SUBDIRS = gtest/googletest
|
||||
|
||||
# Tests
|
||||
check_PROGRAMS += \
|
||||
capn-test
|
||||
capn_test_SOURCES = \
|
||||
tests/capn-test.cpp \
|
||||
tests/capn-stream-test.cpp \
|
||||
tests/example-test.cpp \
|
||||
tests/addressbook.capnp.c \
|
||||
compiler/test.capnp.c \
|
||||
compiler/schema-test.cpp \
|
||||
compiler/schema.capnp.c
|
||||
noinst_HEADERS += \
|
||||
compiler/test.capnp.h \
|
||||
tests/addressbook.capnp.h
|
||||
EXTRA_DIST += \
|
||||
compiler/c.capnp \
|
||||
compiler/c++.capnp \
|
||||
compiler/schema.capnp \
|
||||
compiler/test.capnp \
|
||||
tests/addressbook.capnp
|
||||
capn_test_CPPFLAGS = $(AM_CPPFLAGS) $(GTEST_CPPFLAGS)
|
||||
capn_test_CXXFLAGS = -std=gnu++11 -pthread
|
||||
capn_test_LDADD = libcapnp_c.la $(GTEST_LDADD)
|
||||
capn_test_LDFLAGS = -pthread
|
||||
TESTS = capn-test
|
||||
|
||||
CAPNP_SCHEMA_FILES := $(shell find . -type f -name \*.capnp)
|
||||
|
||||
CAPNP ?= capnp
|
||||
.PHONY: capnp-compile
|
||||
capnp-compile:
|
||||
$(CAPNP) compile \
|
||||
--output=./capnpc-c \
|
||||
-Icompiler \
|
||||
$(CAPNP_SCHEMA_FILES)
|
||||
|
|
|
|||
108
README.md
108
README.md
|
|
@ -4,44 +4,19 @@ capnpc-c
|
|||
This is a C plugin for [Cap'n Proto](http://kentonv.github.io/capnproto), an
|
||||
efficient protocol for sharing data and capabilities.
|
||||
|
||||
This is only the plugin, to properly make use of it you need to download, build
|
||||
and install capnpc and then build and install this project and then you can
|
||||
utilize it as:
|
||||
This is only the code generator plugin, to properly make use of it you
|
||||
need to download, build and install capnpc and then build and install
|
||||
this project and then you can utilize it as:
|
||||
|
||||
capnpc compiler/test.capnp -oc
|
||||
```sh
|
||||
capnpc compiler/test.capnp -oc
|
||||
```
|
||||
|
||||
[](https://travis-ci.org/opensourcerouting/c-capnproto)
|
||||
|
||||
## status
|
||||
## Building on Linux
|
||||
|
||||
This is a merge of 3 forks of [James McKaskill's great
|
||||
work](https://github.com/jmckaskill/c-capnproto), which has been untouched for
|
||||
a while:
|
||||
|
||||
- [liamstask's fork](https://github.com/liamstask/c-capnproto)
|
||||
- [baruch's fork](https://github.com/baruch/c-capnproto)
|
||||
- [kylemanna's fork](https://github.com/kylemanna/c-capnproto)
|
||||
|
||||
|
||||
## usage
|
||||
|
||||
The `compiler` directory contains the C language plugin (`capnpc-c`) for use with the `capnp` tool: https://capnproto.org/capnp-tool.html.
|
||||
|
||||
`capnp` will by default search `$PATH` for `capnpc-c` - if it's on your PATH, you can generate code for your schema as follows:
|
||||
|
||||
$ capnp compile -o c myschema.capnp
|
||||
|
||||
Otherwise, you can specify the path to the c plugin:
|
||||
|
||||
$ capnp compile -o ./capnpc-c myschema.capnp
|
||||
|
||||
`capnp` generates a C struct that corresponds to each capn proto struct, along with read/write functions that convert to/from capn proto form.
|
||||
|
||||
TBD whether it will make sense in the future to provide accessor functions for struct members, rather than converting entire structs.
|
||||
|
||||
## building on linux
|
||||
|
||||
```
|
||||
```sh
|
||||
git clone https://github.com/opensourcerouting/c-capnproto
|
||||
cd c-capnproto
|
||||
git submodule update --init --recursive
|
||||
|
|
@ -51,3 +26,70 @@ make
|
|||
make check
|
||||
```
|
||||
|
||||
## Usage
|
||||
|
||||
### Generating C code from a `.capnp` schema file
|
||||
|
||||
The `compiler` directory contains the C language plugin (`capnpc-c`) for use with the `capnp` tool: https://capnproto.org/capnp-tool.html.
|
||||
|
||||
`capnp` will by default search `$PATH` for `capnpc-c` - if it's on your PATH, you can generate code for your schema as follows:
|
||||
|
||||
```sh
|
||||
capnp compile -o c myschema.capnp
|
||||
```
|
||||
|
||||
Otherwise, you can specify the path to the c plugin:
|
||||
|
||||
```sh
|
||||
capnp compile -o ./capnpc-c myschema.capnp
|
||||
```
|
||||
|
||||
`capnp` generates a C struct that corresponds to each capn proto struct, along with read/write functions that convert to/from capn proto form.
|
||||
|
||||
If you want accessor functions for struct members, use attribute `fieldgetset` in your `.capnp` file as follows:
|
||||
|
||||
```capnp
|
||||
using C = import "${c-capnproto}/compiler/c.capnp";
|
||||
|
||||
$C.fieldgetset;
|
||||
|
||||
struct MyStruct {}
|
||||
```
|
||||
|
||||
### Example C code
|
||||
|
||||
See the unit tests in [`tests/example-test.cpp`](tests/example-test.cpp).
|
||||
The example schema file is [`tests/addressbook.capnp`](tests/addressbook.capnp).
|
||||
The tests are written in C++, but only use C features.
|
||||
|
||||
You need to compile these runtime library files and link them into your own project's binaries:
|
||||
|
||||
* [`lib/capn.c`](lib/capn.c)
|
||||
* [`lib/capn-malloc.c`](lib/capn-malloc.c)
|
||||
* [`lib/capn-stream.c`](lib/capn-stream.c)
|
||||
|
||||
Your include path must contain the runtime library directory
|
||||
[`lib`](lib). Header file [`lib/capnp_c.h`](lib/capnp_c.h) contains
|
||||
the public interfaces of the library.
|
||||
|
||||
Using make-based builds, make may try to compile `${x}.capnp` from
|
||||
`${x}.capnp.c` using its built-in rule for compiling `${y}` from
|
||||
`${y}.c`. You can either disable make's built-in compile rules or just
|
||||
this specific case with the no-op rule: `%.capnp: ;`.
|
||||
|
||||
For further reference, please see the other unit tests in [`tests`](tests), and header file [`lib/capnp_c.h`](lib/capnp_c.h).
|
||||
|
||||
The project [`quagga-capnproto`](https://github.com/opensourcerouting/quagga-capnproto) uses `c-capnproto` and contains some good examples, as found with [this github repository search](https://github.com/opensourcerouting/quagga-capnproto/search?utf8=%E2%9C%93&q=capn&type=):
|
||||
|
||||
* Serialization in function [`bgp_notify_send()`](https://github.com/opensourcerouting/quagga-capnproto/blob/27061648f3418fac0d217b16a46add534343e841/bgpd/bgp_zmq.c#L81-L96) in file `quagga-capnproto/bgpd/bgp_zmq.c`
|
||||
* Deserialization in function [`qzc_callback()`](https://github.com/opensourcerouting/quagga-capnproto/blob/27061648f3418fac0d217b16a46add534343e841/lib/qzc.c#L249-L257) in file `quagga-capnproto/lib/qzc.c`
|
||||
|
||||
## Status
|
||||
|
||||
This is a merge of 3 forks of [James McKaskill's great
|
||||
work](https://github.com/jmckaskill/c-capnproto), which has been untouched for
|
||||
a while:
|
||||
|
||||
- [liamstask's fork](https://github.com/liamstask/c-capnproto)
|
||||
- [baruch's fork](https://github.com/baruch/c-capnproto)
|
||||
- [kylemanna's fork](https://github.com/kylemanna/c-capnproto)
|
||||
|
|
|
|||
|
|
@ -29,6 +29,10 @@ annotation nameinfix @0x85a8d86d736ba637 (file): Text;
|
|||
# to a loop. $nameinfix (recommended parameter: "-gen") inserts its parameter
|
||||
# before the ".c", so the filename becomes "foo-gen.c"
|
||||
#
|
||||
# Alternatively, add this Makefile rule to disable compiling "foo.capnp.c" -> "foo.capnp":
|
||||
# %.capnp: ;
|
||||
#
|
||||
#
|
||||
# ("foo" is really "foo.capnp", so it's foo.capnp-gen.c)
|
||||
|
||||
annotation fieldgetset @0xf72bc690355d66de (file): Void;
|
||||
|
|
|
|||
2
compiler/c.capnp.c
Normal file
2
compiler/c.capnp.c
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
#include "c.capnp.h"
|
||||
/* AUTO GENERATED - DO NOT EDIT */
|
||||
27
compiler/c.capnp.h
Normal file
27
compiler/c.capnp.h
Normal file
|
|
@ -0,0 +1,27 @@
|
|||
#ifndef CAPN_C0183DD65FFEF0F3
|
||||
#define CAPN_C0183DD65FFEF0F3
|
||||
/* AUTO GENERATED - DO NOT EDIT */
|
||||
#include <capnp_c.h>
|
||||
|
||||
#if CAPN_VERSION != 1
|
||||
#error "version mismatch between capnp_c.h and generated code"
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
|
|
@ -8,6 +8,7 @@
|
|||
|
||||
#include "schema.capnp.h"
|
||||
#include "str.h"
|
||||
#include <stdbool.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
|
|
@ -261,6 +262,7 @@ static void decode_value(struct value* v, Type_ptr type, Value_ptr value, const
|
|||
|
||||
v->ptrval = p;
|
||||
|
||||
bool symbol_provided = symbol;
|
||||
if (!symbol) {
|
||||
static struct str buf = STR_INIT;
|
||||
v->intval = ++g_valc;
|
||||
|
|
@ -268,7 +270,7 @@ static void decode_value(struct value* v, Type_ptr type, Value_ptr value, const
|
|||
}
|
||||
|
||||
str_addf(&SRC, "%scapn_text %s = {%d,(char*)&capn_buf[%d],(struct capn_segment*)&capn_seg};\n",
|
||||
symbol ? "" : "static ",
|
||||
symbol_provided ? "" : "static ",
|
||||
symbol,
|
||||
p.len-1,
|
||||
(int) (p.data-p.seg->data-8));
|
||||
|
|
@ -291,13 +293,14 @@ static void decode_value(struct value* v, Type_ptr type, Value_ptr value, const
|
|||
|
||||
v->ptrval = p;
|
||||
|
||||
bool symbol_provided = symbol;
|
||||
if (!symbol) {
|
||||
static struct str buf = STR_INIT;
|
||||
v->intval = ++g_valc;
|
||||
symbol = strf(&buf, "capn_val%d", (int) v->intval);
|
||||
}
|
||||
|
||||
str_addf(&SRC, "%s%s %s = {", symbol ? "" : "static ", v->tname, symbol);
|
||||
str_addf(&SRC, "%s%s %s = {", symbol_provided ? "" : "static ", v->tname, symbol);
|
||||
if (strcmp(v->tname, "capn_ptr"))
|
||||
str_addf(&SRC, "{");
|
||||
|
||||
|
|
@ -1290,7 +1293,11 @@ int main() {
|
|||
for (j = 0; j < capn_len(file_req.imports); j++) {
|
||||
struct CodeGeneratorRequest_RequestedFile_Import im;
|
||||
get_CodeGeneratorRequest_RequestedFile_Import(&im, file_req.imports, j);
|
||||
str_addf(&HDR, "#include \"%s%s.h\"\n", im.name.str, nameinfix);
|
||||
|
||||
// Ignore leading slashes when generating C file #include's.
|
||||
// This signifies an absolute import in a library directory.
|
||||
const char *base_path = im.name.str[0] == '/' ? &im.name.str[1] : im.name.str;
|
||||
str_addf(&HDR, "#include \"%s%s.h\"\n", base_path, nameinfix);
|
||||
}
|
||||
|
||||
str_addf(&HDR, "\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n");
|
||||
|
|
|
|||
|
|
@ -19,11 +19,14 @@
|
|||
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
# THE SOFTWARE.
|
||||
|
||||
using C = import "c.capnp";
|
||||
using Cxx = import "c++.capnp";
|
||||
|
||||
@0xa93fc509624c72d9;
|
||||
$Cxx.namespace("capnp::schema");
|
||||
|
||||
$C.fieldgetset;
|
||||
|
||||
using Id = UInt64;
|
||||
# The globally-unique ID of a file, type, or annotation.
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
#include "schema.capnp.h"
|
||||
/* AUTO GENERATED - DO NOT EDIT */
|
||||
static const capn_text capn_val0 = {0,""};
|
||||
static const capn_text capn_val0 = {0,"",0};
|
||||
uint16_t Field_noDiscriminant = 65535;
|
||||
|
||||
Node_ptr new_Node(struct capn_segment *s) {
|
||||
|
|
|
|||
|
|
@ -8,6 +8,7 @@
|
|||
#endif
|
||||
|
||||
#include "c++.capnp.h"
|
||||
#include "c.capnp.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
|
|
|
|||
|
|
@ -21,8 +21,11 @@
|
|||
|
||||
@0xd508eebdc2dc42b8;
|
||||
|
||||
using C = import "c.capnp";
|
||||
using Cxx = import "c++.capnp";
|
||||
|
||||
$C.fieldgetset;
|
||||
|
||||
# Use a namespace likely to cause trouble if the generated code doesn't use fully-qualified
|
||||
# names for stuff in the capnproto namespace.
|
||||
$Cxx.namespace("capnproto_test::capnp::test");
|
||||
|
|
|
|||
|
|
@ -1,19 +1,43 @@
|
|||
#include "test.capnp.h"
|
||||
/* AUTO GENERATED - DO NOT EDIT */
|
||||
static const capn_text capn_val0 = {0,""};
|
||||
static const capn_text capn_val0 = {0,"",0};
|
||||
static const capn_ptr capn_null = {CAPN_NULL};
|
||||
static const uint8_t capn_buf[72] = {
|
||||
static const uint8_t capn_buf[264] = {
|
||||
102,111,111,0,0,0,0,0,
|
||||
98,97,114,0,0,0,0,0,
|
||||
9,0,0,0,0,0,0,0,
|
||||
111,145,0,0,0,0,0,0,
|
||||
103,43,153,212,0,0,0,0,
|
||||
199,107,159,6,57,148,96,249,
|
||||
199,113,196,43,171,117,107,15,
|
||||
57,142,59,212,84,138,148,240,
|
||||
111,222,0,0,0,0,0,0
|
||||
1,244,128,13,14,16,76,251,
|
||||
78,115,232,56,166,51,0,0,
|
||||
90,0,210,4,20,136,98,3,
|
||||
210,10,111,18,33,25,204,4,
|
||||
95,112,9,175,2,0,0,0,
|
||||
0,0,0,0,0,144,117,64,
|
||||
77,0,0,0,34,0,0,0,
|
||||
77,0,0,0,26,0,0,0,
|
||||
2,0,0,0,1,0,0,0,
|
||||
73,0,0,0,24,0,0,0,
|
||||
69,0,0,0,41,0,0,0,
|
||||
69,0,0,0,34,0,0,0,
|
||||
69,0,0,0,35,0,0,0,
|
||||
194,1,0,0,1,0,0,0,
|
||||
218,1,0,0,1,0,0,0,
|
||||
2,2,0,0,1,0,0,0,
|
||||
18,2,0,0,1,0,0,0,
|
||||
34,2,0,0,1,0,0,0,
|
||||
58,2,0,0,1,0,0,0,
|
||||
98,2,0,0,1,0,0,0,
|
||||
130,2,0,0,1,0,0,0,
|
||||
186,2,0,0,1,0,0,0,
|
||||
242,2,0,0,1,0,0,0,
|
||||
42,3,0,0,1,0,0,0,
|
||||
218,5,0,0,1,0,0,0,
|
||||
0,0,0,0,0,0,0,0,
|
||||
98,97,122,0,0,0,0,0,
|
||||
113,117,120,0,0,0,0,0,
|
||||
26,0,0,0,0,0,0,0,
|
||||
12,222,128,127,0,0,0,0,
|
||||
210,4,210,233,0,128,255,127
|
||||
};
|
||||
static const struct capn_segment capn_seg = {{0},0,0,0,(char*)&capn_buf[0],72,72};
|
||||
static const struct capn_segment capn_seg = {{0},0,0,0,(char*)&capn_buf[0],264,264,0};
|
||||
union capn_conv_f32 TestWholeFloatDefault_constant = {0x43e40000u};
|
||||
union capn_conv_f32 TestWholeFloatDefault_bigConstant = {0x7249f2cau};
|
||||
unsigned TestConstants_boolConst = 1;
|
||||
|
|
@ -29,29 +53,29 @@ union capn_conv_f32 TestConstants_float32Const = {0x449a5000u};
|
|||
union capn_conv_f64 TestConstants_float64Const = {((uint64_t) 0xc9b58b82u << 32) | 0xc0e0bb00u};
|
||||
capn_text TestConstants_textConst = {3,(char*)&capn_buf[0],(struct capn_segment*)&capn_seg};
|
||||
capn_data TestConstants_dataConst = {{2,0,0,0,1,0,3,(char*)&capn_buf[8],(struct capn_segment*)&capn_seg}};
|
||||
TestAllTypes_ptr TestConstants_structConst = {{1,1,0,0,48,20,0,(char*)&capn_buf[0],(struct capn_segment*)&capn_seg}};
|
||||
TestAllTypes_ptr TestConstants_structConst = {{1,0,0,0,48,20,0,(char*)&capn_buf[16],(struct capn_segment*)&capn_seg}};
|
||||
enum TestEnum TestConstants_enumConst = (enum TestEnum) 5u;
|
||||
capn_ptr TestConstants_voidListConst = {2,0,0,0,0,0,6,(char*)&capn_buf[16],(struct capn_segment*)&capn_seg};
|
||||
capn_list1 TestConstants_boolListConst = {{4,0,0,0,1,0,4,(char*)&capn_buf[16],(struct capn_segment*)&capn_seg}};
|
||||
capn_list8 TestConstants_int8ListConst = {{2,0,0,0,1,0,2,(char*)&capn_buf[24],(struct capn_segment*)&capn_seg}};
|
||||
capn_list16 TestConstants_int16ListConst = {{2,0,0,0,2,0,2,(char*)&capn_buf[32],(struct capn_segment*)&capn_seg}};
|
||||
capn_list32 TestConstants_int32ListConst = {{2,0,0,0,4,0,2,(char*)&capn_buf[40],(struct capn_segment*)&capn_seg}};
|
||||
capn_list64 TestConstants_int64ListConst = {{2,0,0,0,8,0,2,(char*)&capn_buf[48],(struct capn_segment*)&capn_seg}};
|
||||
capn_list8 TestConstants_uint8ListConst = {{2,0,0,0,1,0,2,(char*)&capn_buf[64],(struct capn_segment*)&capn_seg}};
|
||||
capn_list16 TestConstants_uint16ListConst = {{2,1,0,0,2,0,2,(char*)&capn_buf[1664],(struct capn_segment*)&capn_seg}};
|
||||
capn_list32 TestConstants_uint32ListConst = {{2,1,0,0,4,0,1,(char*)&capn_buf[1680],(struct capn_segment*)&capn_seg}};
|
||||
capn_list64 TestConstants_uint64ListConst = {{2,1,0,0,8,0,1,(char*)&capn_buf[1696],(struct capn_segment*)&capn_seg}};
|
||||
capn_list32 TestConstants_float32ListConst = {{2,1,0,0,4,0,4,(char*)&capn_buf[1712],(struct capn_segment*)&capn_seg}};
|
||||
capn_list64 TestConstants_float64ListConst = {{2,1,0,0,8,0,4,(char*)&capn_buf[1736],(struct capn_segment*)&capn_seg}};
|
||||
capn_ptr TestConstants_textListConst = {3,1,0,0,0,0,3,(char*)&capn_buf[1776],(struct capn_segment*)&capn_seg};
|
||||
capn_ptr TestConstants_dataListConst = {3,1,0,0,0,0,3,(char*)&capn_buf[1832],(struct capn_segment*)&capn_seg};
|
||||
TestAllTypes_list TestConstants_structListConst = {{2,1,0,1,48,20,3,(char*)&capn_buf[1904],(struct capn_segment*)&capn_seg}};
|
||||
capn_list16 TestConstants_enumListConst = {{2,1,0,0,2,0,2,(char*)&capn_buf[2584],(struct capn_segment*)&capn_seg}};
|
||||
capn_ptr TestConstants_voidListConst = {2,0,0,0,0,0,6,(char*)&capn_buf[264],(struct capn_segment*)&capn_seg};
|
||||
capn_list1 TestConstants_boolListConst = {{4,1,0,0,1,0,4,(char*)&capn_buf[1512],(struct capn_segment*)&capn_seg}};
|
||||
capn_list8 TestConstants_int8ListConst = {{2,1,0,0,1,0,2,(char*)&capn_buf[1528],(struct capn_segment*)&capn_seg}};
|
||||
capn_list16 TestConstants_int16ListConst = {{2,1,0,0,2,0,2,(char*)&capn_buf[1544],(struct capn_segment*)&capn_seg}};
|
||||
capn_list32 TestConstants_int32ListConst = {{2,1,0,0,4,0,2,(char*)&capn_buf[1560],(struct capn_segment*)&capn_seg}};
|
||||
capn_list64 TestConstants_int64ListConst = {{2,1,0,0,8,0,2,(char*)&capn_buf[1576],(struct capn_segment*)&capn_seg}};
|
||||
capn_list8 TestConstants_uint8ListConst = {{2,1,0,0,1,0,2,(char*)&capn_buf[1600],(struct capn_segment*)&capn_seg}};
|
||||
capn_list16 TestConstants_uint16ListConst = {{2,1,0,0,2,0,2,(char*)&capn_buf[1616],(struct capn_segment*)&capn_seg}};
|
||||
capn_list32 TestConstants_uint32ListConst = {{2,1,0,0,4,0,1,(char*)&capn_buf[1632],(struct capn_segment*)&capn_seg}};
|
||||
capn_list64 TestConstants_uint64ListConst = {{2,1,0,0,8,0,1,(char*)&capn_buf[1648],(struct capn_segment*)&capn_seg}};
|
||||
capn_list32 TestConstants_float32ListConst = {{2,1,0,0,4,0,4,(char*)&capn_buf[1664],(struct capn_segment*)&capn_seg}};
|
||||
capn_list64 TestConstants_float64ListConst = {{2,1,0,0,8,0,4,(char*)&capn_buf[1688],(struct capn_segment*)&capn_seg}};
|
||||
capn_ptr TestConstants_textListConst = {3,1,0,0,0,0,3,(char*)&capn_buf[1728],(struct capn_segment*)&capn_seg};
|
||||
capn_ptr TestConstants_dataListConst = {3,1,0,0,0,0,3,(char*)&capn_buf[1784],(struct capn_segment*)&capn_seg};
|
||||
TestAllTypes_list TestConstants_structListConst = {{2,1,0,1,48,20,3,(char*)&capn_buf[1856],(struct capn_segment*)&capn_seg}};
|
||||
capn_list16 TestConstants_enumListConst = {{2,1,0,0,2,0,2,(char*)&capn_buf[2536],(struct capn_segment*)&capn_seg}};
|
||||
uint32_t globalInt = 12345u;
|
||||
capn_text globalText = {6,(char*)&capn_buf[2600],(struct capn_segment*)&capn_seg};
|
||||
TestAllTypes_ptr globalStruct = {{1,1,0,0,48,20,0,(char*)&capn_buf[2616],(struct capn_segment*)&capn_seg}};
|
||||
TestPrintInlineStructs_ptr globalPrintableStruct = {{1,1,0,0,0,2,0,(char*)&capn_buf[2832],(struct capn_segment*)&capn_seg}};
|
||||
TestAllTypes_ptr derivedConstant = {{1,1,0,0,48,20,0,(char*)&capn_buf[2864],(struct capn_segment*)&capn_seg}};
|
||||
capn_text globalText = {6,(char*)&capn_buf[2552],(struct capn_segment*)&capn_seg};
|
||||
TestAllTypes_ptr globalStruct = {{1,1,0,0,48,20,0,(char*)&capn_buf[2568],(struct capn_segment*)&capn_seg}};
|
||||
TestPrintInlineStructs_ptr globalPrintableStruct = {{1,1,0,0,0,2,0,(char*)&capn_buf[2784],(struct capn_segment*)&capn_seg}};
|
||||
TestAllTypes_ptr derivedConstant = {{1,1,0,0,48,20,0,(char*)&capn_buf[2816],(struct capn_segment*)&capn_seg}};
|
||||
|
||||
TestAllTypes_ptr new_TestAllTypes(struct capn_segment *s) {
|
||||
TestAllTypes_ptr p;
|
||||
|
|
@ -527,25 +551,25 @@ void TestAllTypes_set_interfaceList(TestAllTypes_ptr p, capn_ptr interfaceList)
|
|||
{
|
||||
capn_setp(p.p, 19, interfaceList);
|
||||
}
|
||||
capn_text capn_val1 = {3,(char*)&capn_buf[1464],(struct capn_segment*)&capn_seg};
|
||||
capn_data capn_val2 = {{2,1,0,0,1,0,3,(char*)&capn_buf[1480],(struct capn_segment*)&capn_seg}};
|
||||
TestAllTypes_ptr capn_val3 = {{1,1,0,0,48,20,0,(char*)&capn_buf[1496],(struct capn_segment*)&capn_seg}};
|
||||
capn_ptr capn_val4 = {2,0,0,0,0,0,6,(char*)&capn_buf[72],(struct capn_segment*)&capn_seg};
|
||||
capn_list1 capn_val5 = {{4,1,0,0,1,0,4,(char*)&capn_buf[3160],(struct capn_segment*)&capn_seg}};
|
||||
capn_list8 capn_val6 = {{2,1,0,0,1,0,2,(char*)&capn_buf[3176],(struct capn_segment*)&capn_seg}};
|
||||
capn_list16 capn_val7 = {{2,1,0,0,2,0,2,(char*)&capn_buf[3192],(struct capn_segment*)&capn_seg}};
|
||||
capn_list32 capn_val8 = {{2,1,0,0,4,0,2,(char*)&capn_buf[3208],(struct capn_segment*)&capn_seg}};
|
||||
capn_list64 capn_val9 = {{2,1,0,0,8,0,2,(char*)&capn_buf[3224],(struct capn_segment*)&capn_seg}};
|
||||
capn_list8 capn_val10 = {{2,1,0,0,1,0,2,(char*)&capn_buf[3248],(struct capn_segment*)&capn_seg}};
|
||||
capn_list16 capn_val11 = {{2,1,0,0,2,0,2,(char*)&capn_buf[3264],(struct capn_segment*)&capn_seg}};
|
||||
capn_list32 capn_val12 = {{2,1,0,0,4,0,1,(char*)&capn_buf[3280],(struct capn_segment*)&capn_seg}};
|
||||
capn_list64 capn_val13 = {{2,1,0,0,8,0,1,(char*)&capn_buf[3296],(struct capn_segment*)&capn_seg}};
|
||||
capn_list32 capn_val14 = {{2,1,0,0,4,0,4,(char*)&capn_buf[3312],(struct capn_segment*)&capn_seg}};
|
||||
capn_list64 capn_val15 = {{2,1,0,0,8,0,4,(char*)&capn_buf[3336],(struct capn_segment*)&capn_seg}};
|
||||
capn_ptr capn_val16 = {3,1,0,0,0,0,3,(char*)&capn_buf[3376],(struct capn_segment*)&capn_seg};
|
||||
capn_ptr capn_val17 = {3,1,0,0,0,0,3,(char*)&capn_buf[3432],(struct capn_segment*)&capn_seg};
|
||||
TestAllTypes_list capn_val18 = {{2,1,0,1,48,20,3,(char*)&capn_buf[8],(struct capn_segment*)&capn_seg}};
|
||||
capn_list16 capn_val19 = {{2,1,0,0,2,0,2,(char*)&capn_buf[3496],(struct capn_segment*)&capn_seg}};
|
||||
static capn_text capn_val1 = {3,(char*)&capn_buf[1408],(struct capn_segment*)&capn_seg};
|
||||
static capn_data capn_val2 = {{2,1,0,0,1,0,3,(char*)&capn_buf[1424],(struct capn_segment*)&capn_seg}};
|
||||
static TestAllTypes_ptr capn_val3 = {{1,1,0,0,48,20,0,(char*)&capn_buf[1440],(struct capn_segment*)&capn_seg}};
|
||||
static capn_ptr capn_val4 = {2,0,0,0,0,0,6,(char*)&capn_buf[264],(struct capn_segment*)&capn_seg};
|
||||
static capn_list1 capn_val5 = {{4,1,0,0,1,0,4,(char*)&capn_buf[3104],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list8 capn_val6 = {{2,1,0,0,1,0,2,(char*)&capn_buf[3120],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list16 capn_val7 = {{2,1,0,0,2,0,2,(char*)&capn_buf[3136],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list32 capn_val8 = {{2,1,0,0,4,0,2,(char*)&capn_buf[3152],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list64 capn_val9 = {{2,1,0,0,8,0,2,(char*)&capn_buf[3168],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list8 capn_val10 = {{2,1,0,0,1,0,2,(char*)&capn_buf[3192],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list16 capn_val11 = {{2,1,0,0,2,0,2,(char*)&capn_buf[3208],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list32 capn_val12 = {{2,1,0,0,4,0,1,(char*)&capn_buf[3224],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list64 capn_val13 = {{2,1,0,0,8,0,1,(char*)&capn_buf[3240],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list32 capn_val14 = {{2,1,0,0,4,0,4,(char*)&capn_buf[3256],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list64 capn_val15 = {{2,1,0,0,8,0,4,(char*)&capn_buf[3280],(struct capn_segment*)&capn_seg}};
|
||||
static capn_ptr capn_val16 = {3,1,0,0,0,0,3,(char*)&capn_buf[3320],(struct capn_segment*)&capn_seg};
|
||||
static capn_ptr capn_val17 = {3,1,0,0,0,0,3,(char*)&capn_buf[3376],(struct capn_segment*)&capn_seg};
|
||||
static TestAllTypes_list capn_val18 = {{2,1,0,1,48,20,3,(char*)&capn_buf[8],(struct capn_segment*)&capn_seg}};
|
||||
static capn_list16 capn_val19 = {{2,1,0,0,2,0,2,(char*)&capn_buf[3440],(struct capn_segment*)&capn_seg}};
|
||||
|
||||
TestDefaults_ptr new_TestDefaults(struct capn_segment *s) {
|
||||
TestDefaults_ptr p;
|
||||
|
|
@ -1976,10 +2000,10 @@ void set_TestInterleavedGroups(const struct TestInterleavedGroups *s, TestInterl
|
|||
p.p = capn_getp(l.p, i, 0);
|
||||
write_TestInterleavedGroups(s, p);
|
||||
}
|
||||
TestUnion_ptr capn_val20 = {{1,1,0,0,64,2,0,(char*)&capn_buf[3512],(struct capn_segment*)&capn_seg}};
|
||||
TestUnion_ptr capn_val21 = {{1,1,0,0,64,2,0,(char*)&capn_buf[3600],(struct capn_segment*)&capn_seg}};
|
||||
TestUnnamedUnion_ptr capn_val22 = {{1,1,0,0,16,2,0,(char*)&capn_buf[3696],(struct capn_segment*)&capn_seg}};
|
||||
TestUnnamedUnion_ptr capn_val23 = {{1,1,0,0,16,2,0,(char*)&capn_buf[3736],(struct capn_segment*)&capn_seg}};
|
||||
static TestUnion_ptr capn_val20 = {{1,1,0,0,64,2,0,(char*)&capn_buf[3456],(struct capn_segment*)&capn_seg}};
|
||||
static TestUnion_ptr capn_val21 = {{1,1,0,0,64,2,0,(char*)&capn_buf[3544],(struct capn_segment*)&capn_seg}};
|
||||
static TestUnnamedUnion_ptr capn_val22 = {{1,1,0,0,16,2,0,(char*)&capn_buf[3640],(struct capn_segment*)&capn_seg}};
|
||||
static TestUnnamedUnion_ptr capn_val23 = {{1,1,0,0,16,2,0,(char*)&capn_buf[3680],(struct capn_segment*)&capn_seg}};
|
||||
|
||||
TestUnionDefaults_ptr new_TestUnionDefaults(struct capn_segment *s) {
|
||||
TestUnionDefaults_ptr p;
|
||||
|
|
@ -3146,7 +3170,7 @@ void TestFieldZeroIsBit_set_thirdField(TestFieldZeroIsBit_ptr p, uint8_t thirdFi
|
|||
{
|
||||
capn_write8(p.p, 1, thirdField ^ 123u);
|
||||
}
|
||||
TestLists_ptr capn_val24 = {{1,1,0,0,0,10,0,(char*)&capn_buf[3792],(struct capn_segment*)&capn_seg}};
|
||||
static TestLists_ptr capn_val24 = {{1,1,0,0,0,10,0,(char*)&capn_buf[3736],(struct capn_segment*)&capn_seg}};
|
||||
|
||||
TestListDefaults_ptr new_TestListDefaults(struct capn_segment *s) {
|
||||
TestListDefaults_ptr p;
|
||||
|
|
@ -3388,7 +3412,7 @@ void TestOldVersion_set_old3(TestOldVersion_ptr p, TestOldVersion_ptr old3)
|
|||
{
|
||||
capn_setp(p.p, 1, old3.p);
|
||||
}
|
||||
capn_text capn_val25 = {3,(char*)&capn_buf[1544],(struct capn_segment*)&capn_seg};
|
||||
static capn_text capn_val25 = {3,(char*)&capn_buf[1480],(struct capn_segment*)&capn_seg};
|
||||
|
||||
TestNewVersion_ptr new_TestNewVersion(struct capn_segment *s) {
|
||||
TestNewVersion_ptr p;
|
||||
|
|
|
|||
|
|
@ -8,6 +8,7 @@
|
|||
#endif
|
||||
|
||||
#include "c++.capnp.h"
|
||||
#include "c.capnp.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
|
|
|
|||
59
tests/addressbook.capnp
Normal file
59
tests/addressbook.capnp
Normal file
|
|
@ -0,0 +1,59 @@
|
|||
# Based on the addressbook.capnp example in the capnproto C++ project:
|
||||
# https://github.com/sandstorm-io/capnproto/blob/6816634a08b08bc8f52b4ee809afb58389f19655/c%2B%2B/samples/addressbook.capnp
|
||||
#
|
||||
# Copyright (c) 2013-2014 Sandstorm Development Group, Inc. and contributors
|
||||
# Licensed under the MIT License:
|
||||
#
|
||||
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
# of this software and associated documentation files (the "Software"), to deal
|
||||
# in the Software without restriction, including without limitation the rights
|
||||
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
# copies of the Software, and to permit persons to whom the Software is
|
||||
# furnished to do so, subject to the following conditions:
|
||||
#
|
||||
# The above copyright notice and this permission notice shall be included in
|
||||
# all copies or substantial portions of the Software.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
||||
# THE SOFTWARE.
|
||||
|
||||
@0x9eb32e19f86ee174;
|
||||
|
||||
using C = import "/c.capnp";
|
||||
$C.fieldgetset;
|
||||
|
||||
struct Person {
|
||||
id @0 :UInt32;
|
||||
name @1 :Text;
|
||||
email @2 :Text;
|
||||
phones @3 :List(PhoneNumber);
|
||||
|
||||
struct PhoneNumber {
|
||||
number @0 :Text;
|
||||
type @1 :Type;
|
||||
|
||||
enum Type {
|
||||
mobile @0;
|
||||
home @1;
|
||||
work @2;
|
||||
}
|
||||
}
|
||||
|
||||
employment :union {
|
||||
unemployed @4 :Void;
|
||||
employer @5 :Text;
|
||||
school @6 :Text;
|
||||
selfEmployed @7 :Void;
|
||||
# We assume that a person is only one of these.
|
||||
}
|
||||
}
|
||||
|
||||
struct AddressBook {
|
||||
people @0 :List(Person);
|
||||
}
|
||||
|
||||
200
tests/addressbook.capnp.c
Normal file
200
tests/addressbook.capnp.c
Normal file
|
|
@ -0,0 +1,200 @@
|
|||
#include "addressbook.capnp.h"
|
||||
/* AUTO GENERATED - DO NOT EDIT */
|
||||
static const capn_text capn_val0 = {0,"",0};
|
||||
|
||||
Person_ptr new_Person(struct capn_segment *s) {
|
||||
Person_ptr p;
|
||||
p.p = capn_new_struct(s, 8, 4);
|
||||
return p;
|
||||
}
|
||||
Person_list new_Person_list(struct capn_segment *s, int len) {
|
||||
Person_list p;
|
||||
p.p = capn_new_list(s, len, 8, 4);
|
||||
return p;
|
||||
}
|
||||
void read_Person(struct Person *s, Person_ptr p) {
|
||||
capn_resolve(&p.p);
|
||||
s->id = capn_read32(p.p, 0);
|
||||
s->name = capn_get_text(p.p, 0, capn_val0);
|
||||
s->email = capn_get_text(p.p, 1, capn_val0);
|
||||
s->phones.p = capn_getp(p.p, 2, 0);
|
||||
s->employment_which = (enum Person_employment_which)(int) capn_read16(p.p, 4);
|
||||
switch (s->employment_which) {
|
||||
case Person_employment_employer:
|
||||
case Person_employment_school:
|
||||
s->employment.school = capn_get_text(p.p, 3, capn_val0);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
void write_Person(const struct Person *s, Person_ptr p) {
|
||||
capn_resolve(&p.p);
|
||||
capn_write32(p.p, 0, s->id);
|
||||
capn_set_text(p.p, 0, s->name);
|
||||
capn_set_text(p.p, 1, s->email);
|
||||
capn_setp(p.p, 2, s->phones.p);
|
||||
capn_write16(p.p, 4, s->employment_which);
|
||||
switch (s->employment_which) {
|
||||
case Person_employment_employer:
|
||||
case Person_employment_school:
|
||||
capn_set_text(p.p, 3, s->employment.school);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
void get_Person(struct Person *s, Person_list l, int i) {
|
||||
Person_ptr p;
|
||||
p.p = capn_getp(l.p, i, 0);
|
||||
read_Person(s, p);
|
||||
}
|
||||
void set_Person(const struct Person *s, Person_list l, int i) {
|
||||
Person_ptr p;
|
||||
p.p = capn_getp(l.p, i, 0);
|
||||
write_Person(s, p);
|
||||
}
|
||||
|
||||
uint32_t Person_get_id(Person_ptr p)
|
||||
{
|
||||
uint32_t id;
|
||||
id = capn_read32(p.p, 0);
|
||||
return id;
|
||||
}
|
||||
|
||||
capn_text Person_get_name(Person_ptr p)
|
||||
{
|
||||
capn_text name;
|
||||
name = capn_get_text(p.p, 0, capn_val0);
|
||||
return name;
|
||||
}
|
||||
|
||||
capn_text Person_get_email(Person_ptr p)
|
||||
{
|
||||
capn_text email;
|
||||
email = capn_get_text(p.p, 1, capn_val0);
|
||||
return email;
|
||||
}
|
||||
|
||||
Person_PhoneNumber_list Person_get_phones(Person_ptr p)
|
||||
{
|
||||
Person_PhoneNumber_list phones;
|
||||
phones.p = capn_getp(p.p, 2, 0);
|
||||
return phones;
|
||||
}
|
||||
|
||||
void Person_set_id(Person_ptr p, uint32_t id)
|
||||
{
|
||||
capn_write32(p.p, 0, id);
|
||||
}
|
||||
|
||||
void Person_set_name(Person_ptr p, capn_text name)
|
||||
{
|
||||
capn_set_text(p.p, 0, name);
|
||||
}
|
||||
|
||||
void Person_set_email(Person_ptr p, capn_text email)
|
||||
{
|
||||
capn_set_text(p.p, 1, email);
|
||||
}
|
||||
|
||||
void Person_set_phones(Person_ptr p, Person_PhoneNumber_list phones)
|
||||
{
|
||||
capn_setp(p.p, 2, phones.p);
|
||||
}
|
||||
|
||||
Person_PhoneNumber_ptr new_Person_PhoneNumber(struct capn_segment *s) {
|
||||
Person_PhoneNumber_ptr p;
|
||||
p.p = capn_new_struct(s, 8, 1);
|
||||
return p;
|
||||
}
|
||||
Person_PhoneNumber_list new_Person_PhoneNumber_list(struct capn_segment *s, int len) {
|
||||
Person_PhoneNumber_list p;
|
||||
p.p = capn_new_list(s, len, 8, 1);
|
||||
return p;
|
||||
}
|
||||
void read_Person_PhoneNumber(struct Person_PhoneNumber *s, Person_PhoneNumber_ptr p) {
|
||||
capn_resolve(&p.p);
|
||||
s->number = capn_get_text(p.p, 0, capn_val0);
|
||||
s->type = (enum Person_PhoneNumber_Type)(int) capn_read16(p.p, 0);
|
||||
}
|
||||
void write_Person_PhoneNumber(const struct Person_PhoneNumber *s, Person_PhoneNumber_ptr p) {
|
||||
capn_resolve(&p.p);
|
||||
capn_set_text(p.p, 0, s->number);
|
||||
capn_write16(p.p, 0, (uint16_t) (s->type));
|
||||
}
|
||||
void get_Person_PhoneNumber(struct Person_PhoneNumber *s, Person_PhoneNumber_list l, int i) {
|
||||
Person_PhoneNumber_ptr p;
|
||||
p.p = capn_getp(l.p, i, 0);
|
||||
read_Person_PhoneNumber(s, p);
|
||||
}
|
||||
void set_Person_PhoneNumber(const struct Person_PhoneNumber *s, Person_PhoneNumber_list l, int i) {
|
||||
Person_PhoneNumber_ptr p;
|
||||
p.p = capn_getp(l.p, i, 0);
|
||||
write_Person_PhoneNumber(s, p);
|
||||
}
|
||||
|
||||
capn_text Person_PhoneNumber_get_number(Person_PhoneNumber_ptr p)
|
||||
{
|
||||
capn_text number;
|
||||
number = capn_get_text(p.p, 0, capn_val0);
|
||||
return number;
|
||||
}
|
||||
|
||||
enum Person_PhoneNumber_Type Person_PhoneNumber_get_type(Person_PhoneNumber_ptr p)
|
||||
{
|
||||
enum Person_PhoneNumber_Type type;
|
||||
type = (enum Person_PhoneNumber_Type)(int) capn_read16(p.p, 0);
|
||||
return type;
|
||||
}
|
||||
|
||||
void Person_PhoneNumber_set_number(Person_PhoneNumber_ptr p, capn_text number)
|
||||
{
|
||||
capn_set_text(p.p, 0, number);
|
||||
}
|
||||
|
||||
void Person_PhoneNumber_set_type(Person_PhoneNumber_ptr p, enum Person_PhoneNumber_Type type)
|
||||
{
|
||||
capn_write16(p.p, 0, (uint16_t) (type));
|
||||
}
|
||||
|
||||
AddressBook_ptr new_AddressBook(struct capn_segment *s) {
|
||||
AddressBook_ptr p;
|
||||
p.p = capn_new_struct(s, 0, 1);
|
||||
return p;
|
||||
}
|
||||
AddressBook_list new_AddressBook_list(struct capn_segment *s, int len) {
|
||||
AddressBook_list p;
|
||||
p.p = capn_new_list(s, len, 0, 1);
|
||||
return p;
|
||||
}
|
||||
void read_AddressBook(struct AddressBook *s, AddressBook_ptr p) {
|
||||
capn_resolve(&p.p);
|
||||
s->people.p = capn_getp(p.p, 0, 0);
|
||||
}
|
||||
void write_AddressBook(const struct AddressBook *s, AddressBook_ptr p) {
|
||||
capn_resolve(&p.p);
|
||||
capn_setp(p.p, 0, s->people.p);
|
||||
}
|
||||
void get_AddressBook(struct AddressBook *s, AddressBook_list l, int i) {
|
||||
AddressBook_ptr p;
|
||||
p.p = capn_getp(l.p, i, 0);
|
||||
read_AddressBook(s, p);
|
||||
}
|
||||
void set_AddressBook(const struct AddressBook *s, AddressBook_list l, int i) {
|
||||
AddressBook_ptr p;
|
||||
p.p = capn_getp(l.p, i, 0);
|
||||
write_AddressBook(s, p);
|
||||
}
|
||||
|
||||
Person_list AddressBook_get_people(AddressBook_ptr p)
|
||||
{
|
||||
Person_list people;
|
||||
people.p = capn_getp(p.p, 0, 0);
|
||||
return people;
|
||||
}
|
||||
|
||||
void AddressBook_set_people(AddressBook_ptr p, Person_list people)
|
||||
{
|
||||
capn_setp(p.p, 0, people.p);
|
||||
}
|
||||
134
tests/addressbook.capnp.h
Normal file
134
tests/addressbook.capnp.h
Normal file
|
|
@ -0,0 +1,134 @@
|
|||
#ifndef CAPN_9EB32E19F86EE174
|
||||
#define CAPN_9EB32E19F86EE174
|
||||
/* AUTO GENERATED - DO NOT EDIT */
|
||||
#include <capnp_c.h>
|
||||
|
||||
#if CAPN_VERSION != 1
|
||||
#error "version mismatch between capnp_c.h and generated code"
|
||||
#endif
|
||||
|
||||
#include "c.capnp.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
struct Person;
|
||||
struct Person_PhoneNumber;
|
||||
struct AddressBook;
|
||||
|
||||
typedef struct {capn_ptr p;} Person_ptr;
|
||||
typedef struct {capn_ptr p;} Person_PhoneNumber_ptr;
|
||||
typedef struct {capn_ptr p;} AddressBook_ptr;
|
||||
|
||||
typedef struct {capn_ptr p;} Person_list;
|
||||
typedef struct {capn_ptr p;} Person_PhoneNumber_list;
|
||||
typedef struct {capn_ptr p;} AddressBook_list;
|
||||
|
||||
enum Person_PhoneNumber_Type {
|
||||
Person_PhoneNumber_Type_mobile = 0,
|
||||
Person_PhoneNumber_Type_home = 1,
|
||||
Person_PhoneNumber_Type_work = 2
|
||||
};
|
||||
enum Person_employment_which {
|
||||
Person_employment_unemployed = 0,
|
||||
Person_employment_employer = 1,
|
||||
Person_employment_school = 2,
|
||||
Person_employment_selfEmployed = 3
|
||||
};
|
||||
|
||||
struct Person {
|
||||
uint32_t id;
|
||||
capn_text name;
|
||||
capn_text email;
|
||||
Person_PhoneNumber_list phones;
|
||||
enum Person_employment_which employment_which;
|
||||
union {
|
||||
capn_text employer;
|
||||
capn_text school;
|
||||
} employment;
|
||||
};
|
||||
|
||||
static const size_t Person_word_count = 1;
|
||||
|
||||
static const size_t Person_pointer_count = 4;
|
||||
|
||||
static const size_t Person_struct_bytes_count = 40;
|
||||
|
||||
uint32_t Person_get_id(Person_ptr p);
|
||||
|
||||
capn_text Person_get_name(Person_ptr p);
|
||||
|
||||
capn_text Person_get_email(Person_ptr p);
|
||||
|
||||
Person_PhoneNumber_list Person_get_phones(Person_ptr p);
|
||||
|
||||
void Person_set_id(Person_ptr p, uint32_t id);
|
||||
|
||||
void Person_set_name(Person_ptr p, capn_text name);
|
||||
|
||||
void Person_set_email(Person_ptr p, capn_text email);
|
||||
|
||||
void Person_set_phones(Person_ptr p, Person_PhoneNumber_list phones);
|
||||
|
||||
struct Person_PhoneNumber {
|
||||
capn_text number;
|
||||
enum Person_PhoneNumber_Type type;
|
||||
};
|
||||
|
||||
static const size_t Person_PhoneNumber_word_count = 1;
|
||||
|
||||
static const size_t Person_PhoneNumber_pointer_count = 1;
|
||||
|
||||
static const size_t Person_PhoneNumber_struct_bytes_count = 16;
|
||||
|
||||
capn_text Person_PhoneNumber_get_number(Person_PhoneNumber_ptr p);
|
||||
|
||||
enum Person_PhoneNumber_Type Person_PhoneNumber_get_type(Person_PhoneNumber_ptr p);
|
||||
|
||||
void Person_PhoneNumber_set_number(Person_PhoneNumber_ptr p, capn_text number);
|
||||
|
||||
void Person_PhoneNumber_set_type(Person_PhoneNumber_ptr p, enum Person_PhoneNumber_Type type);
|
||||
|
||||
struct AddressBook {
|
||||
Person_list people;
|
||||
};
|
||||
|
||||
static const size_t AddressBook_word_count = 0;
|
||||
|
||||
static const size_t AddressBook_pointer_count = 1;
|
||||
|
||||
static const size_t AddressBook_struct_bytes_count = 8;
|
||||
|
||||
Person_list AddressBook_get_people(AddressBook_ptr p);
|
||||
|
||||
void AddressBook_set_people(AddressBook_ptr p, Person_list people);
|
||||
|
||||
Person_ptr new_Person(struct capn_segment*);
|
||||
Person_PhoneNumber_ptr new_Person_PhoneNumber(struct capn_segment*);
|
||||
AddressBook_ptr new_AddressBook(struct capn_segment*);
|
||||
|
||||
Person_list new_Person_list(struct capn_segment*, int len);
|
||||
Person_PhoneNumber_list new_Person_PhoneNumber_list(struct capn_segment*, int len);
|
||||
AddressBook_list new_AddressBook_list(struct capn_segment*, int len);
|
||||
|
||||
void read_Person(struct Person*, Person_ptr);
|
||||
void read_Person_PhoneNumber(struct Person_PhoneNumber*, Person_PhoneNumber_ptr);
|
||||
void read_AddressBook(struct AddressBook*, AddressBook_ptr);
|
||||
|
||||
void write_Person(const struct Person*, Person_ptr);
|
||||
void write_Person_PhoneNumber(const struct Person_PhoneNumber*, Person_PhoneNumber_ptr);
|
||||
void write_AddressBook(const struct AddressBook*, AddressBook_ptr);
|
||||
|
||||
void get_Person(struct Person*, Person_list, int i);
|
||||
void get_Person_PhoneNumber(struct Person_PhoneNumber*, Person_PhoneNumber_list, int i);
|
||||
void get_AddressBook(struct AddressBook*, AddressBook_list, int i);
|
||||
|
||||
void set_Person(const struct Person*, Person_list, int i);
|
||||
void set_Person_PhoneNumber(const struct Person_PhoneNumber*, Person_PhoneNumber_list, int i);
|
||||
void set_AddressBook(const struct AddressBook*, AddressBook_list, int i);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
165
tests/example-test.cpp
Normal file
165
tests/example-test.cpp
Normal file
|
|
@ -0,0 +1,165 @@
|
|||
/* example-test.cpp
|
||||
*
|
||||
* Some simple examples using c-capnproto.
|
||||
*
|
||||
* Based on the addressbook.capnp example in the capnproto C++ project:
|
||||
* https://github.com/sandstorm-io/capnproto/blob/6816634a08b08bc8f52b4ee809afb58389f19655/c%2B%2B/samples/addressbook.capnp
|
||||
*
|
||||
* Copyright (C) 2017 Alex Helfet
|
||||
*
|
||||
* This software may be modified and distributed under the terms
|
||||
* of the MIT license. See the LICENSE file for details.
|
||||
*/
|
||||
|
||||
#include <gtest/gtest.h>
|
||||
#include <cstdint>
|
||||
|
||||
#include "capnp_c.h"
|
||||
#include "addressbook.capnp.h"
|
||||
|
||||
static capn_text chars_to_text(const char *chars) {
|
||||
return (capn_text) {
|
||||
.len = (int) strlen(chars),
|
||||
.str = chars,
|
||||
.seg = NULL,
|
||||
};
|
||||
}
|
||||
|
||||
// EXPECT_CAPN_TEXT_EQ arguments:
|
||||
// const char * expected
|
||||
// capn_text t
|
||||
#define EXPECT_CAPN_TEXT_EQ(expected, t) \
|
||||
do { \
|
||||
EXPECT_EQ(strlen((expected)), (uint32_t) (t).len); \
|
||||
EXPECT_STREQ((expected), (t).str); \
|
||||
} while(0);
|
||||
|
||||
|
||||
// Demonstrates serializing an object tree to a byte array, then deserializing it
|
||||
// back into an object tree and asserting on the expected values therein.
|
||||
//
|
||||
// This example uses generated read_*, write_*, get_*, set_* functions
|
||||
// to deserialize into structs.
|
||||
TEST(Examples, RoundTripPerson) {
|
||||
uint8_t buf[4096];
|
||||
ssize_t sz = 0;
|
||||
|
||||
const char *name = "Firstname Lastname";
|
||||
const char *email = "username@domain.com";
|
||||
const char *school = "of life";
|
||||
|
||||
{
|
||||
struct capn c;
|
||||
capn_init_malloc(&c);
|
||||
capn_ptr cr = capn_root(&c);
|
||||
struct capn_segment *cs = cr.seg;
|
||||
|
||||
// Set initial object in `p`.
|
||||
struct Person p = {
|
||||
.id = 17,
|
||||
.name = chars_to_text(name),
|
||||
.email = chars_to_text(email),
|
||||
};
|
||||
p.employment_which = Person_employment_school;
|
||||
p.employment.school = chars_to_text(school);
|
||||
|
||||
p.phones = new_Person_PhoneNumber_list(cs, 2);
|
||||
struct Person_PhoneNumber pn0 = {
|
||||
.number = chars_to_text("123"),
|
||||
.type = Person_PhoneNumber_Type_work,
|
||||
};
|
||||
set_Person_PhoneNumber(&pn0, p.phones, 0);
|
||||
struct Person_PhoneNumber pn1 = {
|
||||
.number = chars_to_text("234"),
|
||||
.type = Person_PhoneNumber_Type_home,
|
||||
};
|
||||
set_Person_PhoneNumber(&pn1, p.phones, 1);
|
||||
|
||||
Person_ptr pp = new_Person(cs);
|
||||
write_Person(&p, pp);
|
||||
int setp_ret = capn_setp(capn_root(&c), 0, pp.p);
|
||||
ASSERT_EQ(0, setp_ret);
|
||||
sz = capn_write_mem(&c, buf, sizeof(buf), 0 /* packed */);
|
||||
capn_free(&c);
|
||||
}
|
||||
|
||||
{
|
||||
// Write serialized object to file system.
|
||||
FILE *f = fopen("tests/example-test.cpp.Person.out", "wb");
|
||||
ASSERT_NE(f, (void*)0);
|
||||
fwrite(buf, 1 /* size */, sz /* count */, f);
|
||||
int close_ret = fclose(f);
|
||||
ASSERT_EQ(0, close_ret);
|
||||
}
|
||||
|
||||
{
|
||||
// Deserialize `buf[0..sz-1]` to `rp`.
|
||||
struct capn rc;
|
||||
int init_mem_ret = capn_init_mem(&rc, buf, sz, 0 /* packed */);
|
||||
ASSERT_EQ(0, init_mem_ret);
|
||||
Person_ptr rroot;
|
||||
struct Person rp;
|
||||
rroot.p = capn_getp(capn_root(&rc), 0 /* off */, 1 /* resolve */);
|
||||
read_Person(&rp, rroot);
|
||||
|
||||
// Assert deserialized values in `rp`
|
||||
EXPECT_EQ(rp.id, (uint32_t) 17);
|
||||
EXPECT_CAPN_TEXT_EQ(name, rp.name);
|
||||
EXPECT_CAPN_TEXT_EQ(email, rp.email);
|
||||
|
||||
EXPECT_EQ(rp.employment_which, Person_employment_school);
|
||||
EXPECT_CAPN_TEXT_EQ(school, rp.employment.school);
|
||||
|
||||
EXPECT_EQ(2, capn_len(rp.phones));
|
||||
|
||||
struct Person_PhoneNumber rpn0;
|
||||
get_Person_PhoneNumber(&rpn0, rp.phones, 0);
|
||||
EXPECT_CAPN_TEXT_EQ("123", rpn0.number);
|
||||
EXPECT_EQ(rpn0.type, Person_PhoneNumber_Type_work);
|
||||
|
||||
struct Person_PhoneNumber rpn1;
|
||||
get_Person_PhoneNumber(&rpn1, rp.phones, 1);
|
||||
EXPECT_CAPN_TEXT_EQ("234", rpn1.number);
|
||||
EXPECT_EQ(rpn1.type, Person_PhoneNumber_Type_home);
|
||||
|
||||
capn_free(&rc);
|
||||
}
|
||||
}
|
||||
|
||||
// Demonstrate accessing serialized objects using accessor functions without
|
||||
// first copying values into structs.
|
||||
TEST(Examples, PersonWithAccessors) {
|
||||
struct capn c;
|
||||
capn_init_malloc(&c);
|
||||
capn_ptr cr = capn_root(&c);
|
||||
struct capn_segment *cs = cr.seg;
|
||||
|
||||
// Set fields with set_ accessors.
|
||||
Person_ptr pp = new_Person(cs);
|
||||
{
|
||||
Person_set_id(pp, 17);
|
||||
|
||||
capn_text name = chars_to_text("Name");
|
||||
EXPECT_CAPN_TEXT_EQ("Name", name);
|
||||
Person_set_name(pp, name);
|
||||
|
||||
Person_PhoneNumber_list pnl = new_Person_PhoneNumber_list(cs, 1);
|
||||
Person_set_phones(pp, pnl);
|
||||
Person_PhoneNumber_ptr pn0;
|
||||
pn0.p = capn_getp(pnl.p, 0 /* offset */, 0 /* resolve */);
|
||||
Person_PhoneNumber_set_type(pn0, Person_PhoneNumber_Type_home);
|
||||
}
|
||||
|
||||
// Assert field values returned by get_ accessors.
|
||||
{
|
||||
EXPECT_EQ(Person_get_id(pp), 17);
|
||||
EXPECT_CAPN_TEXT_EQ("Name", Person_get_name(pp));
|
||||
|
||||
Person_PhoneNumber_list pnl = Person_get_phones(pp);
|
||||
Person_PhoneNumber_ptr pn0;
|
||||
pn0.p = capn_getp(pnl.p, 0 /* offset */, 0 /* resolve */);
|
||||
EXPECT_EQ(Person_PhoneNumber_Type_home, Person_PhoneNumber_get_type(pn0));
|
||||
}
|
||||
|
||||
capn_free(&c);
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue