Skip to content

Commit 442dc14

Browse files
authored
Merge pull request #1327 from dsyme/fix-93
Fix 93 - prefer accessible types over inaccessible types
2 parents 296e7f2 + 10f67ef commit 442dc14

File tree

5 files changed

+82
-25
lines changed

5 files changed

+82
-25
lines changed

src/fsharp/NameResolution.fs

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1031,7 +1031,7 @@ let ResolveProvidedTypeNameInEntity (amap, m, typeName, modref: ModuleOrNamespac
10311031
#endif
10321032

10331033
/// Lookup a type name in an entity.
1034-
let LookupTypeNameInEntityMaybeHaveArity (amap, m, nm, staticResInfo:TypeNameResolutionStaticArgsInfo, modref: ModuleOrNamespaceRef) =
1034+
let LookupTypeNameInEntityMaybeHaveArity (amap, m, ad, nm, staticResInfo:TypeNameResolutionStaticArgsInfo, modref: ModuleOrNamespaceRef) =
10351035
let mtyp = modref.ModuleOrNamespaceType
10361036
let tcrefs =
10371037
match staticResInfo with
@@ -1051,6 +1051,7 @@ let LookupTypeNameInEntityMaybeHaveArity (amap, m, nm, staticResInfo:TypeNameRes
10511051
#else
10521052
amap |> ignore
10531053
#endif
1054+
let tcrefs = tcrefs |> List.filter (IsEntityAccessible amap m ad)
10541055
tcrefs
10551056

10561057

@@ -1081,15 +1082,15 @@ let GetNestedTypesOfType (ad, ncenv:NameResolver, optFilter, staticResInfo, chec
10811082

10821083
match optFilter with
10831084
| Some nm ->
1084-
LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, m, nm, staticResInfo, tcref)
1085-
|> List.map (MakeNestedType ncenv tinst m)
1085+
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, m, ad, nm, staticResInfo, tcref)
1086+
tcrefs |> List.map (MakeNestedType ncenv tinst m)
10861087
| None ->
10871088
#if EXTENSIONTYPING
10881089
match tycon.TypeReprInfo with
10891090
| TProvidedTypeExtensionPoint info ->
10901091
[ for nestedType in info.ProvidedType.PApplyArray((fun sty -> sty.GetNestedTypes()), "GetNestedTypes", m) do
10911092
let nestedTypeName = nestedType.PUntaint((fun t -> t.Name), m)
1092-
for nestedTcref in LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, m, nestedTypeName, staticResInfo, tcref) do
1093+
for nestedTcref in LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, m, ad, nestedTypeName, staticResInfo, tcref) do
10931094
yield MakeNestedType ncenv tinst m nestedTcref ]
10941095

10951096
| _ ->
@@ -1980,7 +1981,7 @@ let rec ResolveExprLongIdentInModuleOrNamespace (ncenv:NameResolver) nenv (typeN
19801981

19811982
// Something in a type?
19821983
let tyconSearch =
1983-
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, id.idText, (if isNil rest then typeNameResInfo.StaticArgsInfo else TypeNameResolutionStaticArgsInfo.Indefinite), modref)
1984+
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, ad, id.idText, (if isNil rest then typeNameResInfo.StaticArgsInfo else TypeNameResolutionStaticArgsInfo.Indefinite), modref)
19841985
let tcrefs = tcrefs |> List.map (fun tcref -> (resInfo,tcref))
19851986
if nonNil rest then
19861987
let tcrefs = CheckForTypeLegitimacyAndMultipleGenericTypeAmbiguities (tcrefs, TypeNameResolutionInfo (ResolveTypeNamesToTypeRefs,TypeNameResolutionStaticArgsInfo.Indefinite), PermitDirectReferenceToGeneratedType.No, unionRanges m id.idRange)
@@ -2190,7 +2191,7 @@ let rec ResolvePatternLongIdentInModuleOrNamespace (ncenv:NameResolver) nenv num
21902191
success(resInfo,Item.Value (mkNestedValRef modref vspec),rest)
21912192
| _ ->
21922193
// Something in a type? e.g. a literal field
2193-
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, id.idText, TypeNameResolutionStaticArgsInfo.Indefinite, modref)
2194+
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, ad, id.idText, TypeNameResolutionStaticArgsInfo.Indefinite, modref)
21942195
let tcrefs = tcrefs |> List.map (fun tcref -> (resInfo,tcref))
21952196
let tyconSearch =
21962197
match lid with
@@ -2309,7 +2310,7 @@ let rec ResolveTypeLongIdentInTyconRefPrim (ncenv:NameResolver) (typeNameResInfo
23092310
CheckForDirectReferenceToGeneratedType (tcref, PermitDirectReferenceToGeneratedType.No, m)
23102311
#endif
23112312
let m = unionRanges m id.idRange
2312-
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, id.idText, typeNameResInfo.StaticArgsInfo, tcref)
2313+
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, ad, id.idText, typeNameResInfo.StaticArgsInfo, tcref)
23132314
let tcrefs = tcrefs |> List.map (fun tcref -> (resInfo,tcref))
23142315
let tcrefs = CheckForTypeLegitimacyAndMultipleGenericTypeAmbiguities (tcrefs, typeNameResInfo, genOk, m)
23152316
match tcrefs with
@@ -2323,7 +2324,7 @@ let rec ResolveTypeLongIdentInTyconRefPrim (ncenv:NameResolver) (typeNameResInfo
23232324
let m = unionRanges m id.idRange
23242325
// Search nested types
23252326
let tyconSearch =
2326-
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, id.idText, TypeNameResolutionStaticArgsInfo.Indefinite, tcref)
2327+
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, ad, id.idText, TypeNameResolutionStaticArgsInfo.Indefinite, tcref)
23272328
let tcrefs = tcrefs |> List.map (fun tcref -> (resInfo,tcref))
23282329
let tcrefs = CheckForTypeLegitimacyAndMultipleGenericTypeAmbiguities (tcrefs, typeNameResInfo.DropStaticArgsInfo, genOk, m)
23292330
match tcrefs with
@@ -2356,7 +2357,7 @@ let rec private ResolveTypeLongIdentInModuleOrNamespace (ncenv:NameResolver) (ty
23562357
| [] -> error(Error(FSComp.SR.nrUnexpectedEmptyLongId(),m))
23572358
| [id] ->
23582359
// On all paths except error reporting we have isSome(staticResInfo), hence get at most one result back
2359-
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, id.idText, typeNameResInfo.StaticArgsInfo, modref)
2360+
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, ad, id.idText, typeNameResInfo.StaticArgsInfo, modref)
23602361
match tcrefs with
23612362
| _ :: _ -> tcrefs |> CollectResults (fun tcref -> success(resInfo,tcref))
23622363
| [] -> raze (SuggestTypeLongIdentInModuleOrNamespace depth modref id)
@@ -2370,7 +2371,7 @@ let rec private ResolveTypeLongIdentInModuleOrNamespace (ncenv:NameResolver) (ty
23702371
| _ ->
23712372
raze (UndefinedName(depth,FSComp.SR.undefinedNameNamespaceOrModule,id,NoPredictions))
23722373
let tyconSearch =
2373-
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, id.idText, TypeNameResolutionStaticArgsInfo.Indefinite, modref)
2374+
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, ad, id.idText, TypeNameResolutionStaticArgsInfo.Indefinite, modref)
23742375
match tcrefs with
23752376
| _ :: _ -> tcrefs |> CollectResults (fun tcref -> ResolveTypeLongIdentInTyconRefPrim ncenv typeNameResInfo ad resInfo genOk (depth+1) m tcref rest)
23762377
| [] -> raze (UndefinedName(depth,FSComp.SR.undefinedNameType,id,NoPredictions))
@@ -2424,8 +2425,9 @@ let rec ResolveTypeLongIdentPrim (ncenv:NameResolver) fullyQualified m nenv ad (
24242425

24252426
let modulSearchFailed() =
24262427
ResolveLongIndentAsModuleOrNamespaceThen ncenv.amap m fullyQualified nenv AccessibleFromSomeFSharpCode lid
2427-
(ResolveTypeLongIdentInModuleOrNamespace ncenv typeNameResInfo.DropStaticArgsInfo ad genOk)
2428+
(ResolveTypeLongIdentInModuleOrNamespace ncenv typeNameResInfo.DropStaticArgsInfo AccessibleFromSomeFSharpCode genOk)
24282429
|?> List.concat
2430+
24292431
match tyconSearch +++ modulSearch with
24302432
| Result results ->
24312433
// NOTE: we delay checking the CheckForTypeLegitimacyAndMultipleGenericTypeAmbiguities condition until right at the end after we've
@@ -2478,7 +2480,7 @@ let rec ResolveFieldInModuleOrNamespace (ncenv:NameResolver) nenv ad (resInfo:Re
24782480
let tyconSearch =
24792481
match lid with
24802482
| _tn:: rest when nonNil rest ->
2481-
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, id.idText, TypeNameResolutionStaticArgsInfo.Indefinite, modref)
2483+
let tcrefs = LookupTypeNameInEntityMaybeHaveArity (ncenv.amap, id.idRange, ad, id.idText, TypeNameResolutionStaticArgsInfo.Indefinite, modref)
24822484
let tcrefs = tcrefs |> List.map (fun tcref -> (ResolutionInfo.Empty,tcref))
24832485
let tyconSearch = ResolveLongIdentInTyconRefs ncenv nenv LookupKind.RecdField (depth+1) m ad rest typeNameResInfo id.idRange tcrefs
24842486
// choose only fields

tests/fsharp/core/fsfromfsviacs/lib2.cs

Lines changed: 28 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -2,29 +2,31 @@
22
using Microsoft.FSharp.Core;
33
using Microsoft.FSharp.Collections;
44

5+
[assembly: System.Runtime.CompilerServices.InternalsVisibleTo("a")]
6+
57
public class Lib2
68
{
79
public static Lib.recd1 r1 = new Lib.recd1(3);
810
public static Lib.recd2 r2 = new Lib.recd2(3, "a");
911
public static Lib.rrecd2 rr2 = new Lib.rrecd2("a", 3);
1012
public static Lib.recd3<string> r3 = new Lib.recd3<string>(4, "c", null);
11-
13+
1214
public static Lib.discr1_0 d10a = Lib.discr1_0.Discr1_0_A;
1315
public static Lib.discr1_1 d11a = Lib.discr1_1.NewDiscr1_1_A(3);
1416
public static Lib.discr1_2 d12a = Lib.discr1_2.NewDiscr1_2_A(3, 4);
15-
17+
1618
public static Lib.discr2_0_0 d200a = Lib.discr2_0_0.Discr2_0_0_A;
1719
public static Lib.discr2_1_0 d210a = Lib.discr2_1_0.NewDiscr2_1_0_A(3);
1820
public static Lib.discr2_0_1 d201a = Lib.discr2_0_1.Discr2_0_1_A;
1921
public static Lib.discr2_1_1 d211a = Lib.discr2_1_1.NewDiscr2_1_1_A(3);
20-
22+
2123
public static Lib.discr2_0_0 d200b = Lib.discr2_0_0.Discr2_0_0_B;
2224
public static Lib.discr2_1_0 d210b = Lib.discr2_1_0.Discr2_1_0_B;
2325
public static Lib.discr2_0_1 d201b = Lib.discr2_0_1.NewDiscr2_0_1_B(3);
2426
public static Lib.discr2_1_1 d211b = Lib.discr2_1_1.NewDiscr2_1_1_B(4);
2527

26-
public static FSharpList<int> li1 = FSharpList<int>.Cons(3,FSharpList<int>.Empty);
27-
public static FSharpList<Lib.recd1> lr1 = FSharpList<Lib.recd1>.Cons(r1,FSharpList<Lib.recd1>.Empty);
28+
public static FSharpList<int> li1 = FSharpList<int>.Cons(3, FSharpList<int>.Empty);
29+
public static FSharpList<Lib.recd1> lr1 = FSharpList<Lib.recd1>.Cons(r1, FSharpList<Lib.recd1>.Empty);
2830

2931
public static FSharpOption<int> oi1 = FSharpOption<int>.Some(3);
3032
public static FSharpOption<Lib.recd1> or1 = FSharpOption<Lib.recd1>.Some(r1);
@@ -34,8 +36,27 @@ public class Lib2
3436

3537
public static Lib.StructUnionsTests.U0 u0 = Lib.StructUnionsTests.U0.U0;
3638
public static Lib.StructUnionsTests.U1 u1 = Lib.StructUnionsTests.U1.NewU1(3);
37-
public static Lib.StructUnionsTests.U2 u2 = Lib.StructUnionsTests.U2.NewU2(3,4);
39+
public static Lib.StructUnionsTests.U2 u2 = Lib.StructUnionsTests.U2.NewU2(3, 4);
3840

39-
static Lib2() { r3.recd3field3 = r3; }
41+
static Lib2() { r3.recd3field3 = r3; }
42+
43+
}
44+
45+
namespace Newtonsoft.Json.Converters
46+
{
47+
internal class SomeClass
48+
{
49+
public SomeClass() { }
50+
public static void SomeMethod() { }
51+
}
52+
public class ContainerClass
53+
{
54+
public ContainerClass() { }
55+
internal class SomeClass
56+
{
57+
public SomeClass() { }
58+
public static void SomeMethod() { }
59+
}
4060

61+
}
4162
}
Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
using Microsoft.FSharp;
2+
using Microsoft.FSharp.Core;
3+
using Microsoft.FSharp.Collections;
4+
5+
namespace Newtonsoft.Json.Converters
6+
{
7+
// This should be preferred over the same type in lib2.cs
8+
public class SomeClass
9+
{
10+
public SomeClass() { }
11+
public static void SomeMethod() { }
12+
}
13+
14+
public class ContainerClass
15+
{
16+
public ContainerClass() { }
17+
18+
// This should be preferred over the same type in lib2.cs
19+
public class SomeClass
20+
{
21+
public SomeClass() { }
22+
public static void SomeMethod() { }
23+
}
24+
25+
}
26+
}

tests/fsharp/core/fsfromfsviacs/test.fsx

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,12 @@ module NestedStructPatternMatchingAcrossAssemblyBoundaries =
9292
let _ = test "structunion394b3f" (testPattern3mut(u2))
9393

9494

95+
let TestAccessibility() =
96+
let x = new Newtonsoft.Json.Converters.SomeClass()
97+
let x2 = new Newtonsoft.Json.Converters.ContainerClass.SomeClass()
98+
Newtonsoft.Json.Converters.SomeClass.SomeMethod()
99+
Newtonsoft.Json.Converters.ContainerClass.SomeClass.SomeMethod()
100+
95101
(*
96102
public Lib.discr1_0 d10a = Lib.discr1_0.MkDiscr1_0_A();
97103
public Lib.discr1_1 d11a = Lib.discr1_1.MkDiscr1_1_A(3);

tests/fsharp/core/tests_core.fs

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -316,19 +316,21 @@ module FsFromFsViaCs =
316316
let csc = Printf.ksprintf (Commands.csc exec cfg.CSC)
317317
let fsc_flags = cfg.fsc_flags
318318

319-
// "%FSC%" %fsc_flags% -a -o:lib.dll -g lib.fs
320319
do! fsc "%s -a -o:lib.dll -g" fsc_flags ["lib.fs"]
321320

322-
// "%PEVERIFY%" lib.dll
323321
do! peverify "lib.dll"
324322

325-
// %CSC% /nologo /target:library /r:"%FSCOREDLLPATH%" /r:lib.dll /out:lib2.dll lib2.cs
326323
do! csc """/nologo /target:library /r:"%s" /r:lib.dll /out:lib2.dll""" cfg.FSCOREDLLPATH ["lib2.cs"]
327324

328-
// "%FSC%" %fsc_flags% -r:lib.dll -r:lib2.dll -o:test.exe -g test.fsx
329-
do! fsc "%s -r:lib.dll -r:lib2.dll -o:test.exe -g" fsc_flags ["test.fsx"]
325+
do! csc """/nologo /target:library /r:"%s" /out:lib3.dll""" cfg.FSCOREDLLPATH ["lib3.cs"]
326+
327+
do! fsc "%s -r:lib.dll -r:lib2.dll -r:lib3.dll -o:test.exe -g" fsc_flags ["test.fsx"]
328+
329+
do! peverify "test.exe"
330+
331+
// Same with library refrences the other way around
332+
do! fsc "%s -r:lib.dll -r:lib3.dll -r:lib2.dll -o:test.exe -g" fsc_flags ["test.fsx"]
330333

331-
// "%PEVERIFY%" test.exe
332334
do! peverify "test.exe"
333335

334336
}

0 commit comments

Comments
 (0)