1 /**************************************************************************/
2 /*                                                                        */
3 /*       Copyright (c) Microsoft Corporation. All rights reserved.        */
4 /*                                                                        */
5 /*       This software is licensed under the Microsoft Software License   */
6 /*       Terms for Microsoft Azure RTOS. Full text of the license can be  */
7 /*       found in the LICENSE file at https://aka.ms/AzureRTOS_EULA       */
8 /*       and in the root directory of this software.                      */
9 /*                                                                        */
10 /**************************************************************************/
11 
12 
13 /**************************************************************************/
14 /**************************************************************************/
15 /**                                                                       */
16 /** NetX Component                                                        */
17 /**                                                                       */
18 /**   Internet Protocol (IP)                                              */
19 /**                                                                       */
20 /**************************************************************************/
21 /**************************************************************************/
22 
23 #define NX_SOURCE_CODE
24 
25 
26 /* Include necessary system files.  */
27 
28 #include "nx_api.h"
29 #include "nx_ipv6.h"
30 
31 #ifdef FEATURE_NX_IPV6
32 #include "nx_ip.h"
33 #include "nx_nd_cache.h"
34 #include "nx_icmpv6.h"
35 #endif /* FEATURE_NX_IPV6 */
36 
37 /**************************************************************************/
38 /*                                                                        */
39 /*  FUNCTION                                               RELEASE        */
40 /*                                                                        */
41 /*    _nxd_ipv6_enable                                    PORTABLE C      */
42 /*                                                           6.1          */
43 /*  AUTHOR                                                                */
44 /*                                                                        */
45 /*    Yuxin Zhou, Microsoft Corporation                                   */
46 /*                                                                        */
47 /*  DESCRIPTION                                                           */
48 /*                                                                        */
49 /*    This function enables the IPv6 for the specified IP instance.       */
50 /*                                                                        */
51 /*  INPUT                                                                 */
52 /*                                                                        */
53 /*    ip_ptr                                IP instance pointer           */
54 /*                                                                        */
55 /*  OUTPUT                                                                */
56 /*                                                                        */
57 /*    status                                Completion status             */
58 /*                                                                        */
59 /*  CALLS                                                                 */
60 /*                                                                        */
61 /*    _nx_ipv6_multicast_join               Join the multicast group      */
62 /*    _nxd_ipv6_default_router_table_init   Initialize IPv6 routing table */
63 /*    _nx_ip_fast_periodic_timer_create     Create timer for IPv6 events  */
64 /*    tx_mutex_get                          Obtain a protection mutex     */
65 /*    tx_mutex_put                          Release protection mutex      */
66 /*                                                                        */
67 /*  CALLED BY                                                             */
68 /*                                                                        */
69 /*    Application Code                                                    */
70 /*                                                                        */
71 /*  RELEASE HISTORY                                                       */
72 /*                                                                        */
73 /*    DATE              NAME                      DESCRIPTION             */
74 /*                                                                        */
75 /*  05-19-2020     Yuxin Zhou               Initial Version 6.0           */
76 /*  09-30-2020     Yuxin Zhou               Modified comment(s),          */
77 /*                                            resulting in version 6.1    */
78 /*                                                                        */
79 /**************************************************************************/
_nxd_ipv6_enable(NX_IP * ip_ptr)80 UINT  _nxd_ipv6_enable(NX_IP *ip_ptr)
81 {
82 
83 
84 #ifdef FEATURE_NX_IPV6
85 
86 TX_INTERRUPT_SAVE_AREA
87 UINT  i;
88 #ifndef NX_DISABLE_ICMPV6_ROUTER_SOLICITATION
89 ULONG address[4];
90 #endif /* NX_DISABLE_ICMPV6_ROUTER_SOLICITATION */
91 
92 
93     /* Make sure IPv6 is not already enabled. */
94     if (ip_ptr -> nx_ipv6_packet_receive)
95     {
96         return(NX_ALREADY_ENABLED);
97     }
98 
99     /* If trace is enabled, insert this event into the trace buffer.  */
100     NX_TRACE_IN_LINE_INSERT(NX_TRACE_IPV6_ENABLE, ip_ptr, 0, 0, 0, NX_TRACE_IP_EVENTS, 0, 0);
101 
102 
103     /* Obtain the IP mutex so we can manipulate the internal routing table. */
104     tx_mutex_get(&(ip_ptr -> nx_ip_protection), TX_WAIT_FOREVER);
105 
106     /* Disable Interrupt */
107     TX_DISABLE
108 
109     /* Install IPv6 packet receive processing function pointer */
110     ip_ptr -> nx_ipv6_packet_receive = _nx_ipv6_packet_receive;
111 
112     /* Enable Interrupt */
113     TX_RESTORE
114 
115     /* Initialize IPv6 default router table */
116     _nxd_ipv6_default_router_table_init(ip_ptr);
117 
118     /* Set the default reachable timer. */
119     ip_ptr -> nx_ipv6_reachable_timer = NX_REACHABLE_TIME;
120 
121     /*
122        Set the default retrans timer. The retrans timer value is
123        expressed in millisecond.  To compute the timer ticks, first
124        covert the retrans timer to second and then multiply
125        the system_ticks_per_second value, or multiply system_ticks_per_second
126        before doing division.
127        If the retrans_timer is smaller than tick resolution, set it to 1.
128      */
129 #if ((NX_RETRANS_TIMER * NX_IP_FAST_TIMER_RATE) > 1000)
130     ip_ptr -> nx_ipv6_retrans_timer_ticks = (NX_RETRANS_TIMER * NX_IP_FAST_TIMER_RATE) / 1000;
131 #else
132     ip_ptr -> nx_ipv6_retrans_timer_ticks = 1;
133 #endif
134 
135     /* Set the default hop limit. */
136     ip_ptr -> nx_ipv6_hop_limit = 0xFF;
137 
138     /* Set index of each address. */
139     for (i = 0; i < (NX_MAX_IPV6_ADDRESSES + NX_LOOPBACK_IPV6_ENABLED); i++)
140     {
141         ip_ptr -> nx_ipv6_address[i].nxd_ipv6_address_index = (UCHAR)i;
142     }
143 
144     /* Check if router solicitation is not disabled. */
145 #ifndef NX_DISABLE_ICMPV6_ROUTER_SOLICITATION
146 
147     /* Create the all-node multicast group address, */
148     address[0] = 0xFF020000;
149     address[1] = 0;
150     address[2] = 0;
151     address[3] = 1;
152 
153     /* Initializes the router solicitation values . */
154     for (i = 0; i < NX_MAX_PHYSICAL_INTERFACES; i++)
155     {
156         if (ip_ptr -> nx_ip_interface[i].nx_interface_valid == NX_TRUE)
157         {
158             ip_ptr -> nx_ip_interface[i].nx_ipv6_rtr_solicitation_max = NX_ICMPV6_MAX_RTR_SOLICITATIONS;
159             ip_ptr -> nx_ip_interface[i].nx_ipv6_rtr_solicitation_count = ip_ptr -> nx_ip_interface[i].nx_ipv6_rtr_solicitation_max;
160             ip_ptr -> nx_ip_interface[i].nx_ipv6_rtr_solicitation_interval = NX_ICMPV6_RTR_SOLICITATION_INTERVAL;
161             ip_ptr -> nx_ip_interface[i].nx_ipv6_rtr_solicitation_timer = NX_ICMPV6_RTR_SOLICITATION_DELAY;
162 
163             /* Join all-node multicast group. */
164             _nx_ipv6_multicast_join(ip_ptr, address, &ip_ptr -> nx_ip_interface[i]);
165         }
166     }
167 #endif /* NX_DISABLE_ICMPV6_ROUTER_SOLICITATION */
168 
169     /* Start a faster periodic timer for IPv6 .*/
170     _nx_ip_fast_periodic_timer_create(ip_ptr);
171 
172 #ifndef NX_DISABLE_LOOPBACK_INTERFACE
173 
174     /* Setup loop back address. */
175     /* Page 9, section 2.5.3, RFC 4291. */
176     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address[0] = 0x0;
177     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address[1] = 0x0;
178     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address[2] = 0x0;
179     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address[3] = 0x1;
180 
181     /* Config loop bcak address. */
182     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address_valid = NX_TRUE;
183     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address_type = NX_IP_VERSION_V6;
184     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address_prefix_length = 128;
185     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address_next = NX_NULL;
186     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address_attached = &ip_ptr -> nx_ip_interface[NX_LOOPBACK_INTERFACE];
187     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address_ConfigurationMethod = NX_IPV6_ADDRESS_MANUAL_CONFIG;
188     ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX].nxd_ipv6_address_state = NX_IPV6_ADDR_STATE_VALID;
189 
190     ip_ptr -> nx_ip_interface[NX_LOOPBACK_INTERFACE].nxd_interface_ipv6_address_list_head = &ip_ptr -> nx_ipv6_address[NX_LOOPBACK_IPV6_SOURCE_INDEX];
191 #endif /* NX_DISABLE_LOOPBACK_INTERFACE */
192 
193     /* Release the IP protection. */
194     tx_mutex_put(&(ip_ptr -> nx_ip_protection));
195 
196     /* Return successful completion.  */
197     return(NX_SUCCESS);
198 
199 #else /* !FEATURE_NX_IPV6 */
200     NX_PARAMETER_NOT_USED(ip_ptr);
201 
202     return(NX_NOT_SUPPORTED);
203 
204 #endif /* FEATURE_NX_IPV6 */
205 }
206 
207