Unverified Commit f7d019c5 authored by sschneiders's avatar sschneiders Committed by GitHub
Browse files

Merge pull request #16 from EmbeddedMontiArc/ryndin

add StreamScanner for CPP Unit Tests Generation
parents 9bf76dec 5a538553
#
#
# ******************************************************************************
# MontiCAR Modeling Family, www.se-rwth.de
# Copyright (c) 2017, Software Engineering Group at RWTH Aachen,
# All rights reserved.
#
# This project is free software; you can redistribute it and/or
# modify it under the terms of the GNU Lesser General Public
# License as published by the Free Software Foundation; either
# version 3.0 of the License, or (at your option) any later version.
# This library is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# Lesser General Public License for more details.
#
# You should have received a copy of the GNU Lesser General Public
# License along with this project. If not, see <http://www.gnu.org/licenses/>.
# *******************************************************************************
#
# Java Maven CircleCI 2.0 configuration file
#
# Check https://circleci.com/docs/2.0/language-java/ for more details
......
......@@ -30,8 +30,7 @@
<groupId>de.monticore.lang.monticar</groupId>
<artifactId>embedded-montiarc</artifactId>
<version>0.0.6-SNAPSHOT</version>
<version>0.0.7</version>
<!-- == PROJECT DEPENDENCIES ============================================= -->
......@@ -47,8 +46,8 @@
<mc.grammars.assembly.version>0.0.6-SNAPSHOT</mc.grammars.assembly.version>
<languages.version>4.0.1-SNAPSHOT</languages.version>
<SIUnit.version>0.0.7</SIUnit.version>
<struct.version>0.0.4</struct.version>
<Common-MontiCar.version>0.0.6-SNAPSHOT</Common-MontiCar.version>
<struct.version>0.0.5</struct.version>
<Common-MontiCar.version>0.0.7</Common-MontiCar.version>
<!-- .. Libraries .................................................. -->
<guava.version>18.0</guava.version>
......
/**
*
* ******************************************************************************
* MontiCAR Modeling Family, www.se-rwth.de
* Copyright (c) 2017, Software Engineering Group at RWTH Aachen,
* All rights reserved.
*
* This project is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 3.0 of the License, or (at your option) any later version.
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this project. If not, see <http://www.gnu.org/licenses/>.
* *******************************************************************************
*/
package de.monticore.lang.embeddedmontiarc.embeddedmontiarc;
import de.monticore.lang.embeddedmontiarc.embeddedmontiarc._symboltable.ComponentSymbol;
import de.monticore.lang.monticar.stream._symboltable.StreamLanguage;
import de.monticore.lang.monticar.streamunits._symboltable.ComponentStreamUnitsSymbol;
import de.monticore.symboltable.Scope;
import de.se_rwth.commons.Names;
import de.se_rwth.commons.logging.Log;
import java.io.File;
import java.io.IOException;
import java.nio.file.FileVisitResult;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.SimpleFileVisitor;
import java.nio.file.attribute.BasicFileAttributes;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
public final class StreamScanner {
private final Path basePath;
private final Scope symTab;
public StreamScanner(Path basePath, Scope symTab) {
this.basePath = Log.errorIfNull(basePath);
this.symTab = Log.errorIfNull(symTab);
}
public Map<ComponentSymbol, Set<ComponentStreamUnitsSymbol>> scan() {
StreamLanguageFileVisitor v = new StreamLanguageFileVisitor(this);
try {
Files.walkFileTree(basePath, v);
} catch (IOException e) {
Log.error("error while processing stream files", e);
}
return new HashMap<>(v.getMapping());
}
private static class StreamLanguageFileVisitor extends SimpleFileVisitor<Path> {
private final StreamScanner scanner;
private final Map<ComponentSymbol, Set<ComponentStreamUnitsSymbol>> mapping = new HashMap<>();
StreamLanguageFileVisitor(StreamScanner scanner) {
this.scanner = scanner;
}
Map<ComponentSymbol, Set<ComponentStreamUnitsSymbol>> getMapping() {
return Collections.unmodifiableMap(mapping);
}
@Override
public FileVisitResult visitFile(Path file, BasicFileAttributes attrs) throws IOException {
if (attrs.isSymbolicLink() || !attrs.isRegularFile()) {
return FileVisitResult.CONTINUE;
}
File f = file.toFile();
if (!isProcessFile(f)) {
return FileVisitResult.CONTINUE;
}
Path relativePath = scanner.basePath.relativize(file);
String streamModelName = getStreamModelName(relativePath);
ComponentStreamUnitsSymbol s = scanner.symTab.<ComponentStreamUnitsSymbol>resolve(streamModelName, ComponentStreamUnitsSymbol.KIND).orElse(null);
if (s != null) {
processComponentStreamUnitsSymbol(s, f);
} else {
Log.warn("could not resolve stream model defined in file " + f.getAbsolutePath());
}
return FileVisitResult.CONTINUE;
}
private void processComponentStreamUnitsSymbol(ComponentStreamUnitsSymbol s, File f) {
ComponentSymbol relatedComponent = s.<ComponentSymbol>getComponentSymbol(ComponentSymbol.KIND).orElse(null);
if (relatedComponent == null) {
Log.warn("could not resolve component for which stream is defined in " + f.getAbsolutePath());
return;
}
Set<ComponentStreamUnitsSymbol> streams = mapping.computeIfAbsent(relatedComponent, k -> new HashSet<>());
streams.add(s);
}
private static boolean isProcessFile(File f) {
if (f == null) {
return false;
}
if (!f.exists() || !f.isFile()) {
return false;
}
String fName = f.getName().toLowerCase();
return fName.endsWith(StreamLanguage.FILE_ENDING);
}
private static String getStreamModelName(Path p) {
List<String> parts = new ArrayList<>();
for (Path dirName : p.getParent()) {
parts.add(dirName.toString());
}
String fileNameWithoutExtension = (p.getFileName().toString().split("\\."))[0];
parts.add(fileNameWithoutExtension);
return Names.getQualifiedName(parts);
}
}
}
......@@ -152,7 +152,7 @@ public class EmbeddedMontiArcSymbolTableCreator extends EmbeddedMontiArcSymbolTa
return;
}
// creates all instances which are created through the top level component
System.out.println("endVisit of " + node.getComponent().getSymbol().get().getFullName()); //,"MontiArcSymbolTableCreator");
Log.debug("endVisit of " + node.getComponent().getSymbol().get().getFullName(),"SymbolTableCreator:"); //,"MontiArcSymbolTableCreator");
// new Error().printStackTrace();
instanceSymbolCreator.createInstances(
(ComponentSymbol) (Log.errorIfNull(node.getComponent().getSymbol().orElse(null)))
......@@ -422,7 +422,7 @@ public class EmbeddedMontiArcSymbolTableCreator extends EmbeddedMontiArcSymbolTa
} else if (portName.getPortArray().get().getLowerbound().isPresent()) {
names = getmnPortNameParts(name, portName);
} else {
System.out.println(portName.toString());
Log.debug(portName.toString(),"PortName:");
int size = countPortArrayInstances(name, portName.getCompName().orElse(null), portName.getCompArray().orElse(null));
Log.debug("Size" + size, "PortNameParts");
......@@ -476,7 +476,7 @@ public class EmbeddedMontiArcSymbolTableCreator extends EmbeddedMontiArcSymbolTa
present = curScope.resolve(portName + "[" + (counter + 1) + "]", PortSymbol.KIND).isPresent();
if (present) ++counter;
else {
System.out.println(curScope.toString());
Log.debug(curScope.toString(),"CurScope:");
Log.debug("Could not resolve " + portName + "[" + (counter + 1) + "]", "countPortArrayInstances");
}
}
......@@ -484,7 +484,7 @@ public class EmbeddedMontiArcSymbolTableCreator extends EmbeddedMontiArcSymbolTa
//TODO
present = true;
Log.debug("compInstanceName: " + compName, "Resolving");
System.out.println(compName);
Log.debug(compName,"ComponentName");
ComponentInstanceSymbol symbol;
symbol = curScope.<ComponentInstanceSymbol>resolve(compName, ComponentInstanceSymbol.KIND).get();
for (PortSymbol portSymbol : symbol.getComponentType().getAllPorts()) {
......
/**
*
* ******************************************************************************
* MontiCAR Modeling Family, www.se-rwth.de
* Copyright (c) 2017, Software Engineering Group at RWTH Aachen,
* All rights reserved.
*
* This project is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 3.0 of the License, or (at your option) any later version.
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this project. If not, see <http://www.gnu.org/licenses/>.
* *******************************************************************************
*/
package de.monticore.lang.embeddedmontiarc;
import de.monticore.ModelingLanguageFamily;
import de.monticore.io.paths.ModelPath;
import de.monticore.lang.embeddedmontiarc.embeddedmontiarc.StreamScanner;
import de.monticore.lang.embeddedmontiarc.embeddedmontiarc._symboltable.ComponentSymbol;
import de.monticore.lang.embeddedmontiarc.embeddedmontiarc._symboltable.EmbeddedMontiArcLanguage;
import de.monticore.lang.monticar.streamunits._symboltable.ComponentStreamUnitsSymbol;
import de.monticore.lang.monticar.streamunits._symboltable.StreamUnitsLanguage;
import de.monticore.lang.monticar.struct._symboltable.StructLanguage;
import de.monticore.symboltable.GlobalScope;
import de.monticore.symboltable.Scope;
import org.junit.Assert;
import org.junit.Test;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
public class StreamScannerTest {
private static final Path BASE_PATH = Paths.get("src/test/resources");
@Test
public void testMySuperNiceComponent() {
Scope symTab = createSymTab(BASE_PATH.toString());
StreamScanner scanner = new StreamScanner(BASE_PATH, symTab);
Map<ComponentSymbol, Set<ComponentStreamUnitsSymbol>> result = scanner.scan();
Assert.assertNotNull(result);
Assert.assertFalse(result.isEmpty());
ComponentSymbol mySuperNiceComponent = symTab.<ComponentSymbol>resolve("testing.MySuperNiceComponent", ComponentSymbol.KIND).orElse(null);
Assert.assertNotNull(mySuperNiceComponent);
Set<ComponentStreamUnitsSymbol> mySuperNiceStreams = result.get(mySuperNiceComponent);
Assert.assertNotNull(mySuperNiceStreams);
Assert.assertFalse(mySuperNiceStreams.isEmpty());
Assert.assertEquals(2, mySuperNiceStreams.size());
Iterator<ComponentStreamUnitsSymbol> it = mySuperNiceStreams.iterator();
ComponentStreamUnitsSymbol mySuperNiceStream1 = it.next();
ComponentStreamUnitsSymbol mySuperNiceStream2 = it.next();
if (!"MySuperNiceStream1".equals(mySuperNiceStream1.getName())) {
ComponentStreamUnitsSymbol swap = mySuperNiceStream1;
mySuperNiceStream1 = mySuperNiceStream2;
mySuperNiceStream2 = swap;
}
Assert.assertEquals("testing.MySuperNiceStream1", mySuperNiceStream1.getFullName());
Assert.assertEquals("testing.MySuperNiceStream2", mySuperNiceStream2.getFullName());
Assert.assertEquals(6, mySuperNiceStream1.getNamedStreams().size());
Assert.assertEquals(6, mySuperNiceStream2.getNamedStreams().size());
}
private static Scope createSymTab(String... modelPath) {
ModelingLanguageFamily fam = new ModelingLanguageFamily();
fam.addModelingLanguage(new EmbeddedMontiArcLanguage());
fam.addModelingLanguage(new StreamUnitsLanguage());
fam.addModelingLanguage(new StructLanguage());
final ModelPath mp = new ModelPath();
for (String m : modelPath) {
mp.addEntry(Paths.get(m));
}
GlobalScope scope = new GlobalScope(mp, fam);
de.monticore.lang.monticar.Utils.addBuiltInTypes(scope);
LogConfig.init();
return scope;
}
}
package testing;
component MySuperNiceComponent {
port
in B in1,
in Q (0.0 : 0.001 : 1.0) in2,
in Z (0 : oo) in3,
out B out1,
out Q (-1.0 : 0.001 : 0.0) out2,
out Z (-oo : 0) out3;
}
package testing;
stream MySuperNiceStream1 for MySuperNiceComponent {
in1: true tick false tick true;
in2: 0.500 tick 0.003 tick 0.750;
in3: 0 tick 1 tick 2;
out1: false tick true tick false;
out2: -0.500 tick -0.003 tick -0.750;
out3: 0 tick -1 tick -2;
}
package testing;
stream MySuperNiceStream2 for MySuperNiceComponent {
in1: false tick false tick false;
in2: 0.123 tick 0.345 tick 0.678;
in3: 1000 tick 10000 tick 100000;
out1: true tick true tick true;
out2: 0.123 +/- 0.1 tick 0.345 +/- 0.01 tick 0.678 +/- 0.001;
out3: 0 tick -1 +/- 1 tick -2 +/- 1;
}
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment