forked from thesofproject/sof
-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathpipeline.c
More file actions
131 lines (112 loc) · 3.61 KB
/
pipeline.c
File metadata and controls
131 lines (112 loc) · 3.61 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
// SPDX-License-Identifier: BSD-3-Clause
//
// Copyright(c) 2019 Intel Corporation. All rights reserved.
//
// Author: Ranjani Sridharan <ranjani.sridharan@linux.intel.com>
/* Topology parser */
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <stddef.h>
#include <errno.h>
#include <string.h>
#include <ipc/topology.h>
#include <sof/lib/uuid.h>
#include <sof/ipc/topology.h>
#include <tplg_parser/topology.h>
#include <tplg_parser/tokens.h>
/* scheduling */
static const struct sof_topology_token sched_tokens[] = {
{SOF_TKN_SCHED_PERIOD, SND_SOC_TPLG_TUPLE_TYPE_WORD,
get_token_uint32_t,
offsetof(struct sof_ipc_pipe_new, period), 0},
{SOF_TKN_SCHED_PRIORITY, SND_SOC_TPLG_TUPLE_TYPE_WORD,
get_token_uint32_t,
offsetof(struct sof_ipc_pipe_new, priority), 0},
{SOF_TKN_SCHED_MIPS, SND_SOC_TPLG_TUPLE_TYPE_WORD,
get_token_uint32_t,
offsetof(struct sof_ipc_pipe_new, period_mips), 0},
{SOF_TKN_SCHED_CORE, SND_SOC_TPLG_TUPLE_TYPE_WORD,
get_token_uint32_t,
offsetof(struct sof_ipc_pipe_new, core), 0},
{SOF_TKN_SCHED_FRAMES, SND_SOC_TPLG_TUPLE_TYPE_WORD,
get_token_uint32_t,
offsetof(struct sof_ipc_pipe_new, frames_per_sched), 0},
{SOF_TKN_SCHED_TIME_DOMAIN, SND_SOC_TPLG_TUPLE_TYPE_WORD,
get_token_uint32_t,
offsetof(struct sof_ipc_pipe_new, time_domain), 0},
};
/* load scheduler dapm widget */
int tplg_create_pipeline(struct tplg_context *ctx,
struct sof_ipc_pipe_new *pipeline)
{
struct snd_soc_tplg_vendor_array *array = NULL;
size_t total_array_size = 0, read_size;
FILE *file = ctx->file;
int size = ctx->widget->priv.size;
int comp_id = ctx->comp_id;
int ret;
/* configure pipeline */
pipeline->comp_id = comp_id;
pipeline->pipeline_id = ctx->pipeline_id;
pipeline->hdr.size = sizeof(*pipeline);
pipeline->hdr.cmd = SOF_IPC_GLB_TPLG_MSG | SOF_IPC_TPLG_PIPE_NEW;
/* allocate memory for vendor tuple array */
array = (struct snd_soc_tplg_vendor_array *)malloc(size);
if (!array) {
fprintf(stderr, "error: mem alloc\n");
return -errno;
}
/* read vendor arrays */
while (total_array_size < size) {
read_size = sizeof(struct snd_soc_tplg_vendor_array);
ret = fread(array, read_size, 1, file);
if (ret != 1) {
free(MOVE_POINTER_BY_BYTES(array, -total_array_size));
return -EINVAL;
}
/* check for array size mismatch */
if (!is_valid_priv_size(total_array_size, size, array)) {
fprintf(stderr, "error: load pipeline array size mismatch\n");
free(MOVE_POINTER_BY_BYTES(array, -total_array_size));
return -EINVAL;
}
ret = tplg_read_array(array, file);
if (ret) {
fprintf(stderr, "error: read array fail\n");
free(MOVE_POINTER_BY_BYTES(array, -total_array_size));
return -EINVAL;
}
/* parse scheduler tokens */
ret = sof_parse_tokens(pipeline, sched_tokens,
ARRAY_SIZE(sched_tokens), array,
array->size);
if (ret != 0) {
fprintf(stderr, "error: parse pipeline tokens %d\n",
size);
free(MOVE_POINTER_BY_BYTES(array, -total_array_size));
return -EINVAL;
}
total_array_size += array->size;
/* read next array */
array = MOVE_POINTER_BY_BYTES(array, array->size);
}
/* point to the start of array so it gets freed properly */
array = MOVE_POINTER_BY_BYTES(array, -total_array_size);
free(array);
return 0;
}
/* load pipeline dapm widget */
int tplg_new_pipeline(struct tplg_context *ctx, struct sof_ipc_pipe_new *pipeline,
struct snd_soc_tplg_ctl_hdr *rctl)
{
int ret;
ret = tplg_create_pipeline(ctx, pipeline);
if (ret < 0)
return ret;
if (tplg_create_controls(ctx->widget->num_kcontrols, ctx->file, rctl, 0) < 0) {
fprintf(stderr, "error: loading controls\n");
return -EINVAL;
}
return ret;
}