feat: fully remove typescript init code

This commit is contained in:
TopchetoEU 2023-10-04 08:08:54 +03:00
parent 63b04019cf
commit 68f3b6d926
Signed by: topchetoeu
GPG Key ID: 6531B8583E5F6ED4
12 changed files with 160 additions and 397 deletions

View File

@ -1,114 +0,0 @@
interface Environment {
global: typeof globalThis & Record<string, any>;
proto(name: string): object;
setProto(name: string, val: object): void;
symbol(name: string): symbol;
}
interface Internals {
object: ObjectConstructor;
function: FunctionConstructor;
array: ArrayConstructor;
promise: PromiseConstructor;
bool: BooleanConstructor;
number: NumberConstructor;
string: StringConstructor;
symbol: SymbolConstructor;
error: ErrorConstructor;
syntax: SyntaxErrorConstructor;
type: TypeErrorConstructor;
range: RangeErrorConstructor;
regexp: typeof RegExp;
map: typeof Map;
set: typeof Set;
timers: {
setTimeout: <T extends any[]>(handle: (...args: [ ...T, ...any[] ]) => void, delay?: number, ...args: T) => number,
setInterval: <T extends any[]>(handle: (...args: [ ...T, ...any[] ]) => void, delay?: number, ...args: T) => number,
clearTimeout: (id: number) => void,
clearInterval: (id: number) => void,
}
markSpecial(...funcs: Function[]): void;
getEnv(func: Function): Environment | undefined;
setEnv<T>(func: T, env: Environment): T;
apply(func: Function, thisArg: any, args: any[], env?: Environment): any;
bind(func: Function, thisArg: any): any;
delay(timeout: number, callback: Function): () => void;
pushMessage(micro: boolean, func: Function, thisArg: any, args: any[]): void;
strlen(val: string): number;
char(val: string): number;
stringFromStrings(arr: string[]): string;
stringFromChars(arr: number[]): string;
getSymbol(name?: string): symbol;
symbolToString(sym: symbol): string;
isArray(obj: any): boolean;
generator(func: (_yield: <T>(val: T) => unknown) => (...args: any[]) => unknown): GeneratorFunction;
defineField(obj: object, key: any, val: any, writable: boolean, enumerable: boolean, configurable: boolean): boolean;
defineProp(obj: object, key: any, get: Function | undefined, set: Function | undefined, enumerable: boolean, configurable: boolean): boolean;
keys(obj: object, onlyString: boolean): any[];
ownProp(obj: any, key: string): PropertyDescriptor<any, any>;
ownPropKeys(obj: any): any[];
lock(obj: object, type: 'ext' | 'seal' | 'freeze'): void;
extensible(obj: object): boolean;
sort(arr: any[], comaprator: (a: any, b: any) => number): void;
log(...args: any[]): void;
}
var env: Environment = arguments[0], internals: Internals = arguments[1];
try {
const Array = env.global.Array = internals.array;
env.global.Object = internals.object;
env.global.Function = internals.function;
env.global.Promise = internals.promise;
env.global.Boolean = internals.bool;
env.global.Number = internals.number;
env.global.String = internals.string;
env.global.Symbol = internals.symbol;
env.global.Error = internals.error;
env.global.SyntaxError = internals.syntax;
env.global.TypeError = internals.type;
env.global.RangeError = internals.range;
env.global.RegExp = internals.regexp;
env.global.Map = internals.map;
env.global.Set = internals.set;
env.global.setInterval = internals.bind(internals.timers.setInterval, internals.timers);
env.global.setTimeout = internals.bind(internals.timers.setTimeout, internals.timers);
env.global.clearInterval = internals.bind(internals.timers.clearInterval, internals.timers);
env.global.clearTimeout = internals.bind(internals.timers.clearTimeout, internals.timers);
const log = env.global.log = internals.bind(internals.log, internals);
env.setProto('object', env.global.Object.prototype);
env.setProto('function', env.global.Function.prototype);
env.setProto('array', env.global.Array.prototype);
env.setProto('number', env.global.Number.prototype);
env.setProto('string', env.global.String.prototype);
env.setProto('symbol', env.global.Symbol.prototype);
env.setProto('bool', env.global.Boolean.prototype);
env.setProto('error', env.global.Error.prototype);
env.setProto('rangeErr', env.global.RangeError.prototype);
env.setProto('typeErr', env.global.TypeError.prototype);
env.setProto('syntaxErr', env.global.SyntaxError.prototype);
(env.global.Object.prototype as any).__proto__ = null;
log('Loaded polyfills!');
}
catch (e: any) {
let err = 'Uncaught error while loading polyfills: ';
if (typeof Error !== 'undefined' && e instanceof Error && e.toString !== {}.toString) err += e;
else if ('message' in e) {
if ('name' in e) err += e.name + ": " + e.message;
else err += 'Error: ' + e.message;
}
else err += "[unknown]";
internals.log(err);
}

View File

@ -7,10 +7,11 @@ import java.io.InputStreamReader;
import java.nio.file.Files; import java.nio.file.Files;
import java.nio.file.Path; import java.nio.file.Path;
import me.topchetoeu.jscript.engine.MessageContext; import me.topchetoeu.jscript.engine.Message;
import me.topchetoeu.jscript.engine.Context; import me.topchetoeu.jscript.engine.Context;
import me.topchetoeu.jscript.engine.Engine; import me.topchetoeu.jscript.engine.Engine;
import me.topchetoeu.jscript.engine.Environment; import me.topchetoeu.jscript.engine.Environment;
import me.topchetoeu.jscript.engine.values.NativeFunction;
import me.topchetoeu.jscript.engine.values.Values; import me.topchetoeu.jscript.engine.values.Values;
import me.topchetoeu.jscript.events.Observer; import me.topchetoeu.jscript.events.Observer;
import me.topchetoeu.jscript.exceptions.EngineException; import me.topchetoeu.jscript.exceptions.EngineException;
@ -63,30 +64,35 @@ public class Main {
engine = new Engine(); engine = new Engine();
env = new Environment(null, null, null); env = new Environment(null, null, null);
var builderEnv = new Environment(null, null, null);
var exited = new boolean[1]; var exited = new boolean[1];
env.global.define("exit", ctx -> { engine.pushMsg(false, new Message(engine), new NativeFunction((ctx, thisArg, _a) -> {
exited[0] = true; new Internals().apply(env);
task.interrupt();
throw new InterruptedException();
});
env.global.define("go", ctx -> {
try {
var func = ctx.compile("do.js", new String(Files.readAllBytes(Path.of("do.js"))));
return func.call(ctx);
}
catch (IOException e) {
throw new EngineException("Couldn't open do.js");
}
});
engine.pushMsg( env.global.define("exit", _ctx -> {
false, exited[0] = true;
new Context(builderEnv, new MessageContext(engine)), task.interrupt();
"core.js", resourceToString("js/core.js"), throw new InterruptedException();
null, env, new Internals(env) });
).toObservable().on(valuePrinter); env.global.define("go", _ctx -> {
try {
var func = _ctx.compile("do.js", new String(Files.readAllBytes(Path.of("do.js"))));
return func.call(_ctx);
}
catch (IOException e) {
throw new EngineException("Couldn't open do.js");
}
});
return null;
}), null);
// engine.pushMsg(
// false,
// new Context(builderEnv, new MessageContext(engine)),
// "core.js", resourceToString("js/core.js"),
// null, env, new Internals(env)
// ).toObservable().on(valuePrinter);
task = engine.start(); task = engine.start();
var reader = new Thread(() -> { var reader = new Thread(() -> {
@ -96,7 +102,7 @@ public class Main {
var raw = in.readLine(); var raw = in.readLine();
if (raw == null) break; if (raw == null) break;
engine.pushMsg(false, new Context(env, new MessageContext(engine)), "<stdio>", raw, null).toObservable().once(valuePrinter); engine.pushMsg(false, new Context(env, new Message(engine)), "<stdio>", raw, null).toObservable().once(valuePrinter);
} }
catch (EngineException e) { catch (EngineException e) {
try { try {

View File

@ -6,15 +6,22 @@ import me.topchetoeu.jscript.parsing.Parsing;
public class Context { public class Context {
public final Environment env; public final Environment env;
public final MessageContext message; public final Message message;
public FunctionValue compile(String filename, String raw) throws InterruptedException { public FunctionValue compile(String filename, String raw) throws InterruptedException {
var res = Values.toString(this, env.compile.call(this, null, raw, filename)); var res = Values.toString(this, env.compile.call(this, null, raw, filename));
return Parsing.compile(env, filename, res); return Parsing.compile(env, filename, res);
} }
public Context(Environment funcCtx, MessageContext msgCtx) { public Context setEnv(Environment env) {
this.env = funcCtx; return new Context(env, message);
this.message = msgCtx; }
public Context setMsg(Message msg) {
return new Context(env, msg);
}
public Context(Environment env, Message msg) {
this.env = env;
this.message = msg;
} }
} }

View File

@ -32,9 +32,9 @@ public class Engine {
public final Object thisArg; public final Object thisArg;
public final Object[] args; public final Object[] args;
public final DataNotifier<Object> notifier = new DataNotifier<>(); public final DataNotifier<Object> notifier = new DataNotifier<>();
public final MessageContext ctx; public final Message ctx;
public Task(MessageContext ctx, FunctionValue func, Object thisArg, Object[] args) { public Task(Message ctx, FunctionValue func, Object thisArg, Object[] args) {
this.ctx = ctx; this.ctx = ctx;
this.func = func; this.func = func;
this.thisArg = thisArg; this.thisArg = thisArg;
@ -102,7 +102,7 @@ public class Engine {
return this.thread != null; return this.thread != null;
} }
public Awaitable<Object> pushMsg(boolean micro, MessageContext ctx, FunctionValue func, Object thisArg, Object ...args) { public Awaitable<Object> pushMsg(boolean micro, Message ctx, FunctionValue func, Object thisArg, Object ...args) {
var msg = new Task(ctx, func, thisArg, args); var msg = new Task(ctx, func, thisArg, args);
if (micro) microTasks.addLast(msg); if (micro) microTasks.addLast(msg);
else macroTasks.addLast(msg); else macroTasks.addLast(msg);

View File

@ -60,6 +60,10 @@ public class Environment {
return res; return res;
} }
public Context context(Message msg) {
return new Context(this, msg);
}
public Environment(FunctionValue compile, WrappersProvider nativeConverter, GlobalScope global) { public Environment(FunctionValue compile, WrappersProvider nativeConverter, GlobalScope global) {
if (compile == null) compile = new NativeFunction("compile", (ctx, thisArg, args) -> args.length == 0 ? "" : args[0]); if (compile == null) compile = new NativeFunction("compile", (ctx, thisArg, args) -> args.length == 0 ? "" : args[0]);
if (nativeConverter == null) nativeConverter = new NativeWrapperProvider(this); if (nativeConverter == null) nativeConverter = new NativeWrapperProvider(this);

View File

@ -7,7 +7,7 @@ import java.util.List;
import me.topchetoeu.jscript.engine.frame.CodeFrame; import me.topchetoeu.jscript.engine.frame.CodeFrame;
import me.topchetoeu.jscript.exceptions.EngineException; import me.topchetoeu.jscript.exceptions.EngineException;
public class MessageContext { public class Message {
public final Engine engine; public final Engine engine;
private final ArrayList<CodeFrame> frames = new ArrayList<>(); private final ArrayList<CodeFrame> frames = new ArrayList<>();
@ -15,7 +15,7 @@ public class MessageContext {
public List<CodeFrame> frames() { return Collections.unmodifiableList(frames); } public List<CodeFrame> frames() { return Collections.unmodifiableList(frames); }
public MessageContext pushFrame(Context ctx, CodeFrame frame) throws InterruptedException { public Message pushFrame(Context ctx, CodeFrame frame) throws InterruptedException {
this.frames.add(frame); this.frames.add(frame);
if (this.frames.size() > maxStackFrames) throw EngineException.ofRange("Stack overflow!"); if (this.frames.size() > maxStackFrames) throw EngineException.ofRange("Stack overflow!");
return this; return this;
@ -46,7 +46,11 @@ public class MessageContext {
return res; return res;
} }
public MessageContext(Engine engine) { public Context context(Environment env) {
return new Context(env, this);
}
public Message(Engine engine) {
this.engine = engine; this.engine = engine;
} }
} }

View File

@ -55,7 +55,7 @@ public class ObjectValue {
public final boolean memberWritable(Object key) { public final boolean memberWritable(Object key) {
if (state == State.FROZEN) return false; if (state == State.FROZEN) return false;
return values.containsKey(key) && !nonWritableSet.contains(key); return !values.containsKey(key) || !nonWritableSet.contains(key);
} }
public final boolean memberConfigurable(Object key) { public final boolean memberConfigurable(Object key) {
if (state == State.SEALED || state == State.FROZEN) return false; if (state == State.SEALED || state == State.FROZEN) return false;

View File

@ -20,7 +20,7 @@ public class FunctionPolyfill {
return func.call(ctx, thisArg, args); return func.call(ctx, thisArg, args);
} }
@Native(thisArg = true) public static FunctionValue bind(Context ctx, FunctionValue func, Object thisArg, Object... args) throws InterruptedException { @Native(thisArg = true) public static FunctionValue bind(FunctionValue func, Object thisArg, Object... args) {
if (!(func instanceof FunctionValue)) throw EngineException.ofError("Expected this to be a function."); if (!(func instanceof FunctionValue)) throw EngineException.ofError("Expected this to be a function.");
return new NativeFunction(func.name + " (bound)", (callCtx, _0, callArgs) -> { return new NativeFunction(func.name + " (bound)", (callCtx, _0, callArgs) -> {
@ -33,7 +33,7 @@ public class FunctionPolyfill {
System.arraycopy(callArgs, 0, resArgs, args.length, callArgs.length); System.arraycopy(callArgs, 0, resArgs, args.length, callArgs.length);
} }
return func.call(ctx, thisArg, resArgs); return func.call(callCtx, thisArg, resArgs);
}); });
} }
@Native(thisArg = true) public static String toString(Context ctx, Object func) { @Native(thisArg = true) public static String toString(Context ctx, Object func) {

View File

@ -1,49 +1,29 @@
package me.topchetoeu.jscript.polyfills; package me.topchetoeu.jscript.polyfills;
import java.util.HashMap;
import me.topchetoeu.jscript.engine.Context; import me.topchetoeu.jscript.engine.Context;
import me.topchetoeu.jscript.engine.Environment; import me.topchetoeu.jscript.engine.Environment;
import me.topchetoeu.jscript.engine.values.ArrayValue;
import me.topchetoeu.jscript.engine.values.CodeFunction;
import me.topchetoeu.jscript.engine.values.FunctionValue; import me.topchetoeu.jscript.engine.values.FunctionValue;
import me.topchetoeu.jscript.engine.values.NativeFunction;
import me.topchetoeu.jscript.engine.values.ObjectValue;
import me.topchetoeu.jscript.engine.values.Symbol;
import me.topchetoeu.jscript.engine.values.Values; import me.topchetoeu.jscript.engine.values.Values;
import me.topchetoeu.jscript.interop.Native; import me.topchetoeu.jscript.interop.Native;
public class Internals { public class Internals {
public final Environment targetEnv; private HashMap<Integer, Thread> threads = new HashMap<>();
private int i = 0;
@Native public final FunctionValue @Native public FunctionValue bind(FunctionValue func, Object thisArg) throws InterruptedException {
object, function, array, return FunctionPolyfill.bind(func, thisArg);
bool, number, string, symbol, }
promise, map, set, regexp, @Native public void log(Context ctx, Object ...args) throws InterruptedException {
error, syntax, type, range; for (var arg : args) {
Values.printValue(ctx, arg);
@Native public final TimerPolyfills timers = new TimerPolyfills();
@Native public void markSpecial(FunctionValue ...funcs) {
for (var func : funcs) {
func.special = true;
} }
System.out.println();
} }
@Native public Environment getEnv(Object func) {
if (func instanceof CodeFunction) return ((CodeFunction)func).environment; @Native public int setTimeout(Context ctx, FunctionValue func, int delay, Object ...args) {
else return null; var thread = new Thread(() -> {
}
@Native public Object setEnv(Object func, Environment env) {
if (func instanceof CodeFunction) ((CodeFunction)func).environment = env;
return func;
}
@Native public Object apply(Context ctx, FunctionValue func, Object thisArg, ArrayValue args, Environment env) throws InterruptedException {
if (env != null) ctx = new Context(env, ctx.message);
return func.call(ctx, thisArg, args.toArray());
}
@Native public FunctionValue bind(Context ctx, FunctionValue func, Object thisArg) throws InterruptedException {
return FunctionPolyfill.bind(ctx, func, thisArg);
}
@Native public FunctionValue delay(Context ctx, double delay, FunctionValue callback) throws InterruptedException {
var thread = new Thread((Runnable)() -> {
var ms = (long)delay; var ms = (long)delay;
var ns = (int)((delay - ms) * 10000000); var ns = (int)((delay - ms) * 10000000);
@ -52,130 +32,66 @@ public class Internals {
} }
catch (InterruptedException e) { return; } catch (InterruptedException e) { return; }
ctx.message.engine.pushMsg(false, ctx.message, callback, null); ctx.message.engine.pushMsg(false, ctx.message, func, null, args);
}); });
thread.start(); thread.start();
return new NativeFunction((_ctx, thisArg, args) -> { threads.put(++i, thread);
thread.interrupt();
return null;
});
}
@Native public void pushMessage(Context ctx, boolean micro, FunctionValue func, Object thisArg, Object[] args) {
ctx.message.engine.pushMsg(micro, ctx.message, func, thisArg, args);
}
@Native public int strlen(String str) { return i;
return str.length();
} }
@Native("char") public int _char(String str) { @Native public int setInterval(Context ctx, FunctionValue func, int delay, Object ...args) {
return str.charAt(0); var thread = new Thread(() -> {
} var ms = (long)delay;
@Native public String stringFromChars(char[] str) { var ns = (int)((delay - ms) * 10000000);
return new String(str);
}
@Native public String stringFromStrings(String[] str) {
var res = new char[str.length];
for (var i = 0; i < str.length; i++) res[i] = str[i].charAt(0); while (true) {
try {
return stringFromChars(res); Thread.sleep(ms, ns);
} }
@Native public Symbol getSymbol(String str) { catch (InterruptedException e) { return; }
return new Symbol(str);
} ctx.message.engine.pushMsg(false, ctx.message, func, null, args);
@Native public String symbolToString(Symbol str) {
return str.value;
}
@Native public void log(Context ctx, Object ...args) throws InterruptedException {
for (var arg : args) {
Values.printValue(ctx, arg);
}
System.out.println();
}
@Native public boolean isArray(Object obj) {
return obj instanceof ArrayValue;
}
@Native public GeneratorPolyfill generator(FunctionValue obj) {
return new GeneratorPolyfill(obj);
}
@Native public boolean defineField(Context ctx, ObjectValue obj, Object key, Object val, boolean writable, boolean enumerable, boolean configurable) {
return obj.defineProperty(ctx, key, val, writable, configurable, enumerable);
}
@Native public boolean defineProp(Context ctx, ObjectValue obj, Object key, FunctionValue getter, FunctionValue setter, boolean enumerable, boolean configurable) {
return obj.defineProperty(ctx, key, getter, setter, configurable, enumerable);
}
@Native public ArrayValue keys(Context ctx, Object obj, boolean onlyString) throws InterruptedException {
var res = new ArrayValue();
var i = 0;
var list = Values.getMembers(ctx, obj, true, false);
for (var el : list) res.set(ctx, i++, el);
return res;
}
@Native public ArrayValue ownPropKeys(Context ctx, Object obj, boolean symbols) throws InterruptedException {
var res = new ArrayValue();
if (Values.isObject(obj)) {
var i = 0;
var list = Values.object(obj).keys(true);
for (var el : list) res.set(ctx, i++, el);
}
return res;
}
@Native public ObjectValue ownProp(Context ctx, ObjectValue val, Object key) throws InterruptedException {
return val.getMemberDescriptor(ctx, key);
}
@Native public void lock(ObjectValue val, String type) {
switch (type) {
case "ext": val.preventExtensions(); break;
case "seal": val.seal(); break;
case "freeze": val.freeze(); break;
}
}
@Native public boolean extensible(ObjectValue val) {
return val.extensible();
}
@Native public void sort(Context ctx, ArrayValue arr, FunctionValue cmp) {
arr.sort((a, b) -> {
try {
var res = Values.toNumber(ctx, cmp.call(ctx, null, a, b));
if (res < 0) return -1;
if (res > 0) return 1;
return 0;
}
catch (InterruptedException e) {
Thread.currentThread().interrupt();
return 0;
} }
}); });
thread.start();
threads.put(++i, thread);
return i;
} }
public Internals(Environment targetEnv) { @Native public void clearTimeout(Context ctx, int i) {
this.targetEnv = targetEnv; var thread = threads.remove(i);
this.object = targetEnv.wrappersProvider.getConstr(ObjectPolyfill.class); if (thread != null) thread.interrupt();
this.function = targetEnv.wrappersProvider.getConstr(FunctionPolyfill.class); }
this.promise = targetEnv.wrappersProvider.getConstr(PromisePolyfill.class); @Native public void clearInterval(Context ctx, int i) {
this.array = targetEnv.wrappersProvider.getConstr(ArrayPolyfill.class); clearTimeout(ctx, i);
this.bool = targetEnv.wrappersProvider.getConstr(BooleanPolyfill.class); }
this.number = targetEnv.wrappersProvider.getConstr(NumberPolyfill.class);
this.string = targetEnv.wrappersProvider.getConstr(StringPolyfill.class); public void apply(Environment env) {
this.symbol = targetEnv.wrappersProvider.getConstr(SymbolPolyfill.class); var wp = env.wrappersProvider;
this.map = targetEnv.wrappersProvider.getConstr(MapPolyfill.class); var glob = env.global;
this.set = targetEnv.wrappersProvider.getConstr(SetPolyfill.class);
this.error = targetEnv.wrappersProvider.getConstr(ErrorPolyfill.class); glob.define(null, "Object", false, wp.getConstr(ObjectPolyfill.class));
this.syntax = targetEnv.wrappersProvider.getConstr(SyntaxErrorPolyfill.class); glob.define(null, "Function", false, wp.getConstr(FunctionPolyfill.class));
this.type = targetEnv.wrappersProvider.getConstr(TypeErrorPolyfill.class); glob.define(null, "Array", false, wp.getConstr(ArrayPolyfill.class));
this.range = targetEnv.wrappersProvider.getConstr(RangeErrorPolyfill.class);
this.regexp = targetEnv.wrappersProvider.getConstr(RegExpPolyfill.class); glob.define(null, "Boolean", false, wp.getConstr(BooleanPolyfill.class));
glob.define(null, "Number", false, wp.getConstr(NumberPolyfill.class));
glob.define(null, "String", false, wp.getConstr(StringPolyfill.class));
glob.define(null, "Symbol", false, wp.getConstr(SymbolPolyfill.class));
glob.define(null, "Promise", false, wp.getConstr(PromisePolyfill.class));
glob.define(null, "RegExp", false, wp.getConstr(RegExpPolyfill.class));
glob.define(null, "Map", false, wp.getConstr(MapPolyfill.class));
glob.define(null, "Set", false, wp.getConstr(SetPolyfill.class));
glob.define(null, "Error", false, wp.getConstr(ErrorPolyfill.class));
glob.define(null, "SyntaxError", false, wp.getConstr(SyntaxErrorPolyfill.class));
glob.define(null, "TypeError", false, wp.getConstr(TypeErrorPolyfill.class));
glob.define(null, "RangeError", false, wp.getConstr(RangeErrorPolyfill.class));
System.out.println("Loaded polyfills!");
} }
} }

View File

@ -1,6 +1,6 @@
package me.topchetoeu.jscript.polyfills; package me.topchetoeu.jscript.polyfills;
import me.topchetoeu.jscript.engine.MessageContext; import me.topchetoeu.jscript.engine.Message;
import me.topchetoeu.jscript.interop.Native; import me.topchetoeu.jscript.interop.Native;
public class Math { public class Math {
@ -22,19 +22,19 @@ public class Math {
public static final double LOG10E = java.lang.Math.log10(java.lang.Math.E); public static final double LOG10E = java.lang.Math.log10(java.lang.Math.E);
@Native @Native
public static double asin(MessageContext ctx, double x) throws InterruptedException { public static double asin(Message ctx, double x) throws InterruptedException {
return java.lang.Math.asin(x); return java.lang.Math.asin(x);
} }
@Native @Native
public static double acos(MessageContext ctx, double x) throws InterruptedException { public static double acos(Message ctx, double x) throws InterruptedException {
return java.lang.Math.acos(x); return java.lang.Math.acos(x);
} }
@Native @Native
public static double atan(MessageContext ctx, double x) throws InterruptedException { public static double atan(Message ctx, double x) throws InterruptedException {
return java.lang.Math.atan(x); return java.lang.Math.atan(x);
} }
@Native @Native
public static double atan2(MessageContext ctx, double y, double x) throws InterruptedException { public static double atan2(Message ctx, double y, double x) throws InterruptedException {
double _y = y; double _y = y;
double _x = x; double _x = x;
if (_x == 0) { if (_x == 0) {
@ -51,59 +51,59 @@ public class Math {
} }
@Native @Native
public static double asinh(MessageContext ctx, double x) throws InterruptedException { public static double asinh(Message ctx, double x) throws InterruptedException {
double _x = x; double _x = x;
return java.lang.Math.log(_x + java.lang.Math.sqrt(_x * _x + 1)); return java.lang.Math.log(_x + java.lang.Math.sqrt(_x * _x + 1));
} }
@Native @Native
public static double acosh(MessageContext ctx, double x) throws InterruptedException { public static double acosh(Message ctx, double x) throws InterruptedException {
double _x = x; double _x = x;
return java.lang.Math.log(_x + java.lang.Math.sqrt(_x * _x - 1)); return java.lang.Math.log(_x + java.lang.Math.sqrt(_x * _x - 1));
} }
@Native @Native
public static double atanh(MessageContext ctx, double x) throws InterruptedException { public static double atanh(Message ctx, double x) throws InterruptedException {
double _x = x; double _x = x;
if (_x <= -1 || _x >= 1) return Double.NaN; if (_x <= -1 || _x >= 1) return Double.NaN;
return .5 * java.lang.Math.log((1 + _x) / (1 - _x)); return .5 * java.lang.Math.log((1 + _x) / (1 - _x));
} }
@Native @Native
public static double sin(MessageContext ctx, double x) throws InterruptedException { public static double sin(Message ctx, double x) throws InterruptedException {
return java.lang.Math.sin(x); return java.lang.Math.sin(x);
} }
@Native @Native
public static double cos(MessageContext ctx, double x) throws InterruptedException { public static double cos(Message ctx, double x) throws InterruptedException {
return java.lang.Math.cos(x); return java.lang.Math.cos(x);
} }
@Native @Native
public static double tan(MessageContext ctx, double x) throws InterruptedException { public static double tan(Message ctx, double x) throws InterruptedException {
return java.lang.Math.tan(x); return java.lang.Math.tan(x);
} }
@Native @Native
public static double sinh(MessageContext ctx, double x) throws InterruptedException { public static double sinh(Message ctx, double x) throws InterruptedException {
return java.lang.Math.sinh(x); return java.lang.Math.sinh(x);
} }
@Native @Native
public static double cosh(MessageContext ctx, double x) throws InterruptedException { public static double cosh(Message ctx, double x) throws InterruptedException {
return java.lang.Math.cosh(x); return java.lang.Math.cosh(x);
} }
@Native @Native
public static double tanh(MessageContext ctx, double x) throws InterruptedException { public static double tanh(Message ctx, double x) throws InterruptedException {
return java.lang.Math.tanh(x); return java.lang.Math.tanh(x);
} }
@Native @Native
public static double sqrt(MessageContext ctx, double x) throws InterruptedException { public static double sqrt(Message ctx, double x) throws InterruptedException {
return java.lang.Math.sqrt(x); return java.lang.Math.sqrt(x);
} }
@Native @Native
public static double cbrt(MessageContext ctx, double x) throws InterruptedException { public static double cbrt(Message ctx, double x) throws InterruptedException {
return java.lang.Math.cbrt(x); return java.lang.Math.cbrt(x);
} }
@Native @Native
public static double hypot(MessageContext ctx, double ...vals) throws InterruptedException { public static double hypot(Message ctx, double ...vals) throws InterruptedException {
var res = 0.; var res = 0.;
for (var el : vals) { for (var el : vals) {
var val = el; var val = el;
@ -112,68 +112,68 @@ public class Math {
return java.lang.Math.sqrt(res); return java.lang.Math.sqrt(res);
} }
@Native @Native
public static int imul(MessageContext ctx, double a, double b) throws InterruptedException { public static int imul(Message ctx, double a, double b) throws InterruptedException {
return (int)a * (int)b; return (int)a * (int)b;
} }
@Native @Native
public static double exp(MessageContext ctx, double x) throws InterruptedException { public static double exp(Message ctx, double x) throws InterruptedException {
return java.lang.Math.exp(x); return java.lang.Math.exp(x);
} }
@Native @Native
public static double expm1(MessageContext ctx, double x) throws InterruptedException { public static double expm1(Message ctx, double x) throws InterruptedException {
return java.lang.Math.expm1(x); return java.lang.Math.expm1(x);
} }
@Native @Native
public static double pow(MessageContext ctx, double x, double y) throws InterruptedException { public static double pow(Message ctx, double x, double y) throws InterruptedException {
return java.lang.Math.pow(x, y); return java.lang.Math.pow(x, y);
} }
@Native @Native
public static double log(MessageContext ctx, double x) throws InterruptedException { public static double log(Message ctx, double x) throws InterruptedException {
return java.lang.Math.log(x); return java.lang.Math.log(x);
} }
@Native @Native
public static double log10(MessageContext ctx, double x) throws InterruptedException { public static double log10(Message ctx, double x) throws InterruptedException {
return java.lang.Math.log10(x); return java.lang.Math.log10(x);
} }
@Native @Native
public static double log1p(MessageContext ctx, double x) throws InterruptedException { public static double log1p(Message ctx, double x) throws InterruptedException {
return java.lang.Math.log1p(x); return java.lang.Math.log1p(x);
} }
@Native @Native
public static double log2(MessageContext ctx, double x) throws InterruptedException { public static double log2(Message ctx, double x) throws InterruptedException {
return java.lang.Math.log(x) / LN2; return java.lang.Math.log(x) / LN2;
} }
@Native @Native
public static double ceil(MessageContext ctx, double x) throws InterruptedException { public static double ceil(Message ctx, double x) throws InterruptedException {
return java.lang.Math.ceil(x); return java.lang.Math.ceil(x);
} }
@Native @Native
public static double floor(MessageContext ctx, double x) throws InterruptedException { public static double floor(Message ctx, double x) throws InterruptedException {
return java.lang.Math.floor(x); return java.lang.Math.floor(x);
} }
@Native @Native
public static double round(MessageContext ctx, double x) throws InterruptedException { public static double round(Message ctx, double x) throws InterruptedException {
return java.lang.Math.round(x); return java.lang.Math.round(x);
} }
@Native @Native
public static float fround(MessageContext ctx, double x) throws InterruptedException { public static float fround(Message ctx, double x) throws InterruptedException {
return (float)x; return (float)x;
} }
@Native @Native
public static double trunc(MessageContext ctx, double x) throws InterruptedException { public static double trunc(Message ctx, double x) throws InterruptedException {
var _x = x; var _x = x;
return java.lang.Math.floor(java.lang.Math.abs(_x)) * java.lang.Math.signum(_x); return java.lang.Math.floor(java.lang.Math.abs(_x)) * java.lang.Math.signum(_x);
} }
@Native @Native
public static double abs(MessageContext ctx, double x) throws InterruptedException { public static double abs(Message ctx, double x) throws InterruptedException {
return java.lang.Math.abs(x); return java.lang.Math.abs(x);
} }
@Native @Native
public static double max(MessageContext ctx, double ...vals) throws InterruptedException { public static double max(Message ctx, double ...vals) throws InterruptedException {
var res = Double.NEGATIVE_INFINITY; var res = Double.NEGATIVE_INFINITY;
for (var el : vals) { for (var el : vals) {
@ -184,7 +184,7 @@ public class Math {
return res; return res;
} }
@Native @Native
public static double min(MessageContext ctx, double ...vals) throws InterruptedException { public static double min(Message ctx, double ...vals) throws InterruptedException {
var res = Double.POSITIVE_INFINITY; var res = Double.POSITIVE_INFINITY;
for (var el : vals) { for (var el : vals) {
@ -196,7 +196,7 @@ public class Math {
} }
@Native @Native
public static double sign(MessageContext ctx, double x) throws InterruptedException { public static double sign(Message ctx, double x) throws InterruptedException {
return java.lang.Math.signum(x); return java.lang.Math.signum(x);
} }
@ -205,7 +205,7 @@ public class Math {
return java.lang.Math.random(); return java.lang.Math.random();
} }
@Native @Native
public static int clz32(MessageContext ctx, double x) throws InterruptedException { public static int clz32(Message ctx, double x) throws InterruptedException {
return Integer.numberOfLeadingZeros((int)x); return Integer.numberOfLeadingZeros((int)x);
} }
} }

View File

@ -6,7 +6,7 @@ import java.util.Map;
import me.topchetoeu.jscript.engine.Context; import me.topchetoeu.jscript.engine.Context;
import me.topchetoeu.jscript.engine.Environment; import me.topchetoeu.jscript.engine.Environment;
import me.topchetoeu.jscript.engine.MessageContext; import me.topchetoeu.jscript.engine.Message;
import me.topchetoeu.jscript.engine.values.ArrayValue; import me.topchetoeu.jscript.engine.values.ArrayValue;
import me.topchetoeu.jscript.engine.values.FunctionValue; import me.topchetoeu.jscript.engine.values.FunctionValue;
import me.topchetoeu.jscript.engine.values.NativeFunction; import me.topchetoeu.jscript.engine.values.NativeFunction;
@ -297,9 +297,9 @@ public class PromisePolyfill {
} }
private void handle(Context ctx, FunctionValue fulfill, FunctionValue reject) { private void handle(Context ctx, FunctionValue fulfill, FunctionValue reject) {
if (state == STATE_FULFILLED) ctx.message.engine.pushMsg(true, new MessageContext(ctx.message.engine), fulfill, null, val); if (state == STATE_FULFILLED) ctx.message.engine.pushMsg(true, new Message(ctx.message.engine), fulfill, null, val);
else if (state == STATE_REJECTED) { else if (state == STATE_REJECTED) {
ctx.message.engine.pushMsg(true, new MessageContext(ctx.message.engine), reject, null, val); ctx.message.engine.pushMsg(true, new Message(ctx.message.engine), reject, null, val);
handled = true; handled = true;
} }
else handles.add(new Handle(ctx, fulfill, reject)); else handles.add(new Handle(ctx, fulfill, reject));

View File

@ -1,60 +0,0 @@
package me.topchetoeu.jscript.polyfills;
import java.util.HashMap;
import me.topchetoeu.jscript.engine.Context;
import me.topchetoeu.jscript.engine.values.FunctionValue;
import me.topchetoeu.jscript.interop.Native;
public class TimerPolyfills {
private HashMap<Integer, Thread> threads = new HashMap<>();
private int i = 0;
@Native public int setTimeout(Context ctx, FunctionValue func, int delay, Object ...args) {
var thread = new Thread(() -> {
var ms = (long)delay;
var ns = (int)((delay - ms) * 10000000);
try {
Thread.sleep(ms, ns);
}
catch (InterruptedException e) { return; }
ctx.message.engine.pushMsg(false, ctx.message, func, null, args);
});
thread.start();
threads.put(++i, thread);
return i;
}
@Native public int setInterval(Context ctx, FunctionValue func, int delay, Object ...args) {
var thread = new Thread(() -> {
var ms = (long)delay;
var ns = (int)((delay - ms) * 10000000);
while (true) {
try {
Thread.sleep(ms, ns);
}
catch (InterruptedException e) { return; }
ctx.message.engine.pushMsg(false, ctx.message, func, null, args);
}
});
thread.start();
threads.put(++i, thread);
return i;
}
@Native public void clearTimeout(Context ctx, int i) {
var thread = threads.remove(i);
if (thread != null) thread.interrupt();
}
@Native public void clearInterval(Context ctx, int i) {
clearTimeout(ctx, i);
}
}