зеркало из https://github.com/dotnet/fsharp.git
Improve implied lambda and delegate argument names (#15277)
* Improve implied lambda and delegate argument names * Fix * Add tests * Revert non-preview tests * Sigh * Re-revert * Fix test * Add testx
This commit is contained in:
Родитель
97c650fe28
Коммит
fd25719855
|
@ -8445,7 +8445,19 @@ and TcUnionCaseOrExnCaseOrActivePatternResultItemThen (cenv: cenv) overallTy env
|
|||
// This is where the constructor expects arguments but is not applied to arguments, hence build a lambda
|
||||
numArgTys,
|
||||
(fun () ->
|
||||
let vs, args = argTys |> List.mapi (fun i ty -> mkCompGenLocal mItem ("arg" + string i) ty) |> List.unzip
|
||||
let argNamesIfFeatureEnabled =
|
||||
if g.langVersion.SupportsFeature LanguageFeature.ImprovedImpliedArgumentNames then
|
||||
argNames
|
||||
else
|
||||
[]
|
||||
|
||||
let vs, args =
|
||||
argTys
|
||||
|> List.mapi (fun i ty ->
|
||||
let argName = argNamesIfFeatureEnabled |> List.tryItem i |> Option.map (fun x -> x.idText) |> Option.defaultWith (fun () -> "arg" + string i)
|
||||
mkCompGenLocal mItem argName ty)
|
||||
|> List.unzip
|
||||
|
||||
let constrApp = mkConstrApp mItem args
|
||||
let lam = mkMultiLambda mItem vs (constrApp, tyOfExpr g constrApp)
|
||||
lam)
|
||||
|
@ -9535,7 +9547,13 @@ and TcMethodApplication_CheckArguments
|
|||
let denv = env.DisplayEnv
|
||||
match curriedCallerArgsOpt with
|
||||
| None ->
|
||||
let curriedArgTys, returnTy =
|
||||
let curriedArgTys, curriedArgNamesIfFeatureEnabled, returnTy =
|
||||
let paramNamesIfFeatureEnabled (g: TcGlobals) (meth: MethInfo) =
|
||||
if g.langVersion.SupportsFeature LanguageFeature.ImprovedImpliedArgumentNames then
|
||||
meth.GetParamNames()
|
||||
else
|
||||
[]
|
||||
|
||||
match candidates with
|
||||
// "single named item" rule. This is where we have a single accessible method
|
||||
// member x.M(arg1, ..., argN)
|
||||
|
@ -9547,19 +9565,23 @@ and TcMethodApplication_CheckArguments
|
|||
// to their default values (for optionals) and be part of the return tuple (for out args).
|
||||
| [calledMeth] ->
|
||||
let curriedArgTys, returnTy = UnifyMatchingSimpleArgumentTypes cenv env exprTy.Commit calledMeth mMethExpr mItem
|
||||
curriedArgTys, MustEqual returnTy
|
||||
curriedArgTys, paramNamesIfFeatureEnabled g calledMeth, MustEqual returnTy
|
||||
| _ ->
|
||||
let domainTy, returnTy = UnifyFunctionType None cenv denv mMethExpr exprTy.Commit
|
||||
let argTys = if isUnitTy g domainTy then [] else tryDestRefTupleTy g domainTy
|
||||
// Only apply this rule if a candidate method exists with this number of arguments
|
||||
let argTys =
|
||||
if candidates |> List.exists (CalledMethHasSingleArgumentGroupOfThisLength argTys.Length) then
|
||||
argTys
|
||||
else
|
||||
[domainTy]
|
||||
[argTys], MustEqual returnTy
|
||||
let argTys, argNames =
|
||||
match candidates |> List.tryFind (CalledMethHasSingleArgumentGroupOfThisLength argTys.Length) with
|
||||
| Some meth -> argTys, paramNamesIfFeatureEnabled g meth
|
||||
| None -> [domainTy], [[None]]
|
||||
[argTys], argNames, MustEqual returnTy
|
||||
|
||||
let lambdaVarsAndExprs = curriedArgTys |> List.mapiSquared (fun i j ty -> mkCompGenLocal mMethExpr ("arg"+string i+string j) ty)
|
||||
let lambdaVarsAndExprs =
|
||||
curriedArgTys
|
||||
|> List.mapiSquared (fun i j ty ->
|
||||
let argName = curriedArgNamesIfFeatureEnabled |> List.tryItem i |> Option.bind (List.tryItem j) |> Option.flatten |> Option.defaultWith (fun () -> "arg" + string i + string j)
|
||||
mkCompGenLocal mMethExpr argName ty)
|
||||
|
||||
let unnamedCurriedCallerArgs = lambdaVarsAndExprs |> List.mapSquared (fun (_, e) -> CallerArg(tyOfExpr g e, e.Range, false, e))
|
||||
let namedCurriedCallerArgs = lambdaVarsAndExprs |> List.map (fun _ -> [])
|
||||
let lambdaVars = List.mapSquared fst lambdaVarsAndExprs
|
||||
|
|
|
@ -1266,8 +1266,23 @@ let BuildNewDelegateExpr (eventInfoOpt: EventInfo option, g, amap, delegateTy, d
|
|||
if List.exists (isByrefTy g) delArgTys then
|
||||
error(Error(FSComp.SR.tcFunctionRequiresExplicitLambda(delArgTys.Length), m))
|
||||
|
||||
let delFuncArgNamesIfFeatureEnabled =
|
||||
match delFuncExpr with
|
||||
| Expr.Val (valRef = vref) when g.langVersion.SupportsFeature LanguageFeature.ImprovedImpliedArgumentNames ->
|
||||
match vref.ValReprInfo with
|
||||
| Some repr when repr.ArgNames.Length = delArgTys.Length -> Some repr.ArgNames
|
||||
| _ -> None
|
||||
| _ -> None
|
||||
|
||||
let delArgVals =
|
||||
delArgTys |> List.mapi (fun i argTy -> fst (mkCompGenLocal m ("delegateArg" + string i) argTy))
|
||||
delArgTys
|
||||
|> List.mapi (fun i argTy ->
|
||||
let argName =
|
||||
match delFuncArgNamesIfFeatureEnabled with
|
||||
| Some argNames -> argNames[i]
|
||||
| None -> "delegateArg" + string i
|
||||
|
||||
fst (mkCompGenLocal m argName argTy))
|
||||
|
||||
let expr =
|
||||
let args =
|
||||
|
|
|
@ -1100,6 +1100,21 @@ type MethInfo =
|
|||
member x.GetFSharpReturnType(amap, m, minst) =
|
||||
x.GetCompiledReturnType(amap, m, minst) |> GetFSharpViewOfReturnType amap.g
|
||||
|
||||
member x.GetParamNames() =
|
||||
match x with
|
||||
| FSMeth (g, _, vref, _) ->
|
||||
ParamNameAndType.FromMember x.IsCSharpStyleExtensionMember g vref |> List.mapSquared (fun (ParamNameAndType (name, _)) -> name |> Option.map (fun x -> x.idText))
|
||||
| ILMeth (ilMethInfo = ilminfo) ->
|
||||
// A single group of tupled arguments
|
||||
[ ilminfo.ParamMetadata |> List.map (fun x -> x.Name) ]
|
||||
#if !NO_TYPEPROVIDERS
|
||||
| ProvidedMeth (_, mi, _, m) ->
|
||||
// A single group of tupled arguments
|
||||
[ [ for p in mi.PApplyArray((fun mi -> mi.GetParameters()), "GetParameters", m) do
|
||||
yield p.PUntaint((fun p -> Some p.Name), m) ] ]
|
||||
#endif
|
||||
| _ -> []
|
||||
|
||||
/// Get the parameter types of a method info
|
||||
member x.GetParamTypes(amap, m, minst) =
|
||||
match x with
|
||||
|
|
|
@ -517,6 +517,9 @@ type MethInfo =
|
|||
/// Get the ParamData objects for the parameters of a MethInfo
|
||||
member GetParamDatas: amap: ImportMap * m: range * minst: TType list -> ParamData list list
|
||||
|
||||
/// Get the parameter names of a MethInfo
|
||||
member GetParamNames: unit -> string option list list
|
||||
|
||||
/// Get the parameter types of a method info
|
||||
member GetParamTypes: amap: ImportMap * m: range * minst: TType list -> TType list list
|
||||
|
||||
|
|
|
@ -1573,6 +1573,7 @@ featureNonInlineLiteralsAsPrintfFormat,"String values marked as literals and IL
|
|||
featureNestedCopyAndUpdate,"Nested record field copy-and-update"
|
||||
featureExtendedStringInterpolation,"Extended string interpolation similar to C# raw string literals."
|
||||
featureWarningWhenMultipleRecdTypeChoice,"Raises warnings when multiple record type matches were found during name resolution because of overlapping field names."
|
||||
featureImprovedImpliedArgumentNames,"Improved implied argument names"
|
||||
3353,fsiInvalidDirective,"Invalid directive '#%s %s'"
|
||||
3354,tcNotAFunctionButIndexerNamedIndexingNotYetEnabled,"This value supports indexing, e.g. '%s.[index]'. The syntax '%s[index]' requires /langversion:preview. See https://aka.ms/fsharp-index-notation."
|
||||
3354,tcNotAFunctionButIndexerIndexingNotYetEnabled,"This expression supports indexing, e.g. 'expr.[index]'. The syntax 'expr[index]' requires /langversion:preview. See https://aka.ms/fsharp-index-notation."
|
||||
|
|
|
@ -68,6 +68,7 @@ type LanguageFeature =
|
|||
| NestedCopyAndUpdate
|
||||
| ExtendedStringInterpolation
|
||||
| WarningWhenMultipleRecdTypeChoice
|
||||
| ImprovedImpliedArgumentNames
|
||||
|
||||
/// LanguageVersion management
|
||||
type LanguageVersion(versionText) =
|
||||
|
@ -159,6 +160,7 @@ type LanguageVersion(versionText) =
|
|||
LanguageFeature.NestedCopyAndUpdate, previewVersion
|
||||
LanguageFeature.ExtendedStringInterpolation, previewVersion
|
||||
LanguageFeature.WarningWhenMultipleRecdTypeChoice, previewVersion
|
||||
LanguageFeature.ImprovedImpliedArgumentNames, previewVersion
|
||||
|
||||
]
|
||||
|
||||
|
@ -282,6 +284,7 @@ type LanguageVersion(versionText) =
|
|||
| LanguageFeature.NestedCopyAndUpdate -> FSComp.SR.featureNestedCopyAndUpdate ()
|
||||
| LanguageFeature.ExtendedStringInterpolation -> FSComp.SR.featureExtendedStringInterpolation ()
|
||||
| LanguageFeature.WarningWhenMultipleRecdTypeChoice -> FSComp.SR.featureWarningWhenMultipleRecdTypeChoice ()
|
||||
| LanguageFeature.ImprovedImpliedArgumentNames -> FSComp.SR.featureImprovedImpliedArgumentNames ()
|
||||
|
||||
/// Get a version string associated with the given feature.
|
||||
static member GetFeatureVersionString feature =
|
||||
|
|
|
@ -58,6 +58,7 @@ type LanguageFeature =
|
|||
| NestedCopyAndUpdate
|
||||
| ExtendedStringInterpolation
|
||||
| WarningWhenMultipleRecdTypeChoice
|
||||
| ImprovedImpliedArgumentNames
|
||||
|
||||
/// LanguageVersion management
|
||||
type LanguageVersion =
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">implicitní yield</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">Notace expr[idx] pro indexování a vytváření řezů</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">implizite yield-Anweisung</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">expr[idx]-Notation zum Indizieren und Aufteilen</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">elemento yield implícito</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">Notación para indexación y segmentación expr[idx]</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">yield implicite</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">Notation expr[idx] pour l’indexation et le découpage</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">istruzione yield implicita</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">Notazione expr[idx] per l'indicizzazione e il sezionamento</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">暗黙的な yield</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">インデックス作成とスライス用の expr[idx] 表記</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">암시적 yield</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">인덱싱 및 슬라이싱을 위한 expr[idx] 표기법</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">niejawne słowo kluczowe yield</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">notacja wyrażenia expr[idx] do indeksowania i fragmentowania</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">yield implícito</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">notação expr[idx] para indexação e fatia</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">неявное использование yield</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">expr[idx] для индексации и среза</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">örtük yield</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">Dizin oluşturma ve dilimleme için expr[idx] gösterimi</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">隐式 yield</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">用于索引和切片的 expr[idx] 表示法</target>
|
||||
|
|
|
@ -272,6 +272,11 @@
|
|||
<target state="translated">隱含 yield</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureImprovedImpliedArgumentNames">
|
||||
<source>Improved implied argument names</source>
|
||||
<target state="new">Improved implied argument names</target>
|
||||
<note />
|
||||
</trans-unit>
|
||||
<trans-unit id="featureIndexerNotationWithoutDot">
|
||||
<source>expr[idx] notation for indexing and slicing</source>
|
||||
<target state="translated">用於編製索引和分割的 expr[idx] 註釋</target>
|
||||
|
|
|
@ -0,0 +1,178 @@
|
|||
// Copyright (c) Microsoft Corporation. All Rights Reserved. See License.txt in the project root for license information.
|
||||
|
||||
namespace FSharp.Compiler.ComponentTests.EmittedIL
|
||||
|
||||
open Xunit
|
||||
open FSharp.Test.Compiler
|
||||
|
||||
module ArgumentNames =
|
||||
|
||||
[<Fact>]
|
||||
let ``Implied argument names are taken from method or constructor``() =
|
||||
FSharp """
|
||||
module ArgumentNames
|
||||
|
||||
type M (name: string, count: int) =
|
||||
[<System.Runtime.CompilerServices.MethodImpl(System.Runtime.CompilerServices.MethodImplOptions.NoInlining)>]
|
||||
static member Open (fileName: string) = ()
|
||||
|
||||
let test1 = M
|
||||
let test2 = M.Open
|
||||
"""
|
||||
|> withLangVersionPreview
|
||||
|> compile
|
||||
|> shouldSucceed
|
||||
|> verifyIL ["""
|
||||
.method public static class ArgumentNames/M
|
||||
test1(string name,
|
||||
int32 count) cil managed
|
||||
{
|
||||
|
||||
.maxstack 8
|
||||
IL_0000: ldarg.0
|
||||
IL_0001: ldarg.1
|
||||
IL_0002: newobj instance void ArgumentNames/M::.ctor(string,
|
||||
int32)
|
||||
IL_0007: ret
|
||||
}
|
||||
|
||||
.method public static void test2(string fileName) cil managed
|
||||
{
|
||||
|
||||
.maxstack 8
|
||||
IL_0000: ldarg.0
|
||||
IL_0001: call void ArgumentNames/M::Open(string)
|
||||
IL_0006: ret
|
||||
} """ ]
|
||||
|
||||
[<Fact>]
|
||||
let ``Implied argument names are taken from curried method``() =
|
||||
FSharp """
|
||||
module ArgumentNames
|
||||
|
||||
type M =
|
||||
[<System.Runtime.CompilerServices.MethodImpl(System.Runtime.CompilerServices.MethodImplOptions.NoInlining)>]
|
||||
static member Write (fileName: string, offset: int) (data: byte[]) = ()
|
||||
|
||||
let test1 = M.Write
|
||||
"""
|
||||
|> withLangVersionPreview
|
||||
|> compile
|
||||
|> shouldSucceed
|
||||
|> verifyIL ["""
|
||||
.method public static void test1(string fileName,
|
||||
int32 offset,
|
||||
uint8[] data) cil managed
|
||||
{
|
||||
.custom instance void [FSharp.Core]Microsoft.FSharp.Core.CompilationArgumentCountsAttribute::.ctor(int32[]) = ( 01 00 02 00 00 00 02 00 00 00 01 00 00 00 00 00 )
|
||||
|
||||
.maxstack 8
|
||||
IL_0000: ldarg.0
|
||||
IL_0001: ldarg.1
|
||||
IL_0002: ldarg.2
|
||||
IL_0003: call void ArgumentNames/M::Write(string,
|
||||
int32,
|
||||
uint8[])
|
||||
IL_0008: ret
|
||||
} """ ]
|
||||
|
||||
[<Fact>]
|
||||
let ``Implied argument names are taken from C#-style extension method``() =
|
||||
FSharp """
|
||||
module ArgumentNames
|
||||
|
||||
open System.Runtime.CompilerServices
|
||||
|
||||
[<Extension>]
|
||||
type Ext =
|
||||
[<System.Runtime.CompilerServices.MethodImpl(System.Runtime.CompilerServices.MethodImplOptions.NoInlining)>]
|
||||
[<Extension>]
|
||||
static member Print(x: int, yy: string) = printfn "%d%s" x yy
|
||||
|
||||
let test1 = (3).Print
|
||||
"""
|
||||
|> withLangVersionPreview
|
||||
|> compile
|
||||
|> shouldSucceed
|
||||
|> verifyIL ["""
|
||||
Invoke(string yy) cil managed
|
||||
{
|
||||
|
||||
.maxstack 8
|
||||
IL_0000: ldc.i4.3
|
||||
IL_0001: ldarg.1
|
||||
IL_0002: call void ArgumentNames/Ext::Print(int32,
|
||||
string)
|
||||
IL_0007: ldnull
|
||||
IL_0008: ret
|
||||
} """ ]
|
||||
|
||||
[<Fact>]
|
||||
let ``Implied argument names are taken from DU case constructor or exception``() =
|
||||
FSharp """
|
||||
module ArgumentNames
|
||||
|
||||
exception X of code: int * string
|
||||
|
||||
type DU =
|
||||
| Case1 of code: int * string
|
||||
|
||||
let test1 = X
|
||||
let test2 = Case1
|
||||
"""
|
||||
|> withLangVersionPreview
|
||||
|> compile
|
||||
|> shouldSucceed
|
||||
|> verifyIL ["""
|
||||
.method public static class [runtime]System.Exception
|
||||
test1(int32 code,
|
||||
string Data1) cil managed
|
||||
{
|
||||
|
||||
.maxstack 8
|
||||
IL_0000: ldarg.0
|
||||
IL_0001: ldarg.1
|
||||
IL_0002: newobj instance void ArgumentNames/X::.ctor(int32,
|
||||
string)
|
||||
IL_0007: ret
|
||||
}
|
||||
|
||||
.method public static class ArgumentNames/DU
|
||||
test2(int32 code,
|
||||
string Item2) cil managed
|
||||
{
|
||||
|
||||
.maxstack 8
|
||||
IL_0000: ldarg.0
|
||||
IL_0001: ldarg.1
|
||||
IL_0002: call class ArgumentNames/DU ArgumentNames/DU::NewCase1(int32,
|
||||
string)
|
||||
IL_0007: ret
|
||||
} """ ]
|
||||
|
||||
[<Fact>]
|
||||
let ``Implied argument names are taken from function and used in delegate Invoke``() =
|
||||
FSharp """
|
||||
module ArgumentNames
|
||||
|
||||
[<System.Runtime.CompilerServices.MethodImpl(System.Runtime.CompilerServices.MethodImplOptions.NoInlining)>]
|
||||
let add num1 num2 = printfn "%d" (num1 + num2)
|
||||
|
||||
let test1 = System.Action<_, _>(add)
|
||||
"""
|
||||
|> withLangVersionPreview
|
||||
|> compile
|
||||
|> shouldSucceed
|
||||
|> verifyIL ["""
|
||||
.method assembly static void Invoke(int32 num1,
|
||||
int32 num2) cil managed
|
||||
{
|
||||
|
||||
.maxstack 8
|
||||
IL_0000: ldarg.0
|
||||
IL_0001: ldarg.1
|
||||
IL_0002: tail.
|
||||
IL_0004: call void ArgumentNames::'add'(int32,
|
||||
int32)
|
||||
IL_0009: ret
|
||||
} """ ]
|
|
@ -113,6 +113,7 @@
|
|||
<Compile Include="EmittedIL\TupleElimination.fs" />
|
||||
<Compile Include="EmittedIL\TypeTestsInPatternMatching.fs" />
|
||||
<Compile Include="EmittedIL\WhileLoops.fs" />
|
||||
<Compile Include="EmittedIL\ArgumentNames.fs" />
|
||||
<Compile Include="EmittedIL\AssemblyBoundary\AssemblyBoundary.fs" />
|
||||
<Compile Include="EmittedIL\AsyncExpressionStepping\AsyncExpressionStepping.fs" />
|
||||
<Compile Include="EmittedIL\AttributeTargets\AttributeTargets.fs" />
|
||||
|
|
|
@ -661,7 +661,9 @@ let testMutableVar = mutableVar 1
|
|||
let testMutableConst = mutableConst ()
|
||||
"""
|
||||
|
||||
let createOptions() = createOptionsAux [fileSource1; fileSource2] []
|
||||
let createOptionsWithArgs args = createOptionsAux [ fileSource1; fileSource2 ] args
|
||||
|
||||
let createOptions() = createOptionsWithArgs []
|
||||
|
||||
let operatorTests = """
|
||||
module OperatorTests{0}
|
||||
|
@ -732,7 +734,7 @@ let ignoreTestIfStackOverflowExpected () =
|
|||
/// This test is run in unison with its optimized counterpart below
|
||||
[<Test>]
|
||||
let ``Test Unoptimized Declarations Project1`` () =
|
||||
let cleanup, options = Project1.createOptions()
|
||||
let cleanup, options = Project1.createOptionsWithArgs [ "--langversion:preview" ]
|
||||
use _holder = cleanup
|
||||
let exprChecker = FSharpChecker.Create(keepAssemblyContents=true)
|
||||
let wholeProjectResults = exprChecker.ParseAndCheckProject(options) |> Async.RunImmediate
|
||||
|
@ -796,7 +798,7 @@ let ``Test Unoptimized Declarations Project1`` () =
|
|||
"member .ctor(c,d) = (new Object(); ()) @ (105,5--105,20)";
|
||||
"member Method(x) (a,b) = 1 @ (106,37--106,38)";
|
||||
"member CurriedMethod(x) (a1,b1) (a2,b2) = 1 @ (107,63--107,64)";
|
||||
"let testFunctionThatCallsMultiArgMethods(unitVar0) = let m: M.MultiArgMethods = new MultiArgMethods(3,4) in Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),m.Method(7,8),fun tupledArg -> let arg00: Microsoft.FSharp.Core.int = tupledArg.Item0 in let arg01: Microsoft.FSharp.Core.int = tupledArg.Item1 in fun tupledArg -> let arg10: Microsoft.FSharp.Core.int = tupledArg.Item0 in let arg11: Microsoft.FSharp.Core.int = tupledArg.Item1 in m.CurriedMethod(arg00,arg01,arg10,arg11) (9,10) (11,12)) @ (110,8--110,9)";
|
||||
"let testFunctionThatCallsMultiArgMethods(unitVar0) = let m: M.MultiArgMethods = new MultiArgMethods(3,4) in Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),m.Method(7,8),fun tupledArg -> let a1: Microsoft.FSharp.Core.int = tupledArg.Item0 in let b1: Microsoft.FSharp.Core.int = tupledArg.Item1 in fun tupledArg -> let a2: Microsoft.FSharp.Core.int = tupledArg.Item0 in let b2: Microsoft.FSharp.Core.int = tupledArg.Item1 in m.CurriedMethod(a1,b1,a2,b2) (9,10) (11,12)) @ (110,8--110,9)";
|
||||
"let testFunctionThatUsesUnitsOfMeasure(x) (y) = Operators.op_Addition<Microsoft.FSharp.Core.float<'u>,Microsoft.FSharp.Core.float<'u>,Microsoft.FSharp.Core.float<'u>> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.float<'u>,Microsoft.FSharp.Core.float<'u>,Microsoft.FSharp.Core.float<'u>> (arg0_0,arg1_0),x,y) @ (122,70--122,75)";
|
||||
"let testFunctionThatUsesAddressesAndByrefs(x) = let mutable w: Microsoft.FSharp.Core.int = 4 in let y1: Microsoft.FSharp.Core.byref<Microsoft.FSharp.Core.int> = x in let y2: Microsoft.FSharp.Core.byref<Microsoft.FSharp.Core.int> = &w in let arr: Microsoft.FSharp.Core.int Microsoft.FSharp.Core.array = [|3; 4|] in let r: Microsoft.FSharp.Core.int Microsoft.FSharp.Core.ref = Operators.Ref<Microsoft.FSharp.Core.int> (3) in let y3: Microsoft.FSharp.Core.byref<Microsoft.FSharp.Core.int> = [I_ldelema (NormalAddress, false, ILArrayShape [(Some 0, None)], !0)](arr,0) in let y4: Microsoft.FSharp.Core.byref<Microsoft.FSharp.Core.int> = &r.contents in let z: Microsoft.FSharp.Core.int = Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),x,y1),y2),y3) in (w <- 3; (x <- 4; (y2 <- 4; (y3 <- 5; Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),z,x),y1),y2),y3),y4),IntrinsicFunctions.GetArray<Microsoft.FSharp.Core.int> (arr,0)),r.contents))))) @ (125,16--125,17)";
|
||||
"let testFunctionThatUsesStructs1(dt) = dt.AddDays(3) @ (139,57--139,72)";
|
||||
|
@ -867,7 +869,7 @@ let ``Test Unoptimized Declarations Project1`` () =
|
|||
|
||||
[<Test>]
|
||||
let ``Test Optimized Declarations Project1`` () =
|
||||
let cleanup, options = Project1.createOptions()
|
||||
let cleanup, options = Project1.createOptionsWithArgs [ "--langversion:preview" ]
|
||||
use _holder = cleanup
|
||||
let exprChecker = FSharpChecker.Create(keepAssemblyContents=true)
|
||||
let wholeProjectResults = exprChecker.ParseAndCheckProject(options) |> Async.RunImmediate
|
||||
|
@ -931,7 +933,7 @@ let ``Test Optimized Declarations Project1`` () =
|
|||
"member .ctor(c,d) = (new Object(); ()) @ (105,5--105,20)";
|
||||
"member Method(x) (a,b) = 1 @ (106,37--106,38)";
|
||||
"member CurriedMethod(x) (a1,b1) (a2,b2) = 1 @ (107,63--107,64)";
|
||||
"let testFunctionThatCallsMultiArgMethods(unitVar0) = let m: M.MultiArgMethods = new MultiArgMethods(3,4) in Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),m.Method(7,8),let arg00: Microsoft.FSharp.Core.int = 9 in let arg01: Microsoft.FSharp.Core.int = 10 in let arg10: Microsoft.FSharp.Core.int = 11 in let arg11: Microsoft.FSharp.Core.int = 12 in m.CurriedMethod(arg00,arg01,arg10,arg11)) @ (110,8--110,9)";
|
||||
"let testFunctionThatCallsMultiArgMethods(unitVar0) = let m: M.MultiArgMethods = new MultiArgMethods(3,4) in Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),m.Method(7,8),let a1: Microsoft.FSharp.Core.int = 9 in let b1: Microsoft.FSharp.Core.int = 10 in let a2: Microsoft.FSharp.Core.int = 11 in let b2: Microsoft.FSharp.Core.int = 12 in m.CurriedMethod(a1,b1,a2,b2)) @ (110,8--110,9)";
|
||||
"let testFunctionThatUsesUnitsOfMeasure(x) (y) = Operators.op_Addition<Microsoft.FSharp.Core.float<'u>,Microsoft.FSharp.Core.float<'u>,Microsoft.FSharp.Core.float<'u>> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.float<'u>,Microsoft.FSharp.Core.float<'u>,Microsoft.FSharp.Core.float<'u>> (arg0_0,arg1_0),x,y) @ (122,70--122,75)";
|
||||
"let testFunctionThatUsesAddressesAndByrefs(x) = let mutable w: Microsoft.FSharp.Core.int = 4 in let y1: Microsoft.FSharp.Core.byref<Microsoft.FSharp.Core.int> = x in let y2: Microsoft.FSharp.Core.byref<Microsoft.FSharp.Core.int> = &w in let arr: Microsoft.FSharp.Core.int Microsoft.FSharp.Core.array = [|3; 4|] in let r: Microsoft.FSharp.Core.int Microsoft.FSharp.Core.ref = Operators.Ref<Microsoft.FSharp.Core.int> (3) in let y3: Microsoft.FSharp.Core.byref<Microsoft.FSharp.Core.int> = [I_ldelema (NormalAddress, false, ILArrayShape [(Some 0, None)], !0)](arr,0) in let y4: Microsoft.FSharp.Core.byref<Microsoft.FSharp.Core.int> = &r.contents in let z: Microsoft.FSharp.Core.int = Operators.op_Addition<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),x,y1),y2),y3) in (w <- 3; (x <- 4; (y2 <- 4; (y3 <- 5; Operators.op_Addition<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32,Microsoft.FSharp.Core.int32> (arg0_0,arg1_0),Operators.op_Addition<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (fun arg0_0 -> fun arg1_0 -> LanguagePrimitives.AdditionDynamic<Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int,Microsoft.FSharp.Core.int> (arg0_0,arg1_0),z,x),y1),y2),y3),y4),IntrinsicFunctions.GetArray<Microsoft.FSharp.Core.int> (arr,0)),r.contents))))) @ (125,16--125,17)";
|
||||
"let testFunctionThatUsesStructs1(dt) = dt.AddDays(3) @ (139,57--139,72)";
|
||||
|
|
Загрузка…
Ссылка в новой задаче