1 // SPDX-License-Identifier: (GPL-2.0 OR BSD-3-Clause)
2 // Copyright(c) 2024 Intel Corporation
3
4 /*
5 * The MIPI SDCA specification is available for public downloads at
6 * https://www.mipi.org/mipi-sdca-v1-0-download
7 */
8
9 #define dev_fmt(fmt) "%s: " fmt, __func__
10
11 #include <linux/acpi.h>
12 #include <linux/byteorder/generic.h>
13 #include <linux/cleanup.h>
14 #include <linux/device.h>
15 #include <linux/dev_printk.h>
16 #include <linux/module.h>
17 #include <linux/property.h>
18 #include <linux/soundwire/sdw.h>
19 #include <linux/types.h>
20 #include <sound/sdca.h>
21 #include <sound/sdca_function.h>
22 #include <sound/sdca_hid.h>
23
24 /*
25 * Should be long enough to encompass all the MIPI DisCo properties.
26 */
27 #define SDCA_PROPERTY_LENGTH 64
28
patch_sdca_function_type(u32 interface_revision,u32 * function_type)29 static int patch_sdca_function_type(u32 interface_revision, u32 *function_type)
30 {
31 /*
32 * Unfortunately early SDCA specifications used different indices for Functions,
33 * for backwards compatibility we have to reorder the values found.
34 */
35 if (interface_revision < 0x0801) {
36 switch (*function_type) {
37 case 1:
38 *function_type = SDCA_FUNCTION_TYPE_SMART_AMP;
39 break;
40 case 2:
41 *function_type = SDCA_FUNCTION_TYPE_SMART_MIC;
42 break;
43 case 3:
44 *function_type = SDCA_FUNCTION_TYPE_SPEAKER_MIC;
45 break;
46 case 4:
47 *function_type = SDCA_FUNCTION_TYPE_UAJ;
48 break;
49 case 5:
50 *function_type = SDCA_FUNCTION_TYPE_RJ;
51 break;
52 case 6:
53 *function_type = SDCA_FUNCTION_TYPE_HID;
54 break;
55 default:
56 return -EINVAL;
57 }
58 }
59
60 return 0;
61 }
62
get_sdca_function_name(u32 function_type)63 static const char *get_sdca_function_name(u32 function_type)
64 {
65 switch (function_type) {
66 case SDCA_FUNCTION_TYPE_SMART_AMP:
67 return SDCA_FUNCTION_TYPE_SMART_AMP_NAME;
68 case SDCA_FUNCTION_TYPE_SMART_MIC:
69 return SDCA_FUNCTION_TYPE_SMART_MIC_NAME;
70 case SDCA_FUNCTION_TYPE_UAJ:
71 return SDCA_FUNCTION_TYPE_UAJ_NAME;
72 case SDCA_FUNCTION_TYPE_HID:
73 return SDCA_FUNCTION_TYPE_HID_NAME;
74 case SDCA_FUNCTION_TYPE_SIMPLE_AMP:
75 return SDCA_FUNCTION_TYPE_SIMPLE_AMP_NAME;
76 case SDCA_FUNCTION_TYPE_SIMPLE_MIC:
77 return SDCA_FUNCTION_TYPE_SIMPLE_MIC_NAME;
78 case SDCA_FUNCTION_TYPE_SPEAKER_MIC:
79 return SDCA_FUNCTION_TYPE_SPEAKER_MIC_NAME;
80 case SDCA_FUNCTION_TYPE_RJ:
81 return SDCA_FUNCTION_TYPE_RJ_NAME;
82 case SDCA_FUNCTION_TYPE_IMP_DEF:
83 return SDCA_FUNCTION_TYPE_IMP_DEF_NAME;
84 default:
85 return NULL;
86 }
87 }
88
find_sdca_function(struct acpi_device * adev,void * data)89 static int find_sdca_function(struct acpi_device *adev, void *data)
90 {
91 struct fwnode_handle *function_node = acpi_fwnode_handle(adev);
92 struct sdca_device_data *sdca_data = data;
93 struct device *dev = &adev->dev;
94 struct fwnode_handle *control5; /* used to identify function type */
95 const char *function_name;
96 u32 function_type;
97 int function_index;
98 u64 addr;
99 int ret;
100
101 if (sdca_data->num_functions >= SDCA_MAX_FUNCTION_COUNT) {
102 dev_err(dev, "maximum number of functions exceeded\n");
103 return -EINVAL;
104 }
105
106 ret = acpi_get_local_u64_address(adev->handle, &addr);
107 if (ret < 0)
108 return ret;
109
110 if (!addr || addr > 0x7) {
111 dev_err(dev, "invalid addr: 0x%llx\n", addr);
112 return -ENODEV;
113 }
114
115 /*
116 * Extracting the topology type for an SDCA function is a
117 * convoluted process.
118 * The Function type is only visible as a result of a read
119 * from a control. In theory this would mean reading from the hardware,
120 * but the SDCA/DisCo specs defined the notion of "DC value" - a constant
121 * represented with a DSD subproperty.
122 * Drivers have to query the properties for the control
123 * SDCA_CONTROL_ENTITY_0_FUNCTION_TOPOLOGY (0x05)
124 */
125 control5 = fwnode_get_named_child_node(function_node,
126 "mipi-sdca-control-0x5-subproperties");
127 if (!control5)
128 return -ENODEV;
129
130 ret = fwnode_property_read_u32(control5, "mipi-sdca-control-dc-value",
131 &function_type);
132
133 fwnode_handle_put(control5);
134
135 if (ret < 0) {
136 dev_err(dev, "function type only supported as DisCo constant\n");
137 return ret;
138 }
139
140 ret = patch_sdca_function_type(sdca_data->interface_revision, &function_type);
141 if (ret < 0) {
142 dev_err(dev, "SDCA version %#x invalid function type %d\n",
143 sdca_data->interface_revision, function_type);
144 return ret;
145 }
146
147 function_name = get_sdca_function_name(function_type);
148 if (!function_name) {
149 dev_err(dev, "invalid SDCA function type %d\n", function_type);
150 return -EINVAL;
151 }
152
153 dev_info(dev, "SDCA function %s (type %d) at 0x%llx\n",
154 function_name, function_type, addr);
155
156 /* store results */
157 function_index = sdca_data->num_functions;
158 sdca_data->function[function_index].adr = addr;
159 sdca_data->function[function_index].type = function_type;
160 sdca_data->function[function_index].name = function_name;
161 sdca_data->function[function_index].node = function_node;
162 sdca_data->num_functions++;
163
164 return 0;
165 }
166
167 /**
168 * sdca_lookup_functions - Parse sdca_device_desc for each Function
169 * @slave: SoundWire slave device to be processed.
170 *
171 * Iterate through the available SDCA Functions and fill in a short
172 * descriptor (struct sdca_function_desc) for each function, this
173 * information is stored along with the SoundWire slave device and
174 * used for adding drivers and quirks before the devices have fully
175 * probed.
176 */
sdca_lookup_functions(struct sdw_slave * slave)177 void sdca_lookup_functions(struct sdw_slave *slave)
178 {
179 struct device *dev = &slave->dev;
180 struct acpi_device *adev = to_acpi_device_node(dev->fwnode);
181
182 if (!adev) {
183 dev_info(dev, "no matching ACPI device found, ignoring peripheral\n");
184 return;
185 }
186
187 acpi_dev_for_each_child(adev, find_sdca_function, &slave->sdca_data);
188 }
189 EXPORT_SYMBOL_NS(sdca_lookup_functions, "SND_SOC_SDCA");
190
191 struct raw_init_write {
192 __le32 addr;
193 u8 val;
194 } __packed;
195
find_sdca_init_table(struct device * dev,struct fwnode_handle * function_node,struct sdca_function_data * function)196 static int find_sdca_init_table(struct device *dev,
197 struct fwnode_handle *function_node,
198 struct sdca_function_data *function)
199 {
200 struct raw_init_write *raw __free(kfree) = NULL;
201 struct sdca_init_write *init_write;
202 int i, num_init_writes;
203
204 num_init_writes = fwnode_property_count_u8(function_node,
205 "mipi-sdca-function-initialization-table");
206 if (!num_init_writes || num_init_writes == -EINVAL) {
207 return 0;
208 } else if (num_init_writes < 0) {
209 dev_err(dev, "%pfwP: failed to read initialization table: %d\n",
210 function_node, num_init_writes);
211 return num_init_writes;
212 } else if (num_init_writes % sizeof(*raw) != 0) {
213 dev_err(dev, "%pfwP: init table size invalid\n", function_node);
214 return -EINVAL;
215 } else if ((num_init_writes / sizeof(*raw)) > SDCA_MAX_INIT_COUNT) {
216 dev_err(dev, "%pfwP: maximum init table size exceeded\n", function_node);
217 return -EINVAL;
218 }
219
220 raw = kzalloc(num_init_writes, GFP_KERNEL);
221 if (!raw)
222 return -ENOMEM;
223
224 fwnode_property_read_u8_array(function_node,
225 "mipi-sdca-function-initialization-table",
226 (u8 *)raw, num_init_writes);
227
228 num_init_writes /= sizeof(*raw);
229
230 init_write = devm_kcalloc(dev, num_init_writes, sizeof(*init_write), GFP_KERNEL);
231 if (!init_write)
232 return -ENOMEM;
233
234 for (i = 0; i < num_init_writes; i++) {
235 init_write[i].addr = le32_to_cpu(raw[i].addr);
236 init_write[i].val = raw[i].val;
237 }
238
239 function->num_init_table = num_init_writes;
240 function->init_table = init_write;
241
242 return 0;
243 }
244
find_sdca_control_label(struct device * dev,const struct sdca_entity * entity,const struct sdca_control * control)245 static const char *find_sdca_control_label(struct device *dev,
246 const struct sdca_entity *entity,
247 const struct sdca_control *control)
248 {
249 switch (SDCA_CTL_TYPE(entity->type, control->sel)) {
250 case SDCA_CTL_TYPE_S(IT, MIC_BIAS):
251 return SDCA_CTL_MIC_BIAS_NAME;
252 case SDCA_CTL_TYPE_S(IT, USAGE):
253 case SDCA_CTL_TYPE_S(OT, USAGE):
254 return SDCA_CTL_USAGE_NAME;
255 case SDCA_CTL_TYPE_S(IT, LATENCY):
256 case SDCA_CTL_TYPE_S(OT, LATENCY):
257 case SDCA_CTL_TYPE_S(MU, LATENCY):
258 case SDCA_CTL_TYPE_S(SU, LATENCY):
259 case SDCA_CTL_TYPE_S(FU, LATENCY):
260 case SDCA_CTL_TYPE_S(XU, LATENCY):
261 case SDCA_CTL_TYPE_S(CRU, LATENCY):
262 case SDCA_CTL_TYPE_S(UDMPU, LATENCY):
263 case SDCA_CTL_TYPE_S(MFPU, LATENCY):
264 case SDCA_CTL_TYPE_S(SMPU, LATENCY):
265 case SDCA_CTL_TYPE_S(SAPU, LATENCY):
266 case SDCA_CTL_TYPE_S(PPU, LATENCY):
267 return SDCA_CTL_LATENCY_NAME;
268 case SDCA_CTL_TYPE_S(IT, CLUSTERINDEX):
269 case SDCA_CTL_TYPE_S(CRU, CLUSTERINDEX):
270 case SDCA_CTL_TYPE_S(UDMPU, CLUSTERINDEX):
271 case SDCA_CTL_TYPE_S(MFPU, CLUSTERINDEX):
272 return SDCA_CTL_CLUSTERINDEX_NAME;
273 case SDCA_CTL_TYPE_S(IT, DATAPORT_SELECTOR):
274 case SDCA_CTL_TYPE_S(OT, DATAPORT_SELECTOR):
275 return SDCA_CTL_DATAPORT_SELECTOR_NAME;
276 case SDCA_CTL_TYPE_S(IT, MATCHING_GUID):
277 case SDCA_CTL_TYPE_S(OT, MATCHING_GUID):
278 case SDCA_CTL_TYPE_S(ENTITY_0, MATCHING_GUID):
279 return SDCA_CTL_MATCHING_GUID_NAME;
280 case SDCA_CTL_TYPE_S(IT, KEEP_ALIVE):
281 case SDCA_CTL_TYPE_S(OT, KEEP_ALIVE):
282 return SDCA_CTL_KEEP_ALIVE_NAME;
283 case SDCA_CTL_TYPE_S(IT, NDAI_STREAM):
284 case SDCA_CTL_TYPE_S(OT, NDAI_STREAM):
285 return SDCA_CTL_NDAI_STREAM_NAME;
286 case SDCA_CTL_TYPE_S(IT, NDAI_CATEGORY):
287 case SDCA_CTL_TYPE_S(OT, NDAI_CATEGORY):
288 return SDCA_CTL_NDAI_CATEGORY_NAME;
289 case SDCA_CTL_TYPE_S(IT, NDAI_CODINGTYPE):
290 case SDCA_CTL_TYPE_S(OT, NDAI_CODINGTYPE):
291 return SDCA_CTL_NDAI_CODINGTYPE_NAME;
292 case SDCA_CTL_TYPE_S(IT, NDAI_PACKETTYPE):
293 case SDCA_CTL_TYPE_S(OT, NDAI_PACKETTYPE):
294 return SDCA_CTL_NDAI_PACKETTYPE_NAME;
295 case SDCA_CTL_TYPE_S(MU, MIXER):
296 return SDCA_CTL_MIXER_NAME;
297 case SDCA_CTL_TYPE_S(SU, SELECTOR):
298 return SDCA_CTL_SELECTOR_NAME;
299 case SDCA_CTL_TYPE_S(FU, MUTE):
300 return SDCA_CTL_MUTE_NAME;
301 case SDCA_CTL_TYPE_S(FU, CHANNEL_VOLUME):
302 return SDCA_CTL_CHANNEL_VOLUME_NAME;
303 case SDCA_CTL_TYPE_S(FU, AGC):
304 return SDCA_CTL_AGC_NAME;
305 case SDCA_CTL_TYPE_S(FU, BASS_BOOST):
306 return SDCA_CTL_BASS_BOOST_NAME;
307 case SDCA_CTL_TYPE_S(FU, LOUDNESS):
308 return SDCA_CTL_LOUDNESS_NAME;
309 case SDCA_CTL_TYPE_S(FU, GAIN):
310 return SDCA_CTL_GAIN_NAME;
311 case SDCA_CTL_TYPE_S(XU, BYPASS):
312 case SDCA_CTL_TYPE_S(MFPU, BYPASS):
313 return SDCA_CTL_BYPASS_NAME;
314 case SDCA_CTL_TYPE_S(XU, XU_ID):
315 return SDCA_CTL_XU_ID_NAME;
316 case SDCA_CTL_TYPE_S(XU, XU_VERSION):
317 return SDCA_CTL_XU_VERSION_NAME;
318 case SDCA_CTL_TYPE_S(XU, FDL_CURRENTOWNER):
319 return SDCA_CTL_FDL_CURRENTOWNER_NAME;
320 case SDCA_CTL_TYPE_S(XU, FDL_MESSAGEOFFSET):
321 return SDCA_CTL_FDL_MESSAGEOFFSET_NAME;
322 case SDCA_CTL_TYPE_S(XU, FDL_MESSAGELENGTH):
323 return SDCA_CTL_FDL_MESSAGELENGTH_NAME;
324 case SDCA_CTL_TYPE_S(XU, FDL_STATUS):
325 return SDCA_CTL_FDL_STATUS_NAME;
326 case SDCA_CTL_TYPE_S(XU, FDL_SET_INDEX):
327 return SDCA_CTL_FDL_SET_INDEX_NAME;
328 case SDCA_CTL_TYPE_S(XU, FDL_HOST_REQUEST):
329 return SDCA_CTL_FDL_HOST_REQUEST_NAME;
330 case SDCA_CTL_TYPE_S(CS, CLOCK_VALID):
331 return SDCA_CTL_CLOCK_VALID_NAME;
332 case SDCA_CTL_TYPE_S(CS, SAMPLERATEINDEX):
333 return SDCA_CTL_SAMPLERATEINDEX_NAME;
334 case SDCA_CTL_TYPE_S(CX, CLOCK_SELECT):
335 return SDCA_CTL_CLOCK_SELECT_NAME;
336 case SDCA_CTL_TYPE_S(PDE, REQUESTED_PS):
337 return SDCA_CTL_REQUESTED_PS_NAME;
338 case SDCA_CTL_TYPE_S(PDE, ACTUAL_PS):
339 return SDCA_CTL_ACTUAL_PS_NAME;
340 case SDCA_CTL_TYPE_S(GE, SELECTED_MODE):
341 return SDCA_CTL_SELECTED_MODE_NAME;
342 case SDCA_CTL_TYPE_S(GE, DETECTED_MODE):
343 return SDCA_CTL_DETECTED_MODE_NAME;
344 case SDCA_CTL_TYPE_S(SPE, PRIVATE):
345 return SDCA_CTL_PRIVATE_NAME;
346 case SDCA_CTL_TYPE_S(SPE, PRIVACY_POLICY):
347 return SDCA_CTL_PRIVACY_POLICY_NAME;
348 case SDCA_CTL_TYPE_S(SPE, PRIVACY_LOCKSTATE):
349 return SDCA_CTL_PRIVACY_LOCKSTATE_NAME;
350 case SDCA_CTL_TYPE_S(SPE, PRIVACY_OWNER):
351 return SDCA_CTL_PRIVACY_OWNER_NAME;
352 case SDCA_CTL_TYPE_S(SPE, AUTHTX_CURRENTOWNER):
353 return SDCA_CTL_AUTHTX_CURRENTOWNER_NAME;
354 case SDCA_CTL_TYPE_S(SPE, AUTHTX_MESSAGEOFFSET):
355 return SDCA_CTL_AUTHTX_MESSAGEOFFSET_NAME;
356 case SDCA_CTL_TYPE_S(SPE, AUTHTX_MESSAGELENGTH):
357 return SDCA_CTL_AUTHTX_MESSAGELENGTH_NAME;
358 case SDCA_CTL_TYPE_S(SPE, AUTHRX_CURRENTOWNER):
359 return SDCA_CTL_AUTHRX_CURRENTOWNER_NAME;
360 case SDCA_CTL_TYPE_S(SPE, AUTHRX_MESSAGEOFFSET):
361 return SDCA_CTL_AUTHRX_MESSAGEOFFSET_NAME;
362 case SDCA_CTL_TYPE_S(SPE, AUTHRX_MESSAGELENGTH):
363 return SDCA_CTL_AUTHRX_MESSAGELENGTH_NAME;
364 case SDCA_CTL_TYPE_S(UDMPU, ACOUSTIC_ENERGY_LEVEL_MONITOR):
365 return SDCA_CTL_ACOUSTIC_ENERGY_LEVEL_MONITOR_NAME;
366 case SDCA_CTL_TYPE_S(UDMPU, ULTRASOUND_LOOP_GAIN):
367 return SDCA_CTL_ULTRASOUND_LOOP_GAIN_NAME;
368 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_0):
369 return SDCA_CTL_OPAQUESET_0_NAME;
370 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_1):
371 return SDCA_CTL_OPAQUESET_1_NAME;
372 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_2):
373 return SDCA_CTL_OPAQUESET_2_NAME;
374 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_3):
375 return SDCA_CTL_OPAQUESET_3_NAME;
376 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_4):
377 return SDCA_CTL_OPAQUESET_4_NAME;
378 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_5):
379 return SDCA_CTL_OPAQUESET_5_NAME;
380 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_6):
381 return SDCA_CTL_OPAQUESET_6_NAME;
382 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_7):
383 return SDCA_CTL_OPAQUESET_7_NAME;
384 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_8):
385 return SDCA_CTL_OPAQUESET_8_NAME;
386 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_9):
387 return SDCA_CTL_OPAQUESET_9_NAME;
388 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_10):
389 return SDCA_CTL_OPAQUESET_10_NAME;
390 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_11):
391 return SDCA_CTL_OPAQUESET_11_NAME;
392 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_12):
393 return SDCA_CTL_OPAQUESET_12_NAME;
394 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_13):
395 return SDCA_CTL_OPAQUESET_13_NAME;
396 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_14):
397 return SDCA_CTL_OPAQUESET_14_NAME;
398 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_15):
399 return SDCA_CTL_OPAQUESET_15_NAME;
400 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_16):
401 return SDCA_CTL_OPAQUESET_16_NAME;
402 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_17):
403 return SDCA_CTL_OPAQUESET_17_NAME;
404 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_18):
405 return SDCA_CTL_OPAQUESET_18_NAME;
406 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_19):
407 return SDCA_CTL_OPAQUESET_19_NAME;
408 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_20):
409 return SDCA_CTL_OPAQUESET_20_NAME;
410 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_21):
411 return SDCA_CTL_OPAQUESET_21_NAME;
412 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_22):
413 return SDCA_CTL_OPAQUESET_22_NAME;
414 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_23):
415 return SDCA_CTL_OPAQUESET_23_NAME;
416 case SDCA_CTL_TYPE_S(MFPU, ALGORITHM_READY):
417 return SDCA_CTL_ALGORITHM_READY_NAME;
418 case SDCA_CTL_TYPE_S(MFPU, ALGORITHM_ENABLE):
419 return SDCA_CTL_ALGORITHM_ENABLE_NAME;
420 case SDCA_CTL_TYPE_S(MFPU, ALGORITHM_PREPARE):
421 return SDCA_CTL_ALGORITHM_PREPARE_NAME;
422 case SDCA_CTL_TYPE_S(MFPU, CENTER_FREQUENCY_INDEX):
423 return SDCA_CTL_CENTER_FREQUENCY_INDEX_NAME;
424 case SDCA_CTL_TYPE_S(MFPU, ULTRASOUND_LEVEL):
425 return SDCA_CTL_ULTRASOUND_LEVEL_NAME;
426 case SDCA_CTL_TYPE_S(MFPU, AE_NUMBER):
427 return SDCA_CTL_AE_NUMBER_NAME;
428 case SDCA_CTL_TYPE_S(MFPU, AE_CURRENTOWNER):
429 return SDCA_CTL_AE_CURRENTOWNER_NAME;
430 case SDCA_CTL_TYPE_S(MFPU, AE_MESSAGEOFFSET):
431 return SDCA_CTL_AE_MESSAGEOFFSET_NAME;
432 case SDCA_CTL_TYPE_S(MFPU, AE_MESSAGELENGTH):
433 return SDCA_CTL_AE_MESSAGELENGTH_NAME;
434 case SDCA_CTL_TYPE_S(SMPU, TRIGGER_ENABLE):
435 return SDCA_CTL_TRIGGER_ENABLE_NAME;
436 case SDCA_CTL_TYPE_S(SMPU, TRIGGER_STATUS):
437 return SDCA_CTL_TRIGGER_STATUS_NAME;
438 case SDCA_CTL_TYPE_S(SMPU, HIST_BUFFER_MODE):
439 return SDCA_CTL_HIST_BUFFER_MODE_NAME;
440 case SDCA_CTL_TYPE_S(SMPU, HIST_BUFFER_PREAMBLE):
441 return SDCA_CTL_HIST_BUFFER_PREAMBLE_NAME;
442 case SDCA_CTL_TYPE_S(SMPU, HIST_ERROR):
443 return SDCA_CTL_HIST_ERROR_NAME;
444 case SDCA_CTL_TYPE_S(SMPU, TRIGGER_EXTENSION):
445 return SDCA_CTL_TRIGGER_EXTENSION_NAME;
446 case SDCA_CTL_TYPE_S(SMPU, TRIGGER_READY):
447 return SDCA_CTL_TRIGGER_READY_NAME;
448 case SDCA_CTL_TYPE_S(SMPU, HIST_CURRENTOWNER):
449 return SDCA_CTL_HIST_CURRENTOWNER_NAME;
450 case SDCA_CTL_TYPE_S(SMPU, HIST_MESSAGEOFFSET):
451 return SDCA_CTL_HIST_MESSAGEOFFSET_NAME;
452 case SDCA_CTL_TYPE_S(SMPU, HIST_MESSAGELENGTH):
453 return SDCA_CTL_HIST_MESSAGELENGTH_NAME;
454 case SDCA_CTL_TYPE_S(SMPU, DTODTX_CURRENTOWNER):
455 return SDCA_CTL_DTODTX_CURRENTOWNER_NAME;
456 case SDCA_CTL_TYPE_S(SMPU, DTODTX_MESSAGEOFFSET):
457 return SDCA_CTL_DTODTX_MESSAGEOFFSET_NAME;
458 case SDCA_CTL_TYPE_S(SMPU, DTODTX_MESSAGELENGTH):
459 return SDCA_CTL_DTODTX_MESSAGELENGTH_NAME;
460 case SDCA_CTL_TYPE_S(SMPU, DTODRX_CURRENTOWNER):
461 return SDCA_CTL_DTODRX_CURRENTOWNER_NAME;
462 case SDCA_CTL_TYPE_S(SMPU, DTODRX_MESSAGEOFFSET):
463 return SDCA_CTL_DTODRX_MESSAGEOFFSET_NAME;
464 case SDCA_CTL_TYPE_S(SMPU, DTODRX_MESSAGELENGTH):
465 return SDCA_CTL_DTODRX_MESSAGELENGTH_NAME;
466 case SDCA_CTL_TYPE_S(SAPU, PROTECTION_MODE):
467 return SDCA_CTL_PROTECTION_MODE_NAME;
468 case SDCA_CTL_TYPE_S(SAPU, PROTECTION_STATUS):
469 return SDCA_CTL_PROTECTION_STATUS_NAME;
470 case SDCA_CTL_TYPE_S(SAPU, OPAQUESETREQ_INDEX):
471 return SDCA_CTL_OPAQUESETREQ_INDEX_NAME;
472 case SDCA_CTL_TYPE_S(SAPU, DTODTX_CURRENTOWNER):
473 return SDCA_CTL_DTODTX_CURRENTOWNER_NAME;
474 case SDCA_CTL_TYPE_S(SAPU, DTODTX_MESSAGEOFFSET):
475 return SDCA_CTL_DTODTX_MESSAGEOFFSET_NAME;
476 case SDCA_CTL_TYPE_S(SAPU, DTODTX_MESSAGELENGTH):
477 return SDCA_CTL_DTODTX_MESSAGELENGTH_NAME;
478 case SDCA_CTL_TYPE_S(SAPU, DTODRX_CURRENTOWNER):
479 return SDCA_CTL_DTODRX_CURRENTOWNER_NAME;
480 case SDCA_CTL_TYPE_S(SAPU, DTODRX_MESSAGEOFFSET):
481 return SDCA_CTL_DTODRX_MESSAGEOFFSET_NAME;
482 case SDCA_CTL_TYPE_S(SAPU, DTODRX_MESSAGELENGTH):
483 return SDCA_CTL_DTODRX_MESSAGELENGTH_NAME;
484 case SDCA_CTL_TYPE_S(PPU, POSTURENUMBER):
485 return SDCA_CTL_POSTURENUMBER_NAME;
486 case SDCA_CTL_TYPE_S(PPU, POSTUREEXTENSION):
487 return SDCA_CTL_POSTUREEXTENSION_NAME;
488 case SDCA_CTL_TYPE_S(PPU, HORIZONTALBALANCE):
489 return SDCA_CTL_HORIZONTALBALANCE_NAME;
490 case SDCA_CTL_TYPE_S(PPU, VERTICALBALANCE):
491 return SDCA_CTL_VERTICALBALANCE_NAME;
492 case SDCA_CTL_TYPE_S(TG, TONE_DIVIDER):
493 return SDCA_CTL_TONE_DIVIDER_NAME;
494 case SDCA_CTL_TYPE_S(HIDE, HIDTX_CURRENTOWNER):
495 return SDCA_CTL_HIDTX_CURRENTOWNER_NAME;
496 case SDCA_CTL_TYPE_S(HIDE, HIDTX_MESSAGEOFFSET):
497 return SDCA_CTL_HIDTX_MESSAGEOFFSET_NAME;
498 case SDCA_CTL_TYPE_S(HIDE, HIDTX_MESSAGELENGTH):
499 return SDCA_CTL_HIDTX_MESSAGELENGTH_NAME;
500 case SDCA_CTL_TYPE_S(HIDE, HIDRX_CURRENTOWNER):
501 return SDCA_CTL_HIDRX_CURRENTOWNER_NAME;
502 case SDCA_CTL_TYPE_S(HIDE, HIDRX_MESSAGEOFFSET):
503 return SDCA_CTL_HIDRX_MESSAGEOFFSET_NAME;
504 case SDCA_CTL_TYPE_S(HIDE, HIDRX_MESSAGELENGTH):
505 return SDCA_CTL_HIDRX_MESSAGELENGTH_NAME;
506 case SDCA_CTL_TYPE_S(ENTITY_0, COMMIT_GROUP_MASK):
507 return SDCA_CTL_COMMIT_GROUP_MASK_NAME;
508 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_SDCA_VERSION):
509 return SDCA_CTL_FUNCTION_SDCA_VERSION_NAME;
510 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_TYPE):
511 return SDCA_CTL_FUNCTION_TYPE_NAME;
512 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_MANUFACTURER_ID):
513 return SDCA_CTL_FUNCTION_MANUFACTURER_ID_NAME;
514 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_ID):
515 return SDCA_CTL_FUNCTION_ID_NAME;
516 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_VERSION):
517 return SDCA_CTL_FUNCTION_VERSION_NAME;
518 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_EXTENSION_ID):
519 return SDCA_CTL_FUNCTION_EXTENSION_ID_NAME;
520 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_EXTENSION_VERSION):
521 return SDCA_CTL_FUNCTION_EXTENSION_VERSION_NAME;
522 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_STATUS):
523 return SDCA_CTL_FUNCTION_STATUS_NAME;
524 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_ACTION):
525 return SDCA_CTL_FUNCTION_ACTION_NAME;
526 case SDCA_CTL_TYPE_S(ENTITY_0, DEVICE_MANUFACTURER_ID):
527 return SDCA_CTL_DEVICE_MANUFACTURER_ID_NAME;
528 case SDCA_CTL_TYPE_S(ENTITY_0, DEVICE_PART_ID):
529 return SDCA_CTL_DEVICE_PART_ID_NAME;
530 case SDCA_CTL_TYPE_S(ENTITY_0, DEVICE_VERSION):
531 return SDCA_CTL_DEVICE_VERSION_NAME;
532 case SDCA_CTL_TYPE_S(ENTITY_0, DEVICE_SDCA_VERSION):
533 return SDCA_CTL_DEVICE_SDCA_VERSION_NAME;
534 default:
535 return devm_kasprintf(dev, GFP_KERNEL, "Imp-Def %#x", control->sel);
536 }
537 }
538
find_sdca_control_bits(const struct sdca_entity * entity,const struct sdca_control * control)539 static unsigned int find_sdca_control_bits(const struct sdca_entity *entity,
540 const struct sdca_control *control)
541 {
542 switch (SDCA_CTL_TYPE(entity->type, control->sel)) {
543 case SDCA_CTL_TYPE_S(IT, LATENCY):
544 case SDCA_CTL_TYPE_S(OT, LATENCY):
545 case SDCA_CTL_TYPE_S(MU, LATENCY):
546 case SDCA_CTL_TYPE_S(SU, LATENCY):
547 case SDCA_CTL_TYPE_S(FU, LATENCY):
548 case SDCA_CTL_TYPE_S(XU, LATENCY):
549 case SDCA_CTL_TYPE_S(XU, FDL_MESSAGEOFFSET):
550 case SDCA_CTL_TYPE_S(XU, FDL_MESSAGELENGTH):
551 case SDCA_CTL_TYPE_S(SPE, AUTHTX_MESSAGEOFFSET):
552 case SDCA_CTL_TYPE_S(SPE, AUTHTX_MESSAGELENGTH):
553 case SDCA_CTL_TYPE_S(SPE, AUTHRX_MESSAGEOFFSET):
554 case SDCA_CTL_TYPE_S(SPE, AUTHRX_MESSAGELENGTH):
555 case SDCA_CTL_TYPE_S(CRU, LATENCY):
556 case SDCA_CTL_TYPE_S(UDMPU, LATENCY):
557 case SDCA_CTL_TYPE_S(MFPU, LATENCY):
558 case SDCA_CTL_TYPE_S(MFPU, AE_MESSAGEOFFSET):
559 case SDCA_CTL_TYPE_S(MFPU, AE_MESSAGELENGTH):
560 case SDCA_CTL_TYPE_S(SMPU, LATENCY):
561 case SDCA_CTL_TYPE_S(SMPU, HIST_MESSAGEOFFSET):
562 case SDCA_CTL_TYPE_S(SMPU, HIST_MESSAGELENGTH):
563 case SDCA_CTL_TYPE_S(SMPU, DTODTX_MESSAGEOFFSET):
564 case SDCA_CTL_TYPE_S(SMPU, DTODTX_MESSAGELENGTH):
565 case SDCA_CTL_TYPE_S(SMPU, DTODRX_MESSAGEOFFSET):
566 case SDCA_CTL_TYPE_S(SMPU, DTODRX_MESSAGELENGTH):
567 case SDCA_CTL_TYPE_S(SAPU, LATENCY):
568 case SDCA_CTL_TYPE_S(SAPU, DTODTX_MESSAGEOFFSET):
569 case SDCA_CTL_TYPE_S(SAPU, DTODTX_MESSAGELENGTH):
570 case SDCA_CTL_TYPE_S(SAPU, DTODRX_MESSAGEOFFSET):
571 case SDCA_CTL_TYPE_S(SAPU, DTODRX_MESSAGELENGTH):
572 case SDCA_CTL_TYPE_S(PPU, LATENCY):
573 case SDCA_CTL_TYPE_S(HIDE, HIDTX_MESSAGEOFFSET):
574 case SDCA_CTL_TYPE_S(HIDE, HIDTX_MESSAGELENGTH):
575 case SDCA_CTL_TYPE_S(HIDE, HIDRX_MESSAGEOFFSET):
576 case SDCA_CTL_TYPE_S(HIDE, HIDRX_MESSAGELENGTH):
577 return 32;
578 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_MANUFACTURER_ID):
579 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_ID):
580 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_EXTENSION_ID):
581 case SDCA_CTL_TYPE_S(ENTITY_0, DEVICE_MANUFACTURER_ID):
582 case SDCA_CTL_TYPE_S(ENTITY_0, DEVICE_PART_ID):
583 case SDCA_CTL_TYPE_S(IT, DATAPORT_SELECTOR):
584 case SDCA_CTL_TYPE_S(OT, DATAPORT_SELECTOR):
585 case SDCA_CTL_TYPE_S(MU, MIXER):
586 case SDCA_CTL_TYPE_S(FU, CHANNEL_VOLUME):
587 case SDCA_CTL_TYPE_S(FU, GAIN):
588 case SDCA_CTL_TYPE_S(XU, XU_ID):
589 case SDCA_CTL_TYPE_S(UDMPU, ACOUSTIC_ENERGY_LEVEL_MONITOR):
590 case SDCA_CTL_TYPE_S(UDMPU, ULTRASOUND_LOOP_GAIN):
591 case SDCA_CTL_TYPE_S(MFPU, ULTRASOUND_LEVEL):
592 case SDCA_CTL_TYPE_S(PPU, HORIZONTALBALANCE):
593 case SDCA_CTL_TYPE_S(PPU, VERTICALBALANCE):
594 return 16;
595 case SDCA_CTL_TYPE_S(FU, MUTE):
596 case SDCA_CTL_TYPE_S(FU, AGC):
597 case SDCA_CTL_TYPE_S(FU, BASS_BOOST):
598 case SDCA_CTL_TYPE_S(FU, LOUDNESS):
599 case SDCA_CTL_TYPE_S(XU, BYPASS):
600 case SDCA_CTL_TYPE_S(MFPU, BYPASS):
601 return 1;
602 default:
603 return 8;
604 }
605 }
606
607 static enum sdca_control_datatype
find_sdca_control_datatype(const struct sdca_entity * entity,const struct sdca_control * control)608 find_sdca_control_datatype(const struct sdca_entity *entity,
609 const struct sdca_control *control)
610 {
611 switch (SDCA_CTL_TYPE(entity->type, control->sel)) {
612 case SDCA_CTL_TYPE_S(XU, BYPASS):
613 case SDCA_CTL_TYPE_S(MFPU, BYPASS):
614 case SDCA_CTL_TYPE_S(FU, MUTE):
615 case SDCA_CTL_TYPE_S(FU, AGC):
616 case SDCA_CTL_TYPE_S(FU, BASS_BOOST):
617 case SDCA_CTL_TYPE_S(FU, LOUDNESS):
618 return SDCA_CTL_DATATYPE_ONEBIT;
619 case SDCA_CTL_TYPE_S(IT, LATENCY):
620 case SDCA_CTL_TYPE_S(OT, LATENCY):
621 case SDCA_CTL_TYPE_S(MU, LATENCY):
622 case SDCA_CTL_TYPE_S(SU, LATENCY):
623 case SDCA_CTL_TYPE_S(FU, LATENCY):
624 case SDCA_CTL_TYPE_S(XU, LATENCY):
625 case SDCA_CTL_TYPE_S(CRU, LATENCY):
626 case SDCA_CTL_TYPE_S(UDMPU, LATENCY):
627 case SDCA_CTL_TYPE_S(MFPU, LATENCY):
628 case SDCA_CTL_TYPE_S(SMPU, LATENCY):
629 case SDCA_CTL_TYPE_S(SAPU, LATENCY):
630 case SDCA_CTL_TYPE_S(PPU, LATENCY):
631 case SDCA_CTL_TYPE_S(SU, SELECTOR):
632 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_0):
633 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_1):
634 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_2):
635 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_3):
636 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_4):
637 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_5):
638 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_6):
639 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_7):
640 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_8):
641 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_9):
642 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_10):
643 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_11):
644 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_12):
645 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_13):
646 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_14):
647 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_15):
648 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_16):
649 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_17):
650 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_18):
651 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_19):
652 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_20):
653 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_21):
654 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_22):
655 case SDCA_CTL_TYPE_S(UDMPU, OPAQUESET_23):
656 case SDCA_CTL_TYPE_S(SAPU, PROTECTION_MODE):
657 case SDCA_CTL_TYPE_S(SMPU, HIST_BUFFER_PREAMBLE):
658 case SDCA_CTL_TYPE_S(XU, FDL_HOST_REQUEST):
659 case SDCA_CTL_TYPE_S(XU, XU_ID):
660 case SDCA_CTL_TYPE_S(CX, CLOCK_SELECT):
661 case SDCA_CTL_TYPE_S(TG, TONE_DIVIDER):
662 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_MANUFACTURER_ID):
663 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_ID):
664 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_EXTENSION_ID):
665 case SDCA_CTL_TYPE_S(ENTITY_0, DEVICE_MANUFACTURER_ID):
666 case SDCA_CTL_TYPE_S(ENTITY_0, DEVICE_PART_ID):
667 case SDCA_CTL_TYPE_S(XU, FDL_MESSAGEOFFSET):
668 case SDCA_CTL_TYPE_S(XU, FDL_MESSAGELENGTH):
669 case SDCA_CTL_TYPE_S(SPE, AUTHTX_MESSAGEOFFSET):
670 case SDCA_CTL_TYPE_S(SPE, AUTHTX_MESSAGELENGTH):
671 case SDCA_CTL_TYPE_S(SPE, AUTHRX_MESSAGEOFFSET):
672 case SDCA_CTL_TYPE_S(SPE, AUTHRX_MESSAGELENGTH):
673 case SDCA_CTL_TYPE_S(MFPU, AE_MESSAGEOFFSET):
674 case SDCA_CTL_TYPE_S(MFPU, AE_MESSAGELENGTH):
675 case SDCA_CTL_TYPE_S(SMPU, HIST_MESSAGEOFFSET):
676 case SDCA_CTL_TYPE_S(SMPU, HIST_MESSAGELENGTH):
677 case SDCA_CTL_TYPE_S(SMPU, DTODTX_MESSAGEOFFSET):
678 case SDCA_CTL_TYPE_S(SMPU, DTODTX_MESSAGELENGTH):
679 case SDCA_CTL_TYPE_S(SMPU, DTODRX_MESSAGEOFFSET):
680 case SDCA_CTL_TYPE_S(SMPU, DTODRX_MESSAGELENGTH):
681 case SDCA_CTL_TYPE_S(SAPU, DTODTX_MESSAGEOFFSET):
682 case SDCA_CTL_TYPE_S(SAPU, DTODTX_MESSAGELENGTH):
683 case SDCA_CTL_TYPE_S(SAPU, DTODRX_MESSAGEOFFSET):
684 case SDCA_CTL_TYPE_S(SAPU, DTODRX_MESSAGELENGTH):
685 case SDCA_CTL_TYPE_S(HIDE, HIDTX_MESSAGEOFFSET):
686 case SDCA_CTL_TYPE_S(HIDE, HIDTX_MESSAGELENGTH):
687 case SDCA_CTL_TYPE_S(HIDE, HIDRX_MESSAGEOFFSET):
688 case SDCA_CTL_TYPE_S(HIDE, HIDRX_MESSAGELENGTH):
689 return SDCA_CTL_DATATYPE_INTEGER;
690 case SDCA_CTL_TYPE_S(IT, MIC_BIAS):
691 case SDCA_CTL_TYPE_S(SMPU, HIST_BUFFER_MODE):
692 case SDCA_CTL_TYPE_S(PDE, REQUESTED_PS):
693 case SDCA_CTL_TYPE_S(PDE, ACTUAL_PS):
694 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_TYPE):
695 return SDCA_CTL_DATATYPE_SPEC_ENCODED_VALUE;
696 case SDCA_CTL_TYPE_S(XU, XU_VERSION):
697 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_SDCA_VERSION):
698 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_VERSION):
699 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_EXTENSION_VERSION):
700 case SDCA_CTL_TYPE_S(ENTITY_0, DEVICE_VERSION):
701 case SDCA_CTL_TYPE_S(ENTITY_0, DEVICE_SDCA_VERSION):
702 return SDCA_CTL_DATATYPE_BCD;
703 case SDCA_CTL_TYPE_S(FU, CHANNEL_VOLUME):
704 case SDCA_CTL_TYPE_S(FU, GAIN):
705 case SDCA_CTL_TYPE_S(MU, MIXER):
706 case SDCA_CTL_TYPE_S(PPU, HORIZONTALBALANCE):
707 case SDCA_CTL_TYPE_S(PPU, VERTICALBALANCE):
708 case SDCA_CTL_TYPE_S(MFPU, ULTRASOUND_LEVEL):
709 case SDCA_CTL_TYPE_S(UDMPU, ACOUSTIC_ENERGY_LEVEL_MONITOR):
710 case SDCA_CTL_TYPE_S(UDMPU, ULTRASOUND_LOOP_GAIN):
711 return SDCA_CTL_DATATYPE_Q7P8DB;
712 case SDCA_CTL_TYPE_S(IT, USAGE):
713 case SDCA_CTL_TYPE_S(OT, USAGE):
714 case SDCA_CTL_TYPE_S(IT, CLUSTERINDEX):
715 case SDCA_CTL_TYPE_S(CRU, CLUSTERINDEX):
716 case SDCA_CTL_TYPE_S(UDMPU, CLUSTERINDEX):
717 case SDCA_CTL_TYPE_S(MFPU, CLUSTERINDEX):
718 case SDCA_CTL_TYPE_S(MFPU, CENTER_FREQUENCY_INDEX):
719 case SDCA_CTL_TYPE_S(MFPU, AE_NUMBER):
720 case SDCA_CTL_TYPE_S(SAPU, OPAQUESETREQ_INDEX):
721 case SDCA_CTL_TYPE_S(XU, FDL_SET_INDEX):
722 case SDCA_CTL_TYPE_S(CS, SAMPLERATEINDEX):
723 case SDCA_CTL_TYPE_S(GE, SELECTED_MODE):
724 case SDCA_CTL_TYPE_S(GE, DETECTED_MODE):
725 return SDCA_CTL_DATATYPE_BYTEINDEX;
726 case SDCA_CTL_TYPE_S(PPU, POSTURENUMBER):
727 return SDCA_CTL_DATATYPE_POSTURENUMBER;
728 case SDCA_CTL_TYPE_S(IT, DATAPORT_SELECTOR):
729 case SDCA_CTL_TYPE_S(OT, DATAPORT_SELECTOR):
730 return SDCA_CTL_DATATYPE_DP_INDEX;
731 case SDCA_CTL_TYPE_S(MFPU, ALGORITHM_READY):
732 case SDCA_CTL_TYPE_S(MFPU, ALGORITHM_ENABLE):
733 case SDCA_CTL_TYPE_S(MFPU, ALGORITHM_PREPARE):
734 case SDCA_CTL_TYPE_S(SAPU, PROTECTION_STATUS):
735 case SDCA_CTL_TYPE_S(SMPU, TRIGGER_ENABLE):
736 case SDCA_CTL_TYPE_S(SMPU, TRIGGER_STATUS):
737 case SDCA_CTL_TYPE_S(SMPU, TRIGGER_READY):
738 case SDCA_CTL_TYPE_S(SPE, PRIVACY_POLICY):
739 case SDCA_CTL_TYPE_S(SPE, PRIVACY_OWNER):
740 return SDCA_CTL_DATATYPE_BITINDEX;
741 case SDCA_CTL_TYPE_S(IT, KEEP_ALIVE):
742 case SDCA_CTL_TYPE_S(OT, KEEP_ALIVE):
743 case SDCA_CTL_TYPE_S(IT, NDAI_STREAM):
744 case SDCA_CTL_TYPE_S(OT, NDAI_STREAM):
745 case SDCA_CTL_TYPE_S(IT, NDAI_CATEGORY):
746 case SDCA_CTL_TYPE_S(OT, NDAI_CATEGORY):
747 case SDCA_CTL_TYPE_S(IT, NDAI_CODINGTYPE):
748 case SDCA_CTL_TYPE_S(OT, NDAI_CODINGTYPE):
749 case SDCA_CTL_TYPE_S(IT, NDAI_PACKETTYPE):
750 case SDCA_CTL_TYPE_S(OT, NDAI_PACKETTYPE):
751 case SDCA_CTL_TYPE_S(SMPU, HIST_ERROR):
752 case SDCA_CTL_TYPE_S(XU, FDL_STATUS):
753 case SDCA_CTL_TYPE_S(CS, CLOCK_VALID):
754 case SDCA_CTL_TYPE_S(SPE, PRIVACY_LOCKSTATE):
755 case SDCA_CTL_TYPE_S(ENTITY_0, COMMIT_GROUP_MASK):
756 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_STATUS):
757 case SDCA_CTL_TYPE_S(ENTITY_0, FUNCTION_ACTION):
758 case SDCA_CTL_TYPE_S(XU, FDL_CURRENTOWNER):
759 case SDCA_CTL_TYPE_S(SPE, AUTHTX_CURRENTOWNER):
760 case SDCA_CTL_TYPE_S(SPE, AUTHRX_CURRENTOWNER):
761 case SDCA_CTL_TYPE_S(MFPU, AE_CURRENTOWNER):
762 case SDCA_CTL_TYPE_S(SMPU, HIST_CURRENTOWNER):
763 case SDCA_CTL_TYPE_S(SMPU, DTODTX_CURRENTOWNER):
764 case SDCA_CTL_TYPE_S(SMPU, DTODRX_CURRENTOWNER):
765 case SDCA_CTL_TYPE_S(SAPU, DTODTX_CURRENTOWNER):
766 case SDCA_CTL_TYPE_S(SAPU, DTODRX_CURRENTOWNER):
767 case SDCA_CTL_TYPE_S(HIDE, HIDTX_CURRENTOWNER):
768 case SDCA_CTL_TYPE_S(HIDE, HIDRX_CURRENTOWNER):
769 return SDCA_CTL_DATATYPE_BITMAP;
770 case SDCA_CTL_TYPE_S(IT, MATCHING_GUID):
771 case SDCA_CTL_TYPE_S(OT, MATCHING_GUID):
772 case SDCA_CTL_TYPE_S(ENTITY_0, MATCHING_GUID):
773 return SDCA_CTL_DATATYPE_GUID;
774 default:
775 return SDCA_CTL_DATATYPE_IMPDEF;
776 }
777 }
778
find_sdca_control_range(struct device * dev,struct fwnode_handle * control_node,struct sdca_control_range * range)779 static int find_sdca_control_range(struct device *dev,
780 struct fwnode_handle *control_node,
781 struct sdca_control_range *range)
782 {
783 u8 *range_list;
784 int num_range;
785 u16 *limits;
786 int i;
787
788 num_range = fwnode_property_count_u8(control_node, "mipi-sdca-control-range");
789 if (!num_range || num_range == -EINVAL)
790 return 0;
791 else if (num_range < 0)
792 return num_range;
793
794 range_list = devm_kcalloc(dev, num_range, sizeof(*range_list), GFP_KERNEL);
795 if (!range_list)
796 return -ENOMEM;
797
798 fwnode_property_read_u8_array(control_node, "mipi-sdca-control-range",
799 range_list, num_range);
800
801 limits = (u16 *)range_list;
802
803 range->cols = le16_to_cpu(limits[0]);
804 range->rows = le16_to_cpu(limits[1]);
805 range->data = (u32 *)&limits[2];
806
807 num_range = (num_range - (2 * sizeof(*limits))) / sizeof(*range->data);
808 if (num_range != range->cols * range->rows)
809 return -EINVAL;
810
811 for (i = 0; i < num_range; i++)
812 range->data[i] = le32_to_cpu(range->data[i]);
813
814 return 0;
815 }
816
find_sdca_control_value(struct device * dev,struct sdca_entity * entity,struct fwnode_handle * control_node,struct sdca_control * control,const char * const label)817 static int find_sdca_control_value(struct device *dev, struct sdca_entity *entity,
818 struct fwnode_handle *control_node,
819 struct sdca_control *control,
820 const char * const label)
821 {
822 char property[SDCA_PROPERTY_LENGTH];
823 bool global = true;
824 int ret, cn, i;
825 u32 tmp;
826
827 snprintf(property, sizeof(property), "mipi-sdca-control-%s", label);
828
829 ret = fwnode_property_read_u32(control_node, property, &tmp);
830 if (ret == -EINVAL)
831 global = false;
832 else if (ret)
833 return ret;
834
835 i = 0;
836 for_each_set_bit(cn, (unsigned long *)&control->cn_list,
837 BITS_PER_TYPE(control->cn_list)) {
838 if (!global) {
839 snprintf(property, sizeof(property),
840 "mipi-sdca-control-cn-%d-%s", cn, label);
841
842 ret = fwnode_property_read_u32(control_node, property, &tmp);
843 if (ret)
844 return ret;
845 }
846
847 control->values[i] = tmp;
848 i++;
849 }
850
851 return 0;
852 }
853
854 /*
855 * TODO: Add support for -cn- properties, allowing different channels to have
856 * different defaults etc.
857 */
find_sdca_entity_control(struct device * dev,struct sdca_entity * entity,struct fwnode_handle * control_node,struct sdca_control * control)858 static int find_sdca_entity_control(struct device *dev, struct sdca_entity *entity,
859 struct fwnode_handle *control_node,
860 struct sdca_control *control)
861 {
862 u32 tmp;
863 int ret;
864
865 ret = fwnode_property_read_u32(control_node, "mipi-sdca-control-access-mode", &tmp);
866 if (ret) {
867 dev_err(dev, "%s: control %#x: access mode missing: %d\n",
868 entity->label, control->sel, ret);
869 return ret;
870 }
871
872 control->mode = tmp;
873
874 ret = fwnode_property_read_u32(control_node, "mipi-sdca-control-access-layer", &tmp);
875 if (ret) {
876 dev_err(dev, "%s: control %#x: access layer missing: %d\n",
877 entity->label, control->sel, ret);
878 return ret;
879 }
880
881 control->layers = tmp;
882
883 ret = fwnode_property_read_u64(control_node, "mipi-sdca-control-cn-list",
884 &control->cn_list);
885 if (ret == -EINVAL) {
886 /* Spec allows not specifying cn-list if only the first number is used */
887 control->cn_list = 0x1;
888 } else if (ret || !control->cn_list) {
889 dev_err(dev, "%s: control %#x: cn list missing: %d\n",
890 entity->label, control->sel, ret);
891 return ret;
892 }
893
894 control->values = devm_kzalloc(dev, hweight64(control->cn_list), GFP_KERNEL);
895 if (!control->values)
896 return -ENOMEM;
897
898 switch (control->mode) {
899 case SDCA_ACCESS_MODE_DC:
900 ret = find_sdca_control_value(dev, entity, control_node, control,
901 "dc-value");
902 if (ret) {
903 dev_err(dev, "%s: control %#x: dc value missing: %d\n",
904 entity->label, control->sel, ret);
905 return ret;
906 }
907
908 control->has_fixed = true;
909 break;
910 case SDCA_ACCESS_MODE_RW:
911 case SDCA_ACCESS_MODE_DUAL:
912 ret = find_sdca_control_value(dev, entity, control_node, control,
913 "default-value");
914 if (!ret)
915 control->has_default = true;
916
917 ret = find_sdca_control_value(dev, entity, control_node, control,
918 "fixed-value");
919 if (!ret)
920 control->has_fixed = true;
921 fallthrough;
922 case SDCA_ACCESS_MODE_RO:
923 control->deferrable = fwnode_property_read_bool(control_node,
924 "mipi-sdca-control-deferrable");
925 break;
926 default:
927 break;
928 }
929
930 ret = find_sdca_control_range(dev, control_node, &control->range);
931 if (ret) {
932 dev_err(dev, "%s: control %#x: range missing: %d\n",
933 entity->label, control->sel, ret);
934 return ret;
935 }
936
937 ret = fwnode_property_read_u32(control_node,
938 "mipi-sdca-control-interrupt-position",
939 &tmp);
940 if (!ret)
941 control->interrupt_position = tmp;
942 else
943 control->interrupt_position = SDCA_NO_INTERRUPT;
944
945 control->label = find_sdca_control_label(dev, entity, control);
946 if (!control->label)
947 return -ENOMEM;
948
949 control->type = find_sdca_control_datatype(entity, control);
950 control->nbits = find_sdca_control_bits(entity, control);
951
952 dev_info(dev, "%s: %s: control %#x mode %#x layers %#x cn %#llx int %d %s\n",
953 entity->label, control->label, control->sel,
954 control->mode, control->layers, control->cn_list,
955 control->interrupt_position, control->deferrable ? "deferrable" : "");
956
957 return 0;
958 }
959
find_sdca_entity_controls(struct device * dev,struct fwnode_handle * entity_node,struct sdca_entity * entity)960 static int find_sdca_entity_controls(struct device *dev,
961 struct fwnode_handle *entity_node,
962 struct sdca_entity *entity)
963 {
964 struct sdca_control *controls;
965 int num_controls;
966 u64 control_list;
967 int control_sel;
968 int i, ret;
969
970 ret = fwnode_property_read_u64(entity_node, "mipi-sdca-control-list", &control_list);
971 if (ret == -EINVAL) {
972 /* Allow missing control lists, assume no controls. */
973 dev_warn(dev, "%s: missing control list\n", entity->label);
974 return 0;
975 } else if (ret) {
976 dev_err(dev, "%s: failed to read control list: %d\n", entity->label, ret);
977 return ret;
978 } else if (!control_list) {
979 return 0;
980 }
981
982 num_controls = hweight64(control_list);
983 controls = devm_kcalloc(dev, num_controls, sizeof(*controls), GFP_KERNEL);
984 if (!controls)
985 return -ENOMEM;
986
987 i = 0;
988 for_each_set_bit(control_sel, (unsigned long *)&control_list,
989 BITS_PER_TYPE(control_list)) {
990 struct fwnode_handle *control_node;
991 char control_property[SDCA_PROPERTY_LENGTH];
992
993 /* DisCo uses upper-case for hex numbers */
994 snprintf(control_property, sizeof(control_property),
995 "mipi-sdca-control-0x%X-subproperties", control_sel);
996
997 control_node = fwnode_get_named_child_node(entity_node, control_property);
998 if (!control_node) {
999 dev_err(dev, "%s: control node %s not found\n",
1000 entity->label, control_property);
1001 return -EINVAL;
1002 }
1003
1004 controls[i].sel = control_sel;
1005
1006 ret = find_sdca_entity_control(dev, entity, control_node, &controls[i]);
1007 fwnode_handle_put(control_node);
1008 if (ret)
1009 return ret;
1010
1011 i++;
1012 }
1013
1014 entity->num_controls = num_controls;
1015 entity->controls = controls;
1016
1017 return 0;
1018 }
1019
find_sdca_iot_dataport(struct sdca_entity_iot * terminal)1020 static bool find_sdca_iot_dataport(struct sdca_entity_iot *terminal)
1021 {
1022 switch (terminal->type) {
1023 case SDCA_TERM_TYPE_GENERIC:
1024 case SDCA_TERM_TYPE_ULTRASOUND:
1025 case SDCA_TERM_TYPE_CAPTURE_DIRECT_PCM_MIC:
1026 case SDCA_TERM_TYPE_RAW_PDM_MIC:
1027 case SDCA_TERM_TYPE_SPEECH:
1028 case SDCA_TERM_TYPE_VOICE:
1029 case SDCA_TERM_TYPE_SECONDARY_PCM_MIC:
1030 case SDCA_TERM_TYPE_ACOUSTIC_CONTEXT_AWARENESS:
1031 case SDCA_TERM_TYPE_DTOD_STREAM:
1032 case SDCA_TERM_TYPE_REFERENCE_STREAM:
1033 case SDCA_TERM_TYPE_SENSE_CAPTURE:
1034 case SDCA_TERM_TYPE_STREAMING_MIC:
1035 case SDCA_TERM_TYPE_OPTIMIZATION_STREAM:
1036 case SDCA_TERM_TYPE_PDM_RENDER_STREAM:
1037 case SDCA_TERM_TYPE_COMPANION_DATA:
1038 return true;
1039 default:
1040 return false;
1041 }
1042 }
1043
find_sdca_entity_iot(struct device * dev,struct fwnode_handle * entity_node,struct sdca_entity * entity)1044 static int find_sdca_entity_iot(struct device *dev,
1045 struct fwnode_handle *entity_node,
1046 struct sdca_entity *entity)
1047 {
1048 struct sdca_entity_iot *terminal = &entity->iot;
1049 u32 tmp;
1050 int ret;
1051
1052 ret = fwnode_property_read_u32(entity_node, "mipi-sdca-terminal-type", &tmp);
1053 if (ret) {
1054 dev_err(dev, "%s: terminal type missing: %d\n", entity->label, ret);
1055 return ret;
1056 }
1057
1058 terminal->type = tmp;
1059 terminal->is_dataport = find_sdca_iot_dataport(terminal);
1060
1061 ret = fwnode_property_read_u32(entity_node,
1062 "mipi-sdca-terminal-reference-number", &tmp);
1063 if (!ret)
1064 terminal->reference = tmp;
1065
1066 ret = fwnode_property_read_u32(entity_node,
1067 "mipi-sdca-terminal-connector-type", &tmp);
1068 if (!ret)
1069 terminal->connector = tmp;
1070
1071 ret = fwnode_property_read_u32(entity_node,
1072 "mipi-sdca-terminal-transducer-count", &tmp);
1073 if (!ret)
1074 terminal->num_transducer = tmp;
1075
1076 dev_info(dev, "%s: terminal type %#x ref %#x conn %#x count %d\n",
1077 entity->label, terminal->type, terminal->reference,
1078 terminal->connector, terminal->num_transducer);
1079
1080 return 0;
1081 }
1082
find_sdca_entity_cs(struct device * dev,struct fwnode_handle * entity_node,struct sdca_entity * entity)1083 static int find_sdca_entity_cs(struct device *dev,
1084 struct fwnode_handle *entity_node,
1085 struct sdca_entity *entity)
1086 {
1087 struct sdca_entity_cs *clock = &entity->cs;
1088 u32 tmp;
1089 int ret;
1090
1091 ret = fwnode_property_read_u32(entity_node, "mipi-sdca-cs-type", &tmp);
1092 if (ret) {
1093 dev_err(dev, "%s: clock type missing: %d\n", entity->label, ret);
1094 return ret;
1095 }
1096
1097 clock->type = tmp;
1098
1099 ret = fwnode_property_read_u32(entity_node,
1100 "mipi-sdca-clock-valid-max-delay", &tmp);
1101 if (!ret)
1102 clock->max_delay = tmp;
1103
1104 dev_info(dev, "%s: clock type %#x delay %d\n", entity->label,
1105 clock->type, clock->max_delay);
1106
1107 return 0;
1108 }
1109
find_sdca_entity_pde(struct device * dev,struct fwnode_handle * entity_node,struct sdca_entity * entity)1110 static int find_sdca_entity_pde(struct device *dev,
1111 struct fwnode_handle *entity_node,
1112 struct sdca_entity *entity)
1113 {
1114 static const int mult_delay = 3;
1115 struct sdca_entity_pde *power = &entity->pde;
1116 u32 *delay_list __free(kfree) = NULL;
1117 struct sdca_pde_delay *delays;
1118 int num_delays;
1119 int i, j;
1120
1121 num_delays = fwnode_property_count_u32(entity_node,
1122 "mipi-sdca-powerdomain-transition-max-delay");
1123 if (num_delays <= 0) {
1124 dev_err(dev, "%s: max delay list missing: %d\n",
1125 entity->label, num_delays);
1126 return -EINVAL;
1127 } else if (num_delays % mult_delay != 0) {
1128 dev_err(dev, "%s: delays not multiple of %d\n",
1129 entity->label, mult_delay);
1130 return -EINVAL;
1131 } else if (num_delays > SDCA_MAX_DELAY_COUNT) {
1132 dev_err(dev, "%s: maximum number of transition delays exceeded\n",
1133 entity->label);
1134 return -EINVAL;
1135 }
1136
1137 delay_list = kcalloc(num_delays, sizeof(*delay_list), GFP_KERNEL);
1138 if (!delay_list)
1139 return -ENOMEM;
1140
1141 fwnode_property_read_u32_array(entity_node,
1142 "mipi-sdca-powerdomain-transition-max-delay",
1143 delay_list, num_delays);
1144
1145 num_delays /= mult_delay;
1146
1147 delays = devm_kcalloc(dev, num_delays, sizeof(*delays), GFP_KERNEL);
1148 if (!delays)
1149 return -ENOMEM;
1150
1151 for (i = 0, j = 0; i < num_delays; i++) {
1152 delays[i].from_ps = delay_list[j++];
1153 delays[i].to_ps = delay_list[j++];
1154 delays[i].us = delay_list[j++];
1155
1156 dev_info(dev, "%s: from %#x to %#x delay %dus\n", entity->label,
1157 delays[i].from_ps, delays[i].to_ps, delays[i].us);
1158 }
1159
1160 power->num_max_delay = num_delays;
1161 power->max_delay = delays;
1162
1163 return 0;
1164 }
1165
1166 struct raw_ge_mode {
1167 u8 val;
1168 u8 num_controls;
1169 struct {
1170 u8 id;
1171 u8 sel;
1172 u8 cn;
1173 __le32 val;
1174 } __packed controls[] __counted_by(num_controls);
1175 } __packed;
1176
find_sdca_entity_ge(struct device * dev,struct fwnode_handle * entity_node,struct sdca_entity * entity)1177 static int find_sdca_entity_ge(struct device *dev,
1178 struct fwnode_handle *entity_node,
1179 struct sdca_entity *entity)
1180 {
1181 struct sdca_entity_ge *group = &entity->ge;
1182 u8 *affected_list __free(kfree) = NULL;
1183 u8 *affected_iter;
1184 int num_affected;
1185 int i, j;
1186
1187 num_affected = fwnode_property_count_u8(entity_node,
1188 "mipi-sdca-ge-selectedmode-controls-affected");
1189 if (!num_affected) {
1190 return 0;
1191 } else if (num_affected < 0) {
1192 dev_err(dev, "%s: failed to read affected controls: %d\n",
1193 entity->label, num_affected);
1194 return num_affected;
1195 } else if (num_affected > SDCA_MAX_AFFECTED_COUNT) {
1196 dev_err(dev, "%s: maximum affected controls size exceeded\n",
1197 entity->label);
1198 return -EINVAL;
1199 }
1200
1201 affected_list = kcalloc(num_affected, sizeof(*affected_list), GFP_KERNEL);
1202 if (!affected_list)
1203 return -ENOMEM;
1204
1205 fwnode_property_read_u8_array(entity_node,
1206 "mipi-sdca-ge-selectedmode-controls-affected",
1207 affected_list, num_affected);
1208
1209 group->num_modes = *affected_list;
1210 affected_iter = affected_list + 1;
1211
1212 group->modes = devm_kcalloc(dev, group->num_modes, sizeof(*group->modes),
1213 GFP_KERNEL);
1214 if (!group->modes)
1215 return -ENOMEM;
1216
1217 for (i = 0; i < group->num_modes; i++) {
1218 struct raw_ge_mode *raw = (struct raw_ge_mode *)affected_iter;
1219 struct sdca_ge_mode *mode = &group->modes[i];
1220
1221 affected_iter += sizeof(*raw);
1222 if (affected_iter > affected_list + num_affected)
1223 goto bad_list;
1224
1225 mode->val = raw->val;
1226 mode->num_controls = raw->num_controls;
1227
1228 affected_iter += mode->num_controls * sizeof(raw->controls[0]);
1229 if (affected_iter > affected_list + num_affected)
1230 goto bad_list;
1231
1232 mode->controls = devm_kcalloc(dev, mode->num_controls,
1233 sizeof(*mode->controls), GFP_KERNEL);
1234 if (!mode->controls)
1235 return -ENOMEM;
1236
1237 for (j = 0; j < mode->num_controls; j++) {
1238 mode->controls[j].id = raw->controls[j].id;
1239 mode->controls[j].sel = raw->controls[j].sel;
1240 mode->controls[j].cn = raw->controls[j].cn;
1241 mode->controls[j].val = le32_to_cpu(raw->controls[j].val);
1242 }
1243 }
1244
1245 return 0;
1246
1247 bad_list:
1248 dev_err(dev, "%s: malformed affected controls list\n", entity->label);
1249 return -EINVAL;
1250 }
1251
1252 static int
find_sdca_entity_hide(struct device * dev,struct fwnode_handle * function_node,struct fwnode_handle * entity_node,struct sdca_entity * entity)1253 find_sdca_entity_hide(struct device *dev, struct fwnode_handle *function_node,
1254 struct fwnode_handle *entity_node, struct sdca_entity *entity)
1255 {
1256 struct sdca_entity_hide *hide = &entity->hide;
1257 unsigned int delay, *af_list = hide->af_number_list;
1258 int nval, ret;
1259 unsigned char *report_desc = NULL;
1260
1261 ret = fwnode_property_read_u32(entity_node,
1262 "mipi-sdca-RxUMP-ownership-transition-maxdelay", &delay);
1263 if (!ret)
1264 hide->max_delay = delay;
1265
1266 nval = fwnode_property_count_u32(entity_node, "mipi-sdca-HIDTx-supported-report-ids");
1267 if (nval > 0) {
1268 hide->num_hidtx_ids = nval;
1269 hide->hidtx_ids = devm_kcalloc(dev, hide->num_hidtx_ids,
1270 sizeof(*hide->hidtx_ids), GFP_KERNEL);
1271 if (!hide->hidtx_ids)
1272 return -ENOMEM;
1273
1274 ret = fwnode_property_read_u32_array(entity_node,
1275 "mipi-sdca-HIDTx-supported-report-ids",
1276 hide->hidtx_ids,
1277 hide->num_hidtx_ids);
1278 if (ret < 0)
1279 return ret;
1280 }
1281
1282 nval = fwnode_property_count_u32(entity_node, "mipi-sdca-HIDRx-supported-report-ids");
1283 if (nval > 0) {
1284 hide->num_hidrx_ids = nval;
1285 hide->hidrx_ids = devm_kcalloc(dev, hide->num_hidrx_ids,
1286 sizeof(*hide->hidrx_ids), GFP_KERNEL);
1287 if (!hide->hidrx_ids)
1288 return -ENOMEM;
1289
1290 ret = fwnode_property_read_u32_array(entity_node,
1291 "mipi-sdca-HIDRx-supported-report-ids",
1292 hide->hidrx_ids,
1293 hide->num_hidrx_ids);
1294 if (ret < 0)
1295 return ret;
1296 }
1297
1298 nval = fwnode_property_count_u32(entity_node, "mipi-sdca-hide-related-audio-function-list");
1299 if (nval <= 0) {
1300 dev_err(dev, "%pfwP: audio function numbers list missing: %d\n",
1301 entity_node, nval);
1302 return -EINVAL;
1303 } else if (nval > SDCA_MAX_FUNCTION_COUNT) {
1304 dev_err(dev, "%pfwP: maximum number of audio function exceeded\n", entity_node);
1305 return -EINVAL;
1306 }
1307
1308 hide->hide_reside_function_num = nval;
1309 fwnode_property_read_u32_array(entity_node,
1310 "mipi-sdca-hide-related-audio-function-list", af_list, nval);
1311
1312 nval = fwnode_property_count_u8(function_node, "mipi-sdca-hid-descriptor");
1313 if (nval)
1314 fwnode_property_read_u8_array(function_node, "mipi-sdca-hid-descriptor",
1315 (u8 *)&hide->hid_desc, nval);
1316
1317 if (hide->hid_desc.bNumDescriptors) {
1318 nval = fwnode_property_count_u8(function_node, "mipi-sdca-report-descriptor");
1319 if (nval) {
1320 report_desc = devm_kzalloc(dev, nval, GFP_KERNEL);
1321 if (!report_desc)
1322 return -ENOMEM;
1323 hide->hid_report_desc = report_desc;
1324 fwnode_property_read_u8_array(function_node, "mipi-sdca-report-descriptor",
1325 report_desc, nval);
1326
1327 /* add HID device */
1328 ret = sdca_add_hid_device(dev, entity);
1329 if (ret) {
1330 dev_err(dev, "%pfwP: failed to add HID device: %d\n", entity_node, ret);
1331 return ret;
1332 }
1333 }
1334 }
1335
1336 return 0;
1337 }
1338
find_sdca_entity(struct device * dev,struct fwnode_handle * function_node,struct fwnode_handle * entity_node,struct sdca_entity * entity)1339 static int find_sdca_entity(struct device *dev,
1340 struct fwnode_handle *function_node,
1341 struct fwnode_handle *entity_node,
1342 struct sdca_entity *entity)
1343 {
1344 u32 tmp;
1345 int ret;
1346
1347 ret = fwnode_property_read_string(entity_node, "mipi-sdca-entity-label",
1348 &entity->label);
1349 if (ret) {
1350 dev_err(dev, "%pfwP: entity %#x: label missing: %d\n",
1351 function_node, entity->id, ret);
1352 return ret;
1353 }
1354
1355 ret = fwnode_property_read_u32(entity_node, "mipi-sdca-entity-type", &tmp);
1356 if (ret) {
1357 dev_err(dev, "%s: type missing: %d\n", entity->label, ret);
1358 return ret;
1359 }
1360
1361 entity->type = tmp;
1362
1363 dev_info(dev, "%s: entity %#x type %#x\n",
1364 entity->label, entity->id, entity->type);
1365
1366 switch (entity->type) {
1367 case SDCA_ENTITY_TYPE_IT:
1368 case SDCA_ENTITY_TYPE_OT:
1369 ret = find_sdca_entity_iot(dev, entity_node, entity);
1370 break;
1371 case SDCA_ENTITY_TYPE_CS:
1372 ret = find_sdca_entity_cs(dev, entity_node, entity);
1373 break;
1374 case SDCA_ENTITY_TYPE_PDE:
1375 ret = find_sdca_entity_pde(dev, entity_node, entity);
1376 break;
1377 case SDCA_ENTITY_TYPE_GE:
1378 ret = find_sdca_entity_ge(dev, entity_node, entity);
1379 break;
1380 case SDCA_ENTITY_TYPE_HIDE:
1381 ret = find_sdca_entity_hide(dev, function_node, entity_node, entity);
1382 break;
1383 default:
1384 break;
1385 }
1386 if (ret)
1387 return ret;
1388
1389 ret = find_sdca_entity_controls(dev, entity_node, entity);
1390 if (ret)
1391 return ret;
1392
1393 return 0;
1394 }
1395
find_sdca_entities(struct device * dev,struct fwnode_handle * function_node,struct sdca_function_data * function)1396 static int find_sdca_entities(struct device *dev,
1397 struct fwnode_handle *function_node,
1398 struct sdca_function_data *function)
1399 {
1400 u32 *entity_list __free(kfree) = NULL;
1401 struct sdca_entity *entities;
1402 int num_entities;
1403 int i, ret;
1404
1405 num_entities = fwnode_property_count_u32(function_node,
1406 "mipi-sdca-entity-id-list");
1407 if (num_entities <= 0) {
1408 dev_err(dev, "%pfwP: entity id list missing: %d\n",
1409 function_node, num_entities);
1410 return -EINVAL;
1411 } else if (num_entities > SDCA_MAX_ENTITY_COUNT) {
1412 dev_err(dev, "%pfwP: maximum number of entities exceeded\n",
1413 function_node);
1414 return -EINVAL;
1415 }
1416
1417 /* Add 1 to make space for Entity 0 */
1418 entities = devm_kcalloc(dev, num_entities + 1, sizeof(*entities), GFP_KERNEL);
1419 if (!entities)
1420 return -ENOMEM;
1421
1422 entity_list = kcalloc(num_entities, sizeof(*entity_list), GFP_KERNEL);
1423 if (!entity_list)
1424 return -ENOMEM;
1425
1426 fwnode_property_read_u32_array(function_node, "mipi-sdca-entity-id-list",
1427 entity_list, num_entities);
1428
1429 for (i = 0; i < num_entities; i++)
1430 entities[i].id = entity_list[i];
1431
1432 /* now read subproperties */
1433 for (i = 0; i < num_entities; i++) {
1434 char entity_property[SDCA_PROPERTY_LENGTH];
1435 struct fwnode_handle *entity_node;
1436
1437 /* DisCo uses upper-case for hex numbers */
1438 snprintf(entity_property, sizeof(entity_property),
1439 "mipi-sdca-entity-id-0x%X-subproperties", entities[i].id);
1440
1441 entity_node = fwnode_get_named_child_node(function_node, entity_property);
1442 if (!entity_node) {
1443 dev_err(dev, "%pfwP: entity node %s not found\n",
1444 function_node, entity_property);
1445 return -EINVAL;
1446 }
1447
1448 ret = find_sdca_entity(dev, function_node, entity_node, &entities[i]);
1449 fwnode_handle_put(entity_node);
1450 if (ret)
1451 return ret;
1452 }
1453
1454 /*
1455 * Add Entity 0 at end of the array, makes it easy to skip during
1456 * all the Entity searches involved in creating connections.
1457 */
1458 entities[num_entities].label = "entity0";
1459
1460 ret = find_sdca_entity_controls(dev, function_node, &entities[num_entities]);
1461 if (ret)
1462 return ret;
1463
1464 function->num_entities = num_entities + 1;
1465 function->entities = entities;
1466
1467 return 0;
1468 }
1469
find_sdca_entity_by_label(struct sdca_function_data * function,const char * entity_label)1470 static struct sdca_entity *find_sdca_entity_by_label(struct sdca_function_data *function,
1471 const char *entity_label)
1472 {
1473 int i;
1474
1475 for (i = 0; i < function->num_entities; i++) {
1476 struct sdca_entity *entity = &function->entities[i];
1477
1478 if (!strcmp(entity->label, entity_label))
1479 return entity;
1480 }
1481
1482 return NULL;
1483 }
1484
find_sdca_entity_by_id(struct sdca_function_data * function,const int id)1485 static struct sdca_entity *find_sdca_entity_by_id(struct sdca_function_data *function,
1486 const int id)
1487 {
1488 int i;
1489
1490 for (i = 0; i < function->num_entities; i++) {
1491 struct sdca_entity *entity = &function->entities[i];
1492
1493 if (entity->id == id)
1494 return entity;
1495 }
1496
1497 return NULL;
1498 }
1499
find_sdca_entity_connection_iot(struct device * dev,struct sdca_function_data * function,struct fwnode_handle * entity_node,struct sdca_entity * entity)1500 static int find_sdca_entity_connection_iot(struct device *dev,
1501 struct sdca_function_data *function,
1502 struct fwnode_handle *entity_node,
1503 struct sdca_entity *entity)
1504 {
1505 struct sdca_entity_iot *terminal = &entity->iot;
1506 struct fwnode_handle *clock_node;
1507 struct sdca_entity *clock_entity;
1508 const char *clock_label;
1509 int ret;
1510
1511 clock_node = fwnode_get_named_child_node(entity_node,
1512 "mipi-sdca-terminal-clock-connection");
1513 if (!clock_node)
1514 return 0;
1515
1516 ret = fwnode_property_read_string(clock_node, "mipi-sdca-entity-label",
1517 &clock_label);
1518 if (ret) {
1519 dev_err(dev, "%s: clock label missing: %d\n", entity->label, ret);
1520 fwnode_handle_put(clock_node);
1521 return ret;
1522 }
1523
1524 clock_entity = find_sdca_entity_by_label(function, clock_label);
1525 if (!clock_entity) {
1526 dev_err(dev, "%s: failed to find clock with label %s\n",
1527 entity->label, clock_label);
1528 fwnode_handle_put(clock_node);
1529 return -EINVAL;
1530 }
1531
1532 terminal->clock = clock_entity;
1533
1534 dev_info(dev, "%s -> %s\n", clock_entity->label, entity->label);
1535
1536 fwnode_handle_put(clock_node);
1537 return 0;
1538 }
1539
find_sdca_entity_connection_pde(struct device * dev,struct sdca_function_data * function,struct fwnode_handle * entity_node,struct sdca_entity * entity)1540 static int find_sdca_entity_connection_pde(struct device *dev,
1541 struct sdca_function_data *function,
1542 struct fwnode_handle *entity_node,
1543 struct sdca_entity *entity)
1544 {
1545 struct sdca_entity_pde *power = &entity->pde;
1546 u32 *managed_list __free(kfree) = NULL;
1547 struct sdca_entity **managed;
1548 int num_managed;
1549 int i;
1550
1551 num_managed = fwnode_property_count_u32(entity_node,
1552 "mipi-sdca-powerdomain-managed-list");
1553 if (!num_managed) {
1554 return 0;
1555 } else if (num_managed < 0) {
1556 dev_err(dev, "%s: managed list missing: %d\n", entity->label, num_managed);
1557 return num_managed;
1558 } else if (num_managed > SDCA_MAX_ENTITY_COUNT) {
1559 dev_err(dev, "%s: maximum number of managed entities exceeded\n",
1560 entity->label);
1561 return -EINVAL;
1562 }
1563
1564 managed = devm_kcalloc(dev, num_managed, sizeof(*managed), GFP_KERNEL);
1565 if (!managed)
1566 return -ENOMEM;
1567
1568 managed_list = kcalloc(num_managed, sizeof(*managed_list), GFP_KERNEL);
1569 if (!managed_list)
1570 return -ENOMEM;
1571
1572 fwnode_property_read_u32_array(entity_node,
1573 "mipi-sdca-powerdomain-managed-list",
1574 managed_list, num_managed);
1575
1576 for (i = 0; i < num_managed; i++) {
1577 managed[i] = find_sdca_entity_by_id(function, managed_list[i]);
1578 if (!managed[i]) {
1579 dev_err(dev, "%s: failed to find entity with id %#x\n",
1580 entity->label, managed_list[i]);
1581 return -EINVAL;
1582 }
1583
1584 dev_info(dev, "%s -> %s\n", managed[i]->label, entity->label);
1585 }
1586
1587 power->num_managed = num_managed;
1588 power->managed = managed;
1589
1590 return 0;
1591 }
1592
find_sdca_entity_connection_ge(struct device * dev,struct sdca_function_data * function,struct fwnode_handle * entity_node,struct sdca_entity * entity)1593 static int find_sdca_entity_connection_ge(struct device *dev,
1594 struct sdca_function_data *function,
1595 struct fwnode_handle *entity_node,
1596 struct sdca_entity *entity)
1597 {
1598 int i, j;
1599
1600 for (i = 0; i < entity->ge.num_modes; i++) {
1601 struct sdca_ge_mode *mode = &entity->ge.modes[i];
1602
1603 for (j = 0; j < mode->num_controls; j++) {
1604 struct sdca_ge_control *affected = &mode->controls[j];
1605 struct sdca_entity *managed;
1606
1607 managed = find_sdca_entity_by_id(function, affected->id);
1608 if (!managed) {
1609 dev_err(dev, "%s: failed to find entity with id %#x\n",
1610 entity->label, affected->id);
1611 return -EINVAL;
1612 }
1613
1614 if (managed->group && managed->group != entity) {
1615 dev_err(dev,
1616 "%s: entity controlled by two groups %s, %s\n",
1617 managed->label, managed->group->label,
1618 entity->label);
1619 return -EINVAL;
1620 }
1621
1622 managed->group = entity;
1623 }
1624 }
1625
1626 return 0;
1627 }
1628
find_sdca_entity_connection(struct device * dev,struct sdca_function_data * function,struct fwnode_handle * entity_node,struct sdca_entity * entity)1629 static int find_sdca_entity_connection(struct device *dev,
1630 struct sdca_function_data *function,
1631 struct fwnode_handle *entity_node,
1632 struct sdca_entity *entity)
1633 {
1634 struct sdca_entity **pins;
1635 int num_pins, pin;
1636 u64 pin_list;
1637 int i, ret;
1638
1639 switch (entity->type) {
1640 case SDCA_ENTITY_TYPE_IT:
1641 case SDCA_ENTITY_TYPE_OT:
1642 ret = find_sdca_entity_connection_iot(dev, function,
1643 entity_node, entity);
1644 break;
1645 case SDCA_ENTITY_TYPE_PDE:
1646 ret = find_sdca_entity_connection_pde(dev, function,
1647 entity_node, entity);
1648 break;
1649 case SDCA_ENTITY_TYPE_GE:
1650 ret = find_sdca_entity_connection_ge(dev, function,
1651 entity_node, entity);
1652 break;
1653 default:
1654 ret = 0;
1655 break;
1656 }
1657 if (ret)
1658 return ret;
1659
1660 ret = fwnode_property_read_u64(entity_node, "mipi-sdca-input-pin-list", &pin_list);
1661 if (ret == -EINVAL) {
1662 /* Allow missing pin lists, assume no pins. */
1663 return 0;
1664 } else if (ret) {
1665 dev_err(dev, "%s: failed to read pin list: %d\n", entity->label, ret);
1666 return ret;
1667 } else if (pin_list & BIT(0)) {
1668 /*
1669 * Each bit set in the pin-list refers to an entity_id in this
1670 * Function. Entity 0 is an illegal connection since it is used
1671 * for Function-level configurations.
1672 */
1673 dev_err(dev, "%s: pin 0 used as input\n", entity->label);
1674 return -EINVAL;
1675 } else if (!pin_list) {
1676 return 0;
1677 }
1678
1679 num_pins = hweight64(pin_list);
1680 pins = devm_kcalloc(dev, num_pins, sizeof(*pins), GFP_KERNEL);
1681 if (!pins)
1682 return -ENOMEM;
1683
1684 i = 0;
1685 for_each_set_bit(pin, (unsigned long *)&pin_list, BITS_PER_TYPE(pin_list)) {
1686 char pin_property[SDCA_PROPERTY_LENGTH];
1687 struct fwnode_handle *connected_node;
1688 struct sdca_entity *connected_entity;
1689 const char *connected_label;
1690
1691 snprintf(pin_property, sizeof(pin_property), "mipi-sdca-input-pin-%d", pin);
1692
1693 connected_node = fwnode_get_named_child_node(entity_node, pin_property);
1694 if (!connected_node) {
1695 dev_err(dev, "%s: pin node %s not found\n",
1696 entity->label, pin_property);
1697 return -EINVAL;
1698 }
1699
1700 ret = fwnode_property_read_string(connected_node, "mipi-sdca-entity-label",
1701 &connected_label);
1702 if (ret) {
1703 dev_err(dev, "%s: pin %d label missing: %d\n",
1704 entity->label, pin, ret);
1705 fwnode_handle_put(connected_node);
1706 return ret;
1707 }
1708
1709 connected_entity = find_sdca_entity_by_label(function, connected_label);
1710 if (!connected_entity) {
1711 dev_err(dev, "%s: failed to find entity with label %s\n",
1712 entity->label, connected_label);
1713 fwnode_handle_put(connected_node);
1714 return -EINVAL;
1715 }
1716
1717 pins[i] = connected_entity;
1718
1719 dev_info(dev, "%s -> %s\n", connected_entity->label, entity->label);
1720
1721 i++;
1722 fwnode_handle_put(connected_node);
1723 }
1724
1725 entity->num_sources = num_pins;
1726 entity->sources = pins;
1727
1728 return 0;
1729 }
1730
find_sdca_connections(struct device * dev,struct fwnode_handle * function_node,struct sdca_function_data * function)1731 static int find_sdca_connections(struct device *dev,
1732 struct fwnode_handle *function_node,
1733 struct sdca_function_data *function)
1734 {
1735 int i;
1736
1737 /* Entity 0 cannot have connections */
1738 for (i = 0; i < function->num_entities - 1; i++) {
1739 struct sdca_entity *entity = &function->entities[i];
1740 char entity_property[SDCA_PROPERTY_LENGTH];
1741 struct fwnode_handle *entity_node;
1742 int ret;
1743
1744 /* DisCo uses upper-case for hex numbers */
1745 snprintf(entity_property, sizeof(entity_property),
1746 "mipi-sdca-entity-id-0x%X-subproperties",
1747 entity->id);
1748
1749 entity_node = fwnode_get_named_child_node(function_node, entity_property);
1750 if (!entity_node) {
1751 dev_err(dev, "%pfwP: entity node %s not found\n",
1752 function_node, entity_property);
1753 return -EINVAL;
1754 }
1755
1756 ret = find_sdca_entity_connection(dev, function, entity_node, entity);
1757 fwnode_handle_put(entity_node);
1758 if (ret)
1759 return ret;
1760 }
1761
1762 return 0;
1763 }
1764
find_sdca_cluster_channel(struct device * dev,struct sdca_cluster * cluster,struct fwnode_handle * channel_node,struct sdca_channel * channel)1765 static int find_sdca_cluster_channel(struct device *dev,
1766 struct sdca_cluster *cluster,
1767 struct fwnode_handle *channel_node,
1768 struct sdca_channel *channel)
1769 {
1770 u32 tmp;
1771 int ret;
1772
1773 ret = fwnode_property_read_u32(channel_node, "mipi-sdca-cluster-channel-id", &tmp);
1774 if (ret) {
1775 dev_err(dev, "cluster %#x: missing channel id: %d\n",
1776 cluster->id, ret);
1777 return ret;
1778 }
1779
1780 channel->id = tmp;
1781
1782 ret = fwnode_property_read_u32(channel_node,
1783 "mipi-sdca-cluster-channel-purpose",
1784 &tmp);
1785 if (ret) {
1786 dev_err(dev, "cluster %#x: channel %#x: missing purpose: %d\n",
1787 cluster->id, channel->id, ret);
1788 return ret;
1789 }
1790
1791 channel->purpose = tmp;
1792
1793 ret = fwnode_property_read_u32(channel_node,
1794 "mipi-sdca-cluster-channel-relationship",
1795 &tmp);
1796 if (ret) {
1797 dev_err(dev, "cluster %#x: channel %#x: missing relationship: %d\n",
1798 cluster->id, channel->id, ret);
1799 return ret;
1800 }
1801
1802 channel->relationship = tmp;
1803
1804 dev_info(dev, "cluster %#x: channel id %#x purpose %#x relationship %#x\n",
1805 cluster->id, channel->id, channel->purpose, channel->relationship);
1806
1807 return 0;
1808 }
1809
find_sdca_cluster_channels(struct device * dev,struct fwnode_handle * cluster_node,struct sdca_cluster * cluster)1810 static int find_sdca_cluster_channels(struct device *dev,
1811 struct fwnode_handle *cluster_node,
1812 struct sdca_cluster *cluster)
1813 {
1814 struct sdca_channel *channels;
1815 u32 num_channels;
1816 int i, ret;
1817
1818 ret = fwnode_property_read_u32(cluster_node, "mipi-sdca-channel-count",
1819 &num_channels);
1820 if (ret < 0) {
1821 dev_err(dev, "cluster %#x: failed to read channel list: %d\n",
1822 cluster->id, ret);
1823 return ret;
1824 } else if (num_channels > SDCA_MAX_CHANNEL_COUNT) {
1825 dev_err(dev, "cluster %#x: maximum number of channels exceeded\n",
1826 cluster->id);
1827 return -EINVAL;
1828 }
1829
1830 channels = devm_kcalloc(dev, num_channels, sizeof(*channels), GFP_KERNEL);
1831 if (!channels)
1832 return -ENOMEM;
1833
1834 for (i = 0; i < num_channels; i++) {
1835 char channel_property[SDCA_PROPERTY_LENGTH];
1836 struct fwnode_handle *channel_node;
1837
1838 /* DisCo uses upper-case for hex numbers */
1839 snprintf(channel_property, sizeof(channel_property),
1840 "mipi-sdca-channel-%d-subproperties", i + 1);
1841
1842 channel_node = fwnode_get_named_child_node(cluster_node, channel_property);
1843 if (!channel_node) {
1844 dev_err(dev, "cluster %#x: channel node %s not found\n",
1845 cluster->id, channel_property);
1846 return -EINVAL;
1847 }
1848
1849 ret = find_sdca_cluster_channel(dev, cluster, channel_node, &channels[i]);
1850 fwnode_handle_put(channel_node);
1851 if (ret)
1852 return ret;
1853 }
1854
1855 cluster->num_channels = num_channels;
1856 cluster->channels = channels;
1857
1858 return 0;
1859 }
1860
find_sdca_clusters(struct device * dev,struct fwnode_handle * function_node,struct sdca_function_data * function)1861 static int find_sdca_clusters(struct device *dev,
1862 struct fwnode_handle *function_node,
1863 struct sdca_function_data *function)
1864 {
1865 u32 *cluster_list __free(kfree) = NULL;
1866 struct sdca_cluster *clusters;
1867 int num_clusters;
1868 int i, ret;
1869
1870 num_clusters = fwnode_property_count_u32(function_node, "mipi-sdca-cluster-id-list");
1871 if (!num_clusters || num_clusters == -EINVAL) {
1872 return 0;
1873 } else if (num_clusters < 0) {
1874 dev_err(dev, "%pfwP: failed to read cluster id list: %d\n",
1875 function_node, num_clusters);
1876 return num_clusters;
1877 } else if (num_clusters > SDCA_MAX_CLUSTER_COUNT) {
1878 dev_err(dev, "%pfwP: maximum number of clusters exceeded\n", function_node);
1879 return -EINVAL;
1880 }
1881
1882 clusters = devm_kcalloc(dev, num_clusters, sizeof(*clusters), GFP_KERNEL);
1883 if (!clusters)
1884 return -ENOMEM;
1885
1886 cluster_list = kcalloc(num_clusters, sizeof(*cluster_list), GFP_KERNEL);
1887 if (!cluster_list)
1888 return -ENOMEM;
1889
1890 fwnode_property_read_u32_array(function_node, "mipi-sdca-cluster-id-list",
1891 cluster_list, num_clusters);
1892
1893 for (i = 0; i < num_clusters; i++)
1894 clusters[i].id = cluster_list[i];
1895
1896 /* now read subproperties */
1897 for (i = 0; i < num_clusters; i++) {
1898 char cluster_property[SDCA_PROPERTY_LENGTH];
1899 struct fwnode_handle *cluster_node;
1900
1901 /* DisCo uses upper-case for hex numbers */
1902 snprintf(cluster_property, sizeof(cluster_property),
1903 "mipi-sdca-cluster-id-0x%X-subproperties", clusters[i].id);
1904
1905 cluster_node = fwnode_get_named_child_node(function_node, cluster_property);
1906 if (!cluster_node) {
1907 dev_err(dev, "%pfwP: cluster node %s not found\n",
1908 function_node, cluster_property);
1909 return -EINVAL;
1910 }
1911
1912 ret = find_sdca_cluster_channels(dev, cluster_node, &clusters[i]);
1913 fwnode_handle_put(cluster_node);
1914 if (ret)
1915 return ret;
1916 }
1917
1918 function->num_clusters = num_clusters;
1919 function->clusters = clusters;
1920
1921 return 0;
1922 }
1923
1924 /**
1925 * sdca_parse_function - parse ACPI DisCo for a Function
1926 * @dev: Pointer to device against which function data will be allocated.
1927 * @function_desc: Pointer to the Function short descriptor.
1928 * @function: Pointer to the Function information, to be populated.
1929 *
1930 * Return: Returns 0 for success.
1931 */
sdca_parse_function(struct device * dev,struct sdca_function_desc * function_desc,struct sdca_function_data * function)1932 int sdca_parse_function(struct device *dev,
1933 struct sdca_function_desc *function_desc,
1934 struct sdca_function_data *function)
1935 {
1936 u32 tmp;
1937 int ret;
1938
1939 function->desc = function_desc;
1940
1941 ret = fwnode_property_read_u32(function_desc->node,
1942 "mipi-sdca-function-busy-max-delay", &tmp);
1943 if (!ret)
1944 function->busy_max_delay = tmp;
1945
1946 dev_info(dev, "%pfwP: name %s delay %dus\n", function->desc->node,
1947 function->desc->name, function->busy_max_delay);
1948
1949 ret = find_sdca_init_table(dev, function_desc->node, function);
1950 if (ret)
1951 return ret;
1952
1953 ret = find_sdca_entities(dev, function_desc->node, function);
1954 if (ret)
1955 return ret;
1956
1957 ret = find_sdca_connections(dev, function_desc->node, function);
1958 if (ret)
1959 return ret;
1960
1961 ret = find_sdca_clusters(dev, function_desc->node, function);
1962 if (ret < 0)
1963 return ret;
1964
1965 return 0;
1966 }
1967 EXPORT_SYMBOL_NS(sdca_parse_function, "SND_SOC_SDCA");
1968
sdca_selector_find_control(struct device * dev,struct sdca_entity * entity,const int sel)1969 struct sdca_control *sdca_selector_find_control(struct device *dev,
1970 struct sdca_entity *entity,
1971 const int sel)
1972 {
1973 int i;
1974
1975 for (i = 0; i < entity->num_controls; i++) {
1976 struct sdca_control *control = &entity->controls[i];
1977
1978 if (control->sel == sel)
1979 return control;
1980 }
1981
1982 dev_err(dev, "%s: control %#x: missing\n", entity->label, sel);
1983 return NULL;
1984 }
1985 EXPORT_SYMBOL_NS(sdca_selector_find_control, "SND_SOC_SDCA");
1986
sdca_control_find_range(struct device * dev,struct sdca_entity * entity,struct sdca_control * control,int cols,int rows)1987 struct sdca_control_range *sdca_control_find_range(struct device *dev,
1988 struct sdca_entity *entity,
1989 struct sdca_control *control,
1990 int cols, int rows)
1991 {
1992 struct sdca_control_range *range = &control->range;
1993
1994 if ((cols && range->cols != cols) || (rows && range->rows != rows) ||
1995 !range->data) {
1996 dev_err(dev, "%s: control %#x: ranges invalid (%d,%d)\n",
1997 entity->label, control->sel, range->cols, range->rows);
1998 return NULL;
1999 }
2000
2001 return range;
2002 }
2003 EXPORT_SYMBOL_NS(sdca_control_find_range, "SND_SOC_SDCA");
2004
sdca_selector_find_range(struct device * dev,struct sdca_entity * entity,int sel,int cols,int rows)2005 struct sdca_control_range *sdca_selector_find_range(struct device *dev,
2006 struct sdca_entity *entity,
2007 int sel, int cols, int rows)
2008 {
2009 struct sdca_control *control;
2010
2011 control = sdca_selector_find_control(dev, entity, sel);
2012 if (!control)
2013 return NULL;
2014
2015 return sdca_control_find_range(dev, entity, control, cols, rows);
2016 }
2017 EXPORT_SYMBOL_NS(sdca_selector_find_range, "SND_SOC_SDCA");
2018
sdca_id_find_cluster(struct device * dev,struct sdca_function_data * function,const int id)2019 struct sdca_cluster *sdca_id_find_cluster(struct device *dev,
2020 struct sdca_function_data *function,
2021 const int id)
2022 {
2023 int i;
2024
2025 for (i = 0; i < function->num_clusters; i++) {
2026 struct sdca_cluster *cluster = &function->clusters[i];
2027
2028 if (cluster->id == id)
2029 return cluster;
2030 }
2031
2032 dev_err(dev, "%s: cluster %#x: missing\n", function->desc->name, id);
2033 return NULL;
2034 }
2035 EXPORT_SYMBOL_NS(sdca_id_find_cluster, "SND_SOC_SDCA");
2036
2037 MODULE_LICENSE("Dual BSD/GPL");
2038 MODULE_DESCRIPTION("SDCA library");
2039