diff --git a/bootstrap/makefile b/bootstrap/makefile index 0654872..952794a 100644 --- a/bootstrap/makefile +++ b/bootstrap/makefile @@ -1,5 +1,13 @@ -.ty/token.o: - ty obj src/token.ty +SRCS := $(wildcard src/*.ty) +OBJS := $(patsubst src/%.ty,.ty/%.o,$(SRCS)) + +all: $(OBJS) + echo $(OBJS) + echo $(SRCS) + touch .ty/all + +$(OBJS): $(SRCS) + ty obj $< .PHONY: clean clean: diff --git a/bootstrap/src/lexer.ty b/bootstrap/src/lexer.ty new file mode 100644 index 0000000..f2a6b7a --- /dev/null +++ b/bootstrap/src/lexer.ty @@ -0,0 +1,47 @@ +const Token = import "token.Token" +pub const TokenError = import "token.TokenError" +const get_next = import "token.get_next" + +pub type Lexeme = struct { + token: Token, + slice: [char], + start: u32, + end: u32 +} + +pub type Lexer = struct { + current: ?Lexeme, + buffer: &[char], + idx: u32, +} + +pub const new = fn(buffer: &[char]) Lexer { + return Lexer { + buffer: buffer, + current : undefined, + idx: 0 + } +} + +pub const peek = fn(self: *Lexer) TokenError!?Lexeme { + if (self.current) { + return clone self.current + } + let len = 0 + let end = self.buf.len() + let result = try get_next(self.buf[self.idx..end], *len)? + self.current = Lexeme { + token: result, + slice: clone self.buf[self.idx..len], + start: self.idx, + end: len + } + self.idx += len + return clone self.current +} + +pub const collect = fn(self: *Lexer) Lexeme { + let temp = clone self.current.unwrap() + self.current = undefined + return temp +} diff --git a/bootstrap/src/token.ty b/bootstrap/src/token.ty index 4115518..4b80147 100644 --- a/bootstrap/src/token.ty +++ b/bootstrap/src/token.ty @@ -302,10 +302,11 @@ const build_string = fn(buf: &[char], len: *u32, end: char) TokenError!Token { } return Token.String } -pub const get_next = fn(buf: &[char], len: *u32) TokenError!Token { + +pub const get_next = fn(buf: &[char], len: *u32) TokenError!?Token { len = 0 const c = buf[0] - return match (c) { + return match (c?) { c.isAlphabetic() => tokenize_chars(buf, len) c.isDigit() => tokenize_num(buf, len) _ => { diff --git a/linter/src/lib.rs b/linter/src/lib.rs index abfd644..eb454ff 100644 --- a/linter/src/lib.rs +++ b/linter/src/lib.rs @@ -77,6 +77,7 @@ impl<'buf, 'ttb, 'sco> LintSource<'buf, 'ttb, 'sco> { Expr::UnOp(un) => match un.op.token { Token::Dash => self.check_negate(un), Token::Exclam => self.check_not(un), + Token::Try => self.check_try(un), Token::Ampersand => self.check_borrow_ro(un), Token::Asterisk => self.check_borrow_mut(un), Token::Copy => self.check_copy(un), @@ -112,6 +113,7 @@ impl<'buf, 'ttb, 'sco> LintSource<'buf, 'ttb, 'sco> { Expr::ArgDef(arg) => self.check_arg_def(&arg), Expr::ArrayType(arr) => self.check_array_type(&arr), Expr::ArrayAccess(arr) => self.check_array_access(&arr), + Expr::UndefBubble(u) => self.check_undefined_bubble(&u), _ => panic!("type-lang linter issue, expr not implemented {:?}", to_cmp), } } @@ -750,16 +752,22 @@ impl<'buf, 'ttb, 'sco> LintSource<'buf, 'ttb, 'sco> { return ok_tree!(Copy, unop, curried); } + pub fn check_undefined_bubble(&mut self, un: &UndefBubble) -> ResultTreeType { + let result = self.lint_recurse(&un.prev)?; + let unop = UnaryOp { + val: result.0, + curried: result.1, + }; + let curried = unop.curried.clone(); + return ok_tree!(BubbleUndef, unop, curried); + } + pub fn check_clone(&mut self, un: &UnOp) -> ResultTreeType { let result = self.lint_recurse(&un.val)?; - let mut unop = UnaryOp { + let unop = UnaryOp { val: result.0, curried: result.1, }; - match unop.val.as_ref().as_ref() { - TypeTree::BoolValue(_) => unop.curried = Ty::Bool, - _ => panic!("clone check failed"), - } let curried = unop.curried.clone(); return ok_tree!(Clone, unop, curried); } @@ -896,6 +904,16 @@ impl<'buf, 'ttb, 'sco> LintSource<'buf, 'ttb, 'sco> { return ok_tree!(NotEq, binop, curried); } + pub fn check_try(&mut self, un: &UnOp) -> ResultTreeType { + let result = self.lint_recurse(&un.val)?; + let unop = UnaryOp { + val: result.0, + curried: result.1, + }; + let curried = unop.curried.clone(); + return ok_tree!(BubbleError, unop, curried); + } + pub fn check_not(&mut self, un: &UnOp) -> ResultTreeType { let result = self.lint_recurse(&un.val)?; let mut unop = UnaryOp { diff --git a/parser/src/lib.rs b/parser/src/lib.rs index 2ac90fc..72453b1 100644 --- a/parser/src/lib.rs +++ b/parser/src/lib.rs @@ -745,7 +745,6 @@ impl<'s> Parser<'s> { ]) { match x.token { Token::Question => self.resolve_access(expr!(UndefBubble, prev)), - Token::Try => self.resolve_access(expr!(ErrBubble, prev)), Token::Period => { let ident = self .ident() diff --git a/types/src/lib.rs b/types/src/lib.rs index b0cf2a0..21529f8 100644 --- a/types/src/lib.rs +++ b/types/src/lib.rs @@ -230,9 +230,9 @@ pub enum TypeTree { Range(BinaryOp), CastAs(BinaryOp), Gt(BinaryOp), - BubbleUndef(BinaryOp), - BubbleError(BinaryOp), // unops + BubbleUndef(UnaryOp), + BubbleError(UnaryOp), ReadBorrow(UnaryOp), MutBorrow(UnaryOp), Copy(UnaryOp),