diff --git a/README.md b/README.md
index 3341b04..f411657 100644
--- a/README.md
+++ b/README.md
@@ -1,3 +1,8 @@
# PL/XML
-Please don't ever use this language. Thank you.
\ No newline at end of file
+Please don't ever use this language. Thank you.
+
+However, if, for some reason, you feel like sharing
+my suffering, check out the [syntax](doc/syntax.md),
+[documentation](doc/language.md), and
+[standard library](doc/stl.md)!
diff --git a/doc/language.md b/doc/language.md
new file mode 100644
index 0000000..f7175e8
--- /dev/null
+++ b/doc/language.md
@@ -0,0 +1,436 @@
+# PL/XML: The Handbook
+
+## Introduction
+
+As do many ideas, PL/XML sprang from the need
+to do something extremely useless just for fun,
+to see how it would turn out. The original premise
+was a programming language based on XML syntax.
+Its name came from (PL/SQL)[https://en.wikipedia.org/wiki/PL/SQL],
+some kind of torture device for IT students.
+
+In order not to make this project completely useless,
+I wrote the original interpreter in Rust (WIIR!)
+to get better acquainted with the language.
+
+The result is a dynamically-typed procedural language,
+which is provably Turing-complete since I was able to
+write a blazing slow (Brainfuck interpreter)[../sample/bf.pl.xml]
+with it. All the convenient aspects are overshadowed
+by the utter agony that manually writing XML is.
+
+## Quick guide
+
+```xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+```
+
+This slightly over-engineered hello world program
+contains some basics of PL/XML, such as program structure,
+variable assignment and retrieval, instanciation, and function
+definition and calls.
+
+### Program structure
+
+Every PL/XML program should be wrapped in a `program`
+node specifying its name. This program must contain a
+`main` node that will be executed first, and can define
+a set of functions using `function` nodes. Inside `main`
+and the function `body` nodes is actual code that will be
+sequentially executed.
+
+### Values
+
+PL/XML has a few value types. The first two are the signed numeric
+`integer` and `real` types, which have no precision guarantee.
+Another type is the usual character `string`, which may or may not
+support Unicode. The `array` type is a generic iterable collection
+of any value, including arrays. Functions are values as well, and
+as such can be (and technically are) stored in variables.
+
+Integer, Real and String values can be instanciated by using the
+eponymous node with a `value` attribute. For instance:
+
+```xml
+
+
+
+```
+
+Value nodes `integer`, `real`, and `string` can also be used
+to cast a value to another type. For instance, a `string` value
+can be parsed into a `real`, and a `real` value can be rounded down
+by casting it to an `integer`.
+
+```xml
+
+
+
+
+
+```
+
+Arrays can be initialized empty or with contained elements. Array
+manipulation is performed through [standard library](stl.md) functions.
+
+```xml
+
+
+
+
+
+
+
+
+
+```
+
+When boolean-like values are needed, all values
+are considered truthy, except the integer 0.
+
+### Variable manipulation
+
+A value can be assigned to and retrieved from a variable.
+Variables are dynamically-typed, meaning you can assign any
+type to any variable, no matter its previous type.
+
+To assign a value to a variable, use an `assign` node with a
+`variable` attribute specifying the name of the variable, and
+add a child node containing any value-returning node, such as
+`string`.
+
+```xml
+
+
+
+```
+
+To retrieve a value, use a `value` node with the same
+`variable` attribute.
+
+```xml
+
+```
+
+Variables have some sort of scoping which is function body-bound:
+there is a global scope containing standard and user-defined
+functions from which local scopes inherit.
+
+### Function calls
+
+A `call` node is used to call functions. Function arguments
+are passed as child nodes to a `arguments` node. The short
+syntax uses the `function` attribute to specify the function
+to call.
+
+```xml
+
+
+
+
+
+```
+
+Functions are values that can also be stored and retrieved
+through variables. Thus exists a longer syntax allowing dynamic
+calls, without the `function` attribute but putting the function
+value as a child of the `call` node.
+
+```xml
+
+
+
+
+
+
+```
+
+You can find a variety of utility functions in the
+[standard library](stl.md).
+
+### Function definition
+
+Functions are defined at the top level, as child nodes to the
+`program` node. The `name` attribute specifies the function name
+to use when called. They have a `arguments` node, defining to which
+local variables arguments will be assigned, in order of `argument` nodes,
+and a `body` node containing the code that will be executed when the function
+is called.
+
+```xml
+
+
+
+
+
+
+
+
+
+
+
+
+```
+
+This function, named "my-print" takes one argument, called "the-text".
+It uses this value to call the standard library "print-line" function.
+
+Functions can return values. Wrap a value in a `return` node to use it as
+a return value for the function. Subsequent code will not be executed, and
+the caller can use the `call` node as any other value.
+
+```xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+```
+
+This function takes two arguments and adds them together,
+adding two to the sum, and returns the result.
+
+### Built-in operations
+
+The previous example uses an `add` node to sum integer values.
+PL/XML has multiple usual arithmetic and logic operators to
+manipulate values, used directly as nodes containing them.
+
+Only compatible values will be used together. Integers will
+automatically be promoted to reals if needed.
+
+`add` and `multiply` both take any number of number arguments and will
+compute their sum or product. `add` can also be used to concatenate
+string values.
+
+```xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+```
+
+`subtract` and `divide` take at least one numeric argument, which will be
+subtracted from or divided using subsequent arguments.
+
+```xml
+
+
+
+
+
+
+
+
+
+```
+
+`and` and `or` also take at least one argument, and will chain their
+corresponding logic operation on all arguments.
+
+```xml
+
+
+
+
+
+
+
+
+
+```
+
+`not` takes exactly one argument, and will give a truthy value
+(the integer 1) if the argument is falsy (the integer 0), and
+a falsy value otherwise.
+
+```xml
+
+
+
+```
+
+`equal`, `greater`, and `lower` all take exactly two arguments,
+and will give a truthy value if the first is respectively
+equal to, greater than, or lower than the second, and a falsy
+value otherwise.
+
+```xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+```
+
+### Control structures
+
+As in many imperative languages, control structures are
+used to manipulate the flow of code execution. The first
+one is the `if` structure. Its first child is the value checked
+for truthyness, after which a `then` block contains the code
+to execute if it is truthy, otherwise the code contained in the
+optional `else` block will be executed.
+
+```xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+```
+
+Three other structures give access to loops. `while` loops
+contain the condition to check, which will be executed at the beginning
+of each loop turn, and a `do` node containing the code to execute.
+
+```xml
+
+
+
+
+
+
+
+
+
+
+```
+
+The `for` loop takes `from`, `to`, and `step` child nodes, which should
+evaluate to integer values. Code contained in the `do` child node
+will be executed with a variable whose name is specified in the `variable`
+attribute on the `for` node containing the current iteration value.
+
+```xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+```
+
+Finally, the `each` loop iterates over an array, assigning its values
+in order to the specified `variable`.
+
+```xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+```
+
+### Error handling
+
+Some standard library functions or language nodes may raise
+errors during execution. In a `handle` node, errors can be
+caught inside a `try` node to use them in a `catch` node, which
+will only be executed if an error was raised.
+
+```xml
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+```
\ No newline at end of file
diff --git a/doc/stl.md b/doc/stl.md
index 034b4d4..06cf992 100644
--- a/doc/stl.md
+++ b/doc/stl.md
@@ -20,21 +20,19 @@ such as input/output, file access and array manipulation.
- [WRITE-FILE](#write-file)
- [READ-FILE](#read-file)
-## Functions
-
-### PRINT
+## PRINT
Writes a string as-is to the standard output
-#### Arguments
+### Arguments
- `string` value to print
-#### Returns
+### Returns
Nothing
-#### Minimal example
+### Minimal example
```xml
@@ -44,19 +42,19 @@ Nothing
```
-### PRINT-LINE
+## PRINT-LINE
Writes a string to the standard output, appending a new line
-#### Arguments
+### Arguments
- `string` value to print
-#### Returns
+### Returns
Nothing
-#### Minimal example
+### Minimal example
```xml
@@ -66,19 +64,19 @@ Nothing
```
-### INPUT
+## INPUT
Reads from the standard input
-#### Arguments
+### Arguments
Nothing
-#### Returns
+### Returns
`string` value read
-#### Minimal example
+### Minimal example
```xml
@@ -86,19 +84,19 @@ Nothing
```
-### STRING-SPLIT
+## STRING-SPLIT
Splits a string into a vector of single-character strings
-#### Arguments
+### Arguments
- `string` value to split
-#### Returns
+### Returns
`array` value of strings
-#### Minimal examples
+### Minimal examples
```xml
@@ -117,21 +115,21 @@ Splits a string into a vector of single-character strings
```
-### ARRAY-SET
+## ARRAY-SET
Sets a value at a specific index of an array.
-#### Arguments
+### Arguments
- `array` to update
- `integer` index
- `any` value to set
-#### Returns
+### Returns
Nothing
-#### Minimal example
+### Minimal example
```xml
@@ -148,20 +146,20 @@ Nothing
```
-### ARRAY-PUSH
+## ARRAY-PUSH
Pushes a value at the end of an array
-#### Arguments
+### Arguments
- `array` to update
- `any` value to push
-#### Returns
+### Returns
Nothing
-#### Minimal example
+### Minimal example
```xml
@@ -177,19 +175,19 @@ Nothing
```
-### ARRAY-POP
+## ARRAY-POP
Removes and returns the value at the end of an array
-#### Arguments
+### Arguments
- `array` to update
-#### Returns
+### Returns
`any` value
-#### Minimal example
+### Minimal example
```xml
@@ -204,20 +202,20 @@ Removes and returns the value at the end of an array
```
-### ARRAY-GET
+## ARRAY-GET
Returns the value at index of an array
-#### Arguments
+### Arguments
- `array` to query
- `integer` index
-#### Returns
+### Returns
`any` value
-#### Minimal example
+### Minimal example
```xml
@@ -233,19 +231,19 @@ Returns the value at index of an array
```
-### ARRAY-LENGTH
+## ARRAY-LENGTH
Returns the length of an array
-#### Arguments
+### Arguments
- `array` to query
-#### Returns
+### Returns
`integer` length
-#### Minimal example
+### Minimal example
```xml
@@ -260,19 +258,19 @@ Returns the length of an array
```
-### TO-ASCII
+## TO-ASCII
Converts an integer value into an ASCII character string
-#### Arguments
+### Arguments
- `integer` to convert
-#### Returns
+### Returns
`string` corresponding ASCII character
-#### Minimal example
+### Minimal example
```xml
@@ -282,19 +280,19 @@ Converts an integer value into an ASCII character string
```
-### FROM-ASCII
+## FROM-ASCII
Converts a one-character string into its ASCII integer value
-#### Arguments
+### Arguments
- `string` character to convert
-#### Returns
+### Returns
`integer` ASCII value
-#### Minimal example
+### Minimal example
```xml
@@ -304,19 +302,19 @@ Converts a one-character string into its ASCII integer value
```
-### GET-ARGS
+## GET-ARGS
Returns an array of arguments passed to the program
-#### Arguments
+### Arguments
Nothing
-#### Returns
+### Returns
`array` of strings
-#### Minimal example
+### Minimal example
```xml
@@ -324,21 +322,21 @@ Nothing
```
-### WRITE-FILE
+## WRITE-FILE
Writes a string to a file, optionally appending
-#### Arguments
+### Arguments
- `string` filename
- `string` to write
- `any` falsy to replace, truthy to append
-#### Returns
+### Returns
Nothing
-#### Minimal example
+### Minimal example
```xml
@@ -350,19 +348,19 @@ Nothing
```
-### READ-FILE
+## READ-FILE
Reads a file into a string
-#### Arguments
+### Arguments
- `string` filename
-#### Returns
+### Returns
- `string` file contents
-#### Minimal example
+### Minimal example
```xml
diff --git a/doc/syntax.md b/doc/syntax.md
index 595a110..b289adb 100644
--- a/doc/syntax.md
+++ b/doc/syntax.md
@@ -118,19 +118,19 @@ add
"" instructions ""
subtract
- "" instructions ""
+ "" instruction instructions ""
multiply
"" instructions ""
divide
- "" instructions ""
+ "" instruction instructions ""
and
- "" instructions ""
+ "" instruction instructions ""
or
- "" instructions ""
+ "" instruction instructions ""
not
"" instruction ""