Fix licensing issues
[ric-plt/resource-status-manager.git] / RSM / 3rdparty / asn1codec / e2ap_engine / OPEN_TYPE.c
1
2 /*
3  * Copyright (c) 2017 Lev Walkin <vlm@lionet.info>. All rights reserved.
4  * Redistribution and modifications are permitted subject to BSD license.
5  */
6 #include <asn_internal.h>
7 #include <OPEN_TYPE.h>
8 #include <constr_CHOICE.h>
9 #include <per_opentype.h>
10 #include <errno.h>
11
12 asn_TYPE_operation_t asn_OP_OPEN_TYPE = {
13         OPEN_TYPE_free,
14         OPEN_TYPE_print,
15         OPEN_TYPE_compare,
16         OPEN_TYPE_decode_ber,
17         OPEN_TYPE_encode_der,
18         OPEN_TYPE_decode_xer,
19         OPEN_TYPE_encode_xer,
20 #ifdef ASN_DISABLE_OER_SUPPORT
21         0, 0,   /* No OER support, use "-gen-OER" to enable */
22 #else
23         OPEN_TYPE_decode_oer,
24         OPEN_TYPE_encode_oer,
25 #endif
26 #ifdef ASN_DISABLE_PER_SUPPORT
27         0, 0, 0, 0,
28 #else
29         OPEN_TYPE_decode_uper,
30         OPEN_TYPE_encode_uper,
31         OPEN_TYPE_decode_aper,
32         OPEN_TYPE_encode_aper,
33 #endif
34         0,  /* Random fill is not supported for open type */
35         0       /* Use generic outmost tag fetcher */
36 };
37
38 #undef  ADVANCE
39 #define ADVANCE(num_bytes)               \
40     do {                                 \
41         size_t num = num_bytes;          \
42         ptr = ((const char *)ptr) + num; \
43         size -= num;                     \
44         consumed_myself += num;          \
45     } while(0)
46
47 asn_dec_rval_t
48 OPEN_TYPE_ber_get(const asn_codec_ctx_t *opt_codec_ctx,
49                   const asn_TYPE_descriptor_t *td, void *sptr,
50                   const asn_TYPE_member_t *elm, const void *ptr, size_t size) {
51     size_t consumed_myself = 0;
52     asn_type_selector_result_t selected;
53     void *memb_ptr;   /* Pointer to the member */
54     void **memb_ptr2; /* Pointer to that pointer */
55     void *inner_value;
56     asn_dec_rval_t rv;
57
58     if(!(elm->flags & ATF_OPEN_TYPE)) {
59         ASN__DECODE_FAILED;
60     }
61
62     if(!elm->type_selector) {
63         ASN_DEBUG("Type selector is not defined for Open Type %s->%s->%s",
64                   td->name, elm->name, elm->type->name);
65         ASN__DECODE_FAILED;
66     }
67
68     selected = elm->type_selector(td, sptr);
69     if(!selected.presence_index) {
70         ASN__DECODE_FAILED;
71     }
72
73     /* Fetch the pointer to this member */
74     if(elm->flags & ATF_POINTER) {
75         memb_ptr2 = (void **)((char *)sptr + elm->memb_offset);
76     } else {
77         memb_ptr = (char *)sptr + elm->memb_offset;
78         memb_ptr2 = &memb_ptr;
79     }
80     if(*memb_ptr2 != NULL) {
81         /* Make sure we reset the structure first before encoding */
82         if(CHOICE_variant_set_presence(elm->type, *memb_ptr2, 0) != 0) {
83             ASN__DECODE_FAILED;
84         }
85     }
86
87     inner_value =
88         (char *)*memb_ptr2
89         + elm->type->elements[selected.presence_index - 1].memb_offset;
90
91     ASN_DEBUG("presence %d\n", selected.presence_index);
92
93     rv = selected.type_descriptor->op->ber_decoder(
94         opt_codec_ctx, selected.type_descriptor, &inner_value, ptr, size,
95         elm->tag_mode);
96     ADVANCE(rv.consumed);
97     rv.consumed = 0;
98     switch(rv.code) {
99     case RC_OK:
100         if(CHOICE_variant_set_presence(elm->type, *memb_ptr2,
101                                        selected.presence_index)
102            == 0) {
103             rv.code = RC_OK;
104             rv.consumed = consumed_myself;
105             return rv;
106         } else {
107             /* Oh, now a full-blown failure failure */
108         }
109         /* Fall through */
110     case RC_FAIL:
111         rv.consumed = consumed_myself;
112         /* Fall through */
113     case RC_WMORE:
114         break;
115     }
116
117     if(*memb_ptr2) {
118         if(elm->flags & ATF_POINTER) {
119             ASN_STRUCT_FREE(*selected.type_descriptor, inner_value);
120             *memb_ptr2 = NULL;
121         } else {
122             ASN_STRUCT_RESET(*selected.type_descriptor,
123                                           inner_value);
124         }
125     }
126     return rv;
127 }
128
129 asn_dec_rval_t
130 OPEN_TYPE_xer_get(const asn_codec_ctx_t *opt_codec_ctx,
131                   const asn_TYPE_descriptor_t *td, void *sptr,
132                   const asn_TYPE_member_t *elm, const void *ptr, size_t size) {
133     size_t consumed_myself = 0;
134     asn_type_selector_result_t selected;
135     void *memb_ptr;   /* Pointer to the member */
136     void **memb_ptr2; /* Pointer to that pointer */
137     void *inner_value;
138     asn_dec_rval_t rv;
139
140     int xer_context = 0;
141     ssize_t ch_size;
142     pxer_chunk_type_e ch_type;
143
144     if(!(elm->flags & ATF_OPEN_TYPE)) {
145         ASN__DECODE_FAILED;
146     }
147
148     if(!elm->type_selector) {
149         ASN_DEBUG("Type selector is not defined for Open Type %s->%s->%s",
150                   td->name, elm->name, elm->type->name);
151         ASN__DECODE_FAILED;
152     }
153
154     selected = elm->type_selector(td, sptr);
155     if(!selected.presence_index) {
156         ASN__DECODE_FAILED;
157     }
158
159     /* Fetch the pointer to this member */
160     assert(elm->flags == ATF_OPEN_TYPE);
161     if(elm->flags & ATF_POINTER) {
162         memb_ptr2 = (void **)((char *)sptr + elm->memb_offset);
163     } else {
164         memb_ptr = (char *)sptr + elm->memb_offset;
165         memb_ptr2 = &memb_ptr;
166     }
167     if(*memb_ptr2 != NULL) {
168         /* Make sure we reset the structure first before encoding */
169         if(CHOICE_variant_set_presence(elm->type, *memb_ptr2, 0)
170            != 0) {
171             ASN__DECODE_FAILED;
172         }
173     }
174
175     /*
176      * Confirm wrapper.
177      */
178     for(;;) {
179         ch_size = xer_next_token(&xer_context, ptr, size, &ch_type);
180         if(ch_size < 0) {
181             ASN__DECODE_FAILED;
182         } else {
183             switch(ch_type) {
184             case PXER_WMORE:
185                 ASN__DECODE_STARVED;
186             case PXER_COMMENT:
187             case PXER_TEXT:
188                 ADVANCE(ch_size);
189                 continue;
190             case PXER_TAG:
191                 break;
192             }
193             break;
194         }
195     }
196
197     /*
198      * Wrapper value confirmed.
199      */
200     switch(xer_check_tag(ptr, ch_size, elm->name)) {
201     case XCT_OPENING:
202         ADVANCE(ch_size);
203         break;
204     case XCT_BROKEN:
205     default:
206         ASN__DECODE_FAILED;
207     }
208
209     inner_value =
210         (char *)*memb_ptr2
211         + elm->type->elements[selected.presence_index - 1].memb_offset;
212
213     rv = selected.type_descriptor->op->xer_decoder(
214         opt_codec_ctx, selected.type_descriptor, &inner_value, NULL, ptr, size);
215     ADVANCE(rv.consumed);
216     rv.consumed = 0;
217     switch(rv.code) {
218     case RC_OK:
219         if(CHOICE_variant_set_presence(elm->type, *memb_ptr2,
220                                        selected.presence_index)
221            == 0) {
222             break;
223         } else {
224             rv.code = RC_FAIL;
225         }
226         /* Fall through */
227     case RC_FAIL:
228         /* Point to a best position where failure occurred */
229         rv.consumed = consumed_myself;
230         /* Fall through */
231     case RC_WMORE:
232         /* Wrt. rv.consumed==0:
233          * In case a genuine RC_WMORE, the whole Open Type decoding
234          * will have to be restarted.
235          */
236         if(*memb_ptr2) {
237             if(elm->flags & ATF_POINTER) {
238                 ASN_STRUCT_FREE(*selected.type_descriptor, inner_value);
239                 *memb_ptr2 = NULL;
240             } else {
241                 ASN_STRUCT_RESET(*selected.type_descriptor,
242                                               inner_value);
243             }
244         }
245         return rv;
246     }
247
248     /*
249      * Finalize wrapper.
250      */
251     for(;;) {
252         ch_size = xer_next_token(&xer_context, ptr, size, &ch_type);
253         if(ch_size < 0) {
254             ASN__DECODE_FAILED;
255         } else {
256             switch(ch_type) {
257             case PXER_WMORE:
258                 ASN__DECODE_STARVED;
259             case PXER_COMMENT:
260             case PXER_TEXT:
261                 ADVANCE(ch_size);
262                 continue;
263             case PXER_TAG:
264                 break;
265             }
266             break;
267         }
268     }
269
270     /*
271      * Wrapper value confirmed.
272      */
273     switch(xer_check_tag(ptr, ch_size, elm->name)) {
274     case XCT_CLOSING:
275         ADVANCE(ch_size);
276         break;
277     case XCT_BROKEN:
278     default:
279         ASN__DECODE_FAILED;
280     }
281
282     rv.consumed += consumed_myself;
283
284     return rv;
285 }
286
287
288 #ifndef  ASN_DISABLE_PER_SUPPORT
289
290 asn_dec_rval_t
291 OPEN_TYPE_uper_get(const asn_codec_ctx_t *opt_codec_ctx,
292                    const asn_TYPE_descriptor_t *td, void *sptr,
293                    const asn_TYPE_member_t *elm, asn_per_data_t *pd) {
294     asn_type_selector_result_t selected;
295     void *memb_ptr;   /* Pointer to the member */
296     void **memb_ptr2; /* Pointer to that pointer */
297     void *inner_value;
298     asn_dec_rval_t rv;
299
300     if(!(elm->flags & ATF_OPEN_TYPE)) {
301         ASN__DECODE_FAILED;
302     }
303
304     if(!elm->type_selector) {
305         ASN_DEBUG("Type selector is not defined for Open Type %s->%s->%s",
306                   td->name, elm->name, elm->type->name);
307         ASN__DECODE_FAILED;
308     }
309
310     selected = elm->type_selector(td, sptr);
311     if(!selected.presence_index) {
312         ASN__DECODE_FAILED;
313     }
314
315     /* Fetch the pointer to this member */
316     assert(elm->flags == ATF_OPEN_TYPE);
317     if(elm->flags & ATF_POINTER) {
318         memb_ptr2 = (void **)((char *)sptr + elm->memb_offset);
319     } else {
320         memb_ptr = (char *)sptr + elm->memb_offset;
321         memb_ptr2 = &memb_ptr;
322     }
323     if(*memb_ptr2 != NULL) {
324         /* Make sure we reset the structure first before encoding */
325         if(CHOICE_variant_set_presence(elm->type, *memb_ptr2, 0)
326            != 0) {
327             ASN__DECODE_FAILED;
328         }
329     }
330
331     inner_value =
332         (char *)*memb_ptr2
333         + elm->type->elements[selected.presence_index - 1].memb_offset;
334
335     rv = uper_open_type_get(opt_codec_ctx, selected.type_descriptor, NULL,
336                             &inner_value, pd);
337     switch(rv.code) {
338     case RC_OK:
339         if(CHOICE_variant_set_presence(elm->type, *memb_ptr2,
340                                        selected.presence_index)
341            == 0) {
342             break;
343         } else {
344             rv.code = RC_FAIL;
345         }
346         /* Fall through */
347     case RC_WMORE:
348     case RC_FAIL:
349         if(*memb_ptr2) {
350             if(elm->flags & ATF_POINTER) {
351                 ASN_STRUCT_FREE(*selected.type_descriptor, inner_value);
352                 *memb_ptr2 = NULL;
353             } else {
354                 ASN_STRUCT_RESET(*selected.type_descriptor,
355                                               inner_value);
356             }
357         }
358     }
359     return rv;
360 }
361
362 asn_enc_rval_t
363 OPEN_TYPE_encode_uper(const asn_TYPE_descriptor_t *td,
364                       const asn_per_constraints_t *constraints,
365                       const void *sptr, asn_per_outp_t *po) {
366     const void *memb_ptr;   /* Pointer to the member */
367     asn_TYPE_member_t *elm; /* CHOICE's element */
368     asn_enc_rval_t er = {0,0,0};
369     unsigned present;
370
371     (void)constraints;
372
373     present = CHOICE_variant_get_presence(td, sptr);
374     if(present == 0 || present > td->elements_count) {
375         ASN__ENCODE_FAILED;
376     } else {
377         present--;
378     }
379
380     ASN_DEBUG("Encoding %s OPEN TYPE element %d", td->name, present);
381
382     elm = &td->elements[present];
383     if(elm->flags & ATF_POINTER) {
384         /* Member is a pointer to another structure */
385         memb_ptr =
386             *(const void *const *)((const char *)sptr + elm->memb_offset);
387         if(!memb_ptr) ASN__ENCODE_FAILED;
388     } else {
389         memb_ptr = (const char *)sptr + elm->memb_offset;
390     }
391
392     if(uper_open_type_put(elm->type, NULL, memb_ptr, po) < 0) {
393         ASN__ENCODE_FAILED;
394     }
395
396     er.encoded = 0;
397     ASN__ENCODED_OK(er);
398 }
399
400 asn_dec_rval_t
401 OPEN_TYPE_aper_get(const asn_codec_ctx_t *opt_codec_ctx,
402                    const asn_TYPE_descriptor_t *td, void *sptr,
403                    const asn_TYPE_member_t *elm, asn_per_data_t *pd) {
404     asn_type_selector_result_t selected;
405     void *memb_ptr;   /* Pointer to the member */
406     void **memb_ptr2; /* Pointer to that pointer */
407     void *inner_value;
408     asn_dec_rval_t rv;
409
410     if(!(elm->flags & ATF_OPEN_TYPE)) {
411         ASN__DECODE_FAILED;
412     }
413
414     if(!elm->type_selector) {
415         ASN_DEBUG("Type selector is not defined for Open Type %s->%s->%s",
416                   td->name, elm->name, elm->type->name);
417         ASN__DECODE_FAILED;
418     }
419
420     selected = elm->type_selector(td, sptr);
421     if(!selected.presence_index) {
422         ASN__DECODE_FAILED;
423     }
424
425     /* Fetch the pointer to this member */
426     assert(elm->flags == ATF_OPEN_TYPE);
427     if(elm->flags & ATF_POINTER) {
428         memb_ptr2 = (void **)((char *)sptr + elm->memb_offset);
429     } else {
430         memb_ptr = (char *)sptr + elm->memb_offset;
431         memb_ptr2 = &memb_ptr;
432     }
433     if(*memb_ptr2 != NULL) {
434         /* Make sure we reset the structure first before encoding */
435         if(CHOICE_variant_set_presence(elm->type, *memb_ptr2, 0)
436            != 0) {
437             ASN__DECODE_FAILED;
438         }
439     }
440
441     inner_value =
442         (char *)*memb_ptr2
443         + elm->type->elements[selected.presence_index - 1].memb_offset;
444
445     rv = aper_open_type_get(opt_codec_ctx, selected.type_descriptor, NULL,
446                             &inner_value, pd);
447     switch(rv.code) {
448     case RC_OK:
449         if(CHOICE_variant_set_presence(elm->type, *memb_ptr2,
450                                        selected.presence_index)
451            == 0) {
452             break;
453         } else {
454             rv.code = RC_FAIL;
455         }
456         /* Fall through */
457     case RC_WMORE:
458     case RC_FAIL:
459         if(*memb_ptr2) {
460             if(elm->flags & ATF_POINTER) {
461                 ASN_STRUCT_FREE(*selected.type_descriptor, inner_value);
462                 *memb_ptr2 = NULL;
463             } else {
464                 ASN_STRUCT_RESET(*selected.type_descriptor,
465                                               inner_value);
466             }
467         }
468     }
469     return rv;
470 }
471
472 asn_enc_rval_t
473 OPEN_TYPE_encode_aper(const asn_TYPE_descriptor_t *td,
474                       const asn_per_constraints_t *constraints,
475                       const void *sptr, asn_per_outp_t *po) {
476     const void *memb_ptr;   /* Pointer to the member */
477     asn_TYPE_member_t *elm; /* CHOICE's element */
478     asn_enc_rval_t er = {0,0,0};
479     unsigned present;
480
481     (void)constraints;
482
483     present = CHOICE_variant_get_presence(td, sptr);
484     if(present == 0 || present > td->elements_count) {
485         ASN__ENCODE_FAILED;
486     } else {
487         present--;
488     }
489
490     ASN_DEBUG("Encoding %s OPEN TYPE element %d", td->name, present);
491
492     elm = &td->elements[present];
493     if(elm->flags & ATF_POINTER) {
494         /* Member is a pointer to another structure */
495         memb_ptr =
496             *(const void *const *)((const char *)sptr + elm->memb_offset);
497         if(!memb_ptr) ASN__ENCODE_FAILED;
498     } else {
499         memb_ptr = (const char *)sptr + elm->memb_offset;
500     }
501
502     if(aper_open_type_put(elm->type, NULL, memb_ptr, po) < 0) {
503         ASN__ENCODE_FAILED;
504     }
505
506     er.encoded = 0;
507     ASN__ENCODED_OK(er);
508 }
509
510 #endif  /* ASN_DISABLE_PER_SUPPORT */