WebAssembly/표준

큰숲백과, 나무를 보지 말고 큰 숲을 보라.

현재의 웹어셈블리 표준안(2023년 12월 01일 기준 2.0 초안)은 여기 서 확인할 수 있다.

상기한 표준안은 Extended Backus–Naur Form(확장된 베커스-나우르 형식)으로 서술되어 있으며 이 문서에서는 해당 명세에 기반하여 한글로 풀어 설명하는 것을 목표로 한다.

값과 데이터 타입[편집 | 원본 편집]

값의 종류[편집 | 원본 편집]

  • 바이트(Byte)
  • 정수(Integer)
  • 부동소수점 실수(Floating-Point)
  • 벡터(Vector)
  • 이름(Name)

데이터 타입과 자료구조[편집 | 원본 편집]

  • 숫자 타입(Number)
  • 벡터 타입(Vector)
  • 참조 타입(Reference)
  • 값 타입(Value)
  • 결과 타입(Result)
  • 함수 타입(Function)
  • 리미트(Limit)
  • 메모리 타입(Memory)
  • 테이블 타입(Table)
  • 전역 타입(Global)
  • 외부 타입(External)

명령어 목록[편집 | 원본 편집]

웹어셈블리 명령어는 바이트 코드(Opcode라고도 한다)로 표기된다. ???은 미래에 쓰일 수 있는 Opcode이다.

WebAssembly의 Binary Code
분류 헥스 코드 설명
제어 0x00 unreachable: 예외 발생
제어 0x01 nop: 아무 것도 안함
제어 0x02 block: 조건문/반복문 이외에 인스턴스 등이 유효한 인라인 Scope(범위)를 지정한다.
제어 0x03 loop: 인라인 반복문을 지정한다.
제어 0x04 if: 인라인 조건문을 지정한다.
제어 0x05 else: 사용할 경우 if(0x04)와 붙어 나온다.
??? 0x06 ???
??? 0x07 ???
??? 0x08 ???
??? 0x09 ???
??? 0x0A ???
제어 0x0B end: 스코프를 닫는다(조건문, 반복문 포함). 그러므로 위에 설명한 명령어 0x02~0x05와 같이 쓰이는 경우가 많다.
제어 0x0C branch: 무조건 분기 명령어
제어 0x0D branch_if: 조건 분기[1].
제어 0x0E branch_table: 간접 분기 - 분기할 기준점이 되는 라벨(또는 테이블 인덱스)이 가리키는 지점과 그 오프셋(offset)이 따라붙으며, 만약에 분기한 위치가 프로그램의 메모리 범위를 벗어나면(out of bound) 기본 라벨로 분기한다(보통 이 상황은 원하던 상황이 아니므로 예외를 일으키는 프로시저가 기본 라벨이 된다.)
제어 0x0F return: 함수 및 프로시저 종료
제어 0x10 call: 함수/프로시저를 직접 호출한다.
제어 0x11 call_indirect: 함수/프로시저를 간접 호출한다. 함수 타입과 라벨이 되는 테이블 인덱스가 순서대로 뒤따른다.
??? 0x12 ???
??? 0x13 ???
??? 0x14 ???
??? 0x15 ???
??? 0x16 ???
??? 0x17 ???
??? 0x18 ???
??? 0x19 ???
파라미터 0x1A drop
파라미터 0x1B select
파라미터 0x1C value type을 정하는 select
??? 0x1D ???
??? 0x1E ???
??? 0x1F ???
변수 0x20 로컬 변수 get
변수 0x21 로컬 변수 set
변수 0x22 로컬 변수 tee(set + return)
변수 0x23 전역 변수 get
변수 0x24 전역 변수 set
테이블 0x25 table_get: 테이블 변수의 값을 가져온다
테이블 0x26 table_set: 테이블에 변수의 값을 저장한다.
??? 0x27 ???
메모리(Load) 0x28 32비트 정수 값을 메모리의 특정 영역에서 로드, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x29 64비트 정수 값을 메모리의 특정 영역에서 로드, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x2A IEEE 754 포맷을 따르는 32비트 부동 소수점 실수 값을 메모리의 특정 영역에서 로드, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x2B IEEE 754 포맷을 따르는 64비트 부동 소수점 실수 값을 메모리의 특정 영역에서 로드, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x2C 32비트 변수에 하위 8비트 부호 있는 정수 값을 메모리의 특정 영역에서 로드, 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x2D 32비트 변수에 하위 8비트 부호 없는 음 아닌 정수 값을 메모리의 특정 영역에서 로드, 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x2E 32비트 변수에 하위 16비트 부호 있는 정수 값을 메모리의 특정 영역에서 로드, 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x2F 32비트 변수에 하위 16비트 부호 없는 음 아닌 정수 값을 메모리의 특정 영역에서 로드, 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x30 64비트 변수에 하위 8비트 부호 있는 정수 값을 메모리의 특정 영역에서 로드, 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x31 64비트 변수에 하위 8비트 부호 없는 음 아닌 정수 값을 메모리의 특정 영역에서 로드, 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x32 64비트 변수에 하위 16비트 부호 있는 정수 값을 메모리의 특정 영역에서 로드, 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x33 64비트 변수에 하위 16비트 부호 없는 음 아닌 정수 값을 메모리의 특정 영역에서 로드, 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x34 64비트 변수에 하위 32비트 부호 있는 정수 값을 메모리의 특정 영역에서 로드, 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x35 64비트 변수에 하위 32비트 부호 없는 음 아닌 정수 값을 메모리의 특정 영역에서 로드, 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Load) 0x36 32비트 정수 값을 메모리의 특정 영역으로 저장, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Store) 0x37 64비트 정수 값을 메모리의 특정 영역에 저장, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Store) 0x38 IEEE 754 포맷을 따르는 32비트 부동 소수점 실수 값을 메모리의 특정 영역에 저장, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Store) 0x39 IEEE 754 포맷을 따르는 64비트 부동 소수점 실수 값을 메모리의 특정 영역에 저장, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Store) 0x3A 32비트 변수에 하위 8비트 정수 값을 메모리의 특정 영역에 저장, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Store) 0x3B 32비트 변수에 하위 16비트 정수 값을 메모리의 특정 영역에 저장, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Store) 0x3C 64비트 변수에 하위 8비트 정수 값을 메모리의 특정 영역에 저장, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Store) 0x3D 64비트 변수에 하위 16비트 정수 값을 메모리의 특정 영역에 저장, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Store) 0x3E 64비트 변수에 하위 32비트 정수 값을 메모리의 특정 영역에 저장, 부호는 상관 없으며 뒤에 인덱스로 부호 없는 0 이상의 32비트 정수[2] 가 붙는다.
메모리(Store) 0x3F 현재 웹어셈블리 모듈의 총 메모리 크기(TOTAL_MEMORY)를 반환한다. 뒤에 0x00 값이 붙어야 하는데, 추후 이 보조 명령어를 바꿔서 다른 메모리 연산 기능이 붙을지도 모른다.
제어 / 메모리(기타) 0x40 두 가지 역할이 있다.
  • 분기 제어 명령어 뒤에 보조 명령어로 붙으면 negative LEB128[3] 을 위해 존재하는 값이 되며, 타입 영역 인덱스와 충돌하지 않도록 설계된 값이다.
  • 뒤에 0x00이 붙어 명령어로 쓰이면, 웹 브라우저에게 웹어셈블리 모듈에 할당된 RAM 영역을 확장하라는 명령이 된다.
숫자 연산 0x41 32비트 정수 값을 상수로 선언하여 반환한다.
숫자 연산 0x42 64비트 정수 값을 상수로 선언하여 반환한다.
숫자 연산 0x43 IEEE 754 포맷의 32비트 부동 소수점 실수 값을 상수로 선언하여 반환한다.
숫자 연산 0x44 IEEE 754 포맷의 64비트 부동 소수점 실수 값을 상수로 선언하여 반환한다.
숫자 연산(비교 연산) 0x45 32비트 정수 값이 0인지 확인한다. 보통 사용하지 않는 포인터는 NULL(보통 0의 값임)로 하는 점을 고려하여 메모리 주소의 값이 유효한지 확인할 때 사용한다.
숫자 연산(비교 연산) 0x46 32비트 정수 두 개를 비교하여 같은지 확인한다.
숫자 연산(비교 연산) 0x47 32비트 정수 두 개를 비교하여 다른지 확인한다.
숫자 연산(비교 연산) 0x48 부호를 고려하여 이전에 위치한 명령어로 지정한 32비트 정수 2개에 대해 첫 번째가 두 번째보다 작은지 확인한다.
숫자 연산(비교 연산) 0x49 부호를 고려하지 않고 이전에 위치한 명령어로 지정한 32비트 정수 2개에 대해 첫 번째가 두 번째보다 작은지 확인한다.
숫자 연산(비교 연산) 0x4A 부호를 고려하여 이전에 위치한 명령어로 지정한 32비트 정수 2개에 대해 첫 번째가 두 번째보다 큰지 확인한다.
숫자 연산(비교 연산) 0x4B 부호를 고려하지 않고 이전에 위치한 명령어로 지정한 32비트 정수 2개에 대해 첫 번째가 두 번째보다 큰지 확인한다.
숫자 연산(비교 연산) 0x4C 부호를 고려하여 이전에 위치한 명령어로 지정한 32비트 정수 2개에 대해 첫 번째가 두 번째보다 작거나 같은지 확인한다.
숫자 연산(비교 연산) 0x4D 부호를 고려하지 않고 이전에 위치한 명령어로 지정한 32비트 정수 2개에 대해 첫 번째가 두 번째보다 작거나 같은지 확인한다.
숫자 연산(비교 연산) 0x4E 부호를 고려하여 이전에 위치한 명령어로 지정한 32비트 정수 2개에 대해 첫 번째가 두 번째보다 크거나 같은지 확인한다.
숫자 연산(비교 연산) 0x4F 부호를 고려하지 않고 이전에 위치한 명령어로 지정한 32비트 정수 2개에 대해 첫 번째가 두 번째보다 크거나 같은지 확인한다.
숫자 연산(비교 연산) 0x50 64비트 정수 값이 0인지 확인한다. 보통 사용하지 않는 포인터는 NULL(보통 0의 값임)로 하는 점을 고려하여 메모리 주소의 값이 유효한지 확인할 때 사용한다.
숫자 연산(비교 연산) 0x51 64비트 정수 두 개를 비교하여 같은지 확인한다.
숫자 연산(비교 연산) 0x52 64비트 정수 두 개를 비교하여 다른지 확인한다.
숫자 연산(비교 연산) 0x53 부호를 고려하여 이전에 위치한 명령어로 지정한 64비트 정수 2개에 대해 첫 번째가 두 번째보다 작은지 확인한다.
숫자 연산(비교 연산) 0x54 부호를 고려하지 않고 이전에 위치한 명령어로 지정한 64비트 정수 2개에 대해 첫 번째가 두 번째보다 작은지 확인한다.
숫자 연산(비교 연산) 0x55 부호를 고려하여 이전에 위치한 명령어로 지정한 64비트 정수 2개에 대해 첫 번째가 두 번째보다 큰지 확인한다.
숫자 연산(비교 연산) 0x56 부호를 고려하지 않고 이전에 위치한 명령어로 지정한 64비트 정수 2개에 대해 첫 번째가 두 번째보다 큰지 확인한다.
숫자 연산(비교 연산) 0x57 부호를 고려하여 이전에 위치한 명령어로 지정한 64비트 정수 2개에 대해 첫 번째가 두 번째보다 작거나 같은지 확인한다.
숫자 연산(비교 연산) 0x58 부호를 고려하지 않고 이전에 위치한 명령어로 지정한 64비트 정수 2개에 대해 첫 번째가 두 번째보다 작거나 같은지 확인한다.
숫자 연산(비교 연산) 0x59 부호를 고려하여 이전에 위치한 명령어로 지정한 64비트 정수 2개에 대해 첫 번째가 두 번째보다 크거나 같은지 확인한다.
숫자 연산(비교 연산) 0x5A 부호를 고려하지 않고 이전에 위치한 명령어로 지정한 64비트 정수 2개에 대해 첫 번째가 두 번째보다 크거나 같은지 확인한다.
숫자 연산(비교 연산) 0x5B IEEE 754 32비트 부동 소수점 실수 2개를 비교하여 같은지 확인한다.
숫자 연산(비교 연산) 0x5C IEEE 754 32비트 부동 소수점 실수 2개를 비교하여 다른지 확인한다.
숫자 연산(비교 연산) 0x5D IEEE 754 32비트 부동 소수점 실수 2개에 대해 첫 번째가 두 번째보다 작은지 확인한다.
숫자 연산(비교 연산) 0x5E IEEE 754 32비트 부동 소수점 실수 2개에 대해 첫 번째가 두 번째보다 큰지 확인한다.
숫자 연산(비교 연산) 0x5F IEEE 754 32비트 부동 소수점 실수 2개에 대해 첫 번째가 두 번째보다 작거나 같은지 확인한다.
숫자 연산(비교 연산) 0x60 IEEE 754 32비트 부동 소수점 실수 2개에 대해 첫 번째가 두 번째보다 크거나 같은지 확인한다.
숫자 연산(비교 연산) 0x61 IEEE 754 64비트 부동 소수점 실수 2개를 비교하여 같은지 확인한다.
숫자 연산(비교 연산) 0x62 IEEE 754 64비트 부동 소수점 실수 2개를 비교하여 다른지 확인한다.
숫자 연산(비교 연산) 0x63 IEEE 754 64비트 부동 소수점 실수 2개에 대해 첫 번째가 두 번째보다 작은지 확인한다.
숫자 연산(비교 연산) 0x64 IEEE 754 64비트 부동 소수점 실수 2개에 대해 첫 번째가 두 번째보다 큰지 확인한다.
숫자 연산(비교 연산) 0x65 IEEE 754 64비트 부동 소수점 실수 2개에 대해 첫 번째가 두 번째보다 작거나 같은지 확인한다.
숫자 연산(비교 연산) 0x66 IEEE 754 64비트 부동 소수점 실수 2개에 대해 첫 번째가 두 번째보다 크거나 같은지 확인한다.
숫자 연산(비트 연산) 0x67 32비트 정수 데이터의 앞(상위)부터 몇 개의 0이 붙었는지 반환한다.
숫자 연산(비트 연산) 0x68 32비트 정수 데이터의 뒤(하위)부터 몇 개의 0이 붙었는지 반환한다.
숫자 연산(비트 연산) 0x69 32비트 정수 데이터의 1의 갯수를 반환한다.
숫자 연산(사칙 연산) 0x6A 32비트 정수 데이터의 덧셈을 수행한다(오버플로 있음).
숫자 연산(사칙 연산) 0x6B 32비트 정수 데이터의 뺄셈을 수행한다(오버플로 있음).
숫자 연산(사칙 연산) 0x6C 32비트 정수 데이터의 곱셈을 수행한다(오버플로 가능).
숫자 연산(사칙 연산) 0x6D 부호를 고려하며 32비트 정수 데이터의 나눗셈을 수행하고, 몫을 반환하고 나머지는 버린다.
숫자 연산(사칙 연산) 0x6E 부호를 고려하지 않고 32비트 정수 데이터의 나눗셈을 수행하고, 몫을 반환하고 나머지는 버린다.
숫자 연산(사칙 연산) 0x6F 부호를 고려하며 32비트 정수 데이터의 나눗셈을 수행한 뒤 나머지를 반환한다.
숫자 연산(사칙 연산) 0x70 부호를 고려하지 않고 32비트 정수 데이터의 나눗셈을 수행한 뒤 나머지를 반환한다.
숫자 연산(비트 연산) 0x71 32비트 정수 데이터 2개에 대해 Bit 단위로 AND 불리언 연산을 한다.
숫자 연산(비트 연산) 0x72 32비트 정수 데이터 2개에 대해 Bit 단위로 OR 불리언 연산을 한다.
숫자 연산(비트 연산) 0x73 32비트 정수 데이터 2개에 대해 Bit 단위로 XOR 불리언 연산을 한다.
숫자 연산(비트 연산) 0x74 32비트 정수 데이터 1개에 대해 Bit 단위로 왼쪽 Shift 연산[4] 을 한다. 결과물의 최하위 비트는 0으로 채운다.
숫자 연산(비트 연산) 0x75 32비트 정수 데이터 1개에 대해 Bit 단위로 오른쪽 Shift 연산[4] 을 한다. 결과물의 최상위 비트는 이전 최상위 비트(Most Significant Bit, MSB)와 같게 채운다.
숫자 연산(비트 연산) 0x76 32비트 정수 데이터 1개에 대해 Bit 단위로 오른쪽 Shift 연산[4] 을 한다. 결과물의 최상위 비트는 무조건 0이다.
숫자 연산(비트 연산) 0x77 32비트 정수 데이터 1개에 대해 Bit 단위로 왼쪽 Rotate 연산[5] 을 한다.
숫자 연산(비트 연산) 0x78 32비트 정수 데이터 1개에 대해 Bit 단위로 오른쪽 Rotate 연산[5] 을 한다.
숫자 연산(비트 연산) 0x79 clz(count leading zero): 64비트 정수 데이터의 앞(상위)부터 몇 개의 0이 붙었는지 반환한다.
숫자 연산(비트 연산) 0x7A ctz(count trailing zero): 64비트 정수 데이터의 뒤(하위)부터 몇 개의 0이 붙었는지 반환한다.
숫자 연산(비트 연산) 0x7B popcnt: 64비트 정수 데이터의 1의 갯수를 반환한다.
숫자 연산(사칙 연산) 0x7C 64비트 정수 데이터의 덧셈을 수행한다(오버플로 있음).
숫자 연산(사칙 연산) 0x7D 64비트 정수 데이터의 뺄셈을 수행한다(오버플로 있음).
숫자 연산(사칙 연산) 0x7E 64비트 정수 데이터의 곱셈을 수행한다(오버플로 가능).
숫자 연산(사칙 연산) 0x7F 부호를 고려하며 64비트 정수 데이터의 나눗셈을 수행하고, 몫을 반환하고 나머지는 버린다.
숫자 연산(사칙 연산) 0x80 부호를 고려하지 않고 64비트 정수 데이터의 나눗셈을 수행하고, 몫을 반환하고 나머지는 버린다.
숫자 연산(사칙 연산) 0x81 부호를 고려하며 64비트 정수 데이터의 나눗셈을 수행한 뒤 나머지를 반환한다.
숫자 연산(사칙 연산) 0x82 부호를 고려하지 않고 64비트 정수 데이터의 나눗셈을 수행한 뒤 나머지를 반환한다.
숫자 연산(비트 연산) 0x83 64비트 정수 데이터 2개에 대해 Bit 단위로 AND 불리언 연산을 한다.
숫자 연산(비트 연산) 0x84 64비트 정수 데이터 2개에 대해 Bit 단위로 OR 불리언 연산을 한다.
숫자 연산(비트 연산) 0x85 64비트 정수 데이터 2개에 대해 Bit 단위로 XOR 불리언 연산을 한다.
숫자 연산(비트 연산) 0x86 64비트 정수 데이터 1개에 대해 Bit 단위로 왼쪽 Shift 연산[4] 을 한다. 결과물의 최하위 비트는 0으로 채운다.
숫자 연산(비트 연산) 0x87 64비트 정수 데이터 1개에 대해 Bit 단위로 오른쪽 Shift 연산[4] 을 한다. 결과물의 최상위 비트는 이전 최상위 비트(Most Significant Bit, MSB)와 같게 채운다.
숫자 연산(비트 연산) 0x88 64비트 정수 데이터 1개에 대해 Bit 단위로 오른쪽 Shift 연산[4] 을 한다. 결과물의 최상위 비트는 무조건 0이다.
숫자 연산(비트 연산) 0x89 64비트 정수 데이터 1개에 대해 Bit 단위로 왼쪽 Rotate 연산[5] 을 한다.
숫자 연산(비트 연산) 0x8A 64비트 정수 데이터 1개에 대해 Bit 단위로 오른쪽 Rotate 연산[5] 을 한다.
숫자 연산 0x8B IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 절대값을 구한다.
숫자 연산 0x8C IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 부호를 바꾼다.
숫자 연산 0x8D IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 소수점을 올림 처리한다. 즉 부호 상괍 없이 그보다 큰 최소한의 정수를 반환한다.
숫자 연산 0x8E IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 소수점을 내림 처리한다. 즉 부호 상괍 없이 그보다 작은 최대한의 정수를 반환한다.
숫자 연산 0x8F IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 소수점을 버림 처리한다. 즉 절대값이 주어진 숫자보다 작은 최대한의 정수를 반환한다(양수인 경우에는 내림, 음수인 경우에는 올림과 같음).
숫자 연산 0x90 IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 소수점을 반올림 처리한다. 단, 정확하게 중간(x.5)인 경우에는 짝수인 정수값을 반환하니 주의.
숫자 연산 0x91 IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 제곱근을 구한다.
숫자 연산 0x92 IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 덧셈을 수행한다.
숫자 연산 0x93 IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 뺄셈을 수행한다.
숫자 연산 0x94 IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 곱셈을 수행한다.
숫자 연산 0x95 IEEE 754 포맷에 따른 32비트 부동 소수점 실수의 나눗셈을 수행한다.
숫자 연산 0x96 IEEE 754 포맷에 따른 32비트 부동 소수점 실수 두 개 중 작은 값을 반환한다.
숫자 연산 0x97 IEEE 754 포맷에 따른 32비트 부동 소수점 실수 두 개 중 큰 값을 반환한다.
숫자 연산 0x98 IEEE 754 포맷에 따른 32비트 부동 소수점 실수 두 개에 대해 하나의 부호를 다른 하나로 복사한다.
숫자 연산 0x99 IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 절대값을 구한다.
숫자 연산 0x9A IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 부호를 바꾼다.
숫자 연산 0x9B IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 소수점을 올림 처리한다. 즉 부호 상괍 없이 그보다 큰 최소한의 정수를 반환한다.
숫자 연산 0x9C IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 소수점을 내림 처리한다. 즉 부호 상괍 없이 그보다 작은 최대한의 정수를 반환한다.
숫자 연산 0x9D IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 소수점을 버림 처리한다. 즉 절대값이 주어진 숫자보다 작은 최대한의 정수를 반환한다(양수인 경우에는 내림, 음수인 경우에는 올림과 같음).
숫자 연산 0x9E IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 소수점을 반올림 처리한다. 단, 정확하게 중간(x.5)인 경우에는 짝수인 정수값을 반환하니 주의.
숫자 연산 0x9F IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 제곱근을 구한다.
숫자 연산 0xA0 IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 덧셈을 수행한다.
숫자 연산 0xA1 IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 뺄셈을 수행한다.
숫자 연산 0xA2 IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 곱셈을 수행한다.
숫자 연산 0xA3 IEEE 754 포맷에 따른 64비트 부동 소수점 실수의 나눗셈을 수행한다.
숫자 연산 0xA4 IEEE 754 포맷에 따른 64비트 부동 소수점 실수 두 개 중 작은 값을 반환한다.
숫자 연산 0xA5 IEEE 754 포맷에 따른 64비트 부동 소수점 실수 두 개 중 큰 값을 반환한다.
숫자 연산 0xA6 IEEE 754 포맷에 따른 64비트 부동 소수점 실수 두 개에 대해 하나의 부호를 다른 하나로 복사한다.
숫자 연산(변환) 0xA7 wrap_i64: 64비트 정수를 32비트 정수로 깎는다
숫자 연산(변환) 0xA8 IEEE 754 32비트 부동 소수점 실수를 부호 있는 32비트 정수로 변환하며 소수점은 버린다.
숫자 연산(변환) 0xA9 IEEE 754 32비트 부동 소수점 실수를 부호 없는 32비트 정수로 변환하며 소수점은 버린다.
숫자 연산(변환) 0xAA IEEE 754 64비트 부동 소수점 실수를 부호 있는 32비트 정수로 변환하며 소수점은 버린다.
숫자 연산(변환) 0xAB IEEE 754 64비트 부동 소수점 실수를 부호 없는 32비트 정수로 변환하며 소수점은 버린다.
숫자 연산(변환) 0xAC wrap_i32_s: 32비트 정수를 64비트 정수로 부호를 고려하여 확장한다
숫자 연산(변환) 0xAD wrap_i32_u: 32비트 정수를 64비트 정수로 부호를 무시하고 확장한다
숫자 연산(변환) 0xAE IEEE 754 32비트 부동 소수점 실수를 부호 있는 64비트 정수로 변환하며 소수점은 버린다.
숫자 연산(변환) 0xAF IEEE 754 32비트 부동 소수점 실수를 부호 없는 64비트 정수로 변환하며 소수점은 버린다.
숫자 연산(변환) 0xB0 IEEE 754 64비트 부동 소수점 실수를 부호 있는 64비트 정수로 변환하며 소수점은 버린다.
숫자 연산(변환) 0xB1 IEEE 754 64비트 부동 소수점 실수를 부호 없는 64비트 정수로 변환하며 소수점은 버린다.
숫자 연산(변환) 0xB2 32비트 정수를 IEEE 754 32비트 부동 소수점 실수로 부호를 고려하여 변환한다.
숫자 연산(변환) 0xB3 32비트 정수를 IEEE 754 32비트 부동 소수점 실수로 부호를 무시하고 변환한다.
숫자 연산(변환) 0xB4 64비트 정수를 IEEE 754 32비트 부동 소수점 실수로 부호를 고려하여 변환한다.
숫자 연산(변환) 0xB5 64비트 정수를 IEEE 754 32비트 부동 소수점 실수로 부호를 무시하고 변환한다.
숫자 연산(변환) 0xB6 f32.demote: IEEE 754 포맷의 64비트 부동 소수점 실수를 동일 규격의 32비트 부동 소수점 실수로 바꾼다.
숫자 연산(변환) 0xB7 32비트 정수를 IEEE 754 64비트 부동 소수점 실수로 부호를 고려하여 변환한다.
숫자 연산(변환) 0xB8 32비트 정수를 IEEE 754 64비트 부동 소수점 실수로 부호를 무시하고 변환한다.
숫자 연산(변환) 0xB9 64비트 정수를 IEEE 754 64비트 부동 소수점 실수로 부호를 고려하여 변환한다.
숫자 연산(변환) 0xBA 64비트 정수를 IEEE 754 64비트 부동 소수점 실수로 부호를 무시하고 변환한다.
숫자 연산(변환) 0xBB f64.promote: IEEE 754 포맷의 32비트 부동 소수점 실수를 동일 규격의 64비트 부동 소수점 실수로 바꾼다.
숫자 연산(변환) 0xBC i32.reinterpret_f32: IEEE 754 포맷의 32비트 부동 소수점 실수의 비트값을 순서를 유지하며 변환 없이 32비트 정수로 취급한다. 즉 비트 순서를 유지하면서 부동 소수점 실수가 아닌 정수로 보므로 비트 값이 나타내는 수치가 달라진다.
숫자 연산(변환) 0xBD i64.reinterpret_f64: IEEE 754 포맷의 64비트 부동 소수점 실수의 비트 값을 순서를 유지하며 변환 없이 64비트 정수로 취급한다. 즉 비트 순서를 유지하면서 부동 소수점 실수가 아닌 정수로 보므로 비트 값이 나타내는 수치가 달라진다.
숫자 연산(변환) 0xBE f32.reinterpret_i32: 32비트 정수의 비트값을 순서를 유지하며 변환 없이 IEEE 754 포맷의 32비트 부동 소수점 실수로 취급한다. 즉 비트 순서를 유지하면서 정수가 아닌 부동 소수점 실수로 보므로 비트 값이 나타내는 수치가 달라진다.
숫자 연산(변환) 0xBF f64.reinterpret_i64: 64비트 정수의 비트 값을 순서를 유지하며 변환 없이 IEEE 754 포맷의 64비트 부동 소수점 실수로 취급한다. 즉 비트 순서를 유지하면서 정수가 아닌 부동 소수점 실수로 보므로 비트 값이 나타내는 수치가 달라진다.
숫자 연산(변환) 0xC0 8비트 정수 값을 부호를 유지하며 32비트 정수로 변환한다.
숫자 연산(변환) 0xC1 16비트 정수 값을 부호를 유지하며 32비트 정수로 변환한다.
숫자 연산(변환) 0xC2 8비트 정수 값을 부호를 유지하며 64비트 정수로 변환한다.
숫자 연산(변환) 0xC3 16비트 정수 값을 부호를 유지하며 64비트 정수로 변환한다.
숫자 연산(변환) 0xC4 32비트 정수 값을 부호를 유지하며 64비트 정수로 변환한다.
??? 0xC5 ???
??? 0xC6 ???
??? 0xC7 ???
??? 0xC8 ???
??? 0xC9 ???
??? 0xCA ???
??? 0xCB ???
??? 0xCC ???
??? 0xCD ???
??? 0xCE ???
??? 0xCF ???
참조 0xD0 메모리 참조 포인터를 Null로 설정
참조 0xD1 메모리 참조 포인터가 Null인지 확인
참조 0xD2 메모리 참조 포인터를 함수 포인터로 사용
??? 0xD3 ???
??? 0xD4 ???
??? 0xD5 ???
??? 0xD6 ???
??? 0xD7 ???
??? 0xD8 ???
??? 0xD9 ???
??? 0xDA ???
??? 0xDB ???
??? 0xDC ???
??? 0xDD ???
??? 0xDE ???
??? 0xDF ???
??? 0xE0 ???
??? 0xE1 ???
??? 0xE2 ???
??? 0xE3 ???
??? 0xE4 ???
??? 0xE5 ???
??? 0xE6 ???
??? 0xE7 ???
??? 0xE8 ???
??? 0xE9 ???
??? 0xEA ???
??? 0xEB ???
??? 0xEC ???
??? 0xED ???
??? 0xEE ???
??? 0xEF ???
??? 0xF0 ???
??? 0xF1 ???
??? 0xF2 ???
??? 0xF3 ???
??? 0xF4 ???
??? 0xF5 ???
??? 0xF6 ???
??? 0xF7 ???
??? 0xF8 ???
??? 0xF9 ???
??? 0xFA ???
??? 0xFB ???
숫자 연산(변환) / 테이블 관리 0xFC 이 명령어는 두 가지 역할을 한다.
  • IEEE 754 부동 소수점 실수를 정수 결과값의 비트 범위에 맞춰서 비트 수가 다른 데이터 간의 변환을 수행한다. 이 Opcode 뒤에 0~7까지 명령어 오프셋 역할을 하는 32비트 정수 데이터가 붙으며, 상세한 사항은 다음과 같다.
    • 0: 32비트 부동 소수점 실수에서 부호 있는 32비트 정수로 변환하며, 최대값 너머( 이상)은 으로, 최소값 아래( 미만)는 으로 한다.
    • 1: 32비트 부동 소수점 실수에서 부호 없는 32비트 정수로 변환하며, 최대값 너머(이상)은 으로, 최소값 아래(음수)는 0으로 한다.
    • 2: 64비트 부동 소수점 실수에서 부호 있는 32비트 정수로 변환하며, 최대값 너머( 이상)은 으로, 최소값 아래( 미만)는 으로 한다.
    • 3: 64비트 부동 소수점 실수에서 부호 없는 32비트 정수로 변환하며, 최대값 너머(이상)은 으로, 최소값 아래(음수)는 0으로 한다.
    • 4: 32비트 부동 소수점 실수에서 부호 있는 64비트 정수로 변환하며, 최대값 너머( 이상)은 으로, 최소값 아래( 미만)는 으로 한다.
    • 5: 32비트 부동 소수점 실수에서 부호 없는 64비트 정수로 변환하며, 최대값 너머(이상)은 으로, 최소값 아래(음수)는 0으로 한다.
    • 6: 64비트 부동 소수점 실수에서 부호 있는 64비트 정수로 변환하며, 최대값 너머( 이상)은 으로, 최소값 아래( 미만)는 으로 한다.
    • 7: 64비트 부동 소수점 실수에서 부호 없는 64비트 정수로 변환하며, 최대값 너머(이상)은 으로, 최소값 아래(음수)는 0으로 한다.
  • 또는 변수나 함수의 포인터 등이 저장되는 테이블 영역에 대한 동작을 수행한다. 이 Opcode 뒤에 12~17까지 명령어 오프셋 역할을 하는 32비트 정수 데이터가 붙는다.
벡터 연산 0xFD 128비트 폭의 SIMD 연산을 수행한다. 뒤에 십진수로 0~255 범위의 명령어 오프셋이 32비트 정수 데이터로 존재한다. 넣을 수 있는 데이터는 8비트에서 64비트까지 다양하지만 SIMD 연산답게 한 벡터 변수 내에 들어가는 데이터의 비트 길이는 전부 같아야 한다.
??? 0xFE ???
??? 0xFF ???

웹어셈블리 모듈[편집 | 원본 편집]

웹어셈블리로 컴파일된 애플리케이션은 자바스크립트가 로딩하는 모듈로 존재한다.

모듈 내의 모든 자료구조는 자기가 속한 영역에서 부호 없는 32비트 정수(U32) 인덱스로 가리킬 수 있다.

모듈 내의 모든 자료 구조 영역은 다음과 같다.

  • 타입 선언
  • 함수 선언
  • 테이블 선언: 메모리 위치를 표시하는 테이블이 위치한다.
  • 메모리 내 자료구조 선언(Memory Structure)
  • 전역 변수 선언(Global Variables)
  • 엘리먼트 세그먼트(Element Segment)
  • 데이터 세그먼트(Data Segment)
  • 시작 함수(Start function): 웹어셈블리 모듈의 진입점(Entry Point)이다.
  • 임포트(Import)
  • 익스포트(Export)

런타임 실행 과정[편집 | 원본 편집]

웹어셈블리 기반 웹앱에서 주의할 점[편집 | 원본 편집]

  • 웹어셈블리 모듈의 MIME 타입은 'application/wasm'이다.
  • Emscripten 3.x 기준 모듈의 동적 링킹을 할 때 메인 모듈과 사이드 모듈 구분이 존재한다. 이 구분은 하드웨어에 접근 가능한 API를 다루는 시스템 라이브러리의 사용 가능 여부에 따라 결정된다. 메인 모듈은 시스템 라이브러리를 사용할 수 있으나, 한 프로젝트에 1개만 존재할 수 있다. 모듈 분할이 필요할 경우 간단한 자료구조 정의 및 연산 위주로 사이드 모듈을 분할하고, 이벤트 처리나 하드웨어 기능 접근이 필요한 부분(예: WebGL 사용)은 메인 모듈에 남겨야 한다.
  • POSIX 규격 멀티스레딩(pthread)가 가능하나, 실험 단계에 있으며, 2018년 인텔 CPU 보안 취약점 대란의 영향으로 웹 프로그래밍의 멀티스레딩에 꼭 필요한 SharedArrayBuffer의 사용에 제약이 붙음에 따라 2020년대에도 실제 활용 사례가 많지 않다.
  1. CPU ISA에서 상태 플래그를 보고 조건에 따라 다음 명령어를 읽을지, 아니면 다른 곳으로 점프(jump)할 것인지 결정하는 명령어
  2. 2.00 2.01 2.02 2.03 2.04 2.05 2.06 2.07 2.08 2.09 2.10 2.11 2.12 2.13 2.14 2.15 2.16 2.17 2.18 2.19 2.20 2.21 2.22 이로 인해 현재는 웹 브라우저가 웹어셈블리의 한 모듈에 최대 4GB의 RAM만 할당할 수 있으며, 추후 버전에서 64비트 정수 인덱스가 도입될 여지가 있다
  3. 가변 길이 정수 데이터 포맷이다
  4. 4.0 4.1 4.2 4.3 4.4 4.5 각 비트를 한쪽으로 한 칸씩 밀며, 끝에 있는 비트는 일반적으로 사라진다. 시작점 뒤에 채우는 데이터는 상황에 따라 다르다
  5. 5.0 5.1 5.2 5.3 각 비트를 한쪽으로 한 칸씩 밀며, 끝에 있는 비트는 시작점으로 되돌아간다