From bf5efb53929020ddde36f84381c859446f13ecb2 Mon Sep 17 00:00:00 2001 From: subkey <2822448396@qq.com> Date: Fri, 22 Mar 2024 05:45:46 +0800 Subject: [PATCH] =?UTF-8?q?refact:=20=E7=BB=9F=E4=B8=80=E4=BA=86err?= =?UTF-8?q?=E5=92=8Cpanic?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- samples/helloworld.ks | 7 +- src/main.rs | 24 ++-- src/native.rs | 2 +- src/primitive/buf.rs | 239 ++++++++++++++++++++++++++++++++++++++-- src/primitive/func.rs | 16 ++- src/primitive/mod.rs | 12 +- src/primitive/obj.rs | 26 ++--- src/runtime/calc.rs | 113 +++++++++---------- src/runtime/call.rs | 49 ++++---- src/runtime/evil.rs | 18 +-- src/runtime/externer.rs | 8 +- src/runtime/mod.rs | 22 +--- src/scan/expr.rs | 14 +-- src/scan/literal.rs | 32 +++--- src/scan/mod.rs | 26 ++--- src/scan/stmt.rs | 90 ++++++--------- 16 files changed, 436 insertions(+), 262 deletions(-) diff --git a/samples/helloworld.ks b/samples/helloworld.ks index 344ce33..dbd56d1 100644 --- a/samples/helloworld.ks +++ b/samples/helloworld.ks @@ -3,12 +3,13 @@ //mod D:\code\rs\key-lang\samples\testmod.ks> m; class a { - a, + a! .t(v) { log(v,t) } } -let a = '{ff aa da}'; -a.push(29u) +let a = '{00 01 02 03 04 05}'; +a.copy_within(2,6,1) log(a) + diff --git a/src/main.rs b/src/main.rs index 03200da..510c796 100644 --- a/src/main.rs +++ b/src/main.rs @@ -13,19 +13,23 @@ mod utils; mod c; mod native; +static mut LINE:usize = 0; + fn main()-> ExitCode { - // 自定义panic - // std::panic::set_hook(Box::new(|inf| { - // let str = inf.payload().downcast_ref::(); - // if let Some(s) = str { - // println!("\n> {}\n\n> Key Script CopyLeft by Subkey\n {}\n", s, utils::date()); - // }else { - // println!("\n{}\n\nKey Script CopyLeft by Subkey\n{}\n", inf, utils::date()); - // } - // })); + // 自定义报错 + std::panic::set_hook(Box::new(|inf| { + use crate::utils::date; + let line = unsafe{LINE}; + let s = if let Some(payload) = inf.payload().downcast_ref::<&'static str>() { + payload + }else {"错误"}; + println!("\n> {}\n 第{}行\n\n> Key Script CopyLeft by Subkey\n {}\n", s, line, date()); + })); // 基本类型的方法,也就是所有litr的prop - // 方法必须直接调用,不能作为值使用 (get_prop做成prop_getter, setter直接重做不要依赖get_prop的*mut) + // @index_set @next之类的 + // obj之类的to_str + // push之类的方法要注意outlive // str::next_char(start) // let [] = x // let a=0,b=0 diff --git a/src/native.rs b/src/native.rs index b95e240..64ddcec 100644 --- a/src/native.rs +++ b/src/native.rs @@ -94,7 +94,7 @@ pub struct BoundNativeMethod { } fn err(s:&str)->! { - panic!("{} \n 运行时({})", s, unsafe{crate::runtime::LINE}) + panic!("{s}") } pub fn parse(path:&[u8])-> Result<*const NativeMod, String> { diff --git a/src/primitive/buf.rs b/src/primitive/buf.rs index 1c16fcf..aab4502 100644 --- a/src/primitive/buf.rs +++ b/src/primitive/buf.rs @@ -1,10 +1,22 @@ + use super::*; -pub fn method(v:&mut Vec, name:Interned, args:Vec)-> Litr { +pub fn method(v:&mut Vec, scope:Scope, name:Interned, args:Vec)-> Litr { match name.vec() { b"push"=> push(v, args), - b"splice"=> splice(v, args), - _=> err!("Buf没有{}方法",name) + b"push_front"=> push_front(v, args), + b"dedup"=> dedup(v, args, scope), + b"sort"=> sort(v, args, scope), + b"for_each"=> for_each(v, args, scope), + b"map"=> map(v, args, scope), + b"pop"=> pop(v, args), + b"pop_front"=> pop_front(v, args), + b"rev"=> rev(v), + b"filter"=> filter(v, args, scope), + b"filter_clone"=> filter_clone(v, args, scope), + b"copy_within"=> copy_within(v, args), + // b"splice"=> splice(v, args), + _=> panic!("Buf没有{}方法",name) } } @@ -15,20 +27,227 @@ const fn to_u8(v:&Litr)-> u8 { _=> 0 } } +const fn to_usize(v:&Litr)-> usize { + match v { + Litr::Int(n)=> *n as usize, + Litr::Uint(n)=> *n, + _=> 0 + } +} -pub fn push(v:&mut Vec, args:Vec)-> Litr { - let mut args = args.into_iter(); - match &*next_arg!(args "'push'方法需要一个数字,列表或数组作为参数") { +/// 推进数组或者单数字 +fn push(v:&mut Vec, mut args:Vec)-> Litr { + let mut args = args.iter_mut(); + match &**next_arg!(args "'push'方法需要一个数字,列表或数组作为参数") { Litr::Buf(right)=> v.extend_from_slice(right), Litr::List(right)=> v.extend_from_slice( - &right.iter().map(|litr|to_u8(litr)).collect::>()), + &right.iter().map(|litr|to_u8(litr)).collect::>()), n=> v.push(to_u8(n)) }; Litr::Uninit } -fn splice(v:&mut Vec, args:Vec)-> Litr { - let mut args = args.into_iter(); - let arg0 = next_arg!(args "splice方法至少提供一个参数"); +/// 像是js的unshift +fn push_front(v:&mut Vec, mut args:Vec)-> Litr { + let mut args = args.iter_mut(); + match &**next_arg!(args "'push_front'方法需要一个数字,列表或数组作为参数") { + Litr::Buf(right)=> *v = [&**right, v].concat(), + Litr::List(right)=> *v = [ + &*right.iter().map(|litr|to_u8(litr)).collect::>(), v].concat(), + n=> v.insert(0, to_u8(n)) + }; + Litr::Uninit +} + +/// 去重 建议和sort联用 +fn dedup(v:&mut Vec, args:Vec, scope:Scope)-> Litr { + // 如果传了第一个参数就用dedup_by + if let Some(f) = args.get(0) { + let f = match &**f { + Litr::Func(f)=> f, + _=> panic!("buf.dedup第一个参数只能传函数") + }; + v.dedup_by(|a,b| match scope.call(vec![ + CalcRef::Own(Litr::Uint(*a as usize)), CalcRef::Own(Litr::Uint(*b as usize)) + ], f) { + Litr::Bool(b)=> b, + _=> false + }); + }else { + v.dedup(); + } + Litr::Uninit +} + +/// 排序 +fn sort(v:&mut Vec, args:Vec, scope:Scope)-> Litr { + // 如果传了第一个参数就用sort_by + if let Some(f) = args.get(0) { + let f = match &**f { + Litr::Func(f)=> f, + _=> panic!("buf.sort第一个参数只能传函数") + }; + use std::cmp::Ordering; + v.sort_unstable_by(|a,b| match scope.call(vec![ + CalcRef::Own(Litr::Uint(*a as usize)), CalcRef::Own(Litr::Uint(*b as usize)) + ], f) { + Litr::Bool(b)=> match b { + true=> Ordering::Greater, + false=> Ordering::Less, + }, + _=> Ordering::Greater + }); + }else { + v.sort_unstable(); + } + Litr::Uninit +} + +/// 循环调用 +fn for_each(v:&mut Vec, mut args:Vec, scope:Scope)-> Litr { + let mut args = args.iter_mut(); + let f = match &**next_arg!(args "buf.foreach需要一个函数作为参数") { + Litr::Func(f)=> f, + _=> panic!("buf.foreach第一个参数只能传函数") + }; + v.iter().for_each(|a| {scope.call(vec![ + CalcRef::Own(Litr::Uint(*a as usize)) + ], f);}); + Litr::Uninit +} + +/// 映射重构新Buf +fn map(v:&mut Vec, args:Vec, scope:Scope)-> Litr { + let f = match args.get(0) { + Some(f)=> match &**f { + Litr::Func(f)=> f, + _=> panic!("buf.map第一个参数只能传函数") + }, + None=> panic!("buf.map需要一个函数作为参数") + }; + Litr::Buf(v.iter().map(|a| match scope.call(vec![ + CalcRef::Own(Litr::Uint(*a as usize)) + ], f) { + Litr::Uint(n)=> n as u8, + Litr::Int(n)=> n as u8, + _=> 0 + }).collect()) +} + +/// 从末尾切去一个, 可传一个数字作为切去数量 +fn pop(v:&mut Vec, args:Vec)-> Litr { + if let Some(arg0) = args.get(0) { + let at = match &**arg0 { + Litr::Uint(n)=> *n, + Litr::Int(n)=> *n as usize, + _=> panic!("buf.pop的参数必须为整数") + }; + if at >= v.len() { + panic!("分界线索引{at}大于数组长度{}", v.len()); + } + + Litr::Buf(v.split_off(v.len() - at)) + }else { + match v.pop() { + Some(n)=> Litr::Uint(n as usize), + None=> Litr::Uninit + } + } +} + +/// 从开头切去一个, 可传一个数字作为切掉数量 +fn pop_front(v:&mut Vec, args:Vec)-> Litr { + if let Some(arg0) = args.get(0) { + let at = match &**arg0 { + Litr::Uint(n)=> *n, + Litr::Int(n)=> *n as usize, + _=> panic!("buf.pop_front的参数必须为整数") + }; + if at >= v.len() { + panic!("分界线索引{at}大于数组长度{}", v.len()); + } + + let mut part = v.split_off(at); + std::mem::swap(v, &mut part); + Litr::Buf(part) + }else { + if v.len()==0 {return Litr::Uninit;} + Litr::Uint(v.remove(0) as usize) + } +} + +/// 反转Buf +fn rev(v:&mut Vec)-> Litr { + v.reverse(); + Litr::Uninit +} + +/// 将当前数组按函数过滤 +fn filter(v:&mut Vec, mut args:Vec, scope:Scope)-> Litr { + let mut args = args.iter_mut(); + let f = match &**next_arg!(args "buf.filter需要一个函数作为参数") { + Litr::Func(f)=> f, + _=> panic!("buf.map第一个参数只能传函数") + }; + v.retain(|a|match scope.call( + vec![CalcRef::Own(Litr::Uint(*a as usize))], f + ) { + Litr::Bool(b)=> b, + _=> false + }); + Litr::Uninit +} + +/// filter的复制版本 +fn filter_clone(v:&mut Vec, mut args:Vec, scope:Scope)-> Litr { + let mut args = args.iter_mut(); + let f = match &**next_arg!(args "buf.filter需要一个函数作为参数") { + Litr::Func(f)=> f, + _=> panic!("buf.map第一个参数只能传函数") + }; + + Litr::Buf(v.iter().filter_map(|&a|match scope.call( + vec![CalcRef::Own(Litr::Uint(a as usize))], f + ) { + Litr::Bool(b)=> b.then(||a), + _=> None + }).collect::>()) +} + +/// 在数组范围内进行就地复制 +fn copy_within(v:&mut Vec, mut args:Vec)-> Litr { + let mut args = args.iter_mut(); + let start = to_usize(&**next_arg!(args "buf.copy_within需要传入第一个参数作为起始索引")); + let end = to_usize(&**next_arg!(args "buf.copy_within需要传入第二个参数作为结束索引")); + let dest = to_usize(&**next_arg!(args "buf.copy_within需要传入第三个参数作为复制目标位置索引")); + let len = v.len(); + + assert!(start <= end, "起始索引{start} 不可大于结束索引{end}"); + assert!(end <= len, "结束索引{end} 不可大于数组长度{len}"); + assert!(dest < len, "目标索引{dest} 不可大于等于数组长度{len}"); + + let count = end - start; + assert!(count <= len - dest, "可写入空间{} 不足选中长度{count}", len - dest); + + // SAFETY: 看slice::copy_within + unsafe { + let ptr = v.as_mut_ptr(); + let src_ptr = ptr.add(start); + let dest_ptr = ptr.add(dest); + std::ptr::copy(src_ptr, dest_ptr, count); + } Litr::Uninit } + +/// 在指定索引处写入另一个Buf +fn write() {} + +// rotate + +// concat join join_str join_hex to_str + +// fn splice(v:&mut Vec, args:Vec)-> Litr { +// let mut args = args.into_iter(); +// let arg0 = next_arg!(args "splice方法至少提供一个参数"); +// Litr::Uninit +// } diff --git a/src/primitive/func.rs b/src/primitive/func.rs index 2b2e3f6..356f8a1 100644 --- a/src/primitive/func.rs +++ b/src/primitive/func.rs @@ -1,7 +1,7 @@ use crate::{ intern::{intern, Interned}, native::{BoundNativeMethod, NaitveInstanceRef, NativeFn}, - runtime::{calc::CalcRef, err, Scope}, + runtime::{calc::CalcRef, Scope}, scan::{literal::{ArgDecl, Function, KsType, Litr, LocalFunc, LocalFuncRaw}, stmt::Statements} }; @@ -11,27 +11,25 @@ pub fn statics()-> Vec<(Interned, NativeFn)> { ] } -fn s_new(s:Vec, cx:Scope)-> Litr { - let mut itr = s.into_iter(); - let arg1 = itr.next(); - let stmts = match &arg1 { +fn s_new(mut s:Vec, cx:Scope)-> Litr { + let mut itr = s.iter_mut(); + let stmts = match itr.next() { Some(arg)=> crate::scan::scan(match &**arg { Litr::Str(s)=> s.as_bytes(), Litr::Buf(b)=> b, - _=> err!("Func::new第一个参数必须是Str或Buf, 用来被解析为函数体") + _=> panic!("Func::new第一个参数必须是Str或Buf, 用来被解析为函数体") }), None=> Statements(Vec::new()) }; - let arg2 = itr.next(); - let argdecl = match &arg2 { + let argdecl = match itr.next() { Some(arg)=> match &**arg { Litr::List(v)=> v.iter().map(|v|match v { Litr::Str(s)=> ArgDecl {default: Litr::Uninit, name: intern(s.as_bytes()), t:KsType::Any}, _=> ArgDecl {default: Litr::Uninit, name: intern(b"#ignored"), t:KsType::Any} }).collect(), - _=> err!("Func::new第二个参数必须是Str组成的List, 用来定义该函数的参数名") + _=> panic!("Func::new第二个参数必须是Str组成的List, 用来定义该函数的参数名") }, None=> Vec::new() }; diff --git a/src/primitive/mod.rs b/src/primitive/mod.rs index 2674fac..1fd44bf 100644 --- a/src/primitive/mod.rs +++ b/src/primitive/mod.rs @@ -7,7 +7,7 @@ use crate::native::{ NativeFn, NativeInstance }; -use crate::runtime::{calc::CalcRef, Class, err}; +use crate::runtime::{calc::CalcRef, Class, Scope}; use crate::scan::literal::Litr; use crate::intern::{Interned, intern}; @@ -54,22 +54,22 @@ pub fn classes()-> Vec<(Interned, Class)> {unsafe { } }} +/// 从args迭代器中获取下一个参数 macro_rules! next_arg { ($args:ident $($err:literal)+)=> { match $args.next() { Some(v)=> v, - None=> err!($($err,)+) + None=> panic!($($err,)+) } }; ($args:ident $t:ty:$e:ident:$($t_err:literal)+; $($err:literal)+)=> { match $args.next() { Some(v)=> match v { Litr::$t(v)=> v, - _=> err!($($t_err,)+) + _=> panic!($($t_err,)+) }, - None=> err!($($err,)+) + None=> panic!($($err,)+) } } } - -pub(super) use next_arg; +pub(self) use next_arg; diff --git a/src/primitive/obj.rs b/src/primitive/obj.rs index ee286ae..abdb3fc 100644 --- a/src/primitive/obj.rs +++ b/src/primitive/obj.rs @@ -1,6 +1,6 @@ //! Obj基本类型的静态方法 -use crate::{intern::{intern, Interned}, native::NativeFn, runtime::{calc::CalcRef, err, Scope}, scan::literal::Litr}; +use crate::{intern::{intern, Interned}, native::NativeFn, runtime::{calc::CalcRef, Scope}, scan::literal::Litr}; use std::collections::HashMap; pub fn statics()-> Vec<(Interned, NativeFn)> { @@ -14,15 +14,15 @@ pub fn statics()-> Vec<(Interned, NativeFn)> { /// static insert fn s_insert(mut args:Vec, _cx:Scope)-> Litr { - if args.len()<3 {err!("Obj::insert需要3个参数: obj, name:Str, val")}; + assert!(args.len()>=3, "Obj::insert需要3个参数: obj, name:Str, val"); let mut args = args.iter_mut(); let targ = match &mut**args.next().unwrap() { Litr::Obj(m)=> m, - _=> err!("insert第一个参数必须是Obj") + _=> panic!("insert第一个参数必须是Obj") }; let id = match &mut **args.next().unwrap() { Litr::Str(s)=> s, - _=> err!("insert第二个参数必须是Str") + _=> panic!("insert第二个参数必须是Str") }; let v = args.next().unwrap().clone(); match targ.insert(intern(id.as_bytes()), v.own()) { @@ -33,15 +33,15 @@ fn s_insert(mut args:Vec, _cx:Scope)-> Litr { /// static remove fn s_remove(mut args:Vec, _cx:Scope)-> Litr { - if args.len()<2 {err!("Obj::remove需要2个参数: obj, name:Str")}; + assert!(args.len()>=2, "Obj::remove需要2个参数: obj, name:Str"); let mut args = args.iter_mut(); let targ = match &mut**args.next().unwrap() { Litr::Obj(m)=> m, - _=> err!("remove第一个参数必须是Obj") + _=> panic!("remove第一个参数必须是Obj") }; let id = match &mut **args.next().unwrap() { Litr::Str(s)=> s, - _=> err!("remove第二个参数必须是Str") + _=> panic!("remove第二个参数必须是Str") }; match targ.remove(&intern(id.as_bytes())) { Some(v)=> v, @@ -51,15 +51,15 @@ fn s_remove(mut args:Vec, _cx:Scope)-> Litr { /// static has fn s_has(mut args:Vec, _cx:Scope)-> Litr { - if args.len()<2 {err!("Obj::has需要2个参数: obj, name:Str")}; + assert!(args.len()>=2, "Obj::has需要2个参数: obj, name:Str"); let mut args = args.iter_mut(); let targ = match &mut**args.next().unwrap() { Litr::Obj(m)=> m, - _=> err!("has第一个参数必须是Obj") + _=> panic!("has第一个参数必须是Obj") }; let id = match &mut **args.next().unwrap() { Litr::Str(s)=> s, - _=> err!("has第二个参数必须是Str") + _=> panic!("has第二个参数必须是Str") }; match targ.get(&intern(id.as_bytes())) { Some(_)=> Litr::Bool(true), @@ -69,15 +69,15 @@ fn s_has(mut args:Vec, _cx:Scope)-> Litr { /// static get fn s_get(mut args:Vec, _cx:Scope)-> Litr { - if args.len()<2 {err!("Obj::has需要2个参数: obj, name:Str")}; + assert!(args.len()>=2, "Obj::has需要2个参数: obj, name:Str"); let mut args = args.iter_mut(); let targ = match &mut**args.next().unwrap() { Litr::Obj(m)=> m, - _=> err!("has第一个参数必须是Obj") + _=> panic!("has第一个参数必须是Obj") }; let id = match &mut **args.next().unwrap() { Litr::Str(s)=> s, - _=> err!("has第二个参数必须是Str") + _=> panic!("has第二个参数必须是Str") }; match targ.get(&intern(id.as_bytes())) { Some(v)=> v.clone(), diff --git a/src/runtime/calc.rs b/src/runtime/calc.rs index 21a4c7e..2f8b185 100644 --- a/src/runtime/calc.rs +++ b/src/runtime/calc.rs @@ -47,7 +47,11 @@ impl Scope { pub fn calc(mut self,e:&Expr)-> Litr { match e { Expr::Call { args, targ }=> { - let targ = self.calc_ref(targ); + let targ_ = self.calc_ref(targ); + let targ = match &*targ_ { + Litr::Func(f)=> f, + _=> panic!("{targ:?}不是一个函数") + }; let args = args.iter().map(|v|self.calc_ref(v)).collect(); self.call(args, targ) }, @@ -66,7 +70,7 @@ impl Scope { Expr::Literal(litr)=> litr.clone(), - Expr::Variant(id)=> self.var(*id).unwrap_or_else(||err!("无法找到变量 '{}'", id.str())).own(), + Expr::Variant(id)=> self.var(*id).unwrap_or_else(||panic!("无法找到变量 '{}'", id.str())).own(), // 函数表达式 Expr::LocalDecl(local)=> { @@ -86,7 +90,7 @@ impl Scope { match &*right { Int(n)=> Int(-n), Float(n)=> Float(-n), - _=> err!("负号只能用在有符号数") + _=> panic!("负号只能用在有符号数") } } b'!'=> { @@ -95,7 +99,7 @@ impl Scope { Int(n)=> Int(!n), Uint(n)=> Uint(!n), Uninit => Bool(true), - _=> err!("!运算符只能用于整数和Bool") + _=> panic!("!运算符只能用于整数和Bool") } }_=>Uninit } @@ -121,28 +125,27 @@ impl Scope { Expr::ModClsAcc(modname, clsname)=> (self.find_class_in(*modname, *clsname), clsname), Expr::Variant(clsname)=> - (self.find_class(*clsname).unwrap_or_else(||err!("未定义类 '{}'", clsname.str())), clsname), - _=> err!("构建实例::左侧必须是类型名") + (self.find_class(*clsname).unwrap_or_else(||panic!("未定义类 '{}'", clsname.str())), clsname), + _=> panic!("构建实例::左侧必须是类型名") }; if let Class::Local(cls) = cls { let cls = unsafe {&mut *cls}; let mut v = vec![Litr::Uninit;cls.props.len()]; - let cannot_access_private = self.exports != cls.module; + let can_access_private = self.exports == cls.module; 'a: for (id, e) in val.iter() { for (n, prop) in cls.props.iter().enumerate() { if prop.name == *id { - if !prop.public && cannot_access_private { - err!("成员属性'{}'是私有的。",id) - } + assert!(prop.public || can_access_private, + "成员属性'{}'是私有的",id); v[n] = self.clone().calc(e); continue 'a; } } - err!("'{}'类型不存在'{}'属性。", cls.name, id.str()) + panic!("'{}'类型不存在'{}'属性", cls.name, id.str()) } Litr::Inst(Instance {cls, v:v.into()}) }else { - err!("无法直接构建原生类型'{}'", clsname.str()) + panic!("无法直接构建原生类型'{}'", clsname.str()) } } @@ -158,7 +161,7 @@ impl Scope { return Litr::Func(Function::Local(func.clone())); } } - err!("模块'{}'中没有'{}'函数",modname,funcname) + panic!("模块'{}'中没有'{}'函数",modname,funcname) } Module::Native(m)=> { for (id, func) in unsafe{(**m).funcs.iter()} { @@ -166,15 +169,15 @@ impl Scope { return Litr::Func(Function::Native(func.clone())); } } - err!("原生模块'{}'中没有'{}'函数",modname,funcname) + panic!("原生模块'{}'中没有'{}'函数",modname,funcname) } } } } - err!("没有导入'{}'模块",modname) + panic!("没有导入'{}'模块",modname) } - Expr::ModClsAcc(a,b)=> err!("类型声明不是一个值。考虑使用`class T = {}-:{}`语句代替",a b), + Expr::ModClsAcc(a,b)=> panic!("类型声明不是一个值。考虑使用`class T = {}-:{}`语句代替",a, b), // 访问类方法 Expr::ImplAccess(e, find)=> { @@ -183,24 +186,22 @@ impl Scope { match cls { Class::Local(m)=> { let cls = unsafe {&*m}; - let cannot_access_private = cls.module != this_module; + let can_access_private = cls.module == this_module; for func in cls.statics.iter() { if func.name == find { - if !func.public && cannot_access_private { - err!("'{}'类型的静态方法'{}'是私有的。", cls.name, find) - } + assert!(func.public || can_access_private, + "'{}'类型的静态方法'{}'是私有的。", cls.name, find); return Litr::Func(Function::Local(func.f.clone())); } } for func in cls.methods.iter() { if func.name == find { - if !func.public && cannot_access_private { - err!("'{}'类型中的方法'{}'是私有的。", cls.name, find) - } + assert!(!func.public || can_access_private, + "'{}'类型中的方法'{}'是私有的。", cls.name, find); return Litr::Func(Function::Local(func.f.clone())); } } - err!("'{}'类型没有'{}'方法", cls.name, find.str()); + panic!("'{}'类型没有'{}'方法", cls.name, find.str()); } Class::Native(m)=> { let cls = unsafe {&*m}; @@ -209,14 +210,14 @@ impl Scope { return Litr::Func(Function::Native(*func)); } } - err!("'{}'原生类型中没有'{}'静态方法", cls.name, find.str()) + panic!("'{}'原生类型中没有'{}'静态方法", cls.name, find.str()) // native模块的method使用bind太不安全了,只允许访问静态方法 } } } if let Expr::Variant(id) = &**e { - let cls = self.find_class(*id).unwrap_or_else(||err!("未定义类 '{}'", id.str())); + let cls = self.find_class(*id).unwrap_or_else(||panic!("未定义类 '{}'", id.str())); return find_fn(cls, *find, self.exports); } @@ -225,7 +226,7 @@ impl Scope { return find_fn(cls, *find, self.exports); } - err!("::左侧必须是个类型") + panic!("::左侧必须是个类型") } Expr::Property(e, find)=> { @@ -255,7 +256,7 @@ impl Scope { _=> false }) } - _=> err!("is操作符右边必须是类型名") + _=> panic!("is操作符右边必须是类型名") }; macro_rules! matcher {($($d:ident)*)=> { match &*v { @@ -277,7 +278,7 @@ impl Scope { Bool Buf Float Func Int List Obj Str Sym Uint } } - Expr::Empty => err!("得到空表达式"), + Expr::Empty => panic!("得到空表达式"), } } @@ -293,7 +294,7 @@ impl Scope { let i = self.calc_ref(i); index(left, i) }, - Expr::Variant(id)=> self.var(*id).unwrap_or_else(||err!("无法找到变量 '{}'", id.str())), + Expr::Variant(id)=> self.var(*id).unwrap_or_else(||panic!("无法找到变量 '{}'", id.str())), _=> { let v = self.calc(e); CalcRef::Own(v) @@ -309,20 +310,19 @@ fn expr_set(mut this: Scope, left: &Expr, right: Litr) { /// 获取属性的引用 pub fn get_prop_ref(this: Scope, mut from:CalcRef, find:&Interned)-> CalcRef { match &mut *from { - Litr::Obj(map)=> CalcRef::Ref(map.get_mut(find).unwrap_or_else(||err!("Obj中没有'{}'", find))), + Litr::Obj(map)=> CalcRef::Ref(map.get_mut(find).unwrap_or_else(||panic!("Obj中没有'{}'", find))), Litr::Inst(inst)=> { let cls = unsafe {&*inst.cls}; - let cannot_access_private = unsafe {(*inst.cls).module} != this.exports; + let can_access_private = unsafe {(*inst.cls).module} == this.exports; let props = &cls.props; for (n, prop) in props.iter().enumerate() { if prop.name == *find { - if !prop.public && cannot_access_private { - err!("'{}'类型的成员属性'{}'是私有的", cls.name, find) - } + assert!(prop.public || can_access_private, + "'{}'类型的成员属性'{}'是私有的", cls.name, find); return CalcRef::Ref(&mut inst.v[n]); } } - err!("'{}'类型上没有'{}'属性", cls.name, find) + panic!("'{}'类型上没有'{}'属性", cls.name, find) } // native instance有自己的setter和getter,引用传递不了的 _=> CalcRef::Own(Litr::Uninit) @@ -411,7 +411,7 @@ fn expr_set(mut this: Scope, left: &Expr, right: Litr) { todo!();// f.bound = Some(Box::new(CalcRef::Ref(left))); f.scope.call_local(f, vec![i.own(), right]); } - None=> err!("为'{}'实例索引赋值需要定义`@index_set`方法", cls.name) + None=> panic!("为'{}'实例索引赋值需要定义`@index_set`方法", cls.name) } }, Litr::Ninst(inst)=> { @@ -420,7 +420,7 @@ fn expr_set(mut this: Scope, left: &Expr, right: Litr) { Litr::Obj(map)=> { if let Litr::Str(s) = &*i { map.insert(intern(s.as_bytes()), right); - }else {err!("Obj索引必须是Str")} + }else {panic!("Obj索引必须是Str")} } _=> *index(CalcRef::Ref(left), i) = right } @@ -440,21 +440,20 @@ fn get_prop(this:Scope, mut from:CalcRef, find:Interned)-> Litr { match &mut *from { // 本地class的实例 Litr::Inst(inst)=> { - let cannot_access_private = unsafe {(*inst.cls).module} != this.exports; + let can_access_private = unsafe {(*inst.cls).module} == this.exports; let cls = unsafe {&*inst.cls}; // 寻找属性 let props = &cls.props; for (n, prop) in props.iter().enumerate() { if prop.name == find { - if !prop.public && cannot_access_private { - err!("'{}'类型的成员属性'{}'是私有的", cls.name, find) - } + assert!(prop.public || can_access_private, + "'{}'类型的成员属性'{}'是私有的", cls.name, find); return inst.v[n].clone(); } } - err!("'{}'类型上没有'{}'属性", cls.name, find) + panic!("'{}'类型上没有'{}'属性", cls.name, find) }, // 原生类的实例 @@ -517,7 +516,7 @@ fn index(mut left:CalcRef, i:CalcRef)-> CalcRef { None=> CalcRef::uninit() }; } - err!("Obj的索引必须使用Str") + panic!("Obj的索引必须使用Str") } // 判断实例index_get @@ -530,7 +529,7 @@ fn index(mut left:CalcRef, i:CalcRef)-> CalcRef { todo!();// f.bound = Some(Box::new(left)); return CalcRef::Own(f.scope.call_local(f, vec![i.own()])); } - err!("读取'{}'实例索引需要定义`@index_get`方法", cls.name) + panic!("读取'{}'实例索引需要定义`@index_get`方法", cls.name) } // 判断原生类实例 @@ -542,7 +541,7 @@ fn index(mut left:CalcRef, i:CalcRef)-> CalcRef { let i = match &*i { Litr::Uint(n)=> *n, Litr::Int(n)=> (*n) as usize, - _=> err!("index必须是整数") + _=> panic!("index必须是整数") }; match &mut *left { Litr::Buf(v)=> { @@ -587,7 +586,7 @@ fn binary(mut this: Scope, left:&Box, right:&Box, op:&Box<[u8]>)-> L (Uint(l),Int(r))=> Uint(l $op *r as usize), (Float(l),Float(r))=> Float(l $op r), (Float(l),Int(r))=> Float(l $op *r as f64), - _=> err!($pan) + _=> panic!($pan) } }}; ($pan:literal $op:tt $n:tt)=> {{ @@ -596,7 +595,7 @@ fn binary(mut this: Scope, left:&Box, right:&Box, op:&Box<[u8]>)-> L Uint(r) => *r == 0, Float(r) => *r == 0.0, _=> false - } {err!("除数必须非0")} + } {panic!("除数必须非0")} impl_num!($pan $op) }}; } @@ -607,7 +606,7 @@ fn binary(mut this: Scope, left:&Box, right:&Box, op:&Box<[u8]>)-> L match (&*left, &*right) { (Uint(l), Uint(r))=> Uint(l $op r), (Uint(l), Int(r))=> Uint(l $op *r as usize), - _=> err!($pan) + _=> panic!($pan) } }}; } @@ -622,7 +621,7 @@ fn binary(mut this: Scope, left:&Box, right:&Box, op:&Box<[u8]>)-> L (Int(l), Int(r))=> Int(l $o r), (Float(l), Float(r))=> Float(l $o r), (Float(l), Int(r))=> Float(l $o *r as f64), - _=> err!("运算并赋值的左右类型不同") + _=> panic!("运算并赋值的左右类型不同") }; *left = n; Uninit @@ -636,7 +635,7 @@ fn binary(mut this: Scope, left:&Box, right:&Box, op:&Box<[u8]>)-> L let n = match (&*left, &*right) { (Uint(l), Uint(r))=> Uint(l $op r), (Uint(l), Int(r))=> Uint(l $op *r as usize), - _=> err!("按位运算并赋值只允许无符号数") + _=> panic!("按位运算并赋值只允许无符号数") }; *left = n; Uninit @@ -671,9 +670,7 @@ fn binary(mut this: Scope, left:&Box, right:&Box, op:&Box<[u8]>)-> L } }, (Inst(l),Inst(r))=> { - if l.cls != r.cls { - err!("实例类型不同无法比较"); - } + assert!(l.cls==r.cls, "实例类型不同无法比较"); match_list(&*l.v, &*r.v) }, (Sym(l), Sym(r))=> l $o r, @@ -683,9 +680,7 @@ fn binary(mut this: Scope, left:&Box, right:&Box, op:&Box<[u8]>)-> L fn match_list(l:&[Litr], r:&[Litr])-> bool { let len = l.len(); - if len != r.len() { - err!("列表长度不同,无法比较"); - } + assert!(len==r.len(), "列表长度不同,无法比较"); for i in 0..len { if !match_basic(&l[i],&r[i]) { return false @@ -704,7 +699,7 @@ fn binary(mut this: Scope, left:&Box, right:&Box, op:&Box<[u8]>)-> L (Bool(l), Bool(r))=> Bool(*l $o *r), (Bool(l), Uninit)=> Bool(*l $o false), (Uninit, Bool(r))=> Bool(false $o *r), - _=> err!("{}两边必须都为Bool或uninit", stringify!($o)) + _=> panic!("{}两边必须都为Bool或uninit", stringify!($o)) } }}; } @@ -760,7 +755,7 @@ fn binary(mut this: Scope, left:&Box, right:&Box, op:&Box<[u8]>)-> L b"&&" => impl_logic!(&&), b"||" => impl_logic!(||), - _=> err!("未知运算符'{}'", String::from_utf8_lossy(&op)) + _=> panic!("未知运算符'{}'", String::from_utf8_lossy(&op)) } } diff --git a/src/runtime/call.rs b/src/runtime/call.rs index a95ffaf..6e5c44a 100644 --- a/src/runtime/call.rs +++ b/src/runtime/call.rs @@ -6,36 +6,31 @@ use super::*; impl Scope { /// 解析Expr的调用 - pub fn call(mut self, args:Vec, targ:CalcRef)-> Litr { - if let Litr::Func(exec) = &*targ { - use Function::*; - match exec { - Native(f)=> f(args, self), - Local(f)=> { - let args = args.into_iter().map(|e|e.own()).collect(); - self.call_local(&f, args) - }, - Extern(f)=> { - let args = args.into_iter().map(|e|e.own()).collect(); - super::externer::call_extern(&f, args) - } + pub fn call(mut self, args:Vec, targ:&Function)-> Litr { + use Function::*; + match targ { + Native(f)=> f(args, self), + Local(f)=> { + let args = args.into_iter().map(|e|e.own()).collect(); + self.call_local(&f, args) + }, + Extern(f)=> { + let args = args.into_iter().map(|e|e.own()).collect(); + super::externer::call_extern(&f, args) } - }else { - err!("'{}' 不是一个函数", targ.str()) } } /// 为a.b()的行为匹配对应方法并调用 pub fn call_method(mut self, mut args:Vec, mut targ:CalcRef, name:Interned)-> Litr { - match &mut*targ { + match &mut *targ { Litr::Bool(v)=> match name.vec() { b"rev"=> Litr::Bool(!*v), b"then"=> { let f = match args.get_mut(0) { - Some(f)=> { - let mut s = CalcRef::uninit(); - std::mem::swap(&mut s,f); - s + Some(f)=> match &**f { + Litr::Func(f)=> f, + _=> panic!("bool.then第一个参数必须是函数") }, None=> return Litr::Uninit }; @@ -45,10 +40,10 @@ impl Scope { Litr::Uninit } } - _=> err!("Bool类型只有'rev'和'then'方法") + _=> panic!("Bool类型只有'rev'和'then'方法") } - Litr::Buf(v)=> primitive::buf::method(v, name, args), - _=> err!("没有'{}'方法\n 如果你需要调用属性作为函数,请使用(a.b)()的写法", name) + Litr::Buf(v)=> primitive::buf::method(v, self, name, args), + _=> panic!("没有'{}'方法\n 如果你需要调用属性作为函数,请使用(a.b)()的写法", name) } // let mut left = self.calc_ref(left); // // 匹配所有可能使用.运算符得到函数的类型(instance, obj) @@ -62,7 +57,7 @@ impl Scope { // for mthd in methods.iter() { // if mthd.name == right { // if !mthd.public && cannot_access_private { - // err!("'{}'类型的成员方法'{}'是私有的", cls.name, right) + // panic!("'{}'类型的成员方法'{}'是私有的", cls.name, right) // } // // 为函数绑定self // let mut f = mthd.f.clone(); @@ -77,7 +72,7 @@ impl Scope { // for (n, prop) in props.iter().enumerate() { // if prop.name == right { // if !prop.public && cannot_access_private { - // err!("'{}'类型的成员属性'{}'是私有的", cls.name, right) + // panic!("'{}'类型的成员属性'{}'是私有的", cls.name, right) // } // return self.call(args, CalcRef::Ref(&mut inst.v[n])); // } @@ -106,8 +101,8 @@ impl Scope { // return self.call(args, CalcRef::Own((cls.getter)(inst, right))); // } // Litr::Obj(map)=> return self.call( - // args, CalcRef::Ref(map.get_mut(&right).unwrap_or_else(||err!("'{}'不是一个函数", right)))), - // Litr::Bool(v)=> err!("Bool没有方法"), + // args, CalcRef::Ref(map.get_mut(&right).unwrap_or_else(||panic!("'{}'不是一个函数", right)))), + // Litr::Bool(v)=> panic!("Bool没有方法"), // Litr::Buf(v)=> return primitive::buf::method(v, right, args), // _=> () // } diff --git a/src/runtime/evil.rs b/src/runtime/evil.rs index 48bc283..7d8aa2b 100644 --- a/src/runtime/evil.rs +++ b/src/runtime/evil.rs @@ -42,14 +42,14 @@ impl Scope { Stmt::Using(alia, e)=> { match e { Expr::Variant(id)=> { - let cls = self.find_class(*id).unwrap_or_else(||err!("未定义类'{}'", id.str())); + let cls = self.find_class(*id).unwrap_or_else(||panic!("未定义类'{}'", id.str())); self.class_uses.push((*alia, cls)); } Expr::ModClsAcc(s, modname)=> { let cls = self.find_class_in(*s, *modname); self.class_uses.push((*alia, cls)); } - _=> err!("class = 语句后必须是个类声明") + _=> panic!("class = 语句后必须是个类声明") } } @@ -159,8 +159,8 @@ impl Scope { } scope.evil(exec); } - Stmt::Break=> err!("不允许`for v:iter break`的写法"), - Stmt::Continue=> err!("不允许`for v:iter continue`的写法`"), + Stmt::Break=> panic!("不允许`for v:iter break`的写法"), + Stmt::Continue=> panic!("不允许`for v:iter continue`的写法`"), } scope.ended = true; outlive::scope_end(scope); @@ -169,8 +169,8 @@ impl Scope { Stmt::Match=>(), // - - Stmt::Break=> err!("break不在循环体内"), - Stmt::Continue=> err!("continue不在循环体内"), + Stmt::Break=> panic!("break不在循环体内"), + Stmt::Continue=> panic!("continue不在循环体内"), Stmt::Empty=> (), } } @@ -181,7 +181,7 @@ fn cond(v:Litr)-> bool { match v { Litr::Bool(b)=> b, Litr::Uninit=> false, - _=> err!("条件必须为Bool或uninit") + _=> panic!("条件必须为Bool或uninit") } } @@ -206,8 +206,8 @@ fn start_loop(mut this:Scope, mut condition:impl FnMut()-> bool, exec:&Box // 单语句将由当前作用域代为执行,不再创建新作用域 }else { match &**exec { - Stmt::Break=> err!("不允许`for() break`的写法"), - Stmt::Continue=> err!("不允许`for() continue`的写法`"), + Stmt::Break=> panic!("不允许`for() break`的写法"), + Stmt::Continue=> panic!("不允许`for() continue`的写法`"), _=> while condition() { if this.ended { return; diff --git a/src/runtime/externer.rs b/src/runtime/externer.rs index 8a981d8..3374bae 100644 --- a/src/runtime/externer.rs +++ b/src/runtime/externer.rs @@ -29,7 +29,7 @@ macro_rules! translate_local_impl {{ let ret = scope.call_local(exec, args); match translate(ret) { Ok(v)=> v, - Err(e)=> crate::runtime::err!("{}",e) + Err(e)=> panic!("{}",e) } } )* @@ -81,7 +81,7 @@ pub fn translate(arg:Litr)-> Result { } -use super::{ExternFunc, Scope, err, LINE}; +use super::{ExternFunc, Scope}; pub fn call_extern(f:&ExternFunc, args:Vec)-> Litr { let len = f.argdecl.len(); let mut args = args.into_iter(); @@ -97,7 +97,7 @@ pub fn call_extern(f:&ExternFunc, args:Vec)-> Litr { let mut eargs = [0usize;$n]; eargs.iter_mut().enumerate().for_each(|(i,p)| { if let Some(v) = args.next() { - let transed = translate(v).unwrap_or_else(|e|panic!("{} 运行时({})",e,unsafe{LINE})); + let transed = translate(v).unwrap_or_else(|e|panic!("{e}")); *p = transed } }); @@ -106,7 +106,7 @@ pub fn call_extern(f:&ExternFunc, args:Vec)-> Litr { Litr::Uint(ret) } )* - _=> {panic!("extern函数不支持{}位参数 运行时({})", len, unsafe {LINE})} + _=> {panic!("extern函数不支持{}位参数", len)} } } } diff --git a/src/runtime/mod.rs b/src/runtime/mod.rs index 579d629..fda1cca 100644 --- a/src/runtime/mod.rs +++ b/src/runtime/mod.rs @@ -3,6 +3,7 @@ //! 将解析的ast放在实际作用域中运行 use crate::intern::{intern, Interned}; +use crate::LINE; use std::collections::HashMap; use std::sync::atomic::{AtomicUsize,self}; use std::ptr::NonNull; @@ -12,6 +13,7 @@ use crate::scan::{ expr::* }; use crate::native::{NativeClassDef, NativeMod}; +use self::calc::CalcRef; mod outlive; pub use outlive::Outlives; @@ -22,18 +24,6 @@ mod call; mod externer; -/// 运行期追踪行号 -/// -/// 只有主线程会访问,不存在多线程同步问题 -pub static mut LINE:usize = 0; -#[macro_use] macro_rules! err {($($a:expr$(,)?)*) => { - panic!("{} 运行时({})", format_args!($($a,)*), unsafe{crate::runtime::LINE}) -}} -pub(super) use err; - -use self::calc::CalcRef; - - #[derive(Debug, Clone)] pub enum Module { Native(*const NativeMod), @@ -182,7 +172,7 @@ impl Scope { if let Some(parent) = &mut inner.parent { return parent.var_with_scope(s); } - err!("无法找到变量 '{}'", s.str()); + panic!("无法找到变量 '{}'", s.str()); } @@ -209,7 +199,7 @@ impl Scope { return Class::Local(*cls); } } - err!("模块'{}'中没有'{}'类型",modname.str(), s.str()) + panic!("模块'{}'中没有'{}'类型",modname.str(), s.str()) } Module::Native(p)=> { let m = unsafe {&*p}; @@ -219,7 +209,7 @@ impl Scope { return Class::Native(*cls); } } - err!("原生模块'{}'中没有'{}'类型",modname.str(), s.str()) + panic!("原生模块'{}'中没有'{}'类型",modname.str(), s.str()) } } } @@ -233,7 +223,7 @@ impl Scope { return module.clone(); } } - err!("当前模块中没有导入'{}'模块", find.str()) + panic!("当前模块中没有导入'{}'模块", find.str()) } } diff --git a/src/scan/expr.rs b/src/scan/expr.rs index 4863d2f..b9b69bc 100644 --- a/src/scan/expr.rs +++ b/src/scan/expr.rs @@ -127,9 +127,9 @@ impl Scanner<'_> { expr_stack.push(Expr::$ty(left, right)); continue; } - self.err(&format!("{}右侧需要一个标识符",String::from_utf8_lossy($op))) + panic!("{}右侧需要一个标识符",String::from_utf8_lossy($op)) } - self.err(&format!("{}左侧需要一个标识符",String::from_utf8_lossy($op))) + panic!("{}左侧需要一个标识符",String::from_utf8_lossy($op)) } }}} impl_access!(b"-.",ModFuncAcc); @@ -142,7 +142,7 @@ impl Scanner<'_> { expr_stack.push(Expr::ImplAccess(Box::new(left), id)), Expr::Obj(o)=> expr_stack.push(Expr::NewInst { cls: Box::new(left), val: o }), - _=> self.err("::右侧只能是标识符或对象") + _=> panic!("::右侧只能是标识符或对象") } continue; } @@ -201,7 +201,7 @@ impl Scanner<'_> { let left = Box::new(expr_stack.pop().unwrap()); let name = match self.ident() { Some(n)=> intern(n), - None=> self.err("'.'右边需要属性名") + None=> panic!("'.'右边需要属性名") }; self.spaces(); // 属性后直接使用括号就是调用方法 @@ -222,7 +222,7 @@ impl Scanner<'_> { let left = Box::new(expr_stack.pop().unwrap()); let i = Box::new(self.expr()); if self.i() >= self.src.len() || self.cur() != b']' { - self.err("未闭合的右括号']'。"); + panic!("未闭合的右括号']'。"); } self.next(); expr_stack.push(Expr::Index{ @@ -267,7 +267,7 @@ impl Scanner<'_> { let expr = self.expr(); self.spaces(); if self.i() >= self.src.len() || self.cur() != b')' { - self.err("未闭合的右括号')'。"); + panic!("未闭合的右括号')'。"); } self.next(); expr @@ -313,7 +313,7 @@ fn parse_input_args(this:&Scanner)-> Vec { this.next(); } if this.i() >= this.src.len() || this.cur() != b')' { - this.err("未闭合的右括号')'。"); + panic!("未闭合的右括号')'。"); } this.next(); args diff --git a/src/scan/literal.rs b/src/scan/literal.rs index b0d076e..999cb95 100644 --- a/src/scan/literal.rs +++ b/src/scan/literal.rs @@ -60,7 +60,7 @@ impl Litr { str.push_str("]"); str }, - Buf(b)=> format!("{:?}",b), + Buf(b)=> format!("Buf{:02X?}",b), Obj(map)=> { let mut s = String::new(); s.push_str("{ "); @@ -262,7 +262,7 @@ impl Scanner<'_> { i += 1; while self.src[i] != b'"' { i += 1; - if i >= len {self.err("未闭合的\"。")} + assert!(i < len, "未闭合的\"。"); } let s = String::from_utf8_lossy(&self.src[(self.i()+1)..i]); self.set_i(i+1); @@ -302,7 +302,7 @@ impl Scanner<'_> { _=> { let escaped = charts::escape(escaper); if escaped == 255 { - self.err(&format!("错误的转义符:{}", String::from_utf8_lossy(&[escaper]))); + panic!("错误的转义符:{}", String::from_utf8_lossy(&[escaper])); } vec.push(escaped); i += 1; @@ -314,13 +314,15 @@ impl Scanner<'_> { } _=> i += 1 } - if i >= len {self.err("未闭合的'`'。")} + if i >= len {panic!("未闭合的'`'。")} } // 结算 结算起点到末尾 vec.extend_from_slice(&self.src[start..i]); - let str = String::from_utf8(vec) - .expect(&format!("字符串含非法字符 解析错误({})",self.line())); + let str = match String::from_utf8(vec) { + Ok(s)=> s, + Err(_)=> panic!("字符串含非法字符") + }; self.set_i(i + 1); Expr::Literal(Litr::Str(str)) @@ -346,9 +348,9 @@ impl Scanner<'_> { match char { b'0'..=b'9'|b'a'..=b'f'|b'A'..=b'F'|b'\n'|b'\r'|b' ' => i += 1, b'}' => break, - _=> self.err(&format!("十六进制非法字符:{}",String::from_utf8_lossy(&[char]))) + _=> panic!("十六进制非法字符:{}",String::from_utf8_lossy(&[char])) }; - if i >= len {self.err("未闭合的}")} + if i >= len {panic!("未闭合的}}")} }; // 结算起点延后到大括号后面 @@ -363,7 +365,7 @@ impl Scanner<'_> { if braced >= i {break} }; if braced >= i { - self.err("未闭合的}") + panic!("未闭合的}}") } let res:Result; @@ -381,7 +383,7 @@ impl Scanner<'_> { match res { Ok(n)=> hex.push(n), - Err(_)=> self.err("十六进制解析:不要把一个Byte的两个字符拆开") + Err(_)=> panic!("十六进制解析:不要把一个Byte的两个字符拆开") } } vec.append(&mut hex); @@ -395,7 +397,7 @@ impl Scanner<'_> { b'{' => parse_hex!(), _=> i += 1 } - if i >= len {self.err("未闭合的'。")} + if i >= len {panic!("未闭合的'。")} } // 结算 结算起点到末尾 vec.extend_from_slice(&self.src[start..i]); @@ -426,7 +428,7 @@ impl Scanner<'_> { let n: Result<$t,_> = str.parse(); match n { Err(e)=> { - panic!("无法解析数字:{} 解析错误({})\n {}",str,self.line(),e) + panic!("无法解析数字:{}\n {}",str,e) } Ok(n)=> { self.next(); @@ -475,9 +477,9 @@ impl Scanner<'_> { } if self.i() >= self.src.len() || self.cur() != b']' { if self.cur() == b',' { - self.err("列表不允许空元素"); + panic!("列表不允许空元素"); } - self.err("未闭合的右括号']'。"); + panic!("未闭合的右括号']'。"); } self.next(); Expr::List(ls) @@ -523,7 +525,7 @@ impl Scanner<'_> { } if self.cur() != b'}' { - self.err("未闭合的大括号") + panic!("未闭合的大括号") }; self.next(); decl diff --git a/src/scan/mod.rs b/src/scan/mod.rs index bd5f54b..830b7ae 100644 --- a/src/scan/mod.rs +++ b/src/scan/mod.rs @@ -7,6 +7,7 @@ use crate::intern::{ Interned }; use crate::runtime::Scope; +use crate::LINE; pub mod charts; pub mod stmt; @@ -22,10 +23,9 @@ pub fn scan(src: &[u8])-> Statements { // 已知此处所有变量未泄露 // 为了规避&mut所有权检查,将引用改为指针 let mut i = 0; - let mut line = 1; let mut sttms = Statements::default(); let mut scanner = Scanner { - src, i:&mut i, line:&mut line, + src, i:&mut i, sttms:&mut sttms as *mut Statements }; scanner.scan(); @@ -35,7 +35,6 @@ pub fn scan(src: &[u8])-> Statements { struct Scanner<'a> { src: &'a [u8], i: *mut usize, - line: *mut usize, sttms: *mut Statements, } @@ -56,7 +55,7 @@ impl Scanner<'_> { #[inline] fn push(&self, s:Stmt) { - unsafe{(*self.sttms).0.push((self.line(), s));} + unsafe{(*self.sttms).0.push((LINE, s));} } /// 获取当前字符(ascii u8) #[inline] @@ -77,15 +76,6 @@ impl Scanner<'_> { fn set_i(&self,n:usize) { unsafe{*self.i = n;} } - #[inline] - fn line(&self)->usize { - unsafe{*self.line} - } - - /// 报错模板 - fn err(&self, s:&str)-> ! { - panic!("{} 解析错误({})",s,self.line()) - } /// 跳过一段空格,换行符和注释 fn spaces(&self) { @@ -93,7 +83,7 @@ impl Scanner<'_> { loop { let c = self.cur(); if c == b'\n' { - unsafe{*self.line += 1;} + unsafe{LINE += 1;} } match c { b'\n' | b'\r' | b' ' => { @@ -113,7 +103,7 @@ impl Scanner<'_> { return; } } - unsafe{*self.line += 1;} + unsafe{LINE += 1;} self.next(); } // 多行 @@ -122,7 +112,7 @@ impl Scanner<'_> { loop { self.next(); if self.cur() == b'\n' { - unsafe{*self.line += 1;} + unsafe{LINE += 1;} } if self.cur() == b'\'' { let next = self.i() + 1; @@ -229,7 +219,7 @@ impl Scanner<'_> { b"Obj"=>Obj, _=> Class(intern(decl)) } - }else {self.err("类型声明不可为空")} + }else {panic!("类型声明不可为空")} }else {KsType::Any} } @@ -247,7 +237,7 @@ impl Scanner<'_> { self.spaces(); if let Expr::Literal(def) = self.literal() { def - }else {self.err("默认参数只允许字面量")} + }else {panic!("默认参数只允许字面量")} }else {Litr::Uninit}; if self.cur() == b',' { diff --git a/src/scan/stmt.rs b/src/scan/stmt.rs index aa295e9..7a654cb 100644 --- a/src/scan/stmt.rs +++ b/src/scan/stmt.rs @@ -2,6 +2,7 @@ use super::{Scanner, scan}; use crate::intern::{Interned,intern}; use crate::native::NativeMod; use crate::runtime::{Scope, ScopeInner, Module}; +use crate::LINE; use super::{ literal::{Litr, Function, LocalFuncRaw, LocalFunc, ExternFunc, KsType}, expr::Expr @@ -143,9 +144,7 @@ impl Scanner<'_> { let len = self.src.len(); self.next(); loop { - if self.i() >= len { - self.err("未闭合的块大括号"); - } + assert!(self.i() { if let Stmt::Empty = s { continue; } - stmts.0.push((self.line(), s)); + stmts.0.push((unsafe{LINE}, s)); } } // 返回语句语法糖 @@ -180,7 +179,7 @@ impl Scanner<'_> { b"if"=> self.ifing(), b"break"=> Stmt::Break, b"continue"=> Stmt::Continue, - b"async"|b"await"=> self.err("异步关键词暂未实现"), + b"async"|b"await"=> panic!("异步关键词暂未实现"), _=> { let expr = self.expr_with_left(ident, vec![]); Stmt::Expression(expr) @@ -207,7 +206,7 @@ impl Scanner<'_> { /// 解析let关键词 fn letting(&self)-> AssignDef { self.spaces(); - let id = self.ident().unwrap_or_else(||self.err("let后需要标识符")); + let id = self.ident().unwrap_or_else(||panic!("let后需要标识符")); let id = intern(id); // 检查标识符后的符号 @@ -218,7 +217,7 @@ impl Scanner<'_> { self.next(); let val = self.expr(); if let Expr::Empty = val { - self.err("无法为空气赋值") + panic!("无法为空气赋值") } AssignDef { id, val @@ -227,16 +226,14 @@ impl Scanner<'_> { b'(' => { self.next(); let args = self.arguments(); - if self.cur() != b')' { - self.err("函数声明右括号缺失"); - } + assert!(self.cur()==b')', "函数声明右括号缺失"); self.next(); let stmt = self.stmt(); let mut stmts = if let Stmt::Block(b) = stmt { b }else { - Statements(vec![(self.line(), stmt)]) + Statements(vec![(unsafe{LINE}, stmt)]) }; // scan过程产生的LocalFunc是没绑定作用域的,因此不能由运行时来控制其内存释放 @@ -264,14 +261,12 @@ impl Scanner<'_> { let mut i = self.i(); let len = self.src.len(); while self.src[i] != b'>' { - if i >= len { - self.err("extern后需要 > 符号"); - } + assert!(i 符号"); i += 1; } let path = &self.src[self.i()..i]; - let lib = Clib::load(path).unwrap_or_else(|e|self.err(&e)); + let lib = Clib::load(path).unwrap_or_else(|e|panic!("{}",e)); self.set_i(i + 1); self.spaces(); @@ -285,22 +280,18 @@ impl Scanner<'_> { if let Some(i) = self.ident() { sym = i; }else { - self.err(":后需要别名") + panic!(":后需要别名") }; }else { sym = $id; } // 解析小括号包裹的参数声明 - if self.cur() != b'(' { - self.err("extern函数后应有括号"); - } + assert!(self.cur()==b'(', "extern函数后应有括号"); self.next(); let argdecl = self.arguments(); self.spaces(); - if self.cur() != b')' { - self.err("extern函数声明右括号缺失"); - } + assert!(self.cur() == b')', "extern函数声明右括号缺失"); self.next(); if self.cur() == b';' { @@ -308,10 +299,10 @@ impl Scanner<'_> { } // 将函数名(id)和指针(ptr)作为赋值语句推到语句列表里 - let ptr = lib.get(sym).unwrap_or_else(||self.err( - &format!("动态库'{}'中不存在'{}'函数", + let ptr = lib.get(sym).unwrap_or_else(||panic!( + "动态库'{}'中不存在'{}'函数", String::from_utf8_lossy(path), - String::from_utf8_lossy(sym)))); + String::from_utf8_lossy(sym))); self.push(Stmt::Let(AssignDef { id:intern($id), val: Expr::Literal(Litr::Func(Function::Extern(ExternFunc { @@ -330,13 +321,11 @@ impl Scanner<'_> { self.spaces(); } self.spaces(); - if self.cur() != b'}' { - self.err("extern大括号未闭合") - } + assert!(self.cur() == b'}', "extern大括号未闭合"); self.next(); }else { // 省略大括号语法 - let id = self.ident().unwrap_or_else(||self.err("extern后应有函数名")); + let id = self.ident().unwrap_or_else(||panic!("extern后应有函数名")); parse_decl!(id); } } @@ -355,16 +344,15 @@ impl Scanner<'_> { /// 解析类声明 fn classing(&self)-> Stmt { self.spaces(); - let id = self.ident().unwrap_or_else(||self.err("class后需要标识符")); + let id = self.ident().unwrap_or_else(||panic!("class后需要标识符")); self.spaces(); if self.cur() == b'=' { self.next(); let right = self.expr(); return Stmt::Using(intern(id),right); } - if self.cur() != b'{' { - self.err("class需要大括号"); - } + + assert!(self.cur() == b'{', "class需要大括号"); self.next(); let mut props = Vec::new(); @@ -390,9 +378,7 @@ impl Scanner<'_> { self.next(); // 参数 let args = self.arguments(); - if self.cur() != b')' { - self.err("函数声明右括号缺失??"); - } + assert!(self.cur() == b')', "函数声明右括号缺失"); self.next(); // 函数体 @@ -400,7 +386,7 @@ impl Scanner<'_> { let mut stmts = if let Stmt::Block(b) = stmt { b }else { - Statements(vec![(self.line(), stmt)]) + Statements(vec![(unsafe{LINE}, stmt)]) }; let v = ClassFuncRaw {name: intern(id), f:LocalFuncRaw{argdecl:args,stmts}, public}; @@ -426,9 +412,7 @@ impl Scanner<'_> { } self.spaces(); - if self.cur() != b'}' { - self.err("class大括号未闭合"); - } + assert!(self.cur()==b'}', "class大括号未闭合"); self.next(); Stmt::Class(ClassDefRaw { name:intern(id), props, methods, statics @@ -447,14 +431,14 @@ impl Scanner<'_> { if let Expr::LocalDecl(f) = asn.val { return Stmt::ExportFn(asn.id, f.clone()); } - self.err("模块只能导出本地函数。\n 若导出外界函数请用本地函数包裹。") + panic!("模块只能导出本地函数。\n 若导出外界函数请用本地函数包裹。") }, b':' => { self.next(); let cls = self.classing(); match cls { Stmt::Class(cls)=> return Stmt::ExportCls(cls), - Stmt::Using(_,_)=> self.err("无法导出using"), + Stmt::Using(_,_)=> panic!("无法导出using"), _=> unreachable!() } } @@ -466,9 +450,7 @@ impl Scanner<'_> { let len = self.src.len(); let mut dot = 0; loop { - if i >= len { - self.err("mod后需要 > 符号"); - } + assert!(i 符号"); let cur = self.src[i]; if cur == b'>' { break; @@ -483,28 +465,26 @@ impl Scanner<'_> { self.set_i(i + 1); self.spaces(); - let name = intern(&self.ident().unwrap_or_else(||self.err("需要为模块命名"))); + let name = intern(&self.ident().unwrap_or_else(||panic!("需要为模块命名"))); self.spaces(); - - if dot == 0 { - self.err("未知模块类型") - } + + assert!(dot!=0, "未知模块类型"); let suffix = &self.src[dot..i]; match suffix { b".ksm"|b".dll"=> { let module = crate::native::parse(path).unwrap_or_else(|e| - self.err(&format!("模块解析失败:{}\n {}",e,String::from_utf8_lossy(path)))); + panic!("模块解析失败:{}\n {}",e,String::from_utf8_lossy(path))); Stmt::NativeMod(name, module) } b".ks"=> { let path = &*String::from_utf8_lossy(path); - let file = std::fs::read(path).unwrap_or_else(|e|self.err(&format!( + let file = std::fs::read(path).unwrap_or_else(|e|panic!( "无法找到模块'{}'", path - ))); + )); let mut module = crate::runtime::run(&scan(&file)).exports; Stmt::Mod(name, module) } - _ => self.err("未知模块类型") + _ => panic!("未知模块类型") } } @@ -546,7 +526,7 @@ impl Scanner<'_> { let exec = Box::new(self.stmt()); return Stmt::ForIter {iterator:right, id:Some(id), exec}; } - self.err("`for v:iter`语句中:左边必须是标识符") + panic!("`for v:iter`语句中:左边必须是标识符") } // 不使用迭代器值