OLD | NEW |
1 // Protocol Buffers - Google's data interchange format | 1 // Protocol Buffers - Google's data interchange format |
2 // Copyright 2008 Google Inc. All rights reserved. | 2 // Copyright 2008 Google Inc. All rights reserved. |
3 // https://developers.google.com/protocol-buffers/ | 3 // https://developers.google.com/protocol-buffers/ |
4 // | 4 // |
5 // Redistribution and use in source and binary forms, with or without | 5 // Redistribution and use in source and binary forms, with or without |
6 // modification, are permitted provided that the following conditions are | 6 // modification, are permitted provided that the following conditions are |
7 // met: | 7 // met: |
8 // | 8 // |
9 // * Redistributions of source code must retain the above copyright | 9 // * Redistributions of source code must retain the above copyright |
10 // notice, this list of conditions and the following disclaimer. | 10 // notice, this list of conditions and the following disclaimer. |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
44 #include <google/protobuf/io/zero_copy_stream.h> | 44 #include <google/protobuf/io/zero_copy_stream.h> |
45 #include <google/protobuf/descriptor.pb.h> | 45 #include <google/protobuf/descriptor.pb.h> |
46 #include <google/protobuf/descriptor.h> | 46 #include <google/protobuf/descriptor.h> |
47 #include <google/protobuf/stubs/strutil.h> | 47 #include <google/protobuf/stubs/strutil.h> |
48 | 48 |
49 namespace google { | 49 namespace google { |
50 namespace protobuf { | 50 namespace protobuf { |
51 namespace compiler { | 51 namespace compiler { |
52 namespace java { | 52 namespace java { |
53 | 53 |
54 SharedCodeGenerator::SharedCodeGenerator(const FileDescriptor* file) | 54 SharedCodeGenerator::SharedCodeGenerator(const FileDescriptor* file, |
55 : name_resolver_(new ClassNameResolver), | 55 const Options& options) |
56 enforce_lite_(false), | 56 : name_resolver_(new ClassNameResolver), file_(file), options_(options) {} |
57 file_(file) {} | |
58 | 57 |
59 SharedCodeGenerator::~SharedCodeGenerator() { | 58 SharedCodeGenerator::~SharedCodeGenerator() { |
60 } | 59 } |
61 | 60 |
62 void SharedCodeGenerator::Generate(GeneratorContext* context, | 61 void SharedCodeGenerator::Generate(GeneratorContext* context, |
63 vector<string>* file_list) { | 62 std::vector<string>* file_list, |
| 63 std::vector<string>* annotation_file_list) { |
64 string java_package = FileJavaPackage(file_); | 64 string java_package = FileJavaPackage(file_); |
65 string package_dir = JavaPackageToDir(java_package); | 65 string package_dir = JavaPackageToDir(java_package); |
66 | 66 |
67 if (HasDescriptorMethods(file_, enforce_lite_)) { | 67 if (HasDescriptorMethods(file_, options_.enforce_lite)) { |
68 // Generate descriptors. | 68 // Generate descriptors. |
69 string classname = name_resolver_->GetDescriptorClassName(file_); | 69 string classname = name_resolver_->GetDescriptorClassName(file_); |
70 string filename = package_dir + classname + ".java"; | 70 string filename = package_dir + classname + ".java"; |
71 file_list->push_back(filename); | 71 file_list->push_back(filename); |
72 google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(context->Open(
filename)); | 72 google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> output(context->Open(
filename)); |
73 google::protobuf::scoped_ptr<io::Printer> printer(new io::Printer(output.get
(), '$')); | 73 GeneratedCodeInfo annotations; |
74 | 74 io::AnnotationProtoCollector<GeneratedCodeInfo> annotation_collector( |
| 75 &annotations); |
| 76 google::protobuf::scoped_ptr<io::Printer> printer( |
| 77 new io::Printer(output.get(), '$', |
| 78 options_.annotate_code ? &annotation_collector : NULL)); |
| 79 string info_relative_path = classname + ".java.pb.meta"; |
| 80 string info_full_path = filename + ".pb.meta"; |
75 printer->Print( | 81 printer->Print( |
76 "// Generated by the protocol buffer compiler. DO NOT EDIT!\n" | 82 "// Generated by the protocol buffer compiler. DO NOT EDIT!\n" |
77 "// source: $filename$\n" | 83 "// source: $filename$\n" |
78 "\n", | 84 "\n", |
79 "filename", file_->name()); | 85 "filename", file_->name()); |
80 if (!java_package.empty()) { | 86 if (!java_package.empty()) { |
81 printer->Print( | 87 printer->Print( |
82 "package $package$;\n" | 88 "package $package$;\n" |
83 "\n", | 89 "\n", |
84 "package", java_package); | 90 "package", java_package); |
85 } | 91 } |
| 92 PrintGeneratedAnnotation(printer.get(), '$', |
| 93 options_.annotate_code ? info_relative_path : ""); |
86 printer->Print( | 94 printer->Print( |
87 "public final class $classname$ {\n" | 95 "public final class $classname$ {\n" |
88 " public static com.google.protobuf.Descriptors.FileDescriptor\n" | 96 " public static com.google.protobuf.Descriptors.FileDescriptor\n" |
89 " descriptor;\n" | 97 " descriptor;\n" |
90 " static {\n", | 98 " static {\n", |
91 "classname", classname); | 99 "classname", classname); |
| 100 printer->Annotate("classname", file_->name()); |
92 printer->Indent(); | 101 printer->Indent(); |
93 printer->Indent(); | 102 printer->Indent(); |
94 GenerateDescriptors(printer.get()); | 103 GenerateDescriptors(printer.get()); |
95 printer->Outdent(); | 104 printer->Outdent(); |
96 printer->Outdent(); | 105 printer->Outdent(); |
97 printer->Print( | 106 printer->Print( |
98 " }\n" | 107 " }\n" |
99 "}\n"); | 108 "}\n"); |
100 | 109 |
| 110 if (options_.annotate_code) { |
| 111 google::protobuf::scoped_ptr<io::ZeroCopyOutputStream> info_output( |
| 112 context->Open(info_full_path)); |
| 113 annotations.SerializeToZeroCopyStream(info_output.get()); |
| 114 annotation_file_list->push_back(info_full_path); |
| 115 } |
| 116 |
101 printer.reset(); | 117 printer.reset(); |
102 output.reset(); | 118 output.reset(); |
103 } | 119 } |
104 } | 120 } |
105 | 121 |
106 | |
107 void SharedCodeGenerator::GenerateDescriptors(io::Printer* printer) { | 122 void SharedCodeGenerator::GenerateDescriptors(io::Printer* printer) { |
108 // Embed the descriptor. We simply serialize the entire FileDescriptorProto | 123 // Embed the descriptor. We simply serialize the entire FileDescriptorProto |
109 // and embed it as a string literal, which is parsed and built into real | 124 // and embed it as a string literal, which is parsed and built into real |
110 // descriptors at initialization time. We unfortunately have to put it in | 125 // descriptors at initialization time. We unfortunately have to put it in |
111 // a string literal, not a byte array, because apparently using a literal | 126 // a string literal, not a byte array, because apparently using a literal |
112 // byte array causes the Java compiler to generate *instructions* to | 127 // byte array causes the Java compiler to generate *instructions* to |
113 // initialize each and every byte of the array, e.g. as if you typed: | 128 // initialize each and every byte of the array, e.g. as if you typed: |
114 // b[0] = 123; b[1] = 456; b[2] = 789; | 129 // b[0] = 123; b[1] = 456; b[2] = 789; |
115 // This makes huge bytecode files and can easily hit the compiler's internal | 130 // This makes huge bytecode files and can easily hit the compiler's internal |
116 // code size limits (error "code to large"). String literals are apparently | 131 // code size limits (error "code to large"). String literals are apparently |
117 // embedded raw, which is what we want. | 132 // embedded raw, which is what we want. |
118 FileDescriptorProto file_proto; | 133 FileDescriptorProto file_proto; |
119 file_->CopyTo(&file_proto); | 134 file_->CopyTo(&file_proto); |
120 | 135 |
121 | |
122 string file_data; | 136 string file_data; |
123 file_proto.SerializeToString(&file_data); | 137 file_proto.SerializeToString(&file_data); |
124 | 138 |
125 printer->Print( | 139 printer->Print( |
126 "java.lang.String[] descriptorData = {\n"); | 140 "java.lang.String[] descriptorData = {\n"); |
127 printer->Indent(); | 141 printer->Indent(); |
128 | 142 |
129 // Only write 40 bytes per line. | 143 // Only write 40 bytes per line. |
130 static const int kBytesPerLine = 40; | 144 static const int kBytesPerLine = 40; |
131 for (int i = 0; i < file_data.size(); i += kBytesPerLine) { | 145 for (int i = 0; i < file_data.size(); i += kBytesPerLine) { |
(...skipping 26 matching lines...) Expand all Loading... |
158 " descriptor = root;\n" | 172 " descriptor = root;\n" |
159 // Custom options will be handled when immutable messages' outer class is | 173 // Custom options will be handled when immutable messages' outer class is |
160 // loaded. Here we just return null and let custom options be unknown | 174 // loaded. Here we just return null and let custom options be unknown |
161 // fields. | 175 // fields. |
162 " return null;\n" | 176 " return null;\n" |
163 " }\n" | 177 " }\n" |
164 " };\n"); | 178 " };\n"); |
165 | 179 |
166 // ----------------------------------------------------------------- | 180 // ----------------------------------------------------------------- |
167 // Find out all dependencies. | 181 // Find out all dependencies. |
168 vector<pair<string, string> > dependencies; | 182 std::vector<std::pair<string, string> > dependencies; |
169 for (int i = 0; i < file_->dependency_count(); i++) { | 183 for (int i = 0; i < file_->dependency_count(); i++) { |
170 if (ShouldIncludeDependency(file_->dependency(i))) { | 184 if (ShouldIncludeDependency(file_->dependency(i))) { |
171 string filename = file_->dependency(i)->name(); | 185 string filename = file_->dependency(i)->name(); |
172 string classname = FileJavaPackage(file_->dependency(i)) + "." + | 186 string classname = FileJavaPackage(file_->dependency(i)) + "." + |
173 name_resolver_->GetDescriptorClassName( | 187 name_resolver_->GetDescriptorClassName( |
174 file_->dependency(i)); | 188 file_->dependency(i)); |
175 dependencies.push_back(std::make_pair(filename, classname)); | 189 dependencies.push_back(std::make_pair(filename, classname)); |
176 } | 190 } |
177 } | 191 } |
178 | 192 |
(...skipping 18 matching lines...) Expand all Loading... |
197 | 211 |
198 bool SharedCodeGenerator::ShouldIncludeDependency( | 212 bool SharedCodeGenerator::ShouldIncludeDependency( |
199 const FileDescriptor* descriptor) { | 213 const FileDescriptor* descriptor) { |
200 return true; | 214 return true; |
201 } | 215 } |
202 | 216 |
203 } // namespace java | 217 } // namespace java |
204 } // namespace compiler | 218 } // namespace compiler |
205 } // namespace protobuf | 219 } // namespace protobuf |
206 } // namespace google | 220 } // namespace google |
OLD | NEW |