summary refs log tree commit diff stats
diff options
context:
space:
mode:
authorAndreas Rumpf <rumpf_a@web.de>2021-12-10 14:28:59 +0100
committerGitHub <noreply@github.com>2021-12-10 14:28:59 +0100
commit7ff43d07b2b983271d666b1c654b1426cbbbf236 (patch)
tree2336e45e1dab2f80e311cbdcc016f02b68117e88
parent9338aa24977e84a33b9a7802eaff0777fcf4d9c3 (diff)
downloadNim-7ff43d07b2b983271d666b1c654b1426cbbbf236.tar.gz
added --nimMainPrefix switch; fixes #15955; refs #16945 [backport:1.6] (#19235)
-rw-r--r--changelog.md2
-rw-r--r--compiler/cgen.nim37
-rw-r--r--compiler/commands.nim1
-rw-r--r--compiler/options.nim1
-rw-r--r--doc/advopt.txt2
-rw-r--r--doc/backends.rst3
-rw-r--r--doc/nimc.rst7
7 files changed, 36 insertions, 17 deletions
diff --git a/changelog.md b/changelog.md
index ebad54fe4..df8051a16 100644
--- a/changelog.md
+++ b/changelog.md
@@ -71,3 +71,5 @@
 - The `gc` switch has been renamed to `mm` ("memory management") in order to reflect the
   reality better. (Nim moved away from all techniques based on "tracing".)
 
+- There is a new switch `--nimMainPrefix:prefix` to influence the `NimMain` that the
+  compiler produces. This is particularly useful for generating static libraries.
diff --git a/compiler/cgen.nim b/compiler/cgen.nim
index c862d4d30..032c22ec0 100644
--- a/compiler/cgen.nim
+++ b/compiler/cgen.nim
@@ -154,6 +154,11 @@ macro ropecg(m: BModule, frmt: static[FormatStr], args: untyped): Rope =
         inc(i)
         result.add newCall(formatValue, resVar, args[num])
         inc(num)
+      of '^':
+        flushStrLit()
+        inc(i)
+        result.add newCall(formatValue, resVar, args[^1])
+        inc(num)
       of '0'..'9':
         var j = 0
         while true:
@@ -1366,7 +1371,7 @@ proc genMainProc(m: BModule) =
       "}$N$N"
 
     MainProcs =
-      "\tNimMain();$N"
+      "\t$^NimMain();$N"
 
     MainProcsWithResult =
       MainProcs & ("\treturn $1nim_program_result;$N")
@@ -1376,7 +1381,7 @@ proc genMainProc(m: BModule) =
       "}$N$N"
 
     NimMainProc =
-      "N_CDECL(void, NimMain)(void) {$N" &
+      "N_CDECL(void, $5NimMain)(void) {$N" &
         "\tvoid (*volatile inner)(void);$N" &
         "$4" &
         "\tinner = NimMainInner;$N" &
@@ -1456,28 +1461,27 @@ proc genMainProc(m: BModule) =
     if optGenGuiApp in m.config.globalOptions:
       const nimMain = WinNimMain
       appcg(m, m.s[cfsProcs], nimMain,
-        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode])
+        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode, m.config.nimMainPrefix])
     else:
       const nimMain = WinNimDllMain
       appcg(m, m.s[cfsProcs], nimMain,
-        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode])
+        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode, m.config.nimMainPrefix])
   elif m.config.target.targetOS == osGenode:
     const nimMain = GenodeNimMain
     appcg(m, m.s[cfsProcs], nimMain,
-        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode])
+        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode, m.config.nimMainPrefix])
   elif optGenDynLib in m.config.globalOptions:
     const nimMain = PosixNimDllMain
     appcg(m, m.s[cfsProcs], nimMain,
-        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode])
+        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode, m.config.nimMainPrefix])
   elif m.config.target.targetOS == osStandalone:
     const nimMain = NimMainBody
     appcg(m, m.s[cfsProcs], nimMain,
-        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode])
+        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode, m.config.nimMainPrefix])
   else:
     const nimMain = NimMainBody
     appcg(m, m.s[cfsProcs], nimMain,
-        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode])
-
+        [m.g.mainModInit, initStackBottomCall, m.labels, preMainCode, m.config.nimMainPrefix])
 
   if optNoMain notin m.config.globalOptions:
     if m.config.cppCustomNamespace.len > 0:
@@ -1487,23 +1491,22 @@ proc genMainProc(m: BModule) =
         m.config.globalOptions * {optGenGuiApp, optGenDynLib} != {}:
       if optGenGuiApp in m.config.globalOptions:
         const otherMain = WinCMain
-        appcg(m, m.s[cfsProcs], otherMain, [if m.hcrOn: "*" else: ""])
+        appcg(m, m.s[cfsProcs], otherMain, [if m.hcrOn: "*" else: "", m.config.nimMainPrefix])
       else:
         const otherMain = WinCDllMain
-        appcg(m, m.s[cfsProcs], otherMain, [])
+        appcg(m, m.s[cfsProcs], otherMain, [m.config.nimMainPrefix])
     elif m.config.target.targetOS == osGenode:
       const otherMain = ComponentConstruct
-      appcg(m, m.s[cfsProcs], otherMain, [])
+      appcg(m, m.s[cfsProcs], otherMain, [m.config.nimMainPrefix])
     elif optGenDynLib in m.config.globalOptions:
       const otherMain = PosixCDllMain
-      appcg(m, m.s[cfsProcs], otherMain, [])
+      appcg(m, m.s[cfsProcs], otherMain, [m.config.nimMainPrefix])
     elif m.config.target.targetOS == osStandalone:
       const otherMain = StandaloneCMain
-      appcg(m, m.s[cfsProcs], otherMain, [])
+      appcg(m, m.s[cfsProcs], otherMain, [m.config.nimMainPrefix])
     else:
       const otherMain = PosixCMain
-      appcg(m, m.s[cfsProcs], otherMain, [if m.hcrOn: "*" else: ""])
-
+      appcg(m, m.s[cfsProcs], otherMain, [if m.hcrOn: "*" else: "", m.config.nimMainPrefix])
 
     if m.config.cppCustomNamespace.len > 0:
       m.s[cfsProcs].add openNamespaceNim(m.config.cppCustomNamespace)
@@ -1885,7 +1888,7 @@ proc writeHeader(m: BModule) =
 
   if optGenDynLib in m.config.globalOptions:
     result.add("N_LIB_IMPORT ")
-  result.addf("N_CDECL(void, NimMain)(void);$n", [])
+  result.addf("N_CDECL(void, $1NimMain)(void);$n", [rope m.config.nimMainPrefix])
   if m.config.cppCustomNamespace.len > 0: result.add closeNamespaceNim()
   result.addf("#endif /* $1 */$n", [guard])
   if not writeRope(result, m.filename):
diff --git a/compiler/commands.nim b/compiler/commands.nim
index d5c5f24e4..c4df46bc2 100644
--- a/compiler/commands.nim
+++ b/compiler/commands.nim
@@ -1052,6 +1052,7 @@ proc processSwitch*(switch, arg: string, pass: TCmdLinePass, info: TLineInfo;
   of "": # comes from "-" in for example: `nim c -r -` (gets stripped from -)
     handleStdinInput(conf)
   of "nilseqs", "nilchecks", "mainmodule", "m", "symbol", "taintmode", "cs", "deadcodeelim": warningOptionNoop(switch)
+  of "nimmainprefix": conf.nimMainPrefix = arg
   else:
     if strutils.find(switch, '.') >= 0: options.setConfigVar(conf, switch, arg)
     else: invalidCmdLineOption(conf, pass, switch, info)
diff --git a/compiler/options.nim b/compiler/options.nim
index 383b6fa2a..9e957332f 100644
--- a/compiler/options.nim
+++ b/compiler/options.nim
@@ -390,6 +390,7 @@ type
     structuredErrorHook*: proc (config: ConfigRef; info: TLineInfo; msg: string;
                                 severity: Severity) {.closure, gcsafe.}
     cppCustomNamespace*: string
+    nimMainPrefix*: string
     vmProfileData*: ProfileData
 
 proc parseNimVersion*(a: string): NimVer =
diff --git a/doc/advopt.txt b/doc/advopt.txt
index 79e784fde..e27c75ada 100644
--- a/doc/advopt.txt
+++ b/doc/advopt.txt
@@ -135,6 +135,8 @@ Advanced options:
   --cppCompileToNamespace:namespace
                             use the provided namespace for the generated C++ code,
                             if no namespace is provided "Nim" will be used
+  --nimMainPrefix:prefix    use `{prefix}NimMain` instead of `NimMain` in the produced
+                            C/C++ code
   --expandMacro:MACRO       dump every generated AST from MACRO
   --expandArc:PROCNAME      show how PROCNAME looks like after diverse optimizations
                             before the final backend phase (mostly ARC/ORC specific)
diff --git a/doc/backends.rst b/doc/backends.rst
index 3a3359fca..65dd8a6f2 100644
--- a/doc/backends.rst
+++ b/doc/backends.rst
@@ -246,6 +246,9 @@ Also, C code requires you to specify a forward declaration for functions or
 the compiler will assume certain types for the return value and parameters
 which will likely make your program crash at runtime.
 
+The name `NimMain` can be influenced via the `--nimMainPrefix:prefix` switch.
+Use `--nimMainPrefix:MyLib` and the function to call is named `MyLibNimMain`.
+
 
 Nim invocation example from C
 ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
diff --git a/doc/nimc.rst b/doc/nimc.rst
index 0ab1501ff..6b4f3c9a1 100644
--- a/doc/nimc.rst
+++ b/doc/nimc.rst
@@ -385,6 +385,10 @@ of your program.
     NimMain() # initialize garbage collector memory, types and stack
 
 
+The name `NimMain` can be influenced via the `--nimMainPrefix:prefix` switch.
+Use `--nimMainPrefix:MyLib` and the function to call is named `MyLibNimMain`.
+
+
 Cross-compilation for iOS
 =========================
 
@@ -413,6 +417,9 @@ of your program.
 Note: XCode's "make clean" gets confused about the generated nim.c files,
 so you need to clean those files manually to do a clean build.
 
+The name `NimMain` can be influenced via the `--nimMainPrefix:prefix` switch.
+Use `--nimMainPrefix:MyLib` and the function to call is named `MyLibNimMain`.
+
 
 Cross-compilation for Nintendo Switch
 =====================================