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 /** Audio 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_audio.h"
29 #include "ux_host_stack.h"
30
31
32 /**************************************************************************/
33 /* */
34 /* FUNCTION RELEASE */
35 /* */
36 /* _ux_host_class_audio_write PORTABLE C */
37 /* 6.1.12 */
38 /* AUTHOR */
39 /* */
40 /* Chaoqiong Xiao, Microsoft Corporation */
41 /* */
42 /* DESCRIPTION */
43 /* */
44 /* This function writes to the audio streaming interface. */
45 /* */
46 /* Note the request packet size should not exceed endpoint max packet */
47 /* size, and the request length should be aligned with packet size. */
48 /* */
49 /* INPUT */
50 /* */
51 /* audio Pointer to audio class */
52 /* audio_transfer_request Pointer to transfer request */
53 /* */
54 /* OUTPUT */
55 /* */
56 /* Completion Status */
57 /* */
58 /* CALLS */
59 /* */
60 /* _ux_host_class_audio_transfer_request Start audio transfer request */
61 /* _ux_host_stack_class_instance_verify Verify instance is valid */
62 /* _ux_host_mutex_on Get mutex */
63 /* _ux_host_mutex_off Release mutex */
64 /* */
65 /* CALLED BY */
66 /* */
67 /* Application */
68 /* Audio Class */
69 /* */
70 /* RELEASE HISTORY */
71 /* */
72 /* DATE NAME DESCRIPTION */
73 /* */
74 /* 05-19-2020 Chaoqiong Xiao Initial Version 6.0 */
75 /* 09-30-2020 Chaoqiong Xiao Modified comment(s), */
76 /* resulting in version 6.1 */
77 /* 01-31-2022 Chaoqiong Xiao Modified comment(s), */
78 /* refined macros names, */
79 /* resulting in version 6.1.10 */
80 /* 04-25-2022 Chaoqiong Xiao Modified comment(s), */
81 /* fixed standalone compile, */
82 /* resulting in version 6.1.11 */
83 /* 07-29-2022 Chaoqiong Xiao Modified comment(s), */
84 /* refined packet size manage, */
85 /* protect reentry with mutex, */
86 /* refined transfer implement, */
87 /* fixed error return code, */
88 /* resulting in version 6.1.12 */
89 /* */
90 /**************************************************************************/
_ux_host_class_audio_write(UX_HOST_CLASS_AUDIO * audio,UX_HOST_CLASS_AUDIO_TRANSFER_REQUEST * audio_transfer_request)91 UINT _ux_host_class_audio_write(UX_HOST_CLASS_AUDIO *audio, UX_HOST_CLASS_AUDIO_TRANSFER_REQUEST *audio_transfer_request)
92 {
93
94 UINT status;
95 ULONG mps;
96
97 /* If trace is enabled, insert this event into the trace buffer. */
98 UX_TRACE_IN_LINE_INSERT(UX_TRACE_HOST_CLASS_AUDIO_WRITE, audio, audio_transfer_request -> ux_host_class_audio_transfer_request_data_pointer,
99 audio_transfer_request -> ux_host_class_audio_transfer_request_requested_length, 0, UX_TRACE_HOST_CLASS_EVENTS, 0, 0)
100
101 /* Ensure the instance is valid. */
102 if (_ux_host_stack_class_instance_verify(_ux_system_host_class_audio_name, (VOID *) audio) != UX_SUCCESS)
103 {
104
105 /* Error trap. */
106 _ux_system_error_handler(UX_SYSTEM_LEVEL_THREAD, UX_SYSTEM_CONTEXT_CLASS, UX_HOST_CLASS_INSTANCE_UNKNOWN);
107
108 /* If trace is enabled, insert this event into the trace buffer. */
109 UX_TRACE_IN_LINE_INSERT(UX_TRACE_ERROR, UX_HOST_CLASS_INSTANCE_UNKNOWN, audio, 0, 0, UX_TRACE_ERRORS, 0, 0)
110
111 return(UX_HOST_CLASS_INSTANCE_UNKNOWN);
112 }
113
114 /* Protect thread reentry to this instance. */
115 _ux_host_mutex_on(&audio -> ux_host_class_audio_mutex);
116
117 /* Ensure we have a selected interface that allows isoch transmission. */
118 if (audio -> ux_host_class_audio_isochronous_endpoint -> ux_endpoint_descriptor.wMaxPacketSize == 0)
119 {
120
121 /* Unprotect thread reentry to this instance. */
122 _ux_host_mutex_off(&audio -> ux_host_class_audio_mutex);
123
124 /* Error trap. */
125 _ux_system_error_handler(UX_SYSTEM_LEVEL_THREAD, UX_SYSTEM_CONTEXT_CLASS, UX_HOST_CLASS_AUDIO_WRONG_INTERFACE);
126
127 /* Return error status. */
128 return(UX_HOST_CLASS_AUDIO_WRONG_INTERFACE);
129 }
130
131 /* Correct packet size to apply (not exceeding endpoint max packet size). */
132 mps = _ux_host_class_audio_max_packet_size_get(audio);
133 if ((audio_transfer_request -> ux_host_class_audio_transfer_request_packet_size == 0) ||
134 (audio_transfer_request -> ux_host_class_audio_transfer_request_packet_size > mps))
135 audio_transfer_request -> ux_host_class_audio_transfer_request_packet_size = mps;
136
137 /* Ask the stack to hook this transfer request to the iso ED. */
138 status = _ux_host_class_audio_transfer_request(audio, audio_transfer_request);
139
140 /* Unprotect thread reentry to this instance. */
141 _ux_host_mutex_off(&audio -> ux_host_class_audio_mutex);
142
143 /* Return completion status. */
144 return(status);
145 }
146
147
148 /**************************************************************************/
149 /* */
150 /* FUNCTION RELEASE */
151 /* */
152 /* _uxe_host_class_audio_write PORTABLE C */
153 /* 6.3.0 */
154 /* AUTHOR */
155 /* */
156 /* Chaoqiong Xiao, Microsoft Corporation */
157 /* */
158 /* DESCRIPTION */
159 /* */
160 /* This function checks errors in audio write function call. */
161 /* */
162 /* INPUT */
163 /* */
164 /* audio Pointer to audio class */
165 /* audio_transfer_request Pointer to transfer request */
166 /* */
167 /* OUTPUT */
168 /* */
169 /* Status */
170 /* */
171 /* CALLS */
172 /* */
173 /* _ux_host_class_audio_write Hook a audio write request */
174 /* */
175 /* CALLED BY */
176 /* */
177 /* Application */
178 /* */
179 /* RELEASE HISTORY */
180 /* */
181 /* DATE NAME DESCRIPTION */
182 /* */
183 /* 10-31-2023 Chaoqiong Xiao Initial Version 6.3.0 */
184 /* */
185 /**************************************************************************/
_uxe_host_class_audio_write(UX_HOST_CLASS_AUDIO * audio,UX_HOST_CLASS_AUDIO_TRANSFER_REQUEST * audio_transfer_request)186 UINT _uxe_host_class_audio_write(UX_HOST_CLASS_AUDIO *audio, UX_HOST_CLASS_AUDIO_TRANSFER_REQUEST *audio_transfer_request)
187 {
188
189 /* Sanity checks. */
190 if ((UX_NULL == audio) || (audio_transfer_request == UX_NULL))
191 return(UX_INVALID_PARAMETER);
192
193 /* Invoke audio write function. */
194 return(_ux_host_class_audio_write(audio, audio_transfer_request));
195 }
196