Skip to content

Commit 9da3907

Browse files
authored
Reintroduce unchecked indexed access on views (AssemblyScript#756)
1 parent 227c626 commit 9da3907

File tree

5 files changed

+264
-154
lines changed

5 files changed

+264
-154
lines changed

std/assembly/typedarray.ts

Lines changed: 132 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -22,18 +22,28 @@ export class Int8Array extends ArrayBufferView {
2222
return this.byteLength;
2323
}
2424

25-
@operator("[]") // unchecked is built-in
25+
@operator("[]")
2626
private __get(index: i32): i8 {
2727
if (<u32>index >= <u32>this.dataLength) throw new RangeError(E_INDEXOUTOFRANGE);
2828
return load<i8>(this.dataStart + <usize>index);
2929
}
3030

31-
@operator("[]=") // unchecked is built-in
31+
@unsafe @operator("{}")
32+
private __uget(index: i32): i8 {
33+
return load<i8>(this.dataStart + <usize>index);
34+
}
35+
36+
@operator("[]=")
3237
private __set(index: i32, value: native<i8>): void {
3338
if (<u32>index >= <u32>this.dataLength) throw new RangeError(E_INDEXOUTOFRANGE);
3439
store<i8>(this.dataStart + <usize>index, value);
3540
}
3641

42+
@unsafe @operator("{}=")
43+
private __uset(index: i32, value: native<i8>): void {
44+
store<i8>(this.dataStart + <usize>index, value);
45+
}
46+
3747
includes(searchElement: i8, fromIndex: i32 = 0): bool {
3848
return INCLUDES<Int8Array, i8>(this, searchElement, fromIndex);
3949
}
@@ -120,18 +130,28 @@ export class Uint8Array extends ArrayBufferView {
120130
return this.byteLength;
121131
}
122132

123-
@operator("[]") // unchecked is built-in
133+
@operator("[]")
124134
private __get(index: i32): u8 {
125135
if (<u32>index >= <u32>this.dataLength) throw new RangeError(E_INDEXOUTOFRANGE);
126136
return load<u8>(this.dataStart + <usize>index);
127137
}
128138

129-
@operator("[]=") // unchecked is built-in
139+
@unsafe @operator("{}")
140+
private __uget(index: i32): u8 {
141+
return load<u8>(this.dataStart + <usize>index);
142+
}
143+
144+
@operator("[]=")
130145
private __set(index: i32, value: native<u8>): void {
131146
if (<u32>index >= <u32>this.dataLength) throw new RangeError(E_INDEXOUTOFRANGE);
132147
store<u8>(this.dataStart + <usize>index, value);
133148
}
134149

150+
@unsafe @operator("{}=")
151+
private __uset(index: i32, value: native<u8>): void {
152+
store<u8>(this.dataStart + <usize>index, value);
153+
}
154+
135155
includes(searchElement: u8, fromIndex: i32 = 0): bool {
136156
return INCLUDES<Uint8Array, u8>(this, searchElement, fromIndex);
137157
}
@@ -218,18 +238,28 @@ export class Uint8ClampedArray extends ArrayBufferView {
218238
return this.byteLength;
219239
}
220240

221-
@operator("[]") // unchecked is built-in
241+
@operator("[]")
222242
private __get(index: i32): u8 {
223243
if (<u32>index >= <u32>this.dataLength) throw new RangeError(E_INDEXOUTOFRANGE);
224244
return load<u8>(this.dataStart + <usize>index);
225245
}
226246

227-
@operator("[]=") // unchecked is built-in
247+
@unsafe @operator("{}")
248+
private __uget(index: i32): u8 {
249+
return load<u8>(this.dataStart + <usize>index);
250+
}
251+
252+
@operator("[]=")
228253
private __set(index: i32, value: native<u8>): void {
229254
if (<u32>index >= <u32>this.dataLength) throw new RangeError(E_INDEXOUTOFRANGE);
230255
store<u8>(this.dataStart + <usize>index, ~(<i32>value >> 31) & (((255 - value) >> 31) | value));
231256
}
232257

258+
@unsafe @operator("{}=")
259+
private __uset(index: i32, value: native<u8>): void {
260+
store<u8>(this.dataStart + <usize>index, ~(<i32>value >> 31) & (((255 - value) >> 31) | value));
261+
}
262+
233263
includes(searchElement: u8, fromIndex: i32 = 0): bool {
234264
return INCLUDES<Uint8ClampedArray, u8>(this, searchElement, fromIndex);
235265
}
@@ -316,18 +346,28 @@ export class Int16Array extends ArrayBufferView {
316346
return this.byteLength >>> alignof<i16>();
317347
}
318348

319-
@operator("[]") // unchecked is built-in
349+
@operator("[]")
320350
private __get(index: i32): i16 {
321351
if (<u32>index >= <u32>this.dataLength >>> alignof<i16>()) throw new RangeError(E_INDEXOUTOFRANGE);
322352
return load<i16>(this.dataStart + (<usize>index << alignof<i16>()));
323353
}
324354

325-
@operator("[]=") // unchecked is built-in
355+
@unsafe @operator("{}")
356+
private __uget(index: i32): i16 {
357+
return load<i16>(this.dataStart + (<usize>index << alignof<i16>()));
358+
}
359+
360+
@operator("[]=")
326361
private __set(index: i32, value: native<i16>): void {
327362
if (<u32>index >= <u32>this.dataLength >>> alignof<i16>()) throw new RangeError(E_INDEXOUTOFRANGE);
328363
store<i16>(this.dataStart + (<usize>index << alignof<i16>()), value);
329364
}
330365

366+
@unsafe @operator("{}=")
367+
private __uset(index: i32, value: native<i16>): void {
368+
store<i16>(this.dataStart + (<usize>index << alignof<i16>()), value);
369+
}
370+
331371
includes(searchElement: i16, fromIndex: i32 = 0): bool {
332372
return INCLUDES<Int16Array, i16>(this, searchElement, fromIndex);
333373
}
@@ -414,18 +454,28 @@ export class Uint16Array extends ArrayBufferView {
414454
return this.byteLength >>> alignof<u16>();
415455
}
416456

417-
@operator("[]") // unchecked is built-in
457+
@operator("[]")
418458
private __get(index: i32): u16 {
419459
if (<u32>index >= <u32>this.dataLength >>> alignof<u16>()) throw new RangeError(E_INDEXOUTOFRANGE);
420460
return load<u16>(this.dataStart + (<usize>index << alignof<u16>()));
421461
}
422462

423-
@operator("[]=") // unchecked is built-in
463+
@unsafe @operator("{}")
464+
private __uget(index: i32): u16 {
465+
return load<u16>(this.dataStart + (<usize>index << alignof<u16>()));
466+
}
467+
468+
@operator("[]=")
424469
private __set(index: i32, value: native<u16>): void {
425470
if (<u32>index >= <u32>this.dataLength >>> alignof<u16>()) throw new RangeError(E_INDEXOUTOFRANGE);
426471
store<u16>(this.dataStart + (<usize>index << alignof<u16>()), value);
427472
}
428473

474+
@unsafe @operator("{}=")
475+
private __uset(index: i32, value: native<u16>): void {
476+
store<u16>(this.dataStart + (<usize>index << alignof<u16>()), value);
477+
}
478+
429479
includes(searchElement: u16, fromIndex: i32 = 0): bool {
430480
return INCLUDES<Uint16Array, u16>(this, searchElement, fromIndex);
431481
}
@@ -512,18 +562,28 @@ export class Int32Array extends ArrayBufferView {
512562
return this.byteLength >>> alignof<i32>();
513563
}
514564

515-
@operator("[]") // unchecked is built-in
565+
@operator("[]")
516566
private __get(index: i32): i32 {
517567
if (<u32>index >= <u32>this.dataLength >>> alignof<i32>()) throw new RangeError(E_INDEXOUTOFRANGE);
518568
return load<i32>(this.dataStart + (<usize>index << alignof<i32>()));
519569
}
520570

521-
@operator("[]=") // unchecked is built-in
571+
@unsafe @operator("{}")
572+
private __uget(index: i32): i32 {
573+
return load<i32>(this.dataStart + (<usize>index << alignof<i32>()));
574+
}
575+
576+
@operator("[]=")
522577
private __set(index: i32, value: i32): void {
523578
if (<u32>index >= <u32>this.dataLength >>> alignof<i32>()) throw new RangeError(E_INDEXOUTOFRANGE);
524579
store<i32>(this.dataStart + (<usize>index << alignof<i32>()), value);
525580
}
526581

582+
@unsafe @operator("{}=")
583+
private __uset(index: i32, value: i32): void {
584+
store<i32>(this.dataStart + (<usize>index << alignof<i32>()), value);
585+
}
586+
527587
includes(searchElement: i32, fromIndex: i32 = 0): bool {
528588
return INCLUDES<Int32Array, i32>(this, searchElement, fromIndex);
529589
}
@@ -610,18 +670,28 @@ export class Uint32Array extends ArrayBufferView {
610670
return this.byteLength >>> alignof<u32>();
611671
}
612672

613-
@operator("[]") // unchecked is built-in
673+
@operator("[]")
614674
private __get(index: i32): u32 {
615675
if (<u32>index >= <u32>this.dataLength >>> alignof<u32>()) throw new RangeError(E_INDEXOUTOFRANGE);
616676
return load<u32>(this.dataStart + (<usize>index << alignof<u32>()));
617677
}
618678

619-
@operator("[]=") // unchecked is built-in
679+
@unsafe @operator("{}")
680+
private __uget(index: i32): u32 {
681+
return load<u32>(this.dataStart + (<usize>index << alignof<u32>()));
682+
}
683+
684+
@operator("[]=")
620685
private __set(index: i32, value: u32): void {
621686
if (<u32>index >= <u32>this.dataLength >>> alignof<u32>()) throw new RangeError(E_INDEXOUTOFRANGE);
622687
store<u32>(this.dataStart + (<usize>index << alignof<u32>()), value);
623688
}
624689

690+
@unsafe @operator("{}=")
691+
private __uset(index: i32, value: u32): void {
692+
store<u32>(this.dataStart + (<usize>index << alignof<u32>()), value);
693+
}
694+
625695
includes(searchElement: u32, fromIndex: i32 = 0): bool {
626696
return INCLUDES<Uint32Array, u32>(this, searchElement, fromIndex);
627697
}
@@ -708,18 +778,28 @@ export class Int64Array extends ArrayBufferView {
708778
return this.byteLength >>> alignof<i64>();
709779
}
710780

711-
@operator("[]") // unchecked is built-in
781+
@operator("[]")
712782
private __get(index: i32): i64 {
713783
if (<u32>index >= <u32>this.dataLength >>> alignof<i64>()) throw new RangeError(E_INDEXOUTOFRANGE);
714784
return load<i64>(this.dataStart + (<usize>index << alignof<i64>()));
715785
}
716786

717-
@operator("[]=") // unchecked is built-in
787+
@unsafe @operator("{}")
788+
private __uget(index: i32): i64 {
789+
return load<i64>(this.dataStart + (<usize>index << alignof<i64>()));
790+
}
791+
792+
@operator("[]=")
718793
private __set(index: i32, value: i64): void {
719794
if (<u32>index >= <u32>this.dataLength >>> alignof<i64>()) throw new RangeError(E_INDEXOUTOFRANGE);
720795
store<i64>(this.dataStart + (<usize>index << alignof<i64>()), value);
721796
}
722797

798+
@unsafe @operator("{}=")
799+
private __uset(index: i32, value: i64): void {
800+
store<i64>(this.dataStart + (<usize>index << alignof<i64>()), value);
801+
}
802+
723803
includes(searchElement: i64, fromIndex: i32 = 0): bool {
724804
return INCLUDES<Int64Array, i64>(this, searchElement, fromIndex);
725805
}
@@ -806,18 +886,28 @@ export class Uint64Array extends ArrayBufferView {
806886
return this.byteLength >>> alignof<u64>();
807887
}
808888

809-
@operator("[]") // unchecked is built-in
889+
@operator("[]")
810890
private __get(index: i32): u64 {
811891
if (<u32>index >= <u32>this.dataLength >>> alignof<u64>()) throw new RangeError(E_INDEXOUTOFRANGE);
812892
return load<u64>(this.dataStart + (<usize>index << alignof<u64>()));
813893
}
814894

815-
@operator("[]=") // unchecked is built-in
895+
@unsafe @operator("{}")
896+
private __uget(index: i32): u64 {
897+
return load<u64>(this.dataStart + (<usize>index << alignof<u64>()));
898+
}
899+
900+
@operator("[]=")
816901
private __set(index: i32, value: u64): void {
817902
if (<u32>index >= <u32>this.dataLength >>> alignof<u64>()) throw new RangeError(E_INDEXOUTOFRANGE);
818903
store<u64>(this.dataStart + (<usize>index << alignof<u64>()), value);
819904
}
820905

906+
@unsafe @operator("{}=")
907+
private __uset(index: i32, value: u64): void {
908+
store<u64>(this.dataStart + (<usize>index << alignof<u64>()), value);
909+
}
910+
821911
includes(searchElement: u64, fromIndex: i32 = 0): bool {
822912
return INCLUDES<Uint64Array, u64>(this, searchElement, fromIndex);
823913
}
@@ -904,18 +994,28 @@ export class Float32Array extends ArrayBufferView {
904994
return this.byteLength >>> alignof<f32>();
905995
}
906996

907-
@operator("[]") // unchecked is built-in
997+
@operator("[]")
908998
private __get(index: i32): f32 {
909999
if (<u32>index >= <u32>this.dataLength >>> alignof<f32>()) throw new RangeError(E_INDEXOUTOFRANGE);
9101000
return load<f32>(this.dataStart + (<usize>index << alignof<f32>()));
9111001
}
9121002

913-
@operator("[]=") // unchecked is built-in
1003+
@unsafe @operator("{}")
1004+
private __uget(index: i32): f32 {
1005+
return load<f32>(this.dataStart + (<usize>index << alignof<f32>()));
1006+
}
1007+
1008+
@operator("[]=")
9141009
private __set(index: i32, value: f32): void {
9151010
if (<u32>index >= <u32>this.dataLength >>> alignof<f32>()) throw new RangeError(E_INDEXOUTOFRANGE);
9161011
store<f32>(this.dataStart + (<usize>index << alignof<f32>()), value);
9171012
}
9181013

1014+
@unsafe @operator("{}=")
1015+
private __uset(index: i32, value: f32): void {
1016+
store<f32>(this.dataStart + (<usize>index << alignof<f32>()), value);
1017+
}
1018+
9191019
includes(searchElement: f32, fromIndex: i32 = 0): bool {
9201020
return INCLUDES<Float32Array, f32>(this, searchElement, fromIndex);
9211021
}
@@ -1002,18 +1102,28 @@ export class Float64Array extends ArrayBufferView {
10021102
return this.byteLength >>> alignof<f64>();
10031103
}
10041104

1005-
@operator("[]") // unchecked is built-in
1105+
@operator("[]")
10061106
private __get(index: i32): f64 {
10071107
if (<u32>index >= <u32>this.dataLength >>> alignof<f64>()) throw new RangeError(E_INDEXOUTOFRANGE);
10081108
return load<f64>(this.dataStart + (<usize>index << alignof<f64>()));
10091109
}
10101110

1011-
@operator("[]=") // unchecked is built-in
1111+
@unsafe @operator("{}")
1112+
private __uget(index: i32): f64 {
1113+
return load<f64>(this.dataStart + (<usize>index << alignof<f64>()));
1114+
}
1115+
1116+
@operator("[]=")
10121117
private __set(index: i32, value: f64): void {
10131118
if (<u32>index >= <u32>this.dataLength >>> alignof<f64>()) throw new RangeError(E_INDEXOUTOFRANGE);
10141119
store<f64>(this.dataStart + (<usize>index << alignof<f64>()), value);
10151120
}
10161121

1122+
@unsafe @operator("{}=")
1123+
private __uset(index: i32, value: f64): void {
1124+
store<f64>(this.dataStart + (<usize>index << alignof<f64>()), value);
1125+
}
1126+
10171127
includes(searchElement: f64, fromIndex: i32 = 0): bool {
10181128
return INCLUDES<Float64Array, f64>(this, searchElement, fromIndex);
10191129
}

tests/compiler/std/dataview.optimized.wat

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1634,7 +1634,7 @@
16341634
if
16351635
i32.const 280
16361636
i32.const 376
1637-
i32.const 131
1637+
i32.const 146
16381638
i32.const 44
16391639
call $~lib/builtins/abort
16401640
unreachable

tests/compiler/std/dataview.untouched.wat

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3327,7 +3327,7 @@
33273327
if
33283328
i32.const 280
33293329
i32.const 376
3330-
i32.const 131
3330+
i32.const 146
33313331
i32.const 44
33323332
call $~lib/builtins/abort
33333333
unreachable

0 commit comments

Comments
 (0)