blob: 3ff80ce0d2273984a034b72af57813eacf681654 [file] [log] [blame]
/**
* Copyright (c) 2020-2021 Robert Bosch GmbH.
*
* This program and the accompanying materials are made
* available under the terms of the Eclipse Public License 2.0
* which is available at https://www.eclipse.org/legal/epl-2.0/
*
* SPDX-License-Identifier: EPL-2.0
*
* Contributors:
* Robert Bosch GmbH - initial API and implementation
*/
package org.eclipse.app4mc.slg.ros2.generators;
import java.math.BigInteger;
import java.util.ArrayList;
import java.util.LinkedHashSet;
import java.util.LinkedList;
import java.util.function.BiConsumer;
import java.util.function.Consumer;
import org.eclipse.app4mc.amalthea.model.ActivityGraph;
import org.eclipse.app4mc.amalthea.model.ActivityGraphItem;
import org.eclipse.app4mc.amalthea.model.Component;
import org.eclipse.app4mc.amalthea.model.EventStimulus;
import org.eclipse.app4mc.amalthea.model.Group;
import org.eclipse.app4mc.amalthea.model.InterProcessStimulus;
import org.eclipse.app4mc.amalthea.model.PeriodicStimulus;
import org.eclipse.app4mc.amalthea.model.RunnableCall;
import org.eclipse.app4mc.amalthea.model.Stimulus;
import org.eclipse.app4mc.amalthea.model.Tag;
import org.eclipse.app4mc.amalthea.model.Task;
import org.eclipse.app4mc.amalthea.model.TimeUnit;
import org.eclipse.app4mc.slg.commons.m2t.generators.LabelTranslationUnit;
import org.eclipse.app4mc.slg.commons.m2t.generators.RunnableTranslationUnit;
import org.eclipse.app4mc.slg.commons.m2t.generators.TaskTranslationUnit;
import org.eclipse.app4mc.slg.ros2.transformers.RosInterProcessStimulusTransformer;
import org.eclipse.app4mc.slg.ros2.transformers.RosLabelTransformer;
import org.eclipse.app4mc.slg.ros2.transformers.RosRunnableTransformer;
import org.eclipse.app4mc.slg.ros2.transformers.utils.Utils;
import org.eclipse.app4mc.transformation.util.OutputBuffer;
import org.eclipse.emf.common.util.EList;
import org.eclipse.xtend2.lib.StringConcatenation;
import org.eclipse.xtext.xbase.lib.Functions.Function1;
import org.eclipse.xtext.xbase.lib.IterableExtensions;
public class RosTaskTranslationUnit extends TaskTranslationUnit {
private RosInterProcessStimulusTransformer ipStimulusTransformer;
private Task task;
private final LinkedHashSet<String> includes = new LinkedHashSet<>();
private final LinkedList<String> initCalls = new LinkedList<>();
private final LinkedList<String> stepCalls = new LinkedList<>();
private final ArrayList<Stimulus> stimuli = new ArrayList<>();
private ArrayList<String> publishers = new ArrayList<>();
private ArrayList<String> clientDeclarations = new ArrayList<>();
private ArrayList<String> clientInits = new ArrayList<>();
public RosTaskTranslationUnit(final OutputBuffer outputBuffer, final RosRunnableTransformer transformerRunnable, final RosLabelTransformer transformerLabel, final RosInterProcessStimulusTransformer ipStimulusTransformer, final Task task, final Component c) {
super(outputBuffer, transformerRunnable, transformerLabel, task);
this.ipStimulusTransformer = ipStimulusTransformer;
this.task = task;
this.genFiles();
}
@Override
public String getBasePath() {
return "";
}
@Override
public String getModuleName() {
return this.task.getName();
}
@Override
public boolean genFiles() {
boolean _xblockexpression = false;
{
ActivityGraph _activityGraph = null;
if (this.task!=null) {
_activityGraph=this.task.getActivityGraph();
}
EList<ActivityGraphItem> _items = null;
if (_activityGraph!=null) {
_items=_activityGraph.getItems();
}
if (_items!=null) {
final Consumer<ActivityGraphItem> _function = (ActivityGraphItem item) -> {
if ((item instanceof RunnableCall)) {
final org.eclipse.app4mc.amalthea.model.Runnable runnable = ((RunnableCall) item).getRunnable();
RunnableTranslationUnit _transform = this.runnableTransformer.transform(runnable);
final RosRunnableTranslationUnit tu = ((RosRunnableTranslationUnit) _transform);
this.includes.add(tu.getIncFile());
final Function1<Tag, Boolean> _function_1 = (Tag tag) -> {
return Boolean.valueOf("initialize".equals(tag.getName()));
};
boolean _isEmpty = IterableExtensions.isEmpty(IterableExtensions.<Tag>filter(((RunnableCall)item).getTags(), _function_1));
boolean _not = (!_isEmpty);
if (_not) {
this.initCalls.add(tu.getNodeCall());
} else {
this.stepCalls.add(tu.getNodeCall());
}
this.publishers.addAll(tu.getPublishers());
this.clientDeclarations.addAll(tu.getClientDeclarations());
this.clientInits.addAll(tu.getClientInits());
} else {
if ((item instanceof Group)) {
final Group group = ((Group) item);
final Consumer<ActivityGraphItem> _function_2 = (ActivityGraphItem groupitem) -> {
if ((groupitem instanceof RunnableCall)) {
final org.eclipse.app4mc.amalthea.model.Runnable runnable_1 = ((RunnableCall) groupitem).getRunnable();
RunnableTranslationUnit _transform_1 = this.runnableTransformer.transform(((org.eclipse.app4mc.amalthea.model.Runnable) runnable_1));
final RosRunnableTranslationUnit tu_1 = ((RosRunnableTranslationUnit) _transform_1);
this.includes.add(tu_1.getIncFile());
final Function1<Tag, Boolean> _function_3 = (Tag tag) -> {
return Boolean.valueOf("initialize".equals(tag.getName()));
};
boolean _isEmpty_1 = IterableExtensions.isEmpty(IterableExtensions.<Tag>filter(((RunnableCall)groupitem).getTags(), _function_3));
boolean _not_1 = (!_isEmpty_1);
if (_not_1) {
this.initCalls.add(tu_1.getNodeCall());
} else {
this.stepCalls.add(tu_1.getNodeCall());
}
}
};
group.getItems().forEach(_function_2);
}
}
};
_items.forEach(_function);
}
final BiConsumer<ArrayList<?>, LabelTranslationUnit> _function_1 = (ArrayList<?> label, LabelTranslationUnit tu) -> {
this.includes.add(tu.getIncFile());
this.initCalls.add(tu.getInitCall());
};
this.labelTransformer.getCache().forEach(_function_1);
final Function1<Stimulus, Boolean> _function_2 = (Stimulus stimulus) -> {
return Boolean.valueOf((stimulus instanceof InterProcessStimulus));
};
final Consumer<Stimulus> _function_3 = (Stimulus stimulus) -> {
StringConcatenation _builder = new StringConcatenation();
String _name = stimulus.getName();
_builder.append(_name);
_builder.append("_service/srv/");
String _name_1 = stimulus.getName();
_builder.append(_name_1);
_builder.append("_service.hpp");
this.includes.add(_builder.toString());
this.ipStimulusTransformer.transform(((InterProcessStimulus) stimulus));
};
IterableExtensions.<Stimulus>filter(IterableExtensions.<Stimulus>toList(this.task.getStimuli()), _function_2).forEach(_function_3);
_xblockexpression = this.stimuli.addAll(IterableExtensions.<Stimulus>toList(this.task.getStimuli()));
}
return _xblockexpression;
}
public CharSequence getDeclaration() {
StringConcatenation _builder = new StringConcatenation();
{
for(final Stimulus stimulus : this.stimuli) {
{
if ((stimulus instanceof PeriodicStimulus)) {
_builder.append("rclcpp::TimerBase::SharedPtr ");
String _name = ((PeriodicStimulus) stimulus).getName();
_builder.append(_name);
_builder.append("_timer_;");
_builder.newLineIfNotEmpty();
}
}
{
if ((stimulus instanceof EventStimulus)) {
_builder.append("rclcpp::Subscription<std_msgs::msg::String>::SharedPtr ");
String _name_1 = ((EventStimulus) stimulus).getName();
_builder.append(_name_1);
_builder.append("_subscription_;");
_builder.newLineIfNotEmpty();
}
}
{
if ((stimulus instanceof InterProcessStimulus)) {
_builder.append("rclcpp::Service<");
String _name_2 = ((InterProcessStimulus) stimulus).getName();
_builder.append(_name_2);
_builder.append("_service::srv::");
String _name_3 = ((InterProcessStimulus) stimulus).getName();
String _plus = (_name_3 + "_service");
String _idlCompliantName = Utils.toIdlCompliantName(_plus);
_builder.append(_idlCompliantName);
_builder.append(">::SharedPtr ");
String _name_4 = ((InterProcessStimulus) stimulus).getName();
_builder.append(_name_4);
_builder.append("_service;");
_builder.newLineIfNotEmpty();
}
}
}
}
{
for(final String publisher : this.publishers) {
_builder.append("rclcpp::Publisher<std_msgs::msg::String>::SharedPtr ");
_builder.append(publisher);
_builder.append(";");
_builder.newLineIfNotEmpty();
}
}
{
for(final String decl : this.clientDeclarations) {
_builder.append(decl);
_builder.append(";");
_builder.newLineIfNotEmpty();
}
}
return _builder;
}
public CharSequence getInitialisation(final String nodeName) {
StringConcatenation _builder = new StringConcatenation();
{
for(final Stimulus stimulus : this.stimuli) {
{
if ((stimulus instanceof PeriodicStimulus)) {
String _name = ((PeriodicStimulus) stimulus).getName();
_builder.append(_name);
_builder.append("_timer_ = this->create_wall_timer(");
_builder.newLineIfNotEmpty();
_builder.append("\t\t");
BigInteger _value = ((PeriodicStimulus) stimulus).getRecurrence().getValue();
_builder.append(_value, "\t\t");
TimeUnit _unit = ((PeriodicStimulus) stimulus).getRecurrence().getUnit();
_builder.append(_unit, "\t\t");
_builder.append(", std::bind(&");
_builder.append(nodeName, "\t\t");
_builder.append("::");
String _name_1 = ((PeriodicStimulus) stimulus).getName();
_builder.append(_name_1, "\t\t");
_builder.append("_timer_callback, this));");
_builder.newLineIfNotEmpty();
}
}
{
if ((stimulus instanceof EventStimulus)) {
String _name_2 = ((EventStimulus) stimulus).getName();
_builder.append(_name_2);
_builder.append("_subscription_ = this->create_subscription<std_msgs::msg::String>(");
_builder.newLineIfNotEmpty();
_builder.append("\t");
_builder.append("\"");
String _name_3 = ((EventStimulus) stimulus).getName();
_builder.append(_name_3, "\t");
_builder.append("\", 10, std::bind(&");
_builder.append(nodeName, "\t");
_builder.append("::");
String _name_4 = ((EventStimulus) stimulus).getName();
_builder.append(_name_4, "\t");
_builder.append("_subscription_callback, this, _1));");
_builder.newLineIfNotEmpty();
}
}
{
if ((stimulus instanceof InterProcessStimulus)) {
String _name_5 = ((InterProcessStimulus) stimulus).getName();
_builder.append(_name_5);
_builder.append("_service = this->create_service<");
String _name_6 = ((InterProcessStimulus) stimulus).getName();
_builder.append(_name_6);
_builder.append("_service::srv::");
String _name_7 = ((InterProcessStimulus) stimulus).getName();
String _plus = (_name_7 + "_service");
String _idlCompliantName = Utils.toIdlCompliantName(_plus);
_builder.append(_idlCompliantName);
_builder.append(">(\"");
String _name_8 = ((InterProcessStimulus) stimulus).getName();
_builder.append(_name_8);
_builder.append("_service\", &");
String _name_9 = ((InterProcessStimulus) stimulus).getName();
_builder.append(_name_9);
_builder.append("_service_callback);");
_builder.newLineIfNotEmpty();
}
}
}
}
{
for(final String publisher : this.publishers) {
_builder.append(publisher);
_builder.append(" = this->create_publisher<std_msgs::msg::String>(\"");
String _replace = publisher.replace("_publisher", "");
_builder.append(_replace);
_builder.append("\", 10);");
_builder.newLineIfNotEmpty();
}
}
{
for(final String init : this.clientInits) {
_builder.append(init);
_builder.append(";");
_builder.newLineIfNotEmpty();
}
}
return _builder;
}
public CharSequence getServiceCallback() {
StringConcatenation _builder = new StringConcatenation();
{
for(final Stimulus stimulus : this.stimuli) {
{
if ((stimulus instanceof InterProcessStimulus)) {
_builder.append("void ");
String _name = ((InterProcessStimulus) stimulus).getName();
_builder.append(_name);
_builder.append("_service_callback(const std::shared_ptr<");
String _name_1 = ((InterProcessStimulus) stimulus).getName();
_builder.append(_name_1);
_builder.append("_service::srv::");
String _name_2 = ((InterProcessStimulus) stimulus).getName();
String _plus = (_name_2 + "_service");
String _idlCompliantName = Utils.toIdlCompliantName(_plus);
_builder.append(_idlCompliantName);
_builder.append("::Request> request,");
_builder.newLineIfNotEmpty();
_builder.append("\t");
_builder.append("std::shared_ptr<");
String _name_3 = ((InterProcessStimulus) stimulus).getName();
_builder.append(_name_3, "\t");
_builder.append("_service::srv::");
String _name_4 = ((InterProcessStimulus) stimulus).getName();
String _plus_1 = (_name_4 + "_service");
String _idlCompliantName_1 = Utils.toIdlCompliantName(_plus_1);
_builder.append(_idlCompliantName_1, "\t");
_builder.append("::Response> response) {");
_builder.newLineIfNotEmpty();
{
for(final String call : this.stepCalls) {
_builder.append("\t\t");
_builder.append(call);
_builder.append(";");
_builder.newLineIfNotEmpty();
}
}
_builder.append("\t");
_builder.append("}");
_builder.newLine();
}
}
_builder.newLine();
_builder.newLine();
}
}
return _builder;
}
public CharSequence getCallback() {
StringConcatenation _builder = new StringConcatenation();
{
for(final Stimulus stimulus : this.stimuli) {
{
if ((stimulus instanceof PeriodicStimulus)) {
_builder.append("void ");
String _name = ((PeriodicStimulus) stimulus).getName();
_builder.append(_name);
_builder.append("_timer_callback() {");
_builder.newLineIfNotEmpty();
{
for(final String call : this.stepCalls) {
_builder.append("\t");
_builder.append(call);
_builder.append(";");
_builder.newLineIfNotEmpty();
}
}
_builder.append("}");
_builder.newLine();
}
}
{
if ((stimulus instanceof EventStimulus)) {
_builder.append("void ");
String _name_1 = ((EventStimulus) stimulus).getName();
_builder.append(_name_1);
_builder.append("_subscription_callback(const std_msgs::msg::String::SharedPtr msg) {");
_builder.newLineIfNotEmpty();
{
for(final String call_1 : this.stepCalls) {
_builder.append("\t");
_builder.append(call_1);
_builder.append(";");
_builder.newLineIfNotEmpty();
}
}
_builder.append("}");
_builder.newLine();
}
}
}
}
return _builder;
}
public CharSequence getHeaders() {
StringConcatenation _builder = new StringConcatenation();
{
for(final String include : this.includes) {
_builder.append("#include \"");
_builder.append(include);
_builder.append("\"");
_builder.newLineIfNotEmpty();
}
}
return _builder;
}
}