edacation
Version:
Library and CLI for interacting with Yosys and nextpnr.
157 lines • 7.08 kB
JavaScript
;
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
exports.getYosysSynthesisWorkerOptions = exports.getYosysRTLWorkerOptions = exports.getYosysOptions = void 0;
const path_1 = __importDefault(require("path"));
const util_js_1 = require("../util.js");
const devices_js_1 = require("./devices.js");
const target_js_1 = require("./target.js");
const DEFAULT_OPTIONS = {
optimize: true,
topLevelModule: undefined,
synthArguments: undefined,
};
const getYosysOptions = (configuration, targetId) => (0, target_js_1.getOptions)(configuration, targetId, 'yosys', DEFAULT_OPTIONS);
exports.getYosysOptions = getYosysOptions;
const getFileIngestCommands = (inputFiles, options) => {
const commands = [];
// Load vhdl files
const vhdlFiles = inputFiles.filter((file) => util_js_1.FILE_EXTENSIONS_VHDL.includes(path_1.default.extname(file).substring(1)));
if (vhdlFiles.length) {
if (!options.topLevelModule) {
throw new Error('Top level module must be defined when synthesizing VHDL');
}
commands.push('plugin -i ghdl;', `ghdl ${vhdlFiles.join(' ')} -e ${options.topLevelModule};`);
}
// Load verilog files
const verilogFiles = inputFiles.filter((file) => util_js_1.FILE_EXTENSIONS_VERILOG.includes(path_1.default.extname(file).substring(1)));
if (verilogFiles.length) {
commands.push(...verilogFiles.map((file) => `read_verilog -sv "${file}";`));
}
// (auto-)set top-level module
if (options.topLevelModule) {
commands.push(`hierarchy -top ${options.topLevelModule};`);
}
else {
commands.push('hierarchy -auto-top;');
}
return commands;
};
const getInputFiles = (project, targetId) => {
const generatedInputFiles = project.getInputFiles()
.filter((inputFile) => inputFile.type === 'design' && util_js_1.FILE_EXTENSIONS_HDL.includes(path_1.default.extname(inputFile.path).substring(1)))
.map((file) => file.path);
return (0, target_js_1.getCombined)(project.getConfiguration(), targetId, 'yosys', 'inputFiles', generatedInputFiles).filter((f) => !!f);
};
const getOutputFiles = (project, targetId, files) => {
const target = project.getTarget(targetId);
if (target === null)
throw new Error('Target not found');
const generatedOutputFiles = files.map(f => (0, target_js_1.getTargetFile)(target.config, f));
return (0, target_js_1.getCombined)(project.getConfiguration(), targetId, 'yosys', 'outputFiles', generatedOutputFiles).filter((f) => !!f);
};
const getYosysRTLWorkerOptions = (project, targetId) => {
const configuration = project.getConfiguration();
const target = (0, target_js_1.getTarget)(configuration, targetId);
const options = (0, exports.getYosysOptions)(configuration, targetId);
// Input files
const inputFiles = getInputFiles(project, targetId);
// Output files
const outputFiles = getOutputFiles(project, targetId, ["stats.yosys.json", "rtl.yosys.json"]);
// Commands
const generatedCommands = [
...getFileIngestCommands(inputFiles, options),
'proc;',
];
if (options.optimize)
generatedCommands.push('opt;');
generatedCommands.push('memory -nomap;');
if (options.optimize)
generatedCommands.push('wreduce -memx;', 'opt -full;');
generatedCommands.push(`tee -q -o "${(0, target_js_1.getTargetFile)(target, 'stats.yosys.json')}" stat -json -width *;`, `write_json "${(0, target_js_1.getTargetFile)(target, 'rtl.yosys.json')}";`, '');
const commands = (0, target_js_1.getCombined)(configuration, targetId, 'yosys', 'rtlCommands', generatedCommands);
const encoder = new TextEncoder();
return {
inputFiles,
outputFiles,
target,
options,
steps: [
{
id: 'rtl',
tool: 'yosys',
arguments: ['rtl.ys'],
generatedInputFiles: [
{ name: 'rtl.ys', content: encoder.encode(commands.join('\n')) }
],
commands,
}
]
};
};
exports.getYosysRTLWorkerOptions = getYosysRTLWorkerOptions;
const getYosysSynthesisWorkerOptions = (project, targetId) => {
const configuration = project.getConfiguration();
const target = (0, target_js_1.getTarget)(configuration, targetId);
const options = (0, exports.getYosysOptions)(configuration, targetId);
const vendor = devices_js_1.VENDORS[target.vendor];
const family = vendor.families[target.family];
// Input files
const inputFiles = getInputFiles(project, targetId);
// Output files
const outputFiles = getOutputFiles(project, targetId, [`${family.architecture}.json`]);
// Commands (preparation)
const generatedPrepareCommands = [
...getFileIngestCommands(inputFiles, options),
'proc;',
];
if (options.optimize)
generatedPrepareCommands.push('opt;');
generatedPrepareCommands.push(`write_json "${(0, target_js_1.getTargetFile)(target, 'presynth.yosys.json')}";`, '');
const prepareCommands = (0, target_js_1.getCombined)(configuration, targetId, 'yosys', 'synthPrepareCommands', generatedPrepareCommands);
// Commands (synthesis)
const generatedSynthCommands = [
`read_json "${(0, target_js_1.getTargetFile)(target, 'presynth.yosys.json')}";`,
];
const synthArgs = options.synthArguments || '';
if (family.architecture === 'generic') {
generatedSynthCommands.push(`synth ${synthArgs};`);
generatedSynthCommands.push(`write_json "${(0, target_js_1.getTargetFile)(target, family.architecture)}.json";`);
}
else {
generatedSynthCommands.push(`synth_${family.architecture} -json "${(0, target_js_1.getTargetFile)(target, family.architecture)}.json" ${synthArgs};`);
}
generatedSynthCommands.push('');
const synthCommands = (0, target_js_1.getCombined)(configuration, targetId, 'yosys', 'synthCommands', generatedSynthCommands);
const encoder = new TextEncoder();
return {
inputFiles,
outputFiles,
target,
options,
steps: [
{
id: 'prepare',
tool: 'yosys',
arguments: ['synth-prepare.ys'],
generatedInputFiles: [
{ name: 'synth-prepare.ys', content: encoder.encode(prepareCommands.join('\n')) }
],
commands: prepareCommands,
},
{
id: 'synth',
tool: 'yosys',
arguments: ['synth.ys'],
generatedInputFiles: [
{ name: 'synth.ys', content: encoder.encode(synthCommands.join('\n')) }
],
commands: synthCommands,
}
]
};
};
exports.getYosysSynthesisWorkerOptions = getYosysSynthesisWorkerOptions;
//# sourceMappingURL=yosys.js.map