|
10 | 10 | #include <sof/ipc/msg.h> |
11 | 11 | #include <stdbool.h> |
12 | 12 | #include <ipc4/notification.h> |
| 13 | +#include <sof/ipc/notification_pool.h> |
13 | 14 |
|
14 | 15 | #include <rtos/symbol.h> |
15 | 16 |
|
16 | | -static void resource_notif_header_init(struct ipc_msg *msg) |
| 17 | +static bool send_resource_notif(uint32_t resource_id, uint32_t event_type, uint32_t resource_type, |
| 18 | + void *data, uint32_t data_size) |
17 | 19 | { |
18 | | - struct ipc4_resource_event_data_notification *notif_data = msg->tx_data; |
| 20 | + struct ipc_msg *msg = ipc_notification_pool_get(IPC4_RESOURCE_EVENT_SIZE); |
| 21 | + |
| 22 | + if (!msg) |
| 23 | + return false; |
| 24 | + |
| 25 | + struct ipc4_resource_event_data_notification *notif = msg->tx_data; |
19 | 26 | union ipc4_notification_header header; |
20 | 27 |
|
21 | 28 | header.r.notif_type = SOF_IPC4_NOTIFY_RESOURCE_EVENT; |
22 | 29 | header.r.type = SOF_IPC4_GLB_NOTIFICATION; |
23 | 30 | header.r.rsp = SOF_IPC4_MESSAGE_DIR_MSG_REQUEST; |
24 | 31 | header.r.msg_tgt = SOF_IPC4_MESSAGE_TARGET_FW_GEN_MSG; |
25 | 32 | msg->header = header.dat; |
26 | | - memset(¬if_data->event_data, 0, sizeof(notif_data->event_data)); |
| 33 | + |
| 34 | + notif->resource_id = resource_id; |
| 35 | + notif->event_type = event_type; |
| 36 | + notif->resource_type = resource_type; |
| 37 | + memset(¬if->event_data, 0, sizeof(notif->event_data)); |
| 38 | + if (data && data_size) { |
| 39 | + int ret = memcpy_s(¬if->event_data, sizeof(notif->event_data), data, data_size); |
| 40 | + |
| 41 | + if (!ret) { |
| 42 | + /* Most likely a simple coding mistake: |
| 43 | + * Using a data type that is not included in the event_data union. |
| 44 | + * Return true to prevent an infinite re-try loop in non-debug builds |
| 45 | + */ |
| 46 | + assert(false); |
| 47 | + return true; |
| 48 | + } |
| 49 | + } |
| 50 | + |
| 51 | + ipc_msg_send(msg, msg->tx_data, false); |
| 52 | + |
| 53 | + return true; |
27 | 54 | } |
28 | 55 |
|
29 | | -void copier_gateway_underrun_notif_msg_init(struct ipc_msg *msg, uint32_t pipeline_id) |
| 56 | +static enum sof_ipc4_resource_event_type dir_to_xrun_event(enum sof_ipc_stream_direction dir) |
30 | 57 | { |
31 | | - struct ipc4_resource_event_data_notification *notif_data = msg->tx_data; |
32 | | - |
33 | | - resource_notif_header_init(msg); |
34 | | - notif_data->resource_id = pipeline_id; |
35 | | - notif_data->event_type = SOF_IPC4_GATEWAY_UNDERRUN_DETECTED; |
36 | | - notif_data->resource_type = SOF_IPC4_PIPELINE; |
| 58 | + return (dir == SOF_IPC_STREAM_PLAYBACK) ? SOF_IPC4_GATEWAY_UNDERRUN_DETECTED : |
| 59 | + SOF_IPC4_GATEWAY_OVERRUN_DETECTED; |
37 | 60 | } |
38 | 61 |
|
39 | | -void gateway_underrun_notif_msg_init(struct ipc_msg *msg, uint32_t resource_id) |
| 62 | +bool send_copier_gateway_xrun_notif_msg(uint32_t pipeline_id, enum sof_ipc_stream_direction dir) |
40 | 63 | { |
41 | | - struct ipc4_resource_event_data_notification *notif_data = msg->tx_data; |
42 | | - |
43 | | - resource_notif_header_init(msg); |
44 | | - notif_data->resource_id = resource_id; |
45 | | - notif_data->event_type = SOF_IPC4_GATEWAY_UNDERRUN_DETECTED; |
46 | | - notif_data->resource_type = SOF_IPC4_GATEWAY; |
| 64 | + return send_resource_notif(pipeline_id, dir_to_xrun_event(dir), SOF_IPC4_PIPELINE, NULL, |
| 65 | + 0); |
47 | 66 | } |
48 | 67 |
|
49 | | -void copier_gateway_overrun_notif_msg_init(struct ipc_msg *msg, uint32_t pipeline_id) |
| 68 | +bool send_gateway_xrun_notif_msg(uint32_t resource_id, enum sof_ipc_stream_direction dir) |
50 | 69 | { |
51 | | - struct ipc4_resource_event_data_notification *notif_data = msg->tx_data; |
52 | | - |
53 | | - resource_notif_header_init(msg); |
54 | | - notif_data->resource_id = pipeline_id; |
55 | | - notif_data->event_type = SOF_IPC4_GATEWAY_OVERRUN_DETECTED; |
56 | | - notif_data->resource_type = SOF_IPC4_PIPELINE; |
| 70 | + return send_resource_notif(resource_id, dir_to_xrun_event(dir), SOF_IPC4_GATEWAY, NULL, 0); |
57 | 71 | } |
58 | 72 |
|
59 | | -void gateway_overrun_notif_msg_init(struct ipc_msg *msg, uint32_t resource_id) |
| 73 | +void send_mixer_underrun_notif_msg(uint32_t resource_id, uint32_t eos_flag, uint32_t data_mixed, |
| 74 | + uint32_t expected_data_mixed) |
60 | 75 | { |
61 | | - struct ipc4_resource_event_data_notification *notif_data = msg->tx_data; |
| 76 | + struct ipc4_mixer_underrun_event_data mixer_underrun_data; |
62 | 77 |
|
63 | | - resource_notif_header_init(msg); |
64 | | - notif_data->resource_id = resource_id; |
65 | | - notif_data->event_type = SOF_IPC4_GATEWAY_OVERRUN_DETECTED; |
66 | | - notif_data->resource_type = SOF_IPC4_GATEWAY; |
67 | | -} |
| 78 | + mixer_underrun_data.eos_flag = eos_flag; |
| 79 | + mixer_underrun_data.data_mixed = data_mixed; |
| 80 | + mixer_underrun_data.expected_data_mixed = expected_data_mixed; |
68 | 81 |
|
69 | | -void mixer_underrun_notif_msg_init(struct ipc_msg *msg, uint32_t resource_id, uint32_t eos_flag, |
70 | | - uint32_t data_mixed, uint32_t expected_data_mixed) |
71 | | -{ |
72 | | - struct ipc4_resource_event_data_notification *notif_data = msg->tx_data; |
73 | | - |
74 | | - resource_notif_header_init(msg); |
75 | | - notif_data->resource_id = resource_id; |
76 | | - notif_data->event_type = SOF_IPC4_MIXER_UNDERRUN_DETECTED; |
77 | | - notif_data->resource_type = SOF_IPC4_PIPELINE; |
78 | | - notif_data->event_data.mixer_underrun.eos_flag = eos_flag; |
79 | | - notif_data->event_data.mixer_underrun.data_mixed = data_mixed; |
80 | | - notif_data->event_data.mixer_underrun.expected_data_mixed = expected_data_mixed; |
| 82 | + send_resource_notif(resource_id, SOF_IPC4_MIXER_UNDERRUN_DETECTED, SOF_IPC4_PIPELINE, |
| 83 | + &mixer_underrun_data, sizeof(mixer_underrun_data)); |
81 | 84 | } |
82 | | -EXPORT_SYMBOL(mixer_underrun_notif_msg_init); |
| 85 | +EXPORT_SYMBOL(send_mixer_underrun_notif_msg); |
83 | 86 |
|
84 | | -void process_data_error_notif_msg_init(struct ipc_msg *msg, uint32_t resource_id, |
85 | | - uint32_t error_code) |
| 87 | +void send_process_data_error_notif_msg(uint32_t resource_id, uint32_t error_code) |
86 | 88 | { |
87 | | - struct ipc4_resource_event_data_notification *notif_data = msg->tx_data; |
| 89 | + struct ipc4_process_data_error_event_data error_data; |
| 90 | + |
| 91 | + error_data.error_code = error_code; |
88 | 92 |
|
89 | | - resource_notif_header_init(msg); |
90 | | - notif_data->resource_id = resource_id; |
91 | | - notif_data->event_type = SOF_IPC4_PROCESS_DATA_ERROR; |
92 | | - notif_data->resource_type = SOF_IPC4_MODULE_INSTANCE; |
93 | | - notif_data->event_data.process_data_error.error_code = error_code; |
| 93 | + send_resource_notif(resource_id, SOF_IPC4_PROCESS_DATA_ERROR, SOF_IPC4_MODULE_INSTANCE, |
| 94 | + &error_data, sizeof(error_data)); |
94 | 95 | } |
0 commit comments