Home | History | Annotate | Download | only in objectivec
      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 <map>
     32 #include <string>
     33 
     34 #include <google/protobuf/compiler/objectivec/objectivec_primitive_field.h>
     35 #include <google/protobuf/stubs/common.h>
     36 #include <google/protobuf/compiler/objectivec/objectivec_helpers.h>
     37 #include <google/protobuf/io/printer.h>
     38 #include <google/protobuf/wire_format.h>
     39 #include <google/protobuf/wire_format_lite_inl.h>
     40 #include <google/protobuf/stubs/strutil.h>
     41 #include <google/protobuf/stubs/substitute.h>
     42 
     43 namespace google {
     44 namespace protobuf {
     45 namespace compiler {
     46 namespace objectivec {
     47 
     48 using internal::WireFormat;
     49 using internal::WireFormatLite;
     50 
     51 namespace {
     52 
     53 const char* PrimitiveTypeName(const FieldDescriptor* descriptor) {
     54   ObjectiveCType type = GetObjectiveCType(descriptor);
     55   switch (type) {
     56     case OBJECTIVECTYPE_INT32:
     57       return "int32_t";
     58     case OBJECTIVECTYPE_UINT32:
     59       return "uint32_t";
     60     case OBJECTIVECTYPE_INT64:
     61       return "int64_t";
     62     case OBJECTIVECTYPE_UINT64:
     63       return "uint64_t";
     64     case OBJECTIVECTYPE_FLOAT:
     65       return "float";
     66     case OBJECTIVECTYPE_DOUBLE:
     67       return "double";
     68     case OBJECTIVECTYPE_BOOLEAN:
     69       return "BOOL";
     70     case OBJECTIVECTYPE_STRING:
     71       return "NSString";
     72     case OBJECTIVECTYPE_DATA:
     73       return "NSData";
     74     case OBJECTIVECTYPE_ENUM:
     75       return "int32_t";
     76     case OBJECTIVECTYPE_MESSAGE:
     77       return NULL;  // Messages go through objectivec_message_field.cc|h.
     78   }
     79 
     80   // Some compilers report reaching end of function even though all cases of
     81   // the enum are handed in the switch.
     82   GOOGLE_LOG(FATAL) << "Can't get here.";
     83   return NULL;
     84 }
     85 
     86 const char* PrimitiveArrayTypeName(const FieldDescriptor* descriptor) {
     87   ObjectiveCType type = GetObjectiveCType(descriptor);
     88   switch (type) {
     89     case OBJECTIVECTYPE_INT32:
     90       return "Int32";
     91     case OBJECTIVECTYPE_UINT32:
     92       return "UInt32";
     93     case OBJECTIVECTYPE_INT64:
     94       return "Int64";
     95     case OBJECTIVECTYPE_UINT64:
     96       return "UInt64";
     97     case OBJECTIVECTYPE_FLOAT:
     98       return "Float";
     99     case OBJECTIVECTYPE_DOUBLE:
    100       return "Double";
    101     case OBJECTIVECTYPE_BOOLEAN:
    102       return "Bool";
    103     case OBJECTIVECTYPE_STRING:
    104       return "";  // Want NSArray
    105     case OBJECTIVECTYPE_DATA:
    106       return "";  // Want NSArray
    107     case OBJECTIVECTYPE_ENUM:
    108       return "Enum";
    109     case OBJECTIVECTYPE_MESSAGE:
    110       // Want NSArray (but goes through objectivec_message_field.cc|h).
    111       return "";
    112   }
    113 
    114   // Some compilers report reaching end of function even though all cases of
    115   // the enum are handed in the switch.
    116   GOOGLE_LOG(FATAL) << "Can't get here.";
    117   return NULL;
    118 }
    119 
    120 void SetPrimitiveVariables(const FieldDescriptor* descriptor,
    121                            map<string, string>* variables) {
    122   std::string primitive_name = PrimitiveTypeName(descriptor);
    123   (*variables)["type"] = primitive_name;
    124   (*variables)["storage_type"] = primitive_name;
    125 }
    126 
    127 }  // namespace
    128 
    129 PrimitiveFieldGenerator::PrimitiveFieldGenerator(
    130     const FieldDescriptor* descriptor, const Options& options)
    131     : SingleFieldGenerator(descriptor, options) {
    132   SetPrimitiveVariables(descriptor, &variables_);
    133 }
    134 
    135 PrimitiveFieldGenerator::~PrimitiveFieldGenerator() {}
    136 
    137 void PrimitiveFieldGenerator::GenerateFieldStorageDeclaration(
    138     io::Printer* printer) const {
    139   if (GetObjectiveCType(descriptor_) == OBJECTIVECTYPE_BOOLEAN) {
    140     // Nothing, BOOLs are stored in the has bits.
    141   } else {
    142     SingleFieldGenerator::GenerateFieldStorageDeclaration(printer);
    143   }
    144 }
    145 
    146 int PrimitiveFieldGenerator::ExtraRuntimeHasBitsNeeded(void) const {
    147   if (GetObjectiveCType(descriptor_) == OBJECTIVECTYPE_BOOLEAN) {
    148     // Reserve a bit for the storage of the boolean.
    149     return 1;
    150   }
    151   return 0;
    152 }
    153 
    154 void PrimitiveFieldGenerator::SetExtraRuntimeHasBitsBase(int has_base) {
    155   if (GetObjectiveCType(descriptor_) == OBJECTIVECTYPE_BOOLEAN) {
    156     // Set into the offset the has bit to use for the actual value.
    157     variables_["storage_offset_value"] = SimpleItoa(has_base);
    158     variables_["storage_offset_comment"] =
    159         "  // Stored in _has_storage_ to save space.";
    160   }
    161 }
    162 
    163 PrimitiveObjFieldGenerator::PrimitiveObjFieldGenerator(
    164     const FieldDescriptor* descriptor, const Options& options)
    165     : ObjCObjFieldGenerator(descriptor, options) {
    166   SetPrimitiveVariables(descriptor, &variables_);
    167   variables_["property_storage_attribute"] = "copy";
    168 }
    169 
    170 PrimitiveObjFieldGenerator::~PrimitiveObjFieldGenerator() {}
    171 
    172 RepeatedPrimitiveFieldGenerator::RepeatedPrimitiveFieldGenerator(
    173     const FieldDescriptor* descriptor, const Options& options)
    174     : RepeatedFieldGenerator(descriptor, options) {
    175   SetPrimitiveVariables(descriptor, &variables_);
    176 
    177   string base_name = PrimitiveArrayTypeName(descriptor);
    178   if (base_name.length()) {
    179     variables_["array_storage_type"] = "GPB" + base_name + "Array";
    180   } else {
    181     variables_["array_storage_type"] = "NSMutableArray";
    182     variables_["array_property_type"] =
    183         "NSMutableArray<" + variables_["storage_type"] + "*>";
    184   }
    185 }
    186 
    187 RepeatedPrimitiveFieldGenerator::~RepeatedPrimitiveFieldGenerator() {}
    188 
    189 }  // namespace objectivec
    190 }  // namespace compiler
    191 }  // namespace protobuf
    192 }  // namespace google
    193