summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMoonchild <moonchild@palemoon.org>2021-12-08 18:02:29 +0000
committerMoonchild <moonchild@palemoon.org>2022-04-07 23:52:40 +0200
commita9046dcd55c721bb3ddedadbbdb217848cb99d8e (patch)
tree7e32e7a322d73b40512cd993e3303b93ac86179a
parentc265d1cb7ca98616426ee7c0a3d7cc0dd1a4cc50 (diff)
downloaduxp-a9046dcd55c721bb3ddedadbbdb217848cb99d8e.tar.gz
[Network] Escape external protocol handler URLs
-rw-r--r--netwerk/base/nsINetUtil.idl3
-rw-r--r--uriloader/exthandler/nsExternalHelperAppService.cpp40
-rw-r--r--uriloader/exthandler/nsExternalHelperAppService.h2
-rw-r--r--xpcom/io/nsEscape.cpp47
-rw-r--r--xpcom/io/nsEscape.h6
5 files changed, 58 insertions, 40 deletions
diff --git a/netwerk/base/nsINetUtil.idl b/netwerk/base/nsINetUtil.idl
index 800a9ae905..1b5de18b61 100644
--- a/netwerk/base/nsINetUtil.idl
+++ b/netwerk/base/nsINetUtil.idl
@@ -167,6 +167,9 @@ interface nsINetUtil : nsISupports
/** Skip C0 and DEL from unescaping */
const unsigned long ESCAPE_URL_SKIP_CONTROL = 1 << 15;
+ /** %XX-escape external protocol handler URL */
+ const unsigned long ESCAPE_URL_EXT_HANDLER = 1 << 17;
+
/**
* %XX-Escape invalid chars in a URL segment.
*
diff --git a/uriloader/exthandler/nsExternalHelperAppService.cpp b/uriloader/exthandler/nsExternalHelperAppService.cpp
index e3e135b053..02a555f04c 100644
--- a/uriloader/exthandler/nsExternalHelperAppService.cpp
+++ b/uriloader/exthandler/nsExternalHelperAppService.cpp
@@ -1,5 +1,4 @@
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
- * vim:expandtab:shiftwidth=2:tabstop=2:cin:
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
@@ -851,6 +850,25 @@ NS_IMETHODIMP nsExternalHelperAppService::LoadUrl(nsIURI * aURL)
static const char kExternalProtocolPrefPrefix[] = "network.protocol-handler.external.";
static const char kExternalProtocolDefaultPref[] = "network.protocol-handler.external-default";
+// static
+nsresult nsExternalHelperAppService::EscapeURI(nsIURI* aURI, nsIURI** aResult) {
+ MOZ_ASSERT(aURI);
+ MOZ_ASSERT(aResult);
+
+ nsAutoCString spec;
+ aURI->GetSpec(spec);
+
+ if (spec.Find("%00") != -1) return NS_ERROR_MALFORMED_URI;
+
+ nsAutoCString escapedSpec;
+ nsresult rv = NS_EscapeURL(spec, esc_AlwaysCopy | esc_ExtHandler, escapedSpec,
+ fallible);
+ NS_ENSURE_SUCCESS(rv, rv);
+
+ nsCOMPtr<nsIIOService> ios(do_GetIOService());
+ return ios->NewURI(escapedSpec, nullptr, nullptr, aResult);
+}
+
NS_IMETHODIMP
nsExternalHelperAppService::LoadURI(nsIURI *aURI,
nsIInterfaceRequestor *aWindowContext)
@@ -867,22 +885,12 @@ nsExternalHelperAppService::LoadURI(nsIURI *aURI,
return NS_OK;
}
- nsAutoCString spec;
- aURI->GetSpec(spec);
-
- if (spec.Find("%00") != -1)
- return NS_ERROR_MALFORMED_URI;
-
- spec.ReplaceSubstring("\"", "%22");
- spec.ReplaceSubstring("`", "%60");
-
- nsCOMPtr<nsIIOService> ios(do_GetIOService());
- nsCOMPtr<nsIURI> uri;
- nsresult rv = ios->NewURI(spec, nullptr, nullptr, getter_AddRefs(uri));
+ nsCOMPtr<nsIURI> escapedURI;
+ nsresult rv = EscapeURI(aURI, getter_AddRefs(escapedURI));
NS_ENSURE_SUCCESS(rv, rv);
nsAutoCString scheme;
- uri->GetScheme(scheme);
+ escapedURI->GetScheme(scheme);
if (scheme.IsEmpty())
return NS_OK; // must have a scheme
@@ -915,13 +923,13 @@ nsExternalHelperAppService::LoadURI(nsIURI *aURI,
// a helper app or the system default, we just launch the URI.
if (!alwaysAsk && (preferredAction == nsIHandlerInfo::useHelperApp ||
preferredAction == nsIHandlerInfo::useSystemDefault))
- return handler->LaunchWithURI(uri, aWindowContext);
+ return handler->LaunchWithURI(escapedURI, aWindowContext);
nsCOMPtr<nsIContentDispatchChooser> chooser =
do_CreateInstance("@mozilla.org/content-dispatch-chooser;1", &rv);
NS_ENSURE_SUCCESS(rv, rv);
- return chooser->Ask(handler, aWindowContext, uri,
+ return chooser->Ask(handler, aWindowContext, escapedURI,
nsIContentDispatchChooser::REASON_CANNOT_HANDLE);
}
diff --git a/uriloader/exthandler/nsExternalHelperAppService.h b/uriloader/exthandler/nsExternalHelperAppService.h
index ceec66661d..13dcbb7122 100644
--- a/uriloader/exthandler/nsExternalHelperAppService.h
+++ b/uriloader/exthandler/nsExternalHelperAppService.h
@@ -198,6 +198,8 @@ private:
bool aForceSave,
nsIInterfaceRequestor *aWindowContext,
nsIStreamListener ** aStreamListener);
+
+ static nsresult EscapeURI(nsIURI* aURI, nsIURI** aResult);
};
/**
diff --git a/xpcom/io/nsEscape.cpp b/xpcom/io/nsEscape.cpp
index 50de7db08c..7a5e3a3355 100644
--- a/xpcom/io/nsEscape.cpp
+++ b/xpcom/io/nsEscape.cpp
@@ -329,39 +329,40 @@ nsEscapeHTML2(const char16_t* aSourceBuffer, int32_t aSourceBufferLen)
// parts of an URL. The bits are the "url components" in the enum EscapeMask,
// see nsEscape.h.
//
-// esc_Scheme = 1
-// esc_Username = 2
-// esc_Password = 4
-// esc_Host = 8
-// esc_Directory = 16
-// esc_FileBaseName = 32
-// esc_FileExtension = 64
-// esc_Param = 128
-// esc_Query = 256
-// esc_Ref = 512
+// esc_Scheme = 1
+// esc_Username = 2
+// esc_Password = 4
+// esc_Host = 8
+// esc_Directory = 16
+// esc_FileBaseName = 32
+// esc_FileExtension = 64
+// esc_Param = 128
+// esc_Query = 256
+// esc_Ref = 512
+// esc_ExtHandler = 131072
static const uint32_t EscapeChars[256] =
-// 0 1 2 3 4 5 6 7 8 9 A B C D E F
+// 0 1 2 3 4 5 6 7 8 9 A B C D E F
{
- 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 0x
- 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 1x
- 0,1023, 0, 512,1023, 0,1023, 624,1023,1023,1023,1023,1023,1023, 953, 784, // 2x !"#$%&'()*+,-./
- 1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1008,1008, 0,1008, 0, 768, // 3x 0123456789:;<=>?
- 1008,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023, // 4x @ABCDEFGHIJKLMNO
- 1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1008, 896,1008, 896,1023, // 5x PQRSTUVWXYZ[\]^_
- 384,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023, // 6x `abcdefghijklmno
- 1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1023, 896,1012, 896,1023, 0, // 7x pqrstuvwxyz{|}~ DEL
- 0 // 80 to FF are zero
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 0x
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, // 1x
+ 0,132095, 0,131584,132095, 0,132095,131696,132095,132095,132095,132095,132095,132095,132025,131856, // 2x !"#$%&'()*+,-./
+ 132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132080,132080, 0,132080, 0,131840, // 3x 0123456789:;<=>?
+ 132080,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095, // 4x @ABCDEFGHIJKLMNO
+ 132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132080, 896,132080, 896,132095, // 5x PQRSTUVWXYZ[\]^_
+ 384,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095, // 6x `abcdefghijklmno
+ 132095,132095,132095,132095,132095,132095,132095,132095,132095,132095,132095, 896, 1012, 896,132095, 0, // 7x pqrstuvwxyz{|}~ DEL
+ 0 // 80 to FF are zero
};
-static uint16_t dontNeedEscape(unsigned char aChar, uint32_t aFlags)
+static bool dontNeedEscape(unsigned char aChar, uint32_t aFlags)
{
return EscapeChars[(uint32_t)aChar] & aFlags;
}
-static uint16_t dontNeedEscape(uint16_t aChar, uint32_t aFlags)
+static bool dontNeedEscape(uint16_t aChar, uint32_t aFlags)
{
return aChar < mozilla::ArrayLength(EscapeChars) ?
- (EscapeChars[(uint32_t)aChar] & aFlags) : 0;
+ (EscapeChars[(uint32_t)aChar] & aFlags) : false;
}
//----------------------------------------------------------------------------------------
diff --git a/xpcom/io/nsEscape.h b/xpcom/io/nsEscape.h
index b25e9ef8e7..f8ad8c7c8e 100644
--- a/xpcom/io/nsEscape.h
+++ b/xpcom/io/nsEscape.h
@@ -97,7 +97,11 @@ enum EscapeMask {
* ascii octets (<= 0x7F) to be skipped when unescaping */
esc_AlwaysCopy = 1u << 13, /* copy input to result buf even if escaping is unnecessary */
esc_Colon = 1u << 14, /* forces escape of colon */
- esc_SkipControl = 1u << 15 /* skips C0 and DEL from unescaping */
+ esc_SkipControl = 1u << 15, /* skips C0 and DEL from unescaping */
+ esc_Spaces = 1u << 16, /* forces escape of spaces */
+ esc_ExtHandler = 1u << 17 /* For escaping external protocol handler urls.
+ * Escapes everything except:
+ * a-z, 0-9 and !#$&'()*+,-./:;=?@[]_~ */
};
/**