@@ -63,8 +63,10 @@ static void mpack_write_utf8_lossy_cstr(mpack_writer_t *writer, const char *str,
6363#define KEY_TRACE_ID "trace_id"
6464#define KEY_SPAN_ID "span_id"
6565#define KEY_PARENT_ID "parent_id"
66+ #define KEY_META_STRUCT "meta_struct"
6667
6768static int msgpack_write_zval (mpack_writer_t * writer , zval * trace , int level );
69+ static void serialize_meta_struct (mpack_writer_t * writer , zval * trace );
6870
6971static int write_hash_table (mpack_writer_t * writer , HashTable * ht , int level ) {
7072 zval * tmp ;
@@ -89,6 +91,7 @@ static int write_hash_table(mpack_writer_t *writer, HashTable *ht, int level) {
8991 ZEND_HASH_FOREACH_KEY_VAL_IND (ht , num_key , string_key , tmp ) {
9092 // Writing the key, if associative
9193 bool zval_string_as_uint64 = false;
94+ bool is_meta_struct = false;
9295 if (is_assoc == 1 ) {
9396 char num_str_buf [MAX_ID_BUFSIZ ], * key ;
9497 size_t len ;
@@ -105,11 +108,17 @@ static int write_hash_table(mpack_writer_t *writer, HashTable *ht, int level) {
105108 (0 == strcmp (KEY_TRACE_ID , key ) || 0 == strcmp (KEY_SPAN_ID , key ) || 0 == strcmp (KEY_PARENT_ID , key ))) {
106109 zval_string_as_uint64 = true;
107110 }
111+ if (level <= 3 &&
112+ (0 == strcmp (KEY_META_STRUCT , key ))) {
113+ is_meta_struct = true;
114+ }
108115 }
109116
110117 // Writing the value
111118 if (zval_string_as_uint64 ) {
112119 mpack_write_u64 (writer , strtoull (Z_STRVAL_P (tmp ), NULL , 10 ));
120+ } else if (is_meta_struct ) {
121+ serialize_meta_struct (writer , tmp );
113122 } else if (msgpack_write_zval (writer , tmp , level ) != 1 ) {
114123 return 0 ;
115124 }
@@ -128,7 +137,6 @@ static int msgpack_write_zval(mpack_writer_t *writer, zval *trace, int level) {
128137 if (Z_TYPE_P (trace ) == IS_REFERENCE ) {
129138 trace = Z_REFVAL_P (trace );
130139 }
131-
132140 switch (Z_TYPE_P (trace )) {
133141 case IS_ARRAY :
134142 if (write_hash_table (writer , Z_ARRVAL_P (trace ), level + 1 ) != 1 ) {
@@ -159,6 +167,26 @@ static int msgpack_write_zval(mpack_writer_t *writer, zval *trace, int level) {
159167 return 1 ;
160168}
161169
170+ static void serialize_meta_struct (mpack_writer_t * writer , zval * meta_struct ) {
171+ zval * tmp ;
172+ zend_string * string_key ;
173+
174+ HashTable * ht = Z_ARRVAL_P (meta_struct );
175+
176+ mpack_start_map (writer , zend_hash_num_elements (ht ));
177+
178+ ZEND_HASH_FOREACH_STR_KEY_VAL_IND (ht , string_key , tmp ) {
179+ if (!string_key ) {
180+ continue ;
181+ }
182+ mpack_write_cstr (writer , ZSTR_VAL (string_key ));
183+ mpack_write_bin (writer , Z_STRVAL_P (tmp ), Z_STRLEN_P (tmp ));
184+ }
185+ ZEND_HASH_FOREACH_END ();
186+
187+ mpack_finish_map (writer );
188+ }
189+
162190int ddtrace_serialize_simple_array_into_c_string (zval * trace , char * * data_p , size_t * size_p ) {
163191 // encode to memory buffer
164192 char * data ;
@@ -1017,6 +1045,26 @@ static void dd_serialize_array_metrics_recursively(zend_array *target, zend_stri
10171045 dd_serialize_array_recursively (target , str , value , true);
10181046}
10191047
1048+ static void dd_serialize_array_meta_struct_recursively (zend_array * target , zend_string * str , zval * value ) {
1049+ char * data ;
1050+ size_t size ;
1051+
1052+ mpack_writer_t writer ;
1053+ mpack_writer_init_growable (& writer , & data , & size );
1054+ int result = msgpack_write_zval (& writer , value , 5 );
1055+ mpack_writer_destroy (& writer );
1056+
1057+ if (size == 0 || result == 0 ) {
1058+ return ;
1059+ }
1060+
1061+ zval serialised ;
1062+ ZVAL_STRINGL (& serialised , data , size );
1063+
1064+ zend_hash_update (target , str , & serialised );
1065+ free (data );
1066+ }
1067+
10201068struct iter {
10211069 // caller owns key/value
10221070 bool (* next )(struct iter * self , zend_string * * key , zend_string * * value );
@@ -1426,7 +1474,6 @@ static zend_always_inline double strconv_parse_bool(zend_string *str) {
14261474
14271475void ddtrace_serialize_span_to_array (ddtrace_span_data * span , zval * array ) {
14281476 bool is_root_span = span -> std .ce == ddtrace_ce_root_span_data ;
1429-
14301477 zval * el ;
14311478 zval zv ;
14321479 el = & zv ;
@@ -1794,6 +1841,23 @@ void ddtrace_serialize_span_to_array(ddtrace_span_data *span, zval *array) {
17941841 zend_array_destroy (Z_ARR (metrics_zv ));
17951842 }
17961843
1844+ zend_array * meta_struct = ddtrace_property_array (& span -> property_meta_struct );
1845+ zval meta_struct_zv ;
1846+ array_init (& meta_struct_zv );
1847+ zend_string * ms_str_key ;
1848+ zval * ms_val ;
1849+ ZEND_HASH_FOREACH_STR_KEY_VAL_IND (meta_struct , ms_str_key , ms_val ) {
1850+ if (ms_str_key ) {
1851+ dd_serialize_array_meta_struct_recursively (Z_ARRVAL (meta_struct_zv ), ms_str_key , ms_val );
1852+ }
1853+ }
1854+ ZEND_HASH_FOREACH_END ();
1855+ if (zend_hash_num_elements (Z_ARR (meta_struct_zv ))) {
1856+ zend_hash_str_add_new (Z_ARR_P (el ), ZEND_STRL ("meta_struct" ), & meta_struct_zv );
1857+ } else {
1858+ zend_array_destroy (Z_ARR (meta_struct_zv ));
1859+ }
1860+
17971861 add_next_index_zval (array , el );
17981862}
17991863
0 commit comments