Metadata-Version: 2.4
Name: blackspace
Version: 0.0.76
Summary: BlackSpace is a programming language that compiles to WhiteSpace.
Author: Bence Skorka
License-Expression: MIT
Classifier: Development Status :: 3 - Alpha
Classifier: Environment :: Console
Requires-Python: >=3.12
Description-Content-Type: text/markdown
License-File: LICENSE
Provides-Extra: build
Requires-Dist: pip-tools; extra == "build"
Requires-Dist: setuptools; extra == "build"
Requires-Dist: twine; extra == "build"
Provides-Extra: publish
Requires-Dist: twine; extra == "publish"
Provides-Extra: types
Requires-Dist: types-mock; extra == "types"
Provides-Extra: test
Requires-Dist: black; extra == "test"
Requires-Dist: mock; extra == "test"
Requires-Dist: mypy; extra == "test"
Requires-Dist: pytest-cov; extra == "test"
Requires-Dist: pytest-mock; extra == "test"
Requires-Dist: pytest-mypy; extra == "test"
Requires-Dist: pytest-timeout; extra == "test"
Requires-Dist: pytest; extra == "test"
Provides-Extra: dotenv
Requires-Dist: python-dotenv; extra == "dotenv"
Dynamic: license-file

# BlackSpace

BlackSpace is a small programming language that compiles to [Whitespace](https://esolangs.org/wiki/Whitespace).
It provides a readable surface syntax, parses `.bsp` source files into an AST, and then emits Whitespace code.

## Status

The project currently supports:

- hand-written lexer and parser
- functions and recursion
- local variables and parameters
- arithmetic, boolean, and comparison expressions
- arrays and strings
- `if` / `else`
- `while`, `do ... while`, and `for`
- built-in input/output expressions

The compiler entry point expects a `main` function:

- the entry function name must be `main`
- `main` must not take parameters
- `main` must return `void`

## Language Overview

BlackSpace programs are made of function definitions.

### Functions

Function syntax:

```blackspace
fn fib(n: int) -> int {
    if (n <= 0) {
        return 0;
    } else if (n <= 1) {
        return 1;
    } else {
        return fib(n - 1) + fib(n - 2);
    }
}
```

Functions may optionally declare locals in a declaration block placed between the return type and the body:

```blackspace
fn main() -> void [
    var n: int,
    var result: int
] {
    n = read_int();
    result = fib(n);
    print_int(result);
}
```

Notes:

- top level contains only function definitions
- the local declaration block is optional
- if a function has no locals, omit the declaration block entirely
- empty `[]` is not used for "no locals"

### Types

Currently supported types:

- `int`
- `bool`
- `string`
- `void`
- array types such as `int[]` and `int[][]`

`void` is valid for function return types, but not for parameters or variables.

### Variables

Parameters are written as:

```blackspace
n: int
```

Local declarations use:

```blackspace
var value: int
const limit: int
```

`var` creates a mutable variable, `const` creates an immutable one.

### Statements

Supported statement forms include:

```blackspace
x = 1;
return;
return x + 1;
if (x < 10) { ... } else { ... }
while (x < 10) { ... }
do { ... } while (x < 10)
for (i = 0; i < n; i = i + 1) { ... }
myfunc();
;
```

Notes:

- assignment statements end with `;`
- expression statements are allowed and become void statements internally
- `do ... while` does not require a trailing semicolon
- `;` by itself is a valid empty statement

### Expressions

Supported expression forms include:

- integer, boolean, and string literals
- variable usage
- function calls
- array indexing
- parenthesized expressions
- unary operators: `-`, `!`
- binary operators:
  - `*`, `/`, `%`
  - `+`, `-`
  - `<`, `<=`, `>`, `>=`
  - `==`, `!=`
  - `&&`, `||`

Examples:

```blackspace
fib(n - 1) + fib(n - 2)
arr[i + 1]
!(a < b)
```

### Built-in Functions

Some names are handled as built-ins rather than normal user-defined function calls:

```blackspace
read_int()
read_text()
print_int(expr)
print_text(expr)
sizeof(expr)
```

Examples:

```blackspace
n = read_int();
print_int(fib(n));
print_text("done\n");
```

Notes:

- `read_int()` reads a number
- `read_text()` currently reads a single character value
- `print_int(expr)` prints numbers
- `print_text(expr)` prints strings and character-like integer values as text

## Example Programs

Iterative Fibonacci:

```blackspace
fn main() -> void [
    var n: int,
    var a: int,
    var b: int,
    var c: int,
    var i: int
] {
    n = read_int();
    a = 0;
    b = 1;
    c = 0;

    for (i = 0; i < n; i = i + 1) {
        c = a + b;
        a = b;
        b = c;
    }

    print_int(a);
}
```

Recursive Fibonacci:

```blackspace
fn fib(n: int) -> int {
    if (n <= 0) {
        return 0;
    } else if (n <= 1) {
        return 1;
    } else {
        return fib(n - 1) + fib(n - 2);
    }
}

fn main() -> void {
    print_int(fib(read_int()));
}
```

## Compiler Usage

After installing the project, the compiler is available as:

```bash
blackspace input.bsp -o output.ws
```

You can also run it as a module:

```bash
python -m blackspace_compiler input.bsp -o output.ws
```

Arguments:

- `input_file`: path to the BlackSpace source file
- `-o`, `--output`: path to write the generated Whitespace program
- `--disable-optimizations`: disables the compiler's optimization-related behavior

Example:

```bash
blackspace blackspace_compiler/__tests__/scripts/fib_iterative.bsp -o fib.ws
```

By default the output file is named `a.out`.
