Add documentation
This commit is contained in:
parent
6511145513
commit
8a4fb0faca
3 changed files with 82 additions and 19 deletions
10
README.md
10
README.md
|
|
@ -55,11 +55,11 @@ Detailed documentation is still forthcoming.
|
||||||
|
|
||||||
`cDebug()` - enable debug messages
|
`cDebug()` - enable debug messages
|
||||||
|
|
||||||
`cDefine("XXX")` - `#define` an identifer that is forwarded to the C/C++ compiler using `{.passC: "-DXXX".}` as well as _eventually_ used in processing `#ifdef` statements
|
`cDefine("XXX")` - `#define` an identifer that is forwarded to the C/C++ compiler using `{.passC: "-DXXX".}`
|
||||||
|
|
||||||
`cIncludeDir("XXX")` - add an include directory that is forwarded to the compiler using `{.passC: "-IXXX".}`
|
`cIncludeDir("XXX")` - add an include directory that is forwarded to the C/C++ compiler using `{.passC: "-IXXX".}`
|
||||||
|
|
||||||
`cImport("header.h")` - import all supported definitions from header file. Output is cached in nimcache unless header.h changes or by using `nim -f`
|
`cImport("header.h")` - Import all supported definitions from specified header file. Generated content is cached in `nimcache` until `header.h` changes. If files imported by `header.h` change and affect the generated content, use `nim -f` to force regeneration of Nim code.
|
||||||
|
|
||||||
`cImport("header.h", recurse=true)` - import all supported definitions from header file and #includes
|
`cImport("header.h", recurse=true)` - import all supported definitions from header file and #includes
|
||||||
|
|
||||||
|
|
@ -69,9 +69,9 @@ Detailed documentation is still forthcoming.
|
||||||
|
|
||||||
`cCompile("path/to/dir", "cpp")` - compile in all C++ files found recursively
|
`cCompile("path/to/dir", "cpp")` - compile in all C++ files found recursively
|
||||||
|
|
||||||
`cAddSearchDir("XXX")` - add directory XXX to search path in calls to `cSearchPath()`
|
`cAddSearchDir("XXX")` - add directory XXX to the search path used in calls to `cSearchPath()`
|
||||||
|
|
||||||
`cAddStdDir("XXX")` - add standard "c" [default] or "cpp" include paths to search path
|
`cAddStdDir("XXX")` - add standard "c" [default] or "cpp" include paths to search path used in calls to `cSearchPath()`
|
||||||
|
|
||||||
`cSearchPath("header.h")` - return a file or directory found in search path configured using `cSearchPath()` - can be used in `cCompile()`, `cIncludeDir()` and `cImport()` calls
|
`cSearchPath("header.h")` - return a file or directory found in search path configured using `cSearchPath()` - can be used in `cCompile()`, `cIncludeDir()` and `cImport()` calls
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -73,7 +73,7 @@ proc getToastError(output: string): string =
|
||||||
# Filter out preprocessor errors
|
# Filter out preprocessor errors
|
||||||
for line in output.splitLines():
|
for line in output.splitLines():
|
||||||
if "fatal error:" in line.toLowerAscii:
|
if "fatal error:" in line.toLowerAscii:
|
||||||
result &= &"\nERROR: {line.split(\"fatal error\")[1]}\n"
|
result &= "\nERROR:$1\n" % line.split("fatal error:")[1]
|
||||||
|
|
||||||
# Toast error
|
# Toast error
|
||||||
if result.len == 0:
|
if result.len == 0:
|
||||||
|
|
@ -100,7 +100,7 @@ proc getToast(fullpath: string, recurse: bool = false): string =
|
||||||
(result, ret) = gorgeEx(cmd, cache=getFileDate(fullpath))
|
(result, ret) = gorgeEx(cmd, cache=getFileDate(fullpath))
|
||||||
doAssert ret == 0, getToastError(result)
|
doAssert ret == 0, getToastError(result)
|
||||||
|
|
||||||
proc getGccPaths*(mode = "c"): string =
|
proc getGccPaths(mode = "c"): string =
|
||||||
var
|
var
|
||||||
ret = 0
|
ret = 0
|
||||||
nul = when defined(Windows): "nul" else: "/dev/null"
|
nul = when defined(Windows): "nul" else: "/dev/null"
|
||||||
|
|
@ -109,6 +109,12 @@ proc getGccPaths*(mode = "c"): string =
|
||||||
(result, ret) = gorgeEx("gcc -Wp,-v -x" & mmode & " " & nul)
|
(result, ret) = gorgeEx("gcc -Wp,-v -x" & mmode & " " & nul)
|
||||||
|
|
||||||
proc cSearchPath*(path: string): string {.compileTime.}=
|
proc cSearchPath*(path: string): string {.compileTime.}=
|
||||||
|
## Return a file or directory found in search path configured using
|
||||||
|
## ``cSearchPath()``
|
||||||
|
##
|
||||||
|
## This proc can be used to locate files or directories in calls to
|
||||||
|
## ``cCompile()``, ``cIncludeDir()`` and ``cImport()``.
|
||||||
|
|
||||||
result = findPath(path, fail = false)
|
result = findPath(path, fail = false)
|
||||||
if result.len == 0:
|
if result.len == 0:
|
||||||
var found = false
|
var found = false
|
||||||
|
|
@ -117,12 +123,18 @@ proc cSearchPath*(path: string): string {.compileTime.}=
|
||||||
if fileExists(result) or dirExists(result):
|
if fileExists(result) or dirExists(result):
|
||||||
found = true
|
found = true
|
||||||
break
|
break
|
||||||
doAssert found, "File or directory not found: " & path & " gStateCT.searchDirs: " & $gStateCT.searchDirs
|
doAssert found, "File or directory not found: " & path &
|
||||||
|
" gStateCT.searchDirs: " & $gStateCT.searchDirs
|
||||||
|
|
||||||
macro cDebug*(): untyped =
|
macro cDebug*(): untyped =
|
||||||
|
## Enable debug messages and display the generated Nim code
|
||||||
|
|
||||||
gStateCT.debug = true
|
gStateCT.debug = true
|
||||||
|
|
||||||
macro cDefine*(name: static string, val: static string = ""): untyped =
|
macro cDefine*(name: static string, val: static string = ""): untyped =
|
||||||
|
## ``#define`` an identifer that is forwarded to the C/C++ compiler
|
||||||
|
## using ``{.passC: "-DXXX".}``
|
||||||
|
|
||||||
result = newNimNode(nnkStmtList)
|
result = newNimNode(nnkStmtList)
|
||||||
|
|
||||||
var str = name
|
var str = name
|
||||||
|
|
@ -141,11 +153,24 @@ macro cDefine*(name: static string, val: static string = ""): untyped =
|
||||||
echo result.repr
|
echo result.repr
|
||||||
|
|
||||||
macro cAddSearchDir*(dir: static string): untyped =
|
macro cAddSearchDir*(dir: static string): untyped =
|
||||||
|
## Add directory ``dir`` to the search path used in calls to
|
||||||
|
## ``cSearchPath()``
|
||||||
|
##
|
||||||
|
## This allows something like this:
|
||||||
|
##
|
||||||
|
## .. code-block:: nim
|
||||||
|
##
|
||||||
|
## cAddSearchDir("path/to/includes")
|
||||||
|
## cImport cSearchPath("file.h")
|
||||||
|
|
||||||
var dir = interpPath(dir)
|
var dir = interpPath(dir)
|
||||||
if dir notin gStateCT.searchDirs:
|
if dir notin gStateCT.searchDirs:
|
||||||
gStateCT.searchDirs.add(dir)
|
gStateCT.searchDirs.add(dir)
|
||||||
|
|
||||||
macro cIncludeDir*(dir: static string): untyped =
|
macro cIncludeDir*(dir: static string): untyped =
|
||||||
|
## Add an include directory that is forwarded to the C/C++ compiler
|
||||||
|
## using ``{.passC: "-IXXX".}``
|
||||||
|
|
||||||
var dir = interpPath(dir)
|
var dir = interpPath(dir)
|
||||||
result = newNimNode(nnkStmtList)
|
result = newNimNode(nnkStmtList)
|
||||||
|
|
||||||
|
|
@ -164,6 +189,16 @@ macro cIncludeDir*(dir: static string): untyped =
|
||||||
echo result.repr
|
echo result.repr
|
||||||
|
|
||||||
macro cAddStdDir*(mode = "c"): untyped =
|
macro cAddStdDir*(mode = "c"): untyped =
|
||||||
|
## Add the standard ``c`` [default] or ``cpp`` include paths to search
|
||||||
|
## path used in calls to ``cSearchPath()``
|
||||||
|
##
|
||||||
|
## This allows something like this:
|
||||||
|
##
|
||||||
|
## .. code-block:: nim
|
||||||
|
##
|
||||||
|
## cAddStdDir()
|
||||||
|
## cImport cSearchPath("math.h")
|
||||||
|
|
||||||
result = newNimNode(nnkStmtList)
|
result = newNimNode(nnkStmtList)
|
||||||
|
|
||||||
var
|
var
|
||||||
|
|
@ -182,6 +217,22 @@ macro cAddStdDir*(mode = "c"): untyped =
|
||||||
cAddSearchDir(`sline`)
|
cAddSearchDir(`sline`)
|
||||||
|
|
||||||
macro cCompile*(path: static string, mode = "c"): untyped =
|
macro cCompile*(path: static string, mode = "c"): untyped =
|
||||||
|
## Compile and link C/C++ implementation into resulting binary using ``{.compile.}``
|
||||||
|
##
|
||||||
|
## ``path`` can be a specific file or contain wildcards:
|
||||||
|
##
|
||||||
|
## .. code-block:: nim
|
||||||
|
##
|
||||||
|
## cCompile("file.c")
|
||||||
|
## cCompile("path/to/*.c")
|
||||||
|
##
|
||||||
|
## ``mode`` can be ``c`` or ``cpp`` and recursively searches for code files in
|
||||||
|
## specified path. ``c`` = ``*.c``, ``cpp`` = ``*.C``, ``*.cpp``, ``*.c++``, ``*.cc``, ``*.cxx``
|
||||||
|
##
|
||||||
|
## .. code-block:: nim
|
||||||
|
##
|
||||||
|
## cCompile("path/to/dir", "cpp")
|
||||||
|
|
||||||
result = newNimNode(nnkStmtList)
|
result = newNimNode(nnkStmtList)
|
||||||
|
|
||||||
var
|
var
|
||||||
|
|
@ -229,6 +280,15 @@ macro cCompile*(path: static string, mode = "c"): untyped =
|
||||||
echo result.repr
|
echo result.repr
|
||||||
|
|
||||||
macro cImport*(filename: static string, recurse: static bool = false): untyped =
|
macro cImport*(filename: static string, recurse: static bool = false): untyped =
|
||||||
|
## Import all supported definitions from specified header file. Generated
|
||||||
|
## content is cached in ``nimcache`` until ``filename`` changes. If files
|
||||||
|
## imported by ``filename`` change and affect the generated content, use
|
||||||
|
## ``nim -f`` to force regeneration of Nim code.
|
||||||
|
##
|
||||||
|
## ``recurse`` can be used to generate Nim wrappers from ``#include`` files
|
||||||
|
## referenced in ``filename``. This is only done for files in the same
|
||||||
|
## directory as ``filename`` or in a directory added using ``cIncludeDir()``.
|
||||||
|
|
||||||
result = newNimNode(nnkStmtList)
|
result = newNimNode(nnkStmtList)
|
||||||
|
|
||||||
let
|
let
|
||||||
|
|
|
||||||
|
|
@ -6,7 +6,7 @@ when not declared(CIMPORT):
|
||||||
import "."/treesitter/runtime
|
import "."/treesitter/runtime
|
||||||
|
|
||||||
const
|
const
|
||||||
gAtoms* = @[
|
gAtoms {.used.} = @[
|
||||||
"field_identifier",
|
"field_identifier",
|
||||||
"identifier",
|
"identifier",
|
||||||
"number_literal",
|
"number_literal",
|
||||||
|
|
@ -16,27 +16,27 @@ const
|
||||||
"type_identifier"
|
"type_identifier"
|
||||||
].toSet()
|
].toSet()
|
||||||
|
|
||||||
gExpressions* = @[
|
gExpressions {.used.} = @[
|
||||||
"parenthesized_expression",
|
"parenthesized_expression",
|
||||||
"bitwise_expression",
|
"bitwise_expression",
|
||||||
"shift_expression",
|
"shift_expression",
|
||||||
"math_expression"
|
"math_expression"
|
||||||
].toSet()
|
].toSet()
|
||||||
|
|
||||||
gEnumVals* = @[
|
gEnumVals {.used.} = @[
|
||||||
"identifier",
|
"identifier",
|
||||||
"number_literal"
|
"number_literal"
|
||||||
].concat(toSeq(gExpressions.items))
|
].concat(toSeq(gExpressions.items))
|
||||||
|
|
||||||
type
|
type
|
||||||
Kind* = enum
|
Kind = enum
|
||||||
exactlyOne
|
exactlyOne
|
||||||
oneOrMore # +
|
oneOrMore # +
|
||||||
zeroOrMore # *
|
zeroOrMore # *
|
||||||
zeroOrOne # ?
|
zeroOrOne # ?
|
||||||
orWithNext # !
|
orWithNext # !
|
||||||
|
|
||||||
Ast* = object
|
Ast = object
|
||||||
name*: string
|
name*: string
|
||||||
kind*: Kind
|
kind*: Kind
|
||||||
recursive*: bool
|
recursive*: bool
|
||||||
|
|
@ -45,7 +45,7 @@ type
|
||||||
tonim*: proc (ast: ref Ast, node: TSNode)
|
tonim*: proc (ast: ref Ast, node: TSNode)
|
||||||
regex*: Regex
|
regex*: Regex
|
||||||
|
|
||||||
State* = object
|
State = object
|
||||||
compile*, defines*, headers*, includeDirs*, searchDirs*: seq[string]
|
compile*, defines*, headers*, includeDirs*, searchDirs*: seq[string]
|
||||||
|
|
||||||
debug*, past*, preprocess*, pnim*, pretty*, recurse*: bool
|
debug*, past*, preprocess*, pnim*, pretty*, recurse*: bool
|
||||||
|
|
@ -61,15 +61,18 @@ type
|
||||||
grammar*: seq[tuple[grammar: string, call: proc(ast: ref Ast, node: TSNode) {.nimcall.}]]
|
grammar*: seq[tuple[grammar: string, call: proc(ast: ref Ast, node: TSNode) {.nimcall.}]]
|
||||||
|
|
||||||
var
|
var
|
||||||
gStateCT* {.compiletime.}: State
|
gStateCT {.compiletime, used.}: State
|
||||||
gStateRT*: State
|
gStateRT {.used.}: State
|
||||||
|
|
||||||
template nBl*(s: typed): untyped =
|
template nBl(s: typed): untyped {.used.} =
|
||||||
(s.len != 0)
|
(s.len != 0)
|
||||||
|
|
||||||
type CompileMode* = enum
|
type CompileMode = enum
|
||||||
c,
|
c,
|
||||||
cpp,
|
cpp,
|
||||||
|
|
||||||
# TODO: can cligen accept enum instead of string?
|
# TODO: can cligen accept enum instead of string?
|
||||||
const modeDefault* = $cpp # TODO: USE this everywhere relevant
|
const modeDefault {.used.} = $cpp # TODO: USE this everywhere relevant
|
||||||
|
|
||||||
|
when not declared(CIMPORT):
|
||||||
|
export gAtoms, gExpressions, gEnumVals, Kind, Ast, State, gStateRT, nBl, CompileMode, modeDefault
|
||||||
Loading…
Add table
Add a link
Reference in a new issue