Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/mono/mono.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKatelyn Gadd <kg@luminance.org>2017-10-20 11:53:25 +0300
committerMarek Safar <marek.safar@gmail.com>2017-10-20 11:53:25 +0300
commit44b21bca28f9d262e07ebd31c39829447582de5f (patch)
treee503b3e86227e6e1fd28d9004f89f2b6818d7bf0 /mcs/class/referencesource
parentc26e069703d74e0b7a5da4b0326ae72cfde3f5d3 (diff)
Fix bug #58400 - incorrect implementation of LocalPath for file URLs (#5779)
Diffstat (limited to 'mcs/class/referencesource')
-rw-r--r--mcs/class/referencesource/System/net/System/URI.cs51
1 files changed, 48 insertions, 3 deletions
diff --git a/mcs/class/referencesource/System/net/System/URI.cs b/mcs/class/referencesource/System/net/System/URI.cs
index 24ddbc66e15..8a740ce08b8 100644
--- a/mcs/class/referencesource/System/net/System/URI.cs
+++ b/mcs/class/referencesource/System/net/System/URI.cs
@@ -1070,11 +1070,50 @@ namespace System {
EnsureParseRemaining();
#if MONO
+ // https://bugzilla.xamarin.com/show_bug.cgi?id=58400
+ bool isFileUrlWithHost =
+ (m_Info.Offset.Host != m_Info.Offset.Path) &&
+ // only file URLs
+ IsFile &&
+ // Paths that got reinterpreted as files would be treated
+ // as if they have a host, like "/a/b" which maps to "file:///a/b/",
+ // or "C:\a\b\" which maps to "file:///c:/a/b"
+ OriginalString.StartsWith("file://", StringComparison.Ordinal) &&
+ // file://localhost/x/y needs to produce /x/y
+ !IsLoopback;
+
+ // Manually check for "hosts" that are just forward slashes.
+ if (isFileUrlWithHost) {
+ isFileUrlWithHost = false;
+
+ for (int i = m_Info.Offset.Host; i < m_Info.Offset.Path; i++) {
+ if (OriginalString[i] != '/') {
+ isFileUrlWithHost = true;
+ break;
+ }
+ }
+ }
+
+ // We need to force generation of a UNC-style path instead of a unix one,
+ // despite the path not being UNC originally
+ bool treatAsUncPath = IsUncPath || isFileUrlWithHost;
+
//
// I think this is wrong but it keeps LocalPath fully backward compatible
//
- if (IsUncOrDosPath && (IsWindowsFileSystem || !IsUncPath))
+ if (
+ (IsUncOrDosPath &&
+ (
+ IsWindowsFileSystem ||
+ !IsUncPath
+ )
+ ) ||
+ // If a path has a host name force it into this branch so the UNC code runs
+ isFileUrlWithHost
+ )
#else
+ bool treatAsUncPath = IsUncPath;
+
//Other cases will get a Unix-style path
if (IsUncOrDosPath)
#endif
@@ -1083,7 +1122,13 @@ namespace System {
int start;
// Do we have a valid local path right in m_string?
- if (NotAny(Flags.HostNotCanonical|Flags.PathNotCanonical|Flags.ShouldBeCompressed)) {
+ if (
+ NotAny(Flags.HostNotCanonical|Flags.PathNotCanonical|Flags.ShouldBeCompressed)
+#if MONO
+ // This branch drops the host name so we can't use it
+ && !isFileUrlWithHost
+#endif
+ ) {
start = IsUncPath? m_Info.Offset.Host-2 :m_Info.Offset.Path;
@@ -1121,7 +1166,7 @@ namespace System {
string host = m_Info.Host;
result = new char [host.Length + 3 + m_Info.Offset.Fragment - m_Info.Offset.Path ];
- if (IsUncPath)
+ if (treatAsUncPath)
{
result[0] = '\\';
result[1] = '\\';