1 /***************************************************************************
2 * Copyright (c) 2024 Microsoft Corporation
3 *
4 * This program and the accompanying materials are made available under the
5 * terms of the MIT License which is available at
6 * https://opensource.org/licenses/MIT.
7 *
8 * SPDX-License-Identifier: MIT
9 **************************************************************************/
10
11 /**************************************************************************/
12 /**************************************************************************/
13 /** */
14 /** NetX MSRP Component */
15 /** */
16 /** Multiple Stream Registration Protocol (MSRP) */
17 /** */
18 /**************************************************************************/
19 /**************************************************************************/
20
21 #include "nx_msrp.h"
22
23 #ifdef NX_ENABLE_VLAN
24 #ifdef NX_MSRP_DEBUG
25 #ifndef NX_MSRP_DEBUG_PRINTF
26 #define NX_MSRP_DEBUG_PRINTF(x) printf x
27 #endif
28 #else
29 #define NX_MSRP_DEBUG_PRINTF(x)
30 #endif
31
32 static NX_MSRP_ATTRIBUTE msrp_attribute_array[NX_MSRP_ATTRIBUTE_ARRAY_MAX_SIZE];
33
34 /**************************************************************************/
35 /* */
36 /* FUNCTION RELEASE */
37 /* */
38 /* nx_msrp_init PORTABLE C */
39 /* 6.4.0 */
40 /* AUTHOR */
41 /* */
42 /* Wen Wang, Microsoft Corporation */
43 /* */
44 /* DESCRIPTION */
45 /* */
46 /* This function initialize MSRP paramter. */
47 /* */
48 /* INPUT */
49 /* */
50 /* msrp_ptr MSRP instance pointer */
51 /* */
52 /* OUTPUT */
53 /* */
54 /* status Completion status */
55 /* */
56 /* CALLS */
57 /* */
58 /* None */
59 /* */
60 /* CALLED BY */
61 /* */
62 /* nx_srp_init Initialize SRP */
63 /* */
64 /* RELEASE HISTORY */
65 /* */
66 /* DATE NAME DESCRIPTION */
67 /* */
68 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
69 /* */
70 /**************************************************************************/
nx_msrp_init(NX_MSRP * msrp_ptr)71 UINT nx_msrp_init(NX_MSRP *msrp_ptr)
72 {
73 /* Initialize MSRP structure.*/
74 msrp_ptr -> nx_msrp_participant.participant_type = NX_MRP_PARTICIPANT_MSRP;
75 msrp_ptr -> nx_msrp_participant.protocol_version = NX_MRP_MSRP_PROTOCOL_VERSION;
76 msrp_ptr -> nx_msrp_participant.indication_function = nx_msrp_indication_process;
77 msrp_ptr -> nx_msrp_participant.unpack_function = nx_msrp_mrpdu_parse;
78 msrp_ptr -> nx_msrp_participant.pack_function = nx_msrp_mrpdu_pack;
79
80 msrp_ptr -> nx_msrp_participant.join_timer = NX_MRP_TIMER_JOIN;
81 msrp_ptr -> nx_msrp_participant.leaveall_timer = NX_MRP_TIMER_LEAVEALL;
82
83 msrp_ptr -> msrp_callback_data = NX_NULL;
84
85 return(NX_MSRP_SUCCESS);
86 }
87
88 /**************************************************************************/
89 /* */
90 /* FUNCTION RELEASE */
91 /* */
92 /* nx_msrp_attribute_find PORTABLE C */
93 /* 6.4.0 */
94 /* AUTHOR */
95 /* */
96 /* Wen Wang, Microsoft Corporation */
97 /* */
98 /* DESCRIPTION */
99 /* */
100 /* This function finds an MSRP attribute. Create new one if nothing */
101 /* can be find. */
102 /* INPUT */
103 /* */
104 /* mrp MRP instance pointer */
105 /* participant MRP participant */
106 /* attribute_ptr Attribute pointer */
107 /* attribute_type Attribute type */
108 /* attribute_value Attribute value */
109 /* */
110 /* OUTPUT */
111 /* */
112 /* status Completion status */
113 /* */
114 /* CALLS */
115 /* */
116 /* nx_mrp_attribute_new Create new mrp attribute */
117 /* NX_MSRP_DEBUG_PRINTF Printf for debug */
118 /* memcpy Standard library function */
119 /* */
120 /* CALLED BY */
121 /* */
122 /* nx_msrp_register_stream_request MSRP register stream requset */
123 /* nx_msrp_register_attach_request MSRP register stream attach */
124 /* nx_msrp_deregister_stream_request MSRP deregister stream requset*/
125 /* nx_msrp_deregister_attach_request MSRP deregister stream attach */
126 /* nx_msrp_register_domain_request MSRP register domain requset */
127 /* nx_msrp_deregister_domain_request MSRP deregister domain requset*/
128 /* nx_msrp_mrpdu_parse MSRP parse MRP date unit */
129 /* */
130 /* RELEASE HISTORY */
131 /* */
132 /* DATE NAME DESCRIPTION */
133 /* */
134 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
135 /* */
136 /**************************************************************************/
nx_msrp_attribute_find(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_MRP_ATTRIBUTE ** attribute_ptr,UCHAR attribute_type,UCHAR * attribute_value)137 UINT nx_msrp_attribute_find(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_MRP_ATTRIBUTE **attribute_ptr, UCHAR attribute_type, UCHAR *attribute_value)
138 {
139 NX_MRP_ATTRIBUTE *msrp_attribute;
140 NX_MRP_ATTRIBUTE *tmp;
141 INT difference;
142
143 /* Look up attribute_type in attribute array.*/
144 NX_MRP_ATTRIBUTE *attribute_head = participant -> inused_head;
145
146 while (NX_NULL != attribute_head)
147 {
148 if (attribute_head -> attribute_type == attribute_type)
149 {
150 switch (attribute_type)
151 {
152 case NX_MSRP_TALKER_ADVERTISE_VECTOR:
153
154 if (memcmp(((NX_MSRP_ATTRIBUTE *)attribute_head) -> msrp_attribute_union.talker_advertise.stream_id, (UCHAR *)attribute_value, 8) == 0)
155 {
156 *attribute_ptr = attribute_head;
157
158 return(NX_MSRP_ATTRIBUTE_FOUND);
159 }
160
161 break;
162
163 case NX_MSRP_TALKER_LISTENER_VECTOR:
164
165 if (memcmp(((NX_MSRP_ATTRIBUTE *)attribute_head) -> msrp_attribute_union.listener.stream_id, (UCHAR *)attribute_value, 8) == 0)
166 {
167
168 *attribute_ptr = attribute_head;
169
170 return(NX_MSRP_ATTRIBUTE_FOUND);
171 }
172
173 break;
174
175 case NX_MSRP_TALKER_DOMAIN_VECTOR:
176
177 if (((NX_MSRP_ATTRIBUTE *)attribute_head) -> msrp_attribute_union.domain.sr_class_id == *(UCHAR *)attribute_value)
178 {
179 *attribute_ptr = attribute_head;
180
181 return(NX_MSRP_ATTRIBUTE_FOUND);
182 }
183 NX_MSRP_DEBUG_PRINTF(("sr_class_id = %d \r\n", ((NX_MSRP_ATTRIBUTE *)attribute_head) -> msrp_attribute_union.domain.sr_class_id));
184
185 NX_MSRP_DEBUG_PRINTF(("attribute_value = %d \r\n", *(UCHAR *)attribute_value));
186
187 break;
188
189 case NX_MSRP_TALKER_FAILED_VECTOR:
190
191 if (memcmp(((NX_MSRP_ATTRIBUTE *)attribute_head) -> msrp_attribute_union.talker_advertise.stream_id, (UCHAR *)attribute_value, 8) == 0)
192 {
193 *attribute_ptr = attribute_head;
194
195 return(NX_MSRP_ATTRIBUTE_FOUND);
196 }
197
198 break;
199
200 default:
201
202 break;
203 }
204
205 attribute_head = attribute_head -> next;
206 }
207 else
208 {
209 attribute_head = attribute_head -> next;
210 }
211 }
212
213 *attribute_ptr = nx_mrp_attribute_new(mrp, participant, (NX_MRP_ATTRIBUTE *)msrp_attribute_array, sizeof(NX_MSRP_ATTRIBUTE), NX_MSRP_ATTRIBUTE_ARRAY_MAX_SIZE);
214
215 /*Initialize attribute_type and part of attribute value.*/
216 (*attribute_ptr) -> attribute_type = attribute_type;
217
218 switch ((*attribute_ptr) -> attribute_type)
219 {
220
221 case NX_MSRP_TALKER_ADVERTISE_VECTOR:
222
223 memcpy(((NX_MSRP_ATTRIBUTE *)*attribute_ptr) -> msrp_attribute_union.talker_advertise.stream_id,
224 (UCHAR *)attribute_value, 8); /* use case of memcpy is verified. */
225 break;
226
227 case NX_MSRP_TALKER_LISTENER_VECTOR:
228
229 memcpy(((NX_MSRP_ATTRIBUTE *)*attribute_ptr) -> msrp_attribute_union.listener.stream_id,
230 (UCHAR *)attribute_value, 8); /* use case of memcpy is verified. */
231 break;
232
233 case NX_MSRP_TALKER_DOMAIN_VECTOR:
234
235 memcpy(&((NX_MSRP_ATTRIBUTE *)*attribute_ptr) -> msrp_attribute_union.domain.sr_class_id,
236 (UCHAR *)attribute_value, 1); /* use case of memcpy is verified. */
237 break;
238
239 case NX_MSRP_TALKER_FAILED_VECTOR:
240 default:
241
242 return(NX_MSRP_ATTRIBUTE_TYPE_ERROR);
243 }
244
245
246 if (*attribute_ptr == NX_NULL)
247 {
248
249 return(NX_MSRP_ATTRIBUTE_FIND_ERROR);
250 }
251
252
253 /* Do insert and sort as attribute type value when needs to create a new one.*/
254 if (participant -> inused_head == NX_NULL)
255 {
256
257 participant -> inused_head = *attribute_ptr;
258
259 return(NX_MSRP_ATTRIBUTE_NEW);
260 }
261
262 msrp_attribute = participant -> inused_head;
263
264 while (msrp_attribute)
265 {
266 if (((*attribute_ptr) -> attribute_type) > (msrp_attribute -> attribute_type))
267 {
268
269 tmp = msrp_attribute;
270
271 msrp_attribute = msrp_attribute -> next;
272
273 if (msrp_attribute == NX_NULL)
274 {
275 tmp -> next = *attribute_ptr;
276 (*attribute_ptr) -> next = NX_NULL;
277 return(NX_MSRP_ATTRIBUTE_NEW);
278 }
279
280 continue;
281 }
282 else if ((*attribute_ptr) -> attribute_type == msrp_attribute -> attribute_type)
283 {
284
285 while ((*attribute_ptr) -> attribute_type == msrp_attribute -> attribute_type)
286 {
287 switch ((*attribute_ptr) -> attribute_type)
288 {
289
290 case NX_MSRP_TALKER_ADVERTISE_VECTOR:
291
292 difference = memcmp(((NX_MSRP_ATTRIBUTE *)*attribute_ptr) -> msrp_attribute_union.talker_advertise.stream_id,
293 ((NX_MSRP_ATTRIBUTE *)*attribute_ptr) -> msrp_attribute_union.talker_advertise.stream_id, 8);
294 break;
295
296 case NX_MSRP_TALKER_LISTENER_VECTOR:
297
298 difference = memcmp(((NX_MSRP_ATTRIBUTE *)*attribute_ptr) -> msrp_attribute_union.listener.stream_id,
299 ((NX_MSRP_ATTRIBUTE *)*attribute_ptr) -> msrp_attribute_union.listener.stream_id, 8);
300
301 break;
302 case NX_MSRP_TALKER_DOMAIN_VECTOR:
303
304 difference = memcmp(&((NX_MSRP_ATTRIBUTE *)*attribute_ptr) -> msrp_attribute_union.domain.sr_class_id,
305 &((NX_MSRP_ATTRIBUTE *)*attribute_ptr) -> msrp_attribute_union.domain.sr_class_id, 1);
306
307 break;
308
309 case NX_MSRP_TALKER_FAILED_VECTOR:
310 default:
311
312 return(NX_MSRP_ATTRIBUTE_TYPE_ERROR);
313 }
314
315 if (difference < 0)
316 {
317
318 (*attribute_ptr) -> next = msrp_attribute;
319
320 if (msrp_attribute == participant -> inused_head)
321 {
322 participant -> inused_head = *attribute_ptr;
323
324 break;
325 }
326 else
327 {
328 tmp -> next = *attribute_ptr;
329 }
330 }
331 else
332 {
333
334 tmp = msrp_attribute;
335 msrp_attribute = msrp_attribute -> next;
336 if (msrp_attribute == NX_NULL)
337 {
338 tmp -> next = *attribute_ptr;
339 (*attribute_ptr) -> next = NX_NULL;
340 return(NX_MSRP_ATTRIBUTE_NEW);
341 }
342 }
343 }
344 }
345 else
346 {
347
348 (*attribute_ptr) -> next = msrp_attribute;
349
350 if (msrp_attribute == participant -> inused_head)
351 {
352 participant -> inused_head = *attribute_ptr;
353
354 break;
355 }
356 else
357 {
358 tmp -> next = *attribute_ptr;
359
360 break;
361 }
362 }
363 }
364
365 return(NX_MSRP_ATTRIBUTE_NEW);
366 }
367
368 /**************************************************************************/
369 /* */
370 /* FUNCTION RELEASE */
371 /* */
372 /* nx_msrp_register_stream_request PORTABLE C */
373 /* 6.4.0 */
374 /* AUTHOR */
375 /* */
376 /* Wen Wang, Microsoft Corporation */
377 /* */
378 /* DESCRIPTION */
379 /* */
380 /* This function register stream request. */
381 /* */
382 /* INPUT */
383 /* */
384 /* mrp MRP instance pointer */
385 /* participant MRP participant */
386 /* talker_advertise Talker advertise properties */
387 /* attribute_type Attribute type */
388 /* new_request Create new request */
389 /* */
390 /* OUTPUT */
391 /* */
392 /* status Completion status */
393 /* */
394 /* CALLS */
395 /* */
396 /* nx_msrp_attribute_find Find MSRP attribute */
397 /* nx_mrp_event_process Process mrp_event */
398 /* */
399 /* CALLED BY */
400 /* */
401 /* nx_srp_talker_start Start SRP talker */
402 /* */
403 /* RELEASE HISTORY */
404 /* */
405 /* DATE NAME DESCRIPTION */
406 /* */
407 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
408 /* */
409 /**************************************************************************/
nx_msrp_register_stream_request(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_MSRP_TALKER_ADVERTISE * talker_advertise,UINT new_request)410 UINT nx_msrp_register_stream_request(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_MSRP_TALKER_ADVERTISE *talker_advertise, UINT new_request)
411 {
412 NX_MRP_ATTRIBUTE *attribute = NX_NULL;
413 UINT status;
414 UCHAR *attribute_value;
415 UCHAR attribute_type;
416 UCHAR mrp_event;
417
418 if (new_request)
419 {
420
421 mrp_event = NX_MRP_EVENT_NEW;
422 }
423 else
424 {
425
426 mrp_event = NX_MRP_EVENT_JOIN;
427 return(NX_MSRP_EVENT_NOT_SUPPORTED);
428 }
429
430 attribute_type = NX_MSRP_TALKER_ADVERTISE_VECTOR;
431
432 attribute_value = talker_advertise -> stream_id;
433
434 /* Get mrp mutex. */
435 tx_mutex_get(&mrp -> mrp_mutex, NX_WAIT_FOREVER);
436
437 status = nx_msrp_attribute_find(mrp, participant, &attribute, attribute_type, attribute_value);
438
439 if (attribute != NX_NULL)
440 {
441
442 attribute -> attribute_type = NX_MSRP_TALKER_ADVERTISE_VECTOR;
443
444 memcpy(&(((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.talker_advertise),
445 talker_advertise, sizeof(NX_MSRP_TALKER_ADVERTISE)); /* use case of memcpy is verified. */
446
447 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 0;
448
449 status = nx_mrp_event_process(mrp, participant, attribute, mrp_event);
450 }
451 else
452 {
453 status = NX_MSRP_ATTRIBUTE_FIND_ERROR;
454 }
455
456 /* Release the mutex. */
457 tx_mutex_put(&(mrp -> mrp_mutex));
458 return(status);
459 }
460
461 /**************************************************************************/
462 /* */
463 /* FUNCTION RELEASE */
464 /* */
465 /* nx_msrp_register_attach_request PORTABLE C */
466 /* 6.4.0 */
467 /* AUTHOR */
468 /* */
469 /* Wen Wang, Microsoft Corporation */
470 /* */
471 /* DESCRIPTION */
472 /* */
473 /* This function register stream attach request. */
474 /* */
475 /* INPUT */
476 /* */
477 /* mrp MRP instance pointer */
478 /* participant MRP participant */
479 /* stream_id Stream ID */
480 /* fourpacked_value fourpacked value */
481 /* */
482 /* OUTPUT */
483 /* */
484 /* status Completion status */
485 /* */
486 /* CALLS */
487 /* */
488 /* nx_msrp_attribute_find Find MSRP attribute */
489 /* nx_mrp_event_process Process mrp_event */
490 /* */
491 /* CALLED BY */
492 /* */
493 /* nx_msrp_register_stream_indication Indication MSRP register */
494 /* */
495 /* RELEASE HISTORY */
496 /* */
497 /* DATE NAME DESCRIPTION */
498 /* */
499 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
500 /* */
501 /**************************************************************************/
nx_msrp_register_attach_request(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,UCHAR * stream_id,UINT mrp_event,UCHAR fourpacked_value)502 UINT nx_msrp_register_attach_request(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, UCHAR *stream_id, UINT mrp_event, UCHAR fourpacked_value)
503 {
504 NX_MRP_ATTRIBUTE *attribute = NX_NULL;
505 UINT status;
506 UCHAR attribute_type = NX_MSRP_TALKER_LISTENER_VECTOR;
507
508 /* Get mutex. */
509 tx_mutex_get(&mrp -> mrp_mutex, NX_WAIT_FOREVER);
510
511 status = nx_msrp_attribute_find(mrp, participant, &attribute, attribute_type, stream_id);
512
513 if (attribute != NX_NULL)
514 {
515
516 attribute -> attribute_type = NX_MSRP_TALKER_LISTENER_VECTOR;
517
518 memcpy(((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.stream_id,
519 stream_id, 8); /* use case of memcpy is verified. */
520
521 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 0;
522
523 ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.fourpacked_event = fourpacked_value;
524
525 status = nx_mrp_event_process(mrp, participant, attribute, (UCHAR)mrp_event);
526 }
527 else
528 {
529 status = NX_MSRP_ATTRIBUTE_FIND_ERROR;
530 }
531
532 /* Release the mutex. */
533 tx_mutex_put(&(mrp -> mrp_mutex));
534 return(status);
535 }
536
537 /**************************************************************************/
538 /* */
539 /* FUNCTION RELEASE */
540 /* */
541 /* nx_msrp_deregister_stream_request PORTABLE C */
542 /* 6.4.0 */
543 /* AUTHOR */
544 /* */
545 /* Wen Wang, Microsoft Corporation */
546 /* */
547 /* DESCRIPTION */
548 /* */
549 /* This function deregister stream request. */
550 /* */
551 /* INPUT */
552 /* */
553 /* mrp MRP instance pointer */
554 /* participant MRP participant */
555 /* stream_id Stream ID */
556 /* */
557 /* OUTPUT */
558 /* */
559 /* status Completion status */
560 /* */
561 /* CALLS */
562 /* */
563 /* nx_msrp_attribute_find Find MSRP attribute */
564 /* nx_mrp_event_process Process mrp_event */
565 /* */
566 /* CALLED BY */
567 /* */
568 /* nx_srp_talker_stop Stop SRP talker */
569 /* */
570 /* RELEASE HISTORY */
571 /* */
572 /* DATE NAME DESCRIPTION */
573 /* */
574 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
575 /* */
576 /**************************************************************************/
nx_msrp_deregister_stream_request(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,UCHAR * stream_id)577 UINT nx_msrp_deregister_stream_request(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, UCHAR *stream_id)
578 {
579 UINT status;
580 NX_MRP_ATTRIBUTE *attribute = NX_NULL;
581 UINT mrp_event = NX_MRP_EVENT_LV;
582 UCHAR attribute_type = NX_MSRP_TALKER_ADVERTISE_VECTOR;
583
584 /* Get mutex. */
585 tx_mutex_get(&mrp -> mrp_mutex, NX_WAIT_FOREVER);
586
587 status = nx_msrp_attribute_find(mrp, participant, &attribute, attribute_type, stream_id);
588
589 if (status == NX_MSRP_ATTRIBUTE_FOUND)
590 {
591 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 0;
592
593 status = nx_mrp_event_process(mrp, participant, attribute, (UCHAR)mrp_event);
594 }
595 else
596 {
597 status = NX_MSRP_ATTRIBUTE_FIND_ERROR;
598 }
599
600 /* Release the mutex. */
601 tx_mutex_put(&(mrp -> mrp_mutex));
602 return(status);
603 }
604
605 /**************************************************************************/
606 /* */
607 /* FUNCTION RELEASE */
608 /* */
609 /* nx_msrp_deregister_attach_request PORTABLE C */
610 /* 6.4.0 */
611 /* AUTHOR */
612 /* */
613 /* Wen Wang, Microsoft Corporation */
614 /* */
615 /* DESCRIPTION */
616 /* */
617 /* This function deregister stream attach request. */
618 /* */
619 /* INPUT */
620 /* */
621 /* mrp MRP instance pointer */
622 /* participant MRP participant */
623 /* stream_id Stream ID */
624 /* */
625 /* OUTPUT */
626 /* */
627 /* status Completion status */
628 /* */
629 /* CALLS */
630 /* */
631 /* nx_msrp_attribute_find Find MSRP attribute */
632 /* nx_mrp_event_process Process MRP mrp_event */
633 /* */
634 /* CALLED BY */
635 /* */
636 /* nx_msrp_deregister_stream_indication receive deregister stream */
637 /* nx_srp_listener_stop Stop SRP listener */
638 /* */
639 /* RELEASE HISTORY */
640 /* */
641 /* DATE NAME DESCRIPTION */
642 /* */
643 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
644 /* */
645 /**************************************************************************/
nx_msrp_deregister_attach_request(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,UCHAR * stream_id)646 UINT nx_msrp_deregister_attach_request(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, UCHAR *stream_id)
647 {
648 UINT status;
649 NX_MRP_ATTRIBUTE *attribute = NX_NULL;
650 UINT mrp_event = NX_MRP_EVENT_LV;
651 UCHAR attribute_type = NX_MSRP_TALKER_LISTENER_VECTOR;
652
653 /* Get mrp mutex. */
654 tx_mutex_get(&mrp -> mrp_mutex, NX_WAIT_FOREVER);
655
656 status = nx_msrp_attribute_find(mrp, participant, &attribute, attribute_type, stream_id);
657
658 if (status == NX_MSRP_ATTRIBUTE_FOUND)
659 {
660
661 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 0;
662
663 status = nx_mrp_event_process(mrp, participant, attribute, (UCHAR)mrp_event);
664 }
665 else
666 {
667 status = NX_MSRP_ATTRIBUTE_FIND_ERROR;
668 }
669
670 /* Release the mutex.*/
671 tx_mutex_put(&(mrp -> mrp_mutex));
672 return(status);
673 }
674
675 /**************************************************************************/
676 /* */
677 /* FUNCTION RELEASE */
678 /* */
679 /* nx_msrp_register_domain_request PORTABLE C */
680 /* 6.4.0 */
681 /* AUTHOR */
682 /* */
683 /* Wen Wang, Microsoft Corporation */
684 /* */
685 /* DESCRIPTION */
686 /* */
687 /* This function register domain request. */
688 /* */
689 /* INPUT */
690 /* */
691 /* mrp MRP instance pointer */
692 /* participant MRP participant */
693 /* domain Stream properties */
694 /* new_request Create new request */
695 /* */
696 /* OUTPUT */
697 /* */
698 /* status Completion status */
699 /* */
700 /* CALLS */
701 /* */
702 /* nx_msrp_attribute_find Find MSRP attribute */
703 /* nx_mrp_event_process Process MRP mrp_event */
704 /* */
705 /* CALLED BY */
706 /* */
707 /* nx_srp_talker_start Start SRP talker */
708 /* */
709 /* RELEASE HISTORY */
710 /* */
711 /* DATE NAME DESCRIPTION */
712 /* */
713 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
714 /* */
715 /**************************************************************************/
nx_msrp_register_domain_request(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_MSRP_DOMAIN * domain,UINT new_request)716 UINT nx_msrp_register_domain_request(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_MSRP_DOMAIN *domain, UINT new_request)
717 {
718
719 NX_MRP_ATTRIBUTE *attribute = NX_NULL;
720 UINT mrp_event;
721 UINT status;
722
723
724 if (new_request)
725 {
726 mrp_event = NX_MRP_EVENT_NEW;
727 }
728 else
729 {
730 mrp_event = NX_MRP_EVENT_JOIN;
731 return(NX_MSRP_EVENT_NOT_SUPPORTED);
732 }
733
734 /* Get mutex. */
735 tx_mutex_get(&mrp -> mrp_mutex, NX_WAIT_FOREVER);
736
737 status = nx_msrp_attribute_find(mrp, participant, &attribute, NX_MSRP_TALKER_DOMAIN_VECTOR, &domain -> sr_class_id);
738
739 if (attribute == NX_NULL)
740 {
741 status = NX_MSRP_ATTRIBUTE_FIND_ERROR;
742 }
743 else if (status == NX_MSRP_ATTRIBUTE_NEW)
744 {
745
746 attribute -> attribute_type = NX_MSRP_TALKER_DOMAIN_VECTOR;
747
748 memcpy(&(((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain),
749 domain, sizeof(NX_MSRP_DOMAIN)); /* use case of memcpy is verified. */
750
751 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 0;
752
753 status = nx_mrp_event_process(mrp, participant, attribute, (UCHAR)mrp_event);
754 }
755 else
756 {
757 status = NX_MSRP_SUCCESS;
758 }
759
760 /* Release the mutex. */
761 tx_mutex_put(&(mrp -> mrp_mutex));
762 return(status);
763 }
764
765 /**************************************************************************/
766 /* */
767 /* FUNCTION RELEASE */
768 /* */
769 /* nx_msrp_deregister_domain_request PORTABLE C */
770 /* 6.4.0 */
771 /* AUTHOR */
772 /* */
773 /* Wen Wang, Microsoft Corporation */
774 /* */
775 /* DESCRIPTION */
776 /* */
777 /* This function deregister domain request. */
778 /* */
779 /* INPUT */
780 /* */
781 /* mrp MRP instance pointer */
782 /* participant MRP participant */
783 /* domain Stream properties */
784 /* */
785 /* OUTPUT */
786 /* */
787 /* status Completion status */
788 /* */
789 /* CALLS */
790 /* */
791 /* nx_msrp_attribute_find Find MSRP attribute */
792 /* nx_mrp_event_process Process MRP mrp_event */
793 /* */
794 /* CALLED BY */
795 /* */
796 /* nx_srp_talker_stop Stop SRP talker */
797 /* nx_srp_listener_stop Stop SRP listener */
798 /* nx_msrp_deregister_domain_indication Deregister MSRP domain */
799 /* indication */
800 /* */
801 /* RELEASE HISTORY */
802 /* */
803 /* DATE NAME DESCRIPTION */
804 /* */
805 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
806 /* */
807 /**************************************************************************/
nx_msrp_deregister_domain_request(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_MSRP_DOMAIN * domain)808 UINT nx_msrp_deregister_domain_request(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_MSRP_DOMAIN *domain)
809 {
810
811 NX_MRP_ATTRIBUTE *attribute = NX_NULL;
812 UINT mrp_event = NX_MRP_EVENT_LV;
813 UINT status;
814
815 /* Get mutex. */
816 tx_mutex_get(&mrp -> mrp_mutex, NX_WAIT_FOREVER);
817
818 status = nx_msrp_attribute_find(mrp, participant, &attribute, NX_MSRP_TALKER_DOMAIN_VECTOR, &domain -> sr_class_id);
819
820 if (status == NX_MSRP_ATTRIBUTE_FOUND)
821 {
822
823 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 0;
824
825 status = nx_mrp_event_process(mrp, participant, attribute, (UCHAR)mrp_event);
826 }
827 else
828 {
829 status = NX_MSRP_ATTRIBUTE_FIND_ERROR;
830 }
831
832 /* Release the mutex. */
833 tx_mutex_put(&(mrp -> mrp_mutex));
834 return(status);
835 }
836
837 /**************************************************************************/
838 /* */
839 /* FUNCTION RELEASE */
840 /* */
841 /* nx_msrp_register_stream_indication PORTABLE C */
842 /* 6.4.0 */
843 /* AUTHOR */
844 /* */
845 /* Wen Wang, Microsoft Corporation */
846 /* */
847 /* DESCRIPTION */
848 /* */
849 /* This function register stream indication. */
850 /* */
851 /* INPUT */
852 /* */
853 /* mrp MRP instance pointer */
854 /* participant MRP participant */
855 /* attribute Attribute */
856 /* indication_type Indication type */
857 /* */
858 /* OUTPUT */
859 /* */
860 /* status Completion status */
861 /* */
862 /* CALLS */
863 /* */
864 /* nx_msrp_register_attach_request MSRP register attach request */
865 /* event_callback Application callback */
866 /* */
867 /* CALLED BY */
868 /* */
869 /* nx_msrp_indication_process Process MSRP indication */
870 /* */
871 /* RELEASE HISTORY */
872 /* */
873 /* DATE NAME DESCRIPTION */
874 /* */
875 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
876 /* */
877 /**************************************************************************/
nx_msrp_register_stream_indication(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_MRP_ATTRIBUTE * attribute,UINT indication_type)878 UINT nx_msrp_register_stream_indication(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_MRP_ATTRIBUTE *attribute, UINT indication_type)
879 {
880 UINT status;
881 UCHAR *stream_id;
882 NX_MRP_EVENT_CALLBACK event_callback;
883
884
885 if (((NX_MSRP *)participant) -> listener_enable)
886 {
887
888 event_callback = ((NX_MSRP *)participant) -> msrp_event_callback;
889
890
891 if (event_callback != NX_NULL)
892 {
893
894 status = event_callback(participant, attribute, (UCHAR)indication_type, ((NX_MSRP *)participant) -> msrp_callback_data);
895
896 /* Listener receives register stream idication, then starts to register attach request*/
897 if (status == NX_MSRP_SUCCESS)
898 {
899
900 stream_id = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.talker_advertise.stream_id;
901
902 status = nx_msrp_register_attach_request(mrp, participant, stream_id, indication_type, NX_MSRP_FOURPACKED_READY);
903 }
904 }
905 else
906 {
907 stream_id = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.talker_advertise.stream_id;
908
909 ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.fourpacked_event = NX_MSRP_FOURPACKED_READY;
910
911 status = nx_msrp_register_attach_request(mrp, participant, stream_id, indication_type, NX_MSRP_FOURPACKED_READY);
912 }
913 }
914 else
915 {
916
917 return(NX_MSRP_LISTENER_NOT_ENABLED);
918 }
919
920 return(status);
921 }
922
923 /**************************************************************************/
924 /* */
925 /* FUNCTION RELEASE */
926 /* */
927 /* nx_msrp_deregister_stream_indication PORTABLE C */
928 /* 6.4.0 */
929 /* AUTHOR */
930 /* */
931 /* Wen Wang, Microsoft Corporation */
932 /* */
933 /* DESCRIPTION */
934 /* */
935 /* This function deregister stream indication. */
936 /* */
937 /* INPUT */
938 /* */
939 /* mrp MRP instance pointer */
940 /* participant MRP participant */
941 /* attribute Attribute */
942 /* indication_type Indication type */
943 /* */
944 /* OUTPUT */
945 /* */
946 /* status Completion status */
947 /* */
948 /* CALLS */
949 /* */
950 /* nx_msrp_deregister_attach_request MSRP deregister attach request*/
951 /* event_callback Application callback */
952 /* */
953 /* CALLED BY */
954 /* */
955 /* nx_msrp_indication_process Process MSRP indication */
956 /* */
957 /* RELEASE HISTORY */
958 /* */
959 /* DATE NAME DESCRIPTION */
960 /* */
961 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
962 /* */
963 /**************************************************************************/
nx_msrp_deregister_stream_indication(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_MRP_ATTRIBUTE * attribute,UCHAR indication_type)964 UINT nx_msrp_deregister_stream_indication(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_MRP_ATTRIBUTE *attribute, UCHAR indication_type)
965 {
966
967 UINT status;
968 NX_MRP_EVENT_CALLBACK event_callback;
969
970 event_callback = ((NX_MSRP *)participant) -> msrp_event_callback;
971 UCHAR *stream_id;
972
973 if (event_callback)
974 {
975
976 status = event_callback(participant, attribute, indication_type, ((NX_MSRP *)participant) -> msrp_callback_data);
977
978 if (status)
979 {
980 return(status);
981 }
982
983 stream_id = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.talker_advertise.stream_id;
984
985 /*Listener Receive deregister indication, send deregister attach*/
986 nx_msrp_deregister_attach_request(mrp, participant, stream_id);
987 }
988
989 return(status);
990 }
991
992 /**************************************************************************/
993 /* */
994 /* FUNCTION RELEASE */
995 /* */
996 /* nx_msrp_register_attach_indication PORTABLE C */
997 /* 6.4.0 */
998 /* AUTHOR */
999 /* */
1000 /* Wen Wang, Microsoft Corporation */
1001 /* */
1002 /* DESCRIPTION */
1003 /* */
1004 /* This function register attach indication. */
1005 /* */
1006 /* INPUT */
1007 /* */
1008 /* participant MRP participant */
1009 /* attribute Attribute */
1010 /* indication_type Indication type */
1011 /* */
1012 /* OUTPUT */
1013 /* */
1014 /* status Completion status */
1015 /* */
1016 /* CALLS */
1017 /* */
1018 /* event_callback Application callback */
1019 /* */
1020 /* CALLED BY */
1021 /* */
1022 /* nx_msrp_indication_process Process MSRP indication */
1023 /* */
1024 /* RELEASE HISTORY */
1025 /* */
1026 /* DATE NAME DESCRIPTION */
1027 /* */
1028 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
1029 /* */
1030 /**************************************************************************/
nx_msrp_register_attach_indication(NX_MRP_PARTICIPANT * participant,NX_MRP_ATTRIBUTE * attribute,UCHAR indication_type)1031 UINT nx_msrp_register_attach_indication(NX_MRP_PARTICIPANT *participant, NX_MRP_ATTRIBUTE *attribute, UCHAR indication_type)
1032 {
1033 UINT status = NX_MSRP_SUCCESS;
1034 NX_MRP_EVENT_CALLBACK event_callback;
1035
1036 event_callback = ((NX_MSRP *)participant) -> msrp_event_callback;
1037
1038 if (event_callback != NX_NULL)
1039 {
1040
1041 status = event_callback(participant, attribute, indication_type, ((NX_MSRP *)participant) -> msrp_callback_data);
1042 }
1043
1044 return(status);
1045 }
1046
1047 /**************************************************************************/
1048 /* */
1049 /* FUNCTION RELEASE */
1050 /* */
1051 /* nx_msrp_deregister_attach_indication PORTABLE C */
1052 /* 6.4.0 */
1053 /* AUTHOR */
1054 /* */
1055 /* Wen Wang, Microsoft Corporation */
1056 /* */
1057 /* DESCRIPTION */
1058 /* */
1059 /* This function deregister attach indication. */
1060 /* */
1061 /* INPUT */
1062 /* */
1063 /* participant MRP participant */
1064 /* attribute Attribute */
1065 /* indication_type Indication type */
1066 /* */
1067 /* OUTPUT */
1068 /* */
1069 /* status Completion status */
1070 /* */
1071 /* CALLS */
1072 /* */
1073 /* event_callback Application callback */
1074 /* */
1075 /* CALLED BY */
1076 /* */
1077 /* nx_msrp_indication_process Process MSRP indication */
1078 /* */
1079 /* RELEASE HISTORY */
1080 /* */
1081 /* DATE NAME DESCRIPTION */
1082 /* */
1083 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
1084 /* */
1085 /**************************************************************************/
nx_msrp_deregister_attach_indication(NX_MRP_PARTICIPANT * participant,NX_MRP_ATTRIBUTE * attribute,UCHAR indication_type)1086 UINT nx_msrp_deregister_attach_indication(NX_MRP_PARTICIPANT *participant, NX_MRP_ATTRIBUTE *attribute, UCHAR indication_type)
1087 {
1088 UINT status = NX_MSRP_SUCCESS;
1089 NX_MRP_EVENT_CALLBACK event_callback;
1090
1091 event_callback = ((NX_MSRP *)participant) -> msrp_event_callback;
1092
1093 if (event_callback != NX_NULL)
1094 {
1095
1096 status = event_callback(participant, attribute, indication_type, ((NX_MSRP *)participant) -> msrp_callback_data);
1097 }
1098
1099 return(status);
1100 }
1101
1102 /**************************************************************************/
1103 /* */
1104 /* FUNCTION RELEASE */
1105 /* */
1106 /* nx_msrp_register_domain_indication PORTABLE C */
1107 /* 6.4.0 */
1108 /* AUTHOR */
1109 /* */
1110 /* Wen Wang, Microsoft Corporation */
1111 /* */
1112 /* DESCRIPTION */
1113 /* */
1114 /* This function register domain indication. */
1115 /* */
1116 /* INPUT */
1117 /* */
1118 /* mrp MRP instance pointer */
1119 /* participant MRP participant */
1120 /* attribute Attribute */
1121 /* indication_type Indication type */
1122 /* */
1123 /* OUTPUT */
1124 /* */
1125 /* status Completion status */
1126 /* */
1127 /* CALLS */
1128 /* */
1129 /* event_callback Application callback */
1130 /* nx_msrp_register_domain_request MSRP register domain request */
1131 /* */
1132 /* CALLED BY */
1133 /* */
1134 /* nx_msrp_indication_process Process MSRP indication */
1135 /* */
1136 /* RELEASE HISTORY */
1137 /* */
1138 /* DATE NAME DESCRIPTION */
1139 /* */
1140 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
1141 /* */
1142 /**************************************************************************/
nx_msrp_register_domain_indication(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_MRP_ATTRIBUTE * attribute,UCHAR indication_type)1143 UINT nx_msrp_register_domain_indication(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_MRP_ATTRIBUTE *attribute, UCHAR indication_type)
1144 {
1145 UINT status;
1146 NX_MRP_EVENT_CALLBACK event_callback;
1147
1148 event_callback = ((NX_MSRP *)participant) -> msrp_event_callback;
1149 NX_MSRP_DOMAIN *domain;
1150
1151
1152 if (event_callback != NX_NULL)
1153 {
1154 status = event_callback(participant, attribute, indication_type, ((NX_MSRP *)participant) -> msrp_callback_data);
1155
1156 if (status != NX_MSRP_SUCCESS)
1157 {
1158 return(status);
1159 }
1160
1161 domain = &(((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain);
1162
1163 nx_msrp_register_domain_request(mrp, participant, domain, NX_MSRP_ACTION_NEW);
1164 }
1165
1166 return(status);
1167 }
1168
1169 /**************************************************************************/
1170 /* */
1171 /* FUNCTION RELEASE */
1172 /* */
1173 /* nx_msrp_deregister_domain_indication PORTABLE C */
1174 /* 6.4.0 */
1175 /* AUTHOR */
1176 /* */
1177 /* Wen Wang, Microsoft Corporation */
1178 /* */
1179 /* DESCRIPTION */
1180 /* */
1181 /* This function deregister domain indication. */
1182 /* */
1183 /* INPUT */
1184 /* */
1185 /* mrp MRP instance pointer */
1186 /* participant MRP participant */
1187 /* attribute Attribute */
1188 /* indication_type Indication type */
1189 /* */
1190 /* OUTPUT */
1191 /* */
1192 /* status Completion status */
1193 /* */
1194 /* CALLS */
1195 /* */
1196 /* event_callback Application callback */
1197 /* nx_msrp_deregister_domain_request MSRP deregister domain request*/
1198 /* */
1199 /* CALLED BY */
1200 /* */
1201 /* nx_msrp_indication_process Process MSRP indication */
1202 /* */
1203 /* RELEASE HISTORY */
1204 /* */
1205 /* DATE NAME DESCRIPTION */
1206 /* */
1207 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
1208 /* */
1209 /**************************************************************************/
nx_msrp_deregister_domain_indication(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_MRP_ATTRIBUTE * attribute,UCHAR indication_type)1210 UINT nx_msrp_deregister_domain_indication(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_MRP_ATTRIBUTE *attribute, UCHAR indication_type)
1211 {
1212 UINT status = NX_MSRP_SUCCESS;
1213 NX_MRP_EVENT_CALLBACK event_callback;
1214
1215 event_callback = ((NX_MSRP *)participant) -> msrp_event_callback;
1216 NX_MSRP_DOMAIN *domain;
1217
1218 if (event_callback)
1219 {
1220 status = event_callback(participant, attribute, indication_type, ((NX_MSRP *)participant) -> msrp_callback_data);
1221
1222 if (status != NX_MSRP_SUCCESS)
1223 {
1224 return(status);
1225 }
1226
1227 domain = &(((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain);
1228
1229 nx_msrp_deregister_domain_request(mrp, participant, domain);
1230 }
1231
1232 return(status);
1233 }
1234
1235 /**************************************************************************/
1236 /* */
1237 /* FUNCTION RELEASE */
1238 /* */
1239 /* nx_msrp_indication_process PORTABLE C */
1240 /* 6.4.0 */
1241 /* AUTHOR */
1242 /* */
1243 /* Wen Wang, Microsoft Corporation */
1244 /* */
1245 /* DESCRIPTION */
1246 /* */
1247 /* This function process MSRP indication. */
1248 /* */
1249 /* INPUT */
1250 /* */
1251 /* mrp MRP instance pointer */
1252 /* participant MRP participant */
1253 /* attribute Attribute */
1254 /* indication_type Indication type */
1255 /* */
1256 /* OUTPUT */
1257 /* */
1258 /* status Completion status */
1259 /* */
1260 /* CALLS */
1261 /* */
1262 /* nx_msrp_register_stream_indication MSRP register stream indicate */
1263 /* nx_msrp_deregister_stream_indication MSRP deregister srteam */
1264 /* indicate */
1265 /* nx_msrp_register_attach_indication MSRP register attach indicate */
1266 /* nx_msrp_deregister_attach_indication MSRP deregister attach */
1267 /* indicate */
1268 /* nx_msrp_register_domain_indication MSRP register domain indicate */
1269 /* nx_msrp_deregister_domain_indication MSRP deregister domain */
1270 /* indicate */
1271 /* */
1272 /* CALLED BY */
1273 /* */
1274 /* nx_mrp_registrar_event_process Process registrar mrp_event */
1275 /* nx_mrp_attribute_evict Evict MRP attribute */
1276 /* */
1277 /* RELEASE HISTORY */
1278 /* */
1279 /* DATE NAME DESCRIPTION */
1280 /* */
1281 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
1282 /* */
1283 /**************************************************************************/
nx_msrp_indication_process(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_MRP_ATTRIBUTE * attribute,UCHAR indication_type)1284 UINT nx_msrp_indication_process(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_MRP_ATTRIBUTE *attribute, UCHAR indication_type)
1285 {
1286
1287 UINT status;
1288
1289
1290 switch (attribute -> attribute_type)
1291 {
1292 case NX_MSRP_TALKER_ADVERTISE_VECTOR:
1293
1294 if (indication_type == NX_MRP_INDICATION_NEW || indication_type == NX_MRP_INDICATION_JOIN)
1295 {
1296 {
1297 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 1;
1298
1299 status = nx_msrp_register_stream_indication(mrp, participant, attribute, indication_type);
1300
1301 if (status != NX_MSRP_SUCCESS)
1302 {
1303 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 0;
1304 }
1305 }
1306 }
1307 else if (indication_type == NX_MRP_INDICATION_LV)
1308 {
1309 {
1310 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 1;
1311
1312 status = nx_msrp_deregister_stream_indication(mrp, participant, attribute, indication_type);
1313 }
1314 }
1315 else
1316 {
1317
1318 status = NX_MSRP_INDICATION_TYPE_ERROR;
1319 }
1320
1321 break;
1322
1323 case NX_MSRP_TALKER_LISTENER_VECTOR:
1324
1325 if (indication_type == NX_MRP_INDICATION_NEW || indication_type == NX_MRP_INDICATION_JOIN)
1326 {
1327 {
1328 if (((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.fourpacked_event >= NX_MSRP_FOURPACKED_READY)
1329 {
1330 status = nx_msrp_register_attach_indication(participant, attribute, indication_type);
1331
1332 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 1;
1333 }
1334 }
1335 }
1336 else if (indication_type == NX_MRP_INDICATION_LV)
1337 {
1338 {
1339
1340 if (((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.fourpacked_event >= NX_MSRP_FOURPACKED_READY)
1341 {
1342 status = nx_msrp_deregister_attach_indication(participant, attribute, indication_type);
1343
1344 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 1;
1345 }
1346 }
1347 }
1348 else
1349 {
1350
1351 status = NX_MSRP_INDICATION_TYPE_ERROR;
1352 }
1353
1354 break;
1355
1356 case NX_MSRP_TALKER_DOMAIN_VECTOR:
1357
1358 if (indication_type == NX_MRP_INDICATION_NEW || indication_type == NX_MRP_INDICATION_JOIN)
1359 {
1360 {
1361 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 1;
1362
1363 status = nx_msrp_register_domain_indication(mrp, participant, attribute, indication_type);
1364 }
1365 }
1366 else if (indication_type == NX_MRP_INDICATION_LV)
1367 {
1368 {
1369 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 1;
1370
1371 status = nx_msrp_deregister_domain_indication(mrp, participant, attribute, indication_type);
1372 }
1373 }
1374 else
1375 {
1376 status = NX_MSRP_INDICATION_TYPE_ERROR;
1377 }
1378
1379 break;
1380
1381 case NX_MSRP_TALKER_FAILED_VECTOR:
1382
1383 break;
1384
1385 default:
1386
1387 status = NX_MSRP_ATTRIBUTE_TYPE_ERROR;
1388 break;
1389 }
1390
1391 return(status);
1392 }
1393
1394 /**************************************************************************/
1395 /* */
1396 /* FUNCTION RELEASE */
1397 /* */
1398 /* nx_msrp_mrpdu_parse PORTABLE C */
1399 /* 6.4.0 */
1400 /* AUTHOR */
1401 /* */
1402 /* Wen Wang, Microsoft Corporation */
1403 /* */
1404 /* DESCRIPTION */
1405 /* */
1406 /* This function parse MRP data unit. */
1407 /* */
1408 /* INPUT */
1409 /* */
1410 /* mrp MRP instance pointer */
1411 /* participant MRP participant */
1412 /* packet_ptr Packet pointer */
1413 /* */
1414 /* OUTPUT */
1415 /* */
1416 /* status Completion status */
1417 /* */
1418 /* CALLS */
1419 /* */
1420 /* nx_msrp_attribute_find MSRP attribute traverse */
1421 /* memcpy standard library */
1422 /* */
1423 /* */
1424 /* CALLED BY */
1425 /* */
1426 /* nx_mrp_registrar_event_process Process registrar mrp_event */
1427 /* nx_mrp_attribute_evict Evict MRP attribute */
1428 /* */
1429 /* RELEASE HISTORY */
1430 /* */
1431 /* DATE NAME DESCRIPTION */
1432 /* */
1433 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
1434 /* */
1435 /**************************************************************************/
nx_msrp_mrpdu_parse(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_PACKET * packet_ptr)1436 UINT nx_msrp_mrpdu_parse(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_PACKET *packet_ptr)
1437 {
1438 UINT status;
1439 NX_MRP_ATTRIBUTE *attribute = NX_NULL;
1440 NX_MSRP_TALKER_ADVERTISE *talker_advertise_ptr;
1441 NX_MSRP_TALKER_FAILED *talker_failed_ptr;
1442 UCHAR attribute_type;
1443 UINT attribute_type_index;
1444 UCHAR mrp_event;
1445 UCHAR is_end = 0;
1446 UINT attribute_list_length_index;
1447 USHORT num_of_value;
1448 UINT num_of_value_index;
1449 UINT first_value_index;
1450 UCHAR lva_event;
1451 UCHAR four_packed_event;
1452 UCHAR three_packed_event;
1453 USHORT attribute_list_length;
1454 UCHAR SRclass_id;
1455 UCHAR *stream_id;
1456 UCHAR *data_ptr = packet_ptr -> nx_packet_data_start;
1457
1458
1459
1460 if (*(data_ptr + NX_MSRP_PROTOCAL_VERSION_INDEX) != 0)
1461 {
1462 return(NX_MSRP_VERSION_NOT_SUPPORTED);
1463 }
1464
1465
1466 attribute_type_index = NX_MSRP_PROTOCAL_VERSION_INDEX + 1;
1467
1468
1469 while (is_end == 0)
1470 {
1471
1472 num_of_value_index = attribute_type_index + 4;
1473 attribute_list_length_index = attribute_type_index + 2;
1474
1475 lva_event = *(data_ptr + num_of_value_index) >> 5;
1476 num_of_value = (USHORT)((*(data_ptr + num_of_value_index) & 0x1f) | *(data_ptr + num_of_value_index + 1));
1477
1478 /*attribute header = 5 bytes*/
1479 first_value_index = attribute_type_index + 6;
1480
1481 if (num_of_value > 1)
1482 {
1483
1484 return(NX_MSRP_NOT_SUPPORTED);
1485 }
1486
1487 attribute_type = *(data_ptr + attribute_type_index);
1488
1489 attribute_list_length = (USHORT)(*(data_ptr + attribute_list_length_index) << 8 | *(data_ptr + attribute_list_length_index + 1));
1490
1491
1492 if (num_of_value)
1493 {
1494
1495
1496 switch (attribute_type)
1497 {
1498
1499 case NX_MSRP_TALKER_ADVERTISE_VECTOR:
1500
1501
1502
1503 talker_advertise_ptr = (NX_MSRP_TALKER_ADVERTISE *)(data_ptr + first_value_index);
1504
1505 status = nx_msrp_attribute_find(mrp, participant, &attribute, attribute_type, talker_advertise_ptr -> stream_id);
1506
1507 /* No attribute was found or created.*/
1508 if (attribute == NX_NULL)
1509 {
1510
1511 return(NX_MSRP_ATTRIBUTE_FIND_ERROR);
1512 }
1513
1514 if (status == NX_MSRP_ATTRIBUTE_NEW)
1515 {
1516
1517 memcpy(&((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.talker_advertise, talker_advertise_ptr,
1518 sizeof(NX_MSRP_TALKER_ADVERTISE)); /* use case of memcpy is verified. */
1519 }
1520
1521
1522 break;
1523
1524 case NX_MSRP_TALKER_LISTENER_VECTOR:
1525
1526 stream_id = (data_ptr + first_value_index);
1527
1528 nx_msrp_attribute_find(mrp, participant, &attribute, attribute_type, stream_id);
1529
1530 /* No attribute was found or created.*/
1531 if (attribute == NX_NULL)
1532 {
1533
1534 return(NX_MSRP_ATTRIBUTE_FIND_ERROR);
1535 }
1536
1537 if (status == NX_MSRP_ATTRIBUTE_NEW)
1538 {
1539
1540 memcpy(&((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener, stream_id,
1541 sizeof(NX_MSRP_LISTENER)); /* use case of memcpy is verified. */
1542 }
1543
1544 four_packed_event = *(data_ptr + attribute_list_length_index + attribute_list_length - 1);
1545
1546 /* FourPackedEvents BYTE ::= ((FourPackedType *64) + (FourPackedType *16)+ (FourPackedType *4) + FourPackedType).*/
1547 four_packed_event = four_packed_event / 64;
1548
1549 ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.fourpacked_event = four_packed_event;
1550
1551 break;
1552
1553 case NX_MSRP_TALKER_DOMAIN_VECTOR:
1554
1555 SRclass_id = *(data_ptr + first_value_index);
1556
1557 status = nx_msrp_attribute_find(mrp, participant, &attribute, attribute_type, &SRclass_id);
1558
1559 /* No attribute was found or created.*/
1560 if (attribute == NX_NULL)
1561 {
1562
1563 return(NX_MSRP_ATTRIBUTE_FIND_ERROR);
1564 }
1565
1566 if (status == NX_MSRP_ATTRIBUTE_NEW)
1567 {
1568 /* If this is a exsit attribute, we assume that it comes from talker,*/
1569 /* and if the applicaion did not start listener, send notify to user callback shouldn't happen.*/
1570 if (((NX_MSRP *)participant) -> listener_enable == 0)
1571 {
1572
1573 ((NX_MSRP_ATTRIBUTE *)attribute) -> indication_flag = 1;
1574 }
1575
1576 memcpy(&((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain, (data_ptr + first_value_index),
1577 sizeof(NX_MSRP_DOMAIN)); /* use case of memcpy is verified. */
1578
1579 NX_CHANGE_USHORT_ENDIAN(((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain.sr_class_vid);
1580 }
1581
1582 break;
1583
1584 case NX_MSRP_TALKER_FAILED_VECTOR:
1585
1586
1587
1588 talker_failed_ptr = (NX_MSRP_TALKER_FAILED *)(data_ptr + first_value_index);
1589
1590 nx_msrp_attribute_find(mrp, participant, &attribute, attribute_type, talker_failed_ptr -> stream_id);
1591
1592 /* No attribute was found or created.*/
1593 if (attribute == NX_NULL)
1594 {
1595
1596 return(NX_MSRP_ATTRIBUTE_FIND_ERROR);
1597 }
1598
1599 break;
1600
1601 default:
1602
1603 return(NX_MSRP_ATTRIBUTE_TYPE_ERROR);
1604 break;
1605 }
1606
1607
1608 if (lva_event)
1609 {
1610
1611 mrp_event = NX_MRP_EVENT_RLA;
1612
1613 nx_mrp_event_process(mrp, participant, attribute, mrp_event);
1614 }
1615
1616 /* ThreePackedEvents BYTE ::= (((((AttributeEvent) *6) + AttributeEvent) *6) + AttributeEvent).*/
1617 three_packed_event = *(data_ptr + attribute_list_length_index + attribute_list_length - 2);
1618
1619 three_packed_event = three_packed_event / 36;
1620
1621 status = nx_mrp_event_process(mrp, participant, attribute, three_packed_event);
1622
1623 if (status != NX_MSRP_SUCCESS)
1624 {
1625 return(status);
1626 }
1627 }
1628
1629 /* Endmask of each attribute *(data_ptr + attribute_list_length_index + attribute_list_length )*/
1630 /* Endmask of each attribute *(data_ptr + attribute_list_length_index + attribute_list_length + 1))*/
1631 if (*(data_ptr + attribute_list_length_index + attribute_list_length + 2) == NX_MSRP_ATTRIBUTE_END_MASK &&
1632 *(data_ptr + attribute_list_length_index + attribute_list_length + 3) == NX_MSRP_ATTRIBUTE_END_MASK)
1633 {
1634
1635 is_end = 1;
1636 }
1637 else
1638 {
1639
1640 /* 4bytes : attrubute length + attribute_list_length + 1*/
1641 attribute_type_index = attribute_type_index + attribute_list_length + 4;
1642 }
1643 }
1644
1645 return(NX_MSRP_SUCCESS);
1646 }
1647
1648 /**************************************************************************/
1649 /* */
1650 /* FUNCTION RELEASE */
1651 /* */
1652 /* nx_msrp_mrpdu_pack_attribute PORTABLE C */
1653 /* 6.4.0 */
1654 /* AUTHOR */
1655 /* */
1656 /* Wen Wang, Microsoft Corporation */
1657 /* */
1658 /* DESCRIPTION */
1659 /* */
1660 /* This function pack attribute into MRP data unit. */
1661 /* */
1662 /* INPUT */
1663 /* */
1664 /* participant MRP participant */
1665 /* attribute Attribute */
1666 /* num_of_value Number of value */
1667 /* threepacked_event Threepacked mrp_event */
1668 /* fourpacked_event Fourpacked_event */
1669 /* data_ptr Data pointer */
1670 /* length_ptr Length pointer */
1671 /* */
1672 /* OUTPUT */
1673 /* */
1674 /* status Completion status */
1675 /* */
1676 /* CALLS */
1677 /* */
1678 /* memcpy standard library */
1679 /* */
1680 /* */
1681 /* CALLED BY */
1682 /* */
1683 /* nx_msrp_mrpdu_pack MSRP pack MRP data unit */
1684 /* */
1685 /* RELEASE HISTORY */
1686 /* */
1687 /* DATE NAME DESCRIPTION */
1688 /* */
1689 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
1690 /* */
1691 /**************************************************************************/
nx_msrp_mrpdu_pack_attribute(NX_MRP_PARTICIPANT * participant,NX_MRP_ATTRIBUTE * attribute,USHORT num_of_value,UCHAR * threepacked_event,UCHAR * fourpacked_event,UCHAR * data_ptr,UINT * length_ptr)1692 UINT nx_msrp_mrpdu_pack_attribute(NX_MRP_PARTICIPANT *participant, NX_MRP_ATTRIBUTE *attribute, USHORT num_of_value,
1693 UCHAR *threepacked_event, UCHAR *fourpacked_event, UCHAR *data_ptr, UINT *length_ptr)
1694 {
1695
1696 UCHAR threepacked_value[NX_MSRP_ATTRIBUTE_ARRAY_MAX_SIZE / 4 / 3 + 1];
1697 UCHAR fourpacked_value[NX_MSRP_ATTRIBUTE_ARRAY_MAX_SIZE / 4 / 3 + 1];
1698 UINT num_of_threepacked;
1699 UINT num_of_fourpacked;
1700 UINT i, index = 0;
1701 UINT lva_event = 0;
1702 USHORT tmp;
1703 USHORT attribute_list_length;
1704
1705 /* Allowed max value of talker and listener.*/
1706 if (num_of_value > NX_MSRP_ATTRIBUTE_ARRAY_MAX_SIZE / 4)
1707 {
1708
1709 return(NX_MSRP_PARAMETER_ERROR);
1710 }
1711
1712 if (participant -> leaveall.action == NX_MRP_ACTION_SLA)
1713 {
1714
1715 lva_event = 1;
1716
1717 /* Send only lva mrp_event, the attribute content will be null.*/
1718 if ((attribute -> applicant.action == NX_MRP_ACTION_NULL) || (attribute -> applicant.action > NX_MRP_ACTION_S_OPT))
1719 {
1720
1721 num_of_value = 0;
1722
1723 switch (attribute -> attribute_type)
1724 {
1725
1726 case NX_MSRP_TALKER_ADVERTISE_VECTOR:
1727
1728 *data_ptr++ = NX_MSRP_TALKER_ADVERTISE_VECTOR;
1729 *data_ptr++ = NX_MSRP_TALKER_ADVERTISE_ATTRIBUTE_LENGTH;
1730 *data_ptr++ = 0;
1731
1732 /* 4 = vectorhead + endmark.*/
1733 attribute_list_length = NX_MSRP_TALKER_ADVERTISE_ATTRIBUTE_LENGTH + 4;
1734 *data_ptr++ = (UCHAR)attribute_list_length;
1735 tmp = (USHORT)(lva_event << 13 | num_of_value);
1736 *data_ptr++ = (UCHAR)(tmp >> 8);
1737 *data_ptr++ = (UCHAR)tmp;
1738 memset(data_ptr, 00, attribute_list_length);
1739 /* 4 = attribute_type + attribute_length_attribute_list_length.*/
1740 *length_ptr = (UINT)(attribute_list_length + 4);
1741
1742 break;
1743
1744 case NX_MSRP_TALKER_LISTENER_VECTOR:
1745
1746 *data_ptr++ = NX_MSRP_TALKER_LISTENER_VECTOR;
1747 *data_ptr++ = NX_MSRP_LISTENER_ATTRIBUTE_LENGTH;
1748 *data_ptr++ = 0;
1749 attribute_list_length = NX_MSRP_LISTENER_ATTRIBUTE_LENGTH + 4;
1750 *data_ptr++ = (UCHAR)attribute_list_length;
1751 tmp = (USHORT)(lva_event << 13 | num_of_value);
1752 *data_ptr++ = (UCHAR)(tmp >> 8);
1753 *data_ptr++ = (UCHAR)tmp;
1754 memset(data_ptr, 00, attribute_list_length);
1755 *length_ptr = (UINT)(attribute_list_length + 4); // 4 = attribute_type + attribute_length_attribute_list_length
1756 break;
1757
1758 case NX_MSRP_TALKER_DOMAIN_VECTOR:
1759
1760 *data_ptr++ = NX_MSRP_TALKER_DOMAIN_VECTOR;
1761 *data_ptr++ = NX_MSRP_DOMAIN_ATTRIBUTE_LENGTH;
1762 *data_ptr++ = 0;
1763 attribute_list_length = NX_MSRP_DOMAIN_ATTRIBUTE_LENGTH + 4;
1764 *data_ptr++ = (UCHAR)attribute_list_length;
1765 tmp = (USHORT)(lva_event << 13 | num_of_value);
1766 *data_ptr++ = (UCHAR)(tmp >> 8);
1767 *data_ptr++ = (UCHAR)tmp;
1768 memset(data_ptr, 00, attribute_list_length);
1769 *length_ptr = (UINT)(attribute_list_length + 4); // 4 = attribute_type + attribute_length_attribute_list_length
1770
1771 break;
1772 case NX_MSRP_TALKER_FAILED_VECTOR:
1773 default:
1774 break;
1775 }
1776
1777 return(NX_MSRP_SUCCESS);
1778 }
1779 }
1780
1781 /* Fill packet content next.*/
1782 if (num_of_value % 3)
1783 {
1784 num_of_threepacked = (UINT)(num_of_value / 3 + 1);
1785
1786 num_of_fourpacked = (UINT)(num_of_value / 3 + 1);
1787 }
1788 else
1789 {
1790
1791 num_of_threepacked = (UINT)(num_of_value / 3);
1792
1793 num_of_fourpacked = (UINT)(num_of_value / 4);
1794 }
1795
1796 /*ThreePackedEvents BYTE ::= (((((AttributeEvent) *6) + AttributeEvent) *6) + AttributeEvent)*/
1797 for (i = 0; i < num_of_threepacked; i++)
1798 {
1799
1800 threepacked_value[i++] = (UCHAR)(((((threepacked_event[index]) * 6) + threepacked_event[index + 1]) * 6) + threepacked_event[index + 2]);
1801
1802 index += 3;
1803 }
1804
1805 switch (attribute -> attribute_type)
1806 {
1807
1808 case NX_MSRP_TALKER_ADVERTISE_VECTOR:
1809
1810 *data_ptr++ = NX_MSRP_TALKER_ADVERTISE_VECTOR;
1811 *data_ptr++ = NX_MSRP_TALKER_ADVERTISE_ATTRIBUTE_LENGTH;
1812 *data_ptr++ = 0;
1813
1814 /* 4 = vectorhead + endmark*/
1815 attribute_list_length = (USHORT)(NX_MSRP_TALKER_ADVERTISE_ATTRIBUTE_LENGTH + 4 + num_of_threepacked);
1816 *data_ptr++ = (UCHAR)attribute_list_length;
1817 tmp = (USHORT)(lva_event << 13 | num_of_value);
1818 *data_ptr++ = (UCHAR)(tmp >> 8);
1819 *data_ptr++ = (UCHAR)tmp;
1820
1821 memcpy(data_ptr, ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.talker_advertise.stream_id,
1822 sizeof(NX_MSRP_TALKER_ADVERTISE)); /* use case of memcpy is verified. */
1823
1824 /* Fix the above copy endian 14 = stream_id + dest_addr*/
1825 *(data_ptr + 14) = (UCHAR)(((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.talker_advertise.vlan_identifier >> 8);
1826
1827 *(data_ptr + 15) = (UCHAR)(((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.talker_advertise.vlan_identifier);
1828
1829 for (i = 0; i < num_of_threepacked; i++)
1830 {
1831 *(data_ptr + sizeof(NX_MSRP_TALKER_ADVERTISE) + i) = threepacked_value[i];
1832 }
1833
1834 /* Endmark*/
1835 (*(data_ptr + sizeof(NX_MSRP_TALKER_ADVERTISE) + num_of_threepacked)) = 0;
1836
1837 (*(data_ptr + sizeof(NX_MSRP_TALKER_ADVERTISE) + num_of_threepacked + 1)) = 0;
1838
1839 *length_ptr = (UINT)(attribute_list_length + 4);
1840
1841 break;
1842
1843 case NX_MSRP_TALKER_LISTENER_VECTOR:
1844
1845 index = 0;
1846
1847 /* FourPackedEvents BYTE ::= ((FourPackedType *64) + (FourPackedType *16)+ (FourPackedType *4) + FourPackedType)*/
1848 for (i = 0; i < num_of_fourpacked; i++)
1849 {
1850
1851 fourpacked_value[i++] = (UCHAR)((fourpacked_event[index] * 64) + (fourpacked_event[index + 1] * 16) +
1852 (fourpacked_event[index + 2] * 4) + fourpacked_event[index + 3]);
1853
1854 index += 4;
1855 }
1856 *data_ptr++ = NX_MSRP_TALKER_LISTENER_VECTOR;
1857 *data_ptr++ = NX_MSRP_LISTENER_ATTRIBUTE_LENGTH;
1858 *data_ptr++ = 0;
1859 attribute_list_length = (USHORT)(NX_MSRP_LISTENER_ATTRIBUTE_LENGTH + 4 + num_of_threepacked + num_of_fourpacked);
1860 *data_ptr++ = (UCHAR)attribute_list_length;
1861 tmp = (USHORT)(lva_event << 13 | num_of_value);
1862 *data_ptr++ = (UCHAR)(tmp >> 8);
1863 *data_ptr++ = (UCHAR)tmp;
1864
1865 memcpy(data_ptr, ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.stream_id,
1866 STREAM_ID_SIZE); /* use case of memcpy is verified. */
1867
1868 for (i = 0; i < num_of_threepacked; i++)
1869 {
1870 *(data_ptr + STREAM_ID_SIZE + i) = threepacked_value[i];
1871 }
1872
1873 for (i = 0; i < num_of_fourpacked; i++)
1874 {
1875 *(data_ptr + STREAM_ID_SIZE + num_of_threepacked + i) = fourpacked_value[i];
1876 }
1877
1878 /* Endmark*/
1879 (*(data_ptr + STREAM_ID_SIZE + num_of_threepacked + num_of_fourpacked)) = 0;
1880
1881 (*(data_ptr + STREAM_ID_SIZE + num_of_threepacked + num_of_fourpacked + 1)) = 0;
1882
1883 /* 4 = attribute_type + attribute_length_attribute_list_length*/
1884 *length_ptr = (UINT)(attribute_list_length + 4);
1885
1886 break;
1887
1888 case NX_MSRP_TALKER_DOMAIN_VECTOR:
1889
1890 *data_ptr++ = NX_MSRP_TALKER_DOMAIN_VECTOR;
1891 *data_ptr++ = NX_MSRP_DOMAIN_ATTRIBUTE_LENGTH;
1892 *data_ptr++ = 0;
1893 attribute_list_length = (USHORT)(NX_MSRP_DOMAIN_ATTRIBUTE_LENGTH + 4 + num_of_threepacked);
1894 *data_ptr++ = (UCHAR)attribute_list_length;
1895 tmp = (USHORT)((lva_event) << 13 | num_of_value);
1896 *data_ptr++ = (UCHAR)(tmp >> 8);
1897 *data_ptr++ = (UCHAR)tmp;
1898
1899 *data_ptr = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain.sr_class_id;
1900 *(data_ptr + 1) = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain.sr_class_priority;
1901 *(data_ptr + 2) = (UCHAR)(((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain.sr_class_vid >> 8);
1902 *(data_ptr + 3) = (UCHAR)(((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain.sr_class_vid);
1903
1904 for (i = 0; i < num_of_threepacked; i++)
1905 {
1906 *(data_ptr + sizeof(NX_MSRP_DOMAIN) + i) = threepacked_value[i];
1907 }
1908
1909 /* Endmark*/
1910 (*(data_ptr + sizeof(NX_MSRP_DOMAIN) + num_of_threepacked)) = 0;
1911 (*(data_ptr + sizeof(NX_MSRP_DOMAIN) + num_of_threepacked + 1)) = 0;
1912
1913 /* 4 = attribute_type + attribute_length_attribute_list_length*/
1914 *length_ptr = (UINT)(attribute_list_length + 4);
1915
1916 break;
1917
1918 case NX_MSRP_TALKER_FAILED_VECTOR:
1919 default:
1920
1921 return(NX_MSRP_ATTRIBUTE_TYPE_ERROR);
1922 break;
1923 }
1924
1925 return(NX_MSRP_SUCCESS);
1926 }
1927
1928 /**************************************************************************/
1929 /* */
1930 /* FUNCTION RELEASE */
1931 /* */
1932 /* nx_msrp_mrpdu_pack PORTABLE C */
1933 /* 6.4.0 */
1934 /* AUTHOR */
1935 /* */
1936 /* Wen Wang, Microsoft Corporation */
1937 /* */
1938 /* DESCRIPTION */
1939 /* */
1940 /* This function pack MRP data unit. */
1941 /* */
1942 /* INPUT */
1943 /* */
1944 /* mrp MRP instance pointer */
1945 /* participant MRP participant */
1946 /* packet_ptr Packet pointer */
1947 /* */
1948 /* OUTPUT */
1949 /* */
1950 /* status Completion status */
1951 /* */
1952 /* CALLS */
1953 /* */
1954 /* nx_packet_data_append Append data into packet */
1955 /* nx_msrp_mrpdu_pack_attribute Pack MSRP attribute */
1956 /* nx_mrp_attribute_event_get Get MRP attribute mrp_event */
1957 /* */
1958 /* */
1959 /* CALLED BY */
1960 /* */
1961 /* nx_mrp_join_timeout_process MRP join timer timeout process*/
1962 /* */
1963 /* RELEASE HISTORY */
1964 /* */
1965 /* DATE NAME DESCRIPTION */
1966 /* */
1967 /* 12-31-2023 Wen Wang Initial Version 6.4.0 */
1968 /* */
1969 /**************************************************************************/
nx_msrp_mrpdu_pack(NX_MRP * mrp,NX_MRP_PARTICIPANT * participant,NX_PACKET * packet_ptr)1970 UINT nx_msrp_mrpdu_pack(NX_MRP *mrp, NX_MRP_PARTICIPANT *participant, NX_PACKET *packet_ptr)
1971 {
1972
1973 UCHAR *data_ptr = packet_ptr -> nx_packet_prepend_ptr;
1974 UINT data_length = 0;
1975 UINT status;
1976 NX_MRP_ATTRIBUTE *attribute = participant -> inused_head;
1977 NX_MRP_ATTRIBUTE *attribute_start;
1978 UCHAR *id[NX_MSRP_ATTRIBUTE_ARRAY_MAX_SIZE];
1979 UCHAR threepacked_event[NX_MSRP_ATTRIBUTE_ARRAY_MAX_SIZE];
1980 UCHAR fourpacked_event[NX_MSRP_ATTRIBUTE_ARRAY_MAX_SIZE];
1981 UCHAR index = 0;
1982 USHORT num_of_value = 0;
1983
1984 if (attribute -> attribute_type == 0)
1985 {
1986 return(NX_MSRP_ATTRIBUTE_TYPE_ERROR);
1987 }
1988
1989 memset(threepacked_event, 0, sizeof(threepacked_event));
1990
1991 *data_ptr = NX_MRP_MSRP_PROTOCOL_VERSION;
1992
1993 data_length = 1;
1994
1995 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
1996
1997 if (status)
1998 {
1999 return(status);
2000 }
2001
2002 data_ptr++;
2003
2004 /*Look up talkeradvertise attribute to pack*/
2005 while (attribute && attribute -> attribute_type == NX_MSRP_TALKER_ADVERTISE_VECTOR)
2006 {
2007
2008 if ((attribute -> applicant.action == NX_MRP_ACTION_NULL) || (attribute -> applicant.action > NX_MRP_ACTION_S_OPT))
2009 {
2010 /* If lva action is needed, send lva attribute anyway.*/
2011 if (participant -> leaveall.action == NX_MRP_ACTION_SLA)
2012 {
2013
2014 status = nx_msrp_mrpdu_pack_attribute(participant, attribute, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2015
2016 if (status)
2017 {
2018 return(status);
2019 }
2020
2021 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2022
2023 if (status)
2024 {
2025 return(status);
2026 }
2027
2028 data_ptr = data_ptr + data_length;
2029 }
2030
2031 attribute = attribute -> next;
2032
2033 continue;
2034 }
2035
2036 attribute_start = attribute;
2037
2038 nx_mrp_attribute_event_get(attribute, &threepacked_event[0]);
2039
2040 id[0] = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.talker_advertise.stream_id;
2041
2042
2043 num_of_value = 1;
2044 index = 1;
2045
2046
2047 if (attribute -> next == NX_NULL || attribute -> next -> attribute_type != NX_MSRP_TALKER_ADVERTISE_VECTOR)
2048 {
2049
2050 status = nx_msrp_mrpdu_pack_attribute(participant, attribute_start, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2051
2052 if (status)
2053 {
2054 return(status);
2055 }
2056
2057 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2058
2059 if (status)
2060 {
2061 return(status);
2062 }
2063
2064 data_ptr = data_ptr + data_length;
2065
2066 attribute = attribute -> next;
2067
2068 break;
2069 }
2070
2071 /* Continue looking up talkeradvertise attribute to pack.*/
2072 while ((attribute = attribute -> next) && (attribute -> attribute_type == NX_MSRP_TALKER_ADVERTISE_VECTOR))
2073 {
2074
2075 if ((attribute -> applicant.action == NX_MRP_ACTION_NULL) || (attribute -> applicant.action > NX_MRP_ACTION_SLA))
2076 {
2077 /* If lva action is needed, send lva attribute anyway.*/
2078 if (participant -> leaveall.action == NX_MRP_ACTION_SLA)
2079 {
2080 /* Need to check the paramter attribute_start or attribute*/
2081 status = nx_msrp_mrpdu_pack_attribute(participant, attribute, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2082
2083 if (status)
2084 {
2085 return(status);
2086 }
2087
2088 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2089
2090 if (status)
2091 {
2092 return(status);
2093 }
2094
2095 data_ptr = data_ptr + data_length;
2096 }
2097
2098 continue;
2099 }
2100
2101 id[index] = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.talker_advertise.stream_id;
2102
2103 nx_mrp_attribute_event_get(attribute, &threepacked_event[index]);
2104
2105 if (memcmp(id[index], id[index - 1], 8) == 1)
2106 {
2107
2108 num_of_value++;
2109 index++;
2110
2111 continue;
2112 }
2113 else
2114 {
2115
2116 status = nx_msrp_mrpdu_pack_attribute(participant, attribute_start, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2117
2118 if (status)
2119 {
2120 return(status);
2121 }
2122
2123 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2124
2125 if (status)
2126 {
2127 return(status);
2128 }
2129
2130 data_ptr = data_ptr + data_length;
2131
2132
2133 break;
2134 }
2135 }
2136 }
2137
2138 /*Look up listener attribute to pack*/
2139 while (attribute && attribute -> attribute_type == NX_MSRP_TALKER_LISTENER_VECTOR)
2140 {
2141
2142 if ((attribute -> applicant.action == NX_MRP_ACTION_NULL) || (attribute -> applicant.action > NX_MRP_ACTION_SLA))
2143 {
2144 /* If lva action is needed, send lva attribute anyway.*/
2145 if (participant -> leaveall.action == NX_MRP_ACTION_SLA)
2146 {
2147
2148 status = nx_msrp_mrpdu_pack_attribute(participant, attribute, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2149
2150 if (status)
2151 {
2152 return(status);
2153 }
2154
2155 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2156
2157 if (status)
2158 {
2159 return(status);
2160 }
2161
2162 data_ptr = data_ptr + data_length;
2163 }
2164
2165 attribute = attribute -> next;
2166
2167 continue;
2168 }
2169
2170 attribute_start = attribute;
2171
2172 nx_mrp_attribute_event_get(attribute, &threepacked_event[0]);
2173
2174 fourpacked_event[0] = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.fourpacked_event;
2175
2176 id[0] = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.stream_id;
2177
2178 num_of_value = 1;
2179
2180 index = 1;
2181
2182 if (attribute -> next == NX_NULL || attribute -> next -> attribute_type != NX_MSRP_TALKER_LISTENER_VECTOR)
2183 {
2184
2185 status = nx_msrp_mrpdu_pack_attribute(participant, attribute_start, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2186
2187 if (status)
2188 {
2189 return(status);
2190 }
2191
2192 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2193
2194 if (status)
2195 {
2196 return(status);
2197 }
2198
2199 data_ptr = data_ptr + data_length;
2200
2201 attribute = attribute -> next;
2202
2203 break;
2204 }
2205 /* Continue looking up listener attribute to pack.*/
2206 while ((attribute = attribute -> next) && (attribute -> attribute_type == NX_MSRP_TALKER_LISTENER_VECTOR))
2207 {
2208
2209 if ((attribute -> applicant.action == NX_MRP_ACTION_NULL) || (attribute -> applicant.action > NX_MRP_ACTION_SLA))
2210 {
2211
2212 /* If lva action is needed, send lva attribute anyway.*/
2213 if (participant -> leaveall.action == NX_MRP_ACTION_SLA)
2214 {
2215
2216 status = nx_msrp_mrpdu_pack_attribute(participant, attribute, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2217
2218 if (status)
2219 {
2220 return(status);
2221 }
2222
2223 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2224
2225 if (status)
2226 {
2227 return(status);
2228 }
2229
2230 data_ptr = data_ptr + data_length;
2231 }
2232 continue;
2233 }
2234
2235 id[index] = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.stream_id;
2236
2237 fourpacked_event[index] = ((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.listener.fourpacked_event;
2238
2239 nx_mrp_attribute_event_get(attribute, &threepacked_event[index]);
2240
2241 if (memcmp(id[index], id[index - 1], 8) == 1)
2242 {
2243
2244 num_of_value++;
2245 index++;
2246
2247 continue;
2248 }
2249 else
2250 {
2251
2252 status = nx_msrp_mrpdu_pack_attribute(participant, attribute_start, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2253
2254 if (status)
2255 {
2256 return(status);
2257 }
2258
2259 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2260
2261 if (status)
2262 {
2263 return(status);
2264 }
2265
2266 data_ptr = data_ptr + data_length;
2267
2268 break;
2269 }
2270 }
2271 }
2272
2273 /*Look up domain attribute to pack*/
2274 while (attribute && attribute -> attribute_type == NX_MSRP_TALKER_DOMAIN_VECTOR)
2275 {
2276
2277 if ((attribute -> applicant.action == NX_MRP_ACTION_NULL) || (attribute -> applicant.action > NX_MRP_ACTION_SLA))
2278 {
2279 /* If lva action is needed, send lva attribute anyway.*/
2280 if (participant -> leaveall.action == NX_MRP_ACTION_SLA)
2281 {
2282
2283 status = nx_msrp_mrpdu_pack_attribute(participant, attribute, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2284
2285 if (status)
2286 {
2287 return(status);
2288 }
2289
2290 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2291
2292 if (status)
2293 {
2294 return(status);
2295 }
2296
2297 data_ptr = data_ptr + data_length;
2298 }
2299
2300 attribute = attribute -> next;
2301
2302 continue;
2303 }
2304
2305 attribute_start = attribute;
2306
2307 nx_mrp_attribute_event_get(attribute, &threepacked_event[0]);
2308
2309 id[0] = &((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain.sr_class_id;
2310
2311 num_of_value = 1;
2312 index = 1;
2313
2314 if (attribute -> next == NX_NULL)
2315 {
2316
2317 status = nx_msrp_mrpdu_pack_attribute(participant, attribute_start, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2318
2319 if (status)
2320 {
2321 return(status);
2322 }
2323
2324 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2325
2326 if (status)
2327 {
2328 return(status);
2329 }
2330
2331 data_ptr = data_ptr + data_length;
2332
2333 attribute = attribute -> next;
2334
2335 break;
2336 }
2337 /* Continue looking up domain attribute to pack.*/
2338 while ((attribute = attribute -> next) && (attribute -> attribute_type == NX_MSRP_TALKER_DOMAIN_VECTOR))
2339 {
2340
2341 if ((attribute -> applicant.action == NX_MRP_ACTION_NULL) || (attribute -> applicant.action > NX_MRP_ACTION_SLA))
2342 {
2343 /* If lva action is needed, send lva attribute anyway.*/
2344 if (participant -> leaveall.action == NX_MRP_ACTION_SLA)
2345 {
2346
2347 status = nx_msrp_mrpdu_pack_attribute(participant, attribute, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2348
2349 if (status)
2350 {
2351 return(status);
2352 }
2353
2354 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2355
2356 if (status)
2357 {
2358 return(status);
2359 }
2360
2361 data_ptr = data_ptr + data_length;
2362 }
2363
2364 continue;
2365 }
2366
2367 id[index] = &((NX_MSRP_ATTRIBUTE *)attribute) -> msrp_attribute_union.domain.sr_class_id;
2368
2369 nx_mrp_attribute_event_get(attribute, &threepacked_event[index]);
2370
2371 if (memcmp(id[index], id[index - 1], 1) == 1)
2372 {
2373
2374 num_of_value++;
2375 index++;
2376
2377 continue;
2378 }
2379 else
2380 {
2381
2382 status = nx_msrp_mrpdu_pack_attribute(participant, attribute_start, num_of_value, threepacked_event, fourpacked_event, data_ptr, &data_length);
2383
2384 if (status)
2385 {
2386 return(status);
2387 }
2388
2389 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2390
2391 if (status)
2392 {
2393 return(status);
2394 }
2395
2396 data_ptr = data_ptr + data_length;
2397
2398 break;
2399 }
2400 }
2401 }
2402
2403 /* No attribute needs to be send.*/
2404 if (packet_ptr -> nx_packet_length == 1)
2405 {
2406 packet_ptr -> nx_packet_length = 0;
2407
2408 return NX_MSRP_WAIT;
2409 }
2410 else
2411 {
2412 /* Add endmark*/
2413 *data_ptr = 0;
2414 *(data_ptr + 1) = 0;
2415
2416 data_length = 2;
2417
2418 status = nx_packet_data_append(packet_ptr, data_ptr, data_length, mrp -> pkt_pool, NX_NO_WAIT);
2419
2420 if (status)
2421 {
2422 return(status);
2423 }
2424 }
2425
2426 return(status);
2427 }
2428 #endif /* NX_ENABLE_VLAN */
2429
2430