aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorFeng Xiao <xfxyjwf@gmail.com>2015-06-12 14:56:02 -0700
committerFeng Xiao <xfxyjwf@gmail.com>2015-06-12 14:56:02 -0700
commit54a4cccb97e9314fbe7eeb5ccd603feb842167c1 (patch)
tree8c99d768e20da9c4306dcabfcfbe92ada46569c4
parent68c8762b981a2bbd2b7df3c5565b32ba014c3e34 (diff)
parent2fe6d7bc5773b6888d0db80eca75e392b3549814 (diff)
downloadprotobuf-54a4cccb97e9314fbe7eeb5ccd603feb842167c1.tar.gz
protobuf-54a4cccb97e9314fbe7eeb5ccd603feb842167c1.tar.bz2
protobuf-54a4cccb97e9314fbe7eeb5ccd603feb842167c1.zip
Merge pull request #481 from Qartar/master
Workaround for MSVC's string literal compiler limit.
-rw-r--r--cmake/tests.cmake1
-rw-r--r--src/Makefile.am6
-rw-r--r--src/google/protobuf/compiler/cpp/cpp_file.cc58
-rw-r--r--src/google/protobuf/compiler/cpp/cpp_unittest.cc12
4 files changed, 62 insertions, 15 deletions
diff --git a/cmake/tests.cmake b/cmake/tests.cmake
index 24891521..8fb5eef1 100644
--- a/cmake/tests.cmake
+++ b/cmake/tests.cmake
@@ -25,6 +25,7 @@ set(tests_protos
google/protobuf/unittest_drop_unknown_fields.proto
google/protobuf/unittest_embed_optimize_for.proto
google/protobuf/unittest_empty.proto
+ google/protobuf/unittest_enormous_descriptor.proto
google/protobuf/unittest_import.proto
google/protobuf/unittest_import_public.proto
google/protobuf/unittest_lite_imports_nonlite.proto
diff --git a/src/Makefile.am b/src/Makefile.am
index 6affcbf4..7d3a5945 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -412,6 +412,7 @@ protoc_inputs = \
google/protobuf/unittest_drop_unknown_fields.proto \
google/protobuf/unittest_embed_optimize_for.proto \
google/protobuf/unittest_empty.proto \
+ google/protobuf/unittest_enormous_descriptor.proto \
google/protobuf/unittest_import_lite.proto \
google/protobuf/unittest_import.proto \
google/protobuf/unittest_import_public_lite.proto \
@@ -453,8 +454,7 @@ EXTRA_DIST = \
google/protobuf/compiler/ruby/ruby_generated_code.proto \
google/protobuf/compiler/ruby/ruby_generated_code.rb \
google/protobuf/compiler/package_info.h \
- google/protobuf/compiler/zip_output_unittest.sh \
- google/protobuf/unittest_enormous_descriptor.proto
+ google/protobuf/compiler/zip_output_unittest.sh
protoc_lite_outputs = \
google/protobuf/map_lite_unittest.pb.cc \
@@ -486,6 +486,8 @@ protoc_outputs = \
google/protobuf/unittest_embed_optimize_for.pb.h \
google/protobuf/unittest_empty.pb.cc \
google/protobuf/unittest_empty.pb.h \
+ google/protobuf/unittest_enormous_descriptor.pb.cc \
+ google/protobuf/unittest_enormous_descriptor.pb.h \
google/protobuf/unittest_import.pb.cc \
google/protobuf/unittest_import.pb.h \
google/protobuf/unittest_import_public.pb.cc \
diff --git a/src/google/protobuf/compiler/cpp/cpp_file.cc b/src/google/protobuf/compiler/cpp/cpp_file.cc
index b997a51a..1f0a8205 100644
--- a/src/google/protobuf/compiler/cpp/cpp_file.cc
+++ b/src/google/protobuf/compiler/cpp/cpp_file.cc
@@ -434,20 +434,52 @@ void FileGenerator::GenerateBuildDescriptors(io::Printer* printer) {
string file_data;
file_proto.SerializeToString(&file_data);
- printer->Print(
- "::google::protobuf::DescriptorPool::InternalAddGeneratedFile(");
-
- // Only write 40 bytes per line.
- static const int kBytesPerLine = 40;
- for (int i = 0; i < file_data.size(); i += kBytesPerLine) {
- printer->Print("\n \"$data$\"",
- "data",
- EscapeTrigraphs(
- CEscape(file_data.substr(i, kBytesPerLine))));
+ // Workaround for MSVC: "Error C1091: compiler limit: string exceeds 65535
+ // bytes in length". Declare a static array of characters rather than use a
+ // string literal.
+ if (file_data.size() > 65535) {
+ printer->Print(
+ "static const char descriptor[] = {\n");
+ printer->Indent();
+
+ // Only write 25 bytes per line.
+ static const int kBytesPerLine = 25;
+ for (int i = 0; i < file_data.size();) {
+ for (int j = 0; j < kBytesPerLine && i < file_data.size(); ++i, ++j) {
+ printer->Print(
+ "$char$, ",
+ "char", SimpleItoa(file_data[i]));
+ }
+ printer->Print(
+ "\n");
+ }
+
+ printer->Outdent();
+ printer->Print(
+ "};\n");
+
+ printer->Print(
+ "::google::protobuf::DescriptorPool::InternalAddGeneratedFile(descriptor, $size$);\n",
+ "size", SimpleItoa(file_data.size()));
+
+ } else {
+
+ printer->Print(
+ "::google::protobuf::DescriptorPool::InternalAddGeneratedFile(");
+
+ // Only write 40 bytes per line.
+ static const int kBytesPerLine = 40;
+ for (int i = 0; i < file_data.size(); i += kBytesPerLine) {
+ printer->Print("\n \"$data$\"",
+ "data",
+ EscapeTrigraphs(
+ CEscape(file_data.substr(i, kBytesPerLine))));
+ }
+ printer->Print(
+ ", $size$);\n",
+ "size", SimpleItoa(file_data.size()));
+
}
- printer->Print(
- ", $size$);\n",
- "size", SimpleItoa(file_data.size()));
// Call MessageFactory::InternalRegisterGeneratedFile().
printer->Print(
diff --git a/src/google/protobuf/compiler/cpp/cpp_unittest.cc b/src/google/protobuf/compiler/cpp/cpp_unittest.cc
index b11fb21a..bd1c0fde 100644
--- a/src/google/protobuf/compiler/cpp/cpp_unittest.cc
+++ b/src/google/protobuf/compiler/cpp/cpp_unittest.cc
@@ -55,6 +55,7 @@
#include <google/protobuf/unittest.pb.h>
#include <google/protobuf/unittest_optimize_for.pb.h>
#include <google/protobuf/unittest_embed_optimize_for.pb.h>
+#include <google/protobuf/unittest_enormous_descriptor.pb.h>
#include <google/protobuf/unittest_no_generic_services.pb.h>
#include <google/protobuf/test_util.h>
#include <google/protobuf/compiler/cpp/cpp_helpers.h>
@@ -130,6 +131,17 @@ TEST(GeneratedDescriptorTest, IdenticalDescriptors) {
generated_decsriptor_proto.DebugString());
}
+// Test that generated code has proper descriptors:
+// Touch a descriptor generated from an enormous message to validate special
+// handling for descriptors exceeding the C++ standard's recommended minimum
+// limit for string literal size
+TEST(GeneratedDescriptorTest, EnormousDescriptor) {
+ const Descriptor* generated_descriptor =
+ TestEnormousDescriptor::descriptor();
+
+ EXPECT_TRUE(generated_descriptor != NULL);
+}
+
#endif // !PROTOBUF_TEST_NO_DESCRIPTORS
// ===================================================================