1 // Protocol Buffers - Google's data interchange format
2 // Copyright 2014 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 <php.h>
32 #include <Zend/zend_exceptions.h>
33 #include <stdlib.h>
34 #include <inttypes.h>
35 
36 #if PHP_MAJOR_VERSION < 7
37 #include <Zend/zend_compile.h>
38 #else
39 #include <Zend/zend_inheritance.h>
40 #endif
41 
42 #include "protobuf.h"
43 #include "utf8.h"
44 
45 zend_class_entry* message_type;
46 zend_object_handlers* message_handlers;
47 static const char TYPE_URL_PREFIX[] = "type.googleapis.com/";
48 static void hex_to_binary(const char* hex, char** binary, int* binary_len);
49 
50 static  zend_function_entry message_methods[] = {
51   PHP_ME(Message, clear, NULL, ZEND_ACC_PUBLIC)
52   PHP_ME(Message, discardUnknownFields, NULL, ZEND_ACC_PUBLIC)
53   PHP_ME(Message, serializeToString, NULL, ZEND_ACC_PUBLIC)
54   PHP_ME(Message, mergeFromString, NULL, ZEND_ACC_PUBLIC)
55   PHP_ME(Message, serializeToJsonString, NULL, ZEND_ACC_PUBLIC)
56   PHP_ME(Message, mergeFromJsonString, NULL, ZEND_ACC_PUBLIC)
57   PHP_ME(Message, mergeFrom, NULL, ZEND_ACC_PUBLIC)
58   PHP_ME(Message, readOneof, NULL, ZEND_ACC_PROTECTED)
59   PHP_ME(Message, writeOneof, NULL, ZEND_ACC_PROTECTED)
60   PHP_ME(Message, whichOneof, NULL, ZEND_ACC_PROTECTED)
61   PHP_ME(Message, __construct, NULL, ZEND_ACC_PROTECTED)
62   {NULL, NULL, NULL}
63 };
64 
65 // Forward declare static functions.
66 
67 #if PHP_MAJOR_VERSION < 7
68 static void message_set_property(zval* object, zval* member, zval* value,
69                                  php_proto_zend_literal key TSRMLS_DC);
70 static zval* message_get_property(zval* object, zval* member, int type,
71                                   const zend_literal* key TSRMLS_DC);
72 static zval** message_get_property_ptr_ptr(zval* object, zval* member, int type,
73                                            php_proto_zend_literal key TSRMLS_DC);
74 static HashTable* message_get_gc(zval* object, zval*** table, int* n TSRMLS_DC);
75 #else
76 static void message_set_property(zval* object, zval* member, zval* value,
77                                  void** cache_slot);
78 static zval* message_get_property(zval* object, zval* member, int type,
79                                   void** cache_slot, zval* rv);
80 static zval* message_get_property_ptr_ptr(zval* object, zval* member, int type,
81                                           void** cache_slot);
82 static HashTable* message_get_gc(zval* object, zval** table, int* n);
83 #endif
84 static HashTable* message_get_properties(zval* object TSRMLS_DC);
85 
86 // -----------------------------------------------------------------------------
87 // PHP Message Handlers
88 // -----------------------------------------------------------------------------
89 
90 // Define object free method.
91 PHP_PROTO_OBJECT_FREE_START(MessageHeader, message)
92   if (*(void**)intern->data != NULL) {
93     stringsink_uninit_opaque(*(void**)intern->data);
94     FREE(*(void**)intern->data);
95   }
96   FREE(intern->data);
97 PHP_PROTO_OBJECT_FREE_END
98 
99 PHP_PROTO_OBJECT_DTOR_START(MessageHeader, message)
100 PHP_PROTO_OBJECT_DTOR_END
101 
102 // Define object create method.
103 PHP_PROTO_OBJECT_CREATE_START(MessageHeader, message)
104 // Because php call this create func before calling the sub-message's
105 // constructor defined in PHP, it's possible that the decriptor of this class
106 // hasn't been added to descritpor pool (when the class is first
107 // instantiated). In that case, we will defer the initialization of the custom
108 // data to the parent Message's constructor, which will be called by
109 // sub-message's constructors after the descriptor has been added.
110 PHP_PROTO_OBJECT_CREATE_END(MessageHeader, message)
111 
112 // Init class entry.
113 PHP_PROTO_INIT_CLASS_START("Google\\Protobuf\\Internal\\Message",
114                            MessageHeader, message)
115   message_handlers->write_property = message_set_property;
116   message_handlers->read_property = message_get_property;
117   message_handlers->get_property_ptr_ptr = message_get_property_ptr_ptr;
118   message_handlers->get_properties = message_get_properties;
119   message_handlers->get_gc = message_get_gc;
120 PHP_PROTO_INIT_CLASS_END
121 
message_set_property_internal(zval * object,zval * member,zval * value TSRMLS_DC)122 static void message_set_property_internal(zval* object, zval* member,
123                                           zval* value TSRMLS_DC) {
124   const upb_fielddef* field;
125 
126   MessageHeader* self = UNBOX(MessageHeader, object);
127 
128   field = upb_msgdef_ntofz(self->descriptor->msgdef, Z_STRVAL_P(member));
129   if (field == NULL) {
130     zend_error(E_USER_ERROR, "Unknown field: %s", Z_STRVAL_P(member));
131   }
132 
133   layout_set(self->descriptor->layout, self, field, value TSRMLS_CC);
134 }
135 
136 #if PHP_MAJOR_VERSION < 7
message_set_property(zval * object,zval * member,zval * value,php_proto_zend_literal key TSRMLS_DC)137 static void message_set_property(zval* object, zval* member, zval* value,
138                                  php_proto_zend_literal key TSRMLS_DC) {
139 #else
140 static void message_set_property(zval* object, zval* member, zval* value,
141                                  void** cache_slot) {
142 #endif
143   if (Z_TYPE_P(member) != IS_STRING) {
144     zend_error(E_USER_ERROR, "Unexpected type for field name");
145     return;
146   }
147 
148 #if PHP_MAJOR_VERSION < 7 || (PHP_MAJOR_VERSION == 7 && PHP_MINOR_VERSION == 0)
149   if (Z_OBJCE_P(object) != EG(scope)) {
150 #else
151   if (Z_OBJCE_P(object) != zend_get_executed_scope()) {
152 #endif
153     // User cannot set property directly (e.g., $m->a = 1)
154     zend_error(E_USER_ERROR, "Cannot access private property.");
155     return;
156   }
157 
158   message_set_property_internal(object, member, value TSRMLS_CC);
159 }
160 
161 static zval* message_get_property_internal(zval* object,
162                                            zval* member TSRMLS_DC) {
163   MessageHeader* self = UNBOX(MessageHeader, object);
164   const upb_fielddef* field;
165   field = upb_msgdef_ntofz(self->descriptor->msgdef, Z_STRVAL_P(member));
166   if (field == NULL) {
167     return PHP_PROTO_GLOBAL_UNINITIALIZED_ZVAL;
168   }
169 
170   zend_property_info* property_info;
171 #if PHP_MAJOR_VERSION < 7
172   property_info =
173       zend_get_property_info(Z_OBJCE_P(object), member, true TSRMLS_CC);
174 #else
175   property_info =
176       zend_get_property_info(Z_OBJCE_P(object), Z_STR_P(member), true);
177 #endif
178   return layout_get(
179       self->descriptor->layout, message_data(self), field,
180       OBJ_PROP(Z_OBJ_P(object), property_info->offset) TSRMLS_CC);
181 }
182 
183 static void message_get_oneof_property_internal(zval* object, zval* member,
184                                                 zval* return_value TSRMLS_DC) {
185   MessageHeader* self = UNBOX(MessageHeader, object);
186   const upb_fielddef* field;
187   field = upb_msgdef_ntofz(self->descriptor->msgdef, Z_STRVAL_P(member));
188   if (field == NULL) {
189     return;
190   }
191 
192   layout_get(self->descriptor->layout, message_data(self), field,
193              ZVAL_PTR_TO_CACHED_PTR(return_value) TSRMLS_CC);
194 }
195 
196 #if PHP_MAJOR_VERSION < 7
197 static zval* message_get_property(zval* object, zval* member, int type,
198                                   const zend_literal* key TSRMLS_DC) {
199 #else
200 static zval* message_get_property(zval* object, zval* member, int type,
201                                   void** cache_slot, zval* rv) {
202 #endif
203   if (Z_TYPE_P(member) != IS_STRING) {
204     zend_error(E_USER_ERROR, "Property name has to be a string.");
205     return PHP_PROTO_GLOBAL_UNINITIALIZED_ZVAL;
206   }
207 
208 #if PHP_MAJOR_VERSION < 7 || (PHP_MAJOR_VERSION == 7 && PHP_MINOR_VERSION == 0)
209   if (Z_OBJCE_P(object) != EG(scope)) {
210 #else
211   if (Z_OBJCE_P(object) != zend_get_executed_scope()) {
212 #endif
213     // User cannot get property directly (e.g., $a = $m->a)
214     zend_error(E_USER_ERROR, "Cannot access private property.");
215     return PHP_PROTO_GLOBAL_UNINITIALIZED_ZVAL;
216   }
217 
218   return message_get_property_internal(object, member TSRMLS_CC);
219 }
220 
221 #if PHP_MAJOR_VERSION < 7
222 static zval** message_get_property_ptr_ptr(zval* object, zval* member, int type,
223                                            php_proto_zend_literal key
224                                                TSRMLS_DC) {
225 #else
226 static zval* message_get_property_ptr_ptr(zval* object, zval* member, int type,
227                                           void** cache_slot) {
228 #endif
229   return NULL;
230 }
231 
232 static HashTable* message_get_properties(zval* object TSRMLS_DC) {
233   return NULL;
234 }
235 
236 static HashTable* message_get_gc(zval* object, CACHED_VALUE** table,
237                                  int* n TSRMLS_DC) {
238   zend_object* zobj = Z_OBJ_P(object);
239   *table = zobj->properties_table;
240   *n = zobj->ce->default_properties_count;
241   return NULL;
242 }
243 
244 // -----------------------------------------------------------------------------
245 // C Message Utilities
246 // -----------------------------------------------------------------------------
247 
248 void* message_data(MessageHeader* msg) {
249   return msg->data;
250 }
251 
252 void custom_data_init(const zend_class_entry* ce,
253                       MessageHeader* intern PHP_PROTO_TSRMLS_DC) {
254   Descriptor* desc = UNBOX_HASHTABLE_VALUE(Descriptor, get_ce_obj(ce));
255   intern->data = ALLOC_N(uint8_t, desc->layout->size);
256   memset(message_data(intern), 0, desc->layout->size);
257   // We wrap first so that everything in the message object is GC-rooted in
258   // case a collection happens during object creation in layout_init().
259   intern->descriptor = desc;
260   layout_init(desc->layout, message_data(intern),
261               &intern->std PHP_PROTO_TSRMLS_CC);
262 }
263 
264 #define INIT_MESSAGE_WITH_ARRAY                                    \
265   {                                                                \
266     zval* array_wrapper = NULL;                                    \
267     if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC,           \
268                               "|a!", &array_wrapper) == FAILURE) { \
269       return;                                                      \
270     }                                                              \
271     Message_construct(getThis(), array_wrapper);                   \
272   }
273 
274 void build_class_from_descriptor(
275     PHP_PROTO_HASHTABLE_VALUE php_descriptor TSRMLS_DC) {
276   Descriptor* desc = UNBOX_HASHTABLE_VALUE(Descriptor, php_descriptor);
277 
278   // Map entries don't have existing php class.
279   if (upb_msgdef_mapentry(desc->msgdef)) {
280     return;
281   }
282 
283   zend_class_entry* registered_ce = desc->klass;
284 
285   if (desc->layout == NULL) {
286     MessageLayout* layout = create_layout(desc->msgdef);
287     desc->layout = layout;
288   }
289 
290   registered_ce->create_object = message_create;
291 }
292 
293 // -----------------------------------------------------------------------------
294 // PHP Methods
295 // -----------------------------------------------------------------------------
296 
297 static bool is_wrapper_msg(const upb_msgdef* m) {
298   upb_wellknowntype_t type = upb_msgdef_wellknowntype(m);
299   return type >= UPB_WELLKNOWN_DOUBLEVALUE &&
300          type <= UPB_WELLKNOWN_BOOLVALUE;
301 }
302 
303 static void append_wrapper_message(
304     zend_class_entry* subklass, RepeatedField* intern, zval* value TSRMLS_DC) {
305   MessageHeader* submsg;
306   const upb_fielddef* field;
307 #if PHP_MAJOR_VERSION < 7
308   zval* val = NULL;
309   MAKE_STD_ZVAL(val);
310   ZVAL_OBJ(val, subklass->create_object(subklass TSRMLS_CC));
311   repeated_field_push_native(intern, &val);
312   submsg = UNBOX(MessageHeader, val);
313 #else
314   zend_object* obj = subklass->create_object(subklass TSRMLS_CC);
315   repeated_field_push_native(intern, &obj);
316   submsg = (MessageHeader*)((char*)obj - XtOffsetOf(MessageHeader, std));
317 #endif
318   custom_data_init(subklass, submsg PHP_PROTO_TSRMLS_CC);
319 
320   field = upb_msgdef_itof(submsg->descriptor->msgdef, 1);
321   layout_set(submsg->descriptor->layout, submsg, field, value TSRMLS_CC);
322 }
323 
324 static void set_wrapper_message_as_map_value(
325     zend_class_entry* subklass, zval* map, zval* key,  zval* value TSRMLS_DC) {
326   MessageHeader* submsg;
327   const upb_fielddef* field;
328 #if PHP_MAJOR_VERSION < 7
329   zval* val = NULL;
330   MAKE_STD_ZVAL(val);
331   ZVAL_OBJ(val, subklass->create_object(subklass TSRMLS_CC));
332   map_field_handlers->write_dimension(
333       map, key, val TSRMLS_CC);
334   submsg = UNBOX(MessageHeader, val);
335 #else
336   zval val;
337   zend_object* obj = subklass->create_object(subklass TSRMLS_CC);
338   ZVAL_OBJ(&val, obj);
339   map_field_handlers->write_dimension(map, key, &val TSRMLS_CC);
340   submsg = (MessageHeader*)((char*)obj - XtOffsetOf(MessageHeader, std));
341 #endif
342   custom_data_init(subklass, submsg PHP_PROTO_TSRMLS_CC);
343 
344   field = upb_msgdef_itof(submsg->descriptor->msgdef, 1);
345   layout_set(submsg->descriptor->layout, submsg, field, value TSRMLS_CC);
346 }
347 
348 void Message_construct(zval* msg, zval* array_wrapper) {
349   TSRMLS_FETCH();
350   zend_class_entry* ce = Z_OBJCE_P(msg);
351   MessageHeader* intern = NULL;
352   if (EXPECTED(class_added(ce))) {
353     intern = UNBOX(MessageHeader, msg);
354     custom_data_init(ce, intern PHP_PROTO_TSRMLS_CC);
355   }
356 
357   if (array_wrapper == NULL) {
358     return;
359   }
360 
361   HashTable* array = Z_ARRVAL_P(array_wrapper);
362   HashPosition pointer;
363   zval key;
364   void* value;
365   const upb_fielddef* field;
366 
367   for (zend_hash_internal_pointer_reset_ex(array, &pointer);
368        php_proto_zend_hash_get_current_data_ex(array, (void**)&value,
369                                                &pointer) == SUCCESS;
370        zend_hash_move_forward_ex(array, &pointer)) {
371     zend_hash_get_current_key_zval_ex(array, &key, &pointer);
372     field = upb_msgdef_ntofz(intern->descriptor->msgdef, Z_STRVAL_P(&key));
373 #if PHP_MAJOR_VERSION >= 7
374     if (Z_ISREF_P((CACHED_VALUE*)value)) {
375       value = Z_REFVAL_P((CACHED_VALUE*)value);
376     }
377 #endif
378     if (field == NULL) {
379       zend_error(E_USER_ERROR, "Unknown field: %s", Z_STRVAL_P(&key));
380     }
381     if (upb_fielddef_ismap(field)) {
382       PHP_PROTO_FAKE_SCOPE_BEGIN(Z_OBJCE_P(msg));
383       zval* submap = message_get_property_internal(msg, &key TSRMLS_CC);
384       PHP_PROTO_FAKE_SCOPE_END;
385       HashTable* subtable = HASH_OF(
386           CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)value));
387       HashPosition subpointer;
388       zval subkey;
389       void* memory;
390       bool is_wrapper = false;
391       zend_class_entry* subklass = NULL;
392       const upb_msgdef* mapentry = upb_fielddef_msgsubdef(field);
393       const upb_fielddef *value_field = upb_msgdef_itof(mapentry, 2);
394 
395       if (upb_fielddef_issubmsg(value_field)) {
396         const upb_msgdef* submsgdef = upb_fielddef_msgsubdef(value_field);
397         upb_wellknowntype_t type = upb_msgdef_wellknowntype(submsgdef);
398         is_wrapper = is_wrapper_msg(submsgdef);
399 
400         if (is_wrapper) {
401           PHP_PROTO_HASHTABLE_VALUE subdesc_php = get_def_obj(submsgdef);
402           Descriptor* subdesc = UNBOX_HASHTABLE_VALUE(Descriptor, subdesc_php);
403           subklass = subdesc->klass;
404         }
405       }
406 
407       for (zend_hash_internal_pointer_reset_ex(subtable, &subpointer);
408            php_proto_zend_hash_get_current_data_ex(subtable, (void**)&memory,
409                                                    &subpointer) == SUCCESS;
410            zend_hash_move_forward_ex(subtable, &subpointer)) {
411         zend_hash_get_current_key_zval_ex(subtable, &subkey, &subpointer);
412         if (is_wrapper &&
413             Z_TYPE_P(CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)memory)) != IS_OBJECT) {
414           set_wrapper_message_as_map_value(
415               subklass, submap, &subkey,
416               CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)memory) TSRMLS_CC);
417         } else {
418           map_field_handlers->write_dimension(
419               submap, &subkey,
420               CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)memory) TSRMLS_CC);
421         }
422         zval_dtor(&subkey);
423       }
424     } else if (upb_fielddef_isseq(field)) {
425       PHP_PROTO_FAKE_SCOPE_BEGIN(Z_OBJCE_P(msg));
426       zval* subarray = message_get_property_internal(msg, &key TSRMLS_CC);
427       PHP_PROTO_FAKE_SCOPE_END;
428       HashTable* subtable = HASH_OF(
429           CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)value));
430       HashPosition subpointer;
431       void* memory;
432       bool is_wrapper = false;
433       zend_class_entry* subklass = NULL;
434 
435       if (upb_fielddef_issubmsg(field)) {
436         const upb_msgdef* submsgdef = upb_fielddef_msgsubdef(field);
437         upb_wellknowntype_t type = upb_msgdef_wellknowntype(submsgdef);
438         is_wrapper = is_wrapper_msg(submsgdef);
439 
440         if (is_wrapper) {
441           PHP_PROTO_HASHTABLE_VALUE subdesc_php = get_def_obj(submsgdef);
442           Descriptor* subdesc = UNBOX_HASHTABLE_VALUE(Descriptor, subdesc_php);
443           subklass = subdesc->klass;
444         }
445       }
446 
447       for (zend_hash_internal_pointer_reset_ex(subtable, &subpointer);
448            php_proto_zend_hash_get_current_data_ex(subtable, (void**)&memory,
449                                                    &subpointer) == SUCCESS;
450            zend_hash_move_forward_ex(subtable, &subpointer)) {
451         if (is_wrapper &&
452             Z_TYPE_P(CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)memory)) != IS_OBJECT) {
453           RepeatedField* intern = UNBOX(RepeatedField, subarray);
454           append_wrapper_message(
455               subklass, intern,
456               CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)memory) TSRMLS_CC);
457         } else {
458           repeated_field_handlers->write_dimension(
459               subarray, NULL,
460               CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)memory) TSRMLS_CC);
461         }
462       }
463     } else if (upb_fielddef_issubmsg(field)) {
464       const upb_msgdef* submsgdef = upb_fielddef_msgsubdef(field);
465       PHP_PROTO_HASHTABLE_VALUE desc_php = get_def_obj(submsgdef);
466       Descriptor* desc = UNBOX_HASHTABLE_VALUE(Descriptor, desc_php);
467 
468       CACHED_VALUE* cached = NULL;
469       if (upb_fielddef_containingoneof(field)) {
470         void* memory = slot_memory(intern->descriptor->layout,
471                                    message_data(intern), field);
472         uint32_t* oneof_case = slot_oneof_case(intern->descriptor->layout,
473                                                message_data(intern), field);
474         int property_cache_index =
475             intern->descriptor->layout->fields[upb_fielddef_index(field)]
476                 .cache_index;
477         cached = OBJ_PROP(Z_OBJ_P(msg), property_cache_index);
478         *(CACHED_VALUE**)(memory) = cached;
479         *oneof_case = upb_fielddef_number(field);
480       } else {
481         zend_property_info* property_info;
482         PHP_PROTO_FAKE_SCOPE_BEGIN(Z_OBJCE_P(msg));
483 #if PHP_MAJOR_VERSION < 7
484         property_info =
485             zend_get_property_info(Z_OBJCE_P(msg), &key, true TSRMLS_CC);
486 #else
487         property_info =
488             zend_get_property_info(Z_OBJCE_P(msg), Z_STR_P(&key), true);
489 #endif
490         PHP_PROTO_FAKE_SCOPE_END;
491         cached = OBJ_PROP(Z_OBJ_P(msg), property_info->offset);
492       }
493 #if PHP_MAJOR_VERSION < 7
494       SEPARATE_ZVAL_IF_NOT_REF(cached);
495 #endif
496       zval* submsg = CACHED_PTR_TO_ZVAL_PTR(cached);
497       ZVAL_OBJ(submsg, desc->klass->create_object(desc->klass TSRMLS_CC));
498       Message_construct(submsg, NULL);
499       MessageHeader* to = UNBOX(MessageHeader, submsg);
500       const upb_filedef *file = upb_msgdef_file(submsgdef);
501       if (!strcmp(upb_filedef_name(file), "google/protobuf/wrappers.proto") &&
502           Z_TYPE_P(CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)value)) != IS_OBJECT) {
503         const upb_fielddef *value_field = upb_msgdef_itof(submsgdef, 1);
504         layout_set(to->descriptor->layout, to,
505                    value_field, CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)value)
506                    TSRMLS_CC);
507       } else {
508         MessageHeader* from =
509             UNBOX(MessageHeader,
510                   CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)value));
511         if(from->descriptor != to->descriptor) {
512           zend_error(E_USER_ERROR,
513                      "Cannot merge messages with different class.");
514           return;
515         }
516 
517         layout_merge(from->descriptor->layout, from, to TSRMLS_CC);
518       }
519     } else {
520       message_set_property_internal(msg, &key,
521           CACHED_PTR_TO_ZVAL_PTR((CACHED_VALUE*)value) TSRMLS_CC);
522     }
523     zval_dtor(&key);
524   }
525 }
526 
527 // At the first time the message is created, the class entry hasn't been
528 // modified. As a result, the first created instance will be a normal zend
529 // object. Here, we manually modify it to our message in such a case.
530 PHP_METHOD(Message, __construct) {
531   INIT_MESSAGE_WITH_ARRAY;
532 }
533 
534 PHP_METHOD(Message, clear) {
535   MessageHeader* msg = UNBOX(MessageHeader, getThis());
536   Descriptor* desc = msg->descriptor;
537   zend_class_entry* ce = desc->klass;
538 
539   zend_object_std_dtor(&msg->std TSRMLS_CC);
540   object_properties_init(&msg->std, ce);
541 
542   layout_init(desc->layout, message_data(msg), &msg->std TSRMLS_CC);
543 }
544 
545 PHP_METHOD(Message, mergeFrom) {
546   zval* value;
547   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "O", &value,
548                             message_type) == FAILURE) {
549     return;
550   }
551 
552   MessageHeader* from = UNBOX(MessageHeader, value);
553   MessageHeader* to = UNBOX(MessageHeader, getThis());
554 
555   if(from->descriptor != to->descriptor) {
556     zend_error(E_USER_ERROR, "Cannot merge messages with different class.");
557     return;
558   }
559 
560   layout_merge(from->descriptor->layout, from, to TSRMLS_CC);
561 }
562 
563 PHP_METHOD(Message, readOneof) {
564   PHP_PROTO_LONG index;
565 
566   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &index) ==
567       FAILURE) {
568     return;
569   }
570 
571   MessageHeader* msg = UNBOX(MessageHeader, getThis());
572 
573   const upb_fielddef* field = upb_msgdef_itof(msg->descriptor->msgdef, index);
574 
575   // Unlike singular fields, oneof fields share cached property. So we cannot
576   // let lay_get modify the cached property. Instead, we pass in the return
577   // value directly.
578   layout_get(msg->descriptor->layout, message_data(msg), field,
579              ZVAL_PTR_TO_CACHED_PTR(return_value) TSRMLS_CC);
580 }
581 
582 PHP_METHOD(Message, writeOneof) {
583   PHP_PROTO_LONG index;
584   zval* value;
585   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "lz", &index, &value) ==
586       FAILURE) {
587     return;
588   }
589 
590   MessageHeader* msg = UNBOX(MessageHeader, getThis());
591 
592   const upb_fielddef* field = upb_msgdef_itof(msg->descriptor->msgdef, index);
593 
594   layout_set(msg->descriptor->layout, msg, field, value TSRMLS_CC);
595 }
596 
597 PHP_METHOD(Message, whichOneof) {
598   char* oneof_name;
599   PHP_PROTO_SIZE length;
600 
601   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &oneof_name,
602                             &length) == FAILURE) {
603     return;
604   }
605 
606   MessageHeader* msg = UNBOX(MessageHeader, getThis());
607 
608   const upb_oneofdef* oneof =
609       upb_msgdef_ntoo(msg->descriptor->msgdef, oneof_name, length);
610   const char* oneof_case_name = layout_get_oneof_case(
611       msg->descriptor->layout, message_data(msg), oneof TSRMLS_CC);
612   PHP_PROTO_RETURN_STRING(oneof_case_name, 1);
613 }
614 
615 // -----------------------------------------------------------------------------
616 // Well Known Types Support
617 // -----------------------------------------------------------------------------
618 
619 #define PHP_PROTO_FIELD_ACCESSORS(UPPER_CLASS, LOWER_CLASS, UPPER_FIELD,       \
620                                   LOWER_FIELD)                                 \
621   PHP_METHOD(UPPER_CLASS, get##UPPER_FIELD) {                                  \
622     zval member;                                                               \
623     PHP_PROTO_ZVAL_STRING(&member, LOWER_FIELD, 1);                            \
624     PHP_PROTO_FAKE_SCOPE_BEGIN(LOWER_CLASS##_type);                            \
625     zval* value = message_get_property_internal(getThis(), &member TSRMLS_CC); \
626     PHP_PROTO_FAKE_SCOPE_END;                                                  \
627     zval_dtor(&member);                                                        \
628     PHP_PROTO_RETVAL_ZVAL(value);                                              \
629   }                                                                            \
630   PHP_METHOD(UPPER_CLASS, set##UPPER_FIELD) {                                  \
631     zval* value = NULL;                                                        \
632     if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "z", &value) ==       \
633         FAILURE) {                                                             \
634       return;                                                                  \
635     }                                                                          \
636     zval member;                                                               \
637     PHP_PROTO_ZVAL_STRING(&member, LOWER_FIELD, 1);                            \
638     message_set_property_internal(getThis(), &member, value TSRMLS_CC);        \
639     zval_dtor(&member);                                                        \
640     PHP_PROTO_RETVAL_ZVAL(getThis());                                          \
641   }
642 
643 #define PHP_PROTO_ONEOF_FIELD_ACCESSORS(UPPER_CLASS, LOWER_CLASS, UPPER_FIELD, \
644                                         LOWER_FIELD)                           \
645   PHP_METHOD(UPPER_CLASS, get##UPPER_FIELD) {                                  \
646     zval member;                                                               \
647     PHP_PROTO_ZVAL_STRING(&member, LOWER_FIELD, 1);                            \
648     PHP_PROTO_FAKE_SCOPE_BEGIN(LOWER_CLASS##_type);                            \
649     message_get_oneof_property_internal(getThis(), &member,                    \
650                                         return_value TSRMLS_CC);               \
651     PHP_PROTO_FAKE_SCOPE_END;                                                  \
652     zval_dtor(&member);                                                        \
653   }                                                                            \
654   PHP_METHOD(UPPER_CLASS, set##UPPER_FIELD) {                                  \
655     zval* value = NULL;                                                        \
656     if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "z", &value) ==       \
657         FAILURE) {                                                             \
658       return;                                                                  \
659     }                                                                          \
660     zval member;                                                               \
661     PHP_PROTO_ZVAL_STRING(&member, LOWER_FIELD, 1);                            \
662     message_set_property_internal(getThis(), &member, value TSRMLS_CC);        \
663     zval_dtor(&member);                                                        \
664     PHP_PROTO_RETVAL_ZVAL(getThis());                                          \
665   }
666 
667 #define PHP_PROTO_ONEOF_ACCESSORS(UPPER_CLASS, LOWER_CLASS, UPPER_FIELD, \
668                                   LOWER_FIELD)                           \
669   PHP_METHOD(UPPER_CLASS, get##UPPER_FIELD) {                            \
670     MessageHeader* msg = UNBOX(MessageHeader, getThis());                \
671     PHP_PROTO_FAKE_SCOPE_BEGIN(LOWER_CLASS##_type);                      \
672     const upb_oneofdef* oneof = upb_msgdef_ntoo(                         \
673         msg->descriptor->msgdef, LOWER_FIELD, strlen(LOWER_FIELD));      \
674     const char* oneof_case_name = layout_get_oneof_case(                 \
675         msg->descriptor->layout, message_data(msg), oneof TSRMLS_CC);    \
676     PHP_PROTO_FAKE_SCOPE_END;                                            \
677     PHP_PROTO_RETURN_STRING(oneof_case_name, 1);                         \
678   }
679 
680 // Forward declare file init functions
681 static void init_file_any(TSRMLS_D);
682 static void init_file_api(TSRMLS_D);
683 static void init_file_duration(TSRMLS_D);
684 static void init_file_field_mask(TSRMLS_D);
685 static void init_file_empty(TSRMLS_D);
686 static void init_file_source_context(TSRMLS_D);
687 static void init_file_struct(TSRMLS_D);
688 static void init_file_timestamp(TSRMLS_D);
689 static void init_file_type(TSRMLS_D);
690 static void init_file_wrappers(TSRMLS_D);
691 
692 // Define file init functions
693 static void init_file_any(TSRMLS_D) {
694   if (is_inited_file_any) return;
695   init_generated_pool_once(TSRMLS_C);
696   const char* generated_file =
697       "0acd010a19676f6f676c652f70726f746f6275662f616e792e70726f746f"
698       "120f676f6f676c652e70726f746f62756622260a03416e7912100a087479"
699       "70655f75726c180120012809120d0a0576616c756518022001280c426f0a"
700       "13636f6d2e676f6f676c652e70726f746f6275664208416e7950726f746f"
701       "50015a256769746875622e636f6d2f676f6c616e672f70726f746f627566"
702       "2f7074797065732f616e79a20203475042aa021e476f6f676c652e50726f"
703       "746f6275662e57656c6c4b6e6f776e5479706573620670726f746f33";
704   char* binary;
705   int binary_len;
706   hex_to_binary(generated_file, &binary, &binary_len);
707   internal_add_generated_file(binary, binary_len,
708                               generated_pool, true TSRMLS_CC);
709   FREE(binary);
710   is_inited_file_any = true;
711 }
712 
713 static void init_file_api(TSRMLS_D) {
714   if (is_inited_file_api) return;
715   init_file_source_context(TSRMLS_C);
716   init_file_type(TSRMLS_C);
717   init_generated_pool_once(TSRMLS_C);
718   const char* generated_file =
719       "0aee050a19676f6f676c652f70726f746f6275662f6170692e70726f746f"
720       "120f676f6f676c652e70726f746f6275661a24676f6f676c652f70726f74"
721       "6f6275662f736f757263655f636f6e746578742e70726f746f1a1a676f6f"
722       "676c652f70726f746f6275662f747970652e70726f746f2281020a034170"
723       "69120c0a046e616d6518012001280912280a076d6574686f647318022003"
724       "280b32172e676f6f676c652e70726f746f6275662e4d6574686f6412280a"
725       "076f7074696f6e7318032003280b32172e676f6f676c652e70726f746f62"
726       "75662e4f7074696f6e120f0a0776657273696f6e18042001280912360a0e"
727       "736f757263655f636f6e7465787418052001280b321e2e676f6f676c652e"
728       "70726f746f6275662e536f75726365436f6e7465787412260a066d697869"
729       "6e7318062003280b32162e676f6f676c652e70726f746f6275662e4d6978"
730       "696e12270a0673796e74617818072001280e32172e676f6f676c652e7072"
731       "6f746f6275662e53796e74617822d5010a064d6574686f64120c0a046e61"
732       "6d6518012001280912180a10726571756573745f747970655f75726c1802"
733       "2001280912190a11726571756573745f73747265616d696e671803200128"
734       "0812190a11726573706f6e73655f747970655f75726c180420012809121a"
735       "0a12726573706f6e73655f73747265616d696e6718052001280812280a07"
736       "6f7074696f6e7318062003280b32172e676f6f676c652e70726f746f6275"
737       "662e4f7074696f6e12270a0673796e74617818072001280e32172e676f6f"
738       "676c652e70726f746f6275662e53796e74617822230a054d6978696e120c"
739       "0a046e616d65180120012809120c0a04726f6f7418022001280942750a13"
740       "636f6d2e676f6f676c652e70726f746f627566420841706950726f746f50"
741       "015a2b676f6f676c652e676f6c616e672e6f72672f67656e70726f746f2f"
742       "70726f746f6275662f6170693b617069a20203475042aa021e476f6f676c"
743       "652e50726f746f6275662e57656c6c4b6e6f776e5479706573620670726f"
744       "746f33";
745   char* binary;
746   int binary_len;
747   hex_to_binary(generated_file, &binary, &binary_len);
748   internal_add_generated_file(binary, binary_len,
749                               generated_pool, true TSRMLS_CC);
750   FREE(binary);
751   is_inited_file_api = true;
752 }
753 
754 static void init_file_duration(TSRMLS_D) {
755   if (is_inited_file_duration) return;
756   init_generated_pool_once(TSRMLS_C);
757   const char* generated_file =
758       "0ae3010a1e676f6f676c652f70726f746f6275662f6475726174696f6e2e"
759       "70726f746f120f676f6f676c652e70726f746f627566222a0a0844757261"
760       "74696f6e120f0a077365636f6e6473180120012803120d0a056e616e6f73"
761       "180220012805427c0a13636f6d2e676f6f676c652e70726f746f62756642"
762       "0d4475726174696f6e50726f746f50015a2a6769746875622e636f6d2f67"
763       "6f6c616e672f70726f746f6275662f7074797065732f6475726174696f6e"
764       "f80101a20203475042aa021e476f6f676c652e50726f746f6275662e5765"
765       "6c6c4b6e6f776e5479706573620670726f746f33";
766   char* binary;
767   int binary_len;
768   hex_to_binary(generated_file, &binary, &binary_len);
769   internal_add_generated_file(binary, binary_len,
770                               generated_pool, true TSRMLS_CC);
771   FREE(binary);
772   is_inited_file_duration = true;
773 }
774 
775 static void init_file_field_mask(TSRMLS_D) {
776   if (is_inited_file_field_mask) return;
777   init_generated_pool_once(TSRMLS_C);
778   const char* generated_file =
779       "0ae3010a20676f6f676c652f70726f746f6275662f6669656c645f6d6173"
780       "6b2e70726f746f120f676f6f676c652e70726f746f627566221a0a094669"
781       "656c644d61736b120d0a0570617468731801200328094289010a13636f6d"
782       "2e676f6f676c652e70726f746f627566420e4669656c644d61736b50726f"
783       "746f50015a39676f6f676c652e676f6c616e672e6f72672f67656e70726f"
784       "746f2f70726f746f6275662f6669656c645f6d61736b3b6669656c645f6d"
785       "61736ba20203475042aa021e476f6f676c652e50726f746f6275662e5765"
786       "6c6c4b6e6f776e5479706573620670726f746f33";
787   char* binary;
788   int binary_len;
789   hex_to_binary(generated_file, &binary, &binary_len);
790   internal_add_generated_file(binary, binary_len,
791                               generated_pool, true TSRMLS_CC);
792   FREE(binary);
793   is_inited_file_field_mask = true;
794 }
795 
796 static void init_file_empty(TSRMLS_D) {
797   if (is_inited_file_empty) return;
798   init_generated_pool_once(TSRMLS_C);
799   const char* generated_file =
800       "0ab7010a1b676f6f676c652f70726f746f6275662f656d7074792e70726f"
801       "746f120f676f6f676c652e70726f746f62756622070a05456d7074794276"
802       "0a13636f6d2e676f6f676c652e70726f746f627566420a456d7074795072"
803       "6f746f50015a276769746875622e636f6d2f676f6c616e672f70726f746f"
804       "6275662f7074797065732f656d707479f80101a20203475042aa021e476f"
805       "6f676c652e50726f746f6275662e57656c6c4b6e6f776e54797065736206"
806       "70726f746f33";
807   char* binary;
808   int binary_len;
809   hex_to_binary(generated_file, &binary, &binary_len);
810   internal_add_generated_file(binary, binary_len,
811                               generated_pool, true TSRMLS_CC);
812   FREE(binary);
813   is_inited_file_empty = true;
814 }
815 
816 static void init_file_source_context(TSRMLS_D) {
817   if (is_inited_file_source_context) return;
818   init_generated_pool_once(TSRMLS_C);
819   const char* generated_file =
820       "0afb010a24676f6f676c652f70726f746f6275662f736f757263655f636f"
821       "6e746578742e70726f746f120f676f6f676c652e70726f746f6275662222"
822       "0a0d536f75726365436f6e7465787412110a0966696c655f6e616d651801"
823       "200128094295010a13636f6d2e676f6f676c652e70726f746f6275664212"
824       "536f75726365436f6e7465787450726f746f50015a41676f6f676c652e67"
825       "6f6c616e672e6f72672f67656e70726f746f2f70726f746f6275662f736f"
826       "757263655f636f6e746578743b736f757263655f636f6e74657874a20203"
827       "475042aa021e476f6f676c652e50726f746f6275662e57656c6c4b6e6f77"
828       "6e5479706573620670726f746f33";
829   char* binary;
830   int binary_len;
831   hex_to_binary(generated_file, &binary, &binary_len);
832   internal_add_generated_file(binary, binary_len,
833                               generated_pool, true TSRMLS_CC);
834   FREE(binary);
835   is_inited_file_source_context = true;
836 }
837 
838 static void init_file_struct(TSRMLS_D) {
839   if (is_inited_file_struct) return;
840   init_generated_pool_once(TSRMLS_C);
841   const char* generated_file =
842       "0a81050a1c676f6f676c652f70726f746f6275662f7374727563742e7072"
843       "6f746f120f676f6f676c652e70726f746f6275662284010a065374727563"
844       "7412330a066669656c647318012003280b32232e676f6f676c652e70726f"
845       "746f6275662e5374727563742e4669656c6473456e7472791a450a0b4669"
846       "656c6473456e747279120b0a036b657918012001280912250a0576616c75"
847       "6518022001280b32162e676f6f676c652e70726f746f6275662e56616c75"
848       "653a02380122ea010a0556616c756512300a0a6e756c6c5f76616c756518"
849       "012001280e321a2e676f6f676c652e70726f746f6275662e4e756c6c5661"
850       "6c7565480012160a0c6e756d6265725f76616c7565180220012801480012"
851       "160a0c737472696e675f76616c7565180320012809480012140a0a626f6f"
852       "6c5f76616c75651804200128084800122f0a0c7374727563745f76616c75"
853       "6518052001280b32172e676f6f676c652e70726f746f6275662e53747275"
854       "6374480012300a0a6c6973745f76616c756518062001280b321a2e676f6f"
855       "676c652e70726f746f6275662e4c69737456616c7565480042060a046b69"
856       "6e6422330a094c69737456616c756512260a0676616c7565731801200328"
857       "0b32162e676f6f676c652e70726f746f6275662e56616c75652a1b0a094e"
858       "756c6c56616c7565120e0a0a4e554c4c5f56414c554510004281010a1363"
859       "6f6d2e676f6f676c652e70726f746f627566420b53747275637450726f74"
860       "6f50015a316769746875622e636f6d2f676f6c616e672f70726f746f6275"
861       "662f7074797065732f7374727563743b7374727563747062f80101a20203"
862       "475042aa021e476f6f676c652e50726f746f6275662e57656c6c4b6e6f77"
863       "6e5479706573620670726f746f33";
864   char* binary;
865   int binary_len;
866   hex_to_binary(generated_file, &binary, &binary_len);
867   internal_add_generated_file(binary, binary_len,
868                               generated_pool, true TSRMLS_CC);
869   FREE(binary);
870   is_inited_file_struct = true;
871 }
872 
873 static void init_file_timestamp(TSRMLS_D) {
874   if (is_inited_file_timestamp) return;
875   init_generated_pool_once(TSRMLS_C);
876   const char* generated_file =
877       "0ae7010a1f676f6f676c652f70726f746f6275662f74696d657374616d70"
878       "2e70726f746f120f676f6f676c652e70726f746f627566222b0a0954696d"
879       "657374616d70120f0a077365636f6e6473180120012803120d0a056e616e"
880       "6f73180220012805427e0a13636f6d2e676f6f676c652e70726f746f6275"
881       "66420e54696d657374616d7050726f746f50015a2b6769746875622e636f"
882       "6d2f676f6c616e672f70726f746f6275662f7074797065732f74696d6573"
883       "74616d70f80101a20203475042aa021e476f6f676c652e50726f746f6275"
884       "662e57656c6c4b6e6f776e5479706573620670726f746f33";
885   char* binary;
886   int binary_len;
887   hex_to_binary(generated_file, &binary, &binary_len);
888   internal_add_generated_file(binary, binary_len,
889                               generated_pool, true TSRMLS_CC);
890   FREE(binary);
891   is_inited_file_timestamp = true;
892 }
893 
894 static void init_file_type(TSRMLS_D) {
895   if (is_inited_file_type) return;
896   init_file_any(TSRMLS_C);
897   init_file_source_context(TSRMLS_C);
898   init_generated_pool_once(TSRMLS_C);
899   const char* generated_file =
900       "0aba0c0a1a676f6f676c652f70726f746f6275662f747970652e70726f74"
901       "6f120f676f6f676c652e70726f746f6275661a19676f6f676c652f70726f"
902       "746f6275662f616e792e70726f746f1a24676f6f676c652f70726f746f62"
903       "75662f736f757263655f636f6e746578742e70726f746f22d7010a045479"
904       "7065120c0a046e616d6518012001280912260a066669656c647318022003"
905       "280b32162e676f6f676c652e70726f746f6275662e4669656c64120e0a06"
906       "6f6e656f667318032003280912280a076f7074696f6e7318042003280b32"
907       "172e676f6f676c652e70726f746f6275662e4f7074696f6e12360a0e736f"
908       "757263655f636f6e7465787418052001280b321e2e676f6f676c652e7072"
909       "6f746f6275662e536f75726365436f6e7465787412270a0673796e746178"
910       "18062001280e32172e676f6f676c652e70726f746f6275662e53796e7461"
911       "7822d5050a054669656c6412290a046b696e6418012001280e321b2e676f"
912       "6f676c652e70726f746f6275662e4669656c642e4b696e6412370a0b6361"
913       "7264696e616c69747918022001280e32222e676f6f676c652e70726f746f"
914       "6275662e4669656c642e43617264696e616c697479120e0a066e756d6265"
915       "72180320012805120c0a046e616d6518042001280912100a08747970655f"
916       "75726c18062001280912130a0b6f6e656f665f696e646578180720012805"
917       "120e0a067061636b656418082001280812280a076f7074696f6e73180920"
918       "03280b32172e676f6f676c652e70726f746f6275662e4f7074696f6e1211"
919       "0a096a736f6e5f6e616d65180a2001280912150a0d64656661756c745f76"
920       "616c7565180b2001280922c8020a044b696e6412100a0c545950455f554e"
921       "4b4e4f574e1000120f0a0b545950455f444f55424c451001120e0a0a5459"
922       "50455f464c4f41541002120e0a0a545950455f494e5436341003120f0a0b"
923       "545950455f55494e5436341004120e0a0a545950455f494e543332100512"
924       "100a0c545950455f46495845443634100612100a0c545950455f46495845"
925       "4433321007120d0a09545950455f424f4f4c1008120f0a0b545950455f53"
926       "5452494e471009120e0a0a545950455f47524f5550100a12100a0c545950"
927       "455f4d455353414745100b120e0a0a545950455f4259544553100c120f0a"
928       "0b545950455f55494e543332100d120d0a09545950455f454e554d100e12"
929       "110a0d545950455f5346495845443332100f12110a0d545950455f534649"
930       "58454436341010120f0a0b545950455f53494e5433321011120f0a0b5459"
931       "50455f53494e543634101222740a0b43617264696e616c69747912170a13"
932       "43415244494e414c4954595f554e4b4e4f574e100012180a144341524449"
933       "4e414c4954595f4f5054494f4e414c100112180a1443415244494e414c49"
934       "54595f5245515549524544100212180a1443415244494e414c4954595f52"
935       "45504541544544100322ce010a04456e756d120c0a046e616d6518012001"
936       "2809122d0a09656e756d76616c756518022003280b321a2e676f6f676c65"
937       "2e70726f746f6275662e456e756d56616c756512280a076f7074696f6e73"
938       "18032003280b32172e676f6f676c652e70726f746f6275662e4f7074696f"
939       "6e12360a0e736f757263655f636f6e7465787418042001280b321e2e676f"
940       "6f676c652e70726f746f6275662e536f75726365436f6e7465787412270a"
941       "0673796e74617818052001280e32172e676f6f676c652e70726f746f6275"
942       "662e53796e74617822530a09456e756d56616c7565120c0a046e616d6518"
943       "0120012809120e0a066e756d62657218022001280512280a076f7074696f"
944       "6e7318032003280b32172e676f6f676c652e70726f746f6275662e4f7074"
945       "696f6e223b0a064f7074696f6e120c0a046e616d6518012001280912230a"
946       "0576616c756518022001280b32142e676f6f676c652e70726f746f627566"
947       "2e416e792a2e0a0653796e74617812110a0d53594e5441585f50524f544f"
948       "32100012110a0d53594e5441585f50524f544f331001427d0a13636f6d2e"
949       "676f6f676c652e70726f746f62756642095479706550726f746f50015a2f"
950       "676f6f676c652e676f6c616e672e6f72672f67656e70726f746f2f70726f"
951       "746f6275662f70747970653b7074797065f80101a20203475042aa021e47"
952       "6f6f676c652e50726f746f6275662e57656c6c4b6e6f776e547970657362"
953       "0670726f746f33";
954   char* binary;
955   int binary_len;
956   hex_to_binary(generated_file, &binary, &binary_len);
957   internal_add_generated_file(binary, binary_len,
958                               generated_pool, true TSRMLS_CC);
959   FREE(binary);
960   is_inited_file_type = true;
961 }
962 
963 static void init_file_wrappers(TSRMLS_D) {
964   if (is_inited_file_wrappers) return;
965   init_generated_pool_once(TSRMLS_C);
966   const char* generated_file =
967       "0abf030a1e676f6f676c652f70726f746f6275662f77726170706572732e"
968       "70726f746f120f676f6f676c652e70726f746f627566221c0a0b446f7562"
969       "6c6556616c7565120d0a0576616c7565180120012801221b0a0a466c6f61"
970       "7456616c7565120d0a0576616c7565180120012802221b0a0a496e743634"
971       "56616c7565120d0a0576616c7565180120012803221c0a0b55496e743634"
972       "56616c7565120d0a0576616c7565180120012804221b0a0a496e74333256"
973       "616c7565120d0a0576616c7565180120012805221c0a0b55496e74333256"
974       "616c7565120d0a0576616c756518012001280d221a0a09426f6f6c56616c"
975       "7565120d0a0576616c7565180120012808221c0a0b537472696e6756616c"
976       "7565120d0a0576616c7565180120012809221b0a0a427974657356616c75"
977       "65120d0a0576616c756518012001280c427c0a13636f6d2e676f6f676c65"
978       "2e70726f746f627566420d577261707065727350726f746f50015a2a6769"
979       "746875622e636f6d2f676f6c616e672f70726f746f6275662f7074797065"
980       "732f7772617070657273f80101a20203475042aa021e476f6f676c652e50"
981       "726f746f6275662e57656c6c4b6e6f776e5479706573620670726f746f33";
982   char* binary;
983   int binary_len;
984   hex_to_binary(generated_file, &binary, &binary_len);
985   internal_add_generated_file(binary, binary_len,
986                               generated_pool, true TSRMLS_CC);
987   FREE(binary);
988   is_inited_file_wrappers = true;
989 }
990 
991 // -----------------------------------------------------------------------------
992 // Define enum
993 // -----------------------------------------------------------------------------
994 
995 // -----------------------------------------------------------------------------
996 // Field_Cardinality
997 // -----------------------------------------------------------------------------
998 
999 static zend_function_entry field_cardinality_methods[] = {
1000   PHP_ME(Field_Cardinality, name, NULL, ZEND_ACC_PUBLIC|ZEND_ACC_STATIC)
1001   PHP_ME(Field_Cardinality, value, NULL, ZEND_ACC_PUBLIC|ZEND_ACC_STATIC)
1002   {NULL, NULL, NULL}
1003 };
1004 
1005 zend_class_entry* field_cardinality_type;
1006 
1007 // Init class entry.
1008 PHP_PROTO_INIT_ENUMCLASS_START("Google\\Protobuf\\Field\\Cardinality",
1009                                 Field_Cardinality, field_cardinality)
1010   zend_declare_class_constant_long(field_cardinality_type,
1011                                    "CARDINALITY_UNKNOWN", 19, 0 TSRMLS_CC);
1012   zend_declare_class_constant_long(field_cardinality_type,
1013                                    "CARDINALITY_OPTIONAL", 20, 1 TSRMLS_CC);
1014   zend_declare_class_constant_long(field_cardinality_type,
1015                                    "CARDINALITY_REQUIRED", 20, 2 TSRMLS_CC);
1016   zend_declare_class_constant_long(field_cardinality_type,
1017                                    "CARDINALITY_REPEATED", 20, 3 TSRMLS_CC);
1018   const char *alias = "Google\\Protobuf\\Field_Cardinality";
1019 #if PHP_VERSION_ID < 70300
1020   zend_register_class_alias_ex(alias, strlen(alias), field_cardinality_type TSRMLS_CC);
1021 #else
1022   zend_register_class_alias_ex(alias, strlen(alias), field_cardinality_type, 1);
1023 #endif
1024 PHP_PROTO_INIT_ENUMCLASS_END
1025 
1026 PHP_METHOD(Field_Cardinality, name) {
1027   PHP_PROTO_LONG value;
1028   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &value) ==
1029       FAILURE) {
1030     return;
1031   }
1032   switch (value) {
1033     case 0:
1034       PHP_PROTO_RETURN_STRING("CARDINALITY_UNKNOWN", 1);
1035     case 1:
1036       PHP_PROTO_RETURN_STRING("CARDINALITY_OPTIONAL", 1);
1037     case 2:
1038       PHP_PROTO_RETURN_STRING("CARDINALITY_REQUIRED", 1);
1039     case 3:
1040       PHP_PROTO_RETURN_STRING("CARDINALITY_REPEATED", 1);
1041     default:
1042       zend_throw_exception_ex(
1043           NULL, 0 TSRMLS_CC,
1044           "Enum Google\\Protobuf\\Field_Cardinality has no name "
1045           "defined for value %d.",
1046           value);
1047   }
1048 }
1049 
1050 PHP_METHOD(Field_Cardinality, value) {
1051   char *name = NULL;
1052   PHP_PROTO_SIZE name_len;
1053 
1054   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &name, &name_len) ==
1055       FAILURE) {
1056     return;
1057   }
1058 
1059   if (strncmp(name, "CARDINALITY_UNKNOWN", name_len) == 0) RETURN_LONG(0);
1060   if (strncmp(name, "CARDINALITY_OPTIONAL", name_len) == 0) RETURN_LONG(1);
1061   if (strncmp(name, "CARDINALITY_REQUIRED", name_len) == 0) RETURN_LONG(2);
1062   if (strncmp(name, "CARDINALITY_REPEATED", name_len) == 0) RETURN_LONG(3);
1063 
1064   zend_throw_exception_ex(
1065       NULL, 0 TSRMLS_CC,
1066       "Enum Google\\Protobuf\\Field_Cardinality has no value "
1067       "defined for name %s.",
1068       name);
1069 }
1070 
1071 // -----------------------------------------------------------------------------
1072 // Field_Kind
1073 // -----------------------------------------------------------------------------
1074 
1075 static zend_function_entry field_kind_methods[] = {
1076   PHP_ME(Field_Kind, name, NULL, ZEND_ACC_PUBLIC|ZEND_ACC_STATIC)
1077   PHP_ME(Field_Kind, value, NULL, ZEND_ACC_PUBLIC|ZEND_ACC_STATIC)
1078   {NULL, NULL, NULL}
1079 };
1080 
1081 zend_class_entry* field_kind_type;
1082 
1083 // Init class entry.
1084 PHP_PROTO_INIT_ENUMCLASS_START("Google\\Protobuf\\Field\\Kind",
1085                                 Field_Kind, field_kind)
1086   zend_declare_class_constant_long(field_kind_type,
1087                                    "TYPE_UNKNOWN", 12, 0 TSRMLS_CC);
1088   zend_declare_class_constant_long(field_kind_type,
1089                                    "TYPE_DOUBLE", 11, 1 TSRMLS_CC);
1090   zend_declare_class_constant_long(field_kind_type,
1091                                    "TYPE_FLOAT", 10, 2 TSRMLS_CC);
1092   zend_declare_class_constant_long(field_kind_type,
1093                                    "TYPE_INT64", 10, 3 TSRMLS_CC);
1094   zend_declare_class_constant_long(field_kind_type,
1095                                    "TYPE_UINT64", 11, 4 TSRMLS_CC);
1096   zend_declare_class_constant_long(field_kind_type,
1097                                    "TYPE_INT32", 10, 5 TSRMLS_CC);
1098   zend_declare_class_constant_long(field_kind_type,
1099                                    "TYPE_FIXED64", 12, 6 TSRMLS_CC);
1100   zend_declare_class_constant_long(field_kind_type,
1101                                    "TYPE_FIXED32", 12, 7 TSRMLS_CC);
1102   zend_declare_class_constant_long(field_kind_type,
1103                                    "TYPE_BOOL", 9, 8 TSRMLS_CC);
1104   zend_declare_class_constant_long(field_kind_type,
1105                                    "TYPE_STRING", 11, 9 TSRMLS_CC);
1106   zend_declare_class_constant_long(field_kind_type,
1107                                    "TYPE_GROUP", 10, 10 TSRMLS_CC);
1108   zend_declare_class_constant_long(field_kind_type,
1109                                    "TYPE_MESSAGE", 12, 11 TSRMLS_CC);
1110   zend_declare_class_constant_long(field_kind_type,
1111                                    "TYPE_BYTES", 10, 12 TSRMLS_CC);
1112   zend_declare_class_constant_long(field_kind_type,
1113                                    "TYPE_UINT32", 11, 13 TSRMLS_CC);
1114   zend_declare_class_constant_long(field_kind_type,
1115                                    "TYPE_ENUM", 9, 14 TSRMLS_CC);
1116   zend_declare_class_constant_long(field_kind_type,
1117                                    "TYPE_SFIXED32", 13, 15 TSRMLS_CC);
1118   zend_declare_class_constant_long(field_kind_type,
1119                                    "TYPE_SFIXED64", 13, 16 TSRMLS_CC);
1120   zend_declare_class_constant_long(field_kind_type,
1121                                    "TYPE_SINT32", 11, 17 TSRMLS_CC);
1122   zend_declare_class_constant_long(field_kind_type,
1123                                    "TYPE_SINT64", 11, 18 TSRMLS_CC);
1124   const char *alias = "Google\\Protobuf\\Field_Kind";
1125 #if PHP_VERSION_ID < 70300
1126   zend_register_class_alias_ex(alias, strlen(alias), field_kind_type TSRMLS_CC);
1127 #else
1128   zend_register_class_alias_ex(alias, strlen(alias), field_kind_type, 1);
1129 #endif
1130 PHP_PROTO_INIT_ENUMCLASS_END
1131 
1132 PHP_METHOD(Field_Kind, name) {
1133   PHP_PROTO_LONG value;
1134   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &value) ==
1135       FAILURE) {
1136     return;
1137   }
1138   switch (value) {
1139     case 0:
1140       PHP_PROTO_RETURN_STRING("TYPE_UNKNOWN", 1);
1141     case 1:
1142       PHP_PROTO_RETURN_STRING("TYPE_DOUBLE", 1);
1143     case 2:
1144       PHP_PROTO_RETURN_STRING("TYPE_FLOAT", 1);
1145     case 3:
1146       PHP_PROTO_RETURN_STRING("TYPE_INT64", 1);
1147     case 4:
1148       PHP_PROTO_RETURN_STRING("TYPE_UINT64", 1);
1149     case 5:
1150       PHP_PROTO_RETURN_STRING("TYPE_INT32", 1);
1151     case 6:
1152       PHP_PROTO_RETURN_STRING("TYPE_FIXED64", 1);
1153     case 7:
1154       PHP_PROTO_RETURN_STRING("TYPE_FIXED32", 1);
1155     case 8:
1156       PHP_PROTO_RETURN_STRING("TYPE_BOOL", 1);
1157     case 9:
1158       PHP_PROTO_RETURN_STRING("TYPE_STRING", 1);
1159     case 10:
1160       PHP_PROTO_RETURN_STRING("TYPE_GROUP", 1);
1161     case 11:
1162       PHP_PROTO_RETURN_STRING("TYPE_MESSAGE", 1);
1163     case 12:
1164       PHP_PROTO_RETURN_STRING("TYPE_BYTES", 1);
1165     case 13:
1166       PHP_PROTO_RETURN_STRING("TYPE_UINT32", 1);
1167     case 14:
1168       PHP_PROTO_RETURN_STRING("TYPE_ENUM", 1);
1169     case 15:
1170       PHP_PROTO_RETURN_STRING("TYPE_SFIXED32", 1);
1171     case 16:
1172       PHP_PROTO_RETURN_STRING("TYPE_SFIXED64", 1);
1173     case 17:
1174       PHP_PROTO_RETURN_STRING("TYPE_SINT32", 1);
1175     case 18:
1176       PHP_PROTO_RETURN_STRING("TYPE_SINT64", 1);
1177     default:
1178       zend_throw_exception_ex(NULL, 0 TSRMLS_CC,
1179                               "Enum Google\\Protobuf\\Field_Kind has no name "
1180                               "defined for value %d.",
1181                               value);
1182   }
1183 }
1184 
1185 PHP_METHOD(Field_Kind, value) {
1186   char *name = NULL;
1187   PHP_PROTO_SIZE name_len;
1188 
1189   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &name, &name_len) ==
1190       FAILURE) {
1191     return;
1192   }
1193 
1194   if (strncmp(name, "TYPE_UNKNOWN", name_len) == 0) RETURN_LONG(0);
1195   if (strncmp(name, "TYPE_DOUBLE", name_len) == 0) RETURN_LONG(1);
1196   if (strncmp(name, "TYPE_FLOAT", name_len) == 0) RETURN_LONG(2);
1197   if (strncmp(name, "TYPE_INT64", name_len) == 0) RETURN_LONG(3);
1198   if (strncmp(name, "TYPE_UINT64", name_len) == 0) RETURN_LONG(4);
1199   if (strncmp(name, "TYPE_INT32", name_len) == 0) RETURN_LONG(5);
1200   if (strncmp(name, "TYPE_FIXED64", name_len) == 0) RETURN_LONG(6);
1201   if (strncmp(name, "TYPE_FIXED32", name_len) == 0) RETURN_LONG(7);
1202   if (strncmp(name, "TYPE_BOOL", name_len) == 0) RETURN_LONG(8);
1203   if (strncmp(name, "TYPE_STRING", name_len) == 0) RETURN_LONG(9);
1204   if (strncmp(name, "TYPE_GROUP", name_len) == 0) RETURN_LONG(10);
1205   if (strncmp(name, "TYPE_MESSAGE", name_len) == 0) RETURN_LONG(11);
1206   if (strncmp(name, "TYPE_BYTES", name_len) == 0) RETURN_LONG(12);
1207   if (strncmp(name, "TYPE_UINT32", name_len) == 0) RETURN_LONG(13);
1208   if (strncmp(name, "TYPE_ENUM", name_len) == 0) RETURN_LONG(14);
1209   if (strncmp(name, "TYPE_SFIXED32", name_len) == 0) RETURN_LONG(15);
1210   if (strncmp(name, "TYPE_SFIXED64", name_len) == 0) RETURN_LONG(16);
1211   if (strncmp(name, "TYPE_SINT32", name_len) == 0) RETURN_LONG(17);
1212   if (strncmp(name, "TYPE_SINT64", name_len) == 0) RETURN_LONG(18);
1213 
1214   zend_throw_exception_ex(NULL, 0 TSRMLS_CC,
1215                           "Enum Google\\Protobuf\\Field_Kind has no value "
1216                           "defined for name %s.",
1217                           name);
1218 }
1219 
1220 // -----------------------------------------------------------------------------
1221 // NullValue
1222 // -----------------------------------------------------------------------------
1223 
1224 static zend_function_entry null_value_methods[] = {
1225   PHP_ME(NullValue, name, NULL, ZEND_ACC_PUBLIC|ZEND_ACC_STATIC)
1226   PHP_ME(NullValue, value, NULL, ZEND_ACC_PUBLIC|ZEND_ACC_STATIC)
1227   {NULL, NULL, NULL}
1228 };
1229 
1230 zend_class_entry* null_value_type;
1231 
1232 // Init class entry.
1233 PHP_PROTO_INIT_ENUMCLASS_START("Google\\Protobuf\\NullValue",
1234                                 NullValue, null_value)
1235   zend_declare_class_constant_long(null_value_type,
1236                                    "NULL_VALUE", 10, 0 TSRMLS_CC);
1237 PHP_PROTO_INIT_ENUMCLASS_END
1238 
1239 PHP_METHOD(NullValue, name) {
1240   PHP_PROTO_LONG value;
1241   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &value) ==
1242       FAILURE) {
1243     return;
1244   }
1245   switch (value) {
1246     case 0:
1247       PHP_PROTO_RETURN_STRING("NULL_VALUE", 1);
1248     default:
1249       zend_throw_exception_ex(NULL, 0 TSRMLS_CC,
1250                               "Enum Google\\Protobuf\\NullValue has no name "
1251                               "defined for value %d.",
1252                               value);
1253   }
1254 }
1255 
1256 PHP_METHOD(NullValue, value) {
1257   char *name = NULL;
1258   PHP_PROTO_SIZE name_len;
1259 
1260   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &name, &name_len) ==
1261       FAILURE) {
1262     return;
1263   }
1264 
1265   if (strncmp(name, "NULL_VALUE", name_len) == 0) RETURN_LONG(0);
1266 
1267   zend_throw_exception_ex(NULL, 0 TSRMLS_CC,
1268                           "Enum Google\\Protobuf\\NullValue has no value "
1269                           "defined for name %s.",
1270                           name);
1271 }
1272 
1273 // -----------------------------------------------------------------------------
1274 // Syntax
1275 // -----------------------------------------------------------------------------
1276 
1277 static zend_function_entry syntax_methods[] = {
1278   PHP_ME(Syntax, name, NULL, ZEND_ACC_PUBLIC|ZEND_ACC_STATIC)
1279   PHP_ME(Syntax, value, NULL, ZEND_ACC_PUBLIC|ZEND_ACC_STATIC)
1280   {NULL, NULL, NULL}
1281 };
1282 
1283 zend_class_entry* syntax_type;
1284 
1285 // Init class entry.
1286 PHP_PROTO_INIT_ENUMCLASS_START("Google\\Protobuf\\Syntax",
1287                                 Syntax, syntax)
1288   zend_declare_class_constant_long(syntax_type,
1289                                    "SYNTAX_PROTO2", 13, 0 TSRMLS_CC);
1290   zend_declare_class_constant_long(syntax_type,
1291                                    "SYNTAX_PROTO3", 13, 1 TSRMLS_CC);
1292 PHP_PROTO_INIT_ENUMCLASS_END
1293 
1294 PHP_METHOD(Syntax, name) {
1295   PHP_PROTO_LONG value;
1296   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "l", &value) ==
1297       FAILURE) {
1298     return;
1299   }
1300   switch (value) {
1301     case 0:
1302       PHP_PROTO_RETURN_STRING("SYNTAX_PROTO2", 1);
1303     case 1:
1304       PHP_PROTO_RETURN_STRING("SYNTAX_PROTO3", 1);
1305     default:
1306       zend_throw_exception_ex(NULL, 0 TSRMLS_CC,
1307                               "Enum Google\\Protobuf\\Syntax has no name "
1308                               "defined for value %d.",
1309                               value);
1310   }
1311 }
1312 
1313 PHP_METHOD(Syntax, value) {
1314   char *name = NULL;
1315   PHP_PROTO_SIZE name_len;
1316 
1317   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "s", &name, &name_len) ==
1318       FAILURE) {
1319     return;
1320   }
1321 
1322   if (strncmp(name, "SYNTAX_PROTO2", name_len) == 0) RETURN_LONG(0);
1323   if (strncmp(name, "SYNTAX_PROTO3", name_len) == 0) RETURN_LONG(1);
1324 
1325   zend_throw_exception_ex(NULL, 0 TSRMLS_CC,
1326                           "Enum Google\\Protobuf\\Syntax has no value "
1327                           "defined for name %s.",
1328                           name);
1329 }
1330 
1331 // -----------------------------------------------------------------------------
1332 // Define message
1333 // -----------------------------------------------------------------------------
1334 
1335 // -----------------------------------------------------------------------------
1336 // Any
1337 // -----------------------------------------------------------------------------
1338 
1339 static  zend_function_entry any_methods[] = {
1340   PHP_ME(Any, __construct, NULL, ZEND_ACC_PUBLIC)
1341   PHP_ME(Any, getTypeUrl, NULL, ZEND_ACC_PUBLIC)
1342   PHP_ME(Any, setTypeUrl, NULL, ZEND_ACC_PUBLIC)
1343   PHP_ME(Any, getValue, NULL, ZEND_ACC_PUBLIC)
1344   PHP_ME(Any, setValue, NULL, ZEND_ACC_PUBLIC)
1345   PHP_ME(Any, pack,     NULL, ZEND_ACC_PUBLIC)
1346   PHP_ME(Any, unpack,   NULL, ZEND_ACC_PUBLIC)
1347   PHP_ME(Any, is,       NULL, ZEND_ACC_PUBLIC)
1348   {NULL, NULL, NULL}
1349 };
1350 
1351 zend_class_entry* any_type;
1352 
1353 // Init class entry.
1354 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Any", Any, any)
1355   zend_declare_property_string(any_type, "type_url", strlen("type_url"),
1356                                "" ,ZEND_ACC_PRIVATE TSRMLS_CC);
1357   zend_declare_property_string(any_type, "value", strlen("value"),
1358                                "" ,ZEND_ACC_PRIVATE TSRMLS_CC);
1359 PHP_PROTO_INIT_SUBMSGCLASS_END
1360 
1361 static void hex_to_binary(const char* hex, char** binary, int* binary_len) {
1362   int i;
1363   int hex_len = strlen(hex);
1364   *binary_len = hex_len / 2;
1365   *binary = ALLOC_N(char, *binary_len);
1366   for (i = 0; i < *binary_len; i++) {
1367     char value = 0;
1368     if (hex[i * 2] >= '0' && hex[i * 2] <= '9') {
1369       value += (hex[i * 2] - '0') * 16;
1370     } else {
1371       value += (hex[i * 2] - 'a' + 10) * 16;
1372     }
1373     if (hex[i * 2 + 1] >= '0' && hex[i * 2 + 1] <= '9') {
1374       value += hex[i * 2 + 1] - '0';
1375     } else {
1376       value += hex[i * 2 + 1] - 'a' + 10;
1377     }
1378     (*binary)[i] = value;
1379   }
1380 }
1381 
1382 PHP_METHOD(Any, __construct) {
1383   init_file_any(TSRMLS_C);
1384   MessageHeader* intern = UNBOX(MessageHeader, getThis());
1385   INIT_MESSAGE_WITH_ARRAY;
1386 }
1387 
1388 PHP_PROTO_FIELD_ACCESSORS(Any, any, TypeUrl, "type_url")
1389 PHP_PROTO_FIELD_ACCESSORS(Any, any, Value,   "value")
1390 
1391 PHP_METHOD(Any, unpack) {
1392   // Get type url.
1393   zval type_url_member;
1394   PHP_PROTO_ZVAL_STRING(&type_url_member, "type_url", 1);
1395   PHP_PROTO_FAKE_SCOPE_BEGIN(any_type);
1396   zval* type_url_php = php_proto_message_read_property(
1397       getThis(), &type_url_member PHP_PROTO_TSRMLS_CC);
1398   zval_dtor(&type_url_member);
1399   PHP_PROTO_FAKE_SCOPE_END;
1400 
1401   // Get fully-qualified name from type url.
1402   size_t url_prefix_len = strlen(TYPE_URL_PREFIX);
1403   const char* type_url = Z_STRVAL_P(type_url_php);
1404   size_t type_url_len = Z_STRLEN_P(type_url_php);
1405 
1406   if (url_prefix_len > type_url_len ||
1407       strncmp(TYPE_URL_PREFIX, type_url, url_prefix_len) != 0) {
1408     zend_throw_exception(
1409         NULL, "Type url needs to be type.googleapis.com/fully-qualified",
1410         0 TSRMLS_CC);
1411     return;
1412   }
1413 
1414   const char* fully_qualified_name = type_url + url_prefix_len;
1415   PHP_PROTO_HASHTABLE_VALUE desc_php = get_proto_obj(fully_qualified_name);
1416   if (desc_php == NULL) {
1417     zend_throw_exception(
1418         NULL, "Specified message in any hasn't been added to descriptor pool",
1419         0 TSRMLS_CC);
1420     return;
1421   }
1422   Descriptor* desc = UNBOX_HASHTABLE_VALUE(Descriptor, desc_php);
1423   zend_class_entry* klass = desc->klass;
1424   ZVAL_OBJ(return_value, klass->create_object(klass TSRMLS_CC));
1425   MessageHeader* msg = UNBOX(MessageHeader, return_value);
1426   custom_data_init(klass, msg PHP_PROTO_TSRMLS_CC);
1427 
1428   // Get value.
1429   zval value_member;
1430   PHP_PROTO_ZVAL_STRING(&value_member, "value", 1);
1431   PHP_PROTO_FAKE_SCOPE_RESTART(any_type);
1432   zval* value = php_proto_message_read_property(
1433       getThis(), &value_member PHP_PROTO_TSRMLS_CC);
1434   zval_dtor(&value_member);
1435   PHP_PROTO_FAKE_SCOPE_END;
1436 
1437   merge_from_string(Z_STRVAL_P(value), Z_STRLEN_P(value), desc, msg);
1438 }
1439 
1440 PHP_METHOD(Any, pack) {
1441   zval* val;
1442 
1443   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "o", &val) ==
1444       FAILURE) {
1445     return;
1446   }
1447 
1448   if (!instanceof_function(Z_OBJCE_P(val), message_type TSRMLS_CC)) {
1449     zend_error(E_USER_ERROR, "Given value is not an instance of Message.");
1450     return;
1451   }
1452 
1453   // Set value by serialized data.
1454   zval data;
1455   serialize_to_string(val, &data TSRMLS_CC);
1456 
1457   zval member;
1458   PHP_PROTO_ZVAL_STRING(&member, "value", 1);
1459 
1460   PHP_PROTO_FAKE_SCOPE_BEGIN(any_type);
1461   message_handlers->write_property(getThis(), &member, &data,
1462                                    NULL PHP_PROTO_TSRMLS_CC);
1463   zval_dtor(&data);
1464   zval_dtor(&member);
1465   PHP_PROTO_FAKE_SCOPE_END;
1466 
1467   // Set type url.
1468   Descriptor* desc =
1469       UNBOX_HASHTABLE_VALUE(Descriptor, get_ce_obj(Z_OBJCE_P(val)));
1470   const char* fully_qualified_name = upb_msgdef_fullname(desc->msgdef);
1471   size_t type_url_len =
1472       strlen(TYPE_URL_PREFIX) + strlen(fully_qualified_name) + 1;
1473   char* type_url = ALLOC_N(char, type_url_len);
1474   sprintf(type_url, "%s%s", TYPE_URL_PREFIX, fully_qualified_name);
1475   zval type_url_php;
1476   PHP_PROTO_ZVAL_STRING(&type_url_php, type_url, 1);
1477   PHP_PROTO_ZVAL_STRING(&member, "type_url", 1);
1478 
1479   PHP_PROTO_FAKE_SCOPE_RESTART(any_type);
1480   message_handlers->write_property(getThis(), &member, &type_url_php,
1481                                    NULL PHP_PROTO_TSRMLS_CC);
1482   zval_dtor(&type_url_php);
1483   zval_dtor(&member);
1484   PHP_PROTO_FAKE_SCOPE_END;
1485   FREE(type_url);
1486 }
1487 
1488 PHP_METHOD(Any, is) {
1489   zend_class_entry *klass = NULL;
1490 
1491   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "C", &klass) ==
1492       FAILURE) {
1493     return;
1494   }
1495 
1496   PHP_PROTO_HASHTABLE_VALUE desc_php = get_ce_obj(klass);
1497   if (desc_php == NULL) {
1498     RETURN_BOOL(false);
1499   }
1500 
1501   // Create corresponded type url.
1502   Descriptor* desc =
1503       UNBOX_HASHTABLE_VALUE(Descriptor, get_ce_obj(klass));
1504   const char* fully_qualified_name = upb_msgdef_fullname(desc->msgdef);
1505   size_t type_url_len =
1506       strlen(TYPE_URL_PREFIX) + strlen(fully_qualified_name) + 1;
1507   char* type_url = ALLOC_N(char, type_url_len);
1508   sprintf(type_url, "%s%s", TYPE_URL_PREFIX, fully_qualified_name);
1509 
1510   // Fetch stored type url.
1511   zval member;
1512   PHP_PROTO_ZVAL_STRING(&member, "type_url", 1);
1513   PHP_PROTO_FAKE_SCOPE_BEGIN(any_type);
1514   zval* value =
1515       php_proto_message_read_property(getThis(), &member PHP_PROTO_TSRMLS_CC);
1516   zval_dtor(&member);
1517   PHP_PROTO_FAKE_SCOPE_END;
1518 
1519   // Compare two type url.
1520   bool is = strcmp(type_url, Z_STRVAL_P(value)) == 0;
1521   FREE(type_url);
1522 
1523   RETURN_BOOL(is);
1524 }
1525 
1526 // -----------------------------------------------------------------------------
1527 // Duration
1528 // -----------------------------------------------------------------------------
1529 
1530 static  zend_function_entry duration_methods[] = {
1531   PHP_ME(Duration, __construct, NULL, ZEND_ACC_PUBLIC)
1532   PHP_ME(Duration, getSeconds, NULL, ZEND_ACC_PUBLIC)
1533   PHP_ME(Duration, setSeconds, NULL, ZEND_ACC_PUBLIC)
1534   PHP_ME(Duration, getNanos, NULL, ZEND_ACC_PUBLIC)
1535   PHP_ME(Duration, setNanos, NULL, ZEND_ACC_PUBLIC)
1536   {NULL, NULL, NULL}
1537 };
1538 
1539 zend_class_entry* duration_type;
1540 
1541 // Init class entry.
1542 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Duration",
1543                                  Duration, duration)
1544   zend_declare_property_long(duration_type, "seconds", strlen("seconds"),
1545                              0 ,ZEND_ACC_PRIVATE TSRMLS_CC);
1546   zend_declare_property_long(duration_type, "nanos", strlen("nanos"),
1547                              0 ,ZEND_ACC_PRIVATE TSRMLS_CC);
1548 PHP_PROTO_INIT_SUBMSGCLASS_END
1549 
1550 PHP_METHOD(Duration, __construct) {
1551   init_file_duration(TSRMLS_C);
1552   MessageHeader* intern = UNBOX(MessageHeader, getThis());
1553   INIT_MESSAGE_WITH_ARRAY;
1554 }
1555 
1556 PHP_PROTO_FIELD_ACCESSORS(Duration, duration, Seconds, "seconds")
1557 PHP_PROTO_FIELD_ACCESSORS(Duration, duration, Nanos,   "nanos")
1558 
1559 // -----------------------------------------------------------------------------
1560 // Timestamp
1561 // -----------------------------------------------------------------------------
1562 
1563 static  zend_function_entry timestamp_methods[] = {
1564   PHP_ME(Timestamp, __construct, NULL, ZEND_ACC_PUBLIC)
1565   PHP_ME(Timestamp, fromDateTime, NULL, ZEND_ACC_PUBLIC)
1566   PHP_ME(Timestamp, toDateTime, NULL, ZEND_ACC_PUBLIC)
1567   PHP_ME(Timestamp, getSeconds, NULL, ZEND_ACC_PUBLIC)
1568   PHP_ME(Timestamp, setSeconds, NULL, ZEND_ACC_PUBLIC)
1569   PHP_ME(Timestamp, getNanos, NULL, ZEND_ACC_PUBLIC)
1570   PHP_ME(Timestamp, setNanos, NULL, ZEND_ACC_PUBLIC)
1571   {NULL, NULL, NULL}
1572 };
1573 
1574 zend_class_entry* timestamp_type;
1575 
1576 // Init class entry.
1577 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Timestamp",
1578                                  Timestamp, timestamp)
1579   zend_declare_property_long(timestamp_type, "seconds", strlen("seconds"),
1580                              0 ,ZEND_ACC_PRIVATE TSRMLS_CC);
1581   zend_declare_property_long(timestamp_type, "nanos", strlen("nanos"),
1582                              0 ,ZEND_ACC_PRIVATE TSRMLS_CC);
1583 PHP_PROTO_INIT_SUBMSGCLASS_END
1584 
1585 PHP_METHOD(Timestamp, __construct) {
1586   init_file_timestamp(TSRMLS_C);
1587   MessageHeader* intern = UNBOX(MessageHeader, getThis());
1588   INIT_MESSAGE_WITH_ARRAY;
1589 }
1590 
1591 PHP_PROTO_FIELD_ACCESSORS(Timestamp, timestamp, Seconds, "seconds")
1592 PHP_PROTO_FIELD_ACCESSORS(Timestamp, timestamp, Nanos,   "nanos")
1593 
1594 PHP_METHOD(Timestamp, fromDateTime) {
1595   zval* datetime;
1596   zval member;
1597 
1598   PHP_PROTO_CE_DECLARE date_interface_ce;
1599   if (php_proto_zend_lookup_class("\\DatetimeInterface", 18,
1600                                   &date_interface_ce) == FAILURE) {
1601     zend_error(E_ERROR, "Make sure date extension is enabled.");
1602     return;
1603   }
1604 
1605   if (zend_parse_parameters(ZEND_NUM_ARGS() TSRMLS_CC, "O", &datetime,
1606                             PHP_PROTO_CE_UNREF(date_interface_ce)) == FAILURE) {
1607     zend_error(E_USER_ERROR, "Expect DatetimeInterface.");
1608     return;
1609   }
1610 
1611   int64_t timestamp_seconds;
1612   {
1613     zval retval;
1614     zval function_name;
1615 
1616 #if PHP_MAJOR_VERSION < 7
1617     INIT_ZVAL(retval);
1618     INIT_ZVAL(function_name);
1619 #endif
1620 
1621     PHP_PROTO_ZVAL_STRING(&function_name, "date_timestamp_get", 1);
1622 
1623     if (call_user_function(EG(function_table), NULL, &function_name, &retval, 1,
1624             ZVAL_PTR_TO_CACHED_PTR(datetime) TSRMLS_CC) == FAILURE) {
1625       zend_error(E_ERROR, "Cannot get timestamp from DateTime.");
1626       return;
1627     }
1628 
1629     protobuf_convert_to_int64(&retval, &timestamp_seconds);
1630 
1631     zval_dtor(&retval);
1632     zval_dtor(&function_name);
1633   }
1634 
1635   int64_t timestamp_micros;
1636   {
1637     zval retval;
1638     zval function_name;
1639     zval format_string;
1640 
1641 #if PHP_MAJOR_VERSION < 7
1642     INIT_ZVAL(retval);
1643     INIT_ZVAL(function_name);
1644     INIT_ZVAL(format_string);
1645 #endif
1646 
1647     PHP_PROTO_ZVAL_STRING(&function_name, "date_format", 1);
1648     PHP_PROTO_ZVAL_STRING(&format_string, "u", 1);
1649 
1650     CACHED_VALUE params[2] = {
1651       ZVAL_PTR_TO_CACHED_VALUE(datetime),
1652       ZVAL_TO_CACHED_VALUE(format_string),
1653     };
1654 
1655     if (call_user_function(EG(function_table), NULL, &function_name, &retval,
1656             ARRAY_SIZE(params), params TSRMLS_CC) == FAILURE) {
1657       zend_error(E_ERROR, "Cannot format DateTime.");
1658       return;
1659     }
1660 
1661     protobuf_convert_to_int64(&retval, &timestamp_micros);
1662 
1663     zval_dtor(&retval);
1664     zval_dtor(&function_name);
1665     zval_dtor(&format_string);
1666   }
1667 
1668   // Set seconds
1669   MessageHeader* self = UNBOX(MessageHeader, getThis());
1670   const upb_fielddef* field =
1671       upb_msgdef_ntofz(self->descriptor->msgdef, "seconds");
1672   void* storage = message_data(self);
1673   void* memory = slot_memory(self->descriptor->layout, storage, field);
1674   *(int64_t*)memory = timestamp_seconds;
1675 
1676   // Set nanos
1677   field = upb_msgdef_ntofz(self->descriptor->msgdef, "nanos");
1678   storage = message_data(self);
1679   memory = slot_memory(self->descriptor->layout, storage, field);
1680   *(int32_t*)memory = timestamp_micros * 1000;
1681 
1682   RETURN_NULL();
1683 }
1684 
1685 PHP_METHOD(Timestamp, toDateTime) {
1686   // Get seconds
1687   MessageHeader* self = UNBOX(MessageHeader, getThis());
1688   const upb_fielddef* field =
1689       upb_msgdef_ntofz(self->descriptor->msgdef, "seconds");
1690   void* storage = message_data(self);
1691   void* memory = slot_memory(self->descriptor->layout, storage, field);
1692   int64_t seconds = *(int64_t*)memory;
1693 
1694   // Get nanos
1695   field = upb_msgdef_ntofz(self->descriptor->msgdef, "nanos");
1696   memory = slot_memory(self->descriptor->layout, storage, field);
1697   int32_t nanos = *(int32_t*)memory;
1698 
1699   // Get formatted time string.
1700   char formatted_time[32];
1701   snprintf(formatted_time, sizeof(formatted_time), "%" PRId64 ".%06" PRId32,
1702            seconds, nanos / 1000);
1703 
1704   // Create Datetime object.
1705   zval datetime;
1706   zval function_name;
1707   zval format_string;
1708   zval formatted_time_php;
1709 
1710 #if PHP_MAJOR_VERSION < 7
1711   INIT_ZVAL(function_name);
1712   INIT_ZVAL(format_string);
1713   INIT_ZVAL(formatted_time_php);
1714 #endif
1715 
1716   PHP_PROTO_ZVAL_STRING(&function_name, "date_create_from_format", 1);
1717   PHP_PROTO_ZVAL_STRING(&format_string, "U.u", 1);
1718   PHP_PROTO_ZVAL_STRING(&formatted_time_php, formatted_time, 1);
1719 
1720   CACHED_VALUE params[2] = {
1721     ZVAL_TO_CACHED_VALUE(format_string),
1722     ZVAL_TO_CACHED_VALUE(formatted_time_php),
1723   };
1724 
1725   if (call_user_function(EG(function_table), NULL, &function_name, &datetime,
1726           ARRAY_SIZE(params), params TSRMLS_CC) == FAILURE) {
1727     zend_error(E_ERROR, "Cannot create DateTime.");
1728     return;
1729   }
1730 
1731   zval_dtor(&function_name);
1732   zval_dtor(&format_string);
1733   zval_dtor(&formatted_time_php);
1734 
1735 #if PHP_MAJOR_VERSION < 7
1736   zval* datetime_ptr = &datetime;
1737   PHP_PROTO_RETVAL_ZVAL(datetime_ptr);
1738 #else
1739   ZVAL_OBJ(return_value, Z_OBJ(datetime));
1740 #endif
1741 }
1742 
1743 // -----------------------------------------------------------------------------
1744 // Api
1745 // -----------------------------------------------------------------------------
1746 
1747 static  zend_function_entry api_methods[] = {
1748   PHP_ME(Api, __construct, NULL, ZEND_ACC_PUBLIC)
1749   PHP_ME(Api, getName, NULL, ZEND_ACC_PUBLIC)
1750   PHP_ME(Api, setName, NULL, ZEND_ACC_PUBLIC)
1751   PHP_ME(Api, getMethods, NULL, ZEND_ACC_PUBLIC)
1752   PHP_ME(Api, setMethods, NULL, ZEND_ACC_PUBLIC)
1753   PHP_ME(Api, getOptions, NULL, ZEND_ACC_PUBLIC)
1754   PHP_ME(Api, setOptions, NULL, ZEND_ACC_PUBLIC)
1755   PHP_ME(Api, getVersion, NULL, ZEND_ACC_PUBLIC)
1756   PHP_ME(Api, setVersion, NULL, ZEND_ACC_PUBLIC)
1757   PHP_ME(Api, getSourceContext, NULL, ZEND_ACC_PUBLIC)
1758   PHP_ME(Api, setSourceContext, NULL, ZEND_ACC_PUBLIC)
1759   PHP_ME(Api, getMixins, NULL, ZEND_ACC_PUBLIC)
1760   PHP_ME(Api, setMixins, NULL, ZEND_ACC_PUBLIC)
1761   PHP_ME(Api, getSyntax, NULL, ZEND_ACC_PUBLIC)
1762   PHP_ME(Api, setSyntax, NULL, ZEND_ACC_PUBLIC)
1763   {NULL, NULL, NULL}
1764 };
1765 
1766 zend_class_entry* api_type;
1767 
1768 // Init class entry.
1769 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Api",
1770                                  Api, api)
1771   zend_declare_property_null(api_type, "name", strlen("name"),
1772                              ZEND_ACC_PRIVATE TSRMLS_CC);
1773   zend_declare_property_null(api_type, "methods", strlen("methods"),
1774                              ZEND_ACC_PRIVATE TSRMLS_CC);
1775   zend_declare_property_null(api_type, "options", strlen("options"),
1776                              ZEND_ACC_PRIVATE TSRMLS_CC);
1777   zend_declare_property_null(api_type, "version", strlen("version"),
1778                              ZEND_ACC_PRIVATE TSRMLS_CC);
1779   zend_declare_property_null(api_type, "source_context", strlen("source_context"),
1780                              ZEND_ACC_PRIVATE TSRMLS_CC);
1781   zend_declare_property_null(api_type, "mixins", strlen("mixins"),
1782                              ZEND_ACC_PRIVATE TSRMLS_CC);
1783   zend_declare_property_null(api_type, "syntax", strlen("syntax"),
1784                              ZEND_ACC_PRIVATE TSRMLS_CC);
1785 PHP_PROTO_INIT_SUBMSGCLASS_END
1786 
1787 PHP_METHOD(Api, __construct) {
1788   init_file_api(TSRMLS_C);
1789   MessageHeader* intern = UNBOX(MessageHeader, getThis());
1790   INIT_MESSAGE_WITH_ARRAY;
1791 }
1792 
1793 PHP_PROTO_FIELD_ACCESSORS(Api, api, Name, "name")
1794 PHP_PROTO_FIELD_ACCESSORS(Api, api, Methods, "methods")
1795 PHP_PROTO_FIELD_ACCESSORS(Api, api, Options, "options")
1796 PHP_PROTO_FIELD_ACCESSORS(Api, api, Version, "version")
1797 PHP_PROTO_FIELD_ACCESSORS(Api, api, SourceContext, "source_context")
1798 PHP_PROTO_FIELD_ACCESSORS(Api, api, Mixins, "mixins")
1799 PHP_PROTO_FIELD_ACCESSORS(Api, api, Syntax, "syntax")
1800 
1801 // -----------------------------------------------------------------------------
1802 // BoolValue
1803 // -----------------------------------------------------------------------------
1804 
1805 static  zend_function_entry bool_value_methods[] = {
1806   PHP_ME(BoolValue, __construct, NULL, ZEND_ACC_PUBLIC)
1807   PHP_ME(BoolValue, getValue, NULL, ZEND_ACC_PUBLIC)
1808   PHP_ME(BoolValue, setValue, NULL, ZEND_ACC_PUBLIC)
1809   {NULL, NULL, NULL}
1810 };
1811 
1812 zend_class_entry* bool_value_type;
1813 
1814 // Init class entry.
1815 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\BoolValue",
1816                                  BoolValue, bool_value)
1817   zend_declare_property_null(bool_value_type, "value", strlen("value"),
1818                              ZEND_ACC_PRIVATE TSRMLS_CC);
1819 PHP_PROTO_INIT_SUBMSGCLASS_END
1820 
1821 PHP_METHOD(BoolValue, __construct) {
1822   init_file_wrappers(TSRMLS_C);
1823   MessageHeader* intern = UNBOX(MessageHeader, getThis());
1824   INIT_MESSAGE_WITH_ARRAY;
1825 }
1826 
1827 PHP_PROTO_FIELD_ACCESSORS(BoolValue, bool_value, Value, "value")
1828 
1829 // -----------------------------------------------------------------------------
1830 // BytesValue
1831 // -----------------------------------------------------------------------------
1832 
1833 static  zend_function_entry bytes_value_methods[] = {
1834   PHP_ME(BytesValue, __construct, NULL, ZEND_ACC_PUBLIC)
1835   PHP_ME(BytesValue, getValue, NULL, ZEND_ACC_PUBLIC)
1836   PHP_ME(BytesValue, setValue, NULL, ZEND_ACC_PUBLIC)
1837   {NULL, NULL, NULL}
1838 };
1839 
1840 zend_class_entry* bytes_value_type;
1841 
1842 // Init class entry.
1843 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\BytesValue",
1844                                  BytesValue, bytes_value)
1845   zend_declare_property_null(bytes_value_type, "value", strlen("value"),
1846                              ZEND_ACC_PRIVATE TSRMLS_CC);
1847 PHP_PROTO_INIT_SUBMSGCLASS_END
1848 
1849 PHP_METHOD(BytesValue, __construct) {
1850   init_file_wrappers(TSRMLS_C);
1851   MessageHeader* intern = UNBOX(MessageHeader, getThis());
1852   INIT_MESSAGE_WITH_ARRAY;
1853 }
1854 
1855 PHP_PROTO_FIELD_ACCESSORS(BytesValue, bytes_value, Value, "value")
1856 
1857 // -----------------------------------------------------------------------------
1858 // DoubleValue
1859 // -----------------------------------------------------------------------------
1860 
1861 static  zend_function_entry double_value_methods[] = {
1862   PHP_ME(DoubleValue, __construct, NULL, ZEND_ACC_PUBLIC)
1863   PHP_ME(DoubleValue, getValue, NULL, ZEND_ACC_PUBLIC)
1864   PHP_ME(DoubleValue, setValue, NULL, ZEND_ACC_PUBLIC)
1865   {NULL, NULL, NULL}
1866 };
1867 
1868 zend_class_entry* double_value_type;
1869 
1870 // Init class entry.
1871 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\DoubleValue",
1872                                  DoubleValue, double_value)
1873   zend_declare_property_null(double_value_type, "value", strlen("value"),
1874                              ZEND_ACC_PRIVATE TSRMLS_CC);
1875 PHP_PROTO_INIT_SUBMSGCLASS_END
1876 
1877 PHP_METHOD(DoubleValue, __construct) {
1878   init_file_wrappers(TSRMLS_C);
1879   MessageHeader* intern = UNBOX(MessageHeader, getThis());
1880   INIT_MESSAGE_WITH_ARRAY;
1881 }
1882 
1883 PHP_PROTO_FIELD_ACCESSORS(DoubleValue, double_value, Value, "value")
1884 
1885 // -----------------------------------------------------------------------------
1886 // Enum
1887 // -----------------------------------------------------------------------------
1888 
1889 static  zend_function_entry enum_methods[] = {
1890   PHP_ME(Enum, __construct, NULL, ZEND_ACC_PUBLIC)
1891   PHP_ME(Enum, getName, NULL, ZEND_ACC_PUBLIC)
1892   PHP_ME(Enum, setName, NULL, ZEND_ACC_PUBLIC)
1893   PHP_ME(Enum, getEnumvalue, NULL, ZEND_ACC_PUBLIC)
1894   PHP_ME(Enum, setEnumvalue, NULL, ZEND_ACC_PUBLIC)
1895   PHP_ME(Enum, getOptions, NULL, ZEND_ACC_PUBLIC)
1896   PHP_ME(Enum, setOptions, NULL, ZEND_ACC_PUBLIC)
1897   PHP_ME(Enum, getSourceContext, NULL, ZEND_ACC_PUBLIC)
1898   PHP_ME(Enum, setSourceContext, NULL, ZEND_ACC_PUBLIC)
1899   PHP_ME(Enum, getSyntax, NULL, ZEND_ACC_PUBLIC)
1900   PHP_ME(Enum, setSyntax, NULL, ZEND_ACC_PUBLIC)
1901   {NULL, NULL, NULL}
1902 };
1903 
1904 zend_class_entry* enum_type;
1905 
1906 // Init class entry.
1907 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Enum",
1908                                  Enum, enum)
1909   zend_declare_property_null(enum_type, "name", strlen("name"),
1910                              ZEND_ACC_PRIVATE TSRMLS_CC);
1911   zend_declare_property_null(enum_type, "enumvalue", strlen("enumvalue"),
1912                              ZEND_ACC_PRIVATE TSRMLS_CC);
1913   zend_declare_property_null(enum_type, "options", strlen("options"),
1914                              ZEND_ACC_PRIVATE TSRMLS_CC);
1915   zend_declare_property_null(enum_type, "source_context", strlen("source_context"),
1916                              ZEND_ACC_PRIVATE TSRMLS_CC);
1917   zend_declare_property_null(enum_type, "syntax", strlen("syntax"),
1918                              ZEND_ACC_PRIVATE TSRMLS_CC);
1919 PHP_PROTO_INIT_SUBMSGCLASS_END
1920 
1921 PHP_METHOD(Enum, __construct) {
1922   init_file_type(TSRMLS_C);
1923   MessageHeader* intern = UNBOX(MessageHeader, getThis());
1924   INIT_MESSAGE_WITH_ARRAY;
1925 }
1926 
1927 PHP_PROTO_FIELD_ACCESSORS(Enum, enum, Name, "name")
1928 PHP_PROTO_FIELD_ACCESSORS(Enum, enum, Enumvalue, "enumvalue")
1929 PHP_PROTO_FIELD_ACCESSORS(Enum, enum, Options, "options")
1930 PHP_PROTO_FIELD_ACCESSORS(Enum, enum, SourceContext, "source_context")
1931 PHP_PROTO_FIELD_ACCESSORS(Enum, enum, Syntax, "syntax")
1932 
1933 // -----------------------------------------------------------------------------
1934 // EnumValue
1935 // -----------------------------------------------------------------------------
1936 
1937 static  zend_function_entry enum_value_methods[] = {
1938   PHP_ME(EnumValue, __construct, NULL, ZEND_ACC_PUBLIC)
1939   PHP_ME(EnumValue, getName, NULL, ZEND_ACC_PUBLIC)
1940   PHP_ME(EnumValue, setName, NULL, ZEND_ACC_PUBLIC)
1941   PHP_ME(EnumValue, getNumber, NULL, ZEND_ACC_PUBLIC)
1942   PHP_ME(EnumValue, setNumber, NULL, ZEND_ACC_PUBLIC)
1943   PHP_ME(EnumValue, getOptions, NULL, ZEND_ACC_PUBLIC)
1944   PHP_ME(EnumValue, setOptions, NULL, ZEND_ACC_PUBLIC)
1945   {NULL, NULL, NULL}
1946 };
1947 
1948 zend_class_entry* enum_value_type;
1949 
1950 // Init class entry.
1951 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\EnumValue",
1952                                  EnumValue, enum_value)
1953   zend_declare_property_null(enum_value_type, "name", strlen("name"),
1954                              ZEND_ACC_PRIVATE TSRMLS_CC);
1955   zend_declare_property_null(enum_value_type, "number", strlen("number"),
1956                              ZEND_ACC_PRIVATE TSRMLS_CC);
1957   zend_declare_property_null(enum_value_type, "options", strlen("options"),
1958                              ZEND_ACC_PRIVATE TSRMLS_CC);
1959 PHP_PROTO_INIT_SUBMSGCLASS_END
1960 
1961 PHP_METHOD(EnumValue, __construct) {
1962   init_file_type(TSRMLS_C);
1963   MessageHeader* intern = UNBOX(MessageHeader, getThis());
1964   INIT_MESSAGE_WITH_ARRAY;
1965 }
1966 
1967 PHP_PROTO_FIELD_ACCESSORS(EnumValue, enum_value, Name, "name")
1968 PHP_PROTO_FIELD_ACCESSORS(EnumValue, enum_value, Number, "number")
1969 PHP_PROTO_FIELD_ACCESSORS(EnumValue, enum_value, Options, "options")
1970 
1971 // -----------------------------------------------------------------------------
1972 // FieldMask
1973 // -----------------------------------------------------------------------------
1974 
1975 static  zend_function_entry field_mask_methods[] = {
1976   PHP_ME(FieldMask, __construct, NULL, ZEND_ACC_PUBLIC)
1977   PHP_ME(FieldMask, getPaths, NULL, ZEND_ACC_PUBLIC)
1978   PHP_ME(FieldMask, setPaths, NULL, ZEND_ACC_PUBLIC)
1979   {NULL, NULL, NULL}
1980 };
1981 
1982 zend_class_entry* field_mask_type;
1983 
1984 // Init class entry.
1985 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\FieldMask",
1986                                  FieldMask, field_mask)
1987   zend_declare_property_null(field_mask_type, "paths", strlen("paths"),
1988                              ZEND_ACC_PRIVATE TSRMLS_CC);
1989 PHP_PROTO_INIT_SUBMSGCLASS_END
1990 
1991 PHP_METHOD(FieldMask, __construct) {
1992   init_file_field_mask(TSRMLS_C);
1993   MessageHeader* intern = UNBOX(MessageHeader, getThis());
1994   INIT_MESSAGE_WITH_ARRAY;
1995 }
1996 
1997 PHP_PROTO_FIELD_ACCESSORS(FieldMask, field_mask, Paths, "paths")
1998 
1999 // -----------------------------------------------------------------------------
2000 // Field
2001 // -----------------------------------------------------------------------------
2002 
2003 static  zend_function_entry field_methods[] = {
2004   PHP_ME(Field, __construct, NULL, ZEND_ACC_PUBLIC)
2005   PHP_ME(Field, getKind, NULL, ZEND_ACC_PUBLIC)
2006   PHP_ME(Field, setKind, NULL, ZEND_ACC_PUBLIC)
2007   PHP_ME(Field, getCardinality, NULL, ZEND_ACC_PUBLIC)
2008   PHP_ME(Field, setCardinality, NULL, ZEND_ACC_PUBLIC)
2009   PHP_ME(Field, getNumber, NULL, ZEND_ACC_PUBLIC)
2010   PHP_ME(Field, setNumber, NULL, ZEND_ACC_PUBLIC)
2011   PHP_ME(Field, getName, NULL, ZEND_ACC_PUBLIC)
2012   PHP_ME(Field, setName, NULL, ZEND_ACC_PUBLIC)
2013   PHP_ME(Field, getTypeUrl, NULL, ZEND_ACC_PUBLIC)
2014   PHP_ME(Field, setTypeUrl, NULL, ZEND_ACC_PUBLIC)
2015   PHP_ME(Field, getOneofIndex, NULL, ZEND_ACC_PUBLIC)
2016   PHP_ME(Field, setOneofIndex, NULL, ZEND_ACC_PUBLIC)
2017   PHP_ME(Field, getPacked, NULL, ZEND_ACC_PUBLIC)
2018   PHP_ME(Field, setPacked, NULL, ZEND_ACC_PUBLIC)
2019   PHP_ME(Field, getOptions, NULL, ZEND_ACC_PUBLIC)
2020   PHP_ME(Field, setOptions, NULL, ZEND_ACC_PUBLIC)
2021   PHP_ME(Field, getJsonName, NULL, ZEND_ACC_PUBLIC)
2022   PHP_ME(Field, setJsonName, NULL, ZEND_ACC_PUBLIC)
2023   PHP_ME(Field, getDefaultValue, NULL, ZEND_ACC_PUBLIC)
2024   PHP_ME(Field, setDefaultValue, NULL, ZEND_ACC_PUBLIC)
2025   {NULL, NULL, NULL}
2026 };
2027 
2028 zend_class_entry* field_type;
2029 
2030 // Init class entry.
2031 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Field",
2032                                  Field, field)
2033   zend_declare_property_null(field_type, "kind", strlen("kind"),
2034                              ZEND_ACC_PRIVATE TSRMLS_CC);
2035   zend_declare_property_null(field_type, "cardinality", strlen("cardinality"),
2036                              ZEND_ACC_PRIVATE TSRMLS_CC);
2037   zend_declare_property_null(field_type, "number", strlen("number"),
2038                              ZEND_ACC_PRIVATE TSRMLS_CC);
2039   zend_declare_property_null(field_type, "name", strlen("name"),
2040                              ZEND_ACC_PRIVATE TSRMLS_CC);
2041   zend_declare_property_null(field_type, "type_url", strlen("type_url"),
2042                              ZEND_ACC_PRIVATE TSRMLS_CC);
2043   zend_declare_property_null(field_type, "oneof_index", strlen("oneof_index"),
2044                              ZEND_ACC_PRIVATE TSRMLS_CC);
2045   zend_declare_property_null(field_type, "packed", strlen("packed"),
2046                              ZEND_ACC_PRIVATE TSRMLS_CC);
2047   zend_declare_property_null(field_type, "options", strlen("options"),
2048                              ZEND_ACC_PRIVATE TSRMLS_CC);
2049   zend_declare_property_null(field_type, "json_name", strlen("json_name"),
2050                              ZEND_ACC_PRIVATE TSRMLS_CC);
2051   zend_declare_property_null(field_type, "default_value", strlen("default_value"),
2052                              ZEND_ACC_PRIVATE TSRMLS_CC);
2053 PHP_PROTO_INIT_SUBMSGCLASS_END
2054 
2055 PHP_METHOD(Field, __construct) {
2056   init_file_type(TSRMLS_C);
2057   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2058   INIT_MESSAGE_WITH_ARRAY;
2059 }
2060 
2061 PHP_PROTO_FIELD_ACCESSORS(Field, field, Kind, "kind")
2062 PHP_PROTO_FIELD_ACCESSORS(Field, field, Cardinality, "cardinality")
2063 PHP_PROTO_FIELD_ACCESSORS(Field, field, Number, "number")
2064 PHP_PROTO_FIELD_ACCESSORS(Field, field, Name, "name")
2065 PHP_PROTO_FIELD_ACCESSORS(Field, field, TypeUrl, "type_url")
2066 PHP_PROTO_FIELD_ACCESSORS(Field, field, OneofIndex, "oneof_index")
2067 PHP_PROTO_FIELD_ACCESSORS(Field, field, Packed, "packed")
2068 PHP_PROTO_FIELD_ACCESSORS(Field, field, Options, "options")
2069 PHP_PROTO_FIELD_ACCESSORS(Field, field, JsonName, "json_name")
2070 PHP_PROTO_FIELD_ACCESSORS(Field, field, DefaultValue, "default_value")
2071 
2072 // -----------------------------------------------------------------------------
2073 // FloatValue
2074 // -----------------------------------------------------------------------------
2075 
2076 static  zend_function_entry float_value_methods[] = {
2077   PHP_ME(FloatValue, __construct, NULL, ZEND_ACC_PUBLIC)
2078   PHP_ME(FloatValue, getValue, NULL, ZEND_ACC_PUBLIC)
2079   PHP_ME(FloatValue, setValue, NULL, ZEND_ACC_PUBLIC)
2080   {NULL, NULL, NULL}
2081 };
2082 
2083 zend_class_entry* float_value_type;
2084 
2085 // Init class entry.
2086 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\FloatValue",
2087                                  FloatValue, float_value)
2088   zend_declare_property_null(float_value_type, "value", strlen("value"),
2089                              ZEND_ACC_PRIVATE TSRMLS_CC);
2090 PHP_PROTO_INIT_SUBMSGCLASS_END
2091 
2092 PHP_METHOD(FloatValue, __construct) {
2093   init_file_wrappers(TSRMLS_C);
2094   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2095   INIT_MESSAGE_WITH_ARRAY;
2096 }
2097 
2098 PHP_PROTO_FIELD_ACCESSORS(FloatValue, float_value, Value, "value")
2099 
2100 // -----------------------------------------------------------------------------
2101 // GPBEmpty
2102 // -----------------------------------------------------------------------------
2103 
2104 static  zend_function_entry empty_methods[] = {
2105   PHP_ME(GPBEmpty, __construct, NULL, ZEND_ACC_PUBLIC)
2106   {NULL, NULL, NULL}
2107 };
2108 
2109 zend_class_entry* empty_type;
2110 
2111 // Init class entry.
2112 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\GPBEmpty",
2113                                  GPBEmpty, empty)
2114 PHP_PROTO_INIT_SUBMSGCLASS_END
2115 
2116 PHP_METHOD(GPBEmpty, __construct) {
2117   init_file_empty(TSRMLS_C);
2118   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2119   INIT_MESSAGE_WITH_ARRAY;
2120 }
2121 
2122 
2123 // -----------------------------------------------------------------------------
2124 // Int32Value
2125 // -----------------------------------------------------------------------------
2126 
2127 static  zend_function_entry int32_value_methods[] = {
2128   PHP_ME(Int32Value, __construct, NULL, ZEND_ACC_PUBLIC)
2129   PHP_ME(Int32Value, getValue, NULL, ZEND_ACC_PUBLIC)
2130   PHP_ME(Int32Value, setValue, NULL, ZEND_ACC_PUBLIC)
2131   {NULL, NULL, NULL}
2132 };
2133 
2134 zend_class_entry* int32_value_type;
2135 
2136 // Init class entry.
2137 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Int32Value",
2138                                  Int32Value, int32_value)
2139   zend_declare_property_null(int32_value_type, "value", strlen("value"),
2140                              ZEND_ACC_PRIVATE TSRMLS_CC);
2141 PHP_PROTO_INIT_SUBMSGCLASS_END
2142 
2143 PHP_METHOD(Int32Value, __construct) {
2144   init_file_wrappers(TSRMLS_C);
2145   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2146   INIT_MESSAGE_WITH_ARRAY;
2147 }
2148 
2149 PHP_PROTO_FIELD_ACCESSORS(Int32Value, int32_value, Value, "value")
2150 
2151 // -----------------------------------------------------------------------------
2152 // Int64Value
2153 // -----------------------------------------------------------------------------
2154 
2155 static  zend_function_entry int64_value_methods[] = {
2156   PHP_ME(Int64Value, __construct, NULL, ZEND_ACC_PUBLIC)
2157   PHP_ME(Int64Value, getValue, NULL, ZEND_ACC_PUBLIC)
2158   PHP_ME(Int64Value, setValue, NULL, ZEND_ACC_PUBLIC)
2159   {NULL, NULL, NULL}
2160 };
2161 
2162 zend_class_entry* int64_value_type;
2163 
2164 // Init class entry.
2165 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Int64Value",
2166                                  Int64Value, int64_value)
2167   zend_declare_property_null(int64_value_type, "value", strlen("value"),
2168                              ZEND_ACC_PRIVATE TSRMLS_CC);
2169 PHP_PROTO_INIT_SUBMSGCLASS_END
2170 
2171 PHP_METHOD(Int64Value, __construct) {
2172   init_file_wrappers(TSRMLS_C);
2173   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2174   INIT_MESSAGE_WITH_ARRAY;
2175 }
2176 
2177 PHP_PROTO_FIELD_ACCESSORS(Int64Value, int64_value, Value, "value")
2178 
2179 // -----------------------------------------------------------------------------
2180 // ListValue
2181 // -----------------------------------------------------------------------------
2182 
2183 static  zend_function_entry list_value_methods[] = {
2184   PHP_ME(ListValue, __construct, NULL, ZEND_ACC_PUBLIC)
2185   PHP_ME(ListValue, getValues, NULL, ZEND_ACC_PUBLIC)
2186   PHP_ME(ListValue, setValues, NULL, ZEND_ACC_PUBLIC)
2187   {NULL, NULL, NULL}
2188 };
2189 
2190 zend_class_entry* list_value_type;
2191 
2192 // Init class entry.
2193 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\ListValue",
2194                                  ListValue, list_value)
2195   zend_declare_property_null(list_value_type, "values", strlen("values"),
2196                              ZEND_ACC_PRIVATE TSRMLS_CC);
2197 PHP_PROTO_INIT_SUBMSGCLASS_END
2198 
2199 PHP_METHOD(ListValue, __construct) {
2200   init_file_struct(TSRMLS_C);
2201   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2202   INIT_MESSAGE_WITH_ARRAY;
2203 }
2204 
2205 PHP_PROTO_FIELD_ACCESSORS(ListValue, list_value, Values, "values")
2206 
2207 // -----------------------------------------------------------------------------
2208 // Method
2209 // -----------------------------------------------------------------------------
2210 
2211 static  zend_function_entry method_methods[] = {
2212   PHP_ME(Method, __construct, NULL, ZEND_ACC_PUBLIC)
2213   PHP_ME(Method, getName, NULL, ZEND_ACC_PUBLIC)
2214   PHP_ME(Method, setName, NULL, ZEND_ACC_PUBLIC)
2215   PHP_ME(Method, getRequestTypeUrl, NULL, ZEND_ACC_PUBLIC)
2216   PHP_ME(Method, setRequestTypeUrl, NULL, ZEND_ACC_PUBLIC)
2217   PHP_ME(Method, getRequestStreaming, NULL, ZEND_ACC_PUBLIC)
2218   PHP_ME(Method, setRequestStreaming, NULL, ZEND_ACC_PUBLIC)
2219   PHP_ME(Method, getResponseTypeUrl, NULL, ZEND_ACC_PUBLIC)
2220   PHP_ME(Method, setResponseTypeUrl, NULL, ZEND_ACC_PUBLIC)
2221   PHP_ME(Method, getResponseStreaming, NULL, ZEND_ACC_PUBLIC)
2222   PHP_ME(Method, setResponseStreaming, NULL, ZEND_ACC_PUBLIC)
2223   PHP_ME(Method, getOptions, NULL, ZEND_ACC_PUBLIC)
2224   PHP_ME(Method, setOptions, NULL, ZEND_ACC_PUBLIC)
2225   PHP_ME(Method, getSyntax, NULL, ZEND_ACC_PUBLIC)
2226   PHP_ME(Method, setSyntax, NULL, ZEND_ACC_PUBLIC)
2227   {NULL, NULL, NULL}
2228 };
2229 
2230 zend_class_entry* method_type;
2231 
2232 // Init class entry.
2233 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Method",
2234                                  Method, method)
2235   zend_declare_property_null(method_type, "name", strlen("name"),
2236                              ZEND_ACC_PRIVATE TSRMLS_CC);
2237   zend_declare_property_null(method_type, "request_type_url", strlen("request_type_url"),
2238                              ZEND_ACC_PRIVATE TSRMLS_CC);
2239   zend_declare_property_null(method_type, "request_streaming", strlen("request_streaming"),
2240                              ZEND_ACC_PRIVATE TSRMLS_CC);
2241   zend_declare_property_null(method_type, "response_type_url", strlen("response_type_url"),
2242                              ZEND_ACC_PRIVATE TSRMLS_CC);
2243   zend_declare_property_null(method_type, "response_streaming", strlen("response_streaming"),
2244                              ZEND_ACC_PRIVATE TSRMLS_CC);
2245   zend_declare_property_null(method_type, "options", strlen("options"),
2246                              ZEND_ACC_PRIVATE TSRMLS_CC);
2247   zend_declare_property_null(method_type, "syntax", strlen("syntax"),
2248                              ZEND_ACC_PRIVATE TSRMLS_CC);
2249 PHP_PROTO_INIT_SUBMSGCLASS_END
2250 
2251 PHP_METHOD(Method, __construct) {
2252   init_file_api(TSRMLS_C);
2253   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2254   INIT_MESSAGE_WITH_ARRAY;
2255 }
2256 
2257 PHP_PROTO_FIELD_ACCESSORS(Method, method, Name, "name")
2258 PHP_PROTO_FIELD_ACCESSORS(Method, method, RequestTypeUrl, "request_type_url")
2259 PHP_PROTO_FIELD_ACCESSORS(Method, method, RequestStreaming, "request_streaming")
2260 PHP_PROTO_FIELD_ACCESSORS(Method, method, ResponseTypeUrl, "response_type_url")
2261 PHP_PROTO_FIELD_ACCESSORS(Method, method, ResponseStreaming, "response_streaming")
2262 PHP_PROTO_FIELD_ACCESSORS(Method, method, Options, "options")
2263 PHP_PROTO_FIELD_ACCESSORS(Method, method, Syntax, "syntax")
2264 
2265 // -----------------------------------------------------------------------------
2266 // Mixin
2267 // -----------------------------------------------------------------------------
2268 
2269 static  zend_function_entry mixin_methods[] = {
2270   PHP_ME(Mixin, __construct, NULL, ZEND_ACC_PUBLIC)
2271   PHP_ME(Mixin, getName, NULL, ZEND_ACC_PUBLIC)
2272   PHP_ME(Mixin, setName, NULL, ZEND_ACC_PUBLIC)
2273   PHP_ME(Mixin, getRoot, NULL, ZEND_ACC_PUBLIC)
2274   PHP_ME(Mixin, setRoot, NULL, ZEND_ACC_PUBLIC)
2275   {NULL, NULL, NULL}
2276 };
2277 
2278 zend_class_entry* mixin_type;
2279 
2280 // Init class entry.
2281 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Mixin",
2282                                  Mixin, mixin)
2283   zend_declare_property_null(mixin_type, "name", strlen("name"),
2284                              ZEND_ACC_PRIVATE TSRMLS_CC);
2285   zend_declare_property_null(mixin_type, "root", strlen("root"),
2286                              ZEND_ACC_PRIVATE TSRMLS_CC);
2287 PHP_PROTO_INIT_SUBMSGCLASS_END
2288 
2289 PHP_METHOD(Mixin, __construct) {
2290   init_file_api(TSRMLS_C);
2291   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2292   INIT_MESSAGE_WITH_ARRAY;
2293 }
2294 
2295 PHP_PROTO_FIELD_ACCESSORS(Mixin, mixin, Name, "name")
2296 PHP_PROTO_FIELD_ACCESSORS(Mixin, mixin, Root, "root")
2297 
2298 // -----------------------------------------------------------------------------
2299 // Option
2300 // -----------------------------------------------------------------------------
2301 
2302 static  zend_function_entry option_methods[] = {
2303   PHP_ME(Option, __construct, NULL, ZEND_ACC_PUBLIC)
2304   PHP_ME(Option, getName, NULL, ZEND_ACC_PUBLIC)
2305   PHP_ME(Option, setName, NULL, ZEND_ACC_PUBLIC)
2306   PHP_ME(Option, getValue, NULL, ZEND_ACC_PUBLIC)
2307   PHP_ME(Option, setValue, NULL, ZEND_ACC_PUBLIC)
2308   {NULL, NULL, NULL}
2309 };
2310 
2311 zend_class_entry* option_type;
2312 
2313 // Init class entry.
2314 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Option",
2315                                  Option, option)
2316   zend_declare_property_null(option_type, "name", strlen("name"),
2317                              ZEND_ACC_PRIVATE TSRMLS_CC);
2318   zend_declare_property_null(option_type, "value", strlen("value"),
2319                              ZEND_ACC_PRIVATE TSRMLS_CC);
2320 PHP_PROTO_INIT_SUBMSGCLASS_END
2321 
2322 PHP_METHOD(Option, __construct) {
2323   init_file_type(TSRMLS_C);
2324   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2325   INIT_MESSAGE_WITH_ARRAY;
2326 }
2327 
2328 PHP_PROTO_FIELD_ACCESSORS(Option, option, Name, "name")
2329 PHP_PROTO_FIELD_ACCESSORS(Option, option, Value, "value")
2330 
2331 // -----------------------------------------------------------------------------
2332 // SourceContext
2333 // -----------------------------------------------------------------------------
2334 
2335 static  zend_function_entry source_context_methods[] = {
2336   PHP_ME(SourceContext, __construct, NULL, ZEND_ACC_PUBLIC)
2337   PHP_ME(SourceContext, getFileName, NULL, ZEND_ACC_PUBLIC)
2338   PHP_ME(SourceContext, setFileName, NULL, ZEND_ACC_PUBLIC)
2339   {NULL, NULL, NULL}
2340 };
2341 
2342 zend_class_entry* source_context_type;
2343 
2344 // Init class entry.
2345 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\SourceContext",
2346                                  SourceContext, source_context)
2347   zend_declare_property_null(source_context_type, "file_name", strlen("file_name"),
2348                              ZEND_ACC_PRIVATE TSRMLS_CC);
2349 PHP_PROTO_INIT_SUBMSGCLASS_END
2350 
2351 PHP_METHOD(SourceContext, __construct) {
2352   init_file_source_context(TSRMLS_C);
2353   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2354   INIT_MESSAGE_WITH_ARRAY;
2355 }
2356 
2357 PHP_PROTO_FIELD_ACCESSORS(SourceContext, source_context, FileName, "file_name")
2358 
2359 // -----------------------------------------------------------------------------
2360 // StringValue
2361 // -----------------------------------------------------------------------------
2362 
2363 static  zend_function_entry string_value_methods[] = {
2364   PHP_ME(StringValue, __construct, NULL, ZEND_ACC_PUBLIC)
2365   PHP_ME(StringValue, getValue, NULL, ZEND_ACC_PUBLIC)
2366   PHP_ME(StringValue, setValue, NULL, ZEND_ACC_PUBLIC)
2367   {NULL, NULL, NULL}
2368 };
2369 
2370 zend_class_entry* string_value_type;
2371 
2372 // Init class entry.
2373 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\StringValue",
2374                                  StringValue, string_value)
2375   zend_declare_property_null(string_value_type, "value", strlen("value"),
2376                              ZEND_ACC_PRIVATE TSRMLS_CC);
2377 PHP_PROTO_INIT_SUBMSGCLASS_END
2378 
2379 PHP_METHOD(StringValue, __construct) {
2380   init_file_wrappers(TSRMLS_C);
2381   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2382   INIT_MESSAGE_WITH_ARRAY;
2383 }
2384 
2385 PHP_PROTO_FIELD_ACCESSORS(StringValue, string_value, Value, "value")
2386 
2387 // -----------------------------------------------------------------------------
2388 // Struct
2389 // -----------------------------------------------------------------------------
2390 
2391 static  zend_function_entry struct_methods[] = {
2392   PHP_ME(Struct, __construct, NULL, ZEND_ACC_PUBLIC)
2393   PHP_ME(Struct, getFields, NULL, ZEND_ACC_PUBLIC)
2394   PHP_ME(Struct, setFields, NULL, ZEND_ACC_PUBLIC)
2395   {NULL, NULL, NULL}
2396 };
2397 
2398 zend_class_entry* struct_type;
2399 
2400 // Init class entry.
2401 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Struct",
2402                                  Struct, struct)
2403   zend_declare_property_null(struct_type, "fields", strlen("fields"),
2404                              ZEND_ACC_PRIVATE TSRMLS_CC);
2405 PHP_PROTO_INIT_SUBMSGCLASS_END
2406 
2407 PHP_METHOD(Struct, __construct) {
2408   init_file_struct(TSRMLS_C);
2409   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2410   INIT_MESSAGE_WITH_ARRAY;
2411 }
2412 
2413 PHP_PROTO_FIELD_ACCESSORS(Struct, struct, Fields, "fields")
2414 
2415 // -----------------------------------------------------------------------------
2416 // Type
2417 // -----------------------------------------------------------------------------
2418 
2419 static  zend_function_entry type_methods[] = {
2420   PHP_ME(Type, __construct, NULL, ZEND_ACC_PUBLIC)
2421   PHP_ME(Type, getName, NULL, ZEND_ACC_PUBLIC)
2422   PHP_ME(Type, setName, NULL, ZEND_ACC_PUBLIC)
2423   PHP_ME(Type, getFields, NULL, ZEND_ACC_PUBLIC)
2424   PHP_ME(Type, setFields, NULL, ZEND_ACC_PUBLIC)
2425   PHP_ME(Type, getOneofs, NULL, ZEND_ACC_PUBLIC)
2426   PHP_ME(Type, setOneofs, NULL, ZEND_ACC_PUBLIC)
2427   PHP_ME(Type, getOptions, NULL, ZEND_ACC_PUBLIC)
2428   PHP_ME(Type, setOptions, NULL, ZEND_ACC_PUBLIC)
2429   PHP_ME(Type, getSourceContext, NULL, ZEND_ACC_PUBLIC)
2430   PHP_ME(Type, setSourceContext, NULL, ZEND_ACC_PUBLIC)
2431   PHP_ME(Type, getSyntax, NULL, ZEND_ACC_PUBLIC)
2432   PHP_ME(Type, setSyntax, NULL, ZEND_ACC_PUBLIC)
2433   {NULL, NULL, NULL}
2434 };
2435 
2436 zend_class_entry* type_type;
2437 
2438 // Init class entry.
2439 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Type",
2440                                  Type, type)
2441   zend_declare_property_null(type_type, "name", strlen("name"),
2442                              ZEND_ACC_PRIVATE TSRMLS_CC);
2443   zend_declare_property_null(type_type, "fields", strlen("fields"),
2444                              ZEND_ACC_PRIVATE TSRMLS_CC);
2445   zend_declare_property_null(type_type, "oneofs", strlen("oneofs"),
2446                              ZEND_ACC_PRIVATE TSRMLS_CC);
2447   zend_declare_property_null(type_type, "options", strlen("options"),
2448                              ZEND_ACC_PRIVATE TSRMLS_CC);
2449   zend_declare_property_null(type_type, "source_context", strlen("source_context"),
2450                              ZEND_ACC_PRIVATE TSRMLS_CC);
2451   zend_declare_property_null(type_type, "syntax", strlen("syntax"),
2452                              ZEND_ACC_PRIVATE TSRMLS_CC);
2453 PHP_PROTO_INIT_SUBMSGCLASS_END
2454 
2455 PHP_METHOD(Type, __construct) {
2456   init_file_type(TSRMLS_C);
2457   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2458   INIT_MESSAGE_WITH_ARRAY;
2459 }
2460 
2461 PHP_PROTO_FIELD_ACCESSORS(Type, type, Name, "name")
2462 PHP_PROTO_FIELD_ACCESSORS(Type, type, Fields, "fields")
2463 PHP_PROTO_FIELD_ACCESSORS(Type, type, Oneofs, "oneofs")
2464 PHP_PROTO_FIELD_ACCESSORS(Type, type, Options, "options")
2465 PHP_PROTO_FIELD_ACCESSORS(Type, type, SourceContext, "source_context")
2466 PHP_PROTO_FIELD_ACCESSORS(Type, type, Syntax, "syntax")
2467 
2468 // -----------------------------------------------------------------------------
2469 // UInt32Value
2470 // -----------------------------------------------------------------------------
2471 
2472 static  zend_function_entry u_int32_value_methods[] = {
2473   PHP_ME(UInt32Value, __construct, NULL, ZEND_ACC_PUBLIC)
2474   PHP_ME(UInt32Value, getValue, NULL, ZEND_ACC_PUBLIC)
2475   PHP_ME(UInt32Value, setValue, NULL, ZEND_ACC_PUBLIC)
2476   {NULL, NULL, NULL}
2477 };
2478 
2479 zend_class_entry* u_int32_value_type;
2480 
2481 // Init class entry.
2482 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\UInt32Value",
2483                                  UInt32Value, u_int32_value)
2484   zend_declare_property_null(u_int32_value_type, "value", strlen("value"),
2485                              ZEND_ACC_PRIVATE TSRMLS_CC);
2486 PHP_PROTO_INIT_SUBMSGCLASS_END
2487 
2488 PHP_METHOD(UInt32Value, __construct) {
2489   init_file_wrappers(TSRMLS_C);
2490   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2491   INIT_MESSAGE_WITH_ARRAY;
2492 }
2493 
2494 PHP_PROTO_FIELD_ACCESSORS(UInt32Value, u_int32_value, Value, "value")
2495 
2496 // -----------------------------------------------------------------------------
2497 // UInt64Value
2498 // -----------------------------------------------------------------------------
2499 
2500 static  zend_function_entry u_int64_value_methods[] = {
2501   PHP_ME(UInt64Value, __construct, NULL, ZEND_ACC_PUBLIC)
2502   PHP_ME(UInt64Value, getValue, NULL, ZEND_ACC_PUBLIC)
2503   PHP_ME(UInt64Value, setValue, NULL, ZEND_ACC_PUBLIC)
2504   {NULL, NULL, NULL}
2505 };
2506 
2507 zend_class_entry* u_int64_value_type;
2508 
2509 // Init class entry.
2510 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\UInt64Value",
2511                                  UInt64Value, u_int64_value)
2512   zend_declare_property_null(u_int64_value_type, "value", strlen("value"),
2513                              ZEND_ACC_PRIVATE TSRMLS_CC);
2514 PHP_PROTO_INIT_SUBMSGCLASS_END
2515 
2516 PHP_METHOD(UInt64Value, __construct) {
2517   init_file_wrappers(TSRMLS_C);
2518   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2519   INIT_MESSAGE_WITH_ARRAY;
2520 }
2521 
2522 PHP_PROTO_FIELD_ACCESSORS(UInt64Value, u_int64_value, Value, "value")
2523 
2524 // -----------------------------------------------------------------------------
2525 // Value
2526 // -----------------------------------------------------------------------------
2527 
2528 static zend_function_entry value_methods[] = {
2529   PHP_ME(Value, __construct, NULL, ZEND_ACC_PUBLIC)
2530   PHP_ME(Value, getNullValue, NULL, ZEND_ACC_PUBLIC)
2531   PHP_ME(Value, setNullValue, NULL, ZEND_ACC_PUBLIC)
2532   PHP_ME(Value, getNumberValue, NULL, ZEND_ACC_PUBLIC)
2533   PHP_ME(Value, setNumberValue, NULL, ZEND_ACC_PUBLIC)
2534   PHP_ME(Value, getStringValue, NULL, ZEND_ACC_PUBLIC)
2535   PHP_ME(Value, setStringValue, NULL, ZEND_ACC_PUBLIC)
2536   PHP_ME(Value, getBoolValue, NULL, ZEND_ACC_PUBLIC)
2537   PHP_ME(Value, setBoolValue, NULL, ZEND_ACC_PUBLIC)
2538   PHP_ME(Value, getStructValue, NULL, ZEND_ACC_PUBLIC)
2539   PHP_ME(Value, setStructValue, NULL, ZEND_ACC_PUBLIC)
2540   PHP_ME(Value, getListValue, NULL, ZEND_ACC_PUBLIC)
2541   PHP_ME(Value, setListValue, NULL, ZEND_ACC_PUBLIC)
2542   PHP_ME(Value, getKind, NULL, ZEND_ACC_PUBLIC)
2543   {NULL, NULL, NULL}
2544 };
2545 
2546 zend_class_entry* value_type;
2547 
2548 // Init class entry.
2549 PHP_PROTO_INIT_SUBMSGCLASS_START("Google\\Protobuf\\Value",
2550                                  Value, value)
2551   zend_declare_property_null(value_type, "kind", strlen("kind"),
2552                              ZEND_ACC_PRIVATE TSRMLS_CC);
2553 PHP_PROTO_INIT_SUBMSGCLASS_END
2554 
2555 PHP_METHOD(Value, __construct) {
2556   init_file_struct(TSRMLS_C);
2557   MessageHeader* intern = UNBOX(MessageHeader, getThis());
2558   INIT_MESSAGE_WITH_ARRAY;
2559 }
2560 
2561 PHP_PROTO_ONEOF_FIELD_ACCESSORS(Value, value, NullValue, "null_value")
2562 PHP_PROTO_ONEOF_FIELD_ACCESSORS(Value, value, NumberValue, "number_value")
2563 PHP_PROTO_ONEOF_FIELD_ACCESSORS(Value, value, StringValue, "string_value")
2564 PHP_PROTO_ONEOF_FIELD_ACCESSORS(Value, value, BoolValue, "bool_value")
2565 PHP_PROTO_ONEOF_FIELD_ACCESSORS(Value, value, StructValue, "struct_value")
2566 PHP_PROTO_ONEOF_FIELD_ACCESSORS(Value, value, ListValue, "list_value")
2567 PHP_PROTO_ONEOF_ACCESSORS(Value, value, Kind, "kind")
2568 
2569 // -----------------------------------------------------------------------------
2570 // GPBMetadata files for well known types
2571 // -----------------------------------------------------------------------------
2572 
2573 #define DEFINE_GPBMETADATA_FILE(LOWERNAME, CAMELNAME, CLASSNAME)      \
2574   zend_class_entry* gpb_metadata_##LOWERNAME##_type;                  \
2575   static zend_function_entry gpb_metadata_##LOWERNAME##_methods[] = { \
2576     PHP_ME(GPBMetadata_##CAMELNAME, initOnce, NULL,                   \
2577            ZEND_ACC_PUBLIC | ZEND_ACC_STATIC)                         \
2578     ZEND_FE_END                                                       \
2579   };                                                                  \
2580   void gpb_metadata_##LOWERNAME##_init(TSRMLS_D) {                    \
2581     zend_class_entry class_type;                                      \
2582     INIT_CLASS_ENTRY(class_type, CLASSNAME,                           \
2583                      gpb_metadata_##LOWERNAME##_methods);             \
2584     gpb_metadata_##LOWERNAME##_type =                                 \
2585         zend_register_internal_class(&class_type TSRMLS_CC);          \
2586   }                                                                   \
2587   PHP_METHOD(GPBMetadata_##CAMELNAME, initOnce) {                     \
2588     init_file_##LOWERNAME(TSRMLS_C);                                  \
2589   }
2590 
2591 DEFINE_GPBMETADATA_FILE(any, Any, "GPBMetadata\\Google\\Protobuf\\Any");
2592 DEFINE_GPBMETADATA_FILE(api, Api, "GPBMetadata\\Google\\Protobuf\\Api");
2593 DEFINE_GPBMETADATA_FILE(duration, Duration,
2594                         "GPBMetadata\\Google\\Protobuf\\Duration");
2595 DEFINE_GPBMETADATA_FILE(field_mask, FieldMask,
2596                         "GPBMetadata\\Google\\Protobuf\\FieldMask");
2597 DEFINE_GPBMETADATA_FILE(empty, Empty,
2598                         "GPBMetadata\\Google\\Protobuf\\GPBEmpty");
2599 DEFINE_GPBMETADATA_FILE(source_context, SourceContext,
2600                         "GPBMetadata\\Google\\Protobuf\\SourceContext");
2601 DEFINE_GPBMETADATA_FILE(struct, Struct,
2602                         "GPBMetadata\\Google\\Protobuf\\Struct");
2603 DEFINE_GPBMETADATA_FILE(timestamp, Timestamp,
2604                         "GPBMetadata\\Google\\Protobuf\\Timestamp");
2605 DEFINE_GPBMETADATA_FILE(type, Type, "GPBMetadata\\Google\\Protobuf\\Type");
2606 DEFINE_GPBMETADATA_FILE(wrappers, Wrappers,
2607                         "GPBMetadata\\Google\\Protobuf\\Wrappers");
2608 
2609 #undef DEFINE_GPBMETADATA_FILE
2610