semtypes.nim 97 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626162716281629163016311632163316341635163616371638163916401641164216431644164516461647164816491650165116521653165416551656165716581659166016611662166316641665166616671668166916701671167216731674167516761677167816791680168116821683168416851686168716881689169016911692169316941695169616971698169917001701170217031704170517061707170817091710171117121713171417151716171717181719172017211722172317241725172617271728172917301731173217331734173517361737173817391740174117421743174417451746174717481749175017511752175317541755175617571758175917601761176217631764176517661767176817691770177117721773177417751776177717781779178017811782178317841785178617871788178917901791179217931794179517961797179817991800180118021803180418051806180718081809181018111812181318141815181618171818181918201821182218231824182518261827182818291830183118321833183418351836183718381839184018411842184318441845184618471848184918501851185218531854185518561857185818591860186118621863186418651866186718681869187018711872187318741875187618771878187918801881188218831884188518861887188818891890189118921893189418951896189718981899190019011902190319041905190619071908190919101911191219131914191519161917191819191920192119221923192419251926192719281929193019311932193319341935193619371938193919401941194219431944194519461947194819491950195119521953195419551956195719581959196019611962196319641965196619671968196919701971197219731974197519761977197819791980198119821983198419851986198719881989199019911992199319941995199619971998199920002001200220032004200520062007200820092010201120122013201420152016201720182019202020212022202320242025202620272028202920302031203220332034203520362037203820392040204120422043204420452046204720482049205020512052205320542055205620572058205920602061206220632064206520662067206820692070207120722073207420752076207720782079208020812082208320842085208620872088208920902091209220932094209520962097209820992100210121022103210421052106210721082109211021112112211321142115211621172118211921202121212221232124212521262127212821292130213121322133213421352136213721382139214021412142214321442145214621472148214921502151215221532154215521562157215821592160216121622163216421652166216721682169217021712172217321742175217621772178217921802181218221832184218521862187218821892190219121922193219421952196219721982199220022012202220322042205220622072208220922102211221222132214221522162217221822192220222122222223222422252226222722282229223022312232223322342235223622372238223922402241224222432244224522462247224822492250225122522253225422552256225722582259226022612262226322642265226622672268226922702271227222732274227522762277227822792280228122822283228422852286228722882289229022912292229322942295229622972298229923002301230223032304230523062307230823092310231123122313231423152316231723182319232023212322232323242325232623272328232923302331233223332334233523362337233823392340234123422343234423452346234723482349235023512352235323542355235623572358235923602361236223632364236523662367236823692370237123722373237423752376237723782379238023812382238323842385238623872388238923902391239223932394239523962397239823992400240124022403240424052406240724082409241024112412241324142415241624172418241924202421242224232424242524262427242824292430243124322433243424352436243724382439244024412442244324442445244624472448244924502451245224532454245524562457245824592460246124622463246424652466246724682469247024712472247324742475247624772478247924802481248224832484248524862487248824892490249124922493249424952496249724982499
  1. #
  2. #
  3. # The Nim Compiler
  4. # (c) Copyright 2012 Andreas Rumpf
  5. #
  6. # See the file "copying.txt", included in this
  7. # distribution, for details about the copyright.
  8. #
  9. # this module does the semantic checking of type declarations
  10. # included from sem.nim
  11. const
  12. errStringOrIdentNodeExpected = "string or ident node expected"
  13. errStringLiteralExpected = "string literal expected"
  14. errIntLiteralExpected = "integer literal expected"
  15. errWrongNumberOfVariables = "wrong number of variables"
  16. errDuplicateAliasInEnumX = "duplicate value in enum '$1'"
  17. errOverflowInEnumX = "The enum '$1' exceeds its maximum value ($2)"
  18. errOrdinalTypeExpected = "ordinal type expected; given: $1"
  19. errSetTooBig = "set is too large; use `std/sets` for ordinal types with more than 2^16 elements"
  20. errBaseTypeMustBeOrdinal = "base type of a set must be an ordinal"
  21. errInheritanceOnlyWithNonFinalObjects = "inheritance only works with non-final objects"
  22. errXExpectsOneTypeParam = "'$1' expects one type parameter"
  23. errArrayExpectsTwoTypeParams = "array expects two type parameters"
  24. errInvalidVisibilityX = "invalid visibility: '$1'"
  25. errXCannotBeAssignedTo = "'$1' cannot be assigned to"
  26. errIteratorNotAllowed = "iterators can only be defined at the module's top level"
  27. errXNeedsReturnType = "$1 needs a return type"
  28. errNoReturnTypeDeclared = "no return type declared"
  29. errTIsNotAConcreteType = "'$1' is not a concrete type"
  30. errTypeExpected = "type expected"
  31. errXOnlyAtModuleScope = "'$1' is only allowed at top level"
  32. errDuplicateCaseLabel = "duplicate case label"
  33. errMacroBodyDependsOnGenericTypes = "the macro body cannot be compiled, " &
  34. "because the parameter '$1' has a generic type"
  35. errIllegalRecursionInTypeX = "illegal recursion in type '$1'"
  36. errNoGenericParamsAllowedForX = "no generic parameters allowed for $1"
  37. errInOutFlagNotExtern = "the '$1' modifier can be used only with imported types"
  38. proc newOrPrevType(kind: TTypeKind, prev: PType, c: PContext, son: sink PType): PType =
  39. if prev == nil or prev.kind == tyGenericBody:
  40. result = newTypeS(kind, c, son)
  41. else:
  42. result = prev
  43. result.setSon(son)
  44. if result.kind == tyForward: result.kind = kind
  45. #if kind == tyError: result.flags.incl tfCheckedForDestructor
  46. proc newOrPrevType(kind: TTypeKind, prev: PType, c: PContext): PType =
  47. if prev == nil or prev.kind == tyGenericBody:
  48. result = newTypeS(kind, c)
  49. else:
  50. result = prev
  51. if result.kind == tyForward: result.kind = kind
  52. proc newConstraint(c: PContext, k: TTypeKind): PType =
  53. result = newTypeS(tyBuiltInTypeClass, c)
  54. result.flags.incl tfCheckedForDestructor
  55. result.addSonSkipIntLit(newTypeS(k, c), c.idgen)
  56. proc semEnum(c: PContext, n: PNode, prev: PType): PType =
  57. if n.len == 0: return newConstraint(c, tyEnum)
  58. elif n.len == 1:
  59. # don't create an empty tyEnum; fixes #3052
  60. return errorType(c)
  61. var
  62. counter, x: BiggestInt = 0
  63. e: PSym = nil
  64. base: PType = nil
  65. identToReplace: ptr PNode = nil
  66. counterSet = initPackedSet[BiggestInt]()
  67. counter = 0
  68. base = nil
  69. result = newOrPrevType(tyEnum, prev, c)
  70. result.n = newNodeI(nkEnumTy, n.info)
  71. checkMinSonsLen(n, 1, c.config)
  72. if n[0].kind != nkEmpty:
  73. base = semTypeNode(c, n[0][0], nil)
  74. if base.kind != tyEnum:
  75. localError(c.config, n[0].info, "inheritance only works with an enum")
  76. counter = toInt64(lastOrd(c.config, base)) + 1
  77. rawAddSon(result, base)
  78. let isPure = result.sym != nil and sfPure in result.sym.flags
  79. var symbols: TStrTable = initStrTable()
  80. var hasNull = false
  81. var needsReorder = false
  82. for i in 1..<n.len:
  83. if n[i].kind == nkEmpty: continue
  84. var useAutoCounter = false
  85. case n[i].kind
  86. of nkEnumFieldDef:
  87. if n[i][0].kind == nkPragmaExpr:
  88. e = newSymS(skEnumField, n[i][0][0], c)
  89. identToReplace = addr n[i][0][0]
  90. pragma(c, e, n[i][0][1], enumFieldPragmas)
  91. else:
  92. e = newSymS(skEnumField, n[i][0], c)
  93. identToReplace = addr n[i][0]
  94. var v = semConstExpr(c, n[i][1])
  95. var strVal: PNode = nil
  96. case skipTypes(v.typ, abstractInst-{tyTypeDesc}).kind
  97. of tyTuple:
  98. if v.len == 2:
  99. strVal = v[1] # second tuple part is the string value
  100. if skipTypes(strVal.typ, abstractInst).kind in {tyString, tyCstring}:
  101. if not isOrdinalType(v[0].typ, allowEnumWithHoles=true):
  102. localError(c.config, v[0].info, errOrdinalTypeExpected % typeToString(v[0].typ, preferDesc))
  103. x = toInt64(getOrdValue(v[0])) # first tuple part is the ordinal
  104. n[i][1][0] = newIntTypeNode(x, getSysType(c.graph, unknownLineInfo, tyInt))
  105. else:
  106. localError(c.config, strVal.info, errStringLiteralExpected)
  107. else:
  108. localError(c.config, v.info, errWrongNumberOfVariables)
  109. of tyString, tyCstring:
  110. strVal = v
  111. x = counter
  112. useAutoCounter = true
  113. else:
  114. if isOrdinalType(v.typ, allowEnumWithHoles=true):
  115. x = toInt64(getOrdValue(v))
  116. n[i][1] = newIntTypeNode(x, getSysType(c.graph, unknownLineInfo, tyInt))
  117. else:
  118. localError(c.config, v.info, errOrdinalTypeExpected % typeToString(v.typ, preferDesc))
  119. if i != 1:
  120. if x != counter:
  121. needsReorder = true
  122. incl(result.flags, tfEnumHasHoles)
  123. e.ast = strVal # might be nil
  124. counter = x
  125. of nkSym:
  126. e = n[i].sym
  127. useAutoCounter = true
  128. of nkIdent, nkAccQuoted:
  129. e = newSymS(skEnumField, n[i], c)
  130. identToReplace = addr n[i]
  131. useAutoCounter = true
  132. of nkPragmaExpr:
  133. e = newSymS(skEnumField, n[i][0], c)
  134. pragma(c, e, n[i][1], enumFieldPragmas)
  135. identToReplace = addr n[i][0]
  136. useAutoCounter = true
  137. else:
  138. illFormedAst(n[i], c.config)
  139. if useAutoCounter:
  140. while counter in counterSet and counter != high(typeof(counter)):
  141. inc counter
  142. counterSet.incl counter
  143. elif counterSet.containsOrIncl(counter):
  144. localError(c.config, n[i].info, errDuplicateAliasInEnumX % e.name.s)
  145. e.typ = result
  146. e.position = int(counter)
  147. let symNode = newSymNode(e)
  148. if identToReplace != nil and c.config.cmd notin cmdDocLike:
  149. # A hack to produce documentation for enum fields.
  150. identToReplace[] = symNode
  151. if e.position == 0: hasNull = true
  152. if result.sym != nil and sfExported in result.sym.flags:
  153. e.flags.incl {sfUsed, sfExported}
  154. result.n.add symNode
  155. styleCheckDef(c, e)
  156. onDef(e.info, e)
  157. suggestSym(c.graph, e.info, e, c.graph.usageSym)
  158. if sfGenSym notin e.flags:
  159. if not isPure:
  160. addInterfaceOverloadableSymAt(c, c.currentScope, e)
  161. else:
  162. declarePureEnumField(c, e)
  163. if (let conflict = strTableInclReportConflict(symbols, e); conflict != nil):
  164. wrongRedefinition(c, e.info, e.name.s, conflict.info)
  165. if counter == high(typeof(counter)):
  166. if i > 1 and result.n[i-2].sym.position == high(int):
  167. localError(c.config, n[i].info, errOverflowInEnumX % [e.name.s, $high(typeof(counter))])
  168. else:
  169. inc(counter)
  170. if needsReorder:
  171. result.n.sons.sort(
  172. proc (x, y: PNode): int =
  173. result = cmp(x.sym.position, y.sym.position)
  174. )
  175. if isPure and sfExported in result.sym.flags:
  176. addPureEnum(c, LazySym(sym: result.sym))
  177. if tfNotNil in e.typ.flags and not hasNull:
  178. result.flags.incl tfRequiresInit
  179. setToStringProc(c.graph, result, genEnumToStrProc(result, n.info, c.graph, c.idgen))
  180. proc semSet(c: PContext, n: PNode, prev: PType): PType =
  181. result = newOrPrevType(tySet, prev, c)
  182. if n.len == 2 and n[1].kind != nkEmpty:
  183. var base = semTypeNode(c, n[1], nil)
  184. addSonSkipIntLit(result, base, c.idgen)
  185. if base.kind in {tyGenericInst, tyAlias, tySink}: base = skipModifier(base)
  186. if base.kind notin {tyGenericParam, tyGenericInvocation}:
  187. if base.kind == tyForward:
  188. c.skipTypes.add n
  189. elif not isOrdinalType(base, allowEnumWithHoles = true):
  190. localError(c.config, n.info, errOrdinalTypeExpected % typeToString(base, preferDesc))
  191. elif lengthOrd(c.config, base) > MaxSetElements:
  192. localError(c.config, n.info, errSetTooBig)
  193. else:
  194. localError(c.config, n.info, errXExpectsOneTypeParam % "set")
  195. addSonSkipIntLit(result, errorType(c), c.idgen)
  196. proc semContainerArg(c: PContext; n: PNode, kindStr: string; result: PType) =
  197. if n.len == 2:
  198. var base = semTypeNode(c, n[1], nil)
  199. if base.kind == tyVoid:
  200. localError(c.config, n.info, errTIsNotAConcreteType % typeToString(base))
  201. addSonSkipIntLit(result, base, c.idgen)
  202. else:
  203. localError(c.config, n.info, errXExpectsOneTypeParam % kindStr)
  204. addSonSkipIntLit(result, errorType(c), c.idgen)
  205. proc semContainer(c: PContext, n: PNode, kind: TTypeKind, kindStr: string,
  206. prev: PType): PType =
  207. result = newOrPrevType(kind, prev, c)
  208. semContainerArg(c, n, kindStr, result)
  209. proc semVarargs(c: PContext, n: PNode, prev: PType): PType =
  210. result = newOrPrevType(tyVarargs, prev, c)
  211. if n.len == 2 or n.len == 3:
  212. var base = semTypeNode(c, n[1], nil)
  213. addSonSkipIntLit(result, base, c.idgen)
  214. if n.len == 3:
  215. result.n = newIdentNode(considerQuotedIdent(c, n[2]), n[2].info)
  216. else:
  217. localError(c.config, n.info, errXExpectsOneTypeParam % "varargs")
  218. addSonSkipIntLit(result, errorType(c), c.idgen)
  219. proc semVarOutType(c: PContext, n: PNode, prev: PType; flags: TTypeFlags): PType =
  220. if n.len == 1:
  221. result = newOrPrevType(tyVar, prev, c)
  222. result.flags = flags
  223. var base = semTypeNode(c, n[0], nil)
  224. if base.kind == tyTypeDesc and not isSelf(base):
  225. base = base[0]
  226. if base.kind == tyVar:
  227. localError(c.config, n.info, "type 'var var' is not allowed")
  228. base = base[0]
  229. addSonSkipIntLit(result, base, c.idgen)
  230. else:
  231. result = newConstraint(c, tyVar)
  232. proc isRecursiveType(t: PType, cycleDetector: var IntSet): bool =
  233. if t == nil:
  234. return false
  235. if cycleDetector.containsOrIncl(t.id):
  236. return true
  237. case t.kind
  238. of tyAlias, tyGenericInst, tyDistinct:
  239. return isRecursiveType(t.skipModifier, cycleDetector)
  240. else:
  241. return false
  242. proc annotateClosureConv(n: PNode) =
  243. case n.kind
  244. of {nkNone..nkNilLit}:
  245. discard
  246. of nkTupleConstr:
  247. if n.typ.kind == tyProc and n.typ.callConv == ccClosure and
  248. n[0].typ.kind == tyProc and n[0].typ.callConv != ccClosure:
  249. # restores `transf.generateThunk`
  250. n[0] = newTreeIT(nkHiddenSubConv, n[0].info, n.typ,
  251. newNodeI(nkEmpty, n[0].info), n[0])
  252. n.transitionSonsKind(nkClosure)
  253. n.flags.incl nfTransf
  254. else:
  255. for i in 0..<n.len:
  256. annotateClosureConv(n[i])
  257. proc fitDefaultNode(c: PContext, n: var PNode, expectedType: PType) =
  258. inc c.inStaticContext
  259. n = semConstExpr(c, n, expectedType = expectedType)
  260. let oldType = n.typ
  261. n.flags.incl nfSem
  262. if expectedType != nil and oldType != expectedType:
  263. n = fitNodeConsiderViewType(c, expectedType, n, n.info)
  264. changeType(c, n, expectedType, true) # infer types for default fields value
  265. # bug #22926; be cautious that it uses `semConstExpr` to
  266. # evaulate the default fields; it's only natural to use
  267. # `changeType` to infer types for constant values
  268. # that's also the reason why we don't use `semExpr` to check
  269. # the type since two overlapping error messages might be produced
  270. annotateClosureConv(n)
  271. # xxx any troubles related to defaults fields, consult `semConst` for a potential answer
  272. if n.kind != nkNilLit:
  273. typeAllowedCheck(c, n.info, n.typ, skConst, {taProcContextIsNotMacro, taIsDefaultField})
  274. dec c.inStaticContext
  275. proc isRecursiveType*(t: PType): bool =
  276. # handle simple recusive types before typeFinalPass
  277. var cycleDetector = initIntSet()
  278. isRecursiveType(t, cycleDetector)
  279. proc addSonSkipIntLitChecked(c: PContext; father, son: PType; it: PNode, id: IdGenerator) =
  280. let s = son.skipIntLit(id)
  281. father.add(s)
  282. if isRecursiveType(s):
  283. localError(c.config, it.info, "illegal recursion in type '" & typeToString(s) & "'")
  284. else:
  285. propagateToOwner(father, s)
  286. proc semDistinct(c: PContext, n: PNode, prev: PType): PType =
  287. if n.len == 0: return newConstraint(c, tyDistinct)
  288. result = newOrPrevType(tyDistinct, prev, c)
  289. addSonSkipIntLitChecked(c, result, semTypeNode(c, n[0], nil), n[0], c.idgen)
  290. if n.len > 1: result.n = n[1]
  291. proc semRangeAux(c: PContext, n: PNode, prev: PType): PType =
  292. assert isRange(n)
  293. checkSonsLen(n, 3, c.config)
  294. result = newOrPrevType(tyRange, prev, c)
  295. result.n = newNodeI(nkRange, n.info)
  296. # always create a 'valid' range type, but overwrite it later
  297. # because 'semExprWithType' can raise an exception. See bug #6895.
  298. addSonSkipIntLit(result, errorType(c), c.idgen)
  299. if (n[1].kind == nkEmpty) or (n[2].kind == nkEmpty):
  300. localError(c.config, n.info, "range is empty")
  301. var range: array[2, PNode]
  302. # XXX this is still a hard compilation in a generic context, this can
  303. # result in unresolved generic parameters being treated like real types
  304. range[0] = semExprWithType(c, n[1], {efDetermineType})
  305. range[1] = semExprWithType(c, n[2], {efDetermineType})
  306. var rangeT: array[2, PType] = default(array[2, PType])
  307. for i in 0..1:
  308. rangeT[i] = range[i].typ.skipTypes({tyStatic}).skipIntLit(c.idgen)
  309. let hasUnknownTypes = c.inGenericContext > 0 and
  310. (rangeT[0].kind == tyFromExpr or rangeT[1].kind == tyFromExpr)
  311. if not hasUnknownTypes:
  312. if not sameType(rangeT[0].skipTypes({tyRange}), rangeT[1].skipTypes({tyRange})):
  313. typeMismatch(c.config, n.info, rangeT[0], rangeT[1], n)
  314. elif not isOrdinalType(rangeT[0]) and rangeT[0].kind notin {tyFloat..tyFloat128} or
  315. rangeT[0].kind == tyBool:
  316. localError(c.config, n.info, "ordinal or float type expected, but got " & typeToString(rangeT[0]))
  317. elif enumHasHoles(rangeT[0]):
  318. localError(c.config, n.info, "enum '$1' has holes" % typeToString(rangeT[0]))
  319. for i in 0..1:
  320. if hasUnresolvedArgs(c, range[i]):
  321. result.n.add makeStaticExpr(c, range[i])
  322. result.flags.incl tfUnresolved
  323. else:
  324. result.n.add semConstExpr(c, range[i])
  325. if result.n[i].kind in {nkFloatLit..nkFloat64Lit} and result.n[i].floatVal.isNaN:
  326. localError(c.config, n.info, "NaN is not a valid range " & (if i == 0: "start" else: "end"))
  327. if weakLeValue(result.n[0], result.n[1]) == impNo:
  328. localError(c.config, n.info, "range is empty")
  329. result[0] = rangeT[0]
  330. proc semRange(c: PContext, n: PNode, prev: PType): PType =
  331. result = nil
  332. if n.len == 2:
  333. if isRange(n[1]):
  334. result = semRangeAux(c, n[1], prev)
  335. if not isDefined(c.config, "nimPreviewRangeDefault"):
  336. let n = result.n
  337. if n[0].kind in {nkCharLit..nkUInt64Lit} and n[0].intVal > 0:
  338. incl(result.flags, tfRequiresInit)
  339. elif n[1].kind in {nkCharLit..nkUInt64Lit} and n[1].intVal < 0:
  340. incl(result.flags, tfRequiresInit)
  341. elif n[0].kind in {nkFloatLit..nkFloat64Lit} and
  342. n[0].floatVal > 0.0:
  343. incl(result.flags, tfRequiresInit)
  344. elif n[1].kind in {nkFloatLit..nkFloat64Lit} and
  345. n[1].floatVal < 0.0:
  346. incl(result.flags, tfRequiresInit)
  347. else:
  348. if n[1].kind == nkInfix and considerQuotedIdent(c, n[1][0]).s == "..<":
  349. localError(c.config, n[0].info, "range types need to be constructed with '..', '..<' is not supported")
  350. else:
  351. localError(c.config, n[0].info, "expected range")
  352. result = newOrPrevType(tyError, prev, c)
  353. else:
  354. localError(c.config, n.info, errXExpectsOneTypeParam % "range")
  355. result = newOrPrevType(tyError, prev, c)
  356. proc semArrayIndexConst(c: PContext, e: PNode, info: TLineInfo): PType =
  357. let x = semConstExpr(c, e)
  358. if x.kind in {nkIntLit..nkUInt64Lit}:
  359. result = makeRangeType(c, 0, x.intVal-1, info,
  360. x.typ.skipTypes({tyTypeDesc}))
  361. else:
  362. result = x.typ.skipTypes({tyTypeDesc})
  363. proc semArrayIndex(c: PContext, n: PNode): PType =
  364. if isRange(n):
  365. result = semRangeAux(c, n, nil)
  366. elif n.kind == nkInfix and n[0].kind == nkIdent and n[0].ident.s == "..<":
  367. result = errorType(c)
  368. else:
  369. # XXX this is still a hard compilation in a generic context, this can
  370. # result in unresolved generic parameters being treated like real types
  371. let e = semExprWithType(c, n, {efDetermineType})
  372. if e.typ.kind == tyFromExpr:
  373. result = makeRangeWithStaticExpr(c, e.typ.n)
  374. elif e.kind in {nkIntLit..nkUInt64Lit}:
  375. if e.intVal < 0:
  376. localError(c.config, n.info,
  377. "Array length can't be negative, but was " & $e.intVal)
  378. result = makeRangeType(c, 0, e.intVal-1, n.info, e.typ)
  379. elif e.kind == nkSym and (e.typ.kind == tyStatic or e.typ.kind == tyTypeDesc):
  380. if e.typ.kind == tyStatic:
  381. if e.sym.ast != nil:
  382. return semArrayIndex(c, e.sym.ast)
  383. if e.typ.skipModifier.kind != tyGenericParam and not isOrdinalType(e.typ.skipModifier):
  384. let info = if n.safeLen > 1: n[1].info else: n.info
  385. localError(c.config, info, errOrdinalTypeExpected % typeToString(e.typ, preferDesc))
  386. result = makeRangeWithStaticExpr(c, e)
  387. if c.inGenericContext > 0: result.flags.incl tfUnresolved
  388. else:
  389. result = e.typ.skipTypes({tyTypeDesc})
  390. result.flags.incl tfImplicitStatic
  391. elif e.kind in (nkCallKinds + {nkBracketExpr}) and hasUnresolvedArgs(c, e):
  392. if not isOrdinalType(e.typ.skipTypes({tyStatic, tyAlias, tyGenericInst, tySink})):
  393. localError(c.config, n[1].info, errOrdinalTypeExpected % typeToString(e.typ, preferDesc))
  394. # This is an int returning call, depending on an
  395. # yet unknown generic param (see tuninstantiatedgenericcalls).
  396. # We are going to construct a range type that will be
  397. # properly filled-out in semtypinst (see how tyStaticExpr
  398. # is handled there).
  399. result = makeRangeWithStaticExpr(c, e)
  400. elif e.kind == nkIdent:
  401. result = e.typ.skipTypes({tyTypeDesc})
  402. else:
  403. result = semArrayIndexConst(c, e, n.info)
  404. #localError(c.config, n[1].info, errConstExprExpected)
  405. proc semArray(c: PContext, n: PNode, prev: PType): PType =
  406. var base: PType
  407. if n.len == 3:
  408. # 3 = length(array indx base)
  409. let indx = semArrayIndex(c, n[1])
  410. var indxB = indx
  411. if indxB.kind in {tyGenericInst, tyAlias, tySink}: indxB = skipModifier(indxB)
  412. if indxB.kind notin {tyGenericParam, tyStatic, tyFromExpr} and
  413. tfUnresolved notin indxB.flags:
  414. if not isOrdinalType(indxB):
  415. localError(c.config, n[1].info, errOrdinalTypeExpected % typeToString(indxB, preferDesc))
  416. elif enumHasHoles(indxB):
  417. localError(c.config, n[1].info, "enum '$1' has holes" %
  418. typeToString(indxB.skipTypes({tyRange})))
  419. elif indxB.kind != tyRange and
  420. lengthOrd(c.config, indxB) > high(uint16).int:
  421. # assume range type is intentional
  422. localError(c.config, n[1].info,
  423. "index type '$1' for array is too large" % typeToString(indxB))
  424. base = semTypeNode(c, n[2], nil)
  425. # ensure we only construct a tyArray when there was no error (bug #3048):
  426. # bug #6682: Do not propagate initialization requirements etc for the
  427. # index type:
  428. result = newOrPrevType(tyArray, prev, c, indx)
  429. addSonSkipIntLit(result, base, c.idgen)
  430. else:
  431. localError(c.config, n.info, errArrayExpectsTwoTypeParams)
  432. result = newOrPrevType(tyError, prev, c)
  433. proc semIterableType(c: PContext, n: PNode, prev: PType): PType =
  434. result = newOrPrevType(tyIterable, prev, c)
  435. if n.len == 2:
  436. let base = semTypeNode(c, n[1], nil)
  437. addSonSkipIntLit(result, base, c.idgen)
  438. else:
  439. localError(c.config, n.info, errXExpectsOneTypeParam % "iterable")
  440. result = newOrPrevType(tyError, prev, c)
  441. proc semOrdinal(c: PContext, n: PNode, prev: PType): PType =
  442. result = newOrPrevType(tyOrdinal, prev, c)
  443. if n.len == 2:
  444. var base = semTypeNode(c, n[1], nil)
  445. if base.kind != tyGenericParam:
  446. if not isOrdinalType(base):
  447. localError(c.config, n[1].info, errOrdinalTypeExpected % typeToString(base, preferDesc))
  448. addSonSkipIntLit(result, base, c.idgen)
  449. else:
  450. localError(c.config, n.info, errXExpectsOneTypeParam % "ordinal")
  451. result = newOrPrevType(tyError, prev, c)
  452. proc semAnonTuple(c: PContext, n: PNode, prev: PType): PType =
  453. if n.len == 0:
  454. localError(c.config, n.info, errTypeExpected)
  455. result = newOrPrevType(tyTuple, prev, c)
  456. for it in n:
  457. let t = semTypeNode(c, it, nil)
  458. addSonSkipIntLitChecked(c, result, t, it, c.idgen)
  459. proc firstRange(config: ConfigRef, t: PType): PNode =
  460. if t.skipModifier().kind in tyFloat..tyFloat64:
  461. result = newFloatNode(nkFloatLit, firstFloat(t))
  462. else:
  463. result = newIntNode(nkIntLit, firstOrd(config, t))
  464. result.typ() = t
  465. proc semTuple(c: PContext, n: PNode, prev: PType): PType =
  466. var typ: PType
  467. result = newOrPrevType(tyTuple, prev, c)
  468. result.n = newNodeI(nkRecList, n.info)
  469. var check = initIntSet()
  470. var counter = 0
  471. for i in ord(n.kind == nkBracketExpr)..<n.len:
  472. var a = n[i]
  473. if (a.kind != nkIdentDefs): illFormedAst(a, c.config)
  474. checkMinSonsLen(a, 3, c.config)
  475. var hasDefaultField = a[^1].kind != nkEmpty
  476. if hasDefaultField:
  477. typ = if a[^2].kind != nkEmpty: semTypeNode(c, a[^2], nil) else: nil
  478. if c.inGenericContext > 0:
  479. a[^1] = semExprWithType(c, a[^1], {efDetermineType, efAllowSymChoice}, typ)
  480. if typ == nil:
  481. typ = a[^1].typ
  482. else:
  483. fitDefaultNode(c, a[^1], typ)
  484. typ = a[^1].typ
  485. elif a[^2].kind != nkEmpty:
  486. typ = semTypeNode(c, a[^2], nil)
  487. if c.graph.config.isDefined("nimPreviewRangeDefault") and typ.skipTypes(abstractInst).kind == tyRange:
  488. a[^1] = firstRange(c.config, typ)
  489. hasDefaultField = true
  490. else:
  491. localError(c.config, a.info, errTypeExpected)
  492. typ = errorType(c)
  493. for j in 0..<a.len - 2:
  494. var field = newSymG(skField, a[j], c)
  495. field.typ = typ
  496. field.position = counter
  497. inc(counter)
  498. if containsOrIncl(check, field.name.id):
  499. localError(c.config, a[j].info, "attempt to redefine: '" & field.name.s & "'")
  500. else:
  501. let fSym = newSymNode(field)
  502. if hasDefaultField:
  503. fSym.sym.ast = a[^1]
  504. fSym.sym.ast.flags.incl nfSkipFieldChecking
  505. result.n.add fSym
  506. addSonSkipIntLit(result, typ, c.idgen)
  507. styleCheckDef(c, a[j].info, field)
  508. onDef(field.info, field)
  509. if result.n.len == 0: result.n = nil
  510. if isTupleRecursive(result):
  511. localError(c.config, n.info, errIllegalRecursionInTypeX % typeToString(result))
  512. proc semIdentVis(c: PContext, kind: TSymKind, n: PNode,
  513. allowed: TSymFlags): PSym =
  514. # identifier with visibility
  515. if n.kind == nkPostfix:
  516. if n.len == 2:
  517. # for gensym'ed identifiers the identifier may already have been
  518. # transformed to a symbol and we need to use that here:
  519. result = newSymG(kind, n[1], c)
  520. var v = considerQuotedIdent(c, n[0])
  521. if sfExported in allowed and v.id == ord(wStar):
  522. incl(result.flags, sfExported)
  523. else:
  524. if not (sfExported in allowed):
  525. localError(c.config, n[0].info, errXOnlyAtModuleScope % "export")
  526. else:
  527. localError(c.config, n[0].info, errInvalidVisibilityX % renderTree(n[0]))
  528. else:
  529. result = nil
  530. illFormedAst(n, c.config)
  531. else:
  532. result = newSymG(kind, n, c)
  533. proc semIdentWithPragma(c: PContext, kind: TSymKind, n: PNode,
  534. allowed: TSymFlags, fromTopLevel = false): PSym =
  535. if n.kind == nkPragmaExpr:
  536. checkSonsLen(n, 2, c.config)
  537. result = semIdentVis(c, kind, n[0], allowed)
  538. case kind
  539. of skType:
  540. # process pragmas later, because result.typ has not been set yet
  541. discard
  542. of skField: pragma(c, result, n[1], fieldPragmas)
  543. of skVar: pragma(c, result, n[1], varPragmas)
  544. of skLet: pragma(c, result, n[1], letPragmas)
  545. of skConst: pragma(c, result, n[1], constPragmas)
  546. else: discard
  547. else:
  548. result = semIdentVis(c, kind, n, allowed)
  549. let invalidPragmasForPush = if fromTopLevel and sfWasGenSym notin result.flags:
  550. {}
  551. else:
  552. {wExportc, wExportCpp, wDynlib}
  553. case kind
  554. of skField: implicitPragmas(c, result, n.info, fieldPragmas)
  555. of skVar: implicitPragmas(c, result, n.info, varPragmas-invalidPragmasForPush)
  556. of skLet: implicitPragmas(c, result, n.info, letPragmas-invalidPragmasForPush)
  557. of skConst: implicitPragmas(c, result, n.info, constPragmas-invalidPragmasForPush)
  558. else: discard
  559. proc checkForOverlap(c: PContext, t: PNode, currentEx, branchIndex: int) =
  560. let ex = t[branchIndex][currentEx].skipConv
  561. for i in 1..branchIndex:
  562. for j in 0..<t[i].len - 1:
  563. if i == branchIndex and j == currentEx: break
  564. if overlap(t[i][j].skipConv, ex):
  565. localError(c.config, ex.info, errDuplicateCaseLabel)
  566. proc semBranchRange(c: PContext, n, a, b: PNode, covered: var Int128): PNode =
  567. checkMinSonsLen(n, 1, c.config)
  568. let ac = semConstExpr(c, a)
  569. let bc = semConstExpr(c, b)
  570. if ac.kind in {nkStrLit..nkTripleStrLit} or bc.kind in {nkStrLit..nkTripleStrLit}:
  571. localError(c.config, b.info, "range of string is invalid")
  572. var at = fitNode(c, n[0].typ, ac, ac.info).skipConvTakeType
  573. var bt = fitNode(c, n[0].typ, bc, bc.info).skipConvTakeType
  574. # the calls to fitNode may introduce calls to converters
  575. # mirrored with semCaseBranch for single elements
  576. if at.kind in {nkHiddenCallConv, nkHiddenStdConv, nkHiddenSubConv}:
  577. at = semConstExpr(c, at)
  578. if bt.kind in {nkHiddenCallConv, nkHiddenStdConv, nkHiddenSubConv}:
  579. bt = semConstExpr(c, bt)
  580. result = newNodeI(nkRange, a.info)
  581. result.add(at)
  582. result.add(bt)
  583. if emptyRange(ac, bc): localError(c.config, b.info, "range is empty")
  584. else: covered = covered + getOrdValue(bc) + 1 - getOrdValue(ac)
  585. proc semCaseBranchRange(c: PContext, t, b: PNode,
  586. covered: var Int128): PNode =
  587. checkSonsLen(b, 3, c.config)
  588. result = semBranchRange(c, t, b[1], b[2], covered)
  589. proc semCaseBranchSetElem(c: PContext, n, b: PNode,
  590. covered: var Int128): PNode =
  591. if isRange(b):
  592. checkSonsLen(b, 3, c.config)
  593. result = semBranchRange(c, n, b[1], b[2], covered)
  594. elif b.kind == nkRange:
  595. checkSonsLen(b, 2, c.config)
  596. result = semBranchRange(c, n, b[0], b[1], covered)
  597. else:
  598. result = fitNode(c, n[0].typ, b, b.info)
  599. inc(covered)
  600. proc semCaseBranch(c: PContext, n, branch: PNode, branchIndex: int,
  601. covered: var Int128) =
  602. let lastIndex = branch.len - 2
  603. for i in 0..lastIndex:
  604. var b = branch[i]
  605. if b.kind == nkRange:
  606. branch[i] = b
  607. # same check as in semBranchRange for exhaustiveness
  608. covered = covered + getOrdValue(b[1]) + 1 - getOrdValue(b[0])
  609. elif isRange(b):
  610. branch[i] = semCaseBranchRange(c, n, b, covered)
  611. else:
  612. # constant sets and arrays are allowed:
  613. # set expected type to selector type for type inference
  614. # even if it can be a different type like a set or array
  615. var r = semConstExpr(c, b, expectedType = n[0].typ)
  616. if r.kind in {nkCurly, nkBracket} and r.len == 0 and branch.len == 2:
  617. # discarding ``{}`` and ``[]`` branches silently
  618. delSon(branch, 0)
  619. return
  620. elif r.kind notin {nkCurly, nkBracket} or r.len == 0:
  621. checkMinSonsLen(n, 1, c.config)
  622. var tmp = fitNode(c, n[0].typ, r, r.info)
  623. # the call to fitNode may introduce a call to a converter
  624. # mirrored with semBranchRange
  625. if tmp.kind in {nkHiddenCallConv, nkHiddenStdConv, nkHiddenSubConv}:
  626. tmp = semConstExpr(c, tmp)
  627. branch[i] = skipConv(tmp)
  628. inc(covered)
  629. else:
  630. if r.kind == nkCurly:
  631. r = deduplicate(c.config, r)
  632. # first element is special and will overwrite: branch[i]:
  633. branch[i] = semCaseBranchSetElem(c, n, r[0], covered)
  634. # other elements have to be added to ``branch``
  635. for j in 1..<r.len:
  636. branch.add(semCaseBranchSetElem(c, n, r[j], covered))
  637. # caution! last son of branch must be the actions to execute:
  638. swap(branch[^2], branch[^1])
  639. checkForOverlap(c, n, i, branchIndex)
  640. # Elements added above needs to be checked for overlaps.
  641. for i in lastIndex.succ..<branch.len - 1:
  642. checkForOverlap(c, n, i, branchIndex)
  643. proc toCover(c: PContext, t: PType): Int128 =
  644. let t2 = skipTypes(t, abstractVarRange-{tyTypeDesc})
  645. if t2.kind == tyEnum and enumHasHoles(t2):
  646. result = toInt128(t2.n.len)
  647. else:
  648. # <----
  649. let t = skipTypes(t, abstractVar-{tyTypeDesc})
  650. # XXX: hack incoming. lengthOrd is incorrect for 64bit integer
  651. # types because it doesn't uset Int128 yet. This entire branching
  652. # should be removed as soon as lengthOrd uses int128.
  653. if t.kind in {tyInt64, tyUInt64}:
  654. result = toInt128(1) shl 64
  655. elif t.kind in {tyInt, tyUInt}:
  656. result = toInt128(1) shl (c.config.target.intSize * 8)
  657. else:
  658. result = lengthOrd(c.config, t)
  659. proc semRecordNodeAux(c: PContext, n: PNode, check: var IntSet, pos: var int,
  660. father: PNode, rectype: PType, hasCaseFields = false)
  661. proc getIntSetOfType(c: PContext, t: PType): IntSet =
  662. result = initIntSet()
  663. if t.enumHasHoles:
  664. let t = t.skipTypes(abstractRange)
  665. for field in t.n.sons:
  666. result.incl(field.sym.position)
  667. else:
  668. assert(lengthOrd(c.config, t) <= BiggestInt(MaxSetElements))
  669. for i in toInt64(firstOrd(c.config, t))..toInt64(lastOrd(c.config, t)):
  670. result.incl(i.int)
  671. iterator processBranchVals(b: PNode): int =
  672. assert b.kind in {nkOfBranch, nkElifBranch, nkElse}
  673. if b.kind == nkOfBranch:
  674. for i in 0..<b.len-1:
  675. if b[i].kind in {nkIntLit, nkCharLit}:
  676. yield b[i].intVal.int
  677. elif b[i].kind == nkRange:
  678. for i in b[i][0].intVal..b[i][1].intVal:
  679. yield i.int
  680. proc renderAsType(vals: IntSet, t: PType): string =
  681. result = "{"
  682. let t = t.skipTypes(abstractRange)
  683. var enumSymOffset = 0
  684. var i = 0
  685. for val in vals:
  686. if result.len > 1:
  687. result &= ", "
  688. case t.kind:
  689. of tyEnum, tyBool:
  690. while t.n[enumSymOffset].sym.position < val: inc(enumSymOffset)
  691. result &= t.n[enumSymOffset].sym.name.s
  692. of tyChar:
  693. result.addQuoted(char(val))
  694. else:
  695. if i == 64:
  696. result &= "omitted $1 values..." % $(vals.len - i)
  697. break
  698. else:
  699. result &= $val
  700. inc(i)
  701. result &= "}"
  702. proc formatMissingEnums(c: PContext, n: PNode): string =
  703. var coveredCases = initIntSet()
  704. for i in 1..<n.len:
  705. for val in processBranchVals(n[i]):
  706. coveredCases.incl val
  707. result = (c.getIntSetOfType(n[0].typ) - coveredCases).renderAsType(n[0].typ)
  708. proc semRecordCase(c: PContext, n: PNode, check: var IntSet, pos: var int,
  709. father: PNode, rectype: PType) =
  710. var a = copyNode(n)
  711. checkMinSonsLen(n, 2, c.config)
  712. semRecordNodeAux(c, n[0], check, pos, a, rectype, hasCaseFields = true)
  713. if a[0].kind != nkSym:
  714. internalError(c.config, "semRecordCase: discriminant is no symbol")
  715. return
  716. incl(a[0].sym.flags, sfDiscriminant)
  717. var covered = toInt128(0)
  718. var chckCovered = false
  719. var typ = skipTypes(a[0].typ, abstractVar-{tyTypeDesc})
  720. const shouldChckCovered = {tyInt..tyInt64, tyChar, tyEnum, tyUInt..tyUInt32, tyBool}
  721. case typ.kind
  722. of shouldChckCovered:
  723. chckCovered = true
  724. of tyFloat..tyFloat128, tyError:
  725. discard
  726. of tyRange:
  727. if skipTypes(typ.elementType, abstractInst).kind in shouldChckCovered:
  728. chckCovered = true
  729. of tyForward:
  730. errorUndeclaredIdentifier(c, n[0].info, typ.sym.name.s)
  731. elif not isOrdinalType(typ):
  732. localError(c.config, n[0].info, "selector must be of an ordinal type, float")
  733. if firstOrd(c.config, typ) != 0:
  734. localError(c.config, n.info, "low(" & $a[0].sym.name.s &
  735. ") must be 0 for discriminant")
  736. elif lengthOrd(c.config, typ) > 0x00007FFF:
  737. localError(c.config, n.info, "len($1) must be less than 32768" % a[0].sym.name.s)
  738. for i in 1..<n.len:
  739. var b = copyTree(n[i])
  740. a.add b
  741. case n[i].kind
  742. of nkOfBranch:
  743. checkMinSonsLen(b, 2, c.config)
  744. semCaseBranch(c, a, b, i, covered)
  745. of nkElse:
  746. checkSonsLen(b, 1, c.config)
  747. if chckCovered and covered == toCover(c, a[0].typ):
  748. message(c.config, b.info, warnUnreachableElse)
  749. chckCovered = false
  750. else: illFormedAst(n, c.config)
  751. delSon(b, b.len - 1)
  752. semRecordNodeAux(c, lastSon(n[i]), check, pos, b, rectype, hasCaseFields = true)
  753. if chckCovered and covered != toCover(c, a[0].typ):
  754. if a[0].typ.skipTypes(abstractRange).kind == tyEnum:
  755. localError(c.config, a.info, "not all cases are covered; missing: $1" %
  756. formatMissingEnums(c, a))
  757. else:
  758. localError(c.config, a.info, "not all cases are covered")
  759. father.add a
  760. proc semRecordNodeAux(c: PContext, n: PNode, check: var IntSet, pos: var int,
  761. father: PNode, rectype: PType, hasCaseFields: bool) =
  762. if n == nil: return
  763. case n.kind
  764. of nkRecWhen:
  765. var a = copyTree(n)
  766. var branch: PNode = nil # the branch to take
  767. var cannotResolve = false # no branch should be taken
  768. for i in 0..<a.len:
  769. var it = a[i]
  770. if it == nil: illFormedAst(n, c.config)
  771. var idx = 1
  772. case it.kind
  773. of nkElifBranch:
  774. checkSonsLen(it, 2, c.config)
  775. if c.inGenericContext == 0:
  776. var e = semConstBoolExpr(c, it[0])
  777. if e.kind != nkIntLit: discard "don't report followup error"
  778. elif e.intVal != 0 and branch == nil: branch = it[1]
  779. else:
  780. # XXX this is still a hard compilation in a generic context, this can
  781. # result in unresolved generic parameters being treated like real types
  782. let e = semExprWithType(c, it[0], {efDetermineType})
  783. if e.typ.kind == tyFromExpr:
  784. it[0] = makeStaticExpr(c, e)
  785. cannotResolve = true
  786. else:
  787. it[0] = forceBool(c, e)
  788. let val = getConstExpr(c.module, it[0], c.idgen, c.graph)
  789. if val == nil or val.kind != nkIntLit:
  790. cannotResolve = true
  791. elif not cannotResolve and val.intVal != 0 and branch == nil:
  792. branch = it[1]
  793. of nkElse:
  794. checkSonsLen(it, 1, c.config)
  795. if branch == nil and not cannotResolve: branch = it[0]
  796. idx = 0
  797. else: illFormedAst(n, c.config)
  798. if c.inGenericContext > 0 and cannotResolve:
  799. # use a new check intset here for each branch:
  800. var newCheck: IntSet = check
  801. var newPos = pos
  802. var newf = newNodeI(nkRecList, n.info)
  803. semRecordNodeAux(c, it[idx], newCheck, newPos, newf, rectype, hasCaseFields)
  804. it[idx] = if newf.len == 1: newf[0] else: newf
  805. if branch != nil:
  806. semRecordNodeAux(c, branch, check, pos, father, rectype, hasCaseFields)
  807. elif cannotResolve:
  808. father.add a
  809. elif father.kind in {nkElse, nkOfBranch}:
  810. father.add newNodeI(nkRecList, n.info)
  811. of nkRecCase:
  812. semRecordCase(c, n, check, pos, father, rectype)
  813. of nkNilLit:
  814. if father.kind != nkRecList: father.add newNodeI(nkRecList, n.info)
  815. of nkRecList:
  816. # attempt to keep the nesting at a sane level:
  817. var a = if father.kind == nkRecList: father else: copyNode(n)
  818. for i in 0..<n.len:
  819. semRecordNodeAux(c, n[i], check, pos, a, rectype, hasCaseFields)
  820. if a != father: father.add a
  821. of nkIdentDefs:
  822. checkMinSonsLen(n, 3, c.config)
  823. var a: PNode
  824. if father.kind != nkRecList and n.len >= 4: a = newNodeI(nkRecList, n.info)
  825. else: a = newNodeI(nkEmpty, n.info)
  826. var typ: PType
  827. var hasDefaultField = n[^1].kind != nkEmpty
  828. if hasDefaultField:
  829. typ = if n[^2].kind != nkEmpty: semTypeNode(c, n[^2], nil) else: nil
  830. if c.inGenericContext > 0:
  831. n[^1] = semExprWithType(c, n[^1], {efDetermineType, efAllowSymChoice}, typ)
  832. if typ == nil:
  833. typ = n[^1].typ
  834. else:
  835. fitDefaultNode(c, n[^1], typ)
  836. typ = n[^1].typ
  837. propagateToOwner(rectype, typ)
  838. elif n[^2].kind == nkEmpty:
  839. localError(c.config, n.info, errTypeExpected)
  840. typ = errorType(c)
  841. else:
  842. typ = semTypeNode(c, n[^2], nil)
  843. if c.graph.config.isDefined("nimPreviewRangeDefault") and typ.skipTypes(abstractInst).kind == tyRange:
  844. n[^1] = firstRange(c.config, typ)
  845. hasDefaultField = true
  846. propagateToOwner(rectype, typ)
  847. var fieldOwner = if c.inGenericContext > 0: c.getCurrOwner
  848. else: rectype.sym
  849. for i in 0..<n.len-2:
  850. var f = semIdentWithPragma(c, skField, n[i], {sfExported})
  851. let info = if n[i].kind == nkPostfix:
  852. n[i][1].info
  853. else:
  854. n[i].info
  855. suggestSym(c.graph, info, f, c.graph.usageSym)
  856. f.typ = typ
  857. f.position = pos
  858. f.options = c.config.options
  859. if fieldOwner != nil and
  860. {sfImportc, sfExportc} * fieldOwner.flags != {} and
  861. not hasCaseFields and f.loc.snippet == "":
  862. f.loc.snippet = rope(f.name.s)
  863. f.flags.incl {sfImportc, sfExportc} * fieldOwner.flags
  864. inc(pos)
  865. if containsOrIncl(check, f.name.id):
  866. localError(c.config, info, "attempt to redefine: '" & f.name.s & "'")
  867. let fSym = newSymNode(f)
  868. if hasDefaultField:
  869. fSym.sym.ast = n[^1]
  870. fSym.sym.ast.flags.incl nfSkipFieldChecking
  871. if a.kind == nkEmpty: father.add fSym
  872. else: a.add fSym
  873. styleCheckDef(c, f)
  874. onDef(f.info, f)
  875. if a.kind != nkEmpty: father.add a
  876. of nkSym:
  877. # This branch only valid during generic object
  878. # inherited from generic/partial specialized parent second check.
  879. # There is no branch validity check here
  880. if containsOrIncl(check, n.sym.name.id):
  881. localError(c.config, n.info, "attempt to redefine: '" & n.sym.name.s & "'")
  882. father.add n
  883. of nkEmpty:
  884. if father.kind in {nkElse, nkOfBranch}:
  885. father.add n
  886. else: illFormedAst(n, c.config)
  887. proc addInheritedFieldsAux(c: PContext, check: var IntSet, pos: var int,
  888. n: PNode) =
  889. case n.kind
  890. of nkRecCase:
  891. if (n[0].kind != nkSym): internalError(c.config, n.info, "addInheritedFieldsAux")
  892. addInheritedFieldsAux(c, check, pos, n[0])
  893. for i in 1..<n.len:
  894. case n[i].kind
  895. of nkOfBranch, nkElse:
  896. addInheritedFieldsAux(c, check, pos, lastSon(n[i]))
  897. else: internalError(c.config, n.info, "addInheritedFieldsAux(record case branch)")
  898. of nkRecList, nkRecWhen, nkElifBranch, nkElse:
  899. for i in int(n.kind == nkElifBranch)..<n.len:
  900. addInheritedFieldsAux(c, check, pos, n[i])
  901. of nkSym:
  902. incl(check, n.sym.name.id)
  903. inc(pos)
  904. else: internalError(c.config, n.info, "addInheritedFieldsAux()")
  905. proc skipGenericInvocation(t: PType): PType {.inline.} =
  906. result = t
  907. if result.kind == tyGenericInvocation:
  908. result = result[0]
  909. while result.kind in {tyGenericInst, tyGenericBody, tyRef, tyPtr, tyAlias, tySink, tyOwned}:
  910. result = skipModifier(result)
  911. proc tryAddInheritedFields(c: PContext, check: var IntSet, pos: var int,
  912. obj: PType, n: PNode, isPartial = false, innerObj: PType = nil): bool =
  913. if ((not isPartial) and (obj.kind notin {tyObject, tyGenericParam} or tfFinal in obj.flags)) or
  914. (innerObj != nil and obj.sym.id == innerObj.sym.id):
  915. localError(c.config, n.info, "Cannot inherit from: '" & $obj & "'")
  916. result = false
  917. elif obj.kind == tyObject:
  918. result = true
  919. if (obj.len > 0) and (obj[0] != nil):
  920. result = result and tryAddInheritedFields(c, check, pos, obj[0].skipGenericInvocation, n, false, obj)
  921. addInheritedFieldsAux(c, check, pos, obj.n)
  922. else:
  923. result = true
  924. proc semObjectNode(c: PContext, n: PNode, prev: PType; flags: TTypeFlags): PType =
  925. result = nil
  926. if n.len == 0:
  927. return newConstraint(c, tyObject)
  928. var check = initIntSet()
  929. var pos = 0
  930. var base, realBase: PType = nil
  931. # n[0] contains the pragmas (if any). We process these later...
  932. checkSonsLen(n, 3, c.config)
  933. if n[1].kind != nkEmpty:
  934. realBase = semTypeNode(c, n[1][0], nil)
  935. base = skipTypesOrNil(realBase, skipPtrs)
  936. if base.isNil:
  937. localError(c.config, n.info, "cannot inherit from a type that is not an object type")
  938. else:
  939. var concreteBase = skipGenericInvocation(base)
  940. if concreteBase.kind in {tyObject, tyGenericParam,
  941. tyGenericInvocation} and tfFinal notin concreteBase.flags:
  942. # we only check fields duplication of object inherited from
  943. # concrete object. If inheriting from generic object or partial
  944. # specialized object, there will be second check after instantiation
  945. # located in semGeneric.
  946. if concreteBase.kind == tyObject:
  947. if concreteBase.sym != nil and concreteBase.sym.magic == mException and
  948. sfSystemModule notin c.module.flags:
  949. message(c.config, n.info, warnInheritFromException, "")
  950. if not tryAddInheritedFields(c, check, pos, concreteBase, n):
  951. return newType(tyError, c.idgen, result.owner)
  952. elif concreteBase.kind == tyForward:
  953. c.skipTypes.add n #we retry in the final pass
  954. else:
  955. if concreteBase.kind != tyError:
  956. localError(c.config, n[1].info, "inheritance only works with non-final objects; " &
  957. "for " & typeToString(realBase) & " to be inheritable it must be " &
  958. "'object of RootObj' instead of 'object'")
  959. base = nil
  960. realBase = nil
  961. if n.kind != nkObjectTy: internalError(c.config, n.info, "semObjectNode")
  962. result = newOrPrevType(tyObject, prev, c)
  963. rawAddSon(result, realBase)
  964. if realBase == nil and tfInheritable in flags:
  965. result.flags.incl tfInheritable
  966. if tfAcyclic in flags: result.flags.incl tfAcyclic
  967. if result.n.isNil:
  968. result.n = newNodeI(nkRecList, n.info)
  969. else:
  970. # partial object so add things to the check
  971. if not tryAddInheritedFields(c, check, pos, result, n, isPartial = true):
  972. return newType(tyError, c.idgen, result.owner)
  973. semRecordNodeAux(c, n[2], check, pos, result.n, result)
  974. if n[0].kind != nkEmpty:
  975. # dummy symbol for `pragma`:
  976. var s = newSymS(skType, newIdentNode(getIdent(c.cache, "dummy"), n.info), c)
  977. s.typ = result
  978. pragma(c, s, n[0], typePragmas)
  979. if base == nil and tfInheritable notin result.flags:
  980. incl(result.flags, tfFinal)
  981. if c.inGenericContext == 0 and computeRequiresInit(c, result):
  982. result.flags.incl tfRequiresInit
  983. proc semAnyRef(c: PContext; n: PNode; kind: TTypeKind; prev: PType): PType =
  984. if n.len < 1:
  985. result = newConstraint(c, kind)
  986. else:
  987. let isCall = int ord(n.kind in nkCallKinds+{nkBracketExpr})
  988. let n = if n[0].kind == nkBracket: n[0] else: n
  989. checkMinSonsLen(n, 1, c.config)
  990. let body = n.lastSon
  991. var t = if prev != nil and prev.kind != tyGenericBody and body.kind == nkObjectTy:
  992. semObjectNode(c, body, nil, prev.flags)
  993. else:
  994. semTypeNode(c, body, nil)
  995. if t.kind == tyTypeDesc and tfUnresolved notin t.flags:
  996. t = t.base
  997. if t.kind == tyVoid:
  998. localError(c.config, n.info, "type '$1 void' is not allowed" % kind.toHumanStr)
  999. result = newOrPrevType(kind, prev, c)
  1000. var isNilable = false
  1001. var wrapperKind = tyNone
  1002. # check every except the last is an object:
  1003. for i in isCall..<n.len-1:
  1004. let ni = n[i]
  1005. # echo "semAnyRef ", "n: ", n, "i: ", i, "ni: ", ni
  1006. if ni.kind == nkNilLit:
  1007. isNilable = true
  1008. else:
  1009. let region = semTypeNode(c, ni, nil)
  1010. if region.kind in {tyOwned, tySink}:
  1011. wrapperKind = region.kind
  1012. elif region.skipTypes({tyGenericInst, tyAlias, tySink}).kind notin {
  1013. tyError, tyObject}:
  1014. message c.config, n[i].info, errGenerated, "region needs to be an object type"
  1015. addSonSkipIntLit(result, region, c.idgen)
  1016. else:
  1017. message(c.config, n.info, warnDeprecated, "region for pointer types is deprecated")
  1018. addSonSkipIntLit(result, region, c.idgen)
  1019. addSonSkipIntLit(result, t, c.idgen)
  1020. if tfPartial in result.flags:
  1021. if result.elementType.kind == tyObject: incl(result.elementType.flags, tfPartial)
  1022. # if not isNilable: result.flags.incl tfNotNil
  1023. case wrapperKind
  1024. of tyOwned:
  1025. if optOwnedRefs in c.config.globalOptions:
  1026. let t = newTypeS(tyOwned, c, result)
  1027. t.flags.incl tfHasOwned
  1028. result = t
  1029. of tySink:
  1030. let t = newTypeS(tySink, c, result)
  1031. result = t
  1032. else: discard
  1033. if result.kind == tyRef and c.config.selectedGC in {gcArc, gcOrc, gcAtomicArc}:
  1034. result.flags.incl tfHasAsgn
  1035. proc findEnforcedStaticType(t: PType): PType =
  1036. # This handles types such as `static[T] and Foo`,
  1037. # which are subset of `static[T]`, hence they could
  1038. # be treated in the same way
  1039. result = nil
  1040. if t == nil: return nil
  1041. if t.kind == tyStatic: return t
  1042. if t.kind == tyAnd:
  1043. for s in t.kids:
  1044. let t = findEnforcedStaticType(s)
  1045. if t != nil: return t
  1046. proc addParamOrResult(c: PContext, param: PSym, kind: TSymKind) =
  1047. if kind == skMacro:
  1048. let staticType = findEnforcedStaticType(param.typ)
  1049. if staticType != nil:
  1050. var a = copySym(param, c.idgen)
  1051. a.typ = staticType.base
  1052. addDecl(c, a)
  1053. #elif param.typ != nil and param.typ.kind == tyTypeDesc:
  1054. # addDecl(c, param)
  1055. else:
  1056. # within a macro, every param has the type NimNode!
  1057. let nn = getSysSym(c.graph, param.info, "NimNode")
  1058. var a = copySym(param, c.idgen)
  1059. a.typ = nn.typ
  1060. addDecl(c, a)
  1061. else:
  1062. if sfGenSym in param.flags:
  1063. # bug #XXX, fix the gensym'ed parameters owner:
  1064. if param.owner == nil:
  1065. setOwner(param, getCurrOwner(c))
  1066. else: addDecl(c, param)
  1067. template shouldHaveMeta(t) =
  1068. internalAssert c.config, tfHasMeta in t.flags
  1069. # result.lastSon.flags.incl tfHasMeta
  1070. proc addImplicitGeneric(c: PContext; typeClass: PType, typId: PIdent;
  1071. info: TLineInfo; genericParams: PNode;
  1072. paramName: string): PType =
  1073. if genericParams == nil:
  1074. # This happens with anonymous proc types appearing in signatures
  1075. # XXX: we need to lift these earlier
  1076. return
  1077. let finalTypId = if typId != nil: typId
  1078. else: getIdent(c.cache, paramName & ":type")
  1079. # is this a bindOnce type class already present in the param list?
  1080. for i in 0..<genericParams.len:
  1081. if genericParams[i].sym.name.id == finalTypId.id:
  1082. return genericParams[i].typ
  1083. let owner = if typeClass.sym != nil: typeClass.sym
  1084. else: getCurrOwner(c)
  1085. var s = newSym(skType, finalTypId, c.idgen, owner, info)
  1086. if sfExplain in owner.flags: s.flags.incl sfExplain
  1087. if typId == nil: s.flags.incl(sfAnon)
  1088. s.linkTo(typeClass)
  1089. typeClass.flags.incl tfImplicitTypeParam
  1090. s.position = genericParams.len
  1091. genericParams.add newSymNode(s)
  1092. result = typeClass
  1093. addDecl(c, s)
  1094. proc liftParamType(c: PContext, procKind: TSymKind, genericParams: PNode,
  1095. paramType: PType, paramName: string,
  1096. info: TLineInfo, anon = false): PType =
  1097. if paramType == nil: return # (e.g. proc return type)
  1098. template recurse(typ: PType, anonFlag = false): untyped =
  1099. liftParamType(c, procKind, genericParams, typ, paramName, info, anonFlag)
  1100. var paramTypId = if not anon and paramType.sym != nil: paramType.sym.name
  1101. else: nil
  1102. case paramType.kind
  1103. of tyAnything:
  1104. result = addImplicitGeneric(c, newTypeS(tyGenericParam, c), nil, info, genericParams, paramName)
  1105. of tyStatic:
  1106. if paramType.base.kind != tyNone and paramType.n != nil:
  1107. # this is a concrete static value
  1108. return
  1109. if tfUnresolved in paramType.flags: return # already lifted
  1110. let lifted = recurse(paramType.base)
  1111. let base = (if lifted != nil: lifted else: paramType.base)
  1112. if base.isMetaType and procKind == skMacro:
  1113. localError(c.config, info, errMacroBodyDependsOnGenericTypes % paramName)
  1114. result = addImplicitGeneric(c, newTypeS(tyStatic, c, base),
  1115. paramTypId, info, genericParams, paramName)
  1116. if result != nil: result.flags.incl({tfHasStatic, tfUnresolved})
  1117. of tyTypeDesc:
  1118. if tfUnresolved notin paramType.flags:
  1119. # naked typedescs are not bindOnce types
  1120. if paramType.base.kind == tyNone and paramTypId != nil and
  1121. (paramTypId.id == getIdent(c.cache, "typedesc").id or
  1122. paramTypId.id == getIdent(c.cache, "type").id):
  1123. # XXX Why doesn't this check for tyTypeDesc instead?
  1124. paramTypId = nil
  1125. let t = newTypeS(tyTypeDesc, c, paramType.base)
  1126. incl t.flags, tfCheckedForDestructor
  1127. result = addImplicitGeneric(c, t, paramTypId, info, genericParams, paramName)
  1128. else:
  1129. result = nil
  1130. of tyDistinct:
  1131. if paramType.len == 1:
  1132. # disable the bindOnce behavior for the type class
  1133. result = recurse(paramType.base, true)
  1134. else:
  1135. result = nil
  1136. of tyTuple:
  1137. result = nil
  1138. for i in 0..<paramType.len:
  1139. let t = recurse(paramType[i])
  1140. if t != nil:
  1141. paramType[i] = t
  1142. result = paramType
  1143. of tyAlias, tyOwned:
  1144. result = recurse(paramType.base)
  1145. of tySequence, tySet, tyArray, tyOpenArray,
  1146. tyVar, tyLent, tyPtr, tyRef, tyProc, tySink:
  1147. # XXX: this is a bit strange, but proc(s: seq)
  1148. # produces tySequence(tyGenericParam, tyNone).
  1149. # This also seems to be true when creating aliases
  1150. # like: type myseq = distinct seq.
  1151. # Maybe there is another better place to associate
  1152. # the seq type class with the seq identifier.
  1153. if paramType.kind == tySequence and paramType.elementType.kind == tyNone:
  1154. let typ = newTypeS(tyBuiltInTypeClass, c,
  1155. newTypeS(paramType.kind, c))
  1156. result = addImplicitGeneric(c, typ, paramTypId, info, genericParams, paramName)
  1157. else:
  1158. result = nil
  1159. for i in 0..<paramType.len:
  1160. if paramType[i] == paramType:
  1161. globalError(c.config, info, errIllegalRecursionInTypeX % typeToString(paramType))
  1162. var lifted = recurse(paramType[i])
  1163. if lifted != nil:
  1164. paramType[i] = lifted
  1165. result = paramType
  1166. of tyGenericBody:
  1167. result = newTypeS(tyGenericInvocation, c)
  1168. result.rawAddSon(paramType)
  1169. for i in 0..<paramType.len - 1:
  1170. if paramType[i].kind == tyStatic:
  1171. var staticCopy = paramType[i].exactReplica
  1172. staticCopy.flags.incl tfInferrableStatic
  1173. result.rawAddSon staticCopy
  1174. else:
  1175. result.rawAddSon newTypeS(tyAnything, c)
  1176. if paramType.typeBodyImpl.kind == tyUserTypeClass:
  1177. result.kind = tyUserTypeClassInst
  1178. result.rawAddSon paramType.typeBodyImpl
  1179. return addImplicitGeneric(c, result, paramTypId, info, genericParams, paramName)
  1180. let x = instGenericContainer(c, paramType.sym.info, result,
  1181. allowMetaTypes = true)
  1182. result = newTypeS(tyCompositeTypeClass, c)
  1183. result.rawAddSon paramType
  1184. result.rawAddSon x
  1185. result = addImplicitGeneric(c, result, paramTypId, info, genericParams, paramName)
  1186. of tyGenericInst:
  1187. result = nil
  1188. if paramType.skipModifier.kind == tyUserTypeClass:
  1189. var cp = copyType(paramType, c.idgen, getCurrOwner(c))
  1190. copyTypeProps(c.graph, c.idgen.module, cp, paramType)
  1191. cp.kind = tyUserTypeClassInst
  1192. return addImplicitGeneric(c, cp, paramTypId, info, genericParams, paramName)
  1193. for i in 1..<paramType.len-1:
  1194. var lifted = recurse(paramType[i])
  1195. if lifted != nil:
  1196. paramType[i] = lifted
  1197. result = paramType
  1198. result.last.shouldHaveMeta
  1199. let liftBody = recurse(paramType.skipModifier, true)
  1200. if liftBody != nil:
  1201. result = liftBody
  1202. result.flags.incl tfHasMeta
  1203. #result.shouldHaveMeta
  1204. of tyGenericInvocation:
  1205. result = nil
  1206. for i in 1..<paramType.len:
  1207. #if paramType[i].kind != tyTypeDesc:
  1208. let lifted = recurse(paramType[i])
  1209. if lifted != nil: paramType[i] = lifted
  1210. let body = paramType.base
  1211. if body.kind in {tyForward, tyError}:
  1212. # this may happen for proc type appearing in a type section
  1213. # before one of its param types
  1214. return
  1215. if body.last.kind == tyUserTypeClass:
  1216. let expanded = instGenericContainer(c, info, paramType,
  1217. allowMetaTypes = true)
  1218. result = recurse(expanded, true)
  1219. of tyUserTypeClasses, tyBuiltInTypeClass, tyCompositeTypeClass,
  1220. tyAnd, tyOr, tyNot, tyConcept:
  1221. result = addImplicitGeneric(c,
  1222. copyType(paramType, c.idgen, getCurrOwner(c)), paramTypId,
  1223. info, genericParams, paramName)
  1224. of tyGenericParam:
  1225. result = nil
  1226. markUsed(c, paramType.sym.info, paramType.sym)
  1227. onUse(paramType.sym.info, paramType.sym)
  1228. if tfWildcard in paramType.flags:
  1229. paramType.flags.excl tfWildcard
  1230. paramType.sym.transitionGenericParamToType()
  1231. else: result = nil
  1232. proc semParamType(c: PContext, n: PNode, constraint: var PNode): PType =
  1233. ## Semchecks the type of parameters.
  1234. if n.kind == nkCurlyExpr:
  1235. result = semTypeNode(c, n[0], nil)
  1236. constraint = semNodeKindConstraints(n, c.config, 1)
  1237. elif n.kind == nkCall and
  1238. n[0].kind in {nkIdent, nkSym, nkOpenSymChoice, nkClosedSymChoice, nkOpenSym} and
  1239. considerQuotedIdent(c, n[0]).s == "{}":
  1240. result = semTypeNode(c, n[1], nil)
  1241. constraint = semNodeKindConstraints(n, c.config, 2)
  1242. else:
  1243. result = semTypeNode(c, n, nil)
  1244. proc newProcType(c: PContext; info: TLineInfo; prev: PType = nil): PType =
  1245. result = newOrPrevType(tyProc, prev, c)
  1246. result.callConv = lastOptionEntry(c).defaultCC
  1247. result.n = newNodeI(nkFormalParams, info)
  1248. rawAddSon(result, nil) # return type
  1249. # result.n[0] used to be `nkType`, but now it's `nkEffectList` because
  1250. # the effects are now stored in there too ... this is a bit hacky, but as
  1251. # usual we desperately try to save memory:
  1252. result.n.add newNodeI(nkEffectList, info)
  1253. proc isMagic(sym: PSym): bool =
  1254. if sym.ast == nil: return false
  1255. let nPragmas = sym.ast[pragmasPos]
  1256. return hasPragma(nPragmas, wMagic)
  1257. proc semProcTypeNode(c: PContext, n, genericParams: PNode,
  1258. prev: PType, kind: TSymKind; isType=false): PType =
  1259. # for historical reasons (code grows) this is invoked for parameter
  1260. # lists too and then 'isType' is false.
  1261. checkMinSonsLen(n, 1, c.config)
  1262. result = newProcType(c, n.info, prev)
  1263. var check = initIntSet()
  1264. var counter = 0
  1265. template isCurrentlyGeneric: bool =
  1266. # genericParams might update as implicit generic params are added
  1267. genericParams != nil and genericParams.len > 0
  1268. for i in 1..<n.len:
  1269. var a = n[i]
  1270. if a.kind != nkIdentDefs:
  1271. # for some generic instantiations the passed ':env' parameter
  1272. # for closures has already been produced (see bug #898). We simply
  1273. # skip this parameter here. It'll then be re-generated in another LL
  1274. # pass over this instantiation:
  1275. if a.kind == nkSym and sfFromGeneric in a.sym.flags: continue
  1276. illFormedAst(a, c.config)
  1277. checkMinSonsLen(a, 3, c.config)
  1278. var
  1279. typ: PType = nil
  1280. def: PNode = nil
  1281. constraint: PNode = nil
  1282. hasType = a[^2].kind != nkEmpty
  1283. hasDefault = a[^1].kind != nkEmpty
  1284. if hasType:
  1285. let isGeneric = isCurrentlyGeneric()
  1286. inc c.inGenericContext, ord(isGeneric)
  1287. typ = semParamType(c, a[^2], constraint)
  1288. dec c.inGenericContext, ord(isGeneric)
  1289. # TODO: Disallow typed/untyped in procs in the compiler/stdlib
  1290. if kind in {skProc, skFunc} and (typ.kind == tyTyped or typ.kind == tyUntyped):
  1291. if not isMagic(getCurrOwner(c)):
  1292. localError(c.config, a[^2].info, "'" & typ.sym.name.s & "' is only allowed in templates and macros or magic procs")
  1293. if hasDefault:
  1294. def = a[^1]
  1295. if a.len > 3:
  1296. var msg = ""
  1297. for j in 0 ..< a.len - 2:
  1298. if msg.len != 0: msg.add(", ")
  1299. msg.add($a[j])
  1300. msg.add(" all have default value '")
  1301. msg.add(def.renderTree)
  1302. msg.add("', this may be unintentional, " &
  1303. "either use ';' (semicolon) or explicitly write each default value")
  1304. message(c.config, a.info, warnImplicitDefaultValue, msg)
  1305. block determineType:
  1306. var canBeVoid = false
  1307. if kind == skTemplate:
  1308. if typ != nil and typ.kind == tyUntyped:
  1309. # don't do any typechecking or assign a type for
  1310. # `untyped` parameter default value
  1311. break determineType
  1312. elif hasUnresolvedArgs(c, def):
  1313. # template default value depends on other parameter
  1314. # don't do any typechecking
  1315. def.typ() = makeTypeFromExpr(c, def.copyTree)
  1316. break determineType
  1317. elif typ != nil and typ.kind == tyTyped:
  1318. canBeVoid = true
  1319. let isGeneric = isCurrentlyGeneric()
  1320. inc c.inGenericContext, ord(isGeneric)
  1321. if canBeVoid:
  1322. def = semExpr(c, def, {efDetermineType, efAllowSymChoice}, typ)
  1323. else:
  1324. def = semExprWithType(c, def, {efDetermineType, efAllowSymChoice}, typ)
  1325. dec c.inGenericContext, ord(isGeneric)
  1326. if def.referencesAnotherParam(getCurrOwner(c)):
  1327. def.flags.incl nfDefaultRefsParam
  1328. if typ == nil:
  1329. typ = def.typ
  1330. if isEmptyContainer(typ):
  1331. localError(c.config, a.info, "cannot infer the type of parameter '" & $a[0] & "'")
  1332. if typ.kind == tyTypeDesc:
  1333. # consider a proc such as:
  1334. # proc takesType(T = int)
  1335. # a naive analysis may conclude that the proc type is type[int]
  1336. # which will prevent other types from matching - clearly a very
  1337. # surprising behavior. We must instead fix the expected type of
  1338. # the proc to be the unbound typedesc type:
  1339. typ = newTypeS(tyTypeDesc, c, newTypeS(tyNone, c))
  1340. typ.flags.incl tfCheckedForDestructor
  1341. elif def.typ != nil and def.typ.kind != tyFromExpr: # def.typ can be void
  1342. # if def.typ != nil and def.typ.kind != tyNone:
  1343. # example code that triggers it:
  1344. # proc sort[T](cmp: proc(a, b: T): int = cmp)
  1345. if not containsGenericType(typ):
  1346. # check type compatibility between def.typ and typ:
  1347. def = fitNode(c, typ, def, def.info)
  1348. elif typ.kind == tyStatic:
  1349. def = semConstExpr(c, def)
  1350. def = fitNode(c, typ, def, def.info)
  1351. if not hasType and not hasDefault:
  1352. if isType: localError(c.config, a.info, "':' expected")
  1353. if kind in {skTemplate, skMacro}:
  1354. typ = newTypeS(tyUntyped, c)
  1355. elif skipTypes(typ, {tyGenericInst, tyAlias, tySink}).kind == tyVoid:
  1356. continue
  1357. for j in 0..<a.len-2:
  1358. var arg = newSymG(skParam, if a[j].kind == nkPragmaExpr: a[j][0] else: a[j], c)
  1359. if arg.name.id == ord(wUnderscore):
  1360. arg.flags.incl(sfGenSym)
  1361. elif containsOrIncl(check, arg.name.id):
  1362. localError(c.config, a[j].info, "attempt to redefine: '" & arg.name.s & "'")
  1363. if a[j].kind == nkPragmaExpr:
  1364. pragma(c, arg, a[j][1], paramPragmas)
  1365. if not hasType and not hasDefault and kind notin {skTemplate, skMacro}:
  1366. let param = strTableGet(c.signatures, arg.name)
  1367. if param != nil: typ = param.typ
  1368. else:
  1369. localError(c.config, a.info, "parameter '$1' requires a type" % arg.name.s)
  1370. typ = errorType(c)
  1371. var nameForLift = arg.name.s
  1372. if sfGenSym in arg.flags:
  1373. nameForLift.add("`gensym" & $arg.id)
  1374. let lifted = liftParamType(c, kind, genericParams, typ,
  1375. nameForLift, arg.info)
  1376. let finalType = if lifted != nil: lifted else: typ.skipIntLit(c.idgen)
  1377. arg.typ = finalType
  1378. arg.position = counter
  1379. if constraint != nil:
  1380. #only replace the constraint when it has been set as arg could contain codegenDecl
  1381. arg.constraint = constraint
  1382. inc(counter)
  1383. if def != nil and def.kind != nkEmpty:
  1384. arg.ast = copyTree(def)
  1385. result.n.add newSymNode(arg)
  1386. rawAddSon(result, finalType)
  1387. addParamOrResult(c, arg, kind)
  1388. styleCheckDef(c, a[j].info, arg)
  1389. onDef(a[j].info, arg)
  1390. a[j] = newSymNode(arg)
  1391. var r: PType = nil
  1392. if n[0].kind != nkEmpty:
  1393. let isGeneric = isCurrentlyGeneric()
  1394. inc c.inGenericContext, ord(isGeneric)
  1395. r = semTypeNode(c, n[0], nil)
  1396. dec c.inGenericContext, ord(isGeneric)
  1397. if r != nil and kind in {skMacro, skTemplate} and r.kind == tyTyped:
  1398. # XXX: To implement the proposed change in the warning, just
  1399. # delete this entire if block. The rest is (at least at time of
  1400. # writing this comment) already implemented.
  1401. let info = n[0].info
  1402. const msg = "`typed` will change its meaning in future versions of Nim. " &
  1403. "`void` or no return type declaration at all has the same " &
  1404. "meaning as the current meaning of `typed` as return type " &
  1405. "declaration."
  1406. message(c.config, info, warnDeprecated, msg)
  1407. r = nil
  1408. if r != nil:
  1409. # turn explicit 'void' return type into 'nil' because the rest of the
  1410. # compiler only checks for 'nil':
  1411. if skipTypes(r, {tyGenericInst, tyAlias, tySink}).kind != tyVoid:
  1412. if kind notin {skMacro, skTemplate} and r.kind in {tyTyped, tyUntyped}:
  1413. localError(c.config, n[0].info, "return type '" & typeToString(r) &
  1414. "' is only valid for macros and templates")
  1415. # 'auto' as a return type does not imply a generic:
  1416. elif r.kind == tyAnything:
  1417. r = copyType(r, c.idgen, r.owner)
  1418. r.flags.incl tfRetType
  1419. elif r.kind == tyStatic:
  1420. # type allowed should forbid this type
  1421. discard
  1422. else:
  1423. if r.sym == nil or sfAnon notin r.sym.flags:
  1424. let lifted = liftParamType(c, kind, genericParams, r, "result",
  1425. n[0].info)
  1426. if lifted != nil:
  1427. r = lifted
  1428. #if r.kind != tyGenericParam:
  1429. #echo "came here for ", typeToString(r)
  1430. r.flags.incl tfRetType
  1431. r = skipIntLit(r, c.idgen)
  1432. if kind == skIterator:
  1433. # see tchainediterators
  1434. # in cases like iterator foo(it: iterator): typeof(it)
  1435. # we don't need to change the return type to iter[T]
  1436. result.flags.incl tfIterator
  1437. # XXX Would be nice if we could get rid of this
  1438. result[0] = r
  1439. let oldFlags = result.flags
  1440. propagateToOwner(result, r)
  1441. if oldFlags != result.flags:
  1442. # XXX This rather hacky way keeps 'tflatmap' compiling:
  1443. if tfHasMeta notin oldFlags:
  1444. result.flags.excl tfHasMeta
  1445. result.n.typ() = r
  1446. if isCurrentlyGeneric():
  1447. for n in genericParams:
  1448. if {sfUsed, sfAnon} * n.sym.flags == {}:
  1449. result.flags.incl tfUnresolved
  1450. if tfWildcard in n.sym.typ.flags:
  1451. n.sym.transitionGenericParamToType()
  1452. n.sym.typ.flags.excl tfWildcard
  1453. proc semStmtListType(c: PContext, n: PNode, prev: PType): PType =
  1454. checkMinSonsLen(n, 1, c.config)
  1455. for i in 0..<n.len - 1:
  1456. n[i] = semStmt(c, n[i], {})
  1457. if n.len > 0:
  1458. result = semTypeNode(c, n[^1], prev)
  1459. n.typ() = result
  1460. n[^1].typ() = result
  1461. else:
  1462. result = nil
  1463. proc semBlockType(c: PContext, n: PNode, prev: PType): PType =
  1464. inc(c.p.nestedBlockCounter)
  1465. let oldBreakInLoop = c.p.breakInLoop
  1466. c.p.breakInLoop = false
  1467. checkSonsLen(n, 2, c.config)
  1468. openScope(c)
  1469. if n[0].kind notin {nkEmpty, nkSym}:
  1470. addDecl(c, newSymS(skLabel, n[0], c))
  1471. result = semStmtListType(c, n[1], prev)
  1472. n[1].typ() = result
  1473. n.typ() = result
  1474. closeScope(c)
  1475. c.p.breakInLoop = oldBreakInLoop
  1476. dec(c.p.nestedBlockCounter)
  1477. proc semGenericParamInInvocation(c: PContext, n: PNode): PType =
  1478. result = semTypeNode(c, n, nil)
  1479. n.typ() = makeTypeDesc(c, result)
  1480. proc trySemObjectTypeForInheritedGenericInst(c: PContext, n: PNode, t: PType): bool =
  1481. var
  1482. check = initIntSet()
  1483. pos = 0
  1484. let
  1485. realBase = t.baseClass
  1486. base = skipTypesOrNil(realBase, skipPtrs)
  1487. result = true
  1488. if base.isNil:
  1489. localError(c.config, n.info, errIllegalRecursionInTypeX % "object")
  1490. else:
  1491. let concreteBase = skipGenericInvocation(base)
  1492. if concreteBase.kind == tyObject and tfFinal notin concreteBase.flags:
  1493. if not tryAddInheritedFields(c, check, pos, concreteBase, n):
  1494. return false
  1495. else:
  1496. if concreteBase.kind != tyError:
  1497. localError(c.config, n.info, errInheritanceOnlyWithNonFinalObjects)
  1498. var newf = newNodeI(nkRecList, n.info)
  1499. semRecordNodeAux(c, t.n, check, pos, newf, t)
  1500. proc containsGenericInvocationWithForward(n: PNode): bool =
  1501. if n.kind == nkSym and n.sym.ast != nil and n.sym.ast.len > 1 and n.sym.ast[2].kind == nkObjectTy:
  1502. for p in n.sym.ast[2][^1]:
  1503. if p.kind == nkIdentDefs and p[1].typ != nil and p[1].typ.kind == tyGenericInvocation and
  1504. p[1][0].kind == nkSym and p[1][0].typ.kind == tyForward:
  1505. return true
  1506. return false
  1507. proc semGeneric(c: PContext, n: PNode, s: PSym, prev: PType): PType =
  1508. if s.typ == nil:
  1509. localError(c.config, n.info, "cannot instantiate the '$1' $2" %
  1510. [s.name.s, s.kind.toHumanStr])
  1511. return newOrPrevType(tyError, prev, c)
  1512. var t = s.typ.skipTypes({tyAlias})
  1513. if t.kind == tyCompositeTypeClass and t.base.kind == tyGenericBody:
  1514. t = t.base
  1515. result = newOrPrevType(tyGenericInvocation, prev, c)
  1516. addSonSkipIntLit(result, t, c.idgen)
  1517. template addToResult(typ, skip) =
  1518. if typ.isNil:
  1519. internalAssert c.config, false
  1520. rawAddSon(result, typ)
  1521. else:
  1522. if skip:
  1523. addSonSkipIntLit(result, typ, c.idgen)
  1524. else:
  1525. rawAddSon(result, makeRangeWithStaticExpr(c, typ.n))
  1526. if t.kind == tyForward:
  1527. for i in 1..<n.len:
  1528. var elem = semGenericParamInInvocation(c, n[i])
  1529. addToResult(elem, true)
  1530. return
  1531. elif t.kind != tyGenericBody:
  1532. # we likely got code of the form TypeA[TypeB] where TypeA is
  1533. # not generic.
  1534. localError(c.config, n.info, errNoGenericParamsAllowedForX % s.name.s)
  1535. return newOrPrevType(tyError, prev, c)
  1536. else:
  1537. var m = newCandidate(c, t)
  1538. m.isNoCall = true
  1539. matches(c, n, copyTree(n), m)
  1540. if m.state != csMatch:
  1541. var err = "cannot instantiate "
  1542. err.addTypeHeader(c.config, t)
  1543. err.add "\ngot: <$1>\nbut expected: <$2>" % [describeArgs(c, n), describeArgs(c, t.n, 0)]
  1544. localError(c.config, n.info, errGenerated, err)
  1545. return newOrPrevType(tyError, prev, c)
  1546. var isConcrete = true
  1547. let rType = m.call[0].typ
  1548. let mIndex = if rType != nil: rType.len - 1 else: -1
  1549. for i in 1..<m.call.len:
  1550. var typ = m.call[i].typ
  1551. # is this a 'typedesc' *parameter*? If so, use the typedesc type,
  1552. # unstripped.
  1553. if m.call[i].kind == nkSym and m.call[i].sym.kind == skParam and
  1554. typ.kind == tyTypeDesc and containsGenericType(typ):
  1555. isConcrete = false
  1556. addToResult(typ, true)
  1557. else:
  1558. typ = typ.skipTypes({tyTypeDesc})
  1559. if containsGenericType(typ): isConcrete = false
  1560. var skip = true
  1561. if mIndex >= i - 1 and tfImplicitStatic in rType[i - 1].flags and isIntLit(typ):
  1562. skip = false
  1563. addToResult(typ, skip)
  1564. if isConcrete:
  1565. if s.ast == nil and s.typ.kind != tyCompositeTypeClass:
  1566. # XXX: What kind of error is this? is it still relevant?
  1567. localError(c.config, n.info, errCannotInstantiateX % s.name.s)
  1568. result = newOrPrevType(tyError, prev, c)
  1569. elif containsGenericInvocationWithForward(n[0]):
  1570. c.skipTypes.add n #fixes 1500
  1571. else:
  1572. result = instGenericContainer(c, n.info, result,
  1573. allowMetaTypes = false)
  1574. # special check for generic object with
  1575. # generic/partial specialized parent
  1576. let tx = result.skipTypes(abstractPtrs, 50)
  1577. if tx.isNil or isTupleRecursive(tx):
  1578. localError(c.config, n.info, "illegal recursion in type '$1'" % typeToString(result[0]))
  1579. return errorType(c)
  1580. if tx != result and tx.kind == tyObject:
  1581. if tx[0] != nil:
  1582. if not trySemObjectTypeForInheritedGenericInst(c, n, tx):
  1583. return newOrPrevType(tyError, prev, c)
  1584. var position = 0
  1585. recomputeFieldPositions(tx, tx.n, position)
  1586. proc maybeAliasType(c: PContext; typeExpr, prev: PType): PType =
  1587. if prev != nil and (prev.kind == tyGenericBody or
  1588. typeExpr.kind in {tyObject, tyEnum, tyDistinct, tyForward, tyGenericBody}):
  1589. result = newTypeS(tyAlias, c)
  1590. result.rawAddSon typeExpr
  1591. result.sym = prev.sym
  1592. if prev.kind != tyGenericBody:
  1593. assignType(prev, result)
  1594. else:
  1595. result = nil
  1596. proc fixupTypeOf(c: PContext, prev: PType, typExpr: PNode) =
  1597. if prev != nil:
  1598. let result = newTypeS(tyAlias, c)
  1599. result.rawAddSon typExpr.typ
  1600. result.sym = prev.sym
  1601. if prev.kind != tyGenericBody:
  1602. assignType(prev, result)
  1603. proc semTypeExpr(c: PContext, n: PNode; prev: PType): PType =
  1604. var n = semExprWithType(c, n, {efDetermineType})
  1605. if n.typ.kind == tyTypeDesc:
  1606. result = n.typ.base
  1607. # fix types constructed by macros/template:
  1608. if prev != nil and prev.kind != tyGenericBody and prev.sym != nil:
  1609. if result.sym.isNil:
  1610. # Behold! you're witnessing enormous power yielded
  1611. # by macros. Only macros can summon unnamed types
  1612. # and cast spell upon AST. Here we need to give
  1613. # it a name taken from left hand side's node
  1614. result.sym = prev.sym
  1615. result.sym.typ = result
  1616. else:
  1617. # Less powerful routine like template do not have
  1618. # the ability to produce unnamed types. But still
  1619. # it has wild power to push a type a bit too far.
  1620. # So we need to hold it back using alias and prevent
  1621. # unnecessary new type creation
  1622. let alias = maybeAliasType(c, result, prev)
  1623. if alias != nil: result = alias
  1624. elif n.typ.kind == tyFromExpr and c.inGenericContext > 0:
  1625. # sometimes not possible to distinguish type from value in generic body,
  1626. # for example `T.Foo`, so both are handled under `tyFromExpr`
  1627. result = n.typ
  1628. else:
  1629. localError(c.config, n.info, "expected type, but got: " & n.renderTree)
  1630. result = errorType(c)
  1631. proc freshType(c: PContext; res, prev: PType): PType {.inline.} =
  1632. if prev.isNil or prev.kind == tyGenericBody:
  1633. result = copyType(res, c.idgen, res.owner)
  1634. copyTypeProps(c.graph, c.idgen.module, result, res)
  1635. else:
  1636. result = res
  1637. template modifierTypeKindOfNode(n: PNode): TTypeKind =
  1638. case n.kind
  1639. of nkVarTy: tyVar
  1640. of nkRefTy: tyRef
  1641. of nkPtrTy: tyPtr
  1642. of nkStaticTy: tyStatic
  1643. of nkTypeOfExpr: tyTypeDesc
  1644. else: tyNone
  1645. proc semTypeClass(c: PContext, n: PNode, prev: PType): PType =
  1646. # if n.len == 0: return newConstraint(c, tyTypeClass)
  1647. if isNewStyleConcept(n):
  1648. result = newOrPrevType(tyConcept, prev, c)
  1649. result.flags.incl tfCheckedForDestructor
  1650. result.n = semConceptDeclaration(c, n)
  1651. return result
  1652. let
  1653. pragmas = n[1]
  1654. inherited = n[2]
  1655. var owner = getCurrOwner(c)
  1656. var candidateTypeSlot = newTypeS(tyAlias, c, c.errorType)
  1657. result = newOrPrevType(tyUserTypeClass, prev, c, son = candidateTypeSlot)
  1658. result.flags.incl tfCheckedForDestructor
  1659. result.n = n
  1660. if inherited.kind != nkEmpty:
  1661. for n in inherited.sons:
  1662. let typ = semTypeNode(c, n, nil)
  1663. result.add(typ)
  1664. openScope(c)
  1665. for param in n[0]:
  1666. var
  1667. dummyName: PNode
  1668. dummyType: PType
  1669. let modifier = param.modifierTypeKindOfNode
  1670. if modifier != tyNone:
  1671. dummyName = param[0]
  1672. dummyType = c.makeTypeWithModifier(modifier, candidateTypeSlot)
  1673. # if modifier == tyRef:
  1674. # dummyType.flags.incl tfNotNil
  1675. if modifier == tyTypeDesc:
  1676. dummyType.flags.incl tfConceptMatchedTypeSym
  1677. dummyType.flags.incl tfCheckedForDestructor
  1678. else:
  1679. dummyName = param
  1680. dummyType = candidateTypeSlot
  1681. # this can be true for 'nim check' on incomplete concepts,
  1682. # see bug #8230
  1683. if dummyName.kind == nkEmpty: continue
  1684. internalAssert c.config, dummyName.kind == nkIdent
  1685. var dummyParam = newSym(if modifier == tyTypeDesc: skType else: skVar,
  1686. dummyName.ident, c.idgen, owner, param.info)
  1687. dummyParam.typ = dummyType
  1688. incl dummyParam.flags, sfUsed
  1689. addDecl(c, dummyParam)
  1690. result.n[3] = semConceptBody(c, n[3])
  1691. closeScope(c)
  1692. proc applyTypeSectionPragmas(c: PContext; pragmas, operand: PNode): PNode =
  1693. result = nil
  1694. for p in pragmas:
  1695. let key = if p.kind in nkPragmaCallKinds and p.len >= 1: p[0] else: p
  1696. if p.kind == nkEmpty or whichPragma(p) != wInvalid:
  1697. discard "builtin pragma"
  1698. else:
  1699. trySuggestPragmas(c, key)
  1700. let ident =
  1701. if key.kind in nkIdentKinds:
  1702. considerQuotedIdent(c, key)
  1703. else:
  1704. nil
  1705. if ident != nil and strTableGet(c.userPragmas, ident) != nil:
  1706. discard "User-defined pragma"
  1707. else:
  1708. let sym = qualifiedLookUp(c, key, {})
  1709. # XXX: What to do here if amb is true?
  1710. if sym != nil and sfCustomPragma in sym.flags:
  1711. discard "Custom user pragma"
  1712. else:
  1713. # we transform ``(arg1, arg2: T) {.m, rest.}`` into ``m((arg1, arg2: T) {.rest.})`` and
  1714. # let the semantic checker deal with it:
  1715. var x = newNodeI(nkCall, key.info)
  1716. x.add(key)
  1717. if p.kind in nkPragmaCallKinds and p.len > 1:
  1718. # pass pragma arguments to the macro too:
  1719. for i in 1 ..< p.len:
  1720. x.add(p[i])
  1721. # Also pass the node the pragma has been applied to
  1722. x.add(operand.copyTreeWithoutNode(p))
  1723. # recursion assures that this works for multiple macro annotations too:
  1724. var r = semOverloadedCall(c, x, x, {skMacro, skTemplate}, {efNoUndeclared})
  1725. if r != nil:
  1726. doAssert r[0].kind == nkSym
  1727. let m = r[0].sym
  1728. case m.kind
  1729. of skMacro: return semMacroExpr(c, r, r, m, {efNoSemCheck})
  1730. of skTemplate: return semTemplateExpr(c, r, m, {efNoSemCheck})
  1731. else: doAssert(false, "cannot happen")
  1732. proc semProcTypeWithScope(c: PContext, n: PNode,
  1733. prev: PType, kind: TSymKind): PType =
  1734. checkSonsLen(n, 2, c.config)
  1735. if n[1].kind != nkEmpty and n[1].len > 0:
  1736. let macroEval = applyTypeSectionPragmas(c, n[1], n)
  1737. if macroEval != nil:
  1738. return semTypeNode(c, macroEval, prev)
  1739. openScope(c)
  1740. result = semProcTypeNode(c, n[0], nil, prev, kind, isType=true)
  1741. # start with 'ccClosure', but of course pragmas can overwrite this:
  1742. result.callConv = ccClosure
  1743. # dummy symbol for `pragma`:
  1744. var s = newSymS(kind, newIdentNode(getIdent(c.cache, "dummy"), n.info), c)
  1745. s.typ = result
  1746. if n[1].kind != nkEmpty and n[1].len > 0:
  1747. pragma(c, s, n[1], procTypePragmas)
  1748. when useEffectSystem: setEffectsForProcType(c.graph, result, n[1])
  1749. elif c.optionStack.len > 0:
  1750. # we construct a fake 'nkProcDef' for the 'mergePragmas' inside 'implicitPragmas'...
  1751. s.ast = newTree(nkProcDef, newNodeI(nkEmpty, n.info), newNodeI(nkEmpty, n.info),
  1752. newNodeI(nkEmpty, n.info), newNodeI(nkEmpty, n.info), newNodeI(nkEmpty, n.info))
  1753. implicitPragmas(c, s, n.info, {wTags, wRaises})
  1754. when useEffectSystem: setEffectsForProcType(c.graph, result, s.ast[pragmasPos])
  1755. closeScope(c)
  1756. proc symFromExpectedTypeNode(c: PContext, n: PNode): PSym =
  1757. if n.kind == nkType:
  1758. result = symFromType(c, n.typ, n.info)
  1759. else:
  1760. localError(c.config, n.info, errTypeExpected)
  1761. result = errorSym(c, n)
  1762. proc semStaticType(c: PContext, childNode: PNode, prev: PType): PType =
  1763. result = newOrPrevType(tyStatic, prev, c)
  1764. var base = semTypeNode(c, childNode, nil).skipTypes({tyTypeDesc, tyAlias})
  1765. result.rawAddSon(base)
  1766. result.flags.incl tfHasStatic
  1767. proc semTypeOf(c: PContext; n: PNode; prev: PType): PType =
  1768. openScope(c)
  1769. inc c.inTypeofContext
  1770. defer: dec c.inTypeofContext # compiles can raise an exception
  1771. let t = semExprWithType(c, n, {efInTypeof})
  1772. closeScope(c)
  1773. fixupTypeOf(c, prev, t)
  1774. result = t.typ
  1775. if result.kind == tyFromExpr:
  1776. result.flags.incl tfNonConstExpr
  1777. proc semTypeOf2(c: PContext; n: PNode; prev: PType): PType =
  1778. openScope(c)
  1779. var m = BiggestInt 1 # typeOfIter
  1780. if n.len == 3:
  1781. let mode = semConstExpr(c, n[2])
  1782. if mode.kind != nkIntLit:
  1783. localError(c.config, n.info, "typeof: cannot evaluate 'mode' parameter at compile-time")
  1784. else:
  1785. m = mode.intVal
  1786. inc c.inTypeofContext
  1787. defer: dec c.inTypeofContext # compiles can raise an exception
  1788. let t = semExprWithType(c, n[1], if m == 1: {efInTypeof} else: {})
  1789. closeScope(c)
  1790. fixupTypeOf(c, prev, t)
  1791. result = t.typ
  1792. if result.kind == tyFromExpr:
  1793. result.flags.incl tfNonConstExpr
  1794. proc semTypeIdent(c: PContext, n: PNode): PSym =
  1795. if n.kind == nkSym:
  1796. result = getGenSym(c, n.sym)
  1797. else:
  1798. result = pickSym(c, n, {skType, skGenericParam, skParam})
  1799. if result.isNil:
  1800. result = qualifiedLookUp(c, n, {checkAmbiguity, checkUndeclared})
  1801. if result != nil:
  1802. markUsed(c, n.info, result)
  1803. onUse(n.info, result)
  1804. # alias syntax, see semSym for skTemplate, skMacro
  1805. if result.kind in {skTemplate, skMacro} and sfNoalias notin result.flags:
  1806. let t = semTypeExpr(c, n, nil)
  1807. result = symFromType(c, t, n.info)
  1808. if result.kind == skParam and result.typ.kind == tyTypeDesc:
  1809. # This is a typedesc param. is it already bound?
  1810. # it's not bound when it's used multiple times in the
  1811. # proc signature for example
  1812. if c.inGenericInst > 0:
  1813. let bound = result.typ.elementType.sym
  1814. if bound != nil: return bound
  1815. return result
  1816. if result.typ.sym == nil:
  1817. localError(c.config, n.info, errTypeExpected)
  1818. return errorSym(c, n)
  1819. result = result.typ.sym.copySym(c.idgen)
  1820. result.typ = exactReplica(result.typ)
  1821. result.typ.flags.incl tfUnresolved
  1822. if result.kind == skGenericParam:
  1823. if result.typ.kind == tyGenericParam and result.typ.len == 0 and
  1824. tfWildcard in result.typ.flags:
  1825. # collapse the wild-card param to a type
  1826. result.transitionGenericParamToType()
  1827. result.typ.flags.excl tfWildcard
  1828. return
  1829. else:
  1830. localError(c.config, n.info, errTypeExpected)
  1831. return errorSym(c, n)
  1832. if result.kind != skType and result.magic notin {mStatic, mType, mTypeOf}:
  1833. # this implements the wanted ``var v: V, x: V`` feature ...
  1834. var ov: TOverloadIter = default(TOverloadIter)
  1835. var amb = initOverloadIter(ov, c, n)
  1836. while amb != nil and amb.kind != skType:
  1837. amb = nextOverloadIter(ov, c, n)
  1838. if amb != nil: result = amb
  1839. else:
  1840. if result.kind != skError: localError(c.config, n.info, errTypeExpected)
  1841. return errorSym(c, n)
  1842. if result.typ.kind != tyGenericParam:
  1843. # XXX get rid of this hack!
  1844. var oldInfo = n.info
  1845. when defined(useNodeIds):
  1846. let oldId = n.id
  1847. reset(n[])
  1848. when defined(useNodeIds):
  1849. n.id = oldId
  1850. n.transitionNoneToSym()
  1851. n.sym = result
  1852. n.info = oldInfo
  1853. n.typ() = result.typ
  1854. else:
  1855. localError(c.config, n.info, "identifier expected")
  1856. result = errorSym(c, n)
  1857. proc semTypeNode(c: PContext, n: PNode, prev: PType): PType =
  1858. result = nil
  1859. inc c.inTypeContext
  1860. if c.config.cmd == cmdIdeTools: suggestExpr(c, n)
  1861. case n.kind
  1862. of nkEmpty: result = n.typ
  1863. of nkTypeOfExpr:
  1864. # for ``typeof(countup(1,3))``, see ``tests/ttoseq``.
  1865. checkSonsLen(n, 1, c.config)
  1866. result = semTypeOf(c, n[0], prev)
  1867. if result.kind == tyTypeDesc: result.flags.incl tfExplicit
  1868. of nkPar:
  1869. if n.len == 1: result = semTypeNode(c, n[0], prev)
  1870. else:
  1871. result = semAnonTuple(c, n, prev)
  1872. of nkTupleConstr: result = semAnonTuple(c, n, prev)
  1873. of nkCallKinds:
  1874. let x = n[0]
  1875. let ident = x.getPIdent
  1876. if ident != nil and ident.s == "[]":
  1877. let b = newNodeI(nkBracketExpr, n.info)
  1878. for i in 1..<n.len: b.add(n[i])
  1879. result = semTypeNode(c, b, prev)
  1880. elif ident != nil and ident.id == ord(wDotDot):
  1881. result = semRangeAux(c, n, prev)
  1882. elif n[0].kind == nkNilLit and n.len == 2:
  1883. result = semTypeNode(c, n[1], prev)
  1884. if result.skipTypes({tyGenericInst, tyAlias, tySink, tyOwned}).kind in NilableTypes+GenericTypes:
  1885. if tfNotNil in result.flags:
  1886. result = freshType(c, result, prev)
  1887. result.flags.excl(tfNotNil)
  1888. else:
  1889. localError(c.config, n.info, errGenerated, "invalid type")
  1890. elif n[0].kind notin nkIdentKinds:
  1891. result = semTypeExpr(c, n, prev)
  1892. else:
  1893. let op = considerQuotedIdent(c, n[0])
  1894. if op.id == ord(wAnd) or op.id == ord(wOr) or op.s == "|":
  1895. checkSonsLen(n, 3, c.config)
  1896. var
  1897. t1 = semTypeNode(c, n[1], nil)
  1898. t2 = semTypeNode(c, n[2], nil)
  1899. if t1 == nil:
  1900. localError(c.config, n[1].info, errTypeExpected)
  1901. result = newOrPrevType(tyError, prev, c)
  1902. elif t2 == nil:
  1903. localError(c.config, n[2].info, errTypeExpected)
  1904. result = newOrPrevType(tyError, prev, c)
  1905. else:
  1906. result = if op.id == ord(wAnd): makeAndType(c, t1, t2)
  1907. else: makeOrType(c, t1, t2)
  1908. elif op.id == ord(wNot):
  1909. case n.len
  1910. of 3:
  1911. result = semTypeNode(c, n[1], prev)
  1912. if result.kind == tyTypeDesc and tfUnresolved notin result.flags:
  1913. result = result.base
  1914. if n[2].kind != nkNilLit:
  1915. localError(c.config, n.info,
  1916. "Invalid syntax. When used with a type, 'not' can be followed only by 'nil'")
  1917. if notnil notin c.features and strictNotNil notin c.features:
  1918. localError(c.config, n.info,
  1919. "enable the 'not nil' annotation with {.experimental: \"notnil\".} or " &
  1920. " the `strict not nil` annotation with {.experimental: \"strictNotNil\".} " &
  1921. " the \"notnil\" one is going to be deprecated, so please use \"strictNotNil\"")
  1922. let resolvedType = result.skipTypes({tyGenericInst, tyAlias, tySink, tyOwned})
  1923. case resolvedType.kind
  1924. of tyGenericParam, tyTypeDesc, tyFromExpr:
  1925. # XXX: This is a really inappropraite hack, but it solves
  1926. # https://github.com/nim-lang/Nim/issues/4907 for now.
  1927. #
  1928. # A proper solution is to introduce a new type kind such
  1929. # as `tyNotNil[tyRef[SomeGenericParam]]`. This will allow
  1930. # semtypinst to replace the generic param correctly in
  1931. # situations like the following:
  1932. #
  1933. # type Foo[T] = object
  1934. # bar: ref T not nil
  1935. # baz: ref T
  1936. #
  1937. # The root of the problem is that `T` here must have a specific
  1938. # ID that is bound to a concrete type during instantiation.
  1939. # The use of `freshType` below breaks this. Another hack would
  1940. # be to reuse the same ID for the not nil type, but this will
  1941. # fail if the `T` parameter is referenced multiple times as in
  1942. # the example above.
  1943. #
  1944. # I suggest revisiting this once the language decides on whether
  1945. # `not nil` should be the default. We can then map nilable refs
  1946. # to other types such as `Option[T]`.
  1947. result = makeTypeFromExpr(c, newTree(nkStmtListType, n.copyTree))
  1948. of NilableTypes + {tyGenericInvocation, tyForward}:
  1949. result = freshType(c, result, prev)
  1950. result.flags.incl(tfNotNil)
  1951. else:
  1952. localError(c.config, n.info, errGenerated, "invalid type")
  1953. of 2:
  1954. let negated = semTypeNode(c, n[1], prev)
  1955. result = makeNotType(c, negated)
  1956. else:
  1957. localError(c.config, n.info, errGenerated, "invalid type")
  1958. elif op.id == ord(wPtr):
  1959. result = semAnyRef(c, n, tyPtr, prev)
  1960. elif op.id == ord(wRef):
  1961. result = semAnyRef(c, n, tyRef, prev)
  1962. elif op.id == ord(wType):
  1963. checkSonsLen(n, 2, c.config)
  1964. result = semTypeOf(c, n[1], prev)
  1965. elif op.s == "typeof" and (
  1966. (n[0].kind == nkSym and n[0].sym.magic == mTypeOf) or
  1967. (n[0].kind == nkOpenSym and n[0][0].sym.magic == mTypeOf)):
  1968. result = semTypeOf2(c, n, prev)
  1969. elif op.s == "owned" and optOwnedRefs notin c.config.globalOptions and n.len == 2:
  1970. result = semTypeExpr(c, n[1], prev)
  1971. else:
  1972. result = semTypeExpr(c, n, prev)
  1973. of nkWhenStmt:
  1974. var whenResult = semWhen(c, n, false)
  1975. if whenResult.kind == nkStmtList: whenResult.transitionSonsKind(nkStmtListType)
  1976. if whenResult.kind == nkWhenStmt:
  1977. result = whenResult.typ
  1978. else:
  1979. result = semTypeNode(c, whenResult, prev)
  1980. of nkBracketExpr:
  1981. checkMinSonsLen(n, 2, c.config)
  1982. var head = n[0]
  1983. var s = if head.kind notin nkCallKinds: semTypeIdent(c, head)
  1984. else: symFromExpectedTypeNode(c, semExpr(c, head))
  1985. case s.magic
  1986. of mArray: result = semArray(c, n, prev)
  1987. of mOpenArray: result = semContainer(c, n, tyOpenArray, "openarray", prev)
  1988. of mUncheckedArray: result = semContainer(c, n, tyUncheckedArray, "UncheckedArray", prev)
  1989. of mRange: result = semRange(c, n, prev)
  1990. of mSet: result = semSet(c, n, prev)
  1991. of mOrdinal: result = semOrdinal(c, n, prev)
  1992. of mIterableType: result = semIterableType(c, n, prev)
  1993. of mSeq:
  1994. result = semContainer(c, n, tySequence, "seq", prev)
  1995. if optSeqDestructors in c.config.globalOptions:
  1996. incl result.flags, tfHasAsgn
  1997. of mVarargs: result = semVarargs(c, n, prev)
  1998. of mTypeDesc, mType, mTypeOf:
  1999. result = makeTypeDesc(c, semTypeNode(c, n[1], nil))
  2000. result.flags.incl tfExplicit
  2001. of mStatic:
  2002. result = semStaticType(c, n[1], prev)
  2003. of mExpr:
  2004. result = semTypeNode(c, n[0], nil)
  2005. if result != nil:
  2006. let old = result
  2007. result = copyType(result, c.idgen, getCurrOwner(c))
  2008. copyTypeProps(c.graph, c.idgen.module, result, old)
  2009. for i in 1..<n.len:
  2010. result.rawAddSon(semTypeNode(c, n[i], nil))
  2011. of mDistinct:
  2012. result = newOrPrevType(tyDistinct, prev, c)
  2013. addSonSkipIntLit(result, semTypeNode(c, n[1], nil), c.idgen)
  2014. of mVar:
  2015. result = newOrPrevType(tyVar, prev, c)
  2016. var base = semTypeNode(c, n[1], nil)
  2017. if base.kind in {tyVar, tyLent}:
  2018. localError(c.config, n.info, "type 'var var' is not allowed")
  2019. base = base[0]
  2020. addSonSkipIntLit(result, base, c.idgen)
  2021. of mRef: result = semAnyRef(c, n, tyRef, prev)
  2022. of mPtr: result = semAnyRef(c, n, tyPtr, prev)
  2023. of mTuple: result = semTuple(c, n, prev)
  2024. of mBuiltinType:
  2025. case s.name.s
  2026. of "lent": result = semAnyRef(c, n, tyLent, prev)
  2027. of "sink": result = semAnyRef(c, n, tySink, prev)
  2028. of "owned": result = semAnyRef(c, n, tyOwned, prev)
  2029. else: result = semGeneric(c, n, s, prev)
  2030. else: result = semGeneric(c, n, s, prev)
  2031. of nkDotExpr:
  2032. let typeExpr = semExpr(c, n)
  2033. if typeExpr.typ.isNil:
  2034. localError(c.config, n.info, "object constructor needs an object type;" &
  2035. " for named arguments use '=' instead of ':'")
  2036. result = errorType(c)
  2037. elif typeExpr.typ.kind == tyFromExpr:
  2038. result = typeExpr.typ
  2039. elif typeExpr.typ.kind != tyTypeDesc:
  2040. localError(c.config, n.info, errTypeExpected)
  2041. result = errorType(c)
  2042. else:
  2043. result = typeExpr.typ.base
  2044. if result.isMetaType and
  2045. result.kind != tyUserTypeClass:
  2046. # the dot expression may refer to a concept type in
  2047. # a different module. allow a normal alias then.
  2048. let preprocessed = semGenericStmt(c, n)
  2049. result = makeTypeFromExpr(c, preprocessed.copyTree)
  2050. else:
  2051. let alias = maybeAliasType(c, result, prev)
  2052. if alias != nil: result = alias
  2053. of nkIdent, nkAccQuoted:
  2054. var s = semTypeIdent(c, n)
  2055. if s.typ == nil:
  2056. if s.kind != skError: localError(c.config, n.info, errTypeExpected)
  2057. result = newOrPrevType(tyError, prev, c)
  2058. elif s.kind == skParam and s.typ.kind == tyTypeDesc:
  2059. internalAssert c.config, s.typ.base.kind != tyNone
  2060. result = s.typ.base
  2061. elif prev == nil:
  2062. result = s.typ
  2063. else:
  2064. let alias = maybeAliasType(c, s.typ, prev)
  2065. if alias != nil:
  2066. result = alias
  2067. elif prev.kind == tyGenericBody:
  2068. result = s.typ
  2069. else:
  2070. assignType(prev, s.typ)
  2071. # bugfix: keep the fresh id for aliases to integral types:
  2072. if s.typ.kind notin {tyBool, tyChar, tyInt..tyInt64, tyFloat..tyFloat128,
  2073. tyUInt..tyUInt64}:
  2074. prev.itemId = s.typ.itemId
  2075. result = prev
  2076. of nkSym:
  2077. let s = getGenSym(c, n.sym)
  2078. if s.typ != nil and (s.kind == skType or s.typ.kind == tyTypeDesc):
  2079. var t =
  2080. if s.kind == skType:
  2081. s.typ
  2082. else:
  2083. internalAssert c.config, s.typ.base.kind != tyNone
  2084. s.typ.base
  2085. let alias = maybeAliasType(c, t, prev)
  2086. if alias != nil:
  2087. result = alias
  2088. elif prev == nil or prev.kind == tyGenericBody:
  2089. result = t
  2090. else:
  2091. assignType(prev, t)
  2092. result = prev
  2093. markUsed(c, n.info, n.sym)
  2094. onUse(n.info, n.sym)
  2095. else:
  2096. if s.kind != skError:
  2097. if s.typ == nil:
  2098. localError(c.config, n.info, "type expected, but symbol '$1' has no type." % [s.name.s])
  2099. else:
  2100. localError(c.config, n.info, "type expected, but got symbol '$1' of kind '$2'" %
  2101. [s.name.s, s.kind.toHumanStr])
  2102. result = newOrPrevType(tyError, prev, c)
  2103. of nkObjectTy: result = semObjectNode(c, n, prev, {})
  2104. of nkTupleTy: result = semTuple(c, n, prev)
  2105. of nkTupleClassTy: result = newConstraint(c, tyTuple)
  2106. of nkTypeClassTy: result = semTypeClass(c, n, prev)
  2107. of nkRefTy: result = semAnyRef(c, n, tyRef, prev)
  2108. of nkPtrTy: result = semAnyRef(c, n, tyPtr, prev)
  2109. of nkVarTy: result = semVarOutType(c, n, prev, {})
  2110. of nkOutTy: result = semVarOutType(c, n, prev, {tfIsOutParam})
  2111. of nkDistinctTy: result = semDistinct(c, n, prev)
  2112. of nkStaticTy: result = semStaticType(c, n[0], prev)
  2113. of nkProcTy, nkIteratorTy:
  2114. if n.len == 0 or n[0].kind == nkEmpty:
  2115. # 0 length or empty param list with possible pragmas imply typeclass
  2116. result = newTypeS(tyBuiltInTypeClass, c)
  2117. let child = newTypeS(tyProc, c)
  2118. if n.kind == nkIteratorTy:
  2119. child.flags.incl tfIterator
  2120. if n.len > 0 and n[1].kind != nkEmpty and n[1].len > 0:
  2121. # typeclass with pragma
  2122. let symKind = if n.kind == nkIteratorTy: skIterator else: skProc
  2123. # dummy symbol for `pragma`:
  2124. var s = newSymS(symKind, newIdentNode(getIdent(c.cache, "dummy"), n.info), c)
  2125. s.typ = child
  2126. # for now only call convention pragmas supported in proc typeclass
  2127. pragma(c, s, n[1], {FirstCallConv..LastCallConv})
  2128. result.addSonSkipIntLit(child, c.idgen)
  2129. else:
  2130. let symKind = if n.kind == nkIteratorTy: skIterator else: skProc
  2131. result = semProcTypeWithScope(c, n, prev, symKind)
  2132. if result == nil:
  2133. localError(c.config, n.info, "type expected, but got: " & renderTree(n))
  2134. result = newOrPrevType(tyError, prev, c)
  2135. if n.kind == nkIteratorTy and result.kind == tyProc:
  2136. result.flags.incl(tfIterator)
  2137. if result.callConv == ccClosure and c.config.selectedGC in {gcArc, gcOrc, gcAtomicArc}:
  2138. result.flags.incl tfHasAsgn
  2139. of nkEnumTy: result = semEnum(c, n, prev)
  2140. of nkType: result = n.typ
  2141. of nkStmtListType: result = semStmtListType(c, n, prev)
  2142. of nkBlockType: result = semBlockType(c, n, prev)
  2143. of nkOpenSym: result = semTypeNode(c, n[0], prev)
  2144. else:
  2145. result = semTypeExpr(c, n, prev)
  2146. when false:
  2147. localError(c.config, n.info, "type expected, but got: " & renderTree(n))
  2148. result = newOrPrevType(tyError, prev, c)
  2149. n.typ() = result
  2150. dec c.inTypeContext
  2151. proc setMagicType(conf: ConfigRef; m: PSym, kind: TTypeKind, size: int) =
  2152. # source : https://en.wikipedia.org/wiki/Data_structure_alignment#x86
  2153. m.typ.kind = kind
  2154. m.typ.size = size
  2155. # this usually works for most basic types
  2156. # Assuming that since ARM, ARM64 don't support unaligned access
  2157. # data is aligned to type size
  2158. m.typ.align = size.int16
  2159. # FIXME: proper support for clongdouble should be added.
  2160. # long double size can be 8, 10, 12, 16 bytes depending on platform & compiler
  2161. if kind in {tyFloat64, tyFloat, tyInt, tyUInt, tyInt64, tyUInt64} and size == 8:
  2162. m.typ.align = int16(conf.floatInt64Align)
  2163. proc setMagicIntegral(conf: ConfigRef; m: PSym, kind: TTypeKind, size: int) =
  2164. setMagicType(conf, m, kind, size)
  2165. incl m.typ.flags, tfCheckedForDestructor
  2166. proc processMagicType(c: PContext, m: PSym) =
  2167. case m.magic
  2168. of mInt: setMagicIntegral(c.config, m, tyInt, c.config.target.intSize)
  2169. of mInt8: setMagicIntegral(c.config, m, tyInt8, 1)
  2170. of mInt16: setMagicIntegral(c.config, m, tyInt16, 2)
  2171. of mInt32: setMagicIntegral(c.config, m, tyInt32, 4)
  2172. of mInt64: setMagicIntegral(c.config, m, tyInt64, 8)
  2173. of mUInt: setMagicIntegral(c.config, m, tyUInt, c.config.target.intSize)
  2174. of mUInt8: setMagicIntegral(c.config, m, tyUInt8, 1)
  2175. of mUInt16: setMagicIntegral(c.config, m, tyUInt16, 2)
  2176. of mUInt32: setMagicIntegral(c.config, m, tyUInt32, 4)
  2177. of mUInt64: setMagicIntegral(c.config, m, tyUInt64, 8)
  2178. of mFloat: setMagicIntegral(c.config, m, tyFloat, c.config.target.floatSize)
  2179. of mFloat32: setMagicIntegral(c.config, m, tyFloat32, 4)
  2180. of mFloat64: setMagicIntegral(c.config, m, tyFloat64, 8)
  2181. of mFloat128: setMagicIntegral(c.config, m, tyFloat128, 16)
  2182. of mBool: setMagicIntegral(c.config, m, tyBool, 1)
  2183. of mChar: setMagicIntegral(c.config, m, tyChar, 1)
  2184. of mString:
  2185. setMagicType(c.config, m, tyString, szUncomputedSize)
  2186. rawAddSon(m.typ, getSysType(c.graph, m.info, tyChar))
  2187. if optSeqDestructors in c.config.globalOptions:
  2188. incl m.typ.flags, tfHasAsgn
  2189. of mCstring:
  2190. setMagicIntegral(c.config, m, tyCstring, c.config.target.ptrSize)
  2191. rawAddSon(m.typ, getSysType(c.graph, m.info, tyChar))
  2192. of mPointer: setMagicIntegral(c.config, m, tyPointer, c.config.target.ptrSize)
  2193. of mNil: setMagicType(c.config, m, tyNil, c.config.target.ptrSize)
  2194. of mExpr:
  2195. if m.name.s == "auto":
  2196. setMagicIntegral(c.config, m, tyAnything, 0)
  2197. else:
  2198. setMagicIntegral(c.config, m, tyUntyped, 0)
  2199. of mStmt:
  2200. setMagicIntegral(c.config, m, tyTyped, 0)
  2201. of mTypeDesc, mType:
  2202. setMagicIntegral(c.config, m, tyTypeDesc, 0)
  2203. rawAddSon(m.typ, newTypeS(tyNone, c))
  2204. of mStatic:
  2205. setMagicType(c.config, m, tyStatic, 0)
  2206. rawAddSon(m.typ, newTypeS(tyNone, c))
  2207. of mVoidType:
  2208. setMagicIntegral(c.config, m, tyVoid, 0)
  2209. of mArray:
  2210. setMagicType(c.config, m, tyArray, szUncomputedSize)
  2211. of mOpenArray:
  2212. setMagicType(c.config, m, tyOpenArray, szUncomputedSize)
  2213. of mVarargs:
  2214. setMagicType(c.config, m, tyVarargs, szUncomputedSize)
  2215. of mRange:
  2216. setMagicIntegral(c.config, m, tyRange, szUncomputedSize)
  2217. rawAddSon(m.typ, newTypeS(tyNone, c))
  2218. of mSet:
  2219. setMagicIntegral(c.config, m, tySet, szUncomputedSize)
  2220. of mUncheckedArray:
  2221. setMagicIntegral(c.config, m, tyUncheckedArray, szUncomputedSize)
  2222. of mSeq:
  2223. setMagicType(c.config, m, tySequence, szUncomputedSize)
  2224. if optSeqDestructors in c.config.globalOptions:
  2225. incl m.typ.flags, tfHasAsgn
  2226. if defined(nimsuggest) or c.config.cmd == cmdCheck: # bug #18985
  2227. discard
  2228. else:
  2229. assert c.graph.sysTypes[tySequence] == nil
  2230. c.graph.sysTypes[tySequence] = m.typ
  2231. of mOrdinal:
  2232. setMagicIntegral(c.config, m, tyOrdinal, szUncomputedSize)
  2233. rawAddSon(m.typ, newTypeS(tyNone, c))
  2234. of mIterableType:
  2235. setMagicIntegral(c.config, m, tyIterable, 0)
  2236. rawAddSon(m.typ, newTypeS(tyNone, c))
  2237. of mPNimrodNode:
  2238. incl m.typ.flags, tfTriggersCompileTime
  2239. incl m.typ.flags, tfCheckedForDestructor
  2240. of mException: discard
  2241. of mBuiltinType:
  2242. case m.name.s
  2243. of "lent": setMagicType(c.config, m, tyLent, c.config.target.ptrSize)
  2244. of "sink": setMagicType(c.config, m, tySink, szUncomputedSize)
  2245. of "owned":
  2246. setMagicType(c.config, m, tyOwned, c.config.target.ptrSize)
  2247. incl m.typ.flags, tfHasOwned
  2248. else: localError(c.config, m.info, errTypeExpected)
  2249. else: localError(c.config, m.info, errTypeExpected)
  2250. proc semGenericConstraints(c: PContext, x: PType): PType =
  2251. result = newTypeS(tyGenericParam, c, x)
  2252. proc semGenericParamList(c: PContext, n: PNode, father: PType = nil): PNode =
  2253. template addSym(result: PNode, s: PSym): untyped =
  2254. if father != nil: addSonSkipIntLit(father, s.typ, c.idgen)
  2255. if sfGenSym notin s.flags: addDecl(c, s)
  2256. result.add newSymNode(s)
  2257. result = copyNode(n)
  2258. if n.kind != nkGenericParams:
  2259. illFormedAst(n, c.config)
  2260. return
  2261. for i in 0..<n.len:
  2262. var a = n[i]
  2263. case a.kind
  2264. of nkSym: result.addSym(a.sym)
  2265. of nkIdentDefs:
  2266. var def = a[^1]
  2267. let constraint = a[^2]
  2268. var typ: PType = nil
  2269. if constraint.kind != nkEmpty:
  2270. typ = semTypeNode(c, constraint, nil)
  2271. if typ.kind != tyStatic or typ.len == 0:
  2272. if typ.kind == tyTypeDesc:
  2273. if typ.elementType.kind == tyNone:
  2274. typ = newTypeS(tyTypeDesc, c, newTypeS(tyNone, c))
  2275. incl typ.flags, tfCheckedForDestructor
  2276. else:
  2277. typ = semGenericConstraints(c, typ)
  2278. if def.kind != nkEmpty:
  2279. def = semConstExpr(c, def)
  2280. if typ == nil:
  2281. if def.typ.kind != tyTypeDesc:
  2282. typ = newTypeS(tyStatic, c, def.typ)
  2283. else:
  2284. # the following line fixes ``TV2*[T:SomeNumber=TR] = array[0..1, T]``
  2285. # from manyloc/named_argument_bug/triengine:
  2286. def.typ() = def.typ.skipTypes({tyTypeDesc})
  2287. if not containsGenericType(def.typ):
  2288. def = fitNode(c, typ, def, def.info)
  2289. if typ == nil:
  2290. typ = newTypeS(tyGenericParam, c)
  2291. if father == nil: typ.flags.incl tfWildcard
  2292. typ.flags.incl tfGenericTypeParam
  2293. for j in 0..<a.len-2:
  2294. var finalType: PType
  2295. if j == 0:
  2296. finalType = typ
  2297. else:
  2298. finalType = copyType(typ, c.idgen, typ.owner)
  2299. copyTypeProps(c.graph, c.idgen.module, finalType, typ)
  2300. # it's important the we create an unique
  2301. # type for each generic param. the index
  2302. # of the parameter will be stored in the
  2303. # attached symbol.
  2304. var paramName = a[j]
  2305. var covarianceFlag = tfUnresolved
  2306. if paramName.safeLen == 2:
  2307. if not nimEnableCovariance or paramName[0].ident.s == "in":
  2308. if father == nil or sfImportc notin father.sym.flags:
  2309. localError(c.config, paramName.info, errInOutFlagNotExtern % $paramName[0])
  2310. covarianceFlag = if paramName[0].ident.s == "in": tfContravariant
  2311. else: tfCovariant
  2312. if father != nil: father.flags.incl tfCovariant
  2313. paramName = paramName[1]
  2314. var s = if finalType.kind == tyStatic or tfWildcard in typ.flags:
  2315. newSymG(skGenericParam, paramName, c).linkTo(finalType)
  2316. else:
  2317. newSymG(skType, paramName, c).linkTo(finalType)
  2318. if covarianceFlag != tfUnresolved: s.typ.flags.incl(covarianceFlag)
  2319. if def.kind != nkEmpty: s.ast = def
  2320. s.position = result.len
  2321. result.addSym(s)
  2322. else:
  2323. illFormedAst(n, c.config)