summaryrefslogtreecommitdiffstats
path: root/source/compiler-core/slang-command-line-args.cpp
diff options
context:
space:
mode:
authorjsmall-nvidia <jsmall@nvidia.com>2021-05-21 18:41:54 -0400
committerGitHub <noreply@github.com>2021-05-21 15:41:54 -0700
commit172538fdb418f7a2faab1f5a410f3b2cb8e18ba5 (patch)
treeb17fd1cae7ace4bb3f2dbdd4ad29f4f57df0b286 /source/compiler-core/slang-command-line-args.cpp
parent0389546b0b065303d3c6874891a9fab4428910b9 (diff)
Downstream option handling (#1850)
* #include an absolute path didn't work - because paths were taken to always be relative. * Added SourceLoc handling for command line parsing. * Fix typo in debug. * Fix issue around the DiagnosticSink used in options parsing not having a writer available - by having DiagnosticSink parenting. * Small rename for clarity. * WIP extracting command line args for downstream tools. * Unit tests/bug fixes around extracting args. * Use DownstreamArgs in the EndToEndCompileRequest * Passing downstream compiler options downstream. * Fix issue with endToEndReq being nullptr. * Fix issue with diagnostics number change. * Small improvements to how the source line is displayed if it's too long. Default to 120, as suggested in previous review. Co-authored-by: T. Foley <tfoleyNV@users.noreply.github.com>
Diffstat (limited to 'source/compiler-core/slang-command-line-args.cpp')
-rw-r--r--source/compiler-core/slang-command-line-args.cpp187
1 files changed, 183 insertions, 4 deletions
diff --git a/source/compiler-core/slang-command-line-args.cpp b/source/compiler-core/slang-command-line-args.cpp
index da262e9bb..1d452bb10 100644
--- a/source/compiler-core/slang-command-line-args.cpp
+++ b/source/compiler-core/slang-command-line-args.cpp
@@ -11,7 +11,9 @@ void CommandLineArgs::setArgs(const char*const* args, size_t argCount)
{
m_args.clear();
- const SourceLoc startLoc = m_sourceManager->getNextRangeStart();
+ SourceManager* sourceManager = m_context->getSourceManager();
+
+ const SourceLoc startLoc = sourceManager->getNextRangeStart();
StringBuilder buf;
@@ -36,12 +38,32 @@ void CommandLineArgs::setArgs(const char*const* args, size_t argCount)
buf << " ";
}
- SourceFile* sourceFile = m_sourceManager->createSourceFileWithString(PathInfo::makeUnknown(), buf.ProduceString());
- m_sourceView = m_sourceManager->createSourceView(sourceFile, nullptr, SourceLoc::fromRaw(0));
+ SourceFile* sourceFile = sourceManager->createSourceFileWithString(PathInfo::makeUnknown(), buf.ProduceString());
+ SourceView* sourceView = sourceManager->createSourceView(sourceFile, nullptr, SourceLoc::fromRaw(0));
- SLANG_ASSERT(m_sourceView->getRange().begin == startLoc);
+ SLANG_UNUSED(sourceView);
+ SLANG_ASSERT(sourceView->getRange().begin == startLoc);
}
+bool CommandLineArgs::hasArgs(const char*const* args, Index count) const
+{
+ if (m_args.getCount() != count)
+ {
+ return false;
+ }
+
+ for (Index i = 0; i < count; ++i)
+ {
+ if (m_args[i].value != args[i])
+ {
+ return false;
+ }
+ }
+
+ return true;
+}
+
+
/* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
CommandLineReader
@@ -91,5 +113,162 @@ SlangResult CommandLineReader::expectArg(CommandLineArg& outArg)
}
}
+/* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
+
+ DownstreamArgs
+
+!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!! */
+
+Index DownstreamArgs::addName(const String& name)
+{
+ Index index = m_names.indexOf(name);
+ if (index < 0)
+ {
+ index = m_names.getCount();
+ m_names.add(name);
+
+ CommandLineArgs args(m_context);
+ m_args.add(args);
+ }
+ return index;
+}
+
+Index DownstreamArgs::_findOrAddName(SourceLoc loc, const UnownedStringSlice& name, Flags flags, DiagnosticSink* sink)
+{
+ if (name.getLength() <= 0)
+ {
+ sink->diagnose(loc, MiscDiagnostics::downstreamToolNameNotDefined);
+ return -1;
+ }
+
+ if (flags & Flag::AllowNewNames)
+ {
+ return addName(name);
+ }
+
+ Index index = findName(name);
+ if (index >= 0)
+ {
+ return index;
+ }
+
+ sink->diagnose(loc, MiscDiagnostics::downstreamNameNotKnown);
+ return -1;
+}
+
+CommandLineArgs& DownstreamArgs::getArgsByName(char* name)
+{
+ Index index = findName(name);
+ SLANG_ASSERT(index >= 0);
+ return m_args[index];
+}
+
+SlangResult DownstreamArgs::stripDownstreamArgs(CommandLineArgs& ioArgs, Flags flags, DiagnosticSink* sink)
+{
+ CommandLineReader reader(&ioArgs, sink);
+
+ while (reader.hasArg())
+ {
+ const CommandLineArg& arg = reader.peekArg();
+
+ if (arg.value.startsWith("-X"))
+ {
+ if (arg.value.endsWith("..."))
+ {
+ const UnownedStringSlice name = arg.value.getUnownedSlice().subString(2, arg.value.getLength() - 5);
+ const Index nameIndex = _findOrAddName(arg.loc, name, flags, sink);
+ if (nameIndex < 0)
+ {
+ return SLANG_FAIL;
+ }
+
+ Index depth = 1;
+ const Index startIndex = reader.getIndex();
+
+ Int index = startIndex + 1;
+ const Int count = ioArgs.m_args.getCount();
+
+ for (; index < count; ++index)
+ {
+ const auto& curArg = ioArgs.m_args[index];
+
+ if (curArg.value == "-X.")
+ {
+ depth--;
+ // If we are at end of scope we are done
+ if (depth <= 0)
+ {
+ break;
+ }
+ }
+ else if (curArg.value.startsWith("-X") && curArg.value.endsWith("..."))
+ {
+ depth++;
+ }
+ }
+
+ // We don't care if its 1, as we allow the main scope to be left open
+ if (depth > 1)
+ {
+ sink->diagnose(arg.loc, MiscDiagnostics::unbalancedDownstreamArguments);
+ return SLANG_FAIL;
+ }
+
+ // We are either at end of scope or at end of list
+ SLANG_ASSERT(depth <= 0 || index >= count);
+
+ // Add all of these args
+ CommandLineArgs& args = getArgsAt(nameIndex);
+
+ // Copy the values in the range
+ args.m_args.addRange(ioArgs.m_args.getBuffer() + startIndex + 1, index - (startIndex + 1));
+
+ // If we aren't at the end, we must be pointing to -X., so skip that
+ index += Index(index < count);
+ // Remove the range. The readers position, needs to be fixed though
+ ioArgs.m_args.removeRange(startIndex, index - startIndex);
+
+ // The reader should be at startIndex, and so doesn't need fixing
+ SLANG_ASSERT(reader.getIndex() == startIndex);
+ }
+ else if (arg.value == "-X.")
+ {
+ sink->diagnose(arg.loc, MiscDiagnostics::closeOfUnopenDownstreamArgs);
+ return SLANG_FAIL;
+ }
+ else
+ {
+ const Index startIndex = reader.getIndex();
+
+ // Extract the name
+ UnownedStringSlice name = arg.value.getUnownedSlice().tail(2);
+ const Index nameIndex = _findOrAddName(arg.loc, name, flags, sink);
+ if (nameIndex < 0)
+ {
+ return SLANG_FAIL;
+ }
+
+ reader.advance();
+
+ CommandLineArg nextArg;
+ SLANG_RETURN_ON_FAIL(reader.expectArg(nextArg));
+
+ getArgsAt(nameIndex).add(nextArg);
+
+ // Rewind to the start index
+ reader.setIndex(startIndex);
+ // Remove the args
+ ioArgs.m_args.removeRange(startIndex, 2);
+ }
+ }
+ else
+ {
+ // Advance and leave
+ reader.advance();
+ }
+ }
+
+ return SLANG_OK;
+}
} // namespace Slang