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 /** */
15 /** NetX Component */
16 /** */
17 /** Internet Protocol (IP) */
18 /** */
19 /**************************************************************************/
20 /**************************************************************************/
21
22 #define NX_SOURCE_CODE
23
24
25 /* Include necessary system files. */
26
27 #include "nx_api.h"
28 #include "nx_ip.h"
29 #include "nx_packet.h"
30
31
32
33 /**************************************************************************/
34 /* */
35 /* FUNCTION RELEASE */
36 /* */
37 /* _nx_ip_fragment_disable PORTABLE C */
38 /* 6.1 */
39 /* AUTHOR */
40 /* */
41 /* Yuxin Zhou, Microsoft Corporation */
42 /* */
43 /* DESCRIPTION */
44 /* */
45 /* This function disables IP fragment assembly processing and releases */
46 /* all partial fragments being assembled. */
47 /* */
48 /* INPUT */
49 /* */
50 /* ip_ptr Pointer to IP instance */
51 /* */
52 /* OUTPUT */
53 /* */
54 /* status Completion status */
55 /* */
56 /* CALLS */
57 /* */
58 /* _nx_packet_release Release packet */
59 /* tx_mutex_get Get protection mutex */
60 /* tx_mutex_put Put protection mutex */
61 /* */
62 /* CALLED BY */
63 /* */
64 /* Application */
65 /* */
66 /* RELEASE HISTORY */
67 /* */
68 /* DATE NAME DESCRIPTION */
69 /* */
70 /* 05-19-2020 Yuxin Zhou Initial Version 6.0 */
71 /* 09-30-2020 Yuxin Zhou Modified comment(s), */
72 /* resulting in version 6.1 */
73 /* */
74 /**************************************************************************/
_nx_ip_fragment_disable(NX_IP * ip_ptr)75 UINT _nx_ip_fragment_disable(NX_IP *ip_ptr)
76 {
77 #ifndef NX_DISABLE_FRAGMENTATION
78 TX_INTERRUPT_SAVE_AREA
79
80 #ifndef NX_FRAGMENT_IMMEDIATE_ASSEMBLY
81 NX_PACKET *new_fragment_head;
82 #endif /* NX_FRAGMENT_IMMEDIATE_ASSEMBLY */
83 NX_PACKET *assemble_head;
84 NX_PACKET *next_packet;
85 NX_PACKET *release_packet;
86
87
88 /* If trace is enabled, insert this event into the trace buffer. */
89 NX_TRACE_IN_LINE_INSERT(NX_TRACE_IP_FRAGMENT_DISABLE, ip_ptr, 0, 0, 0, NX_TRACE_IP_EVENTS, 0, 0);
90
91 /* Get mutex protection. */
92 tx_mutex_get(&(ip_ptr -> nx_ip_protection), TX_WAIT_FOREVER);
93
94 /* Disable interrupts temporarily. */
95 TX_DISABLE
96
97 /* Clear the IP fragment processing routine pointer. */
98 ip_ptr -> nx_ip_fragment_processing = NX_NULL;
99
100 /* Clear the IP fragment assembly routine pointer. */
101 ip_ptr -> nx_ip_fragment_assembly = NX_NULL;
102
103 /* Clear the IP fragment timeout routine pointer. */
104 ip_ptr -> nx_ip_fragment_timeout_check = NX_NULL;
105
106 /* Pickup the fragment list pointer. */
107 #ifndef NX_FRAGMENT_IMMEDIATE_ASSEMBLY
108 new_fragment_head = ip_ptr -> nx_ip_received_fragment_head;
109 #else
110 NX_ASSERT(ip_ptr -> nx_ip_received_fragment_head == NX_NULL);
111 #endif /* NX_FRAGMENT_IMMEDIATE_ASSEMBLY */
112 assemble_head = ip_ptr -> nx_ip_fragment_assembly_head;
113
114 /* Clear the IP structure lists. */
115 ip_ptr -> nx_ip_received_fragment_head = NX_NULL;
116 ip_ptr -> nx_ip_received_fragment_tail = NX_NULL;
117 ip_ptr -> nx_ip_fragment_assembly_head = NX_NULL;
118 ip_ptr -> nx_ip_fragment_assembly_tail = NX_NULL;
119
120 /* Restore interrupts. */
121 TX_RESTORE
122
123 /* Release mutex protection. */
124 tx_mutex_put(&(ip_ptr -> nx_ip_protection));
125
126 #ifndef NX_FRAGMENT_IMMEDIATE_ASSEMBLY
127 /* Now walk through the receive and assembly lists to free the packets. */
128 next_packet = new_fragment_head;
129 while (next_packet)
130 {
131
132 /* Set the release packet to this packet. */
133 release_packet = next_packet;
134
135 /* Move next packet to the next in the list. */
136 next_packet = next_packet -> nx_packet_queue_next;
137
138 /* Release the current packet. */
139 _nx_packet_release(release_packet);
140 }
141 #endif /* NX_FRAGMENT_IMMEDIATE_ASSEMBLY */
142
143 /* Now walk through the assemble list and release all packets. */
144 while (assemble_head)
145 {
146
147 /* Walk through the list of packets being assembled for this packet and release them. */
148 next_packet = assemble_head;
149 assemble_head = next_packet -> nx_packet_queue_next;
150 while (next_packet)
151 {
152
153 /* Set the release packet to this packet. */
154 release_packet = next_packet;
155
156 /* Move next packet to the next in the list. */
157 next_packet = next_packet -> nx_packet_union_next.nx_packet_fragment_next;
158
159 /* Reset tcp_queue_next before releasing. */
160 /*lint -e{923} suppress cast of ULONG to pointer. */
161 release_packet -> nx_packet_union_next.nx_packet_tcp_queue_next = (NX_PACKET *)NX_PACKET_ALLOCATED;
162
163 /* Release the current packet. */
164 _nx_packet_release(release_packet);
165 }
166 }
167
168 /* Return success to the caller. */
169 return(NX_SUCCESS);
170 #else /* NX_DISABLE_FRAGMENTATION */
171 NX_PARAMETER_NOT_USED(ip_ptr);
172
173 return(NX_NOT_ENABLED);
174
175 #endif /* NX_DISABLE_FRAGMENTATION */
176 }
177
178