implements multi-line-comments; pounds are stripped from the doc comments
This commit is contained in:
parent
2910096cce
commit
2e71bd50b2
7 changed files with 137 additions and 37 deletions
|
|
@ -149,10 +149,10 @@ proc ropeFormatNamedVars(frmt: FormatStr, varnames: openArray[string],
|
||||||
proc genComment(d: PDoc, n: PNode): string =
|
proc genComment(d: PDoc, n: PNode): string =
|
||||||
result = ""
|
result = ""
|
||||||
var dummyHasToc: bool
|
var dummyHasToc: bool
|
||||||
if n.comment != nil and startsWith(n.comment, "##"):
|
if n.comment != nil:
|
||||||
renderRstToOut(d[], parseRst(n.comment, toFilename(n.info),
|
renderRstToOut(d[], parseRst(n.comment, toFilename(n.info),
|
||||||
toLinenumber(n.info), toColumn(n.info),
|
toLinenumber(n.info), toColumn(n.info),
|
||||||
dummyHasToc, d.options + {roSkipPounds}), result)
|
dummyHasToc, d.options), result)
|
||||||
|
|
||||||
proc genRecComment(d: PDoc, n: PNode): Rope =
|
proc genRecComment(d: PDoc, n: PNode): Rope =
|
||||||
if n == nil: return nil
|
if n == nil: return nil
|
||||||
|
|
|
||||||
|
|
@ -769,24 +769,78 @@ proc getOperator(L: var TLexer, tok: var TToken) =
|
||||||
if buf[pos] in {CR, LF, nimlexbase.EndOfFile}:
|
if buf[pos] in {CR, LF, nimlexbase.EndOfFile}:
|
||||||
tok.strongSpaceB = -1
|
tok.strongSpaceB = -1
|
||||||
|
|
||||||
|
proc skipMultiLineComment(L: var TLexer; tok: var TToken; start: int;
|
||||||
|
isDoc: bool) =
|
||||||
|
var pos = start
|
||||||
|
var buf = L.buf
|
||||||
|
while buf[pos] == '[':
|
||||||
|
inc pos
|
||||||
|
let brackets = pos - start
|
||||||
|
var toStrip = 0
|
||||||
|
# detect the amount of indentation:
|
||||||
|
if isDoc:
|
||||||
|
toStrip = getColNumber(L, pos)
|
||||||
|
while buf[pos] == ' ': inc pos
|
||||||
|
if buf[pos] in {CR, LF}:
|
||||||
|
pos = handleCRLF(L, pos)
|
||||||
|
buf = L.buf
|
||||||
|
toStrip = 0
|
||||||
|
while buf[pos] == ' ':
|
||||||
|
inc pos
|
||||||
|
inc toStrip
|
||||||
|
while true:
|
||||||
|
case buf[pos]
|
||||||
|
of ']':
|
||||||
|
var p = pos
|
||||||
|
while buf[p] == ']':
|
||||||
|
inc p
|
||||||
|
if p-pos == brackets:
|
||||||
|
pos = p
|
||||||
|
break
|
||||||
|
else:
|
||||||
|
if isDoc: tok.literal.add ']'
|
||||||
|
inc pos
|
||||||
|
of '\t':
|
||||||
|
lexMessagePos(L, errTabulatorsAreNotAllowed, pos)
|
||||||
|
inc(pos)
|
||||||
|
if isDoc: tok.literal.add '\t'
|
||||||
|
of CR, LF:
|
||||||
|
pos = handleCRLF(L, pos)
|
||||||
|
buf = L.buf
|
||||||
|
# strip leading whitespace:
|
||||||
|
if isDoc:
|
||||||
|
tok.literal.add "\n"
|
||||||
|
inc tok.iNumber
|
||||||
|
var c = toStrip
|
||||||
|
while buf[pos] == ' ' and c > 0:
|
||||||
|
inc pos
|
||||||
|
dec c
|
||||||
|
of nimlexbase.EndOfFile:
|
||||||
|
lexMessagePos(L, errGenerated, pos, "end of multiline comment expected")
|
||||||
|
break
|
||||||
|
else:
|
||||||
|
if isDoc: tok.literal.add buf[pos]
|
||||||
|
inc(pos)
|
||||||
|
L.bufpos = pos
|
||||||
|
|
||||||
proc scanComment(L: var TLexer, tok: var TToken) =
|
proc scanComment(L: var TLexer, tok: var TToken) =
|
||||||
var pos = L.bufpos
|
var pos = L.bufpos
|
||||||
var buf = L.buf
|
var buf = L.buf
|
||||||
when not defined(nimfix):
|
|
||||||
assert buf[pos+1] == '#'
|
|
||||||
if buf[pos+2] == '[':
|
|
||||||
if buf[pos+3] == ']':
|
|
||||||
# ##[] is the (rather complex) "cursor token" for idetools
|
|
||||||
tok.tokType = tkComment
|
|
||||||
tok.literal = "[]"
|
|
||||||
inc(L.bufpos, 4)
|
|
||||||
return
|
|
||||||
else:
|
|
||||||
lexMessagePos(L, warnDeprecated, pos, "use '## [' instead; '##['")
|
|
||||||
|
|
||||||
tok.tokType = tkComment
|
tok.tokType = tkComment
|
||||||
# iNumber contains the number of '\n' in the token
|
# iNumber contains the number of '\n' in the token
|
||||||
tok.iNumber = 0
|
tok.iNumber = 0
|
||||||
|
when not defined(nimfix):
|
||||||
|
assert buf[pos+1] == '#'
|
||||||
|
if buf[pos+2] == '[':
|
||||||
|
skipMultiLineComment(L, tok, pos+2, true)
|
||||||
|
return
|
||||||
|
inc(pos, 2)
|
||||||
|
|
||||||
|
var toStrip = 0
|
||||||
|
while buf[pos] == ' ':
|
||||||
|
inc pos
|
||||||
|
inc toStrip
|
||||||
|
|
||||||
when defined(nimfix):
|
when defined(nimfix):
|
||||||
var col = getColNumber(L, pos)
|
var col = getColNumber(L, pos)
|
||||||
while true:
|
while true:
|
||||||
|
|
@ -820,6 +874,12 @@ proc scanComment(L: var TLexer, tok: var TToken) =
|
||||||
if doContinue():
|
if doContinue():
|
||||||
tok.literal.add "\n"
|
tok.literal.add "\n"
|
||||||
when defined(nimfix): col = indent
|
when defined(nimfix): col = indent
|
||||||
|
else:
|
||||||
|
inc(pos, 2)
|
||||||
|
var c = toStrip
|
||||||
|
while buf[pos] == ' ' and c > 0:
|
||||||
|
inc pos
|
||||||
|
dec c
|
||||||
inc tok.iNumber
|
inc tok.iNumber
|
||||||
else:
|
else:
|
||||||
if buf[pos] > ' ':
|
if buf[pos] > ' ':
|
||||||
|
|
@ -863,7 +923,8 @@ proc skip(L: var TLexer, tok: var TToken) =
|
||||||
# do not skip documentation comment:
|
# do not skip documentation comment:
|
||||||
if buf[pos+1] == '#': break
|
if buf[pos+1] == '#': break
|
||||||
if buf[pos+1] == '[':
|
if buf[pos+1] == '[':
|
||||||
lexMessagePos(L, warnDeprecated, pos, "use '# [' instead; '#['")
|
skipMultiLineComment(L, tok, pos+1, false)
|
||||||
|
return
|
||||||
while buf[pos] notin {CR, LF, nimlexbase.EndOfFile}: inc(pos)
|
while buf[pos] notin {CR, LF, nimlexbase.EndOfFile}: inc(pos)
|
||||||
else:
|
else:
|
||||||
break # EndOfFile also leaves the loop
|
break # EndOfFile also leaves the loop
|
||||||
|
|
|
||||||
|
|
@ -112,12 +112,7 @@ proc rawSkipComment(p: var TParser, node: PNode) =
|
||||||
if p.tok.tokType == tkComment:
|
if p.tok.tokType == tkComment:
|
||||||
if node != nil:
|
if node != nil:
|
||||||
if node.comment == nil: node.comment = ""
|
if node.comment == nil: node.comment = ""
|
||||||
if p.tok.literal == "[]":
|
add(node.comment, p.tok.literal)
|
||||||
node.flags.incl nfIsCursor
|
|
||||||
#echo "parser: "
|
|
||||||
#debug node
|
|
||||||
else:
|
|
||||||
add(node.comment, p.tok.literal)
|
|
||||||
else:
|
else:
|
||||||
parMessage(p, errInternal, "skipComment")
|
parMessage(p, errInternal, "skipComment")
|
||||||
getTok(p)
|
getTok(p)
|
||||||
|
|
|
||||||
|
|
@ -167,33 +167,24 @@ proc makeNimString(s: string): string =
|
||||||
proc putComment(g: var TSrcGen, s: string) =
|
proc putComment(g: var TSrcGen, s: string) =
|
||||||
if s.isNil: return
|
if s.isNil: return
|
||||||
var i = 0
|
var i = 0
|
||||||
var comIndent = 1
|
|
||||||
var isCode = (len(s) >= 2) and (s[1] != ' ')
|
var isCode = (len(s) >= 2) and (s[1] != ' ')
|
||||||
var ind = g.lineLen
|
var ind = g.lineLen
|
||||||
var com = ""
|
var com = "## "
|
||||||
while true:
|
while true:
|
||||||
case s[i]
|
case s[i]
|
||||||
of '\0':
|
of '\0':
|
||||||
break
|
break
|
||||||
of '\x0D':
|
of '\x0D':
|
||||||
put(g, tkComment, com)
|
put(g, tkComment, com)
|
||||||
com = ""
|
com = "## "
|
||||||
inc(i)
|
inc(i)
|
||||||
if s[i] == '\x0A': inc(i)
|
if s[i] == '\x0A': inc(i)
|
||||||
optNL(g, ind)
|
optNL(g, ind)
|
||||||
of '\x0A':
|
of '\x0A':
|
||||||
put(g, tkComment, com)
|
put(g, tkComment, com)
|
||||||
com = ""
|
com = "## "
|
||||||
inc(i)
|
inc(i)
|
||||||
optNL(g, ind)
|
optNL(g, ind)
|
||||||
of '#':
|
|
||||||
add(com, s[i])
|
|
||||||
inc(i)
|
|
||||||
comIndent = 0
|
|
||||||
while s[i] == ' ':
|
|
||||||
add(com, s[i])
|
|
||||||
inc(i)
|
|
||||||
inc(comIndent)
|
|
||||||
of ' ', '\x09':
|
of ' ', '\x09':
|
||||||
add(com, s[i])
|
add(com, s[i])
|
||||||
inc(i)
|
inc(i)
|
||||||
|
|
@ -206,7 +197,7 @@ proc putComment(g: var TSrcGen, s: string) =
|
||||||
if not isCode and (g.lineLen + (j - i) > MaxLineLen):
|
if not isCode and (g.lineLen + (j - i) > MaxLineLen):
|
||||||
put(g, tkComment, com)
|
put(g, tkComment, com)
|
||||||
optNL(g, ind)
|
optNL(g, ind)
|
||||||
com = '#' & spaces(comIndent)
|
com = "## "
|
||||||
while s[i] > ' ':
|
while s[i] > ' ':
|
||||||
add(com, s[i])
|
add(com, s[i])
|
||||||
inc(i)
|
inc(i)
|
||||||
|
|
@ -283,7 +274,7 @@ proc shouldRenderComment(g: var TSrcGen, n: PNode): bool =
|
||||||
result = false
|
result = false
|
||||||
if n.comment != nil:
|
if n.comment != nil:
|
||||||
result = (renderNoComments notin g.flags) or
|
result = (renderNoComments notin g.flags) or
|
||||||
(renderDocComments in g.flags) and startsWith(n.comment, "##")
|
(renderDocComments in g.flags)
|
||||||
|
|
||||||
proc gcom(g: var TSrcGen, n: PNode) =
|
proc gcom(g: var TSrcGen, n: PNode) =
|
||||||
assert(n != nil)
|
assert(n != nil)
|
||||||
|
|
|
||||||
|
|
@ -69,6 +69,44 @@ Documentation comments are tokens; they are only allowed at certain places in
|
||||||
the input file as they belong to the syntax tree!
|
the input file as they belong to the syntax tree!
|
||||||
|
|
||||||
|
|
||||||
|
Multiline comments
|
||||||
|
------------------
|
||||||
|
|
||||||
|
Starting with version 0.13.0 of the language Nim supports multiline comments.
|
||||||
|
They look like:
|
||||||
|
|
||||||
|
.. code-block:: nim
|
||||||
|
#[Comment here.
|
||||||
|
Multiple lines
|
||||||
|
are not a problem.]
|
||||||
|
|
||||||
|
.. code-block:: nim
|
||||||
|
#[[comment here]]
|
||||||
|
|
||||||
|
.. code-block:: nim
|
||||||
|
#[[[comment here]]]
|
||||||
|
|
||||||
|
.. code-block:: nim
|
||||||
|
#[[[[comment here]]]]
|
||||||
|
|
||||||
|
The number of opening brackets must match the number of closing brackets
|
||||||
|
but they do not nest in the traditional sense:
|
||||||
|
|
||||||
|
.. code-block:: nim
|
||||||
|
# Does not comment out 'p' properly:
|
||||||
|
#[
|
||||||
|
proc p[T](x: T) = discard
|
||||||
|
]
|
||||||
|
|
||||||
|
Multiline documentation comments look like:
|
||||||
|
|
||||||
|
.. code-block:: nim
|
||||||
|
proc foo =
|
||||||
|
##[Long documentation comment
|
||||||
|
here.
|
||||||
|
]
|
||||||
|
|
||||||
|
|
||||||
Identifiers & Keywords
|
Identifiers & Keywords
|
||||||
----------------------
|
----------------------
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -173,7 +173,22 @@ proc nimNextToken(g: var GeneralTokenizer) =
|
||||||
while g.buf[pos] in {' ', '\x09'..'\x0D'}: inc(pos)
|
while g.buf[pos] in {' ', '\x09'..'\x0D'}: inc(pos)
|
||||||
of '#':
|
of '#':
|
||||||
g.kind = gtComment
|
g.kind = gtComment
|
||||||
while not (g.buf[pos] in {'\0', '\x0A', '\x0D'}): inc(pos)
|
inc(pos)
|
||||||
|
if g.buf[pos] == '#': inc(pos)
|
||||||
|
if g.buf[pos] == '[':
|
||||||
|
g.kind = gtLongComment
|
||||||
|
var brackets = 0
|
||||||
|
while g.buf[pos] == '[':
|
||||||
|
inc(pos)
|
||||||
|
inc(brackets)
|
||||||
|
while g.buf[pos] != '\0':
|
||||||
|
if g.buf[pos] == ']':
|
||||||
|
var q = pos
|
||||||
|
while g.buf[pos] == ']': inc(pos)
|
||||||
|
if pos-q == brackets: break
|
||||||
|
inc(pos)
|
||||||
|
else:
|
||||||
|
while g.buf[pos] notin {'\0', '\x0A', '\x0D'}: inc(pos)
|
||||||
of 'a'..'z', 'A'..'Z', '_', '\x80'..'\xFF':
|
of 'a'..'z', 'A'..'Z', '_', '\x80'..'\xFF':
|
||||||
var id = ""
|
var id = ""
|
||||||
while g.buf[pos] in SymChars + {'_'}:
|
while g.buf[pos] in SymChars + {'_'}:
|
||||||
|
|
|
||||||
2
todo.txt
2
todo.txt
|
|
@ -10,7 +10,6 @@ essential for 1.0
|
||||||
- make '--implicitStatic:on' the default; then we can also clean up the
|
- make '--implicitStatic:on' the default; then we can also clean up the
|
||||||
'static[T]' mess in the compiler!
|
'static[T]' mess in the compiler!
|
||||||
|
|
||||||
- add "all threads are blocked" detection to 'spawn'
|
|
||||||
- Deprecate ``immediate`` for templates and macros
|
- Deprecate ``immediate`` for templates and macros
|
||||||
- document NimMain and check whether it works for threading
|
- document NimMain and check whether it works for threading
|
||||||
- ``not`` or ``~`` for the effects system
|
- ``not`` or ``~`` for the effects system
|
||||||
|
|
@ -19,6 +18,7 @@ essential for 1.0
|
||||||
Not critical for 1.0
|
Not critical for 1.0
|
||||||
====================
|
====================
|
||||||
|
|
||||||
|
- add "all threads are blocked" detection to 'spawn'
|
||||||
- figure out why C++ bootstrapping is so much slower
|
- figure out why C++ bootstrapping is so much slower
|
||||||
- The bitwise 'not' operator cold be renamed to 'bnot' to
|
- The bitwise 'not' operator cold be renamed to 'bnot' to
|
||||||
prevent 'not 4 == 5' from compiling. -> requires 'mixin' annotation for procs!
|
prevent 'not 4 == 5' from compiling. -> requires 'mixin' annotation for procs!
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue