Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
27 changes: 14 additions & 13 deletions src/resolver.ts
Original file line number Diff line number Diff line change
@@ -834,20 +834,21 @@ export class Resolver extends DiagnosticEmitter {
} else if (node.kind == NodeKind.FUNCTIONTYPE) { // foo<T>(bar: (baz: T) => i32))
let functionTypeNode = <FunctionTypeNode>node;
let parameterNodes = functionTypeNode.parameters;
if (parameterNodes && parameterNodes.length > 0) {
let signatureReference = type.signatureReference;
if (signatureReference) {
let parameterTypes = signatureReference.parameterTypes;
let thisType = signatureReference.thisType;
if (parameterTypes.length == parameterNodes.length && !thisType == !functionTypeNode.explicitThisType) {
for (let i = 0, k = parameterTypes.length; i < k; ++i) {
this.propagateInferredGenericTypes(parameterNodes[i].type, parameterTypes[i], ctxElement, ctxTypes, typeParameterNames);
}
this.propagateInferredGenericTypes(functionTypeNode.returnType, signatureReference.returnType, ctxElement, ctxTypes, typeParameterNames);
if (thisType) this.propagateInferredGenericTypes(functionTypeNode.explicitThisType!, thisType, ctxElement, ctxTypes, typeParameterNames);
return;
}
let signatureReference = type.signatureReference;
if (signatureReference) {
let parameterTypes = signatureReference.parameterTypes;
for (let i = 0, k = min(parameterTypes.length, parameterNodes.length) ; i < k; ++i) {
this.propagateInferredGenericTypes(parameterNodes[i].type, parameterTypes[i], ctxElement, ctxTypes, typeParameterNames);
}
if (signatureReference.returnType != Type.void) {
this.propagateInferredGenericTypes(functionTypeNode.returnType, signatureReference.returnType, ctxElement, ctxTypes, typeParameterNames);
}
let thisType = signatureReference.thisType;
let explicitThisType = functionTypeNode.explicitThisType;
if (thisType && explicitThisType) {
this.propagateInferredGenericTypes(explicitThisType, thisType, ctxElement, ctxTypes, typeParameterNames);
}
return;
}
}
}
96 changes: 70 additions & 26 deletions tests/compiler/infer-generic.debug.wat
Original file line number Diff line number Diff line change
@@ -29,9 +29,9 @@
(global $~lib/rt/tlsf/ROOT (mut i32) (i32.const 0))
(global $~lib/native/ASC_LOW_MEMORY_LIMIT i32 (i32.const 0))
(global $~lib/rt/__rtti_base i32 (i32.const 592))
(global $~lib/memory/__data_end i32 (i32.const 660))
(global $~lib/memory/__stack_pointer (mut i32) (i32.const 17044))
(global $~lib/memory/__heap_base i32 (i32.const 17044))
(global $~lib/memory/__data_end i32 (i32.const 668))
(global $~lib/memory/__stack_pointer (mut i32) (i32.const 17052))
(global $~lib/memory/__heap_base i32 (i32.const 17052))
(memory $0 1)
(data (i32.const 12) "<\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00 \00\00\00i\00n\00f\00e\00r\00-\00g\00e\00n\00e\00r\00i\00c\00.\00t\00s\00\00\00\00\00\00\00\00\00\00\00\00\00")
(data (i32.const 76) "\1c\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\0c\00\00\00\00\00\80?\00\00\00@\00\00@@")
@@ -45,14 +45,15 @@
(data (i32.const 444) ",\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00\14\00\00\00~\00l\00i\00b\00/\00r\00t\00.\00t\00s\00\00\00\00\00\00\00\00\00")
(data (i32.const 496) "\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00")
(data (i32.const 524) "<\00\00\00\00\00\00\00\00\00\00\00\01\00\00\00\1e\00\00\00~\00l\00i\00b\00/\00r\00t\00/\00t\00l\00s\00f\00.\00t\00s\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00")
(data (i32.const 592) "\08\00\00\00 \00\00\00\00\00\00\00 \00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\02\19\00\00\00\00\00\00\00\00\00\00\00\00\00\00 \00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00")
(data (i32.const 592) "\t\00\00\00 \00\00\00\00\00\00\00 \00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\02\19\00\00\00\00\00\00\00\00\00\00\00\00\00\00 \00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00\00")
(table $0 2 2 funcref)
(elem $0 (i32.const 1) $start:infer-generic~anonymous|0)
(export "test1" (func $infer-generic/test1))
(export "memory" (memory $0))
(export "test2" (func $export:infer-generic/test2))
(export "test3" (func $export:infer-generic/test3))
(export "test4" (func $export:infer-generic/test4))
(export "test5" (func $export:infer-generic/test5))
(export "inferAssert" (func $export:infer-generic/inferAssert))
(start $~start)
(func $infer-generic/inferCompatible<f64> (param $a f64) (param $b f64) (result i32)
@@ -2220,17 +2221,24 @@
local.get $arr
call $infer-generic/inferEncapsulatedClass<f32>
)
(func $infer-generic/inferEncapsulatedFunction<f32,f64> (param $fn i32) (result i32)
(func $infer-generic/inferEncapsulatedFunctionNull<f64> (param $fn i32) (result i32)
local.get $fn
)
(func $infer-generic/test3 (param $fn i32) (result i32)
local.get $fn
call $infer-generic/inferEncapsulatedFunctionNull<f64>
)
(func $infer-generic/inferEncapsulatedFunction<f32,f64> (param $fn i32) (result i32)
local.get $fn
)
(func $infer-generic/test4 (param $fn i32) (result i32)
local.get $fn
call $infer-generic/inferEncapsulatedFunction<f32,f64>
)
(func $infer-generic/inferEncapsulatedFunctionMixed<f32,f64> (param $fn i32) (result i32)
local.get $fn
)
(func $infer-generic/test4 (param $fn i32) (result i32)
(func $infer-generic/test5 (param $fn i32) (result i32)
local.get $fn
call $infer-generic/inferEncapsulatedFunctionMixed<f32,f64>
)
@@ -2242,7 +2250,7 @@
if (result i32)
i32.const 0
i32.const 32
i32.const 67
i32.const 75
i32.const 3
call $~lib/builtins/abort
unreachable
@@ -2303,6 +2311,17 @@
local.get $1
call $~lib/function/Function<%28bool%2Cf32%2Ci32%2C~lib/array/Array<f32>%29=>bool>#__visit
)
(func $~lib/function/Function<%28%29=>f64>#__visit (param $this i32) (param $cookie i32)
local.get $this
i32.load offset=4
local.get $cookie
call $~lib/rt/itcms/__visit
)
(func $~lib/function/Function<%28%29=>f64>~visit (param $0 i32) (param $1 i32)
local.get $0
local.get $1
call $~lib/function/Function<%28%29=>f64>#__visit
)
(func $~lib/function/Function<%28f32%29=>f64>#__visit (param $this i32) (param $cookie i32)
local.get $this
i32.load offset=4
@@ -2329,37 +2348,43 @@
block $invalid
block $~lib/function/Function<%28f32%2Ci32%29=>f64>
block $~lib/function/Function<%28f32%29=>f64>
block $infer-generic/Ref
block $~lib/function/Function<%28bool%2Cf32%2Ci32%2C~lib/array/Array<f32>%29=>bool>
block $~lib/array/Array<f32>
block $~lib/arraybuffer/ArrayBufferView
block $~lib/string/String
block $~lib/arraybuffer/ArrayBuffer
local.get $0
i32.const 8
i32.sub
i32.load
br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $~lib/arraybuffer/ArrayBufferView $~lib/array/Array<f32> $~lib/function/Function<%28bool%2Cf32%2Ci32%2C~lib/array/Array<f32>%29=>bool> $infer-generic/Ref $~lib/function/Function<%28f32%29=>f64> $~lib/function/Function<%28f32%2Ci32%29=>f64> $invalid
block $~lib/function/Function<%28%29=>f64>
block $infer-generic/Ref
block $~lib/function/Function<%28bool%2Cf32%2Ci32%2C~lib/array/Array<f32>%29=>bool>
block $~lib/array/Array<f32>
block $~lib/arraybuffer/ArrayBufferView
block $~lib/string/String
block $~lib/arraybuffer/ArrayBuffer
local.get $0
i32.const 8
i32.sub
i32.load
br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $~lib/arraybuffer/ArrayBufferView $~lib/array/Array<f32> $~lib/function/Function<%28bool%2Cf32%2Ci32%2C~lib/array/Array<f32>%29=>bool> $infer-generic/Ref $~lib/function/Function<%28%29=>f64> $~lib/function/Function<%28f32%29=>f64> $~lib/function/Function<%28f32%2Ci32%29=>f64> $invalid
end
return
end
return
end
local.get $0
local.get $1
call $~lib/arraybuffer/ArrayBufferView~visit
return
end
local.get $0
local.get $1
call $~lib/arraybuffer/ArrayBufferView~visit
call $~lib/array/Array<f32>~visit
return
end
local.get $0
local.get $1
call $~lib/array/Array<f32>~visit
call $~lib/function/Function<%28bool%2Cf32%2Ci32%2C~lib/array/Array<f32>%29=>bool>~visit
return
end
local.get $0
local.get $1
call $~lib/function/Function<%28bool%2Cf32%2Ci32%2C~lib/array/Array<f32>%29=>bool>~visit
return
end
local.get $0
local.get $1
call $~lib/function/Function<%28%29=>f64>~visit
return
end
local.get $0
@@ -2412,7 +2437,7 @@
if
i32.const 0
i32.const 32
i32.const 46
i32.const 54
i32.const 1
call $~lib/builtins/abort
unreachable
@@ -2440,7 +2465,7 @@
if
i32.const 0
i32.const 32
i32.const 62
i32.const 70
i32.const 1
call $~lib/builtins/abort
unreachable
@@ -2483,7 +2508,7 @@
if
i32.const 0
i32.const 32
i32.const 63
i32.const 71
i32.const 1
call $~lib/builtins/abort
unreachable
@@ -2581,6 +2606,25 @@
global.set $~lib/memory/__stack_pointer
local.get $1
)
(func $export:infer-generic/test5 (param $0 i32) (result i32)
(local $1 i32)
global.get $~lib/memory/__stack_pointer
i32.const 4
i32.sub
global.set $~lib/memory/__stack_pointer
call $~stack_check
global.get $~lib/memory/__stack_pointer
local.get $0
i32.store
local.get $0
call $infer-generic/test5
local.set $1
global.get $~lib/memory/__stack_pointer
i32.const 4
i32.add
global.set $~lib/memory/__stack_pointer
local.get $1
)
(func $export:infer-generic/inferAssert (param $0 i32)
global.get $~lib/memory/__stack_pointer
i32.const 4
27 changes: 14 additions & 13 deletions tests/compiler/infer-generic.release.wat
Original file line number Diff line number Diff line change
@@ -19,7 +19,7 @@
(global $~lib/rt/itcms/white (mut i32) (i32.const 0))
(global $~lib/rt/itcms/fromSpace (mut i32) (i32.const 0))
(global $~lib/rt/tlsf/ROOT (mut i32) (i32.const 0))
(global $~lib/memory/__stack_pointer (mut i32) (i32.const 18068))
(global $~lib/memory/__stack_pointer (mut i32) (i32.const 18076))
(memory $0 1)
(data (i32.const 1036) "<")
(data (i32.const 1048) "\01\00\00\00 \00\00\00i\00n\00f\00e\00r\00-\00g\00e\00n\00e\00r\00i\00c\00.\00t\00s")
@@ -39,7 +39,7 @@
(data (i32.const 1480) "\01\00\00\00\14\00\00\00~\00l\00i\00b\00/\00r\00t\00.\00t\00s")
(data (i32.const 1548) "<")
(data (i32.const 1560) "\01\00\00\00\1e\00\00\00~\00l\00i\00b\00/\00r\00t\00/\00t\00l\00s\00f\00.\00t\00s")
(data (i32.const 1616) "\08\00\00\00 \00\00\00\00\00\00\00 ")
(data (i32.const 1616) "\t\00\00\00 \00\00\00\00\00\00\00 ")
(data (i32.const 1644) "\02\19")
(data (i32.const 1660) " ")
(table $0 2 2 funcref)
@@ -49,6 +49,7 @@
(export "test2" (func $export:infer-generic/test2))
(export "test3" (func $export:infer-generic/test2))
(export "test4" (func $export:infer-generic/test2))
(export "test5" (func $export:infer-generic/test2))
(export "inferAssert" (func $export:infer-generic/inferAssert))
(start $~start)
(func $start:infer-generic~anonymous|0 (param $0 i32) (param $1 f32) (param $2 i32) (param $3 i32) (result i32)
@@ -778,7 +779,7 @@
local.set $0
loop $while-continue|0
local.get $0
i32.const 18068
i32.const 18076
i32.lt_u
if
local.get $0
@@ -878,7 +879,7 @@
unreachable
end
local.get $0
i32.const 18068
i32.const 18076
i32.lt_u
if
local.get $0
@@ -901,7 +902,7 @@
i32.const 4
i32.add
local.tee $0
i32.const 18068
i32.const 18076
i32.ge_u
if
global.get $~lib/rt/tlsf/ROOT
@@ -1266,7 +1267,7 @@
i32.const 8
i32.sub
i32.load
br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $folding-inner1 $folding-inner1 $folding-inner0 $infer-generic/Ref $folding-inner0 $folding-inner0 $invalid
br_table $~lib/arraybuffer/ArrayBuffer $~lib/string/String $folding-inner1 $folding-inner1 $folding-inner0 $infer-generic/Ref $folding-inner0 $folding-inner0 $folding-inner0 $invalid
end
return
end
@@ -1304,7 +1305,7 @@
global.set $~lib/memory/__stack_pointer
block $folding-inner0
global.get $~lib/memory/__stack_pointer
i32.const 1684
i32.const 1692
i32.lt_s
br_if $folding-inner0
global.get $~lib/memory/__stack_pointer
@@ -1359,7 +1360,7 @@
memory.size
i32.const 16
i32.shl
i32.const 18068
i32.const 18076
i32.sub
i32.const 1
i32.shr_u
@@ -1394,7 +1395,7 @@
i32.sub
global.set $~lib/memory/__stack_pointer
global.get $~lib/memory/__stack_pointer
i32.const 1684
i32.const 1692
i32.lt_s
br_if $folding-inner0
global.get $~lib/memory/__stack_pointer
@@ -1441,7 +1442,7 @@
i32.sub
global.set $~lib/memory/__stack_pointer
global.get $~lib/memory/__stack_pointer
i32.const 1684
i32.const 1692
i32.lt_s
if
i32.const 18096
@@ -1467,7 +1468,7 @@
i32.sub
global.set $~lib/memory/__stack_pointer
global.get $~lib/memory/__stack_pointer
i32.const 1684
i32.const 1692
i32.lt_s
if
i32.const 18096
@@ -1485,7 +1486,7 @@
if
i32.const 0
i32.const 1056
i32.const 67
i32.const 75
i32.const 3
call $~lib/builtins/abort
unreachable
@@ -1541,7 +1542,7 @@
if
i32.const 0
local.get $1
i32.const 18068
i32.const 18076
i32.lt_u
local.get $1
i32.load offset=8
12 changes: 10 additions & 2 deletions tests/compiler/infer-generic.ts
Original file line number Diff line number Diff line change
@@ -18,13 +18,21 @@ export function test2(arr: f32[]): f32[] {
return inferEncapsulatedClass(arr);
}

// () => R should infer R
function inferEncapsulatedFunctionNull<R>(fn: () => R): () => R {
return fn;
}
export function test3(fn: () => f64): () => f64 {
return inferEncapsulatedFunctionNull(fn);
}

// (a: T) => R should infer T,R

function inferEncapsulatedFunction<T, R>(fn: (a: T) => R): (a: T) => R {
return fn;
}

export function test3(fn: (a: f32) => f64): (a: f32) => f64 {
export function test4(fn: (a: f32) => f64): (a: f32) => f64 {
return inferEncapsulatedFunction(fn);
}

@@ -34,7 +42,7 @@ function inferEncapsulatedFunctionMixed<T, R>(fn: (a: T, b: i32) => R): (a: T, b
return fn;
}

export function test4(fn: (a: f32, b: i32) => f64): (a: f32, b: i32) => f64 {
export function test5(fn: (a: f32, b: i32) => f64): (a: f32, b: i32) => f64 {
return inferEncapsulatedFunctionMixed(fn);
}