| Index: third_party/protobuf/python/google/protobuf/pyext/descriptor_pool.cc
|
| diff --git a/third_party/protobuf/python/google/protobuf/pyext/descriptor_pool.cc b/third_party/protobuf/python/google/protobuf/pyext/descriptor_pool.cc
|
| index fa66bf9ace7091c59d36db93f463d27c8a3557e8..1faff96bc2e44c40a3aa8da0550f947cd67b40df 100644
|
| --- a/third_party/protobuf/python/google/protobuf/pyext/descriptor_pool.cc
|
| +++ b/third_party/protobuf/python/google/protobuf/pyext/descriptor_pool.cc
|
| @@ -33,11 +33,11 @@
|
| #include <Python.h>
|
|
|
| #include <google/protobuf/descriptor.pb.h>
|
| +#include <google/protobuf/dynamic_message.h>
|
| #include <google/protobuf/pyext/descriptor.h>
|
| #include <google/protobuf/pyext/descriptor_database.h>
|
| #include <google/protobuf/pyext/descriptor_pool.h>
|
| #include <google/protobuf/pyext/message.h>
|
| -#include <google/protobuf/pyext/message_factory.h>
|
| #include <google/protobuf/pyext/scoped_pyobject_ptr.h>
|
|
|
| #if PY_MAJOR_VERSION >= 3
|
| @@ -73,16 +73,18 @@ static PyDescriptorPool* _CreateDescriptorPool() {
|
| cpool->underlay = NULL;
|
| cpool->database = NULL;
|
|
|
| + DynamicMessageFactory* message_factory = new DynamicMessageFactory();
|
| + // This option might be the default some day.
|
| + message_factory->SetDelegateToGeneratedFactory(true);
|
| + cpool->message_factory = message_factory;
|
| +
|
| + // TODO(amauryfa): Rewrite the SymbolDatabase in C so that it uses the same
|
| + // storage.
|
| + cpool->classes_by_descriptor =
|
| + new PyDescriptorPool::ClassesByMessageMap();
|
| cpool->descriptor_options =
|
| new hash_map<const void*, PyObject *>();
|
|
|
| - cpool->py_message_factory = message_factory::NewMessageFactory(
|
| - &PyMessageFactory_Type, cpool);
|
| - if (cpool->py_message_factory == NULL) {
|
| - Py_DECREF(cpool);
|
| - return NULL;
|
| - }
|
| -
|
| return cpool;
|
| }
|
|
|
| @@ -149,14 +151,20 @@ static PyObject* New(PyTypeObject* type,
|
| }
|
|
|
| static void Dealloc(PyDescriptorPool* self) {
|
| + typedef PyDescriptorPool::ClassesByMessageMap::iterator iterator;
|
| descriptor_pool_map.erase(self->pool);
|
| - Py_CLEAR(self->py_message_factory);
|
| + for (iterator it = self->classes_by_descriptor->begin();
|
| + it != self->classes_by_descriptor->end(); ++it) {
|
| + Py_DECREF(it->second);
|
| + }
|
| + delete self->classes_by_descriptor;
|
| for (hash_map<const void*, PyObject*>::iterator it =
|
| self->descriptor_options->begin();
|
| it != self->descriptor_options->end(); ++it) {
|
| Py_DECREF(it->second);
|
| }
|
| delete self->descriptor_options;
|
| + delete self->message_factory;
|
| delete self->database;
|
| delete self->pool;
|
| Py_TYPE(self)->tp_free(reinterpret_cast<PyObject*>(self));
|
| @@ -180,8 +188,35 @@ PyObject* FindMessageByName(PyDescriptorPool* self, PyObject* arg) {
|
| return PyMessageDescriptor_FromDescriptor(message_descriptor);
|
| }
|
|
|
| +// Add a message class to our database.
|
| +int RegisterMessageClass(PyDescriptorPool* self,
|
| + const Descriptor* message_descriptor,
|
| + CMessageClass* message_class) {
|
| + Py_INCREF(message_class);
|
| + typedef PyDescriptorPool::ClassesByMessageMap::iterator iterator;
|
| + std::pair<iterator, bool> ret = self->classes_by_descriptor->insert(
|
| + std::make_pair(message_descriptor, message_class));
|
| + if (!ret.second) {
|
| + // Update case: DECREF the previous value.
|
| + Py_DECREF(ret.first->second);
|
| + ret.first->second = message_class;
|
| + }
|
| + return 0;
|
| +}
|
|
|
| -
|
| +// Retrieve the message class added to our database.
|
| +CMessageClass* GetMessageClass(PyDescriptorPool* self,
|
| + const Descriptor* message_descriptor) {
|
| + typedef PyDescriptorPool::ClassesByMessageMap::iterator iterator;
|
| + iterator ret = self->classes_by_descriptor->find(message_descriptor);
|
| + if (ret == self->classes_by_descriptor->end()) {
|
| + PyErr_Format(PyExc_TypeError, "No message class registered for '%s'",
|
| + message_descriptor->full_name().c_str());
|
| + return NULL;
|
| + } else {
|
| + return ret->second;
|
| + }
|
| +}
|
|
|
| PyObject* FindFileByName(PyDescriptorPool* self, PyObject* arg) {
|
| Py_ssize_t name_size;
|
| @@ -193,9 +228,11 @@ PyObject* FindFileByName(PyDescriptorPool* self, PyObject* arg) {
|
| const FileDescriptor* file_descriptor =
|
| self->pool->FindFileByName(string(name, name_size));
|
| if (file_descriptor == NULL) {
|
| - PyErr_Format(PyExc_KeyError, "Couldn't find file %.200s", name);
|
| + PyErr_Format(PyExc_KeyError, "Couldn't find file %.200s",
|
| + name);
|
| return NULL;
|
| }
|
| +
|
| return PyFileDescriptor_FromDescriptor(file_descriptor);
|
| }
|
|
|
| @@ -268,40 +305,6 @@ PyObject* FindOneofByName(PyDescriptorPool* self, PyObject* arg) {
|
| return PyOneofDescriptor_FromDescriptor(oneof_descriptor);
|
| }
|
|
|
| -PyObject* FindServiceByName(PyDescriptorPool* self, PyObject* arg) {
|
| - Py_ssize_t name_size;
|
| - char* name;
|
| - if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
|
| - return NULL;
|
| - }
|
| -
|
| - const ServiceDescriptor* service_descriptor =
|
| - self->pool->FindServiceByName(string(name, name_size));
|
| - if (service_descriptor == NULL) {
|
| - PyErr_Format(PyExc_KeyError, "Couldn't find service %.200s", name);
|
| - return NULL;
|
| - }
|
| -
|
| - return PyServiceDescriptor_FromDescriptor(service_descriptor);
|
| -}
|
| -
|
| -PyObject* FindMethodByName(PyDescriptorPool* self, PyObject* arg) {
|
| - Py_ssize_t name_size;
|
| - char* name;
|
| - if (PyString_AsStringAndSize(arg, &name, &name_size) < 0) {
|
| - return NULL;
|
| - }
|
| -
|
| - const MethodDescriptor* method_descriptor =
|
| - self->pool->FindMethodByName(string(name, name_size));
|
| - if (method_descriptor == NULL) {
|
| - PyErr_Format(PyExc_KeyError, "Couldn't find method %.200s", name);
|
| - return NULL;
|
| - }
|
| -
|
| - return PyMethodDescriptor_FromDescriptor(method_descriptor);
|
| -}
|
| -
|
| PyObject* FindFileContainingSymbol(PyDescriptorPool* self, PyObject* arg) {
|
| Py_ssize_t name_size;
|
| char* name;
|
| @@ -319,51 +322,6 @@ PyObject* FindFileContainingSymbol(PyDescriptorPool* self, PyObject* arg) {
|
| return PyFileDescriptor_FromDescriptor(file_descriptor);
|
| }
|
|
|
| -PyObject* FindExtensionByNumber(PyDescriptorPool* self, PyObject* args) {
|
| - PyObject* message_descriptor;
|
| - int number;
|
| - if (!PyArg_ParseTuple(args, "Oi", &message_descriptor, &number)) {
|
| - return NULL;
|
| - }
|
| - const Descriptor* descriptor = PyMessageDescriptor_AsDescriptor(
|
| - message_descriptor);
|
| - if (descriptor == NULL) {
|
| - return NULL;
|
| - }
|
| -
|
| - const FieldDescriptor* extension_descriptor =
|
| - self->pool->FindExtensionByNumber(descriptor, number);
|
| - if (extension_descriptor == NULL) {
|
| - PyErr_Format(PyExc_KeyError, "Couldn't find extension %d", number);
|
| - return NULL;
|
| - }
|
| -
|
| - return PyFieldDescriptor_FromDescriptor(extension_descriptor);
|
| -}
|
| -
|
| -PyObject* FindAllExtensions(PyDescriptorPool* self, PyObject* arg) {
|
| - const Descriptor* descriptor = PyMessageDescriptor_AsDescriptor(arg);
|
| - if (descriptor == NULL) {
|
| - return NULL;
|
| - }
|
| -
|
| - std::vector<const FieldDescriptor*> extensions;
|
| - self->pool->FindAllExtensions(descriptor, &extensions);
|
| -
|
| - ScopedPyObjectPtr result(PyList_New(extensions.size()));
|
| - if (result == NULL) {
|
| - return NULL;
|
| - }
|
| - for (int i = 0; i < extensions.size(); i++) {
|
| - PyObject* extension = PyFieldDescriptor_FromDescriptor(extensions[i]);
|
| - if (extension == NULL) {
|
| - return NULL;
|
| - }
|
| - PyList_SET_ITEM(result.get(), i, extension); // Steals the reference.
|
| - }
|
| - return result.release();
|
| -}
|
| -
|
| // These functions should not exist -- the only valid way to create
|
| // descriptors is to call Add() or AddSerializedFile().
|
| // But these AddDescriptor() functions were created in Python and some people
|
| @@ -421,22 +379,6 @@ PyObject* AddEnumDescriptor(PyDescriptorPool* self, PyObject* descriptor) {
|
| Py_RETURN_NONE;
|
| }
|
|
|
| -PyObject* AddExtensionDescriptor(PyDescriptorPool* self, PyObject* descriptor) {
|
| - const FieldDescriptor* extension_descriptor =
|
| - PyFieldDescriptor_AsDescriptor(descriptor);
|
| - if (!extension_descriptor) {
|
| - return NULL;
|
| - }
|
| - if (extension_descriptor !=
|
| - self->pool->FindExtensionByName(extension_descriptor->full_name())) {
|
| - PyErr_Format(PyExc_ValueError,
|
| - "The extension descriptor %s does not belong to this pool",
|
| - extension_descriptor->full_name().c_str());
|
| - return NULL;
|
| - }
|
| - Py_RETURN_NONE;
|
| -}
|
| -
|
| // The code below loads new Descriptors from a serialized FileDescriptorProto.
|
|
|
|
|
| @@ -536,8 +478,6 @@ static PyMethodDef Methods[] = {
|
| "No-op. Add() must have been called before." },
|
| { "AddEnumDescriptor", (PyCFunction)AddEnumDescriptor, METH_O,
|
| "No-op. Add() must have been called before." },
|
| - { "AddExtensionDescriptor", (PyCFunction)AddExtensionDescriptor, METH_O,
|
| - "No-op. Add() must have been called before." },
|
|
|
| { "FindFileByName", (PyCFunction)FindFileByName, METH_O,
|
| "Searches for a file descriptor by its .proto name." },
|
| @@ -551,17 +491,9 @@ static PyMethodDef Methods[] = {
|
| "Searches for enum type descriptor by full name." },
|
| { "FindOneofByName", (PyCFunction)FindOneofByName, METH_O,
|
| "Searches for oneof descriptor by full name." },
|
| - { "FindServiceByName", (PyCFunction)FindServiceByName, METH_O,
|
| - "Searches for service descriptor by full name." },
|
| - { "FindMethodByName", (PyCFunction)FindMethodByName, METH_O,
|
| - "Searches for method descriptor by full name." },
|
|
|
| { "FindFileContainingSymbol", (PyCFunction)FindFileContainingSymbol, METH_O,
|
| "Gets the FileDescriptor containing the specified symbol." },
|
| - { "FindExtensionByNumber", (PyCFunction)FindExtensionByNumber, METH_VARARGS,
|
| - "Gets the extension descriptor for the given number." },
|
| - { "FindAllExtensions", (PyCFunction)FindAllExtensions, METH_O,
|
| - "Gets all known extensions of the given message descriptor." },
|
| {NULL}
|
| };
|
|
|
|
|