aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGanesh Viswanathan <dev@genotrance.com>2019-01-20 15:53:14 -0600
committerGanesh Viswanathan <dev@genotrance.com>2019-01-20 15:53:14 -0600
commit8a4fb0facac95351b266c8424bb864d34dde8446 (patch)
tree1158b4f44c1cf8c0028d3a04542c46be44a39b2d
parent65111455134774bd965bc52b22556d9942e1888f (diff)
downloadnimterop-8a4fb0facac95351b266c8424bb864d34dde8446.tar.gz
nimterop-8a4fb0facac95351b266c8424bb864d34dde8446.zip
Add documentation
-rw-r--r--README.md10
-rw-r--r--nimterop/cimport.nim66
-rw-r--r--nimterop/globals.nim25
3 files changed, 82 insertions, 19 deletions
diff --git a/README.md b/README.md
index 147daf1..60e9eb5 100644
--- a/README.md
+++ b/README.md
@@ -55,11 +55,11 @@ Detailed documentation is still forthcoming.
`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
@@ -69,9 +69,9 @@ Detailed documentation is still forthcoming.
`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
diff --git a/nimterop/cimport.nim b/nimterop/cimport.nim
index bb2217c..af66953 100644
--- a/nimterop/cimport.nim
+++ b/nimterop/cimport.nim
@@ -73,7 +73,7 @@ proc getToastError(output: string): string =
# Filter out preprocessor errors
for line in output.splitLines():
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
if result.len == 0:
@@ -100,7 +100,7 @@ proc getToast(fullpath: string, recurse: bool = false): string =
(result, ret) = gorgeEx(cmd, cache=getFileDate(fullpath))
doAssert ret == 0, getToastError(result)
-proc getGccPaths*(mode = "c"): string =
+proc getGccPaths(mode = "c"): string =
var
ret = 0
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)
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)
if result.len == 0:
var found = false
@@ -117,12 +123,18 @@ proc cSearchPath*(path: string): string {.compileTime.}=
if fileExists(result) or dirExists(result):
found = true
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 =
+ ## Enable debug messages and display the generated Nim code
+
gStateCT.debug = true
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)
var str = name
@@ -141,11 +153,24 @@ macro cDefine*(name: static string, val: static string = ""): untyped =
echo result.repr
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)
if dir notin gStateCT.searchDirs:
gStateCT.searchDirs.add(dir)
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)
result = newNimNode(nnkStmtList)
@@ -164,6 +189,16 @@ macro cIncludeDir*(dir: static string): untyped =
echo result.repr
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)
var
@@ -182,6 +217,22 @@ macro cAddStdDir*(mode = "c"): untyped =
cAddSearchDir(`sline`)
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)
var
@@ -229,6 +280,15 @@ macro cCompile*(path: static string, mode = "c"): untyped =
echo result.repr
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)
let
diff --git a/nimterop/globals.nim b/nimterop/globals.nim
index 0c81e27..11882a7 100644
--- a/nimterop/globals.nim
+++ b/nimterop/globals.nim
@@ -6,7 +6,7 @@ when not declared(CIMPORT):
import "."/treesitter/runtime
const
- gAtoms* = @[
+ gAtoms {.used.} = @[
"field_identifier",
"identifier",
"number_literal",
@@ -16,27 +16,27 @@ const
"type_identifier"
].toSet()
- gExpressions* = @[
+ gExpressions {.used.} = @[
"parenthesized_expression",
"bitwise_expression",
"shift_expression",
"math_expression"
].toSet()
- gEnumVals* = @[
+ gEnumVals {.used.} = @[
"identifier",
"number_literal"
].concat(toSeq(gExpressions.items))
type
- Kind* = enum
+ Kind = enum
exactlyOne
oneOrMore # +
zeroOrMore # *
zeroOrOne # ?
orWithNext # !
- Ast* = object
+ Ast = object
name*: string
kind*: Kind
recursive*: bool
@@ -45,7 +45,7 @@ type
tonim*: proc (ast: ref Ast, node: TSNode)
regex*: Regex
- State* = object
+ State = object
compile*, defines*, headers*, includeDirs*, searchDirs*: seq[string]
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.}]]
var
- gStateCT* {.compiletime.}: State
- gStateRT*: State
+ gStateCT {.compiletime, used.}: State
+ gStateRT {.used.}: State
-template nBl*(s: typed): untyped =
+template nBl(s: typed): untyped {.used.} =
(s.len != 0)
-type CompileMode* = enum
+type CompileMode = enum
c,
cpp,
# 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 \ No newline at end of file