opened
adam-mcdaniel
username_0
Implemented conditional compilation, user compiler errors, and the extern flag
issue
created
kevinramharak
username_1
Wow this is looking promising
comment
created
adam-mcdaniel
username_0
This pull request introduces _**several**_ breaking changes. Here's a comprehensive list.

- The `==`, `!=`, `>`, `<`, `>=`, and `<=` operators for constant expressions (the `==` and `!=` operators are not yet implemented for non-constants expressions)
- The `isdef` constant operator used to determine whether or not a constant is defined. This is intended to make the Oak equivalent of C header files possible.
```rust
// example usage of isdef
// If `TEST_H` is not defined, compile the following code.
#[if(!isdef("TEST_H")) {
    const TEST_H = 1;
    fn test() {
        putstrln("conditional compilation!");
    }
}]
```
- Constants can be defined in any order.
- The `Target` trait has a new method, `get_name(&self) -> char`, which returns a character representing the name of the target. For example, the `C` target returns the character `'c'`, and the `Go` target returns the character `'g'`.
- The predefined `TARGET` constant specifies the output target being used by returning the Target specified name character.
- Added the `#[if(CONSTANT_EXPRESSION) { // oak code }]` and the  `#[if(CONSTANT_EXPRESSION) { // if oak code } else { // else oak code }]` flags for conditional compilation.
- The `extern` flag allows users to specify which FFI files to include.
```rust
// example usage of extern flag
#[if(TARGET == 'c') {
    // if the target is C, include the C version
    #[extern("foreign.c")]
} else {
    // if the target is Go, include the Go version
    #[extern("foreign.go")]
}]

fn test() { test!() }

fn main() -> void {
    test();
}
```
- The `-f` command line argument flag has been removed because of the `extern` flag.
comment
created
kevinramharak
username_1
Do you think a character is enough? It feels a bit limited. Other than that this seems like good progess.
comment
created
adam-mcdaniel
username_0
I definitely think a character is enough. Surely there's no way we can exhaust the 95 printable characters, right? Also, the `HirConstant` structure only supports data of size `1`, so the only other alternative is a float, which seems less intuitive.
comment
created
adam-mcdaniel
username_0
I'm incredibly surprised at how quickly this is coming together. The robustness of the HIR and MIR implementations make it so much easier to add features than I anticipated.
comment
created
kevinramharak
username_1
:D yeah I guess that should be enough. Just need to make sure there are no conflicts.

Yeah thats what I like about this project. Its architecture make it very easy to understand and work with. I have no idea how most of it works, but I don't have to since I can focus on the part that interfaces with the target for now. I am also looking forward to optimization passes. I have noticed a few patterns that seem redundant like a store then a load of the same value again.
comment
created
adam-mcdaniel
username_0
Yes, because the resulting ASM instructions are so simple, it should be incredibly easy to do some low-level optimization. Additionally, the structure of the MIR should make high level optimizations a breeze, too. I'm very excited. I want to thoroughly vet the soundness of the type system and the rest of the compilation process before tackling this, though.
comment