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 /** USBX Component */
17 /** */
18 /** Device Stack */
19 /** */
20 /**************************************************************************/
21 /**************************************************************************/
22
23 #define UX_SOURCE_CODE
24
25
26 /* Include necessary system files. */
27
28 #include "ux_api.h"
29 #include "ux_device_stack.h"
30
31
32 /**************************************************************************/
33 /* */
34 /* FUNCTION RELEASE */
35 /* */
36 /* _ux_device_stack_clear_feature PORTABLE C */
37 /* 6.1.12 */
38 /* AUTHOR */
39 /* */
40 /* Chaoqiong Xiao, Microsoft Corporation */
41 /* */
42 /* DESCRIPTION */
43 /* */
44 /* This function clears a specific feature (Device, Interface, */
45 /* Endpoint ....). */
46 /* */
47 /* INPUT */
48 /* */
49 /* request_type Request type */
50 /* request_value Request value */
51 /* request_index Request index */
52 /* */
53 /* OUTPUT */
54 /* */
55 /* Completion Status */
56 /* */
57 /* CALLS */
58 /* */
59 /* (ux_slave_dcd_function) DCD dispatch function */
60 /* */
61 /* CALLED BY */
62 /* */
63 /* Device Stack */
64 /* */
65 /* RELEASE HISTORY */
66 /* */
67 /* DATE NAME DESCRIPTION */
68 /* */
69 /* 05-19-2020 Chaoqiong Xiao Initial Version 6.0 */
70 /* 09-30-2020 Chaoqiong Xiao Modified comment(s), */
71 /* optimized based on compile */
72 /* definitions, */
73 /* resulting in version 6.1 */
74 /* 07-29-2022 Chaoqiong Xiao Modified comment(s), */
75 /* fixed parameter/variable */
76 /* names conflict C++ keyword, */
77 /* resulting in version 6.1.12 */
78 /* */
79 /**************************************************************************/
_ux_device_stack_clear_feature(ULONG request_type,ULONG request_value,ULONG request_index)80 UINT _ux_device_stack_clear_feature(ULONG request_type, ULONG request_value, ULONG request_index)
81 {
82
83 UX_SLAVE_DCD *dcd;
84 UX_SLAVE_DEVICE *device;
85 UX_SLAVE_INTERFACE *interface_ptr;
86 UX_SLAVE_ENDPOINT *endpoint;
87 UX_SLAVE_ENDPOINT *endpoint_target;
88
89 UX_PARAMETER_NOT_USED(request_value);
90
91 /* If trace is enabled, insert this event into the trace buffer. */
92 UX_TRACE_IN_LINE_INSERT(UX_TRACE_DEVICE_STACK_CLEAR_FEATURE, request_type, request_value, request_index, 0, UX_TRACE_DEVICE_STACK_EVENTS, 0, 0)
93
94 /* Get the pointer to the DCD. */
95 dcd = &_ux_system_slave -> ux_system_slave_dcd;
96
97 /* Get the pointer to the device. */
98 device = &_ux_system_slave -> ux_system_slave_device;
99
100 /* Get the control endpoint for the device. */
101 endpoint = &device -> ux_slave_device_control_endpoint;
102
103 /* The request can be for either the device or the endpoint. */
104 switch (request_type & UX_REQUEST_TARGET)
105 {
106
107 case UX_REQUEST_TARGET_DEVICE:
108
109 /* Check if we have a DEVICE_REMOTE_WAKEUP Feature. */
110 if (request_value == UX_REQUEST_FEATURE_DEVICE_REMOTE_WAKEUP)
111 {
112
113 /* Check if we have the capability. */
114 if (_ux_system_slave -> ux_system_slave_remote_wakeup_capability)
115 {
116
117 /* Disable the feature. */
118 _ux_system_slave -> ux_system_slave_remote_wakeup_enabled = UX_FALSE;
119 }
120
121 else
122
123 /* Protocol error. */
124 return (UX_FUNCTION_NOT_SUPPORTED);
125 }
126
127 break;
128
129 case UX_REQUEST_TARGET_ENDPOINT:
130
131 /* The only clear feature for endpoint is ENDPOINT_STALL. This clears
132 the endpoint of the stall situation and resets its data toggle.
133 We need to find the endpoint through the interface(s). */
134 interface_ptr = device -> ux_slave_device_first_interface;
135
136 #if !defined(UX_DEVICE_INITIALIZE_FRAMEWORK_SCAN_DISABLE) || UX_MAX_DEVICE_INTERFACES > 1
137 while (interface_ptr != UX_NULL)
138 {
139 #endif
140
141 /* Get the first endpoint for this interface. */
142 endpoint_target = interface_ptr -> ux_slave_interface_first_endpoint;
143
144 /* Parse all the endpoints. */
145 while (endpoint_target != UX_NULL)
146 {
147
148 /* Check the endpoint index. */
149 if (endpoint_target -> ux_slave_endpoint_descriptor.bEndpointAddress == request_index)
150 {
151
152 /* Reset the endpoint. */
153 dcd -> ux_slave_dcd_function(dcd, UX_DCD_RESET_ENDPOINT, endpoint_target);
154
155 /* Mark its state now. */
156 endpoint_target -> ux_slave_endpoint_state = UX_ENDPOINT_RESET;
157
158 /* Return the function status. */
159 return(UX_SUCCESS);
160 }
161
162 /* Next endpoint. */
163 endpoint_target = endpoint_target -> ux_slave_endpoint_next_endpoint;
164 }
165
166 #if !defined(UX_DEVICE_INITIALIZE_FRAMEWORK_SCAN_DISABLE) || UX_MAX_DEVICE_INTERFACES > 1
167 /* Next interface. */
168 interface_ptr = interface_ptr -> ux_slave_interface_next_interface;
169 }
170 #endif
171
172 /* Intentional fallthrough and go into the default case. */
173 /* fall through */
174
175 /* We get here when the endpoint is wrong. Should not happen though. */
176 default:
177
178 /* We stall the command. */
179 dcd -> ux_slave_dcd_function(dcd, UX_DCD_STALL_ENDPOINT, endpoint);
180
181 /* No more work to do here. The command failed but the upper layer does not depend on it. */
182 return(UX_SUCCESS);
183 }
184
185 /* Return the function status. */
186 return(UX_SUCCESS);
187 }
188
189