diff options
author | ringabout <43030857+ringabout@users.noreply.github.com> | 2023-11-30 21:05:45 +0800 |
---|---|---|
committer | GitHub <noreply@github.com> | 2023-11-30 14:05:45 +0100 |
commit | b5f5b74fc8308593f04e3bc11f7c5ead24b73eb5 (patch) | |
tree | e373a39deab03649a8fbc4bed9a9c0582f48ba64 /compiler | |
parent | 9140f8e2212c91347704cec0f98c0345ddf0ea1e (diff) | |
download | Nim-b5f5b74fc8308593f04e3bc11f7c5ead24b73eb5.tar.gz |
enable vtable implementation for C++ and make it an experimental feature (#23004)
follow up https://github.com/nim-lang/Nim/pull/22991 - [x] turning it into an experimental feature --------- Co-authored-by: Andreas Rumpf <rumpf_a@web.de>
Diffstat (limited to 'compiler')
-rw-r--r-- | compiler/ccgtypes.nim | 22 | ||||
-rw-r--r-- | compiler/cgen.nim | 3 | ||||
-rw-r--r-- | compiler/cgmeth.nim | 2 | ||||
-rw-r--r-- | compiler/condsyms.nim | 2 | ||||
-rw-r--r-- | compiler/nim.cfg | 5 | ||||
-rw-r--r-- | compiler/options.nim | 3 | ||||
-rw-r--r-- | compiler/sem.nim | 4 |
7 files changed, 26 insertions, 15 deletions
diff --git a/compiler/ccgtypes.nim b/compiler/ccgtypes.nim index 2f304852b..462b08a43 100644 --- a/compiler/ccgtypes.nim +++ b/compiler/ccgtypes.nim @@ -1678,6 +1678,13 @@ proc genDisplay(m: BModule; t: PType, depth: int): Rope = result.add seqs[0] result.add "}" +proc genVTable(seqs: seq[PSym]): string = + result = "{" + for i in 0..<seqs.len: + if i > 0: result.add ", " + result.add "(void *) " & seqs[i].loc.r + result.add "}" + proc genTypeInfoV2OldImpl(m: BModule; t, origType: PType, name: Rope; info: TLineInfo) = cgsym(m, "TNimTypeV2") m.s[cfsStrData].addf("N_LIB_PRIVATE TNimTypeV2 $1;$n", [name]) @@ -1714,18 +1721,19 @@ proc genTypeInfoV2OldImpl(m: BModule; t, origType: PType, name: Rope; info: TLin m.s[cfsVars].addf("static $1 $2[$3] = $4;$n", [getTypeDesc(m, getSysType(m.g.graph, unknownLineInfo, tyUInt32), dkVar), objDisplayStore, rope(objDepth+1), objDisplay]) addf(typeEntry, "$1.display = $2;$n", [name, rope(objDisplayStore)]) + let dispatchMethods = toSeq(getMethodsPerType(m.g.graph, t)) + if dispatchMethods.len > 0: + let vTablePointerName = getTempName(m) + m.s[cfsVars].addf("static void* $1[$2] = $3;$n", [vTablePointerName, rope(dispatchMethods.len), genVTable(dispatchMethods)]) + for i in dispatchMethods: + genProcPrototype(m, i) + addf(typeEntry, "$1.vTable = $2;$n", [name, vTablePointerName]) + m.s[cfsTypeInit3].add typeEntry if t.kind == tyObject and t.len > 0 and t[0] != nil and optEnableDeepCopy in m.config.globalOptions: discard genTypeInfoV1(m, t, info) -proc genVTable(seqs: seq[PSym]): string = - result = "{" - for i in 0..<seqs.len: - if i > 0: result.add ", " - result.add "(void *) " & seqs[i].loc.r - result.add "}" - proc genTypeInfoV2Impl(m: BModule; t, origType: PType, name: Rope; info: TLineInfo) = cgsym(m, "TNimTypeV2") m.s[cfsStrData].addf("N_LIB_PRIVATE TNimTypeV2 $1;$n", [name]) diff --git a/compiler/cgen.nim b/compiler/cgen.nim index 5a331ae7c..d22a6bdc2 100644 --- a/compiler/cgen.nim +++ b/compiler/cgen.nim @@ -2234,8 +2234,7 @@ proc finalCodegenActions*(graph: ModuleGraph; m: BModule; n: PNode) = incl m.flags, objHasKidsValid if optMultiMethods in m.g.config.globalOptions or m.g.config.selectedGC notin {gcArc, gcOrc, gcAtomicArc} or - not m.g.config.isDefined("nimPreviewVtables") or - m.g.config.backend == backendCpp or sfCompileToCpp in m.module.flags: + vtables notin m.g.config.features: generateIfMethodDispatchers(graph, m.idgen) diff --git a/compiler/cgmeth.nim b/compiler/cgmeth.nim index 3bbe7b3f4..833bb6fe5 100644 --- a/compiler/cgmeth.nim +++ b/compiler/cgmeth.nim @@ -157,7 +157,7 @@ proc fixupDispatcher(meth, disp: PSym; conf: ConfigRef) = proc methodDef*(g: ModuleGraph; idgen: IdGenerator; s: PSym) = var witness: PSym = nil - if s.typ[1].owner.getModule != s.getModule and g.config.isDefined("nimPreviewVtables"): + if s.typ[1].owner.getModule != s.getModule and vtables in g.config.features and not g.config.isDefined("nimInternalNonVtablesTesting"): localError(g.config, s.info, errGenerated, "method `" & s.name.s & "` can be defined only in the same module with its type (" & s.typ[1].typeToString() & ")") for i in 0..<g.methods.len: diff --git a/compiler/condsyms.nim b/compiler/condsyms.nim index aa619c932..5865e5310 100644 --- a/compiler/condsyms.nim +++ b/compiler/condsyms.nim @@ -163,3 +163,5 @@ proc initDefines*(symbols: StringTableRef) = defineSymbol("nimHasCastExtendedVm") defineSymbol("nimHasWarnStdPrefix") + + defineSymbol("nimHasVtables") diff --git a/compiler/nim.cfg b/compiler/nim.cfg index 43da7e3e0..ce5a22ad2 100644 --- a/compiler/nim.cfg +++ b/compiler/nim.cfg @@ -9,7 +9,6 @@ define:nimPreviewSlimSystem define:nimPreviewCstringConversion define:nimPreviewProcConversion define:nimPreviewRangeDefault -define:nimPreviewVtables define:nimPreviewNonVarDestructor threads:off @@ -58,3 +57,7 @@ define:useStdoutAsStdmsg warning[StdPrefix]:on warningAsError[StdPrefix]:on @end + +@if nimHasVtables: + experimental:vtables +@end diff --git a/compiler/options.nim b/compiler/options.nim index 3731304c7..9282247c3 100644 --- a/compiler/options.nim +++ b/compiler/options.nim @@ -226,7 +226,8 @@ type flexibleOptionalParams, strictDefs, strictCaseObjects, - inferGenericTypes + inferGenericTypes, + vtables LegacyFeature* = enum allowSemcheckedAstModification, diff --git a/compiler/sem.nim b/compiler/sem.nim index 2bdb1284f..03e599753 100644 --- a/compiler/sem.nim +++ b/compiler/sem.nim @@ -861,9 +861,7 @@ proc semStmtAndGenerateGenerics(c: PContext, n: PNode): PNode = trackStmt(c, c.module, result, isTopLevel = true) if optMultiMethods notin c.config.globalOptions and c.config.selectedGC in {gcArc, gcOrc, gcAtomicArc} and - c.config.isDefined("nimPreviewVtables") and - c.config.backend != backendCpp and - sfCompileToCpp notin c.module.flags: + Feature.vtables in c.config.features: sortVTableDispatchers(c.graph) if sfMainModule in c.module.flags: |