Bug 665706 - Remove historic special handling for semicolons in URIs. r=rjesup
authorJulian Reschke <julian.reschke@gmx.de>
Mon, 22 Aug 2011 16:51:52 +0200
changeset 75661 1a09781a5480a2c8ae6f193a326cbf34167bc52b
parent 75654 ac57320746e8e9ec9dd3091740f84899d1d688b2
child 75662 f56c271dec3505cdeb356fb46266f7dde34855f0
push id21051
push usermlamouri@mozilla.com
push dateTue, 23 Aug 2011 08:20:16 +0000
treeherdermozilla-central@a41b781330a6 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersrjesup
bugs665706
milestone9.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 665706 - Remove historic special handling for semicolons in URIs. r=rjesup
modules/libjar/nsJARURI.cpp
netwerk/base/public/nsIURL.idl
netwerk/base/public/nsIURLParser.idl
netwerk/base/src/nsStandardURL.cpp
netwerk/base/src/nsStandardURL.h
netwerk/base/src/nsURLHelper.cpp
netwerk/base/src/nsURLParsers.cpp
netwerk/test/TestURLParser.cpp
netwerk/test/unit/test_bug429347.js
netwerk/test/urltest.cpp
xpcom/io/nsEscape.cpp
--- a/modules/libjar/nsJARURI.cpp
+++ b/modules/libjar/nsJARURI.cpp
@@ -580,29 +580,16 @@ nsJARURI::GetFilePath(nsACString& filePa
 
 NS_IMETHODIMP
 nsJARURI::SetFilePath(const nsACString& filePath)
 {
     return mJAREntry->SetFilePath(filePath);
 }
 
 NS_IMETHODIMP
-nsJARURI::GetParam(nsACString& param)
-{
-    param.Truncate();
-    return NS_OK;
-}
-
-NS_IMETHODIMP
-nsJARURI::SetParam(const nsACString& param)
-{
-    return NS_ERROR_NOT_AVAILABLE;
-}
-
-NS_IMETHODIMP
 nsJARURI::GetQuery(nsACString& query)
 {
     return mJAREntry->GetQuery(query);
 }
 
 NS_IMETHODIMP
 nsJARURI::SetQuery(const nsACString& query)
 {
--- a/netwerk/base/public/nsIURL.idl
+++ b/netwerk/base/public/nsIURL.idl
@@ -40,17 +40,16 @@
 #include "nsIURI.idl"
 
 /**
  * The nsIURL interface provides convenience methods that further
  * break down the path portion of nsIURI:
  *
  * http://host/directory/fileBaseName.fileExtension?query
  * http://host/directory/fileBaseName.fileExtension#ref
- * http://host/directory/fileBaseName.fileExtension;param
  *            \          \                       /
  *             \          -----------------------
  *              \                   |          /
  *               \               fileName     /
  *                ----------------------------
  *                            |
  *                        filePath
  */
@@ -66,23 +65,16 @@ interface nsIURL : nsIURI
      * URL.  For example, the filePath of "http://host/foo/bar.html#baz"
      * is "/foo/bar.html".
      *
      * Some characters may be escaped.
      */
     attribute AUTF8String filePath;
 
     /**
-     * Returns the parameters specified after the ; in the URL. 
-     *
-     * Some characters may be escaped.
-     */
-    attribute AUTF8String param;
-
-    /**
      * Returns the query portion (the part after the "?") of the URL.
      * If there isn't one, an empty string is returned.
      *
      * Some characters may be escaped.
      */
     attribute AUTF8String query;
 
 
--- a/netwerk/base/public/nsIURLParser.idl
+++ b/netwerk/base/public/nsIURLParser.idl
@@ -90,24 +90,23 @@ interface nsIURLParser : nsISupports
     /**
      * serverinfo = <hostname>:<port>
      */
     void parseServerInfo (in string serverinfo,            in long serverinfoLen,
                           out unsigned long hostnamePos,  out long hostnameLen,
                           out long port);
 
     /**
-     * ParsePath breaks the path string up into its 4 major components: a file path,
-     * a param string, a query string, and a reference string.
+     * ParsePath breaks the path string up into its 3 major components: a file path,
+     * a query string, and a reference string.
      *
-     * path = <filepath>;<param>?<query>#<ref>
+     * path = <filepath>?<query>#<ref>
      */
     void parsePath       (in string path,                  in long pathLen,
                           out unsigned long filepathPos,  out long filepathLen,
-                          out unsigned long paramPos,     out long paramLen,
                           out unsigned long queryPos,     out long queryLen,
                           out unsigned long refPos,       out long refLen);
 
     /**
      * ParseFilePath breaks the file path string up into: the directory portion,
      * file base name, and file extension.
      *
      * filepath = <directory><basename>.<extension>
--- a/netwerk/base/src/nsStandardURL.cpp
+++ b/netwerk/base/src/nsStandardURL.cpp
@@ -395,17 +395,16 @@ nsStandardURL::Clear()
     mHostEncoding = eEncoding_ASCII;
 
     mPath.Reset();
     mFilepath.Reset();
     mDirectory.Reset();
     mBasename.Reset();
 
     mExtension.Reset();
-    mParam.Reset();
     mQuery.Reset();
     mRef.Reset();
 
     InvalidateCache();
 }
 
 void
 nsStandardURL::InvalidateCache(PRBool invalidateCachedFile)
@@ -506,26 +505,26 @@ nsresult
 nsStandardURL::BuildNormalizedSpec(const char *spec)
 {
     // Assumptions: all member URLSegments must be relative the |spec| argument
     // passed to this function.
 
     // buffers for holding escaped url segments (these will remain empty unless
     // escaping is required).
     nsCAutoString encUsername, encPassword, encHost, encDirectory,
-      encBasename, encExtension, encParam, encQuery, encRef;
+      encBasename, encExtension, encQuery, encRef;
     PRBool useEncUsername, useEncPassword, useEncHost, useEncDirectory,
-      useEncBasename, useEncExtension, useEncParam, useEncQuery, useEncRef;
+      useEncBasename, useEncExtension, useEncQuery, useEncRef;
     nsCAutoString portbuf;
 
     //
     // escape each URL segment, if necessary, and calculate approximate normalized
     // spec length.
     //
-    // [scheme://][username[:password]@]host[:port]/path[;param][?query_string][#ref]
+    // [scheme://][username[:password]@]host[:port]/path[?query_string][#ref]
 
     PRUint32 approxLen = 0;
 
     // the scheme is already ASCII
     if (mScheme.mLen > 0)
         approxLen += mScheme.mLen + 3; // includes room for "://";
 
     // encode URL segments; convert UTF-8 to origin charset and possibly escape.
@@ -551,19 +550,16 @@ nsStandardURL::BuildNormalizedSpec(const
         approxLen += 1; // reserve space for possible leading '/' - may not be needed
         // Should just use mPath?  These are pessimistic, and thus waste space
         approxLen += encoder.EncodeSegmentCount(spec, mDirectory, esc_Directory,     encDirectory, useEncDirectory, 1);
         approxLen += encoder.EncodeSegmentCount(spec, mBasename,  esc_FileBaseName,  encBasename,  useEncBasename);
         approxLen += encoder.EncodeSegmentCount(spec, mExtension, esc_FileExtension, encExtension, useEncExtension, 1);
 
         // These next ones *always* add their leading character even if length is 0
         // Handles items like "http://#"
-        // ;param
-        if (mParam.mLen >= 0)
-            approxLen += 1 + encoder.EncodeSegmentCount(spec, mParam,     esc_Param,         encParam,     useEncParam);
         // ?query
         if (mQuery.mLen >= 0)
             approxLen += 1 + queryEncoder.EncodeSegmentCount(spec, mQuery, esc_Query,        encQuery,     useEncQuery);
         // #ref
         if (mRef.mLen >= 0)
             approxLen += 1 + encoder.EncodeSegmentCount(spec, mRef,       esc_Ref,           encRef,       useEncRef);
     }
 
@@ -673,20 +669,16 @@ nsStandardURL::BuildNormalizedSpec(const
 
         if (mExtension.mLen >= 0) {
             buf[i++] = '.';
             i = AppendSegmentToBuf(buf, i, spec, mExtension, &encExtension, useEncExtension);
         }
         // calculate corrected filepath length
         mFilepath.mLen = i - mFilepath.mPos;
 
-        if (mParam.mLen >= 0) {
-            buf[i++] = ';';
-            i = AppendSegmentToBuf(buf, i, spec, mParam, &encParam, useEncParam);
-        }
         if (mQuery.mLen >= 0) {
             buf[i++] = '?';
             i = AppendSegmentToBuf(buf, i, spec, mQuery, &encQuery, useEncQuery);
         }
         if (mRef.mLen >= 0) {
             buf[i++] = '#';
             i = AppendSegmentToBuf(buf, i, spec, mRef, &encRef, useEncRef);
         }
@@ -833,23 +825,21 @@ nsStandardURL::ParseURL(const char *spec
 
 nsresult
 nsStandardURL::ParsePath(const char *spec, PRUint32 pathPos, PRInt32 pathLen)
 {
     LOG(("ParsePath: %s pathpos %d len %d\n",spec,pathPos,pathLen));
 
     nsresult rv = mParser->ParsePath(spec + pathPos, pathLen,
                                      &mFilepath.mPos, &mFilepath.mLen,
-                                     &mParam.mPos, &mParam.mLen,
                                      &mQuery.mPos, &mQuery.mLen,
                                      &mRef.mPos, &mRef.mLen);
     if (NS_FAILED(rv)) return rv;
 
     mFilepath.mPos += pathPos;
-    mParam.mPos += pathPos;
     mQuery.mPos += pathPos;
     mRef.mPos += pathPos;
 
     if (mFilepath.mLen > 0) {
         rv = mParser->ParseFilePath(spec + mFilepath.mPos, mFilepath.mLen,
                                     &mDirectory.mPos, &mDirectory.mLen,
                                     &mBasename.mPos, &mBasename.mLen,
                                     &mExtension.mPos, &mExtension.mLen);
@@ -1203,17 +1193,16 @@ nsStandardURL::SetSpec(const nsACString 
         LOG((" username  = (%u,%d)\n", mUsername.mPos,  mUsername.mLen));
         LOG((" password  = (%u,%d)\n", mPassword.mPos,  mPassword.mLen));
         LOG((" hostname  = (%u,%d)\n", mHost.mPos,      mHost.mLen));
         LOG((" path      = (%u,%d)\n", mPath.mPos,      mPath.mLen));
         LOG((" filepath  = (%u,%d)\n", mFilepath.mPos,  mFilepath.mLen));
         LOG((" directory = (%u,%d)\n", mDirectory.mPos, mDirectory.mLen));
         LOG((" basename  = (%u,%d)\n", mBasename.mPos,  mBasename.mLen));
         LOG((" extension = (%u,%d)\n", mExtension.mPos, mExtension.mLen));
-        LOG((" param     = (%u,%d)\n", mParam.mPos,     mParam.mLen));
         LOG((" query     = (%u,%d)\n", mQuery.mPos,     mQuery.mLen));
         LOG((" ref       = (%u,%d)\n", mRef.mPos,       mRef.mLen));
     }
 #endif
     return rv;
 }
 
 NS_IMETHODIMP
@@ -1628,17 +1617,16 @@ nsStandardURL::SetPath(const nsACString 
         mSpec.Cut(mPath.mPos + 1, mPath.mLen - 1);
         // these contain only a '/'
         mPath.mLen = 1;
         mDirectory.mLen = 1;
         mFilepath.mLen = 1;
         // these are no longer defined
         mBasename.mLen = -1;
         mExtension.mLen = -1;
-        mParam.mLen = -1;
         mQuery.mLen = -1;
         mRef.mLen = -1;
     }
     return NS_OK;
 }
 
 NS_IMETHODIMP
 nsStandardURL::Equals(nsIURI *unknownOther, PRBool *result)
@@ -1679,18 +1667,17 @@ nsStandardURL::EqualsInternal(nsIURI *un
     // URIs different
     if (!SegmentIs(mScheme, other->mSpec.get(), other->mScheme) ||
         // Check for host manually, since conversion to file will
         // ignore the host!
         !SegmentIs(mHost, other->mSpec.get(), other->mHost) ||
         !SegmentIs(mQuery, other->mSpec.get(), other->mQuery) ||
         !SegmentIs(mUsername, other->mSpec.get(), other->mUsername) ||
         !SegmentIs(mPassword, other->mSpec.get(), other->mPassword) ||
-        Port() != other->Port() ||
-        !SegmentIs(mParam, other->mSpec.get(), other->mParam)) {
+        Port() != other->Port()) {
         // No need to compare files or other URI parts -- these are different
         // beasties
         *result = PR_FALSE;
         return NS_OK;
     }
 
     if (refHandlingMode == eHonorRef &&
         !SegmentIs(mRef, other->mSpec.get(), other->mRef)) {
@@ -1790,17 +1777,16 @@ nsStandardURL::CloneInternal(nsStandardU
     clone->mUsername = mUsername;
     clone->mPassword = mPassword;
     clone->mHost = mHost;
     clone->mPath = mPath;
     clone->mFilepath = mFilepath;
     clone->mDirectory = mDirectory;
     clone->mBasename = mBasename;
     clone->mExtension = mExtension;
-    clone->mParam = mParam;
     clone->mQuery = mQuery;
     clone->mRef = mRef;
     clone->mOriginCharset = mOriginCharset;
     clone->mURLType = mURLType;
     clone->mParser = mParser;
     clone->mFile = mFile;
     clone->mHostA = mHostA ? nsCRT::strdup(mHostA) : nsnull;
     clone->mMutable = PR_TRUE;
@@ -2015,17 +2001,17 @@ nsStandardURL::GetCommonBaseSpec(nsIURI 
     while ((*thisIndex == *thatIndex) && *thisIndex)
     {
         thisIndex++;
         thatIndex++;
     }
 
     // backup to just after previous slash so we grab an appropriate path
     // segment such as a directory (not partial segments)
-    // todo:  also check for file matches which include '?', '#', and ';'
+    // todo:  also check for file matches which include '?' and '#'
     while ((thisIndex != startCharPos) && (*(thisIndex-1) != '/'))
         thisIndex--;
 
     // grab spec from beginning to thisIndex
     aResult = Substring(mSpec, mScheme.mPos, thisIndex - mSpec.get());
 
     NS_RELEASE(stdurl2);
     return rv;
@@ -2096,17 +2082,17 @@ nsStandardURL::GetRelativeSpec(nsIURI *u
     while ((*thisIndex == *thatIndex) && *thisIndex)
     {
         thisIndex++;
         thatIndex++;
     }
 
     // backup to just after previous slash so we grab an appropriate path
     // segment such as a directory (not partial segments)
-    // todo:  also check for file matches with '#', '?' and ';'
+    // todo:  also check for file matches with '#' and '?'
     while ((*(thatIndex-1) != '/') && (thatIndex != startCharPos))
         thatIndex--;
 
     const char *limit = mSpec.get() + mFilepath.mPos + mFilepath.mLen;
 
     // need to account for slashes and add corresponding "../"
     for (; thisIndex <= limit && *thisIndex; ++thisIndex)
     {
@@ -2132,24 +2118,16 @@ NS_IMETHODIMP
 nsStandardURL::GetFilePath(nsACString &result)
 {
     result = Filepath();
     return NS_OK;
 }
 
 // result may contain unescaped UTF-8 characters
 NS_IMETHODIMP
-nsStandardURL::GetParam(nsACString &result)
-{
-    result = Param();
-    return NS_OK;
-}
-
-// result may contain unescaped UTF-8 characters
-NS_IMETHODIMP
 nsStandardURL::GetQuery(nsACString &result)
 {
     result = Query();
     return NS_OK;
 }
 
 // result may contain unescaped UTF-8 characters
 NS_IMETHODIMP
@@ -2258,37 +2236,30 @@ nsStandardURL::SetFilePath(const nsACStr
             if (mSpec.Length() > end)
                 spec.Append(mSpec.get() + end, mSpec.Length() - end);
         }
 
         return SetSpec(spec);
     }
     else if (mPath.mLen > 1) {
         mSpec.Cut(mPath.mPos + 1, mFilepath.mLen - 1);
-        // left shift param, query, and ref
-        ShiftFromParam(1 - mFilepath.mLen);
+        // left shift query, and ref
+        ShiftFromQuery(1 - mFilepath.mLen);
         // these contain only a '/'
         mPath.mLen = 1;
         mDirectory.mLen = 1;
         mFilepath.mLen = 1;
         // these are no longer defined
         mBasename.mLen = -1;
         mExtension.mLen = -1;
     }
     return NS_OK;
 }
 
 NS_IMETHODIMP
-nsStandardURL::SetParam(const nsACString &input)
-{
-    NS_NOTYETIMPLEMENTED("");
-    return NS_ERROR_NOT_IMPLEMENTED;
-}
-
-NS_IMETHODIMP
 nsStandardURL::SetQuery(const nsACString &input)
 {
     ENSURE_MUTABLE();
 
     const nsPromiseFlatCString &flat = PromiseFlatCString(input);
     const char *query = flat.get();
 
     LOG(("nsStandardURL::SetQuery [query=%s]\n", query));
@@ -2498,17 +2469,17 @@ nsStandardURL::SetFileName(const nsACStr
             
             mBasename.mLen = basename.mLen;
             mExtension.mLen = extension.mLen;
             if (mExtension.mLen >= 0)
                 mExtension.mPos = mBasename.mPos + mBasename.mLen + 1;
         }
     }
     if (shift) {
-        ShiftFromParam(shift);
+        ShiftFromQuery(shift);
         mFilepath.mLen += shift;
         mPath.mLen += shift;
     }
     return NS_OK;
 }
 
 NS_IMETHODIMP
 nsStandardURL::SetFileBaseName(const nsACString &input)
@@ -2795,19 +2766,16 @@ nsStandardURL::Read(nsIObjectInputStream
     if (NS_FAILED(rv)) return rv;
 
     rv = ReadSegment(stream, mBasename);
     if (NS_FAILED(rv)) return rv;
 
     rv = ReadSegment(stream, mExtension);
     if (NS_FAILED(rv)) return rv;
 
-    rv = ReadSegment(stream, mParam);
-    if (NS_FAILED(rv)) return rv;
-
     rv = ReadSegment(stream, mQuery);
     if (NS_FAILED(rv)) return rv;
 
     rv = ReadSegment(stream, mRef);
     if (NS_FAILED(rv)) return rv;
 
     rv = NS_ReadOptionalCString(stream, mOriginCharset);
     if (NS_FAILED(rv)) return rv;
@@ -2884,19 +2852,16 @@ nsStandardURL::Write(nsIObjectOutputStre
     if (NS_FAILED(rv)) return rv;
 
     rv = WriteSegment(stream, mBasename);
     if (NS_FAILED(rv)) return rv;
 
     rv = WriteSegment(stream, mExtension);
     if (NS_FAILED(rv)) return rv;
 
-    rv = WriteSegment(stream, mParam);
-    if (NS_FAILED(rv)) return rv;
-
     rv = WriteSegment(stream, mQuery);
     if (NS_FAILED(rv)) return rv;
 
     rv = WriteSegment(stream, mRef);
     if (NS_FAILED(rv)) return rv;
 
     rv = NS_WriteOptionalStringZ(stream, mOriginCharset.get());
     if (NS_FAILED(rv)) return rv;
@@ -2959,17 +2924,16 @@ nsStandardURL::Read(const IPC::Message *
         !ReadSegment(aMsg, aIter, mUsername) ||
         !ReadSegment(aMsg, aIter, mPassword) ||
         !ReadSegment(aMsg, aIter, mHost) ||
         !ReadSegment(aMsg, aIter, mPath) ||
         !ReadSegment(aMsg, aIter, mFilepath) ||
         !ReadSegment(aMsg, aIter, mDirectory) ||
         !ReadSegment(aMsg, aIter, mBasename) ||
         !ReadSegment(aMsg, aIter, mExtension) ||
-        !ReadSegment(aMsg, aIter, mParam) ||
         !ReadSegment(aMsg, aIter, mQuery) ||
         !ReadSegment(aMsg, aIter, mRef) ||
         !ReadParam(aMsg, aIter, &mOriginCharset) ||
         !ReadParam(aMsg, aIter, &isMutable) ||
         !ReadParam(aMsg, aIter, &supportsFileURL) ||
         !ReadParam(aMsg, aIter, &hostEncoding))
         return PR_FALSE;
 
@@ -3000,17 +2964,16 @@ nsStandardURL::Write(IPC::Message *aMsg)
     WriteSegment(aMsg, mUsername);
     WriteSegment(aMsg, mPassword);
     WriteSegment(aMsg, mHost);
     WriteSegment(aMsg, mPath);
     WriteSegment(aMsg, mFilepath);
     WriteSegment(aMsg, mDirectory);
     WriteSegment(aMsg, mBasename);
     WriteSegment(aMsg, mExtension);
-    WriteSegment(aMsg, mParam);
     WriteSegment(aMsg, mQuery);
     WriteSegment(aMsg, mRef);
     WriteParam(aMsg, mOriginCharset);
     WriteParam(aMsg, bool(mMutable));
     WriteParam(aMsg, bool(mSupportsFileURL));
     WriteParam(aMsg, mHostEncoding);
     // mSpecEncoding and mHostA are just caches that can be recovered as needed.
 }
--- a/netwerk/base/src/nsStandardURL.h
+++ b/netwerk/base/src/nsStandardURL.h
@@ -218,31 +218,29 @@ private:
     const nsDependentCSubstring Hostport(); // see below
     const nsDependentCSubstring Host();     // see below
     const nsDependentCSubstring Path()      { return Segment(mPath); }
     const nsDependentCSubstring Filepath()  { return Segment(mFilepath); }
     const nsDependentCSubstring Directory() { return Segment(mDirectory); }
     const nsDependentCSubstring Filename(); // see below
     const nsDependentCSubstring Basename()  { return Segment(mBasename); }
     const nsDependentCSubstring Extension() { return Segment(mExtension); }
-    const nsDependentCSubstring Param()     { return Segment(mParam); }
     const nsDependentCSubstring Query()     { return Segment(mQuery); }
     const nsDependentCSubstring Ref()       { return Segment(mRef); }
 
     // shift the URLSegments to the right by diff
     void ShiftFromAuthority(PRInt32 diff) { mAuthority.mPos += diff; ShiftFromUsername(diff); }
     void ShiftFromUsername(PRInt32 diff)  { mUsername.mPos += diff; ShiftFromPassword(diff); }
     void ShiftFromPassword(PRInt32 diff)  { mPassword.mPos += diff; ShiftFromHost(diff); }
     void ShiftFromHost(PRInt32 diff)      { mHost.mPos += diff; ShiftFromPath(diff); }
     void ShiftFromPath(PRInt32 diff)      { mPath.mPos += diff; ShiftFromFilepath(diff); }
     void ShiftFromFilepath(PRInt32 diff)  { mFilepath.mPos += diff; ShiftFromDirectory(diff); }
     void ShiftFromDirectory(PRInt32 diff) { mDirectory.mPos += diff; ShiftFromBasename(diff); }
     void ShiftFromBasename(PRInt32 diff)  { mBasename.mPos += diff; ShiftFromExtension(diff); }
-    void ShiftFromExtension(PRInt32 diff) { mExtension.mPos += diff; ShiftFromParam(diff); }
-    void ShiftFromParam(PRInt32 diff)     { mParam.mPos += diff; ShiftFromQuery(diff); }
+    void ShiftFromExtension(PRInt32 diff) { mExtension.mPos += diff; ShiftFromQuery(diff); }
     void ShiftFromQuery(PRInt32 diff)     { mQuery.mPos += diff; ShiftFromRef(diff); }
     void ShiftFromRef(PRInt32 diff)       { mRef.mPos += diff; }
 
     // fastload helper functions
     nsresult ReadSegment(nsIBinaryInputStream *, URLSegment &);
     nsresult WriteSegment(nsIBinaryOutputStream *, const URLSegment &);
 
     // ipc helper functions
@@ -262,17 +260,16 @@ private:
     URLSegment mUsername;
     URLSegment mPassword;
     URLSegment mHost;
     URLSegment mPath;
     URLSegment mFilepath;
     URLSegment mDirectory;
     URLSegment mBasename;
     URLSegment mExtension;
-    URLSegment mParam;
     URLSegment mQuery;
     URLSegment mRef;
 
     nsCString              mOriginCharset;
     nsCOMPtr<nsIURLParser> mParser;
 
     // mFile is protected so subclasses can access it directly
 protected:
--- a/netwerk/base/src/nsURLHelper.cpp
+++ b/netwerk/base/src/nsURLHelper.cpp
@@ -216,17 +216,16 @@ net_ParseFileURL(const nsACString &inURL
                           nsnull, nsnull, // don't care about scheme
                           nsnull, nsnull, // don't care about authority
                           &pathPos, &pathLen);
     if (NS_FAILED(rv)) return rv;
 
     // invoke the parser to extract filepath from the path
     rv = parser->ParsePath(url + pathPos, pathLen,
                            &filepathPos, &filepathLen,
-                           nsnull, nsnull,  // don't care about param
                            nsnull, nsnull,  // don't care about query
                            nsnull, nsnull); // don't care about ref
     if (NS_FAILED(rv)) return rv;
 
     filepathPos += pathPos;
 
     // invoke the parser to extract the directory and filename from filepath
     rv = parser->ParseFilePath(url + filepathPos, filepathLen,
@@ -446,17 +445,16 @@ net_ResolveRelativePath(const nsACString
     PRBool stop = PR_FALSE;
     char c;
     for (; !stop; ++beg) {
         c = (beg == end) ? '\0' : *beg;
         //printf("%c [name=%s] [path=%s]\n", c, name.get(), path.get());
         switch (c) {
           case '\0':
           case '#':
-          case ';':
           case '?':
             stop = PR_TRUE;
             // fall through...
           case '/':
             // delimiter found
             if (name.EqualsLiteral("..")) {
                 // pop path
                 // If we already have the delim at end, then
--- a/netwerk/base/src/nsURLParsers.cpp
+++ b/netwerk/base/src/nsURLParsers.cpp
@@ -112,17 +112,16 @@ nsBaseURLParser::ParseURL(const char *sp
         switch (*p) {
             case ':':
                 if (!colon)
                     colon = p;
                 break;
             case '/': // start of filepath
             case '?': // start of query
             case '#': // start of ref
-            case ';': // start of param
                 if (!slash)
                     slash = p;
                 break;
             case '@': // username@hostname
             case '[': // start of IPv6 address literal
                 if (!stop)
                     stop = p;
                 break;
@@ -235,26 +234,25 @@ nsBaseURLParser::ParseServerInfo(const c
     if (port)
        *port = -1;
     return NS_OK;
 }
 
 NS_IMETHODIMP
 nsBaseURLParser::ParsePath(const char *path, PRInt32 pathLen,
                            PRUint32 *filepathPos, PRInt32 *filepathLen,
-                           PRUint32 *paramPos, PRInt32 *paramLen,
                            PRUint32 *queryPos, PRInt32 *queryLen,
                            PRUint32 *refPos, PRInt32 *refLen)
 {
     NS_PRECONDITION(path, "null pointer");
 
     if (pathLen < 0)
         pathLen = strlen(path);
 
-    // path = [/]<segment1>/<segment2>/<...>/<segmentN>;<param>?<query>#<ref>
+    // path = [/]<segment1>/<segment2>/<...>/<segmentN>?<query>#<ref>
 
     // XXX PL_strnpbrk would be nice, but it's buggy
 
     // search for first occurrence of either ? or #
     const char *query_beg = 0, *query_end = 0;
     const char *ref_beg = 0;
     const char *p = 0;
     for (p = path; p < path + pathLen; ++p) {
@@ -278,39 +276,23 @@ nsBaseURLParser::ParsePath(const char *p
     else
         SET_RESULT(query, 0, -1);
 
     if (ref_beg)
         SET_RESULT(ref, ref_beg - path, pathLen - (ref_beg - path));
     else
         SET_RESULT(ref, 0, -1);
 
-    // search backwards for param
-    const char *param_beg = 0;
     const char *end;
     if (query_beg)
         end = query_beg - 1;
     else if (ref_beg)
         end = ref_beg - 1;
     else
         end = path + pathLen;
-    for (p = end - 1; p >= path && *p != '/'; --p) {
-        if (*p == ';') {
-            // found param
-            param_beg = p + 1;
-        }
-    }
-
-    if (param_beg) {
-        // found <filepath>;<param>
-        SET_RESULT(param, param_beg - path, end - param_beg);
-        end = param_beg - 1;
-    }
-    else
-        SET_RESULT(param, 0, -1);
 
     // an empty file path is no file path
     if (end != path)
         SET_RESULT(filepath, 0, end - path);
     else
         SET_RESULT(filepath, 0, -1);
     return NS_OK;
 }
@@ -432,17 +414,17 @@ nsNoAuthURLParser::ParseAfterScheme(cons
                     nsCRT::IsAsciiAlpha(spec[2]) &&
                     ((specLen == 4) || (spec[4] == '/') || (spec[4] == '\\'))) {
                     pos = 1;
                     break;  
                 } 
 #endif
                 // Ignore apparent authority; path is everything after it
                 for (p = spec + 2; p < spec + specLen; ++p) {
-                    if (*p == '/' || *p == '?' || *p == '#' || *p == ';')
+                    if (*p == '/' || *p == '?' || *p == '#')
                         break;
                 }
             }
             SET_RESULT(auth, 0, -1);
             if (p && p != spec+specLen)
                 SET_RESULT(path, p - spec, specLen - (p - spec));
             else
                 SET_RESULT(path, 0, -1);
@@ -662,17 +644,17 @@ nsAuthURLParser::ParseAfterScheme(const 
     NS_PRECONDITION(specLen >= 0, "unexpected");
 
     PRUint32 nslash = CountConsecutiveSlashes(spec, specLen);
 
     // search for the end of the authority section
     const char *end = spec + specLen;
     const char *p;
     for (p = spec + nslash; p < end; ++p) {
-        if (*p == '/' || *p == '?' || *p == '#' || *p == ';')
+        if (*p == '/' || *p == '?' || *p == '#')
             break;
     }
     if (p < end) {
         // spec = [/]<auth><path>
         SET_RESULT(auth, nslash, p - (spec + nslash));
         SET_RESULT(path, p - spec, specLen - (p - spec));
     }
     else {
--- a/netwerk/test/TestURLParser.cpp
+++ b/netwerk/test/TestURLParser.cpp
@@ -65,28 +65,26 @@ parse_file_path(nsIURLParser *urlParser,
     PRINT_SUBFIELD(filepath, ext);
 }
 
 static void
 parse_path(nsIURLParser *urlParser, char *path, PRInt32 pathLen)
 {
     PRINT_FIELD(path);
 
-    PRUint32 filePos, paramPos, queryPos, refPos;
-    PRInt32 fileLen, paramLen, queryLen, refLen;
+    PRUint32 filePos, queryPos, refPos;
+    PRInt32 fileLen, queryLen, refLen;
 
     urlParser->ParsePath(path, pathLen,
                          &filePos, &fileLen,
-                         &paramPos, &paramLen,
                          &queryPos, &queryLen,
                          &refPos, &refLen);
 
     if (fileLen != -1)
         parse_file_path(urlParser, path + filePos, fileLen);
-    PRINT_SUBFIELD(path, param);
     PRINT_SUBFIELD(path, query);
     PRINT_SUBFIELD(path, ref);
 }
 
 int
 main(int argc, char **argv)
 {
     if (test_common_init(&argc, &argv) != 0)
--- a/netwerk/test/unit/test_bug429347.js
+++ b/netwerk/test/unit/test_bug429347.js
@@ -9,28 +9,34 @@ function run_test() {
   var uri1 = ios.newURI("http://example.com#bar", null, null);
   var uri2 = ios.newURI("http://example.com/#bar", null, null);
   do_check_true(uri1.equals(uri2));
 
   uri1.spec = "http://example.com?bar";
   uri2.spec = "http://example.com/?bar";
   do_check_true(uri1.equals(uri2));
 
+  // see https://bugzilla.mozilla.org/show_bug.cgi?id=665706
+  // ";" is not parsed as special anymore and thus ends up
+  // in the authority component (see RFC 3986)
   uri1.spec = "http://example.com;bar";
   uri2.spec = "http://example.com/;bar";
-  do_check_true(uri1.equals(uri2));
+  do_check_false(uri1.equals(uri2));
 
   uri1.spec = "http://example.com#";
   uri2.spec = "http://example.com/#";
   do_check_true(uri1.equals(uri2));
 
   uri1.spec = "http://example.com?";
   uri2.spec = "http://example.com/?";
   do_check_true(uri1.equals(uri2));
 
+  // see https://bugzilla.mozilla.org/show_bug.cgi?id=665706
+  // ";" is not parsed as special anymore and thus ends up
+  // in the authority component (see RFC 3986)
   uri1.spec = "http://example.com;";
   uri2.spec = "http://example.com/;";
-  do_check_true(uri1.equals(uri2));
+  do_check_false(uri1.equals(uri2));
 
   uri1.spec = "http://example.com";
   uri2.spec = "http://example.com/";
   do_check_true(uri1.equals(uri2));
 }
--- a/netwerk/test/urltest.cpp
+++ b/netwerk/test/urltest.cpp
@@ -132,18 +132,19 @@ nsresult writeoutto(const char* i_pURL, 
         output += RESULT();
         output += ',';
         rv = tURL->GetFileBaseName(temp);
         output += RESULT();
         output += ',';
         rv = tURL->GetFileExtension(temp);
         output += RESULT();
         output += ',';
-        rv = tURL->GetParam(temp);
-        output += RESULT();
+        // removed with https://bugzilla.mozilla.org/show_bug.cgi?id=665706
+        // rv = tURL->GetParam(temp); 
+        // output += RESULT();
         output += ',';
         rv = tURL->GetQuery(temp);
         output += RESULT();
         output += ',';
         rv = tURL->GetRef(temp);
         output += RESULT();
         output += ',';
         rv = tURL->GetSpec(temp);
--- a/xpcom/io/nsEscape.cpp
+++ b/xpcom/io/nsEscape.cpp
@@ -348,17 +348,17 @@ nsEscapeHTML2(const PRUnichar *aSourceBu
 //----------------------------------------------------------------------------------------
 
 const int EscapeChars[256] =
 /*      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,   0,1023,1023,1023,1023,1023,1023, 953, 784,       /* 2x   !"#$%&'()*+,-./	 */
-     1023,1023,1023,1023,1023,1023,1023,1023,1023,1023,1008, 912,   0,1008,   0, 768,       /* 3x  0123456789:;<=>?	 */
+     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, 896, 896, 896, 896,1023,       /* 5x  PQRSTUVWXYZ[\]^_	 */
         0,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{|}~	 */
         0    /* 8x  DEL               */
 };
 
 #define NO_NEED_ESC(C) (EscapeChars[((unsigned int) (C))] & (flags))