Skip to content

Rotation shift builtins for small typed integers incorrectly implemented #1492

Closed
@MaxGraey

Description

@MaxGraey

It seems we have wrong polyfills of rotr / rotl for small integers like u16 / u8. Here how it compile now:

function rotL16(a: u16, b: u16): u16 {
  return rotl<u16>(a, b);
}

current result:

(func $rotL16 (param $0 i32) (param $1 i32) (result i32)
  local.get $0
  i32.const 65535
  i32.and
  local.get $1
  i32.rotl
  i32.const 65535
  i32.and
 )

what I expected:

(func $rotL16 (param $0 i32) (param $1 i32) (result i32)
  local.get $0
  local.get $1
  i32.const 15
  i32.and 
  i32.shl 
  local.get $0
  i32.const 0
  local.get $1
  i32.sub 
  i32.const 15
  i32.and 
  i32.shr_u
  i32.or  
  i32.const 65535
  i32.and
)

which equivalent to:

function rotl(a: u16, b: u16): u16 {
  return (a << (b & 15)) | (a >>> (-b & 15));
  // rotr<16>(x, y):
  //   return (x >>> (y & 15)) | (x << (-y & 15));
}

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions