From 53034959f338c952f4cf905890e44aad2ba202ae Mon Sep 17 00:00:00 2001 From: Miodrag Milanovic Date: Fri, 20 Jul 2018 13:27:21 +0200 Subject: Start adding bitstream reading for ice40 --- gui/designwidget.cc | 11 +---------- 1 file changed, 1 insertion(+), 10 deletions(-) (limited to 'gui') diff --git a/gui/designwidget.cc b/gui/designwidget.cc index 4123bf30..d28b843b 100644 --- a/gui/designwidget.cc +++ b/gui/designwidget.cc @@ -334,16 +334,7 @@ void DesignWidget::newContext(Context *ctx) for (auto pip : nameToItem[2].toStdMap()) { pip_root->addChild(pip.second); } - - // Add nets to tree - nets_root = new QTreeWidgetItem(treeWidget); - nets_root->setText(0, "Nets"); - treeWidget->insertTopLevelItem(0, nets_root); - - // Add cells to tree - cells_root = new QTreeWidgetItem(treeWidget); - cells_root->setText(0, "Cells"); - treeWidget->insertTopLevelItem(0, cells_root); + updateTree(); } void DesignWidget::updateTree() -- cgit v1.2.3 From 9f0be8cd5f90b6b471f7e19c393af14377b1dc0b Mon Sep 17 00:00:00 2001 From: Miodrag Milanovic Date: Fri, 20 Jul 2018 19:16:36 +0200 Subject: make new context work again --- gui/designwidget.cc | 3 +++ 1 file changed, 3 insertions(+) (limited to 'gui') diff --git a/gui/designwidget.cc b/gui/designwidget.cc index d28b843b..f7ae82f5 100644 --- a/gui/designwidget.cc +++ b/gui/designwidget.cc @@ -230,6 +230,9 @@ void DesignWidget::addToHistory(QTreeWidgetItem *item) void DesignWidget::newContext(Context *ctx) { treeWidget->clear(); + // reset pointers since they are not valid after clear + nets_root = nullptr; + cells_root = nullptr; history_ignore = false; history_index = -1; history.clear(); -- cgit v1.2.3 From ec4fc0f830b859733b8729b03cdc3c54e84f8cea Mon Sep 17 00:00:00 2001 From: Miodrag Milanovic Date: Sat, 21 Jul 2018 11:24:29 +0200 Subject: made open project to work --- gui/ice40/mainwindow.cc | 75 +++++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 73 insertions(+), 2 deletions(-) (limited to 'gui') diff --git a/gui/ice40/mainwindow.cc b/gui/ice40/mainwindow.cc index 28792ed3..b58d6e8c 100644 --- a/gui/ice40/mainwindow.cc +++ b/gui/ice40/mainwindow.cc @@ -20,9 +20,12 @@ #include "mainwindow.h" #include #include +#include #include #include #include +#include +#include #include "bitstream.h" #include "design_utils.h" #include "jsonparse.h" @@ -252,10 +255,78 @@ void MainWindow::newContext(Context *ctx) void MainWindow::open_proj() { + QMap arch; +#ifdef ICE40_HX1K_ONLY + arch.insert("hx1k", ArchArgs::HX1K); +#else + arch.insert("lp384", ArchArgs::LP384); + arch.insert("lp1k", ArchArgs::LP1K); + arch.insert("hx1k", ArchArgs::HX1K); + arch.insert("up5k", ArchArgs::UP5K); + arch.insert("lp8k", ArchArgs::LP8K); + arch.insert("hx8k", ArchArgs::HX8K); +#endif + QString fileName = QFileDialog::getOpenFileName(this, QString("Open Project"), QString(), QString("*.proj")); if (!fileName.isEmpty()) { - std::string fn = fileName.toStdString(); - disableActions(); + try { + namespace pt = boost::property_tree; + + std::string fn = fileName.toStdString(); + disableActions(); + + pt::ptree root; + std::string filename = fileName.toStdString(); + pt::read_json(filename, root); + log_info("Loading project %s...\n", filename.c_str()); + log_break(); + + int version = root.get("project.version"); + if (version != 1) + log_error("Wrong project format version.\n"); + + std::string arch_name = root.get("project.arch.name"); + if (arch_name != "ice40") + log_error("Unsuported project architecture.\n"); + + std::string arch_type = root.get("project.arch.type"); + std::string arch_package = root.get("project.arch.package"); + + chipArgs.type = (ArchArgs::ArchArgsTypes)arch.value(arch_type); + chipArgs.package = arch_package; + ctx = std::unique_ptr(new Context(chipArgs)); + Q_EMIT contextChanged(ctx.get()); + + QFileInfo fi(fileName); + QDir::setCurrent(fi.absoluteDir().absolutePath()); + log_info("Setting current dir to %s...\n", fi.absoluteDir().absolutePath().toStdString().c_str()); + log_info("Loading project %s...\n", filename.c_str()); + log_info("Context changed to %s (%s)\n", arch_type.c_str(), arch_package.c_str()); + + auto project = root.get_child("project"); + std::string json; + std::string pcf; + if (project.count("input")) { + auto input = project.get_child("input"); + if (input.count("json")) + json = input.get("json"); + if (input.count("pcf")) + pcf = input.get("pcf"); + } + + if (!(QFileInfo::exists(json.c_str()) && QFileInfo(json.c_str()).isFile())) { + log_error("Json file does not exist.\n"); + } + if (!pcf.empty()) { + if (!(QFileInfo::exists(pcf.c_str()) && QFileInfo(pcf.c_str()).isFile())) { + log_error("PCF file does not exist.\n"); + } + } + + log_info("Loading json: %s...\n", json.c_str()); + load_json(json, pcf); + } catch (log_execution_error_exception) { + } } } -- cgit v1.2.3 From fe239366b5ac52374198a061d96b2224ca689412 Mon Sep 17 00:00:00 2001 From: Miodrag Milanovic Date: Sat, 21 Jul 2018 12:15:50 +0200 Subject: Made save project work as well --- gui/basewindow.cc | 2 +- gui/basewindow.h | 1 + gui/ice40/mainwindow.cc | 46 ++++++++++++++++++++++++++++++++++++++++------ gui/ice40/mainwindow.h | 5 ++++- 4 files changed, 46 insertions(+), 8 deletions(-) (limited to 'gui') diff --git a/gui/basewindow.cc b/gui/basewindow.cc index 4a225bd6..78c2fe3a 100644 --- a/gui/basewindow.cc +++ b/gui/basewindow.cc @@ -116,7 +116,7 @@ void BaseMainWindow::createMenusAndBars() actionOpen->setStatusTip("Open an existing project file"); connect(actionOpen, SIGNAL(triggered()), this, SLOT(open_proj())); - QAction *actionSave = new QAction("Save", this); + actionSave = new QAction("Save", this); actionSave->setIcon(QIcon(":/icons/resources/save.png")); actionSave->setShortcuts(QKeySequence::Save); actionSave->setStatusTip("Save existing project to disk"); diff --git a/gui/basewindow.h b/gui/basewindow.h index eee426c7..1184fa80 100644 --- a/gui/basewindow.h +++ b/gui/basewindow.h @@ -73,6 +73,7 @@ class BaseMainWindow : public QMainWindow QStatusBar *statusBar; QAction *actionNew; QAction *actionOpen; + QAction *actionSave; QProgressBar *progressBar; DesignWidget *designview; }; diff --git a/gui/ice40/mainwindow.cc b/gui/ice40/mainwindow.cc index b58d6e8c..017ca2fa 100644 --- a/gui/ice40/mainwindow.cc +++ b/gui/ice40/mainwindow.cc @@ -224,7 +224,9 @@ void MainWindow::new_proj() if (ok && !item.isEmpty()) { disableActions(); - preload_pcf = ""; + currentProj = ""; + currentJson = ""; + currentPCF = ""; chipArgs.package = package.toStdString().c_str(); ctx = std::unique_ptr(new Context(chipArgs)); actionLoadJSON->setEnabled(true); @@ -236,14 +238,16 @@ void MainWindow::new_proj() void MainWindow::load_json(std::string filename, std::string pcf) { - preload_pcf = pcf; disableActions(); + currentJson = filename; + currentPCF = pcf; Q_EMIT task->loadfile(filename); } void MainWindow::load_pcf(std::string filename) { disableActions(); + currentPCF = filename; Q_EMIT task->loadpcf(filename); } @@ -273,6 +277,7 @@ void MainWindow::open_proj() namespace pt = boost::property_tree; std::string fn = fileName.toStdString(); + currentProj = fn; disableActions(); pt::ptree root; @@ -346,7 +351,35 @@ void MainWindow::open_pcf() } } -bool MainWindow::save_proj() { return false; } +bool MainWindow::save_proj() +{ + if (currentProj.empty()) { + QString fileName = QFileDialog::getSaveFileName(this, QString("Save Project"), QString(), QString("*.proj")); + if (fileName.isEmpty()) + return false; + currentProj = fileName.toStdString(); + } + if (!currentProj.empty()) { + namespace pt = boost::property_tree; + QFileInfo fi(currentProj.c_str()); + QDir dir(fi.absoluteDir().absolutePath()); + std::ofstream f(currentProj); + pt::ptree root; + root.put("project.version", 1); + root.put("project.name", fi.baseName().toStdString()); + root.put("project.arch.name", ctx->archId().c_str(ctx.get())); + root.put("project.arch.type", ctx->archArgsToId(chipArgs).c_str(ctx.get())); + root.put("project.arch.package", chipArgs.package); + if (!currentJson.empty()) + root.put("project.input.json", dir.relativeFilePath(currentJson.c_str()).toStdString()); + if (!currentPCF.empty()) + root.put("project.input.pcf", dir.relativeFilePath(currentPCF.c_str()).toStdString()); + pt::write_json(f, root); + log_info("Project %s saved...\n", fi.baseName().toStdString().c_str()); + return true; + } + return false; +} void MainWindow::save_asc() { @@ -374,6 +407,7 @@ void MainWindow::disableActions() actionNew->setEnabled(true); actionOpen->setEnabled(true); + actionSave->setEnabled(!currentJson.empty()); } void MainWindow::loadfile_finished(bool status) @@ -383,12 +417,12 @@ void MainWindow::loadfile_finished(bool status) log("Loading design successful.\n"); actionLoadPCF->setEnabled(true); actionPack->setEnabled(true); - if (!preload_pcf.empty()) - load_pcf(preload_pcf); + if (!currentPCF.empty()) + load_pcf(currentPCF); Q_EMIT updateTreeView(); } else { log("Loading design failed.\n"); - preload_pcf = ""; + currentPCF = ""; } } diff --git a/gui/ice40/mainwindow.h b/gui/ice40/mainwindow.h index cfd938f8..4600d1da 100644 --- a/gui/ice40/mainwindow.h +++ b/gui/ice40/mainwindow.h @@ -79,7 +79,10 @@ class MainWindow : public BaseMainWindow bool timing_driven; ArchArgs chipArgs; - std::string preload_pcf; + + std::string currentProj; + std::string currentJson; + std::string currentPCF; }; NEXTPNR_NAMESPACE_END -- cgit v1.2.3 From 09a68affa388ffafdf361ccd3de621173f2b8b48 Mon Sep 17 00:00:00 2001 From: Miodrag Milanovic Date: Sat, 21 Jul 2018 12:22:41 +0200 Subject: Fix warnings and status --- gui/ice40/mainwindow.cc | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'gui') diff --git a/gui/ice40/mainwindow.cc b/gui/ice40/mainwindow.cc index 017ca2fa..847698c5 100644 --- a/gui/ice40/mainwindow.cc +++ b/gui/ice40/mainwindow.cc @@ -222,11 +222,11 @@ void MainWindow::new_proj() QString package = QInputDialog::getItem(this, "Select package", "Package:", getSupportedPackages(chipArgs.type), 0, false, &ok); - if (ok && !item.isEmpty()) { - disableActions(); + if (ok && !item.isEmpty()) { currentProj = ""; currentJson = ""; currentPCF = ""; + disableActions(); chipArgs.package = package.toStdString().c_str(); ctx = std::unique_ptr(new Context(chipArgs)); actionLoadJSON->setEnabled(true); -- cgit v1.2.3 From 78f40ca0af493b9ba07bb8d7c95f558f2c04d4cb Mon Sep 17 00:00:00 2001 From: Clifford Wolf Date: Sat, 21 Jul 2018 13:52:59 +0200 Subject: Change DelayInfo semantics to what we actually need Signed-off-by: Clifford Wolf --- gui/designwidget.cc | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) (limited to 'gui') diff --git a/gui/designwidget.cc b/gui/designwidget.cc index f7ae82f5..c40e58d3 100644 --- a/gui/designwidget.cc +++ b/gui/designwidget.cc @@ -507,6 +507,14 @@ void DesignWidget::onItemSelectionChanged() addProperty(topItem, QVariant::String, "Conflicting Net", ctx->getConflictingWireNet(wire).c_str(ctx), ElementType::NET); + DelayInfo delay = ctx->getWireDelay(wire); + + QtProperty *delayItem = addSubGroup(topItem, "Delay"); + addProperty(delayItem, QVariant::Double, "Min Raise", delay.minRaiseDelay()); + addProperty(delayItem, QVariant::Double, "Max Raise", delay.maxRaiseDelay()); + addProperty(delayItem, QVariant::Double, "Min Fall", delay.minFallDelay()); + addProperty(delayItem, QVariant::Double, "Max Fall", delay.maxFallDelay()); + QtProperty *belpinItem = addSubGroup(topItem, "BelPin Uphill"); BelPin uphill = ctx->getBelPinUphill(wire); if (uphill.bel != BelId()) @@ -566,9 +574,10 @@ void DesignWidget::onItemSelectionChanged() DelayInfo delay = ctx->getPipDelay(pip); QtProperty *delayItem = addSubGroup(topItem, "Delay"); - addProperty(delayItem, QVariant::Double, "Raise", delay.raiseDelay()); - addProperty(delayItem, QVariant::Double, "Fall", delay.fallDelay()); - addProperty(delayItem, QVariant::Double, "Average", delay.avgDelay()); + addProperty(delayItem, QVariant::Double, "Min Raise", delay.minRaiseDelay()); + addProperty(delayItem, QVariant::Double, "Max Raise", delay.maxRaiseDelay()); + addProperty(delayItem, QVariant::Double, "Min Fall", delay.minFallDelay()); + addProperty(delayItem, QVariant::Double, "Max Fall", delay.maxFallDelay()); } else if (type == ElementType::NET) { NetInfo *net = ctx->nets.at(c).get(); -- cgit v1.2.3 From a8eadb5ba26013f9ec732f431e349fcbcfc8fbe9 Mon Sep 17 00:00:00 2001 From: Clifford Wolf Date: Sat, 21 Jul 2018 13:53:29 +0200 Subject: Fix minor issue in GUI Wire properties Signed-off-by: Clifford Wolf --- gui/designwidget.cc | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'gui') diff --git a/gui/designwidget.cc b/gui/designwidget.cc index c40e58d3..a59307f0 100644 --- a/gui/designwidget.cc +++ b/gui/designwidget.cc @@ -537,7 +537,7 @@ void DesignWidget::onItemSelectionChanged() } int counter = 0; - QtProperty *pipsDownItem = addSubGroup(downhillItem, "Pips Downhill"); + QtProperty *pipsDownItem = addSubGroup(topItem, "Pips Downhill"); for (const auto &item : ctx->getPipsDownhill(wire)) { addProperty(pipsDownItem, QVariant::String, "", ctx->getPipName(item).c_str(ctx), ElementType::PIP); counter++; @@ -548,7 +548,7 @@ void DesignWidget::onItemSelectionChanged() } counter = 0; - QtProperty *pipsUpItem = addSubGroup(downhillItem, "Pips Uphill"); + QtProperty *pipsUpItem = addSubGroup(topItem, "Pips Uphill"); for (const auto &item : ctx->getPipsUphill(wire)) { addProperty(pipsUpItem, QVariant::String, "", ctx->getPipName(item).c_str(ctx), ElementType::PIP); counter++; -- cgit v1.2.3