13
13
],
14
14
llvm/ llvm,
15
15
lllink,
16
- llplatform
16
+ llplatform,
17
+ ../ Nim / dist/ checksums/ src/ checksums/ md5
17
18
18
19
type
19
20
SectionKind = enum
@@ -762,6 +763,9 @@ proc constInt8(g: LLGen, v: int8): ValueRef =
762
763
proc constUInt8 (g: LLGen , v: uint8 ): ValueRef =
763
764
llvm.constInt (g.primitives[tyUInt8], v.culonglong , llvm.False )
764
765
766
+ proc constInt16 (g: LLGen , v: int16 ): ValueRef =
767
+ llvm.constInt (g.primitives[tyInt16], v.culonglong , llvm.False )
768
+
765
769
proc constInt32 (g: LLGen , v: int32 ): ValueRef =
766
770
llvm.constInt (g.primitives[tyInt32], v.culonglong , llvm.False )
767
771
@@ -3275,6 +3279,42 @@ proc genHook(g: LLGen, t: PType, op: TTypeAttachedOp): llvm.ValueRef =
3275
3279
else :
3276
3280
constNull (g.ptrTy)
3277
3281
3282
+ proc getObjDepth (t: PType ): int16 =
3283
+ var x = t
3284
+ result = - 1
3285
+ while x != nil :
3286
+ x = skipTypes (x, skipPtrs)
3287
+ x = x[0 ]
3288
+ inc (result )
3289
+
3290
+ proc genDisplayElem (d: MD5Digest ): uint32 =
3291
+ result = 0
3292
+ for i in 0 .. 3 :
3293
+ result += uint32 (d[i])
3294
+ result = result shl 8
3295
+
3296
+ proc genDisplay (g: LLGen , t: PType , depth: int ): llvm.ValueRef =
3297
+ var x = t
3298
+ var seqs = newSeq [llvm.ValueRef ](depth + 1 )
3299
+ var i = 0
3300
+ while x != nil :
3301
+ x = skipTypes (x, skipPtrs)
3302
+ seqs[seqs.len - i - 1 ] = llvm.constInt (
3303
+ g.primitives[tyUInt32],
3304
+ genDisplayElem (MD5Digest (hashType (x, g.config))).culonglong ,
3305
+ llvm.False ,
3306
+ )
3307
+ x = x[0 ]
3308
+ inc i
3309
+
3310
+ let
3311
+ ty = llvm.arrayType2 (g.primitives[tyUInt32], seqs.len.uint64 )
3312
+ display =
3313
+ g.m.addPrivateConstant (ty, g.nn (" .display." & g.llName (t, hashType (t, g.config))))
3314
+
3315
+ display.setInitializer (llvm.constArray (g.primitives[tyUInt32], seqs))
3316
+ display
3317
+
3278
3318
proc genTypeInfoV2 (g: LLGen , typ: PType ): llvm.ValueRef =
3279
3319
let
3280
3320
origType = typ
@@ -3306,11 +3346,22 @@ proc genTypeInfoV2(g: LLGen, typ: PType): llvm.ValueRef =
3306
3346
g.constNimInt (dl.aBISizeOfType (lt).int )
3307
3347
alignVar =
3308
3348
if lt == nil :
3309
- g.constNimInt (1 )
3349
+ g.constInt16 (1 )
3310
3350
else :
3311
- g.constNimInt (dl.preferredAlignmentOfType (lt).int )
3351
+ g.constInt16 (dl.preferredAlignmentOfType (lt).int16 )
3352
+ depth =
3353
+ if typ.kind == tyObject:
3354
+ getObjDepth (typ)
3355
+ else :
3356
+ - 1
3357
+ depthVar = g.constInt16 (depth)
3358
+ displayVar =
3359
+ if depth >= 0 :
3360
+ g.genDisplay (typ, depth)
3361
+ else :
3362
+ constNull (g.ptrTy)
3312
3363
nameVar =
3313
- if typ.kind in {tyObject, tyDistinct}:
3364
+ if isDefined (g.config, " nimTypeNames " ) and typ.kind in {tyObject, tyDistinct}:
3314
3365
if incompleteType (typ):
3315
3366
g.config.internalError (
3316
3367
" request for RTTI generation for incomplete object: " & typeToString (typ)
@@ -3326,8 +3377,17 @@ proc genTypeInfoV2(g: LLGen, typ: PType): llvm.ValueRef =
3326
3377
else :
3327
3378
constNull (g.ptrTy)
3328
3379
flagsVar = g.constNimInt (flags)
3329
-
3330
- values = [destroyImpl, sizeVar, alignVar, nameVar, traceImpl, v1Var, flagsVar]
3380
+ values =
3381
+ if isDefined (g.config, " nimTypeNames" ):
3382
+ @ [
3383
+ destroyImpl, sizeVar, alignVar, depthVar, displayVar, nameVar, traceImpl,
3384
+ v1Var, flagsVar,
3385
+ ]
3386
+ else :
3387
+ @ [
3388
+ destroyImpl, sizeVar, alignVar, depthVar, displayVar, traceImpl, v1Var,
3389
+ flagsVar,
3390
+ ]
3331
3391
3332
3392
result .setInitializer (llvm.constNamedStruct (nimTypeTy, values))
3333
3393
@@ -3943,13 +4003,20 @@ proc callIsObj(g: LLGen, v: llvm.ValueRef, typ: PType): llvm.ValueRef =
3943
4003
let
3944
4004
# Type resides at the start of the object
3945
4005
mtype = g.b.buildLoad2 (g.ptrTy, v)
3946
- cmpTo =
3947
- if optTinyRtti in g.config.globalOptions:
3948
- g.constCStringPtr (g.genTypeInfo2Name (typ))
3949
- else :
3950
- g.genTypeInfo (typ)
3951
4006
3952
- g.callCompilerProc (" isObj" , [mtype, cmpTo])
4007
+ if optTinyRtti in g.config.globalOptions:
4008
+ let
4009
+ cmpTo = g.constInt16 (getObjDepth (typ))
4010
+ elem = llvm.constInt (
4011
+ g.primitives[tyUInt32],
4012
+ genDisplayElem (MD5Digest (hashType (typ, g.config))).culonglong ,
4013
+ llvm.False ,
4014
+ )
4015
+
4016
+ g.callCompilerProc (" isObjDisplayCheck" , [mtype, cmpTo, elem])
4017
+ else :
4018
+ let cmpTo = g.genTypeInfo (typ)
4019
+ g.callCompilerProc (" isObj" , [mtype, cmpTo])
3953
4020
3954
4021
# These are taken from cgen and take care of some of the fallout from the
3955
4022
# beautiful copy-on-write string literal pessimisation :/
@@ -4974,6 +5041,17 @@ proc genFakeCall(g: LLGen, n: PNode, o: var LLValue, load: bool): bool =
4974
5041
ax.setOrdering (ord)
4975
5042
return true
4976
5043
5044
+ if s.name.s == " atomicExchangeN" :
5045
+ let
5046
+ p0 = g.genNode (n[1 ], true ).v
5047
+ p1 = g.genNode (n[2 ], true ).v
5048
+ ord = getOrdering (n[3 ])
5049
+
5050
+ o =
5051
+ LLValue (v: g.b.buildAtomicRMW (llvm.AtomicRMWBinOpXchg , p0, p1, ord, llvm.False ))
5052
+
5053
+ return true
5054
+
4977
5055
if s.name.s == " atomicAddFetch" :
4978
5056
let
4979
5057
p0 = g.genNode (n[1 ], true ).v
@@ -8740,7 +8818,7 @@ proc genNodeDot(g: LLGen, n: PNode, load: bool): LLValue =
8740
8818
p (" genDotExpr" , n[1 ].sym, g.depth + 1 )
8741
8819
let
8742
8820
v = g.genNode (n[0 ], false )
8743
- typ = skipTypes (n[0 ].typ, abstractInst + tyUserTypeClasses)
8821
+ typ = skipTypes (n[0 ].typ, abstractInstOwned + tyUserTypeClasses)
8744
8822
gep =
8745
8823
LLValue (v: g.toGEP (v.v, g.fieldIndex (typ, n[1 ].sym), " dot" ), storage: v.storage)
8746
8824
@@ -8750,7 +8828,7 @@ proc genNodeCheckedField(g: LLGen, n: PNode, load: bool): LLValue =
8750
8828
if optFieldCheck in g.config.options:
8751
8829
let
8752
8830
v = g.genNode (n[0 ][0 ], false )
8753
- typ = skipTypes (n[0 ][0 ].typ, abstractInst + tyUserTypeClasses)
8831
+ typ = skipTypes (n[0 ][0 ].typ, abstractInstOwned + tyUserTypeClasses)
8754
8832
8755
8833
gep = LLValue (
8756
8834
v: g.toGEP (v.v, g.fieldIndex (typ, n[0 ][1 ].sym), " dot" ), storage: v.storage
0 commit comments