LCOV - code coverage report
Current view: top level - third_party/protobuf/src/google/protobuf/compiler/java - java_context.cc (source / functions) Hit Total Coverage
Test: tmp.zDYK9MVh93 Lines: 0 87 0.0 %
Date: 2015-10-10 Functions: 0 9 0.0 %

          Line data    Source code
       1             : // Protocol Buffers - Google's data interchange format
       2             : // Copyright 2008 Google Inc.  All rights reserved.
       3             : // https://developers.google.com/protocol-buffers/
       4             : //
       5             : // Redistribution and use in source and binary forms, with or without
       6             : // modification, are permitted provided that the following conditions are
       7             : // met:
       8             : //
       9             : //     * Redistributions of source code must retain the above copyright
      10             : // notice, this list of conditions and the following disclaimer.
      11             : //     * Redistributions in binary form must reproduce the above
      12             : // copyright notice, this list of conditions and the following disclaimer
      13             : // in the documentation and/or other materials provided with the
      14             : // distribution.
      15             : //     * Neither the name of Google Inc. nor the names of its
      16             : // contributors may be used to endorse or promote products derived from
      17             : // this software without specific prior written permission.
      18             : //
      19             : // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
      20             : // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
      21             : // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
      22             : // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
      23             : // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
      24             : // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
      25             : // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
      26             : // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
      27             : // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
      28             : // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
      29             : // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
      30             : 
      31             : #include <google/protobuf/compiler/java/java_context.h>
      32             : 
      33             : #include <google/protobuf/compiler/java/java_field.h>
      34             : #include <google/protobuf/compiler/java/java_helpers.h>
      35             : #include <google/protobuf/compiler/java/java_name_resolver.h>
      36             : #include <google/protobuf/descriptor.h>
      37             : #include <google/protobuf/stubs/strutil.h>
      38             : #include <google/protobuf/stubs/map_util.h>
      39             : 
      40             : namespace google {
      41             : namespace protobuf {
      42             : namespace compiler {
      43             : namespace java {
      44             : 
      45           0 : Context::Context(const FileDescriptor* file)
      46           0 :     : name_resolver_(new ClassNameResolver) {
      47           0 :   InitializeFieldGeneratorInfo(file);
      48           0 : }
      49             : 
      50           0 : Context::~Context() {
      51           0 : }
      52             : 
      53           0 : ClassNameResolver* Context::GetNameResolver() {
      54           0 :   return name_resolver_.get();
      55             : }
      56             : 
      57             : namespace {
      58             : // Whether two fields have conflicting accessors (assuming name1 and name2
      59             : // are different). name1 and name2 are field1 and field2's camel-case name
      60             : // respectively.
      61           0 : bool IsConflicting(const FieldDescriptor* field1, const string& name1,
      62           0 :                    const FieldDescriptor* field2, const string& name2,
      63             :                    string* info) {
      64           0 :   if (field1->is_repeated()) {
      65           0 :     if (field2->is_repeated()) {
      66             :       // Both fields are repeated.
      67             :       return false;
      68             :     } else {
      69             :       // field1 is repeated, and field2 is not.
      70           0 :       if (name1 + "Count" == name2) {
      71           0 :         *info = "both repeated field \"" + field1->name() + "\" and singular " +
      72           0 :             "field \"" + field2->name() + "\" generates the method \"" +
      73           0 :             "get" + name1 + "Count()\"";
      74           0 :         return true;
      75             :       }
      76           0 :       if (name1 + "List" == name2) {
      77           0 :         *info = "both repeated field \"" + field1->name() + "\" and singular " +
      78           0 :             "field \"" + field2->name() + "\" generates the method \"" +
      79           0 :             "get" + name1 + "List()\"";
      80           0 :         return true;
      81             :       }
      82             :       // Well, there are obviously many more conflicting cases, but it probably
      83             :       // doesn't worth the effort to exhaust all of them because they rarely
      84             :       // happen and as we are continuing adding new methods/changing existing
      85             :       // methods the number of different conflicting cases will keep growing.
      86             :       // We can just add more cases here when they are found in the real world.
      87             :       return false;
      88             :     }
      89             :   } else {
      90           0 :     if (field2->is_repeated()) {
      91           0 :       return IsConflicting(field2, name2, field1, name1, info);
      92             :     } else {
      93             :       // None of the two fields are repeated.
      94             :       return false;
      95             :     }
      96             :   }
      97             : }
      98             : }  // namespace
      99             : 
     100           0 : void Context::InitializeFieldGeneratorInfo(const FileDescriptor* file) {
     101           0 :   for (int i = 0; i < file->message_type_count(); ++i) {
     102           0 :     InitializeFieldGeneratorInfoForMessage(file->message_type(i));
     103             :   }
     104           0 : }
     105             : 
     106           0 : void Context::InitializeFieldGeneratorInfoForMessage(
     107           0 :     const Descriptor* message) {
     108           0 :   for (int i = 0; i < message->nested_type_count(); ++i) {
     109           0 :     InitializeFieldGeneratorInfoForMessage(message->nested_type(i));
     110             :   }
     111             :   vector<const FieldDescriptor*> fields;
     112           0 :   for (int i = 0; i < message->field_count(); ++i) {
     113           0 :     fields.push_back(message->field(i));
     114             :   }
     115           0 :   InitializeFieldGeneratorInfoForFields(fields);
     116             : 
     117           0 :   for (int i = 0; i < message->oneof_decl_count(); ++i) {
     118           0 :     const OneofDescriptor* oneof = message->oneof_decl(i);
     119             :     OneofGeneratorInfo info;
     120           0 :     info.name = UnderscoresToCamelCase(oneof->name(), false);
     121           0 :     info.capitalized_name = UnderscoresToCamelCase(oneof->name(), true);
     122           0 :     oneof_generator_info_map_[oneof] = info;
     123           0 :   }
     124           0 : }
     125             : 
     126           0 : void Context::InitializeFieldGeneratorInfoForFields(
     127           0 :     const vector<const FieldDescriptor*>& fields) {
     128             :   // Find out all fields that conflict with some other field in the same
     129             :   // message.
     130           0 :   vector<bool> is_conflict(fields.size());
     131           0 :   vector<string> conflict_reason(fields.size());
     132           0 :   for (int i = 0; i < fields.size(); ++i) {
     133           0 :     const FieldDescriptor* field = fields[i];
     134           0 :     const string& name = UnderscoresToCapitalizedCamelCase(field);
     135           0 :     for (int j = i + 1; j < fields.size(); ++j) {
     136           0 :       const FieldDescriptor* other = fields[j];
     137           0 :       const string& other_name = UnderscoresToCapitalizedCamelCase(other);
     138           0 :       if (name == other_name) {
     139           0 :         is_conflict[i] = is_conflict[j] = true;
     140           0 :         conflict_reason[i] = conflict_reason[j] =
     141           0 :             "capitalized name of field \"" + field->name() +
     142           0 :             "\" conflicts with field \"" + other->name() + "\"";
     143           0 :       } else if (IsConflicting(field, name, other, other_name,
     144           0 :                                &conflict_reason[j])) {
     145           0 :         is_conflict[i] = is_conflict[j] = true;
     146           0 :         conflict_reason[i] = conflict_reason[j];
     147             :       }
     148             :     }
     149           0 :     if (is_conflict[i]) {
     150           0 :       GOOGLE_LOG(WARNING) << "field \"" << field->full_name() << "\" is conflicting "
     151           0 :                    << "with another field: " << conflict_reason[i];
     152             :     }
     153             :   }
     154           0 :   for (int i = 0; i < fields.size(); ++i) {
     155           0 :     const FieldDescriptor* field = fields[i];
     156             :     FieldGeneratorInfo info;
     157           0 :     info.name = UnderscoresToCamelCase(field);
     158           0 :     info.capitalized_name = UnderscoresToCapitalizedCamelCase(field);
     159             :     // For fields conflicting with some other fields, we append the field
     160             :     // number to their field names in generated code to avoid conflicts.
     161           0 :     if (is_conflict[i]) {
     162           0 :       info.name += SimpleItoa(field->number());
     163           0 :       info.capitalized_name += SimpleItoa(field->number());
     164           0 :       info.disambiguated_reason = conflict_reason[i];
     165             :     }
     166           0 :     field_generator_info_map_[field] = info;
     167           0 :   }
     168           0 : }
     169             : 
     170           0 : const FieldGeneratorInfo* Context::GetFieldGeneratorInfo(
     171             :     const FieldDescriptor* field) const {
     172             :   const FieldGeneratorInfo* result =
     173           0 :       FindOrNull(field_generator_info_map_, field);
     174           0 :   if (result == NULL) {
     175           0 :     GOOGLE_LOG(FATAL) << "Can not find FieldGeneratorInfo for field: "
     176           0 :                << field->full_name();
     177             :   }
     178           0 :   return result;
     179             : }
     180             : 
     181           0 : const OneofGeneratorInfo* Context::GetOneofGeneratorInfo(
     182             :     const OneofDescriptor* oneof) const {
     183             :   const OneofGeneratorInfo* result =
     184           0 :       FindOrNull(oneof_generator_info_map_, oneof);
     185           0 :   if (result == NULL) {
     186           0 :     GOOGLE_LOG(FATAL) << "Can not find OneofGeneratorInfo for oneof: "
     187           0 :                << oneof->name();
     188             :   }
     189           0 :   return result;
     190             : }
     191             : 
     192             : }  // namespace java
     193             : }  // namespace compiler
     194             : }  // namespace protobuf
     195             : }  // namespace google

Generated by: LCOV version 1.10