Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 18 additions & 0 deletions compiler/ccgtypes.nim
Original file line number Diff line number Diff line change
Expand Up @@ -2112,3 +2112,21 @@ proc genTypeSection(m: BModule, n: PNode) =
discard getTypeDescAux(m, s.typ, intSet, descKindFromSymKind(s.kind))
if m.g.generatedHeader != nil:
discard getTypeDescAux(m.g.generatedHeader, s.typ, intSet, descKindFromSymKind(s.kind))

# Unlike genCppInitializer which returns just the braced value list (e.g. "{a, b}"),
# genCppConstructorExpr returns a full type-prefixed expression (e.g. "Foo(a, b)").
# This is used when a standalone construction expression is needed — e.g. on the
# right-hand side of an assignment — whereas genCppInitializer is used in variable
# declarations where the type is already written separately before the initializer.
proc genCppConstructorExpr(m: BModule, prc: BProc; typ: PType; didGenTemp: var bool): Snippet =
var params = ""
if typ.itemId in m.g.graph.initializersPerType:
let call = m.g.graph.initializersPerType[typ.itemId]
if call != nil:
var p = prc
if p == nil:
p = BProc(module: m)
params = genCppParamsForCtor(p, call, didGenTemp)
if prc == nil:
assert p.blocks.len == 0, "BProc belongs to a struct doesnt have blocks"
result = getTypeDesc(m, typ, dkVar) & "(" & params & ")"
2 changes: 1 addition & 1 deletion compiler/cgen.nim
Original file line number Diff line number Diff line change
Expand Up @@ -526,7 +526,7 @@ proc resetLoc(p: BProc, loc: var TLoc) =
if isImportedCppType(typ):
var didGenTemp = false
let rl = rdLoc(loc)
let init = genCppInitializer(p.module, p, typ, didGenTemp)
let init = genCppConstructorExpr(p.module, p, typ, didGenTemp)
p.s(cpsStmts).addAssignment(rl, init)
return
if optSeqDestructors in p.config.globalOptions and typ.kind in {tyString, tySequence}:
Expand Down
30 changes: 30 additions & 0 deletions tests/cpp/tcpp_default_ctor_assignment.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
#ifndef TCPP_DEFAULT_CTOR_ASSIGNMENT_H
#define TCPP_DEFAULT_CTOR_ASSIGNMENT_H

struct AmbiguousAssign {
int x;
const char* y;

AmbiguousAssign(): x(0), y(nullptr) {}
AmbiguousAssign(int x, const char* y): x(x), y(y) {}

AmbiguousAssign& operator=(int v) {
x = v;
y = nullptr;
return *this;
}

AmbiguousAssign& operator=(const char* s) {
x = 0;
y = s;
return *this;
}

AmbiguousAssign& operator=(const AmbiguousAssign& other) {
x = other.x;
y = other.y;
return *this;
}
};

#endif
14 changes: 14 additions & 0 deletions tests/cpp/tcpp_default_ctor_assignment.nim
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
discard """
cmd: "nim cpp $file"
"""

type
AmbiguousAssign {.importcpp, header: "tcpp_default_ctor_assignment.h".} = object
x: cint
y: cstring

proc main =
var xs = newSeq[AmbiguousAssign](3)
doAssert xs.len == 3

main()
Loading