Skip to content

Commit 0dab476

Browse files
authored
threads: add global.atomic.rmw.* instructions (#1563)
* threads: add `global.atomic.rmw.*` instructions This change adds support for the various `global.atomic.rmw.*` instructions that are now available as a part of the shared-everything-threads [proposal]. [proposal]: https://github.com/WebAssembly/shared-everything-threads * Fix operand validation; refactor validation helpers The `global.atomic.rmw.*` instructions have different validation constraints for different instructions. `xchg` maches `global.atomic.get|set` in that it accepts subtypes of `anyref`. But `cmpxchg` accepts subtypes of `eqref`. All the instructions accept `i32` and `i64`. To make this more clear (and avoid mistakes like the ones I made), I moved these "special" cases up a level to be more visible. This allowed removing some of the other helper functions.
1 parent c034aaf commit 0dab476

13 files changed

Lines changed: 1132 additions & 130 deletions

File tree

crates/wasm-encoder/src/core/code.rs

Lines changed: 91 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1020,6 +1020,34 @@ pub enum Instruction<'a> {
10201020
ordering: Ordering,
10211021
global_index: u32,
10221022
},
1023+
GlobalAtomicRmwAdd {
1024+
ordering: Ordering,
1025+
global_index: u32,
1026+
},
1027+
GlobalAtomicRmwSub {
1028+
ordering: Ordering,
1029+
global_index: u32,
1030+
},
1031+
GlobalAtomicRmwAnd {
1032+
ordering: Ordering,
1033+
global_index: u32,
1034+
},
1035+
GlobalAtomicRmwOr {
1036+
ordering: Ordering,
1037+
global_index: u32,
1038+
},
1039+
GlobalAtomicRmwXor {
1040+
ordering: Ordering,
1041+
global_index: u32,
1042+
},
1043+
GlobalAtomicRmwXchg {
1044+
ordering: Ordering,
1045+
global_index: u32,
1046+
},
1047+
GlobalAtomicRmwCmpxchg {
1048+
ordering: Ordering,
1049+
global_index: u32,
1050+
},
10231051
}
10241052

10251053
impl Encode for Instruction<'_> {
@@ -3183,6 +3211,69 @@ impl Encode for Instruction<'_> {
31833211
ordering.encode(sink);
31843212
global_index.encode(sink);
31853213
}
3214+
Instruction::GlobalAtomicRmwAdd {
3215+
ordering,
3216+
global_index,
3217+
} => {
3218+
sink.push(0xFE);
3219+
sink.push(0x51);
3220+
ordering.encode(sink);
3221+
global_index.encode(sink);
3222+
}
3223+
Instruction::GlobalAtomicRmwSub {
3224+
ordering,
3225+
global_index,
3226+
} => {
3227+
sink.push(0xFE);
3228+
sink.push(0x52);
3229+
ordering.encode(sink);
3230+
global_index.encode(sink);
3231+
}
3232+
Instruction::GlobalAtomicRmwAnd {
3233+
ordering,
3234+
global_index,
3235+
} => {
3236+
sink.push(0xFE);
3237+
sink.push(0x53);
3238+
ordering.encode(sink);
3239+
global_index.encode(sink);
3240+
}
3241+
Instruction::GlobalAtomicRmwOr {
3242+
ordering,
3243+
global_index,
3244+
} => {
3245+
sink.push(0xFE);
3246+
sink.push(0x54);
3247+
ordering.encode(sink);
3248+
global_index.encode(sink);
3249+
}
3250+
Instruction::GlobalAtomicRmwXor {
3251+
ordering,
3252+
global_index,
3253+
} => {
3254+
sink.push(0xFE);
3255+
sink.push(0x55);
3256+
ordering.encode(sink);
3257+
global_index.encode(sink);
3258+
}
3259+
Instruction::GlobalAtomicRmwXchg {
3260+
ordering,
3261+
global_index,
3262+
} => {
3263+
sink.push(0xFE);
3264+
sink.push(0x56);
3265+
ordering.encode(sink);
3266+
global_index.encode(sink);
3267+
}
3268+
Instruction::GlobalAtomicRmwCmpxchg {
3269+
ordering,
3270+
global_index,
3271+
} => {
3272+
sink.push(0xFE);
3273+
sink.push(0x57);
3274+
ordering.encode(sink);
3275+
global_index.encode(sink);
3276+
}
31863277
}
31873278
}
31883279
}

crates/wasmparser/src/binary_reader.rs

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1684,6 +1684,25 @@ impl<'a> BinaryReader<'a> {
16841684
// Decode shared-everything-threads proposal.
16851685
0x4f => visitor.visit_global_atomic_get(self.read_ordering()?, self.read_var_u32()?),
16861686
0x50 => visitor.visit_global_atomic_set(self.read_ordering()?, self.read_var_u32()?),
1687+
0x51 => {
1688+
visitor.visit_global_atomic_rmw_add(self.read_ordering()?, self.read_var_u32()?)
1689+
}
1690+
0x52 => {
1691+
visitor.visit_global_atomic_rmw_sub(self.read_ordering()?, self.read_var_u32()?)
1692+
}
1693+
0x53 => {
1694+
visitor.visit_global_atomic_rmw_and(self.read_ordering()?, self.read_var_u32()?)
1695+
}
1696+
0x54 => visitor.visit_global_atomic_rmw_or(self.read_ordering()?, self.read_var_u32()?),
1697+
0x55 => {
1698+
visitor.visit_global_atomic_rmw_xor(self.read_ordering()?, self.read_var_u32()?)
1699+
}
1700+
0x56 => {
1701+
visitor.visit_global_atomic_rmw_xchg(self.read_ordering()?, self.read_var_u32()?)
1702+
}
1703+
0x57 => {
1704+
visitor.visit_global_atomic_rmw_cmpxchg(self.read_ordering()?, self.read_var_u32()?)
1705+
}
16871706

16881707
_ => bail!(pos, "unknown 0xfe subopcode: 0x{code:x}"),
16891708
})

crates/wasmparser/src/lib.rs

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -498,6 +498,13 @@ macro_rules! for_each_operator {
498498
// https://github.com/WebAssembly/shared-everything-threads
499499
@shared_everything_threads GlobalAtomicGet { ordering: $crate::Ordering, global_index: u32 } => visit_global_atomic_get
500500
@shared_everything_threads GlobalAtomicSet { ordering: $crate::Ordering, global_index: u32 } => visit_global_atomic_set
501+
@shared_everything_threads GlobalAtomicRmwAdd { ordering: $crate::Ordering, global_index: u32 } => visit_global_atomic_rmw_add
502+
@shared_everything_threads GlobalAtomicRmwSub { ordering: $crate::Ordering, global_index: u32 } => visit_global_atomic_rmw_sub
503+
@shared_everything_threads GlobalAtomicRmwAnd { ordering: $crate::Ordering, global_index: u32 } => visit_global_atomic_rmw_and
504+
@shared_everything_threads GlobalAtomicRmwOr { ordering: $crate::Ordering, global_index: u32 } => visit_global_atomic_rmw_or
505+
@shared_everything_threads GlobalAtomicRmwXor { ordering: $crate::Ordering, global_index: u32 } => visit_global_atomic_rmw_xor
506+
@shared_everything_threads GlobalAtomicRmwXchg { ordering: $crate::Ordering, global_index: u32 } => visit_global_atomic_rmw_xchg
507+
@shared_everything_threads GlobalAtomicRmwCmpxchg { ordering: $crate::Ordering, global_index: u32 } => visit_global_atomic_rmw_cmpxchg
501508

502509
// 0xFD operators
503510
// 128-bit SIMD

0 commit comments

Comments
 (0)