Merge branch 'feature/protobuf' into 'master'

feature/protobuf-c: Added the protobuf-C component from esp-idf

See merge request sdk/ESP8266_RTOS_SDK!762
This commit is contained in:
Dong Heng
2019-02-12 17:23:47 +08:00
70 changed files with 18426 additions and 0 deletions

View File

@ -0,0 +1,4 @@
set(COMPONENT_ADD_INCLUDEDIRS protobuf-c)
set(COMPONENT_SRCS "protobuf-c/protobuf-c/protobuf-c.c")
register_component()

View File

@ -0,0 +1,8 @@
#
# Component Makefile
#
COMPONENT_ADD_INCLUDEDIRS := protobuf-c
COMPONENT_SRCDIRS := protobuf-c/protobuf-c
COMPONENT_SUBMODULES += protobuf-c

View File

@ -0,0 +1,76 @@
#!/bin/bash -e
# from git-sh-setup.sh
require_clean_work_tree () {
git rev-parse --verify HEAD >/dev/null || exit 1
git update-index -q --ignore-submodules --refresh
err=0
if ! git diff-files --quiet --ignore-submodules
then
echo >&2 "Cannot $0: You have unstaged changes."
err=1
fi
if ! git diff-index --cached --quiet --ignore-submodules HEAD --
then
if [ $err = 0 ]
then
echo >&2 "Cannot $0: Your index contains uncommitted changes."
else
echo >&2 "Additionally, your index contains uncommitted changes."
fi
err=1
fi
if [ $err = 1 ]
then
test -n "$2" && echo >&2 "$2"
exit 1
fi
}
require_clean_work_tree
if ! which doxygen >/dev/null; then
echo "Error: doxygen is required"
exit 1
fi
DOXYGEN_VERSION="$(doxygen --version)"
DOC_BRANCH="gh-pages"
ORIG_BRANCH="$(git rev-parse --abbrev-ref HEAD)"
ORIG_COMMIT="$(git describe --match=NeVeRmAtCh --always --abbrev=40 --dirty)"
TOP="$(pwd)"
export GIT_DIR="$TOP/.git"
TMPDIR="$(mktemp --tmpdir=$TOP -d)"
HTMLDIR="$TMPDIR/_build/html"
INDEX_FILE="$GIT_DIR/index.${DOC_BRANCH}"
rm -f "$INDEX_FILE"
trap "{ cd $TOP; git checkout --force ${ORIG_BRANCH}; rm -f $INDEX_FILE; rm -rf $TMPDIR; }" EXIT
cd "$TMPDIR"
git reset --hard HEAD
./autogen.sh
mkdir _build
cd _build
../configure
make html
if ! git checkout "${DOC_BRANCH}"; then
git checkout --orphan "${DOC_BRANCH}"
fi
touch "$HTMLDIR/.nojekyll"
echo lib.protobuf-c.io > "$HTMLDIR/CNAME"
GIT_INDEX_FILE="$INDEX_FILE" GIT_WORK_TREE="$HTMLDIR" \
git add --no-ignore-removal .
GIT_INDEX_FILE="$INDEX_FILE" GIT_WORK_TREE="$HTMLDIR" \
git commit -m "Rebuild html documentation from commit ${ORIG_COMMIT} using Doxygen ${DOXYGEN_VERSION}"

View File

@ -0,0 +1,43 @@
*~
.*swp
*.la
*.gcda
*.gcno
*.lo
*.log
*.o
*.tar.gz
*.trs
.deps/
.dirstamp
.libs/
/Doxyfile
/Makefile
/Makefile.in
/aclocal.m4
/autom4te.cache
/build-aux
/config.*
/configure
/doxygen-doc
/html
/libtool
/protobuf-c-*-coverage.info
/protobuf-c-*-coverage/
/stamp-h1
/stamp-html
/test-suite.log
TAGS
protobuf-c/libprotobuf-c.pc
protoc-c/protoc-c
protoc-c/protoc-gen-c
t/generated-code/test-generated-code
t/generated-code2/cxx-generate-packed-data
t/generated-code2/test-full-cxx-output.inc
t/generated-code2/test-generated-code2
t/generated-code3/test-generated-code3
t/version/version
*.pb-c.c
*.pb-c.h
*.pb.cc
*.pb.h

View File

@ -0,0 +1,58 @@
language:
- c
- cpp
# Use Trusty VM
sudo: required
dist: trusty
matrix:
include:
# Test default gcc
- env: GCC_VERSION=4.8
os: linux
compiler: gcc
addons:
apt:
packages:
- lcov
- valgrind
# Test gcc-5.0
- env: GCC_VERSION=5
os: linux
addons:
apt:
packages:
- valgrind
- g++-5
- gcc-5
sources:
- ubuntu-toolchain-r-test
env:
global:
- PROTOBUF_VERSION=3.0.2
- PKG_CONFIG_PATH=$HOME/protobuf-$PROTOBUF_VERSION-bin/lib/pkgconfig
before_install:
- if [ -n "$GCC_VERSION" ]; then export CXX="g++-${GCC_VERSION}" CC="gcc-${GCC_VERSION}"; fi
- if [ -n "$CLANG_VERSION" ]; then export CXX="clang++-${CLANG_VERSION}" CC="clang-${CLANG_VERSION}"; fi
- if [ "$GCC_VERSION" == "4.8" ]; then export CXX="g++" CC="gcc"; fi
- which $CXX
- which $CC
- which valgrind
install:
- pip install --user cpp-coveralls
- wget https://github.com/google/protobuf/archive/v$PROTOBUF_VERSION.tar.gz
- tar xf v$PROTOBUF_VERSION.tar.gz
- ( cd protobuf-$PROTOBUF_VERSION && ./autogen.sh && ./configure --prefix=$HOME/protobuf-$PROTOBUF_VERSION-bin && make -j2 && make install )
script:
- ./autogen.sh
- ./configure && make -j2 distcheck VERBOSE=1 && make clean
- if [ "$GCC_VERSION" != "4.8" ]; then ./configure --enable-valgrind-tests CFLAGS="-fsanitize=undefined -fno-sanitize-recover=undefined" && make -j2 distcheck DISTCHECK_CONFIGURE_FLAGS="--enable-valgrind-tests CFLAGS=\"-fsanitize=undefined -fno-sanitize-recover=undefined\"" VERBOSE=1 && make clean; fi
- if [ "$CC" = "gcc" ]; then ./configure --enable-code-coverage && make -j2 && make check; fi
after_success:
- if [ "$CC" = "gcc" ]; then cpp-coveralls --build-root . --exclude t/ --exclude /usr/include --exclude protobuf-$PROTOBUF_VERSION --exclude protoc-c; fi

View File

@ -0,0 +1,5 @@
## Contributing
The most recently released `protobuf-c` version is kept on the `master` branch, while the `next` branch is used for commits targeted at the next release. Please base patches and pull requests against the `next` branch. __Do not open pull requests against master!__
Copyright to all contributions are retained by the original author, but must be licensed under the terms of the [BSD-2-Clause](http://opensource.org/licenses/BSD-2-Clause) license.

View File

@ -0,0 +1,441 @@
protobuf-c (1.3.0)
[ Robert Edmonds ]
* Release 1.3.0.
* Add test case for the issue in #220 (#254).
* Fix issue #251, "Bad enums with multiple oneofs" (#256).
* Add warning flags to my_CFLAGS (#257).
* Fix namespace errors when compiled with latest protobuf (#280).
* Bump minimum required header version for proto3 syntax (#282).
[ Paolo Borelli ]
* Turn the compiler into a protoc plugin (#206). This allows the protobuf-c
compiler to be invoked as "protoc --c_out=...". For backwards
compatibility, we still ship a protoc-c command, but it's a symlink to the
protoc-gen-c binary.
* proto3 support (#228).
* Remove leftover FIXME comment (#258).
* Fix proto3 "is zeroish" evaluation (#264).
* Small cleanup in oneof handling (#265).
* Rework is_zeroish one more time (#267).
* proto3: make strings default to "" instead of NULL (#274).
[ Tomek Wasilczyk ]
* Fix -Wsign-compare warnings (#213).
* Fix ISO C90 -Wdeclaration-after-statement warnings (#214).
* Fix bigendian -Wunused-label warning (#215).
[ Ilya Lipnitsky ]
* protoc-c/c_message.cc: Force int size on oneof enums (#221). Fixes wrong
enum generation and handling for onceof cases (#220).
[ Adnan ]
* Fix cmake build if built as part of an external project (#231).
[ Gregory Detal ]
* Remove .pb.{cc,h} in distdir instead of top_distdir in order to prevent
removing files from other projects when protobuf-c is included as an
autotools subproject (#232).
[ Ben Farnham ]
* Relax autoconf constraint from v2.64 to v2.63 so that it works on older
Linux distros (#233).
[ Thomas Köckerbauer ]
* rm argument fix for Solaris (#234).
* Add 'const' qualifier to 'init_value' variable in generated files (#236).
[ Richard Kettlewell ]
* Document and extend the effect of passing NULL to ..._free_unpacked
functions (#255).
[ Alex Milich ]
* CMake: Workaround for static builds that use MSVC (#243).
[ Josh Junon ]
* CMake: Allow protobuf-c to be included via include_subdirectory (#245).
[ Alexei Kasatkin ]
* CMake: Windows fixes (#266).
protobuf-c (1.2.1)
[ Robert Edmonds ]
* Release 1.2.1.
[ Paolo Borelli ]
* protoc-c: Generate code that uses the universal zero initializer {0} when
initializing a oneof union (#187, #205).
protobuf-c (1.2.0)
[ Robert Edmonds ]
* Release 1.2.0.
[ Ilya Lipnitsky ]
* Implement the "optimize_for = CODE_SIZE" option (#183).
* Eliminate undefined behavior in zigzag functions (#198).
* Pack negative enum values correctly (#199).
[ Peter Leschev ]
* Fix protobuf_c_message_get_packed_size() on 16-bit systems (#196, #197).
[ Diego Elio Pettenò ]
* Update link to Autotools Mythbuster to canonical site (#201).
[ Zex Li ]
* Skip test suite when cross-compiling (#184).
protobuf-c (1.1.1)
[ Robert Edmonds ]
* Release 1.1.1.
* Use protobuf 2.6.1 in the Travis-CI environment.
[ Ilya Lipnitskiy ]
* Munge C block comment delimiters in protobuf comments, preventing syntax
errors in generated header files (Issue #180, #185).
* Add static qualifier to ProtobufCEnumValue and ProtobufCEnumValueIndex
variables in generated output.
[ Oleg Efimov ]
* Fix -Wpointer-sign compiler diagnostics in the test suite.
* Check for NULL pointers in protobuf_c_message_free_unpacked()
(Issue #177).
* Exclude protoc-c and downloaded protobuf sources from Coveralls report.
[ Andrey Myznikov ]
* Fix incorrect 'short_name' field values in ProtobufCServiceDescriptor
variables in generated output.
protobuf-c (1.1.0)
[ Robert Edmonds ]
* Release 1.1.0.
[ Ilya Lipnitskiy ]
* Fix a bug when merging optional byte fields.
* Documentation updates.
* Implement oneof support (Issue #174). Protobuf 2.6.0 or newer is now
required to build protobuf-c.
* Print leading comments for enum, message, and field definitions into
generated header files (Issue #175).
protobuf-c (1.0.2)
[ Robert Edmonds ]
* Release 1.0.2.
[ Ilya Lipnitskiy ]
* Fix a build failure with Protobuf 2.6.0 related to aliased enum constants
(Issue #163).
* Protobuf 2.5.0 or newer is now required to build protobuf-c (Issue #166).
This is due to the fix for #163.
[ Alexei Kasatkin ]
* Eliminate void pointer arithmetic (Issue #167).
* Always define PROTOBUF_C__DEPRECATED, even on compilers that are not GCC
(Issue #167).
* Work around the lack of the 'inline' keyword in Microsoft compilers
(Issue #167).
* Add a CMakeLists.txt file as a fallback build system for Windows
(Issue #168).
[ Natanael Copa ]
* Fix a build failure in the test suite that occurred with a parallel make
running on a system with a large number of CPUs (Issue #156, #169).
protobuf-c (1.0.1)
[ Robert Edmonds ]
* Explicitly set the .data field of ProtobufCBinaryData's to NULL when
unpacking a zero length byte string (Issue #157).
protobuf-c (1.0.0)
[ Andrei Nigmatulin ]
* Append "u", "ull", and "ll" integer literal suffixes for uint32, uint64,
and int64 default values in generated code, in order to avoid "integer
constant is so large that it is unsigned" compiler warnings.
(Issue #136.)
* Revert the problematic hash-based required field detection.
(Related to Issue #60, #79, #137.)
* Replace the 'packed' member of ProtobufCFieldDescriptor with a 'flags'
word. Define flags for packed and deprecated fields. (Issue #138.)
[ Dave Benson ]
* Treat a "length-prefixed" wire-type message for a repeated field as
packed-repeated whenever it makes sense (for all types other than
messages, strings, and bytes).
* Switch to New BSD license.
* Add protobuf_c_message_check().
* Compile error in packing 64-bit versions on some platforms
(srobbins99: Issue #68 Comment 1).
* Fix for memory error if the required-field check fails. See Issue #63
for demo (w/ nice test case by dror.harari).
* Add PROTOBUF_C_{MAJOR,MINOR} for compile-time checks and
protobuf_c_{major,minor} for checks about the running library
(Issue #53).
* Use a small constant-size hash-table instead of alloca() for detecting
required fields, and it also prevents us from using too much stack, etc.
(Related to Issue #60, #79).
* Add a macro to ensure enums are the size of ints (Issue #69).
[ Ilya Lipnitskiy ]
* Travis-CI integration.
* Add source .proto filename to generated files.
* Add protobuf-c version to protoc-c --version output (Issue #52).
* For embedded submessage fields, merge multiple instances of the same
field, per the protobuf documentation (Issue #91).
* Don't print unpack errors by default.
* Optionally allow running the test suite under valgrind with ./configure
--enable-valgrind-tests. (Based on valgrind-tests.m4 from gnulib.)
[ Kevin Lyda ]
* Autoconf portability fixes.
* Add doxygen detection and make targets to the build system.
* Doxygen documentation for the libprotobuf-c public API (Issue #132).
[ Nick Galbreath ]
* Prevent possible overflow on 64-bit systems (Issue #106).
[ Robert Edmonds ]
* Remove CMake (Issue #87).
* Modernize the build system.
- Don't generate any diagnostics when building the build system with
modern autotools (Issue #89).
- Use the PKG_CHECK_MODULES macro to locate protobuf.
- Use the AC_C_BIGENDIAN macro to detect endianness, rather than custom
code.
- Use the automake silent-rules option so the build output is actually
readable.
- Generate our own pkg-config .pc files.
* Reorganize the source tree. This affects the public protobuf-c header
path, which is now <protobuf-c/protobuf-c.h>. A compatibility symlink from
<google/protobuf-c/> to <protobuf-c/> has been installed so that existing
code will continue to compile. New code should at some point begin using
the new include path, i.e., "#include <protobuf-c/protobuf-c.h>" rather
than "#include <google/protobuf-c/protobuf-c.h>".
* The RPC code has been split out into a separate project, protobuf-c-rpc.
* Fix a potential use of an unitialized value in protobuf_c_message_unpack()
and several memory leaks in protoc-c, discovered by a commercial static code
analysis tool.
* Bump the libprotobuf-c SONAME.
* Begin versioning the library's symbols. (Based on ld-version-script.m4
from gnulib.)
* Preserve case in enum value names generated by protoc-c (Issue #129).
Reported by Oleg Efimov.
* Add library functions protobuf_c_version() and protobuf_c_version_string()
for retrieving the version of the compiled library, and header macros
PROTOBUF_C_VERSION and PROTOBUF_C_VERSION_STRING for retrieving the
version of the header file. This replaces the interfaces for retrieving
the protobuf-c version numbers in Issue #53.
* Add a version guard that ensures that the output of protoc-c is only
compiled against a protobuf-c header file from the exact same protobuf-c
release.
* Add a --enable-code-coverage option to configure, which enables a
"make check-code-coverage" build target. This generates a code coverage
report and requires the lcov tool to be installed.
* Remove the old DocBook documentation in doc/c-code-generator.{html,xml}.
Relevant material has been updated and incorporated into the Doxygen
documentation in the protobuf-c header file.
* Remove the protobuf_c_default_allocator and protobuf_c_system_allocator
global variables from the exported library interface. All exported library
functions that need to perform dynamic memory allocation receive a
user-provided ProtobufCAllocator* parameter. If this parameter is NULL,
the system's default memory allocator will be used.
Client code that previously passed "&protobuf_c_system_allocator" to
protobuf-c library functions taking a ProtobufCAllocator* argument should
be updated to pass "NULL" instead.
Client code that previously overrode protobuf_c_default_allocator with
custom allocation functions and passed NULL as the ProtobufCAllocator*
argument to protobuf-c library functions should be updated to instead
enclose the custom allocation functions in a ProtobufCAllocator struct and
pass this object to protobuf-c library functions taking a
ProtobufCAllocator* parameter.
* Update copyright and license statements throughout. The original
protobuf code released by Google was relicensed from Apache-2.0 to
BSD-3-Clause. Dave Benson also converted his license from BSD-3-Clause
to BSD-2-Clause.
[ Tomasz Wasilczyk ]
* Don't export protobuf_c_message_init_generic() as an external symbol.
* Don't use C++ style comments in C code.
* Fix -Wcast-align warnings when compiled with clang.
protobuf-c (0.15)
- make protobuf_c_message_init() into a function (Issue #49, daveb)
- Fix for freeing memory after unpacking bytes w/o a default-value.
(Andrei Nigmatulin)
- minor windows portability issues (use ProtobufC_FD) (Pop Stelian)
- --with-endianness={little,big} (Pop Stelian)
- bug setting up values of has_idle in public dispatch,
make protobuf_c_dispatch_run() use only public members (daveb)
- provide cmake support and some Windows compatibility (Nikita Manovich)
protobuf-c (0.14)
- build fix (missing dependency in test directory)
- add generation / installation of pkg-config files. (Bobby Powers)
- support for packed repeated fields (Dave Benson)
- bug in protobuf_c_dispatch_close_fd(), which usually only
showed up in later function calls.
- support for deprecated fields -- enable a GCC warning
if a field has the "deprecated" option enabled. (Andrei Nigmatulin)
- hackery to try to avoid touching inttypes.h on windows (Issue #41)
- fix for protobuf_c_message_unpack() to issue error if any
"required" field is missing in input stream. (Andrei Nigmatulin)
protobuf-c (0.13)
- Fix for when the number of connections gets too great in RPC.
(Leszek Swirski) (issue #32)
- Add --disable-protoc to only build libprotobuf-c (daveb)
- Bug fixes for protobuf_c_enum_descriptor_get_value_by_name()
and protobuf_c_service_descriptor_get_method_by_name()
- if descriptor->message_init != NULL, use it from unpack()
as an optimization (daveb)
- implement protobuf_c_{client,server}_set_error_handler()
protobuf-c (0.12)
- for field names which are reserved words, use the real name
given in the protobuf-c file, not the mangled name which
is the name of the member in the C structure. (Andrei Nigmatulin)
- add protobuf_c_message_init() function; add virtual function
that implements it efficiently. (Andrei Nigmatulin)
- bug fix for sfixed32, fixed32, float wire-types on
big-endian platforms (Robert Edmonds)
- compile with the latest protobuf (the header file wire_format_inl.h
is now wire_format.h) (Robert Edmonds)
protobuf-c (0.11)
- allow CFLAGS=-DPRINT_UNPACK_ERRORS=0 to suppress
unpack warnings from being printed at compile time (Andrei Nigmatulin)
- give error if an unknown wire-type is encountered (Andrei Nigmatulin)
- fix technically possible overflows during unpack of very
large messages (Andrei Nigmatulin)
- [UNFINISHED] windows RPC work
- use automake's "foreign" mode from within configure.ac
and add version information to the library (Robert Edmonds)
- ProtobufCServiceDescriptor::method_indices_by_name: missing
const. (Issue 21)
- Update to support new UnknownFields API. (fix by dcreager) (Issue 20)
protobuf-c (0.10)
- build issue on platforms which don't compute library dependencies
automatically.
- fix for certain types of corrupt messages (Landon Fuller) (issue 16)
protobuf-c (0.9)
- build issue: needed $(EXEEXT) in dependency lists for cygwin
- bug fix: protobuf_c_service_get_method_by_name() was not correct b/c
the service's methods were not sorted by name (the header file
used to incorrectly state that they were).
Now we correctly implement protobuf_c_service_get_method_by_name()
(using a bsearch indexed by separate array).
- generated source incompatibility: we added a new
member to ProtobufCServiceDescriptor (method_indices_by_name).
You will have to run the latest protobuf
to generate those structures.
- rename rpc-client's "autoretry" mechanism to "autoreconnect".
- bug fixes using TCP clients with the RPC system.
- handle allocation failures more gracefully (Jason Lunz) (issue 15)
protobuf-c (0.8)
- Destroy function typedef for Services was omitting a "*"
- service_machgen_invoke was broken. (issue 12)
- add RPC system (BETA)
- don't segfault when packing NULL strings and messages. (issue 13)
protobuf-c (0.7)
- memory leak: unknown fields were not being freed by free_unpacked()
- lowercase field names consistently when composing
default_value names. (issue 11)
- remove spurious semicolon (issue 10)
protobuf-c (0.6)
- Warning suppression for -Wcast-qual and -Wshadow.
- Support for default values of all types allowed by core protobuf.
- Generate message__init functions, for when the static initializer
isn't convenient.
- add some reserved fields at the end of the various descriptors
protobuf-c (0.5)
- License now included in major files.
- Use little-endian optimizations; fix a bug therein.
- Include 'make deb' target.
protobuf-c (0.4)
- Update to work with protobuf 2.0.1.
protobuf-c (0.2)
protobuf-c (0.3)
- Minor pedantic concerns about generated code.
protobuf-c (0.1)
- Lots of test code (and bug fixes).
protobuf-c (0.0)
- Initial release.

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,193 @@
<doxygenlayout version="1.0">
<!-- Generated by doxygen 1.8.7 -->
<!-- Navigation index tabs for HTML output -->
<navindex>
<tab type="mainpage" visible="yes" title=""/>
<tab type="pages" visible="yes" title="" intro=""/>
<tab type="modules" visible="yes" title="" intro=""/>
<tab type="namespaces" visible="yes" title="">
<tab type="namespacelist" visible="yes" title="" intro=""/>
<tab type="namespacemembers" visible="yes" title="" intro=""/>
</tab>
<tab type="classes" visible="yes" title="">
<tab type="classlist" visible="yes" title="" intro=""/>
<tab type="classindex" visible="$ALPHABETICAL_INDEX" title=""/>
<tab type="hierarchy" visible="yes" title="" intro=""/>
<tab type="classmembers" visible="yes" title="" intro=""/>
</tab>
<tab type="files" visible="yes" title="">
<tab type="filelist" visible="yes" title="" intro=""/>
<tab type="globals" visible="yes" title="" intro=""/>
</tab>
<tab type="examples" visible="yes" title="" intro=""/>
</navindex>
<!-- Layout definition for a class page -->
<class>
<briefdescription visible="yes"/>
<includes visible="$SHOW_INCLUDE_FILES"/>
<inheritancegraph visible="$CLASS_GRAPH"/>
<collaborationgraph visible="$COLLABORATION_GRAPH"/>
<memberdecl>
<nestedclasses visible="yes" title=""/>
<publictypes title=""/>
<services title=""/>
<interfaces title=""/>
<publicslots title=""/>
<signals title=""/>
<publicmethods title=""/>
<publicstaticmethods title=""/>
<publicattributes title=""/>
<publicstaticattributes title=""/>
<protectedtypes title=""/>
<protectedslots title=""/>
<protectedmethods title=""/>
<protectedstaticmethods title=""/>
<protectedattributes title=""/>
<protectedstaticattributes title=""/>
<packagetypes title=""/>
<packagemethods title=""/>
<packagestaticmethods title=""/>
<packageattributes title=""/>
<packagestaticattributes title=""/>
<properties title=""/>
<events title=""/>
<privatetypes title=""/>
<privateslots title=""/>
<privatemethods title=""/>
<privatestaticmethods title=""/>
<privateattributes title=""/>
<privatestaticattributes title=""/>
<friends title=""/>
<related title="" subtitle=""/>
<membergroups visible="yes"/>
</memberdecl>
<detaileddescription title=""/>
<memberdef>
<inlineclasses title=""/>
<typedefs title=""/>
<enums title=""/>
<services title=""/>
<interfaces title=""/>
<constructors title=""/>
<functions title=""/>
<related title=""/>
<variables title=""/>
<properties title=""/>
<events title=""/>
</memberdef>
<allmemberslink visible="yes"/>
<usedfiles visible="$SHOW_USED_FILES"/>
<authorsection visible="yes"/>
</class>
<!-- Layout definition for a namespace page -->
<namespace>
<briefdescription visible="yes"/>
<memberdecl>
<nestednamespaces visible="yes" title=""/>
<constantgroups visible="yes" title=""/>
<classes visible="yes" title=""/>
<typedefs title=""/>
<enums title=""/>
<functions title=""/>
<variables title=""/>
<membergroups visible="yes"/>
</memberdecl>
<detaileddescription title=""/>
<memberdef>
<inlineclasses title=""/>
<typedefs title=""/>
<enums title=""/>
<functions title=""/>
<variables title=""/>
</memberdef>
<authorsection visible="yes"/>
</namespace>
<!-- Layout definition for a file page -->
<file>
<briefdescription visible="yes"/>
<includes visible="$SHOW_INCLUDE_FILES"/>
<includegraph visible="$INCLUDE_GRAPH"/>
<includedbygraph visible="$INCLUDED_BY_GRAPH"/>
<sourcelink visible="yes"/>
<memberdecl>
<classes visible="yes" title=""/>
<namespaces visible="yes" title=""/>
<constantgroups visible="yes" title=""/>
<defines title=""/>
<typedefs title=""/>
<enums title=""/>
<functions title=""/>
<variables title=""/>
<membergroups visible="yes"/>
</memberdecl>
<detaileddescription title=""/>
<memberdef>
<inlineclasses title=""/>
<defines title=""/>
<typedefs title=""/>
<enums title=""/>
<functions title=""/>
<variables title=""/>
</memberdef>
<authorsection/>
</file>
<!-- Layout definition for a group page -->
<group>
<detaileddescription title=""/>
<groupgraph visible="$GROUP_GRAPHS"/>
<memberdecl>
<nestedgroups visible="yes" title=""/>
<dirs visible="yes" title=""/>
<files visible="yes" title=""/>
<namespaces visible="yes" title=""/>
<classes visible="yes" title=""/>
<defines title=""/>
<typedefs title=""/>
<enums title=""/>
<enumvalues title=""/>
<functions title=""/>
<variables title=""/>
<signals title=""/>
<publicslots title=""/>
<protectedslots title=""/>
<privateslots title=""/>
<events title=""/>
<properties title=""/>
<friends title=""/>
<membergroups visible="yes"/>
</memberdecl>
<memberdef>
<pagedocs/>
<inlineclasses title=""/>
<defines title=""/>
<typedefs title=""/>
<enums title=""/>
<enumvalues title=""/>
<functions title=""/>
<variables title=""/>
<signals title=""/>
<publicslots title=""/>
<protectedslots title=""/>
<privateslots title=""/>
<events title=""/>
<properties title=""/>
<friends title=""/>
</memberdef>
<authorsection visible="yes"/>
</group>
<!-- Layout definition for a directory page -->
<directory>
<briefdescription visible="yes"/>
<directorygraph visible="yes"/>
<memberdecl>
<dirs visible="yes"/>
<files visible="yes"/>
</memberdecl>
<detaileddescription title=""/>
</directory>
</doxygenlayout>

View File

@ -0,0 +1,32 @@
Copyright (c) 2008-2016, Dave Benson and the protobuf-c authors.
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
The code generated by the protoc-gen-c code generator and by the
protoc-c compiler is owned by the owner of the input files used when
generating it. This code is not standalone and requires a support
library to be linked with it. This support library is covered by the
above license.

View File

@ -0,0 +1,294 @@
bin_PROGRAMS =
check_PROGRAMS =
noinst_PROGRAMS =
lib_LTLIBRARIES =
nobase_include_HEADERS =
pkgconfig_DATA =
BUILT_SOURCES =
TESTS =
CLEANFILES =
DISTCLEANFILES =
EXTRA_DIST =
ACLOCAL_AMFLAGS = -I m4 ${ACLOCAL_FLAGS}
EXTRA_DIST += LICENSE
EXTRA_DIST += README.md
AM_CPPFLAGS = \
-include $(top_builddir)/config.h \
-I${top_srcdir}/protobuf-c \
-I${top_builddir} \
-I${top_srcdir}
AM_CFLAGS = ${my_CFLAGS}
AM_LDFLAGS =
# code coverage
AM_CFLAGS += ${CODE_COVERAGE_CFLAGS}
AM_LDFLAGS += ${CODE_COVERAGE_LDFLAGS}
CODE_COVERAGE_LCOV_OPTIONS = --no-external
CODE_COVERAGE_IGNORE_PATTERN = "$(abs_top_builddir)/t/*"
@CODE_COVERAGE_RULES@
#
# libprotobuf-c
#
LIBPROTOBUF_C_CURRENT=1
LIBPROTOBUF_C_REVISION=0
LIBPROTOBUF_C_AGE=0
lib_LTLIBRARIES += \
protobuf-c/libprotobuf-c.la
nobase_include_HEADERS += \
protobuf-c/protobuf-c.h
protobuf_c_libprotobuf_c_la_SOURCES = \
protobuf-c/protobuf-c.c \
protobuf-c/protobuf-c.h
protobuf_c_libprotobuf_c_la_LDFLAGS = $(AM_LDFLAGS) \
-version-info $(LIBPROTOBUF_C_CURRENT):$(LIBPROTOBUF_C_REVISION):$(LIBPROTOBUF_C_AGE) \
-no-undefined
if HAVE_LD_VERSION_SCRIPT
protobuf_c_libprotobuf_c_la_LDFLAGS += \
-Wl,--version-script=$(top_srcdir)/protobuf-c/libprotobuf-c.sym
else
protobuf_c_libprotobuf_c_la_LDFLAGS += \
-export-symbols-regex "^(protobuf_c_[a-z].*)"
endif
EXTRA_DIST += protobuf-c/libprotobuf-c.sym
pkgconfig_DATA += protobuf-c/libprotobuf-c.pc
CLEANFILES += protobuf-c/libprotobuf-c.pc
EXTRA_DIST += protobuf-c/libprotobuf-c.pc.in
#
# protoc-gen-c
#
if BUILD_COMPILER
bin_PROGRAMS += protoc-c/protoc-gen-c
protoc_c_protoc_gen_c_SOURCES = \
protoc-c/c_bytes_field.cc \
protoc-c/c_bytes_field.h \
protoc-c/c_enum.cc \
protoc-c/c_enum.h \
protoc-c/c_enum_field.cc \
protoc-c/c_enum_field.h \
protoc-c/c_extension.cc \
protoc-c/c_extension.h \
protoc-c/c_field.cc \
protoc-c/c_field.h \
protoc-c/c_file.cc \
protoc-c/c_file.h \
protoc-c/c_generator.cc \
protoc-c/c_generator.h \
protoc-c/c_helpers.cc \
protoc-c/c_helpers.h \
protoc-c/c_message.cc \
protoc-c/c_message.h \
protoc-c/c_message_field.cc \
protoc-c/c_message_field.h \
protoc-c/c_primitive_field.cc \
protoc-c/c_primitive_field.h \
protoc-c/c_service.cc \
protoc-c/c_service.h \
protoc-c/c_string_field.cc \
protoc-c/c_string_field.h \
protoc-c/main.cc
protoc_c_protoc_gen_c_CXXFLAGS = \
$(AM_CXXFLAGS) \
$(protobuf_CFLAGS)
protoc_c_protoc_gen_c_LDADD = \
$(protobuf_LIBS) \
-lprotoc
#
# protoc-c compat link
#
install-exec-hook:
rm -f $(DESTDIR)$(bindir)/protoc-c
ln -s protoc-gen-c $(DESTDIR)$(bindir)/protoc-c
#
# protobuf-c tests
#
if CROSS_COMPILING
#
# skip tests on cross-compiling
#
else
LOG_COMPILER = $(VALGRIND)
check_PROGRAMS += \
t/generated-code/test-generated-code \
t/generated-code2/test-generated-code2 \
t/version/version
TESTS += \
t/generated-code/test-generated-code \
t/generated-code2/test-generated-code2 \
t/version/version
t_generated_code_test_generated_code_SOURCES = \
t/generated-code/test-generated-code.c \
t/test.pb-c.c
t_generated_code_test_generated_code_LDADD = \
protobuf-c/libprotobuf-c.la
t_generated_code2_test_generated_code2_SOURCES = \
t/generated-code2/test-generated-code2.c \
t/test-full.pb-c.c \
t/test-optimized.pb-c.c
t_generated_code2_test_generated_code2_LDADD = \
protobuf-c/libprotobuf-c.la
noinst_PROGRAMS += \
t/generated-code2/cxx-generate-packed-data
t_generated_code2_cxx_generate_packed_data_SOURCES = \
t/generated-code2/cxx-generate-packed-data.cc \
t/test-full.pb.cc
$(t_generated_code2_cxx_generate_packed_data_OBJECTS): t/test-full.pb.h
t_generated_code2_cxx_generate_packed_data_CXXFLAGS = \
$(AM_CXXFLAGS) \
$(protobuf_CFLAGS)
t_generated_code2_cxx_generate_packed_data_LDADD = \
$(protobuf_LIBS)
t/test.pb-c.c t/test.pb-c.h: $(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) $(top_srcdir)/t/test.proto
$(AM_V_GEN)@PROTOC@ --plugin=$(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) -I$(top_srcdir) --c_out=$(top_builddir) $(top_srcdir)/t/test.proto
t/test-optimized.pb-c.c t/test-optimized.pb-c.h: $(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) $(top_srcdir)/t/test-optimized.proto
$(AM_V_GEN)@PROTOC@ --plugin=$(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) -I$(top_srcdir) --c_out=$(top_builddir) $(top_srcdir)/t/test-optimized.proto
t/test-full.pb-c.c t/test-full.pb-c.h: $(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) $(top_srcdir)/t/test-full.proto
$(AM_V_GEN)@PROTOC@ --plugin=$(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) -I$(top_srcdir) --c_out=$(top_builddir) $(top_srcdir)/t/test-full.proto
t/test-full.pb.cc t/test-full.pb.h: @PROTOC@ $(top_srcdir)/t/test-full.proto
$(AM_V_GEN)@PROTOC@ -I$(top_srcdir) --cpp_out=$(top_builddir) $(top_srcdir)/t/test-full.proto
t/generated-code2/test-full-cxx-output.inc: t/generated-code2/cxx-generate-packed-data$(EXEEXT)
$(AM_V_GEN)$(top_builddir)/t/generated-code2/cxx-generate-packed-data$(EXEEXT) > $(top_builddir)/t/generated-code2/test-full-cxx-output.inc
BUILT_SOURCES += \
t/test.pb-c.c t/test.pb-c.h \
t/test-full.pb-c.c t/test-full.pb-c.h \
t/test-optimized.pb-c.c t/test-optimized.pb-c.h \
t/test-full.pb.cc t/test-full.pb.h \
t/generated-code2/test-full-cxx-output.inc
if BUILD_PROTO3
check_PROGRAMS += \
t/generated-code3/test-generated-code3
TESTS += \
t/generated-code3/test-generated-code3
t_generated_code3_test_generated_code3_CPPFLAGS = \
-DPROTO3
t_generated_code3_test_generated_code3_LDADD = \
protobuf-c/libprotobuf-c.la
t_generated_code3_test_generated_code3_SOURCES = \
t/generated-code/test-generated-code.c \
t/test-proto3.pb-c.c
t/test-proto3.pb-c.c t/test-proto3.pb-c.h: $(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) $(top_srcdir)/t/test-proto3.proto
$(AM_V_GEN)@PROTOC@ --plugin=$(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) -I$(top_srcdir) --c_out=$(top_builddir) $(top_srcdir)/t/test-proto3.proto
BUILT_SOURCES += \
t/test-proto3.pb-c.c t/test-proto3.pb-c.h
endif # BUILD_PROTO3
t_version_version_SOURCES = \
t/version/version.c
t_version_version_LDADD = \
protobuf-c/libprotobuf-c.la
# Issue #220
check_PROGRAMS += \
t/issue220/issue220
TESTS += \
t/issue220/issue220
t_issue220_issue220_SOURCES = \
t/issue220/issue220.c \
t/issue220/issue220.pb-c.c
t_issue220_issue220_LDADD = \
protobuf-c/libprotobuf-c.la
t/issue220/issue220.pb-c.c t/issue220/issue220.pb-c.h: $(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) $(top_srcdir)/t/issue220/issue220.proto
$(AM_V_GEN)@PROTOC@ --plugin=$(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) -I$(top_srcdir) --c_out=$(top_builddir) $(top_srcdir)/t/issue220/issue220.proto
BUILT_SOURCES += \
t/issue220/issue220.pb-c.c t/issue220/issue220.pb-c.h
EXTRA_DIST += \
t/issue220/issue220.proto
# Issue #251
check_PROGRAMS += \
t/issue251/issue251
TESTS += \
t/issue251/issue251
t_issue251_issue251_SOURCES = \
t/issue251/issue251.c \
t/issue251/issue251.pb-c.c
t_issue251_issue251_LDADD = \
protobuf-c/libprotobuf-c.la
t/issue251/issue251.pb-c.c t/issue251/issue251.pb-c.h: $(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) $(top_srcdir)/t/issue251/issue251.proto
$(AM_V_GEN)@PROTOC@ --plugin=$(top_builddir)/protoc-c/protoc-gen-c$(EXEEXT) -I$(top_srcdir) --c_out=$(top_builddir) $(top_srcdir)/t/issue251/issue251.proto
BUILT_SOURCES += \
t/issue251/issue251.pb-c.c t/issue251/issue251.pb-c.h
EXTRA_DIST += \
t/issue251/issue251.proto
endif # CROSS_COMPILING
endif # BUILD_COMPILER
EXTRA_DIST += \
t/test.proto \
t/test-full.proto \
t/test-optimized.proto \
t/test-proto3.proto \
t/generated-code2/common-test-arrays.h
#
#
#
CLEANFILES += $(BUILT_SOURCES)
dist-hook:
rm -f `find $(distdir) -name '*.pb-c.[ch]' -o -name '*.pb.cc' -o -name '*.pb.h'`
install-data-hook:
$(MKDIR_P) $(DESTDIR)$(includedir)/google/protobuf-c
cd $(DESTDIR)$(includedir)/google/protobuf-c && rm -f protobuf-c.h
cd $(DESTDIR)$(includedir)/google/protobuf-c && $(LN_S) ../../protobuf-c/protobuf-c.h protobuf-c.h
#
# documentation
#
if HAVE_DOXYGEN
stamp-html: $(DOXYGEN_INPUT_FILES) $(top_builddir)/Doxyfile $(top_srcdir)/DoxygenLayout.xml $(include_HEADERS) $(nobase_include_HEADERS)
$(AM_V_GEN) $(DOXYGEN)
@touch $@
html-local: stamp-html
clean-local:
rm -rf $(top_builddir)/html $(top_builddir)/stamp-html
endif
EXTRA_DIST += Doxyfile.in
EXTRA_DIST += DoxygenLayout.xml
EXTRA_DIST += build-cmake/CMakeLists.txt

View File

@ -0,0 +1,67 @@
[![Build Status](https://travis-ci.org/protobuf-c/protobuf-c.png?branch=master)](https://travis-ci.org/protobuf-c/protobuf-c) [![Coverage Status](https://coveralls.io/repos/protobuf-c/protobuf-c/badge.png)](https://coveralls.io/r/protobuf-c/protobuf-c)
## Overview
This is `protobuf-c`, a C implementation of the [Google Protocol Buffers](https://developers.google.com/protocol-buffers/) data serialization format. It includes `libprotobuf-c`, a pure C library that implements protobuf encoding and decoding, and `protoc-c`, a code generator that converts Protocol Buffer `.proto` files to C descriptor code, based on the original `protoc`. `protobuf-c` formerly included an RPC implementation; that code has been split out into the [protobuf-c-rpc](https://github.com/protobuf-c/protobuf-c-rpc) project.
`protobuf-c` was originally written by Dave Benson and maintained by him through version 0.15 but is now being maintained by a new team. Thanks, Dave!
## Mailing list
`protobuf-c`'s mailing list is hosted on a [Google Groups forum](https://groups.google.com/forum/#!forum/protobuf-c). Subscribe by sending an email to [protobuf-c+subscribe@googlegroups.com](mailto:protobuf-c+subscribe@googlegroups.com).
## Building
`protobuf-c` requires a C compiler, a C++ compiler, [protobuf](https://github.com/google/protobuf), and `pkg-config` to be installed.
./configure && make && make install
If building from a git checkout, the `autotools` (`autoconf`, `automake`, `libtool`) must also be installed, and the build system must be generated by running the `autogen.sh` script.
./autogen.sh && ./configure && make && make install
## Documentation
See the [online Doxygen documentation here](http://lib.protobuf-c.io) or [the Wiki](https://github.com/protobuf-c/protobuf-c/wiki) for a detailed reference. The Doxygen documentation can be built from the source tree by running:
make html
## Synopsis
Use the `protoc` command to generate `.pb-c.c` and `.pb-c.h` output files from your `.proto` input file. The `--c_out` options instructs `protoc` to use the protobuf-c plugin.
protoc --c_out=. example.proto
Include the `.pb-c.h` file from your C source code.
#include "example.pb-c.h"
Compile your C source code together with the `.pb-c.c` file. Add the output of the following command to your compile flags.
pkg-config --cflags 'libprotobuf-c >= 1.0.0'
Link against the `libprotobuf-c` support library. Add the output of the following command to your link flags.
pkg-config --libs 'libprotobuf-c >= 1.0.0'
If using autotools, the `PKG_CHECK_MODULES` macro can be used to detect the presence of `libprotobuf-c`. Add the following line to your `configure.ac` file:
PKG_CHECK_MODULES([PROTOBUF_C], [libprotobuf-c >= 1.0.0])
This will place compiler flags in the `PROTOBUF_C_CFLAGS` variable and linker flags in the `PROTOBUF_C_LDFLAGS` variable. Read [more information here](https://autotools.io/pkgconfig/pkg_check_modules.html) about the `PKG_CHECK_MODULES` macro.
## Versioning
`protobuf-c` follows the [Semantic Versioning Specification](http://semver.org/) as of version 1.0.0.
Note that as of version of 1.0.0, the header files generated by the `protoc-c` compiler contain version guards to prevent incompatibilities due to version skew between the `.pb-c.h` files generated by `protoc-c` and the public `protobuf-c.h` include file supplied by the `libprotobuf-c` support library. While we will try not to make changes to `protobuf-c` that will require triggering the version guard often, such as releasing a new major version of `protobuf-c`, this cannot be guaranteed. Thus, it's a good idea to recompile your `.pb-c.c` and `.pb-c.h` files from their source `.proto` files with `protoc-c` as part of your build system, with proper source file dependency tracking, rather than shipping potentially stale `.pb-c.c` and `.pb-c.h` files that may not be compatible with the `libprotobuf-c` headers installed on the system in project artifacts like repositories and release tarballs. (Note that the output of the `protoc-c` code generator is not standalone, as the output of some other tools that generate C code is, such as `flex` and `bison`.)
Major API/ABI changes may occur between major version releases, by definition. It is not recommended to export the symbols in the code generated by `protoc-c` in a stable library interface, as this will embed the `protobuf-c` ABI into your library's ABI. Nor is it recommended to install generated `.pb-c.h` files into a public header file include path as part of a library API, as this will tie clients of your library's API to particular versions of `libprotobuf-c`.
## Contributing
Please send patches to the [protobuf-c mailing list](https://groups.google.com/forum/#!forum/protobuf-c) or by opening a GitHub pull request.
The most recently released `protobuf-c` version is kept on the `master` branch, while the `next` branch is used for commits targeted at the next release. Please base patches and pull requests against the `next` branch, not the `master` branch.
Copyright to all contributions are retained by the original author, but must be licensed under the terms of the [BSD-2-Clause](http://opensource.org/licenses/BSD-2-Clause) license. Please add a `Signed-off-by` header to your commit message (`git commit -s`) to indicate that you are licensing your contribution under these terms.

View File

@ -0,0 +1,82 @@
----------------------
--- IMPORTANT TODO ---
----------------------
--------------------
--- NEEDED TESTS ---
--------------------
- test:
- service method lookups
- out-of-order fields in messages (ie if the number isn't ascending)
- gaps in numbers: check that the number of ranges is correct
- default values
- message unpack alloc failures when allocating new slab
- message unpack alloc failures when allocating unknown field buffers
- packed message corruption.
- meta-todo: get a list of all the unpack errors together to check off
---------------------
--- DOCUMENTATION ---
---------------------
Document:
- services
- check over documentation again
--------------------------
--- LOW PRIORITY STUFF ---
--------------------------
- support Group (whatever it is)
- proper support for extensions
- slot for ranges in descriptor
- extends is implemented as c-style function
whose name is built from the package, the base message type-name
and the member. which takes the base message and returns the
value, if it is found in "unknown_values".
boolean package__extension_member_name__get(Message *message,
type *out);
void package__extension_member_name__set_raw(type in,
ProtobufCUnknownValue *to_init);
------------------------------------
--- EXTREMELY LOW PRIORITY STUFF ---
------------------------------------
- stop using qsort in the code generator: find some c++ish way to do it
----------------------------------------------
--- ISSUES WE ARE PROBABLY GOING TO IGNORE ---
----------------------------------------------
- strings may not contain NULs
-------------------------
--- IDEAS TO CONSIDER ---
-------------------------
- optimization: structures without repeated members could skip
the ScannedMember phase
- optimization: a way to ignore unknown-fields when unpacking
- optimization: certain functions are not well setup for WORDSIZE==64;
especially the int64 routines are inefficient that way.
The best might be an internal #define WORDSIZE (sizeof(long)*8)"
except w/ a real constant there, one that the preprocessor can use.
I think the functions in protobuf-c.c are already tagged.
- lifetime functions for messages:
message__new()
return a new message using an allocator with standard allocation policy
message__unpack_onto(...)
unpack onto an initialized message
message__clear(...)
clears all allocations, does not free the message itself
message__free(...)
free the message.
[yeah, right: after typing it out, i see it's way too complicated]
- switching to pure C.
- Rewrite the code-generator in C, including the parser.
- This would have the huge advantage that we could use ".proto" files
directly, instead of having to invoke the compilers.
- keep in a separate c file for static linking optimziation purposes
- need alignment tests
- the CAVEATS should discuss our structure-packing assumptions

View File

@ -0,0 +1,2 @@
#!/bin/sh
exec autoreconf -fvi

View File

@ -0,0 +1,3 @@
*
!.gitignore
!CMakeLists.txt

View File

@ -0,0 +1,151 @@
SET(PACKAGE protobuf-c)
SET(PACKAGE_NAME protobuf-c)
SET(PACKAGE_VERSION 1.3.0)
CMAKE_MINIMUM_REQUIRED(VERSION 2.8 FATAL_ERROR)
PROJECT(protobuf-c)
#options
option(MSVC_STATIC_BUILD "MSVC_STATIC_BUILD" OFF)
option(BUILD_PROTO3 "BUILD_PROTO3" ON)
INCLUDE(TestBigEndian)
TEST_BIG_ENDIAN(WORDS_BIGENDIAN)
SET(PACKAGE_STRING "${PACKAGE_NAME} ${PACKAGE_VERSION}")
ADD_DEFINITIONS(-DPACKAGE_VERSION="${PACKAGE_VERSION}")
ADD_DEFINITIONS(-DPACKAGE_STRING="${PACKAGE_STRING}")
ADD_DEFINITIONS(-DWORDS_BIGENDIAN=${WORDS_BIGENDIAN})
if(MSVC)
# using Visual Studio C++
SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} /wd4267 /wd4244")
SET(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} /wd4267 /wd4244")
ENDIF()
get_filename_component(MAIN_DIR ${CMAKE_CURRENT_SOURCE_DIR} PATH)
SET(TEST_DIR ${MAIN_DIR}/t)
MESSAGE(${MAIN_DIR})
SET (PC_SOURCES
${MAIN_DIR}/protobuf-c/protobuf-c.c
${MAIN_DIR}/protobuf-c/protobuf-c.h)
ADD_LIBRARY(protobuf-c ${PC_SOURCES})
INCLUDE_DIRECTORIES(${MAIN_DIR})
INCLUDE_DIRECTORIES(${MAIN_DIR}/protobuf-c)
INCLUDE_DIRECTORIES(${CMAKE_BINARY_DIR}) # for generated files
FIND_PACKAGE(Protobuf REQUIRED)
INCLUDE_DIRECTORIES(${PROTOBUF_INCLUDE_DIR})
if (BUILD_PROTO3)
ADD_DEFINITIONS(-DHAVE_PROTO3)
endif()
if (MSVC AND MSVC_STATIC_BUILD)
# In case we are building static libraries, link also the runtime library statically
# so that MSVCR*.DLL is not required at runtime.
# https://msdn.microsoft.com/en-us/library/2kzt1wy3.aspx
# This is achieved by replacing msvc option /MD with /MT and /MDd with /MTd
# http://www.cmake.org/Wiki/CMake_FAQ#How_can_I_build_my_MSVC_application_with_a_static_runtime.3F
foreach(flag_var
CMAKE_CXX_FLAGS CMAKE_CXX_FLAGS_DEBUG CMAKE_CXX_FLAGS_RELEASE
CMAKE_CXX_FLAGS_MINSIZEREL CMAKE_CXX_FLAGS_RELWITHDEBINFO)
if(${flag_var} MATCHES "/MD")
string(REGEX REPLACE "/MD" "/MT" ${flag_var} "${${flag_var}}")
endif(${flag_var} MATCHES "/MD")
endforeach(flag_var)
endif (MSVC AND MSVC_STATIC_BUILD)
FILE(GLOB PROTOC_GEN_C_SRC ${MAIN_DIR}/protoc-c/*.h ${MAIN_DIR}/protoc-c/*.cc )
ADD_EXECUTABLE(protoc-gen-c ${PROTOC_GEN_C_SRC})
TARGET_LINK_LIBRARIES(protoc-gen-c ${PROTOBUF_PROTOC_LIBRARY} ${PROTOBUF_LIBRARY})
IF(CMAKE_HOST_UNIX)
ADD_CUSTOM_COMMAND(TARGET ${PROJECT_NAME} POST_BUILD
COMMAND ln -sf protoc-gen-c protoc-c
DEPENDS protoc-gen-c)
ENDIF()
FUNCTION(GENERATE_TEST_SOURCES PROTO_FILE SRC HDR)
ADD_CUSTOM_COMMAND(OUTPUT ${SRC} ${HDR}
COMMAND ${PROTOBUF_PROTOC_EXECUTABLE}
ARGS --plugin=$<TARGET_FILE:protoc-gen-c> -I${MAIN_DIR} ${PROTO_FILE} --c_out=${CMAKE_BINARY_DIR}
DEPENDS protoc-gen-c)
ENDFUNCTION()
IF(CMAKE_BUILD_TYPE MATCHES Debug)
ENABLE_TESTING()
GENERATE_TEST_SOURCES(${TEST_DIR}/test.proto t/test.pb-c.c t/test.pb-c.h)
ADD_EXECUTABLE(test-generated-code ${TEST_DIR}/generated-code/test-generated-code.c t/test.pb-c.c t/test.pb-c.h )
TARGET_LINK_LIBRARIES(test-generated-code protobuf-c)
ADD_CUSTOM_COMMAND(OUTPUT t/test-full.pb.cc t/test-full.pb.h
COMMAND ${PROTOBUF_PROTOC_EXECUTABLE}
ARGS --cpp_out ${CMAKE_BINARY_DIR} -I${MAIN_DIR} ${TEST_DIR}/test-full.proto)
GENERATE_TEST_SOURCES(${TEST_DIR}/test-full.proto t/test-full.pb-c.c t/test-full.pb-c.h)
ADD_EXECUTABLE(cxx-generate-packed-data ${TEST_DIR}/generated-code2/cxx-generate-packed-data.cc t/test-full.pb.h t/test-full.pb.cc)
TARGET_LINK_LIBRARIES(cxx-generate-packed-data ${PROTOBUF_LIBRARY})
FILE(MAKE_DIRECTORY ${CMAKE_BINARY_DIR}/t/generated-code2)
ADD_CUSTOM_COMMAND(OUTPUT t/generated-code2/test-full-cxx-output.inc
COMMAND ${CMAKE_BINARY_DIR}/cxx-generate-packed-data ">t/generated-code2/test-full-cxx-output.inc"
DEPENDS cxx-generate-packed-data
)
GENERATE_TEST_SOURCES(${TEST_DIR}/test-optimized.proto t/test-optimized.pb-c.c t/test-optimized.pb-c.h)
ADD_EXECUTABLE(test-generated-code2 ${TEST_DIR}/generated-code2/test-generated-code2.c t/generated-code2/test-full-cxx-output.inc t/test-full.pb-c.h t/test-full.pb-c.c t/test-optimized.pb-c.h t/test-optimized.pb-c.c)
TARGET_LINK_LIBRARIES(test-generated-code2 protobuf-c)
GENERATE_TEST_SOURCES(${TEST_DIR}/issue220/issue220.proto t/issue220/issue220.pb-c.c t/issue220/issue220.pb-c.h)
ADD_EXECUTABLE(test-issue220 ${TEST_DIR}/issue220/issue220.c t/issue220/issue220.pb-c.c t/issue220/issue220.pb-c.h)
TARGET_LINK_LIBRARIES(test-issue220 protobuf-c)
GENERATE_TEST_SOURCES(${TEST_DIR}/issue251/issue251.proto t/issue251/issue251.pb-c.c t/issue251/issue251.pb-c.h)
ADD_EXECUTABLE(test-issue251 ${TEST_DIR}/issue251/issue251.c t/issue251/issue251.pb-c.c t/issue251/issue251.pb-c.h)
TARGET_LINK_LIBRARIES(test-issue251 protobuf-c)
ADD_EXECUTABLE(test-version ${TEST_DIR}/version/version.c)
TARGET_LINK_LIBRARIES(test-version protobuf-c)
GENERATE_TEST_SOURCES(${TEST_DIR}/test-proto3.proto t/test-proto3.pb-c.c t/test-proto3.pb-c.h)
ADD_EXECUTABLE(test-generated-code3 ${TEST_DIR}/generated-code/test-generated-code.c t/test-proto3.pb-c.c t/test-proto3.pb-c.h)
TARGET_COMPILE_DEFINITIONS(test-generated-code3 PUBLIC -DPROTO3)
TARGET_LINK_LIBRARIES(test-generated-code3 protobuf-c)
ENDIF()
INSTALL(TARGETS protoc-gen-c protobuf-c RUNTIME DESTINATION bin LIBRARY DESTINATION lib ARCHIVE DESTINATION lib)
INSTALL(FILES ${MAIN_DIR}/protobuf-c/protobuf-c.h DESTINATION include/protobuf-c)
INSTALL(FILES ${MAIN_DIR}/protobuf-c/protobuf-c.h DESTINATION include)
IF(CMAKE_HOST_UNIX)
INSTALL(CODE "EXECUTE_PROCESS (COMMAND ln -sf protoc-gen-c protoc-c WORKING_DIRECTORY ${CMAKE_INSTALL_PREFIX}/bin)")
ENDIF()
INCLUDE(Dart)
SET(DART_TESTING_TIMEOUT 5)
ADD_TEST(test-generated-code test-generated-code)
ADD_TEST(test-generated-code2 test-generated-code2)
ADD_TEST(test-generated-code3 test-generated-code3)
ADD_TEST(test-issue220 test-issue220)
ADD_TEST(test-issue251 test-issue251)
ADD_TEST(test-version test-version)
INCLUDE(CPack)

View File

@ -0,0 +1,137 @@
AC_PREREQ(2.63)
AC_INIT([protobuf-c],
[1.3.0],
[https://github.com/protobuf-c/protobuf-c/issues],
[protobuf-c],
[https://github.com/protobuf-c/protobuf-c])
PACKAGE_DESCRIPTION="Protocol Buffers implementation in C"
AC_SUBST(PACKAGE_DESCRIPTION)
AC_CONFIG_SRCDIR([protobuf-c/protobuf-c.c])
AC_CONFIG_AUX_DIR([build-aux])
AM_INIT_AUTOMAKE([foreign 1.11 -Wall -Wno-portability silent-rules subdir-objects])
AC_PROG_CC_STDC
AC_PROG_CXX
AC_PROG_LN_S
AC_PROG_MKDIR_P
AC_USE_SYSTEM_EXTENSIONS
AC_SYS_LARGEFILE
AC_CONFIG_MACRO_DIR([m4])
AM_SILENT_RULES([yes])
LT_INIT
AC_CONFIG_HEADERS(config.h)
AC_CONFIG_FILES([Makefile protobuf-c/libprotobuf-c.pc])
my_CFLAGS="\
-Wall \
-Wchar-subscripts \
-Wdeclaration-after-statement \
-Wformat-security \
-Wmissing-declarations \
-Wmissing-prototypes \
-Wnested-externs \
-Wpointer-arith \
-Wshadow \
-Wsign-compare \
-Wstrict-prototypes \
-Wtype-limits \
"
#AX_CHECK_COMPILE_FLAG(["-Wc90-c99-compat"],
# [my_CFLAGS="$my_CFLAGS -Wc90-c99-compat"])
AX_CHECK_COMPILE_FLAG(["-Wc99-c11-compat"],
[my_CFLAGS="$my_CFLAGS -Wc99-c11-compat"])
AX_CHECK_COMPILE_FLAG(["-Werror=incompatible-pointer-types"],
[my_CFLAGS="$my_CFLAGS -Werror=incompatible-pointer-types"])
AX_CHECK_COMPILE_FLAG(["-Werror=int-conversion"],
[my_CFLAGS="$my_CFLAGS -Werror=int-conversion"])
AX_CHECK_COMPILE_FLAG(["-Wnull-dereference"],
[my_CFLAGS="$my_CFLAGS -Wnull-dereference"])
AC_SUBST([my_CFLAGS])
AC_CHECK_PROGS([DOXYGEN], [doxygen])
AM_CONDITIONAL([HAVE_DOXYGEN],
[test -n "$DOXYGEN"])
AM_COND_IF([HAVE_DOXYGEN],
[AC_CONFIG_FILES([Doxyfile])
DOXYGEN_INPUT="${srcdir}/protobuf-c"
AC_SUBST(DOXYGEN_INPUT)
])
PKG_PROG_PKG_CONFIG
if test -n "$PKG_CONFIG"; then
# Horrible hack for systems where the pkg-config install directory is simply wrong!
if $PKG_CONFIG --variable=pc_path pkg-config 2>/dev/null | grep -q /libdata/; then
PKG_INSTALLDIR(['${prefix}/libdata/pkgconfig'])
else
PKG_INSTALLDIR
fi
fi
proto3_supported="no"
AC_ARG_ENABLE([protoc],
AS_HELP_STRING([--disable-protoc], [Disable building protoc_c (also disables tests)]))
if test "x$enable_protoc" != "xno"; then
AC_LANG_PUSH([C++])
PKG_CHECK_MODULES([protobuf], [protobuf >= 3.0.0],
[proto3_supported=yes],
[PKG_CHECK_MODULES([protobuf], [protobuf >= 2.6.0])]
)
save_CPPFLAGS="$CPPFLAGS"
CPPFLAGS="$save_CPPFLAGS $protobuf_CFLAGS"
AC_CHECK_HEADERS([google/protobuf/compiler/command_line_interface.h],
[],
[AC_MSG_ERROR([required protobuf header file not found])])
CPPFLAGS="$save_CPPFLAGS"
AC_ARG_VAR([PROTOC], [protobuf compiler command])
AC_PATH_PROG([PROTOC], [protoc], [],
[`$PKG_CONFIG --variable=exec_prefix protobuf`/bin:$PATH])
if test -z "$PROTOC"; then
AC_MSG_ERROR([Please install the protobuf compiler from https://code.google.com/p/protobuf/.])
fi
PROTOBUF_VERSION="$($PROTOC --version)"
else
PROTOBUF_VERSION="not required, not building compiler"
fi
AM_CONDITIONAL([BUILD_COMPILER], [test "x$enable_protoc" != "xno"])
AM_CONDITIONAL([BUILD_PROTO3], [test "x$proto3_supported" != "xno"])
AM_CONDITIONAL([CROSS_COMPILING], [test "x$cross_compiling" != "xno"])
AM_COND_IF([BUILD_PROTO3], [AC_DEFINE([HAVE_PROTO3], [1], [Support proto3 syntax])])
gl_LD_VERSION_SCRIPT
gl_VALGRIND_TESTS
MY_CODE_COVERAGE
AC_C_BIGENDIAN
AC_OUTPUT
AC_MSG_RESULT([
$PACKAGE $VERSION
CC: ${CC}
CFLAGS: ${CFLAGS}
CXX: ${CXX}
CXXFLAGS: ${CXXFLAGS}
LDFLAGS: ${LDFLAGS}
LIBS: ${LIBS}
prefix: ${prefix}
sysconfdir: ${sysconfdir}
libdir: ${libdir}
includedir: ${includedir}
pkgconfigdir: ${pkgconfigdir}
bigendian: ${ac_cv_c_bigendian}
protobuf version: ${PROTOBUF_VERSION}
])

View File

@ -0,0 +1,5 @@
libtool.m4
ltoptions.m4
ltsugar.m4
ltversion.m4
lt~obsolete.m4

View File

@ -0,0 +1,74 @@
# ===========================================================================
# https://www.gnu.org/software/autoconf-archive/ax_check_compile_flag.html
# ===========================================================================
#
# SYNOPSIS
#
# AX_CHECK_COMPILE_FLAG(FLAG, [ACTION-SUCCESS], [ACTION-FAILURE], [EXTRA-FLAGS], [INPUT])
#
# DESCRIPTION
#
# Check whether the given FLAG works with the current language's compiler
# or gives an error. (Warnings, however, are ignored)
#
# ACTION-SUCCESS/ACTION-FAILURE are shell commands to execute on
# success/failure.
#
# If EXTRA-FLAGS is defined, it is added to the current language's default
# flags (e.g. CFLAGS) when the check is done. The check is thus made with
# the flags: "CFLAGS EXTRA-FLAGS FLAG". This can for example be used to
# force the compiler to issue an error when a bad flag is given.
#
# INPUT gives an alternative input source to AC_COMPILE_IFELSE.
#
# NOTE: Implementation based on AX_CFLAGS_GCC_OPTION. Please keep this
# macro in sync with AX_CHECK_{PREPROC,LINK}_FLAG.
#
# LICENSE
#
# Copyright (c) 2008 Guido U. Draheim <guidod@gmx.de>
# Copyright (c) 2011 Maarten Bosmans <mkbosmans@gmail.com>
#
# This program is free software: you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by the
# Free Software Foundation, either version 3 of the License, or (at your
# option) any later version.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
# Public License for more details.
#
# You should have received a copy of the GNU General Public License along
# with this program. If not, see <https://www.gnu.org/licenses/>.
#
# As a special exception, the respective Autoconf Macro's copyright owner
# gives unlimited permission to copy, distribute and modify the configure
# scripts that are the output of Autoconf when processing the Macro. You
# need not follow the terms of the GNU General Public License when using
# or distributing such scripts, even though portions of the text of the
# Macro appear in them. The GNU General Public License (GPL) does govern
# all other use of the material that constitutes the Autoconf Macro.
#
# This special exception to the GPL applies to versions of the Autoconf
# Macro released by the Autoconf Archive. When you make and distribute a
# modified version of the Autoconf Macro, you may extend this special
# exception to the GPL to apply to your modified version as well.
#serial 5
AC_DEFUN([AX_CHECK_COMPILE_FLAG],
[AC_PREREQ(2.64)dnl for _AC_LANG_PREFIX and AS_VAR_IF
AS_VAR_PUSHDEF([CACHEVAR],[ax_cv_check_[]_AC_LANG_ABBREV[]flags_$4_$1])dnl
AC_CACHE_CHECK([whether _AC_LANG compiler accepts $1], CACHEVAR, [
ax_check_save_flags=$[]_AC_LANG_PREFIX[]FLAGS
_AC_LANG_PREFIX[]FLAGS="$[]_AC_LANG_PREFIX[]FLAGS $4 $1"
AC_COMPILE_IFELSE([m4_default([$5],[AC_LANG_PROGRAM()])],
[AS_VAR_SET(CACHEVAR,[yes])],
[AS_VAR_SET(CACHEVAR,[no])])
_AC_LANG_PREFIX[]FLAGS=$ax_check_save_flags])
AS_VAR_IF(CACHEVAR,yes,
[m4_default([$2], :)],
[m4_default([$3], :)])
AS_VAR_POPDEF([CACHEVAR])dnl
])dnl AX_CHECK_COMPILE_FLAGS

View File

@ -0,0 +1,158 @@
# SYNOPSIS
#
# MY_CODE_COVERAGE()
#
# DESCRIPTION
#
# Defines CODE_COVERAGE_CFLAGS and CODE_COVERAGE_LDFLAGS which should be
# included in the CFLAGS and LIBS/LDFLAGS variables of every build target
# (program or library) which should be built with code coverage support.
# Also defines CODE_COVERAGE_RULES which should be substituted in your
# Makefile; and $enable_code_coverage which can be used in subsequent
# configure output. CODE_COVERAGE_ENABLED is defined and substituted, and
# corresponds to the value of the --enable-code-coverage option, which
# defaults to being disabled.
#
# Usage example:
# configure.ac:
# MY_CODE_COVERAGE
#
# Makefile.am:
# @CODE_COVERAGE_RULES@
# my_program_LIBS = … $(CODE_COVERAGE_LDFLAGS) …
# my_program_CFLAGS = … $(CODE_COVERAGE_CFLAGS) …
#
# This results in a “check-code-coverage” rule being added to any Makefile.am
# which includes “@CODE_COVERAGE_RULES@” (assuming the module has been
# configured with --enable-code-coverage). Running `make check-code-coverage`
# in that directory will run the modules test suite (`make check`) and build
# a code coverage report detailing the code which was touched, then print the
# URI for the report.
#
# LICENSE
#
# Copyright © 2012, 2014 Philip Withnall
# Copyright © 2012 Xan Lopez
# Copyright © 2012 Christian Persch
# Copyright © 2012 Paolo Borelli
# Copyright © 2012 Dan Winship
#
# Derived from Makefile.decl in GLib, originally licenced under LGPLv2.1+.
# This file is licenced under LGPLv2.1+.
AC_DEFUN([MY_CODE_COVERAGE],[
dnl Check for --enable-code-coverage
AC_MSG_CHECKING([whether to build with code coverage support])
AC_ARG_ENABLE([code-coverage], AS_HELP_STRING([--enable-code-coverage], [Whether to enable code coverage support]),, enable_code_coverage=no)
AM_CONDITIONAL([CODE_COVERAGE_ENABLED], [test x$enable_code_coverage = xyes])
AC_SUBST([CODE_COVERAGE_ENABLED], [$enable_code_coverage])
AC_MSG_RESULT($enable_code_coverage)
AS_IF([ test "$enable_code_coverage" = "yes" ], [
dnl Check if gcc is being used
AS_IF([ test "$GCC" = "no" ], [
AC_MSG_ERROR([not compiling with gcc, which is required for gcov code coverage])
])
AC_CHECK_PROG([LCOV], [lcov], [lcov])
AC_CHECK_PROG([GENHTML], [genhtml], [genhtml])
AS_IF([ test -z "$LCOV" ], [
AC_MSG_ERROR([The lcov program was not found. Please install lcov!])
])
AS_IF([ test -z "$GENHTML" ], [
AC_MSG_ERROR([The genhtml program was not found. Please install lcov!])
])
dnl Build the code coverage flags
CODE_COVERAGE_CFLAGS="-O0 -g --coverage"
CODE_COVERAGE_LDFLAGS="--coverage"
AC_SUBST([CODE_COVERAGE_CFLAGS])
AC_SUBST([CODE_COVERAGE_LDFLAGS])
dnl Strip optimisation flags
changequote({,})
CFLAGS=`echo "$CFLAGS" | $SED -e 's/-O[0-9]*//g'`
changequote([,])
])
CODE_COVERAGE_RULES='
# Code coverage
#
# Optional:
# - CODE_COVERAGE_DIRECTORY: Top-level directory for code coverage reporting.
# (Default: $(top_builddir))
# - CODE_COVERAGE_OUTPUT_FILE: Filename and path for the .info file generated
# by lcov for code coverage. (Default:
# $(PACKAGE_NAME)-$(PACKAGE_VERSION)-coverage.info)
# - CODE_COVERAGE_OUTPUT_DIRECTORY: Directory for generated code coverage
# reports to be created. (Default:
# $(PACKAGE_NAME)-$(PACKAGE_VERSION)-coverage)
# - CODE_COVERAGE_LCOV_OPTIONS: Extra options to pass to the lcov instance.
# (Default: empty)
# - CODE_COVERAGE_GENHTML_OPTIONS: Extra options to pass to the genhtml
# instance. (Default: empty)
# - CODE_COVERAGE_IGNORE_PATTERN: Extra glob pattern of files to ignore
#
# The generated report will be titled using the $(PACKAGE_NAME) and
# $(PACKAGE_VERSION). In order to add the current git hash to the title,
# use the git-version-gen script, available online.
# Optional variables
CODE_COVERAGE_DIRECTORY ?= $(abs_top_builddir)
CODE_COVERAGE_OUTPUT_FILE ?= $(PACKAGE_NAME)-$(PACKAGE_VERSION)-coverage.info
CODE_COVERAGE_OUTPUT_DIRECTORY ?= $(PACKAGE_NAME)-$(PACKAGE_VERSION)-coverage
CODE_COVERAGE_LCOV_OPTIONS ?=
CODE_COVERAGE_GENHTML_OPTIONS ?=
CODE_COVERAGE_IGNORE_PATTERN ?=
code_coverage_quiet = $(code_coverage_quiet_$(V))
code_coverage_quiet_ = $(code_coverage_quiet_$(AM_DEFAULT_VERBOSITY))
code_coverage_quiet_0 = --quiet
# Use recursive makes in order to ignore errors during check
check-code-coverage:
ifeq ($(CODE_COVERAGE_ENABLED),yes)
-$(MAKE) $(AM_MAKEFLAGS) -k check
$(MAKE) $(AM_MAKEFLAGS) code-coverage-capture
else
@echo "Need to reconfigure with --enable-code-coverage"
endif
# Capture code coverage data
code-coverage-capture: code-coverage-capture-hook
ifeq ($(CODE_COVERAGE_ENABLED),yes)
$(LCOV) $(code_coverage_quiet) --directory $(CODE_COVERAGE_DIRECTORY) --capture --output-file "$(CODE_COVERAGE_OUTPUT_FILE).tmp" --test-name "$(PACKAGE_NAME)-$(PACKAGE_VERSION)" --no-checksum --compat-libtool $(CODE_COVERAGE_LCOV_OPTIONS)
$(LCOV) $(code_coverage_quiet) --directory $(CODE_COVERAGE_DIRECTORY) --remove "$(CODE_COVERAGE_OUTPUT_FILE).tmp" "/tmp/*" $(CODE_COVERAGE_IGNORE_PATTERN) --output-file "$(CODE_COVERAGE_OUTPUT_FILE)"
-@rm -f $(CODE_COVERAGE_OUTPUT_FILE).tmp
LANG=C $(GENHTML) $(code_coverage_quiet) --prefix $(CODE_COVERAGE_DIRECTORY) --output-directory "$(CODE_COVERAGE_OUTPUT_DIRECTORY)" --title "$(PACKAGE_NAME)-$(PACKAGE_VERSION) Code Coverage" --legend --show-details "$(CODE_COVERAGE_OUTPUT_FILE)" $(CODE_COVERAGE_GENHTML_OPTIONS)
@echo "file://$(abs_builddir)/$(CODE_COVERAGE_OUTPUT_DIRECTORY)/index.html"
else
@echo "Need to reconfigure with --enable-code-coverage"
endif
# Hook rule executed before code-coverage-capture, overridable by the user
code-coverage-capture-hook:
ifeq ($(CODE_COVERAGE_ENABLED),yes)
clean: code-coverage-clean
code-coverage-clean:
-$(LCOV) --directory $(CODE_COVERAGE_DIRECTORY) -z
-rm -rf $(CODE_COVERAGE_OUTPUT_FILE) $(CODE_COVERAGE_OUTPUT_FILE).tmp $(CODE_COVERAGE_OUTPUT_DIRECTORY)
-find . -name "*.gcda" -o -name "*.gcov" -delete
endif
GITIGNOREFILES ?=
GITIGNOREFILES += $(CODE_COVERAGE_OUTPUT_FILE) $(CODE_COVERAGE_OUTPUT_DIRECTORY)
DISTCHECK_CONFIGURE_FLAGS ?=
DISTCHECK_CONFIGURE_FLAGS += --disable-code-coverage
.PHONY: check-code-coverage code-coverage-capture code-coverage-capture-hook code-coverage-clean
'
AC_SUBST([CODE_COVERAGE_RULES])
m4_ifdef([_AM_SUBST_NOTMAKE], [_AM_SUBST_NOTMAKE([CODE_COVERAGE_RULES])])
])

View File

@ -0,0 +1,53 @@
# ld-version-script.m4 serial 3
dnl Copyright (C) 2008-2014 Free Software Foundation, Inc.
dnl This file is free software; the Free Software Foundation
dnl gives unlimited permission to copy and/or distribute it,
dnl with or without modifications, as long as this notice is preserved.
dnl From Simon Josefsson
# FIXME: The test below returns a false positive for mingw
# cross-compiles, 'local:' statements does not reduce number of
# exported symbols in a DLL. Use --disable-ld-version-script to work
# around the problem.
# gl_LD_VERSION_SCRIPT
# --------------------
# Check if LD supports linker scripts, and define automake conditional
# HAVE_LD_VERSION_SCRIPT if so.
AC_DEFUN([gl_LD_VERSION_SCRIPT],
[
AC_ARG_ENABLE([ld-version-script],
AS_HELP_STRING([--enable-ld-version-script],
[enable linker version script (default is enabled when possible)]),
[have_ld_version_script=$enableval], [])
if test -z "$have_ld_version_script"; then
AC_MSG_CHECKING([if LD -Wl,--version-script works])
save_LDFLAGS="$LDFLAGS"
LDFLAGS="$LDFLAGS -Wl,--version-script=conftest.map"
cat > conftest.map <<EOF
foo
EOF
AC_LINK_IFELSE([AC_LANG_PROGRAM([], [])],
[accepts_syntax_errors=yes], [accepts_syntax_errors=no])
if test "$accepts_syntax_errors" = no; then
cat > conftest.map <<EOF
VERS_1 {
global: sym;
};
VERS_2 {
global: sym;
} VERS_1;
EOF
AC_LINK_IFELSE([AC_LANG_PROGRAM([], [])],
[have_ld_version_script=yes], [have_ld_version_script=no])
else
have_ld_version_script=no
fi
rm -f conftest.map
LDFLAGS="$save_LDFLAGS"
AC_MSG_RESULT($have_ld_version_script)
fi
AM_CONDITIONAL(HAVE_LD_VERSION_SCRIPT, test "$have_ld_version_script" = "yes")
])

View File

@ -0,0 +1,214 @@
# pkg.m4 - Macros to locate and utilise pkg-config. -*- Autoconf -*-
# serial 1 (pkg-config-0.24)
#
# Copyright © 2004 Scott James Remnant <scott@netsplit.com>.
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#
# As a special exception to the GNU General Public License, if you
# distribute this file as part of a program that contains a
# configuration script generated by Autoconf, you may include it under
# the same distribution terms that you use for the rest of that program.
# PKG_PROG_PKG_CONFIG([MIN-VERSION])
# ----------------------------------
AC_DEFUN([PKG_PROG_PKG_CONFIG],
[m4_pattern_forbid([^_?PKG_[A-Z_]+$])
m4_pattern_allow([^PKG_CONFIG(_(PATH|LIBDIR|SYSROOT_DIR|ALLOW_SYSTEM_(CFLAGS|LIBS)))?$])
m4_pattern_allow([^PKG_CONFIG_(DISABLE_UNINSTALLED|TOP_BUILD_DIR|DEBUG_SPEW)$])
AC_ARG_VAR([PKG_CONFIG], [path to pkg-config utility])
AC_ARG_VAR([PKG_CONFIG_PATH], [directories to add to pkg-config's search path])
AC_ARG_VAR([PKG_CONFIG_LIBDIR], [path overriding pkg-config's built-in search path])
if test "x$ac_cv_env_PKG_CONFIG_set" != "xset"; then
AC_PATH_TOOL([PKG_CONFIG], [pkg-config])
fi
if test -n "$PKG_CONFIG"; then
_pkg_min_version=m4_default([$1], [0.9.0])
AC_MSG_CHECKING([pkg-config is at least version $_pkg_min_version])
if $PKG_CONFIG --atleast-pkgconfig-version $_pkg_min_version; then
AC_MSG_RESULT([yes])
else
AC_MSG_RESULT([no])
PKG_CONFIG=""
fi
fi[]dnl
])# PKG_PROG_PKG_CONFIG
# PKG_CHECK_EXISTS(MODULES, [ACTION-IF-FOUND], [ACTION-IF-NOT-FOUND])
#
# Check to see whether a particular set of modules exists. Similar
# to PKG_CHECK_MODULES(), but does not set variables or print errors.
#
# Please remember that m4 expands AC_REQUIRE([PKG_PROG_PKG_CONFIG])
# only at the first occurence in configure.ac, so if the first place
# it's called might be skipped (such as if it is within an "if", you
# have to call PKG_CHECK_EXISTS manually
# --------------------------------------------------------------
AC_DEFUN([PKG_CHECK_EXISTS],
[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl
if test -n "$PKG_CONFIG" && \
AC_RUN_LOG([$PKG_CONFIG --exists --print-errors "$1"]); then
m4_default([$2], [:])
m4_ifvaln([$3], [else
$3])dnl
fi])
# _PKG_CONFIG([VARIABLE], [COMMAND], [MODULES])
# ---------------------------------------------
m4_define([_PKG_CONFIG],
[if test -n "$$1"; then
pkg_cv_[]$1="$$1"
elif test -n "$PKG_CONFIG"; then
PKG_CHECK_EXISTS([$3],
[pkg_cv_[]$1=`$PKG_CONFIG --[]$2 "$3" 2>/dev/null`
test "x$?" != "x0" && pkg_failed=yes ],
[pkg_failed=yes])
else
pkg_failed=untried
fi[]dnl
])# _PKG_CONFIG
# _PKG_SHORT_ERRORS_SUPPORTED
# -----------------------------
AC_DEFUN([_PKG_SHORT_ERRORS_SUPPORTED],
[AC_REQUIRE([PKG_PROG_PKG_CONFIG])
if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then
_pkg_short_errors_supported=yes
else
_pkg_short_errors_supported=no
fi[]dnl
])# _PKG_SHORT_ERRORS_SUPPORTED
# PKG_CHECK_MODULES(VARIABLE-PREFIX, MODULES, [ACTION-IF-FOUND],
# [ACTION-IF-NOT-FOUND])
#
#
# Note that if there is a possibility the first call to
# PKG_CHECK_MODULES might not happen, you should be sure to include an
# explicit call to PKG_PROG_PKG_CONFIG in your configure.ac
#
#
# --------------------------------------------------------------
AC_DEFUN([PKG_CHECK_MODULES],
[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl
AC_ARG_VAR([$1][_CFLAGS], [C compiler flags for $1, overriding pkg-config])dnl
AC_ARG_VAR([$1][_LIBS], [linker flags for $1, overriding pkg-config])dnl
pkg_failed=no
AC_MSG_CHECKING([for $1])
_PKG_CONFIG([$1][_CFLAGS], [cflags], [$2])
_PKG_CONFIG([$1][_LIBS], [libs], [$2])
m4_define([_PKG_TEXT], [Alternatively, you may set the environment variables $1[]_CFLAGS
and $1[]_LIBS to avoid the need to call pkg-config.
See the pkg-config man page for more details.])
if test $pkg_failed = yes; then
AC_MSG_RESULT([no])
_PKG_SHORT_ERRORS_SUPPORTED
if test $_pkg_short_errors_supported = yes; then
$1[]_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "$2" 2>&1`
else
$1[]_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "$2" 2>&1`
fi
# Put the nasty error message in config.log where it belongs
echo "$$1[]_PKG_ERRORS" >&AS_MESSAGE_LOG_FD
m4_default([$4], [AC_MSG_ERROR(
[Package requirements ($2) were not met:
$$1_PKG_ERRORS
Consider adjusting the PKG_CONFIG_PATH environment variable if you
installed software in a non-standard prefix.
_PKG_TEXT])[]dnl
])
elif test $pkg_failed = untried; then
AC_MSG_RESULT([no])
m4_default([$4], [AC_MSG_FAILURE(
[The pkg-config script could not be found or is too old. Make sure it
is in your PATH or set the PKG_CONFIG environment variable to the full
path to pkg-config.
_PKG_TEXT
To get pkg-config, see <http://pkg-config.freedesktop.org/>.])[]dnl
])
else
$1[]_CFLAGS=$pkg_cv_[]$1[]_CFLAGS
$1[]_LIBS=$pkg_cv_[]$1[]_LIBS
AC_MSG_RESULT([yes])
$3
fi[]dnl
])# PKG_CHECK_MODULES
# PKG_INSTALLDIR(DIRECTORY)
# -------------------------
# Substitutes the variable pkgconfigdir as the location where a module
# should install pkg-config .pc files. By default the directory is
# $libdir/pkgconfig, but the default can be changed by passing
# DIRECTORY. The user can override through the --with-pkgconfigdir
# parameter.
AC_DEFUN([PKG_INSTALLDIR],
[m4_pushdef([pkg_default], [m4_default([$1], ['${libdir}/pkgconfig'])])
m4_pushdef([pkg_description],
[pkg-config installation directory @<:@]pkg_default[@:>@])
AC_ARG_WITH([pkgconfigdir],
[AS_HELP_STRING([--with-pkgconfigdir], pkg_description)],,
[with_pkgconfigdir=]pkg_default)
AC_SUBST([pkgconfigdir], [$with_pkgconfigdir])
m4_popdef([pkg_default])
m4_popdef([pkg_description])
]) dnl PKG_INSTALLDIR
# PKG_NOARCH_INSTALLDIR(DIRECTORY)
# -------------------------
# Substitutes the variable noarch_pkgconfigdir as the location where a
# module should install arch-independent pkg-config .pc files. By
# default the directory is $datadir/pkgconfig, but the default can be
# changed by passing DIRECTORY. The user can override through the
# --with-noarch-pkgconfigdir parameter.
AC_DEFUN([PKG_NOARCH_INSTALLDIR],
[m4_pushdef([pkg_default], [m4_default([$1], ['${datadir}/pkgconfig'])])
m4_pushdef([pkg_description],
[pkg-config arch-independent installation directory @<:@]pkg_default[@:>@])
AC_ARG_WITH([noarch-pkgconfigdir],
[AS_HELP_STRING([--with-noarch-pkgconfigdir], pkg_description)],,
[with_noarch_pkgconfigdir=]pkg_default)
AC_SUBST([noarch_pkgconfigdir], [$with_noarch_pkgconfigdir])
m4_popdef([pkg_default])
m4_popdef([pkg_description])
]) dnl PKG_NOARCH_INSTALLDIR
# PKG_CHECK_VAR(VARIABLE, MODULE, CONFIG-VARIABLE,
# [ACTION-IF-FOUND], [ACTION-IF-NOT-FOUND])
# -------------------------------------------
# Retrieves the value of the pkg-config variable for the given module.
AC_DEFUN([PKG_CHECK_VAR],
[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl
AC_ARG_VAR([$1], [value of $3 for $2, overriding pkg-config])dnl
_PKG_CONFIG([$1], [variable="][$3]["], [$2])
AS_VAR_COPY([$1], [pkg_cv_][$1])
AS_VAR_IF([$1], [""], [$5], [$4])dnl
])# PKG_CHECK_VAR

View File

@ -0,0 +1,35 @@
# valgrind-tests.m4 serial 2
dnl Copyright (C) 2008-2011 Free Software Foundation, Inc.
dnl This file is free software; the Free Software Foundation
dnl gives unlimited permission to copy and/or distribute it,
dnl with or without modifications, as long as this notice is preserved.
dnl From Simon Josefsson
# gl_VALGRIND_TESTS()
# -------------------
# Check if valgrind is available, and set VALGRIND to it if available.
AC_DEFUN([gl_VALGRIND_TESTS],
[
AC_ARG_ENABLE(valgrind-tests,
AS_HELP_STRING([--enable-valgrind-tests],
[run self tests under valgrind]),
[opt_valgrind_tests=$enableval], [opt_valgrind_tests=no])
# Run self-tests under valgrind?
if test "$opt_valgrind_tests" = "yes" && test "$cross_compiling" = no; then
AC_CHECK_PROGS(VALGRIND, valgrind)
fi
if test -n "$VALGRIND" && $VALGRIND -q true > /dev/null 2>&1; then
opt_valgrind_tests=yes
VALGRIND="$VALGRIND -q --error-exitcode=1 --leak-check=full \
--trace-children=yes --trace-children-skip=/usr/*,/bin/*"
else
opt_valgrind_tests=no
VALGRIND=
fi
AC_MSG_CHECKING([whether self tests are run under valgrind])
AC_MSG_RESULT($opt_valgrind_tests)
])

View File

@ -0,0 +1,12 @@
prefix=@prefix@
exec_prefix=@exec_prefix@
libdir=@libdir@
includedir=@includedir@
bindir=@bindir@
Name: libprotobuf-c
Description: Protocol Buffers C library
Version: @VERSION@
Libs: -L${libdir} -lprotobuf-c
Libs.private:
Cflags: -I${includedir}

View File

@ -0,0 +1,28 @@
LIBPROTOBUF_C_1.0.0 {
global:
protobuf_c_buffer_simple_append;
protobuf_c_enum_descriptor_get_value;
protobuf_c_enum_descriptor_get_value_by_name;
protobuf_c_message_check;
protobuf_c_message_descriptor_get_field;
protobuf_c_message_descriptor_get_field_by_name;
protobuf_c_message_free_unpacked;
protobuf_c_message_get_packed_size;
protobuf_c_message_init;
protobuf_c_message_pack;
protobuf_c_message_pack_to_buffer;
protobuf_c_message_unpack;
protobuf_c_service_descriptor_get_method_by_name;
protobuf_c_service_destroy;
protobuf_c_service_generated_init;
protobuf_c_service_invoke_internal;
protobuf_c_version;
protobuf_c_version_number;
local:
*;
};
LIBPROTOBUF_C_1.3.0 {
global:
protobuf_c_empty_string;
} LIBPROTOBUF_C_1.0.0;

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,163 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <protoc-c/c_bytes_field.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/io/printer.h>
#include <google/protobuf/wire_format.h>
#include <google/protobuf/descriptor.pb.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
using internal::WireFormat;
void SetBytesVariables(const FieldDescriptor* descriptor,
std::map<string, string>* variables) {
(*variables)["name"] = FieldName(descriptor);
(*variables)["default"] =
"\"" + CEscape(descriptor->default_value_string()) + "\"";
(*variables)["deprecated"] = FieldDeprecated(descriptor);
}
// ===================================================================
BytesFieldGenerator::
BytesFieldGenerator(const FieldDescriptor* descriptor)
: FieldGenerator(descriptor) {
SetBytesVariables(descriptor, &variables_);
variables_["default_value"] = descriptor->has_default_value()
? GetDefaultValue()
: string("{0,NULL}");
}
BytesFieldGenerator::~BytesFieldGenerator() {}
void BytesFieldGenerator::GenerateStructMembers(io::Printer* printer) const
{
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
printer->Print(variables_, "ProtobufCBinaryData $name$$deprecated$;\n");
break;
case FieldDescriptor::LABEL_OPTIONAL:
if (descriptor_->containing_oneof() == NULL && FieldSyntax(descriptor_) == 2)
printer->Print(variables_, "protobuf_c_boolean has_$name$$deprecated$;\n");
printer->Print(variables_, "ProtobufCBinaryData $name$$deprecated$;\n");
break;
case FieldDescriptor::LABEL_REPEATED:
printer->Print(variables_, "size_t n_$name$$deprecated$;\n");
printer->Print(variables_, "ProtobufCBinaryData *$name$$deprecated$;\n");
break;
}
}
void BytesFieldGenerator::GenerateDefaultValueDeclarations(io::Printer* printer) const
{
std::map<string, string> vars;
vars["default_value_data"] = FullNameToLower(descriptor_->full_name())
+ "__default_value_data";
printer->Print(vars, "extern uint8_t $default_value_data$[];\n");
}
void BytesFieldGenerator::GenerateDefaultValueImplementations(io::Printer* printer) const
{
std::map<string, string> vars;
vars["default_value_data"] = FullNameToLower(descriptor_->full_name())
+ "__default_value_data";
vars["escaped"] = CEscape(descriptor_->default_value_string());
printer->Print(vars, "uint8_t $default_value_data$[] = \"$escaped$\";\n");
}
string BytesFieldGenerator::GetDefaultValue(void) const
{
return "{ "
+ SimpleItoa(descriptor_->default_value_string().size())
+ ", "
+ FullNameToLower(descriptor_->full_name())
+ "__default_value_data }";
}
void BytesFieldGenerator::GenerateStaticInit(io::Printer* printer) const
{
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
printer->Print(variables_, "$default_value$");
break;
case FieldDescriptor::LABEL_OPTIONAL:
if (FieldSyntax(descriptor_) == 2)
printer->Print(variables_, "0, ");
printer->Print(variables_, "$default_value$");
break;
case FieldDescriptor::LABEL_REPEATED:
// no support for default?
printer->Print("0,NULL");
break;
}
}
void BytesFieldGenerator::GenerateDescriptorInitializer(io::Printer* printer) const
{
GenerateDescriptorInitializerGeneric(printer, true, "BYTES", "NULL");
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,100 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_BYTES_FIELD_H__
#define GOOGLE_PROTOBUF_COMPILER_C_BYTES_FIELD_H__
#include <map>
#include <string>
#include <protoc-c/c_field.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
class BytesFieldGenerator : public FieldGenerator {
public:
explicit BytesFieldGenerator(const FieldDescriptor* descriptor);
~BytesFieldGenerator();
// implements FieldGenerator ---------------------------------------
void GenerateStructMembers(io::Printer* printer) const;
void GenerateDescriptorInitializer(io::Printer* printer) const;
void GenerateDefaultValueDeclarations(io::Printer* printer) const;
void GenerateDefaultValueImplementations(io::Printer* printer) const;
string GetDefaultValue(void) const;
void GenerateStaticInit(io::Printer* printer) const;
private:
std::map<string, string> variables_;
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(BytesFieldGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_STRING_FIELD_H__

View File

@ -0,0 +1,334 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <set>
#include <map>
#include <protoc-c/c_enum.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/io/printer.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
EnumGenerator::EnumGenerator(const EnumDescriptor* descriptor,
const string& dllexport_decl)
: descriptor_(descriptor),
dllexport_decl_(dllexport_decl) {
}
EnumGenerator::~EnumGenerator() {}
void EnumGenerator::GenerateDefinition(io::Printer* printer) {
std::map<string, string> vars;
vars["classname"] = FullNameToC(descriptor_->full_name());
vars["shortname"] = descriptor_->name();
vars["uc_name"] = FullNameToUpper(descriptor_->full_name());
SourceLocation sourceLoc;
descriptor_->GetSourceLocation(&sourceLoc);
PrintComment (printer, sourceLoc.leading_comments);
printer->Print(vars, "typedef enum _$classname$ {\n");
printer->Indent();
const EnumValueDescriptor* min_value = descriptor_->value(0);
const EnumValueDescriptor* max_value = descriptor_->value(0);
vars["opt_comma"] = ",";
vars["prefix"] = FullNameToUpper(descriptor_->full_name()) + "__";
for (int i = 0; i < descriptor_->value_count(); i++) {
vars["name"] = descriptor_->value(i)->name();
vars["number"] = SimpleItoa(descriptor_->value(i)->number());
if (i + 1 == descriptor_->value_count())
vars["opt_comma"] = "";
SourceLocation valSourceLoc;
descriptor_->value(i)->GetSourceLocation(&valSourceLoc);
PrintComment (printer, valSourceLoc.leading_comments);
PrintComment (printer, valSourceLoc.trailing_comments);
printer->Print(vars, "$prefix$$name$ = $number$$opt_comma$\n");
if (descriptor_->value(i)->number() < min_value->number()) {
min_value = descriptor_->value(i);
}
if (descriptor_->value(i)->number() > max_value->number()) {
max_value = descriptor_->value(i);
}
}
printer->Print(vars, " PROTOBUF_C__FORCE_ENUM_TO_BE_INT_SIZE($uc_name$)\n");
printer->Outdent();
printer->Print(vars, "} $classname$;\n");
}
void EnumGenerator::GenerateDescriptorDeclarations(io::Printer* printer) {
std::map<string, string> vars;
if (dllexport_decl_.empty()) {
vars["dllexport"] = "";
} else {
vars["dllexport"] = dllexport_decl_ + " ";
}
vars["classname"] = FullNameToC(descriptor_->full_name());
vars["lcclassname"] = FullNameToLower(descriptor_->full_name());
printer->Print(vars,
"extern $dllexport$const ProtobufCEnumDescriptor $lcclassname$__descriptor;\n");
}
struct ValueIndex
{
int value;
unsigned index;
unsigned final_index; /* index in uniqified array of values */
const char *name;
};
void EnumGenerator::GenerateValueInitializer(io::Printer *printer, int index)
{
const EnumValueDescriptor *vd = descriptor_->value(index);
std::map<string, string> vars;
bool optimize_code_size = descriptor_->file()->options().has_optimize_for() &&
descriptor_->file()->options().optimize_for() ==
FileOptions_OptimizeMode_CODE_SIZE;
vars["enum_value_name"] = vd->name();
vars["c_enum_value_name"] = FullNameToUpper(descriptor_->full_name()) + "__" + vd->name();
vars["value"] = SimpleItoa(vd->number());
if (optimize_code_size)
printer->Print(vars, " { NULL, NULL, $value$ }, /* CODE_SIZE */\n");
else
printer->Print(vars,
" { \"$enum_value_name$\", \"$c_enum_value_name$\", $value$ },\n");
}
static int compare_value_indices_by_value_then_index(const void *a, const void *b)
{
const ValueIndex *vi_a = (const ValueIndex *) a;
const ValueIndex *vi_b = (const ValueIndex *) b;
if (vi_a->value < vi_b->value) return -1;
if (vi_a->value > vi_b->value) return +1;
if (vi_a->index < vi_b->index) return -1;
if (vi_a->index > vi_b->index) return +1;
return 0;
}
static int compare_value_indices_by_name(const void *a, const void *b)
{
const ValueIndex *vi_a = (const ValueIndex *) a;
const ValueIndex *vi_b = (const ValueIndex *) b;
return strcmp (vi_a->name, vi_b->name);
}
void EnumGenerator::GenerateEnumDescriptor(io::Printer* printer) {
std::map<string, string> vars;
vars["fullname"] = descriptor_->full_name();
vars["lcclassname"] = FullNameToLower(descriptor_->full_name());
vars["cname"] = FullNameToC(descriptor_->full_name());
vars["shortname"] = descriptor_->name();
vars["packagename"] = descriptor_->file()->package();
vars["value_count"] = SimpleItoa(descriptor_->value_count());
bool optimize_code_size = descriptor_->file()->options().has_optimize_for() &&
descriptor_->file()->options().optimize_for() ==
FileOptions_OptimizeMode_CODE_SIZE;
// Sort by name and value, dropping duplicate values if they appear later.
// TODO: use a c++ paradigm for this!
NameIndex *name_index = new NameIndex[descriptor_->value_count()];
ValueIndex *value_index = new ValueIndex[descriptor_->value_count()];
for (int j = 0; j < descriptor_->value_count(); j++) {
const EnumValueDescriptor *vd = descriptor_->value(j);
name_index[j].index = j;
name_index[j].name = vd->name().c_str();
value_index[j].index = j;
value_index[j].value = vd->number();
value_index[j].name = vd->name().c_str();
}
qsort(value_index, descriptor_->value_count(),
sizeof(ValueIndex), compare_value_indices_by_value_then_index);
// only record unique values
int n_unique_values;
if (descriptor_->value_count() == 0) {
n_unique_values = 0; // should never happen
} else {
n_unique_values = 1;
value_index[0].final_index = 0;
for (int j = 1; j < descriptor_->value_count(); j++) {
if (value_index[j-1].value != value_index[j].value)
value_index[j].final_index = n_unique_values++;
else
value_index[j].final_index = n_unique_values - 1;
}
}
vars["unique_value_count"] = SimpleItoa(n_unique_values);
printer->Print(vars,
"static const ProtobufCEnumValue $lcclassname$__enum_values_by_number[$unique_value_count$] =\n"
"{\n");
if (descriptor_->value_count() > 0) {
GenerateValueInitializer(printer, value_index[0].index);
for (int j = 1; j < descriptor_->value_count(); j++) {
if (value_index[j-1].value != value_index[j].value) {
GenerateValueInitializer(printer, value_index[j].index);
}
}
}
printer->Print(vars, "};\n");
printer->Print(vars, "static const ProtobufCIntRange $lcclassname$__value_ranges[] = {\n");
unsigned n_ranges = 0;
if (descriptor_->value_count() > 0) {
unsigned range_start = 0;
unsigned range_len = 1;
int range_start_value = value_index[0].value;
int last_value = range_start_value;
for (int j = 1; j < descriptor_->value_count(); j++) {
if (value_index[j-1].value != value_index[j].value) {
if (last_value + 1 == value_index[j].value) {
range_len++;
} else {
// output range
vars["range_start_value"] = SimpleItoa(range_start_value);
vars["orig_index"] = SimpleItoa(range_start);
printer->Print (vars, "{$range_start_value$, $orig_index$},");
range_start_value = value_index[j].value;
range_start += range_len;
range_len = 1;
n_ranges++;
}
last_value = value_index[j].value;
}
}
{
vars["range_start_value"] = SimpleItoa(range_start_value);
vars["orig_index"] = SimpleItoa(range_start);
printer->Print (vars, "{$range_start_value$, $orig_index$},");
range_start += range_len;
n_ranges++;
}
{
vars["range_start_value"] = SimpleItoa(0);
vars["orig_index"] = SimpleItoa(range_start);
printer->Print (vars, "{$range_start_value$, $orig_index$}\n};\n");
}
}
vars["n_ranges"] = SimpleItoa(n_ranges);
if (!optimize_code_size) {
qsort(value_index, descriptor_->value_count(),
sizeof(ValueIndex), compare_value_indices_by_name);
printer->Print(vars,
"static const ProtobufCEnumValueIndex $lcclassname$__enum_values_by_name[$value_count$] =\n"
"{\n");
for (int j = 0; j < descriptor_->value_count(); j++) {
vars["index"] = SimpleItoa(value_index[j].final_index);
vars["name"] = value_index[j].name;
printer->Print (vars, " { \"$name$\", $index$ },\n");
}
printer->Print(vars, "};\n");
}
if (optimize_code_size) {
printer->Print(vars,
"const ProtobufCEnumDescriptor $lcclassname$__descriptor =\n"
"{\n"
" PROTOBUF_C__ENUM_DESCRIPTOR_MAGIC,\n"
" NULL,NULL,NULL,NULL, /* CODE_SIZE */\n"
" $unique_value_count$,\n"
" $lcclassname$__enum_values_by_number,\n"
" 0, NULL, /* CODE_SIZE */\n"
" $n_ranges$,\n"
" $lcclassname$__value_ranges,\n"
" NULL,NULL,NULL,NULL /* reserved[1234] */\n"
"};\n");
} else {
printer->Print(vars,
"const ProtobufCEnumDescriptor $lcclassname$__descriptor =\n"
"{\n"
" PROTOBUF_C__ENUM_DESCRIPTOR_MAGIC,\n"
" \"$fullname$\",\n"
" \"$shortname$\",\n"
" \"$cname$\",\n"
" \"$packagename$\",\n"
" $unique_value_count$,\n"
" $lcclassname$__enum_values_by_number,\n"
" $value_count$,\n"
" $lcclassname$__enum_values_by_name,\n"
" $n_ranges$,\n"
" $lcclassname$__value_ranges,\n"
" NULL,NULL,NULL,NULL /* reserved[1234] */\n"
"};\n");
}
delete[] value_index;
delete[] name_index;
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,118 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_ENUM_H__
#define GOOGLE_PROTOBUF_COMPILER_C_ENUM_H__
#include <string>
#include <google/protobuf/descriptor.h>
namespace google {
namespace protobuf {
namespace io {
class Printer; // printer.h
}
}
namespace protobuf {
namespace compiler {
namespace c {
class EnumGenerator {
public:
// See generator.cc for the meaning of dllexport_decl.
explicit EnumGenerator(const EnumDescriptor* descriptor,
const string& dllexport_decl);
~EnumGenerator();
// Header stuff.
// Generate header code defining the enum. This code should be placed
// within the enum's package namespace, but NOT within any class, even for
// nested enums.
void GenerateDefinition(io::Printer* printer);
void GenerateDescriptorDeclarations(io::Printer* printer);
// Source file stuff.
// Generate the ProtobufCEnumDescriptor for this enum
void GenerateEnumDescriptor(io::Printer* printer);
// Generate static initializer for a ProtobufCEnumValue
// given the index of the value in the enum.
void GenerateValueInitializer(io::Printer *printer, int index);
private:
const EnumDescriptor* descriptor_;
string dllexport_decl_;
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_ENUM_H__

View File

@ -0,0 +1,149 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <protoc-c/c_enum_field.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/io/printer.h>
#include <google/protobuf/wire_format.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
using internal::WireFormat;
// TODO(kenton): Factor out a "SetCommonFieldVariables()" to get rid of
// repeat code between this and the other field types.
void SetEnumVariables(const FieldDescriptor* descriptor,
std::map<string, string>* variables) {
(*variables)["name"] = FieldName(descriptor);
(*variables)["type"] = FullNameToC(descriptor->enum_type()->full_name());
const EnumValueDescriptor* default_value = descriptor->default_value_enum();
(*variables)["default"] = FullNameToUpper(default_value->type()->full_name())
+ "__" + default_value->name();
(*variables)["deprecated"] = FieldDeprecated(descriptor);
}
// ===================================================================
EnumFieldGenerator::
EnumFieldGenerator(const FieldDescriptor* descriptor)
: FieldGenerator(descriptor)
{
SetEnumVariables(descriptor, &variables_);
}
EnumFieldGenerator::~EnumFieldGenerator() {}
void EnumFieldGenerator::GenerateStructMembers(io::Printer* printer) const
{
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
printer->Print(variables_, "$type$ $name$$deprecated$;\n");
break;
case FieldDescriptor::LABEL_OPTIONAL:
if (descriptor_->containing_oneof() == NULL && FieldSyntax(descriptor_) == 2)
printer->Print(variables_, "protobuf_c_boolean has_$name$$deprecated$;\n");
printer->Print(variables_, "$type$ $name$$deprecated$;\n");
break;
case FieldDescriptor::LABEL_REPEATED:
printer->Print(variables_, "size_t n_$name$$deprecated$;\n");
printer->Print(variables_, "$type$ *$name$$deprecated$;\n");
break;
}
}
string EnumFieldGenerator::GetDefaultValue(void) const
{
return variables_.find("default")->second;
}
void EnumFieldGenerator::GenerateStaticInit(io::Printer* printer) const
{
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
printer->Print(variables_, "$default$");
break;
case FieldDescriptor::LABEL_OPTIONAL:
if (FieldSyntax(descriptor_) == 2)
printer->Print(variables_, "0, ");
printer->Print(variables_, "$default$");
break;
case FieldDescriptor::LABEL_REPEATED:
// no support for default?
printer->Print("0,NULL");
break;
}
}
void EnumFieldGenerator::GenerateDescriptorInitializer(io::Printer* printer) const
{
string addr = "&" + FullNameToLower(descriptor_->enum_type()->full_name()) + "__descriptor";
GenerateDescriptorInitializerGeneric(printer, true, "ENUM", addr);
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,98 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_ENUM_FIELD_H__
#define GOOGLE_PROTOBUF_COMPILER_C_ENUM_FIELD_H__
#include <map>
#include <string>
#include <protoc-c/c_field.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
class EnumFieldGenerator : public FieldGenerator {
public:
explicit EnumFieldGenerator(const FieldDescriptor* descriptor);
~EnumFieldGenerator();
// implements FieldGenerator ---------------------------------------
void GenerateStructMembers(io::Printer* printer) const;
void GenerateDescriptorInitializer(io::Printer* printer) const;
string GetDefaultValue(void) const;
void GenerateStaticInit(io::Printer* printer) const;
private:
std::map<string, string> variables_;
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(EnumFieldGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_ENUM_FIELD_H__

View File

@ -0,0 +1,90 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <protoc-c/c_extension.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/io/printer.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
ExtensionGenerator::ExtensionGenerator(const FieldDescriptor* descriptor,
const string& dllexport_decl)
: descriptor_(descriptor),
dllexport_decl_(dllexport_decl) {
}
ExtensionGenerator::~ExtensionGenerator() {}
void ExtensionGenerator::GenerateDeclaration(io::Printer* printer) {
}
void ExtensionGenerator::GenerateDefinition(io::Printer* printer) {
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,110 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_EXTENSION_H__
#define GOOGLE_PROTOBUF_COMPILER_C_EXTENSION_H__
#include <string>
#include <google/protobuf/stubs/common.h>
namespace google {
namespace protobuf {
class FieldDescriptor; // descriptor.h
namespace io {
class Printer; // printer.h
}
}
namespace protobuf {
namespace compiler {
namespace c {
// Generates code for an extension, which may be within the scope of some
// message or may be at file scope. This is much simpler than FieldGenerator
// since extensions are just simple identifiers with interesting types.
class ExtensionGenerator {
public:
// See generator.cc for the meaning of dllexport_decl.
explicit ExtensionGenerator(const FieldDescriptor* descriptor,
const string& dllexport_decl);
~ExtensionGenerator();
// Header stuff.
void GenerateDeclaration(io::Printer* printer);
// Source file stuff.
void GenerateDefinition(io::Printer* printer);
private:
const FieldDescriptor* descriptor_;
string type_traits_;
string dllexport_decl_;
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ExtensionGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_MESSAGE_H__

View File

@ -0,0 +1,227 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <protoc-c/c_field.h>
#include <protoc-c/c_primitive_field.h>
#include <protoc-c/c_string_field.h>
#include <protoc-c/c_bytes_field.h>
#include <protoc-c/c_enum_field.h>
#include <protoc-c/c_message_field.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/descriptor.pb.h>
#include <google/protobuf/stubs/common.h>
#include <google/protobuf/io/printer.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
FieldGenerator::~FieldGenerator()
{
}
static bool is_packable_type(FieldDescriptor::Type type)
{
return type == FieldDescriptor::TYPE_DOUBLE
|| type == FieldDescriptor::TYPE_FLOAT
|| type == FieldDescriptor::TYPE_INT64
|| type == FieldDescriptor::TYPE_UINT64
|| type == FieldDescriptor::TYPE_INT32
|| type == FieldDescriptor::TYPE_FIXED64
|| type == FieldDescriptor::TYPE_FIXED32
|| type == FieldDescriptor::TYPE_BOOL
|| type == FieldDescriptor::TYPE_UINT32
|| type == FieldDescriptor::TYPE_ENUM
|| type == FieldDescriptor::TYPE_SFIXED32
|| type == FieldDescriptor::TYPE_SFIXED64
|| type == FieldDescriptor::TYPE_SINT32
|| type == FieldDescriptor::TYPE_SINT64;
//TYPE_BYTES
//TYPE_STRING
//TYPE_GROUP
//TYPE_MESSAGE
}
void FieldGenerator::GenerateDescriptorInitializerGeneric(io::Printer* printer,
bool optional_uses_has,
const string &type_macro,
const string &descriptor_addr) const
{
std::map<string, string> variables;
variables["TYPE"] = type_macro;
variables["classname"] = FullNameToC(FieldScope(descriptor_)->full_name());
variables["name"] = FieldName(descriptor_);
variables["proto_name"] = descriptor_->name();
variables["descriptor_addr"] = descriptor_addr;
variables["value"] = SimpleItoa(descriptor_->number());
const OneofDescriptor *oneof = descriptor_->containing_oneof();
if (oneof != NULL)
variables["oneofname"] = FullNameToLower(oneof->name());
if (FieldSyntax(descriptor_) == 3 &&
descriptor_->label() == FieldDescriptor::LABEL_OPTIONAL) {
variables["LABEL"] = "NONE";
optional_uses_has = false;
} else {
variables["LABEL"] = CamelToUpper(GetLabelName(descriptor_->label()));
}
if (descriptor_->has_default_value()) {
variables["default_value"] = string("&")
+ FullNameToLower(descriptor_->full_name())
+ "__default_value";
} else if (FieldSyntax(descriptor_) == 3 &&
descriptor_->type() == FieldDescriptor::TYPE_STRING) {
variables["default_value"] = "&protobuf_c_empty_string";
} else {
variables["default_value"] = "NULL";
}
variables["flags"] = "0";
if (descriptor_->label() == FieldDescriptor::LABEL_REPEATED
&& is_packable_type (descriptor_->type())
&& descriptor_->options().packed())
variables["flags"] += " | PROTOBUF_C_FIELD_FLAG_PACKED";
if (descriptor_->options().deprecated())
variables["flags"] += " | PROTOBUF_C_FIELD_FLAG_DEPRECATED";
if (oneof != NULL)
variables["flags"] += " | PROTOBUF_C_FIELD_FLAG_ONEOF";
printer->Print("{\n");
if (descriptor_->file()->options().has_optimize_for() &&
descriptor_->file()->options().optimize_for() ==
FileOptions_OptimizeMode_CODE_SIZE) {
printer->Print(" NULL, /* CODE_SIZE */\n");
} else {
printer->Print(variables, " \"$proto_name$\",\n");
}
printer->Print(variables,
" $value$,\n"
" PROTOBUF_C_LABEL_$LABEL$,\n"
" PROTOBUF_C_TYPE_$TYPE$,\n");
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
printer->Print(variables, " 0, /* quantifier_offset */\n");
break;
case FieldDescriptor::LABEL_OPTIONAL:
if (oneof != NULL) {
printer->Print(variables, " offsetof($classname$, $oneofname$_case),\n");
} else if (optional_uses_has) {
printer->Print(variables, " offsetof($classname$, has_$name$),\n");
} else {
printer->Print(variables, " 0, /* quantifier_offset */\n");
}
break;
case FieldDescriptor::LABEL_REPEATED:
printer->Print(variables, " offsetof($classname$, n_$name$),\n");
break;
}
printer->Print(variables, " offsetof($classname$, $name$),\n");
printer->Print(variables, " $descriptor_addr$,\n");
printer->Print(variables, " $default_value$,\n");
printer->Print(variables, " $flags$, /* flags */\n");
printer->Print(variables, " 0,NULL,NULL /* reserved1,reserved2, etc */\n");
printer->Print("},\n");
}
FieldGeneratorMap::FieldGeneratorMap(const Descriptor* descriptor)
: descriptor_(descriptor),
field_generators_(
new scoped_ptr<FieldGenerator>[descriptor->field_count()]) {
// Construct all the FieldGenerators.
for (int i = 0; i < descriptor->field_count(); i++) {
field_generators_[i].reset(MakeGenerator(descriptor->field(i)));
}
}
FieldGenerator* FieldGeneratorMap::MakeGenerator(const FieldDescriptor* field) {
switch (field->type()) {
case FieldDescriptor::TYPE_MESSAGE:
return new MessageFieldGenerator(field);
case FieldDescriptor::TYPE_STRING:
return new StringFieldGenerator(field);
case FieldDescriptor::TYPE_BYTES:
return new BytesFieldGenerator(field);
case FieldDescriptor::TYPE_ENUM:
return new EnumFieldGenerator(field);
case FieldDescriptor::TYPE_GROUP:
return 0; // XXX
default:
return new PrimitiveFieldGenerator(field);
}
}
FieldGeneratorMap::~FieldGeneratorMap() {}
const FieldGenerator& FieldGeneratorMap::get(
const FieldDescriptor* field) const {
GOOGLE_CHECK_EQ(field->containing_type(), descriptor_);
return *field_generators_[field->index()];
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,132 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_FIELD_H__
#define GOOGLE_PROTOBUF_COMPILER_C_FIELD_H__
#include <google/protobuf/stubs/common.h>
#include <google/protobuf/descriptor.h>
namespace google {
namespace protobuf {
namespace io {
class Printer; // printer.h
}
}
namespace protobuf {
namespace compiler {
namespace c {
class FieldGenerator {
public:
explicit FieldGenerator(const FieldDescriptor *descriptor) : descriptor_(descriptor) {}
virtual ~FieldGenerator();
// Generate definitions to be included in the structure.
virtual void GenerateStructMembers(io::Printer* printer) const = 0;
// Generate a static initializer for this field.
virtual void GenerateDescriptorInitializer(io::Printer* printer) const = 0;
virtual void GenerateDefaultValueDeclarations(io::Printer* printer) const { }
virtual void GenerateDefaultValueImplementations(io::Printer* printer) const { }
virtual string GetDefaultValue() const = 0;
// Generate members to initialize this field from a static initializer
virtual void GenerateStaticInit(io::Printer* printer) const = 0;
protected:
void GenerateDescriptorInitializerGeneric(io::Printer* printer,
bool optional_uses_has,
const string &type_macro,
const string &descriptor_addr) const;
const FieldDescriptor *descriptor_;
private:
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldGenerator);
};
// Convenience class which constructs FieldGenerators for a Descriptor.
class FieldGeneratorMap {
public:
explicit FieldGeneratorMap(const Descriptor* descriptor);
~FieldGeneratorMap();
const FieldGenerator& get(const FieldDescriptor* field) const;
private:
const Descriptor* descriptor_;
scoped_array<scoped_ptr<FieldGenerator> > field_generators_;
static FieldGenerator* MakeGenerator(const FieldDescriptor* field);
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FieldGeneratorMap);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_FIELD_H__

View File

@ -0,0 +1,280 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2014, Dave Benson and the protobuf-c authors.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <protoc-c/c_file.h>
#include <protoc-c/c_enum.h>
#include <protoc-c/c_service.h>
#include <protoc-c/c_extension.h>
#include <protoc-c/c_helpers.h>
#include <protoc-c/c_message.h>
#include <google/protobuf/io/printer.h>
#include <google/protobuf/descriptor.pb.h>
#include "protobuf-c.h"
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
// ===================================================================
FileGenerator::FileGenerator(const FileDescriptor* file,
const string& dllexport_decl)
: file_(file),
message_generators_(
new scoped_ptr<MessageGenerator>[file->message_type_count()]),
enum_generators_(
new scoped_ptr<EnumGenerator>[file->enum_type_count()]),
service_generators_(
new scoped_ptr<ServiceGenerator>[file->service_count()]),
extension_generators_(
new scoped_ptr<ExtensionGenerator>[file->extension_count()]) {
for (int i = 0; i < file->message_type_count(); i++) {
message_generators_[i].reset(
new MessageGenerator(file->message_type(i), dllexport_decl));
}
for (int i = 0; i < file->enum_type_count(); i++) {
enum_generators_[i].reset(
new EnumGenerator(file->enum_type(i), dllexport_decl));
}
for (int i = 0; i < file->service_count(); i++) {
service_generators_[i].reset(
new ServiceGenerator(file->service(i), dllexport_decl));
}
for (int i = 0; i < file->extension_count(); i++) {
extension_generators_[i].reset(
new ExtensionGenerator(file->extension(i), dllexport_decl));
}
SplitStringUsing(file_->package(), ".", &package_parts_);
}
FileGenerator::~FileGenerator() {}
void FileGenerator::GenerateHeader(io::Printer* printer) {
string filename_identifier = FilenameIdentifier(file_->name());
int min_header_version = 1000000;
if (file_->syntax() == FileDescriptor::SYNTAX_PROTO3) {
min_header_version = 1003000;
}
// Generate top of header.
printer->Print(
"/* Generated by the protocol buffer compiler. DO NOT EDIT! */\n"
"/* Generated from: $filename$ */\n"
"\n"
"#ifndef PROTOBUF_C_$filename_identifier$__INCLUDED\n"
"#define PROTOBUF_C_$filename_identifier$__INCLUDED\n"
"\n"
"#include <protobuf-c/protobuf-c.h>\n"
"\n"
"PROTOBUF_C__BEGIN_DECLS\n"
"\n",
"filename", file_->name(),
"filename_identifier", filename_identifier);
// Verify the protobuf-c library header version is compatible with the
// protoc-c version before going any further.
printer->Print(
"#if PROTOBUF_C_VERSION_NUMBER < $min_header_version$\n"
"# error This file was generated by a newer version of protoc-c which is "
"incompatible with your libprotobuf-c headers. Please update your headers.\n"
"#elif $protoc_version$ < PROTOBUF_C_MIN_COMPILER_VERSION\n"
"# error This file was generated by an older version of protoc-c which is "
"incompatible with your libprotobuf-c headers. Please regenerate this file "
"with a newer version of protoc-c.\n"
"#endif\n"
"\n",
"min_header_version", SimpleItoa(min_header_version),
"protoc_version", SimpleItoa(PROTOBUF_C_VERSION_NUMBER));
for (int i = 0; i < file_->dependency_count(); i++) {
printer->Print(
"#include \"$dependency$.pb-c.h\"\n",
"dependency", StripProto(file_->dependency(i)->name()));
}
printer->Print("\n");
// Generate forward declarations of classes.
for (int i = 0; i < file_->message_type_count(); i++) {
message_generators_[i]->GenerateStructTypedef(printer);
}
printer->Print("\n");
// Generate enum definitions.
printer->Print("\n/* --- enums --- */\n\n");
for (int i = 0; i < file_->message_type_count(); i++) {
message_generators_[i]->GenerateEnumDefinitions(printer);
}
for (int i = 0; i < file_->enum_type_count(); i++) {
enum_generators_[i]->GenerateDefinition(printer);
}
// Generate class definitions.
printer->Print("\n/* --- messages --- */\n\n");
for (int i = 0; i < file_->message_type_count(); i++) {
message_generators_[i]->GenerateStructDefinition(printer);
}
for (int i = 0; i < file_->message_type_count(); i++) {
message_generators_[i]->GenerateHelperFunctionDeclarations(printer, false);
}
printer->Print("/* --- per-message closures --- */\n\n");
for (int i = 0; i < file_->message_type_count(); i++) {
message_generators_[i]->GenerateClosureTypedef(printer);
}
// Generate service definitions.
printer->Print("\n/* --- services --- */\n\n");
for (int i = 0; i < file_->service_count(); i++) {
service_generators_[i]->GenerateMainHFile(printer);
}
// Declare extension identifiers.
for (int i = 0; i < file_->extension_count(); i++) {
extension_generators_[i]->GenerateDeclaration(printer);
}
printer->Print("\n/* --- descriptors --- */\n\n");
for (int i = 0; i < file_->enum_type_count(); i++) {
enum_generators_[i]->GenerateDescriptorDeclarations(printer);
}
for (int i = 0; i < file_->message_type_count(); i++) {
message_generators_[i]->GenerateDescriptorDeclarations(printer);
}
for (int i = 0; i < file_->service_count(); i++) {
service_generators_[i]->GenerateDescriptorDeclarations(printer);
}
printer->Print(
"\n"
"PROTOBUF_C__END_DECLS\n"
"\n\n#endif /* PROTOBUF_C_$filename_identifier$__INCLUDED */\n",
"filename_identifier", filename_identifier);
}
void FileGenerator::GenerateSource(io::Printer* printer) {
printer->Print(
"/* Generated by the protocol buffer compiler. DO NOT EDIT! */\n"
"/* Generated from: $filename$ */\n"
"\n"
"/* Do not generate deprecated warnings for self */\n"
"#ifndef PROTOBUF_C__NO_DEPRECATED\n"
"#define PROTOBUF_C__NO_DEPRECATED\n"
"#endif\n"
"\n"
"#include \"$basename$.pb-c.h\"\n",
"filename", file_->name(),
"basename", StripProto(file_->name()));
#if 0
// For each dependency, write a prototype for that dependency's
// BuildDescriptors() function. We don't expose these in the header because
// they are internal implementation details, and since this is generated code
// we don't have the usual risks involved with declaring external functions
// within a .cc file.
for (int i = 0; i < file_->dependency_count(); i++) {
const FileDescriptor* dependency = file_->dependency(i);
// Open the dependency's namespace.
vector<string> dependency_package_parts;
SplitStringUsing(dependency->package(), ".", &dependency_package_parts);
// Declare its BuildDescriptors() function.
printer->Print(
"void $function$();",
"function", GlobalBuildDescriptorsName(dependency->name()));
// Close the namespace.
for (int i = 0; i < dependency_package_parts.size(); i++) {
printer->Print(" }");
}
printer->Print("\n");
}
#endif
for (int i = 0; i < file_->message_type_count(); i++) {
message_generators_[i]->GenerateHelperFunctionDefinitions(printer, false);
}
for (int i = 0; i < file_->message_type_count(); i++) {
message_generators_[i]->GenerateMessageDescriptor(printer);
}
for (int i = 0; i < file_->enum_type_count(); i++) {
enum_generators_[i]->GenerateEnumDescriptor(printer);
}
for (int i = 0; i < file_->service_count(); i++) {
service_generators_[i]->GenerateCFile(printer);
}
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,117 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_FILE_H__
#define GOOGLE_PROTOBUF_COMPILER_C_FILE_H__
#include <string>
#include <vector>
#include <google/protobuf/stubs/common.h>
#include <protoc-c/c_field.h>
namespace google {
namespace protobuf {
class FileDescriptor; // descriptor.h
namespace io {
class Printer; // printer.h
}
}
namespace protobuf {
namespace compiler {
namespace c {
class EnumGenerator; // enum.h
class MessageGenerator; // message.h
class ServiceGenerator; // service.h
class ExtensionGenerator; // extension.h
class FileGenerator {
public:
// See generator.cc for the meaning of dllexport_decl.
explicit FileGenerator(const FileDescriptor* file,
const string& dllexport_decl);
~FileGenerator();
void GenerateHeader(io::Printer* printer);
void GenerateSource(io::Printer* printer);
private:
const FileDescriptor* file_;
scoped_array<scoped_ptr<MessageGenerator> > message_generators_;
scoped_array<scoped_ptr<EnumGenerator> > enum_generators_;
scoped_array<scoped_ptr<ServiceGenerator> > service_generators_;
scoped_array<scoped_ptr<ExtensionGenerator> > extension_generators_;
// E.g. if the package is foo.bar, package_parts_ is {"foo", "bar"}.
vector<string> package_parts_;
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(FileGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_FILE_H__

View File

@ -0,0 +1,172 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <protoc-c/c_generator.h>
#include <vector>
#include <utility>
#include <protoc-c/c_file.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/io/printer.h>
#include <google/protobuf/io/zero_copy_stream.h>
#include <google/protobuf/descriptor.pb.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
// Parses a set of comma-delimited name/value pairs, e.g.:
// "foo=bar,baz,qux=corge"
// parses to the pairs:
// ("foo", "bar"), ("baz", ""), ("qux", "corge")
void ParseOptions(const string& text, vector<pair<string, string> >* output) {
vector<string> parts;
SplitStringUsing(text, ",", &parts);
for (unsigned i = 0; i < parts.size(); i++) {
string::size_type equals_pos = parts[i].find_first_of('=');
pair<string, string> value;
if (equals_pos == string::npos) {
value.first = parts[i];
value.second = "";
} else {
value.first = parts[i].substr(0, equals_pos);
value.second = parts[i].substr(equals_pos + 1);
}
output->push_back(value);
}
}
CGenerator::CGenerator() {}
CGenerator::~CGenerator() {}
bool CGenerator::Generate(const FileDescriptor* file,
const string& parameter,
OutputDirectory* output_directory,
string* error) const {
vector<pair<string, string> > options;
ParseOptions(parameter, &options);
// -----------------------------------------------------------------
// parse generator options
// TODO(kenton): If we ever have more options, we may want to create a
// class that encapsulates them which we can pass down to all the
// generator classes. Currently we pass dllexport_decl down to all of
// them via the constructors, but we don't want to have to add another
// constructor parameter for every option.
// If the dllexport_decl option is passed to the compiler, we need to write
// it in front of every symbol that should be exported if this .proto is
// compiled into a Windows DLL. E.g., if the user invokes the protocol
// compiler as:
// protoc --cpp_out=dllexport_decl=FOO_EXPORT:outdir foo.proto
// then we'll define classes like this:
// class FOO_EXPORT Foo {
// ...
// }
// FOO_EXPORT is a macro which should expand to __declspec(dllexport) or
// __declspec(dllimport) depending on what is being compiled.
string dllexport_decl;
for (unsigned i = 0; i < options.size(); i++) {
if (options[i].first == "dllexport_decl") {
dllexport_decl = options[i].second;
} else {
*error = "Unknown generator option: " + options[i].first;
return false;
}
}
// -----------------------------------------------------------------
string basename = StripProto(file->name());
basename.append(".pb-c");
FileGenerator file_generator(file, dllexport_decl);
// Generate header.
{
scoped_ptr<io::ZeroCopyOutputStream> output(
output_directory->Open(basename + ".h"));
io::Printer printer(output.get(), '$');
file_generator.GenerateHeader(&printer);
}
// Generate cc file.
{
scoped_ptr<io::ZeroCopyOutputStream> output(
output_directory->Open(basename + ".c"));
io::Printer printer(output.get(), '$');
file_generator.GenerateSource(&printer);
}
return true;
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,100 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
// Generates C code for a given .proto file.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_GENERATOR_H__
#define GOOGLE_PROTOBUF_COMPILER_C_GENERATOR_H__
#include <string>
#include <google/protobuf/compiler/code_generator.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
// CodeGenerator implementation which generates a C++ source file and
// header. If you create your own protocol compiler binary and you want
// it to support C++ output, you can do so by registering an instance of this
// CodeGenerator with the CommandLineInterface in your main() function.
class LIBPROTOC_EXPORT CGenerator : public CodeGenerator {
public:
CGenerator();
~CGenerator();
// implements CodeGenerator ----------------------------------------
bool Generate(const FileDescriptor* file,
const string& parameter,
OutputDirectory* output_directory,
string* error) const;
private:
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(CGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_GENERATOR_H__

View File

@ -0,0 +1,572 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <vector>
#include <set>
#include <stdio.h> // for snprintf
#include <float.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/stubs/common.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
#if defined(_MSC_VER)
// FIXME: In the case where the generated string is longer than the buffer,
// _snprint() returns a negative value, where snprintf() returns the number
// of characters that *would* have been stored, had there been room.
// That is fundamental, as it allows snprintf() to be used to find the size
// necessary for the buffer, simply by calling it with the size of the buffer
// passed in as zero.
// Note: at the present moment return value isn't used in the code.
#define snprintf _snprintf
#pragma warning(disable:4800)
#pragma warning(disable:4996)
#endif
string DotsToUnderscores(const string& name) {
return StringReplace(name, ".", "_", true);
}
string DotsToColons(const string& name) {
return StringReplace(name, ".", "::", true);
}
string SimpleFtoa(float f) {
char buf[100];
snprintf(buf,sizeof(buf),"%.*g", FLT_DIG, f);
buf[sizeof(buf)-1] = 0; /* should NOT be necessary */
return buf;
}
string SimpleDtoa(double d) {
char buf[100];
snprintf(buf,sizeof(buf),"%.*g", DBL_DIG, d);
buf[sizeof(buf)-1] = 0; /* should NOT be necessary */
return buf;
}
string CamelToUpper(const string &name) {
bool was_upper = true; // suppress initial _
string rv = "";
int len = name.length();
for (int i = 0; i < len; i++) {
bool is_upper = isupper(name[i]);
if (is_upper) {
if (!was_upper)
rv += '_';
rv += name[i];
} else {
rv += toupper(name[i]);
}
was_upper = is_upper;
}
return rv;
}
string CamelToLower(const string &name) {
bool was_upper = true; // suppress initial _
string rv = "";
int len = name.length();
for (int i = 0; i < len; i++) {
bool is_upper = isupper(name[i]);
if (is_upper) {
if (!was_upper)
rv += '_';
rv += tolower(name[i]);
} else {
rv += name[i];
}
was_upper = is_upper;
}
return rv;
}
string ToUpper(const string &name) {
string rv = "";
int len = name.length();
for (int i = 0; i < len; i++) {
rv += toupper(name[i]);
}
return rv;
}
string ToLower(const string &name) {
string rv = "";
int len = name.length();
for (int i = 0; i < len; i++) {
rv += tolower(name[i]);
}
return rv;
}
string ToCamel(const string &name) {
string rv = "";
int len = name.length();
bool next_is_upper = true;
for (int i = 0; i < len; i++) {
if (name[i] == '_') {
next_is_upper = true;
} else if (next_is_upper) {
rv += toupper (name[i]);
next_is_upper = false;
} else {
rv += name[i];
}
}
return rv;
}
string FullNameToLower(const string &full_name) {
vector<string> pieces;
SplitStringUsing(full_name, ".", &pieces);
string rv = "";
for (unsigned i = 0; i < pieces.size(); i++) {
if (pieces[i] == "") continue;
if (rv != "") rv += "__";
rv += CamelToLower(pieces[i]);
}
return rv;
}
string FullNameToUpper(const string &full_name) {
vector<string> pieces;
SplitStringUsing(full_name, ".", &pieces);
string rv = "";
for (unsigned i = 0; i < pieces.size(); i++) {
if (pieces[i] == "") continue;
if (rv != "") rv += "__";
rv += CamelToUpper(pieces[i]);
}
return rv;
}
string FullNameToC(const string &full_name) {
vector<string> pieces;
SplitStringUsing(full_name, ".", &pieces);
string rv = "";
for (unsigned i = 0; i < pieces.size(); i++) {
if (pieces[i] == "") continue;
if (rv != "") rv += "__";
rv += ToCamel(pieces[i]);
}
return rv;
}
void PrintComment (io::Printer* printer, string comment)
{
if (!comment.empty())
{
vector<string> comment_lines;
SplitStringUsing (comment, "\r\n", &comment_lines);
printer->Print ("/*\n");
for (int i = 0; i < comment_lines.size(); i++)
{
if (!comment_lines[i].empty())
{
/* Make sure we don't inadvertently close the comment block */
if (comment_lines[i][0] == '/')
comment_lines[i] = ' ' + comment_lines[i];
/* Or cause other compiler issues. */
size_t delim_i;
while ((delim_i = comment_lines[i].find("/*")) != string::npos)
comment_lines[i][delim_i] = ' ';
while ((delim_i = comment_lines[i].find("*/")) != string::npos)
comment_lines[i][delim_i + 1] = ' ';
printer->Print (" *$line$\n", "line", comment_lines[i]);
}
}
printer->Print (" */\n");
}
}
string ConvertToSpaces(const string &input) {
return string(input.size(), ' ');
}
int compare_name_indices_by_name(const void *a, const void *b)
{
const NameIndex *ni_a = (const NameIndex *) a;
const NameIndex *ni_b = (const NameIndex *) b;
return strcmp (ni_a->name, ni_b->name);
}
string CEscape(const string& src);
const char* const kKeywordList[] = {
"and", "and_eq", "asm", "auto", "bitand", "bitor", "bool", "break", "case",
"catch", "char", "class", "compl", "const", "const_cast", "continue",
"default", "delete", "do", "double", "dynamic_cast", "else", "enum",
"explicit", "extern", "false", "float", "for", "friend", "goto", "if",
"inline", "int", "long", "mutable", "namespace", "new", "not", "not_eq",
"operator", "or", "or_eq", "private", "protected", "public", "register",
"reinterpret_cast", "return", "short", "signed", "sizeof", "static",
"static_cast", "struct", "switch", "template", "this", "throw", "true", "try",
"typedef", "typeid", "typename", "union", "unsigned", "using", "virtual",
"void", "volatile", "wchar_t", "while", "xor", "xor_eq"
};
std::set<string> MakeKeywordsMap() {
std::set<string> result;
for (int i = 0; i < GOOGLE_ARRAYSIZE(kKeywordList); i++) {
result.insert(kKeywordList[i]);
}
return result;
}
std::set<string> kKeywords = MakeKeywordsMap();
string ClassName(const Descriptor* descriptor, bool qualified) {
// Find "outer", the descriptor of the top-level message in which
// "descriptor" is embedded.
const Descriptor* outer = descriptor;
while (outer->containing_type() != NULL) outer = outer->containing_type();
const string& outer_name = outer->full_name();
string inner_name = descriptor->full_name().substr(outer_name.size());
if (qualified) {
return "::" + DotsToColons(outer_name) + DotsToUnderscores(inner_name);
} else {
return outer->name() + DotsToUnderscores(inner_name);
}
}
string ClassName(const EnumDescriptor* enum_descriptor, bool qualified) {
if (enum_descriptor->containing_type() == NULL) {
if (qualified) {
return DotsToColons(enum_descriptor->full_name());
} else {
return enum_descriptor->name();
}
} else {
string result = ClassName(enum_descriptor->containing_type(), qualified);
result += '_';
result += enum_descriptor->name();
return result;
}
}
string FieldName(const FieldDescriptor* field) {
string result = ToLower(field->name());
if (kKeywords.count(result) > 0) {
result.append("_");
}
return result;
}
string FieldDeprecated(const FieldDescriptor* field) {
if (field->options().deprecated()) {
return " PROTOBUF_C__DEPRECATED";
}
return "";
}
string StripProto(const string& filename) {
if (HasSuffixString(filename, ".protodevel")) {
return StripSuffixString(filename, ".protodevel");
} else {
return StripSuffixString(filename, ".proto");
}
}
// Convert a file name into a valid identifier.
string FilenameIdentifier(const string& filename) {
string result;
for (unsigned i = 0; i < filename.size(); i++) {
if (isalnum(filename[i])) {
result.push_back(filename[i]);
} else {
// Not alphanumeric. To avoid any possibility of name conflicts we
// use the hex code for the character.
result.push_back('_');
char buffer[32];
result.append(FastHexToBuffer(static_cast<uint8>(filename[i]), buffer));
}
}
return result;
}
// Return the name of the BuildDescriptors() function for a given file.
string GlobalBuildDescriptorsName(const string& filename) {
return "proto_BuildDescriptors_" + FilenameIdentifier(filename);
}
string GetLabelName(FieldDescriptor::Label label) {
switch (label) {
case FieldDescriptor::LABEL_OPTIONAL: return "optional";
case FieldDescriptor::LABEL_REQUIRED: return "required";
case FieldDescriptor::LABEL_REPEATED: return "repeated";
}
return "bad-label";
}
unsigned
WriteIntRanges(io::Printer* printer, int n_values, const int *values, const string &name)
{
std::map<string, string> vars;
vars["name"] = name;
if (n_values > 0) {
int n_ranges = 1;
for (int i = 1; i < n_values; i++) {
if (values[i-1] + 1 != values[i])
n_ranges++;
}
vars["n_ranges"] = SimpleItoa(n_ranges);
printer->Print(vars, "static const ProtobufCIntRange $name$[$n_ranges$ + 1] =\n"
"{\n");
int last_range_start = 0;
for (int i = 1; i < n_values; i++) {
if (values[i-1] + 1 != values[i]) {
int count = i - last_range_start;
int expected = values[i-1] + 1;
vars["start_value"] = SimpleItoa(expected - count);
vars["orig_offset"] = SimpleItoa(last_range_start);
printer->Print (vars, " { $start_value$, $orig_offset$ },\n");
last_range_start = i;
}
}
// write last real entry
{
int i = n_values;
int count = i - last_range_start;
int expected = values[i-1] + 1;
vars["start_value"] = SimpleItoa(expected - count);
vars["orig_offset"] = SimpleItoa(last_range_start);
printer->Print (vars, " { $start_value$, $orig_offset$ },\n");
}
// write sentinel entry
vars["n_entries"] = SimpleItoa(n_values);
printer->Print (vars, " { 0, $n_entries$ }\n");
printer->Print (vars, "};\n");
return n_ranges;
} else {
printer->Print (vars, "#define $name$ NULL\n");
return 0;
}
}
// XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXx
// XXXXXXXXX this stuff is copied from strutils.cc !!!! XXXXXXXXXXXXXXXXXXXXXXXXXXXXx
// XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXx
// ----------------------------------------------------------------------
// StringReplace()
// Replace the "old" pattern with the "new" pattern in a string,
// and append the result to "res". If replace_all is false,
// it only replaces the first instance of "old."
// ----------------------------------------------------------------------
void StringReplace(const string& s, const string& oldsub,
const string& newsub, bool replace_all,
string* res) {
if (oldsub.empty()) {
res->append(s); // if empty, append the given string.
return;
}
string::size_type start_pos = 0;
string::size_type pos;
do {
pos = s.find(oldsub, start_pos);
if (pos == string::npos) {
break;
}
res->append(s, start_pos, pos - start_pos);
res->append(newsub);
start_pos = pos + oldsub.size(); // start searching again after the "old"
} while (replace_all);
res->append(s, start_pos, s.length() - start_pos);
}
// ----------------------------------------------------------------------
// StringReplace()
// Give me a string and two patterns "old" and "new", and I replace
// the first instance of "old" in the string with "new", if it
// exists. If "global" is true; call this repeatedly until it
// fails. RETURN a new string, regardless of whether the replacement
// happened or not.
// ----------------------------------------------------------------------
string StringReplace(const string& s, const string& oldsub,
const string& newsub, bool replace_all) {
string ret;
StringReplace(s, oldsub, newsub, replace_all, &ret);
return ret;
}
// ----------------------------------------------------------------------
// SplitStringUsing()
// Split a string using a character delimiter. Append the components
// to 'result'.
//
// Note: For multi-character delimiters, this routine will split on *ANY* of
// the characters in the string, not the entire string as a single delimiter.
// ----------------------------------------------------------------------
template <typename ITR>
static inline
void SplitStringToIteratorUsing(const string& full,
const char* delim,
ITR& result) {
// Optimize the common case where delim is a single character.
if (delim[0] != '\0' && delim[1] == '\0') {
char c = delim[0];
const char* p = full.data();
const char* end = p + full.size();
while (p != end) {
if (*p == c) {
++p;
} else {
const char* start = p;
while (++p != end && *p != c);
*result++ = string(start, p - start);
}
}
return;
}
string::size_type begin_index, end_index;
begin_index = full.find_first_not_of(delim);
while (begin_index != string::npos) {
end_index = full.find_first_of(delim, begin_index);
if (end_index == string::npos) {
*result++ = full.substr(begin_index);
return;
}
*result++ = full.substr(begin_index, (end_index - begin_index));
begin_index = full.find_first_not_of(delim, end_index);
}
}
void SplitStringUsing(const string& full,
const char* delim,
vector<string>* result) {
std::back_insert_iterator< vector<string> > it(*result);
SplitStringToIteratorUsing(full, delim, it);
}
char* FastHexToBuffer(int i, char* buffer)
{
snprintf(buffer, 16, "%x", i);
return buffer;
}
static int CEscapeInternal(const char* src, int src_len, char* dest,
int dest_len, bool use_hex) {
const char* src_end = src + src_len;
int used = 0;
bool last_hex_escape = false; // true if last output char was \xNN
for (; src < src_end; src++) {
if (dest_len - used < 2) // Need space for two letter escape
return -1;
bool is_hex_escape = false;
switch (*src) {
case '\n': dest[used++] = '\\'; dest[used++] = 'n'; break;
case '\r': dest[used++] = '\\'; dest[used++] = 'r'; break;
case '\t': dest[used++] = '\\'; dest[used++] = 't'; break;
case '\"': dest[used++] = '\\'; dest[used++] = '\"'; break;
case '\'': dest[used++] = '\\'; dest[used++] = '\''; break;
case '\\': dest[used++] = '\\'; dest[used++] = '\\'; break;
default:
// Note that if we emit \xNN and the src character after that is a hex
// digit then that digit must be escaped too to prevent it being
// interpreted as part of the character code by C.
if (!isprint(*src) || (last_hex_escape && isxdigit(*src))) {
if (dest_len - used < 4) // need space for 4 letter escape
return -1;
sprintf(dest + used, (use_hex ? "\\x%02x" : "\\%03o"),
static_cast<uint8>(*src));
is_hex_escape = use_hex;
used += 4;
} else {
dest[used++] = *src; break;
}
}
last_hex_escape = is_hex_escape;
}
if (dest_len - used < 1) // make sure that there is room for \0
return -1;
dest[used] = '\0'; // doesn't count towards return value though
return used;
}
string CEscape(const string& src) {
const int dest_length = src.size() * 4 + 1; // Maximum possible expansion
scoped_array<char> dest(new char[dest_length]);
const int len = CEscapeInternal(src.data(), src.size(),
dest.get(), dest_length, false);
GOOGLE_DCHECK_GE(len, 0);
return string(dest.get(), len);
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,197 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_HELPERS_H__
#define GOOGLE_PROTOBUF_COMPILER_C_HELPERS_H__
#include <string>
#include <vector>
#include <sstream>
#include <google/protobuf/descriptor.h>
#include <google/protobuf/descriptor.pb.h>
#include <google/protobuf/io/printer.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
// Returns the non-nested type name for the given type. If "qualified" is
// true, prefix the type with the full namespace. For example, if you had:
// package foo.bar;
// message Baz { message Qux {} }
// Then the qualified ClassName for Qux would be:
// Foo__Bar__Baz_Qux
// While the non-qualified version would be:
// Baz_Qux
string ClassName(const Descriptor* descriptor, bool qualified);
string ClassName(const EnumDescriptor* enum_descriptor, bool qualified);
// --- Borrowed from stubs. ---
template <typename T> string SimpleItoa(T n) {
std::stringstream stream;
stream << n;
return stream.str();
}
string SimpleFtoa(float f);
string SimpleDtoa(double f);
void SplitStringUsing(const string &str, const char *delim, std::vector<string> *out);
string CEscape(const string& src);
string StringReplace(const string& s, const string& oldsub, const string& newsub, bool replace_all);
inline bool HasSuffixString(const string& str, const string& suffix) { return str.size() >= suffix.size() && str.compare(str.size() - suffix.size(), suffix.size(), suffix) == 0; }
inline string StripSuffixString(const string& str, const string& suffix) { if (HasSuffixString(str, suffix)) { return str.substr(0, str.size() - suffix.size()); } else { return str; } }
char* FastHexToBuffer(int i, char* buffer);
// Get the (unqualified) name that should be used for this field in C code.
// The name is coerced to lower-case to emulate proto1 behavior. People
// should be using lowercase-with-underscores style for proto field names
// anyway, so normally this just returns field->name().
string FieldName(const FieldDescriptor* field);
// Get macro string for deprecated field
string FieldDeprecated(const FieldDescriptor* field);
// Returns the scope where the field was defined (for extensions, this is
// different from the message type to which the field applies).
inline const Descriptor* FieldScope(const FieldDescriptor* field) {
return field->is_extension() ?
field->extension_scope() : field->containing_type();
}
// convert a CamelCase class name into an all uppercase affair
// with underscores separating words, e.g. MyClass becomes MY_CLASS.
string CamelToUpper(const string &class_name);
string CamelToLower(const string &class_name);
// lowercased, underscored name to camel case
string ToCamel(const string &name);
// lowercase the string
string ToLower(const string &class_name);
string ToUpper(const string &class_name);
// full_name() to lowercase with underscores
string FullNameToLower(const string &full_name);
string FullNameToUpper(const string &full_name);
// full_name() to c-typename (with underscores for packages, otherwise camel case)
string FullNameToC(const string &class_name);
// Splits, indents, formats, and prints comment lines
void PrintComment (io::Printer* printer, string comment);
// make a string of spaces as long as input
string ConvertToSpaces(const string &input);
// Strips ".proto" or ".protodevel" from the end of a filename.
string StripProto(const string& filename);
// Get the C++ type name for a primitive type (e.g. "double", "::google::protobuf::int32", etc.).
// Note: non-built-in type names will be qualified, meaning they will start
// with a ::. If you are using the type as a template parameter, you will
// need to insure there is a space between the < and the ::, because the
// ridiculous C++ standard defines "<:" to be a synonym for "[".
const char* PrimitiveTypeName(FieldDescriptor::CppType type);
// Get the declared type name in CamelCase format, as is used e.g. for the
// methods of WireFormat. For example, TYPE_INT32 becomes "Int32".
const char* DeclaredTypeMethodName(FieldDescriptor::Type type);
// Convert a file name into a valid identifier.
string FilenameIdentifier(const string& filename);
// Return the name of the BuildDescriptors() function for a given file.
string GlobalBuildDescriptorsName(const string& filename);
// return 'required', 'optional', or 'repeated'
string GetLabelName(FieldDescriptor::Label label);
// write IntRanges entries for a bunch of sorted values.
// returns the number of ranges there are to bsearch.
unsigned WriteIntRanges(io::Printer* printer, int n_values, const int *values, const string &name);
struct NameIndex
{
unsigned index;
const char *name;
};
int compare_name_indices_by_name(const void*, const void*);
// Return the syntax version of the file containing the field.
// This wrapper is needed to be able to compile against protobuf2.
inline int FieldSyntax(const FieldDescriptor* field) {
#ifdef HAVE_PROTO3
return field->file()->syntax() == FileDescriptor::SYNTAX_PROTO3 ? 3 : 2;
#else
return 2;
#endif
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_HELPERS_H__

View File

@ -0,0 +1,579 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <algorithm>
#include <map>
#include <protoc-c/c_message.h>
#include <protoc-c/c_enum.h>
#include <protoc-c/c_extension.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/io/printer.h>
#include <google/protobuf/io/coded_stream.h>
#include <google/protobuf/wire_format.h>
#include <google/protobuf/descriptor.pb.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
// ===================================================================
MessageGenerator::MessageGenerator(const Descriptor* descriptor,
const string& dllexport_decl)
: descriptor_(descriptor),
dllexport_decl_(dllexport_decl),
field_generators_(descriptor),
nested_generators_(new scoped_ptr<MessageGenerator>[
descriptor->nested_type_count()]),
enum_generators_(new scoped_ptr<EnumGenerator>[
descriptor->enum_type_count()]),
extension_generators_(new scoped_ptr<ExtensionGenerator>[
descriptor->extension_count()]) {
for (int i = 0; i < descriptor->nested_type_count(); i++) {
nested_generators_[i].reset(
new MessageGenerator(descriptor->nested_type(i), dllexport_decl));
}
for (int i = 0; i < descriptor->enum_type_count(); i++) {
enum_generators_[i].reset(
new EnumGenerator(descriptor->enum_type(i), dllexport_decl));
}
for (int i = 0; i < descriptor->extension_count(); i++) {
extension_generators_[i].reset(
new ExtensionGenerator(descriptor->extension(i), dllexport_decl));
}
}
MessageGenerator::~MessageGenerator() {}
void MessageGenerator::
GenerateStructTypedef(io::Printer* printer) {
printer->Print("typedef struct _$classname$ $classname$;\n",
"classname", FullNameToC(descriptor_->full_name()));
for (int i = 0; i < descriptor_->nested_type_count(); i++) {
nested_generators_[i]->GenerateStructTypedef(printer);
}
}
void MessageGenerator::
GenerateEnumDefinitions(io::Printer* printer) {
for (int i = 0; i < descriptor_->nested_type_count(); i++) {
nested_generators_[i]->GenerateEnumDefinitions(printer);
}
for (int i = 0; i < descriptor_->enum_type_count(); i++) {
enum_generators_[i]->GenerateDefinition(printer);
}
}
void MessageGenerator::
GenerateStructDefinition(io::Printer* printer) {
for (int i = 0; i < descriptor_->nested_type_count(); i++) {
nested_generators_[i]->GenerateStructDefinition(printer);
}
std::map<string, string> vars;
vars["classname"] = FullNameToC(descriptor_->full_name());
vars["lcclassname"] = FullNameToLower(descriptor_->full_name());
vars["ucclassname"] = FullNameToUpper(descriptor_->full_name());
vars["field_count"] = SimpleItoa(descriptor_->field_count());
if (dllexport_decl_.empty()) {
vars["dllexport"] = "";
} else {
vars["dllexport"] = dllexport_decl_ + " ";
}
// Generate the case enums for unions
for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
const OneofDescriptor *oneof = descriptor_->oneof_decl(i);
vars["opt_comma"] = ",";
vars["oneofname"] = FullNameToUpper(oneof->name());
vars["foneofname"] = FullNameToC(oneof->full_name());
printer->Print("typedef enum {\n");
printer->Indent();
printer->Print(vars, "$ucclassname$__$oneofname$__NOT_SET = 0,\n");
for (int j = 0; j < oneof->field_count(); j++) {
const FieldDescriptor *field = oneof->field(j);
vars["fieldname"] = FullNameToUpper(field->name());
vars["fieldnum"] = SimpleItoa(field->number());
bool isLast = j == oneof->field_count() - 1;
if (isLast) {
vars["opt_comma"] = "";
}
printer->Print(vars, "$ucclassname$__$oneofname$_$fieldname$ = $fieldnum$$opt_comma$\n");
}
printer->Print(vars, " PROTOBUF_C__FORCE_ENUM_TO_BE_INT_SIZE($ucclassname$__$oneofname$)\n");
printer->Outdent();
printer->Print(vars, "} $foneofname$Case;\n\n");
}
SourceLocation msgSourceLoc;
descriptor_->GetSourceLocation(&msgSourceLoc);
PrintComment (printer, msgSourceLoc.leading_comments);
printer->Print(vars,
"struct $dllexport$ _$classname$\n"
"{\n"
" ProtobufCMessage base;\n");
// Generate fields.
printer->Indent();
for (int i = 0; i < descriptor_->field_count(); i++) {
const FieldDescriptor *field = descriptor_->field(i);
if (field->containing_oneof() == NULL) {
SourceLocation fieldSourceLoc;
field->GetSourceLocation(&fieldSourceLoc);
PrintComment (printer, fieldSourceLoc.leading_comments);
PrintComment (printer, fieldSourceLoc.trailing_comments);
field_generators_.get(field).GenerateStructMembers(printer);
}
}
// Generate unions from oneofs.
for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
const OneofDescriptor *oneof = descriptor_->oneof_decl(i);
vars["oneofname"] = FullNameToLower(oneof->name());
vars["foneofname"] = FullNameToC(oneof->full_name());
printer->Print(vars, "$foneofname$Case $oneofname$_case;\n");
printer->Print("union {\n");
printer->Indent();
for (int j = 0; j < oneof->field_count(); j++) {
const FieldDescriptor *field = oneof->field(j);
SourceLocation fieldSourceLoc;
field->GetSourceLocation(&fieldSourceLoc);
PrintComment (printer, fieldSourceLoc.leading_comments);
PrintComment (printer, fieldSourceLoc.trailing_comments);
field_generators_.get(field).GenerateStructMembers(printer);
}
printer->Outdent();
printer->Print(vars, "};\n");
}
printer->Outdent();
printer->Print(vars, "};\n");
for (int i = 0; i < descriptor_->field_count(); i++) {
const FieldDescriptor *field = descriptor_->field(i);
if (field->has_default_value()) {
field_generators_.get(field).GenerateDefaultValueDeclarations(printer);
}
}
printer->Print(vars, "#define $ucclassname$__INIT \\\n"
" { PROTOBUF_C_MESSAGE_INIT (&$lcclassname$__descriptor) \\\n ");
for (int i = 0; i < descriptor_->field_count(); i++) {
const FieldDescriptor *field = descriptor_->field(i);
if (field->containing_oneof() == NULL) {
printer->Print(", ");
field_generators_.get(field).GenerateStaticInit(printer);
}
}
for (int i = 0; i < descriptor_->oneof_decl_count(); i++) {
const OneofDescriptor *oneof = descriptor_->oneof_decl(i);
vars["foneofname"] = FullNameToUpper(oneof->full_name());
// Initialize the case enum
printer->Print(vars, ", $foneofname$__NOT_SET");
// Initialize the union
printer->Print(", {0}");
}
printer->Print(" }\n\n\n");
}
void MessageGenerator::
GenerateHelperFunctionDeclarations(io::Printer* printer, bool is_submessage)
{
for (int i = 0; i < descriptor_->nested_type_count(); i++) {
nested_generators_[i]->GenerateHelperFunctionDeclarations(printer, true);
}
std::map<string, string> vars;
vars["classname"] = FullNameToC(descriptor_->full_name());
vars["lcclassname"] = FullNameToLower(descriptor_->full_name());
printer->Print(vars,
"/* $classname$ methods */\n"
"void $lcclassname$__init\n"
" ($classname$ *message);\n"
);
if (!is_submessage) {
printer->Print(vars,
"size_t $lcclassname$__get_packed_size\n"
" (const $classname$ *message);\n"
"size_t $lcclassname$__pack\n"
" (const $classname$ *message,\n"
" uint8_t *out);\n"
"size_t $lcclassname$__pack_to_buffer\n"
" (const $classname$ *message,\n"
" ProtobufCBuffer *buffer);\n"
"$classname$ *\n"
" $lcclassname$__unpack\n"
" (ProtobufCAllocator *allocator,\n"
" size_t len,\n"
" const uint8_t *data);\n"
"void $lcclassname$__free_unpacked\n"
" ($classname$ *message,\n"
" ProtobufCAllocator *allocator);\n"
);
}
}
void MessageGenerator::
GenerateDescriptorDeclarations(io::Printer* printer) {
printer->Print("extern const ProtobufCMessageDescriptor $name$__descriptor;\n",
"name", FullNameToLower(descriptor_->full_name()));
for (int i = 0; i < descriptor_->nested_type_count(); i++) {
nested_generators_[i]->GenerateDescriptorDeclarations(printer);
}
for (int i = 0; i < descriptor_->enum_type_count(); i++) {
enum_generators_[i]->GenerateDescriptorDeclarations(printer);
}
}
void MessageGenerator::GenerateClosureTypedef(io::Printer* printer)
{
for (int i = 0; i < descriptor_->nested_type_count(); i++) {
nested_generators_[i]->GenerateClosureTypedef(printer);
}
std::map<string, string> vars;
vars["name"] = FullNameToC(descriptor_->full_name());
printer->Print(vars,
"typedef void (*$name$_Closure)\n"
" (const $name$ *message,\n"
" void *closure_data);\n");
}
static int
compare_pfields_by_number (const void *a, const void *b)
{
const FieldDescriptor *pa = *(const FieldDescriptor **)a;
const FieldDescriptor *pb = *(const FieldDescriptor **)b;
if (pa->number() < pb->number()) return -1;
if (pa->number() > pb->number()) return +1;
return 0;
}
void MessageGenerator::
GenerateHelperFunctionDefinitions(io::Printer* printer, bool is_submessage)
{
for (int i = 0; i < descriptor_->nested_type_count(); i++) {
nested_generators_[i]->GenerateHelperFunctionDefinitions(printer, true);
}
std::map<string, string> vars;
vars["classname"] = FullNameToC(descriptor_->full_name());
vars["lcclassname"] = FullNameToLower(descriptor_->full_name());
vars["ucclassname"] = FullNameToUpper(descriptor_->full_name());
printer->Print(vars,
"void $lcclassname$__init\n"
" ($classname$ *message)\n"
"{\n"
" static const $classname$ init_value = $ucclassname$__INIT;\n"
" *message = init_value;\n"
"}\n");
if (!is_submessage) {
printer->Print(vars,
"size_t $lcclassname$__get_packed_size\n"
" (const $classname$ *message)\n"
"{\n"
" assert(message->base.descriptor == &$lcclassname$__descriptor);\n"
" return protobuf_c_message_get_packed_size ((const ProtobufCMessage*)(message));\n"
"}\n"
"size_t $lcclassname$__pack\n"
" (const $classname$ *message,\n"
" uint8_t *out)\n"
"{\n"
" assert(message->base.descriptor == &$lcclassname$__descriptor);\n"
" return protobuf_c_message_pack ((const ProtobufCMessage*)message, out);\n"
"}\n"
"size_t $lcclassname$__pack_to_buffer\n"
" (const $classname$ *message,\n"
" ProtobufCBuffer *buffer)\n"
"{\n"
" assert(message->base.descriptor == &$lcclassname$__descriptor);\n"
" return protobuf_c_message_pack_to_buffer ((const ProtobufCMessage*)message, buffer);\n"
"}\n"
"$classname$ *\n"
" $lcclassname$__unpack\n"
" (ProtobufCAllocator *allocator,\n"
" size_t len,\n"
" const uint8_t *data)\n"
"{\n"
" return ($classname$ *)\n"
" protobuf_c_message_unpack (&$lcclassname$__descriptor,\n"
" allocator, len, data);\n"
"}\n"
"void $lcclassname$__free_unpacked\n"
" ($classname$ *message,\n"
" ProtobufCAllocator *allocator)\n"
"{\n"
" if(!message)\n"
" return;\n"
" assert(message->base.descriptor == &$lcclassname$__descriptor);\n"
" protobuf_c_message_free_unpacked ((ProtobufCMessage*)message, allocator);\n"
"}\n"
);
}
}
void MessageGenerator::
GenerateMessageDescriptor(io::Printer* printer) {
std::map<string, string> vars;
vars["fullname"] = descriptor_->full_name();
vars["classname"] = FullNameToC(descriptor_->full_name());
vars["lcclassname"] = FullNameToLower(descriptor_->full_name());
vars["shortname"] = ToCamel(descriptor_->name());
vars["n_fields"] = SimpleItoa(descriptor_->field_count());
vars["packagename"] = descriptor_->file()->package();
bool optimize_code_size = descriptor_->file()->options().has_optimize_for() &&
descriptor_->file()->options().optimize_for() ==
FileOptions_OptimizeMode_CODE_SIZE;
for (int i = 0; i < descriptor_->nested_type_count(); i++) {
nested_generators_[i]->GenerateMessageDescriptor(printer);
}
for (int i = 0; i < descriptor_->enum_type_count(); i++) {
enum_generators_[i]->GenerateEnumDescriptor(printer);
}
for (int i = 0; i < descriptor_->field_count(); i++) {
const FieldDescriptor *fd = descriptor_->field(i);
if (fd->has_default_value()) {
field_generators_.get(fd).GenerateDefaultValueImplementations(printer);
}
}
for (int i = 0; i < descriptor_->field_count(); i++) {
const FieldDescriptor *fd = descriptor_->field(i);
if (fd->has_default_value()) {
bool already_defined = false;
vars["name"] = fd->name();
vars["lcname"] = CamelToLower(fd->name());
vars["maybe_static"] = "static ";
vars["field_dv_ctype_suffix"] = "";
vars["default_value"] = field_generators_.get(fd).GetDefaultValue();
switch (fd->cpp_type()) {
case FieldDescriptor::CPPTYPE_INT32:
vars["field_dv_ctype"] = "int32_t";
break;
case FieldDescriptor::CPPTYPE_INT64:
vars["field_dv_ctype"] = "int64_t";
break;
case FieldDescriptor::CPPTYPE_UINT32:
vars["field_dv_ctype"] = "uint32_t";
break;
case FieldDescriptor::CPPTYPE_UINT64:
vars["field_dv_ctype"] = "uint64_t";
break;
case FieldDescriptor::CPPTYPE_FLOAT:
vars["field_dv_ctype"] = "float";
break;
case FieldDescriptor::CPPTYPE_DOUBLE:
vars["field_dv_ctype"] = "double";
break;
case FieldDescriptor::CPPTYPE_BOOL:
vars["field_dv_ctype"] = "protobuf_c_boolean";
break;
case FieldDescriptor::CPPTYPE_MESSAGE:
// NOTE: not supported by protobuf
vars["maybe_static"] = "";
vars["field_dv_ctype"] = "{ ... }";
GOOGLE_LOG(DFATAL) << "Messages can't have default values!";
break;
case FieldDescriptor::CPPTYPE_STRING:
if (fd->type() == FieldDescriptor::TYPE_BYTES)
{
vars["field_dv_ctype"] = "ProtobufCBinaryData";
}
else /* STRING type */
{
already_defined = true;
vars["maybe_static"] = "";
vars["field_dv_ctype"] = "char";
vars["field_dv_ctype_suffix"] = "[]";
}
break;
case FieldDescriptor::CPPTYPE_ENUM:
{
const EnumValueDescriptor *vd = fd->default_value_enum();
vars["field_dv_ctype"] = FullNameToC(vd->type()->full_name());
break;
}
default:
GOOGLE_LOG(DFATAL) << "Unknown CPPTYPE";
break;
}
if (!already_defined)
printer->Print(vars, "$maybe_static$const $field_dv_ctype$ $lcclassname$__$lcname$__default_value$field_dv_ctype_suffix$ = $default_value$;\n");
}
}
if ( descriptor_->field_count() ) {
printer->Print(vars,
"static const ProtobufCFieldDescriptor $lcclassname$__field_descriptors[$n_fields$] =\n"
"{\n");
printer->Indent();
const FieldDescriptor **sorted_fields = new const FieldDescriptor *[descriptor_->field_count()];
for (int i = 0; i < descriptor_->field_count(); i++) {
sorted_fields[i] = descriptor_->field(i);
}
qsort (sorted_fields, descriptor_->field_count(),
sizeof (const FieldDescriptor *),
compare_pfields_by_number);
for (int i = 0; i < descriptor_->field_count(); i++) {
const FieldDescriptor *field = sorted_fields[i];
field_generators_.get(field).GenerateDescriptorInitializer(printer);
}
printer->Outdent();
printer->Print(vars, "};\n");
if (!optimize_code_size) {
NameIndex *field_indices = new NameIndex [descriptor_->field_count()];
for (int i = 0; i < descriptor_->field_count(); i++) {
field_indices[i].name = sorted_fields[i]->name().c_str();
field_indices[i].index = i;
}
qsort (field_indices, descriptor_->field_count(), sizeof (NameIndex),
compare_name_indices_by_name);
printer->Print(vars, "static const unsigned $lcclassname$__field_indices_by_name[] = {\n");
for (int i = 0; i < descriptor_->field_count(); i++) {
vars["index"] = SimpleItoa(field_indices[i].index);
vars["name"] = field_indices[i].name;
printer->Print(vars, " $index$, /* field[$index$] = $name$ */\n");
}
printer->Print("};\n");
delete[] field_indices;
}
// create range initializers
int *values = new int[descriptor_->field_count()];
for (int i = 0; i < descriptor_->field_count(); i++) {
values[i] = sorted_fields[i]->number();
}
int n_ranges = WriteIntRanges(printer,
descriptor_->field_count(), values,
vars["lcclassname"] + "__number_ranges");
delete [] values;
delete [] sorted_fields;
vars["n_ranges"] = SimpleItoa(n_ranges);
} else {
/* MS compiler can't handle arrays with zero size and empty
* initialization list. Furthermore it is an extension of GCC only but
* not a standard. */
vars["n_ranges"] = "0";
printer->Print(vars,
"#define $lcclassname$__field_descriptors NULL\n"
"#define $lcclassname$__field_indices_by_name NULL\n"
"#define $lcclassname$__number_ranges NULL\n");
}
printer->Print(vars,
"const ProtobufCMessageDescriptor $lcclassname$__descriptor =\n"
"{\n"
" PROTOBUF_C__MESSAGE_DESCRIPTOR_MAGIC,\n");
if (optimize_code_size) {
printer->Print(" NULL,NULL,NULL,NULL, /* CODE_SIZE */\n");
} else {
printer->Print(vars,
" \"$fullname$\",\n"
" \"$shortname$\",\n"
" \"$classname$\",\n"
" \"$packagename$\",\n");
}
printer->Print(vars,
" sizeof($classname$),\n"
" $n_fields$,\n"
" $lcclassname$__field_descriptors,\n");
if (optimize_code_size) {
printer->Print(" NULL, /* CODE_SIZE */\n");
} else {
printer->Print(vars,
" $lcclassname$__field_indices_by_name,\n");
}
printer->Print(vars,
" $n_ranges$,"
" $lcclassname$__number_ranges,\n"
" (ProtobufCMessageInit) $lcclassname$__init,\n"
" NULL,NULL,NULL /* reserved[123] */\n"
"};\n");
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,141 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_MESSAGE_H__
#define GOOGLE_PROTOBUF_COMPILER_C_MESSAGE_H__
#include <string>
#include <google/protobuf/stubs/common.h>
#include <protoc-c/c_field.h>
namespace google {
namespace protobuf {
namespace io {
class Printer; // printer.h
}
}
namespace protobuf {
namespace compiler {
namespace c {
class EnumGenerator; // enum.h
class ExtensionGenerator; // extension.h
class MessageGenerator {
public:
// See generator.cc for the meaning of dllexport_decl.
explicit MessageGenerator(const Descriptor* descriptor,
const string& dllexport_decl);
~MessageGenerator();
// Header stuff.
// Generate typedef.
void GenerateStructTypedef(io::Printer* printer);
// Generate descriptor prototype
void GenerateDescriptorDeclarations(io::Printer* printer);
// Generate descriptor prototype
void GenerateClosureTypedef(io::Printer* printer);
// Generate definitions of all nested enums (must come before class
// definitions because those classes use the enums definitions).
void GenerateEnumDefinitions(io::Printer* printer);
// Generate definitions for this class and all its nested types.
void GenerateStructDefinition(io::Printer* printer);
// Generate __INIT macro for populating this structure
void GenerateStructStaticInitMacro(io::Printer* printer);
// Generate standard helper functions declarations for this message.
void GenerateHelperFunctionDeclarations(io::Printer* printer, bool is_submessage);
// Source file stuff.
// Generate code that initializes the global variable storing the message's
// descriptor.
void GenerateMessageDescriptor(io::Printer* printer);
void GenerateHelperFunctionDefinitions(io::Printer* printer, bool is_submessage);
private:
string GetDefaultValueC(const FieldDescriptor *fd);
const Descriptor* descriptor_;
string dllexport_decl_;
FieldGeneratorMap field_generators_;
scoped_array<scoped_ptr<MessageGenerator> > nested_generators_;
scoped_array<scoped_ptr<EnumGenerator> > enum_generators_;
scoped_array<scoped_ptr<ExtensionGenerator> > extension_generators_;
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_MESSAGE_H__

View File

@ -0,0 +1,129 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <protoc-c/c_message_field.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/io/printer.h>
#include <google/protobuf/wire_format.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
using internal::WireFormat;
// ===================================================================
MessageFieldGenerator::
MessageFieldGenerator(const FieldDescriptor* descriptor)
: FieldGenerator(descriptor) {
}
MessageFieldGenerator::~MessageFieldGenerator() {}
void MessageFieldGenerator::GenerateStructMembers(io::Printer* printer) const
{
std::map<string, string> vars;
vars["name"] = FieldName(descriptor_);
vars["type"] = FullNameToC(descriptor_->message_type()->full_name());
vars["deprecated"] = FieldDeprecated(descriptor_);
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
case FieldDescriptor::LABEL_OPTIONAL:
printer->Print(vars, "$type$ *$name$$deprecated$;\n");
break;
case FieldDescriptor::LABEL_REPEATED:
printer->Print(vars, "size_t n_$name$$deprecated$;\n");
printer->Print(vars, "$type$ **$name$$deprecated$;\n");
break;
}
}
string MessageFieldGenerator::GetDefaultValue(void) const
{
/* XXX: update when protobuf gets support
* for default-values of message fields.
*/
return "NULL";
}
void MessageFieldGenerator::GenerateStaticInit(io::Printer* printer) const
{
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
case FieldDescriptor::LABEL_OPTIONAL:
printer->Print("NULL");
break;
case FieldDescriptor::LABEL_REPEATED:
printer->Print("0,NULL");
break;
}
}
void MessageFieldGenerator::GenerateDescriptorInitializer(io::Printer* printer) const
{
string addr = "&" + FullNameToLower(descriptor_->message_type()->full_name()) + "__descriptor";
GenerateDescriptorInitializerGeneric(printer, false, "MESSAGE", addr);
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,97 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_MESSAGE_FIELD_H__
#define GOOGLE_PROTOBUF_COMPILER_C_MESSAGE_FIELD_H__
#include <map>
#include <string>
#include <protoc-c/c_field.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
class MessageFieldGenerator : public FieldGenerator {
public:
explicit MessageFieldGenerator(const FieldDescriptor* descriptor);
~MessageFieldGenerator();
// implements FieldGenerator ---------------------------------------
void GenerateStructMembers(io::Printer* printer) const;
void GenerateDescriptorInitializer(io::Printer* printer) const;
string GetDefaultValue(void) const;
void GenerateStaticInit(io::Printer* printer) const;
private:
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(MessageFieldGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_MESSAGE_FIELD_H__

View File

@ -0,0 +1,211 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <protoc-c/c_primitive_field.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/io/printer.h>
#include <google/protobuf/wire_format.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
PrimitiveFieldGenerator::
PrimitiveFieldGenerator(const FieldDescriptor* descriptor)
: FieldGenerator(descriptor) {
}
PrimitiveFieldGenerator::~PrimitiveFieldGenerator() {}
void PrimitiveFieldGenerator::GenerateStructMembers(io::Printer* printer) const
{
string c_type;
std::map<string, string> vars;
switch (descriptor_->type()) {
case FieldDescriptor::TYPE_SINT32 :
case FieldDescriptor::TYPE_SFIXED32:
case FieldDescriptor::TYPE_INT32 : c_type = "int32_t"; break;
case FieldDescriptor::TYPE_SINT64 :
case FieldDescriptor::TYPE_SFIXED64:
case FieldDescriptor::TYPE_INT64 : c_type = "int64_t"; break;
case FieldDescriptor::TYPE_UINT32 :
case FieldDescriptor::TYPE_FIXED32 : c_type = "uint32_t"; break;
case FieldDescriptor::TYPE_UINT64 :
case FieldDescriptor::TYPE_FIXED64 : c_type = "uint64_t"; break;
case FieldDescriptor::TYPE_FLOAT : c_type = "float"; break;
case FieldDescriptor::TYPE_DOUBLE : c_type = "double"; break;
case FieldDescriptor::TYPE_BOOL : c_type = "protobuf_c_boolean"; break;
case FieldDescriptor::TYPE_ENUM :
case FieldDescriptor::TYPE_STRING :
case FieldDescriptor::TYPE_BYTES :
case FieldDescriptor::TYPE_GROUP :
case FieldDescriptor::TYPE_MESSAGE : GOOGLE_LOG(FATAL) << "not a primitive type"; break;
// No default because we want the compiler to complain if any new
// types are added.
}
vars["c_type"] = c_type;
vars["name"] = FieldName(descriptor_);
vars["deprecated"] = FieldDeprecated(descriptor_);
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
printer->Print(vars, "$c_type$ $name$$deprecated$;\n");
break;
case FieldDescriptor::LABEL_OPTIONAL:
if (descriptor_->containing_oneof() == NULL && FieldSyntax(descriptor_) == 2)
printer->Print(vars, "protobuf_c_boolean has_$name$$deprecated$;\n");
printer->Print(vars, "$c_type$ $name$$deprecated$;\n");
break;
case FieldDescriptor::LABEL_REPEATED:
printer->Print(vars, "size_t n_$name$$deprecated$;\n");
printer->Print(vars, "$c_type$ *$name$$deprecated$;\n");
break;
}
}
string PrimitiveFieldGenerator::GetDefaultValue() const
{
/* XXX: SimpleItoa seems woefully inadequate for anything but int32,
* but that's what protobuf uses. */
switch (descriptor_->cpp_type()) {
case FieldDescriptor::CPPTYPE_INT32:
return SimpleItoa(descriptor_->default_value_int32());
case FieldDescriptor::CPPTYPE_INT64:
return SimpleItoa(descriptor_->default_value_int64()) + "ll";
case FieldDescriptor::CPPTYPE_UINT32:
return SimpleItoa(descriptor_->default_value_uint32()) + "u";
case FieldDescriptor::CPPTYPE_UINT64:
return SimpleItoa(descriptor_->default_value_uint64()) + "ull";
case FieldDescriptor::CPPTYPE_FLOAT:
return SimpleFtoa(descriptor_->default_value_float());
case FieldDescriptor::CPPTYPE_DOUBLE:
return SimpleDtoa(descriptor_->default_value_double());
case FieldDescriptor::CPPTYPE_BOOL:
return descriptor_->default_value_bool() ? "1" : "0";
default:
GOOGLE_LOG(DFATAL) << "unexpected CPPTYPE in c_primitive_field";
return "UNEXPECTED_CPPTYPE";
}
}
void PrimitiveFieldGenerator::GenerateStaticInit(io::Printer* printer) const
{
std::map<string, string> vars;
if (descriptor_->has_default_value()) {
vars["default_value"] = GetDefaultValue();
} else {
vars["default_value"] = "0";
}
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
printer->Print(vars, "$default_value$");
break;
case FieldDescriptor::LABEL_OPTIONAL:
if (FieldSyntax(descriptor_) == 2)
printer->Print(vars, "0, ");
printer->Print(vars, "$default_value$");
break;
case FieldDescriptor::LABEL_REPEATED:
printer->Print("0,NULL");
break;
}
}
void PrimitiveFieldGenerator::GenerateDescriptorInitializer(io::Printer* printer) const
{
string c_type_macro;
switch (descriptor_->type()) {
#define WRITE_CASE(shortname) case FieldDescriptor::TYPE_##shortname: c_type_macro = #shortname; break;
WRITE_CASE(INT32)
WRITE_CASE(SINT32)
WRITE_CASE(UINT32)
WRITE_CASE(SFIXED32)
WRITE_CASE(FIXED32)
WRITE_CASE(INT64)
WRITE_CASE(SINT64)
WRITE_CASE(UINT64)
WRITE_CASE(FIXED64)
WRITE_CASE(SFIXED64)
WRITE_CASE(FLOAT)
WRITE_CASE(DOUBLE)
WRITE_CASE(BOOL)
#undef WRITE_CASE
case FieldDescriptor::TYPE_ENUM :
case FieldDescriptor::TYPE_STRING :
case FieldDescriptor::TYPE_BYTES :
case FieldDescriptor::TYPE_GROUP :
case FieldDescriptor::TYPE_MESSAGE : GOOGLE_LOG(FATAL) << "not a primitive type"; break;
// No default because we want the compiler to complain if any new
// types are added.
}
GenerateDescriptorInitializerGeneric(printer, true, c_type_macro, "NULL");
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,96 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_PRIMITIVE_FIELD_H__
#define GOOGLE_PROTOBUF_COMPILER_C_PRIMITIVE_FIELD_H__
#include <map>
#include <string>
#include <protoc-c/c_field.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
class PrimitiveFieldGenerator : public FieldGenerator {
public:
explicit PrimitiveFieldGenerator(const FieldDescriptor* descriptor);
~PrimitiveFieldGenerator();
// implements FieldGenerator ---------------------------------------
void GenerateStructMembers(io::Printer* printer) const;
void GenerateDescriptorInitializer(io::Printer* printer) const;
string GetDefaultValue(void) const;
void GenerateStaticInit(io::Printer* printer) const;
private:
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(PrimitiveFieldGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_PRIMITIVE_FIELD_H__

View File

@ -0,0 +1,294 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <protoc-c/c_service.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/io/printer.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
ServiceGenerator::ServiceGenerator(const ServiceDescriptor* descriptor,
const string& dllexport_decl)
: descriptor_(descriptor) {
vars_["name"] = descriptor_->name();
vars_["fullname"] = descriptor_->full_name();
vars_["cname"] = FullNameToC(descriptor_->full_name());
vars_["lcfullname"] = FullNameToLower(descriptor_->full_name());
vars_["ucfullname"] = FullNameToUpper(descriptor_->full_name());
vars_["lcfullpadd"] = ConvertToSpaces(vars_["lcfullname"]);
vars_["package"] = descriptor_->file()->package();
if (dllexport_decl.empty()) {
vars_["dllexport"] = "";
} else {
vars_["dllexport"] = dllexport_decl + " ";
}
}
ServiceGenerator::~ServiceGenerator() {}
// Header stuff.
void ServiceGenerator::GenerateMainHFile(io::Printer* printer)
{
GenerateVfuncs(printer);
GenerateInitMacros(printer);
GenerateCallersDeclarations(printer);
}
void ServiceGenerator::GenerateVfuncs(io::Printer* printer)
{
printer->Print(vars_,
"typedef struct _$cname$_Service $cname$_Service;\n"
"struct _$cname$_Service\n"
"{\n"
" ProtobufCService base;\n");
for (int i = 0; i < descriptor_->method_count(); i++) {
const MethodDescriptor *method = descriptor_->method(i);
string lcname = CamelToLower(method->name());
vars_["method"] = lcname;
vars_["metpad"] = ConvertToSpaces(lcname);
vars_["input_typename"] = FullNameToC(method->input_type()->full_name());
vars_["output_typename"] = FullNameToC(method->output_type()->full_name());
printer->Print(vars_,
" void (*$method$)($cname$_Service *service,\n"
" $metpad$ const $input_typename$ *input,\n"
" $metpad$ $output_typename$_Closure closure,\n"
" $metpad$ void *closure_data);\n");
}
printer->Print(vars_,
"};\n");
printer->Print(vars_,
"typedef void (*$cname$_ServiceDestroy)($cname$_Service *);\n"
"void $lcfullname$__init ($cname$_Service *service,\n"
" $lcfullpadd$ $cname$_ServiceDestroy destroy);\n");
}
void ServiceGenerator::GenerateInitMacros(io::Printer* printer)
{
printer->Print(vars_,
"#define $ucfullname$__BASE_INIT \\\n"
" { &$lcfullname$__descriptor, protobuf_c_service_invoke_internal, NULL }\n"
"#define $ucfullname$__INIT(function_prefix__) \\\n"
" { $ucfullname$__BASE_INIT");
for (int i = 0; i < descriptor_->method_count(); i++) {
const MethodDescriptor *method = descriptor_->method(i);
string lcname = CamelToLower(method->name());
vars_["method"] = lcname;
vars_["metpad"] = ConvertToSpaces(lcname);
printer->Print(vars_,
",\\\n function_prefix__ ## $method$");
}
printer->Print(vars_,
" }\n");
}
void ServiceGenerator::GenerateCallersDeclarations(io::Printer* printer)
{
for (int i = 0; i < descriptor_->method_count(); i++) {
const MethodDescriptor *method = descriptor_->method(i);
string lcname = CamelToLower(method->name());
string lcfullname = FullNameToLower(descriptor_->full_name());
vars_["method"] = lcname;
vars_["metpad"] = ConvertToSpaces(lcname);
vars_["input_typename"] = FullNameToC(method->input_type()->full_name());
vars_["output_typename"] = FullNameToC(method->output_type()->full_name());
vars_["padddddddddddddddddd"] = ConvertToSpaces(lcfullname + "__" + lcname);
printer->Print(vars_,
"void $lcfullname$__$method$(ProtobufCService *service,\n"
" $padddddddddddddddddd$ const $input_typename$ *input,\n"
" $padddddddddddddddddd$ $output_typename$_Closure closure,\n"
" $padddddddddddddddddd$ void *closure_data);\n");
}
}
void ServiceGenerator::GenerateDescriptorDeclarations(io::Printer* printer)
{
printer->Print(vars_, "extern const ProtobufCServiceDescriptor $lcfullname$__descriptor;\n");
}
// Source file stuff.
void ServiceGenerator::GenerateCFile(io::Printer* printer)
{
GenerateServiceDescriptor(printer);
GenerateCallersImplementations(printer);
GenerateInit(printer);
}
void ServiceGenerator::GenerateInit(io::Printer* printer)
{
printer->Print(vars_,
"void $lcfullname$__init ($cname$_Service *service,\n"
" $lcfullpadd$ $cname$_ServiceDestroy destroy)\n"
"{\n"
" protobuf_c_service_generated_init (&service->base,\n"
" &$lcfullname$__descriptor,\n"
" (ProtobufCServiceDestroy) destroy);\n"
"}\n");
}
struct MethodIndexAndName { unsigned i; const char *name; };
static int
compare_method_index_and_name_by_name (const void *a, const void *b)
{
const MethodIndexAndName *ma = (const MethodIndexAndName *) a;
const MethodIndexAndName *mb = (const MethodIndexAndName *) b;
return strcmp (ma->name, mb->name);
}
void ServiceGenerator::GenerateServiceDescriptor(io::Printer* printer)
{
int n_methods = descriptor_->method_count();
MethodIndexAndName *mi_array = new MethodIndexAndName[n_methods];
bool optimize_code_size = descriptor_->file()->options().has_optimize_for() &&
descriptor_->file()->options().optimize_for() ==
FileOptions_OptimizeMode_CODE_SIZE;
vars_["n_methods"] = SimpleItoa(n_methods);
printer->Print(vars_, "static const ProtobufCMethodDescriptor $lcfullname$__method_descriptors[$n_methods$] =\n"
"{\n");
for (int i = 0; i < n_methods; i++) {
const MethodDescriptor *method = descriptor_->method(i);
vars_["method"] = method->name();
vars_["input_descriptor"] = "&" + FullNameToLower(method->input_type()->full_name()) + "__descriptor";
vars_["output_descriptor"] = "&" + FullNameToLower(method->output_type()->full_name()) + "__descriptor";
if (optimize_code_size) {
printer->Print(vars_,
" { NULL, $input_descriptor$, $output_descriptor$ }, /* CODE_SIZE */\n");
} else {
printer->Print(vars_,
" { \"$method$\", $input_descriptor$, $output_descriptor$ },\n");
}
mi_array[i].i = i;
mi_array[i].name = method->name().c_str();
}
printer->Print(vars_, "};\n");
if (!optimize_code_size) {
qsort ((void*)mi_array, n_methods, sizeof (MethodIndexAndName),
compare_method_index_and_name_by_name);
printer->Print(vars_, "const unsigned $lcfullname$__method_indices_by_name[] = {\n");
for (int i = 0; i < n_methods; i++) {
vars_["i"] = SimpleItoa(mi_array[i].i);
vars_["name"] = mi_array[i].name;
vars_["comma"] = (i + 1 < n_methods) ? "," : " ";
printer->Print(vars_, " $i$$comma$ /* $name$ */\n");
}
printer->Print(vars_, "};\n");
vars_["name"] = descriptor_->name();
}
if (optimize_code_size) {
printer->Print(vars_, "const ProtobufCServiceDescriptor $lcfullname$__descriptor =\n"
"{\n"
" PROTOBUF_C__SERVICE_DESCRIPTOR_MAGIC,\n"
" NULL,NULL,NULL,NULL, /* CODE_SIZE */\n"
" $n_methods$,\n"
" $lcfullname$__method_descriptors,\n"
" NULL /* CODE_SIZE */\n"
"};\n");
} else {
printer->Print(vars_, "const ProtobufCServiceDescriptor $lcfullname$__descriptor =\n"
"{\n"
" PROTOBUF_C__SERVICE_DESCRIPTOR_MAGIC,\n"
" \"$fullname$\",\n"
" \"$name$\",\n"
" \"$cname$\",\n"
" \"$package$\",\n"
" $n_methods$,\n"
" $lcfullname$__method_descriptors,\n"
" $lcfullname$__method_indices_by_name\n"
"};\n");
}
delete[] mi_array;
}
void ServiceGenerator::GenerateCallersImplementations(io::Printer* printer)
{
for (int i = 0; i < descriptor_->method_count(); i++) {
const MethodDescriptor *method = descriptor_->method(i);
string lcname = CamelToLower(method->name());
string lcfullname = FullNameToLower(descriptor_->full_name());
vars_["method"] = lcname;
vars_["metpad"] = ConvertToSpaces(lcname);
vars_["input_typename"] = FullNameToC(method->input_type()->full_name());
vars_["output_typename"] = FullNameToC(method->output_type()->full_name());
vars_["padddddddddddddddddd"] = ConvertToSpaces(lcfullname + "__" + lcname);
vars_["index"] = SimpleItoa(i);
printer->Print(vars_,
"void $lcfullname$__$method$(ProtobufCService *service,\n"
" $padddddddddddddddddd$ const $input_typename$ *input,\n"
" $padddddddddddddddddd$ $output_typename$_Closure closure,\n"
" $padddddddddddddddddd$ void *closure_data)\n"
"{\n"
" assert(service->descriptor == &$lcfullname$__descriptor);\n"
" service->invoke(service, $index$, (const ProtobufCMessage *) input, (ProtobufCClosure) closure, closure_data);\n"
"}\n");
}
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,112 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_SERVICE_H__
#define GOOGLE_PROTOBUF_COMPILER_C_SERVICE_H__
#include <map>
#include <string>
#include <google/protobuf/descriptor.h>
namespace google {
namespace protobuf {
namespace io {
class Printer; // printer.h
}
}
namespace protobuf {
namespace compiler {
namespace c {
class ServiceGenerator {
public:
// See generator.cc for the meaning of dllexport_decl.
explicit ServiceGenerator(const ServiceDescriptor* descriptor,
const string& dllexport_decl);
~ServiceGenerator();
// Header stuff.
void GenerateMainHFile(io::Printer* printer);
void GenerateVfuncs(io::Printer* printer);
void GenerateInitMacros(io::Printer* printer);
void GenerateDescriptorDeclarations(io::Printer* printer);
void GenerateCallersDeclarations(io::Printer* printer);
// Source file stuff.
void GenerateCFile(io::Printer* printer);
void GenerateServiceDescriptor(io::Printer* printer);
void GenerateInit(io::Printer* printer);
void GenerateCallersImplementations(io::Printer* printer);
const ServiceDescriptor* descriptor_;
std::map<string, string> vars_;
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(ServiceGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_SERVICE_H__

View File

@ -0,0 +1,151 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#include <protoc-c/c_string_field.h>
#include <protoc-c/c_helpers.h>
#include <google/protobuf/io/printer.h>
#include <google/protobuf/wire_format.h>
#include <google/protobuf/descriptor.pb.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
using internal::WireFormat;
void SetStringVariables(const FieldDescriptor* descriptor,
std::map<string, string>* variables) {
(*variables)["name"] = FieldName(descriptor);
(*variables)["default"] = FullNameToLower(descriptor->full_name())
+ "__default_value";
(*variables)["deprecated"] = FieldDeprecated(descriptor);
}
// ===================================================================
StringFieldGenerator::
StringFieldGenerator(const FieldDescriptor* descriptor)
: FieldGenerator(descriptor) {
SetStringVariables(descriptor, &variables_);
}
StringFieldGenerator::~StringFieldGenerator() {}
void StringFieldGenerator::GenerateStructMembers(io::Printer* printer) const
{
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
case FieldDescriptor::LABEL_OPTIONAL:
printer->Print(variables_, "char *$name$$deprecated$;\n");
break;
case FieldDescriptor::LABEL_REPEATED:
printer->Print(variables_, "size_t n_$name$$deprecated$;\n");
printer->Print(variables_, "char **$name$$deprecated$;\n");
break;
}
}
void StringFieldGenerator::GenerateDefaultValueDeclarations(io::Printer* printer) const
{
printer->Print(variables_, "extern char $default$[];\n");
}
void StringFieldGenerator::GenerateDefaultValueImplementations(io::Printer* printer) const
{
std::map<string, string> vars;
vars["default"] = variables_.find("default")->second;
vars["escaped"] = CEscape(descriptor_->default_value_string());
printer->Print(vars, "char $default$[] = \"$escaped$\";\n");
}
string StringFieldGenerator::GetDefaultValue(void) const
{
return variables_.find("default")->second;
}
void StringFieldGenerator::GenerateStaticInit(io::Printer* printer) const
{
std::map<string, string> vars;
if (descriptor_->has_default_value()) {
vars["default"] = GetDefaultValue();
} else if (FieldSyntax(descriptor_) == 2) {
vars["default"] = "NULL";
} else {
vars["default"] = "(char *)protobuf_c_empty_string";
}
switch (descriptor_->label()) {
case FieldDescriptor::LABEL_REQUIRED:
case FieldDescriptor::LABEL_OPTIONAL:
printer->Print(vars, "$default$");
break;
case FieldDescriptor::LABEL_REPEATED:
printer->Print(vars, "0,NULL");
break;
}
}
void StringFieldGenerator::GenerateDescriptorInitializer(io::Printer* printer) const
{
GenerateDescriptorInitializerGeneric(printer, false, "STRING", "NULL");
}
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google

View File

@ -0,0 +1,100 @@
// Protocol Buffers - Google's data interchange format
// Copyright 2008 Google Inc. All rights reserved.
// http://code.google.com/p/protobuf/
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
// * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Author: kenton@google.com (Kenton Varda)
// Based on original Protocol Buffers design by
// Sanjay Ghemawat, Jeff Dean, and others.
// Copyright (c) 2008-2013, Dave Benson. All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
// * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//
// * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
// Modified to implement C code by Dave Benson.
#ifndef GOOGLE_PROTOBUF_COMPILER_C_STRING_FIELD_H__
#define GOOGLE_PROTOBUF_COMPILER_C_STRING_FIELD_H__
#include <map>
#include <string>
#include <protoc-c/c_field.h>
namespace google {
namespace protobuf {
namespace compiler {
namespace c {
class StringFieldGenerator : public FieldGenerator {
public:
explicit StringFieldGenerator(const FieldDescriptor* descriptor);
~StringFieldGenerator();
// implements FieldGenerator ---------------------------------------
void GenerateStructMembers(io::Printer* printer) const;
void GenerateDescriptorInitializer(io::Printer* printer) const;
void GenerateDefaultValueDeclarations(io::Printer* printer) const;
void GenerateDefaultValueImplementations(io::Printer* printer) const;
string GetDefaultValue(void) const;
void GenerateStaticInit(io::Printer* printer) const;
private:
std::map<string, string> variables_;
GOOGLE_DISALLOW_EVIL_CONSTRUCTORS(StringFieldGenerator);
};
} // namespace c
} // namespace compiler
} // namespace protobuf
} // namespace google
#endif // GOOGLE_PROTOBUF_COMPILER_C_STRING_FIELD_H__

View File

@ -0,0 +1,22 @@
#include <string>
#include <google/protobuf/compiler/plugin.h>
#include <google/protobuf/compiler/command_line_interface.h>
#include <protoc-c/c_generator.h>
int main(int argc, char* argv[]) {
google::protobuf::compiler::c::CGenerator c_generator;
std::string invocation_name = argv[0];
std::string invocation_basename = invocation_name.substr(invocation_name.find_last_of("/") + 1);
const std::string legacy_name = "protoc-c";
if (invocation_basename == legacy_name) {
google::protobuf::compiler::CommandLineInterface cli;
cli.RegisterGenerator("--c_out", &c_generator, "Generate C/H files.");
cli.SetVersionInfo(PACKAGE_STRING);
return cli.Run(argc, argv);
}
return google::protobuf::compiler::PluginMain(argc, argv, &c_generator);
}

View File

@ -0,0 +1,38 @@
There are two tests.
"test-generated-code" is a simple test that can easily be adapted.
"test-generated-code2" is a comprehensive test.
--
If you have a quick problem, hack at "test-generated-code";
but i don't want that file to be too hard to navigate,
so you must eventually add a test to "test-generated-code2".
I appreciate additional test cases!
Please submit them as issues in the tracking system, or email me.
--
Here are the files involved in each test:
test.proto Protobuf declarations for the simple test.
test.pb-c.c Protobuf-C generated code based on test.proto
test.pb-c.h Protobuf-C generated code based on test.proto
test-full.proto Protobuf declarations for the exhaustive test.
test-full.pb-c.c Protobuf-C generated code based on test-full.proto
test-full.pb-c.h Protobuf-C generated code based on test-full.proto
test-full.pb.cc Protobuf (C++) generated code based on test-full.proto
test-full.pb.h Protobuf (C++) generated code based on test-full.proto
generated-code/
test-generated-code.c Actual test code.
test-generated-code Test executable.
generated-code2/
cxx-generate-packed-data.cc C++ code to generated data to compare with C.
cxx-generate-packed-data Program whichs generates data (using C++ api)
test-full-cxx-output.inc Output of cxx-generate-packed-data.
test-generated-code2.c Actual test code.
test-generated-code2 Test executable.

View File

@ -0,0 +1,71 @@
#ifdef PROTO3
#include "t/test-proto3.pb-c.h"
#else
#include "t/test.pb-c.h"
#endif
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
int main(void)
{
Foo__Person__PhoneNumber__Comment comment = FOO__PERSON__PHONE_NUMBER__COMMENT__INIT;
Foo__Person__PhoneNumber phone = FOO__PERSON__PHONE_NUMBER__INIT;
Foo__Person__PhoneNumber *phone_numbers[1];
Foo__Person person = FOO__PERSON__INIT;
Foo__Person *person2;
unsigned char simple_pad[8];
size_t size, size2;
unsigned char *packed;
ProtobufCBufferSimple bs = PROTOBUF_C_BUFFER_SIMPLE_INIT (simple_pad);
comment.comment = "protobuf-c guy";
phone.number = "1234";
#ifndef PROTO3
phone.has_type = 1;
#endif
phone.type = FOO__PERSON__PHONE_TYPE__WORK;
phone.comment = &comment;
phone_numbers[0] = &phone;
person.name = "dave b";
person.id = 42;
person.n_phone = 1;
person.phone = phone_numbers;
size = foo__person__get_packed_size (&person);
packed = malloc (size);
assert (packed);
size2 = foo__person__pack (&person, packed);
assert (size == size2);
foo__person__pack_to_buffer (&person, &bs.base);
assert (bs.len == size);
assert (memcmp (bs.data, packed, size) == 0);
PROTOBUF_C_BUFFER_SIMPLE_CLEAR (&bs);
person2 = foo__person__unpack (NULL, size, packed);
assert (person2 != NULL);
assert (person2->id == 42);
#ifndef PROTO3
assert (person2->email == NULL);
#else
assert (strcmp (person2->email, "") == 0);
#endif
assert (strcmp (person2->name, "dave b") == 0);
assert (person2->n_phone == 1);
assert (strcmp (person2->phone[0]->number, "1234") == 0);
assert (person2->phone[0]->type == FOO__PERSON__PHONE_TYPE__WORK);
assert (strcmp (person2->phone[0]->comment->comment, "protobuf-c guy") == 0);
foo__person__free_unpacked (person2, NULL);
free (packed);
printf ("test succeeded.\n");
return 0;
}

View File

@ -0,0 +1,62 @@
/* data included from the c++ packed-data generator,
and from the c test code. */
#define THOUSAND 1000
#define MILLION 1000000
#define BILLION 1000000000LL
#define TRILLION 1000000000000LL
#define QUADRILLION 1000000000000000LL
#define QUINTILLION 1000000000000000000LL
int32_t int32_arr0[2] = { -1, 1 };
int32_t int32_arr1[5] = { 42, 666, -1123123, 0, 47 };
int32_t int32_arr_min_max[2] = { INT32_MIN, INT32_MAX };
uint32_t uint32_roundnumbers[4] = { BILLION, MILLION, 1, 0 };
uint32_t uint32_0_max[2] = { 0, UINT32_MAX };
int64_t int64_roundnumbers[15] = { -QUINTILLION, -QUADRILLION, -TRILLION,
-BILLION, -MILLION, -THOUSAND,
1,
THOUSAND, MILLION, BILLION,
TRILLION, QUADRILLION, QUINTILLION };
int64_t int64_min_max[2] = { INT64_MIN, INT64_MAX };
uint64_t uint64_roundnumbers[9] = { 1,
THOUSAND, MILLION, BILLION,
TRILLION, QUADRILLION, QUINTILLION };
uint64_t uint64_0_1_max[3] = { 0, 1, UINT64_MAX };
uint64_t uint64_random[] = {0,
666,
4200000000ULL,
16ULL * (uint64_t) QUINTILLION + 33 };
#define FLOATING_POINT_RANDOM \
-1000.0, -100.0, -42.0, 0, 666, 131313
float float_random[] = { FLOATING_POINT_RANDOM };
double double_random[] = { FLOATING_POINT_RANDOM };
protobuf_c_boolean boolean_0[] = {0 };
protobuf_c_boolean boolean_1[] = {1 };
protobuf_c_boolean boolean_random[] = {0,1,1,0,0,1,1,1,0,0,0,0,0,1,1,1,1,1,1,0,1,1,0,1,1,0 };
TEST_ENUM_SMALL_TYPE_NAME enum_small_0[] = { TEST_ENUM_SMALL(VALUE) };
TEST_ENUM_SMALL_TYPE_NAME enum_small_1[] = { TEST_ENUM_SMALL(OTHER_VALUE) };
#define T(v) (TEST_ENUM_SMALL_TYPE_NAME)(v)
TEST_ENUM_SMALL_TYPE_NAME enum_small_random[] = {T(0),T(1),T(1),T(0),T(0),T(1),T(1),T(1),T(0),T(0),T(0),T(0),T(0),T(1),T(1),T(1),T(1),T(1),T(1),T(0),T(1),T(1),T(0),T(1),T(1),T(0) };
#undef T
#define T(v) (TEST_ENUM_TYPE_NAME)(v)
TEST_ENUM_TYPE_NAME enum_0[] = { T(0) };
TEST_ENUM_TYPE_NAME enum_1[] = { T(1) };
TEST_ENUM_TYPE_NAME enum_random[] = {
T(0), T(268435455), T(127), T(16384), T(16383),
T(2097152), T(2097151), T(128), T(268435456),
T(0), T(2097152), T(268435455), T(127), T(16383), T(16384) };
#undef T
char *repeated_strings_0[] = { (char*)"onestring" };
char *repeated_strings_1[] = { (char*)"two", (char*)"string" };
char *repeated_strings_2[] = { (char*)"many", (char*)"tiny", (char*)"little", (char*)"strings", (char*)"should", (char*)"be", (char*)"handled" };
char *repeated_strings_3[] = { (char*)"one very long strings XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX" };

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1 @@
issue220

View File

@ -0,0 +1,13 @@
#include <assert.h>
#include <stdlib.h>
#include <limits.h>
#include "t/issue220/issue220.pb-c.h"
int main(void)
{
assert(_MESSAGE_TYPE1__FLAG_IS_INT_SIZE == INT_MAX);
assert(_MESSAGE_TYPE2__ANOTHER_FLAG_IS_INT_SIZE == INT_MAX);
assert(_TOP_LEVEL__SUBMESSAGES_IS_INT_SIZE == INT_MAX);
return EXIT_SUCCESS;
}

View File

@ -0,0 +1,20 @@
message TopLevel {
oneof submessages {
MessageType1 type1 = 1;
MessageType2 type2 = 2;
}
}
message MessageType1 {
enum Flag {
OK = 1;
}
optional Flag flag = 1;
}
message MessageType2 {
enum AnotherFlag {
OK = 1;
}
optional AnotherFlag flag = 1;
}

View File

@ -0,0 +1 @@
issue251

View File

@ -0,0 +1,12 @@
#include <stdlib.h>
#include "t/issue251/issue251.pb-c.h"
int main(void)
{
/*
* The problem in #251 caused invalid code to be generated in the
* .pb-c.h file, so there's nothing for us to do here.
*/
return EXIT_SUCCESS;
}

View File

@ -0,0 +1,11 @@
message two_oneofs {
oneof first_oneof {
bool a = 10;
bool b = 11;
}
oneof second_oneof {
bool c = 20;
bool d = 21;
}
}

View File

@ -0,0 +1,415 @@
package foo;
message SubMess {
required int32 test = 4;
optional int32 val1 = 6;
optional int32 val2 = 7;
repeated int32 rep = 8;
message SubSubMess {
optional int32 val1 = 1 [default = 100];
repeated int32 rep = 4;
optional bytes bytes1 = 2 [default = "a \0 char"];
optional string str1 = 3 [default = "hello world\n"];
}
optional SubSubMess sub1 = 9;
optional SubSubMess sub2 = 10;
};
enum TestEnumSmall {
NEG_VALUE = -1;
VALUE = 0;
OTHER_VALUE = 1;
}
// these number are specifically chosen to test the
// boundaries of when an enum requires a certain number of bytes.
// e.g. 16383 requires 3 bytes; 16384 requires 4.
enum TestEnum {
VALUENEG123456 = -123456;
VALUENEG1 = -1;
VALUE0 = 0;
VALUE1 = 1;
VALUE127 = 127;
VALUE128 = 128;
VALUE16383 = 16383;
VALUE16384 = 16384;
VALUE2097151 = 2097151;
VALUE2097152 = 2097152;
VALUE268435455 = 268435455;
VALUE268435456 = 268435456;
}
enum TestEnumDupValues {
VALUE_A = 42;
VALUE_B = 42;
VALUE_C = 42;
VALUE_D = 666;
VALUE_E = 666;
VALUE_F = 1000;
VALUE_AA = 1000;
VALUE_BB = 1001;
option allow_alias = true;
}
message TestFieldNo15 { // should use 1 byte header
required string test = 15;
}
message TestFieldNo16 { // requires 2 byte header
required string test = 16;
}
message TestFieldNo2047 { // should use 2 byte header
required string test = 2047;
}
message TestFieldNo2048 { // requires 3 byte header
required string test = 2048;
}
message TestFieldNo262143 { // should use 3 byte header
required string test = 262143;
}
message TestFieldNo262144 { // requires 4 byte header
required string test = 262144;
}
message TestFieldNo33554431 { // should use 4 byte header
required string test = 33554431;
}
message TestFieldNo33554432 { // requires 5 byte header
required string test = 33554432;
}
message TestMess {
repeated int32 test_int32 = 1;
repeated sint32 test_sint32 = 2;
repeated sfixed32 test_sfixed32 = 3;
repeated int64 test_int64 = 4;
repeated sint64 test_sint64 = 5;
repeated sfixed64 test_sfixed64 = 6;
repeated uint32 test_uint32 = 7;
repeated fixed32 test_fixed32 = 8;
repeated uint64 test_uint64 = 9;
repeated fixed64 test_fixed64 = 10;
repeated float test_float = 11;
repeated double test_double = 12;
repeated bool test_boolean = 13;
repeated TestEnumSmall test_enum_small = 14;
repeated TestEnum test_enum = 15;
repeated string test_string = 16;
repeated bytes test_bytes = 17;
repeated SubMess test_message = 18;
}
message TestMessPacked {
repeated int32 test_int32 = 1 [packed=true];
repeated sint32 test_sint32 = 2 [packed=true];
repeated sfixed32 test_sfixed32 = 3 [packed=true];
repeated int64 test_int64 = 4 [packed=true];
repeated sint64 test_sint64 = 5 [packed=true];
repeated sfixed64 test_sfixed64 = 6 [packed=true];
repeated uint32 test_uint32 = 7 [packed=true];
repeated fixed32 test_fixed32 = 8 [packed=true];
repeated uint64 test_uint64 = 9 [packed=true];
repeated fixed64 test_fixed64 = 10 [packed=true];
repeated float test_float = 11 [packed=true];
repeated double test_double = 12 [packed=true];
repeated bool test_boolean = 13 [packed=true];
repeated TestEnumSmall test_enum_small = 14 [packed=true];
repeated TestEnum test_enum = 15 [packed=true];
}
message TestMessOptional {
optional int32 test_int32 = 1;
optional sint32 test_sint32 = 2;
optional sfixed32 test_sfixed32 = 3;
optional int64 test_int64 = 4;
optional sint64 test_sint64 = 5;
optional sfixed64 test_sfixed64 = 6;
optional uint32 test_uint32 = 7;
optional fixed32 test_fixed32 = 8;
optional uint64 test_uint64 = 9;
optional fixed64 test_fixed64 = 10;
optional float test_float = 11;
optional double test_double = 12;
optional bool test_boolean = 13;
optional TestEnumSmall test_enum_small = 14;
optional TestEnum test_enum = 15;
optional string test_string = 16;
optional bytes test_bytes = 17;
optional SubMess test_message = 18;
}
message TestMessOneof {
oneof test_oneof {
int32 test_int32 = 1;
sint32 test_sint32 = 2;
sfixed32 test_sfixed32 = 3;
int64 test_int64 = 4;
sint64 test_sint64 = 5;
sfixed64 test_sfixed64 = 6;
uint32 test_uint32 = 7;
fixed32 test_fixed32 = 8;
uint64 test_uint64 = 9;
fixed64 test_fixed64 = 10;
float test_float = 11;
double test_double = 12;
bool test_boolean = 13;
TestEnumSmall test_enum_small = 14;
TestEnum test_enum = 15;
string test_string = 16;
bytes test_bytes = 17;
SubMess test_message = 18;
}
optional int32 opt_int = 19;
}
message TestMessRequiredInt32 {
required int32 test = 42;
}
message TestMessRequiredSInt32 {
required sint32 test = 43;
}
message TestMessRequiredSFixed32 {
required sfixed32 test = 100;
}
message TestMessRequiredInt64 {
required int64 test = 1;
}
message TestMessRequiredSInt64 {
required sint64 test = 11;
}
message TestMessRequiredSFixed64 {
required sfixed64 test = 12;
}
message TestMessRequiredUInt32 {
required uint32 test = 1;
}
message TestMessRequiredFixed32 {
required fixed32 test = 1;
}
message TestMessRequiredUInt64 {
required uint64 test = 1;
}
message TestMessRequiredFixed64 {
required fixed64 test = 1;
}
message TestMessRequiredFloat {
required float test = 1;
}
message TestMessRequiredDouble {
required double test = 1;
}
message TestMessRequiredBool {
required bool test = 1;
}
message TestMessRequiredEnum {
required TestEnum test = 1;
}
message TestMessRequiredEnumSmall {
required TestEnumSmall test = 1;
}
message TestMessRequiredString {
required string test = 1;
}
message TestMessRequiredBytes {
required bytes test = 1;
}
message TestMessRequiredMessage {
required SubMess test = 1;
}
message EmptyMess {
}
message DefaultRequiredValues {
required int32 v_int32 = 1 [default = -42];
required uint32 v_uint32 = 2 [default = 666];
required int32 v_int64 = 3 [default = 100000];
required uint32 v_uint64 = 4 [default = 100001];
required float v_float = 5 [default = 2.5];
required double v_double = 6 [default = 4.5];
required string v_string = 7 [default = "hi mom\n"];
required bytes v_bytes = 8 [default = "a \0 character"];
}
message DefaultOptionalValues {
optional int32 v_int32 = 1 [default = -42];
optional uint32 v_uint32 = 2 [default = 666];
optional int32 v_int64 = 3 [default = 100000];
optional uint32 v_uint64 = 4 [default = 100001];
optional float v_float = 5 [default = 2.5];
optional double v_double = 6 [default = 4.5];
optional string v_string = 7 [default = "hi mom\n"];
optional bytes v_bytes = 8 [default = "a \0 character"];
}
message LowerCase {
enum CaseEnum {
UPPER = 1;
lower = 2;
}
optional CaseEnum value = 1 [default = lower];
}
message AllocValues {
optional bytes o_bytes = 1;
repeated string r_string = 2;
required string a_string = 3;
required bytes a_bytes = 4;
required DefaultRequiredValues a_mess = 5;
}
message TestRequiredFieldsBitmap {
required string field1 = 1;
optional string field2 = 2;
optional string field3 = 3;
optional string field4 = 4;
optional string field5 = 5;
optional string field6 = 6;
optional string field7 = 7;
optional string field8 = 8;
optional string field9 = 9;
optional string field10 = 10;
optional string field11 = 11;
optional string field12 = 12;
optional string field13 = 13;
optional string field14 = 14;
optional string field15 = 15;
optional string field16 = 16;
optional string field17 = 17;
optional string field18 = 18;
optional string field19 = 19;
optional string field20 = 20;
optional string field21 = 21;
optional string field22 = 22;
optional string field23 = 23;
optional string field24 = 24;
optional string field25 = 25;
optional string field26 = 26;
optional string field27 = 27;
optional string field28 = 28;
optional string field29 = 29;
optional string field30 = 30;
optional string field31 = 31;
optional string field32 = 32;
optional string field33 = 33;
optional string field34 = 34;
optional string field35 = 35;
optional string field36 = 36;
optional string field37 = 37;
optional string field38 = 38;
optional string field39 = 39;
optional string field40 = 40;
optional string field41 = 41;
optional string field42 = 42;
optional string field43 = 43;
optional string field44 = 44;
optional string field45 = 45;
optional string field46 = 46;
optional string field47 = 47;
optional string field48 = 48;
optional string field49 = 49;
optional string field50 = 50;
optional string field51 = 51;
optional string field52 = 52;
optional string field53 = 53;
optional string field54 = 54;
optional string field55 = 55;
optional string field56 = 56;
optional string field57 = 57;
optional string field58 = 58;
optional string field59 = 59;
optional string field60 = 60;
optional string field61 = 61;
optional string field62 = 62;
optional string field63 = 63;
optional string field64 = 64;
optional string field65 = 65;
optional string field66 = 66;
optional string field67 = 67;
optional string field68 = 68;
optional string field69 = 69;
optional string field70 = 70;
optional string field71 = 71;
optional string field72 = 72;
optional string field73 = 73;
optional string field74 = 74;
optional string field75 = 75;
optional string field76 = 76;
optional string field77 = 77;
optional string field78 = 78;
optional string field79 = 79;
optional string field80 = 80;
optional string field81 = 81;
optional string field82 = 82;
optional string field83 = 83;
optional string field84 = 84;
optional string field85 = 85;
optional string field86 = 86;
optional string field87 = 87;
optional string field88 = 88;
optional string field89 = 89;
optional string field90 = 90;
optional string field91 = 91;
optional string field92 = 92;
optional string field93 = 93;
optional string field94 = 94;
optional string field95 = 95;
optional string field96 = 96;
optional string field97 = 97;
optional string field98 = 98;
optional string field99 = 99;
optional string field100 = 100;
optional string field101 = 101;
optional string field102 = 102;
optional string field103 = 103;
optional string field104 = 104;
optional string field105 = 105;
optional string field106 = 106;
optional string field107 = 107;
optional string field108 = 108;
optional string field109 = 109;
optional string field110 = 110;
optional string field111 = 111;
optional string field112 = 112;
optional string field113 = 113;
optional string field114 = 114;
optional string field115 = 115;
optional string field116 = 116;
optional string field117 = 117;
optional string field118 = 118;
optional string field119 = 119;
optional string field120 = 120;
optional string field121 = 121;
optional string field122 = 122;
optional string field123 = 123;
optional string field124 = 124;
optional string field125 = 125;
optional string field126 = 126;
optional string field127 = 127;
optional string field128 = 128;
required string field129 = 129;
}
message TestFieldFlags {
optional int32 no_flags1 = 1;
required int32 no_flags2 = 2;
repeated int32 no_flags3 = 3;
repeated int32 packed = 4 [packed=true];
repeated int32 packed_deprecated = 5 [packed=true, deprecated=true];
repeated int32 deprecated = 6 [deprecated=true];
}
message TestMessageCheck {
message SubMessage {
required string str = 1;
}
required SubMessage required_msg = 1;
repeated SubMessage repeated_msg = 2;
optional SubMessage optional_msg = 3;
required string required_string = 4;
repeated string repeated_string = 5;
optional string optional_string = 6;
required bytes required_bytes = 7;
repeated bytes repeated_bytes = 8;
optional bytes optional_bytes = 9;
}
message TestMessSubMess {
required TestMess rep_mess = 1;
required TestMessOptional opt_mess = 2;
required TestMessOneof oneof_mess = 3;
required SubMess req_mess = 4;
required DefaultOptionalValues def_mess = 5;
}

View File

@ -0,0 +1,13 @@
package foo;
option optimize_for = CODE_SIZE;
enum TestEnumLite {
LITE = 0;
LITE1 = 1;
}
message TestMessLite {
required int32 field1 = 1;
required TestEnumLite field2 = 2;
}

View File

@ -0,0 +1,40 @@
syntax = "proto3";
package foo;
message Person {
string name = 1;
int32 id = 2;
string email = 3;
enum PhoneType {
MOBILE = 0;
HOME = 1;
WORK = 2;
}
message PhoneNumber {
message Comment {
string comment = 1;
}
string number = 1;
PhoneType type = 2;
Comment comment = 3;
}
repeated PhoneNumber phone = 4;
}
message LookupResult
{
Person person = 1;
}
message Name {
string name = 1;
};
service DirLookup {
rpc ByName (Name) returns (LookupResult);
}

View File

@ -0,0 +1,38 @@
package foo;
message Person {
required string name = 1;
required int32 id = 2;
optional string email = 3;
enum PhoneType {
MOBILE = 0;
HOME = 1;
WORK = 2;
}
message PhoneNumber {
message Comment {
required string comment = 1;
}
required string number = 1;
optional PhoneType type = 2 [default = HOME];
optional Comment comment = 3;
}
repeated PhoneNumber phone = 4;
}
message LookupResult
{
optional Person person = 1;
}
message Name {
optional string name = 1;
};
service DirLookup {
rpc ByName (Name) returns (LookupResult);
}

View File

@ -0,0 +1,56 @@
/*
* Copyright (c) 2014, The protobuf-c authors.
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above
* copyright notice, this list of conditions and the following disclaimer
* in the documentation and/or other materials provided with the
* distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
* LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
* A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
* OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
* SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "protobuf-c.h"
int
main(int argc, char **argv)
{
printf("PACKAGE_VERSION = %s\n",
PACKAGE_VERSION);
printf("PROTOBUF_C_VERSION = %s\n",
PROTOBUF_C_VERSION);
printf("PROTOBUF_C_VERSION_NUMBER = %d\n",
PROTOBUF_C_VERSION_NUMBER);
printf("protobuf_c_version() = %s\n",
protobuf_c_version());
printf("protobuf_c_version_number() = %d\n",
protobuf_c_version_number());
assert(strcmp(PACKAGE_VERSION, PROTOBUF_C_VERSION) == 0);
assert(strcmp(PROTOBUF_C_VERSION, protobuf_c_version()) == 0);
assert(PROTOBUF_C_VERSION_NUMBER == protobuf_c_version_number());
return EXIT_SUCCESS;
}