diff --git a/compiler/docgen.nim b/compiler/docgen.nim index d774fd50891e7..005bbbe92a957 100644 --- a/compiler/docgen.nim +++ b/compiler/docgen.nim @@ -216,13 +216,21 @@ proc newDocumentor*(filename: AbsoluteFile; cache: IdentCache; conf: ConfigRef, # Include the current file if we're parsing a nim file let importStmt = if d.isPureRst: "" else: "import \"$1\"\n" % [d.filename.replace("\\", "/")] writeFile(outp, importStmt & content) - let c = if cmd.startsWith("nim "): os.getAppFilename() & " " & $conf.backend & cmd.substr("nim ".len) - elif cmd.startsWith("nim "): os.getAppFilename() & cmd.substr("nim".len) - else: cmd - let c2 = c % quoteShell(outp) - rawMessage(conf, hintExecuting, c2) - if execShellCmd(c2) != status: - rawMessage(conf, errGenerated, "executing of external program failed: " & c2) + + proc interpSnippetCmd(cmd: string): string = + result = cmd + # backward compatibility hacks; interpolation commands should explicitly use `$` + result = result.replace("nim ", "$nim") + result = result.replace("$1", "$options") + result = result % [ + "nim", os.getAppFilename().quoteShell, + "backend", $d.conf.backend, + "options", outp.quoteShell, + ] + let cmd = cmd.interpSnippetCmd + rawMessage(conf, hintExecuting, cmd) + if execShellCmd(cmd) != status: + rawMessage(conf, errGenerated, "executing of external program failed: " & cmd) result.emitted = initIntSet() result.destFile = getOutFile2(conf, presentationPath(conf, filename), outExt, htmldocsDir, false) diff --git a/compiler/main.nim b/compiler/main.nim index 4fc92b06a2c6a..8e6e2c7e3804e 100644 --- a/compiler/main.nim +++ b/compiler/main.nim @@ -196,11 +196,10 @@ proc mainCommand*(graph: ModuleGraph) = when false: setOutDir(conf) if optUseNimcache in conf.globalOptions: setOutDir(conf) - proc customizeForBackend(backend2: TBackend) = + proc customizeForBackend() = ## sets backend specific options but don't compile to backend yet - conf.backend = backend2 - defineSymbol(graph.config.symbols, $backend2) - case backend2 + defineSymbol(graph.config.symbols, $conf.backend) + case conf.backend of backendC: if conf.exc == excNone: conf.exc = excSetjmp of backendCpp: @@ -221,8 +220,11 @@ proc mainCommand*(graph: ModuleGraph) = proc compileToBackend(backend: TBackend = conf.backend, cmd = cmdCompileToBackend) = commandAlreadyProcessed = true - customizeForBackend(backend) conf.cmd = cmd + if conf.backend == backendInvalid: + # only set backend if wasn't already set, to allow override via `nim c -b:cpp` + conf.backend = backend + customizeForBackend() case conf.backend of backendC: commandCompileToC(graph) of backendCpp: commandCompileToC(graph) @@ -238,7 +240,7 @@ proc mainCommand*(graph: ModuleGraph) = of "js", "compiletojs": compileToBackend(backendJs) else: # this ensures all other commands call this - customizeForBackend(conf.backend) + customizeForBackend() ## process all other commands case conf.command.normalize diff --git a/compiler/options.nim b/compiler/options.nim index 3e6c7989fee27..3ff1a7a22f5bb 100644 --- a/compiler/options.nim +++ b/compiler/options.nim @@ -419,7 +419,7 @@ proc newConfigRef*(): ConfigRef = cIncludes: @[], # directories to search for included files cLibs: @[], # directories to search for lib files cLinkedLibs: @[], # libraries to link - backend: backendC, + backend: backendInvalid, externalToLink: @[], linkOptionsCmd: "", compileOptionsCmd: @[], diff --git a/lib/packages/docutils/rstgen.nim b/lib/packages/docutils/rstgen.nim index edd987a76ca00..816d724ef0393 100644 --- a/lib/packages/docutils/rstgen.nim +++ b/lib/packages/docutils/rstgen.nim @@ -865,7 +865,7 @@ proc parseCodeBlockField(d: PDoc, n: PRstNode, params: var CodeBlockParams) = of "test": params.testCmd = n.getFieldValue.strip if params.testCmd.len == 0: - params.testCmd = "nim -r $1" # The nim backend is auto-set in docgen.nim + params.testCmd = "$nim r --backend:$backend $options" # see `interpSnippetCmd` else: params.testCmd = unescape(params.testCmd) of "status", "exitcode": diff --git a/tests/misc/mimportcpp.nim b/tests/misc/mbackend.nim similarity index 55% rename from tests/misc/mimportcpp.nim rename to tests/misc/mbackend.nim index 842c89857bbd7..e38eb2d3e8a9e 100644 --- a/tests/misc/mimportcpp.nim +++ b/tests/misc/mbackend.nim @@ -3,11 +3,18 @@ We can't merge this test inside a `when defined(cpp)` because some bug that was fixed would not trigger in that case. ]# -## bugfix 1: this used to CT error with: Error: unhandled exception: mimportcpp.nim(6, 18) `defined(cpp)` -static: doAssert defined(cpp) +import std/compilesettings +import std/unittest -## checks that `--backend:c` has no side effect (ie, can be overridden by subsequent commands) -static: doAssert not defined(c) +static: + ## bugfix 1: this used to CT error with: Error: unhandled exception: mimportcpp.nim(6, 18) `defined(cpp)` + doAssert defined(cpp) + doAssert querySetting(backend) == "cpp" + + ## checks that `--backend:c` has no side effect (ie, can be overridden by subsequent commands) + doAssert not defined(c) + doAssert not defined(js) + doAssert not defined(js) type std_exception {.importcpp: "std::exception", header: "".} = object diff --git a/tests/trunner.nim b/tests/trunner.nim index a32ba3633c179..e89606bf7f1b5 100644 --- a/tests/trunner.nim +++ b/tests/trunner.nim @@ -123,15 +123,18 @@ else: # don't run twice the same test let cmd = fmt"{nim} r --backend:{mode} --hints:off --nimcache:{nimcache} {file}" check execCmdEx(cmd) == ("ok3\n", 0) - block: # some importc tests - # issue #14314 - let file = testsDir / "misc/mimportc.nim" - let cmd = fmt"{nim} r -b:cpp --hints:off --nimcache:{nimcache} --warningAsError:ProveInit {file}" - check execCmdEx(cmd) == ("witness\n", 0) - block: # further issues with `--backend` - let file = testsDir / "misc/mimportcpp.nim" + let file = testsDir / "misc/mbackend.nim" var cmd = fmt"{nim} doc -b:cpp --hints:off --nimcache:{nimcache} {file}" check execCmdEx(cmd) == ("", 0) cmd = fmt"{nim} check -b:c -b:cpp --hints:off --nimcache:{nimcache} {file}" check execCmdEx(cmd) == ("", 0) + # issue https://github.com/timotheecour/Nim/issues/175 + cmd = fmt"{nim} c -b:js -b:cpp --hints:off --nimcache:{nimcache} {file}" + check execCmdEx(cmd) == ("", 0) + + block: # some importc tests + # issue #14314 + let file = testsDir / "misc/mimportc.nim" + let cmd = fmt"{nim} r -b:cpp --hints:off --nimcache:{nimcache} --warningAsError:ProveInit {file}" + check execCmdEx(cmd) == ("witness\n", 0)