mirror of
https://github.com/hneemann/Digital.git
synced 2025-09-09 12:56:02 -04:00
allows the generic code to load a hex file
This commit is contained in:
parent
a56b04c091
commit
b96714d61c
@ -58,6 +58,7 @@ public class ResolveGenerics {
|
|||||||
boolean isCustom = library.getElementType(ve.getElementName(), ve.getElementAttributes()).isCustom();
|
boolean isCustom = library.getElementType(ve.getElementName(), ve.getElementAttributes()).isCustom();
|
||||||
Statement genS = getStatement(gen);
|
Statement genS = getStatement(gen);
|
||||||
Context mod = new Context();
|
Context mod = new Context();
|
||||||
|
mod.declareVar(Context.BASE_FILE_KEY, circuit.getOrigin().getPath());
|
||||||
if (isCustom) {
|
if (isCustom) {
|
||||||
mod.declareVar("args", args)
|
mod.declareVar("args", args)
|
||||||
.declareFunc("setCircuit", new SetCircuitFunc(ve));
|
.declareFunc("setCircuit", new SetCircuitFunc(ve));
|
||||||
@ -96,6 +97,11 @@ public class ResolveGenerics {
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
context = new Context();
|
context = new Context();
|
||||||
|
try {
|
||||||
|
context.declareVar(Context.BASE_FILE_KEY, circuit.getOrigin().getPath());
|
||||||
|
} catch (HGSEvalException e) {
|
||||||
|
throw new NodeException("error setting the base filename", e);
|
||||||
|
}
|
||||||
List<VisualElement> g = circuit.getElements(v -> v.equalsDescription(GenericInitCode.DESCRIPTION) && v.getElementAttributes().get(Keys.ENABLED));
|
List<VisualElement> g = circuit.getElements(v -> v.equalsDescription(GenericInitCode.DESCRIPTION) && v.getElementAttributes().get(Keys.ENABLED));
|
||||||
if (g.size() == 0)
|
if (g.size() == 0)
|
||||||
throw new NodeException(Lang.get("err_noGenericInitCode"));
|
throw new NodeException(Lang.get("err_noGenericInitCode"));
|
||||||
|
@ -5,7 +5,10 @@
|
|||||||
*/
|
*/
|
||||||
package de.neemann.digital.hdl.hgs;
|
package de.neemann.digital.hdl.hgs;
|
||||||
|
|
||||||
|
import de.neemann.digital.FileLocator;
|
||||||
import de.neemann.digital.core.Bits;
|
import de.neemann.digital.core.Bits;
|
||||||
|
import de.neemann.digital.core.memory.DataField;
|
||||||
|
import de.neemann.digital.core.memory.importer.Importer;
|
||||||
import de.neemann.digital.hdl.hgs.function.Func;
|
import de.neemann.digital.hdl.hgs.function.Func;
|
||||||
import de.neemann.digital.hdl.hgs.function.Function;
|
import de.neemann.digital.hdl.hgs.function.Function;
|
||||||
import de.neemann.digital.hdl.hgs.function.InnerFunction;
|
import de.neemann.digital.hdl.hgs.function.InnerFunction;
|
||||||
@ -13,6 +16,8 @@ import de.neemann.digital.lang.Lang;
|
|||||||
import org.slf4j.Logger;
|
import org.slf4j.Logger;
|
||||||
import org.slf4j.LoggerFactory;
|
import org.slf4j.LoggerFactory;
|
||||||
|
|
||||||
|
import java.io.File;
|
||||||
|
import java.io.IOException;
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -23,6 +28,11 @@ public class Context implements HGSMap {
|
|||||||
// declare some functions which are always present
|
// declare some functions which are always present
|
||||||
private static final HashMap<String, InnerFunction> BUILT_IN = new HashMap<>();
|
private static final HashMap<String, InnerFunction> BUILT_IN = new HashMap<>();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Key used to store the base file name in the context
|
||||||
|
*/
|
||||||
|
public static final String BASE_FILE_KEY = "baseFile";
|
||||||
|
|
||||||
static {
|
static {
|
||||||
BUILT_IN.put("bitsNeededFor", new FunctionBitsNeeded());
|
BUILT_IN.put("bitsNeededFor", new FunctionBitsNeeded());
|
||||||
BUILT_IN.put("ceil", new FunctionCeil());
|
BUILT_IN.put("ceil", new FunctionCeil());
|
||||||
@ -43,6 +53,7 @@ public class Context implements HGSMap {
|
|||||||
BUILT_IN.put("output", new FunctionOutput());
|
BUILT_IN.put("output", new FunctionOutput());
|
||||||
BUILT_IN.put("splitString", new FunctionSplitString());
|
BUILT_IN.put("splitString", new FunctionSplitString());
|
||||||
BUILT_IN.put("identifier", new FunctionIdentifier());
|
BUILT_IN.put("identifier", new FunctionIdentifier());
|
||||||
|
BUILT_IN.put("loadHex", new FunctionLoadHex());
|
||||||
BUILT_IN.put("sizeOf", new Func(1, args -> Value.toArray(args[0]).hgsArraySize()));
|
BUILT_IN.put("sizeOf", new Func(1, args -> Value.toArray(args[0]).hgsArraySize()));
|
||||||
BUILT_IN.put("newMap", new Func(0, args -> new HashMap()));
|
BUILT_IN.put("newMap", new Func(0, args -> new HashMap()));
|
||||||
BUILT_IN.put("newList", new Func(0, args -> new ArrayList()));
|
BUILT_IN.put("newList", new Func(0, args -> new ArrayList()));
|
||||||
@ -605,6 +616,33 @@ public class Context implements HGSMap {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static final class FunctionLoadHex extends InnerFunction {
|
||||||
|
private FunctionLoadHex() {
|
||||||
|
super(2);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Object call(Context c, ArrayList<Expression> args) throws HGSEvalException {
|
||||||
|
String name = args.get(0).value(c).toString();
|
||||||
|
int dataBits = Value.toInt(args.get(1).value(c));
|
||||||
|
FileLocator fileLocator = new FileLocator(name);
|
||||||
|
if (c.contains(BASE_FILE_KEY))
|
||||||
|
fileLocator.setBaseFile(new File(c.getVar(BASE_FILE_KEY).toString()));
|
||||||
|
File hexFile = fileLocator.locate();
|
||||||
|
|
||||||
|
if (hexFile == null)
|
||||||
|
throw new HGSEvalException("file " + name + " not found!");
|
||||||
|
|
||||||
|
try {
|
||||||
|
DataField dataField = Importer.read(hexFile, dataBits);
|
||||||
|
dataField.trim();
|
||||||
|
return dataField;
|
||||||
|
} catch (IOException e) {
|
||||||
|
throw new HGSEvalException("error reading the file " + hexFile.getPath(), e);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean equals(Object o) {
|
public boolean equals(Object o) {
|
||||||
if (this == o) return true;
|
if (this == o) return true;
|
||||||
|
@ -51,8 +51,8 @@ public class VerilogSimulatorTest extends TestCase {
|
|||||||
File examples = new File(Resources.getRoot(), "/dig/test/vhdl");
|
File examples = new File(Resources.getRoot(), "/dig/test/vhdl");
|
||||||
try {
|
try {
|
||||||
int tested = new FileScanner(this::checkVerilogExport).noOutput().scan(examples);
|
int tested = new FileScanner(this::checkVerilogExport).noOutput().scan(examples);
|
||||||
assertEquals(58, tested);
|
assertEquals(60, tested);
|
||||||
assertEquals(52, testBenches);
|
assertEquals(53, testBenches);
|
||||||
} catch (FileScanner.SkipAllException e) {
|
} catch (FileScanner.SkipAllException e) {
|
||||||
// if iverilog is not installed its also ok
|
// if iverilog is not installed its also ok
|
||||||
}
|
}
|
||||||
|
@ -43,8 +43,8 @@ public class VHDLSimulatorTest extends TestCase {
|
|||||||
File examples = new File(Resources.getRoot(), "/dig/test/vhdl");
|
File examples = new File(Resources.getRoot(), "/dig/test/vhdl");
|
||||||
try {
|
try {
|
||||||
int tested = new FileScanner(this::checkVHDLExport).noOutput().scan(examples);
|
int tested = new FileScanner(this::checkVHDLExport).noOutput().scan(examples);
|
||||||
assertEquals(58, tested);
|
assertEquals(60, tested);
|
||||||
assertEquals(52, testBenches);
|
assertEquals(53, testBenches);
|
||||||
} catch (FileScanner.SkipAllException e) {
|
} catch (FileScanner.SkipAllException e) {
|
||||||
// if ghdl is not installed its also ok
|
// if ghdl is not installed its also ok
|
||||||
}
|
}
|
||||||
|
@ -50,8 +50,8 @@ public class TestExamples extends TestCase {
|
|||||||
*/
|
*/
|
||||||
public void testTestExamples() throws Exception {
|
public void testTestExamples() throws Exception {
|
||||||
File examples = new File(Resources.getRoot(), "/dig/test");
|
File examples = new File(Resources.getRoot(), "/dig/test");
|
||||||
assertEquals(196, new FileScanner(this::check).scan(examples));
|
assertEquals(198, new FileScanner(this::check).scan(examples));
|
||||||
assertEquals(186, testCasesInFiles);
|
assertEquals(187, testCasesInFiles);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
89
src/test/resources/dig/test/vhdl/romPreload/lut.dig
Normal file
89
src/test/resources/dig/test/vhdl/romPreload/lut.dig
Normal file
@ -0,0 +1,89 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<circuit>
|
||||||
|
<version>1</version>
|
||||||
|
<attributes>
|
||||||
|
<entry>
|
||||||
|
<string>isGeneric</string>
|
||||||
|
<boolean>true</boolean>
|
||||||
|
</entry>
|
||||||
|
</attributes>
|
||||||
|
<visualElements>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>ROM</elementName>
|
||||||
|
<elementAttributes>
|
||||||
|
<entry>
|
||||||
|
<string>AddrBits</string>
|
||||||
|
<int>3</int>
|
||||||
|
</entry>
|
||||||
|
<entry>
|
||||||
|
<string>Data</string>
|
||||||
|
<data>0,1,1,0,1,0,0,1</data>
|
||||||
|
</entry>
|
||||||
|
<entry>
|
||||||
|
<string>generic</string>
|
||||||
|
<string>this.Data=loadHex(args.hexName,1);
|
||||||
|
this.Label=args.hexName;</string>
|
||||||
|
</entry>
|
||||||
|
</elementAttributes>
|
||||||
|
<pos x="440" y="220"/>
|
||||||
|
</visualElement>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>VDD</elementName>
|
||||||
|
<elementAttributes/>
|
||||||
|
<pos x="420" y="240"/>
|
||||||
|
</visualElement>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>Out</elementName>
|
||||||
|
<elementAttributes>
|
||||||
|
<entry>
|
||||||
|
<string>Label</string>
|
||||||
|
<string>Y</string>
|
||||||
|
</entry>
|
||||||
|
</elementAttributes>
|
||||||
|
<pos x="540" y="240"/>
|
||||||
|
</visualElement>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>In</elementName>
|
||||||
|
<elementAttributes>
|
||||||
|
<entry>
|
||||||
|
<string>Label</string>
|
||||||
|
<string>A</string>
|
||||||
|
</entry>
|
||||||
|
<entry>
|
||||||
|
<string>Bits</string>
|
||||||
|
<int>3</int>
|
||||||
|
</entry>
|
||||||
|
</elementAttributes>
|
||||||
|
<pos x="380" y="220"/>
|
||||||
|
</visualElement>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>GenericInitCode</elementName>
|
||||||
|
<elementAttributes>
|
||||||
|
<entry>
|
||||||
|
<string>generic</string>
|
||||||
|
<string>hexName:="lut1.hex";</string>
|
||||||
|
</entry>
|
||||||
|
</elementAttributes>
|
||||||
|
<pos x="400" y="300"/>
|
||||||
|
</visualElement>
|
||||||
|
</visualElements>
|
||||||
|
<wires>
|
||||||
|
<wire>
|
||||||
|
<p1 x="500" y="240"/>
|
||||||
|
<p2 x="540" y="240"/>
|
||||||
|
</wire>
|
||||||
|
<wire>
|
||||||
|
<p1 x="420" y="260"/>
|
||||||
|
<p2 x="440" y="260"/>
|
||||||
|
</wire>
|
||||||
|
<wire>
|
||||||
|
<p1 x="380" y="220"/>
|
||||||
|
<p2 x="440" y="220"/>
|
||||||
|
</wire>
|
||||||
|
<wire>
|
||||||
|
<p1 x="420" y="240"/>
|
||||||
|
<p2 x="420" y="260"/>
|
||||||
|
</wire>
|
||||||
|
</wires>
|
||||||
|
<measurementOrdering/>
|
||||||
|
</circuit>
|
9
src/test/resources/dig/test/vhdl/romPreload/lut1.hex
Normal file
9
src/test/resources/dig/test/vhdl/romPreload/lut1.hex
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
v2.0 raw
|
||||||
|
0
|
||||||
|
1
|
||||||
|
1
|
||||||
|
0
|
||||||
|
1
|
||||||
|
1
|
||||||
|
1
|
||||||
|
1
|
9
src/test/resources/dig/test/vhdl/romPreload/lut2.hex
Normal file
9
src/test/resources/dig/test/vhdl/romPreload/lut2.hex
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
v2.0 raw
|
||||||
|
0
|
||||||
|
1
|
||||||
|
1
|
||||||
|
0
|
||||||
|
0
|
||||||
|
0
|
||||||
|
0
|
||||||
|
0
|
110
src/test/resources/dig/test/vhdl/romPreload/lutTest.dig
Normal file
110
src/test/resources/dig/test/vhdl/romPreload/lutTest.dig
Normal file
@ -0,0 +1,110 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<circuit>
|
||||||
|
<version>1</version>
|
||||||
|
<attributes/>
|
||||||
|
<visualElements>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>lut.dig</elementName>
|
||||||
|
<elementAttributes>
|
||||||
|
<entry>
|
||||||
|
<string>generic</string>
|
||||||
|
<string>hexName := "lut1.hex";</string>
|
||||||
|
</entry>
|
||||||
|
</elementAttributes>
|
||||||
|
<pos x="420" y="240"/>
|
||||||
|
</visualElement>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>lut.dig</elementName>
|
||||||
|
<elementAttributes>
|
||||||
|
<entry>
|
||||||
|
<string>generic</string>
|
||||||
|
<string>hexName := "lut2.hex";</string>
|
||||||
|
</entry>
|
||||||
|
</elementAttributes>
|
||||||
|
<pos x="420" y="300"/>
|
||||||
|
</visualElement>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>Out</elementName>
|
||||||
|
<elementAttributes>
|
||||||
|
<entry>
|
||||||
|
<string>Label</string>
|
||||||
|
<string>Y</string>
|
||||||
|
</entry>
|
||||||
|
</elementAttributes>
|
||||||
|
<pos x="500" y="240"/>
|
||||||
|
</visualElement>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>Out</elementName>
|
||||||
|
<elementAttributes>
|
||||||
|
<entry>
|
||||||
|
<string>Label</string>
|
||||||
|
<string>X</string>
|
||||||
|
</entry>
|
||||||
|
</elementAttributes>
|
||||||
|
<pos x="500" y="300"/>
|
||||||
|
</visualElement>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>In</elementName>
|
||||||
|
<elementAttributes>
|
||||||
|
<entry>
|
||||||
|
<string>Label</string>
|
||||||
|
<string>A</string>
|
||||||
|
</entry>
|
||||||
|
<entry>
|
||||||
|
<string>Bits</string>
|
||||||
|
<int>3</int>
|
||||||
|
</entry>
|
||||||
|
</elementAttributes>
|
||||||
|
<pos x="380" y="240"/>
|
||||||
|
</visualElement>
|
||||||
|
<visualElement>
|
||||||
|
<elementName>Testcase</elementName>
|
||||||
|
<elementAttributes>
|
||||||
|
<entry>
|
||||||
|
<string>Testdata</string>
|
||||||
|
<testData>
|
||||||
|
<dataString>A Y X
|
||||||
|
|
||||||
|
0b000 0 0
|
||||||
|
0b001 1 1
|
||||||
|
0b010 1 1
|
||||||
|
0b011 0 0
|
||||||
|
0b100 1 0
|
||||||
|
0b101 1 0
|
||||||
|
0b110 1 0
|
||||||
|
0b111 1 0
|
||||||
|
</dataString>
|
||||||
|
</testData>
|
||||||
|
</entry>
|
||||||
|
</elementAttributes>
|
||||||
|
<pos x="400" y="340"/>
|
||||||
|
</visualElement>
|
||||||
|
</visualElements>
|
||||||
|
<wires>
|
||||||
|
<wire>
|
||||||
|
<p1 x="480" y="240"/>
|
||||||
|
<p2 x="500" y="240"/>
|
||||||
|
</wire>
|
||||||
|
<wire>
|
||||||
|
<p1 x="380" y="240"/>
|
||||||
|
<p2 x="400" y="240"/>
|
||||||
|
</wire>
|
||||||
|
<wire>
|
||||||
|
<p1 x="400" y="240"/>
|
||||||
|
<p2 x="420" y="240"/>
|
||||||
|
</wire>
|
||||||
|
<wire>
|
||||||
|
<p1 x="480" y="300"/>
|
||||||
|
<p2 x="500" y="300"/>
|
||||||
|
</wire>
|
||||||
|
<wire>
|
||||||
|
<p1 x="400" y="300"/>
|
||||||
|
<p2 x="420" y="300"/>
|
||||||
|
</wire>
|
||||||
|
<wire>
|
||||||
|
<p1 x="400" y="240"/>
|
||||||
|
<p2 x="400" y="300"/>
|
||||||
|
</wire>
|
||||||
|
</wires>
|
||||||
|
<measurementOrdering/>
|
||||||
|
</circuit>
|
Loading…
x
Reference in New Issue
Block a user