1 /*
2  * Copyright (c) 2017-2020, Texas Instruments Incorporated
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  *
9  * *  Redistributions of source code must retain the above copyright
10  *    notice, this list of conditions and the following disclaimer.
11  *
12  * *  Redistributions in binary form must reproduce the above copyright
13  *    notice, this list of conditions and the following disclaimer in the
14  *    documentation and/or other materials provided with the distribution.
15  *
16  * *  Neither the name of Texas Instruments Incorporated nor the names of
17  *    its contributors may be used to endorse or promote products derived
18  *    from this software without specific prior written permission.
19  *
20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
21  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
22  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
23  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
24  * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
26  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
27  * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
28  * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
29  * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
30  * EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31  */
32 
33 /*****************************************************************************/
34 /* Include files                                                             */
35 /*****************************************************************************/
36 
37 /* Global includes                                                           */
38 #include <unistd.h>
39 #include <string.h>
40 #include <stdlib.h>
41 #include <stdbool.h>
42 
43 #include <ti/net/slnetif.h>
44 #include <ti/net/slneterr.h>
45 
46 /*****************************************************************************/
47 /* Macro declarations                                                        */
48 /*****************************************************************************/
49 
50 #define SLNETIF_NORMALIZE_NEEDED 0
51 #if SLNETIF_NORMALIZE_NEEDED
52     #define SLNETIF_NORMALIZE_RET_VAL(retVal,err)   ((retVal < 0)?(retVal = err):(retVal))
53 #else
54     #define SLNETIF_NORMALIZE_RET_VAL(retVal,err)
55 #endif
56 
57 /* Interface maximum priority                                               */
58 #define SLNETIF_MAX_PRIORITY                        (15)
59 
60 /* The 32bit interface flags structure:
61    Bits  0-3 : interface priority
62    Bit     4 : Interface state
63    Bits 5-31 : Reserved
64 */
65 #define IF_PRIORITY_BITS                            (0x000f)
66 #define IF_STATE_BIT                                (0x0010)
67 
68 /* this macro returns the priority of the interface                          */
69 #define GET_IF_PRIORITY(netIf)                      ((netIf).flags & IF_PRIORITY_BITS)
70 
71 /* this macro reset the priority of the interface                            */
72 #define RESET_IF_PRIORITY(netIf)                    ((netIf).flags &= ~IF_PRIORITY_BITS)
73 
74 /* this macro set the priority of the interface                              */
75 #define SET_IF_PRIORITY(netIf, priority)            ((netIf).flags |= ((int32_t)priority))
76 
77 /* this macro returns the state of the interface                             */
78 #define GET_IF_STATE(netIf)                         (((netIf).flags & IF_STATE_BIT)?SLNETIF_STATE_ENABLE:SLNETIF_STATE_DISABLE)
79 
80 /* this macro set the interface to enable state                              */
81 #define SET_IF_STATE_ENABLE(netIf)                  ((netIf).flags |= IF_STATE_BIT)
82 
83 /* this macro set the interface to disable state                             */
84 #define SET_IF_STATE_DISABLE(netIf)                 ((netIf).flags &= ~IF_STATE_BIT)
85 
86 /* Check if the state bit is set                                             */
87 #define IS_STATE_BIT_SET(queryBitmap)               (0 != (queryBitmap & SLNETIF_QUERY_IF_STATE_BIT))
88 
89 /* Check if the connection status bit is set                                 */
90 #define IS_CONNECTION_STATUS_BIT_SET(queryBitmap)   (0 != (queryBitmap & SLNETIF_QUERY_IF_CONNECTION_STATUS_BIT))
91 
92 /* Return last found netIf, if none of the existing interfaces answers
93    the query                                                                 */
94 #define IS_ALLOW_PARTIAL_MATCH_BIT_SET(queryBitmap) (0 != (queryBitmap & SLNETIF_QUERY_IF_ALLOW_PARTIAL_MATCH_BIT))
95 
96 /*****************************************************************************/
97 /* Structure/Enum declarations                                               */
98 /*****************************************************************************/
99 
100 
101 /* Interface Node */
102 typedef struct SlNetIf_Node_t
103 {
104     SlNetIf_t              netIf;
105     struct SlNetIf_Node_t *next;
106 } SlNetIf_Node_t;
107 
108 /*****************************************************************************/
109 /* Global declarations                                                       */
110 /*****************************************************************************/
111 
112 static SlNetIf_Node_t * SlNetIf_listHead = NULL;
113 
114 /*****************************************************************************/
115 /* Function prototypes                                                       */
116 /*****************************************************************************/
117 
118 static int32_t SlNetIf_configCheck(const SlNetIf_Config_t *ifConf);
119 
120 //*****************************************************************************
121 //
122 // SlNetIf_configCheck - Checks that all mandatory configuration exists
123 //
124 //*****************************************************************************
125 
SlNetIf_configCheck(const SlNetIf_Config_t * ifConf)126 static int32_t SlNetIf_configCheck(const SlNetIf_Config_t *ifConf)
127 {
128     /* Check if the mandatory configuration exists
129        This configuration needs to be updated when new mandatory is added    */
130     if ((NULL != ifConf) &&
131         (NULL != ifConf->sockCreate)   &&
132         (NULL != ifConf->sockClose)    &&
133         (NULL != ifConf->sockSelect)   &&
134         (NULL != ifConf->sockSetOpt)   &&
135         (NULL != ifConf->sockGetOpt)   &&
136         (NULL != ifConf->sockRecvFrom) &&
137         (NULL != ifConf->sockSendTo)   &&
138         (NULL != ifConf->ifGetIPAddr)  &&
139         (NULL != ifConf->ifGetConnectionStatus) )
140     {
141         /* All mandatory configuration exists - return success               */
142         return SLNETERR_RET_CODE_OK;
143     }
144     else
145     {
146         /* Not all mandatory configuration exists - return error code        */
147         return SLNETERR_INVALPARAM;
148     }
149 
150 }
151 
152 //*****************************************************************************
153 //
154 // SlNetIf_init - Initialize the SlNetIf module
155 //
156 //*****************************************************************************
SlNetIf_init(int32_t flags)157 int32_t SlNetIf_init(int32_t flags)
158 {
159     return SLNETERR_RET_CODE_OK;
160 }
161 
162 
163 //*****************************************************************************
164 //
165 // SlNetIf_add - Adding new interface
166 //
167 //*****************************************************************************
SlNetIf_add(uint16_t ifID,char * ifName,const SlNetIf_Config_t * ifConf,uint8_t priority)168 int32_t SlNetIf_add(uint16_t ifID, char *ifName, const SlNetIf_Config_t *ifConf, uint8_t priority)
169 {
170     SlNetIf_Node_t *ifNode    = SlNetIf_listHead;
171     SlNetIf_Node_t *prvNode   = NULL;
172     char           *allocName = NULL;
173     int16_t         strLen;
174     int32_t         retVal;
175 
176     /* Check if ifID is a valid input - Only one bit is set (Pow of 2) or if
177        the priority isn't a valid input                                      */
178     if ( (false == ONLY_ONE_BIT_IS_SET(ifID)) || (priority > SLNETIF_MAX_PRIORITY) )
179     {
180         return SLNETERR_RET_CODE_INVALID_INPUT;
181     }
182 
183     /* Run over the interface list until finding the required ifID or Until
184        reaching the end of the list                                          */
185     while (NULL != ifNode)
186     {
187         /* Check if the identifier of the interface is equal to the input    */
188         if ((ifNode->netIf).ifID == ifID)
189         {
190             /* Required interface found, ifID cannot be used again           */
191             return SLNETERR_RET_CODE_INVALID_INPUT;
192         }
193         /* Check if the identifier of the interface is equal to the input    */
194         if ((GET_IF_PRIORITY(ifNode->netIf)) > priority)
195         {
196             /* Higher priority interface found, save location                */
197             prvNode = ifNode;
198         }
199         else
200         {
201             break;
202         }
203         ifNode = ifNode->next;
204     }
205 
206 
207     /* Check if all required configuration exists                            */
208     retVal = SlNetIf_configCheck(ifConf);
209 
210     /* Check retVal in order to continue with adding the interface           */
211     if (SLNETERR_RET_CODE_OK == retVal)
212     {
213         /* Interface node memory allocation                                  */
214         /* Allocate memory for new interface node for the interface list     */
215         ifNode = malloc(sizeof(SlNetIf_Node_t));
216 
217         /* Check if the memory allocated successfully                        */
218         if (NULL == ifNode)
219         {
220             /* Allocation failed, return error code                          */
221             return SLNETERR_RET_CODE_MALLOC_ERROR;
222         }
223 
224         /* Interface name memory allocation                                  */
225         /* Check if memory allocation for the name of the string is required */
226         if (NULL != ifName)
227         {
228             /* Store the length of the interface name                        */
229             strLen = strlen(ifName);
230 
231             /* Allocate memory that will store the name of the interface     */
232             allocName = malloc(strLen + 1);
233 
234             /* Check if the memory allocated successfully                    */
235             if (NULL == allocName)
236             {
237                 /* Allocation failed, free ifNode before returning from
238                    function                                                  */
239                 free(ifNode);
240                 return SLNETERR_RET_CODE_MALLOC_ERROR;
241             }
242             /* Copy the input name into the allocated memory.
243              *
244              * Note, using strcpy (not strncpy) to work around gcc warning
245              *     https://gcc.gnu.org/bugzilla//show_bug.cgi?id=88059
246              * ... and we know ifName will fit in allocName.
247              */
248             strcpy(allocName, ifName);
249         }
250 
251         /* Fill the allocated interface node with the input parameters       */
252 
253         /* Copy the interface ID                                             */
254         (ifNode->netIf).ifID   = ifID;
255         /* Connect the string allocated memory into the allocated interface  */
256         (ifNode->netIf).ifName = allocName;
257         /* Copy the interface configuration                                  */
258         (ifNode->netIf).ifConf = (SlNetIf_Config_t *)ifConf;
259         /* Reset the flags, set state to ENABLE and set the priority         */
260         (ifNode->netIf).flags  = 0;
261         SET_IF_PRIORITY(ifNode->netIf, priority);
262         SET_IF_STATE_ENABLE(ifNode->netIf);
263 
264         /* Check if CreateContext function exists                            */
265         if (NULL != ifConf->ifCreateContext)
266         {
267             /* Function exists, run it and fill the context                  */
268             retVal = ifConf->ifCreateContext(ifID, allocName, &((ifNode->netIf).ifContext));
269         }
270 
271         /* Check retVal before continuing                                    */
272         if (SLNETERR_RET_CODE_OK == retVal)
273         {
274             /* After creating and filling the interface, add it to the right
275                place in the list according to its priority                   */
276 
277             /* Check if there isn't any higher priority node                 */
278             if (NULL == prvNode)
279             {
280                 /* there isn't any higher priority node so check if list is
281                    empty                                                     */
282                 if (NULL != SlNetIf_listHead)
283                 {
284                     /* List isn't empty, so use the new allocated interface
285                        as the new head and connect the old list head as the
286                        following node                                        */
287                     ifNode->next = SlNetIf_listHead;
288                 }
289                 else
290                 {
291                     /* List is empty, so the new allocated interface will be
292                        the head list                                         */
293                     ifNode->next = NULL;
294                 }
295                 SlNetIf_listHead = ifNode;
296             }
297             else
298             {
299                 /* Higher priority exists, connect the allocated node after
300                    the prvNode and the next node (if exists) of prvNode to
301                    the next of the node                                      */
302                 ifNode->next  = prvNode->next;
303                 prvNode->next = ifNode;
304             }
305         }
306     }
307 
308     return retVal;
309 }
310 
311 
312 //*****************************************************************************
313 //
314 // SlNetIf_getIfByID - Get interface configuration from interface ID
315 //
316 //*****************************************************************************
SlNetIf_getIfByID(uint16_t ifID)317 SlNetIf_t * SlNetIf_getIfByID(uint16_t ifID)
318 {
319     SlNetIf_Node_t *ifNode = SlNetIf_listHead;
320 
321     /* Check if ifID is a valid input - Only one bit is set (Pow of 2)       */
322     if (false == ONLY_ONE_BIT_IS_SET(ifID))
323     {
324         return NULL;
325     }
326 
327     /* Run over the interface list until finding the required ifID or Until
328        reaching the end of the list                                          */
329     while (NULL != ifNode)
330     {
331         /* Check if the identifier of the interface is equal to the input    */
332         if ((ifNode->netIf).ifID == ifID)
333         {
334             /* Required interface found, return the interface pointer        */
335             return &(ifNode->netIf);
336         }
337         ifNode = ifNode->next;
338     }
339 
340     /* Interface identifier was not found                                    */
341     return NULL;
342 }
343 
344 //*****************************************************************************
345 //
346 // SlNetIf_queryIf - Get interface configuration with the highest priority
347 //                   from the provided interface bitmap
348 //                   Note: ifBitmap - 0 is not a valid input
349 //
350 //*****************************************************************************
SlNetIf_queryIf(uint32_t ifBitmap,uint32_t queryBitmap)351 SlNetIf_t * SlNetIf_queryIf(uint32_t ifBitmap, uint32_t queryBitmap)
352 {
353     SlNetIf_Node_t *ifNode             = SlNetIf_listHead;
354     SlNetIf_t      *bestPartialMatchIf = NULL;
355 
356     if (0 == ifBitmap)
357     {
358         return NULL;
359     }
360 
361     /* Run over the interface list until finding the first ifID that is
362        set in the ifBitmap or Until reaching the end of the list if no
363        ifID were found                                                       */
364     while (NULL != ifNode)
365     {
366         /* Check if the identifier of the interface is equal to the input    */
367         if (((ifNode->netIf).ifID) & ifBitmap)
368         {
369             /* Save the netIf only at the first match                        */
370             if (NULL == bestPartialMatchIf)
371             {
372                 bestPartialMatchIf = &(ifNode->netIf);
373             }
374             /* Skip over Bitmap queries                                      */
375             if ( 0 != queryBitmap)
376             {
377                 /* Check if the state bit needs to be set and if it is       */
378                 if ( (true == IS_STATE_BIT_SET(queryBitmap)) &&
379                      (SLNETIF_STATE_DISABLE == (GET_IF_STATE(ifNode->netIf))) )
380                 {
381                     /* State is disabled when needed to be set, continue
382                        to the next interface                                 */
383                     ifNode = ifNode->next;
384                     continue;
385                 }
386                 /* Check if the connection status bit needs to be set
387                    and if it is                                              */
388                 if ( (true == IS_CONNECTION_STATUS_BIT_SET(queryBitmap)) &&
389                      (SLNETIF_STATUS_CONNECTED != SlNetIf_getConnectionStatus((ifNode->netIf).ifID)) )
390                 {
391                     /* Connection status is not connected when it needed to
392                        be - continue to the next interface                    */
393                     ifNode = ifNode->next;
394                     continue;
395                 }
396             }
397             /* Required interface found, return the interface pointer        */
398             return &(ifNode->netIf);
399         }
400         ifNode = ifNode->next;
401     }
402 
403     /* When bit is set, return the last interface found if there isn't
404        an existing interface that answers the query return the last
405        netIf that was found                                                  */
406     if (true == IS_ALLOW_PARTIAL_MATCH_BIT_SET(queryBitmap))
407     {
408         return bestPartialMatchIf;
409     }
410     else
411     {
412         return NULL;
413     }
414 
415 }
416 
417 
418 //*****************************************************************************
419 //
420 // SlNetIf_getNameByID - Get interface Name from interface ID
421 //
422 //*****************************************************************************
SlNetIf_getNameByID(uint16_t ifID)423 const char * SlNetIf_getNameByID(uint16_t ifID)
424 {
425     SlNetIf_t *netIf;
426 
427     /* Run validity check and find the requested interface                   */
428     netIf = SlNetIf_getIfByID(ifID);
429 
430     /* Check if the requested interface exists or the function returned NULL */
431     if (NULL == netIf)
432     {
433         /* Interface doesn't exists or invalid input, return NULL            */
434         return NULL;
435     }
436     else
437     {
438         /* Interface exists, return the interface name                       */
439         return netIf->ifName;
440     }
441 }
442 
443 
444 //*****************************************************************************
445 //
446 // SlNetIf_getIDByName - Get interface ID from interface name
447 //
448 //*****************************************************************************
SlNetIf_getIDByName(char * ifName)449 int32_t SlNetIf_getIDByName(char *ifName)
450 {
451     SlNetIf_Node_t *ifNode = SlNetIf_listHead;
452 
453     /* Check if ifName is a valid input                                      */
454     if (NULL == ifName)
455     {
456         return(SLNETERR_RET_CODE_INVALID_INPUT);
457     }
458 
459     /* Run over the interface list until finding the required ifID or Until
460        reaching the end of the list                                          */
461     while (NULL != ifNode)
462     {
463         /* Check if the identifier of the interface is equal to the input    */
464         if (strcmp((ifNode->netIf).ifName, ifName) == 0)
465         {
466             /* Required interface found, return the interface identifier     */
467             return ((ifNode->netIf).ifID);
468         }
469         ifNode = ifNode->next;
470     }
471 
472     /* Interface identifier was not found, return error code                 */
473     return(SLNETERR_RET_CODE_INVALID_INPUT);
474 }
475 
476 
477 //*****************************************************************************
478 //
479 // SlNetIf_getPriority - Get interface priority
480 //
481 //*****************************************************************************
SlNetIf_getPriority(uint16_t ifID)482 int32_t SlNetIf_getPriority(uint16_t ifID)
483 {
484     SlNetIf_t *netIf;
485 
486     /* Run validity check and find the requested interface                   */
487     netIf = SlNetIf_getIfByID(ifID);
488 
489     /* Check if the requested interface exists or the function returned NULL */
490     if (NULL == netIf)
491     {
492         /* Interface doesn't exists or invalid input, return error code      */
493         return SLNETERR_RET_CODE_INVALID_INPUT;
494     }
495     else
496     {
497         /* Interface exists, return interface priority                       */
498         return GET_IF_PRIORITY(*netIf);
499     }
500 }
501 
502 
503 //*****************************************************************************
504 //
505 // SlNetIf_setPriority - Set interface priority
506 //
507 //*****************************************************************************
SlNetIf_setPriority(uint16_t ifID,uint8_t priority)508 int32_t SlNetIf_setPriority(uint16_t ifID, uint8_t priority)
509 {
510     SlNetIf_Node_t *ifListNode        = SlNetIf_listHead;
511     SlNetIf_Node_t *prvIfListNode     = SlNetIf_listHead;
512     SlNetIf_Node_t *reqIfListNode     = NULL;
513     bool            connectAgain      = false;
514 
515     if (priority > SLNETIF_MAX_PRIORITY)
516     {
517         /* Run validity check and find the requested interface               */
518         return SLNETERR_RET_CODE_INVALID_INPUT;
519     }
520 
521     /* Find the location of required interface                               */
522     while (NULL != ifListNode)
523     {
524         /* If the location of the required interface found, store the
525            location                                                          */
526         if ((ifListNode->netIf.ifID) == ifID)
527         {
528             reqIfListNode = ifListNode;
529             /* Check if the required interface is the last node and needs
530                lower priority than the previous node, only update of the
531                priority is required for this node                            */
532             if (NULL == ifListNode->next)
533             {
534                 if (GET_IF_PRIORITY(prvIfListNode->netIf) >= priority)
535                 {
536                     /* The required interface is the last node and needs
537                        lower priority than the previous node, only update
538                        of the priority is required for this node             */
539                     break;
540                 }
541                 else
542                 {
543                     /* The required interface is the last node but has
544                        higher priority than the previous node, disconnect
545                        the interface from the list. connect the previous node
546                        to the end of the list
547                        If this is not the only node in the list, find where
548                        it now belongs based on its new priority.            */
549                     if (reqIfListNode != SlNetIf_listHead)
550                     {
551                         prvIfListNode->next = NULL;
552                         connectAgain = true;
553                         /* This is the end of the list, so stop looping      */
554                         break;
555                     }
556                 }
557             }
558             /* Check if the required interface is the first node in the list */
559             else if (SlNetIf_listHead == ifListNode)
560             {
561                 if ( (NULL == ifListNode->next) || ((GET_IF_PRIORITY(ifListNode->next->netIf)) <= priority) )
562                 {
563                     /* The required interface is the first node and needs
564                        higher priority than the following node, only update
565                        of the priority is required for this node             */
566                     break;
567                 }
568                 /* The required interface is the first node but doesn't need
569                    higher priority than the following node so the following
570                    node will be the first node of the list                   */
571                 else
572                 {
573                     SlNetIf_listHead = ifListNode->next;
574                     connectAgain = true;
575                 }
576             }
577             /* The required interface isn't the first or last node and needs
578                priority change but is in the correct location, only update
579                of the priority is required for this node                     */
580             else if ( (GET_IF_PRIORITY(prvIfListNode->netIf) >= priority) && ((GET_IF_PRIORITY(ifListNode->next->netIf)) <= priority) )
581             {
582                 break;
583             }
584             /* The required interface isn't the first or last node and needs
585                priority change, disconnect it from the list. connect the
586                previous node with the following node                         */
587             else
588             {
589                 prvIfListNode->next = prvIfListNode->next->next;
590                 connectAgain = true;
591             }
592         }
593         else
594         {
595             prvIfListNode = ifListNode;
596         }
597         ifListNode = ifListNode->next;
598     }
599 
600     /* When connectAgain is set, there's a need to find where to add back
601        the required interface according to the priority                      */
602     if (connectAgain == true)
603     {
604         ifListNode = SlNetIf_listHead;
605         while (NULL != ifListNode)
606         {
607             /* If the incoming priority is higher than any present           */
608             if (ifListNode == SlNetIf_listHead)
609             {
610                 if ((GET_IF_PRIORITY(ifListNode->netIf)) <= priority)
611                 {
612                     reqIfListNode->next = ifListNode;
613                     SlNetIf_listHead = reqIfListNode;
614                     break;
615                 }
616             }
617 
618             /* Check if the priority of the current interface is higher of
619                the required priority, if so, store it as the previous
620                interface and continue to search until finding interface with
621                lower priority and than connect the required interface to the
622                prior interface                                               */
623             if ((GET_IF_PRIORITY(ifListNode->netIf)) > priority)
624             {
625                 prvIfListNode = ifListNode;
626 
627             }
628             else
629             {
630                 reqIfListNode->next = prvIfListNode->next;
631                 prvIfListNode->next = reqIfListNode;
632                 break;
633             }
634             ifListNode = ifListNode->next;
635 
636             if (NULL == ifListNode)
637             {
638                 /* All interfaces have higher priorities than reqIfListNode  */
639                 prvIfListNode->next = reqIfListNode;
640                 reqIfListNode->next = NULL;
641                 break;
642             }
643         }
644     }
645 
646     if (NULL != reqIfListNode)
647     {
648         /* Interface exists, set the interface priority                          */
649         RESET_IF_PRIORITY(reqIfListNode->netIf);
650         SET_IF_PRIORITY(reqIfListNode->netIf, priority);
651     }
652 
653     return SLNETERR_RET_CODE_OK;
654 }
655 
656 
657 //*****************************************************************************
658 //
659 // SlNetIf_setState - Set interface state
660 //
661 //*****************************************************************************
SlNetIf_setState(uint16_t ifID,SlNetIfState_e ifState)662 int32_t SlNetIf_setState(uint16_t ifID, SlNetIfState_e ifState)
663 {
664     SlNetIf_t *netIf;
665 
666     /* Run validity check and find the requested interface                   */
667     netIf = SlNetIf_getIfByID(ifID);
668 
669     /* Check if the requested interface exists or the function returned NULL */
670     if (NULL == netIf)
671     {
672         /* Interface doesn't exists or invalid input, return error code      */
673         return SLNETERR_RET_CODE_INVALID_INPUT;
674     }
675     else
676     {
677         /* Interface exists, set the interface state                         */
678         if (ifState == SLNETIF_STATE_DISABLE)
679         {
680             /* Interface state - Disable                                     */
681             SET_IF_STATE_DISABLE(*netIf);
682         }
683         else
684         {
685             /* Interface state - Enable                                      */
686             SET_IF_STATE_ENABLE(*netIf);
687         }
688     }
689     return SLNETERR_RET_CODE_OK;
690 }
691 
692 
693 //*****************************************************************************
694 //
695 // SlNetIf_getState - Get interface state
696 //
697 //*****************************************************************************
SlNetIf_getState(uint16_t ifID)698 int32_t SlNetIf_getState(uint16_t ifID)
699 {
700     SlNetIf_t *netIf;
701 
702     /* Run validity check and find the requested interface                   */
703     netIf = SlNetIf_getIfByID(ifID);
704 
705     /* Check if the requested interface exists or the function returned NULL */
706     if (NULL == netIf)
707     {
708         /* Interface doesn't exists or invalid input, return error code      */
709         return SLNETERR_RET_CODE_INVALID_INPUT;
710     }
711     else
712     {
713         /* Interface exists, return interface state                          */
714         return GET_IF_STATE(*netIf);
715     }
716 }
717 
718 
719 //*****************************************************************************
720 //
721 // SlNetIf_getIPAddr - Get IP Address of specific interface
722 //
723 //*****************************************************************************
SlNetIf_getIPAddr(uint16_t ifID,SlNetIfAddressType_e addrType,uint16_t * addrConfig,uint32_t * ipAddr)724 int32_t SlNetIf_getIPAddr(uint16_t ifID, SlNetIfAddressType_e addrType, uint16_t *addrConfig, uint32_t *ipAddr)
725 {
726     SlNetIf_t *netIf;
727     int32_t    retVal;
728 
729     /* Run validity check and find the requested interface                   */
730     netIf = SlNetIf_getIfByID(ifID);
731 
732     /* Check if the requested interface exists or the function returned NULL */
733     if (NULL == netIf)
734     {
735         /* Interface doesn't exists or invalid input, return NULL            */
736         return SLNETERR_RET_CODE_INVALID_INPUT;
737     }
738     else
739     {
740         /* Interface exists, return interface IP address                     */
741         retVal = (netIf->ifConf)->ifGetIPAddr(netIf->ifContext, addrType, addrConfig, ipAddr);
742         SLNETIF_NORMALIZE_RET_VAL(retVal,SLNETIF_ERR_IFGETIPADDR_FAILED);
743 
744         /* Check retVal for error codes                                      */
745         if (retVal < SLNETERR_RET_CODE_OK)
746         {
747             /* Return retVal, function error                                 */
748             return retVal;
749         }
750         else
751         {
752             /* Return success                                                */
753             return SLNETERR_RET_CODE_OK;
754         }
755     }
756 }
757 
758 
759 //*****************************************************************************
760 //
761 // SlNetIf_getConnectionStatus - Get interface connection status
762 //
763 //*****************************************************************************
SlNetIf_getConnectionStatus(uint16_t ifID)764 int32_t SlNetIf_getConnectionStatus(uint16_t ifID)
765 {
766     SlNetIf_t *netIf;
767     int16_t    connectionStatus;
768 
769     /* Run validity check and find the requested interface                   */
770     netIf = SlNetIf_getIfByID(ifID);
771 
772     /* Check if the requested interface exists or the function returned NULL */
773     if (NULL == netIf)
774     {
775         /* Interface doesn't exists or invalid input, return NULL            */
776         return SLNETERR_RET_CODE_INVALID_INPUT;
777     }
778     else
779     {
780         /* Interface exists, return interface connection status              */
781         connectionStatus = (netIf->ifConf)->ifGetConnectionStatus(netIf->ifContext);
782 
783         /* Interface exists, set the interface state                         */
784         if (connectionStatus == SLNETIF_STATUS_DISCONNECTED)
785         {
786             /* Interface is disconnected                                     */
787             return SLNETIF_STATUS_DISCONNECTED;
788         }
789         else if (connectionStatus > SLNETIF_STATUS_DISCONNECTED)
790         {
791             SLNETIF_NORMALIZE_RET_VAL(connectionStatus,SLNETIF_STATUS_CONNECTED);
792         }
793         else
794         {
795             SLNETIF_NORMALIZE_RET_VAL(connectionStatus,SLNETIF_ERR_IFGETCONNECTIONSTATUS_FAILED);
796         }
797         return connectionStatus;
798     }
799 }
800 
801 
802 //*****************************************************************************
803 //
804 // SlNetIf_loadSecObj - Load secured buffer to the network stack
805 //
806 //*****************************************************************************
SlNetIf_loadSecObj(uint16_t objType,char * objName,int16_t objNameLen,uint8_t * objBuff,int16_t objBuffLen,uint32_t ifBitmap)807 int32_t SlNetIf_loadSecObj(uint16_t objType, char *objName, int16_t objNameLen, uint8_t *objBuff, int16_t objBuffLen, uint32_t ifBitmap)
808 {
809     SlNetIf_t *netIf;
810     int32_t    retVal;
811     uint32_t   ifIDIndex = 1;  /* Set value to highest bit in uint32_t       */
812     uint32_t   maxIDIndex = (uint32_t)1 << SLNETIF_MAX_IF;
813 
814     /* validate params */
815     if ((objName == NULL) || (strlen(objName) != objNameLen) ||
816             ((objType != SLNETIF_SEC_OBJ_TYPE_RSA_PRIVATE_KEY) &&
817                 (objType != SLNETIF_SEC_OBJ_TYPE_CERTIFICATE) &&
818                 (objType != SLNETIF_SEC_OBJ_TYPE_DH_KEY)))
819     {
820         return SLNETERR_RET_CODE_INVALID_INPUT;
821     }
822 
823     /* bitmap 0 entered, load sec obj to all available interfaces            */
824     if (0 == ifBitmap)
825     {
826         ifBitmap = ~ifBitmap;
827     }
828 
829     while ( ifIDIndex < maxIDIndex )
830     {
831         /* Check if ifIDIndex is a required ifID from the ifBitmap           */
832         if ( ifIDIndex & ifBitmap )
833         {
834             /* Run validity check and find the requested interface           */
835             netIf = SlNetIf_getIfByID(ifIDIndex & ifBitmap);
836 
837             /* Check if the requested interface exists or the function
838                returned NULL                                                 */
839             if ( (NULL != netIf) && (NULL != (netIf->ifConf)->ifLoadSecObj) )
840             {
841                 /* Interface exists, return interface IP address             */
842                 retVal = (netIf->ifConf)->ifLoadSecObj(netIf->ifContext, objType, objName, objNameLen, objBuff, objBuffLen);
843                 SLNETIF_NORMALIZE_RET_VAL(retVal,SLNETIF_ERR_IFLOADSECOBJ_FAILED);
844 
845                 /* Check retVal for error codes                              */
846                 if (retVal < SLNETERR_RET_CODE_OK)
847                 {
848                     /* Return retVal, function error                         */
849                     return retVal;
850                 }
851                 else
852                 {
853                     /* Return success                                        */
854                     return SLNETERR_RET_CODE_OK;
855                 }
856             }
857         }
858         ifIDIndex <<= 1;
859     }
860     /* Interface doesn't exists or invalid input, return error code          */
861     return SLNETERR_RET_CODE_INVALID_INPUT;
862 }
863