mirror of
https://github.com/voltrevo/ValueScript.git
synced 2026-01-14 16:08:02 -05:00
Capture this in arrow functions
This commit is contained in:
@@ -6,6 +6,7 @@ use swc_common::Spanned;
|
||||
use crate::asm::{Array, Instruction, Label, Number, Object, Register, Value};
|
||||
use crate::diagnostic::{Diagnostic, DiagnosticLevel};
|
||||
use crate::function_compiler::{FunctionCompiler, Functionish, QueuedFunction};
|
||||
use crate::ident::Ident as CrateIdent;
|
||||
use crate::scope::{NameId, OwnerId};
|
||||
use crate::scope_analysis::{fn_to_owner_id, NameType};
|
||||
use crate::target_accessor::TargetAccessor;
|
||||
@@ -86,7 +87,7 @@ impl<'a> ExpressionCompiler<'a> {
|
||||
use swc_ecma_ast::Expr::*;
|
||||
|
||||
match expr {
|
||||
This(_) => Value::Register(Register::this()).to_ce(),
|
||||
This(this) => self.ident(&CrateIdent::this(this.span), target_register),
|
||||
Array(array_exp) => self.array_expression(array_exp, target_register),
|
||||
Object(object_exp) => self.object_expression(object_exp, target_register),
|
||||
Fn(fn_) => self.fn_expression(fn_, target_register),
|
||||
@@ -123,7 +124,7 @@ impl<'a> ExpressionCompiler<'a> {
|
||||
|
||||
self.compile(seq_exp.exprs.last().unwrap(), target_register)
|
||||
}
|
||||
Ident(ident) => self.identifier(ident, target_register),
|
||||
Ident(ident) => self.ident(&CrateIdent::from_swc_ident(ident), target_register),
|
||||
Lit(lit) => self.compile_literal(lit).to_ce(),
|
||||
Tpl(tpl) => self.template_literal(tpl, target_register),
|
||||
TaggedTpl(tagged_tpl) => {
|
||||
@@ -292,7 +293,7 @@ impl<'a> ExpressionCompiler<'a> {
|
||||
CompiledExpression::new(Value::Register(target), nested_registers)
|
||||
}
|
||||
|
||||
pub fn get_register_for_ident_mutation(&mut self, ident: &swc_ecma_ast::Ident) -> Register {
|
||||
pub fn get_register_for_ident_mutation(&mut self, ident: &CrateIdent) -> Register {
|
||||
let (reg, err_msg) = match self.fnc.lookup_value(ident) {
|
||||
Some(Value::Register(reg)) => (Some(reg), None),
|
||||
lookup_result => (
|
||||
@@ -343,7 +344,9 @@ impl<'a> ExpressionCompiler<'a> {
|
||||
) -> CompiledExpression {
|
||||
let mut at = match &assign_expr.left {
|
||||
swc_ecma_ast::PatOrExpr::Pat(pat) => match &**pat {
|
||||
swc_ecma_ast::Pat::Ident(ident) => TargetAccessor::compile_ident(self, &ident.id),
|
||||
swc_ecma_ast::Pat::Ident(ident) => {
|
||||
TargetAccessor::compile_ident(self, &CrateIdent::from_swc_ident(&ident.id))
|
||||
}
|
||||
swc_ecma_ast::Pat::Expr(expr) => TargetAccessor::compile(self, expr, true),
|
||||
_ => return self.assign_pat_eq(pat, &assign_expr.right, target_register),
|
||||
},
|
||||
@@ -410,9 +413,9 @@ impl<'a> ExpressionCompiler<'a> {
|
||||
let mut target = match &assign_expr.left {
|
||||
PatOrExpr::Expr(expr) => TargetAccessor::compile(self, expr, true),
|
||||
PatOrExpr::Pat(pat) => match &**pat {
|
||||
Pat::Ident(ident) => {
|
||||
TargetAccessor::Register(self.get_register_for_ident_mutation(&ident.id))
|
||||
}
|
||||
Pat::Ident(ident) => TargetAccessor::Register(
|
||||
self.get_register_for_ident_mutation(&CrateIdent::from_swc_ident(&ident.id)),
|
||||
),
|
||||
_ => {
|
||||
self.fnc.diagnostics.push(Diagnostic {
|
||||
level: DiagnosticLevel::Error,
|
||||
@@ -496,7 +499,7 @@ impl<'a> ExpressionCompiler<'a> {
|
||||
Prop::Shorthand(ident) => {
|
||||
let prop_key = Value::String(ident.sym.to_string());
|
||||
|
||||
let mut compiled_value = self.identifier(ident, None);
|
||||
let mut compiled_value = self.ident(&CrateIdent::from_swc_ident(ident), None);
|
||||
sub_nested_registers.append(&mut compiled_value.nested_registers);
|
||||
compiled_value.release_checker.has_unreleased_registers = false;
|
||||
let prop_value = compiled_value.value;
|
||||
@@ -1224,9 +1227,9 @@ impl<'a> ExpressionCompiler<'a> {
|
||||
CompiledExpression::new(Value::Register(dst), nested_registers)
|
||||
}
|
||||
|
||||
pub fn identifier(
|
||||
pub fn ident(
|
||||
&mut self,
|
||||
ident: &swc_ecma_ast::Ident,
|
||||
ident: &CrateIdent,
|
||||
target_register: Option<Register>,
|
||||
) -> CompiledExpression {
|
||||
let fn_as_owner_id = match self.fnc.scope_analysis.lookup(ident) {
|
||||
@@ -1251,6 +1254,8 @@ impl<'a> ExpressionCompiler<'a> {
|
||||
}
|
||||
};
|
||||
|
||||
let value = self.fnc.lookup_value(ident).unwrap_or_default();
|
||||
|
||||
let name = match self.fnc.lookup(ident) {
|
||||
Some(v) => v,
|
||||
None => {
|
||||
@@ -1258,8 +1263,6 @@ impl<'a> ExpressionCompiler<'a> {
|
||||
}
|
||||
};
|
||||
|
||||
let value = name.value.clone();
|
||||
|
||||
match fn_as_owner_id {
|
||||
Some(owner_id) => {
|
||||
let capture_params = self.fnc.scope_analysis.get_register_captures(&owner_id);
|
||||
@@ -1376,7 +1379,9 @@ impl<'a> ExpressionCompiler<'a> {
|
||||
}
|
||||
ObjectPatProp::Assign(assign) => {
|
||||
let key = assign.key.sym.to_string();
|
||||
let reg = self.fnc.get_variable_register(&assign.key);
|
||||
let reg = self
|
||||
.fnc
|
||||
.get_variable_register(&CrateIdent::from_swc_ident(&assign.key));
|
||||
|
||||
self.fnc.push(Instruction::Sub(
|
||||
Value::Register(register.clone()),
|
||||
|
||||
@@ -14,6 +14,7 @@ use crate::compile_enum_value::compile_enum_value;
|
||||
use crate::diagnostic::{Diagnostic, DiagnosticLevel};
|
||||
use crate::expression_compiler::CompiledExpression;
|
||||
use crate::expression_compiler::ExpressionCompiler;
|
||||
use crate::ident::Ident;
|
||||
use crate::name_allocator::{NameAllocator, RegAllocator};
|
||||
use crate::scope::{NameId, OwnerId};
|
||||
use crate::scope_analysis::{fn_to_owner_id, Name, ScopeAnalysis};
|
||||
@@ -132,7 +133,7 @@ impl FunctionCompiler {
|
||||
self.current.body.push(FnLine::Comment(message));
|
||||
}
|
||||
|
||||
pub fn lookup(&mut self, ident: &swc_ecma_ast::Ident) -> Option<&Name> {
|
||||
pub fn lookup(&mut self, ident: &Ident) -> Option<&Name> {
|
||||
let name = self.scope_analysis.lookup(ident);
|
||||
|
||||
if name.is_none() {
|
||||
@@ -146,7 +147,7 @@ impl FunctionCompiler {
|
||||
name
|
||||
}
|
||||
|
||||
pub fn lookup_value(&self, ident: &swc_ecma_ast::Ident) -> Option<Value> {
|
||||
pub fn lookup_value(&self, ident: &Ident) -> Option<Value> {
|
||||
self.scope_analysis.lookup_value(&self.owner_id, ident)
|
||||
}
|
||||
|
||||
@@ -404,7 +405,7 @@ impl FunctionCompiler {
|
||||
swc_ecma_ast::TsParamPropParam::Ident(ident) => {
|
||||
match ident.id.sym.to_string().as_str() {
|
||||
"this" => None,
|
||||
_ => Some(self.get_variable_register(&ident.id)),
|
||||
_ => Some(self.get_variable_register(&Ident::from_swc_ident(&ident.id))),
|
||||
}
|
||||
}
|
||||
swc_ecma_ast::TsParamPropParam::Assign(assign) => {
|
||||
@@ -431,7 +432,7 @@ impl FunctionCompiler {
|
||||
Some(match param_pat {
|
||||
Pat::Ident(ident) => match ident.id.sym.to_string().as_str() {
|
||||
"this" => return None,
|
||||
_ => self.get_variable_register(&ident.id),
|
||||
_ => self.get_variable_register(&Ident::from_swc_ident(&ident.id)),
|
||||
},
|
||||
Pat::Assign(assign) => return self.get_pattern_register_opt(&assign.left),
|
||||
Pat::Array(_) => self.allocate_numbered_reg("_array_pat"),
|
||||
@@ -452,7 +453,7 @@ impl FunctionCompiler {
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_variable_register(&mut self, ident: &swc_ecma_ast::Ident) -> Register {
|
||||
pub fn get_variable_register(&mut self, ident: &Ident) -> Register {
|
||||
match self.scope_analysis.lookup_value(&self.owner_id, ident) {
|
||||
Some(Value::Register(reg)) => reg,
|
||||
lookup_result => {
|
||||
@@ -462,7 +463,7 @@ impl FunctionCompiler {
|
||||
"Register should have been allocated for variable {}, instead: {:?}",
|
||||
ident.sym, lookup_result,
|
||||
),
|
||||
span: ident.span(),
|
||||
span: ident.span,
|
||||
});
|
||||
|
||||
self.allocate_numbered_reg("_error_variable_without_register")
|
||||
@@ -1220,7 +1221,7 @@ impl FunctionCompiler {
|
||||
self
|
||||
.queue
|
||||
.add(QueuedFunction {
|
||||
definition_pointer: match self.lookup_value(&fn_decl.ident) {
|
||||
definition_pointer: match self.lookup_value(&Ident::from_swc_ident(&fn_decl.ident)) {
|
||||
Some(Value::Pointer(p)) => p,
|
||||
_ => {
|
||||
self.diagnostics.push(Diagnostic {
|
||||
@@ -1228,7 +1229,7 @@ impl FunctionCompiler {
|
||||
message: format!(
|
||||
"Lookup of function {} was not a pointer, lookup_result: {:?}",
|
||||
fn_decl.ident.sym,
|
||||
self.lookup_value(&fn_decl.ident)
|
||||
self.lookup_value(&Ident::from_swc_ident(&fn_decl.ident))
|
||||
),
|
||||
span: fn_decl.ident.span,
|
||||
});
|
||||
@@ -1247,7 +1248,7 @@ impl FunctionCompiler {
|
||||
TsEnum(ts_enum) => {
|
||||
let pointer = match self
|
||||
.scope_analysis
|
||||
.lookup_value(&OwnerId::Module, &ts_enum.id)
|
||||
.lookup_value(&OwnerId::Module, &Ident::from_swc_ident(&ts_enum.id))
|
||||
{
|
||||
Some(Value::Pointer(p)) => p,
|
||||
_ => {
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
#[derive(Debug)]
|
||||
pub struct Ident {
|
||||
pub sym: swc_atoms::JsWord,
|
||||
pub span: swc_common::Span,
|
||||
|
||||
@@ -16,6 +16,7 @@ use crate::compile_enum_value::compile_enum_value;
|
||||
use crate::diagnostic::{Diagnostic, DiagnosticLevel};
|
||||
use crate::expression_compiler::{CompiledExpression, ExpressionCompiler};
|
||||
use crate::function_compiler::{FunctionCompiler, Functionish};
|
||||
use crate::ident::Ident;
|
||||
use crate::name_allocator::{ident_from_str, NameAllocator};
|
||||
use crate::scope::OwnerId;
|
||||
use crate::scope_analysis::ScopeAnalysis;
|
||||
@@ -205,7 +206,7 @@ impl ModuleCompiler {
|
||||
let value = match &*ede.expr {
|
||||
swc_ecma_ast::Expr::Ident(ident) => self
|
||||
.scope_analysis
|
||||
.lookup(ident)
|
||||
.lookup(&Ident::from_swc_ident(ident))
|
||||
.map(|name| name.value.clone()),
|
||||
expr => static_eval_expr(&self.scope_analysis, &self.constants_map.borrow(), expr),
|
||||
};
|
||||
@@ -315,7 +316,7 @@ impl ModuleCompiler {
|
||||
}
|
||||
};
|
||||
|
||||
let pointer = match self.scope_analysis.lookup(ident) {
|
||||
let pointer = match self.scope_analysis.lookup(&Ident::from_swc_ident(ident)) {
|
||||
Some(name) => match &name.value {
|
||||
Value::Pointer(p) => p.clone(),
|
||||
_ => {
|
||||
@@ -363,7 +364,7 @@ impl ModuleCompiler {
|
||||
|
||||
let pointer = match self
|
||||
.scope_analysis
|
||||
.lookup_value(&OwnerId::Module, &fn_.ident)
|
||||
.lookup_value(&OwnerId::Module, &Ident::from_swc_ident(&fn_.ident))
|
||||
{
|
||||
Some(Value::Pointer(p)) => p,
|
||||
_ => {
|
||||
@@ -396,7 +397,7 @@ impl ModuleCompiler {
|
||||
fn compile_enum_decl(&mut self, export: bool, ts_enum: &swc_ecma_ast::TsEnumDecl) {
|
||||
let pointer = match self
|
||||
.scope_analysis
|
||||
.lookup_value(&OwnerId::Module, &ts_enum.id)
|
||||
.lookup_value(&OwnerId::Module, &Ident::from_swc_ident(&ts_enum.id))
|
||||
{
|
||||
Some(Value::Pointer(p)) => p,
|
||||
_ => {
|
||||
@@ -443,7 +444,10 @@ impl ModuleCompiler {
|
||||
Some(ident) => {
|
||||
let fn_name = ident.sym.to_string();
|
||||
|
||||
let defn = match self.scope_analysis.lookup_value(&OwnerId::Module, ident) {
|
||||
let defn = match self
|
||||
.scope_analysis
|
||||
.lookup_value(&OwnerId::Module, &Ident::from_swc_ident(ident))
|
||||
{
|
||||
Some(Value::Pointer(p)) => p,
|
||||
_ => {
|
||||
self.diagnostics.push(Diagnostic {
|
||||
@@ -569,7 +573,7 @@ impl ModuleCompiler {
|
||||
}
|
||||
None => match self
|
||||
.scope_analysis
|
||||
.lookup_value(&OwnerId::Module, orig_name)
|
||||
.lookup_value(&OwnerId::Module, &Ident::from_swc_ident(orig_name))
|
||||
{
|
||||
Some(Value::Pointer(p)) => Some(p),
|
||||
lookup_result => {
|
||||
@@ -694,7 +698,7 @@ impl ModuleCompiler {
|
||||
|
||||
let pointer = match self
|
||||
.scope_analysis
|
||||
.lookup_value(&OwnerId::Module, &named.local)
|
||||
.lookup_value(&OwnerId::Module, &Ident::from_swc_ident(&named.local))
|
||||
{
|
||||
Some(Value::Pointer(p)) => p,
|
||||
_ => {
|
||||
@@ -730,7 +734,7 @@ impl ModuleCompiler {
|
||||
|
||||
let pointer = match self
|
||||
.scope_analysis
|
||||
.lookup_value(&OwnerId::Module, &default.local)
|
||||
.lookup_value(&OwnerId::Module, &Ident::from_swc_ident(&default.local))
|
||||
{
|
||||
Some(Value::Pointer(p)) => p,
|
||||
_ => {
|
||||
@@ -759,7 +763,7 @@ impl ModuleCompiler {
|
||||
|
||||
let pointer = match self
|
||||
.scope_analysis
|
||||
.lookup_value(&OwnerId::Module, &namespace.local)
|
||||
.lookup_value(&OwnerId::Module, &Ident::from_swc_ident(&namespace.local))
|
||||
{
|
||||
Some(Value::Pointer(p)) => p,
|
||||
_ => {
|
||||
@@ -819,7 +823,10 @@ impl ModuleCompiler {
|
||||
let mut dependent_definitions: Vec<Definition>;
|
||||
|
||||
let defn_name = match ident {
|
||||
Some(ident) => match self.scope_analysis.lookup_value(&OwnerId::Module, ident) {
|
||||
Some(ident) => match self
|
||||
.scope_analysis
|
||||
.lookup_value(&OwnerId::Module, &Ident::from_swc_ident(ident))
|
||||
{
|
||||
Some(Value::Pointer(p)) => p,
|
||||
_ => {
|
||||
self.diagnostics.push(Diagnostic {
|
||||
|
||||
@@ -136,12 +136,12 @@ impl ScopeAnalysis {
|
||||
sa
|
||||
}
|
||||
|
||||
pub fn lookup(&self, ident: &swc_ecma_ast::Ident) -> Option<&Name> {
|
||||
pub fn lookup(&self, ident: &Ident) -> Option<&Name> {
|
||||
let name_id = &self.refs.get(&ident.span)?.name_id;
|
||||
self.names.get(name_id)
|
||||
}
|
||||
|
||||
pub fn lookup_value(&self, scope: &OwnerId, ident: &swc_ecma_ast::Ident) -> Option<Value> {
|
||||
pub fn lookup_value(&self, scope: &OwnerId, ident: &Ident) -> Option<Value> {
|
||||
let name_id = &self.refs.get(&ident.span)?.name_id;
|
||||
self.lookup_by_name_id(scope, name_id)
|
||||
}
|
||||
|
||||
@@ -5,6 +5,7 @@ use valuescript_vm::operations::to_i32;
|
||||
use crate::{
|
||||
asm::{Array, Builtin, Number, Object, Pointer, Value},
|
||||
expression_compiler::value_from_literal,
|
||||
ident::Ident,
|
||||
scope_analysis::ScopeAnalysis,
|
||||
};
|
||||
|
||||
@@ -84,7 +85,10 @@ pub fn static_eval_expr(
|
||||
swc_ecma_ast::Expr::SuperProp(_) => None,
|
||||
swc_ecma_ast::Expr::Call(_) => None,
|
||||
swc_ecma_ast::Expr::New(_) => None,
|
||||
swc_ecma_ast::Expr::Ident(ident) => match sa.lookup(ident).map(|name| name.value.clone()) {
|
||||
swc_ecma_ast::Expr::Ident(ident) => match sa
|
||||
.lookup(&Ident::from_swc_ident(ident))
|
||||
.map(|name| name.value.clone())
|
||||
{
|
||||
Some(Value::Pointer(p)) => cm.get(&p).cloned(),
|
||||
Some(value) => Some(value),
|
||||
None => None,
|
||||
|
||||
@@ -3,6 +3,7 @@ use std::mem::take;
|
||||
use crate::{
|
||||
asm::{Instruction, Register, Value},
|
||||
expression_compiler::{CompiledExpression, ExpressionCompiler},
|
||||
ident::Ident as CrateIdent,
|
||||
Diagnostic, DiagnosticLevel,
|
||||
};
|
||||
use swc_common::Spanned;
|
||||
@@ -23,7 +24,7 @@ impl TargetAccessor {
|
||||
use swc_ecma_ast::Expr::*;
|
||||
|
||||
return match expr {
|
||||
Ident(ident) => match ec.fnc.lookup(ident) {
|
||||
Ident(ident) => match ec.fnc.lookup(&crate::ident::Ident::from_swc_ident(ident)) {
|
||||
Some(name) => !name.effectively_const,
|
||||
_ => false, // TODO: InternalError?
|
||||
},
|
||||
@@ -56,8 +57,8 @@ impl TargetAccessor {
|
||||
use swc_ecma_ast::Expr::*;
|
||||
|
||||
return match expr {
|
||||
Ident(ident) => TargetAccessor::compile_ident(ec, ident),
|
||||
This(_) => TargetAccessor::Register(Register::this()),
|
||||
Ident(ident) => TargetAccessor::compile_ident(ec, &CrateIdent::from_swc_ident(ident)),
|
||||
This(this) => TargetAccessor::compile_ident(ec, &CrateIdent::this(this.span)),
|
||||
Member(member) => {
|
||||
let obj = TargetAccessor::compile(ec, &member.obj, false);
|
||||
let subscript = ec.member_prop(&member.prop, None);
|
||||
@@ -100,7 +101,7 @@ impl TargetAccessor {
|
||||
};
|
||||
}
|
||||
|
||||
pub fn compile_ident(ec: &mut ExpressionCompiler, ident: &swc_ecma_ast::Ident) -> TargetAccessor {
|
||||
pub fn compile_ident(ec: &mut ExpressionCompiler, ident: &CrateIdent) -> TargetAccessor {
|
||||
TargetAccessor::Register(ec.get_register_for_ident_mutation(ident))
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user