117 std::string
const& workflowSuffix,
118 std::vector<DataProcessorSpec>
const& workflow,
119 std::vector<DataProcessorInfo>
const& dataProcessorInfos,
120 const std::vector<DeviceSpec>& specs,
121 const std::vector<DeviceExecution>& executions,
124 std::ostringstream asset;
127 bool hasExpendableTask =
false;
128 for (
auto& spec : specs) {
129 for (
auto&
label : spec.labels) {
130 if (
label.value ==
"expendable") {
131 hasExpendableTask =
true;
136 out << R
"(<topology name="o2-dataflow">)"
139 out << R
"(<declrequirement name="odc_expendable_task" type="custom" value="true" />)"
142 out << fmt::format(R
"(<asset name="dpl_json{}" type="inline" visibility="global" value="{}"/>)",
146 assert(specs.size() == executions.size());
147 std::vector<ChannelRewriter> rewriters;
148 rewriters.resize(specs.size());
153 for (
size_t di = 0;
di < specs.size(); ++
di) {
154 auto& rewriter = rewriters[
di];
155 auto& execution = executions[
di];
156 for (
size_t cci = 0; cci < execution.args.size(); cci++) {
157 const char* arg = execution.args[cci];
161 if (strcmp(arg,
"--channel-config") == 0) {
162 if (cci + 1 == execution.args.size()) {
163 throw std::runtime_error(
"wrong channel config found");
168 for (
int ci : rewriter.requiresProperties) {
170 << fmt::format(
"<property name=\"fmqchan_{}\" />\n", rewriter.properties[rewriter.names[ci]].value);
176 << fmt::format(
"<decltask name=\"{}{}\">\n",
"dplDriver", workflowSuffix);
178 << fmt::format(R
"(<assets><name>dpl_json{}</name></assets>)", workflowSuffix) << "\n";
180 << R
"(<exe reachable="true">)";
181 out << fmt::format("cat ${{DDS_LOCATION}}/dpl_json{}.asset | o2-dpl-run --driver-mode embedded", workflowSuffix);
183 << "<requirements>\n"
184 <<
" <name>odc_expendable_task</name>\n"
185 <<
"</requirements>\n"
187 out <<
"</decltask>";
190 for (
size_t di = 0;
di < specs.size(); ++
di) {
191 auto& spec = specs[
di];
192 auto& execution = executions[
di];
193 if (execution.args.empty()) {
198 << fmt::format(
"<decltask name=\"{}{}\">\n", spec.id, workflowSuffix);
200 << fmt::format(R
"(<assets><name>dpl_json{}</name></assets>)", workflowSuffix) << "\n";
202 << R
"(<exe reachable="true">)";
203 out << fmt::format("cat ${{DDS_LOCATION}}/dpl_json{}.asset | ", workflowSuffix);
204 for (
auto ei : execution.environ) {
207 std::string accumulatedChannelPrefix;
208 char* s = strdup(execution.args[0]);
209 out << basename(s) <<
" ";
211 for (
size_t ai = 1; ai < execution.args.size(); ++ai) {
212 const char* arg = execution.args[ai];
216 if (strcmp(arg,
"--id") == 0 && ai + 1 < execution.args.size()) {
217 out << fmt::format(R
"(--id {}_dds%TaskIndex%_%CollectionIndex% )", execution.args[ai + 1]);
222 if (strcmp(arg,
"--driver-client-backend") == 0) {
226 if (strcmp(arg,
"--control") == 0) {
230 if (strcmp(arg,
"--channel-prefix") == 0 &&
231 ai + 1 < execution.args.size() &&
232 *execution.args[ai + 1] == 0) {
236 if (strpbrk(arg,
"' ;@") !=
nullptr || arg[0] == 0) {
237 out << fmt::format(R
"("{}" )", arg);
238 } else if (strpbrk(arg,
"\"") !=
nullptr || arg[0] == 0) {
239 out << fmt::format(R
"('{}' )", arg);
241 out << fmt::format(R
"({} )", arg);
244 out << "--plugin odc";
245 if (accumulatedChannelPrefix.empty() ==
false) {
246 out <<
" --channel-config \"" << accumulatedChannelPrefix <<
"\"";
251 if (std::find_if(spec.labels.begin(), spec.labels.end(), [](
const auto&
label) {
252 return label.value ==
"expendable";
253 }) != spec.labels.end()) {
254 out <<
" <requirements>\n";
255 out <<
" <name>odc_expendable_task</name>\n";
256 out <<
" </requirements>\n";
258 auto& rewriter = rewriters[
di];
259 if (rewriter.requiresProperties.empty() ==
false) {
260 out <<
" <properties>\n";
261 for (
auto pi : rewriter.requiresProperties) {
263 " <name access=\"{}\">fmqchan_{}</name>\n",
264 rewriter.isWrite[pi] ?
"write" :
"read",
265 rewriter.properties[rewriter.names[pi]].value);
267 out <<
" </properties>\n";
269 out <<
" </decltask>\n";
271 out <<
" <declcollection name=\"DPL\">\n <tasks>\n";
272 for (
const auto& spec : specs) {
273 out << fmt::format(
" <name>{}{}</name>\n", spec.id, workflowSuffix);
276 out << fmt::format(
" <name>{}{}</name>\n",
"dplDriver", workflowSuffix);
278 out <<
" </tasks>\n </declcollection>\n";
279 out <<
"</topology>\n";
static void dumpDeviceSpec2DDS(std::ostream &out, DriverMode mode, std::string const &workflowSuffix, std::vector< DataProcessorSpec > const &workflow, std::vector< DataProcessorInfo > const &metadata, std::vector< DeviceSpec > const &specs, std::vector< DeviceExecution > const &executions, CommandInfo const &commandInfo)