PageRenderTime 257ms CodeModel.GetById 184ms app.highlight 63ms RepoModel.GetById 1ms app.codeStats 1ms

/thirdparty/breakpad/third_party/protobuf/protobuf/src/google/protobuf/compiler/python/python_generator.cc

http://github.com/tomahawk-player/tomahawk
C++ | 1006 lines | 693 code | 95 blank | 218 comment | 72 complexity | 6d8d1ab0e129b758282bab8e81005fc0 MD5 | raw file
   1// Protocol Buffers - Google's data interchange format
   2// Copyright 2008 Google Inc.  All rights reserved.
   3// http://code.google.com/p/protobuf/
   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// Author: robinson@google.com (Will Robinson)
  32//
  33// This module outputs pure-Python protocol message classes that will
  34// largely be constructed at runtime via the metaclass in reflection.py.
  35// In other words, our job is basically to output a Python equivalent
  36// of the C++ *Descriptor objects, and fix up all circular references
  37// within these objects.
  38//
  39// Note that the runtime performance of protocol message classes created in
  40// this way is expected to be lousy.  The plan is to create an alternate
  41// generator that outputs a Python/C extension module that lets
  42// performance-minded Python code leverage the fast C++ implementation
  43// directly.
  44
  45#include <limits>
  46#include <map>
  47#include <utility>
  48#include <string>
  49#include <vector>
  50
  51#include <google/protobuf/compiler/python/python_generator.h>
  52#include <google/protobuf/descriptor.pb.h>
  53
  54#include <google/protobuf/stubs/common.h>
  55#include <google/protobuf/io/printer.h>
  56#include <google/protobuf/descriptor.h>
  57#include <google/protobuf/io/zero_copy_stream.h>
  58#include <google/protobuf/stubs/strutil.h>
  59#include <google/protobuf/stubs/substitute.h>
  60
  61namespace google {
  62namespace protobuf {
  63namespace compiler {
  64namespace python {
  65
  66namespace {
  67
  68// Returns a copy of |filename| with any trailing ".protodevel" or ".proto
  69// suffix stripped.
  70// TODO(robinson): Unify with copy in compiler/cpp/internal/helpers.cc.
  71string StripProto(const string& filename) {
  72  const char* suffix = HasSuffixString(filename, ".protodevel")
  73      ? ".protodevel" : ".proto";
  74  return StripSuffixString(filename, suffix);
  75}
  76
  77
  78// Returns the Python module name expected for a given .proto filename.
  79string ModuleName(const string& filename) {
  80  string basename = StripProto(filename);
  81  StripString(&basename, "-", '_');
  82  StripString(&basename, "/", '.');
  83  return basename + "_pb2";
  84}
  85
  86
  87// Returns the name of all containing types for descriptor,
  88// in order from outermost to innermost, followed by descriptor's
  89// own name.  Each name is separated by |separator|.
  90template <typename DescriptorT>
  91string NamePrefixedWithNestedTypes(const DescriptorT& descriptor,
  92                                   const string& separator) {
  93  string name = descriptor.name();
  94  for (const Descriptor* current = descriptor.containing_type();
  95       current != NULL; current = current->containing_type()) {
  96    name = current->name() + separator + name;
  97  }
  98  return name;
  99}
 100
 101
 102// Name of the class attribute where we store the Python
 103// descriptor.Descriptor instance for the generated class.
 104// Must stay consistent with the _DESCRIPTOR_KEY constant
 105// in proto2/public/reflection.py.
 106const char kDescriptorKey[] = "DESCRIPTOR";
 107
 108
 109// Should we generate generic services for this file?
 110inline bool HasGenericServices(const FileDescriptor *file) {
 111  return file->service_count() > 0 &&
 112         file->options().py_generic_services();
 113}
 114
 115
 116// Prints the common boilerplate needed at the top of every .py
 117// file output by this generator.
 118void PrintTopBoilerplate(
 119    io::Printer* printer, const FileDescriptor* file, bool descriptor_proto) {
 120  // TODO(robinson): Allow parameterization of Python version?
 121  printer->Print(
 122      "# Generated by the protocol buffer compiler.  DO NOT EDIT!\n"
 123      "\n"
 124      "from google.protobuf import descriptor\n"
 125      "from google.protobuf import message\n"
 126      "from google.protobuf import reflection\n");
 127  if (HasGenericServices(file)) {
 128    printer->Print(
 129        "from google.protobuf import service\n"
 130        "from google.protobuf import service_reflection\n");
 131  }
 132
 133  // Avoid circular imports if this module is descriptor_pb2.
 134  if (!descriptor_proto) {
 135    printer->Print(
 136        "from google.protobuf import descriptor_pb2\n");
 137  }
 138  printer->Print(
 139    "# @@protoc_insertion_point(imports)\n");
 140  printer->Print("\n\n");
 141}
 142
 143
 144// Returns a Python literal giving the default value for a field.
 145// If the field specifies no explicit default value, we'll return
 146// the default default value for the field type (zero for numbers,
 147// empty string for strings, empty list for repeated fields, and
 148// None for non-repeated, composite fields).
 149//
 150// TODO(robinson): Unify with code from
 151// //compiler/cpp/internal/primitive_field.cc
 152// //compiler/cpp/internal/enum_field.cc
 153// //compiler/cpp/internal/string_field.cc
 154string StringifyDefaultValue(const FieldDescriptor& field) {
 155  if (field.is_repeated()) {
 156    return "[]";
 157  }
 158
 159  switch (field.cpp_type()) {
 160    case FieldDescriptor::CPPTYPE_INT32:
 161      return SimpleItoa(field.default_value_int32());
 162    case FieldDescriptor::CPPTYPE_UINT32:
 163      return SimpleItoa(field.default_value_uint32());
 164    case FieldDescriptor::CPPTYPE_INT64:
 165      return SimpleItoa(field.default_value_int64());
 166    case FieldDescriptor::CPPTYPE_UINT64:
 167      return SimpleItoa(field.default_value_uint64());
 168    case FieldDescriptor::CPPTYPE_DOUBLE: {
 169      double value = field.default_value_double();
 170      if (value == numeric_limits<double>::infinity()) {
 171        // Python pre-2.6 on Windows does not parse "inf" correctly.  However,
 172        // a numeric literal that is too big for a double will become infinity.
 173        return "1e10000";
 174      } else if (value == -numeric_limits<double>::infinity()) {
 175        // See above.
 176        return "-1e10000";
 177      } else if (value != value) {
 178        // infinity * 0 = nan
 179        return "(1e10000 * 0)";
 180      } else {
 181        return SimpleDtoa(value);
 182      }
 183    }
 184    case FieldDescriptor::CPPTYPE_FLOAT: {
 185      float value = field.default_value_float();
 186      if (value == numeric_limits<float>::infinity()) {
 187        // Python pre-2.6 on Windows does not parse "inf" correctly.  However,
 188        // a numeric literal that is too big for a double will become infinity.
 189        return "1e10000";
 190      } else if (value == -numeric_limits<float>::infinity()) {
 191        // See above.
 192        return "-1e10000";
 193      } else if (value != value) {
 194        // infinity - infinity = nan
 195        return "(1e10000 * 0)";
 196      } else {
 197        return SimpleFtoa(value);
 198      }
 199    }
 200    case FieldDescriptor::CPPTYPE_BOOL:
 201      return field.default_value_bool() ? "True" : "False";
 202    case FieldDescriptor::CPPTYPE_ENUM:
 203      return SimpleItoa(field.default_value_enum()->number());
 204    case FieldDescriptor::CPPTYPE_STRING:
 205      if (field.type() == FieldDescriptor::TYPE_STRING) {
 206        return "unicode(\"" + CEscape(field.default_value_string()) +
 207            "\", \"utf-8\")";
 208      } else {
 209        return "\"" + CEscape(field.default_value_string()) + "\"";
 210      }
 211    case FieldDescriptor::CPPTYPE_MESSAGE:
 212      return "None";
 213  }
 214  // (We could add a default case above but then we wouldn't get the nice
 215  // compiler warning when a new type is added.)
 216  GOOGLE_LOG(FATAL) << "Not reached.";
 217  return "";
 218}
 219
 220
 221
 222}  // namespace
 223
 224
 225Generator::Generator() : file_(NULL) {
 226}
 227
 228Generator::~Generator() {
 229}
 230
 231bool Generator::Generate(const FileDescriptor* file,
 232                         const string& parameter,
 233                         GeneratorContext* context,
 234                         string* error) const {
 235
 236  // Completely serialize all Generate() calls on this instance.  The
 237  // thread-safety constraints of the CodeGenerator interface aren't clear so
 238  // just be as conservative as possible.  It's easier to relax this later if
 239  // we need to, but I doubt it will be an issue.
 240  // TODO(kenton):  The proper thing to do would be to allocate any state on
 241  //   the stack and use that, so that the Generator class itself does not need
 242  //   to have any mutable members.  Then it is implicitly thread-safe.
 243  MutexLock lock(&mutex_);
 244  file_ = file;
 245  string module_name = ModuleName(file->name());
 246  string filename = module_name;
 247  StripString(&filename, ".", '/');
 248  filename += ".py";
 249
 250  FileDescriptorProto fdp;
 251  file_->CopyTo(&fdp);
 252  fdp.SerializeToString(&file_descriptor_serialized_);
 253
 254
 255  scoped_ptr<io::ZeroCopyOutputStream> output(context->Open(filename));
 256  GOOGLE_CHECK(output.get());
 257  io::Printer printer(output.get(), '$');
 258  printer_ = &printer;
 259
 260  PrintTopBoilerplate(printer_, file_, GeneratingDescriptorProto());
 261  PrintImports();
 262  PrintFileDescriptor();
 263  PrintTopLevelEnums();
 264  PrintTopLevelExtensions();
 265  PrintAllNestedEnumsInFile();
 266  PrintMessageDescriptors();
 267  FixForeignFieldsInDescriptors();
 268  PrintMessages();
 269  // We have to fix up the extensions after the message classes themselves,
 270  // since they need to call static RegisterExtension() methods on these
 271  // classes.
 272  FixForeignFieldsInExtensions();
 273  if (HasGenericServices(file)) {
 274    PrintServices();
 275  }
 276
 277  printer.Print(
 278    "# @@protoc_insertion_point(module_scope)\n");
 279
 280  return !printer.failed();
 281}
 282
 283// Prints Python imports for all modules imported by |file|.
 284void Generator::PrintImports() const {
 285  for (int i = 0; i < file_->dependency_count(); ++i) {
 286    string module_name = ModuleName(file_->dependency(i)->name());
 287    printer_->Print("import $module$\n", "module",
 288                    module_name);
 289  }
 290  printer_->Print("\n");
 291}
 292
 293// Prints the single file descriptor for this file.
 294void Generator::PrintFileDescriptor() const {
 295  map<string, string> m;
 296  m["descriptor_name"] = kDescriptorKey;
 297  m["name"] = file_->name();
 298  m["package"] = file_->package();
 299  const char file_descriptor_template[] =
 300      "$descriptor_name$ = descriptor.FileDescriptor(\n"
 301      "  name='$name$',\n"
 302      "  package='$package$',\n";
 303  printer_->Print(m, file_descriptor_template);
 304  printer_->Indent();
 305  printer_->Print(
 306      "serialized_pb='$value$'",
 307      "value", strings::CHexEscape(file_descriptor_serialized_));
 308
 309  // TODO(falk): Also print options and fix the message_type, enum_type,
 310  //             service and extension later in the generation.
 311
 312  printer_->Outdent();
 313  printer_->Print(")\n");
 314  printer_->Print("\n");
 315}
 316
 317// Prints descriptors and module-level constants for all top-level
 318// enums defined in |file|.
 319void Generator::PrintTopLevelEnums() const {
 320  vector<pair<string, int> > top_level_enum_values;
 321  for (int i = 0; i < file_->enum_type_count(); ++i) {
 322    const EnumDescriptor& enum_descriptor = *file_->enum_type(i);
 323    PrintEnum(enum_descriptor);
 324    printer_->Print("\n");
 325
 326    for (int j = 0; j < enum_descriptor.value_count(); ++j) {
 327      const EnumValueDescriptor& value_descriptor = *enum_descriptor.value(j);
 328      top_level_enum_values.push_back(
 329          make_pair(value_descriptor.name(), value_descriptor.number()));
 330    }
 331  }
 332
 333  for (int i = 0; i < top_level_enum_values.size(); ++i) {
 334    printer_->Print("$name$ = $value$\n",
 335                    "name", top_level_enum_values[i].first,
 336                    "value", SimpleItoa(top_level_enum_values[i].second));
 337  }
 338  printer_->Print("\n");
 339}
 340
 341// Prints all enums contained in all message types in |file|.
 342void Generator::PrintAllNestedEnumsInFile() const {
 343  for (int i = 0; i < file_->message_type_count(); ++i) {
 344    PrintNestedEnums(*file_->message_type(i));
 345  }
 346}
 347
 348// Prints a Python statement assigning the appropriate module-level
 349// enum name to a Python EnumDescriptor object equivalent to
 350// enum_descriptor.
 351void Generator::PrintEnum(const EnumDescriptor& enum_descriptor) const {
 352  map<string, string> m;
 353  m["descriptor_name"] = ModuleLevelDescriptorName(enum_descriptor);
 354  m["name"] = enum_descriptor.name();
 355  m["full_name"] = enum_descriptor.full_name();
 356  m["file"] = kDescriptorKey;
 357  const char enum_descriptor_template[] =
 358      "$descriptor_name$ = descriptor.EnumDescriptor(\n"
 359      "  name='$name$',\n"
 360      "  full_name='$full_name$',\n"
 361      "  filename=None,\n"
 362      "  file=$file$,\n"
 363      "  values=[\n";
 364  string options_string;
 365  enum_descriptor.options().SerializeToString(&options_string);
 366  printer_->Print(m, enum_descriptor_template);
 367  printer_->Indent();
 368  printer_->Indent();
 369  for (int i = 0; i < enum_descriptor.value_count(); ++i) {
 370    PrintEnumValueDescriptor(*enum_descriptor.value(i));
 371    printer_->Print(",\n");
 372  }
 373  printer_->Outdent();
 374  printer_->Print("],\n");
 375  printer_->Print("containing_type=None,\n");
 376  printer_->Print("options=$options_value$,\n",
 377                  "options_value",
 378                  OptionsValue("EnumOptions", options_string));
 379  EnumDescriptorProto edp;
 380  PrintSerializedPbInterval(enum_descriptor, edp);
 381  printer_->Outdent();
 382  printer_->Print(")\n");
 383  printer_->Print("\n");
 384}
 385
 386// Recursively prints enums in nested types within descriptor, then
 387// prints enums contained at the top level in descriptor.
 388void Generator::PrintNestedEnums(const Descriptor& descriptor) const {
 389  for (int i = 0; i < descriptor.nested_type_count(); ++i) {
 390    PrintNestedEnums(*descriptor.nested_type(i));
 391  }
 392
 393  for (int i = 0; i < descriptor.enum_type_count(); ++i) {
 394    PrintEnum(*descriptor.enum_type(i));
 395  }
 396}
 397
 398void Generator::PrintTopLevelExtensions() const {
 399  const bool is_extension = true;
 400  for (int i = 0; i < file_->extension_count(); ++i) {
 401    const FieldDescriptor& extension_field = *file_->extension(i);
 402    string constant_name = extension_field.name() + "_FIELD_NUMBER";
 403    UpperString(&constant_name);
 404    printer_->Print("$constant_name$ = $number$\n",
 405      "constant_name", constant_name,
 406      "number", SimpleItoa(extension_field.number()));
 407    printer_->Print("$name$ = ", "name", extension_field.name());
 408    PrintFieldDescriptor(extension_field, is_extension);
 409    printer_->Print("\n");
 410  }
 411  printer_->Print("\n");
 412}
 413
 414// Prints Python equivalents of all Descriptors in |file|.
 415void Generator::PrintMessageDescriptors() const {
 416  for (int i = 0; i < file_->message_type_count(); ++i) {
 417    PrintDescriptor(*file_->message_type(i));
 418    printer_->Print("\n");
 419  }
 420}
 421
 422void Generator::PrintServices() const {
 423  for (int i = 0; i < file_->service_count(); ++i) {
 424    PrintServiceDescriptor(*file_->service(i));
 425    PrintServiceClass(*file_->service(i));
 426    PrintServiceStub(*file_->service(i));
 427    printer_->Print("\n");
 428  }
 429}
 430
 431void Generator::PrintServiceDescriptor(
 432    const ServiceDescriptor& descriptor) const {
 433  printer_->Print("\n");
 434  string service_name = ModuleLevelServiceDescriptorName(descriptor);
 435  string options_string;
 436  descriptor.options().SerializeToString(&options_string);
 437
 438  printer_->Print(
 439      "$service_name$ = descriptor.ServiceDescriptor(\n",
 440      "service_name", service_name);
 441  printer_->Indent();
 442  map<string, string> m;
 443  m["name"] = descriptor.name();
 444  m["full_name"] = descriptor.full_name();
 445  m["file"] = kDescriptorKey;
 446  m["index"] = SimpleItoa(descriptor.index());
 447  m["options_value"] = OptionsValue("ServiceOptions", options_string);
 448  const char required_function_arguments[] =
 449      "name='$name$',\n"
 450      "full_name='$full_name$',\n"
 451      "file=$file$,\n"
 452      "index=$index$,\n"
 453      "options=$options_value$,\n";
 454  printer_->Print(m, required_function_arguments);
 455
 456  ServiceDescriptorProto sdp;
 457  PrintSerializedPbInterval(descriptor, sdp);
 458
 459  printer_->Print("methods=[\n");
 460  for (int i = 0; i < descriptor.method_count(); ++i) {
 461    const MethodDescriptor* method = descriptor.method(i);
 462    string options_string;
 463    method->options().SerializeToString(&options_string);
 464
 465    m.clear();
 466    m["name"] = method->name();
 467    m["full_name"] = method->full_name();
 468    m["index"] = SimpleItoa(method->index());
 469    m["serialized_options"] = CEscape(options_string);
 470    m["input_type"] = ModuleLevelDescriptorName(*(method->input_type()));
 471    m["output_type"] = ModuleLevelDescriptorName(*(method->output_type()));
 472    m["options_value"] = OptionsValue("MethodOptions", options_string);
 473    printer_->Print("descriptor.MethodDescriptor(\n");
 474    printer_->Indent();
 475    printer_->Print(
 476        m,
 477        "name='$name$',\n"
 478        "full_name='$full_name$',\n"
 479        "index=$index$,\n"
 480        "containing_service=None,\n"
 481        "input_type=$input_type$,\n"
 482        "output_type=$output_type$,\n"
 483        "options=$options_value$,\n");
 484    printer_->Outdent();
 485    printer_->Print("),\n");
 486  }
 487
 488  printer_->Outdent();
 489  printer_->Print("])\n\n");
 490}
 491
 492void Generator::PrintServiceClass(const ServiceDescriptor& descriptor) const {
 493  // Print the service.
 494  printer_->Print("class $class_name$(service.Service):\n",
 495                  "class_name", descriptor.name());
 496  printer_->Indent();
 497  printer_->Print(
 498      "__metaclass__ = service_reflection.GeneratedServiceType\n"
 499      "$descriptor_key$ = $descriptor_name$\n",
 500      "descriptor_key", kDescriptorKey,
 501      "descriptor_name", ModuleLevelServiceDescriptorName(descriptor));
 502  printer_->Outdent();
 503}
 504
 505void Generator::PrintServiceStub(const ServiceDescriptor& descriptor) const {
 506  // Print the service stub.
 507  printer_->Print("class $class_name$_Stub($class_name$):\n",
 508                  "class_name", descriptor.name());
 509  printer_->Indent();
 510  printer_->Print(
 511      "__metaclass__ = service_reflection.GeneratedServiceStubType\n"
 512      "$descriptor_key$ = $descriptor_name$\n",
 513      "descriptor_key", kDescriptorKey,
 514      "descriptor_name", ModuleLevelServiceDescriptorName(descriptor));
 515  printer_->Outdent();
 516}
 517
 518// Prints statement assigning ModuleLevelDescriptorName(message_descriptor)
 519// to a Python Descriptor object for message_descriptor.
 520//
 521// Mutually recursive with PrintNestedDescriptors().
 522void Generator::PrintDescriptor(const Descriptor& message_descriptor) const {
 523  PrintNestedDescriptors(message_descriptor);
 524
 525  printer_->Print("\n");
 526  printer_->Print("$descriptor_name$ = descriptor.Descriptor(\n",
 527                  "descriptor_name",
 528                  ModuleLevelDescriptorName(message_descriptor));
 529  printer_->Indent();
 530  map<string, string> m;
 531  m["name"] = message_descriptor.name();
 532  m["full_name"] = message_descriptor.full_name();
 533  m["file"] = kDescriptorKey;
 534  const char required_function_arguments[] =
 535      "name='$name$',\n"
 536      "full_name='$full_name$',\n"
 537      "filename=None,\n"
 538      "file=$file$,\n"
 539      "containing_type=None,\n";
 540  printer_->Print(m, required_function_arguments);
 541  PrintFieldsInDescriptor(message_descriptor);
 542  PrintExtensionsInDescriptor(message_descriptor);
 543
 544  // Nested types
 545  printer_->Print("nested_types=[");
 546  for (int i = 0; i < message_descriptor.nested_type_count(); ++i) {
 547    const string nested_name = ModuleLevelDescriptorName(
 548        *message_descriptor.nested_type(i));
 549    printer_->Print("$name$, ", "name", nested_name);
 550  }
 551  printer_->Print("],\n");
 552
 553  // Enum types
 554  printer_->Print("enum_types=[\n");
 555  printer_->Indent();
 556  for (int i = 0; i < message_descriptor.enum_type_count(); ++i) {
 557    const string descriptor_name = ModuleLevelDescriptorName(
 558        *message_descriptor.enum_type(i));
 559    printer_->Print(descriptor_name.c_str());
 560    printer_->Print(",\n");
 561  }
 562  printer_->Outdent();
 563  printer_->Print("],\n");
 564  string options_string;
 565  message_descriptor.options().SerializeToString(&options_string);
 566  printer_->Print(
 567      "options=$options_value$,\n"
 568      "is_extendable=$extendable$",
 569      "options_value", OptionsValue("MessageOptions", options_string),
 570      "extendable", message_descriptor.extension_range_count() > 0 ?
 571                      "True" : "False");
 572  printer_->Print(",\n");
 573
 574  // Extension ranges
 575  printer_->Print("extension_ranges=[");
 576  for (int i = 0; i < message_descriptor.extension_range_count(); ++i) {
 577    const Descriptor::ExtensionRange* range =
 578        message_descriptor.extension_range(i);
 579    printer_->Print("($start$, $end$), ",
 580                    "start", SimpleItoa(range->start),
 581                    "end", SimpleItoa(range->end));
 582  }
 583  printer_->Print("],\n");
 584
 585  // Serialization of proto
 586  DescriptorProto edp;
 587  PrintSerializedPbInterval(message_descriptor, edp);
 588
 589  printer_->Outdent();
 590  printer_->Print(")\n");
 591}
 592
 593// Prints Python Descriptor objects for all nested types contained in
 594// message_descriptor.
 595//
 596// Mutually recursive with PrintDescriptor().
 597void Generator::PrintNestedDescriptors(
 598    const Descriptor& containing_descriptor) const {
 599  for (int i = 0; i < containing_descriptor.nested_type_count(); ++i) {
 600    PrintDescriptor(*containing_descriptor.nested_type(i));
 601  }
 602}
 603
 604// Prints all messages in |file|.
 605void Generator::PrintMessages() const {
 606  for (int i = 0; i < file_->message_type_count(); ++i) {
 607    PrintMessage(*file_->message_type(i));
 608    printer_->Print("\n");
 609  }
 610}
 611
 612// Prints a Python class for the given message descriptor.  We defer to the
 613// metaclass to do almost all of the work of actually creating a useful class.
 614// The purpose of this function and its many helper functions above is merely
 615// to output a Python version of the descriptors, which the metaclass in
 616// reflection.py will use to construct the meat of the class itself.
 617//
 618// Mutually recursive with PrintNestedMessages().
 619void Generator::PrintMessage(
 620    const Descriptor& message_descriptor) const {
 621  printer_->Print("class $name$(message.Message):\n", "name",
 622                  message_descriptor.name());
 623  printer_->Indent();
 624  printer_->Print("__metaclass__ = reflection.GeneratedProtocolMessageType\n");
 625  PrintNestedMessages(message_descriptor);
 626  map<string, string> m;
 627  m["descriptor_key"] = kDescriptorKey;
 628  m["descriptor_name"] = ModuleLevelDescriptorName(message_descriptor);
 629  printer_->Print(m, "$descriptor_key$ = $descriptor_name$\n");
 630
 631  printer_->Print(
 632    "\n"
 633    "# @@protoc_insertion_point(class_scope:$full_name$)\n",
 634    "full_name", message_descriptor.full_name());
 635
 636  printer_->Outdent();
 637}
 638
 639// Prints all nested messages within |containing_descriptor|.
 640// Mutually recursive with PrintMessage().
 641void Generator::PrintNestedMessages(
 642    const Descriptor& containing_descriptor) const {
 643  for (int i = 0; i < containing_descriptor.nested_type_count(); ++i) {
 644    printer_->Print("\n");
 645    PrintMessage(*containing_descriptor.nested_type(i));
 646  }
 647}
 648
 649// Recursively fixes foreign fields in all nested types in |descriptor|, then
 650// sets the message_type and enum_type of all message and enum fields to point
 651// to their respective descriptors.
 652// Args:
 653//   descriptor: descriptor to print fields for.
 654//   containing_descriptor: if descriptor is a nested type, this is its
 655//       containing type, or NULL if this is a root/top-level type.
 656void Generator::FixForeignFieldsInDescriptor(
 657    const Descriptor& descriptor,
 658    const Descriptor* containing_descriptor) const {
 659  for (int i = 0; i < descriptor.nested_type_count(); ++i) {
 660    FixForeignFieldsInDescriptor(*descriptor.nested_type(i), &descriptor);
 661  }
 662
 663  for (int i = 0; i < descriptor.field_count(); ++i) {
 664    const FieldDescriptor& field_descriptor = *descriptor.field(i);
 665    FixForeignFieldsInField(&descriptor, field_descriptor, "fields_by_name");
 666  }
 667
 668  FixContainingTypeInDescriptor(descriptor, containing_descriptor);
 669  for (int i = 0; i < descriptor.enum_type_count(); ++i) {
 670    const EnumDescriptor& enum_descriptor = *descriptor.enum_type(i);
 671    FixContainingTypeInDescriptor(enum_descriptor, &descriptor);
 672  }
 673}
 674
 675void Generator::AddMessageToFileDescriptor(const Descriptor& descriptor) const {
 676  map<string, string> m;
 677  m["descriptor_name"] = kDescriptorKey;
 678  m["message_name"] = descriptor.name();
 679  m["message_descriptor_name"] = ModuleLevelDescriptorName(descriptor);
 680  const char file_descriptor_template[] =
 681      "$descriptor_name$.message_types_by_name['$message_name$'] = "
 682      "$message_descriptor_name$\n";
 683  printer_->Print(m, file_descriptor_template);
 684}
 685
 686// Sets any necessary message_type and enum_type attributes
 687// for the Python version of |field|.
 688//
 689// containing_type may be NULL, in which case this is a module-level field.
 690//
 691// python_dict_name is the name of the Python dict where we should
 692// look the field up in the containing type.  (e.g., fields_by_name
 693// or extensions_by_name).  We ignore python_dict_name if containing_type
 694// is NULL.
 695void Generator::FixForeignFieldsInField(const Descriptor* containing_type,
 696                                        const FieldDescriptor& field,
 697                                        const string& python_dict_name) const {
 698  const string field_referencing_expression = FieldReferencingExpression(
 699      containing_type, field, python_dict_name);
 700  map<string, string> m;
 701  m["field_ref"] = field_referencing_expression;
 702  const Descriptor* foreign_message_type = field.message_type();
 703  if (foreign_message_type) {
 704    m["foreign_type"] = ModuleLevelDescriptorName(*foreign_message_type);
 705    printer_->Print(m, "$field_ref$.message_type = $foreign_type$\n");
 706  }
 707  const EnumDescriptor* enum_type = field.enum_type();
 708  if (enum_type) {
 709    m["enum_type"] = ModuleLevelDescriptorName(*enum_type);
 710    printer_->Print(m, "$field_ref$.enum_type = $enum_type$\n");
 711  }
 712}
 713
 714// Returns the module-level expression for the given FieldDescriptor.
 715// Only works for fields in the .proto file this Generator is generating for.
 716//
 717// containing_type may be NULL, in which case this is a module-level field.
 718//
 719// python_dict_name is the name of the Python dict where we should
 720// look the field up in the containing type.  (e.g., fields_by_name
 721// or extensions_by_name).  We ignore python_dict_name if containing_type
 722// is NULL.
 723string Generator::FieldReferencingExpression(
 724    const Descriptor* containing_type,
 725    const FieldDescriptor& field,
 726    const string& python_dict_name) const {
 727  // We should only ever be looking up fields in the current file.
 728  // The only things we refer to from other files are message descriptors.
 729  GOOGLE_CHECK_EQ(field.file(), file_) << field.file()->name() << " vs. "
 730                                << file_->name();
 731  if (!containing_type) {
 732    return field.name();
 733  }
 734  return strings::Substitute(
 735      "$0.$1['$2']",
 736      ModuleLevelDescriptorName(*containing_type),
 737      python_dict_name, field.name());
 738}
 739
 740// Prints containing_type for nested descriptors or enum descriptors.
 741template <typename DescriptorT>
 742void Generator::FixContainingTypeInDescriptor(
 743    const DescriptorT& descriptor,
 744    const Descriptor* containing_descriptor) const {
 745  if (containing_descriptor != NULL) {
 746    const string nested_name = ModuleLevelDescriptorName(descriptor);
 747    const string parent_name = ModuleLevelDescriptorName(
 748        *containing_descriptor);
 749    printer_->Print(
 750        "$nested_name$.containing_type = $parent_name$;\n",
 751        "nested_name", nested_name,
 752        "parent_name", parent_name);
 753  }
 754}
 755
 756// Prints statements setting the message_type and enum_type fields in the
 757// Python descriptor objects we've already output in ths file.  We must
 758// do this in a separate step due to circular references (otherwise, we'd
 759// just set everything in the initial assignment statements).
 760void Generator::FixForeignFieldsInDescriptors() const {
 761  for (int i = 0; i < file_->message_type_count(); ++i) {
 762    FixForeignFieldsInDescriptor(*file_->message_type(i), NULL);
 763  }
 764  for (int i = 0; i < file_->message_type_count(); ++i) {
 765    AddMessageToFileDescriptor(*file_->message_type(i));
 766  }
 767  printer_->Print("\n");
 768}
 769
 770// We need to not only set any necessary message_type fields, but
 771// also need to call RegisterExtension() on each message we're
 772// extending.
 773void Generator::FixForeignFieldsInExtensions() const {
 774  // Top-level extensions.
 775  for (int i = 0; i < file_->extension_count(); ++i) {
 776    FixForeignFieldsInExtension(*file_->extension(i));
 777  }
 778  // Nested extensions.
 779  for (int i = 0; i < file_->message_type_count(); ++i) {
 780    FixForeignFieldsInNestedExtensions(*file_->message_type(i));
 781  }
 782}
 783
 784void Generator::FixForeignFieldsInExtension(
 785    const FieldDescriptor& extension_field) const {
 786  GOOGLE_CHECK(extension_field.is_extension());
 787  // extension_scope() will be NULL for top-level extensions, which is
 788  // exactly what FixForeignFieldsInField() wants.
 789  FixForeignFieldsInField(extension_field.extension_scope(), extension_field,
 790                          "extensions_by_name");
 791
 792  map<string, string> m;
 793  // Confusingly, for FieldDescriptors that happen to be extensions,
 794  // containing_type() means "extended type."
 795  // On the other hand, extension_scope() will give us what we normally
 796  // mean by containing_type().
 797  m["extended_message_class"] = ModuleLevelMessageName(
 798      *extension_field.containing_type());
 799  m["field"] = FieldReferencingExpression(extension_field.extension_scope(),
 800                                          extension_field,
 801                                          "extensions_by_name");
 802  printer_->Print(m, "$extended_message_class$.RegisterExtension($field$)\n");
 803}
 804
 805void Generator::FixForeignFieldsInNestedExtensions(
 806    const Descriptor& descriptor) const {
 807  // Recursively fix up extensions in all nested types.
 808  for (int i = 0; i < descriptor.nested_type_count(); ++i) {
 809    FixForeignFieldsInNestedExtensions(*descriptor.nested_type(i));
 810  }
 811  // Fix up extensions directly contained within this type.
 812  for (int i = 0; i < descriptor.extension_count(); ++i) {
 813    FixForeignFieldsInExtension(*descriptor.extension(i));
 814  }
 815}
 816
 817// Returns a Python expression that instantiates a Python EnumValueDescriptor
 818// object for the given C++ descriptor.
 819void Generator::PrintEnumValueDescriptor(
 820    const EnumValueDescriptor& descriptor) const {
 821  // TODO(robinson): Fix up EnumValueDescriptor "type" fields.
 822  // More circular references.  ::sigh::
 823  string options_string;
 824  descriptor.options().SerializeToString(&options_string);
 825  map<string, string> m;
 826  m["name"] = descriptor.name();
 827  m["index"] = SimpleItoa(descriptor.index());
 828  m["number"] = SimpleItoa(descriptor.number());
 829  m["options"] = OptionsValue("EnumValueOptions", options_string);
 830  printer_->Print(
 831      m,
 832      "descriptor.EnumValueDescriptor(\n"
 833      "  name='$name$', index=$index$, number=$number$,\n"
 834      "  options=$options$,\n"
 835      "  type=None)");
 836}
 837
 838// Returns a Python expression that calls descriptor._ParseOptions using
 839// the given descriptor class name and serialized options protobuf string.
 840string Generator::OptionsValue(
 841    const string& class_name, const string& serialized_options) const {
 842  if (serialized_options.length() == 0 || GeneratingDescriptorProto()) {
 843    return "None";
 844  } else {
 845    string full_class_name = "descriptor_pb2." + class_name;
 846    return "descriptor._ParseOptions(" + full_class_name + "(), '"
 847        + CEscape(serialized_options)+ "')";
 848  }
 849}
 850
 851// Prints an expression for a Python FieldDescriptor for |field|.
 852void Generator::PrintFieldDescriptor(
 853    const FieldDescriptor& field, bool is_extension) const {
 854  string options_string;
 855  field.options().SerializeToString(&options_string);
 856  map<string, string> m;
 857  m["name"] = field.name();
 858  m["full_name"] = field.full_name();
 859  m["index"] = SimpleItoa(field.index());
 860  m["number"] = SimpleItoa(field.number());
 861  m["type"] = SimpleItoa(field.type());
 862  m["cpp_type"] = SimpleItoa(field.cpp_type());
 863  m["label"] = SimpleItoa(field.label());
 864  m["has_default_value"] = field.has_default_value() ? "True" : "False";
 865  m["default_value"] = StringifyDefaultValue(field);
 866  m["is_extension"] = is_extension ? "True" : "False";
 867  m["options"] = OptionsValue("FieldOptions", options_string);
 868  // We always set message_type and enum_type to None at this point, and then
 869  // these fields in correctly after all referenced descriptors have been
 870  // defined and/or imported (see FixForeignFieldsInDescriptors()).
 871  const char field_descriptor_decl[] =
 872    "descriptor.FieldDescriptor(\n"
 873    "  name='$name$', full_name='$full_name$', index=$index$,\n"
 874    "  number=$number$, type=$type$, cpp_type=$cpp_type$, label=$label$,\n"
 875    "  has_default_value=$has_default_value$, default_value=$default_value$,\n"
 876    "  message_type=None, enum_type=None, containing_type=None,\n"
 877    "  is_extension=$is_extension$, extension_scope=None,\n"
 878    "  options=$options$)";
 879  printer_->Print(m, field_descriptor_decl);
 880}
 881
 882// Helper for Print{Fields,Extensions}InDescriptor().
 883void Generator::PrintFieldDescriptorsInDescriptor(
 884    const Descriptor& message_descriptor,
 885    bool is_extension,
 886    const string& list_variable_name,
 887    int (Descriptor::*CountFn)() const,
 888    const FieldDescriptor* (Descriptor::*GetterFn)(int) const) const {
 889  printer_->Print("$list$=[\n", "list", list_variable_name);
 890  printer_->Indent();
 891  for (int i = 0; i < (message_descriptor.*CountFn)(); ++i) {
 892    PrintFieldDescriptor(*(message_descriptor.*GetterFn)(i),
 893                         is_extension);
 894    printer_->Print(",\n");
 895  }
 896  printer_->Outdent();
 897  printer_->Print("],\n");
 898}
 899
 900// Prints a statement assigning "fields" to a list of Python FieldDescriptors,
 901// one for each field present in message_descriptor.
 902void Generator::PrintFieldsInDescriptor(
 903    const Descriptor& message_descriptor) const {
 904  const bool is_extension = false;
 905  PrintFieldDescriptorsInDescriptor(
 906      message_descriptor, is_extension, "fields",
 907      &Descriptor::field_count, &Descriptor::field);
 908}
 909
 910// Prints a statement assigning "extensions" to a list of Python
 911// FieldDescriptors, one for each extension present in message_descriptor.
 912void Generator::PrintExtensionsInDescriptor(
 913    const Descriptor& message_descriptor) const {
 914  const bool is_extension = true;
 915  PrintFieldDescriptorsInDescriptor(
 916      message_descriptor, is_extension, "extensions",
 917      &Descriptor::extension_count, &Descriptor::extension);
 918}
 919
 920bool Generator::GeneratingDescriptorProto() const {
 921  return file_->name() == "google/protobuf/descriptor.proto";
 922}
 923
 924// Returns the unique Python module-level identifier given to a descriptor.
 925// This name is module-qualified iff the given descriptor describes an
 926// entity that doesn't come from the current file.
 927template <typename DescriptorT>
 928string Generator::ModuleLevelDescriptorName(
 929    const DescriptorT& descriptor) const {
 930  // FIXME(robinson):
 931  // We currently don't worry about collisions with underscores in the type
 932  // names, so these would collide in nasty ways if found in the same file:
 933  //   OuterProto.ProtoA.ProtoB
 934  //   OuterProto_ProtoA.ProtoB  # Underscore instead of period.
 935  // As would these:
 936  //   OuterProto.ProtoA_.ProtoB
 937  //   OuterProto.ProtoA._ProtoB  # Leading vs. trailing underscore.
 938  // (Contrived, but certainly possible).
 939  //
 940  // The C++ implementation doesn't guard against this either.  Leaving
 941  // it for now...
 942  string name = NamePrefixedWithNestedTypes(descriptor, "_");
 943  UpperString(&name);
 944  // Module-private for now.  Easy to make public later; almost impossible
 945  // to make private later.
 946  name = "_" + name;
 947  // We now have the name relative to its own module.  Also qualify with
 948  // the module name iff this descriptor is from a different .proto file.
 949  if (descriptor.file() != file_) {
 950    name = ModuleName(descriptor.file()->name()) + "." + name;
 951  }
 952  return name;
 953}
 954
 955// Returns the name of the message class itself, not the descriptor.
 956// Like ModuleLevelDescriptorName(), module-qualifies the name iff
 957// the given descriptor describes an entity that doesn't come from
 958// the current file.
 959string Generator::ModuleLevelMessageName(const Descriptor& descriptor) const {
 960  string name = NamePrefixedWithNestedTypes(descriptor, ".");
 961  if (descriptor.file() != file_) {
 962    name = ModuleName(descriptor.file()->name()) + "." + name;
 963  }
 964  return name;
 965}
 966
 967// Returns the unique Python module-level identifier given to a service
 968// descriptor.
 969string Generator::ModuleLevelServiceDescriptorName(
 970    const ServiceDescriptor& descriptor) const {
 971  string name = descriptor.name();
 972  UpperString(&name);
 973  name = "_" + name;
 974  if (descriptor.file() != file_) {
 975    name = ModuleName(descriptor.file()->name()) + "." + name;
 976  }
 977  return name;
 978}
 979
 980// Prints standard constructor arguments serialized_start and serialized_end.
 981// Args:
 982//   descriptor: The cpp descriptor to have a serialized reference.
 983//   proto: A proto
 984// Example printer output:
 985// serialized_start=41,
 986// serialized_end=43,
 987//
 988template <typename DescriptorT, typename DescriptorProtoT>
 989void Generator::PrintSerializedPbInterval(
 990    const DescriptorT& descriptor, DescriptorProtoT& proto) const {
 991  descriptor.CopyTo(&proto);
 992  string sp;
 993  proto.SerializeToString(&sp);
 994  int offset = file_descriptor_serialized_.find(sp);
 995  GOOGLE_CHECK_GE(offset, 0);
 996
 997  printer_->Print("serialized_start=$serialized_start$,\n"
 998                  "serialized_end=$serialized_end$,\n",
 999                  "serialized_start", SimpleItoa(offset),
1000                  "serialized_end", SimpleItoa(offset + sp.size()));
1001}
1002
1003}  // namespace python
1004}  // namespace compiler
1005}  // namespace protobuf
1006}  // namespace google