GCC Code Coverage Report
Directory: ./ Exec Total Coverage
File: usbx_host_classes/src/ux_host_class_hid_idle_get.c Lines: 29 33 87.9 %
Date: 2024-12-12 17:16:36 Branches: 12 16 75.0 %

Line Branch Exec Source
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
/** USBX Component                                                        */
16
/**                                                                       */
17
/**   HID Class                                                           */
18
/**                                                                       */
19
/**************************************************************************/
20
/**************************************************************************/
21
22
23
/* Include necessary system files.  */
24
25
#define UX_SOURCE_CODE
26
27
#include "ux_api.h"
28
#include "ux_host_class_hid.h"
29
#include "ux_host_stack.h"
30
31
32
/**************************************************************************/
33
/*                                                                        */
34
/*  FUNCTION                                               RELEASE        */
35
/*                                                                        */
36
/*    _ux_host_class_hid_idle_get                         PORTABLE C      */
37
/*                                                           6.1.10       */
38
/*  AUTHOR                                                                */
39
/*                                                                        */
40
/*    Chaoqiong Xiao, Microsoft Corporation                               */
41
/*                                                                        */
42
/*  DESCRIPTION                                                           */
43
/*                                                                        */
44
/*    This function performs a GET_IDLE to the HID device.                */
45
/*                                                                        */
46
/*  INPUT                                                                 */
47
/*                                                                        */
48
/*    hid                                   Pointer to HID class          */
49
/*    idle_time                             Idle time                     */
50
/*    report_id                             Report ID                     */
51
/*                                                                        */
52
/*  OUTPUT                                                                */
53
/*                                                                        */
54
/*    Completion Status                                                   */
55
/*                                                                        */
56
/*  CALLS                                                                 */
57
/*                                                                        */
58
/*    _ux_host_stack_class_instance_verify  Verify instance is valid      */
59
/*    _ux_host_stack_transfer_request       Process transfer request      */
60
/*    _ux_host_semaphore_get                Get protection semaphore      */
61
/*    _ux_host_semaphore_put                Release protection semaphore  */
62
/*                                                                        */
63
/*  CALLED BY                                                             */
64
/*                                                                        */
65
/*    HID Class                                                           */
66
/*                                                                        */
67
/*  RELEASE HISTORY                                                       */
68
/*                                                                        */
69
/*    DATE              NAME                      DESCRIPTION             */
70
/*                                                                        */
71
/*  05-19-2020     Chaoqiong Xiao           Initial Version 6.0           */
72
/*  09-30-2020     Chaoqiong Xiao           Modified comment(s),          */
73
/*                                            protected default control   */
74
/*                                            endpoint before using it,   */
75
/*                                            resulting in version 6.1    */
76
/*  01-31-2022     Chaoqiong Xiao           Modified comment(s),          */
77
/*                                            added standalone support,   */
78
/*                                            resulting in version 6.1.10 */
79
/*                                                                        */
80
/**************************************************************************/
81
12
UINT  _ux_host_class_hid_idle_get(UX_HOST_CLASS_HID *hid, USHORT *idle_time, USHORT report_id)
82
{
83
#if defined(UX_HOST_STANDALONE)
84
UX_INTERRUPT_SAVE_AREA
85
#endif
86
UX_ENDPOINT     *control_endpoint;
87
UX_TRANSFER     *transfer_request;
88
UCHAR           *idle_byte;
89
UINT            status;
90
91
    /* If trace is enabled, insert this event into the trace buffer.  */
92
    UX_TRACE_IN_LINE_INSERT(UX_TRACE_HOST_CLASS_HID_IDLE_GET, hid, 0, 0, 0, UX_TRACE_HOST_CLASS_EVENTS, 0, 0)
93
94
    /* Ensure the instance is valid.  */
95
12
    if (_ux_host_stack_class_instance_verify(_ux_system_host_class_hid_name, (VOID *) hid) != UX_SUCCESS)
96
    {
97
98
        /* If trace is enabled, insert this event into the trace buffer.  */
99
        UX_TRACE_IN_LINE_INSERT(UX_TRACE_ERROR, UX_HOST_CLASS_INSTANCE_UNKNOWN, hid, 0, 0, UX_TRACE_ERRORS, 0, 0)
100
101
1
        return(UX_HOST_CLASS_INSTANCE_UNKNOWN);
102
    }
103
104
    /* We need to get the default control endpoint transfer request pointer.  */
105
11
    control_endpoint =  &hid -> ux_host_class_hid_device -> ux_device_control_endpoint;
106
11
    transfer_request =  &control_endpoint -> ux_endpoint_transfer_request;
107
108
    /* Protect thread reentry to this instance.  */
109
#if defined(UX_HOST_STANDALONE)
110
    UX_DISABLE
111
    if (hid -> ux_host_class_hid_flags & UX_HOST_CLASS_HID_FLAG_LOCK)
112
    {
113
        UX_RESTORE
114
        return(UX_BUSY);
115
    }
116
    hid -> ux_host_class_hid_flags &= ~UX_HOST_CLASS_HID_FLAG_LOCK;
117
    UX_RESTORE
118
#else
119
120
11
    status =  _ux_host_semaphore_get(&hid -> ux_host_class_hid_semaphore, UX_WAIT_FOREVER);
121
11
    if (status != UX_SUCCESS)
122
123
        /* Return error.  */
124
1
        return(status);
125
#endif
126
127
    /* Need to allocate memory for the idle byte.  */
128
10
    idle_byte =  _ux_utility_memory_allocate(UX_SAFE_ALIGN, UX_CACHE_SAFE_MEMORY, 1);
129
10
    if (idle_byte == UX_NULL)
130
    {
131
132
        /* Unprotect thread reentry to this instance.  */
133
1
        _ux_host_class_hid_unlock(hid);
134
135
        /* Return error status.  */
136
1
        return(UX_MEMORY_INSUFFICIENT);
137
    }
138
139
    /* Protect the control endpoint semaphore here.  It will be unprotected in the
140
       transfer request function.  */
141
#if defined(UX_HOST_STANDALONE)
142
    UX_DISABLE
143
    if (hid -> ux_host_class_hid_device -> ux_device_flags & UX_DEVICE_FLAG_LOCK)
144
    {
145
146
        /* Free allocated return busy.  */
147
        _ux_utility_memory_free(idle_byte);
148
        hid -> ux_host_class_hid_flags &= ~UX_HOST_CLASS_HID_FLAG_LOCK;
149
        UX_RESTORE
150
        return(UX_BUSY);
151
    }
152
    hid -> ux_host_class_hid_device -> ux_device_flags |= UX_DEVICE_FLAG_LOCK;
153
    transfer_request -> ux_transfer_request_flags |= UX_TRANSFER_FLAG_AUTO_DEVICE_UNLOCK;
154
    UX_TRANSFER_STATE_RESET(transfer_request);
155
    UX_RESTORE
156
#else
157
9
    status =  _ux_host_semaphore_get(&hid -> ux_host_class_hid_device -> ux_device_protection_semaphore, UX_WAIT_FOREVER);
158
159
    /* Check for status.  */
160
9
    if (status != UX_SUCCESS)
161
    {
162
163
        /* Something went wrong. */
164
165
        /* Free allocated memory.  */
166
1
        _ux_utility_memory_free(idle_byte);
167
168
        /* Unprotect thread reentry to this instance.  */
169
1
        _ux_host_semaphore_put(&hid -> ux_host_class_hid_semaphore);
170
171
1
        return(status);
172
    }
173
#endif
174
175
    /* Create a transfer request for the GET_IDLE request.  */
176
8
    transfer_request -> ux_transfer_request_data_pointer =      idle_byte;
177
8
    transfer_request -> ux_transfer_request_requested_length =  1;
178
8
    transfer_request -> ux_transfer_request_function =          UX_HOST_CLASS_HID_GET_IDLE;
179
8
    transfer_request -> ux_transfer_request_type =              UX_REQUEST_IN | UX_REQUEST_TYPE_CLASS | UX_REQUEST_TARGET_INTERFACE;
180
8
    transfer_request -> ux_transfer_request_value =             report_id;
181
8
    transfer_request -> ux_transfer_request_index =             hid -> ux_host_class_hid_interface -> ux_interface_descriptor.bInterfaceNumber;
182
183
    /* Send request to HCD layer.  */
184
8
    status =  _ux_host_stack_transfer_request(transfer_request);
185
186
#if defined(UX_HOST_STANDALONE)
187
    if (!(transfer_request -> ux_transfer_request_flags & UX_TRANSFER_FLAG_AUTO_WAIT))
188
    {
189
        hid -> ux_host_class_hid_allocated = idle_byte;
190
        return(status);
191
    }
192
#endif
193
194
    /* Check for correct transfer and for the entire descriptor returned.  */
195

8
    if ((status == UX_SUCCESS) && (transfer_request -> ux_transfer_request_actual_length == 1))
196
6
        *idle_time =  (USHORT) *idle_byte;
197
198
    /* Free used resources.  */
199
8
    _ux_utility_memory_free(idle_byte);
200
201
    /* Unprotect thread reentry to this instance.  */
202
#if defined(UX_HOST_STANDALONE)
203
    _ux_host_class_hid_unlock(hid);
204
#else
205
8
    _ux_host_semaphore_put(&hid -> ux_host_class_hid_semaphore);
206
#endif
207
208
    /* Return the completion status.  */
209
8
    return(status);
210
}
211
212
/**************************************************************************/
213
/*                                                                        */
214
/*  FUNCTION                                               RELEASE        */
215
/*                                                                        */
216
/*    _uxe_host_class_hid_report_idle_get                 PORTABLE C      */
217
/*                                                           6.3.0        */
218
/*  AUTHOR                                                                */
219
/*                                                                        */
220
/*    Chaoqiong Xiao, Microsoft Corporation                               */
221
/*                                                                        */
222
/*  DESCRIPTION                                                           */
223
/*                                                                        */
224
/*    This function checks errors in HID idle get function call.          */
225
/*                                                                        */
226
/*  INPUT                                                                 */
227
/*                                                                        */
228
/*    hid                                   Pointer to HID class          */
229
/*    idle_time                             Idle time                     */
230
/*    report_id                             Report ID                     */
231
/*                                                                        */
232
/*  OUTPUT                                                                */
233
/*                                                                        */
234
/*    Status                                                              */
235
/*                                                                        */
236
/*  CALLS                                                                 */
237
/*                                                                        */
238
/*    _ux_host_class_hid_idle_get           Get idle rate                 */
239
/*                                                                        */
240
/*  CALLED BY                                                             */
241
/*                                                                        */
242
/*    Application                                                         */
243
/*                                                                        */
244
/*  RELEASE HISTORY                                                       */
245
/*                                                                        */
246
/*    DATE              NAME                      DESCRIPTION             */
247
/*                                                                        */
248
/*  10-31-2023     Chaoqiong Xiao           Initial Version 6.3.0         */
249
/*                                                                        */
250
/**************************************************************************/
251
UINT  _uxe_host_class_hid_idle_get(UX_HOST_CLASS_HID *hid, USHORT *idle_time, USHORT report_id)
252
{
253
254
    /* Sanity checks.  */
255
    if ((hid == UX_NULL) || (idle_time == UX_NULL))
256
        return(UX_INVALID_PARAMETER);
257
258
    /* Invoke idle get function.  */
259
    return(_ux_host_class_hid_idle_get(hid, idle_time, report_id));
260
}