22a35394237d28e7d4f8f89d772e038571cfe223 — Martin Angers 8 months ago 629e087
declarations work
4 files changed, 130 insertions(+), 1 deletions(-)

A codegen/array.ssa
A codegen/literal_string.ssa
A syntax/declarations.snow
M syntax/overview.snow
A codegen/array.ssa => codegen/array.ssa +31 -0
@@ 0,0 1,31 @@
+data $fmt = { b "%d\n", b 0 }
+
+export function w $main() {
+@start
+  %ar =l alloc4 16          # allocate array [4]i32
+  %i =l add 0, 0
+  %max =l add 4, 0
+
+@assignloop
+  %off =l mul 4, %i
+  %addr =l add %off, %ar
+  storew %i, %addr
+  %i =l add 1, %i
+  %loop =l sub %max, %i
+  jnz %loop, @assignloop, @print
+
+@print
+  %i =l add 0, 0
+  %max =l add 4, 0
+@printloop
+  %off =l mul 4, %i
+  %addr =l add %off, %ar
+  %val =w loadw %addr
+  call $printf(l $fmt, w %val)
+  %i =l add 1, %i
+  %loop =l sub %max, %i
+  jnz %loop, @printloop, @end
+
+@end
+  ret 0
+}

A codegen/literal_string.ssa => codegen/literal_string.ssa +12 -0
@@ 0,0 1,12 @@
+# Define the string constant.
+data $str = { b "hello world", b 0 }
+
+export function w $main() {
+@start
+        call $puts(l $str)
+        %w =l add $str, 6
+        call $puts(l %w)
+        storeb 62, %w
+        call $puts(l %w)
+        ret 0
+}

A syntax/declarations.snow => syntax/declarations.snow +82 -0
@@ 0,0 1,82 @@
+## Variables
+
+# mutable
+var name type
+# immutable
+let name type
+
+## Types
+
+# structs declare a collection of fields
+struct Name {..}
+# enums declare fields where only one is active at a time
+enum Name {..}
+# protocols declare a "template" of fields, methods and extensions
+# TODO: can an enum match a protocol other than via methods?
+protocol Name {..}
+
+# There is no special way to declare an alias for built-in
+# types or any other type, just declare a struct with a single
+# field of that type, although it won't be compatible, e.g:
+struct Rune { var value i32 }
+
+# There is no special way to declare a tuple, except for a special
+# short syntax for anonymous structs and fields. Such a struct
+# can only access its fields via indices as field names:
+let aTuple struct { int, str } = {1, "a"}
+let age, name = aTuple.0, aTuple.1
+# TODO: syntax sugar, anonymous structs can be created via literals:
+let anotherTuple {int, bool, str} = {1, true, "b"}
+let nestedTuple {int, {bool, str}} = {1, {false, "c"}}
+assert(nestedTuple.1.1 == "c")
+
+# struct fields have their own static mutability, so even a mutable variable
+# of a given struct type may not change immutable fields.
+
+# All types can have methods (even protocols), and an implicit
+# `self` of the current type is available in the method. Unqualified
+# symbols resolve to self automatically, so it isn't required to
+# use `self` most of the time.
+
+# There are no classes, no inheritance, but to ease satisfying
+# the protocols, there is struct embedding, much like Go. When
+# using this, the fields and methods of the embedded struct are
+# seen as belonging to the container struct, unless conflicting
+# members exist in the container struct. Probably cannot embed
+# an unnamed tuple (no way to access it in case of conflict, no
+# name).
+
+## Functions
+
+# function/method statements (label can be "_")
+fn name(label name type[, label name type ...]) type {
+  # can only return a single value, because tuple-like structs
+}
+
+# closures/lambdas, longer form
+let func = (name type, name type) { ... }
+# short form for single-expression implicit return, the arguments
+# are provided on the "_" tuple.
+let shortFunc = (type, type) => _.0 + _.1
+# if the arguments (number and types) can be inferred:
+let inferredFunc = (_) => _.0 + _.1
+
+## Arrays and Slices
+
+# arrays are stack-allocated, value types
+# TODO: actually, *where* it's allocated should depend on whether
+# `new` is called, and not on the type itself?
+var arrayOfFour [4]int
+let arrayOfArrays [3][5]str
+arrayOfFour = [1, 2, 3, 4]
+
+# TODO: slices... Bounds-checking and all. Can probably be a runtime
+# implementation, and syntax sugar so that [] literals can create
+# slices. E.g. let ar = [...] creates arrays (immutable), while
+# var ar = [...] creates slices (mutable)?
+
+## Maps
+
+# purely runtime-implemented (i.e. no compiler magic), but syntax
+# sugar so that [:] literals can create maps?
+

M syntax/overview.snow => syntax/overview.snow +5 -1
@@ 8,7 8,11 @@ mod example
 # it may be specified without quotes; otherwise, the import path is
 # specified in quotes and resolved based on the compiler's module
 # search path.
-import http, json, "github.com/some3rdparty/other"
+import (
+  http
+  json
+  "github.com/some3rdparty/other"
+)
 
 # This is a single-line comment. There is no multiline comment.