porffor 0.41.5 → 0.41.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -31,14 +31,20 @@ export const __Porffor_object_underlying = (obj: any): any => {
31
31
  const key2: bytestring = 'constructor';
32
32
  __Porffor_object_expr_initWithFlags(proto, key2, obj, 0b1010);
33
33
  }
34
+
35
+ const key3: bytestring = 'name';
36
+ __Porffor_object_expr_initWithFlags(underlying, key3, __Porffor_funcLut_name(obj), 0b0010);
37
+
38
+ const key4: bytestring = 'length';
39
+ __Porffor_object_expr_initWithFlags(underlying, key4, __Porffor_funcLut_length(obj), 0b0010);
34
40
  }
35
41
 
36
42
  if (t == Porffor.TYPES.array) {
37
43
  const arr: any[] = obj;
38
44
  const len: i32 = arr.length;
39
45
 
40
- const key3: bytestring = 'length';
41
- __Porffor_object_expr_initWithFlags(underlying, key3, len, 0b1000);
46
+ const key5: bytestring = 'length';
47
+ __Porffor_object_expr_initWithFlags(underlying, key5, len, 0b1000);
42
48
 
43
49
  // todo: this should somehow be kept in sync?
44
50
  for (let i: i32 = 0; i < len; i++) {
@@ -50,8 +56,8 @@ export const __Porffor_object_underlying = (obj: any): any => {
50
56
  const str: string = obj;
51
57
  const len: i32 = str.length;
52
58
 
53
- const key4: bytestring = 'length';
54
- __Porffor_object_expr_initWithFlags(underlying, key4, len, 0b0000);
59
+ const key6: bytestring = 'length';
60
+ __Porffor_object_expr_initWithFlags(underlying, key6, len, 0b0000);
55
61
 
56
62
  for (let i: i32 = 0; i < len; i++) {
57
63
  __Porffor_object_expr_initWithFlags(underlying, __Number_prototype_toString(i), str[i], 0b0100);
@@ -64,8 +70,8 @@ export const __Porffor_object_underlying = (obj: any): any => {
64
70
  const str: bytestring = obj;
65
71
  const len: i32 = str.length;
66
72
 
67
- const key5: bytestring = 'length';
68
- __Porffor_object_expr_initWithFlags(underlying, key5, len, 0b0000);
73
+ const key7: bytestring = 'length';
74
+ __Porffor_object_expr_initWithFlags(underlying, key7, len, 0b0000);
69
75
 
70
76
  for (let i: i32 = 0; i < len; i++) {
71
77
  __Porffor_object_expr_initWithFlags(underlying, __Number_prototype_toString(i), str[i], 0b0100);
@@ -135,34 +135,30 @@ export const __Porffor_object_lookup = (obj: any, target: any): i32 => {
135
135
  const size: i32 = Porffor.wasm.i32.load(obj, 0, 0);
136
136
  const endPtr: i32 = ptr + size * 14;
137
137
 
138
- if (targetType == Porffor.TYPES.bytestring) {
139
- const targetStr: bytestring = target;
140
- for (; ptr < endPtr; ptr += 14) {
141
- const keyRaw: i32 = Porffor.wasm.i32.load(ptr, 0, 0);
142
- if (keyRaw == 0) break; // ran out of keys
143
- if (keyRaw >>> 31) continue; // MSB 1 set, not a bytestring
144
-
145
- const keyStr: bytestring = keyRaw;
146
- if (keyStr == targetStr) return ptr;
147
- }
148
- } else if (targetType == Porffor.TYPES.string) {
149
- const targetStr: string = target;
138
+ if (targetType == Porffor.TYPES.symbol) {
139
+ const targetSym: symbol = target;
150
140
  for (; ptr < endPtr; ptr += 14) {
151
141
  const keyRaw: i32 = Porffor.wasm.i32.load(ptr, 0, 0);
152
142
  if (keyRaw == 0) break; // ran out of keys
153
- if (keyRaw >>> 30 == 2) { // MSB 1 set and 2 unset, regular string type
154
- const keyStr: string = keyRaw & 0x7FFFFFFF; // unset MSB
155
- if (keyStr == targetStr) return ptr;
143
+ if (keyRaw >>> 30 == 3) { // MSB 1 and 2 set, symbol
144
+ const keySym: symbol = keyRaw & 0x3FFFFFFF; // unset MSB
145
+ if (keySym == targetSym) return ptr;
156
146
  }
157
147
  }
158
- } else { // symbol
159
- const targetSym: symbol = target;
148
+ } else {
160
149
  for (; ptr < endPtr; ptr += 14) {
161
150
  const keyRaw: i32 = Porffor.wasm.i32.load(ptr, 0, 0);
162
151
  if (keyRaw == 0) break; // ran out of keys
163
- if (keyRaw >>> 30 == 3) { // MSB 1 and 2 set, symbol
164
- const keySym: symbol = keyRaw & 0x3FFFFFFF; // unset MSB
165
- if (keySym == targetSym) return ptr;
152
+
153
+ const msb: i32 = keyRaw >>> 30;
154
+ if (msb == 0) {
155
+ // bytestring
156
+ const keyStr: bytestring = keyRaw;
157
+ if (Porffor.strcmp(keyStr, target)) return ptr;
158
+ } else if (msb == 2) {
159
+ // string
160
+ const keyStr: string = keyRaw & 0x7FFFFFFF; // unset MSB
161
+ if (Porffor.strcmp(keyStr, target)) return ptr;
166
162
  }
167
163
  }
168
164
  }
@@ -170,58 +166,96 @@ export const __Porffor_object_lookup = (obj: any, target: any): i32 => {
170
166
  return -1;
171
167
  };
172
168
 
173
- export const __Porffor_object_get = (obj: any, key: any): any => {
174
- const trueType: i32 = Porffor.wasm`local.get ${obj+1}`;
175
- if (trueType == Porffor.TYPES.function) {
176
- const tmp1: bytestring = 'name';
177
- if (key == tmp1) {
178
- const o: bytestring = __Porffor_funcLut_name(obj);
179
- const t: i32 = Porffor.TYPES.bytestring;
180
- Porffor.wasm`
181
- local.get ${o}
182
- f64.convert_i32_u
183
- local.get ${t}
184
- return`;
185
- }
186
-
187
- const tmp2: bytestring = 'length';
188
- if (key == tmp2) {
189
- const o: i32 = __Porffor_funcLut_length(obj);
190
- Porffor.wasm`
191
- local.get ${o}
192
- f64.convert_i32_u
193
- i32.const 1
169
+ export const __Porffor_object_readValue = (entryPtr: i32): any => {
170
+ Porffor.wasm`
171
+ local.get ${entryPtr}
172
+ f64.load 0 4
173
+ local.get ${entryPtr}
174
+ i32.load8_u 0 13
194
175
  return`;
195
- }
196
- }
176
+ };
197
177
 
178
+ export const __Porffor_object_get = (obj: any, key: any): any => {
179
+ const trueType: i32 = Porffor.wasm`local.get ${obj+1}`;
198
180
  if (trueType != Porffor.TYPES.object) obj = __Porffor_object_underlying(obj);
199
181
 
200
182
  if (Porffor.wasm`local.get ${obj}` == 0) throw new TypeError('Cannot get property of null');
201
183
 
202
184
  let entryPtr: i32 = __Porffor_object_lookup(obj, key);
203
185
  if (entryPtr == -1) {
204
- if (Porffor.wasm`local.get ${obj+1}` == Porffor.TYPES.object) {
205
- // check prototype chain
206
- const protoKey: bytestring = '__proto__';
207
- let lastProto: any = obj;
208
- if (key != protoKey) {
209
- while (true) {
210
- obj = __Porffor_object_get(obj, protoKey);
211
- if (Porffor.fastOr(obj == null, Porffor.wasm`local.get ${obj}` == Porffor.wasm`local.get ${lastProto}`)) break;
212
- lastProto = obj;
213
-
214
- if ((entryPtr = __Porffor_object_lookup(obj, key)) != -1) break;
186
+ // check prototype chain
187
+ const protoKey: bytestring = '__proto__';
188
+ let lastProto: any = obj;
189
+ if (key != protoKey) {
190
+ while (true) {
191
+ obj = __Porffor_object_get(obj, protoKey);
192
+
193
+ if (Porffor.comptime.flag`hasFunc.#get___String_prototype`) {
194
+ if (Porffor.fastOr(
195
+ trueType == Porffor.TYPES.string,
196
+ trueType == Porffor.TYPES.bytestring,
197
+ trueType == Porffor.TYPES.stringobject
198
+ )) {
199
+ obj = __String_prototype;
200
+ }
215
201
  }
216
- } else {
217
- let proto: i32 = __Object_prototype;
218
- if (trueType == Porffor.TYPES.function) proto = __Function_prototype;
219
- Porffor.wasm`
202
+
203
+ if (Porffor.comptime.flag`hasFunc.#get___Number_prototype`) {
204
+ if (Porffor.fastOr(
205
+ trueType == Porffor.TYPES.number,
206
+ trueType == Porffor.TYPES.numberobject
207
+ )) {
208
+ obj = __Number_prototype;
209
+ }
210
+ }
211
+
212
+ if (Porffor.comptime.flag`hasFunc.#get___Boolean_prototype`) {
213
+ if (Porffor.fastOr(
214
+ trueType == Porffor.TYPES.boolean,
215
+ trueType == Porffor.TYPES.booleanobject
216
+ )) {
217
+ obj = __Boolean_prototype;
218
+ }
219
+ }
220
+
221
+ if (Porffor.comptime.flag`hasFunc.#get___Function_prototype`) {
222
+ if (trueType == Porffor.TYPES.function) {
223
+ obj = __Function_prototype;
224
+ }
225
+ }
226
+
227
+ if (Porffor.comptime.flag`hasFunc.#get___Array_prototype`) {
228
+ if (trueType == Porffor.TYPES.array) {
229
+ obj = __Array_prototype;
230
+ }
231
+ }
232
+
233
+ if (Porffor.comptime.flag`hasFunc.#get___Date_prototype`) {
234
+ if (trueType == Porffor.TYPES.date) {
235
+ obj = __Date_prototype;
236
+ }
237
+ }
238
+
239
+ if (Porffor.comptime.flag`hasFunc.#get___Error_prototype`) {
240
+ if (trueType == Porffor.TYPES.error) {
241
+ obj = __Error_prototype;
242
+ }
243
+ }
244
+
245
+ if (Porffor.fastOr(obj == null, Porffor.wasm`local.get ${obj}` == Porffor.wasm`local.get ${lastProto}`)) break;
246
+ lastProto = obj;
247
+
248
+ if ((entryPtr = __Porffor_object_lookup(obj, key)) != -1) break;
249
+ }
250
+ } else {
251
+ let proto: i32 = __Object_prototype;
252
+ if (trueType == Porffor.TYPES.function) proto = __Function_prototype;
253
+
254
+ Porffor.wasm`
220
255
  local.get ${proto}
221
256
  f64.convert_i32_u
222
257
  i32.const 7 ;; object type
223
258
  return`;
224
- }
225
259
  }
226
260
 
227
261
  if (entryPtr == -1) {
@@ -535,20 +569,6 @@ local.set ${err}`;
535
569
  export const __Porffor_object_delete = (obj: any, key: any): boolean => {
536
570
  if (Porffor.wasm`local.get ${obj}` == 0) throw new TypeError('Cannot delete property of null');
537
571
 
538
- if (Porffor.wasm`local.get ${obj+1}` == Porffor.TYPES.function) {
539
- const tmp1: bytestring = 'name';
540
- if (key == tmp1) {
541
- __Porffor_funcLut_deleteName(obj);
542
- return true;
543
- }
544
-
545
- const tmp2: bytestring = 'length';
546
- if (key == tmp2) {
547
- __Porffor_funcLut_deleteLength(obj);
548
- return true;
549
- }
550
- }
551
-
552
572
  if (Porffor.wasm`local.get ${obj+1}` != Porffor.TYPES.object) obj = __Porffor_object_underlying(obj);
553
573
  if (Porffor.rawType(obj) != Porffor.TYPES.object) {
554
574
  // todo: support non-pure objects
@@ -600,20 +620,6 @@ memory.copy 0 0`;
600
620
  export const __Porffor_object_deleteStrict = (obj: any, key: any): boolean => {
601
621
  if (Porffor.wasm`local.get ${obj}` == 0) throw new TypeError('Cannot delete property of null');
602
622
 
603
- if (Porffor.wasm`local.get ${obj+1}` == Porffor.TYPES.function) {
604
- const tmp1: bytestring = 'name';
605
- if (key == tmp1) {
606
- __Porffor_funcLut_deleteName(obj);
607
- return true;
608
- }
609
-
610
- const tmp2: bytestring = 'length';
611
- if (key == tmp2) {
612
- __Porffor_funcLut_deleteLength(obj);
613
- return true;
614
- }
615
- }
616
-
617
623
  if (Porffor.wasm`local.get ${obj+1}` != Porffor.TYPES.object) obj = __Porffor_object_underlying(obj);
618
624
  if (Porffor.rawType(obj) != Porffor.TYPES.object) {
619
625
  // todo: support non-pure objects
@@ -150,16 +150,6 @@ export const __Object_prototype_hasOwnProperty = (_this: any, prop: any) => {
150
150
  return Porffor.object.lookup(_this, p) != -1;
151
151
  }
152
152
 
153
- if (t == Porffor.TYPES.function) {
154
- const tmp1: bytestring = 'name';
155
- if (p == tmp1) return !__Porffor_funcLut_isNameDeleted(_this);
156
-
157
- const tmp2: bytestring = 'length';
158
- if (p == tmp2) return !__Porffor_funcLut_isLengthDeleted(_this);
159
-
160
- return Porffor.object.lookup(_this, p) != -1;
161
- }
162
-
163
153
  const obj: any = __Porffor_object_underlying(_this);
164
154
  if (Porffor.rawType(obj) == Porffor.TYPES.object) {
165
155
  if (Porffor.object.lookup(obj, p) != -1) return true;
@@ -576,15 +566,27 @@ export const __Object_defineProperty = (target: any, prop: any, desc: any) => {
576
566
 
577
567
  const existingDesc: any = __Object_getOwnPropertyDescriptor(target, prop);
578
568
  if (existingDesc) {
579
- configurable ??= existingDesc.configurable;
580
- enumerable ??= existingDesc.enumerable;
569
+ let inKey: bytestring = '';
570
+
571
+ // probably slow due to excessive in's but needs to have them to be spec compliant handling explicit undefined vs non-existent
572
+ inKey = 'configurable';
573
+ if (configurable == null && !(inKey in desc)) configurable = existingDesc.configurable;
574
+
575
+ inKey = 'enumerable';
576
+ if (enumerable == null && !(inKey in desc)) enumerable = existingDesc.enumerable;
581
577
 
582
578
  if (accessor) {
583
- get ??= existingDesc.get;
584
- set ??= existingDesc.set;
579
+ inKey = 'get';
580
+ if (get == null && !(inKey in desc)) get = existingDesc.get;
581
+
582
+ inKey = 'set';
583
+ if (set == null && !(inKey in desc)) set = existingDesc.set;
585
584
  } else {
586
- value ??= existingDesc.value;
587
- writable ??= existingDesc.writable;
585
+ inKey = 'value';
586
+ if (value == null && !(inKey in desc)) value = existingDesc.value;
587
+
588
+ inKey = 'writable';
589
+ if (writable == null && !(inKey in desc)) writable = existingDesc.writable;
588
590
  }
589
591
  }
590
592
 
@@ -674,11 +676,19 @@ export const __Object_prototype_isPrototypeOf = (_this: any, obj: any) => {
674
676
 
675
677
  export const __Object_prototype_toString = (_this: any) => {
676
678
  if (Porffor.rawType(_this) == Porffor.TYPES.object) {
677
- // todo: breaks with Foo.prototype
679
+ // todo: breaks with Foo.prototype
678
680
  const obj: object = _this;
679
681
  if (obj != null) {
680
- const ovr: any = obj.toString;
681
- if (ovr != null && ovr !== __Object_prototype_toString) return ovr.call(_this);
682
+ let ovr: any = obj.toString;
683
+ if (Porffor.rawType(ovr) == Porffor.TYPES.function && ovr != __Object_prototype_toString) return ovr.call(_this);
684
+
685
+ const key: bytestring = 'toString';
686
+ const entryPtr: i32 = Porffor.object.lookup(obj, key);
687
+ if (entryPtr != -1) {
688
+ ovr = Porffor.object.readValue(entryPtr);
689
+ if (Porffor.rawType(ovr) == Porffor.TYPES.function) return ovr.call(_this);
690
+ else return undefined;
691
+ }
682
692
  }
683
693
  }
684
694
 
@@ -719,8 +729,16 @@ export const __Object_prototype_valueOf = (_this: any) => {
719
729
  // todo: breaks with Foo.prototype
720
730
  const obj: object = _this;
721
731
  if (obj != null) {
722
- const ovr: any = obj.valueOf;
723
- if (ovr != null && ovr !== __Object_prototype_valueOf) return ovr.call(_this);
732
+ let ovr: any = obj.valueOf;
733
+ if (Porffor.rawType(ovr) == Porffor.TYPES.function && ovr != __Object_prototype_valueOf) return ovr.call(_this);
734
+
735
+ const key: bytestring = 'valueOf';
736
+ const entryPtr: i32 = Porffor.object.lookup(obj, key);
737
+ if (entryPtr != -1) {
738
+ ovr = Porffor.object.readValue(entryPtr);
739
+ if (Porffor.rawType(ovr) == Porffor.TYPES.function) return ovr.call(_this);
740
+ else return undefined;
741
+ }
724
742
  }
725
743
  }
726
744
 
@@ -100,7 +100,7 @@ export const BuiltinVars = function(ctx) {
100
100
  this.Infinity.floatOnly = true;
101
101
 
102
102
  for (const x in TYPES) {
103
- this['__Porffor_TYPES_' + x] = number(TYPES[x]);
103
+ this['__Porffor_TYPES_' + x] = () => number(TYPES[x]);
104
104
  }
105
105
 
106
106
  this.__performance_timeOrigin = [
@@ -1048,65 +1048,5 @@ export const BuiltinFuncs = function() {
1048
1048
  table: true
1049
1049
  };
1050
1050
 
1051
- this.__Porffor_funcLut_deleteLength = {
1052
- params: [ Valtype.i32 ],
1053
- returns: [],
1054
- wasm: (scope, { allocPage }) => [
1055
- [ Opcodes.local_get, 0 ],
1056
- ...number(64, Valtype.i32),
1057
- [ Opcodes.i32_mul ],
1058
- ...number(2, Valtype.i32),
1059
- [ Opcodes.i32_add ],
1060
- ...number(0, Valtype.i32),
1061
- [ Opcodes.i32_store16, 0, ...unsignedLEB128(allocPage(scope, 'func lut')) ],
1062
-
1063
- [ Opcodes.local_get, 0 ],
1064
- ...number(1, Valtype.i32),
1065
- [ Opcodes.i32_store8, 0, ...unsignedLEB128(allocPage(scope, 'func length deletion table')) ]
1066
- ],
1067
- table: true
1068
- };
1069
-
1070
- this.__Porffor_funcLut_deleteName = {
1071
- params: [ Valtype.i32 ],
1072
- returns: [],
1073
- wasm: (scope, { allocPage }) => [
1074
- [ Opcodes.local_get, 0 ],
1075
- ...number(64, Valtype.i32),
1076
- [ Opcodes.i32_mul ],
1077
- ...number(5, Valtype.i32),
1078
- [ Opcodes.i32_add ],
1079
- ...number(0, Valtype.i32),
1080
- [ Opcodes.i32_store, 0, ...unsignedLEB128(allocPage(scope, 'func lut')) ],
1081
-
1082
- [ Opcodes.local_get, 0 ],
1083
- ...number(1, Valtype.i32),
1084
- [ Opcodes.i32_store8, 0, ...unsignedLEB128(allocPage(scope, 'func name deletion table')) ],
1085
- ],
1086
- table: true
1087
- };
1088
-
1089
- this.__Porffor_funcLut_isLengthDeleted = {
1090
- params: [ Valtype.i32 ],
1091
- returns: [ Valtype.i32 ],
1092
- returnType: TYPES.boolean,
1093
- wasm: (scope, { allocPage }) => [
1094
- [ Opcodes.local_get, 0 ],
1095
- [ Opcodes.i32_load8_u, 0, ...unsignedLEB128(allocPage(scope, 'func length deletion table')) ]
1096
- ],
1097
- table: true
1098
- };
1099
-
1100
- this.__Porffor_funcLut_isNameDeleted = {
1101
- params: [ Valtype.i32 ],
1102
- returns: [ Valtype.i32 ],
1103
- returnType: TYPES.boolean,
1104
- wasm: (scope, { allocPage }) => [
1105
- [ Opcodes.local_get, 0 ],
1106
- [ Opcodes.i32_load8_u, 0, ...unsignedLEB128(allocPage(scope, 'func name deletion table')) ]
1107
- ],
1108
- table: true
1109
- };
1110
-
1111
1051
  PrecompiledBuiltins.BuiltinFuncs.call(this);
1112
1052
  };
@@ -199,7 +199,16 @@ export default function({ builtinFuncs }, Prefs) {
199
199
  const props = autoFuncs(x);
200
200
 
201
201
  // special case: Object.prototype.__proto__ = null
202
- if (x === '__Object_prototype') Object.defineProperty(props, '__proto__', { value: { value: null }, enumerable: true });
202
+ if (x === '__Object_prototype') {
203
+ Object.defineProperty(props, '__proto__', { value: { value: null, configurable: true }, enumerable: true });
204
+ }
205
+
206
+ // special case: Function.prototype.length = 0
207
+ // special case: Function.prototype.name = ''
208
+ if (x === '__Function_prototype') {
209
+ props.length = { value: 0, configurable: true };
210
+ props.name = { value: '', configurable: true };
211
+ }
203
212
 
204
213
  // add constructor for constructors
205
214
  const name = x.slice(2, x.indexOf('_', 2));