@@ -18,14 +18,16 @@ struct sentry_envelope_item_s {
1818 sentry_value_t event ;
1919 char * payload ;
2020 size_t payload_len ;
21+ sentry_envelope_item_t * next ;
2122};
2223
2324struct sentry_envelope_s {
2425 bool is_raw ;
2526 union {
2627 struct {
2728 sentry_value_t headers ;
28- sentry_envelope_item_t items [SENTRY_MAX_ENVELOPE_ITEMS ];
29+ sentry_envelope_item_t * first_item ;
30+ sentry_envelope_item_t * last_item ;
2931 size_t item_count ;
3032 } items ;
3133 struct {
@@ -41,21 +43,34 @@ envelope_add_item(sentry_envelope_t *envelope)
4143 if (envelope -> is_raw ) {
4244 return NULL ;
4345 }
44- if (envelope -> contents .items .item_count >= SENTRY_MAX_ENVELOPE_ITEMS ) {
45- return NULL ;
46- }
46+
4747 // TODO: Envelopes may have at most one event item or one transaction item,
4848 // and not one of both. Some checking should be done here or in
4949 // `sentry__envelope_add_[transaction|event]` to ensure this can't happen.
5050
51- sentry_envelope_item_t * rv
52- = & envelope -> contents .items
53- .items [envelope -> contents .items .item_count ++ ];
54- rv -> headers = sentry_value_new_object ();
55- rv -> event = sentry_value_new_null ();
56- rv -> payload = NULL ;
57- rv -> payload_len = 0 ;
58- return rv ;
51+ // Allocate new item
52+ sentry_envelope_item_t * item = SENTRY_MAKE (sentry_envelope_item_t );
53+ if (!item ) {
54+ return NULL ;
55+ }
56+
57+ // Initialize item
58+ item -> headers = sentry_value_new_object ();
59+ item -> event = sentry_value_new_null ();
60+ item -> payload = NULL ;
61+ item -> payload_len = 0 ;
62+ item -> next = NULL ;
63+
64+ // Append to linked list
65+ if (envelope -> contents .items .last_item ) {
66+ envelope -> contents .items .last_item -> next = item ;
67+ } else {
68+ envelope -> contents .items .first_item = item ;
69+ }
70+ envelope -> contents .items .last_item = item ;
71+ envelope -> contents .items .item_count ++ ;
72+
73+ return item ;
5974}
6075
6176static void
@@ -141,9 +156,16 @@ sentry_envelope_free(sentry_envelope_t *envelope)
141156 return ;
142157 }
143158 sentry_value_decref (envelope -> contents .items .headers );
144- for (size_t i = 0 ; i < envelope -> contents .items .item_count ; i ++ ) {
145- envelope_item_cleanup (& envelope -> contents .items .items [i ]);
159+
160+ // Free all items in the linked list
161+ sentry_envelope_item_t * item = envelope -> contents .items .first_item ;
162+ while (item ) {
163+ sentry_envelope_item_t * next = item -> next ;
164+ envelope_item_cleanup (item );
165+ sentry_free (item );
166+ item = next ;
146167 }
168+
147169 sentry_free (envelope );
148170}
149171
@@ -166,6 +188,8 @@ sentry__envelope_new(void)
166188 }
167189
168190 rv -> is_raw = false;
191+ rv -> contents .items .first_item = NULL ;
192+ rv -> contents .items .last_item = NULL ;
169193 rv -> contents .items .item_count = 0 ;
170194 rv -> contents .items .headers = sentry_value_new_object ();
171195
@@ -226,12 +250,13 @@ sentry_envelope_get_event(const sentry_envelope_t *envelope)
226250 if (envelope -> is_raw ) {
227251 return sentry_value_new_null ();
228252 }
229- for (size_t i = 0 ; i < envelope -> contents .items .item_count ; i ++ ) {
230253
231- if (!sentry_value_is_null (envelope -> contents .items .items [i ].event )
232- && !sentry__event_is_transaction (
233- envelope -> contents .items .items [i ].event )) {
234- return envelope -> contents .items .items [i ].event ;
254+ for (const sentry_envelope_item_t * item
255+ = envelope -> contents .items .first_item ;
256+ item ; item = item -> next ) {
257+ if (!sentry_value_is_null (item -> event )
258+ && !sentry__event_is_transaction (item -> event )) {
259+ return item -> event ;
235260 }
236261 }
237262 return sentry_value_new_null ();
@@ -243,11 +268,13 @@ sentry_envelope_get_transaction(const sentry_envelope_t *envelope)
243268 if (envelope -> is_raw ) {
244269 return sentry_value_new_null ();
245270 }
246- for (size_t i = 0 ; i < envelope -> contents .items .item_count ; i ++ ) {
247- if (!sentry_value_is_null (envelope -> contents .items .items [i ].event )
248- && sentry__event_is_transaction (
249- envelope -> contents .items .items [i ].event )) {
250- return envelope -> contents .items .items [i ].event ;
271+
272+ for (const sentry_envelope_item_t * item
273+ = envelope -> contents .items .first_item ;
274+ item ; item = item -> next ) {
275+ if (!sentry_value_is_null (item -> event )
276+ && sentry__event_is_transaction (item -> event )) {
277+ return item -> event ;
251278 }
252279 }
253280 return sentry_value_new_null ();
@@ -657,8 +684,9 @@ sentry__envelope_serialize_into_stringbuilder(
657684 SENTRY_DEBUG ("serializing envelope into buffer" );
658685 sentry__envelope_serialize_headers_into_stringbuilder (envelope , sb );
659686
660- for (size_t i = 0 ; i < envelope -> contents .items .item_count ; i ++ ) {
661- const sentry_envelope_item_t * item = & envelope -> contents .items .items [i ];
687+ for (const sentry_envelope_item_t * item
688+ = envelope -> contents .items .first_item ;
689+ item ; item = item -> next ) {
662690 sentry__envelope_serialize_item_into_stringbuilder (item , sb );
663691 }
664692}
@@ -679,8 +707,9 @@ sentry_envelope_serialize_ratelimited(const sentry_envelope_t *envelope,
679707 sentry__envelope_serialize_headers_into_stringbuilder (envelope , & sb );
680708
681709 size_t serialized_items = 0 ;
682- for (size_t i = 0 ; i < envelope -> contents .items .item_count ; i ++ ) {
683- const sentry_envelope_item_t * item = & envelope -> contents .items .items [i ];
710+ for (const sentry_envelope_item_t * item
711+ = envelope -> contents .items .first_item ;
712+ item ; item = item -> next ) {
684713 if (rl ) {
685714 int category = envelope_item_get_ratelimiter_category (item );
686715 if (sentry__rate_limiter_is_disabled (rl , category )) {
@@ -736,9 +765,9 @@ sentry_envelope_write_to_path(
736765 sentry__jsonwriter_write_value (jw , envelope -> contents .items .headers );
737766 sentry__jsonwriter_reset (jw );
738767
739- for (size_t i = 0 ; i < envelope -> contents . items . item_count ; i ++ ) {
740- const sentry_envelope_item_t * item
741- = & envelope -> contents . items . items [ i ];
768+ for (const sentry_envelope_item_t * item
769+ = envelope -> contents . items . first_item ;
770+ item ; item = item -> next ) {
742771 const char newline = '\n' ;
743772 sentry__filewriter_write (fw , & newline , sizeof (char ));
744773
@@ -967,9 +996,22 @@ sentry__envelope_get_item_count(const sentry_envelope_t *envelope)
967996const sentry_envelope_item_t *
968997sentry__envelope_get_item (const sentry_envelope_t * envelope , size_t idx )
969998{
970- return !envelope -> is_raw && idx < envelope -> contents .items .item_count
971- ? & envelope -> contents .items .items [idx ]
972- : NULL ;
999+ if (envelope -> is_raw ) {
1000+ return NULL ;
1001+ }
1002+
1003+ // Traverse linked list to find item at index
1004+ size_t current_idx = 0 ;
1005+ for (const sentry_envelope_item_t * item
1006+ = envelope -> contents .items .first_item ;
1007+ item ; item = item -> next ) {
1008+ if (current_idx == idx ) {
1009+ return item ;
1010+ }
1011+ current_idx ++ ;
1012+ }
1013+
1014+ return NULL ;
9731015}
9741016
9751017sentry_value_t
0 commit comments