diff options
Diffstat (limited to 'doc')
-rw-r--r-- | doc/manual.md | 62 | ||||
-rw-r--r-- | doc/manual_experimental.md | 83 | ||||
-rw-r--r-- | doc/nimc.md | 22 | ||||
-rw-r--r-- | doc/nimdoc.css | 9 | ||||
-rw-r--r-- | doc/nims.md | 33 | ||||
-rw-r--r-- | doc/tut2.md | 2 | ||||
-rw-r--r-- | doc/tut3.md | 30 |
7 files changed, 199 insertions, 42 deletions
diff --git a/doc/manual.md b/doc/manual.md index 3b402e9f4..5c36a0a7b 100644 --- a/doc/manual.md +++ b/doc/manual.md @@ -3220,6 +3220,15 @@ A const section declares constants whose values are constant expressions: Once declared, a constant's symbol can be used as a constant expression. +The value part of a constant declaration opens a new scope for each constant, +so no symbols declared in the constant value are accessible outside of it. + + ```nim + const foo = (var a = 1; a) + const bar = a # error + let baz = a # error + ``` + See [Constants and Constant Expressions] for details. Static statement/expression @@ -3788,9 +3797,6 @@ type conversions to unsigned integers and between unsigned integers. The rationale for this is mostly better interoperability with the C Programming language when algorithms are ported from C to Nim. -Exception: Values that are converted to an unsigned type at compile time -are checked so that code like `byte(-1)` does not compile. - **Note**: Historically the operations were unchecked and the conversions were sometimes checked but starting with the revision 1.0.4 of this document and the language implementation the @@ -4457,7 +4463,42 @@ as an example: Overloading of the subscript operator ------------------------------------- -The `[]` subscript operator for arrays/openarrays/sequences can be overloaded. +The `[]` subscript operator for arrays/openarrays/sequences can be overloaded +for any type (with some exceptions) by defining a routine with the name `[]`. + + ```nim + type Foo = object + data: seq[int] + + proc `[]`(foo: Foo, i: int): int = + result = foo.data[i] + + let foo = Foo(data: @[1, 2, 3]) + echo foo[1] # 2 + ``` + +Assignment to subscripts can also be overloaded by naming a routine `[]=`, +which has precedence over assigning to the result of `[]`. + + ```nim + type Foo = object + data: seq[int] + + proc `[]`(foo: Foo, i: int): int = + result = foo.data[i] + proc `[]=`(foo: var Foo, i: int, val: int) = + foo.data[i] = val + + var foo = Foo(data: @[1, 2, 3]) + echo foo[1] # 2 + foo[1] = 5 + echo foo.data # @[1, 5, 3] + echo foo[1] # 5 + ``` + +Overloads of the subscript operator cannot be applied to routine or type +symbols themselves, as this conflicts with the syntax for instantiating +generic parameters, i.e. `foo[int](1, 2, 3)` or `Foo[int]`. Methods @@ -5419,6 +5460,8 @@ To override the compiler's side effect analysis a `{.noSideEffect.}` **Side effects are usually inferred. The inference for side effects is analogous to the inference for exception tracking.** +When the compiler cannot infer side effects, as is the case for imported +functions, one can annotate them with the `sideEffect` pragma. GC safety effect ---------------- @@ -6214,9 +6257,12 @@ scope is controlled by the `inject`:idx: and `gensym`:idx: pragmas: `gensym`'ed symbols are not exposed but `inject`'ed symbols are. The default for symbols of entity `type`, `var`, `let` and `const` -is `gensym` and for `proc`, `iterator`, `converter`, `template`, -`macro` is `inject`. However, if the name of the entity is passed as a -template parameter, it is an `inject`'ed symbol: +is `gensym`. For `proc`, `iterator`, `converter`, `template`, +`macro`, the default is `inject`, but if a `gensym` symbol with the same name +is defined in the same syntax-level scope, it will be `gensym` by default. +This can be overriden by marking the routine as `inject`. + +If the name of the entity is passed as a template parameter, it is an `inject`'ed symbol: ```nim template withFile(f, fn, mode: untyped, actions: untyped): untyped = @@ -8701,7 +8747,7 @@ after the last specified parameter. Nim string values will be converted to C strings automatically: ```Nim - proc printf(formatstr: cstring) {.nodecl, varargs.} + proc printf(formatstr: cstring) {.header: "<stdio.h>", varargs.} printf("hallo %s", "world") # "world" will be passed as C string ``` diff --git a/doc/manual_experimental.md b/doc/manual_experimental.md index 9b52fbd2a..da51d59ad 100644 --- a/doc/manual_experimental.md +++ b/doc/manual_experimental.md @@ -2522,31 +2522,39 @@ Notice we use the overload of `()` to have the same semantics in Nim, but on the This allows to easy interop with functions that accepts for example a `const` operator in its signature. -Injected symbols in generic procs -================================= - -With the experimental option `genericsOpenSym`, captured symbols in generic -routine bodies may be replaced by symbols injected locally by templates/macros -at instantiation time. `bind` may be used to keep the captured symbols over -the injected ones regardless of enabling the option. - +Injected symbols in generic procs and templates +=============================================== + +With the experimental option `openSym`, captured symbols in generic routine and +template bodies may be replaced by symbols injected locally by templates/macros +at instantiation time. `bind` may be used to keep the captured symbols over the +injected ones regardless of enabling the options, but other methods like +renaming the captured symbols should be used instead so that the code is not +affected by context changes. + Since this change may affect runtime behavior, the experimental switch -`genericsOpenSym` needs to be enabled, and a warning is given in the case -where an injected symbol would replace a captured symbol not bound by `bind` -and the experimental switch isn't enabled. +`openSym` needs to be enabled; and a warning is given in the case where an +injected symbol would replace a captured symbol not bound by `bind` and +the experimental switch isn't enabled. ```nim const value = "captured" -template foo(x: int, body: untyped) = +template foo(x: int, body: untyped): untyped = let value {.inject.} = "injected" body proc old[T](): string = foo(123): - return value # warning: a new `value` has been injected, use `bind` or turn on `experimental:genericsOpenSym` + return value # warning: a new `value` has been injected, use `bind` or turn on `experimental:openSym` echo old[int]() # "captured" -{.experimental: "genericsOpenSym".} +template oldTempl(): string = + block: + foo(123): + value # warning: a new `value` has been injected, use `bind` or turn on `experimental:openSym` +echo oldTempl() # "captured" + +{.experimental: "openSym".} proc bar[T](): string = foo(123): @@ -2558,6 +2566,53 @@ proc baz[T](): string = foo(123): return value assert baz[int]() == "captured" + +template barTempl(): string = + block: + foo(123): + value +assert barTempl() == "injected" # previously it would be "captured" + +template bazTempl(): string = + bind value + block: + foo(123): + value +assert bazTempl() == "captured" +``` + +This option also generates a new node kind `nnkOpenSym` which contains +exactly 1 `nnkSym` node. In the future this might be merged with a slightly +modified `nnkOpenSymChoice` node but macros that want to support the +experimental feature should still handle `nnkOpenSym`, as the node kind would +simply not be generated as opposed to being removed. + +Another experimental switch `genericsOpenSym` exists that enables this behavior +at instantiation time, meaning templates etc can enable it specifically when +they are being called. However this does not generate `nnkOpenSym` nodes +(unless the other switch is enabled) and so doesn't reflect the regular +behavior of the switch. + +```nim +const value = "captured" +template foo(x: int, body: untyped): untyped = + let value {.inject.} = "injected" + {.push experimental: "genericsOpenSym".} + body + {.pop.} + +proc bar[T](): string = + foo(123): + return value +echo bar[int]() # "injected" + +template barTempl(): string = + block: + var res: string + foo(123): + res = value + res +assert barTempl() == "injected" ``` diff --git a/doc/nimc.md b/doc/nimc.md index 25acf31e8..38558454b 100644 --- a/doc/nimc.md +++ b/doc/nimc.md @@ -481,6 +481,28 @@ They are: 5. nl_types. No headers for this. 6. As mmap is not supported, the nimAllocPagesViaMalloc option has to be used. +GPU Compilation +=============== + +Compiling for GPU computation can be achieved with `--cc:nvcc` for CUDA with nvcc, or with `--cc:hipcc` for AMD GPUs with HIP. Both compilers require building for C++ with `nim cpp`. + +Here's a very simple CUDA kernel example using emit, which can be compiled with `nim cpp --cc:nvcc --define:"useMalloc" hello_kernel.nim` assuming you have the CUDA toolkit installed. + +```nim +{.emit: """ +__global__ void add(int a, int b) { + int c; + c = a + b; +} +""".} + +proc main() = + {.emit: """ + add<<<1,1>>>(2,7); + """.} + +main() +``` DLL generation ============== diff --git a/doc/nimdoc.css b/doc/nimdoc.css index a9e4ac9c6..0c399e4c1 100644 --- a/doc/nimdoc.css +++ b/doc/nimdoc.css @@ -623,8 +623,8 @@ pre { table.line-nums-table { border-radius: 4px; - border: 1px solid #cccccc; - background-color: ghostwhite; + border: 1px solid var(--border); + background-color: var(--secondary-background); border-collapse: separate; margin-top: 15px; margin-bottom: 25px; } @@ -660,6 +660,9 @@ table { border-collapse: collapse; border-color: var(--third-background); border-spacing: 0; +} + +table:not(.line-nums-table) { font-size: 0.9em; } @@ -678,7 +681,7 @@ table th.docinfo-name { text-align: right; } -table tr:hover { +table:not(.line-nums-table) tr:hover { background-color: var(--third-background); } diff --git a/doc/nims.md b/doc/nims.md index 42cc6e124..987cc2096 100644 --- a/doc/nims.md +++ b/doc/nims.md @@ -61,43 +61,44 @@ Standard library modules At least the following standard library modules are available: -* [macros](macros.html) -* [os](os.html) -* [strutils](strutils.html) -* [math](math.html) -* [distros](distros.html) -* [sugar](sugar.html) * [algorithm](algorithm.html) * [base64](base64.html) * [bitops](bitops.html) * [chains](chains.html) * [colors](colors.html) * [complex](complex.html) +* [distros](distros.html) +* [std/editdistance](editdistance.html) * [htmlgen](htmlgen.html) +* [htmlparser](htmlparser.html) * [httpcore](httpcore.html) +* [json](json.html) * [lenientops](lenientops.html) +* [macros](macros.html) +* [math](math.html) * [options](options.html) +* [os](os.html) +* [parsecfg](parsecfg.html) +* [parsecsv](parsecsv.html) +* [parsejson](parsejson.html) +* [parsesql](parsesql.html) * [parseutils](parseutils.html) * [punycode](punycode.html) * [random](random.html) +* [ropes](ropes.html) +* [std/setutils](setutils.html) * [stats](stats.html) * [strformat](strformat.html) * [strmisc](strmisc.html) * [strscans](strscans.html) +* [strtabs](strtabs.html) +* [strutils](strutils.html) +* [sugar](sugar.html) * [unicode](unicode.html) +* [unidecode](unidecode.html) * [uri](uri.html) -* [std/editdistance](editdistance.html) * [std/wordwrap](wordwrap.html) -* [parsecsv](parsecsv.html) -* [parsecfg](parsecfg.html) -* [parsesql](parsesql.html) * [xmlparser](xmlparser.html) -* [htmlparser](htmlparser.html) -* [ropes](ropes.html) -* [json](json.html) -* [parsejson](parsejson.html) -* [strtabs](strtabs.html) -* [unidecode](unidecode.html) In addition to the standard Nim syntax ([system](system.html) module), NimScripts support the procs and templates defined in the diff --git a/doc/tut2.md b/doc/tut2.md index 4b9049082..1b59288d5 100644 --- a/doc/tut2.md +++ b/doc/tut2.md @@ -166,7 +166,7 @@ An example: n.strVal = "" ``` -As can been seen from the example, an advantage to an object hierarchy is that +As can be seen from the example, an advantage to an object hierarchy is that no conversion between different object types is needed. Yet, access to invalid object fields raises an exception. diff --git a/doc/tut3.md b/doc/tut3.md index 67f49c879..3a55d4790 100644 --- a/doc/tut3.md +++ b/doc/tut3.md @@ -322,6 +322,36 @@ used to get this output. raise newException(AssertionDefect, $a & " != " & $b) ``` + +Going further +------------- + +It is possible to create more complex macros by combining different +`NimNode` symbols with `quote do:` expressions. For example, you may +use `newStmtList` to build your macro iteratively, and `ident` in cases +in which you wish to create an identifier from a string, as shown below. + + ```nim + import std/macros + + macro createProcedures() = + result = newStmtList() + + for i in 0..<10: + let name = ident("myProc" & $i) + let content = newLit("I am procedure number #" & $i) + + result.add quote do: + proc `name`() = + echo `content` + + createProcedures() + myProc7() + ``` + +The call to `myProc7` will echo `I am procedure number #7`. + + With Power Comes Responsibility ------------------------------- |