From b16a85d03353d7054cbcc24566923b07044e1316 Mon Sep 17 00:00:00 2001 From: Roy Qu Date: Mon, 14 Aug 2023 12:22:24 +0800 Subject: [PATCH] - Retrieve sdcc predefined macros (hacking). - Stop compiling if ihx file is not correct created. - Run/Debug/Generate assembly actions are correctly diabled. --- RedPandaIDE/compiler/compiler.cpp | 25 +++--- RedPandaIDE/compiler/compiler.h | 3 +- RedPandaIDE/compiler/sdccfilecompiler.cpp | 18 ++++- RedPandaIDE/compiler/sdccfilecompiler.h | 3 + RedPandaIDE/editor.cpp | 19 ++--- RedPandaIDE/mainwindow.cpp | 76 ++++++++++++------- RedPandaIDE/settings.cpp | 70 +++++++++++++++-- RedPandaIDE/settingsdialog/settingsdialog.cpp | 10 +-- RedPandaIDE/settingsdialog/settingsdialog.h | 1 - 9 files changed, 155 insertions(+), 70 deletions(-) diff --git a/RedPandaIDE/compiler/compiler.cpp b/RedPandaIDE/compiler/compiler.cpp index 935bd80a..f5518f60 100644 --- a/RedPandaIDE/compiler/compiler.cpp +++ b/RedPandaIDE/compiler/compiler.cpp @@ -42,7 +42,7 @@ Compiler::Compiler(const QString &filename, bool silent, bool onlyCheckSyntax): mOnlyCheckSyntax(onlyCheckSyntax), mFilename(filename), mRebuild(false), - mParser() + mParserForFile() { getParserForFile(filename); } @@ -66,6 +66,8 @@ void Compiler::run() timer.start(); runCommand(mCompiler, mArguments, mDirectory, pipedText()); for(int i=0;ieditor().enableAutolink() - && mParser){ + && mParserForFile){ int waitCount = 0; //wait parsing ends, at most 1 second - while(mParser->parsing()) { + while(mParserForFile->parsing()) { if (waitCount>10) break; waitCount++; @@ -521,10 +528,10 @@ QString Compiler::getLibraryArguments(FileType fileType) // is file and auto link enabled if (pSettings->editor().enableAutolink() && (fileType == FileType::CSource || fileType == FileType::CppSource) - && mParser){ + && mParserForFile){ int waitCount = 0; //wait parsing ends, at most 1 second - while(mParser->parsing()) { + while(mParserForFile->parsing()) { if (waitCount>10) break; waitCount++; @@ -608,7 +615,7 @@ QString Compiler::parseFileIncludesForAutolink( if (autolink) { result += ' '+autolink->linkOption; } - QStringList includedFiles = mParser->getFileDirectIncludes(filename); + QStringList includedFiles = mParserForFile->getFileDirectIncludes(filename); // log(QString("File %1 included:").arg(filename)); // for (int i=includedFiles.size()-1;i>=0;i--) { // QString includeFilename = includedFiles[i]; @@ -634,7 +641,7 @@ bool Compiler::parseForceUTF8ForAutolink(const QString &filename, QSet if (autolink && autolink->execUseUTF8) { return true; } - QStringList includedFiles = mParser->getFileDirectIncludes(filename); + QStringList includedFiles = mParserForFile->getFileDirectIncludes(filename); // log(QString("File %1 included:").arg(filename)); // for (int i=includedFiles.size()-1;i>=0;i--) { // QString includeFilename = includedFiles[i]; @@ -759,7 +766,7 @@ void Compiler::runCommand(const QString &cmd, const QString &arguments, const Q PCppParser Compiler::parser() const { - return mParser; + return mParserForFile; } void Compiler::getParserForFile(const QString &filename) @@ -769,7 +776,7 @@ void Compiler::getParserForFile(const QString &filename) fileType == FileType::CppSource){ Editor* editor = pMainWindow->editorList()->getOpenedEditorByFilename(filename); if (editor && editor->parser()) { - mParser=editor->parser(); + mParserForFile=editor->parser(); } } } diff --git a/RedPandaIDE/compiler/compiler.h b/RedPandaIDE/compiler/compiler.h index 974cb175..326f23ce 100644 --- a/RedPandaIDE/compiler/compiler.h +++ b/RedPandaIDE/compiler/compiler.h @@ -69,6 +69,7 @@ protected: virtual bool prepareForCompile() = 0; virtual QByteArray pipedText(); virtual bool prepareForRebuild() = 0; + virtual bool beforeRunExtraCommand(int idx); virtual QString getCharsetArgument(const QByteArray& encoding, FileType fileType, bool onlyCheckSyntax); virtual QString getCCompileArguments(bool checkSyntax); virtual QString getCppCompileArguments(bool checkSyntax); @@ -103,7 +104,7 @@ protected: bool mRebuild; std::shared_ptr mProject; bool mSetLANG; - PCppParser mParser; + PCppParser mParserForFile; private: bool mStop; diff --git a/RedPandaIDE/compiler/sdccfilecompiler.cpp b/RedPandaIDE/compiler/sdccfilecompiler.cpp index 2d2817c4..dfb6fcb0 100644 --- a/RedPandaIDE/compiler/sdccfilecompiler.cpp +++ b/RedPandaIDE/compiler/sdccfilecompiler.cpp @@ -43,10 +43,10 @@ bool SDCCFileCompiler::prepareForCompile() log(tr("- Filename: %1").arg(mFilename)); log(tr("- Compiler Set Name: %1").arg(compilerSet()->name())); log(""); - QString ihxFile = changeFileExt(mFilename,SDCC_IHX_SUFFIX); + mIhxFilename = changeFileExt(mFilename,SDCC_IHX_SUFFIX); mOutputFile=changeFileExt(mFilename, compilerSet()->executableSuffix()); mArguments = QString(" \"%1\"").arg(mFilename); - mArguments+=QString(" -o \"%1\"").arg(ihxFile); + mArguments+=QString(" -o \"%1\"").arg(mIhxFilename); //remove the old file if it exists QFile outputFile(mOutputFile); @@ -75,7 +75,7 @@ bool SDCCFileCompiler::prepareForCompile() } mExtraCompilersList.append(packihx); QString args; - args = QString(" \"%1\"").arg(ihxFile); + args = QString(" \"%1\"").arg(mIhxFilename); mExtraArgumentsList.append(args); mExtraOutputFilesList.append(mOutputFile); } else if (compilerSet()->executableSuffix() == SDCC_BIN_SUFFIX) { @@ -86,7 +86,7 @@ bool SDCCFileCompiler::prepareForCompile() } mExtraCompilersList.push_back(makebin); QString args; - args = QString(" \"%1\"").arg(ihxFile); + args = QString(" \"%1\"").arg(mIhxFilename); args+=QString(" \"%1\"").arg(mOutputFile); mExtraArgumentsList.push_back(args); mExtraOutputFilesList.append(""); @@ -109,6 +109,16 @@ bool SDCCFileCompiler::prepareForCompile() log(tr("- %1 Compiler: %2").arg(strFileType).arg(mCompiler)); log(tr("- Command: %1 %2").arg(extractFileName(mCompiler)).arg(mArguments)); mDirectory = extractFileDir(mFilename); + mStartCompileTime = QDateTime::currentDateTime(); + return true; +} + +bool SDCCFileCompiler::beforeRunExtraCommand(int idx) +{ + if (idx==0) { + QFileInfo file(mIhxFilename); + return file.exists() && (file.lastModified()>mStartCompileTime); + } return true; } diff --git a/RedPandaIDE/compiler/sdccfilecompiler.h b/RedPandaIDE/compiler/sdccfilecompiler.h index d87b8a51..b7b1108d 100644 --- a/RedPandaIDE/compiler/sdccfilecompiler.h +++ b/RedPandaIDE/compiler/sdccfilecompiler.h @@ -30,10 +30,13 @@ public: protected: bool prepareForCompile() override; + bool beforeRunExtraCommand(int idx) override; private: QByteArray mEncoding; CppCompileType mCompileType; + QDateTime mStartCompileTime; + QString mIhxFilename; // Compiler interface protected: bool prepareForRebuild() override; diff --git a/RedPandaIDE/editor.cpp b/RedPandaIDE/editor.cpp index ccc74bec..26907c3a 100644 --- a/RedPandaIDE/editor.cpp +++ b/RedPandaIDE/editor.cpp @@ -5240,27 +5240,20 @@ void Editor::applySettings() setRightEdge(0); } - if (pSettings->editor().enableCustomCTypeKeywords()) { - if (syntaxer() && syntaxer()->language() == QSynedit::ProgrammingLanguage::CPP) { - QSet set; + if (syntaxer() && syntaxer()->language() == QSynedit::ProgrammingLanguage::CPP) { + QSet set; + if (pSettings->editor().enableCustomCTypeKeywords()) { foreach(const QString& s, pSettings->editor().customCTypeKeywords()) set.insert(s); - ((QSynedit::CppSyntaxer*)(syntaxer().get()))->setCustomTypeKeywords(set); } #ifdef ENABLE_SDCC - } else if (!inProject() && pSettings->compilerSets().defaultSet() + if (!inProject() && pSettings->compilerSets().defaultSet() && pSettings->compilerSets().defaultSet()->compilerType()==CompilerType::SDCC) { - if (syntaxer() && syntaxer()->language() == QSynedit::ProgrammingLanguage::CPP) { - QSet set; - foreach(const QString& s, pSettings->editor().customCTypeKeywords()) + foreach(const QString& s, SDCCKeywords.keys()) set.insert(s); - ((QSynedit::CppSyntaxer*)(syntaxer().get()))->setCustomTypeKeywords(set); } #endif - } else { - if (syntaxer() && syntaxer()->language() == QSynedit::ProgrammingLanguage::CPP) { - ((QSynedit::CppSyntaxer*)(syntaxer().get()))->setCustomTypeKeywords(QSet()); - } + ((QSynedit::CppSyntaxer*)(syntaxer().get()))->setCustomTypeKeywords(set); } this->setUndoLimit(pSettings->editor().undoLimit()); diff --git a/RedPandaIDE/mainwindow.cpp b/RedPandaIDE/mainwindow.cpp index 1577d64c..527fb16e 100644 --- a/RedPandaIDE/mainwindow.cpp +++ b/RedPandaIDE/mainwindow.cpp @@ -718,35 +718,57 @@ void MainWindow::updateCompileActions(const Editor *e) } else { bool forProject=false; bool canRun = false; + bool canDebug = false; bool canCompile = false; bool canGenerateAssembly=false; - if (e) { - if (!e->inProject()) { - FileType fileType = getFileType(e->filename()); - if (fileType == FileType::CSource - || fileType == FileType::CppSource) { - canGenerateAssembly = true; - canCompile = true; - canRun = true; - } else if (fileType == FileType::GAS) { - canCompile = true; - canRun = true; - } - } else { - forProject = (mProject!=nullptr); - } - } else { - forProject = (mProject!=nullptr); - } - if (forProject) { - canCompile = true; - canRun = (mProject->options().type !=ProjectType::DynamicLib) - && (mProject->options().type !=ProjectType::StaticLib); + Settings::PCompilerSet set=pSettings->compilerSets().getSet(mCompilerSet->currentIndex()); + if (set) { if (e) { - FileType fileType = getFileType(e->filename()); - if (fileType == FileType::CSource - || fileType == FileType::CppSource) { - canGenerateAssembly = true; + if (!e->inProject()) { + FileType fileType = getFileType(e->filename()); + switch(fileType) { + case FileType::CSource: + canCompile = set->canCompileC(); +#ifdef ENABLE_SDCC + if (set->compilerType()!=CompilerType::SDCC) +#endif + { + canGenerateAssembly = canCompile; + canRun = canCompile ; + } + canDebug = set->canDebug(); + break; + case FileType::CppSource: + canCompile = set->canCompileCPP(); + canGenerateAssembly = canCompile; + canRun = canCompile; + canDebug = set->canDebug(); + break; + case FileType::GAS: + if (set->compilerType()==CompilerType::GCC) { + canCompile = true; + canRun = canCompile; + canDebug = set->canDebug(); + } + break; + } + } else { + forProject = (mProject!=nullptr); + } + } else { + forProject = (mProject!=nullptr); + } + if (forProject) { + canCompile = true; + canRun = (mProject->options().type !=ProjectType::DynamicLib) + && (mProject->options().type !=ProjectType::StaticLib); + canDebug = set->canDebug() && canRun; + if (e) { + FileType fileType = getFileType(e->filename()); + if (fileType == FileType::CSource + || fileType == FileType::CppSource) { + canGenerateAssembly = true; + } } } } @@ -754,7 +776,7 @@ void MainWindow::updateCompileActions(const Editor *e) ui->actionRun->setEnabled(canRun); ui->actionRebuild->setEnabled(canCompile); ui->actionGenerate_Assembly->setEnabled(canGenerateAssembly); - ui->actionDebug->setEnabled(canRun); + ui->actionDebug->setEnabled(canDebug); mProblem_RunAllCases->setEnabled(canRun && mOJProblemModel.count()>0); } if (!mDebugger->executing()) { diff --git a/RedPandaIDE/settings.cpp b/RedPandaIDE/settings.cpp index 9764a003..8432f341 100644 --- a/RedPandaIDE/settings.cpp +++ b/RedPandaIDE/settings.cpp @@ -2346,6 +2346,7 @@ QStringList Settings::CompilerSet::defines(bool isCpp) { #ifdef ENABLE_SDCC if (mCompilerType==CompilerType::SDCC) { arguments.append("c"); + arguments.append("-V"); key=SDCC_CMD_OPT_PROCESSOR; } else { #endif @@ -2367,17 +2368,62 @@ QStringList Settings::CompilerSet::defines(bool isCpp) { } arguments.append(NULL_FILE); - //qDebug()< lines = output.split('\n'); - for (QByteArray& line:lines) { - QByteArray trimmedLine = line.trimmed(); - if (!trimmedLine.isEmpty()) { - result.append(trimmedLine); +#ifdef ENABLE_SDCC + if (mCompilerType==CompilerType::SDCC) { + QList lines = output.split('\n'); + QByteArray currentLine; + for (QByteArray& line:lines) { + QByteArray trimmedLine = line.trimmed(); + if (trimmedLine.startsWith("+")) { + currentLine = line; + break; + } + } + lines = currentLine.split(' '); + for (QByteArray& line:lines) { + QByteArray trimmedLine = line.trimmed(); + if (trimmedLine.startsWith("-D")) { + trimmedLine = trimmedLine.mid(2); + if (trimmedLine.contains("=")) { + QList items=trimmedLine.split('='); + result.append(QString("#define %1 %2").arg(items[0],items[1])); + } else { + result.append("#define "+trimmedLine); + } + } + } + } else { +#else + { +#endif + QList lines = output.split('\n'); + for (QByteArray& line:lines) { + QByteArray trimmedLine = line.trimmed(); + if (!trimmedLine.isEmpty()) { + result.append(trimmedLine); + } } } return result; @@ -2648,6 +2694,10 @@ bool Settings::CompilerSet::canCompileC() const bool Settings::CompilerSet::canCompileCPP() const { +#ifdef ENABLE_SDCC + if (mCompilerType==CompilerType::SDCC) + return false; +#endif return fileExists(mCppCompiler); } @@ -2658,6 +2708,10 @@ bool Settings::CompilerSet::canMake() const bool Settings::CompilerSet::canDebug() const { +#ifdef ENABLE_SDCC + if (mCompilerType==CompilerType::SDCC) + return false; +#endif return fileExists(mDebugger); } @@ -2705,6 +2759,8 @@ QByteArray Settings::CompilerSet::getCompilerOutput(const QString &binDir, const { QProcessEnvironment env; env.insert("LANG","en"); + QString path = binDir; + env.insert("PATH",path); QByteArray result = runAndGetOutput( includeTrailingPathDelimiter(binDir)+binFile, binDir, diff --git a/RedPandaIDE/settingsdialog/settingsdialog.cpp b/RedPandaIDE/settingsdialog/settingsdialog.cpp index 00fa4e9b..5c3c8132 100644 --- a/RedPandaIDE/settingsdialog/settingsdialog.cpp +++ b/RedPandaIDE/settingsdialog/settingsdialog.cpp @@ -135,7 +135,7 @@ void SettingsDialog::selectFirstWidget() widgetIndex, QItemSelectionModel::Select ); - on_widgetsView_clicked(widgetIndex); + showWidget(widgetIndex); } PSettingsDialog SettingsDialog::optionDialog() @@ -301,19 +301,13 @@ bool SettingsDialog::setCurrentWidget(const QString &widgetName, const QString & QStandardItem* pWidgetItem = pGroupItem->child(i); if (pWidgetItem->text() == widgetName) { ui->widgetsView->setCurrentIndex(pWidgetItem->index()); - on_widgetsView_clicked(pWidgetItem->index()); + showWidget(pWidgetItem->index()); return true; } } return false; } - -void SettingsDialog::on_widgetsView_clicked(const QModelIndex &index) -{ - showWidget(index); -} - void SettingsDialog::widget_settings_changed(bool value) { ui->btnApply->setEnabled(value); diff --git a/RedPandaIDE/settingsdialog/settingsdialog.h b/RedPandaIDE/settingsdialog/settingsdialog.h index 735350e5..006e4fcd 100644 --- a/RedPandaIDE/settingsdialog/settingsdialog.h +++ b/RedPandaIDE/settingsdialog/settingsdialog.h @@ -58,7 +58,6 @@ private slots: void widget_settings_changed(bool value); void onWidgetsViewCurrentChanged(const QModelIndex &index, const QModelIndex &previous); - void on_widgetsView_clicked(const QModelIndex &index); void on_btnCancel_pressed();