wip more array defs
This commit is contained in:
parent
4e9f3973a4
commit
1ec9f7a2d1
4
common.h
4
common.h
|
|
@ -38,8 +38,8 @@ struct symbol_s {
|
|||
u32 ref; /* either constant value or pointer to other thing */
|
||||
u32 size; /* either size of the plex or length of the array/list/etc. */
|
||||
u32 scope; /* scope ref */
|
||||
List *args; /* function params or plex constructor args */
|
||||
List *fields; /* either plex variable fields, or method signatures */
|
||||
List *args; /* function params or plex constructor args or array dimensions */
|
||||
List *fields; /* either plex variable fields, or method signatures or array strides */
|
||||
};
|
||||
|
||||
void *node_value(Node *n);
|
||||
|
|
|
|||
113
compiler.c
113
compiler.c
|
|
@ -2,6 +2,7 @@
|
|||
#include "common.h"
|
||||
#include "emit.h"
|
||||
#include "lexer.h"
|
||||
#include "libc.h"
|
||||
#include "list.h"
|
||||
|
||||
Emitter emitter = {0};
|
||||
|
|
@ -257,6 +258,67 @@ define_function()
|
|||
fn->size = size;
|
||||
}
|
||||
|
||||
void
|
||||
calculate_strides(List *dims, List *strides)
|
||||
{
|
||||
u32 *num;
|
||||
u32 i;
|
||||
u32 num_dims = dims->count;
|
||||
u32 current_stride = 1;
|
||||
|
||||
if (num_dims == 1) {
|
||||
List_push(arena, strides, ¤t_stride, sizeof(u32));
|
||||
return;
|
||||
}
|
||||
|
||||
for(i = num_dims - 1; i > 0; i--) {
|
||||
List_push(arena, strides, ¤t_stride, sizeof(u32));
|
||||
|
||||
/* this is very slow but for small numbers of dimensions its fine */
|
||||
num = (u32*)List_get(dims, i);
|
||||
if (num){
|
||||
current_stride *= (*num);
|
||||
} else {
|
||||
emitter.error("Tried to get a dimension that did not exist", 43, parser.previous.line);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
define_array()
|
||||
{
|
||||
i32 size = 0, n = 0, flat_array_length = 1;
|
||||
TokenType tt = parser.previous.type;
|
||||
SymbolType st = token_type_to_sym_type(tt);
|
||||
Symbol *array;
|
||||
|
||||
List *dims = List_init(arena);
|
||||
List *strides = List_init(arena);
|
||||
advance();
|
||||
|
||||
while(!match(TOKEN_RBRACKET)) {
|
||||
if(parser.current.type == TOKEN_LITERAL_INT) {
|
||||
n = ston(parser.current.start, parser.current.length);
|
||||
flat_array_length *= n;
|
||||
List_push(arena, dims, &n, sizeof(u32));
|
||||
}
|
||||
advance();
|
||||
if(check(TOKEN_LBRACKET)) break;
|
||||
if(check(TOKEN_COMMA)) {
|
||||
/* it is a multidimensional array */
|
||||
}
|
||||
}
|
||||
|
||||
size = emitter.get_size(st) * flat_array_length;
|
||||
|
||||
array = scope_add_symbol(parser.current.start, parser.current.length,
|
||||
SYMBOL_ARRAY, size);
|
||||
array->secondary_type = st;
|
||||
calculate_strides(dims, strides);
|
||||
array->args = dims;
|
||||
array->fields = strides;
|
||||
}
|
||||
|
||||
void
|
||||
build_symbol_table(char *source)
|
||||
{
|
||||
|
|
@ -276,6 +338,12 @@ build_symbol_table(char *source)
|
|||
define_plex();
|
||||
} else if(match(TOKEN_KEYWORD_TRAIT)) {
|
||||
define_trait();
|
||||
} else if (parser.current.type >= TOKEN_TYPE_I8 &&
|
||||
parser.current.type <= TOKEN_TYPE_PTR) {
|
||||
advance();
|
||||
if (check(TOKEN_LBRACKET)) {
|
||||
define_array();
|
||||
}
|
||||
} else {
|
||||
/* in binary bytecode output mode we need to count the bytes here */
|
||||
/* otherwise ignore everything */
|
||||
|
|
@ -291,29 +359,6 @@ ParseRule *get_rule(TokenType type);
|
|||
void parse_precedence(Precedence precedence);
|
||||
|
||||
|
||||
void
|
||||
calculate_strides(i32 *dims, i32 num_dims, i32 *out_strides)
|
||||
{
|
||||
i32 i;
|
||||
i32 current_stride = 1;
|
||||
|
||||
for(i = num_dims - 1; i >= 0; i--) {
|
||||
out_strides[i] = current_stride;
|
||||
current_stride *= dims[i];
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
define_array()
|
||||
{
|
||||
/* example
|
||||
i32 dims[3] = {3, 3, 3};
|
||||
i32 strides[3];
|
||||
|
||||
calculate_strides(dims, 3, strides);
|
||||
*/
|
||||
}
|
||||
|
||||
u32
|
||||
variable_declaration(Symbol *def)
|
||||
{
|
||||
|
|
@ -322,33 +367,17 @@ variable_declaration(Symbol *def)
|
|||
SymbolType st = token_type_to_sym_type(tt);
|
||||
Symbol *variable;
|
||||
|
||||
bool is_array = false;
|
||||
i32 current_stride = 1;
|
||||
List *strides;
|
||||
|
||||
if(parser.current.type == TOKEN_LBRACE) {
|
||||
is_array = true;
|
||||
strides = List_init(arena);
|
||||
|
||||
if (parser.current.type == TOKEN_LBRACE) {
|
||||
while(!check(TOKEN_RBRACKET)) {
|
||||
if(parser.previous.type == TOKEN_LITERAL_NAT) {
|
||||
/* consume dimension if exists */
|
||||
}
|
||||
advance();
|
||||
if(check(TOKEN_LBRACKET)) break;
|
||||
advance();
|
||||
if(check(TOKEN_COMMA)) {
|
||||
/* it is a multidimensional array */
|
||||
}
|
||||
}
|
||||
}
|
||||
USED(is_array);
|
||||
|
||||
if(st != SYMBOL_UNDEFINED) {
|
||||
size = emitter.get_size(st);
|
||||
|
||||
variable =
|
||||
scope_add_symbol(parser.current.start, parser.current.length, st, size);
|
||||
variable = scope_add_symbol(parser.current.start, parser.current.length, st, size);
|
||||
|
||||
if(!def && (parser.pass == 0)) return size;
|
||||
|
||||
if(def) {
|
||||
|
|
|
|||
|
|
@ -16,34 +16,10 @@ It is short for "Undarsċieppan" The name comes from the Proto-West-Germanic wor
|
|||
:PROPERTIES:
|
||||
:CUSTOM_ID: undar-grammar-and-specification
|
||||
:END:
|
||||
** Plexs
|
||||
|
||||
** Primitive Types
|
||||
:PROPERTIES:
|
||||
:CUSTOM_ID: plexs
|
||||
:END:
|
||||
- A =plex= is a container for primitive types.
|
||||
- Not a class: no inheritance, no vtables
|
||||
- Methods are functions with implicit =this= argument
|
||||
|
||||
#+begin_src ul
|
||||
plex «token» {
|
||||
init() {
|
||||
// values
|
||||
}
|
||||
}
|
||||
|
||||
// example
|
||||
plex Vec3 {
|
||||
init(real x, real y, real z) {
|
||||
this.x = x;
|
||||
this.y = z;
|
||||
this.y = z;
|
||||
}
|
||||
}
|
||||
#+end_src ul
|
||||
|
||||
*** Substantial Plexs
|
||||
:PROPERTIES:
|
||||
:CUSTOM_ID: substantial-plexs
|
||||
:CUSTOM_ID: primitive-types
|
||||
:END:
|
||||
|
||||
| Type | Description |
|
||||
|
|
@ -127,7 +103,13 @@ if («token» is real) {
|
|||
}
|
||||
#+end_src ul
|
||||
|
||||
also used for letting constants
|
||||
checks if a atom's plex contains the fields inside of a trait
|
||||
|
||||
#+begin_src ul
|
||||
if («token» is [Tunnel, Drawable]) {
|
||||
print("im tunnel-able and draw-able");
|
||||
}
|
||||
#+end_src ul
|
||||
|
||||
=as=
|
||||
|
||||
|
|
@ -140,18 +122,10 @@ some_functon(«token» as real); // needs a real
|
|||
|
||||
=in=
|
||||
|
||||
checks if a atom's plex contains the fields inside of a trait
|
||||
used inside of the for loops
|
||||
|
||||
#+begin_src ul
|
||||
if («token» in Tunnel, Drawable) {
|
||||
print("im tunnel-able and draw-able");
|
||||
}
|
||||
#+end_src ul
|
||||
|
||||
also used inside of the for loops
|
||||
|
||||
#+begin_src ul
|
||||
for («token» in «collection») { «body» }
|
||||
for («type» «token» in «collection») { «body» }
|
||||
#+end_src ul
|
||||
|
||||
** Control flow
|
||||
|
|
@ -170,7 +144,7 @@ for («variable» in «collection») { «body» }
|
|||
iterates through each atom in the collection setting it to variable
|
||||
|
||||
#+begin_src ul
|
||||
for («variable» = initial_value; end_value; increment) { «body» }
|
||||
for («type» «variable» = initial_value; «boolean expression»; «increment») { «body» }
|
||||
#+end_src ul
|
||||
|
||||
loops from initial value to end value by increment value (like a for loop in other languages)
|
||||
|
|
@ -248,6 +222,35 @@ Array of a specific plex
|
|||
«plex»[«length»] «variable» = [val1, val2, ...];
|
||||
#+end_src ul
|
||||
|
||||
** Plexs
|
||||
:PROPERTIES:
|
||||
:CUSTOM_ID: plexs
|
||||
:END:
|
||||
- A =plex= is a container for primitive types.
|
||||
- Not a class: no inheritance, no vtables
|
||||
- Methods are functions with implicit =this= argument
|
||||
|
||||
#+begin_src ul
|
||||
plex «token» {
|
||||
init() {
|
||||
// values
|
||||
}
|
||||
}
|
||||
|
||||
// example
|
||||
plex Vec3 {
|
||||
real x;
|
||||
real y;
|
||||
real z;
|
||||
|
||||
init(real x, real y, real z) {
|
||||
this.x = x;
|
||||
this.y = y;
|
||||
this.z = z;
|
||||
}
|
||||
}
|
||||
#+end_src ul
|
||||
|
||||
** Tunnel :WIP:
|
||||
:PROPERTIES:
|
||||
:CUSTOM_ID: tunnel-1
|
||||
|
|
|
|||
78
libc.c
78
libc.c
|
|
@ -328,3 +328,81 @@ real_to_string(Arena *a, r32 q)
|
|||
return ascpy(a, buffer + i, MAX_LEN_REAL32 - i);
|
||||
}
|
||||
|
||||
bool
|
||||
is_digit(char c)
|
||||
{
|
||||
return c >= '0' && c <= '9';
|
||||
}
|
||||
|
||||
bool
|
||||
is_space(char c)
|
||||
{
|
||||
switch(c) {
|
||||
case ' ':
|
||||
case '\r':
|
||||
case '\t':
|
||||
case '\v':
|
||||
case '\f':
|
||||
case '\n':
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
i32
|
||||
stoi(const char *str, u32 length)
|
||||
{
|
||||
bool neg = false;
|
||||
i32 n = 0;
|
||||
|
||||
while (is_space(*str)) {
|
||||
if (length-- == 0) return n;
|
||||
str++;
|
||||
}
|
||||
|
||||
if (*str == '-') {
|
||||
neg = true;
|
||||
if (length-- == 0) return n;
|
||||
str++;
|
||||
}
|
||||
|
||||
while (is_digit(*str) && length-- > 0) {
|
||||
int digit = *str++ - '0';
|
||||
|
||||
if (neg) {
|
||||
if (n < (I32_MIN / 10) || (n == (I32_MIN / 10) && digit > -(I32_MIN % 10))) {
|
||||
return I32_MIN;
|
||||
}
|
||||
n = n * 10 - digit;
|
||||
} else {
|
||||
if (n > (I32_MAX / 10) || (n == (I32_MAX / 10) && digit > (I32_MAX % 10))) {
|
||||
return I32_MAX;
|
||||
}
|
||||
n = n * 10 + digit;
|
||||
}
|
||||
}
|
||||
|
||||
return neg ? -n : n;
|
||||
}
|
||||
|
||||
u32
|
||||
ston(const char *str, u32 length)
|
||||
{
|
||||
u32 n = 0;
|
||||
|
||||
while (is_space(*str)) {
|
||||
if (length-- == 0) return n;
|
||||
str++;
|
||||
}
|
||||
|
||||
while (is_digit(*str) && length-- > 0) {
|
||||
int digit = *str++ - '0';
|
||||
|
||||
if (n > (U32_MAX / 10) || (n == (U32_MAX / 10) && digit > (U32_MAX % 10))) {
|
||||
return U32_MAX;
|
||||
}
|
||||
n = n * 10 + digit;
|
||||
}
|
||||
|
||||
return n;
|
||||
}
|
||||
|
|
|
|||
6
libc.h
6
libc.h
|
|
@ -57,7 +57,7 @@ typedef u8 bool;
|
|||
#define I16_MAX 32767
|
||||
#define U16_MAX 65535
|
||||
|
||||
#define I32_MIN -2147483648
|
||||
#define I32_MIN -2147483647
|
||||
#define I32_MAX 2147483647
|
||||
#define U32_MAX 4294967295
|
||||
|
||||
|
|
@ -66,7 +66,7 @@ typedef u8 bool;
|
|||
#define AS_INT(v) ((i32)(v))
|
||||
#define AS_NAT(v) ((u32)(v))
|
||||
#define AS_REAL(v) ((i32)(v))
|
||||
#define FLOAT_TO_REAL(v) (((i32)(v)) * FIXED_CONST)
|
||||
#define FLOAT_TO_REAL(v) ((i32)((v) * FIXED_CONST))
|
||||
#define REAL_TO_FLOAT(v) (((f32)(v)) / FIXED_CONST)
|
||||
|
||||
#define USED(x) ((void)(x))
|
||||
|
|
@ -132,5 +132,7 @@ r32 real_abs(r32 f);
|
|||
char *int_to_string(Arena *a, i32 v);
|
||||
char *nat_to_string(Arena *a, u32 v);
|
||||
char *real_to_string(Arena *a, r32 q);
|
||||
i32 stoi(const char *str, u32 len);
|
||||
u32 ston(const char *str, u32 len);
|
||||
|
||||
#endif
|
||||
|
|
|
|||
|
|
@ -2,17 +2,16 @@
|
|||
nat[6] fixed_size = [1, 2, 3, 4, 5, 6];
|
||||
|
||||
nat i = 0;
|
||||
nat len = array.length;
|
||||
while (i < len) {
|
||||
print(array[i] as str);
|
||||
print("\n");
|
||||
while (i < fixed_size.length) {
|
||||
print(fixed_size[i] as str);
|
||||
print(" ");
|
||||
i = i + 1;
|
||||
}
|
||||
print("\n");
|
||||
|
||||
for (i in array) {
|
||||
print(i as str);
|
||||
print("\n");
|
||||
}
|
||||
// for (i in fixed_size) {
|
||||
// print(i as str);
|
||||
// print("\n");
|
||||
// }
|
||||
|
||||
halt;
|
||||
|
|
|
|||
|
|
@ -17,12 +17,12 @@ bool found = false;
|
|||
for (nat x = 0; x < xSize; x++) {
|
||||
for (nat y = 0; y < ySize; y++) {
|
||||
for (nat z = 0; z < zSize; z++) {
|
||||
if (matrix[x][y][z] == 0) {
|
||||
print("found: [");
|
||||
if (matrix[x, y, z] == 0) {
|
||||
print("found '0' at [");
|
||||
print(x as str);
|
||||
print(",");
|
||||
print(", ");
|
||||
print(y as str);
|
||||
print(",");
|
||||
print(", ");
|
||||
print(z as str);
|
||||
print("]\n");
|
||||
found = true;
|
||||
|
|
|
|||
|
|
@ -47,7 +47,7 @@ System system = devmap(0x00, System);
|
|||
Screen screen = devmap(0x20, Screen);
|
||||
screen.vector = ref render_screen;
|
||||
Mouse mouse = devmap(0x90, Mouse);
|
||||
mouse.vector = ref render_screen;
|
||||
mouse.vector = ref on_mouse_down;
|
||||
halt;
|
||||
|
||||
function on_mouse_down() {
|
||||
|
|
|
|||
Loading…
Reference in New Issue