@@ -163,6 +163,7 @@ export namespace BuiltinNames {
163163 export const trunc = "~lib/builtins/trunc" ;
164164 export const eq = "~lib/builtins/eq" ;
165165 export const ne = "~lib/builtins/ne" ;
166+ export const rem = "~lib/builtins/rem" ;
166167 export const load = "~lib/builtins/load" ;
167168 export const store = "~lib/builtins/store" ;
168169 export const atomic_load = "~lib/builtins/atomic.load" ;
@@ -269,6 +270,9 @@ export namespace BuiltinNames {
269270 export const f32_ne = "~lib/builtins/f32.ne" ;
270271 export const f64_ne = "~lib/builtins/f64.ne" ;
271272
273+ export const i32_rem = "~lib/builtins/i32.rem" ;
274+ export const i64_rem = "~lib/builtins/i64.rem" ;
275+
272276 export const i32_load8_s = "~lib/builtins/i32.load8_s" ;
273277 export const i32_load8_u = "~lib/builtins/i32.load8_u" ;
274278 export const i32_load16_s = "~lib/builtins/i32.load16_s" ;
@@ -815,7 +819,7 @@ function builtin_isString(ctx: BuiltinContext): ExpressionRef {
815819 compiler . currentType = Type . bool ;
816820 if ( ! type ) return module . unreachable ( ) ;
817821 var classReference = type . getClass ( ) ;
818- return reifyConstantType ( ctx ,
822+ return reifyConstantType ( ctx ,
819823 module . i32 (
820824 classReference && classReference . isAssignableTo ( compiler . program . stringInstance )
821825 ? 1
@@ -2231,6 +2235,60 @@ function builtin_store(ctx: BuiltinContext): ExpressionRef {
22312235}
22322236builtins . set ( BuiltinNames . store , builtin_store ) ;
22332237
2238+ // rem<T?>(left: T, right: T) -> T
2239+ function builtin_rem ( ctx : BuiltinContext ) : ExpressionRef {
2240+ var compiler = ctx . compiler ;
2241+ var module = compiler . module ;
2242+ if ( checkTypeOptional ( ctx , true ) | checkArgsRequired ( ctx , 2 ) ) {
2243+ return module . unreachable ( ) ;
2244+ }
2245+ var operands = ctx . operands ;
2246+ var typeArguments = ctx . typeArguments ;
2247+ var left = operands [ 0 ] ;
2248+ var arg0 = typeArguments
2249+ ? compiler . compileExpression (
2250+ left ,
2251+ typeArguments [ 0 ] ,
2252+ Constraints . CONV_IMPLICIT
2253+ )
2254+ : compiler . compileExpression ( operands [ 0 ] , Type . auto ) ;
2255+ var type = compiler . currentType ;
2256+ if ( type . isIntegerValue ) {
2257+ let arg1 : ExpressionRef ;
2258+ if ( ! typeArguments && left . isNumericLiteral ) {
2259+ // prefer right type
2260+ arg1 = compiler . compileExpression (
2261+ operands [ 1 ] ,
2262+ type
2263+ ) ;
2264+ if ( compiler . currentType != type ) {
2265+ arg0 = compiler . compileExpression (
2266+ left ,
2267+ ( type = compiler . currentType ) ,
2268+ Constraints . CONV_IMPLICIT
2269+ ) ;
2270+ }
2271+ } else {
2272+ arg1 = compiler . compileExpression (
2273+ operands [ 1 ] ,
2274+ type ,
2275+ Constraints . CONV_IMPLICIT
2276+ ) ;
2277+ }
2278+ if ( type . isIntegerValue ) {
2279+ return compiler . makeRem ( arg0 , arg1 , type , ctx . reportNode ) ;
2280+ }
2281+ }
2282+ compiler . error (
2283+ DiagnosticCode . Operation_0_cannot_be_applied_to_type_1 ,
2284+ ctx . reportNode . typeArgumentsRange ,
2285+ "rem" ,
2286+ type . toString ( )
2287+ ) ;
2288+ return module . unreachable ( ) ;
2289+ }
2290+ builtins . set ( BuiltinNames . rem , builtin_rem ) ;
2291+
22342292// add<T?>(left: T, right: T) -> T
22352293function builtin_add ( ctx : BuiltinContext ) : ExpressionRef {
22362294 var compiler = ctx . compiler ;
@@ -6638,6 +6696,24 @@ function builtin_f64_trunc(ctx: BuiltinContext): ExpressionRef {
66386696}
66396697builtins . set ( BuiltinNames . f64_trunc , builtin_f64_trunc ) ;
66406698
6699+ // i32.rem -> rem<i32>
6700+ function builtin_i32_rem ( ctx : BuiltinContext ) : ExpressionRef {
6701+ checkTypeAbsent ( ctx ) ;
6702+ ctx . typeArguments = [ Type . i32 ] ;
6703+ ctx . contextualType = Type . i32 ;
6704+ return builtin_rem ( ctx ) ;
6705+ }
6706+ builtins . set ( BuiltinNames . i32_rem , builtin_i32_rem ) ;
6707+
6708+ // i64.rem -> rem<i64>
6709+ function builtin_i64_rem ( ctx : BuiltinContext ) : ExpressionRef {
6710+ checkTypeAbsent ( ctx ) ;
6711+ ctx . typeArguments = [ Type . i64 ] ;
6712+ ctx . contextualType = Type . i64 ;
6713+ return builtin_rem ( ctx ) ;
6714+ }
6715+ builtins . set ( BuiltinNames . i64_rem , builtin_i64_rem ) ;
6716+
66416717// i32.add -> add<i32>
66426718function builtin_i32_add ( ctx : BuiltinContext ) : ExpressionRef {
66436719 checkTypeAbsent ( ctx ) ;
0 commit comments