summaryrefslogtreecommitdiffstats
path: root/netwerk/test/gtest
diff options
context:
space:
mode:
Diffstat (limited to 'netwerk/test/gtest')
-rw-r--r--netwerk/test/gtest/TestBase64Stream.cpp95
-rw-r--r--netwerk/test/gtest/TestBind.cpp176
-rw-r--r--netwerk/test/gtest/TestBufferedInputStream.cpp183
-rw-r--r--netwerk/test/gtest/TestCommon.cpp7
-rw-r--r--netwerk/test/gtest/TestCommon.h44
-rw-r--r--netwerk/test/gtest/TestCookie.cpp1062
-rw-r--r--netwerk/test/gtest/TestHeaders.cpp29
-rw-r--r--netwerk/test/gtest/TestHttpAuthUtils.cpp43
-rw-r--r--netwerk/test/gtest/TestHttpResponseHead.cpp109
-rw-r--r--netwerk/test/gtest/TestInputStreamTransport.cpp190
-rw-r--r--netwerk/test/gtest/TestIsValidIp.cpp178
-rw-r--r--netwerk/test/gtest/TestMIMEInputStream.cpp261
-rw-r--r--netwerk/test/gtest/TestMozURL.cpp390
-rw-r--r--netwerk/test/gtest/TestNamedPipeService.cpp279
-rw-r--r--netwerk/test/gtest/TestNetworkLinkIdHashingDarwin.cpp93
-rw-r--r--netwerk/test/gtest/TestNetworkLinkIdHashingWindows.cpp88
-rw-r--r--netwerk/test/gtest/TestPACMan.cpp242
-rw-r--r--netwerk/test/gtest/TestPartiallySeekableInputStream.cpp494
-rw-r--r--netwerk/test/gtest/TestProtocolProxyService.cpp164
-rw-r--r--netwerk/test/gtest/TestReadStreamToString.cpp190
-rw-r--r--netwerk/test/gtest/TestServerTimingHeader.cpp239
-rw-r--r--netwerk/test/gtest/TestSocketTransportService.cpp140
-rw-r--r--netwerk/test/gtest/TestStandardURL.cpp359
-rw-r--r--netwerk/test/gtest/TestSupportAlpn.cpp61
-rw-r--r--netwerk/test/gtest/TestUDPSocket.cpp395
-rw-r--r--netwerk/test/gtest/TestURIMutator.cpp128
-rw-r--r--netwerk/test/gtest/moz.build84
-rw-r--r--netwerk/test/gtest/parse-ftp/3-guess.in30
-rw-r--r--netwerk/test/gtest/parse-ftp/3-guess.out28
-rw-r--r--netwerk/test/gtest/parse-ftp/C-VMold.in16
-rw-r--r--netwerk/test/gtest/parse-ftp/C-VMold.out12
-rw-r--r--netwerk/test/gtest/parse-ftp/C-zVM.in61
-rw-r--r--netwerk/test/gtest/parse-ftp/C-zVM.out19
-rw-r--r--netwerk/test/gtest/parse-ftp/D-WinNT.in62
-rw-r--r--netwerk/test/gtest/parse-ftp/D-WinNT.out49
-rw-r--r--netwerk/test/gtest/parse-ftp/E-EPLF.in189
-rw-r--r--netwerk/test/gtest/parse-ftp/E-EPLF.out178
-rw-r--r--netwerk/test/gtest/parse-ftp/O-guess.in19
-rw-r--r--netwerk/test/gtest/parse-ftp/O-guess.out13
-rw-r--r--netwerk/test/gtest/parse-ftp/R-dls.in23
-rw-r--r--netwerk/test/gtest/parse-ftp/R-dls.out22
-rw-r--r--netwerk/test/gtest/parse-ftp/README28
-rw-r--r--netwerk/test/gtest/parse-ftp/TestParseFTPList.cpp138
-rw-r--r--netwerk/test/gtest/parse-ftp/U-HellSoft.in25
-rw-r--r--netwerk/test/gtest/parse-ftp/U-HellSoft.out16
-rw-r--r--netwerk/test/gtest/parse-ftp/U-NetPresenz.in31
-rw-r--r--netwerk/test/gtest/parse-ftp/U-NetPresenz.out17
-rw-r--r--netwerk/test/gtest/parse-ftp/U-NetWare.in51
-rw-r--r--netwerk/test/gtest/parse-ftp/U-NetWare.out31
-rw-r--r--netwerk/test/gtest/parse-ftp/U-Novonyx.in92
-rw-r--r--netwerk/test/gtest/parse-ftp/U-Novonyx.out78
-rw-r--r--netwerk/test/gtest/parse-ftp/U-Surge.in66
-rw-r--r--netwerk/test/gtest/parse-ftp/U-Surge.out52
-rw-r--r--netwerk/test/gtest/parse-ftp/U-WarFTPd.in38
-rw-r--r--netwerk/test/gtest/parse-ftp/U-WarFTPd.out22
-rw-r--r--netwerk/test/gtest/parse-ftp/U-WebStar.in41
-rw-r--r--netwerk/test/gtest/parse-ftp/U-WebStar.out21
-rw-r--r--netwerk/test/gtest/parse-ftp/U-WinNT.in68
-rw-r--r--netwerk/test/gtest/parse-ftp/U-WinNT.out54
-rw-r--r--netwerk/test/gtest/parse-ftp/U-hethmon.in42
-rw-r--r--netwerk/test/gtest/parse-ftp/U-hethmon.out30
-rw-r--r--netwerk/test/gtest/parse-ftp/U-murksw.in29
-rw-r--r--netwerk/test/gtest/parse-ftp/U-murksw.out14
-rw-r--r--netwerk/test/gtest/parse-ftp/U-ncFTPd.in1411
-rw-r--r--netwerk/test/gtest/parse-ftp/U-ncFTPd.out1377
-rw-r--r--netwerk/test/gtest/parse-ftp/U-no_ug.in84
-rw-r--r--netwerk/test/gtest/parse-ftp/U-no_ug.out26
-rw-r--r--netwerk/test/gtest/parse-ftp/U-nogid.in82
-rw-r--r--netwerk/test/gtest/parse-ftp/U-nogid.out47
-rw-r--r--netwerk/test/gtest/parse-ftp/U-proftpd.in21
-rw-r--r--netwerk/test/gtest/parse-ftp/U-proftpd.out7
-rw-r--r--netwerk/test/gtest/parse-ftp/U-wu.in71
-rw-r--r--netwerk/test/gtest/parse-ftp/U-wu.out15
-rw-r--r--netwerk/test/gtest/parse-ftp/V-MultiNet.in34
-rw-r--r--netwerk/test/gtest/parse-ftp/V-MultiNet.out14
-rw-r--r--netwerk/test/gtest/parse-ftp/V-VMS-mix.in22
-rw-r--r--netwerk/test/gtest/parse-ftp/V-VMS-mix.out10
-rw-r--r--netwerk/test/gtest/parse-ftp/moz.build68
-rw-r--r--netwerk/test/gtest/urltestdata-orig.json6148
-rw-r--r--netwerk/test/gtest/urltestdata.json6480
80 files changed, 23345 insertions, 0 deletions
diff --git a/netwerk/test/gtest/TestBase64Stream.cpp b/netwerk/test/gtest/TestBase64Stream.cpp
new file mode 100644
index 0000000000..37f5cb824e
--- /dev/null
+++ b/netwerk/test/gtest/TestBase64Stream.cpp
@@ -0,0 +1,95 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* 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/. */
+
+#include "gtest/gtest.h"
+#include "mozilla/Base64.h"
+#include "nsIInputStream.h"
+
+namespace mozilla {
+namespace net {
+
+// An input stream whose ReadSegments method calls aWriter with writes of size
+// aStep from the provided aInput in order to test edge-cases related to small
+// buffers.
+class TestStream final : public nsIInputStream {
+ public:
+ NS_DECL_ISUPPORTS;
+
+ TestStream(const nsACString& aInput, uint32_t aStep)
+ : mInput(aInput), mStep(aStep) {}
+
+ NS_IMETHOD Close() override { MOZ_CRASH("This should not be called"); }
+
+ NS_IMETHOD Available(uint64_t* aLength) override {
+ *aLength = mInput.Length() - mPos;
+ return NS_OK;
+ }
+
+ NS_IMETHOD Read(char* aBuffer, uint32_t aCount,
+ uint32_t* aReadCount) override {
+ MOZ_CRASH("This should not be called");
+ }
+
+ NS_IMETHOD ReadSegments(nsWriteSegmentFun aWriter, void* aClosure,
+ uint32_t aCount, uint32_t* aResult) override {
+ *aResult = 0;
+
+ if (mPos == mInput.Length()) {
+ return NS_OK;
+ }
+
+ while (aCount > 0) {
+ uint32_t amt = std::min(mStep, (uint32_t)(mInput.Length() - mPos));
+
+ uint32_t read = 0;
+ nsresult rv =
+ aWriter(this, aClosure, mInput.get() + mPos, *aResult, amt, &read);
+ if (NS_WARN_IF(NS_FAILED(rv))) {
+ return rv;
+ }
+
+ *aResult += read;
+ aCount -= read;
+ mPos += read;
+ }
+
+ return NS_OK;
+ }
+
+ NS_IMETHOD IsNonBlocking(bool* aNonBlocking) override {
+ *aNonBlocking = true;
+ return NS_OK;
+ }
+
+ private:
+ ~TestStream() = default;
+
+ nsCString mInput;
+ const uint32_t mStep;
+ uint32_t mPos = 0;
+};
+
+NS_IMPL_ISUPPORTS(TestStream, nsIInputStream)
+
+// Test the base64 encoder with writer buffer sizes between 1 byte and the
+// entire length of "Hello World!" in order to exercise various edge cases.
+TEST(TestBase64Stream, Run)
+{
+ nsCString input;
+ input.AssignLiteral("Hello World!");
+
+ for (uint32_t step = 1; step <= input.Length(); ++step) {
+ RefPtr<TestStream> ts = new TestStream(input, step);
+
+ nsAutoString encodedData;
+ nsresult rv = Base64EncodeInputStream(ts, encodedData, input.Length());
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ EXPECT_TRUE(encodedData.EqualsLiteral("SGVsbG8gV29ybGQh"));
+ }
+}
+
+} // namespace net
+} // namespace mozilla
diff --git a/netwerk/test/gtest/TestBind.cpp b/netwerk/test/gtest/TestBind.cpp
new file mode 100644
index 0000000000..e9ee9a7153
--- /dev/null
+++ b/netwerk/test/gtest/TestBind.cpp
@@ -0,0 +1,176 @@
+/* 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/. */
+
+#include "TestCommon.h"
+#include "gtest/gtest.h"
+#include "nsISocketTransportService.h"
+#include "nsISocketTransport.h"
+#include "nsIServerSocket.h"
+#include "nsIAsyncInputStream.h"
+#include "mozilla/net/DNS.h"
+#include "prerror.h"
+#include "nsComponentManagerUtils.h"
+#include "nsServiceManagerUtils.h"
+
+using namespace mozilla::net;
+using namespace mozilla;
+
+class ServerListener : public nsIServerSocketListener {
+ public:
+ NS_DECL_ISUPPORTS
+ NS_DECL_NSISERVERSOCKETLISTENER
+
+ explicit ServerListener(WaitForCondition* waiter);
+
+ // Port that is got from server side will be store here.
+ uint32_t mClientPort;
+ bool mFailed;
+ RefPtr<WaitForCondition> mWaiter;
+
+ private:
+ virtual ~ServerListener();
+};
+
+NS_IMPL_ISUPPORTS(ServerListener, nsIServerSocketListener)
+
+ServerListener::ServerListener(WaitForCondition* waiter)
+ : mClientPort(-1), mFailed(false), mWaiter(waiter) {}
+
+ServerListener::~ServerListener() = default;
+
+NS_IMETHODIMP
+ServerListener::OnSocketAccepted(nsIServerSocket* aServ,
+ nsISocketTransport* aTransport) {
+ // Run on STS thread.
+ NetAddr peerAddr;
+ nsresult rv = aTransport->GetPeerAddr(&peerAddr);
+ if (NS_FAILED(rv)) {
+ mFailed = true;
+ mWaiter->Notify();
+ return NS_OK;
+ }
+ mClientPort = PR_ntohs(peerAddr.inet.port);
+ mWaiter->Notify();
+ return NS_OK;
+}
+
+NS_IMETHODIMP
+ServerListener::OnStopListening(nsIServerSocket* aServ, nsresult aStatus) {
+ return NS_OK;
+}
+
+class ClientInputCallback : public nsIInputStreamCallback {
+ public:
+ NS_DECL_THREADSAFE_ISUPPORTS
+ NS_DECL_NSIINPUTSTREAMCALLBACK
+
+ explicit ClientInputCallback(WaitForCondition* waiter);
+
+ bool mFailed;
+ RefPtr<WaitForCondition> mWaiter;
+
+ private:
+ virtual ~ClientInputCallback();
+};
+
+NS_IMPL_ISUPPORTS(ClientInputCallback, nsIInputStreamCallback)
+
+ClientInputCallback::ClientInputCallback(WaitForCondition* waiter)
+ : mFailed(false), mWaiter(waiter) {}
+
+ClientInputCallback::~ClientInputCallback() = default;
+
+NS_IMETHODIMP
+ClientInputCallback::OnInputStreamReady(nsIAsyncInputStream* aStream) {
+ // Server doesn't send. That means if we are here, we probably have run into
+ // an error.
+ uint64_t avail;
+ nsresult rv = aStream->Available(&avail);
+ if (NS_FAILED(rv)) {
+ mFailed = true;
+ }
+ mWaiter->Notify();
+ return NS_OK;
+}
+
+TEST(TestBind, MainTest)
+{
+ //
+ // Server side.
+ //
+ nsCOMPtr<nsIServerSocket> server =
+ do_CreateInstance("@mozilla.org/network/server-socket;1");
+ ASSERT_TRUE(server);
+
+ nsresult rv = server->Init(-1, true, -1);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ int32_t serverPort;
+ rv = server->GetPort(&serverPort);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ RefPtr<WaitForCondition> waiter = new WaitForCondition();
+
+ // Listening.
+ RefPtr<ServerListener> serverListener = new ServerListener(waiter);
+ rv = server->AsyncListen(serverListener);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ //
+ // Client side
+ //
+ uint32_t bindingPort = 20000;
+ nsCOMPtr<nsISocketTransportService> sts =
+ do_GetService("@mozilla.org/network/socket-transport-service;1", &rv);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ nsCOMPtr<nsIInputStream> inputStream;
+ RefPtr<ClientInputCallback> clientCallback;
+
+ for (int32_t tried = 0; tried < 100; tried++) {
+ nsCOMPtr<nsISocketTransport> client;
+ rv = sts->CreateTransport(nsTArray<nsCString>(), "127.0.0.1"_ns, serverPort,
+ nullptr, getter_AddRefs(client));
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ // Bind to a port. It's possible that we are binding to a port that is
+ // currently in use. If we failed to bind, we try next port.
+ NetAddr bindingAddr;
+ bindingAddr.inet.family = AF_INET;
+ bindingAddr.inet.ip = 0;
+ bindingAddr.inet.port = PR_htons(bindingPort);
+ rv = client->Bind(&bindingAddr);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ // Open IO streams, to make client SocketTransport connect to server.
+ clientCallback = new ClientInputCallback(waiter);
+ rv = client->OpenInputStream(nsITransport::OPEN_UNBUFFERED, 0, 0,
+ getter_AddRefs(inputStream));
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ nsCOMPtr<nsIAsyncInputStream> asyncInputStream =
+ do_QueryInterface(inputStream);
+ rv = asyncInputStream->AsyncWait(clientCallback, 0, 0, nullptr);
+
+ // Wait for server's response or callback of input stream.
+ waiter->Wait(1);
+ if (clientCallback->mFailed) {
+ // if client received error, we likely have bound a port that is in use.
+ // we can try another port.
+ bindingPort++;
+ } else {
+ // We are unlocked by server side, leave the loop and check result.
+ break;
+ }
+ }
+
+ ASSERT_FALSE(serverListener->mFailed);
+ ASSERT_EQ(serverListener->mClientPort, bindingPort);
+
+ inputStream->Close();
+ waiter->Wait(1);
+ ASSERT_TRUE(clientCallback->mFailed);
+
+ server->Close();
+}
diff --git a/netwerk/test/gtest/TestBufferedInputStream.cpp b/netwerk/test/gtest/TestBufferedInputStream.cpp
new file mode 100644
index 0000000000..09527318c5
--- /dev/null
+++ b/netwerk/test/gtest/TestBufferedInputStream.cpp
@@ -0,0 +1,183 @@
+#include "gtest/gtest.h"
+
+#include "mozilla/SpinEventLoopUntil.h"
+#include "nsBufferedStreams.h"
+#include "nsStreamUtils.h"
+#include "nsIThread.h"
+#include "nsThreadUtils.h"
+#include "Helpers.h"
+
+// Helper function for creating a testing::AsyncStringStream
+already_AddRefed<nsBufferedInputStream> CreateStream(uint32_t aSize,
+ nsCString& aBuffer) {
+ aBuffer.SetLength(aSize);
+ for (uint32_t i = 0; i < aSize; ++i) {
+ aBuffer.BeginWriting()[i] = i % 10;
+ }
+
+ nsCOMPtr<nsIInputStream> stream = new testing::AsyncStringStream(aBuffer);
+
+ RefPtr<nsBufferedInputStream> bis = new nsBufferedInputStream();
+ bis->Init(stream, aSize);
+ return bis.forget();
+}
+
+// Simple reading.
+TEST(TestBufferedInputStream, SimpleRead)
+{
+ const size_t kBufSize = 10;
+
+ nsCString buf;
+ RefPtr<nsBufferedInputStream> bis = CreateStream(kBufSize, buf);
+
+ uint64_t length;
+ ASSERT_EQ(NS_OK, bis->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize, length);
+
+ char buf2[kBufSize];
+ uint32_t count;
+ ASSERT_EQ(NS_OK, bis->Read(buf2, sizeof(buf2), &count));
+ ASSERT_EQ(count, buf.Length());
+ ASSERT_TRUE(nsCString(buf.get(), kBufSize).Equals(nsCString(buf2, count)));
+}
+
+// Simple segment reading.
+TEST(TestBufferedInputStream, SimpleReadSegments)
+{
+ const size_t kBufSize = 10;
+
+ nsCString buf;
+ RefPtr<nsBufferedInputStream> bis = CreateStream(kBufSize, buf);
+
+ char buf2[kBufSize];
+ uint32_t count;
+ ASSERT_EQ(NS_OK, bis->ReadSegments(NS_CopySegmentToBuffer, buf2, sizeof(buf2),
+ &count));
+ ASSERT_EQ(count, buf.Length());
+ ASSERT_TRUE(nsCString(buf.get(), kBufSize).Equals(nsCString(buf2, count)));
+}
+
+// AsyncWait - sync
+TEST(TestBufferedInputStream, AsyncWait_sync)
+{
+ const size_t kBufSize = 10;
+
+ nsCString buf;
+ RefPtr<nsBufferedInputStream> bis = CreateStream(kBufSize, buf);
+
+ RefPtr<testing::InputStreamCallback> cb = new testing::InputStreamCallback();
+
+ ASSERT_EQ(NS_OK, bis->AsyncWait(cb, 0, 0, nullptr));
+
+ // Immediatelly called
+ ASSERT_TRUE(cb->Called());
+}
+
+// AsyncWait - async
+TEST(TestBufferedInputStream, AsyncWait_async)
+{
+ const size_t kBufSize = 10;
+
+ nsCString buf;
+ RefPtr<nsBufferedInputStream> bis = CreateStream(kBufSize, buf);
+
+ RefPtr<testing::InputStreamCallback> cb = new testing::InputStreamCallback();
+ nsCOMPtr<nsIThread> thread = do_GetCurrentThread();
+
+ ASSERT_EQ(NS_OK, bis->AsyncWait(cb, 0, 0, thread));
+
+ ASSERT_FALSE(cb->Called());
+
+ // Eventually it is called.
+ MOZ_ALWAYS_TRUE(mozilla::SpinEventLoopUntil([&]() { return cb->Called(); }));
+ ASSERT_TRUE(cb->Called());
+}
+
+// AsyncWait - sync - closureOnly
+TEST(TestBufferedInputStream, AsyncWait_sync_closureOnly)
+{
+ const size_t kBufSize = 10;
+
+ nsCString buf;
+ RefPtr<nsBufferedInputStream> bis = CreateStream(kBufSize, buf);
+
+ RefPtr<testing::InputStreamCallback> cb = new testing::InputStreamCallback();
+
+ ASSERT_EQ(NS_OK, bis->AsyncWait(cb, nsIAsyncInputStream::WAIT_CLOSURE_ONLY, 0,
+ nullptr));
+ ASSERT_FALSE(cb->Called());
+
+ bis->CloseWithStatus(NS_ERROR_FAILURE);
+
+ // Immediatelly called
+ ASSERT_TRUE(cb->Called());
+}
+
+// AsyncWait - async
+TEST(TestBufferedInputStream, AsyncWait_async_closureOnly)
+{
+ const size_t kBufSize = 10;
+
+ nsCString buf;
+ RefPtr<nsBufferedInputStream> bis = CreateStream(kBufSize, buf);
+
+ RefPtr<testing::InputStreamCallback> cb = new testing::InputStreamCallback();
+ nsCOMPtr<nsIThread> thread = do_GetCurrentThread();
+
+ ASSERT_EQ(NS_OK, bis->AsyncWait(cb, nsIAsyncInputStream::WAIT_CLOSURE_ONLY, 0,
+ thread));
+
+ ASSERT_FALSE(cb->Called());
+ bis->CloseWithStatus(NS_ERROR_FAILURE);
+ ASSERT_FALSE(cb->Called());
+
+ // Eventually it is called.
+ MOZ_ALWAYS_TRUE(mozilla::SpinEventLoopUntil([&]() { return cb->Called(); }));
+ ASSERT_TRUE(cb->Called());
+}
+
+TEST(TestBufferedInputStream, AsyncWait_after_close)
+{
+ const size_t kBufSize = 10;
+
+ nsCString buf;
+ RefPtr<nsBufferedInputStream> bis = CreateStream(kBufSize, buf);
+
+ nsCOMPtr<nsIThread> eventTarget = do_GetCurrentThread();
+
+ auto cb = mozilla::MakeRefPtr<testing::InputStreamCallback>();
+ ASSERT_EQ(NS_OK, bis->AsyncWait(cb, 0, 0, eventTarget));
+ MOZ_ALWAYS_TRUE(mozilla::SpinEventLoopUntil([&]() { return cb->Called(); }));
+ ASSERT_TRUE(cb->Called());
+
+ ASSERT_EQ(NS_OK, bis->Close());
+
+ cb = mozilla::MakeRefPtr<testing::InputStreamCallback>();
+ ASSERT_EQ(NS_OK, bis->AsyncWait(cb, 0, 0, eventTarget));
+ MOZ_ALWAYS_TRUE(mozilla::SpinEventLoopUntil([&]() { return cb->Called(); }));
+ ASSERT_TRUE(cb->Called());
+}
+
+TEST(TestBufferedInputStream, AsyncLengthWait_after_close)
+{
+ nsCString buf{"The Quick Brown Fox Jumps over the Lazy Dog"};
+ const size_t kBufSize = 44;
+
+ RefPtr<nsBufferedInputStream> bis = CreateStream(kBufSize, buf);
+
+ nsCOMPtr<nsIThread> eventTarget = do_GetCurrentThread();
+
+ auto cb = mozilla::MakeRefPtr<testing::LengthCallback>();
+ ASSERT_EQ(NS_OK, bis->AsyncLengthWait(cb, eventTarget));
+ MOZ_ALWAYS_TRUE(mozilla::SpinEventLoopUntil([&]() { return cb->Called(); }));
+ ASSERT_TRUE(cb->Called());
+
+ uint64_t length;
+ ASSERT_EQ(NS_OK, bis->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize, length);
+
+ cb = mozilla::MakeRefPtr<testing::LengthCallback>();
+ ASSERT_EQ(NS_OK, bis->AsyncLengthWait(cb, eventTarget));
+ MOZ_ALWAYS_TRUE(mozilla::SpinEventLoopUntil([&]() { return cb->Called(); }));
+ ASSERT_TRUE(cb->Called());
+}
diff --git a/netwerk/test/gtest/TestCommon.cpp b/netwerk/test/gtest/TestCommon.cpp
new file mode 100644
index 0000000000..37c08fbed8
--- /dev/null
+++ b/netwerk/test/gtest/TestCommon.cpp
@@ -0,0 +1,7 @@
+/* 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/. */
+
+#include "TestCommon.h"
+
+NS_IMPL_ISUPPORTS(WaitForCondition, nsIRunnable)
diff --git a/netwerk/test/gtest/TestCommon.h b/netwerk/test/gtest/TestCommon.h
new file mode 100644
index 0000000000..67ff55b1fb
--- /dev/null
+++ b/netwerk/test/gtest/TestCommon.h
@@ -0,0 +1,44 @@
+/* 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/. */
+
+#ifndef TestCommon_h__
+#define TestCommon_h__
+
+#include <stdlib.h>
+#include "nsThreadUtils.h"
+#include "mozilla/Attributes.h"
+#include "mozilla/SpinEventLoopUntil.h"
+
+//-----------------------------------------------------------------------------
+
+class WaitForCondition final : public nsIRunnable {
+ public:
+ NS_DECL_THREADSAFE_ISUPPORTS
+
+ void Wait(int pending) {
+ MOZ_ASSERT(NS_IsMainThread());
+ MOZ_ASSERT(mPending == 0);
+
+ mPending = pending;
+ mozilla::SpinEventLoopUntil([&]() { return !mPending; });
+ NS_ProcessPendingEvents(nullptr);
+ }
+
+ void Notify() { NS_DispatchToMainThread(this); }
+
+ private:
+ virtual ~WaitForCondition() = default;
+
+ NS_IMETHOD Run() override {
+ MOZ_ASSERT(NS_IsMainThread());
+ MOZ_ASSERT(mPending);
+
+ --mPending;
+ return NS_OK;
+ }
+
+ uint32_t mPending = 0;
+};
+
+#endif
diff --git a/netwerk/test/gtest/TestCookie.cpp b/netwerk/test/gtest/TestCookie.cpp
new file mode 100644
index 0000000000..6e6cc9961d
--- /dev/null
+++ b/netwerk/test/gtest/TestCookie.cpp
@@ -0,0 +1,1062 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* 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/. */
+
+#include "TestCommon.h"
+#include "gtest/gtest.h"
+#include "nsContentUtils.h"
+#include "nsICookieService.h"
+#include "nsICookieManager.h"
+#include "nsICookie.h"
+#include <stdio.h>
+#include "plstr.h"
+#include "nsNetUtil.h"
+#include "nsIChannel.h"
+#include "nsIPrincipal.h"
+#include "nsIScriptSecurityManager.h"
+#include "nsServiceManagerUtils.h"
+#include "nsNetCID.h"
+#include "nsIPrefBranch.h"
+#include "nsIPrefService.h"
+#include "mozilla/dom/Document.h"
+#include "mozilla/Preferences.h"
+#include "mozilla/Unused.h"
+#include "mozilla/net/CookieJarSettings.h"
+#include "Cookie.h"
+#include "nsIURI.h"
+
+using mozilla::Unused;
+
+static NS_DEFINE_CID(kCookieServiceCID, NS_COOKIESERVICE_CID);
+static NS_DEFINE_CID(kPrefServiceCID, NS_PREFSERVICE_CID);
+
+// various pref strings
+static const char kCookiesPermissions[] = "network.cookie.cookieBehavior";
+static const char kPrefCookieQuotaPerHost[] = "network.cookie.quotaPerHost";
+static const char kCookiesMaxPerHost[] = "network.cookie.maxPerHost";
+
+#define OFFSET_ONE_WEEK int64_t(604800) * PR_USEC_PER_SEC
+#define OFFSET_ONE_DAY int64_t(86400) * PR_USEC_PER_SEC
+
+// Set server time or expiry time
+void SetTime(PRTime offsetTime, nsAutoCString& serverString,
+ nsAutoCString& cookieString, bool expiry) {
+ char timeStringPreset[40];
+ PRTime CurrentTime = PR_Now();
+ PRTime SetCookieTime = CurrentTime + offsetTime;
+ PRTime SetExpiryTime;
+ if (expiry) {
+ SetExpiryTime = SetCookieTime - OFFSET_ONE_DAY;
+ } else {
+ SetExpiryTime = SetCookieTime + OFFSET_ONE_DAY;
+ }
+
+ // Set server time string
+ PRExplodedTime explodedTime;
+ PR_ExplodeTime(SetCookieTime, PR_GMTParameters, &explodedTime);
+ PR_FormatTimeUSEnglish(timeStringPreset, 40, "%c GMT", &explodedTime);
+ serverString.Assign(timeStringPreset);
+
+ // Set cookie string
+ PR_ExplodeTime(SetExpiryTime, PR_GMTParameters, &explodedTime);
+ PR_FormatTimeUSEnglish(timeStringPreset, 40, "%c GMT", &explodedTime);
+ cookieString.ReplaceLiteral(
+ 0, strlen("test=expiry; expires=") + strlen(timeStringPreset) + 1,
+ "test=expiry; expires=");
+ cookieString.Append(timeStringPreset);
+}
+
+void SetACookieInternal(nsICookieService* aCookieService, const char* aSpec,
+ const char* aCookieString, bool aAllowed) {
+ nsCOMPtr<nsIURI> uri;
+ NS_NewURI(getter_AddRefs(uri), aSpec);
+
+ // We create a dummy channel using the aSpec to simulate same-siteness
+ nsresult rv0;
+ nsCOMPtr<nsIScriptSecurityManager> ssm =
+ do_GetService(NS_SCRIPTSECURITYMANAGER_CONTRACTID, &rv0);
+ ASSERT_TRUE(NS_SUCCEEDED(rv0));
+ nsCOMPtr<nsIPrincipal> specPrincipal;
+ nsCString tmpString(aSpec);
+ ssm->CreateContentPrincipalFromOrigin(tmpString,
+ getter_AddRefs(specPrincipal));
+
+ nsCOMPtr<nsIChannel> dummyChannel;
+ NS_NewChannel(getter_AddRefs(dummyChannel), uri, specPrincipal,
+ nsILoadInfo::SEC_ONLY_FOR_EXPLICIT_CONTENTSEC_CHECK,
+ nsIContentPolicy::TYPE_OTHER);
+
+ nsCOMPtr<nsICookieJarSettings> cookieJarSettings =
+ aAllowed ? CookieJarSettings::Create()
+ : CookieJarSettings::GetBlockingAll();
+ MOZ_ASSERT(cookieJarSettings);
+
+ nsCOMPtr<nsILoadInfo> loadInfo = dummyChannel->LoadInfo();
+ loadInfo->SetCookieJarSettings(cookieJarSettings);
+
+ nsresult rv = aCookieService->SetCookieStringFromHttp(
+ uri, nsDependentCString(aCookieString), dummyChannel);
+ EXPECT_TRUE(NS_SUCCEEDED(rv));
+}
+
+void SetACookieJarBlocked(nsICookieService* aCookieService, const char* aSpec,
+ const char* aCookieString) {
+ SetACookieInternal(aCookieService, aSpec, aCookieString, false);
+}
+
+void SetACookie(nsICookieService* aCookieService, const char* aSpec,
+ const char* aCookieString) {
+ SetACookieInternal(aCookieService, aSpec, aCookieString, true);
+}
+
+// The cookie string is returned via aCookie.
+void GetACookie(nsICookieService* aCookieService, const char* aSpec,
+ nsACString& aCookie) {
+ nsCOMPtr<nsIURI> uri;
+ NS_NewURI(getter_AddRefs(uri), aSpec);
+
+ nsCOMPtr<nsIIOService> service = do_GetIOService();
+
+ nsCOMPtr<nsIChannel> channel;
+ Unused << service->NewChannelFromURI(
+ uri, nullptr, nsContentUtils::GetSystemPrincipal(),
+ nsContentUtils::GetSystemPrincipal(), 0, nsIContentPolicy::TYPE_DOCUMENT,
+ getter_AddRefs(channel));
+
+ Unused << aCookieService->GetCookieStringFromHttp(uri, channel, aCookie);
+}
+
+// The cookie string is returned via aCookie.
+void GetACookieNoHttp(nsICookieService* aCookieService, const char* aSpec,
+ nsACString& aCookie) {
+ nsCOMPtr<nsIURI> uri;
+ NS_NewURI(getter_AddRefs(uri), aSpec);
+
+ RefPtr<BasePrincipal> principal =
+ BasePrincipal::CreateContentPrincipal(uri, OriginAttributes());
+ MOZ_ASSERT(principal);
+
+ nsCOMPtr<mozilla::dom::Document> document;
+ nsresult rv = NS_NewDOMDocument(getter_AddRefs(document),
+ u""_ns, // aNamespaceURI
+ u""_ns, // aQualifiedName
+ nullptr, // aDoctype
+ uri, uri, principal,
+ false, // aLoadedAsData
+ nullptr, // aEventObject
+ DocumentFlavorHTML);
+ Unused << NS_WARN_IF(NS_FAILED(rv));
+
+ Unused << aCookieService->GetCookieStringFromDocument(document, aCookie);
+}
+
+// some #defines for comparison rules
+#define MUST_BE_NULL 0
+#define MUST_EQUAL 1
+#define MUST_CONTAIN 2
+#define MUST_NOT_CONTAIN 3
+#define MUST_NOT_EQUAL 4
+
+// a simple helper function to improve readability:
+// takes one of the #defined rules above, and performs the appropriate test.
+// true means the test passed; false means the test failed.
+static inline bool CheckResult(const char* aLhs, uint32_t aRule,
+ const char* aRhs = nullptr) {
+ switch (aRule) {
+ case MUST_BE_NULL:
+ return !aLhs || !*aLhs;
+
+ case MUST_EQUAL:
+ return !PL_strcmp(aLhs, aRhs);
+
+ case MUST_NOT_EQUAL:
+ return PL_strcmp(aLhs, aRhs);
+
+ case MUST_CONTAIN:
+ return PL_strstr(aLhs, aRhs) != nullptr;
+
+ case MUST_NOT_CONTAIN:
+ return PL_strstr(aLhs, aRhs) == nullptr;
+
+ default:
+ return false; // failure
+ }
+}
+
+void InitPrefs(nsIPrefBranch* aPrefBranch) {
+ // init some relevant prefs, so the tests don't go awry.
+ // we use the most restrictive set of prefs we can;
+ // however, we don't test third party blocking here.
+ aPrefBranch->SetIntPref(kCookiesPermissions, 0); // accept all
+ // Set quotaPerHost to maxPerHost - 1, so there is only one cookie
+ // will be evicted everytime.
+ aPrefBranch->SetIntPref(kPrefCookieQuotaPerHost, 49);
+ // Set the base domain limit to 50 so we have a known value.
+ aPrefBranch->SetIntPref(kCookiesMaxPerHost, 50);
+
+ // SameSite=None by default. We have other tests for lax-by-default.
+ // XXX: Bug 1617611 - Fix all the tests broken by "cookies SameSite=Lax by
+ // default"
+ Preferences::SetBool("network.cookie.sameSite.laxByDefault", false);
+ Preferences::SetBool("network.cookieJarSettings.unblocked_for_testing", true);
+ Preferences::SetBool("dom.securecontext.whitelist_onions", false);
+ Preferences::SetBool("network.cookie.sameSite.schemeful", false);
+}
+
+TEST(TestCookie, TestCookieMain)
+{
+ nsresult rv0;
+
+ nsCOMPtr<nsICookieService> cookieService =
+ do_GetService(kCookieServiceCID, &rv0);
+ ASSERT_TRUE(NS_SUCCEEDED(rv0));
+
+ nsCOMPtr<nsIPrefBranch> prefBranch = do_GetService(kPrefServiceCID, &rv0);
+ ASSERT_TRUE(NS_SUCCEEDED(rv0));
+
+ InitPrefs(prefBranch);
+
+ nsCString cookie;
+
+ /* The basic idea behind these tests is the following:
+ *
+ * we set() some cookie, then try to get() it in various ways. we have
+ * several possible tests we perform on the cookie string returned from
+ * get():
+ *
+ * a) check whether the returned string is null (i.e. we got no cookies
+ * back). this is used e.g. to ensure a given cookie was deleted
+ * correctly, or to ensure a certain cookie wasn't returned to a given
+ * host.
+ * b) check whether the returned string exactly matches a given string.
+ * this is used where we want to make sure our cookie service adheres to
+ * some strict spec (e.g. ordering of multiple cookies), or where we
+ * just know exactly what the returned string should be.
+ * c) check whether the returned string contains/does not contain a given
+ * string. this is used where we don't know/don't care about the
+ * ordering of multiple cookies - we just want to make sure the cookie
+ * string contains them all, in some order.
+ *
+ * NOTE: this testsuite is not yet comprehensive or complete, and is
+ * somewhat contrived - still under development, and needs improving!
+ */
+
+ // test some basic variations of the domain & path
+ SetACookie(cookieService, "http://www.basic.com", "test=basic");
+ GetACookie(cookieService, "http://www.basic.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=basic"));
+ GetACookie(cookieService, "http://www.basic.com/testPath/testfile.txt",
+ cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=basic"));
+ GetACookie(cookieService, "http://www.basic.com./", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ GetACookie(cookieService, "http://www.basic.com.", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ GetACookie(cookieService, "http://www.basic.com./testPath/testfile.txt",
+ cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ GetACookie(cookieService, "http://www.basic2.com/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "http://www.basic.com", "test=basic; max-age=-1");
+ GetACookie(cookieService, "http://www.basic.com/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // *** domain tests
+
+ // test some variations of the domain & path, for different domains of
+ // a domain cookie
+ SetACookie(cookieService, "http://www.domain.com",
+ "test=domain; domain=domain.com");
+ GetACookie(cookieService, "http://domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=domain"));
+ GetACookie(cookieService, "http://domain.com.", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ GetACookie(cookieService, "http://www.domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=domain"));
+ GetACookie(cookieService, "http://foo.domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=domain"));
+ SetACookie(cookieService, "http://www.domain.com",
+ "test=domain; domain=domain.com; max-age=-1");
+ GetACookie(cookieService, "http://domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://www.domain.com",
+ "test=domain; domain=.domain.com");
+ GetACookie(cookieService, "http://domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=domain"));
+ GetACookie(cookieService, "http://www.domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=domain"));
+ GetACookie(cookieService, "http://bah.domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=domain"));
+ SetACookie(cookieService, "http://www.domain.com",
+ "test=domain; domain=.domain.com; max-age=-1");
+ GetACookie(cookieService, "http://domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://www.domain.com",
+ "test=domain; domain=.foo.domain.com");
+ GetACookie(cookieService, "http://foo.domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://www.domain.com",
+ "test=domain; domain=moose.com");
+ GetACookie(cookieService, "http://foo.domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://www.domain.com",
+ "test=domain; domain=domain.com.");
+ GetACookie(cookieService, "http://foo.domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://www.domain.com",
+ "test=domain; domain=..domain.com");
+ GetACookie(cookieService, "http://foo.domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://www.domain.com",
+ "test=domain; domain=..domain.com.");
+ GetACookie(cookieService, "http://foo.domain.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://path.net/path/file",
+ R"(test=taco; path="/bogus")");
+ GetACookie(cookieService, "http://path.net/path/file", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=taco"));
+ SetACookie(cookieService, "http://path.net/path/file",
+ "test=taco; max-age=-1");
+ GetACookie(cookieService, "http://path.net/path/file", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // *** path tests
+
+ // test some variations of the domain & path, for different paths of
+ // a path cookie
+ SetACookie(cookieService, "http://path.net/path/file",
+ "test=path; path=/path");
+ GetACookie(cookieService, "http://path.net/path", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=path"));
+ GetACookie(cookieService, "http://path.net/path/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=path"));
+ GetACookie(cookieService, "http://path.net/path/hithere.foo", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=path"));
+ GetACookie(cookieService, "http://path.net/path?hithere/foo", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=path"));
+ GetACookie(cookieService, "http://path.net/path2", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ GetACookie(cookieService, "http://path.net/path2/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "http://path.net/path/file",
+ "test=path; path=/path; max-age=-1");
+ GetACookie(cookieService, "http://path.net/path/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://path.net/path/file",
+ "test=path; path=/path/");
+ GetACookie(cookieService, "http://path.net/path", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ GetACookie(cookieService, "http://path.net/path/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=path"));
+ SetACookie(cookieService, "http://path.net/path/file",
+ "test=path; path=/path/; max-age=-1");
+ GetACookie(cookieService, "http://path.net/path/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // note that a site can set a cookie for a path it's not on.
+ // this is an intentional deviation from spec (see comments in
+ // CookieService::CheckPath()), so we test this functionality too
+ SetACookie(cookieService, "http://path.net/path/file",
+ "test=path; path=/foo/");
+ GetACookie(cookieService, "http://path.net/path", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ GetACookie(cookieService, "http://path.net/foo", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "http://path.net/path/file",
+ "test=path; path=/foo/; max-age=-1");
+ GetACookie(cookieService, "http://path.net/foo/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // bug 373228: make sure cookies with paths longer than 1024 bytes,
+ // and cookies with paths or names containing tabs, are rejected.
+ // the following cookie has a path > 1024 bytes explicitly specified in the
+ // cookie
+ SetACookie(
+ cookieService, "http://path.net/",
+ "test=path; "
+ "path=/"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "901234567890123456789012345678901234567890123456789012345678901234567890"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "901234567890123456789012345678901234567890123456789012345678901234567890"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "9012345678901234567890/");
+ GetACookie(
+ cookieService,
+ "http://path.net/"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "901234567890123456789012345678901234567890123456789012345678901234567890"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "901234567890123456789012345678901234567890123456789012345678901234567890"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "9012345678901234567890",
+ cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ // the following cookie has a path > 1024 bytes implicitly specified by the
+ // uri path
+ SetACookie(
+ cookieService,
+ "http://path.net/"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "901234567890123456789012345678901234567890123456789012345678901234567890"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "901234567890123456789012345678901234567890123456789012345678901234567890"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "9012345678901234567890/",
+ "test=path");
+ GetACookie(
+ cookieService,
+ "http://path.net/"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "901234567890123456789012345678901234567890123456789012345678901234567890"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "901234567890123456789012345678901234567890123456789012345678901234567890"
+ "123456789012345678901234567890123456789012345678901234567890123456789012"
+ "345678901234567890123456789012345678901234567890123456789012345678901234"
+ "567890123456789012345678901234567890123456789012345678901234567890123456"
+ "789012345678901234567890123456789012345678901234567890123456789012345678"
+ "9012345678901234567890/",
+ cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ // the following cookie includes a tab in the path
+ SetACookie(cookieService, "http://path.net/", "test=path; path=/foo\tbar/");
+ GetACookie(cookieService, "http://path.net/foo\tbar/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ // the following cookie includes a tab in the name
+ SetACookie(cookieService, "http://path.net/", "test\ttabs=tab");
+ GetACookie(cookieService, "http://path.net/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ // the following cookie includes a tab in the value - allowed
+ SetACookie(cookieService, "http://path.net/", "test=tab\ttest");
+ GetACookie(cookieService, "http://path.net/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=tab\ttest"));
+ SetACookie(cookieService, "http://path.net/", "test=tab\ttest; max-age=-1");
+ GetACookie(cookieService, "http://path.net/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // *** expiry & deletion tests
+ // XXX add server time str parsing tests here
+
+ // test some variations of the expiry time,
+ // and test deletion of previously set cookies
+ SetACookie(cookieService, "http://expireme.org/", "test=expiry; max-age=-1");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "http://expireme.org/", "test=expiry; max-age=0");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "http://expireme.org/", "test=expiry; expires=bad");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=expiry"));
+ SetACookie(cookieService, "http://expireme.org/",
+ "test=expiry; expires=Thu, 10 Apr 1980 16:33:12 GMT");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "http://expireme.org/",
+ R"(test=expiry; expires="Thu, 10 Apr 1980 16:33:12 GMT)");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "http://expireme.org/",
+ R"(test=expiry; expires="Thu, 10 Apr 1980 16:33:12 GMT")");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://expireme.org/", "test=expiry; max-age=60");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=expiry"));
+ SetACookie(cookieService, "http://expireme.org/", "test=expiry; max-age=-20");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "http://expireme.org/", "test=expiry; max-age=60");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=expiry"));
+ SetACookie(cookieService, "http://expireme.org/",
+ "test=expiry; expires=Thu, 10 Apr 1980 16:33:12 GMT");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "http://expireme.org/", "test=expiry; max-age=60");
+ SetACookie(cookieService, "http://expireme.org/",
+ "newtest=expiry; max-age=60");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "test=expiry"));
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "newtest=expiry"));
+ SetACookie(cookieService, "http://expireme.org/",
+ "test=differentvalue; max-age=0");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "newtest=expiry"));
+ SetACookie(cookieService, "http://expireme.org/",
+ "newtest=evendifferentvalue; max-age=0");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://foo.expireme.org/",
+ "test=expiry; domain=.expireme.org; max-age=60");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=expiry"));
+ SetACookie(cookieService, "http://bar.expireme.org/",
+ "test=differentvalue; domain=.expireme.org; max-age=0");
+ GetACookie(cookieService, "http://expireme.org/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ nsAutoCString ServerTime;
+ nsAutoCString CookieString;
+
+ // *** multiple cookie tests
+
+ // test the setting of multiple cookies, and test the order of precedence
+ // (a later cookie overwriting an earlier one, in the same header string)
+ SetACookie(cookieService, "http://multiple.cookies/",
+ "test=multiple; domain=.multiple.cookies \n test=different \n "
+ "test=same; domain=.multiple.cookies \n newtest=ciao \n "
+ "newtest=foo; max-age=-6 \n newtest=reincarnated");
+ GetACookie(cookieService, "http://multiple.cookies/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_NOT_CONTAIN, "test=multiple"));
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "test=different"));
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "test=same"));
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_NOT_CONTAIN, "newtest=ciao"));
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_NOT_CONTAIN, "newtest=foo"));
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "newtest=reincarnated"));
+ SetACookie(cookieService, "http://multiple.cookies/",
+ "test=expiry; domain=.multiple.cookies; max-age=0");
+ GetACookie(cookieService, "http://multiple.cookies/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_NOT_CONTAIN, "test=same"));
+ SetACookie(cookieService, "http://multiple.cookies/",
+ "\n test=different; max-age=0 \n");
+ GetACookie(cookieService, "http://multiple.cookies/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_NOT_CONTAIN, "test=different"));
+ SetACookie(cookieService, "http://multiple.cookies/",
+ "newtest=dead; max-age=0");
+ GetACookie(cookieService, "http://multiple.cookies/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // *** parser tests
+
+ // test the cookie header parser, under various circumstances.
+ SetACookie(cookieService, "http://parser.test/",
+ "test=parser; domain=.parser.test; ;; ;=; ,,, ===,abc,=; "
+ "abracadabra! max-age=20;=;;");
+ GetACookie(cookieService, "http://parser.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=parser"));
+ SetACookie(cookieService, "http://parser.test/",
+ "test=parser; domain=.parser.test; max-age=0");
+ GetACookie(cookieService, "http://parser.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "http://parser.test/",
+ "test=\"fubar! = foo;bar\\\";\" parser; domain=.parser.test; "
+ "max-age=6\nfive; max-age=2.63,");
+ GetACookie(cookieService, "http://parser.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, R"(test="fubar! = foo)"));
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "five"));
+ SetACookie(cookieService, "http://parser.test/",
+ "test=kill; domain=.parser.test; max-age=0 \n five; max-age=0");
+ GetACookie(cookieService, "http://parser.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // test the handling of VALUE-only cookies (see bug 169091),
+ // i.e. "six" should assume an empty NAME, which allows other VALUE-only
+ // cookies to overwrite it
+ SetACookie(cookieService, "http://parser.test/", "six");
+ GetACookie(cookieService, "http://parser.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "six"));
+ SetACookie(cookieService, "http://parser.test/", "seven");
+ GetACookie(cookieService, "http://parser.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "seven"));
+ SetACookie(cookieService, "http://parser.test/", " =eight");
+ GetACookie(cookieService, "http://parser.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "eight"));
+ SetACookie(cookieService, "http://parser.test/", "test=six");
+ GetACookie(cookieService, "http://parser.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "test=six"));
+
+ // *** path ordering tests
+
+ // test that cookies are returned in path order - longest to shortest.
+ // if the header doesn't specify a path, it's taken from the host URI.
+ SetACookie(cookieService, "http://multi.path.tests/",
+ "test1=path; path=/one/two/three");
+ SetACookie(cookieService, "http://multi.path.tests/",
+ "test2=path; path=/one \n test3=path; path=/one/two/three/four \n "
+ "test4=path; path=/one/two \n test5=path; path=/one/two/");
+ SetACookie(cookieService, "http://multi.path.tests/one/two/three/four/five/",
+ "test6=path");
+ SetACookie(cookieService,
+ "http://multi.path.tests/one/two/three/four/five/six/",
+ "test7=path; path=");
+ SetACookie(cookieService, "http://multi.path.tests/", "test8=path; path=/");
+ GetACookie(cookieService,
+ "http://multi.path.tests/one/two/three/four/five/six/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL,
+ "test7=path; test6=path; test3=path; test1=path; "
+ "test5=path; test4=path; test2=path; test8=path"));
+
+ // *** Cookie prefix tests
+
+ // prefixed cookies can't be set from insecure HTTP
+ SetACookie(cookieService, "http://prefixed.test/", "__Secure-test1=test");
+ SetACookie(cookieService, "http://prefixed.test/",
+ "__Secure-test2=test; secure");
+ SetACookie(cookieService, "http://prefixed.test/", "__Host-test1=test");
+ SetACookie(cookieService, "http://prefixed.test/",
+ "__Host-test2=test; secure");
+ GetACookie(cookieService, "http://prefixed.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // prefixed cookies won't be set without the secure flag
+ SetACookie(cookieService, "https://prefixed.test/", "__Secure-test=test");
+ SetACookie(cookieService, "https://prefixed.test/", "__Host-test=test");
+ GetACookie(cookieService, "https://prefixed.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // prefixed cookies can be set when done correctly
+ SetACookie(cookieService, "https://prefixed.test/",
+ "__Secure-test=test; secure");
+ SetACookie(cookieService, "https://prefixed.test/",
+ "__Host-test=test; secure");
+ GetACookie(cookieService, "https://prefixed.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "__Secure-test=test"));
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "__Host-test=test"));
+
+ // but when set must not be returned to the host insecurely
+ GetACookie(cookieService, "http://prefixed.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // Host-prefixed cookies cannot specify a domain
+ SetACookie(cookieService, "https://host.prefixed.test/",
+ "__Host-a=test; secure; domain=prefixed.test");
+ SetACookie(cookieService, "https://host.prefixed.test/",
+ "__Host-b=test; secure; domain=.prefixed.test");
+ SetACookie(cookieService, "https://host.prefixed.test/",
+ "__Host-c=test; secure; domain=host.prefixed.test");
+ SetACookie(cookieService, "https://host.prefixed.test/",
+ "__Host-d=test; secure; domain=.host.prefixed.test");
+ GetACookie(cookieService, "https://host.prefixed.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // Host-prefixed cookies can only have a path of "/"
+ SetACookie(cookieService, "https://host.prefixed.test/some/path",
+ "__Host-e=test; secure");
+ SetACookie(cookieService, "https://host.prefixed.test/some/path",
+ "__Host-f=test; secure; path=/");
+ SetACookie(cookieService, "https://host.prefixed.test/some/path",
+ "__Host-g=test; secure; path=/some");
+ GetACookie(cookieService, "https://host.prefixed.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "__Host-f=test"));
+
+ // *** leave-secure-alone tests
+
+ // testing items 0 & 1 for 3.1 of spec Deprecate modification of ’secure’
+ // cookies from non-secure origins
+ SetACookie(cookieService, "http://www.security.test/",
+ "test=non-security; secure");
+ GetACookieNoHttp(cookieService, "https://www.security.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+ SetACookie(cookieService, "https://www.security.test/path/",
+ "test=security; secure; path=/path/");
+ GetACookieNoHttp(cookieService, "https://www.security.test/path/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=security"));
+ // testing items 2 & 3 & 4 for 3.2 of spec Deprecate modification of ’secure’
+ // cookies from non-secure origins
+ // Secure site can modify cookie value
+ SetACookie(cookieService, "https://www.security.test/path/",
+ "test=security2; secure; path=/path/");
+ GetACookieNoHttp(cookieService, "https://www.security.test/path/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=security2"));
+ // If new cookie contains same name, same host and partially matching path
+ // with an existing security cookie on non-security site, it can't modify an
+ // existing security cookie.
+ SetACookie(cookieService, "http://www.security.test/path/foo/",
+ "test=non-security; path=/path/foo");
+ GetACookieNoHttp(cookieService, "https://www.security.test/path/foo/",
+ cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=security2"));
+ // Non-secure cookie can set by same name, same host and non-matching path.
+ SetACookie(cookieService, "http://www.security.test/bar/",
+ "test=non-security; path=/bar");
+ GetACookieNoHttp(cookieService, "http://www.security.test/bar/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=non-security"));
+ // Modify value and downgrade secure level.
+ SetACookie(
+ cookieService, "https://www.security.test/",
+ "test_modify_cookie=security-cookie; secure; domain=.security.test");
+ GetACookieNoHttp(cookieService, "https://www.security.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL,
+ "test_modify_cookie=security-cookie"));
+ SetACookie(cookieService, "https://www.security.test/",
+ "test_modify_cookie=non-security-cookie; domain=.security.test");
+ GetACookieNoHttp(cookieService, "https://www.security.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL,
+ "test_modify_cookie=non-security-cookie"));
+
+ // Test the non-security cookie can set when domain or path not same to secure
+ // cookie of same name.
+ SetACookie(cookieService, "https://www.security.test/", "test=security3");
+ GetACookieNoHttp(cookieService, "http://www.security.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "test=security3"));
+ SetACookie(cookieService, "http://www.security.test/",
+ "test=non-security2; domain=security.test");
+ GetACookieNoHttp(cookieService, "http://www.security.test/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "test=non-security2"));
+
+ Preferences::SetBool("network.cookie.sameSite.schemeful", true);
+ GetACookieNoHttp(cookieService, "http://www.security.test/", cookie);
+ EXPECT_FALSE(CheckResult(cookie.get(), MUST_CONTAIN, "test=security3"));
+ Preferences::SetBool("network.cookie.sameSite.schemeful", false);
+
+ // *** nsICookieManager interface tests
+ nsCOMPtr<nsICookieManager> cookieMgr =
+ do_GetService(NS_COOKIEMANAGER_CONTRACTID, &rv0);
+ ASSERT_TRUE(NS_SUCCEEDED(rv0));
+
+ nsCOMPtr<nsICookieManager> cookieMgr2 = cookieMgr;
+ ASSERT_TRUE(cookieMgr2);
+
+ mozilla::OriginAttributes attrs;
+
+ // first, ensure a clean slate
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->RemoveAll()));
+ // add some cookies
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr2->AddNative("cookiemgr.test"_ns, // domain
+ "/foo"_ns, // path
+ "test1"_ns, // name
+ "yes"_ns, // value
+ false, // is secure
+ false, // is httponly
+ true, // is session
+ INT64_MAX, // expiry time
+ &attrs, // originAttributes
+ nsICookie::SAMESITE_NONE,
+ nsICookie::SCHEME_HTTPS)));
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr2->AddNative(
+ "cookiemgr.test"_ns, // domain
+ "/foo"_ns, // path
+ "test2"_ns, // name
+ "yes"_ns, // value
+ false, // is secure
+ true, // is httponly
+ true, // is session
+ PR_Now() / PR_USEC_PER_SEC + 2, // expiry time
+ &attrs, // originAttributes
+ nsICookie::SAMESITE_NONE, nsICookie::SCHEME_HTTPS)));
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr2->AddNative("new.domain"_ns, // domain
+ "/rabbit"_ns, // path
+ "test3"_ns, // name
+ "yes"_ns, // value
+ false, // is secure
+ false, // is httponly
+ true, // is session
+ INT64_MAX, // expiry time
+ &attrs, // originAttributes
+ nsICookie::SAMESITE_NONE,
+ nsICookie::SCHEME_HTTPS)));
+ // confirm using enumerator
+ nsTArray<RefPtr<nsICookie>> cookies;
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->GetCookies(cookies)));
+ nsCOMPtr<nsICookie> expiredCookie, newDomainCookie;
+ for (const auto& cookie : cookies) {
+ nsAutoCString name;
+ cookie->GetName(name);
+ if (name.EqualsLiteral("test2"))
+ expiredCookie = cookie;
+ else if (name.EqualsLiteral("test3"))
+ newDomainCookie = cookie;
+ }
+ EXPECT_EQ(cookies.Length(), 3ul);
+ // check the httpOnly attribute of the second cookie is honored
+ GetACookie(cookieService, "http://cookiemgr.test/foo/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_CONTAIN, "test2=yes"));
+ GetACookieNoHttp(cookieService, "http://cookiemgr.test/foo/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_NOT_CONTAIN, "test2=yes"));
+ // check CountCookiesFromHost()
+ uint32_t hostCookies = 0;
+ EXPECT_TRUE(NS_SUCCEEDED(
+ cookieMgr2->CountCookiesFromHost("cookiemgr.test"_ns, &hostCookies)));
+ EXPECT_EQ(hostCookies, 2u);
+ // check CookieExistsNative() using the third cookie
+ bool found;
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr2->CookieExistsNative(
+ "new.domain"_ns, "/rabbit"_ns, "test3"_ns, &attrs, &found)));
+ EXPECT_TRUE(found);
+
+ // sleep four seconds, to make sure the second cookie has expired
+ PR_Sleep(4 * PR_TicksPerSecond());
+ // check that both CountCookiesFromHost() and CookieExistsNative() count the
+ // expired cookie
+ EXPECT_TRUE(NS_SUCCEEDED(
+ cookieMgr2->CountCookiesFromHost("cookiemgr.test"_ns, &hostCookies)));
+ EXPECT_EQ(hostCookies, 2u);
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr2->CookieExistsNative(
+ "cookiemgr.test"_ns, "/foo"_ns, "test2"_ns, &attrs, &found)));
+ EXPECT_TRUE(found);
+ // double-check RemoveAll() using the enumerator
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->RemoveAll()));
+ cookies.SetLength(0);
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->GetCookies(cookies)) &&
+ cookies.IsEmpty());
+
+ // *** eviction and creation ordering tests
+
+ // test that cookies are
+ // a) returned by order of creation time (oldest first, newest last)
+ // b) evicted by order of lastAccessed time, if the limit on cookies per host
+ // (50) is reached
+ nsAutoCString name;
+ nsAutoCString expected;
+ for (int32_t i = 0; i < 60; ++i) {
+ name = "test"_ns;
+ name.AppendInt(i);
+ name += "=creation"_ns;
+ SetACookie(cookieService, "http://creation.ordering.tests/", name.get());
+
+ if (i >= 10) {
+ expected += name;
+ if (i < 59) expected += "; "_ns;
+ }
+ }
+ GetACookie(cookieService, "http://creation.ordering.tests/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, expected.get()));
+
+ cookieMgr->RemoveAll();
+
+ for (int32_t i = 0; i < 60; ++i) {
+ name = "test"_ns;
+ name.AppendInt(i);
+ name += "=delete_non_security"_ns;
+
+ // Create 50 cookies that include the secure flag.
+ if (i < 50) {
+ name += "; secure"_ns;
+ SetACookie(cookieService, "https://creation.ordering.tests/", name.get());
+ } else {
+ // non-security cookies will be removed beside the latest cookie that be
+ // created.
+ SetACookie(cookieService, "http://creation.ordering.tests/", name.get());
+ }
+ }
+ GetACookie(cookieService, "http://creation.ordering.tests/", cookie);
+
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ // *** SameSite attribute - parsing and cookie storage tests
+ // Clear the cookies
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->RemoveAll()));
+
+ // None of these cookies will be set because using
+ // CookieJarSettings::GetBlockingAll().
+ SetACookieJarBlocked(cookieService, "http://samesite.test", "unset=yes");
+ SetACookieJarBlocked(cookieService, "http://samesite.test",
+ "unspecified=yes; samesite");
+ SetACookieJarBlocked(cookieService, "http://samesite.test",
+ "empty=yes; samesite=");
+ SetACookieJarBlocked(cookieService, "http://samesite.test",
+ "bogus=yes; samesite=bogus");
+ SetACookieJarBlocked(cookieService, "http://samesite.test",
+ "strict=yes; samesite=strict");
+ SetACookieJarBlocked(cookieService, "http://samesite.test",
+ "lax=yes; samesite=lax");
+
+ cookies.SetLength(0);
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->GetCookies(cookies)));
+
+ EXPECT_TRUE(cookies.IsEmpty());
+
+ // Set cookies with various incantations of the samesite attribute:
+ // No same site attribute present
+ SetACookie(cookieService, "http://samesite.test", "unset=yes");
+ // samesite attribute present but with no value
+ SetACookie(cookieService, "http://samesite.test",
+ "unspecified=yes; samesite");
+ // samesite attribute present but with an empty value
+ SetACookie(cookieService, "http://samesite.test", "empty=yes; samesite=");
+ // samesite attribute present but with an invalid value
+ SetACookie(cookieService, "http://samesite.test",
+ "bogus=yes; samesite=bogus");
+ // samesite=strict
+ SetACookie(cookieService, "http://samesite.test",
+ "strict=yes; samesite=strict");
+ // samesite=lax
+ SetACookie(cookieService, "http://samesite.test", "lax=yes; samesite=lax");
+
+ cookies.SetLength(0);
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->GetCookies(cookies)));
+
+ // check the cookies for the required samesite value
+ for (const auto& cookie : cookies) {
+ nsAutoCString name;
+ cookie->GetName(name);
+ int32_t sameSiteAttr;
+ cookie->GetSameSite(&sameSiteAttr);
+ if (name.EqualsLiteral("unset")) {
+ EXPECT_TRUE(sameSiteAttr == nsICookie::SAMESITE_NONE);
+ } else if (name.EqualsLiteral("unspecified")) {
+ EXPECT_TRUE(sameSiteAttr == nsICookie::SAMESITE_NONE);
+ } else if (name.EqualsLiteral("empty")) {
+ EXPECT_TRUE(sameSiteAttr == nsICookie::SAMESITE_NONE);
+ } else if (name.EqualsLiteral("bogus")) {
+ EXPECT_TRUE(sameSiteAttr == nsICookie::SAMESITE_NONE);
+ } else if (name.EqualsLiteral("strict")) {
+ EXPECT_TRUE(sameSiteAttr == nsICookie::SAMESITE_STRICT);
+ } else if (name.EqualsLiteral("lax")) {
+ EXPECT_TRUE(sameSiteAttr == nsICookie::SAMESITE_LAX);
+ }
+ }
+
+ EXPECT_TRUE(cookies.Length() == 6);
+
+ // *** SameSite attribute
+ // Clear the cookies
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->RemoveAll()));
+
+ // please note that the flag aForeign is always set to true using this test
+ // setup because no nsIChannel is passed to SetCookieString(). therefore we
+ // can only test that no cookies are sent for cross origin requests using
+ // same-site cookies.
+ SetACookie(cookieService, "http://www.samesite.com",
+ "test=sameSiteStrictVal; samesite=strict");
+ GetACookie(cookieService, "http://www.notsamesite.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ SetACookie(cookieService, "http://www.samesite.test",
+ "test=sameSiteLaxVal; samesite=lax");
+ GetACookie(cookieService, "http://www.notsamesite.com", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_BE_NULL));
+
+ static const char* secureURIs[] = {
+ "http://localhost", "http://localhost:1234", "http://127.0.0.1",
+ "http://127.0.0.2", "http://127.1.0.1", "http://[::1]",
+ // TODO bug 1220810 "http://xyzzy.localhost"
+ };
+
+ uint32_t numSecureURIs = sizeof(secureURIs) / sizeof(const char*);
+ for (uint32_t i = 0; i < numSecureURIs; ++i) {
+ SetACookie(cookieService, secureURIs[i], "test=basic; secure");
+ GetACookie(cookieService, secureURIs[i], cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=basic"));
+ SetACookie(cookieService, secureURIs[i], "test=basic1");
+ GetACookie(cookieService, secureURIs[i], cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=basic1"));
+ }
+
+ // XXX the following are placeholders: add these tests please!
+ // *** "noncompliant cookie" tests
+ // *** IP address tests
+ // *** speed tests
+}
+
+TEST(TestCookie, SameSiteLax)
+{
+ Preferences::SetBool("network.cookie.sameSite.laxByDefault", true);
+
+ nsresult rv;
+
+ nsCOMPtr<nsICookieService> cookieService =
+ do_GetService(kCookieServiceCID, &rv);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ nsCOMPtr<nsICookieManager> cookieMgr =
+ do_GetService(NS_COOKIEMANAGER_CONTRACTID, &rv);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->RemoveAll()));
+
+ SetACookie(cookieService, "http://samesite.test", "unset=yes");
+
+ nsTArray<RefPtr<nsICookie>> cookies;
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->GetCookies(cookies)));
+ EXPECT_EQ(cookies.Length(), (uint64_t)1);
+
+ Cookie* cookie = static_cast<Cookie*>(cookies[0].get());
+ EXPECT_EQ(cookie->RawSameSite(), nsICookie::SAMESITE_NONE);
+ EXPECT_EQ(cookie->SameSite(), nsICookie::SAMESITE_LAX);
+
+ Preferences::SetCString("network.cookie.sameSite.laxByDefault.disabledHosts",
+ "foo.com,samesite.test,bar.net");
+
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->RemoveAll()));
+
+ cookies.SetLength(0);
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->GetCookies(cookies)));
+ EXPECT_EQ(cookies.Length(), (uint64_t)0);
+
+ SetACookie(cookieService, "http://samesite.test", "unset=yes");
+
+ cookies.SetLength(0);
+ EXPECT_TRUE(NS_SUCCEEDED(cookieMgr->GetCookies(cookies)));
+ EXPECT_EQ(cookies.Length(), (uint64_t)1);
+
+ cookie = static_cast<Cookie*>(cookies[0].get());
+ EXPECT_EQ(cookie->RawSameSite(), nsICookie::SAMESITE_NONE);
+ EXPECT_EQ(cookie->SameSite(), nsICookie::SAMESITE_NONE);
+}
+
+TEST(TestCookie, OnionSite)
+{
+ Preferences::SetBool("dom.securecontext.whitelist_onions", true);
+ Preferences::SetBool("network.cookie.sameSite.laxByDefault", false);
+
+ nsresult rv;
+ nsCString cookie;
+
+ nsCOMPtr<nsICookieService> cookieService =
+ do_GetService(kCookieServiceCID, &rv);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ // .onion secure cookie tests
+ SetACookie(cookieService, "http://123456789abcdef.onion/",
+ "test=onion-security; secure");
+ GetACookieNoHttp(cookieService, "https://123456789abcdef.onion/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=onion-security"));
+ SetACookie(cookieService, "http://123456789abcdef.onion/",
+ "test=onion-security2; secure");
+ GetACookieNoHttp(cookieService, "http://123456789abcdef.onion/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=onion-security2"));
+ SetACookie(cookieService, "https://123456789abcdef.onion/",
+ "test=onion-security3; secure");
+ GetACookieNoHttp(cookieService, "http://123456789abcdef.onion/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=onion-security3"));
+ SetACookie(cookieService, "http://123456789abcdef.onion/",
+ "test=onion-security4");
+ GetACookieNoHttp(cookieService, "http://123456789abcdef.onion/", cookie);
+ EXPECT_TRUE(CheckResult(cookie.get(), MUST_EQUAL, "test=onion-security4"));
+}
diff --git a/netwerk/test/gtest/TestHeaders.cpp b/netwerk/test/gtest/TestHeaders.cpp
new file mode 100644
index 0000000000..0da6b06c70
--- /dev/null
+++ b/netwerk/test/gtest/TestHeaders.cpp
@@ -0,0 +1,29 @@
+#include "gtest/gtest.h"
+
+#include "nsHttpHeaderArray.h"
+
+TEST(TestHeaders, DuplicateHSTS)
+{
+ // When the Strict-Transport-Security header is sent multiple times, its
+ // effective value is the value of the first item. It is not merged as other
+ // headers are.
+ mozilla::net::nsHttpHeaderArray headers;
+ nsresult rv = headers.SetHeaderFromNet(
+ mozilla::net::nsHttp::Strict_Transport_Security,
+ "Strict_Transport_Security"_ns, "max-age=360"_ns, true);
+ ASSERT_EQ(rv, NS_OK);
+
+ nsAutoCString h;
+ rv = headers.GetHeader(mozilla::net::nsHttp::Strict_Transport_Security, h);
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(h.get(), "max-age=360");
+
+ rv = headers.SetHeaderFromNet(mozilla::net::nsHttp::Strict_Transport_Security,
+ "Strict_Transport_Security"_ns,
+ "max-age=720"_ns, true);
+ ASSERT_EQ(rv, NS_OK);
+
+ rv = headers.GetHeader(mozilla::net::nsHttp::Strict_Transport_Security, h);
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(h.get(), "max-age=360");
+}
diff --git a/netwerk/test/gtest/TestHttpAuthUtils.cpp b/netwerk/test/gtest/TestHttpAuthUtils.cpp
new file mode 100644
index 0000000000..78fb40d4d0
--- /dev/null
+++ b/netwerk/test/gtest/TestHttpAuthUtils.cpp
@@ -0,0 +1,43 @@
+#include "gtest/gtest.h"
+
+#include "mozilla/net/HttpAuthUtils.h"
+#include "mozilla/Preferences.h"
+#include "nsNetUtil.h"
+
+namespace mozilla {
+namespace net {
+
+#define TEST_PREF "network.http_test.auth_utils"
+
+TEST(TestHttpAuthUtils, Bug1351301)
+{
+ nsCOMPtr<nsIURI> url;
+ nsAutoCString spec;
+
+ ASSERT_EQ(Preferences::SetCString(TEST_PREF, "bar.com"), NS_OK);
+ spec = "http://bar.com";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(auth::URIMatchesPrefPattern(url, TEST_PREF), true);
+
+ spec = "http://foo.bar.com";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(auth::URIMatchesPrefPattern(url, TEST_PREF), true);
+
+ spec = "http://foobar.com";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(auth::URIMatchesPrefPattern(url, TEST_PREF), false);
+
+ ASSERT_EQ(Preferences::SetCString(TEST_PREF, ".bar.com"), NS_OK);
+ spec = "http://foo.bar.com";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(auth::URIMatchesPrefPattern(url, TEST_PREF), true);
+
+ spec = "http://bar.com";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(auth::URIMatchesPrefPattern(url, TEST_PREF), false);
+
+ ASSERT_EQ(Preferences::ClearUser(TEST_PREF), NS_OK);
+}
+
+} // namespace net
+} // namespace mozilla
diff --git a/netwerk/test/gtest/TestHttpResponseHead.cpp b/netwerk/test/gtest/TestHttpResponseHead.cpp
new file mode 100644
index 0000000000..2a9a12e21a
--- /dev/null
+++ b/netwerk/test/gtest/TestHttpResponseHead.cpp
@@ -0,0 +1,109 @@
+#include "gtest/gtest.h"
+
+#include "chrome/common/ipc_message.h"
+#include "mozilla/net/PHttpChannelParams.h"
+#include "mozilla/Unused.h"
+#include "nsHttp.h"
+
+namespace mozilla {
+namespace net {
+
+void AssertRoundTrips(const nsHttpResponseHead& aHead) {
+ {
+ // Assert it round-trips via IPC.
+ UniquePtr<IPC::Message> msg(new IPC::Message(MSG_ROUTING_NONE, 0));
+ IPC::ParamTraits<nsHttpResponseHead>::Write(msg.get(), aHead);
+
+ nsHttpResponseHead deserializedHead;
+ PickleIterator iter(*msg);
+ bool res = IPC::ParamTraits<mozilla::net::nsHttpResponseHead>::Read(
+ msg.get(), &iter, &deserializedHead);
+ ASSERT_TRUE(res);
+ ASSERT_EQ(aHead, deserializedHead);
+ }
+
+ {
+ // Assert it round-trips through copy-ctor.
+ nsHttpResponseHead copied(aHead);
+ ASSERT_EQ(aHead, copied);
+ }
+
+ {
+ // Assert it round-trips through operator=
+ nsHttpResponseHead copied;
+ copied = aHead;
+ ASSERT_EQ(aHead, copied);
+ }
+}
+
+TEST(TestHttpResponseHead, Bug1636930)
+{
+ // Only create atom table when it's not already created.
+ if (!nsHttp::ResolveAtom("content-type")) {
+ Unused << nsHttp::CreateAtomTable();
+ }
+
+ nsHttpResponseHead head;
+
+ head.ParseStatusLine("HTTP/1.1 200 OK"_ns);
+ Unused << head.ParseHeaderLine("content-type: text/plain"_ns);
+ Unused << head.ParseHeaderLine("etag: Just testing"_ns);
+ Unused << head.ParseHeaderLine("cache-control: max-age=99999"_ns);
+ Unused << head.ParseHeaderLine("accept-ranges: bytes"_ns);
+ Unused << head.ParseHeaderLine("content-length: 1408"_ns);
+ Unused << head.ParseHeaderLine("connection: close"_ns);
+ Unused << head.ParseHeaderLine("server: httpd.js"_ns);
+ Unused << head.ParseHeaderLine("date: Tue, 12 May 2020 09:24:23 GMT"_ns);
+
+ AssertRoundTrips(head);
+}
+
+TEST(TestHttpResponseHead, bug1649807)
+{
+ // Only create atom table when it's not already created.
+ if (!nsHttp::ResolveAtom("content-type")) {
+ Unused << nsHttp::CreateAtomTable();
+ }
+
+ nsHttpResponseHead head;
+
+ head.ParseStatusLine("HTTP/1.1 200 OK"_ns);
+ Unused << head.ParseHeaderLine("content-type: text/plain"_ns);
+ Unused << head.ParseHeaderLine("etag: Just testing"_ns);
+ Unused << head.ParseHeaderLine("cache-control: age=99999"_ns);
+ Unused << head.ParseHeaderLine("accept-ranges: bytes"_ns);
+ Unused << head.ParseHeaderLine("content-length: 1408"_ns);
+ Unused << head.ParseHeaderLine("connection: close"_ns);
+ Unused << head.ParseHeaderLine("server: httpd.js"_ns);
+ Unused << head.ParseHeaderLine("pragma: no-cache"_ns);
+ Unused << head.ParseHeaderLine("date: Tue, 12 May 2020 09:24:23 GMT"_ns);
+
+ ASSERT_FALSE(head.NoCache())
+ << "Cache-Control wins over Pragma: no-cache";
+ AssertRoundTrips(head);
+}
+
+TEST(TestHttpResponseHead, bug1660200)
+{
+ // Only create atom table when it's not already created.
+ if (!nsHttp::ResolveAtom("content-type")) {
+ Unused << nsHttp::CreateAtomTable();
+ }
+
+ nsHttpResponseHead head;
+
+ head.ParseStatusLine("HTTP/1.1 200 OK"_ns);
+ Unused << head.ParseHeaderLine("content-type: text/plain"_ns);
+ Unused << head.ParseHeaderLine("etag: Just testing"_ns);
+ Unused << head.ParseHeaderLine("cache-control: no-cache"_ns);
+ Unused << head.ParseHeaderLine("accept-ranges: bytes"_ns);
+ Unused << head.ParseHeaderLine("content-length: 1408"_ns);
+ Unused << head.ParseHeaderLine("connection: close"_ns);
+ Unused << head.ParseHeaderLine("server: httpd.js"_ns);
+ Unused << head.ParseHeaderLine("date: Tue, 12 May 2020 09:24:23 GMT"_ns);
+
+ AssertRoundTrips(head);
+}
+
+} // namespace net
+} // namespace mozilla
diff --git a/netwerk/test/gtest/TestInputStreamTransport.cpp b/netwerk/test/gtest/TestInputStreamTransport.cpp
new file mode 100644
index 0000000000..ac133cab16
--- /dev/null
+++ b/netwerk/test/gtest/TestInputStreamTransport.cpp
@@ -0,0 +1,190 @@
+#include "gtest/gtest.h"
+
+#include "nsIStreamTransportService.h"
+#include "nsStreamUtils.h"
+#include "nsThreadUtils.h"
+#include "Helpers.h"
+
+static NS_DEFINE_CID(kStreamTransportServiceCID, NS_STREAMTRANSPORTSERVICE_CID);
+
+void CreateStream(already_AddRefed<nsIInputStream> aSource,
+ nsIAsyncInputStream** aStream) {
+ nsCOMPtr<nsIInputStream> source = std::move(aSource);
+
+ nsresult rv;
+ nsCOMPtr<nsIStreamTransportService> sts =
+ do_GetService(kStreamTransportServiceCID, &rv);
+ ASSERT_EQ(NS_OK, rv);
+
+ nsCOMPtr<nsITransport> transport;
+ rv = sts->CreateInputTransport(source, true, getter_AddRefs(transport));
+ ASSERT_EQ(NS_OK, rv);
+
+ nsCOMPtr<nsIInputStream> wrapper;
+ rv = transport->OpenInputStream(0, 0, 0, getter_AddRefs(wrapper));
+ ASSERT_EQ(NS_OK, rv);
+
+ nsCOMPtr<nsIAsyncInputStream> asyncStream = do_QueryInterface(wrapper);
+ MOZ_ASSERT(asyncStream);
+
+ asyncStream.forget(aStream);
+}
+
+class BlockingSyncStream final : public nsIInputStream {
+ nsCOMPtr<nsIInputStream> mStream;
+
+ public:
+ NS_DECL_THREADSAFE_ISUPPORTS
+
+ explicit BlockingSyncStream(const nsACString& aBuffer) {
+ NS_NewCStringInputStream(getter_AddRefs(mStream), aBuffer);
+ }
+
+ NS_IMETHOD
+ Available(uint64_t* aLength) override { return mStream->Available(aLength); }
+
+ NS_IMETHOD
+ Read(char* aBuffer, uint32_t aCount, uint32_t* aReadCount) override {
+ return mStream->Read(aBuffer, aCount, aReadCount);
+ }
+
+ NS_IMETHOD
+ ReadSegments(nsWriteSegmentFun aWriter, void* aClosure, uint32_t aCount,
+ uint32_t* aResult) override {
+ return mStream->ReadSegments(aWriter, aClosure, aCount, aResult);
+ }
+
+ NS_IMETHOD
+ Close() override { return mStream->Close(); }
+
+ NS_IMETHOD
+ IsNonBlocking(bool* aNonBlocking) override {
+ *aNonBlocking = false;
+ return NS_OK;
+ }
+
+ private:
+ ~BlockingSyncStream() = default;
+};
+
+NS_IMPL_ISUPPORTS(BlockingSyncStream, nsIInputStream)
+
+// Testing a simple blocking stream.
+TEST(TestInputStreamTransport, BlockingNotAsync)
+{
+ RefPtr<BlockingSyncStream> stream = new BlockingSyncStream("Hello world"_ns);
+
+ nsCOMPtr<nsIAsyncInputStream> ais;
+ CreateStream(stream.forget(), getter_AddRefs(ais));
+ ASSERT_TRUE(!!ais);
+
+ nsAutoCString data;
+ nsresult rv = NS_ReadInputStreamToString(ais, data, -1);
+ ASSERT_EQ(NS_OK, rv);
+
+ ASSERT_TRUE(data.EqualsLiteral("Hello world"));
+}
+
+class BlockingAsyncStream final : public nsIAsyncInputStream {
+ nsCOMPtr<nsIInputStream> mStream;
+ bool mPending;
+
+ public:
+ NS_DECL_THREADSAFE_ISUPPORTS
+
+ explicit BlockingAsyncStream(const nsACString& aBuffer) : mPending(false) {
+ NS_NewCStringInputStream(getter_AddRefs(mStream), aBuffer);
+ }
+
+ NS_IMETHOD
+ Available(uint64_t* aLength) override {
+ mStream->Available(aLength);
+
+ // 1 char at the time, just to test the asyncWait+Read loop a bit more.
+ if (*aLength > 0) {
+ *aLength = 1;
+ }
+
+ return NS_OK;
+ }
+
+ NS_IMETHOD
+ Read(char* aBuffer, uint32_t aCount, uint32_t* aReadCount) override {
+ mPending = !mPending;
+ if (mPending) {
+ return NS_BASE_STREAM_WOULD_BLOCK;
+ }
+
+ // 1 char at the time, just to test the asyncWait+Read loop a bit more.
+ aCount = 1;
+
+ return mStream->Read(aBuffer, aCount, aReadCount);
+ }
+
+ NS_IMETHOD
+ ReadSegments(nsWriteSegmentFun aWriter, void* aClosure, uint32_t aCount,
+ uint32_t* aResult) override {
+ mPending = !mPending;
+ if (mPending) {
+ return NS_BASE_STREAM_WOULD_BLOCK;
+ }
+
+ // 1 char at the time, just to test the asyncWait+Read loop a bit more.
+ aCount = 1;
+
+ return mStream->ReadSegments(aWriter, aClosure, aCount, aResult);
+ }
+
+ NS_IMETHOD
+ Close() override { return mStream->Close(); }
+
+ NS_IMETHOD
+ IsNonBlocking(bool* aNonBlocking) override {
+ *aNonBlocking = false;
+ return NS_OK;
+ }
+
+ NS_IMETHOD
+ CloseWithStatus(nsresult aStatus) override { return Close(); }
+
+ NS_IMETHOD
+ AsyncWait(nsIInputStreamCallback* aCallback, uint32_t aFlags,
+ uint32_t aRequestedCount, nsIEventTarget* aEventTarget) override {
+ RefPtr<BlockingAsyncStream> self = this;
+ nsCOMPtr<nsIInputStreamCallback> callback = aCallback;
+
+ nsCOMPtr<nsIRunnable> r = NS_NewRunnableFunction(
+ "gtest-asyncwait",
+ [self, callback]() { callback->OnInputStreamReady(self); });
+
+ if (aEventTarget) {
+ aEventTarget->Dispatch(r.forget());
+ } else {
+ r->Run();
+ }
+
+ return NS_OK;
+ }
+
+ private:
+ ~BlockingAsyncStream() = default;
+};
+
+NS_IMPL_ISUPPORTS(BlockingAsyncStream, nsIInputStream, nsIAsyncInputStream)
+
+// Testing an async blocking stream.
+TEST(TestInputStreamTransport, BlockingAsync)
+{
+ RefPtr<BlockingAsyncStream> stream =
+ new BlockingAsyncStream("Hello world"_ns);
+
+ nsCOMPtr<nsIAsyncInputStream> ais;
+ CreateStream(stream.forget(), getter_AddRefs(ais));
+ ASSERT_TRUE(!!ais);
+
+ nsAutoCString data;
+ nsresult rv = NS_ReadInputStreamToString(ais, data, -1);
+ ASSERT_EQ(NS_OK, rv);
+
+ ASSERT_TRUE(data.EqualsLiteral("Hello world"));
+}
diff --git a/netwerk/test/gtest/TestIsValidIp.cpp b/netwerk/test/gtest/TestIsValidIp.cpp
new file mode 100644
index 0000000000..dfee8c5c0f
--- /dev/null
+++ b/netwerk/test/gtest/TestIsValidIp.cpp
@@ -0,0 +1,178 @@
+#include "gtest/MozGTestBench.h" // For MOZ_GTEST_BENCH
+#include "gtest/gtest.h"
+
+#include "nsURLHelper.h"
+
+TEST(TestIsValidIp, IPV4Localhost)
+{
+ constexpr auto ip = "127.0.0.1"_ns;
+ ASSERT_EQ(true, net_IsValidIPv4Addr(ip));
+}
+
+TEST(TestIsValidIp, IPV4Only0)
+{
+ constexpr auto ip = "0.0.0.0"_ns;
+ ASSERT_EQ(true, net_IsValidIPv4Addr(ip));
+}
+
+TEST(TestIsValidIp, IPV4Max)
+{
+ constexpr auto ip = "255.255.255.255"_ns;
+ ASSERT_EQ(true, net_IsValidIPv4Addr(ip));
+}
+
+TEST(TestIsValidIp, IPV4LeadingZero)
+{
+ constexpr auto ip = "055.225.255.255"_ns;
+ ASSERT_EQ(false, net_IsValidIPv4Addr(ip));
+
+ constexpr auto ip2 = "255.055.255.255"_ns;
+ ASSERT_EQ(false, net_IsValidIPv4Addr(ip2));
+
+ constexpr auto ip3 = "255.255.055.255"_ns;
+ ASSERT_EQ(false, net_IsValidIPv4Addr(ip3));
+
+ constexpr auto ip4 = "255.255.255.055"_ns;
+ ASSERT_EQ(false, net_IsValidIPv4Addr(ip4));
+}
+
+TEST(TestIsValidIp, IPV4StartWithADot)
+{
+ constexpr auto ip = ".192.168.120.197"_ns;
+ ASSERT_EQ(false, net_IsValidIPv4Addr(ip));
+}
+
+TEST(TestIsValidIp, IPV4StartWith4Digits)
+{
+ constexpr auto ip = "1927.168.120.197"_ns;
+ ASSERT_EQ(false, net_IsValidIPv4Addr(ip));
+}
+
+TEST(TestIsValidIp, IPV4OutOfRange)
+{
+ constexpr auto invalid1 = "421.168.120.124"_ns;
+ constexpr auto invalid2 = "192.997.120.124"_ns;
+ constexpr auto invalid3 = "192.168.300.124"_ns;
+ constexpr auto invalid4 = "192.168.120.256"_ns;
+
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid1));
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid2));
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid3));
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid4));
+}
+
+TEST(TestIsValidIp, IPV4EmptyDigits)
+{
+ constexpr auto invalid1 = "..0.0.0"_ns;
+ constexpr auto invalid2 = "127..0.0"_ns;
+ constexpr auto invalid3 = "127.0..0"_ns;
+ constexpr auto invalid4 = "127.0.0."_ns;
+
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid1));
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid2));
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid3));
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid4));
+}
+
+TEST(TestIsValidIp, IPV4NonNumeric)
+{
+ constexpr auto invalid1 = "127.0.0.f"_ns;
+ constexpr auto invalid2 = "127.0.0.!"_ns;
+ constexpr auto invalid3 = "127#0.0.1"_ns;
+
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid1));
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid2));
+ ASSERT_EQ(false, net_IsValidIPv4Addr(invalid3));
+}
+
+TEST(TestIsValidIp, IPV4TooManyDigits)
+{
+ constexpr auto ip = "127.0.0.1.2"_ns;
+ ASSERT_EQ(false, net_IsValidIPv4Addr(ip));
+}
+
+TEST(TestIsValidIp, IPV4TooFewDigits)
+{
+ constexpr auto ip = "127.0.1"_ns;
+ ASSERT_EQ(false, net_IsValidIPv4Addr(ip));
+}
+
+TEST(TestIsValidIp, IPV6WithIPV4Inside)
+{
+ constexpr auto ipv6 = "0123:4567:89ab:cdef:0123:4567:127.0.0.1"_ns;
+ ASSERT_EQ(true, net_IsValidIPv6Addr(ipv6));
+}
+
+TEST(TestIsValidIp, IPv6FullForm)
+{
+ constexpr auto ipv6 = "0123:4567:89ab:cdef:0123:4567:890a:bcde"_ns;
+ ASSERT_EQ(true, net_IsValidIPv6Addr(ipv6));
+}
+
+TEST(TestIsValidIp, IPv6TrimLeading0)
+{
+ constexpr auto ipv6 = "123:4567:0:0:123:4567:890a:bcde"_ns;
+ ASSERT_EQ(true, net_IsValidIPv6Addr(ipv6));
+}
+
+TEST(TestIsValidIp, IPv6Collapsed)
+{
+ constexpr auto ipv6 = "FF01::101"_ns;
+ ASSERT_EQ(true, net_IsValidIPv6Addr(ipv6));
+}
+
+TEST(TestIsValidIp, IPV6WithIPV4InsideCollapsed)
+{
+ constexpr auto ipv6 = "::FFFF:129.144.52.38"_ns;
+ ASSERT_EQ(true, net_IsValidIPv6Addr(ipv6));
+}
+
+TEST(TestIsValidIp, IPV6Localhost)
+{
+ constexpr auto ipv6 = "::1"_ns;
+ ASSERT_EQ(true, net_IsValidIPv6Addr(ipv6));
+}
+
+TEST(TestIsValidIp, IPV6LinkLocalPrefix)
+{
+ constexpr auto ipv6 = "fe80::"_ns;
+ ASSERT_EQ(true, net_IsValidIPv6Addr(ipv6));
+}
+
+TEST(TestIsValidIp, IPV6GlobalUnicastPrefix)
+{
+ constexpr auto ipv6 = "2001::"_ns;
+ ASSERT_EQ(true, net_IsValidIPv6Addr(ipv6));
+}
+
+TEST(TestIsValidIp, IPV6Unspecified)
+{
+ constexpr auto ipv6 = "::"_ns;
+ ASSERT_EQ(true, net_IsValidIPv6Addr(ipv6));
+}
+
+TEST(TestIsValidIp, IPV6InvalidIPV4Inside)
+{
+ constexpr auto ipv6 = "0123:4567:89ab:cdef:0123:4567:127.0."_ns;
+ ASSERT_EQ(false, net_IsValidIPv6Addr(ipv6));
+}
+
+TEST(TestIsValidIp, IPV6InvalidCharacters)
+{
+ constexpr auto ipv6 = "012g:4567:89ab:cdef:0123:4567:127.0.0.1"_ns;
+ ASSERT_EQ(false, net_IsValidIPv6Addr(ipv6));
+
+ constexpr auto ipv6pound = "0123:456#:89ab:cdef:0123:4567:127.0.0.1"_ns;
+ ASSERT_EQ(false, net_IsValidIPv6Addr(ipv6pound));
+}
+
+TEST(TestIsValidIp, IPV6TooManyCharacters)
+{
+ constexpr auto ipv6 = "0123:45671:89ab:cdef:0123:4567:127.0.0.1"_ns;
+ ASSERT_EQ(false, net_IsValidIPv6Addr(ipv6));
+}
+TEST(TestIsValidIp, IPV6DoubleDoubleDots)
+{
+ constexpr auto ipv6 = "0123::4567:890a::bcde:0123:4567"_ns;
+ ASSERT_EQ(false, net_IsValidIPv6Addr(ipv6));
+}
diff --git a/netwerk/test/gtest/TestMIMEInputStream.cpp b/netwerk/test/gtest/TestMIMEInputStream.cpp
new file mode 100644
index 0000000000..ce7f5bd47d
--- /dev/null
+++ b/netwerk/test/gtest/TestMIMEInputStream.cpp
@@ -0,0 +1,261 @@
+#include "gtest/gtest.h"
+
+#include "Helpers.h"
+#include "mozilla/SpinEventLoopUntil.h"
+#include "nsComponentManagerUtils.h"
+#include "nsCOMPtr.h"
+#include "nsStreamUtils.h"
+#include "nsString.h"
+#include "nsStringStream.h"
+#include "nsIMIMEInputStream.h"
+
+using mozilla::GetCurrentSerialEventTarget;
+using mozilla::SpinEventLoopUntil;
+
+namespace {
+
+class SeekableLengthInputStream final : public testing::LengthInputStream,
+ public nsISeekableStream {
+ public:
+ SeekableLengthInputStream(const nsACString& aBuffer,
+ bool aIsInputStreamLength,
+ bool aIsAsyncInputStreamLength,
+ nsresult aLengthRv = NS_OK,
+ bool aNegativeValue = false)
+ : testing::LengthInputStream(aBuffer, aIsInputStreamLength,
+ aIsAsyncInputStreamLength, aLengthRv,
+ aNegativeValue) {}
+
+ NS_DECL_ISUPPORTS_INHERITED
+
+ NS_IMETHOD
+ Seek(int32_t aWhence, int64_t aOffset) override {
+ MOZ_CRASH("This method should not be called.");
+ return NS_ERROR_FAILURE;
+ }
+
+ NS_IMETHOD
+ Tell(int64_t* aResult) override {
+ MOZ_CRASH("This method should not be called.");
+ return NS_ERROR_FAILURE;
+ }
+
+ NS_IMETHOD
+ SetEOF() override {
+ MOZ_CRASH("This method should not be called.");
+ return NS_ERROR_FAILURE;
+ }
+
+ private:
+ ~SeekableLengthInputStream() = default;
+};
+
+NS_IMPL_ISUPPORTS_INHERITED(SeekableLengthInputStream,
+ testing::LengthInputStream, nsISeekableStream)
+
+} // namespace
+
+// nsIInputStreamLength && nsIAsyncInputStreamLength
+
+TEST(TestNsMIMEInputStream, QIInputStreamLength)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ for (int i = 0; i < 4; i++) {
+ nsCOMPtr<nsIInputStream> mis;
+ {
+ RefPtr<SeekableLengthInputStream> stream =
+ new SeekableLengthInputStream(buf, i % 2, i > 1);
+
+ nsresult rv;
+ nsCOMPtr<nsIMIMEInputStream> m(
+ do_CreateInstance("@mozilla.org/network/mime-input-stream;1", &rv));
+ ASSERT_EQ(NS_OK, rv);
+
+ rv = m->SetData(stream);
+ ASSERT_EQ(NS_OK, rv);
+
+ mis = m;
+ ASSERT_TRUE(!!mis);
+ }
+
+ {
+ nsCOMPtr<nsIInputStreamLength> qi = do_QueryInterface(mis);
+ ASSERT_EQ(!!(i % 2), !!qi);
+ }
+
+ {
+ nsCOMPtr<nsIAsyncInputStreamLength> qi = do_QueryInterface(mis);
+ ASSERT_EQ(i > 1, !!qi);
+ }
+ }
+}
+
+TEST(TestNsMIMEInputStream, InputStreamLength)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ nsCOMPtr<nsIInputStream> mis;
+ {
+ RefPtr<SeekableLengthInputStream> stream =
+ new SeekableLengthInputStream(buf, true, false);
+
+ nsresult rv;
+ nsCOMPtr<nsIMIMEInputStream> m(
+ do_CreateInstance("@mozilla.org/network/mime-input-stream;1", &rv));
+ ASSERT_EQ(NS_OK, rv);
+
+ rv = m->SetData(stream);
+ ASSERT_EQ(NS_OK, rv);
+
+ mis = m;
+ ASSERT_TRUE(!!mis);
+ }
+
+ nsCOMPtr<nsIInputStreamLength> qi = do_QueryInterface(mis);
+ ASSERT_TRUE(!!qi);
+
+ int64_t size;
+ nsresult rv = qi->Length(&size);
+ ASSERT_EQ(NS_OK, rv);
+ ASSERT_EQ(buf.Length(), size);
+}
+
+TEST(TestNsMIMEInputStream, NegativeInputStreamLength)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ nsCOMPtr<nsIInputStream> mis;
+ {
+ RefPtr<SeekableLengthInputStream> stream =
+ new SeekableLengthInputStream(buf, true, false, NS_OK, true);
+
+ nsresult rv;
+ nsCOMPtr<nsIMIMEInputStream> m(
+ do_CreateInstance("@mozilla.org/network/mime-input-stream;1", &rv));
+ ASSERT_EQ(NS_OK, rv);
+
+ rv = m->SetData(stream);
+ ASSERT_EQ(NS_OK, rv);
+
+ mis = m;
+ ASSERT_TRUE(!!mis);
+ }
+
+ nsCOMPtr<nsIInputStreamLength> qi = do_QueryInterface(mis);
+ ASSERT_TRUE(!!qi);
+
+ int64_t size;
+ nsresult rv = qi->Length(&size);
+ ASSERT_EQ(NS_OK, rv);
+ ASSERT_EQ(-1, size);
+}
+
+TEST(TestNsMIMEInputStream, AsyncInputStreamLength)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ nsCOMPtr<nsIInputStream> mis;
+ {
+ RefPtr<SeekableLengthInputStream> stream =
+ new SeekableLengthInputStream(buf, false, true);
+
+ nsresult rv;
+ nsCOMPtr<nsIMIMEInputStream> m(
+ do_CreateInstance("@mozilla.org/network/mime-input-stream;1", &rv));
+ ASSERT_EQ(NS_OK, rv);
+
+ rv = m->SetData(stream);
+ ASSERT_EQ(NS_OK, rv);
+
+ mis = m;
+ ASSERT_TRUE(!!mis);
+ }
+
+ nsCOMPtr<nsIAsyncInputStreamLength> qi = do_QueryInterface(mis);
+ ASSERT_TRUE(!!qi);
+
+ RefPtr<testing::LengthCallback> callback = new testing::LengthCallback();
+
+ nsresult rv = qi->AsyncLengthWait(callback, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+ ASSERT_EQ(buf.Length(), callback->Size());
+}
+
+TEST(TestNsMIMEInputStream, NegativeAsyncInputStreamLength)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ nsCOMPtr<nsIInputStream> mis;
+ {
+ RefPtr<SeekableLengthInputStream> stream =
+ new SeekableLengthInputStream(buf, false, true, NS_OK, true);
+
+ nsresult rv;
+ nsCOMPtr<nsIMIMEInputStream> m(
+ do_CreateInstance("@mozilla.org/network/mime-input-stream;1", &rv));
+ ASSERT_EQ(NS_OK, rv);
+
+ rv = m->SetData(stream);
+ ASSERT_EQ(NS_OK, rv);
+
+ mis = m;
+ ASSERT_TRUE(!!mis);
+ }
+
+ nsCOMPtr<nsIAsyncInputStreamLength> qi = do_QueryInterface(mis);
+ ASSERT_TRUE(!!qi);
+
+ RefPtr<testing::LengthCallback> callback = new testing::LengthCallback();
+
+ nsresult rv = qi->AsyncLengthWait(callback, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+ ASSERT_EQ(-1, callback->Size());
+}
+
+TEST(TestNsMIMEInputStream, AbortLengthCallback)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ nsCOMPtr<nsIInputStream> mis;
+ {
+ RefPtr<SeekableLengthInputStream> stream =
+ new SeekableLengthInputStream(buf, false, true, NS_OK, true);
+
+ nsresult rv;
+ nsCOMPtr<nsIMIMEInputStream> m(
+ do_CreateInstance("@mozilla.org/network/mime-input-stream;1", &rv));
+ ASSERT_EQ(NS_OK, rv);
+
+ rv = m->SetData(stream);
+ ASSERT_EQ(NS_OK, rv);
+
+ mis = m;
+ ASSERT_TRUE(!!mis);
+ }
+
+ nsCOMPtr<nsIAsyncInputStreamLength> qi = do_QueryInterface(mis);
+ ASSERT_TRUE(!!qi);
+
+ RefPtr<testing::LengthCallback> callback1 = new testing::LengthCallback();
+ nsresult rv = qi->AsyncLengthWait(callback1, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ RefPtr<testing::LengthCallback> callback2 = new testing::LengthCallback();
+ rv = qi->AsyncLengthWait(callback2, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback2->Called(); }));
+ ASSERT_TRUE(!callback1->Called());
+ ASSERT_EQ(-1, callback2->Size());
+}
diff --git a/netwerk/test/gtest/TestMozURL.cpp b/netwerk/test/gtest/TestMozURL.cpp
new file mode 100644
index 0000000000..de0d69f28d
--- /dev/null
+++ b/netwerk/test/gtest/TestMozURL.cpp
@@ -0,0 +1,390 @@
+#include "gtest/gtest.h"
+#include "gtest/MozGTestBench.h" // For MOZ_GTEST_BENCH
+
+#include <regex>
+#include "json/json.h"
+#include "json/reader.h"
+#include "mozilla/TextUtils.h"
+#include "mozilla/net/MozURL.h"
+#include "nsCOMPtr.h"
+#include "nsDirectoryServiceDefs.h"
+#include "nsNetUtil.h"
+#include "nsIFile.h"
+#include "nsIURI.h"
+#include "nsStreamUtils.h"
+
+using namespace mozilla;
+using namespace mozilla::net;
+
+TEST(TestMozURL, Getters)
+{
+ nsAutoCString href("http://user:pass@example.com/path?query#ref");
+ RefPtr<MozURL> url;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), href), NS_OK);
+
+ ASSERT_TRUE(url->Scheme().EqualsLiteral("http"));
+
+ ASSERT_TRUE(url->Spec() == href);
+
+ ASSERT_TRUE(url->Username().EqualsLiteral("user"));
+
+ ASSERT_TRUE(url->Password().EqualsLiteral("pass"));
+
+ ASSERT_TRUE(url->Host().EqualsLiteral("example.com"));
+
+ ASSERT_TRUE(url->FilePath().EqualsLiteral("/path"));
+
+ ASSERT_TRUE(url->Query().EqualsLiteral("query"));
+
+ ASSERT_TRUE(url->Ref().EqualsLiteral("ref"));
+
+ url = nullptr;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), ""_ns), NS_ERROR_MALFORMED_URI);
+ ASSERT_EQ(url, nullptr);
+}
+
+TEST(TestMozURL, MutatorChain)
+{
+ nsAutoCString href("http://user:pass@example.com/path?query#ref");
+ RefPtr<MozURL> url;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), href), NS_OK);
+ nsAutoCString out;
+
+ RefPtr<MozURL> url2;
+ ASSERT_EQ(url->Mutate()
+ .SetScheme("https"_ns)
+ .SetUsername("newuser"_ns)
+ .SetPassword("newpass"_ns)
+ .SetHostname("test"_ns)
+ .SetFilePath("new/file/path"_ns)
+ .SetQuery("bla"_ns)
+ .SetRef("huh"_ns)
+ .Finalize(getter_AddRefs(url2)),
+ NS_OK);
+
+ ASSERT_TRUE(url2->Spec().EqualsLiteral(
+ "https://newuser:newpass@test/new/file/path?bla#huh"));
+}
+
+TEST(TestMozURL, MutatorFinalizeTwice)
+{
+ nsAutoCString href("http://user:pass@example.com/path?query#ref");
+ RefPtr<MozURL> url;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), href), NS_OK);
+ nsAutoCString out;
+
+ RefPtr<MozURL> url2;
+ MozURL::Mutator mut = url->Mutate();
+ mut.SetScheme("https"_ns); // Change the scheme to https
+ ASSERT_EQ(mut.Finalize(getter_AddRefs(url2)), NS_OK);
+ ASSERT_TRUE(url2->Spec().EqualsLiteral(
+ "https://user:pass@example.com/path?query#ref"));
+
+ // Test that a second call to Finalize will result in an error code
+ url2 = nullptr;
+ ASSERT_EQ(mut.Finalize(getter_AddRefs(url2)), NS_ERROR_NOT_AVAILABLE);
+ ASSERT_EQ(url2, nullptr);
+}
+
+TEST(TestMozURL, MutatorErrorStatus)
+{
+ nsAutoCString href("http://user:pass@example.com/path?query#ref");
+ RefPtr<MozURL> url;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), href), NS_OK);
+ nsAutoCString out;
+
+ // Test that trying to set the scheme to a bad value will get you an error
+ MozURL::Mutator mut = url->Mutate();
+ mut.SetScheme("!@#$%^&*("_ns);
+ ASSERT_EQ(mut.GetStatus(), NS_ERROR_MALFORMED_URI);
+
+ // Test that the mutator will not work after one faulty operation
+ mut.SetScheme("test"_ns);
+ ASSERT_EQ(mut.GetStatus(), NS_ERROR_MALFORMED_URI);
+}
+
+TEST(TestMozURL, InitWithBase)
+{
+ nsAutoCString href("https://example.net/a/b.html");
+ RefPtr<MozURL> url;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), href), NS_OK);
+
+ ASSERT_TRUE(url->Spec().EqualsLiteral("https://example.net/a/b.html"));
+
+ RefPtr<MozURL> url2;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url2), "c.png"_ns, url), NS_OK);
+
+ ASSERT_TRUE(url2->Spec().EqualsLiteral("https://example.net/a/c.png"));
+}
+
+TEST(TestMozURL, Path)
+{
+ nsAutoCString href("about:blank");
+ RefPtr<MozURL> url;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), href), NS_OK);
+
+ ASSERT_TRUE(url->Spec().EqualsLiteral("about:blank"));
+
+ ASSERT_TRUE(url->Scheme().EqualsLiteral("about"));
+
+ ASSERT_TRUE(url->FilePath().EqualsLiteral("blank"));
+}
+
+TEST(TestMozURL, HostPort)
+{
+ nsAutoCString href("https://user:pass@example.net:1234/path?query#ref");
+ RefPtr<MozURL> url;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), href), NS_OK);
+
+ ASSERT_TRUE(url->HostPort().EqualsLiteral("example.net:1234"));
+
+ RefPtr<MozURL> url2;
+ url->Mutate().SetHostPort("test:321"_ns).Finalize(getter_AddRefs(url2));
+
+ ASSERT_TRUE(url2->HostPort().EqualsLiteral("test:321"));
+ ASSERT_TRUE(
+ url2->Spec().EqualsLiteral("https://user:pass@test:321/path?query#ref"));
+
+ href.Assign("https://user:pass@example.net:443/path?query#ref");
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), href), NS_OK);
+ ASSERT_TRUE(url->HostPort().EqualsLiteral("example.net"));
+ ASSERT_EQ(url->Port(), -1);
+}
+
+TEST(TestMozURL, Origin)
+{
+ nsAutoCString href("https://user:pass@example.net:1234/path?query#ref");
+ RefPtr<MozURL> url;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), href), NS_OK);
+
+ nsAutoCString out;
+ url->Origin(out);
+ ASSERT_TRUE(out.EqualsLiteral("https://example.net:1234"));
+
+ RefPtr<MozURL> url2;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url2), "file:///tmp/foo"_ns), NS_OK);
+ url2->Origin(out);
+ ASSERT_TRUE(out.EqualsLiteral("file:///tmp/foo"));
+
+ RefPtr<MozURL> url3;
+ ASSERT_EQ(
+ MozURL::Init(getter_AddRefs(url3),
+ nsLiteralCString(
+ "moz-extension://53711a8f-65ed-e742-9671-1f02e267c0bc/"
+ "foo/bar.html")),
+ NS_OK);
+ url3->Origin(out);
+ ASSERT_TRUE(out.EqualsLiteral(
+ "moz-extension://53711a8f-65ed-e742-9671-1f02e267c0bc"));
+
+ RefPtr<MozURL> url4;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url4), "resource://foo/bar.html"_ns),
+ NS_OK);
+ url4->Origin(out);
+ ASSERT_TRUE(out.EqualsLiteral("resource://foo"));
+
+ RefPtr<MozURL> url5;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url5), "about:home"_ns), NS_OK);
+ url5->Origin(out);
+ ASSERT_TRUE(out.EqualsLiteral("about:home"));
+}
+
+TEST(TestMozURL, BaseDomain)
+{
+ nsAutoCString href("https://user:pass@example.net:1234/path?query#ref");
+ RefPtr<MozURL> url;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), href), NS_OK);
+
+ nsAutoCString out;
+ ASSERT_EQ(url->BaseDomain(out), NS_OK);
+ ASSERT_TRUE(out.EqualsLiteral("example.net"));
+
+ RefPtr<MozURL> url2;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url2), "file:///tmp/foo"_ns), NS_OK);
+ ASSERT_EQ(url2->BaseDomain(out), NS_OK);
+ ASSERT_TRUE(out.EqualsLiteral("/tmp/foo"));
+
+ RefPtr<MozURL> url3;
+ ASSERT_EQ(
+ MozURL::Init(getter_AddRefs(url3),
+ nsLiteralCString(
+ "moz-extension://53711a8f-65ed-e742-9671-1f02e267c0bc/"
+ "foo/bar.html")),
+ NS_OK);
+ ASSERT_EQ(url3->BaseDomain(out), NS_OK);
+ ASSERT_TRUE(out.EqualsLiteral("53711a8f-65ed-e742-9671-1f02e267c0bc"));
+
+ RefPtr<MozURL> url4;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url4), "resource://foo/bar.html"_ns),
+ NS_OK);
+ ASSERT_EQ(url4->BaseDomain(out), NS_OK);
+ ASSERT_TRUE(out.EqualsLiteral("foo"));
+
+ RefPtr<MozURL> url5;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url5), "about:home"_ns), NS_OK);
+ ASSERT_EQ(url5->BaseDomain(out), NS_OK);
+ ASSERT_TRUE(out.EqualsLiteral("about:home"));
+}
+
+namespace {
+
+bool OriginMatchesExpectedOrigin(const nsACString& aOrigin,
+ const nsACString& aExpectedOrigin) {
+ if (aExpectedOrigin.Equals("null") &&
+ StringBeginsWith(aOrigin, "moz-nullprincipal"_ns)) {
+ return true;
+ }
+ return aOrigin == aExpectedOrigin;
+}
+
+bool IsUUID(const nsACString& aString) {
+ if (!IsAscii(aString)) {
+ return false;
+ }
+
+ std::regex pattern(
+ "^\\{[0-9A-Fa-f]{8}-[0-9A-Fa-f]{4}-4[0-9A-Fa-f]{3}-[89ABab"
+ "][0-9A-Fa-f]{3}-[0-9A-Fa-f]{12}\\}$");
+ return regex_match(nsCString(aString).get(), pattern);
+}
+
+bool BaseDomainsEqual(const nsACString& aBaseDomain1,
+ const nsACString& aBaseDomain2) {
+ if (IsUUID(aBaseDomain1) && IsUUID(aBaseDomain2)) {
+ return true;
+ }
+ return aBaseDomain1 == aBaseDomain2;
+}
+
+void CheckOrigin(const nsACString& aSpec, const nsACString& aBase,
+ const nsACString& aOrigin) {
+ nsCOMPtr<nsIURI> baseUri;
+ nsresult rv = NS_NewURI(getter_AddRefs(baseUri), aBase);
+ ASSERT_EQ(rv, NS_OK);
+
+ nsCOMPtr<nsIURI> uri;
+ rv = NS_NewURI(getter_AddRefs(uri), aSpec, nullptr, baseUri);
+ ASSERT_EQ(rv, NS_OK);
+
+ OriginAttributes attrs;
+
+ nsCOMPtr<nsIPrincipal> principal =
+ BasePrincipal::CreateContentPrincipal(uri, attrs);
+ ASSERT_TRUE(principal);
+
+ nsCString origin;
+ rv = principal->GetOriginNoSuffix(origin);
+ ASSERT_EQ(rv, NS_OK);
+
+ EXPECT_TRUE(OriginMatchesExpectedOrigin(origin, aOrigin));
+
+ nsCString baseDomain;
+ rv = principal->GetBaseDomain(baseDomain);
+
+ bool baseDomainSucceeded = NS_SUCCEEDED(rv);
+
+ RefPtr<MozURL> baseUrl;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(baseUrl), aBase), NS_OK);
+
+ RefPtr<MozURL> url;
+ ASSERT_EQ(MozURL::Init(getter_AddRefs(url), aSpec, baseUrl), NS_OK);
+
+ url->Origin(origin);
+
+ EXPECT_TRUE(OriginMatchesExpectedOrigin(origin, aOrigin));
+
+ nsCString baseDomain2;
+ rv = url->BaseDomain(baseDomain2);
+
+ bool baseDomain2Succeeded = NS_SUCCEEDED(rv);
+
+ EXPECT_TRUE(baseDomainSucceeded == baseDomain2Succeeded);
+
+ if (baseDomainSucceeded) {
+ EXPECT_TRUE(BaseDomainsEqual(baseDomain, baseDomain2));
+ }
+}
+
+} // namespace
+
+TEST(TestMozURL, UrlTestData)
+{
+ nsCOMPtr<nsIFile> file;
+ nsresult rv =
+ NS_GetSpecialDirectory(NS_OS_CURRENT_WORKING_DIR, getter_AddRefs(file));
+ ASSERT_EQ(rv, NS_OK);
+
+ rv = file->Append(u"urltestdata.json"_ns);
+ ASSERT_EQ(rv, NS_OK);
+
+ bool exists;
+ rv = file->Exists(&exists);
+ ASSERT_EQ(rv, NS_OK);
+
+ ASSERT_TRUE(exists);
+
+ nsCOMPtr<nsIInputStream> stream;
+ rv = NS_NewLocalFileInputStream(getter_AddRefs(stream), file);
+ ASSERT_EQ(rv, NS_OK);
+
+ nsCOMPtr<nsIInputStream> bufferedStream;
+ rv = NS_NewBufferedInputStream(getter_AddRefs(bufferedStream),
+ stream.forget(), 4096);
+ ASSERT_EQ(rv, NS_OK);
+
+ nsCString data;
+ rv = NS_ConsumeStream(bufferedStream, UINT32_MAX, data);
+ ASSERT_EQ(rv, NS_OK);
+
+ Json::Value root;
+ Json::CharReaderBuilder builder;
+ std::unique_ptr<Json::CharReader> const reader(builder.newCharReader());
+ ASSERT_TRUE(
+ reader->parse(data.BeginReading(), data.EndReading(), &root, nullptr));
+ ASSERT_TRUE(root.isArray());
+
+ for (uint32_t index = 0; index < root.size(); index++) {
+ const Json::Value& item = root[index];
+
+ if (!item.isObject()) {
+ continue;
+ }
+
+ const Json::Value& skip = item["skip"];
+ ASSERT_TRUE(skip.isNull() || skip.isBool());
+ if (skip.isBool() && skip.asBool()) {
+ continue;
+ }
+
+ const Json::Value& failure = item["failure"];
+ ASSERT_TRUE(failure.isNull() || failure.isBool());
+ if (failure.isBool() && failure.asBool()) {
+ continue;
+ }
+
+ const Json::Value& origin = item["origin"];
+ ASSERT_TRUE(origin.isNull() || origin.isString());
+ if (origin.isNull()) {
+ continue;
+ }
+ const char* originBegin;
+ const char* originEnd;
+ origin.getString(&originBegin, &originEnd);
+
+ const Json::Value& base = item["base"];
+ ASSERT_TRUE(base.isString());
+ const char* baseBegin;
+ const char* baseEnd;
+ base.getString(&baseBegin, &baseEnd);
+
+ const Json::Value& input = item["input"];
+ ASSERT_TRUE(input.isString());
+ const char* inputBegin;
+ const char* inputEnd;
+ input.getString(&inputBegin, &inputEnd);
+
+ CheckOrigin(nsDependentCString(inputBegin, inputEnd),
+ nsDependentCString(baseBegin, baseEnd),
+ nsDependentCString(originBegin, originEnd));
+ }
+}
diff --git a/netwerk/test/gtest/TestNamedPipeService.cpp b/netwerk/test/gtest/TestNamedPipeService.cpp
new file mode 100644
index 0000000000..c26424e46c
--- /dev/null
+++ b/netwerk/test/gtest/TestNamedPipeService.cpp
@@ -0,0 +1,279 @@
+/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* 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/. */
+
+#include "TestCommon.h"
+#include "gtest/gtest.h"
+
+#include <windows.h>
+
+#include "mozilla/Atomics.h"
+#include "mozilla/Monitor.h"
+#include "nsNamedPipeService.h"
+#include "nsNetCID.h"
+
+#define PIPE_NAME L"\\\\.\\pipe\\TestNPS"
+#define TEST_STR "Hello World"
+
+using namespace mozilla;
+
+/**
+ * Unlike a monitor, an event allows a thread to wait on another thread
+ * completing an action without regard to ordering of the wait and the notify.
+ */
+class Event {
+ public:
+ explicit Event(const char* aName) : mMonitor(aName) {}
+
+ ~Event() = default;
+
+ void Set() {
+ MonitorAutoLock lock(mMonitor);
+ MOZ_ASSERT(!mSignaled);
+ mSignaled = true;
+ mMonitor.Notify();
+ }
+ void Wait() {
+ MonitorAutoLock lock(mMonitor);
+ while (!mSignaled) {
+ lock.Wait();
+ }
+ mSignaled = false;
+ }
+
+ private:
+ Monitor mMonitor;
+ bool mSignaled = false;
+};
+
+class nsNamedPipeDataObserver final : public nsINamedPipeDataObserver {
+ public:
+ NS_DECL_THREADSAFE_ISUPPORTS
+ NS_DECL_NSINAMEDPIPEDATAOBSERVER
+
+ explicit nsNamedPipeDataObserver(HANDLE aPipe);
+
+ int Read(void* aBuffer, uint32_t aSize);
+ int Write(const void* aBuffer, uint32_t aSize);
+
+ uint32_t Transferred() const { return mBytesTransferred; }
+
+ private:
+ ~nsNamedPipeDataObserver() = default;
+
+ HANDLE mPipe;
+ OVERLAPPED mOverlapped;
+ Atomic<uint32_t> mBytesTransferred;
+ Event mEvent;
+};
+
+NS_IMPL_ISUPPORTS(nsNamedPipeDataObserver, nsINamedPipeDataObserver)
+
+nsNamedPipeDataObserver::nsNamedPipeDataObserver(HANDLE aPipe)
+ : mPipe(aPipe), mOverlapped(), mBytesTransferred(0), mEvent("named-pipe") {
+ mOverlapped.hEvent = CreateEventA(nullptr, TRUE, TRUE, "named-pipe");
+}
+
+int nsNamedPipeDataObserver::Read(void* aBuffer, uint32_t aSize) {
+ DWORD bytesRead = 0;
+ if (!ReadFile(mPipe, aBuffer, aSize, &bytesRead, &mOverlapped)) {
+ switch (GetLastError()) {
+ case ERROR_IO_PENDING: {
+ mEvent.Wait();
+ }
+ if (!GetOverlappedResult(mPipe, &mOverlapped, &bytesRead, FALSE)) {
+ ADD_FAILURE() << "GetOverlappedResult failed";
+ return -1;
+ }
+ if (mBytesTransferred != bytesRead) {
+ ADD_FAILURE() << "GetOverlappedResult mismatch";
+ return -1;
+ }
+
+ break;
+ default:
+ ADD_FAILURE() << "ReadFile error " << GetLastError();
+ return -1;
+ }
+ } else {
+ mEvent.Wait();
+
+ if (mBytesTransferred != bytesRead) {
+ ADD_FAILURE() << "GetOverlappedResult mismatch";
+ return -1;
+ }
+ }
+
+ mBytesTransferred = 0;
+ return bytesRead;
+}
+
+int nsNamedPipeDataObserver::Write(const void* aBuffer, uint32_t aSize) {
+ DWORD bytesWritten = 0;
+ if (!WriteFile(mPipe, aBuffer, aSize, &bytesWritten, &mOverlapped)) {
+ switch (GetLastError()) {
+ case ERROR_IO_PENDING: {
+ mEvent.Wait();
+ }
+ if (!GetOverlappedResult(mPipe, &mOverlapped, &bytesWritten, FALSE)) {
+ ADD_FAILURE() << "GetOverlappedResult failed";
+ return -1;
+ }
+ if (mBytesTransferred != bytesWritten) {
+ ADD_FAILURE() << "GetOverlappedResult mismatch";
+ return -1;
+ }
+
+ break;
+ default:
+ ADD_FAILURE() << "WriteFile error " << GetLastError();
+ return -1;
+ }
+ } else {
+ mEvent.Wait();
+
+ if (mBytesTransferred != bytesWritten) {
+ ADD_FAILURE() << "GetOverlappedResult mismatch";
+ return -1;
+ }
+ }
+
+ mBytesTransferred = 0;
+ return bytesWritten;
+}
+
+NS_IMETHODIMP
+nsNamedPipeDataObserver::OnDataAvailable(uint32_t aBytesTransferred,
+ void* aOverlapped) {
+ if (aOverlapped != &mOverlapped) {
+ ADD_FAILURE() << "invalid overlapped object";
+ return NS_ERROR_FAILURE;
+ }
+
+ DWORD bytesTransferred = 0;
+ BOOL ret =
+ GetOverlappedResult(mPipe, reinterpret_cast<LPOVERLAPPED>(aOverlapped),
+ &bytesTransferred, FALSE);
+
+ if (!ret) {
+ ADD_FAILURE() << "GetOverlappedResult failed";
+ return NS_ERROR_FAILURE;
+ }
+
+ if (bytesTransferred != aBytesTransferred) {
+ ADD_FAILURE() << "GetOverlappedResult mismatch";
+ return NS_ERROR_FAILURE;
+ }
+
+ mBytesTransferred += aBytesTransferred;
+ mEvent.Set();
+
+ return NS_OK;
+}
+
+NS_IMETHODIMP
+nsNamedPipeDataObserver::OnError(uint32_t aError, void* aOverlapped) {
+ return NS_ERROR_NOT_IMPLEMENTED;
+}
+
+BOOL CreateAndConnectInstance(LPOVERLAPPED aOverlapped, LPHANDLE aPipe);
+BOOL ConnectToNewClient(HANDLE aPipe, LPOVERLAPPED aOverlapped);
+
+BOOL CreateAndConnectInstance(LPOVERLAPPED aOverlapped, LPHANDLE aPipe) {
+ // FIXME: adjust parameters
+ *aPipe =
+ CreateNamedPipeW(PIPE_NAME, PIPE_ACCESS_DUPLEX | FILE_FLAG_OVERLAPPED,
+ PIPE_TYPE_MESSAGE | PIPE_READMODE_MESSAGE | PIPE_WAIT, 1,
+ 65536, 65536, 3000, NULL);
+
+ if (*aPipe == INVALID_HANDLE_VALUE) {
+ ADD_FAILURE() << "CreateNamedPipe failed " << GetLastError();
+ return FALSE;
+ }
+
+ return ConnectToNewClient(*aPipe, aOverlapped);
+}
+
+BOOL ConnectToNewClient(HANDLE aPipe, LPOVERLAPPED aOverlapped) {
+ if (ConnectNamedPipe(aPipe, aOverlapped)) {
+ ADD_FAILURE()
+ << "Unexpected, overlapped ConnectNamedPipe() always returns 0.";
+ return FALSE;
+ }
+
+ switch (GetLastError()) {
+ case ERROR_IO_PENDING:
+ return TRUE;
+
+ case ERROR_PIPE_CONNECTED:
+ if (SetEvent(aOverlapped->hEvent)) break;
+
+ default: // error
+ ADD_FAILURE() << "ConnectNamedPipe failed " << GetLastError();
+ break;
+ }
+
+ return FALSE;
+}
+
+static nsresult CreateNamedPipe(LPHANDLE aServer, LPHANDLE aClient) {
+ OVERLAPPED overlapped;
+ overlapped.hEvent = CreateEvent(NULL, TRUE, TRUE, NULL);
+ BOOL ret;
+
+ ret = CreateAndConnectInstance(&overlapped, aServer);
+ if (!ret) {
+ ADD_FAILURE() << "pipe server should be pending";
+ return NS_ERROR_FAILURE;
+ }
+
+ *aClient = CreateFileW(PIPE_NAME, GENERIC_READ | GENERIC_WRITE,
+ FILE_SHARE_READ | FILE_SHARE_WRITE, nullptr,
+ OPEN_EXISTING, FILE_FLAG_OVERLAPPED, nullptr);
+
+ if (*aClient == INVALID_HANDLE_VALUE) {
+ ADD_FAILURE() << "Unable to create pipe client";
+ CloseHandle(*aServer);
+ return NS_ERROR_FAILURE;
+ }
+
+ DWORD pipeMode = PIPE_READMODE_MESSAGE;
+ if (!SetNamedPipeHandleState(*aClient, &pipeMode, nullptr, nullptr)) {
+ ADD_FAILURE() << "SetNamedPipeHandleState error " << GetLastError();
+ CloseHandle(*aServer);
+ CloseHandle(*aClient);
+ return NS_ERROR_FAILURE;
+ }
+
+ WaitForSingleObjectEx(overlapped.hEvent, INFINITE, TRUE);
+
+ return NS_OK;
+}
+
+TEST(TestNamedPipeService, Test)
+{
+ nsCOMPtr<nsINamedPipeService> svc = net::NamedPipeService::GetOrCreate();
+
+ HANDLE readPipe, writePipe;
+ nsresult rv = CreateNamedPipe(&readPipe, &writePipe);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ RefPtr<nsNamedPipeDataObserver> readObserver =
+ new nsNamedPipeDataObserver(readPipe);
+ RefPtr<nsNamedPipeDataObserver> writeObserver =
+ new nsNamedPipeDataObserver(writePipe);
+
+ ASSERT_TRUE(NS_SUCCEEDED(svc->AddDataObserver(readPipe, readObserver)));
+ ASSERT_TRUE(NS_SUCCEEDED(svc->AddDataObserver(writePipe, writeObserver)));
+ ASSERT_EQ(std::size_t(writeObserver->Write(TEST_STR, sizeof(TEST_STR))),
+ sizeof(TEST_STR));
+
+ char buffer[sizeof(TEST_STR)];
+ ASSERT_EQ(std::size_t(readObserver->Read(buffer, sizeof(buffer))),
+ sizeof(TEST_STR));
+ ASSERT_STREQ(buffer, TEST_STR) << "I/O mismatch";
+
+ ASSERT_TRUE(NS_SUCCEEDED(svc->RemoveDataObserver(readPipe, readObserver)));
+ ASSERT_TRUE(NS_SUCCEEDED(svc->RemoveDataObserver(writePipe, writeObserver)));
+}
diff --git a/netwerk/test/gtest/TestNetworkLinkIdHashingDarwin.cpp b/netwerk/test/gtest/TestNetworkLinkIdHashingDarwin.cpp
new file mode 100644
index 0000000000..a07c9438bd
--- /dev/null
+++ b/netwerk/test/gtest/TestNetworkLinkIdHashingDarwin.cpp
@@ -0,0 +1,93 @@
+#include <arpa/inet.h>
+
+#include "gtest/gtest.h"
+#include "mozilla/SHA1.h"
+#include "nsString.h"
+#include "nsPrintfCString.h"
+#include "mozilla/Logging.h"
+#include "nsNetworkLinkService.h"
+
+using namespace mozilla;
+
+in6_addr StringToSockAddr(const std::string& str) {
+ sockaddr_in6 ip;
+ inet_pton(AF_INET6, str.c_str(), &(ip.sin6_addr));
+ return ip.sin6_addr;
+}
+
+TEST(TestNetworkLinkIdHashingDarwin, Single)
+{
+ // Setup
+ SHA1Sum expected_sha1;
+ SHA1Sum::Hash expected_digest;
+
+ in6_addr a1 = StringToSockAddr("2001:db8:8714:3a91::1");
+
+ // Prefix
+ expected_sha1.update(&a1, sizeof(in6_addr));
+ // Netmask
+ expected_sha1.update(&a1, sizeof(in6_addr));
+ expected_sha1.finish(expected_digest);
+
+ std::vector<prefix_and_netmask> prefixNetmaskStore;
+ prefixNetmaskStore.push_back(std::make_pair(a1, a1));
+ SHA1Sum actual_sha1;
+ // Run
+ nsNetworkLinkService::HashSortedPrefixesAndNetmasks(prefixNetmaskStore,
+ &actual_sha1);
+ SHA1Sum::Hash actual_digest;
+ actual_sha1.finish(actual_digest);
+
+ // Assert
+ ASSERT_EQ(0, memcmp(&expected_digest, &actual_digest, sizeof(SHA1Sum::Hash)));
+}
+
+TEST(TestNetworkLinkIdHashingDarwin, Multiple)
+{
+ // Setup
+ SHA1Sum expected_sha1;
+ SHA1Sum::Hash expected_digest;
+
+ std::vector<in6_addr> addresses;
+ addresses.push_back(StringToSockAddr("2001:db8:8714:3a91::1"));
+ addresses.push_back(StringToSockAddr("2001:db8:8714:3a91::2"));
+ addresses.push_back(StringToSockAddr("2001:db8:8714:3a91::3"));
+ addresses.push_back(StringToSockAddr("2001:db8:8714:3a91::4"));
+
+ for (const auto& address : addresses) {
+ // Prefix
+ expected_sha1.update(&address, sizeof(in6_addr));
+ // Netmask
+ expected_sha1.update(&address, sizeof(in6_addr));
+ }
+ expected_sha1.finish(expected_digest);
+
+ // Ordered
+ std::vector<prefix_and_netmask> ordered;
+ for (const auto& address : addresses) {
+ ordered.push_back(std::make_pair(address, address));
+ }
+ SHA1Sum ordered_sha1;
+
+ // Unordered
+ std::vector<prefix_and_netmask> reversed;
+ for (auto it = addresses.rbegin(); it != addresses.rend(); ++it) {
+ reversed.push_back(std::make_pair(*it, *it));
+ }
+ SHA1Sum reversed_sha1;
+
+ // Run
+ nsNetworkLinkService::HashSortedPrefixesAndNetmasks(ordered, &ordered_sha1);
+ SHA1Sum::Hash ordered_digest;
+ ordered_sha1.finish(ordered_digest);
+
+ nsNetworkLinkService::HashSortedPrefixesAndNetmasks(reversed, &reversed_sha1);
+ SHA1Sum::Hash reversed_digest;
+ reversed_sha1.finish(reversed_digest);
+
+ // Assert
+ ASSERT_EQ(0,
+ memcmp(&expected_digest, &ordered_digest, sizeof(SHA1Sum::Hash)));
+ ASSERT_EQ(0,
+ memcmp(&expected_digest, &reversed_digest, sizeof(SHA1Sum::Hash)));
+}
diff --git a/netwerk/test/gtest/TestNetworkLinkIdHashingWindows.cpp b/netwerk/test/gtest/TestNetworkLinkIdHashingWindows.cpp
new file mode 100644
index 0000000000..eb2097d0a4
--- /dev/null
+++ b/netwerk/test/gtest/TestNetworkLinkIdHashingWindows.cpp
@@ -0,0 +1,88 @@
+#include <combaseapi.h>
+
+#include "gtest/gtest.h"
+#include "mozilla/SHA1.h"
+#include "nsNotifyAddrListener.h"
+
+using namespace mozilla;
+
+GUID StringToGuid(const std::string& str) {
+ GUID guid;
+ sscanf(str.c_str(),
+ "%8lx-%4hx-%4hx-%2hhx%2hhx-%2hhx%2hhx%2hhx%2hhx%2hhx%2hhx",
+ &guid.Data1, &guid.Data2, &guid.Data3, &guid.Data4[0], &guid.Data4[1],
+ &guid.Data4[2], &guid.Data4[3], &guid.Data4[4], &guid.Data4[5],
+ &guid.Data4[6], &guid.Data4[7]);
+
+ return guid;
+}
+
+TEST(TestGuidHashWindows, Single)
+{
+ // Setup
+ SHA1Sum expected_sha1;
+ SHA1Sum::Hash expected_digest;
+
+ GUID g1 = StringToGuid("264555b1-289c-4494-83d1-e158d1d95115");
+
+ expected_sha1.update(&g1, sizeof(GUID));
+ expected_sha1.finish(expected_digest);
+
+ std::vector<GUID> nwGUIDS;
+ nwGUIDS.push_back(g1);
+ SHA1Sum actual_sha1;
+ // Run
+ nsNotifyAddrListener::HashSortedNetworkIds(nwGUIDS, actual_sha1);
+ SHA1Sum::Hash actual_digest;
+ actual_sha1.finish(actual_digest);
+
+ // Assert
+ ASSERT_EQ(0, memcmp(&expected_digest, &actual_digest, sizeof(SHA1Sum::Hash)));
+}
+
+TEST(TestNetworkLinkIdHashingWindows, Multiple)
+{
+ // Setup
+ SHA1Sum expected_sha1;
+ SHA1Sum::Hash expected_digest;
+
+ std::vector<GUID> nwGUIDS;
+ nwGUIDS.push_back(StringToGuid("00000000-0000-0000-0000-000000000001"));
+ nwGUIDS.push_back(StringToGuid("00000000-0000-0000-0000-000000000002"));
+ nwGUIDS.push_back(StringToGuid("00000000-0000-0000-0000-000000000003"));
+ nwGUIDS.push_back(StringToGuid("00000000-0000-0000-0000-000000000004"));
+
+ for (const auto& guid : nwGUIDS) {
+ expected_sha1.update(&guid, sizeof(GUID));
+ }
+ expected_sha1.finish(expected_digest);
+
+ // Ordered
+ std::vector<GUID> ordered;
+ for (const auto& guid : nwGUIDS) {
+ ordered.push_back(guid);
+ }
+ SHA1Sum ordered_sha1;
+
+ // Unordered
+ std::vector<GUID> reversed;
+ for (auto it = nwGUIDS.rbegin(); it != nwGUIDS.rend(); ++it) {
+ reversed.push_back(*it);
+ }
+ SHA1Sum reversed_sha1;
+
+ // Run
+ nsNotifyAddrListener::HashSortedNetworkIds(ordered, ordered_sha1);
+ SHA1Sum::Hash ordered_digest;
+ ordered_sha1.finish(ordered_digest);
+
+ nsNotifyAddrListener::HashSortedNetworkIds(reversed, reversed_sha1);
+ SHA1Sum::Hash reversed_digest;
+ reversed_sha1.finish(reversed_digest);
+
+ // Assert
+ ASSERT_EQ(0,
+ memcmp(&expected_digest, &ordered_digest, sizeof(SHA1Sum::Hash)));
+ ASSERT_EQ(0,
+ memcmp(&expected_digest, &reversed_digest, sizeof(SHA1Sum::Hash)));
+}
diff --git a/netwerk/test/gtest/TestPACMan.cpp b/netwerk/test/gtest/TestPACMan.cpp
new file mode 100644
index 0000000000..52a34b4897
--- /dev/null
+++ b/netwerk/test/gtest/TestPACMan.cpp
@@ -0,0 +1,242 @@
+#include "gtest/gtest.h"
+#include "nsServiceManagerUtils.h"
+#include "../../../xpcom/threads/nsThreadManager.h"
+#include "nsIDHCPClient.h"
+#include "nsIPrefBranch.h"
+#include "nsComponentManager.h"
+#include "mozilla/ModuleUtils.h"
+#include "mozilla/GenericFactory.h"
+#include "../../base/nsPACMan.h"
+
+#define TEST_WPAD_DHCP_OPTION "http://pac/pac.dat"
+#define TEST_ASSIGNED_PAC_URL "http://assignedpac/pac.dat"
+#define WPAD_PREF 4
+#define NETWORK_PROXY_TYPE_PREF_NAME "network.proxy.type"
+#define GETTING_NETWORK_PROXY_TYPE_FAILED -1
+
+nsCString WPADOptionResult;
+
+namespace mozilla {
+namespace net {
+
+nsresult SetNetworkProxyType(int32_t pref) {
+ nsCOMPtr<nsIPrefBranch> prefs = do_GetService(NS_PREFSERVICE_CONTRACTID);
+
+ if (!prefs) {
+ return NS_ERROR_FACTORY_NOT_REGISTERED;
+ }
+ return prefs->SetIntPref(NETWORK_PROXY_TYPE_PREF_NAME, pref);
+}
+
+nsresult GetNetworkProxyType(int32_t* pref) {
+ nsCOMPtr<nsIPrefBranch> prefs = do_GetService(NS_PREFSERVICE_CONTRACTID);
+
+ if (!prefs) {
+ return NS_ERROR_FACTORY_NOT_REGISTERED;
+ }
+ return prefs->GetIntPref(NETWORK_PROXY_TYPE_PREF_NAME, pref);
+}
+
+class nsTestDHCPClient final : public nsIDHCPClient {
+ public:
+ NS_DECL_THREADSAFE_ISUPPORTS
+ NS_DECL_NSIDHCPCLIENT
+
+ nsTestDHCPClient() = default;
+
+ nsresult Init() { return NS_OK; };
+
+ private:
+ ~nsTestDHCPClient() = default;
+};
+
+NS_IMETHODIMP
+nsTestDHCPClient::GetOption(uint8_t option, nsACString& _retval) {
+ _retval.Assign(WPADOptionResult);
+ return NS_OK;
+}
+
+NS_IMPL_ISUPPORTS(nsTestDHCPClient, nsIDHCPClient)
+
+#define NS_TESTDHCPCLIENTSERVICE_CID /* {FEBF1D69-4D7D-4891-9524-045AD18B5593} \
+ */ \
+ { \
+ 0xFEBF1D69, 0x4D7D, 0x4891, { \
+ 0x95, 0x24, 0x04, 0x5a, 0xd1, 0x8b, 0x55, 0x93 \
+ } \
+ }
+
+NS_GENERIC_FACTORY_CONSTRUCTOR_INIT(nsTestDHCPClient, Init)
+NS_DEFINE_NAMED_CID(NS_TESTDHCPCLIENTSERVICE_CID);
+
+void SetOptionResult(const char* result) { WPADOptionResult.Assign(result); }
+
+class ProcessPendingEventsAction final : public Runnable {
+ public:
+ ProcessPendingEventsAction() : Runnable("net::ProcessPendingEventsAction") {}
+
+ NS_IMETHOD
+ Run() override {
+ if (NS_HasPendingEvents(nullptr)) {
+ NS_WARNING("Found pending requests on PAC thread");
+ nsresult rv;
+ rv = NS_ProcessPendingEvents(nullptr);
+ EXPECT_EQ(NS_OK, rv);
+ }
+ NS_WARNING("No pending requests on PAC thread");
+ return NS_OK;
+ }
+};
+
+class TestPACMan : public ::testing::Test {
+ protected:
+ RefPtr<nsPACMan> mPACMan;
+
+ void ProcessAllEvents() {
+ ProcessPendingEventsOnPACThread();
+ nsresult rv;
+ while (NS_HasPendingEvents(nullptr)) {
+ NS_WARNING("Pending events on main thread");
+ rv = NS_ProcessPendingEvents(nullptr);
+ ASSERT_EQ(NS_OK, rv);
+ ProcessPendingEventsOnPACThread();
+ }
+ NS_WARNING("End of pending events on main thread");
+ }
+
+ // This method is used to ensure that all pending events on the main thread
+ // and the Proxy thread are processsed.
+ // It iterates over ProcessAllEvents because simply calling ProcessAllEvents
+ // once did not reliably process the events on both threads on all platforms.
+ void ProcessAllEventsTenTimes() {
+ for (int i = 0; i < 10; i++) {
+ ProcessAllEvents();
+ }
+ }
+
+ virtual void SetUp() {
+ ASSERT_EQ(NS_OK, GetNetworkProxyType(&originalNetworkProxyTypePref));
+ nsCOMPtr<nsIFactory> factory;
+ nsresult rv = nsComponentManagerImpl::gComponentManager->GetClassObject(
+ kNS_TESTDHCPCLIENTSERVICE_CID, NS_GET_IID(nsIFactory),
+ getter_AddRefs(factory));
+ if (NS_SUCCEEDED(rv) && factory) {
+ rv = nsComponentManagerImpl::gComponentManager->UnregisterFactory(
+ kNS_TESTDHCPCLIENTSERVICE_CID, factory);
+ ASSERT_EQ(NS_OK, rv);
+ }
+ factory = new mozilla::GenericFactory(nsTestDHCPClientConstructor);
+ nsComponentManagerImpl::gComponentManager->RegisterFactory(
+ kNS_TESTDHCPCLIENTSERVICE_CID, "nsTestDHCPClient",
+ NS_DHCPCLIENT_CONTRACTID, factory);
+
+ mPACMan = new nsPACMan(nullptr);
+ mPACMan->SetWPADOverDHCPEnabled(true);
+ mPACMan->Init(nullptr);
+ ASSERT_EQ(NS_OK, SetNetworkProxyType(WPAD_PREF));
+ }
+
+ virtual void TearDown() {
+ mPACMan->Shutdown();
+ if (originalNetworkProxyTypePref != GETTING_NETWORK_PROXY_TYPE_FAILED) {
+ ASSERT_EQ(NS_OK, SetNetworkProxyType(originalNetworkProxyTypePref));
+ }
+ }
+
+ nsCOMPtr<nsIDHCPClient> GetPACManDHCPCient() { return mPACMan->mDHCPClient; }
+
+ void SetPACManDHCPCient(nsCOMPtr<nsIDHCPClient> aValue) {
+ mPACMan->mDHCPClient = aValue;
+ }
+
+ void AssertPACSpecEqualTo(const char* aExpected) {
+ ASSERT_STREQ(aExpected, mPACMan->mPACURISpec.Data());
+ }
+
+ private:
+ int32_t originalNetworkProxyTypePref = GETTING_NETWORK_PROXY_TYPE_FAILED;
+
+ void ProcessPendingEventsOnPACThread() {
+ RefPtr<ProcessPendingEventsAction> action =
+ new ProcessPendingEventsAction();
+
+ mPACMan->DispatchToPAC(action.forget(), /*aSync =*/true);
+ }
+};
+
+TEST_F(TestPACMan, TestCreateDHCPClientAndGetOption) {
+ SetOptionResult(TEST_WPAD_DHCP_OPTION);
+ nsCString spec;
+
+ GetPACManDHCPCient()->GetOption(252, spec);
+
+ ASSERT_STREQ(TEST_WPAD_DHCP_OPTION, spec.Data());
+}
+
+TEST_F(TestPACMan, TestCreateDHCPClientAndGetEmptyOption) {
+ SetOptionResult("");
+ nsCString spec;
+ spec.AssignLiteral(TEST_ASSIGNED_PAC_URL);
+
+ GetPACManDHCPCient()->GetOption(252, spec);
+
+ ASSERT_TRUE(spec.IsEmpty());
+}
+
+TEST_F(TestPACMan,
+ WhenTheDHCPClientExistsAndDHCPIsNonEmptyDHCPOptionIsUsedAsPACUri) {
+ SetOptionResult(TEST_WPAD_DHCP_OPTION);
+
+ mPACMan->LoadPACFromURI(""_ns);
+ ProcessAllEventsTenTimes();
+
+ ASSERT_STREQ(TEST_WPAD_DHCP_OPTION, WPADOptionResult.Data());
+ AssertPACSpecEqualTo(TEST_WPAD_DHCP_OPTION);
+}
+
+TEST_F(TestPACMan, WhenTheDHCPResponseIsEmptyWPADDefaultsToStandardURL) {
+ SetOptionResult(""_ns.Data());
+
+ mPACMan->LoadPACFromURI(""_ns);
+ ASSERT_TRUE(NS_HasPendingEvents(nullptr));
+ ProcessAllEventsTenTimes();
+
+ ASSERT_STREQ("", WPADOptionResult.Data());
+ AssertPACSpecEqualTo("http://wpad/wpad.dat");
+}
+
+TEST_F(TestPACMan, WhenThereIsNoDHCPClientWPADDefaultsToStandardURL) {
+ SetOptionResult(TEST_WPAD_DHCP_OPTION);
+ SetPACManDHCPCient(nullptr);
+
+ mPACMan->LoadPACFromURI(""_ns);
+ ProcessAllEventsTenTimes();
+
+ ASSERT_STREQ(TEST_WPAD_DHCP_OPTION, WPADOptionResult.Data());
+ AssertPACSpecEqualTo("http://wpad/wpad.dat");
+}
+
+TEST_F(TestPACMan, WhenWPADOverDHCPIsPreffedOffWPADDefaultsToStandardURL) {
+ SetOptionResult(TEST_WPAD_DHCP_OPTION);
+ mPACMan->SetWPADOverDHCPEnabled(false);
+
+ mPACMan->LoadPACFromURI(""_ns);
+ ProcessAllEventsTenTimes();
+
+ ASSERT_STREQ(TEST_WPAD_DHCP_OPTION, WPADOptionResult.Data());
+ AssertPACSpecEqualTo("http://wpad/wpad.dat");
+}
+
+TEST_F(TestPACMan, WhenPACUriIsSetDirectlyItIsUsedRatherThanWPAD) {
+ SetOptionResult(TEST_WPAD_DHCP_OPTION);
+ nsCString spec;
+ spec.AssignLiteral(TEST_ASSIGNED_PAC_URL);
+
+ mPACMan->LoadPACFromURI(spec);
+ ProcessAllEventsTenTimes();
+
+ AssertPACSpecEqualTo(TEST_ASSIGNED_PAC_URL);
+}
+
+} // namespace net
+} // namespace mozilla
diff --git a/netwerk/test/gtest/TestPartiallySeekableInputStream.cpp b/netwerk/test/gtest/TestPartiallySeekableInputStream.cpp
new file mode 100644
index 0000000000..1dffd6fcaf
--- /dev/null
+++ b/netwerk/test/gtest/TestPartiallySeekableInputStream.cpp
@@ -0,0 +1,494 @@
+#include "gtest/gtest.h"
+
+#include "Helpers.h"
+#include "nsCOMPtr.h"
+#include "nsStreamUtils.h"
+#include "nsString.h"
+#include "nsStringStream.h"
+#include "mozilla/SpinEventLoopUntil.h"
+#include "mozilla/net/PartiallySeekableInputStream.h"
+
+using mozilla::GetCurrentSerialEventTarget;
+using mozilla::SpinEventLoopUntil;
+using mozilla::net::PartiallySeekableInputStream;
+
+class NonSeekableStream final : public nsIInputStream {
+ nsCOMPtr<nsIInputStream> mStream;
+
+ public:
+ NS_DECL_THREADSAFE_ISUPPORTS
+
+ explicit NonSeekableStream(const nsACString& aBuffer) {
+ NS_NewCStringInputStream(getter_AddRefs(mStream), aBuffer);
+ }
+
+ NS_IMETHOD
+ Available(uint64_t* aLength) override { return mStream->Available(aLength); }
+
+ NS_IMETHOD
+ Read(char* aBuffer, uint32_t aCount, uint32_t* aReadCount) override {
+ return mStream->Read(aBuffer, aCount, aReadCount);
+ }
+
+ NS_IMETHOD
+ ReadSegments(nsWriteSegmentFun aWriter, void* aClosure, uint32_t aCount,
+ uint32_t* aResult) override {
+ return mStream->ReadSegments(aWriter, aClosure, aCount, aResult);
+ }
+
+ NS_IMETHOD
+ Close() override { return mStream->Close(); }
+
+ NS_IMETHOD
+ IsNonBlocking(bool* aNonBlocking) override {
+ return mStream->IsNonBlocking(aNonBlocking);
+ }
+
+ private:
+ ~NonSeekableStream() = default;
+};
+
+NS_IMPL_ISUPPORTS(NonSeekableStream, nsIInputStream)
+
+// Helper function for creating a non-seekable nsIInputStream + a
+// PartiallySeekableInputStream.
+PartiallySeekableInputStream* CreateStream(uint32_t aSize, uint64_t aStreamSize,
+ nsCString& aBuffer) {
+ aBuffer.SetLength(aSize);
+ for (uint32_t i = 0; i < aSize; ++i) {
+ aBuffer.BeginWriting()[i] = i % 10;
+ }
+
+ RefPtr<NonSeekableStream> stream = new NonSeekableStream(aBuffer);
+ return new PartiallySeekableInputStream(stream.forget(), aStreamSize);
+}
+
+// Simple reading.
+TEST(TestPartiallySeekableInputStream, SimpleRead)
+{
+ const size_t kBufSize = 10;
+
+ nsCString buf;
+ RefPtr<PartiallySeekableInputStream> psi = CreateStream(kBufSize, 5, buf);
+
+ uint64_t length;
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize, length);
+
+ char buf2[kBufSize];
+ uint32_t count;
+ ASSERT_EQ(NS_OK, psi->Read(buf2, sizeof(buf2), &count));
+ ASSERT_EQ(count, buf.Length());
+ ASSERT_TRUE(nsCString(buf.get(), kBufSize).Equals(nsCString(buf2, count)));
+
+ // At this point, after reading more than the buffer size, seek is not
+ // allowed.
+ ASSERT_EQ(NS_ERROR_NOT_IMPLEMENTED,
+ psi->Seek(nsISeekableStream::NS_SEEK_SET, 0));
+
+ ASSERT_EQ(NS_ERROR_NOT_IMPLEMENTED,
+ psi->Seek(nsISeekableStream::NS_SEEK_END, 0));
+
+ ASSERT_EQ(NS_ERROR_NOT_IMPLEMENTED,
+ psi->Seek(nsISeekableStream::NS_SEEK_CUR, 0));
+
+ // Position is at the end of the stream.
+ int64_t pos;
+ ASSERT_EQ(NS_OK, psi->Tell(&pos));
+ ASSERT_EQ((int64_t)kBufSize, pos);
+}
+
+// Simple seek
+TEST(TestPartiallySeekableInputStream, SimpleSeek)
+{
+ const size_t kBufSize = 10;
+
+ nsCString buf;
+ RefPtr<PartiallySeekableInputStream> psi = CreateStream(kBufSize, 5, buf);
+
+ uint64_t length;
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize, length);
+
+ uint32_t count;
+
+ {
+ char buf2[3];
+ ASSERT_EQ(NS_OK, psi->Read(buf2, sizeof(buf2), &count));
+ ASSERT_EQ(count, sizeof(buf2));
+ ASSERT_TRUE(nsCString(buf.get(), sizeof(buf2))
+ .Equals(nsCString(buf2, sizeof(buf2))));
+
+ int64_t pos;
+ ASSERT_EQ(NS_OK, psi->Tell(&pos));
+ ASSERT_EQ((int64_t)sizeof(buf2), pos);
+
+ uint64_t length;
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize - sizeof(buf2), length);
+ }
+
+ // Let's seek back to the beginning using NS_SEEK_SET
+ ASSERT_EQ(NS_OK, psi->Seek(nsISeekableStream::NS_SEEK_SET, 0));
+
+ {
+ uint64_t length;
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize, length);
+
+ char buf2[3];
+ ASSERT_EQ(NS_OK, psi->Read(buf2, sizeof(buf2), &count));
+ ASSERT_EQ(count, sizeof(buf2));
+ ASSERT_TRUE(nsCString(buf.get(), sizeof(buf2))
+ .Equals(nsCString(buf2, sizeof(buf2))));
+
+ int64_t pos;
+ ASSERT_EQ(NS_OK, psi->Tell(&pos));
+ ASSERT_EQ((int64_t)sizeof(buf2), pos);
+
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize - sizeof(buf2), length);
+ }
+
+ // Let's seek back of 2 bytes using NS_SEEK_CUR
+ ASSERT_EQ(NS_OK, psi->Seek(nsISeekableStream::NS_SEEK_CUR, -2));
+
+ {
+ uint64_t length;
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize - 1, length);
+
+ char buf2[3];
+ ASSERT_EQ(NS_OK, psi->Read(buf2, sizeof(buf2), &count));
+ ASSERT_EQ(count, sizeof(buf2));
+ ASSERT_TRUE(nsCString(buf.get() + 1, sizeof(buf2))
+ .Equals(nsCString(buf2, sizeof(buf2))));
+
+ int64_t pos;
+ ASSERT_EQ(NS_OK, psi->Tell(&pos));
+ ASSERT_EQ((int64_t)sizeof(buf2) + 1, pos);
+
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize - sizeof(buf2) - 1, length);
+ }
+
+ // Let's seek back to the beginning using NS_SEEK_SET
+ ASSERT_EQ(NS_OK, psi->Seek(nsISeekableStream::NS_SEEK_SET, 0));
+
+ {
+ uint64_t length;
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize, length);
+
+ char buf2[kBufSize];
+ ASSERT_EQ(NS_OK, psi->Read(buf2, sizeof(buf2), &count));
+ ASSERT_EQ(count, buf.Length());
+ ASSERT_TRUE(nsCString(buf.get(), kBufSize).Equals(nsCString(buf2, count)));
+ }
+}
+
+// Full in cache
+TEST(TestPartiallySeekableInputStream, FullCachedSeek)
+{
+ const size_t kBufSize = 10;
+
+ nsCString buf;
+ RefPtr<PartiallySeekableInputStream> psi = CreateStream(kBufSize, 4096, buf);
+
+ uint64_t length;
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize, length);
+
+ char buf2[kBufSize];
+ uint32_t count;
+ ASSERT_EQ(NS_OK, psi->Read(buf2, sizeof(buf2), &count));
+ ASSERT_EQ(count, buf.Length());
+ ASSERT_TRUE(nsCString(buf.get(), kBufSize).Equals(nsCString(buf2, count)));
+
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)0, length);
+
+ ASSERT_EQ(NS_OK, psi->Seek(nsISeekableStream::NS_SEEK_SET, 0));
+
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)kBufSize, length);
+
+ ASSERT_EQ(NS_OK, psi->Read(buf2, sizeof(buf2), &count));
+ ASSERT_EQ(count, buf.Length());
+ ASSERT_TRUE(nsCString(buf.get(), kBufSize).Equals(nsCString(buf2, count)));
+
+ ASSERT_EQ(NS_OK, psi->Available(&length));
+ ASSERT_EQ((uint64_t)0, length);
+}
+
+TEST(TestPartiallySeekableInputStream, QIInputStreamLength)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ for (int i = 0; i < 4; i++) {
+ nsCOMPtr<nsIInputStream> psis;
+ {
+ RefPtr<testing::LengthInputStream> stream =
+ new testing::LengthInputStream(buf, i % 2, i > 1);
+ psis = new PartiallySeekableInputStream(stream.forget());
+ }
+
+ {
+ nsCOMPtr<nsIInputStreamLength> qi = do_QueryInterface(psis);
+ ASSERT_EQ(!!(i % 2), !!qi);
+ }
+
+ {
+ nsCOMPtr<nsIAsyncInputStreamLength> qi = do_QueryInterface(psis);
+ ASSERT_EQ(i > 1, !!qi);
+ }
+ }
+}
+
+TEST(TestPartiallySeekableInputStream, InputStreamLength)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ nsCOMPtr<nsIInputStream> psis;
+ {
+ RefPtr<testing::LengthInputStream> stream =
+ new testing::LengthInputStream(buf, true, false);
+ psis = new PartiallySeekableInputStream(stream.forget());
+ }
+
+ nsCOMPtr<nsIInputStreamLength> qi = do_QueryInterface(psis);
+ ASSERT_TRUE(!!qi);
+
+ int64_t size;
+ nsresult rv = qi->Length(&size);
+ ASSERT_EQ(NS_OK, rv);
+ ASSERT_EQ(buf.Length(), size);
+}
+
+TEST(TestPartiallySeekableInputStream, NegativeInputStreamLength)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ nsCOMPtr<nsIInputStream> psis;
+ {
+ RefPtr<testing::LengthInputStream> stream =
+ new testing::LengthInputStream(buf, true, false, NS_OK, true);
+ psis = new PartiallySeekableInputStream(stream.forget());
+ }
+
+ nsCOMPtr<nsIInputStreamLength> qi = do_QueryInterface(psis);
+ ASSERT_TRUE(!!qi);
+
+ int64_t size;
+ nsresult rv = qi->Length(&size);
+ ASSERT_EQ(NS_OK, rv);
+ ASSERT_EQ(-1, size);
+}
+
+TEST(TestPartiallySeekableInputStream, AsyncInputStreamLength)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ nsCOMPtr<nsIInputStream> psis;
+ {
+ RefPtr<testing::LengthInputStream> stream =
+ new testing::LengthInputStream(buf, false, true);
+ psis = new PartiallySeekableInputStream(stream.forget());
+ }
+
+ nsCOMPtr<nsIAsyncInputStreamLength> qi = do_QueryInterface(psis);
+ ASSERT_TRUE(!!qi);
+
+ RefPtr<testing::LengthCallback> callback = new testing::LengthCallback();
+
+ nsresult rv = qi->AsyncLengthWait(callback, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+ ASSERT_EQ(buf.Length(), callback->Size());
+}
+
+TEST(TestPartiallySeekableInputStream, NegativeAsyncInputStreamLength)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ nsCOMPtr<nsIInputStream> psis;
+ {
+ RefPtr<testing::LengthInputStream> stream =
+ new testing::LengthInputStream(buf, false, true, NS_OK, true);
+ psis = new PartiallySeekableInputStream(stream.forget());
+ }
+
+ nsCOMPtr<nsIAsyncInputStreamLength> qi = do_QueryInterface(psis);
+ ASSERT_TRUE(!!qi);
+
+ RefPtr<testing::LengthCallback> callback = new testing::LengthCallback();
+
+ nsresult rv = qi->AsyncLengthWait(callback, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+ ASSERT_EQ(-1, callback->Size());
+}
+
+TEST(TestPartiallySeekableInputStream, AbortLengthCallback)
+{
+ nsCString buf;
+ buf.AssignLiteral("Hello world");
+
+ nsCOMPtr<nsIInputStream> psis;
+ {
+ RefPtr<testing::LengthInputStream> stream =
+ new testing::LengthInputStream(buf, false, true, NS_OK, true);
+ psis = new PartiallySeekableInputStream(stream.forget());
+ }
+
+ nsCOMPtr<nsIAsyncInputStreamLength> qi = do_QueryInterface(psis);
+ ASSERT_TRUE(!!qi);
+
+ RefPtr<testing::LengthCallback> callback1 = new testing::LengthCallback();
+ nsresult rv = qi->AsyncLengthWait(callback1, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ RefPtr<testing::LengthCallback> callback2 = new testing::LengthCallback();
+ rv = qi->AsyncLengthWait(callback2, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback2->Called(); }));
+ ASSERT_TRUE(!callback1->Called());
+ ASSERT_EQ(-1, callback2->Size());
+}
+
+TEST(TestPartiallySeekableInputStream, AsyncWaitAfterConsumed)
+{
+ nsCString buf{"The Quick Brown Fox Jumps over the Lazy Dog"};
+ const size_t bufsize = 44;
+
+ auto stream = MakeRefPtr<testing::AsyncStringStream>(buf);
+ nsCOMPtr<nsIAsyncInputStream> psis =
+ new PartiallySeekableInputStream(stream.forget(), bufsize);
+ ASSERT_TRUE(psis);
+
+ auto callback = MakeRefPtr<testing::InputStreamCallback>();
+
+ nsresult rv = psis->AsyncWait(callback, 0, 0, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+
+ char rdbuf[bufsize] = {'\0'};
+ uint32_t count;
+ ASSERT_EQ(NS_OK, psis->Read(rdbuf, sizeof(rdbuf), &count));
+ ASSERT_STREQ(rdbuf, buf.Data());
+
+ callback = MakeRefPtr<testing::InputStreamCallback>();
+
+ rv = psis->AsyncWait(callback, 0, 0, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+
+ memset(rdbuf, 0x0, bufsize);
+ ASSERT_EQ(NS_OK, psis->Read(rdbuf, sizeof(rdbuf), &count));
+ ASSERT_EQ(0U, count);
+}
+
+TEST(TestPartiallySeekableInputStream, AsyncWaitAfterClosed)
+{
+ nsCString buf{"The Quick Brown Fox Jumps over the Lazy Dog"};
+ const size_t bufsize = 44;
+
+ auto stream = MakeRefPtr<testing::AsyncStringStream>(buf);
+ nsCOMPtr<nsIAsyncInputStream> psis =
+ new PartiallySeekableInputStream(stream.forget(), bufsize);
+ ASSERT_TRUE(psis);
+
+ auto callback = MakeRefPtr<testing::InputStreamCallback>();
+
+ nsresult rv = psis->AsyncWait(callback, 0, 0, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+
+ ASSERT_EQ(NS_OK, psis->Close());
+
+ callback = MakeRefPtr<testing::InputStreamCallback>();
+
+ rv = psis->AsyncWait(callback, 0, 0, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+}
+
+TEST(TestPartiallySeekableInputStream, AsyncLengthWaitAfterClosed)
+{
+ nsCString buf{"The Quick Brown Fox Jumps over the Lazy Dog"};
+
+ auto stream = MakeRefPtr<testing::LengthInputStream>(buf, false, true);
+ nsCOMPtr<nsIInputStream> psis =
+ new PartiallySeekableInputStream(stream.forget());
+
+ nsCOMPtr<nsIAsyncInputStreamLength> qi = do_QueryInterface(psis);
+ ASSERT_TRUE(qi);
+
+ auto callback = MakeRefPtr<testing::LengthCallback>();
+
+ nsresult rv = qi->AsyncLengthWait(callback, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+ ASSERT_EQ(buf.Length(), callback->Size());
+
+ ASSERT_EQ(NS_OK, psis->Close());
+
+ callback = MakeRefPtr<testing::LengthCallback>();
+
+ rv = qi->AsyncLengthWait(callback, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+ ASSERT_EQ(-1, callback->Size());
+}
+
+TEST(TestPartiallySeekableInputStream, AsyncLengthWaitAfterConsumed)
+{
+ nsCString buf{"The Quick Brown Fox Jumps over the Lazy Dog"};
+ const size_t bufsize = 44;
+
+ auto stream = MakeRefPtr<testing::LengthInputStream>(buf, false, true);
+ nsCOMPtr<nsIInputStream> psis =
+ new PartiallySeekableInputStream(stream.forget());
+
+ nsCOMPtr<nsIAsyncInputStreamLength> qi = do_QueryInterface(psis);
+ ASSERT_TRUE(qi);
+
+ auto callback = MakeRefPtr<testing::LengthCallback>();
+
+ nsresult rv = qi->AsyncLengthWait(callback, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+ ASSERT_EQ(buf.Length(), callback->Size());
+
+ char rdbuf[bufsize] = {'\0'};
+ uint32_t count;
+ ASSERT_EQ(NS_OK, psis->Read(rdbuf, sizeof(rdbuf), &count));
+ ASSERT_STREQ(rdbuf, buf.Data());
+
+ callback = MakeRefPtr<testing::LengthCallback>();
+
+ rv = qi->AsyncLengthWait(callback, GetCurrentSerialEventTarget());
+ ASSERT_EQ(NS_OK, rv);
+
+ MOZ_ALWAYS_TRUE(SpinEventLoopUntil([&]() { return callback->Called(); }));
+ ASSERT_EQ(0U, callback->Size());
+
+ memset(rdbuf, 0x0, bufsize);
+ ASSERT_EQ(NS_OK, psis->Read(rdbuf, sizeof(rdbuf), &count));
+ ASSERT_EQ(0U, count);
+}
diff --git a/netwerk/test/gtest/TestProtocolProxyService.cpp b/netwerk/test/gtest/TestProtocolProxyService.cpp
new file mode 100644
index 0000000000..a26f5f62a8
--- /dev/null
+++ b/netwerk/test/gtest/TestProtocolProxyService.cpp
@@ -0,0 +1,164 @@
+#include "gtest/gtest.h"
+
+#include "nsCOMPtr.h"
+#include "nsNetCID.h"
+#include "nsString.h"
+#include "nsComponentManagerUtils.h"
+#include "../../base/nsProtocolProxyService.h"
+#include "nsServiceManagerUtils.h"
+#include "mozilla/Preferences.h"
+#include "nsNetUtil.h"
+
+namespace mozilla {
+namespace net {
+
+TEST(TestProtocolProxyService, LoadHostFilters)
+{
+ nsCOMPtr<nsIProtocolProxyService2> ps =
+ do_GetService(NS_PROTOCOLPROXYSERVICE_CID);
+ ASSERT_TRUE(ps);
+ mozilla::net::nsProtocolProxyService* pps =
+ static_cast<mozilla::net::nsProtocolProxyService*>(ps.get());
+
+ nsCOMPtr<nsIURI> url;
+ nsAutoCString spec;
+
+ auto CheckLoopbackURLs = [&](bool expected) {
+ // loopback IPs are always filtered
+ spec = "http://127.0.0.1";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+ spec = "http://[::1]";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+ spec = "http://localhost";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+ };
+
+ auto CheckURLs = [&](bool expected) {
+ spec = "http://example.com";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+
+ spec = "https://10.2.3.4";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 443), expected);
+
+ spec = "http://1.2.3.4";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+
+ spec = "http://1.2.3.4:8080";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+
+ spec = "http://[2001::1]";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+
+ spec = "http://2.3.4.5:7777";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+
+ spec = "http://[abcd::2]:123";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+
+ spec = "http://bla.test.com";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+ };
+
+ auto CheckPortDomain = [&](bool expected) {
+ spec = "http://blabla.com:10";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+ };
+
+ auto CheckLocalDomain = [&](bool expected) {
+ spec = "http://test";
+ ASSERT_EQ(NS_NewURI(getter_AddRefs(url), spec), NS_OK);
+ ASSERT_EQ(pps->CanUseProxy(url, 80), expected);
+ };
+
+ // --------------------------------------------------------------------------
+
+ nsAutoCString filter;
+
+ // Anything is allowed when there are no filters set
+ printf("Testing empty filter: %s\n", filter.get());
+ pps->LoadHostFilters(filter);
+
+ CheckLoopbackURLs(false);
+ CheckLocalDomain(true);
+ CheckURLs(true);
+ CheckPortDomain(true);
+
+ // --------------------------------------------------------------------------
+
+ filter =
+ "example.com, 1.2.3.4/16, [2001::1], 10.0.0.0/8, 2.3.0.0/16:7777, "
+ "[abcd::1]/64:123, *.test.com";
+ printf("Testing filter: %s\n", filter.get());
+ pps->LoadHostFilters(filter);
+
+ CheckLoopbackURLs(false);
+ // Check URLs can no longer use filtered proxy
+ CheckURLs(false);
+ CheckLocalDomain(true);
+ CheckPortDomain(true);
+
+ // --------------------------------------------------------------------------
+
+ // This is space separated. See bug 1346711 comment 4. We check this to keep
+ // backwards compatibility.
+ filter = "<local> blabla.com:10";
+ printf("Testing filter: %s\n", filter.get());
+ pps->LoadHostFilters(filter);
+
+ CheckLoopbackURLs(false);
+ CheckURLs(true);
+ CheckLocalDomain(false);
+ CheckPortDomain(false);
+
+ // Check that we don't crash on weird input
+ filter = "a b c abc:1x2, ,, * ** *.* *:10 :20 :40/12 */12:90";
+ printf("Testing filter: %s\n", filter.get());
+ pps->LoadHostFilters(filter);
+
+ // Check that filtering works properly when the filter is set to "<local>"
+ filter = "<local>";
+ printf("Testing filter: %s\n", filter.get());
+ pps->LoadHostFilters(filter);
+
+ CheckLoopbackURLs(false);
+ CheckURLs(true);
+ CheckLocalDomain(false);
+ CheckPortDomain(true);
+
+ // Check that allow_hijacking_localhost works with empty filter
+ Preferences::SetBool("network.proxy.allow_hijacking_localhost", true);
+
+ filter = "";
+ printf("Testing filter: %s\n", filter.get());
+ pps->LoadHostFilters(filter);
+
+ CheckLoopbackURLs(true);
+ CheckLocalDomain(true);
+ CheckURLs(true);
+ CheckPortDomain(true);
+
+ // Check that allow_hijacking_localhost works with non-trivial filter
+ filter = "127.0.0.1, [::1], localhost, blabla.com:10";
+ printf("Testing filter: %s\n", filter.get());
+ pps->LoadHostFilters(filter);
+
+ CheckLoopbackURLs(false);
+ CheckLocalDomain(true);
+ CheckURLs(true);
+ CheckPortDomain(false);
+}
+
+} // namespace net
+} // namespace mozilla
diff --git a/netwerk/test/gtest/TestReadStreamToString.cpp b/netwerk/test/gtest/TestReadStreamToString.cpp
new file mode 100644
index 0000000000..f5fa0a4979
--- /dev/null
+++ b/netwerk/test/gtest/TestReadStreamToString.cpp
@@ -0,0 +1,190 @@
+#include "gtest/gtest.h"
+
+#include "Helpers.h"
+#include "nsCOMPtr.h"
+#include "nsNetUtil.h"
+#include "nsStringStream.h"
+
+// Here we test the reading a pre-allocated size
+TEST(TestReadStreamToString, SyncStreamPreAllocatedSize)
+{
+ nsCString buffer;
+ buffer.AssignLiteral("Hello world!");
+
+ nsCOMPtr<nsIInputStream> stream;
+ ASSERT_EQ(NS_OK, NS_NewCStringInputStream(getter_AddRefs(stream), buffer));
+
+ uint64_t written;
+ nsAutoCString result;
+ result.SetLength(5);
+
+ void* ptr = result.BeginWriting();
+
+ ASSERT_EQ(NS_OK, NS_ReadInputStreamToString(stream, result, 5, &written));
+ ASSERT_EQ((uint64_t)5, written);
+ ASSERT_TRUE(nsCString(buffer.get(), 5).Equals(result));
+
+ // The pointer should be equal: no relocation.
+ ASSERT_EQ(ptr, result.BeginWriting());
+}
+
+// Here we test the reading the full size of a sync stream
+TEST(TestReadStreamToString, SyncStreamFullSize)
+{
+ nsCString buffer;
+ buffer.AssignLiteral("Hello world!");
+
+ nsCOMPtr<nsIInputStream> stream;
+ ASSERT_EQ(NS_OK, NS_NewCStringInputStream(getter_AddRefs(stream), buffer));
+
+ uint64_t written;
+ nsAutoCString result;
+
+ ASSERT_EQ(NS_OK, NS_ReadInputStreamToString(stream, result, buffer.Length(),
+ &written));
+ ASSERT_EQ(buffer.Length(), written);
+ ASSERT_TRUE(buffer.Equals(result));
+}
+
+// Here we test the reading less than the full size of a sync stream
+TEST(TestReadStreamToString, SyncStreamLessThan)
+{
+ nsCString buffer;
+ buffer.AssignLiteral("Hello world!");
+
+ nsCOMPtr<nsIInputStream> stream;
+ ASSERT_EQ(NS_OK, NS_NewCStringInputStream(getter_AddRefs(stream), buffer));
+
+ uint64_t written;
+ nsAutoCString result;
+
+ ASSERT_EQ(NS_OK, NS_ReadInputStreamToString(stream, result, 5, &written));
+ ASSERT_EQ((uint64_t)5, written);
+ ASSERT_TRUE(nsCString(buffer.get(), 5).Equals(result));
+}
+
+// Here we test the reading more than the full size of a sync stream
+TEST(TestReadStreamToString, SyncStreamMoreThan)
+{
+ nsCString buffer;
+ buffer.AssignLiteral("Hello world!");
+
+ nsCOMPtr<nsIInputStream> stream;
+ ASSERT_EQ(NS_OK, NS_NewCStringInputStream(getter_AddRefs(stream), buffer));
+
+ uint64_t written;
+ nsAutoCString result;
+
+ // Reading more than the buffer size.
+ ASSERT_EQ(NS_OK, NS_ReadInputStreamToString(stream, result,
+ buffer.Length() + 5, &written));
+ ASSERT_EQ(buffer.Length(), written);
+ ASSERT_TRUE(buffer.Equals(result));
+}
+
+// Here we test the reading a sync stream without passing the size
+TEST(TestReadStreamToString, SyncStreamUnknownSize)
+{
+ nsCString buffer;
+ buffer.AssignLiteral("Hello world!");
+
+ nsCOMPtr<nsIInputStream> stream;
+ ASSERT_EQ(NS_OK, NS_NewCStringInputStream(getter_AddRefs(stream), buffer));
+
+ uint64_t written;
+ nsAutoCString result;
+
+ // Reading all without passing the size
+ ASSERT_EQ(NS_OK, NS_ReadInputStreamToString(stream, result, -1, &written));
+ ASSERT_EQ(buffer.Length(), written);
+ ASSERT_TRUE(buffer.Equals(result));
+}
+
+// Here we test the reading the full size of an async stream
+TEST(TestReadStreamToString, AsyncStreamFullSize)
+{
+ nsCString buffer;
+ buffer.AssignLiteral("Hello world!");
+
+ nsCOMPtr<nsIInputStream> stream = new testing::AsyncStringStream(buffer);
+
+ uint64_t written;
+ nsAutoCString result;
+
+ ASSERT_EQ(NS_OK, NS_ReadInputStreamToString(stream, result, buffer.Length(),
+ &written));
+ ASSERT_EQ(buffer.Length(), written);
+ ASSERT_TRUE(buffer.Equals(result));
+}
+
+// Here we test the reading less than the full size of an async stream
+TEST(TestReadStreamToString, AsyncStreamLessThan)
+{
+ nsCString buffer;
+ buffer.AssignLiteral("Hello world!");
+
+ nsCOMPtr<nsIInputStream> stream = new testing::AsyncStringStream(buffer);
+
+ uint64_t written;
+ nsAutoCString result;
+
+ ASSERT_EQ(NS_OK, NS_ReadInputStreamToString(stream, result, 5, &written));
+ ASSERT_EQ((uint64_t)5, written);
+ ASSERT_TRUE(nsCString(buffer.get(), 5).Equals(result));
+}
+
+// Here we test the reading more than the full size of an async stream
+TEST(TestReadStreamToString, AsyncStreamMoreThan)
+{
+ nsCString buffer;
+ buffer.AssignLiteral("Hello world!");
+
+ nsCOMPtr<nsIInputStream> stream = new testing::AsyncStringStream(buffer);
+
+ uint64_t written;
+ nsAutoCString result;
+
+ // Reading more than the buffer size.
+ ASSERT_EQ(NS_OK, NS_ReadInputStreamToString(stream, result,
+ buffer.Length() + 5, &written));
+ ASSERT_EQ(buffer.Length(), written);
+ ASSERT_TRUE(buffer.Equals(result));
+}
+
+// Here we test the reading an async stream without passing the size
+TEST(TestReadStreamToString, AsyncStreamUnknownSize)
+{
+ nsCString buffer;
+ buffer.AssignLiteral("Hello world!");
+
+ nsCOMPtr<nsIInputStream> stream = new testing::AsyncStringStream(buffer);
+
+ uint64_t written;
+ nsAutoCString result;
+
+ // Reading all without passing the size
+ ASSERT_EQ(NS_OK, NS_ReadInputStreamToString(stream, result, -1, &written));
+ ASSERT_EQ(buffer.Length(), written);
+ ASSERT_TRUE(buffer.Equals(result));
+}
+
+// Here we test the reading an async big stream without passing the size
+TEST(TestReadStreamToString, AsyncStreamUnknownBigSize)
+{
+ nsCString buffer;
+
+ buffer.SetLength(4096 * 2);
+ for (uint32_t i = 0; i < 4096 * 2; ++i) {
+ buffer.BeginWriting()[i] = i % 10;
+ }
+
+ nsCOMPtr<nsIInputStream> stream = new testing::AsyncStringStream(buffer);
+
+ uint64_t written;
+ nsAutoCString result;
+
+ // Reading all without passing the size
+ ASSERT_EQ(NS_OK, NS_ReadInputStreamToString(stream, result, -1, &written));
+ ASSERT_EQ(buffer.Length(), written);
+ ASSERT_TRUE(buffer.Equals(result));
+}
diff --git a/netwerk/test/gtest/TestServerTimingHeader.cpp b/netwerk/test/gtest/TestServerTimingHeader.cpp
new file mode 100644
index 0000000000..159e5bd7bc
--- /dev/null
+++ b/netwerk/test/gtest/TestServerTimingHeader.cpp
@@ -0,0 +1,239 @@
+#include "gtest/gtest.h"
+
+#include "mozilla/Unused.h"
+#include "mozilla/net/nsServerTiming.h"
+#include <string>
+#include <vector>
+
+using namespace mozilla;
+using namespace mozilla::net;
+
+void testServerTimingHeader(
+ const char* headerValue,
+ std::vector<std::vector<std::string>> expectedResults) {
+ nsAutoCString header(headerValue);
+ ServerTimingParser parser(header);
+ parser.Parse();
+
+ nsTArray<nsCOMPtr<nsIServerTiming>> results =
+ parser.TakeServerTimingHeaders();
+
+ ASSERT_EQ(results.Length(), expectedResults.size());
+
+ unsigned i = 0;
+ for (const auto& header : results) {
+ std::vector<std::string> expectedResult(expectedResults[i++]);
+ nsCString name;
+ mozilla::Unused << header->GetName(name);
+ ASSERT_TRUE(name.Equals(expectedResult[0].c_str()));
+
+ double duration;
+ mozilla::Unused << header->GetDuration(&duration);
+ ASSERT_EQ(duration, atof(expectedResult[1].c_str()));
+
+ nsCString description;
+ mozilla::Unused << header->GetDescription(description);
+ ASSERT_TRUE(description.Equals(expectedResult[2].c_str()));
+ }
+}
+
+TEST(TestServerTimingHeader, HeaderParsing)
+{
+ // Test cases below are copied from
+ // https://cs.chromium.org/chromium/src/third_party/WebKit/Source/platform/network/HTTPParsersTest.cpp
+
+ testServerTimingHeader("", {});
+ testServerTimingHeader("metric", {{"metric", "0", ""}});
+ testServerTimingHeader("metric;dur", {{"metric", "0", ""}});
+ testServerTimingHeader("metric;dur=123.4", {{"metric", "123.4", ""}});
+ testServerTimingHeader("metric;dur=\"123.4\"", {{"metric", "123.4", ""}});
+
+ testServerTimingHeader("metric;desc", {{"metric", "0", ""}});
+ testServerTimingHeader("metric;desc=description",
+ {{"metric", "0", "description"}});
+ testServerTimingHeader("metric;desc=\"description\"",
+ {{"metric", "0", "description"}});
+
+ testServerTimingHeader("metric;dur;desc", {{"metric", "0", ""}});
+ testServerTimingHeader("metric;dur=123.4;desc", {{"metric", "123.4", ""}});
+ testServerTimingHeader("metric;dur;desc=description",
+ {{"metric", "0", "description"}});
+ testServerTimingHeader("metric;dur=123.4;desc=description",
+ {{"metric", "123.4", "description"}});
+ testServerTimingHeader("metric;desc;dur", {{"metric", "0", ""}});
+ testServerTimingHeader("metric;desc;dur=123.4", {{"metric", "123.4", ""}});
+ testServerTimingHeader("metric;desc=description;dur",
+ {{"metric", "0", "description"}});
+ testServerTimingHeader("metric;desc=description;dur=123.4",
+ {{"metric", "123.4", "description"}});
+
+ // special chars in name
+ testServerTimingHeader("aB3!#$%&'*+-.^_`|~",
+ {{"aB3!#$%&'*+-.^_`|~", "0", ""}});
+
+ // delimiter chars in quoted description
+ testServerTimingHeader("metric;desc=\"descr;,=iption\";dur=123.4",
+ {{"metric", "123.4", "descr;,=iption"}});
+
+ // whitespace
+ testServerTimingHeader("metric ; ", {{"metric", "0", ""}});
+ testServerTimingHeader("metric , ", {{"metric", "0", ""}});
+ testServerTimingHeader("metric ; dur = 123.4 ; desc = description",
+ {{"metric", "123.4", "description"}});
+ testServerTimingHeader("metric ; desc = description ; dur = 123.4",
+ {{"metric", "123.4", "description"}});
+
+ // multiple entries
+ testServerTimingHeader(
+ "metric1;dur=12.3;desc=description1,metric2;dur=45.6;"
+ "desc=description2,metric3;dur=78.9;desc=description3",
+ {{"metric1", "12.3", "description1"},
+ {"metric2", "45.6", "description2"},
+ {"metric3", "78.9", "description3"}});
+ testServerTimingHeader("metric1,metric2 ,metric3, metric4 , metric5",
+ {{"metric1", "0", ""},
+ {"metric2", "0", ""},
+ {"metric3", "0", ""},
+ {"metric4", "0", ""},
+ {"metric5", "0", ""}});
+
+ // quoted-strings
+ // metric;desc=\ --> ''
+ testServerTimingHeader("metric;desc=\\", {{"metric", "0", ""}});
+ // metric;desc=" --> ''
+ testServerTimingHeader("metric;desc=\"", {{"metric", "0", ""}});
+ // metric;desc=\\ --> ''
+ testServerTimingHeader("metric;desc=\\\\", {{"metric", "0", ""}});
+ // metric;desc=\" --> ''
+ testServerTimingHeader("metric;desc=\\\"", {{"metric", "0", ""}});
+ // metric;desc="\ --> ''
+ testServerTimingHeader("metric;desc=\"\\", {{"metric", "0", ""}});
+ // metric;desc="" --> ''
+ testServerTimingHeader("metric;desc=\"\"", {{"metric", "0", ""}});
+ // metric;desc=\\\ --> ''
+ testServerTimingHeader("metric;desc=\\\\\\", {{"metric", "0", ""}});
+ // metric;desc=\\" --> ''
+ testServerTimingHeader("metric;desc=\\\\\"", {{"metric", "0", ""}});
+ // metric;desc=\"\ --> ''
+ testServerTimingHeader("metric;desc=\\\"\\", {{"metric", "0", ""}});
+ // metric;desc=\"" --> ''
+ testServerTimingHeader("metric;desc=\\\"\"", {{"metric", "0", ""}});
+ // metric;desc="\\ --> ''
+ testServerTimingHeader("metric;desc=\"\\\\", {{"metric", "0", ""}});
+ // metric;desc="\" --> ''
+ testServerTimingHeader("metric;desc=\"\\\"", {{"metric", "0", ""}});
+ // metric;desc=""\ --> ''
+ testServerTimingHeader("metric;desc=\"\"\\", {{"metric", "0", ""}});
+ // metric;desc=""" --> ''
+ testServerTimingHeader("metric;desc=\"\"\"", {{"metric", "0", ""}});
+ // metric;desc=\\\\ --> ''
+ testServerTimingHeader("metric;desc=\\\\\\\\", {{"metric", "0", ""}});
+ // metric;desc=\\\" --> ''
+ testServerTimingHeader("metric;desc=\\\\\\\"", {{"metric", "0", ""}});
+ // metric;desc=\\"\ --> ''
+ testServerTimingHeader("metric;desc=\\\\\"\\", {{"metric", "0", ""}});
+ // metric;desc=\\"" --> ''
+ testServerTimingHeader("metric;desc=\\\\\"\"", {{"metric", "0", ""}});
+ // metric;desc=\"\\ --> ''
+ testServerTimingHeader("metric;desc=\\\"\\\\", {{"metric", "0", ""}});
+ // metric;desc=\"\" --> ''
+ testServerTimingHeader("metric;desc=\\\"\\\"", {{"metric", "0", ""}});
+ // metric;desc=\""\ --> ''
+ testServerTimingHeader("metric;desc=\\\"\"\\", {{"metric", "0", ""}});
+ // metric;desc=\""" --> ''
+ testServerTimingHeader("metric;desc=\\\"\"\"", {{"metric", "0", ""}});
+ // metric;desc="\\\ --> ''
+ testServerTimingHeader("metric;desc=\"\\\\\\", {{"metric", "0", ""}});
+ // metric;desc="\\" --> '\'
+ testServerTimingHeader("metric;desc=\"\\\\\"", {{"metric", "0", "\\"}});
+ // metric;desc="\"\ --> ''
+ testServerTimingHeader("metric;desc=\"\\\"\\", {{"metric", "0", ""}});
+ // metric;desc="\"" --> '"'
+ testServerTimingHeader("metric;desc=\"\\\"\"", {{"metric", "0", "\""}});
+ // metric;desc=""\\ --> ''
+ testServerTimingHeader("metric;desc=\"\"\\\\", {{"metric", "0", ""}});
+ // metric;desc=""\" --> ''
+ testServerTimingHeader("metric;desc=\"\"\\\"", {{"metric", "0", ""}});
+ // metric;desc="""\ --> ''
+ testServerTimingHeader("metric;desc=\"\"\"\\", {{"metric", "0", ""}});
+ // metric;desc="""" --> ''
+ testServerTimingHeader("metric;desc=\"\"\"\"", {{"metric", "0", ""}});
+
+ // duplicate entry names
+ testServerTimingHeader(
+ "metric;dur=12.3;desc=description1,metric;dur=45.6;"
+ "desc=description2",
+ {{"metric", "12.3", "description1"}, {"metric", "45.6", "description2"}});
+
+ // non-numeric durations
+ testServerTimingHeader("metric;dur=foo", {{"metric", "0", ""}});
+ testServerTimingHeader("metric;dur=\"foo\"", {{"metric", "0", ""}});
+
+ // unrecognized param names
+ testServerTimingHeader(
+ "metric;foo=bar;desc=description;foo=bar;dur=123.4;foo=bar",
+ {{"metric", "123.4", "description"}});
+
+ // duplicate param names
+ testServerTimingHeader("metric;dur=123.4;dur=567.8",
+ {{"metric", "123.4", ""}});
+ testServerTimingHeader("metric;desc=description1;desc=description2",
+ {{"metric", "0", "description1"}});
+ testServerTimingHeader("metric;dur=foo;dur=567.8", {{"metric", "", ""}});
+
+ // unspecified param values
+ testServerTimingHeader("metric;dur;dur=123.4", {{"metric", "0", ""}});
+ testServerTimingHeader("metric;desc;desc=description", {{"metric", "0", ""}});
+
+ // param name case
+ testServerTimingHeader("metric;DuR=123.4;DeSc=description",
+ {{"metric", "123.4", "description"}});
+
+ // nonsense
+ testServerTimingHeader("metric=foo;dur;dur=123.4,metric2",
+ {{"metric", "0", ""}, {"metric2", "0", ""}});
+ testServerTimingHeader("metric\"foo;dur;dur=123.4,metric2",
+ {{"metric", "0", ""}});
+
+ // nonsense - return zero entries
+ testServerTimingHeader(" ", {});
+ testServerTimingHeader("=", {});
+ testServerTimingHeader("[", {});
+ testServerTimingHeader("]", {});
+ testServerTimingHeader(";", {});
+ testServerTimingHeader(",", {});
+ testServerTimingHeader("=;", {});
+ testServerTimingHeader(";=", {});
+ testServerTimingHeader("=,", {});
+ testServerTimingHeader(",=", {});
+ testServerTimingHeader(";,", {});
+ testServerTimingHeader(",;", {});
+ testServerTimingHeader("=;,", {});
+
+ // Invalid token
+ testServerTimingHeader("met=ric", {{"met", "0", ""}});
+ testServerTimingHeader("met ric", {{"met", "0", ""}});
+ testServerTimingHeader("met[ric", {{"met", "0", ""}});
+ testServerTimingHeader("met]ric", {{"met", "0", ""}});
+ testServerTimingHeader("metric;desc=desc=123, metric2",
+ {{"metric", "0", "desc"}, {"metric2", "0", ""}});
+ testServerTimingHeader("met ric;desc=de sc , metric2",
+ {{"met", "0", "de"}, {"metric2", "0", ""}});
+
+ // test cases from https://w3c.github.io/server-timing/#examples
+ testServerTimingHeader(
+ " miss, ,db;dur=53, app;dur=47.2 ",
+ {{"miss", "0", ""}, {"db", "53", ""}, {"app", "47.2", ""}});
+ testServerTimingHeader(" customView, dc;desc=atl ",
+ {{"customView", "0", ""}, {"dc", "0", "atl"}});
+ testServerTimingHeader(" total;dur=123.4 ", {{"total", "123.4", ""}});
+
+ // test cases for comma in quoted string
+ testServerTimingHeader(
+ " metric ; desc=\"descr\\\"\\\";,=iption\";dur=123.4",
+ {{"metric", "123.4", "descr\"\";,=iption"}});
+ testServerTimingHeader(
+ " metric2;dur=\"123.4\";;desc=\",;\\\",;,\";;, metric ; desc = \" "
+ "\\\", ;\\\" \"; dur=123.4,",
+ {{"metric2", "123.4", ",;\",;,"}, {"metric", "123.4", " \", ;\" "}});
+}
diff --git a/netwerk/test/gtest/TestSocketTransportService.cpp b/netwerk/test/gtest/TestSocketTransportService.cpp
new file mode 100644
index 0000000000..ce8c301c7d
--- /dev/null
+++ b/netwerk/test/gtest/TestSocketTransportService.cpp
@@ -0,0 +1,140 @@
+#include "gtest/gtest.h"
+
+#include "nsCOMPtr.h"
+#include "nsString.h"
+#include "nsComponentManagerUtils.h"
+#include "../../base/nsSocketTransportService2.h"
+#include "nsServiceManagerUtils.h"
+#include "nsThreadUtils.h"
+
+namespace mozilla {
+namespace net {
+
+TEST(TestSocketTransportService, PortRemappingPreferenceReading)
+{
+ nsCOMPtr<nsISocketTransportService> service =
+ do_GetService("@mozilla.org/network/socket-transport-service;1");
+ ASSERT_TRUE(service);
+
+ auto sts = gSocketTransportService;
+ ASSERT_TRUE(sts);
+
+ sts->Dispatch(
+ NS_NewRunnableFunction(
+ "test",
+ [&]() {
+ auto CheckPortRemap = [&](uint16_t input, uint16_t output) -> bool {
+ sts->ApplyPortRemap(&input);
+ return input == output;
+ };
+
+ // Ill-formed prefs
+ ASSERT_FALSE(sts->UpdatePortRemapPreference(";"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference(" ;"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("; "_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("foo"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference(" foo"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference(" foo "_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("10=20;"_ns));
+
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1="_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1,="_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-="_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-,="_ns));
+
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1=2,"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1=2-3"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-2,=3"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-2,3"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-2,3-4"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-2,3-4,"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-2,3-4="_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("10000000=10"_ns));
+
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1=2;3"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-4=2;3"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-4=2;3="_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-foo=2;3=15"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-4=foo;3=15"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-4=2;foo=15"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-4=2;3=foo"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1-4=2x3=15"_ns));
+ ASSERT_FALSE(sts->UpdatePortRemapPreference("1+4=2;3=15"_ns));
+
+ // Well-formed prefs
+ ASSERT_TRUE(sts->UpdatePortRemapPreference("1=2"_ns));
+ ASSERT_TRUE(CheckPortRemap(1, 2));
+ ASSERT_TRUE(CheckPortRemap(2, 2));
+ ASSERT_TRUE(CheckPortRemap(3, 3));
+
+ ASSERT_TRUE(sts->UpdatePortRemapPreference("10=20"_ns));
+ ASSERT_TRUE(CheckPortRemap(1, 1));
+ ASSERT_TRUE(CheckPortRemap(2, 2));
+ ASSERT_TRUE(CheckPortRemap(3, 3));
+ ASSERT_TRUE(CheckPortRemap(10, 20));
+
+ ASSERT_TRUE(sts->UpdatePortRemapPreference("100-200=1000"_ns));
+ ASSERT_TRUE(CheckPortRemap(10, 10));
+ ASSERT_TRUE(CheckPortRemap(99, 99));
+ ASSERT_TRUE(CheckPortRemap(100, 1000));
+ ASSERT_TRUE(CheckPortRemap(101, 1000));
+ ASSERT_TRUE(CheckPortRemap(200, 1000));
+ ASSERT_TRUE(CheckPortRemap(201, 201));
+
+ ASSERT_TRUE(sts->UpdatePortRemapPreference("100-200,500=1000"_ns));
+ ASSERT_TRUE(CheckPortRemap(10, 10));
+ ASSERT_TRUE(CheckPortRemap(99, 99));
+ ASSERT_TRUE(CheckPortRemap(100, 1000));
+ ASSERT_TRUE(CheckPortRemap(101, 1000));
+ ASSERT_TRUE(CheckPortRemap(200, 1000));
+ ASSERT_TRUE(CheckPortRemap(201, 201));
+ ASSERT_TRUE(CheckPortRemap(499, 499));
+ ASSERT_TRUE(CheckPortRemap(500, 1000));
+ ASSERT_TRUE(CheckPortRemap(501, 501));
+
+ ASSERT_TRUE(sts->UpdatePortRemapPreference("1-3=10;5-8,12=20"_ns));
+ ASSERT_TRUE(CheckPortRemap(1, 10));
+ ASSERT_TRUE(CheckPortRemap(2, 10));
+ ASSERT_TRUE(CheckPortRemap(3, 10));
+ ASSERT_TRUE(CheckPortRemap(4, 4));
+ ASSERT_TRUE(CheckPortRemap(5, 20));
+ ASSERT_TRUE(CheckPortRemap(8, 20));
+ ASSERT_TRUE(CheckPortRemap(11, 11));
+ ASSERT_TRUE(CheckPortRemap(12, 20));
+
+ ASSERT_TRUE(sts->UpdatePortRemapPreference("80=8080;443=8080"_ns));
+ ASSERT_TRUE(CheckPortRemap(80, 8080));
+ ASSERT_TRUE(CheckPortRemap(443, 8080));
+
+ // Later rules rewrite earlier rules
+ ASSERT_TRUE(sts->UpdatePortRemapPreference("10=100;10=200"_ns));
+ ASSERT_TRUE(CheckPortRemap(10, 200));
+
+ ASSERT_TRUE(
+ sts->UpdatePortRemapPreference("10-20=100;10-20=200"_ns));
+ ASSERT_TRUE(CheckPortRemap(10, 200));
+ ASSERT_TRUE(CheckPortRemap(20, 200));
+
+ ASSERT_TRUE(sts->UpdatePortRemapPreference("10-20=100;15=200"_ns));
+ ASSERT_TRUE(CheckPortRemap(10, 100));
+ ASSERT_TRUE(CheckPortRemap(15, 200));
+ ASSERT_TRUE(CheckPortRemap(20, 100));
+
+ ASSERT_TRUE(sts->UpdatePortRemapPreference(
+ " 100 - 200 = 1000 ; 150 = 2000 "_ns));
+ ASSERT_TRUE(CheckPortRemap(100, 1000));
+ ASSERT_TRUE(CheckPortRemap(150, 2000));
+ ASSERT_TRUE(CheckPortRemap(200, 1000));
+
+ // Turn off any mapping
+ ASSERT_TRUE(sts->UpdatePortRemapPreference(""_ns));
+ for (uint32_t port = 0; port < 65536; ++port) {
+ ASSERT_TRUE(CheckPortRemap((uint16_t)port, (uint16_t)port));
+ }
+ }),
+ NS_DISPATCH_SYNC);
+}
+
+} // namespace net
+} // namespace mozilla
diff --git a/netwerk/test/gtest/TestStandardURL.cpp b/netwerk/test/gtest/TestStandardURL.cpp
new file mode 100644
index 0000000000..b6a6e71764
--- /dev/null
+++ b/netwerk/test/gtest/TestStandardURL.cpp
@@ -0,0 +1,359 @@
+#include "gtest/gtest.h"
+#include "gtest/MozGTestBench.h" // For MOZ_GTEST_BENCH
+
+#include "nsCOMPtr.h"
+#include "nsNetCID.h"
+#include "nsIURL.h"
+#include "nsIStandardURL.h"
+#include "nsString.h"
+#include "nsPrintfCString.h"
+#include "nsComponentManagerUtils.h"
+#include "nsIURIMutator.h"
+#include "mozilla/ipc/URIUtils.h"
+#include "mozilla/Unused.h"
+
+// In nsStandardURL.cpp
+extern nsresult Test_NormalizeIPv4(const nsACString& host, nsCString& result);
+
+TEST(TestStandardURL, Simple)
+{
+ nsCOMPtr<nsIURI> url;
+ ASSERT_EQ(NS_MutateURI(NS_STANDARDURLMUTATOR_CONTRACTID)
+ .SetSpec("http://example.com"_ns)
+ .Finalize(url),
+ NS_OK);
+ ASSERT_TRUE(url);
+
+ ASSERT_EQ(NS_MutateURI(url).SetSpec("http://example.com"_ns).Finalize(url),
+ NS_OK);
+
+ nsAutoCString out;
+
+ ASSERT_EQ(url->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "http://example.com/"_ns);
+
+ ASSERT_EQ(url->Resolve("foo.html?q=45"_ns, out), NS_OK);
+ ASSERT_TRUE(out == "http://example.com/foo.html?q=45"_ns);
+
+ ASSERT_EQ(NS_MutateURI(url).SetScheme("foo"_ns).Finalize(url), NS_OK);
+
+ ASSERT_EQ(url->GetScheme(out), NS_OK);
+ ASSERT_TRUE(out == "foo"_ns);
+
+ ASSERT_EQ(url->GetHost(out), NS_OK);
+ ASSERT_TRUE(out == "example.com"_ns);
+ ASSERT_EQ(NS_MutateURI(url).SetHost("www.yahoo.com"_ns).Finalize(url), NS_OK);
+ ASSERT_EQ(url->GetHost(out), NS_OK);
+ ASSERT_TRUE(out == "www.yahoo.com"_ns);
+
+ ASSERT_EQ(NS_MutateURI(url)
+ .SetPathQueryRef(nsLiteralCString(
+ "/some-path/one-the-net/about.html?with-a-query#for-you"))
+ .Finalize(url),
+ NS_OK);
+ ASSERT_EQ(url->GetPathQueryRef(out), NS_OK);
+ ASSERT_TRUE(out ==
+ nsLiteralCString(
+ "/some-path/one-the-net/about.html?with-a-query#for-you"));
+
+ ASSERT_EQ(NS_MutateURI(url)
+ .SetQuery(nsLiteralCString(
+ "a=b&d=c&what-ever-you-want-to-be-called=45"))
+ .Finalize(url),
+ NS_OK);
+ ASSERT_EQ(url->GetQuery(out), NS_OK);
+ ASSERT_TRUE(out == "a=b&d=c&what-ever-you-want-to-be-called=45"_ns);
+
+ ASSERT_EQ(NS_MutateURI(url).SetRef("#some-book-mark"_ns).Finalize(url),
+ NS_OK);
+ ASSERT_EQ(url->GetRef(out), NS_OK);
+ ASSERT_TRUE(out == "some-book-mark"_ns);
+}
+
+TEST(TestStandardURL, NormalizeGood)
+{
+ nsCString result;
+ const char* manual[] = {"0.0.0.0",
+ "0.0.0.0",
+ "0",
+ "0.0.0.0",
+ "000",
+ "0.0.0.0",
+ "0x00",
+ "0.0.0.0",
+ "10.20.100.200",
+ "10.20.100.200",
+ "255.255.255.255",
+ "255.255.255.255",
+ "0XFF.0xFF.0xff.0xFf",
+ "255.255.255.255",
+ "0x000ff.0X00FF.0x0ff.0xff",
+ "255.255.255.255",
+ "0x000fA.0X00FB.0x0fC.0xfD",
+ "250.251.252.253",
+ "0x000fE.0X00FF.0x0fC.0xfD",
+ "254.255.252.253",
+ "0x000fa.0x00fb.0x0fc.0xfd",
+ "250.251.252.253",
+ "0x000fe.0x00ff.0x0fc.0xfd",
+ "254.255.252.253",
+ "0377.0377.0377.0377",
+ "255.255.255.255",
+ "0000377.000377.00377.0377",
+ "255.255.255.255",
+ "65535",
+ "0.0.255.255",
+ "0xfFFf",
+ "0.0.255.255",
+ "0x00000ffff",
+ "0.0.255.255",
+ "0177777",
+ "0.0.255.255",
+ "000177777",
+ "0.0.255.255",
+ "0.13.65535",
+ "0.13.255.255",
+ "0.22.0xffff",
+ "0.22.255.255",
+ "0.123.0177777",
+ "0.123.255.255",
+ "65536",
+ "0.1.0.0",
+ "0200000",
+ "0.1.0.0",
+ "0x10000",
+ "0.1.0.0"};
+ for (uint32_t i = 0; i < sizeof(manual) / sizeof(manual[0]); i += 2) {
+ nsCString encHost(manual[i + 0]);
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHost, result));
+ ASSERT_TRUE(result.Equals(manual[i + 1]));
+ }
+
+ // Make sure we're getting the numbers correctly interpreted:
+ for (int i = 0; i < 256; i++) {
+ nsCString encHost = nsPrintfCString("0x%x", i);
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHost, result));
+ ASSERT_TRUE(result.Equals(nsPrintfCString("0.0.0.%d", i)));
+
+ encHost = nsPrintfCString("0%o", i);
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHost, result));
+ ASSERT_TRUE(result.Equals(nsPrintfCString("0.0.0.%d", i)));
+ }
+
+ // Some random numbers in the range, mixing hex, decimal, octal
+ for (int i = 0; i < 8; i++) {
+ int val[4] = {i * 11 + 13, i * 18 + 22, i * 4 + 28, i * 15 + 2};
+
+ nsCString encHost =
+ nsPrintfCString("%d.%d.%d.%d", val[0], val[1], val[2], val[3]);
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHost, result));
+ ASSERT_TRUE(result.Equals(encHost));
+
+ nsCString encHostM =
+ nsPrintfCString("0x%x.0x%x.0x%x.0x%x", val[0], val[1], val[2], val[3]);
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHostM, result));
+ ASSERT_TRUE(result.Equals(encHost));
+
+ encHostM =
+ nsPrintfCString("0%o.0%o.0%o.0%o", val[0], val[1], val[2], val[3]);
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHostM, result));
+ ASSERT_TRUE(result.Equals(encHost));
+
+ encHostM =
+ nsPrintfCString("0x%x.%d.0%o.%d", val[0], val[1], val[2], val[3]);
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHostM, result));
+ ASSERT_TRUE(result.Equals(encHost));
+
+ encHostM =
+ nsPrintfCString("%d.0%o.0%o.0x%x", val[0], val[1], val[2], val[3]);
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHostM, result));
+ ASSERT_TRUE(result.Equals(encHost));
+
+ encHostM =
+ nsPrintfCString("0%o.0%o.0x%x.0x%x", val[0], val[1], val[2], val[3]);
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHostM, result));
+ ASSERT_TRUE(result.Equals(encHost));
+ }
+}
+
+TEST(TestStandardURL, NormalizeBad)
+{
+ nsAutoCString result;
+ const char* manual[] = {
+ "x22.232.12.32", "122..12.32", "122.12.32.12.32", "122.12.32..",
+ "122.12.xx.22", "122.12.0xx.22", "0xx.12.01.22", "0x.12.01.22",
+ "12.12.02x.22", "1q.12.2.22", "122.01f.02.22", "12a.01.02.22",
+ "12.01.02.20x1", "10x2.01.02.20", "0xx.01.02.20", "10.x.02.20",
+ "10.00x2.02.20", "10.13.02x2.20", "10.x13.02.20", "10.0x134def.02.20",
+ "\0.2.2.2", "256.2.2.2", "2.256.2.2", "2.2.256.2",
+ "2.2.2.256", "2.2.-2.3", "+2.2.2.3", "13.0x2x2.2.3",
+ "0x2x2.13.2.3"};
+
+ for (uint32_t i = 0; i < sizeof(manual) / sizeof(manual[0]); i++) {
+ nsCString encHost(manual[i]);
+ ASSERT_EQ(NS_ERROR_FAILURE, Test_NormalizeIPv4(encHost, result));
+ }
+}
+
+TEST(TestStandardURL, From_test_standardurldotjs)
+{
+ // These are test (success and failure) cases from test_standardurl.js
+ nsAutoCString result;
+
+ const char* localIPv4s[] = {
+ "127.0.0.1",
+ "127.0.1",
+ "127.1",
+ "2130706433",
+ "0177.00.00.01",
+ "0177.00.01",
+ "0177.01",
+ "00000000000000000000000000177.0000000.0000000.0001",
+ "000000177.0000001",
+ "017700000001",
+ "0x7f.0x00.0x00.0x01",
+ "0x7f.0x01",
+ "0x7f000001",
+ "0x007f.0x0000.0x0000.0x0001",
+ "000177.0.00000.0x0001",
+ "127.0.0.1.",
+
+ "0X7F.0X00.0X00.0X01",
+ "0X7F.0X01",
+ "0X7F000001",
+ "0X007F.0X0000.0X0000.0X0001",
+ "000177.0.00000.0X0001"};
+ for (uint32_t i = 0; i < sizeof(localIPv4s) / sizeof(localIPv4s[0]); i++) {
+ nsCString encHost(localIPv4s[i]);
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHost, result));
+ ASSERT_TRUE(result.EqualsLiteral("127.0.0.1"));
+ }
+
+ const char* nonIPv4s[] = {"0xfffffffff", "0x100000000",
+ "4294967296", "1.2.0x10000",
+ "1.0x1000000", "256.0.0.1",
+ "1.256.1", "-1.0.0.0",
+ "1.2.3.4.5", "010000000000000000",
+ "2+3", "0.0.0.-1",
+ "1.2.3.4..", "1..2",
+ ".1.2.3.4"};
+ for (uint32_t i = 0; i < sizeof(nonIPv4s) / sizeof(nonIPv4s[0]); i++) {
+ nsCString encHost(nonIPv4s[i]);
+ ASSERT_EQ(NS_ERROR_FAILURE, Test_NormalizeIPv4(encHost, result));
+ }
+}
+
+#define COUNT 10000
+
+MOZ_GTEST_BENCH(TestStandardURL, DISABLED_Perf, [] {
+ nsCOMPtr<nsIURI> url;
+ ASSERT_EQ(NS_OK, NS_MutateURI(NS_STANDARDURLMUTATOR_CONTRACTID)
+ .SetSpec("http://example.com"_ns)
+ .Finalize(url));
+
+ nsAutoCString out;
+ for (int i = COUNT; i; --i) {
+ ASSERT_EQ(NS_MutateURI(url).SetSpec("http://example.com"_ns).Finalize(url),
+ NS_OK);
+ ASSERT_EQ(url->GetSpec(out), NS_OK);
+ url->Resolve("foo.html?q=45"_ns, out);
+ mozilla::Unused << NS_MutateURI(url).SetScheme("foo"_ns).Finalize(url);
+ url->GetScheme(out);
+ mozilla::Unused
+ << NS_MutateURI(url).SetHost("www.yahoo.com"_ns).Finalize(url);
+ url->GetHost(out);
+ mozilla::Unused
+ << NS_MutateURI(url)
+ .SetPathQueryRef(nsLiteralCString(
+ "/some-path/one-the-net/about.html?with-a-query#for-you"))
+ .Finalize(url);
+ url->GetPathQueryRef(out);
+ mozilla::Unused << NS_MutateURI(url)
+ .SetQuery(nsLiteralCString(
+ "a=b&d=c&what-ever-you-want-to-be-called=45"))
+ .Finalize(url);
+ url->GetQuery(out);
+ mozilla::Unused
+ << NS_MutateURI(url).SetRef("#some-book-mark"_ns).Finalize(url);
+ url->GetRef(out);
+ }
+});
+
+// Note the five calls in the loop, so divide by 100k
+MOZ_GTEST_BENCH(TestStandardURL, DISABLED_NormalizePerf, [] {
+ nsAutoCString result;
+ for (int i = 0; i < 20000; i++) {
+ nsAutoCString encHost("123.232.12.32");
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHost, result));
+ nsAutoCString encHost2("83.62.12.92");
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHost2, result));
+ nsAutoCString encHost3("8.7.6.5");
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHost3, result));
+ nsAutoCString encHost4("111.159.123.220");
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHost4, result));
+ nsAutoCString encHost5("1.160.204.200");
+ ASSERT_EQ(NS_OK, Test_NormalizeIPv4(encHost5, result));
+ }
+});
+
+// Bug 1394785 - ignore unstable test on OSX
+#ifndef XP_MACOSX
+// Note the five calls in the loop, so divide by 100k
+MOZ_GTEST_BENCH(TestStandardURL, DISABLED_NormalizePerfFails, [] {
+ nsAutoCString result;
+ for (int i = 0; i < 20000; i++) {
+ nsAutoCString encHost("123.292.12.32");
+ ASSERT_EQ(NS_ERROR_FAILURE, Test_NormalizeIPv4(encHost, result));
+ nsAutoCString encHost2("83.62.12.0x13292");
+ ASSERT_EQ(NS_ERROR_FAILURE, Test_NormalizeIPv4(encHost2, result));
+ nsAutoCString encHost3("8.7.6.0xhello");
+ ASSERT_EQ(NS_ERROR_FAILURE, Test_NormalizeIPv4(encHost3, result));
+ nsAutoCString encHost4("111.159.notonmywatch.220");
+ ASSERT_EQ(NS_ERROR_FAILURE, Test_NormalizeIPv4(encHost4, result));
+ nsAutoCString encHost5("1.160.204.20f");
+ ASSERT_EQ(NS_ERROR_FAILURE, Test_NormalizeIPv4(encHost5, result));
+ }
+});
+#endif
+
+TEST(TestStandardURL, Mutator)
+{
+ nsAutoCString out;
+ nsCOMPtr<nsIURI> uri;
+ nsresult rv = NS_MutateURI(NS_STANDARDURLMUTATOR_CONTRACTID)
+ .SetSpec("http://example.com"_ns)
+ .Finalize(uri);
+ ASSERT_EQ(rv, NS_OK);
+
+ ASSERT_EQ(uri->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "http://example.com/"_ns);
+
+ rv = NS_MutateURI(uri)
+ .SetScheme("ftp"_ns)
+ .SetHost("mozilla.org"_ns)
+ .SetPathQueryRef("/path?query#ref"_ns)
+ .Finalize(uri);
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(uri->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "ftp://mozilla.org/path?query#ref"_ns);
+
+ nsCOMPtr<nsIURL> url;
+ rv = NS_MutateURI(uri).SetScheme("https"_ns).Finalize(url);
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(url->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "https://mozilla.org/path?query#ref"_ns);
+}
+
+TEST(TestStandardURL, Deserialize_Bug1392739)
+{
+ mozilla::ipc::StandardURLParams standard_params;
+ standard_params.urlType() = nsIStandardURL::URLTYPE_STANDARD;
+ standard_params.spec().Truncate();
+ standard_params.host() = mozilla::ipc::StandardURLSegment(4294967295, 1);
+
+ mozilla::ipc::URIParams params(standard_params);
+
+ nsCOMPtr<nsIURIMutator> mutator =
+ do_CreateInstance(NS_STANDARDURLMUTATOR_CID);
+ ASSERT_EQ(mutator->Deserialize(params), NS_ERROR_FAILURE);
+}
diff --git a/netwerk/test/gtest/TestSupportAlpn.cpp b/netwerk/test/gtest/TestSupportAlpn.cpp
new file mode 100644
index 0000000000..ee67c854e6
--- /dev/null
+++ b/netwerk/test/gtest/TestSupportAlpn.cpp
@@ -0,0 +1,61 @@
+#include "gtest/gtest.h"
+
+#include "mozilla/Preferences.h"
+#include "nsIHttpProtocolHandler.h"
+#include "nsHttp.h"
+
+namespace mozilla {
+namespace net {
+
+TEST(TestSupportAlpn, testSvcParamKeyAlpn)
+{
+ Preferences::SetBool("network.http.http3.enabled", true);
+ // initialize gHttphandler.
+ nsCOMPtr<nsIHttpProtocolHandler> http =
+ do_GetService(NS_NETWORK_PROTOCOL_CONTRACTID_PREFIX "http");
+
+ // h2 and h3 are enabled, so first appearance h3 alpn-id is returned.
+ nsTArray<nsCString> alpn = {"h3-28"_ns, "h3-27"_ns, "h2"_ns, "http/1.1"_ns};
+ Tuple<nsCString, bool> result = SelectAlpnFromAlpnList(alpn, false, false);
+ ASSERT_EQ(Get<0>(result), "h3-28"_ns);
+ ASSERT_EQ(Get<1>(result), true);
+
+ // We don't support h3-26, so we should choose h2.
+ alpn = {"h3-26"_ns, "h2"_ns, "http/1.1"_ns};
+ result = SelectAlpnFromAlpnList(alpn, false, false);
+ ASSERT_EQ(Get<0>(result), "h2"_ns);
+ ASSERT_EQ(Get<1>(result), false);
+
+ // h3 is disabled, so we will use h2.
+ alpn = {"h3-28"_ns, "h3-27"_ns, "h2"_ns, "http/1.1"_ns};
+ result = SelectAlpnFromAlpnList(alpn, false, true);
+ ASSERT_EQ(Get<0>(result), "h2"_ns);
+ ASSERT_EQ(Get<1>(result), false);
+
+ // h3 is disabled and h2 is not found, so we will select http/1.1.
+ alpn = {"h3-28"_ns, "h3-27"_ns, "http/1.1"_ns};
+ result = SelectAlpnFromAlpnList(alpn, false, true);
+ ASSERT_EQ(Get<0>(result), "http/1.1"_ns);
+ ASSERT_EQ(Get<1>(result), false);
+
+ // h3 and h2 are disabled, so we will select http/1.1.
+ alpn = {"h3-28"_ns, "h3-27"_ns, "h2"_ns, "http/1.1"_ns};
+ result = SelectAlpnFromAlpnList(alpn, true, true);
+ ASSERT_EQ(Get<0>(result), "http/1.1"_ns);
+ ASSERT_EQ(Get<1>(result), false);
+
+ // h3 and h2 are disabled and http1.1 is not found, we return an empty string.
+ alpn = {"h3-28"_ns, "h3-27"_ns, "h2"_ns};
+ result = SelectAlpnFromAlpnList(alpn, true, true);
+ ASSERT_EQ(Get<0>(result), ""_ns);
+ ASSERT_EQ(Get<1>(result), false);
+
+ // No supported alpn.
+ alpn = {"ftp"_ns, "h2c"_ns};
+ result = SelectAlpnFromAlpnList(alpn, true, true);
+ ASSERT_EQ(Get<0>(result), ""_ns);
+ ASSERT_EQ(Get<1>(result), false);
+}
+
+} // namespace net
+} // namespace mozilla
diff --git a/netwerk/test/gtest/TestUDPSocket.cpp b/netwerk/test/gtest/TestUDPSocket.cpp
new file mode 100644
index 0000000000..84d26fbedf
--- /dev/null
+++ b/netwerk/test/gtest/TestUDPSocket.cpp
@@ -0,0 +1,395 @@
+/* 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/. */
+
+#include "TestCommon.h"
+#include "gtest/gtest.h"
+#include "nsIUDPSocket.h"
+#include "nsISocketTransport.h"
+#include "nsIOutputStream.h"
+#include "nsINetAddr.h"
+#include "nsITimer.h"
+#include "nsContentUtils.h"
+#include "mozilla/net/DNS.h"
+#include "prerror.h"
+
+#define REQUEST 0x68656c6f
+#define RESPONSE 0x6f6c6568
+#define MULTICAST_TIMEOUT 2000
+
+enum TestPhase { TEST_OUTPUT_STREAM, TEST_SEND_API, TEST_MULTICAST, TEST_NONE };
+
+static TestPhase phase = TEST_NONE;
+
+static bool CheckMessageContent(nsIUDPMessage* aMessage,
+ uint32_t aExpectedContent) {
+ nsCString data;
+ aMessage->GetData(data);
+
+ const char* buffer = data.get();
+ uint32_t len = data.Length();
+
+ FallibleTArray<uint8_t>& rawData = aMessage->GetDataAsTArray();
+ uint32_t rawLen = rawData.Length();
+
+ if (len != rawLen) {
+ ADD_FAILURE() << "Raw data length " << rawLen
+ << " does not match String data length " << len;
+ return false;
+ }
+
+ for (uint32_t i = 0; i < len; i++) {
+ if (buffer[i] != rawData[i]) {
+ ADD_FAILURE();
+ return false;
+ }
+ }
+
+ uint32_t input = 0;
+ for (uint32_t i = 0; i < len; i++) {
+ input += buffer[i] << (8 * i);
+ }
+
+ if (len != sizeof(uint32_t)) {
+ ADD_FAILURE() << "Message length mismatch, expected " << sizeof(uint32_t)
+ << " got " << len;
+ return false;
+ }
+ if (input != aExpectedContent) {
+ ADD_FAILURE() << "Message content mismatch, expected 0x" << std::hex
+ << aExpectedContent << " got 0x" << input;
+ return false;
+ }
+
+ return true;
+}
+
+/*
+ * UDPClientListener: listens for incomming UDP packets
+ */
+class UDPClientListener : public nsIUDPSocketListener {
+ protected:
+ virtual ~UDPClientListener();
+
+ public:
+ explicit UDPClientListener(WaitForCondition* waiter) : mWaiter(waiter) {}
+
+ NS_DECL_THREADSAFE_ISUPPORTS
+ NS_DECL_NSIUDPSOCKETLISTENER
+ nsresult mResult = NS_ERROR_FAILURE;
+ RefPtr<WaitForCondition> mWaiter;
+};
+
+NS_IMPL_ISUPPORTS(UDPClientListener, nsIUDPSocketListener)
+
+UDPClientListener::~UDPClientListener() = default;
+
+NS_IMETHODIMP
+UDPClientListener::OnPacketReceived(nsIUDPSocket* socket,
+ nsIUDPMessage* message) {
+ mResult = NS_OK;
+
+ uint16_t port;
+ nsCString ip;
+ nsCOMPtr<nsINetAddr> fromAddr;
+ message->GetFromAddr(getter_AddRefs(fromAddr));
+ fromAddr->GetPort(&port);
+ fromAddr->GetAddress(ip);
+
+ if (TEST_SEND_API == phase && CheckMessageContent(message, REQUEST)) {
+ uint32_t count;
+ nsTArray<uint8_t> data;
+ const uint32_t dataBuffer = RESPONSE;
+ data.AppendElements((const uint8_t*)&dataBuffer, sizeof(uint32_t));
+ mResult = socket->SendWithAddr(fromAddr, data, &count);
+ if (mResult == NS_OK && count == sizeof(uint32_t)) {
+ SUCCEED();
+ } else {
+ ADD_FAILURE();
+ }
+ return NS_OK;
+ } else if (TEST_OUTPUT_STREAM != phase ||
+ !CheckMessageContent(message, RESPONSE)) {
+ mResult = NS_ERROR_FAILURE;
+ }
+
+ // Notify thread
+ mWaiter->Notify();
+ return NS_OK;
+}
+
+NS_IMETHODIMP
+UDPClientListener::OnStopListening(nsIUDPSocket*, nsresult) {
+ mWaiter->Notify();
+ return NS_OK;
+}
+
+/*
+ * UDPServerListener: listens for incomming UDP packets
+ */
+class UDPServerListener : public nsIUDPSocketListener {
+ protected:
+ virtual ~UDPServerListener();
+
+ public:
+ explicit UDPServerListener(WaitForCondition* waiter) : mWaiter(waiter) {}
+
+ NS_DECL_THREADSAFE_ISUPPORTS
+ NS_DECL_NSIUDPSOCKETLISTENER
+
+ nsresult mResult = NS_ERROR_FAILURE;
+ RefPtr<WaitForCondition> mWaiter;
+};
+
+NS_IMPL_ISUPPORTS(UDPServerListener, nsIUDPSocketListener)
+
+UDPServerListener::~UDPServerListener() = default;
+
+NS_IMETHODIMP
+UDPServerListener::OnPacketReceived(nsIUDPSocket* socket,
+ nsIUDPMessage* message) {
+ mResult = NS_OK;
+
+ uint16_t port;
+ nsCString ip;
+ nsCOMPtr<nsINetAddr> fromAddr;
+ message->GetFromAddr(getter_AddRefs(fromAddr));
+ fromAddr->GetPort(&port);
+ fromAddr->GetAddress(ip);
+ SUCCEED();
+
+ if (TEST_OUTPUT_STREAM == phase && CheckMessageContent(message, REQUEST)) {
+ nsCOMPtr<nsIOutputStream> outstream;
+ message->GetOutputStream(getter_AddRefs(outstream));
+
+ uint32_t count;
+ const uint32_t data = RESPONSE;
+ mResult = outstream->Write((const char*)&data, sizeof(uint32_t), &count);
+
+ if (mResult == NS_OK && count == sizeof(uint32_t)) {
+ SUCCEED();
+ } else {
+ ADD_FAILURE();
+ }
+ return NS_OK;
+ } else if (TEST_MULTICAST == phase && CheckMessageContent(message, REQUEST)) {
+ mResult = NS_OK;
+ } else if (TEST_SEND_API != phase ||
+ !CheckMessageContent(message, RESPONSE)) {
+ mResult = NS_ERROR_FAILURE;
+ }
+
+ // Notify thread
+ mWaiter->Notify();
+ return NS_OK;
+}
+
+NS_IMETHODIMP
+UDPServerListener::OnStopListening(nsIUDPSocket*, nsresult) {
+ mWaiter->Notify();
+ return NS_OK;
+}
+
+/**
+ * Multicast timer callback: detects delivery failure
+ */
+class MulticastTimerCallback : public nsITimerCallback {
+ protected:
+ virtual ~MulticastTimerCallback();
+
+ public:
+ explicit MulticastTimerCallback(WaitForCondition* waiter)
+ : mResult(NS_ERROR_NOT_INITIALIZED), mWaiter(waiter) {}
+
+ NS_DECL_THREADSAFE_ISUPPORTS
+ NS_DECL_NSITIMERCALLBACK
+
+ nsresult mResult;
+ RefPtr<WaitForCondition> mWaiter;
+};
+
+NS_IMPL_ISUPPORTS(MulticastTimerCallback, nsITimerCallback)
+
+MulticastTimerCallback::~MulticastTimerCallback() = default;
+
+NS_IMETHODIMP
+MulticastTimerCallback::Notify(nsITimer* timer) {
+ if (TEST_MULTICAST != phase) {
+ return NS_OK;
+ }
+ // Multicast ping failed
+ printf("Multicast ping timeout expired\n");
+ mResult = NS_ERROR_FAILURE;
+ mWaiter->Notify();
+ return NS_OK;
+}
+
+/**** Main ****/
+
+TEST(TestUDPSocket, TestUDPSocketMain)
+{
+ nsresult rv;
+
+ // Create UDPSocket
+ nsCOMPtr<nsIUDPSocket> server, client;
+ server = do_CreateInstance("@mozilla.org/network/udp-socket;1", &rv);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ client = do_CreateInstance("@mozilla.org/network/udp-socket;1", &rv);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ RefPtr<WaitForCondition> waiter = new WaitForCondition();
+
+ // Create UDPServerListener to process UDP packets
+ RefPtr<UDPServerListener> serverListener = new UDPServerListener(waiter);
+
+ nsCOMPtr<nsIPrincipal> systemPrincipal = nsContentUtils::GetSystemPrincipal();
+
+ // Bind server socket to 0.0.0.0
+ rv = server->Init(0, false, systemPrincipal, true, 0);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+ int32_t serverPort;
+ server->GetPort(&serverPort);
+ server->AsyncListen(serverListener);
+
+ // Bind clinet on arbitrary port
+ RefPtr<UDPClientListener> clientListener = new UDPClientListener(waiter);
+ client->Init(0, false, systemPrincipal, true, 0);
+ client->AsyncListen(clientListener);
+
+ // Write data to server
+ uint32_t count;
+ nsTArray<uint8_t> data;
+ const uint32_t dataBuffer = REQUEST;
+ data.AppendElements((const uint8_t*)&dataBuffer, sizeof(uint32_t));
+
+ phase = TEST_OUTPUT_STREAM;
+ rv = client->Send("127.0.0.1"_ns, serverPort, data, &count);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+ EXPECT_EQ(count, sizeof(uint32_t));
+
+ // Wait for server
+ waiter->Wait(1);
+ ASSERT_TRUE(NS_SUCCEEDED(serverListener->mResult));
+
+ // Read response from server
+ ASSERT_TRUE(NS_SUCCEEDED(clientListener->mResult));
+
+ mozilla::net::NetAddr clientAddr;
+ rv = client->GetAddress(&clientAddr);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+ // The client address is 0.0.0.0, but Windows won't receive packets there, so
+ // use 127.0.0.1 explicitly
+ clientAddr.inet.ip = PR_htonl(127 << 24 | 1);
+
+ phase = TEST_SEND_API;
+ rv = server->SendWithAddress(&clientAddr, data, &count);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+ EXPECT_EQ(count, sizeof(uint32_t));
+
+ // Wait for server
+ waiter->Wait(1);
+ ASSERT_TRUE(NS_SUCCEEDED(serverListener->mResult));
+
+ // Read response from server
+ ASSERT_TRUE(NS_SUCCEEDED(clientListener->mResult));
+
+ // Setup timer to detect multicast failure
+ nsCOMPtr<nsITimer> timer = NS_NewTimer();
+ ASSERT_TRUE(timer);
+ RefPtr<MulticastTimerCallback> timerCb = new MulticastTimerCallback(waiter);
+
+ // Join multicast group
+ printf("Joining multicast group\n");
+ phase = TEST_MULTICAST;
+ mozilla::net::NetAddr multicastAddr;
+ multicastAddr.inet.family = AF_INET;
+ multicastAddr.inet.ip = PR_htonl(224 << 24 | 255);
+ multicastAddr.inet.port = PR_htons(serverPort);
+ rv = server->JoinMulticastAddr(multicastAddr, nullptr);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ // Send multicast ping
+ timerCb->mResult = NS_OK;
+ timer->InitWithCallback(timerCb, MULTICAST_TIMEOUT, nsITimer::TYPE_ONE_SHOT);
+ rv = client->SendWithAddress(&multicastAddr, data, &count);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+ EXPECT_EQ(count, sizeof(uint32_t));
+
+ // Wait for server to receive successfully
+ waiter->Wait(1);
+ ASSERT_TRUE(NS_SUCCEEDED(serverListener->mResult));
+ ASSERT_TRUE(NS_SUCCEEDED(timerCb->mResult));
+ timer->Cancel();
+
+ // Disable multicast loopback
+ printf("Disable multicast loopback\n");
+ client->SetMulticastLoopback(false);
+ server->SetMulticastLoopback(false);
+
+ // Send multicast ping
+ timerCb->mResult = NS_OK;
+ timer->InitWithCallback(timerCb, MULTICAST_TIMEOUT, nsITimer::TYPE_ONE_SHOT);
+ rv = client->SendWithAddress(&multicastAddr, data, &count);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+ EXPECT_EQ(count, sizeof(uint32_t));
+
+ // Wait for server to fail to receive
+ waiter->Wait(1);
+ ASSERT_FALSE(NS_SUCCEEDED(timerCb->mResult));
+ timer->Cancel();
+
+ // Reset state
+ client->SetMulticastLoopback(true);
+ server->SetMulticastLoopback(true);
+
+ // Change multicast interface
+ mozilla::net::NetAddr loopbackAddr;
+ loopbackAddr.inet.family = AF_INET;
+ loopbackAddr.inet.ip = PR_htonl(INADDR_LOOPBACK);
+ client->SetMulticastInterfaceAddr(loopbackAddr);
+
+ // Send multicast ping
+ timerCb->mResult = NS_OK;
+ timer->InitWithCallback(timerCb, MULTICAST_TIMEOUT, nsITimer::TYPE_ONE_SHOT);
+ rv = client->SendWithAddress(&multicastAddr, data, &count);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+ EXPECT_EQ(count, sizeof(uint32_t));
+
+ // Wait for server to fail to receive
+ waiter->Wait(1);
+ ASSERT_FALSE(NS_SUCCEEDED(timerCb->mResult));
+ timer->Cancel();
+
+ // Reset state
+ mozilla::net::NetAddr anyAddr;
+ anyAddr.inet.family = AF_INET;
+ anyAddr.inet.ip = PR_htonl(INADDR_ANY);
+ client->SetMulticastInterfaceAddr(anyAddr);
+
+ // Leave multicast group
+ rv = server->LeaveMulticastAddr(multicastAddr, nullptr);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+
+ // Send multicast ping
+ timerCb->mResult = NS_OK;
+ timer->InitWithCallback(timerCb, MULTICAST_TIMEOUT, nsITimer::TYPE_ONE_SHOT);
+ rv = client->SendWithAddress(&multicastAddr, data, &count);
+ ASSERT_TRUE(NS_SUCCEEDED(rv));
+ EXPECT_EQ(count, sizeof(uint32_t));
+
+ // Wait for server to fail to receive
+ waiter->Wait(1);
+ ASSERT_FALSE(NS_SUCCEEDED(timerCb->mResult));
+ timer->Cancel();
+
+ goto close; // suppress warning about unused label
+
+close:
+ // Close server
+ server->Close();
+ client->Close();
+
+ // Wait for client and server to see closing
+ waiter->Wait(2);
+}
diff --git a/netwerk/test/gtest/TestURIMutator.cpp b/netwerk/test/gtest/TestURIMutator.cpp
new file mode 100644
index 0000000000..cd45457a3c
--- /dev/null
+++ b/netwerk/test/gtest/TestURIMutator.cpp
@@ -0,0 +1,128 @@
+#include "gtest/gtest.h"
+#include "nsCOMPtr.h"
+#include "nsNetCID.h"
+#include "nsIURIMutator.h"
+#include "nsIURL.h"
+#include "nsThreadPool.h"
+#include "nsNetUtil.h"
+
+TEST(TestURIMutator, Mutator)
+{
+ nsAutoCString out;
+
+ // This test instantiates a new nsStandardURL::Mutator (via contractID)
+ // and uses it to create a new URI.
+ nsCOMPtr<nsIURI> uri;
+ nsresult rv = NS_MutateURI(NS_STANDARDURLMUTATOR_CONTRACTID)
+ .SetSpec("http://example.com"_ns)
+ .Finalize(uri);
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(uri->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "http://example.com/"_ns);
+
+ // This test verifies that we can use NS_MutateURI to change a URI
+ rv = NS_MutateURI(uri)
+ .SetScheme("ftp"_ns)
+ .SetHost("mozilla.org"_ns)
+ .SetPathQueryRef("/path?query#ref"_ns)
+ .Finalize(uri);
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(uri->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "ftp://mozilla.org/path?query#ref"_ns);
+
+ // This test verifies that we can pass nsIURL to Finalize, and
+ nsCOMPtr<nsIURL> url;
+ rv = NS_MutateURI(uri).SetScheme("https"_ns).Finalize(url);
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(url->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "https://mozilla.org/path?query#ref"_ns);
+
+ // This test verifies that we can pass nsIURL** to Finalize.
+ // We need to use the explicit template because it's actually passing
+ // getter_AddRefs
+ nsCOMPtr<nsIURL> url2;
+ rv = NS_MutateURI(url)
+ .SetRef("newref"_ns)
+ .Finalize<nsIURL>(getter_AddRefs(url2));
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(url2->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "https://mozilla.org/path?query#newref"_ns);
+
+ // This test verifies that we can pass nsIURI** to Finalize.
+ // No need to be explicit.
+ auto functionSetRef = [](nsIURI* aURI, nsIURI** aResult) -> nsresult {
+ return NS_MutateURI(aURI).SetRef("originalRef"_ns).Finalize(aResult);
+ };
+
+ nsCOMPtr<nsIURI> newURI;
+ rv = functionSetRef(url2, getter_AddRefs(newURI));
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(newURI->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "https://mozilla.org/path?query#originalRef"_ns);
+
+ // This test verifies that we can pass nsIURI** to Finalize.
+ nsCOMPtr<nsIURI> uri2;
+ rv =
+ NS_MutateURI(url2).SetQuery("newquery"_ns).Finalize(getter_AddRefs(uri2));
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(uri2->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "https://mozilla.org/path?newquery#newref"_ns);
+
+ // This test verifies that we can pass nsIURI** to Finalize.
+ // No need to be explicit.
+ auto functionSetQuery = [](nsIURI* aURI, nsIURL** aResult) -> nsresult {
+ return NS_MutateURI(aURI).SetQuery("originalQuery"_ns).Finalize(aResult);
+ };
+
+ nsCOMPtr<nsIURL> newURL;
+ rv = functionSetQuery(uri2, getter_AddRefs(newURL));
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(newURL->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "https://mozilla.org/path?originalQuery#newref"_ns);
+
+ // Check that calling Finalize twice will fail.
+ NS_MutateURI mutator(newURL);
+ rv = mutator.SetQuery(""_ns).Finalize(uri2);
+ ASSERT_EQ(rv, NS_OK);
+ ASSERT_EQ(uri2->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "https://mozilla.org/path#newref"_ns);
+ nsCOMPtr<nsIURI> uri3;
+ rv = mutator.Finalize(uri3);
+ ASSERT_EQ(rv, NS_ERROR_NOT_AVAILABLE);
+ ASSERT_TRUE(uri3 == nullptr);
+}
+
+extern MOZ_THREAD_LOCAL(uint32_t) gTlsURLRecursionCount;
+
+TEST(TestURIMutator, OnAnyThread)
+{
+ nsCOMPtr<nsIThreadPool> pool = new nsThreadPool();
+ pool->SetThreadLimit(60);
+
+ pool = new nsThreadPool();
+ for (int i = 0; i < 1000; ++i) {
+ nsCOMPtr<nsIRunnable> task =
+ NS_NewRunnableFunction("gtest-OnAnyThread", []() {
+ nsCOMPtr<nsIURI> uri;
+ nsresult rv = NS_NewURI(getter_AddRefs(uri), "http://example.com"_ns);
+ ASSERT_EQ(rv, NS_OK);
+ nsAutoCString out;
+ ASSERT_EQ(uri->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "http://example.com/"_ns);
+ });
+ EXPECT_TRUE(task);
+
+ pool->Dispatch(task, NS_DISPATCH_NORMAL);
+ }
+
+ nsCOMPtr<nsIURI> uri;
+ nsresult rv = NS_NewURI(getter_AddRefs(uri), "http://example.com"_ns);
+ ASSERT_EQ(rv, NS_OK);
+ nsAutoCString out;
+ ASSERT_EQ(uri->GetSpec(out), NS_OK);
+ ASSERT_TRUE(out == "http://example.com/"_ns);
+
+ pool->Shutdown();
+
+ ASSERT_EQ(gTlsURLRecursionCount.get(), 0u);
+}
diff --git a/netwerk/test/gtest/moz.build b/netwerk/test/gtest/moz.build
new file mode 100644
index 0000000000..5f912c17fe
--- /dev/null
+++ b/netwerk/test/gtest/moz.build
@@ -0,0 +1,84 @@
+# -*- Mode: python; c-basic-offset: 4; indent-tabs-mode: nil; tab-width: 40 -*-
+# vim: set filetype=python:
+# 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/.
+
+UNIFIED_SOURCES += [
+ "TestBase64Stream.cpp",
+ "TestBind.cpp",
+ "TestBufferedInputStream.cpp",
+ "TestCommon.cpp",
+ "TestCookie.cpp",
+ "TestHeaders.cpp",
+ "TestHttpAuthUtils.cpp",
+ "TestHttpResponseHead.cpp",
+ "TestInputStreamTransport.cpp",
+ "TestIsValidIp.cpp",
+ "TestMIMEInputStream.cpp",
+ "TestMozURL.cpp",
+ "TestProtocolProxyService.cpp",
+ "TestReadStreamToString.cpp",
+ "TestServerTimingHeader.cpp",
+ "TestSocketTransportService.cpp",
+ "TestStandardURL.cpp",
+ "TestSupportAlpn.cpp",
+ "TestUDPSocket.cpp",
+]
+
+if CONFIG["OS_TARGET"] == "WINNT":
+ UNIFIED_SOURCES += [
+ "TestNamedPipeService.cpp",
+ ]
+
+if CONFIG["CC_TYPE"] in ("clang", "gcc"):
+ CXXFLAGS += ["-Wno-shadow"]
+
+# skip the test on windows10-aarch64
+if not (CONFIG["OS_TARGET"] == "WINNT" and CONFIG["CPU_ARCH"] == "aarch64"):
+ UNIFIED_SOURCES += [
+ "TestPACMan.cpp",
+ "TestPartiallySeekableInputStream.cpp",
+ "TestURIMutator.cpp",
+ ]
+
+# run the test on windows only
+if CONFIG["OS_TARGET"] == "WINNT":
+ UNIFIED_SOURCES += ["TestNetworkLinkIdHashingWindows.cpp"]
+
+# run the test on mac only
+if CONFIG["OS_TARGET"] == "Darwin":
+ UNIFIED_SOURCES += ["TestNetworkLinkIdHashingDarwin.cpp"]
+
+TEST_HARNESS_FILES.gtest += [
+ "urltestdata.json",
+]
+
+USE_LIBS += [
+ "jsoncpp",
+]
+
+TEST_DIRS += [
+ "parse-ftp",
+]
+
+LOCAL_INCLUDES += [
+ "/netwerk/base",
+ "/netwerk/cookie",
+ "/toolkit/components/jsoncpp/include",
+ "/xpcom/tests/gtest",
+]
+
+# windows includes only
+if CONFIG["OS_TARGET"] == "WINNT":
+ LOCAL_INCLUDES += ["/netwerk/system/win32"]
+
+# mac includes only
+if CONFIG["OS_TARGET"] == "Darwin":
+ LOCAL_INCLUDES += ["/netwerk/system/mac"]
+
+include("/ipc/chromium/chromium-config.mozbuild")
+
+FINAL_LIBRARY = "xul-gtest"
+
+LOCAL_INCLUDES += ["!/xpcom", "/xpcom/components"]
diff --git a/netwerk/test/gtest/parse-ftp/3-guess.in b/netwerk/test/gtest/parse-ftp/3-guess.in
new file mode 100644
index 0000000000..b5e8596c1c
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/3-guess.in
@@ -0,0 +1,30 @@
+I couldn't find any SuperTCP or Chameleon/Newt FTP servers, so the
+following is based on guesswork from the mirror.pl and lynx projects.
+The first 8 are Chameleon/Newt, the remaining 16 entries are SuperTCP
+with two different date styles. The precise amount of whitespace
+between columns might not be correct, but the parser shouldn't care.
+
+. <DIR> Nov 16 1994 17:16
+.. <DIR> Nov 16 1994 17:16
+INSTALL <DIR> Nov 16 1994 17:17
+CMT <DIR> Nov 21 1994 10:17
+DESIGN1.DOC 11264 May 11 1995 14:20 A
+README.TXT 1045 May 10 1995 11:01
+WPKIT1.EXE 960338 Jun 21 1995 17:01 R
+CMT.CSV 0 Jul 06 1995 14:56 RHA
+. <DIR> 11-16-94 17:16
+.. <DIR> 11-16-94 17:16
+INSTALL <DIR> 11-16-94 17:17
+CMT <DIR> 11-21-94 10:17
+DESIGN1.DOC 11264 05-11-95 14:20
+README.TXT 1045 05-10-95 11:01
+WPKIT1.EXE 960338 06-21-95 17:01
+CMT.CSV 0 07-06-95 14:56
+. <DIR> 11/16/94 17:16
+.. <DIR> 11/16/94 17:16
+INSTALL <DIR> 11/16/94 17:17
+CMT <DIR> 11/21/94 10:17
+DESIGN1.DOC 11264 05/11/95 14:20
+README.TXT 1045 05/10/95 11:01
+WPKIT1.EXE 960338 06/21/95 17:01
+CMT.CSV 0 07/06/95 14:56
diff --git a/netwerk/test/gtest/parse-ftp/3-guess.out b/netwerk/test/gtest/parse-ftp/3-guess.out
new file mode 100644
index 0000000000..30a1d0fb98
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/3-guess.out
@@ -0,0 +1,28 @@
+<!-- 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/. -->
+
+11-16-1994 17:16:00 <DIR> .
+11-16-1994 17:16:00 <DIR> ..
+11-16-1994 17:17:00 <DIR> INSTALL
+11-21-1994 10:17:00 <DIR> CMT
+05-11-1995 14:20:00 11264 DESIGN1.DOC
+05-10-1995 11:01:00 1045 README.TXT
+06-21-1995 17:01:00 960338 WPKIT1.EXE
+07-06-1995 14:56:00 0 CMT.CSV
+11-16-1994 17:16:00 <DIR> .
+11-16-1994 17:16:00 <DIR> ..
+11-16-1994 17:17:00 <DIR> INSTALL
+11-21-1994 10:17:00 <DIR> CMT
+05-11-1995 14:20:00 11264 DESIGN1.DOC
+05-10-1995 11:01:00 1045 README.TXT
+06-21-1995 17:01:00 960338 WPKIT1.EXE
+07-06-1995 14:56:00 0 CMT.CSV
+11-16-1994 17:16:00 <DIR> .
+11-16-1994 17:16:00 <DIR> ..
+11-16-1994 17:17:00 <DIR> INSTALL
+11-21-1994 10:17:00 <DIR> CMT
+05-11-1995 14:20:00 11264 DESIGN1.DOC
+05-10-1995 11:01:00 1045 README.TXT
+06-21-1995 17:01:00 960338 WPKIT1.EXE
+07-06-1995 14:56:00 0 CMT.CSV
diff --git a/netwerk/test/gtest/parse-ftp/C-VMold.in b/netwerk/test/gtest/parse-ftp/C-VMold.in
new file mode 100644
index 0000000000..5453b496e7
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/C-VMold.in
@@ -0,0 +1,16 @@
+This is a synthetic LISTing based on comments in mirror.pl and a
+screenshot I saw somewhere. Either way, its 'synthetic' because I
+couldn't find an FTP server that LISTed like this. Note that (as
+with other VM/CMS LISTings) filesize cannot be determined from
+the listing and (AFAIK) files/dirs not on the 'A' minidisk (see
+'Fm' field) are not RETRievable/CHDIR'able without magic.
+
+Filename FileType Fm Format Lrecl Records Blocks Date Time
+LASTING GLOBALV A1 V 41 21 1 9/16/91 15:10:32
+J43401 NETLOG A0 V 77 1 1 9/12/91 12:36:04
+PROFILE EXEC A1 V 17 3 1 9/12/91 12:39:07
+DIRUNIX SCRIPT A1 V 77 1216 17 1/04/93 20:30:47
+MAIL PROFILE A2 F 80 1 1 10/14/92 16:12:27
+ABADY2K DATE A0 V 1 1 1 1/03/100 10:11:12
+BBADY2K DATE A0 V 1 1 1 11/03/100 10:11:12
+AUTHORS A1 DIR - - - 9/20/99 10:31:11
diff --git a/netwerk/test/gtest/parse-ftp/C-VMold.out b/netwerk/test/gtest/parse-ftp/C-VMold.out
new file mode 100644
index 0000000000..0c9c016f61
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/C-VMold.out
@@ -0,0 +1,12 @@
+<!-- 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/. -->
+
+09-16-1991 15:10:32 LASTING.GLOBALV
+09-12-1991 12:36:04 J43401.NETLOG
+09-12-1991 12:39:07 PROFILE.EXEC
+01-04-1993 20:30:47 DIRUNIX.SCRIPT
+10-14-1992 16:12:27 MAIL.PROFILE
+01-03-2000 10:11:12 ABADY2K.DATE
+11-03-2000 10:11:12 BBADY2K.DATE
+09-20-1999 10:31:11 <DIR> AUTHORS
diff --git a/netwerk/test/gtest/parse-ftp/C-zVM.in b/netwerk/test/gtest/parse-ftp/C-zVM.in
new file mode 100644
index 0000000000..bd63f631ff
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/C-zVM.in
@@ -0,0 +1,61 @@
+ftp> open vm.marist.edu
+220-Welcome to FTP.Marist.edu
+220-
+220-All usage logged. Usage restricted.
+220-FTPSERVE IBM VM Level 420 at VM.MARIST.EDU, 05:06:00 EDT WEDNESDAY 2002-07-10
+220 Connection will close if idle for more than 5 minutes.
+Name (vm.marist.edu:cyp):
+230-
+230-
+230-Listserv logs for certain lists are available via CD ACADEM:listname.
+230-
+230-Lists that they are available for are:
+230-
+230-ADSM-L ftp://vm.marist.edu/academ:adsm-l./
+230-CLINTON ftp://vm.marist.edu/academ:clinton./
+230-CMSPIP-L ftp://vm.marist.edu/academ:cmspip-l./
+230-CONCORD ftp://vm.marist.edu/academ:concord./
+230-REPUB-L ftp://vm.marist.edu/academ:repub-l./
+230-SAS-L ftp://vm.marist.edu/academ:sas-l./
+230-VM-UTIL ftp://vm.marist.edu/academ:vm-util./
+230-LINUX-VM ftp://vm.marist.edu/academ:linux-vm./
+230-
+230-For example: (Note the trailing .)
+230-
+230-CD ACADEM:ADSM-L.
+230-
+230-Due to limitations of Netscape, you may need to append ";type=a"
+230-to the end of a URL when obtaining a file.
+230-
+230-CMS Pipelines RLD available as
+230-
+230- ftp://vm.marist.edu/academ:pipeline/eweb./
+230-
+230 ANONYMOU logged in; working directory = ACADEM:ANONYMOU.
+Remote system type is z/VM.
+ftp> ls
+200 Port request OK.
+125 List started OK
+README ANONYMOU V 71 26 1 1997-04-02 12:33:20 TCP291
+README ANONYOLD V 71 15 1 1995-08-25 16:04:27 TCP291
+AUTHORS DIR - - - 1999-09-20 10:31:11 -
+HARRINGTON DIR - - - 1997-02-12 15:33:28 -
+PICS DIR - - - 2000-10-12 15:43:23 -
+SYSFILE DIR - - - 2000-07-20 17:48:01 -
+WELCNVT EXEC V 72 9 1 1999-09-20 17:16:18 -
+WELCOME EREADME F 80 21 1 1999-12-27 16:19:00 -
+WELCOME README V 82 21 1 1999-12-27 16:19:04 -
+PROJECT PDF V 984 10 3 1997-06-15 11:15:02 -
+CAMPUS TIF V 8192 3172 3606 2000-10-06 17:20:37 -
+ROTUNDA TIF V 8192 5745 8750 2000-10-06 17:28:25 -
+STUDENT TIF V 8192 5017 8557 2000-10-06 17:31:26 -
+CHILDREN TXT V 280 310 20 1993-08-06 14:20:00 -
+SYSFILE VMARC F 80 2001 40 2000-07-20 17:47:35 -
+250 List completed successfully.
+ftp> syst
+215-z/VM Version 4 Release 2.0, service level 0101 (32-bit)
+ VM/CMS Level 18, Service Level 101
+215 VM is the operating system of this server.
+ftp> close
+221 Quit command received. Goodbye.
+ftp>
diff --git a/netwerk/test/gtest/parse-ftp/C-zVM.out b/netwerk/test/gtest/parse-ftp/C-zVM.out
new file mode 100644
index 0000000000..04511ebc7e
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/C-zVM.out
@@ -0,0 +1,19 @@
+<!-- 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/. -->
+
+04-02-1997 12:33:20 README.ANONYMOU
+08-25-1995 16:04:27 README.ANONYOLD
+09-20-1999 10:31:11 <DIR> AUTHORS
+02-12-1997 15:33:28 <DIR> HARRINGTON
+10-12-2000 15:43:23 <DIR> PICS
+07-20-2000 17:48:01 <DIR> SYSFILE
+09-20-1999 17:16:18 WELCNVT.EXEC
+12-27-1999 16:19:00 WELCOME.EREADME
+12-27-1999 16:19:04 WELCOME.README
+06-15-1997 11:15:02 PROJECT.PDF
+10-06-2000 17:20:37 CAMPUS.TIF
+10-06-2000 17:28:25 ROTUNDA.TIF
+10-06-2000 17:31:26 STUDENT.TIF
+08-06-1993 14:20:00 CHILDREN.TXT
+07-20-2000 17:47:35 SYSFILE.VMARC
diff --git a/netwerk/test/gtest/parse-ftp/D-WinNT.in b/netwerk/test/gtest/parse-ftp/D-WinNT.in
new file mode 100644
index 0000000000..c27f4d8bff
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/D-WinNT.in
@@ -0,0 +1,62 @@
+ftp> open ftp.microsoft.com
+220 Microsoft FTP Service
+Name (ftp.microsoft.com:cyp):
+331 Anonymous access allowed, send identity (e-mail name) as password.
+230-This is FTP.Microsoft.Com
+230 Anonymous user logged in.
+Remote system type is Windows_NT.
+ftp> quote dirstyle
+200 MSDOS-like directory output is on
+ftp> ls
+200 PORT command successful.
+150 Opening ASCII mode data connection for /bin/ls.
+02-05-01 05:52PM <DIR> 20Year
+09-26-00 03:20PM <DIR> AccessFoxPro
+12-21-00 02:39PM <DIR> AlbGrp
+05-31-01 11:16AM <DIR> Alexandra
+01-19-01 09:36AM <DIR> anna
+04-06-00 12:53PM <DIR> anz
+05-10-00 01:37PM <DIR> Chase Bobko2
+03-29-00 02:43PM <DIR> cnn
+11-21-00 11:21AM <DIR> Darin
+03-09-00 05:55PM <DIR> digitalchicago
+09-06-00 11:38AM <DIR> Dublin
+01-30-01 07:15PM <DIR> eleanorf
+04-26-01 11:04AM <DIR> girvin
+04-26-00 09:28PM <DIR> Hires
+08-15-00 05:03PM <DIR> HR
+10-24-99 01:29AM 4368384 IMG00022.PCD
+05-18-01 07:52AM <DIR> jacubowsky
+10-12-00 10:55AM <DIR> JFalvey
+03-28-01 02:38PM <DIR> johnci
+07-14-00 08:59AM <DIR> Karin
+09-07-00 05:48PM <DIR> Kjung
+09-28-00 08:59AM <DIR> LarryE
+08-17-00 06:06PM <DIR> Larson
+09-12-00 05:22PM <DIR> marion
+08-09-00 12:30PM <DIR> ms25
+11-16-00 03:58PM <DIR> MS25Brochure
+03-29-00 12:07PM <DIR> MShistory
+09-05-00 10:35AM <DIR> Neils
+08-02-00 06:25PM <DIR> NLM
+09-06-00 03:04PM <DIR> PageOne
+06-27-00 06:00PM <DIR> pccomputing
+05-09-01 01:27PM <DIR> pictures
+07-21-00 04:23PM <DIR> pranks
+08-22-00 10:36AM <DIR> Sean
+08-10-00 01:54PM <DIR> SLeong
+09-07-00 05:46PM <DIR> svr
+10-23-00 01:27PM <JUNCTION> b_junction_sample => foo
+06-15-00 07:37AM <JUNCTION> c_junction_sample -> bar too
+07-14-00 01:35PM 2094926 canprankdesk.tif
+07-21-00 01:19PM 95077 Jon Kauffman Enjoys the Good Life.jpg
+07-21-00 01:19PM 52275 Name Plate.jpg
+07-14-00 01:38PM 2250540 Valentineoffprank-HiRes.jpg
+01-11-14 12:25AM 18864566 Bug961346
+10-10-2014 10:10AM <DIR> Bug1061898
+01-18-12 19:00 30724571 Bug1125816
+226 Transfer complete.
+ftp> close
+221 Thank-You For Using Microsoft Products!
+ftp>
+
diff --git a/netwerk/test/gtest/parse-ftp/D-WinNT.out b/netwerk/test/gtest/parse-ftp/D-WinNT.out
new file mode 100644
index 0000000000..0a42d4d668
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/D-WinNT.out
@@ -0,0 +1,49 @@
+<!-- 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/. -->
+
+02-05-2001 17:52:00 <DIR> 20Year
+09-26-2000 15:20:00 <DIR> AccessFoxPro
+12-21-2000 14:39:00 <DIR> AlbGrp
+05-31-2001 11:16:00 <DIR> Alexandra
+01-19-2001 09:36:00 <DIR> anna
+04-06-2000 12:53:00 <DIR> anz
+05-10-2000 13:37:00 <DIR> Chase Bobko2
+03-29-2000 14:43:00 <DIR> cnn
+11-21-2000 11:21:00 <DIR> Darin
+03-09-2000 17:55:00 <DIR> digitalchicago
+09-06-2000 11:38:00 <DIR> Dublin
+01-30-2001 19:15:00 <DIR> eleanorf
+04-26-2001 11:04:00 <DIR> girvin
+04-26-2000 21:28:00 <DIR> Hires
+08-15-2000 17:03:00 <DIR> HR
+10-24-1999 01:29:00 4368384 IMG00022.PCD
+05-18-2001 07:52:00 <DIR> jacubowsky
+10-12-2000 10:55:00 <DIR> JFalvey
+03-28-2001 14:38:00 <DIR> johnci
+07-14-2000 08:59:00 <DIR> Karin
+09-07-2000 17:48:00 <DIR> Kjung
+09-28-2000 08:59:00 <DIR> LarryE
+08-17-2000 18:06:00 <DIR> Larson
+09-12-2000 17:22:00 <DIR> marion
+08-09-2000 12:30:00 <DIR> ms25
+11-16-2000 15:58:00 <DIR> MS25Brochure
+03-29-2000 12:07:00 <DIR> MShistory
+09-05-2000 10:35:00 <DIR> Neils
+08-02-2000 18:25:00 <DIR> NLM
+09-06-2000 15:04:00 <DIR> PageOne
+06-27-2000 18:00:00 <DIR> pccomputing
+05-09-2001 13:27:00 <DIR> pictures
+07-21-2000 16:23:00 <DIR> pranks
+08-22-2000 10:36:00 <DIR> Sean
+08-10-2000 13:54:00 <DIR> SLeong
+09-07-2000 17:46:00 <DIR> svr
+10-23-2000 13:27:00 <JUNCTION> b_junction_sample -> foo
+06-15-2000 07:37:00 <JUNCTION> c_junction_sample -> bar too
+07-14-2000 13:35:00 2094926 canprankdesk.tif
+07-21-2000 13:19:00 95077 Jon Kauffman Enjoys the Good Life.jpg
+07-21-2000 13:19:00 52275 Name Plate.jpg
+07-14-2000 13:38:00 2250540 Valentineoffprank-HiRes.jpg
+01-11-2014 00:25:00 18864566 Bug961346
+10-10-2014 10:10:00 <DIR> Bug1061898
+01-18-2012 19:00:00 30724571 Bug1125816
diff --git a/netwerk/test/gtest/parse-ftp/E-EPLF.in b/netwerk/test/gtest/parse-ftp/E-EPLF.in
new file mode 100644
index 0000000000..3798ea0a9d
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/E-EPLF.in
@@ -0,0 +1,189 @@
+ftp> open cr.yp.to
+Connected to cr.yp.to.
+220 Features: a p .
+Name (cr.yp.to:cyp):
+230 Hi. No need to log in; I'm an anonymous ftp server.
+Remote system type is UNIX.
+Using binary mode to transfer files.
+ftp> ls
+200 Okay.
+150 Making transfer connection...
++i0.307427,m979205905,/, tmp
++i0.631874,m951789705,/, 1998-100
++i0.236492,m977690646,r,s1172, mirrors.html
++i0.718174,m951789707,/, 1999-275
++i0.236496,m957763516,r,s933, 1999-275.html
++i0.236247,m957763626,r,s322, 1998-401.html
++i0.689416,m951789707,/, 1998-401
++i0.714380,m951789705,/, 1997-275
++i0.236426,m957763705,r,s277, 1998-515.html
++i0.236324,m957764203,r,s325, 2000-436.html
++i0.553153,m977554031,/, checkpwd
++i0.73117,m1025804866,/, bib
++i0.2012,m951789707,/, 1999-541
++i0.134494,m988426955,/, 2001-260
++i0.457327,m1019068075,/, 2002-501
++i0.11567,m991428977,/, 1995-514
++i0.716165,m951789705,/, 1999-180
++i0.236327,m991363463,r,s475, 2000-515.html
++i0.687522,m951789707,/, 1998-515
++i0.412995,m951789707,/, 2000-515
++i0.213334,m958117573,/, zpfft
++i0.295901,m1004187614,/, psibound
++i0.236429,m951789711,r,s398, anonftpd.html
++i0.326793,m1014690862,/, nistp224
++i0.587605,m997428440,/, cdb
++i0.516884,m1020211107,/, talks
++i0.255382,m977607275,/, ftpparse
++i0.103809,m947569810,/, clockspeed
++i0.236433,m951789712,r,s1350, clockspeed.html
++i0.530322,m1013028754,/, slashdoc
++i0.10002,m1023465640,/, export
++i0.105740,m995334516,/, daemontools
++i0.236425,m994972628,r,s2187, daemontools.html
++i0.236437,m999204676,r,s175, data.html
++i0.236435,m1009503157,r,s1901, crypto.html
++i0.236430,m1005435923,r,s739, arith.html
++i0.236297,m1007092089,r,s2733, cdb.html
++i0.236475,m1005436262,r,s344, floatasm.html
++i0.126821,m977433956,/, djbfft
++i0.236440,m951789712,r,s1319, djbfft.html
++i0.149876,m963163007,/, dnscache
++i0.236441,m962665064,r,s4016, dnscache.html
++i0.674064,m994734982,/, docs
++i0.236442,m951789712,r,s293, docs.html
++i0.236443,m951789712,r,s952, dot-forward.html
++i0.76895,m947569811,/, etc-mta
++i0.236444,m951789712,r,s3174, etc-mta.html
++i0.236445,m951789712,r,s2990, ezmlm.html
++i0.142082,m977433956,/, ftp
++i0.78826,m951789709,/, im
++i0.236446,m951789712,r,s1823, fastforward.html
++i0.236447,m951789712,r,s1707, ftp.html
++i0.21212,m981944230,/, freebugtraq
++i0.117314,m1022981965,/, hardware
++i0.236326,m991364255,r,s610, 1995-514.html
++i0.63463,m977433957,/, hash127
++i0.236450,m958703342,r,s4835, hash127.html
++i0.236451,m951789712,r,s1515, im.html
++i0.82651,m1013546406,/, immhf
++i0.236299,m988235329,r,s2902, immhf.html
++i0.147915,m980402316,/, lib
++i0.591514,m991784750,/, libtai
++i0.236454,m963255256,r,s2120, libtai.html
++i0.236427,m1006883560,r,s14460, qmail.html
++i0.236452,m999204683,r,s2153, mail.html
++i0.236457,m951789712,r,s108, maildir.html
++i0.71192,m951789710,/, maildisasters
++i0.236458,m951789712,r,s873, maildisasters.html
++i0.236459,m951789712,r,s1688, mess822.html
++i0.13517,m1014605247,/, mirror
++i0.236431,m1009400552,r,s581, ntheory.html
++i0.629891,m1023118587,/, papers
++i0.176720,m1021999815,/, postpropter
++i0.67332,m947569812,/, postings
++i0.101902,m947569812,/, primegen
++i0.236453,m999204693,r,s415, precompiled.html
++i0.236463,m951789712,r,s1121, primegen.html
++i0.574160,m1020562675,/, proto
++i0.236464,m951789712,r,s452, proto.html
++i0.113471,m994717073,/, publicfile
++i0.236295,m1007092757,r,s5651, publicfile.html
++i0.236455,m999204697,r,s409, qlist.html
++i0.15552,m1017725145,/, qmail
++i0.236292,m1012629148,r,s7549, lists.html
++i0.236468,m951789712,r,s1166, qmailanalog.html
++i0.236456,m999204699,r,s1434, qmsmac.html
++i0.236470,m952925886,r,s465, rblsmtpd.html
++i0.236471,m951789712,r,s1225, rights.html
++i0.691333,m947569813,/, sarcasm
++i0.236465,m1000434854,r,s1058, unix.html
++i0.236472,m951789713,r,s1568, serialmail.html
++i0.236473,m970514024,r,s840, sigs.html
++i0.80743,m1021999808,/, smtp
++i0.236300,m988300727,r,s1723, smtp.html
++i0.693264,m977433963,/, software
++i0.236476,m951789713,r,s3671, softwarelaw.html
++i0.710487,m947569813,/, sortedsums
++i0.236477,m951789713,r,s2735, sortedsums.html
++i0.23149,m1014689198,/, speed
++i0.236478,m962664017,r,s572, surveydns.html
++i0.589555,m1002157171,/, surveys
++i0.236278,m1002156396,r,s3503, surveys.html
++i0.96135,m973835888,/, syncookies
++i0.236479,m1012529017,r,s7918, syncookies.html
++i0.236460,m999204703,r,s1115, tcpcontrol.html
++i0.236461,m1016453307,r,s589, tcpip.html
++i0.236483,m951789713,r,s906, thoughts.html
++i0.136514,m996502689,/, threecubes
++i0.236462,m1000430758,r,s525, time.html
++i0.121107,m1022041265,/, ucspi-tcp
++i0.236484,m1011915691,r,s4086, ucspi-tcp.html
++i0.236285,m999204710,r,s732, web.html
++i0.236323,m1025804868,/, www
++i0.236467,m1000430768,r,s2717, y2k.html
++i0.94216,m981624489,/, dnsroot
++i0.236280,m988005697,r,s2745, 2001-260.html
++i0.236489,m951789713,r,s291, zeroseek.html
++i0.90373,m951789713,/, zmodexp
++i0.236490,m958703347,r,s1513, zmodexp.html
++i0.65452,m965092134,/, zmult
++i0.236491,m965093093,r,s669, zmult.html
++i0.236432,m977552387,r,s1097, checkpwd.html
++i0.236480,m1009824436,r,s2077, focus.html
++i0.236493,m964048291,r,s3842, im2000.html
++i0.5981,m1025804863,/, slashcommand
++i0.192219,m1025804864,/, slashpackage
++i0.236277,m995235879,r,s602, slashpackage.html
++i0.236302,m1020384933,r,s23874, talks.html
++i0.236495,m957763499,r,s566, 1997-275.html
++i0.236494,m957763864,r,s313, 1998-100.html
++i0.543361,m951789707,/, 2000-436
++i0.236424,m957764246,r,s660, 1997-494.html
++i0.236428,m957764441,r,s730, 1999-541.html
++i0.236497,m968828938,r,s2367, psibound.html
++i0.236500,m961639740,r,s1866, smallfactors.html
++i0.413016,m960514519,/, smallfactors
++i0.75096,m962492119,/, conferences
++i0.557013,m1022046749,/, djbdns
++i0.236282,m995342458,r,s2712, djbdns.html
++i0.236502,m963796539,r,s216, zpfft.html
++i0.537820,m966797797,/, fastnewton
++i0.236503,m966797851,r,s333, fastnewton.html
++i0.510806,m967833231,/, patents
++i0.236448,m977607617,r,s1748, ftpparse.html
++i0.236281,m1005436670,r,s3261, slash.html
++i0.236279,m979753810,r,s2663, slashdoc.html
++i0.236283,m1016442275,r,s2344, dnsroot.html
++i0.236284,m1009400580,r,s3238, software.html
++i0.236287,m1000434873,r,s3481, compatibility.html
++i0.236291,m1020223834,r,s5525, distributors.html
++i0.236293,m983072943,r,s212, freebugtraq.html
++i0.236294,m1017547190,r,s806, hardware.html
++i0.236296,m986022918,r,s121, securesoftware.html
++i0.236301,m1022035196,r,s10950, conferences.html
++i0.378623,m1007142710,/, 2001-275
++i0.236303,m991095307,r,s459, rwb100.html
++i0.236325,m1002087642,r,s863, nistp224.html
++i0.236436,m996502546,r,s778, threecubes.html
++i0.236298,m1023118336,r,s27125, papers.html
++i0.236439,m1006311069,r,s379, bib.html
++i0.236438,m1007142093,r,s3791, 2001-275.html
++i0.236474,m1002046139,r,s169, dh224.html
++i0.236434,m1016258736,r,s1126, courses.html
++i0.236466,m999469348,r,s355, slashcommand.html
++i0.236449,m1017264022,r,s1199, patents.html
++i0.236469,m1005247635,r,s640, mailcopyright.html
++i0.236286,m1022974070,r,s1257, djb.html
++i0.236481,m1010383954,r,s301, 2002-501.html
++i0.236482,m1020220905,r,s1655, export.html
++i0.236276,m1016966459,r,s6446, index.html
++i0.236485,m1023740653, donations.html
++i0.236486,m1016258948,r,s570, 2005-590.html
++i0.236487,m1016258749,r,s800, 2004-494.html
++i0.236488,m1023740407, thanks.html
++i0.236498,m1022974139,r,s4459, positions.html
++i0.236499,m1022972131,r,s466, contact.html
+226 Success.
+ftp> close
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/E-EPLF.out b/netwerk/test/gtest/parse-ftp/E-EPLF.out
new file mode 100644
index 0000000000..3cb6ae85b1
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/E-EPLF.out
@@ -0,0 +1,178 @@
+<!-- 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/. -->
+
+01-11-2001 09:38:25 <DIR> tmp
+02-29-2000 02:01:45 <DIR> 1998-100
+12-24-2000 20:44:06 1172 mirrors.html
+02-29-2000 02:01:47 <DIR> 1999-275
+05-08-2000 05:25:16 933 1999-275.html
+05-08-2000 05:27:06 322 1998-401.html
+02-29-2000 02:01:47 <DIR> 1998-401
+02-29-2000 02:01:45 <DIR> 1997-275
+05-08-2000 05:28:25 277 1998-515.html
+05-08-2000 05:36:43 325 2000-436.html
+12-23-2000 06:47:11 <DIR> checkpwd
+07-04-2002 17:47:46 <DIR> bib
+02-29-2000 02:01:47 <DIR> 1999-541
+04-28-2001 03:02:35 <DIR> 2001-260
+04-17-2002 18:27:55 <DIR> 2002-501
+06-01-2001 20:56:17 <DIR> 1995-514
+02-29-2000 02:01:45 <DIR> 1999-180
+06-01-2001 02:44:23 475 2000-515.html
+02-29-2000 02:01:47 <DIR> 1998-515
+02-29-2000 02:01:47 <DIR> 2000-515
+05-12-2000 07:46:13 <DIR> zpfft
+10-27-2001 13:00:14 <DIR> psibound
+02-29-2000 02:01:51 398 anonftpd.html
+02-26-2002 02:34:22 <DIR> nistp224
+08-10-2001 07:27:20 <DIR> cdb
+04-30-2002 23:58:27 <DIR> talks
+12-23-2000 21:34:35 <DIR> ftpparse
+01-11-2000 05:50:10 <DIR> clockspeed
+02-29-2000 02:01:52 1350 clockspeed.html
+02-06-2002 20:52:34 <DIR> slashdoc
+06-07-2002 16:00:40 <DIR> export
+07-17-2001 01:48:36 <DIR> daemontools
+07-12-2001 21:17:08 2187 daemontools.html
+08-30-2001 20:51:16 175 data.html
+12-28-2001 01:32:37 1901 crypto.html
+11-10-2001 23:45:23 739 arith.html
+11-30-2001 03:48:09 2733 cdb.html
+11-10-2001 23:51:02 344 floatasm.html
+12-21-2000 21:25:56 <DIR> djbfft
+02-29-2000 02:01:52 1319 djbfft.html
+07-09-2000 17:16:47 <DIR> dnscache
+07-03-2000 22:57:44 4016 dnscache.html
+07-10-2001 03:16:22 <DIR> docs
+02-29-2000 02:01:52 293 docs.html
+02-29-2000 02:01:52 952 dot-forward.html
+01-11-2000 05:50:11 <DIR> etc-mta
+02-29-2000 02:01:52 3174 etc-mta.html
+02-29-2000 02:01:52 2990 ezmlm.html
+12-21-2000 21:25:56 <DIR> ftp
+02-29-2000 02:01:49 <DIR> im
+02-29-2000 02:01:52 1823 fastforward.html
+02-29-2000 02:01:52 1707 ftp.html
+02-12-2001 02:17:10 <DIR> freebugtraq
+06-02-2002 01:39:25 <DIR> hardware
+06-01-2001 02:57:35 610 1995-514.html
+12-21-2000 21:25:57 <DIR> hash127
+05-19-2000 02:29:02 4835 hash127.html
+02-29-2000 02:01:52 1515 im.html
+02-12-2002 20:40:06 <DIR> immhf
+04-25-2001 21:48:49 2902 immhf.html
+01-25-2001 05:58:36 <DIR> lib
+06-05-2001 23:45:50 <DIR> libtai
+07-10-2000 18:54:16 2120 libtai.html
+11-27-2001 17:52:40 14460 qmail.html
+08-30-2001 20:51:23 2153 mail.html
+02-29-2000 02:01:52 108 maildir.html
+02-29-2000 02:01:50 <DIR> maildisasters
+02-29-2000 02:01:52 873 maildisasters.html
+02-29-2000 02:01:52 1688 mess822.html
+02-25-2002 02:47:27 <DIR> mirror
+12-26-2001 21:02:32 581 ntheory.html
+06-03-2002 15:36:27 <DIR> papers
+05-21-2002 16:50:15 <DIR> postpropter
+01-11-2000 05:50:12 <DIR> postings
+01-11-2000 05:50:12 <DIR> primegen
+08-30-2001 20:51:33 415 precompiled.html
+02-29-2000 02:01:52 1121 primegen.html
+05-05-2002 01:37:55 <DIR> proto
+02-29-2000 02:01:52 452 proto.html
+07-09-2001 22:17:53 <DIR> publicfile
+11-30-2001 03:59:17 5651 publicfile.html
+08-30-2001 20:51:37 409 qlist.html
+04-02-2002 05:25:45 <DIR> qmail
+02-02-2002 05:52:28 7549 lists.html
+02-29-2000 02:01:52 1166 qmailanalog.html
+08-30-2001 20:51:39 1434 qmsmac.html
+03-13-2000 05:38:06 465 rblsmtpd.html
+02-29-2000 02:01:52 1225 rights.html
+01-11-2000 05:50:13 <DIR> sarcasm
+09-14-2001 02:34:14 1058 unix.html
+02-29-2000 02:01:53 1568 serialmail.html
+10-02-2000 19:13:44 840 sigs.html
+05-21-2002 16:50:08 <DIR> smtp
+04-26-2001 15:58:47 1723 smtp.html
+12-21-2000 21:26:03 <DIR> software
+02-29-2000 02:01:53 3671 softwarelaw.html
+01-11-2000 05:50:13 <DIR> sortedsums
+02-29-2000 02:01:53 2735 sortedsums.html
+02-26-2002 02:06:38 <DIR> speed
+07-03-2000 22:40:17 572 surveydns.html
+10-04-2001 00:59:31 <DIR> surveys
+10-04-2001 00:46:36 3503 surveys.html
+11-10-2000 05:58:08 <DIR> syncookies
+02-01-2002 02:03:37 7918 syncookies.html
+08-30-2001 20:51:43 1115 tcpcontrol.html
+03-18-2002 12:08:27 589 tcpip.html
+02-29-2000 02:01:53 906 thoughts.html
+07-30-2001 14:18:09 <DIR> threecubes
+09-14-2001 01:25:58 525 time.html
+05-22-2002 04:21:05 <DIR> ucspi-tcp
+01-24-2002 23:41:31 4086 ucspi-tcp.html
+08-30-2001 20:51:50 732 web.html
+07-04-2002 17:47:48 <DIR> www
+09-14-2001 01:26:08 2717 y2k.html
+02-08-2001 09:28:09 <DIR> dnsroot
+04-23-2001 06:01:37 2745 2001-260.html
+02-29-2000 02:01:53 291 zeroseek.html
+02-29-2000 02:01:53 <DIR> zmodexp
+05-19-2000 02:29:07 1513 zmodexp.html
+08-01-2000 01:08:54 <DIR> zmult
+08-01-2000 01:24:53 669 zmult.html
+12-23-2000 06:19:47 1097 checkpwd.html
+12-31-2001 18:47:16 2077 focus.html
+07-19-2000 23:11:31 3842 im2000.html
+07-04-2002 17:47:43 <DIR> slashcommand
+07-04-2002 17:47:44 <DIR> slashpackage
+07-15-2001 22:24:39 602 slashpackage.html
+05-03-2002 00:15:33 23874 talks.html
+05-08-2000 05:24:59 566 1997-275.html
+05-08-2000 05:31:04 313 1998-100.html
+02-29-2000 02:01:47 <DIR> 2000-436
+05-08-2000 05:37:26 660 1997-494.html
+05-08-2000 05:40:41 730 1999-541.html
+09-13-2000 07:08:58 2367 psibound.html
+06-22-2000 02:09:00 1866 smallfactors.html
+06-09-2000 01:35:19 <DIR> smallfactors
+07-01-2000 22:55:19 <DIR> conferences
+05-22-2002 05:52:29 <DIR> djbdns
+07-17-2001 04:00:58 2712 djbdns.html
+07-17-2000 01:15:39 216 zpfft.html
+08-20-2000 18:56:37 <DIR> fastnewton
+08-20-2000 18:57:31 333 fastnewton.html
+09-01-2000 18:33:51 <DIR> patents
+12-23-2000 21:40:17 1748 ftpparse.html
+11-10-2001 23:57:50 3261 slash.html
+01-17-2001 17:50:10 2663 slashdoc.html
+03-18-2002 09:04:35 2344 dnsroot.html
+12-26-2001 21:03:00 3238 software.html
+09-14-2001 02:34:33 3481 compatibility.html
+05-01-2002 03:30:34 5525 distributors.html
+02-25-2001 03:49:03 212 freebugtraq.html
+03-31-2002 03:59:50 806 hardware.html
+03-31-2001 07:15:18 121 securesoftware.html
+05-22-2002 02:39:56 10950 conferences.html
+11-30-2001 17:51:50 <DIR> 2001-275
+05-29-2001 00:15:07 459 rwb100.html
+10-03-2001 05:40:42 863 nistp224.html
+07-30-2001 14:15:46 778 threecubes.html
+06-03-2002 15:32:16 27125 papers.html
+11-21-2001 02:51:09 379 bib.html
+11-30-2001 17:41:33 3791 2001-275.html
+10-02-2001 18:08:59 169 dh224.html
+03-16-2002 06:05:36 1126 courses.html
+09-02-2001 22:22:28 355 slashcommand.html
+03-27-2002 21:20:22 1199 patents.html
+11-08-2001 19:27:15 640 mailcopyright.html
+06-01-2002 23:27:50 1257 djb.html
+01-07-2002 06:12:34 301 2002-501.html
+05-01-2002 02:41:45 1655 export.html
+03-24-2002 10:40:59 6446 index.html
+03-16-2002 06:09:08 570 2005-590.html
+03-16-2002 06:05:49 800 2004-494.html
+06-01-2002 23:28:59 4459 positions.html
+06-01-2002 22:55:31 466 contact.html
diff --git a/netwerk/test/gtest/parse-ftp/O-guess.in b/netwerk/test/gtest/parse-ftp/O-guess.in
new file mode 100644
index 0000000000..4477a9d763
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/O-guess.in
@@ -0,0 +1,19 @@
+220 server IBM TCP/IP for OS/2 - FTP Server ver 23:04:36 on Jan 15 1997
+
+This listing is just a guess because I couldn't find an FTP server that
+LISTs like this. This guess is based on comments in Perl mirror project.
+I'm particularly unsure of the contents of cols 19-34.
+
+ 1 2 3 4 5 6
+0123456789012345678901234567890123456789012345678901234567890123456789
+----- size -------| ?????????????? MM-DD-YY| HH:MM| nnnnnnnnn....
+
+ 0 DIR 04-11-95 16:26 .
+ 0 DIR 04-11-95 16:26 ..
+ 0 DIR 04-11-95 16:26 ADDRESS
+ 612 A 07-28-95 16:45 air_tra1.bag
+ 195 A 08-09-95 10:23 Alfa1.bag
+ 0 DIR 04-11-95 16:26 ATTACH
+ 372 A 08-09-95 10:26 Aussie_1.bag
+ 310992 06-28-94 09:56 INSTALL.EXE
+ 12345 H 10-19-00 15:10 ADOE ADIR MOZILLA.FAKEOUT
diff --git a/netwerk/test/gtest/parse-ftp/O-guess.out b/netwerk/test/gtest/parse-ftp/O-guess.out
new file mode 100644
index 0000000000..402f77b5bf
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/O-guess.out
@@ -0,0 +1,13 @@
+<!-- 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/. -->
+
+04-11-1995 16:26:00 <DIR> .
+04-11-1995 16:26:00 <DIR> ..
+04-11-1995 16:26:00 <DIR> ADDRESS
+07-28-1995 16:45:00 612 air_tra1.bag
+08-09-1995 10:23:00 195 Alfa1.bag
+04-11-1995 16:26:00 <DIR> ATTACH
+08-09-1995 10:26:00 372 Aussie_1.bag
+06-28-1994 09:56:00 310992 INSTALL.EXE
+10-19-2000 15:10:00 12345 ADOE ADIR MOZILLA.FAKEOUT
diff --git a/netwerk/test/gtest/parse-ftp/R-dls.in b/netwerk/test/gtest/parse-ftp/R-dls.in
new file mode 100644
index 0000000000..b472a00bce
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/R-dls.in
@@ -0,0 +1,23 @@
+README 763 Information about this server
+bin/ -
+etc/ =
+ls-lR 0
+ls-lR.Z 3
+pub/ = Public area
+usr/ -
+morgan 14 -> ../real/morgan
+TIMIT.mostlikely.Z
+ 79215
+README 763 Feb 3 18:21 Information about this server
+bin/ - Apr 28 1994
+etc/ = 11 Jul 21:04
+ls-lR 0 6 Aug 17:14
+ls-lR.Z 3 05 Sep 1994
+pub/ = Jul 11 21:04 Public area
+usr/ - Sep 7 09:39
+morgan 14 Apr 18 9:39 -> ../real/morgan
+TIMIT.mostlikely.Z
+ 79215 Jan 4 6:45
+
+*** CAUTION while editing this sample LISTing -
+*** Lines contain trailing whitespace and/or '\r's
diff --git a/netwerk/test/gtest/parse-ftp/R-dls.out b/netwerk/test/gtest/parse-ftp/R-dls.out
new file mode 100644
index 0000000000..414f0320c5
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/R-dls.out
@@ -0,0 +1,22 @@
+<!-- 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/. -->
+
+00-00-0000 00:00:00 763 README
+00-00-0000 00:00:00 <DIR> bin
+00-00-0000 00:00:00 <DIR> etc
+00-00-0000 00:00:00 0 ls-lR
+00-00-0000 00:00:00 3 ls-lR.Z
+00-00-0000 00:00:00 <DIR> pub
+00-00-0000 00:00:00 <DIR> usr
+00-00-0000 00:00:00 <JUNCTION> morgan -> ../real/morgan
+00-00-0000 00:00:00 79215 TIMIT.mostlikely.Z
+02-03-2002 18:21:00 763 README
+04-28-1994 00:00:00 <DIR> bin
+07-11-2002 21:04:00 <DIR> etc
+08-06-2001 17:14:00 0 ls-lR
+09-05-1994 00:00:00 3 ls-lR.Z
+07-11-2002 21:04:00 <DIR> pub
+09-07-2001 09:39:00 <DIR> usr
+04-18-2002 09:39:00 <JUNCTION> morgan -> ../real/morgan
+01-04-2002 06:45:00 79215 TIMIT.mostlikely.Z
diff --git a/netwerk/test/gtest/parse-ftp/README b/netwerk/test/gtest/parse-ftp/README
new file mode 100644
index 0000000000..c49e28c700
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/README
@@ -0,0 +1,28 @@
+Testcases for the following:
+
+- VMS (MultiNet, UCX, and CMU) LIST format (including multi-line format)
+- IBM VM/CMS, VM/ESA LIST format (two known variants)
+- Windows NT's default "DOS-dirstyle"
+- OS/2 basic server format LIST format
+- SuperTCP FTP Server
+- NetManage Chameleon (NEWT)
+- EPLF (Easily Parsable List Format)
+- '/bin/dls' (two known variants, plus multi-line) LIST format
+- '/bin/ls -l' and all variants (even if they are not SYST UNIX)
+ including
+ - Hellsoft FTP for NetWare (non-unix perm-bits)
+ - Hethmon Brothers FTP for OS/2 (all '-' perm bits)
+ - NetPresenz (SYST is "MACOS")
+ - "NETWARE" (Hellsoft-style perms, no linkcount, no UID/GID)
+ - OpenBSD FTPD (numeric UID/GID)
+ - Open Group's FTP servers (no GID)
+ - Novonyx [Netscape/Novell] (fields not in columns)
+ - wuFTPd and other BSD-based ftpd that exec "ls -l"
+ - Windows NT server (internal "ls -l" compatible)
+ - Netmanage ProFTPD for Win32 (internal "ls -l" compatible)
+ - SurgeFTPd for Win32 (internal "ls -l" compatible)
+ - WarFTPd for Win32 (internal "ls -l" compatible)
+ - WebStarFTP for MacOS (internal "ls -l" compatible)
+ - MurkWorks FTP for NetWare (internal "ls -l" compatible)
+ - NcFTPd for Unix (internal "ls -l" compatible).
+
diff --git a/netwerk/test/gtest/parse-ftp/TestParseFTPList.cpp b/netwerk/test/gtest/parse-ftp/TestParseFTPList.cpp
new file mode 100644
index 0000000000..1f8f529b90
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/TestParseFTPList.cpp
@@ -0,0 +1,138 @@
+/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* 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/. */
+
+#include "gtest/gtest.h"
+#include "mozilla/ArrayUtils.h"
+#include "nsPrintfCString.h"
+#include <stdio.h>
+
+#include "ParseFTPList.h"
+
+PRTime gTestTime = 0;
+
+// Pretend this is the current time for the purpose of running the
+// test. The day and year matter because they are used to figure out a
+// default value when no year is specified. Tests will fail if this is
+// changed too much.
+const char* kDefaultTestTime = "01-Aug-2002 00:00:00 GMT";
+
+static PRTime TestTime() { return gTestTime; }
+
+static void ParseFTPLine(char* inputLine, FILE* resultFile, list_state* state) {
+ struct list_result result;
+ int rc = ParseFTPList(inputLine, state, &result, PR_GMTParameters, TestTime);
+
+ if (rc == '?' || rc == '"') {
+ // Ignore junk and comments.
+ return;
+ }
+
+ if (!resultFile) {
+ // No result file was passed in, so there's nothing to check.
+ return;
+ }
+
+ char resultLine[512];
+ ASSERT_NE(fgets(resultLine, sizeof(resultLine), resultFile), nullptr);
+
+ nsPrintfCString parsed(
+ "%02u-%02u-%04u %02u:%02u:%02u %20s %.*s%s%.*s\n",
+ (result.fe_time.tm_mday ? (result.fe_time.tm_month + 1) : 0),
+ result.fe_time.tm_mday,
+ (result.fe_time.tm_mday ? result.fe_time.tm_year : 0),
+ result.fe_time.tm_hour, result.fe_time.tm_min, result.fe_time.tm_sec,
+ (rc == 'd' ? "<DIR> "
+ : (rc == 'l' ? "<JUNCTION> " : result.fe_size)),
+ (int)result.fe_fnlen, result.fe_fname,
+ ((rc == 'l' && result.fe_lnlen) ? " -> " : ""),
+ (int)((rc == 'l' && result.fe_lnlen) ? result.fe_lnlen : 0),
+ ((rc == 'l' && result.fe_lnlen) ? result.fe_lname : ""));
+
+ ASSERT_STREQ(parsed.get(), resultLine);
+}
+
+FILE* OpenResultFile(const char* resultFileName) {
+ if (!resultFileName) {
+ return nullptr;
+ }
+
+ FILE* resultFile = fopen(resultFileName, "r");
+ EXPECT_NE(resultFile, nullptr);
+
+ // Ignore anything in the expected result file before and including the first
+ // blank line.
+ char resultLine[512];
+ while (fgets(resultLine, sizeof(resultLine), resultFile)) {
+ size_t lineLen = strlen(resultLine);
+ EXPECT_LT(lineLen, sizeof(resultLine) - 1);
+ if (lineLen > 0 && resultLine[lineLen - 1] == '\n') {
+ lineLen--;
+ }
+ if (lineLen == 0) {
+ break;
+ }
+ }
+
+ // There must be a blank line somewhere in the result file.
+ EXPECT_EQ(strcmp(resultLine, "\n"), 0);
+
+ return resultFile;
+}
+
+void ParseFTPFile(const char* inputFileName, const char* resultFileName) {
+ printf("Checking %s\n", inputFileName);
+ FILE* inFile = fopen(inputFileName, "r");
+ ASSERT_NE(inFile, nullptr);
+
+ FILE* resultFile = OpenResultFile(resultFileName);
+
+ char inputLine[512];
+ struct list_state state;
+ memset(&state, 0, sizeof(state));
+ while (fgets(inputLine, sizeof(inputLine), inFile)) {
+ size_t lineLen = strlen(inputLine);
+ EXPECT_LT(lineLen, sizeof(inputLine) - 1);
+ if (lineLen > 0 && inputLine[lineLen - 1] == '\n') {
+ lineLen--;
+ }
+
+ ParseFTPLine(inputLine, resultFile, &state);
+ }
+
+ // Make sure there are no extra lines in the result file.
+ if (resultFile) {
+ char resultLine[512];
+ EXPECT_EQ(fgets(resultLine, sizeof(resultLine), resultFile), nullptr)
+ << "There should not be more lines in the expected results file than "
+ "in the parser output.";
+ fclose(resultFile);
+ }
+
+ fclose(inFile);
+}
+
+static const char* testFiles[] = {
+ "3-guess", "C-VMold", "C-zVM", "D-WinNT", "E-EPLF",
+ "O-guess", "R-dls", "U-HellSoft", "U-hethmon", "U-murksw",
+ "U-ncFTPd", "U-NetPresenz", "U-NetWare", "U-nogid", "U-no_ug",
+ "U-Novonyx", "U-proftpd", "U-Surge", "U-WarFTPd", "U-WebStar",
+ "U-WinNT", "U-wu", "V-MultiNet", "V-VMS-mix",
+};
+
+TEST(ParseFTPTest, Check)
+{
+ PRStatus result = PR_ParseTimeString(kDefaultTestTime, true, &gTestTime);
+ ASSERT_EQ(PR_SUCCESS, result);
+
+ char inputFileName[200];
+ char resultFileName[200];
+ for (size_t test = 0; test < mozilla::ArrayLength(testFiles); ++test) {
+ snprintf(inputFileName, mozilla::ArrayLength(inputFileName), "%s.in",
+ testFiles[test]);
+ snprintf(resultFileName, mozilla::ArrayLength(inputFileName), "%s.out",
+ testFiles[test]);
+ ParseFTPFile(inputFileName, resultFileName);
+ }
+}
diff --git a/netwerk/test/gtest/parse-ftp/U-HellSoft.in b/netwerk/test/gtest/parse-ftp/U-HellSoft.in
new file mode 100644
index 0000000000..50f03d664a
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-HellSoft.in
@@ -0,0 +1,25 @@
+ftp> open pandora.anglistik.uni-mainz.de
+220 pandora FTP Server for NW 3.1x, 4.xx (v1.10), (c) 1994 HellSoft.
+Name (pandora.anglistik.uni-mainz.de:cyp):
+331 Password required.
+230-User Logged.
+230 Home Directory: /SYS/USER/FTP
+ftp> ls
+200 Command Accepted.
+150 Opening ASCII data connection.
+d[RWCEMFA] 1 cyp 512 Jul 01 11:49 htdocs
+d[RWCEMFA] 1 cyp 512 Jul 02 08:56 config
+d[RWCEMFA] 1 cyp 512 Jun 20 11:23 other
+d[RWCEMFA] 1 cyp 512 Jun 20 11:23 mail
+d[RWCEMFA] 1 cyp 512 Jun 20 14:35 news
+d[RWCEMFA] 1 cyp 512 Jun 30 08:48 download
+-[RWCEMFA] 1 *unknown 13312 May 27 1997 19calit.doc
+-[RWCEMFA] 1 *unknown 237 Feb 21 1997 forfile.bat
+-[RWCEMFA] 1 *unknown 1401 Mar 03 1997 intertex.txt
+d[RWCEMFA] 1 cyp 512 May 15 08:55 d1
+d[RWCEMFA] 1 cyp 512 May 06 10:57 drivers
+d[RWCEMFA] 1 cyp 512 Mar 28 12:05 --moved-
+226 Transfer complete.
+ftp> close
+221 Goodbye.
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-HellSoft.out b/netwerk/test/gtest/parse-ftp/U-HellSoft.out
new file mode 100644
index 0000000000..a42b16315c
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-HellSoft.out
@@ -0,0 +1,16 @@
+<!-- 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/. -->
+
+07-01-2002 11:49:00 <DIR> htdocs
+07-02-2002 08:56:00 <DIR> config
+06-20-2002 11:23:00 <DIR> other
+06-20-2002 11:23:00 <DIR> mail
+06-20-2002 14:35:00 <DIR> news
+06-30-2002 08:48:00 <DIR> download
+05-27-1997 00:00:00 13312 19calit.doc
+02-21-1997 00:00:00 237 forfile.bat
+03-03-1997 00:00:00 1401 intertex.txt
+05-15-2002 08:55:00 <DIR> d1
+05-06-2002 10:57:00 <DIR> drivers
+03-28-2002 12:05:00 <DIR> --moved-
diff --git a/netwerk/test/gtest/parse-ftp/U-NetPresenz.in b/netwerk/test/gtest/parse-ftp/U-NetPresenz.in
new file mode 100644
index 0000000000..1114ffe4ba
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-NetPresenz.in
@@ -0,0 +1,31 @@
+ftp> open gean5.pfmb.uni-mb.si
+Connected to gean5.pfmb.uni-mb.si.
+220 NetPresenz v4.1 (Unregistered) awaits your command.
+Name (gean5.pfmb.uni-mb.si:cyp):
+331 Guest log in, send Email address (user@host) as password.
+230-This file must be in the Startup Messages folder in either the same
+ folder as NetPresenz or in the NetPresenz Preferences folder in the
+ Preferences folder, and will be displayed to guests user when they log
+ in. Guest users log in by using the username "ftp" or "anonymous".
+230 Anonymous login to 1 volumes. Access restrictions apply. "/Eng Dept web pages/MariborEnglishClub".
+Remote system type is MACOS.
+ftp> ls
+200 PORT command successful.
+150 ASCII transfer started.
+-------r-- 0 2166 2166 Mar 22 09:21 default.htm
+-------r-- 0 16504 16504 Mar 21 14:32 FAQs.htm
+drwxr-xr-x folder 5 Mar 22 10:06 FAQs_files
+-------r-- 0 250 250 Mar 22 09:22 filelist.xml
+-------r-- 0 1575 1575 Mar 21 14:22 image001.gif
+-------r-- 0 631827 631827 Mar 21 14:22 image002.jpg
+-------r-- 0 34318 34318 Mar 21 14:22 image003.jpg
+-------r-- 0 9121 9121 Mar 22 09:30 MariborEnglishClubHomepage.htm
+-------r-- 0 6710 6710 Mar 21 14:30 Photos.htm
+drwxr-xr-x folder 5 Mar 22 10:06 Photos_files
+-------r-- 0 5995 5995 Mar 22 09:23 TOCFrame.htm
+-------r-- 0 7226 7226 Mar 21 14:27 Upcoming Events.htm
+drwxr-xr-x folder 3 Mar 22 10:06 Upcoming Events_files
+226 Transfer complete.
+ftp>ftp> close
+221 Nice chatting with you.
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-NetPresenz.out b/netwerk/test/gtest/parse-ftp/U-NetPresenz.out
new file mode 100644
index 0000000000..754e0e3ca5
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-NetPresenz.out
@@ -0,0 +1,17 @@
+<!-- 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/. -->
+
+03-22-2002 09:21:00 2166 default.htm
+03-21-2002 14:32:00 16504 FAQs.htm
+03-22-2002 10:06:00 <DIR> FAQs_files
+03-22-2002 09:22:00 250 filelist.xml
+03-21-2002 14:22:00 1575 image001.gif
+03-21-2002 14:22:00 631827 image002.jpg
+03-21-2002 14:22:00 34318 image003.jpg
+03-22-2002 09:30:00 9121 MariborEnglishClubHomepage.htm
+03-21-2002 14:30:00 6710 Photos.htm
+03-22-2002 10:06:00 <DIR> Photos_files
+03-22-2002 09:23:00 5995 TOCFrame.htm
+03-21-2002 14:27:00 7226 Upcoming Events.htm
+03-22-2002 10:06:00 <DIR> Upcoming Events_files
diff --git a/netwerk/test/gtest/parse-ftp/U-NetWare.in b/netwerk/test/gtest/parse-ftp/U-NetWare.in
new file mode 100644
index 0000000000..c7252569e8
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-NetWare.in
@@ -0,0 +1,51 @@
+ftp> open netlab2.usu.edu
+Connected to netlab2.usu.edu.
+220 Service Ready for new User
+Name (netlab2.usu.edu:cyp):
+331 Enter E-Mail id as Password
+230 User anonymous Logged in Successfully
+Remote system type is NETWARE.
+ftp> syst
+215 NETWARE Type : L8
+ftp> ls
+200 PORT Command OK
+150 Opening data connection
+total 0
+- [RWCEAFMS] NFAUUser 192 Apr 27 15:21 HEADER.html
+d [RWCEAFMS] jrd 512 Jul 11 03:01 allupdates
+d [RWCEAFMS] jrd 512 Dec 05 2001 apps
+d [RWCEAFMS] jrd 512 Oct 21 2001 bsuk00
+d [RWCEAFMS] jrd 512 Oct 21 2001 bsuk2001
+d [RWCEAFMS] jrd 512 Oct 21 2001 bsuk99
+d [RWCEAFMS] jrd 512 Oct 21 2001 bsus2000
+d [RWCEAFMS] jrd 512 Oct 21 2001 bsus2001
+d [RWCEAFMS] jrd 512 Mar 27 20:23 bsus2002
+d [RWCEAFMS] jrd 512 Oct 21 2001 bsus99
+d [RWCEAFMS] jrd 512 Oct 21 2001 drivers
+d [RWCEAFMS] jrd 512 Oct 24 2001 freebird
+d [RWCEAFMS] jrd 512 Apr 30 13:56 kermit
+d [RWCEAFMS] jrd 512 Oct 21 2001 macipx
+d [RWCEAFMS] jrd 512 Jun 13 01:45 misc
+d [RWCEAFMS] jrd 512 Oct 21 2001 netwatch
+d [RWCEAFMS] jrd 512 Oct 21 2001 netwire
+d [RWCEAFMS] jrd 512 Oct 21 2001 odi
+d [RWCEAFMS] jrd 512 Oct 21 2001 pktdrvr
+d [RWCEAFMS] jrd 512 Mar 02 20:23 rfc
+d [RWCEAFMS] jrd 512 Oct 30 2001 UnixWare
+d [RWCEAFMS] jrd 512 Oct 21 2001 updates
+- [RWCEAFMS] jrd 666258 Oct 30 1992 ENCAPS10.PS
+- [RWCEAFMS] jrd 25085 Oct 28 1992 ENCAPS10.TXT
+- [RWCEAFMS] jrd 611989 Jan 13 1993 ENCAPS11.PS
+- [RWCEAFMS] jrd 27134 Jan 12 1993 ENCAPS11.TXT
+- [RWCEAFMS] jrd 372 Jan 13 1993 README.TXT
+226 Transfer Complete
+ftp> site help
+214-Only DOS and LONG site commands are supported for Anonymous Users
+ DOS :
+ The DOS command shows the file/directory permissions in DOS format.
+ LONG :
+ The LONG command shows the file/directory permissions in LONG format.
+214 End of Help
+ftp> close
+221 Closing Session
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-NetWare.out b/netwerk/test/gtest/parse-ftp/U-NetWare.out
new file mode 100644
index 0000000000..6cf23ffb33
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-NetWare.out
@@ -0,0 +1,31 @@
+<!-- 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/. -->
+
+04-27-2002 15:21:00 192 HEADER.html
+07-11-2002 03:01:00 <DIR> allupdates
+12-05-2001 00:00:00 <DIR> apps
+10-21-2001 00:00:00 <DIR> bsuk00
+10-21-2001 00:00:00 <DIR> bsuk2001
+10-21-2001 00:00:00 <DIR> bsuk99
+10-21-2001 00:00:00 <DIR> bsus2000
+10-21-2001 00:00:00 <DIR> bsus2001
+03-27-2002 20:23:00 <DIR> bsus2002
+10-21-2001 00:00:00 <DIR> bsus99
+10-21-2001 00:00:00 <DIR> drivers
+10-24-2001 00:00:00 <DIR> freebird
+04-30-2002 13:56:00 <DIR> kermit
+10-21-2001 00:00:00 <DIR> macipx
+06-13-2002 01:45:00 <DIR> misc
+10-21-2001 00:00:00 <DIR> netwatch
+10-21-2001 00:00:00 <DIR> netwire
+10-21-2001 00:00:00 <DIR> odi
+10-21-2001 00:00:00 <DIR> pktdrvr
+03-02-2002 20:23:00 <DIR> rfc
+10-30-2001 00:00:00 <DIR> UnixWare
+10-21-2001 00:00:00 <DIR> updates
+10-30-1992 00:00:00 666258 ENCAPS10.PS
+10-28-1992 00:00:00 25085 ENCAPS10.TXT
+01-13-1993 00:00:00 611989 ENCAPS11.PS
+01-12-1993 00:00:00 27134 ENCAPS11.TXT
+01-13-1993 00:00:00 372 README.TXT
diff --git a/netwerk/test/gtest/parse-ftp/U-Novonyx.in b/netwerk/test/gtest/parse-ftp/U-Novonyx.in
new file mode 100644
index 0000000000..e3de9474d9
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-Novonyx.in
@@ -0,0 +1,92 @@
+ftp> open pandora.anglistik.uni-mainz.de
+220- Novonyx FTP Server for NetWare, v0.51 (9-16-98)
+220 Service Ready
+Name (pandora.anglistik.uni-mainz.de:cyp):
+331 User name okay, need password
+230 User logged in, proceed
+Remote system type is UNIX.
+Using binary mode to transfer files.
+ftp> cd login
+250 Directory successfully changed
+ftp> ls
+200 PORT Command OK
+150 File status OK, about to open data connection
+total 123
+-rw-rw-rw- 1 root sysadmin 25775 Sep 29 19:45 NOD$UPD.BAT
+-r--r--r-- 1 root sysadmin 2860 Feb 6 22:03 AX_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 B5DV_AIO.OVL
+-r--r--r-- 1 root sysadmin 7843 Feb 6 22:03 B5DV_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 B5ET_AIO.OVL
+-r--r--r-- 1 root sysadmin 5589 Feb 6 22:03 B5ET_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 B5KC_AIO.OVL
+-r--r--r-- 1 root sysadmin 5042 Feb 6 22:03 B5KC_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 BIG5_AIO.OVL
+-r--r--r-- 1 root sysadmin 3710 Feb 6 22:03 BIG5_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 CMPQ_AIO.OVL
+-r--r--r-- 1 root sysadmin 2815 Feb 6 22:03 CMPQ_RUN.OVL
+-r-xr-xr-x 1 root sysadmin 210009 Feb 6 22:03 CX.EXE
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 DOSV_AIO.OVL
+-r--r--r-- 1 root sysadmin 3825 Feb 6 22:03 DOSV_RUN.OVL
+-r--r--r-- 1 root sysadmin 16264 Feb 6 22:03 ETHER.RPL
+-r--r--r-- 1 root sysadmin 12133 Feb 6 22:03 F1ETH.RPL
+-r--r--r-- 1 root sysadmin 5141 Feb 6 22:03 FMR_AIO.OVL
+-r--r--r-- 1 root sysadmin 4747 Feb 6 22:03 FMR_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 GBCD_AIO.OVL
+-r--r--r-- 1 root sysadmin 3857 Feb 6 22:03 GBCD_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 GBET_AIO.OVL
+-r--r--r-- 1 root sysadmin 5545 Feb 6 22:03 GBET_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 GBLX_AIO.OVL
+-r--r--r-- 1 root sysadmin 3913 Feb 6 22:03 GBLX_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 GBPD_AIO.OVL
+-r--r--r-- 1 root sysadmin 8019 Feb 6 22:03 GBPD_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 GBSP_AIO.OVL
+-r--r--r-- 1 root sysadmin 8141 Feb 6 22:03 GBSP_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 GBTW_AIO.OVL
+-r--r--r-- 1 root sysadmin 4152 Feb 6 22:03 GBTW_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 GBUC_AIO.OVL
+-r--r--r-- 1 root sysadmin 4033 Feb 6 22:03 GBUC_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 GBWM_AIO.OVL
+-r--r--r-- 1 root sysadmin 3710 Feb 6 22:03 GBWM_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 GBXJ_AIO.OVL
+-r--r--r-- 1 root sysadmin 3848 Feb 6 22:03 GBXJ_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 GB_AIO.OVL
+-r--r--r-- 1 root sysadmin 3710 Feb 6 22:03 GB_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 IBM_AIO.OVL
+-r--r--r-- 1 root sysadmin 2815 Feb 6 22:03 IBM_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 J31_AIO.OVL
+-r--r--r-- 1 root sysadmin 5240 Feb 6 22:03 J31_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 KOR_AIO.OVL
+-r--r--r-- 1 root sysadmin 3710 Feb 6 22:03 KOR_RUN.OVL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 KSC_AIO.OVL
+-r--r--r-- 1 root sysadmin 3710 Feb 6 22:03 KSC_RUN.OVL
+-r-xr-xr-x 1 root sysadmin 311171 Apr 4 14:19 LOGIN.EXE
+-r--r--r-- 1 root sysadmin 5167 Feb 6 22:03 PC98_AIO.OVL
+-r--r--r-- 1 root sysadmin 7152 Feb 6 22:03 PC98_RUN.OVL
+-r--r--r-- 1 root sysadmin 10991 Feb 6 22:03 PCN2L.RPL
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 PS55_AIO.OVL
+-r--r--r-- 1 root sysadmin 3616 Feb 6 22:03 PS55_RUN.OVL
+-r--r--r-- 1 root sysadmin 8074 Feb 6 22:03 RBOOT.RPL
+-r--r--r-- 1 root sysadmin 9170 Feb 6 22:03 TEXTUTIL.IDX
+-r--r--r-- 1 root sysadmin 18433 Feb 6 22:03 TOKEN.RPL
+-r-xr-xr-x 1 root sysadmin 43549 Feb 6 22:03 TYPEMSG.EXE
+-r--r--r-- 1 root sysadmin 27 Feb 6 22:03 ATTACH.BAT
+-rwxrwxrwx 1 root sysadmin 439913 Feb 6 23:33 NLIST.EXE
+-r--r--r-- 1 root sysadmin 307 Feb 6 22:03 MENU_X.BAT
+-rwxrwxrwx 1 root sysadmin 269247 Feb 6 23:33 MAP.EXE
+-r--r--r-- 1 root sysadmin 4965 Feb 6 22:03 AX_AIO.OVL
+-r-xr-xr-x 1 root sysadmin 111663 Apr 16 12:20 LOGIN3X.EXE
+-rw-rw-rw- 1 root sysadmin 38 Apr 18 15:19 login.nb
+-r-xr-xr-x 1 root sysadmin 392528 Apr 20 04:02 NPRINTER.EXE
+-r-xr-xr-x 1 root sysadmin 311171 Feb 9 16:29 LOGIN4X.EXE
+-rw-rw-rw- 1 root sysadmin 2102 Feb 8 13:18 lpt$cap.bat
+-rw-rw-rw- 1 root sysadmin 20614 Mar 13 13:42 nod$log.bat
+-rw-rw-rw- 1 root sysadmin 20450 Mar 12 10:36 nod$log.~ba
+drwxrwxrwx 1 root sysadmin 0 Mar 8 13:30 NLS
+drwxrwxrwx 1 root sysadmin 0 Mar 8 13:30 OS2
+drwxrwxrwx 1 root sysadmin 0 Apr 9 16:37 NOD$LOG.DRV
+drwxrwxrwx 1 root sysadmin 0 Apr 9 16:36 LOCAL
+drwxrwxrwx 1 root sysadmin 0 Mar 16 14:25 local.nt4
+226 Requested file action okay, completed
+ftp> close
+221 Service closing connection, user logged out
+ftp>
diff --git a/netwerk/test/gtest/parse-ftp/U-Novonyx.out b/netwerk/test/gtest/parse-ftp/U-Novonyx.out
new file mode 100644
index 0000000000..8755d5fa7b
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-Novonyx.out
@@ -0,0 +1,78 @@
+<!-- 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/. -->
+
+09-29-2001 19:45:00 25775 NOD$UPD.BAT
+02-06-2002 22:03:00 2860 AX_RUN.OVL
+02-06-2002 22:03:00 4965 B5DV_AIO.OVL
+02-06-2002 22:03:00 7843 B5DV_RUN.OVL
+02-06-2002 22:03:00 4965 B5ET_AIO.OVL
+02-06-2002 22:03:00 5589 B5ET_RUN.OVL
+02-06-2002 22:03:00 4965 B5KC_AIO.OVL
+02-06-2002 22:03:00 5042 B5KC_RUN.OVL
+02-06-2002 22:03:00 4965 BIG5_AIO.OVL
+02-06-2002 22:03:00 3710 BIG5_RUN.OVL
+02-06-2002 22:03:00 4965 CMPQ_AIO.OVL
+02-06-2002 22:03:00 2815 CMPQ_RUN.OVL
+02-06-2002 22:03:00 210009 CX.EXE
+02-06-2002 22:03:00 4965 DOSV_AIO.OVL
+02-06-2002 22:03:00 3825 DOSV_RUN.OVL
+02-06-2002 22:03:00 16264 ETHER.RPL
+02-06-2002 22:03:00 12133 F1ETH.RPL
+02-06-2002 22:03:00 5141 FMR_AIO.OVL
+02-06-2002 22:03:00 4747 FMR_RUN.OVL
+02-06-2002 22:03:00 4965 GBCD_AIO.OVL
+02-06-2002 22:03:00 3857 GBCD_RUN.OVL
+02-06-2002 22:03:00 4965 GBET_AIO.OVL
+02-06-2002 22:03:00 5545 GBET_RUN.OVL
+02-06-2002 22:03:00 4965 GBLX_AIO.OVL
+02-06-2002 22:03:00 3913 GBLX_RUN.OVL
+02-06-2002 22:03:00 4965 GBPD_AIO.OVL
+02-06-2002 22:03:00 8019 GBPD_RUN.OVL
+02-06-2002 22:03:00 4965 GBSP_AIO.OVL
+02-06-2002 22:03:00 8141 GBSP_RUN.OVL
+02-06-2002 22:03:00 4965 GBTW_AIO.OVL
+02-06-2002 22:03:00 4152 GBTW_RUN.OVL
+02-06-2002 22:03:00 4965 GBUC_AIO.OVL
+02-06-2002 22:03:00 4033 GBUC_RUN.OVL
+02-06-2002 22:03:00 4965 GBWM_AIO.OVL
+02-06-2002 22:03:00 3710 GBWM_RUN.OVL
+02-06-2002 22:03:00 4965 GBXJ_AIO.OVL
+02-06-2002 22:03:00 3848 GBXJ_RUN.OVL
+02-06-2002 22:03:00 4965 GB_AIO.OVL
+02-06-2002 22:03:00 3710 GB_RUN.OVL
+02-06-2002 22:03:00 4965 IBM_AIO.OVL
+02-06-2002 22:03:00 2815 IBM_RUN.OVL
+02-06-2002 22:03:00 4965 J31_AIO.OVL
+02-06-2002 22:03:00 5240 J31_RUN.OVL
+02-06-2002 22:03:00 4965 KOR_AIO.OVL
+02-06-2002 22:03:00 3710 KOR_RUN.OVL
+02-06-2002 22:03:00 4965 KSC_AIO.OVL
+02-06-2002 22:03:00 3710 KSC_RUN.OVL
+04-04-2002 14:19:00 311171 LOGIN.EXE
+02-06-2002 22:03:00 5167 PC98_AIO.OVL
+02-06-2002 22:03:00 7152 PC98_RUN.OVL
+02-06-2002 22:03:00 10991 PCN2L.RPL
+02-06-2002 22:03:00 4965 PS55_AIO.OVL
+02-06-2002 22:03:00 3616 PS55_RUN.OVL
+02-06-2002 22:03:00 8074 RBOOT.RPL
+02-06-2002 22:03:00 9170 TEXTUTIL.IDX
+02-06-2002 22:03:00 18433 TOKEN.RPL
+02-06-2002 22:03:00 43549 TYPEMSG.EXE
+02-06-2002 22:03:00 27 ATTACH.BAT
+02-06-2002 23:33:00 439913 NLIST.EXE
+02-06-2002 22:03:00 307 MENU_X.BAT
+02-06-2002 23:33:00 269247 MAP.EXE
+02-06-2002 22:03:00 4965 AX_AIO.OVL
+04-16-2002 12:20:00 111663 LOGIN3X.EXE
+04-18-2002 15:19:00 38 login.nb
+04-20-2002 04:02:00 392528 NPRINTER.EXE
+02-09-2002 16:29:00 311171 LOGIN4X.EXE
+02-08-2002 13:18:00 2102 lpt$cap.bat
+03-13-2002 13:42:00 20614 nod$log.bat
+03-12-2002 10:36:00 20450 nod$log.~ba
+03-08-2002 13:30:00 <DIR> NLS
+03-08-2002 13:30:00 <DIR> OS2
+04-09-2002 16:37:00 <DIR> NOD$LOG.DRV
+04-09-2002 16:36:00 <DIR> LOCAL
+03-16-2002 14:25:00 <DIR> local.nt4
diff --git a/netwerk/test/gtest/parse-ftp/U-Surge.in b/netwerk/test/gtest/parse-ftp/U-Surge.in
new file mode 100644
index 0000000000..f1e0963688
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-Surge.in
@@ -0,0 +1,66 @@
+ftp> open netwinsite.com
+Connected to netwinsite.com.
+220 SurgeFTP netwin1 (Version 2.1e)
+Name (netwinsite.com:cyp): 331 Guest login ok, send your complete e-mail address as password.
+230- Alias Real path Access
+230- / /disk2/ftp read
+230 User anonymous logged in.
+Remote system type is UNIX.
+Using binary mode to transfer files.
+ftp> cd pub
+250 CWD command successful now (/pub)
+ftp> ls
+200 PORT command successful.
+150 Opening ASCII mode data connection for file list. (/pub)
+drwxr-xr-x 2 jesseftp netwin 4096 Jul 7 21:37 cgimail
+drwxr-xr-x 4 dnewsftp netwin 4096 May 2 17:38 dbabble
+drwxr-xr-x 2 netwin netwin 4096 Jul 1 2001 dek_temp
+drwxr-xr-x 2 netwin netwin 4096 Jul 1 2001 deye
+drwxr-xr-x 2 jesseftp root 4096 Feb 18 17:50 dfree
+drwxr-xr-x 2 netwin netwin 4096 Jul 1 2001 dgate
+drwxr-xr-x 4 root root 4096 Jan 31 15:18 discontinued
+drwxr-xr-x 4 dmailftp netwin 8192 Jul 7 21:28 dmail
+drwxr-xr-x 4 pnftp netwin 4096 Jun 30 17:56 dmailweb
+drwxr-xr-x 8 dnewsftp netwin 8192 Jul 10 1:40 dnews
+drwxr-xr-x 3 netwin netwin 4096 Jul 1 2001 dnewsweb
+drwxr-xr-x 3 pnftp root 4096 Sep 4 2001 dnotice
+drwxr-xr-x 2 root root 4096 May 6 16:58 fengate
+drwxr-xr-x 2 pnftp root 4096 May 28 19:01 ferngate
+drwxr-xr-x 3 netwin netwin 4096 Jul 1 2001 jeeves
+drwxr-xr-x 2 netwin netwin 4096 Jun 27 20:10 misc
+drwxr-xr-x 3 pnftp bin 4096 Jul 4 21:13 netauth
+drwxr-xr-x 2 pnftp bin 4096 Feb 8 1999 poppassd
+drwxr-xr-x 2 jesseftp netwin 4096 Jul 9 1:39 surgeftp
+drwxr-xr-x 2 surgemail root 4096 Jul 3 0:00 surgemail
+drwxr-xr-x 2 surgemail root 4096 Jul 3 0:01 surgemail-enterprise
+drwxr-xr-x 2 surgemail root 4096 Jul 3 0:01 surgemail-home
+drwxr-xr-x 2 surgemail root 4096 Jul 3 0:01 surgemail-isp
+drwxr-xr-x 2 surgemail root 4096 Jul 3 0:01 surgemail-workplace
+drwxr-xr-x 3 netwin bin 4096 Jul 4 2001 watchdog
+drwxr-xr-x 3 pnftp bin 4096 Mar 21 2001 webimap
+drwxr-xr-x 3 pnftp root 4096 Apr 28 21:30 webmail
+drwxr-xr-x 3 pnftp bin 4096 Jun 30 18:23 webnews
+drwxr-xr-x 2 pnftp root 4096 Jan 30 20:31 webshareit
+drwxr-xr-x 2 netwin bin 4096 Sep 20 1999 webtwin
+drwxr-xr-x 4 pnftp root 4096 Jul 8 17:07 beta
+lrwxrwxrwx 1 pnftp pnftp 12 Mar 18 15:48 wmail.exe -> wmail30h.exe
+-rw-r--r-- 1 pnftp pnftp 2312192 Feb 19 15:33 wmail30h.exe
+-rw-r--r-- 1 pnftp pnftp 3360893 Feb 21 19:24 wmail30h_aix4.tar.Z
+-rw-r--r-- 1 pnftp pnftp 3508885 Mar 18 15:47 wmail30h_bsdi4.tar.Z
+-rw-r--r-- 1 pnftp pnftp 2693234 Feb 19 15:47 wmail30h_freebsd.tar.Z
+-rw-r--r-- 1 pnftp pnftp 2640047 Feb 19 15:38 wmail30h_freebsd3.tar.Z
+-rw-r--r-- 1 pnftp pnftp 2654381 Feb 19 15:43 wmail30h_freebsd4.tar.Z
+-rw-r--r-- 1 pnftp pnftp 3005333 Mar 18 18:21 wmail30h_hpux.tar.Z
+-rw-r--r-- 1 pnftp pnftp 2779942 Feb 19 15:52 wmail30h_linux.tar.Z
+-rw-r--r-- 1 pnftp pnftp 2782353 Feb 19 15:58 wmail30h_linuxlibc6.tar.Z
+-rw-r--r-- 1 pnftp pnftp 1783391 Feb 19 16:01 wmail30h_linuxppc.tar.gz
+-rw-r--r-- 1 pnftp pnftp 2758233 Mar 18 15:47 wmail30h_macosx_aqua.tar.Z
+-rw-r--r-- 1 pnftp pnftp 3113365 Mar 18 15:47 wmail30h_osf.tar.Z
+-rw-r--r-- 1 pnftp pnftp 1779720 Apr 28 21:30 wmail30h_raq3.tar.gz
+-rw-r--r-- 1 pnftp pnftp 1789173 Mar 11 16:38 wmail30h_raq4.tar.gz
+-rw-r--r-- 1 pnftp pnftp 2846045 Feb 19 16:06 wmail30h_solaris.tar.Z
+-rw-r--r-- 1 pnftp pnftp 2858946 Feb 19 16:11 wmail30h_solarisx86.tar.Z
+226 Transfer complete.
+ftp> close
+221 Closing connection - goodbye!
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-Surge.out b/netwerk/test/gtest/parse-ftp/U-Surge.out
new file mode 100644
index 0000000000..e6b6527106
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-Surge.out
@@ -0,0 +1,52 @@
+<!-- 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/. -->
+
+07-07-2002 21:37:00 <DIR> cgimail
+05-02-2002 17:38:00 <DIR> dbabble
+07-01-2001 00:00:00 <DIR> dek_temp
+07-01-2001 00:00:00 <DIR> deye
+02-18-2002 17:50:00 <DIR> dfree
+07-01-2001 00:00:00 <DIR> dgate
+01-31-2002 15:18:00 <DIR> discontinued
+07-07-2002 21:28:00 <DIR> dmail
+06-30-2002 17:56:00 <DIR> dmailweb
+07-10-2002 01:40:00 <DIR> dnews
+07-01-2001 00:00:00 <DIR> dnewsweb
+09-04-2001 00:00:00 <DIR> dnotice
+05-06-2002 16:58:00 <DIR> fengate
+05-28-2002 19:01:00 <DIR> ferngate
+07-01-2001 00:00:00 <DIR> jeeves
+06-27-2002 20:10:00 <DIR> misc
+07-04-2002 21:13:00 <DIR> netauth
+02-08-1999 00:00:00 <DIR> poppassd
+07-09-2002 01:39:00 <DIR> surgeftp
+07-03-2002 00:00:00 <DIR> surgemail
+07-03-2002 00:01:00 <DIR> surgemail-enterprise
+07-03-2002 00:01:00 <DIR> surgemail-home
+07-03-2002 00:01:00 <DIR> surgemail-isp
+07-03-2002 00:01:00 <DIR> surgemail-workplace
+07-04-2001 00:00:00 <DIR> watchdog
+03-21-2001 00:00:00 <DIR> webimap
+04-28-2002 21:30:00 <DIR> webmail
+06-30-2002 18:23:00 <DIR> webnews
+01-30-2002 20:31:00 <DIR> webshareit
+09-20-1999 00:00:00 <DIR> webtwin
+07-08-2002 17:07:00 <DIR> beta
+03-18-2002 15:48:00 <JUNCTION> wmail.exe -> wmail30h.exe
+02-19-2002 15:33:00 2312192 wmail30h.exe
+02-21-2002 19:24:00 3360893 wmail30h_aix4.tar.Z
+03-18-2002 15:47:00 3508885 wmail30h_bsdi4.tar.Z
+02-19-2002 15:47:00 2693234 wmail30h_freebsd.tar.Z
+02-19-2002 15:38:00 2640047 wmail30h_freebsd3.tar.Z
+02-19-2002 15:43:00 2654381 wmail30h_freebsd4.tar.Z
+03-18-2002 18:21:00 3005333 wmail30h_hpux.tar.Z
+02-19-2002 15:52:00 2779942 wmail30h_linux.tar.Z
+02-19-2002 15:58:00 2782353 wmail30h_linuxlibc6.tar.Z
+02-19-2002 16:01:00 1783391 wmail30h_linuxppc.tar.gz
+03-18-2002 15:47:00 2758233 wmail30h_macosx_aqua.tar.Z
+03-18-2002 15:47:00 3113365 wmail30h_osf.tar.Z
+04-28-2002 21:30:00 1779720 wmail30h_raq3.tar.gz
+03-11-2002 16:38:00 1789173 wmail30h_raq4.tar.gz
+02-19-2002 16:06:00 2846045 wmail30h_solaris.tar.Z
+02-19-2002 16:11:00 2858946 wmail30h_solarisx86.tar.Z
diff --git a/netwerk/test/gtest/parse-ftp/U-WarFTPd.in b/netwerk/test/gtest/parse-ftp/U-WarFTPd.in
new file mode 100644
index 0000000000..244c087097
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-WarFTPd.in
@@ -0,0 +1,38 @@
+ftp> open ftp.jgaa.com
+Connected to ftp.jgaa.com.
+220-Jgaa's official FTP server
+ WarFTPd 1.81.00 (Mar 3 2002) Ready
+ (C)opyright 1996 - 2002 by Jarle (jgaa) Aase - all rights reserved.
+220 Please enter your user name.
+Name (ftp.jgaa.com:cyp):
+230 User logged in.
+Remote system type is UNIX.
+Using binary mode to transfer files.
+ftp> passive
+Passive mode on.
+ftp> ls
+227 Entering Passive Mode (80,239,13,229,14,199)
+125 Using existing ASCII mode data connection for /bin/ls (1220 bytes).
+total 5127
+dr-xr--r-- 1 root root 0 Apr 22 2009 .
+dr-xr--r-- 1 root root 0 Apr 22 2009 ..
+-r-xr--r-- 1 root root 359807 Mar 13 2000 adns-0.6-win32-01.zip
+-r-xr--r-- 1 root root 77 Oct 17 2000 adns-0.6-win32-01.zip.md5
+-r-xr--r-- 1 root root 218767 Nov 11 2000 cfs-1.3.3-8bit-fix.r2.tgz
+-r-xr--r-- 1 root root 1606 Jun 13 2000 cfs-1.3.3-eight-bit-fix.diff.tar.gz
+-r-xr--r-- 1 root root 3327 Oct 19 2000 chkmailspool-1.0.tgz
+-r-xr--r-- 1 root root 9356 Oct 21 2000 chkmailspool-1.1.tgz
+-r-xr--r-- 1 root root 32742 Feb 1 2000 iisstat-1.2.zip
+-r-xr--r-- 1 root root 71 Oct 17 2000 iisstat-1.2.zip.md5
+-r-xr--r-- 1 root root 27531 Aug 14 1999 inshtml.zip
+-r-xr--r-- 1 root root 67 Oct 17 2000 inshtml.zip.md5
+-r-xr--r-- 1 root root 23780 Aug 14 1999 netcps.zip
+-r-xr--r-- 1 root root 66 Oct 17 2000 netcps.zip.md5
+-r-xr--r-- 1 root root 1057919 Nov 3 2001 openssl-0.9.6b-win32.zip
+-r-xr--r-- 1 root root 56823 Jan 28 2001 passgen-2.0.zip
+-r-xr--r-- 1 root root 826880 May 25 1997 warftpd-version2-public-source.zip
+-r-xr--r-- 1 root root 90 Oct 17 2000 warftpd-version2-public-source.zip.md5
+226 Transfer complete. 1220 bytes in 0.01 sec. (119.141 Kb/s)
+ftp> close
+221 Goodbye. Control connection closed.
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-WarFTPd.out b/netwerk/test/gtest/parse-ftp/U-WarFTPd.out
new file mode 100644
index 0000000000..b0a0bab43c
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-WarFTPd.out
@@ -0,0 +1,22 @@
+<!-- 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/. -->
+
+04-22-2009 00:00:00 <DIR> .
+04-22-2009 00:00:00 <DIR> ..
+03-13-2000 00:00:00 359807 adns-0.6-win32-01.zip
+10-17-2000 00:00:00 77 adns-0.6-win32-01.zip.md5
+11-11-2000 00:00:00 218767 cfs-1.3.3-8bit-fix.r2.tgz
+06-13-2000 00:00:00 1606 cfs-1.3.3-eight-bit-fix.diff.tar.gz
+10-19-2000 00:00:00 3327 chkmailspool-1.0.tgz
+10-21-2000 00:00:00 9356 chkmailspool-1.1.tgz
+02-01-2000 00:00:00 32742 iisstat-1.2.zip
+10-17-2000 00:00:00 71 iisstat-1.2.zip.md5
+08-14-1999 00:00:00 27531 inshtml.zip
+10-17-2000 00:00:00 67 inshtml.zip.md5
+08-14-1999 00:00:00 23780 netcps.zip
+10-17-2000 00:00:00 66 netcps.zip.md5
+11-03-2001 00:00:00 1057919 openssl-0.9.6b-win32.zip
+01-28-2001 00:00:00 56823 passgen-2.0.zip
+05-25-1997 00:00:00 826880 warftpd-version2-public-source.zip
+10-17-2000 00:00:00 90 warftpd-version2-public-source.zip.md5
diff --git a/netwerk/test/gtest/parse-ftp/U-WebStar.in b/netwerk/test/gtest/parse-ftp/U-WebStar.in
new file mode 100644
index 0000000000..4010d462e1
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-WebStar.in
@@ -0,0 +1,41 @@
+ftp> open ftp.webstar.com
+Connected to ftp.webstar.com.
+220 FTP server ready.
+Name (ftp.webstar.com:cyp):
+331 Anonymous login OK, send login as password.
+230 User logged in.
+Remote system type is UNIX.
+ftp> pwd
+257 "/" is the current directory.
+ftp> syst
+215 UNIX WebSTAR FTP.
+ftp> cd products
+250 CWD OK, "/products".
+ftp> cd WebStar
+250 CWD OK, "/products/WebStar".
+ftp> cd Updates
+250 CWD OK, "/products/WebStar/Updates".
+ftp> ls
+200 PORT OK, IP address 134.93.247.34 port 49247
+150 Opening data connection.
+drwx------ 0 owner group 1 Jan 30 17:16 bundleup
+drwx------ 0 owner group 2 Nov 08 2001 docs
+drwx------ 0 owner group 12 Nov 08 2001 extending_webstar
+drwx------ 0 owner group 2 Apr 25 09:40 Products
+drwx------ 0 owner group 1 Jan 30 16:20 updates
+drwx------ 0 owner group 11 Jan 30 17:16 webstar_dev
+drwx------ 0 owner group 2 May 01 15:46 WebSTAR
+drwx------ 0 owner group 15 May 13 09:54 Installers
+drwx------ 0 owner group 8 Apr 25 09:59 Updates
+drwx------ 0 owner group 7 Apr 25 10:00 Plug-ins
+drwx------ 0 owner group 2 Apr 06 2001 SSL
+-rwx------ 0 owner group 1605421 Mar 30 2001 webstar1.3.2_updater.sea.hqx
+-rwx------ 0 owner group 6883859 Mar 30 2001 WebSTAR211installer.sea.hqx
+-rwx------ 0 owner group 7366223 Mar 30 2001 WebSTAR211updater.sea.hqx
+-rwx------ 0 owner group 13415184 Mar 30 2001 WebSTAR302updater.sea.hqx
+drwx------ 0 owner group 4 Apr 05 2001 WebSTAR_44
+drwx------ 0 owner group 2 Apr 25 10:00 WebSTAR_V
+226 Transfer complete.
+ftp> close
+221 Goodbye.
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-WebStar.out b/netwerk/test/gtest/parse-ftp/U-WebStar.out
new file mode 100644
index 0000000000..3a6720727c
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-WebStar.out
@@ -0,0 +1,21 @@
+<!-- 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/. -->
+
+01-30-2002 17:16:00 <DIR> bundleup
+11-08-2001 00:00:00 <DIR> docs
+11-08-2001 00:00:00 <DIR> extending_webstar
+04-25-2002 09:40:00 <DIR> Products
+01-30-2002 16:20:00 <DIR> updates
+01-30-2002 17:16:00 <DIR> webstar_dev
+05-01-2002 15:46:00 <DIR> WebSTAR
+05-13-2002 09:54:00 <DIR> Installers
+04-25-2002 09:59:00 <DIR> Updates
+04-25-2002 10:00:00 <DIR> Plug-ins
+04-06-2001 00:00:00 <DIR> SSL
+03-30-2001 00:00:00 1605421 webstar1.3.2_updater.sea.hqx
+03-30-2001 00:00:00 6883859 WebSTAR211installer.sea.hqx
+03-30-2001 00:00:00 7366223 WebSTAR211updater.sea.hqx
+03-30-2001 00:00:00 13415184 WebSTAR302updater.sea.hqx
+04-05-2001 00:00:00 <DIR> WebSTAR_44
+04-25-2002 10:00:00 <DIR> WebSTAR_V
diff --git a/netwerk/test/gtest/parse-ftp/U-WinNT.in b/netwerk/test/gtest/parse-ftp/U-WinNT.in
new file mode 100644
index 0000000000..a883fe0aae
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-WinNT.in
@@ -0,0 +1,68 @@
+ftp> open ftp.microsoft.com
+220 Microsoft FTP Service
+Name (ftp.microsoft.com:cyp):
+331 Anonymous access allowed, send identity (e-mail name) as password.
+230-This is FTP.Microsoft.Com
+230 Anonymous user logged in.
+Remote system type is Windows_NT.
+ftp> quote dirstyle
+200 MSDOS-like directory output is on
+ftp> quote dirstyle
+200 MSDOS-like directory output is off
+ftp> ls
+200 PORT command successful.
+150 Opening ASCII mode data connection for /bin/ls.
+dr-xr-xr-x 1 owner group 0 Feb 25 2000 channel
+dr-xr-xr-x 1 owner group 0 Feb 25 2000 Education
+dr-xr-xr-x 1 owner group 0 Feb 25 2000 enterprise
+dr-xr-xr-x 1 owner group 0 Jun 20 2001 ISN
+dr-xr-xr-x 1 owner group 0 May 31 2001 Museum
+dr-xr-xr-x 1 owner group 0 Feb 14 2001 TechNet
+dr-xr-xr-x 1 owner group 0 Oct 24 2001 whql
+dr-xr-xr-x 1 owner group 0 Feb 5 2001 20Year
+dr-xr-xr-x 1 owner group 0 Sep 26 2000 AccessFoxPro
+dr-xr-xr-x 1 owner group 0 Dec 21 2000 AlbGrp
+dr-xr-xr-x 1 owner group 0 May 31 2001 Alexandra
+dr-xr-xr-x 1 owner group 0 Jan 19 2001 anna
+dr-xr-xr-x 1 owner group 0 Apr 6 2000 anz
+dr-xr-xr-x 1 owner group 0 May 10 2000 Chase Bobko2
+dr-xr-xr-x 1 owner group 0 Mar 29 2000 cnn
+dr-xr-xr-x 1 owner group 0 Nov 21 2000 Darin
+dr-xr-xr-x 1 owner group 0 Mar 9 2000 digitalchicago
+dr-xr-xr-x 1 owner group 0 Sep 6 2000 Dublin
+dr-xr-xr-x 1 owner group 0 Jan 30 2001 eleanorf
+dr-xr-xr-x 1 owner group 0 Apr 26 2001 girvin
+dr-xr-xr-x 1 owner group 0 Apr 26 2000 Hires
+dr-xr-xr-x 1 owner group 0 Aug 15 2000 HR
+-r-xr-xr-x 1 owner group 4368384 Oct 24 1999 IMG00022.PCD
+dr-xr-xr-x 1 owner group 0 May 18 2001 jacubowsky
+dr-xr-xr-x 1 owner group 0 Oct 12 2000 JFalvey
+dr-xr-xr-x 1 owner group 0 Mar 28 2001 johnci
+dr-xr-xr-x 1 owner group 0 Jul 14 2000 Karin
+dr-xr-xr-x 1 owner group 0 Sep 7 2000 Kjung
+dr-xr-xr-x 1 owner group 0 Sep 28 2000 LarryE
+dr-xr-xr-x 1 owner group 0 Aug 17 2000 Larson
+dr-xr-xr-x 1 owner group 0 Sep 12 2000 marion
+dr-xr-xr-x 1 owner group 0 Aug 9 2000 ms25
+dr-xr-xr-x 1 owner group 0 Nov 16 2000 MS25Brochure
+dr-xr-xr-x 1 owner group 0 Mar 29 2000 MShistory
+dr-xr-xr-x 1 owner group 0 Sep 5 2000 Neils
+dr-xr-xr-x 1 owner group 0 Aug 2 2000 NLM
+dr-xr-xr-x 1 owner group 0 Sep 6 2000 PageOne
+dr-xr-xr-x 1 owner group 0 Jun 27 2000 pccomputing
+dr-xr-xr-x 1 owner group 0 May 9 2001 pictures
+dr-xr-xr-x 1 owner group 0 Jul 21 2000 pranks
+dr-xr-xr-x 1 owner group 0 Aug 22 2000 Sean
+dr-xr-xr-x 1 owner group 0 Aug 10 2000 SLeong
+dr-xr-xr-x 1 owner group 0 Sep 7 2000 svr
+dr-xr-xr-x 1 owner group 0 Jul 21 2000 Transcontinental
+dr-xr-xr-x 1 owner group 0 Oct 23 2000 veronist
+dr-xr-xr-x 1 owner group 0 Jun 15 2000 zoe
+-r-xr-xr-x 1 owner group 2094926 Jul 14 2000 canprankdesk.tif
+-r-xr-xr-x 1 owner group 95077 Jul 21 2000 Jon Kauffman Enjoys the Good Life.jpg
+-r-xr-xr-x 1 owner group 52275 Jul 21 2000 Name Plate.jpg
+-r-xr-xr-x 1 owner group 2250540 Jul 14 2000 Valentineoffprank-HiRes.jpg
+226 Transfer complete.
+ftp> close
+221 Thank-You For Using Microsoft Products!
+ftp>
diff --git a/netwerk/test/gtest/parse-ftp/U-WinNT.out b/netwerk/test/gtest/parse-ftp/U-WinNT.out
new file mode 100644
index 0000000000..5c4106b9be
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-WinNT.out
@@ -0,0 +1,54 @@
+<!-- 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/. -->
+
+02-25-2000 00:00:00 <DIR> channel
+02-25-2000 00:00:00 <DIR> Education
+02-25-2000 00:00:00 <DIR> enterprise
+06-20-2001 00:00:00 <DIR> ISN
+05-31-2001 00:00:00 <DIR> Museum
+02-14-2001 00:00:00 <DIR> TechNet
+10-24-2001 00:00:00 <DIR> whql
+02-05-2001 00:00:00 <DIR> 20Year
+09-26-2000 00:00:00 <DIR> AccessFoxPro
+12-21-2000 00:00:00 <DIR> AlbGrp
+05-31-2001 00:00:00 <DIR> Alexandra
+01-19-2001 00:00:00 <DIR> anna
+04-06-2000 00:00:00 <DIR> anz
+05-10-2000 00:00:00 <DIR> Chase Bobko2
+03-29-2000 00:00:00 <DIR> cnn
+11-21-2000 00:00:00 <DIR> Darin
+03-09-2000 00:00:00 <DIR> digitalchicago
+09-06-2000 00:00:00 <DIR> Dublin
+01-30-2001 00:00:00 <DIR> eleanorf
+04-26-2001 00:00:00 <DIR> girvin
+04-26-2000 00:00:00 <DIR> Hires
+08-15-2000 00:00:00 <DIR> HR
+10-24-1999 00:00:00 4368384 IMG00022.PCD
+05-18-2001 00:00:00 <DIR> jacubowsky
+10-12-2000 00:00:00 <DIR> JFalvey
+03-28-2001 00:00:00 <DIR> johnci
+07-14-2000 00:00:00 <DIR> Karin
+09-07-2000 00:00:00 <DIR> Kjung
+09-28-2000 00:00:00 <DIR> LarryE
+08-17-2000 00:00:00 <DIR> Larson
+09-12-2000 00:00:00 <DIR> marion
+08-09-2000 00:00:00 <DIR> ms25
+11-16-2000 00:00:00 <DIR> MS25Brochure
+03-29-2000 00:00:00 <DIR> MShistory
+09-05-2000 00:00:00 <DIR> Neils
+08-02-2000 00:00:00 <DIR> NLM
+09-06-2000 00:00:00 <DIR> PageOne
+06-27-2000 00:00:00 <DIR> pccomputing
+05-09-2001 00:00:00 <DIR> pictures
+07-21-2000 00:00:00 <DIR> pranks
+08-22-2000 00:00:00 <DIR> Sean
+08-10-2000 00:00:00 <DIR> SLeong
+09-07-2000 00:00:00 <DIR> svr
+07-21-2000 00:00:00 <DIR> Transcontinental
+10-23-2000 00:00:00 <DIR> veronist
+06-15-2000 00:00:00 <DIR> zoe
+07-14-2000 00:00:00 2094926 canprankdesk.tif
+07-21-2000 00:00:00 95077 Jon Kauffman Enjoys the Good Life.jpg
+07-21-2000 00:00:00 52275 Name Plate.jpg
+07-14-2000 00:00:00 2250540 Valentineoffprank-HiRes.jpg
diff --git a/netwerk/test/gtest/parse-ftp/U-hethmon.in b/netwerk/test/gtest/parse-ftp/U-hethmon.in
new file mode 100644
index 0000000000..2c9887cdbf
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-hethmon.in
@@ -0,0 +1,42 @@
+ftp> open ftp.hethmon.com
+Connected to ftp.hethmon.com.
+220 Hethmon Brothers FTP Server for OS/2 ** BETA 2.0 **. Ready for new user.
+Name (ftp.hethmon.com:cyp):
+331 Guest logins allowed. Email address required for anonymous.
+230 User foo@bar.com logged in.
+Remote system type is UNIX.
+ftp> cd pub
+250 Directory changed to "/pub"
+ftp> ls
+200 Port command ok
+150 Opening ASCII mode data connection.
+d--x------ 1 ftp ftp 5 Mar 21 1999 ..
+d--x------ 1 ftp ftp 0 Feb 16 2002 beta
+---------- 1 ftp ftp 35573 May 5 2000 CheckQ2.zip
+---------- 1 ftp ftp 1550521 May 5 2000 Ftpd106.zip
+---------- 1 ftp ftp 35459 Feb 7 2001 hmailbox.zip
+---------- 1 ftp ftp 55463 May 5 2000 HRxMail.zip
+---------- 1 ftp ftp 34950 May 5 2000 HRxPass.zip
+---------- 1 ftp ftp 1320184 May 5 2000 inetmail-1.2.1.pro.zip
+---------- 1 ftp ftp 1218483 May 5 2000 inetmail-1.2.1.zip
+---------- 1 ftp ftp 1615428 May 5 2000 inetmail-1.3.0.pro.zip
+---------- 1 ftp ftp 1425567 May 5 2000 inetmail-1.3.0.zip
+---------- 1 ftp ftp 1629145 Jan 9 2001 inetmail-1.3.18.zip
+---------- 1 ftp ftp 1625314 Feb 7 2001 inetmail-1.3.18a.zip
+---------- 1 ftp ftp 1407069 May 5 2000 inetmail-1.5.0.pro.zip
+---------- 1 ftp ftp 1470338 Sep 27 2000 inetmail-1.5.31.pro.zip
+---------- 1 ftp ftp 1583435 Jan 4 2001 inetmail-1.5.32.pro.zip
+---------- 1 ftp ftp 1429364 May 5 2000 inetmail-1.5.5.pro.zip
+---------- 1 ftp ftp 1471373 May 5 2000 inetmail-1.5.6.pro.zip
+d--x------ 1 ftp ftp 0 Feb 8 2001 misc
+---------- 1 ftp ftp 30913 May 5 2000 MXLookup.zip
+d--x------ 1 ftp ftp 0 May 2 2002 perseus
+d--x------ 1 ftp ftp 0 Feb 8 2001 rfcs
+d--x------ 1 ftp ftp 0 Feb 8 2001 scripts
+d--x------ 1 ftp ftp 0 Feb 8 2001 tcpip
+d--x------ 1 ftp ftp 0 May 5 2000 testcase
+d--x------ 1 ftp ftp 0 Feb 7 2001 tools
+226 Data transfer complete
+ftp> close
+221 Service closing control connection.
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-hethmon.out b/netwerk/test/gtest/parse-ftp/U-hethmon.out
new file mode 100644
index 0000000000..dada168791
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-hethmon.out
@@ -0,0 +1,30 @@
+<!-- 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/. -->
+
+03-21-1999 00:00:00 <DIR> ..
+02-16-2002 00:00:00 <DIR> beta
+05-05-2000 00:00:00 35573 CheckQ2.zip
+05-05-2000 00:00:00 1550521 Ftpd106.zip
+02-07-2001 00:00:00 35459 hmailbox.zip
+05-05-2000 00:00:00 55463 HRxMail.zip
+05-05-2000 00:00:00 34950 HRxPass.zip
+05-05-2000 00:00:00 1320184 inetmail-1.2.1.pro.zip
+05-05-2000 00:00:00 1218483 inetmail-1.2.1.zip
+05-05-2000 00:00:00 1615428 inetmail-1.3.0.pro.zip
+05-05-2000 00:00:00 1425567 inetmail-1.3.0.zip
+01-09-2001 00:00:00 1629145 inetmail-1.3.18.zip
+02-07-2001 00:00:00 1625314 inetmail-1.3.18a.zip
+05-05-2000 00:00:00 1407069 inetmail-1.5.0.pro.zip
+09-27-2000 00:00:00 1470338 inetmail-1.5.31.pro.zip
+01-04-2001 00:00:00 1583435 inetmail-1.5.32.pro.zip
+05-05-2000 00:00:00 1429364 inetmail-1.5.5.pro.zip
+05-05-2000 00:00:00 1471373 inetmail-1.5.6.pro.zip
+02-08-2001 00:00:00 <DIR> misc
+05-05-2000 00:00:00 30913 MXLookup.zip
+05-02-2002 00:00:00 <DIR> perseus
+02-08-2001 00:00:00 <DIR> rfcs
+02-08-2001 00:00:00 <DIR> scripts
+02-08-2001 00:00:00 <DIR> tcpip
+05-05-2000 00:00:00 <DIR> testcase
+02-07-2001 00:00:00 <DIR> tools
diff --git a/netwerk/test/gtest/parse-ftp/U-murksw.in b/netwerk/test/gtest/parse-ftp/U-murksw.in
new file mode 100644
index 0000000000..0d5786cf2e
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-murksw.in
@@ -0,0 +1,29 @@
+ftp> open tui.lincoln.ac.nz
+Connected to tui.lincoln.ac.nz.
+220 tui.lincoln.ac.nz Novell NetWare FTP Server (V1.80), Copyright (C) 1992-2000 MurkWorks Inc.
+Name (tui.lincoln.ac.nz:cyp): 331 Anonymous Login OK, send id as password.
+230-User logged in, Max Connect time 600 minutes (READONLY)
+230 Current Directory : /
+Remote system type is UNIX.
+Using binary mode to transfer files.
+ftp> ls
+200 Command Accepted
+150 Opening connection for ASCII transfer
+-rwx---r-- 1 anonymou other 1445 Apr 28 1994 ANON.DAT
+-rwx---r-- 1 mcnaughp other 83 Apr 18 09:39 Copy of LABSPACE.SUM
+drwx---r-x 2 anonymou other 512 Jul 11 21:04 JRBUTILS
+-rwx---r-- 1 labspace other 91 Jul 13 02:04 LABSPACE.SUM
+drwx---r-x 2 anonymou other 512 Jul 11 21:04 MAINT
+drwx---r-x 2 anonymou other 512 Jul 11 21:04 MISC
+drwx---r-x 2 anonymou other 512 Jul 11 21:04 PCOUNTER
+drwx---r-x 2 helleupp other 512 Jul 11 21:05 PEGASUS
+-rwx---r-- 1 anonymou other 13662 Aug 6 17:14 VOL$LOG.ERR
+-rwx---r-- 1 anonymou other 27945 Sep 5 1994 WHATIS.MSC
+226 Transfer complete
+ftp> pwd
+257 "/" is the current directory
+ftp> syst
+215 UNIX Type: L8 Version: NetWare MurkWorks, Inc. 1.80
+ftp> close
+221 Goodbye.
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-murksw.out b/netwerk/test/gtest/parse-ftp/U-murksw.out
new file mode 100644
index 0000000000..68ff9448e9
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-murksw.out
@@ -0,0 +1,14 @@
+<!-- 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/. -->
+
+04-28-1994 00:00:00 1445 ANON.DAT
+04-18-2002 09:39:00 83 Copy of LABSPACE.SUM
+07-11-2002 21:04:00 <DIR> JRBUTILS
+07-13-2002 02:04:00 91 LABSPACE.SUM
+07-11-2002 21:04:00 <DIR> MAINT
+07-11-2002 21:04:00 <DIR> MISC
+07-11-2002 21:04:00 <DIR> PCOUNTER
+07-11-2002 21:05:00 <DIR> PEGASUS
+08-06-2001 17:14:00 13662 VOL$LOG.ERR
+09-05-1994 00:00:00 27945 WHATIS.MSC
diff --git a/netwerk/test/gtest/parse-ftp/U-ncFTPd.in b/netwerk/test/gtest/parse-ftp/U-ncFTPd.in
new file mode 100644
index 0000000000..635f556423
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-ncFTPd.in
@@ -0,0 +1,1411 @@
+ftp> ftp ftp.novell.com
+Connected to kmpec.provo.novell.com.
+220 ftp.novell.com NcFTPd Server (licensed copy) ready.
+Name (ftp.novell.com:cyp):
+331 Guest login ok, send your complete e-mail address as password.
+230-You are user #18 of 400 simultaneous users allowed.
+230-
+230-This content is also available via HTTP at http://ftp.novell.com
+230-
+230-Other FTP mirror sites of ftp.novell.com are:
+230-ftp2.novell.com (United States)
+230-ftp3.novell.com (United States)
+230-ftp.novell.com.au (Australia)
+230-ftp.novell.de (Germany)
+230-ftp.novell.co.jp (Japan)
+230-ftp.novell.nl (Netherlands)
+230-
+230-World Wide Web Novell Support sites:
+230-http://support.novell.com (United States)
+230-http://support.novell.com.au (Australia)
+230-http://support.novell.de (Germany)
+230-http://support.novell.co.jp (Japan)
+230-
+230-webmaster@novell.com
+230-
+230 Logged in anonymously.
+Remote system type is UNIX.
+Using binary mode to transfer files.
+ftp> syst
+215 UNIX Type: L8
+ftp> ls
+200 PORT command successful.
+150 Opening ASCII mode data connection for /bin/ls.
+-rw-r--r-- 1 ftpuser ftpusers 2419 Jan 1 1997 Readme
+drwxrwxrwx 2 ftpuser ftpusers 8192 Jul 10 11:03 incoming
+drwxr-x--x 2 ftpuser ftpusers 4096 Jul 10 10:18 outgoing
+drwxr-xr-x 2 ftpuser ftpusers 4096 May 10 10:16 priv
+drwxr-xr-x 5 ftpuser ftpusers 4096 Jul 10 08:12 pub
+drwxr-xr-x 2 ftpuser ftpusers 28672 Jul 8 19:20 allupdates
+drwxr-xr-x 4 ftpuser ftpusers 4096 Jan 1 1997 netwire
+drwxr-xr-x 2 ftpuser ftpusers 4096 Jul 9 19:20 support
+lrwxrwxrwx 1 ftpuser ftpusers 10 Jan 10 2002 updates -> allupdates
+-rw-r--r-- 1 ftpuser ftpusers 19448 Jul 27 1999 0dsb.exe
+-rw-r--r-- 1 ftpuser ftpusers 49351 Sep 17 1993 215mir.exe
+-rw-r--r-- 1 ftpuser ftpusers 32586 Sep 17 1993 215sec.exe
+-rw-r--r-- 1 ftpuser ftpusers 136344 Sep 17 1993 21fix.exe
+-rw-r--r-- 1 ftpuser ftpusers 57276 Sep 17 1993 223200.exe
+-rw-r--r-- 1 ftpuser ftpusers 119616 Nov 1 1995 22bkup.exe
+-rw-r--r-- 1 ftpuser ftpusers 19820 Oct 13 1995 22dos5.exe
+-rw-r--r-- 1 ftpuser ftpusers 32980 Nov 1 1995 22nd2f.exe
+-rw-r--r-- 1 ftpuser ftpusers 92151 May 9 11:30 236779.exe
+-rw-r--r-- 1 ftpuser ftpusers 273958 Jan 17 2001 242234.exe
+-rw-r--r-- 1 ftpuser ftpusers 283462 Jul 10 2001 243798.exe
+-rw-r--r-- 1 ftpuser ftpusers 160893 Dec 18 2001 251000.exe
+-rw-r--r-- 1 ftpuser ftpusers 205531 Dec 18 2001 252143.exe
+-rw-r--r-- 1 ftpuser ftpusers 183262 Dec 18 2001 253720.exe
+-rw-r--r-- 1 ftpuser ftpusers 231638 Nov 6 2001 260624.exe
+-rw-r--r-- 1 ftpuser ftpusers 250545 Jun 21 2001 264837.exe
+-rw-r--r-- 1 ftpuser ftpusers 589722 Feb 21 16:33 265058a.exe
+-rw-r--r-- 1 ftpuser ftpusers 336586 Nov 7 2001 269308.exe
+-rw-r--r-- 1 ftpuser ftpusers 345275 Nov 6 2001 270050.exe
+-rw-r--r-- 1 ftpuser ftpusers 103027 Nov 6 2001 270410.exe
+-rw-r--r-- 1 ftpuser ftpusers 341460 May 9 07:13 275382.exe
+-rw-r--r-- 1 ftpuser ftpusers 365835 May 9 11:23 275436.exe
+-rw-r--r-- 1 ftpuser ftpusers 230063 Oct 9 2001 275520.exe
+-rw-r--r-- 1 ftpuser ftpusers 285953 Oct 2 2001 275820.exe
+-rw-r--r-- 1 ftpuser ftpusers 156517 Nov 16 2001 277412.exe
+-rw-r--r-- 1 ftpuser ftpusers 839272 Dec 19 2001 278415.exe
+-rw-r--r-- 1 ftpuser ftpusers 130983 Dec 19 2001 282848.exe
+-rw-r--r-- 1 ftpuser ftpusers 61891 Sep 17 1993 286dwn.exe
+-rw-r--r-- 1 ftpuser ftpusers 136529 May 9 07:18 290254.exe
+-rw-r--r-- 1 ftpuser ftpusers 96694 Apr 12 17:07 290261.exe
+-rw-r--r-- 1 ftpuser ftpusers 230377 May 9 07:22 291158.exe
+-rw-r--r-- 1 ftpuser ftpusers 114329 Jun 27 12:20 295137.exe
+-rw-r--r-- 1 ftpuser ftpusers 84885 Sep 17 1993 2xto3x.exe
+-rw-r--r-- 1 ftpuser ftpusers 60861 Sep 17 1993 300pt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 180279 Sep 17 1993 310pt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 178076 Nov 11 1996 311ptg.exe
+-rw-r--r-- 1 ftpuser ftpusers 188572 Apr 29 1996 312du1.exe
+-rw-r--r-- 1 ftpuser ftpusers 168258 Mar 18 1998 312ptd.exe
+-rw-r--r-- 1 ftpuser ftpusers 436629 Aug 25 1999 312y2kp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 2365264 Jun 29 2001 33sp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 28881 Sep 17 1993 386dcb.exe
+-rw-r--r-- 1 ftpuser ftpusers 33111 Sep 17 1993 3cboot.exe
+-rw-r--r-- 1 ftpuser ftpusers 27583 Nov 10 1995 400pt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 79295 Oct 23 1995 401pt6.exe
+-rw-r--r-- 1 ftpuser ftpusers 42873 Aug 26 1994 402pa1.exe
+-rw-r--r-- 1 ftpuser ftpusers 50737 Mar 28 1995 402pt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 548398 Jun 8 1998 410pt8b.exe
+-rw-r--r-- 1 ftpuser ftpusers 285471 Aug 25 1999 410y2kp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 538544 Jul 23 1999 411y2kp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 370469 Apr 29 1996 41filr.exe
+-rw-r--r-- 1 ftpuser ftpusers 58965 Jan 2 1997 41migutl.exe
+-rw-r--r-- 1 ftpuser ftpusers 173978 Aug 29 1995 41ndir.exe
+-rw-r--r-- 1 ftpuser ftpusers 42101 Nov 24 1997 41rem1.exe
+-rw-r--r-- 1 ftpuser ftpusers 855292 Jul 9 1996 41rtr2.exe
+-rw-r--r-- 1 ftpuser ftpusers 212785 Jul 23 1999 42y2kp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 3043701 Jul 3 2001 48sp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 308856 May 22 2001 4pent.exe
+-rw-r--r-- 1 ftpuser ftpusers 1072023 Apr 6 1998 4xmigr2.exe
+-rw-r--r-- 1 ftpuser ftpusers 125457 Nov 17 1995 4xrep1.exe
+-rw-r--r-- 1 ftpuser ftpusers 29001 Jul 6 1994 50z70.exe
+-rw-r--r-- 1 ftpuser ftpusers 23248 Nov 1 1995 55sx60.exe
+-rw-r--r-- 1 ftpuser ftpusers 647818 Dec 4 1998 95220p1.exe
+-rw-r--r-- 1 ftpuser ftpusers 905243 Mar 25 1999 95250p2.exe
+-rw-r--r-- 1 ftpuser ftpusers 694344 Jun 21 1999 9530p1.exe
+-rw-r--r-- 1 ftpuser ftpusers 794454 Jun 13 2000 9531pt2.exe
+-rw-r--r-- 1 ftpuser ftpusers 4380134 Oct 3 1999 9531sp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 1306298 Nov 16 2000 95321pt5.exe
+-rw-r--r-- 1 ftpuser ftpusers 494394 Jun 13 2000 9532pt3.exe
+-rw-r--r-- 1 ftpuser ftpusers 483405 Nov 6 2001 95331pt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 19588899 Jun 2 2000 a526aix.z
+-rw-r--r-- 1 ftpuser ftpusers 17196628 Jun 2 2000 a526hp.z
+-rw-r--r-- 1 ftpuser ftpusers 14813432 Jun 2 2000 a526sol.z
+-rw-r--r-- 1 ftpuser ftpusers 238005 Jul 9 1999 accupg1b.exe
+-rw-r--r-- 1 ftpuser ftpusers 19472 Sep 17 1993 aceclp.exe
+-rw-r--r-- 1 ftpuser ftpusers 2061142 Jun 19 2001 acmgtcl.exe
+-rw-r--r-- 1 ftpuser ftpusers 52792 Dec 17 1996 actkey.exe
+-rw-r--r-- 1 ftpuser ftpusers 1026928 Nov 8 1996 adde1.exe
+-rw-r--r-- 1 ftpuser ftpusers 476094 Sep 10 1997 adm32_22.exe
+-rw-r--r-- 1 ftpuser ftpusers 4204451 Jan 10 1997 adm4113x.exe
+-rw-r--r-- 1 ftpuser ftpusers 3813257 Jan 10 1997 adm41195.exe
+-rw-r--r-- 1 ftpuser ftpusers 5377426 Jan 10 1997 adm411nt.exe
+-rw-r--r-- 1 ftpuser ftpusers 130826 May 23 2001 admattrs.exe
+-rw-r--r-- 1 ftpuser ftpusers 3291925 May 23 2001 admn519f.exe
+-rw-r--r-- 1 ftpuser ftpusers 273404 Jul 15 1997 adtus3.exe
+-rw-r--r-- 1 ftpuser ftpusers 25475 Sep 17 1993 afix1.exe
+-rw-r--r-- 1 ftpuser ftpusers 25929 Sep 17 1993 afix2.exe
+-rw-r--r-- 1 ftpuser ftpusers 26184 Sep 17 1993 afix4.exe
+-rw-r--r-- 1 ftpuser ftpusers 116034 Apr 10 2001 afnwcgi1.exe
+-rw-r--r-- 1 ftpuser ftpusers 175949 Jan 28 13:43 afp100j.exe
+-rw-r--r-- 1 ftpuser ftpusers 90415 Jul 12 1999 afp11.exe
+-rw-r--r-- 1 ftpuser ftpusers 513677 Nov 1 1995 aiodrv.exe
+-rw-r--r-- 1 ftpuser ftpusers 26752 Aug 12 1995 aiotrm.exe
+-rw-r--r-- 1 ftpuser ftpusers 113328 Feb 8 2000 alx311cm.exe
+-rw-r--r-- 1 ftpuser ftpusers 202594 Dec 11 2001 am210pt2.exe
+-rw-r--r-- 1 ftpuser ftpusers 1126900 Dec 10 2001 am210snp.exe
+-rw-r--r-- 1 ftpuser ftpusers 267218 Dec 11 2001 amsammg.exe
+-rw-r--r-- 1 ftpuser ftpusers 4394406 Nov 29 2001 amw2ksp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 34959 Nov 6 1996 anlmde.exe
+-rw-r--r-- 1 ftpuser ftpusers 70315 Nov 20 1996 antde.exe
+-rw-r--r-- 1 ftpuser ftpusers 2778036 Dec 10 1997 apinlm.exe
+-rw-r--r-- 1 ftpuser ftpusers 47772 Apr 5 1994 apinst.exe
+-rw-r--r-- 1 ftpuser ftpusers 3367826 Dec 10 1997 apios2.exe
+-rw-r--r-- 1 ftpuser ftpusers 44662 Sep 17 1993 apsvap.exe
+-rw-r--r-- 1 ftpuser ftpusers 1507519 Oct 5 1998 async1.exe
+-rw-r--r-- 1 ftpuser ftpusers 431852 Jul 25 1995 asyq4a.exe
+-rw-r--r-- 1 ftpuser ftpusers 68700 Sep 17 1993 atalk.exe
+-rw-r--r-- 1 ftpuser ftpusers 22944 Sep 17 1993 atdisk.exe
+-rw-r--r-- 1 ftpuser ftpusers 222222 Jan 29 1996 atk307.exe
+-rw-r--r-- 1 ftpuser ftpusers 259359 Sep 24 1999 atmdrv04.exe
+-rw-r--r-- 1 ftpuser ftpusers 22012 Jun 14 1996 atok31.exe
+-rw-r--r-- 1 ftpuser ftpusers 25152 Sep 17 1993 atps1.exe
+-rw-r--r-- 1 ftpuser ftpusers 25812 Sep 17 1993 atps2.exe
+-rw-r--r-- 1 ftpuser ftpusers 206226 Sep 17 1993 atsup.exe
+-rw-r--r-- 1 ftpuser ftpusers 249262 Sep 15 1997 audit410.exe
+-rw-r--r-- 1 ftpuser ftpusers 27058 Jul 25 1995 autoda.exe
+-rw-r--r-- 1 ftpuser ftpusers 53955568 Mar 28 2001 azfd3sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 1267891 Mar 30 2000 bacl105.exe
+-rw-r--r-- 1 ftpuser ftpusers 564407 Apr 24 1998 bm21y2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 64354 Dec 9 1999 bm2ncs2.exe
+-rw-r--r-- 1 ftpuser ftpusers 5025837 Nov 13 2000 bm30sp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 118425 Mar 27 10:48 bm35adm6.exe
+-rw-r--r-- 1 ftpuser ftpusers 8950758 Sep 25 2001 bm35sp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 1560521 May 31 15:43 bm36c02.exe
+-rw-r--r-- 1 ftpuser ftpusers 1995053 Nov 6 2001 bm36nsp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 4187534 Jan 30 13:44 bm36sp1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 146884 Apr 19 13:52 bm37flt.exe
+-rw-r--r-- 1 ftpuser ftpusers 3958423 Apr 19 13:54 bm37vpn1.exe
+-rw-r--r-- 1 ftpuser ftpusers 2192048 Jun 16 2000 bm3cp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 521873 Mar 27 2000 bm3licfx.exe
+-rw-r--r-- 1 ftpuser ftpusers 550905 Jan 21 1999 bm3netad.exe
+-rw-r--r-- 1 ftpuser ftpusers 28435 Oct 8 1999 bm3pcfg.exe
+-rw-r--r-- 1 ftpuser ftpusers 30429 Oct 20 1999 bm3rmv3.exe
+-rw-r--r-- 1 ftpuser ftpusers 4865777 Sep 2 1999 bm3sp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 3934644 Jan 11 2000 bm3sp2j.exe
+-rw-r--r-- 1 ftpuser ftpusers 105579 Jan 16 2001 bm3sso2.exe
+-rw-r--r-- 1 ftpuser ftpusers 114564 Nov 23 1998 bmas203.exe
+-rw-r--r-- 1 ftpuser ftpusers 185953 Jul 27 2000 bmas204.exe
+-rw-r--r-- 1 ftpuser ftpusers 227934 May 29 2001 bmas3x01.exe
+-rw-r--r-- 1 ftpuser ftpusers 2409166 Apr 14 1998 bmnwntb.exe
+-rw-r--r-- 1 ftpuser ftpusers 235512 Oct 7 1999 bmp114.exe
+-rw-r--r-- 1 ftpuser ftpusers 114828 Aug 25 2000 bmsamp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 7822377 Feb 5 2001 bmsp2d.exe
+-rw-r--r-- 1 ftpuser ftpusers 177276 May 9 2001 bmvpn3y.exe
+-rw-r--r-- 1 ftpuser ftpusers 57666 Jul 16 1997 bndfx4.exe
+-rw-r--r-- 1 ftpuser ftpusers 22178 Sep 26 1997 brdrem1.exe
+-rw-r--r-- 1 ftpuser ftpusers 140225 Sep 17 1993 brgcom.exe
+-rw-r--r-- 1 ftpuser ftpusers 64130 Mar 17 1998 bwcc.exe
+-rw-r--r-- 1 ftpuser ftpusers 106576 May 10 2000 c112brj.exe
+-rw-r--r-- 1 ftpuser ftpusers 107820 May 9 2000 c112crcj.exe
+-rw-r--r-- 1 ftpuser ftpusers 106834 May 10 2000 c112crj.exe
+-rw-r--r-- 1 ftpuser ftpusers 35687507 Mar 5 13:14 c1_132.exe
+-rw-r--r-- 1 ftpuser ftpusers 188379 Feb 27 2001 c1unx85a.exe
+-rw-r--r-- 1 ftpuser ftpusers 24246977 Jun 2 2000 c526aix.z
+-rw-r--r-- 1 ftpuser ftpusers 39823205 Jun 2 2000 c526hp.z
+-rw-r--r-- 1 ftpuser ftpusers 31630789 Jun 2 2000 c526sol.z
+-rw-r--r-- 1 ftpuser ftpusers 39967 Dec 4 1996 ccmdll.exe
+-rw-r--r-- 1 ftpuser ftpusers 3532557 Jun 21 1999 ccmln1.exe
+-rw-r--r-- 1 ftpuser ftpusers 3610648 Apr 21 2000 ccmln2.exe
+-rw-r--r-- 1 ftpuser ftpusers 7242383 Oct 30 1998 ccmlo1.exe
+-rw-r--r-- 1 ftpuser ftpusers 71189 Mar 6 1997 cdisc.exe
+-rw-r--r-- 1 ftpuser ftpusers 298109 Aug 19 1998 cdup5a.exe
+-rw-r--r-- 1 ftpuser ftpusers 1554357 Oct 14 1998 cfgrd6b.exe
+-rw-r--r-- 1 ftpuser ftpusers 30799 Sep 17 1993 chk375.exe
+-rw-r--r-- 1 ftpuser ftpusers 85538 Jun 16 1997 chtree1.exe
+-rw-r--r-- 1 ftpuser ftpusers 28171 Dec 8 1999 clibaux1.exe
+-rw-r--r-- 1 ftpuser ftpusers 2819 Sep 8 2000 clients.txt
+-rw-r--r-- 1 ftpuser ftpusers 16820824 Sep 11 2000 clntaot.exe
+-rw-r--r-- 1 ftpuser ftpusers 7269162 Jan 5 1999 clos2d1.exe
+-rw-r--r-- 1 ftpuser ftpusers 2960384 Jun 24 1996 clt511.bin
+-rw-r--r-- 1 ftpuser ftpusers 195429 Mar 24 1999 clty2kp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 76117 Nov 22 1993 comchk.exe
+-rw-r--r-- 1 ftpuser ftpusers 76738 Nov 1 1995 comsub.exe
+-rw-r--r-- 1 ftpuser ftpusers 74759 Aug 16 1996 comx.exe
+-rw-r--r-- 1 ftpuser ftpusers 102496 Feb 22 2001 comx218.exe
+-rw-r--r-- 1 ftpuser ftpusers 117584 Dec 5 2000 confg9.exe
+-rw-r--r-- 1 ftpuser ftpusers 27438 Sep 17 1993 conlog.exe
+-rw-r--r-- 1 ftpuser ftpusers 20051 Sep 17 1993 cpuchk.exe
+-rw-r--r-- 1 ftpuser ftpusers 96755 Jan 7 2000 cron5.exe
+-rw-r--r-- 1 ftpuser ftpusers 22439431 Jul 21 2001 cs1sp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 12643202 Feb 19 16:08 cs1sp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 2395980 Feb 28 2001 cs2ep2.exe
+-rw-r--r-- 1 ftpuser ftpusers 97982 Feb 17 2000 csatpxy2.exe
+-rw-r--r-- 1 ftpuser ftpusers 888262 Jan 30 1997 csserv.exe
+-rw-r--r-- 1 ftpuser ftpusers 888092 Jan 30 1997 ctserv.exe
+-rw-r--r-- 1 ftpuser ftpusers 1195718 Sep 20 1999 ctsv20_1.pdf
+-rw-r--r-- 1 ftpuser ftpusers 97050 Aug 30 2000 cvsbind.exe
+-rw-r--r-- 1 ftpuser ftpusers 1040603 Jan 5 1996 d70f15.exe
+-rw-r--r-- 1 ftpuser ftpusers 1046550 Jan 5 1996 d70g15.exe
+-rw-r--r-- 1 ftpuser ftpusers 1041138 Jan 5 1996 d70i15.exe
+-rw-r--r-- 1 ftpuser ftpusers 1042404 Jan 5 1996 d70s15.exe
+-rw-r--r-- 1 ftpuser ftpusers 1031373 Jan 5 1996 d70u15.exe
+-rw-r--r-- 1 ftpuser ftpusers 309903 Oct 31 1995 d72pnw.exe
+-rw-r--r-- 1 ftpuser ftpusers 26322 Aug 17 1995 daishm.exe
+-rw-r--r-- 1 ftpuser ftpusers 92347 Jan 17 09:55 decrenfx.exe
+-rw-r--r-- 1 ftpuser ftpusers 32573 Nov 24 1997 devmon.exe
+-rw-r--r-- 1 ftpuser ftpusers 225697 Nov 23 1999 dhcp21r.exe
+-rw-r--r-- 1 ftpuser ftpusers 65667 Jul 27 1994 diag.exe
+-rw-r--r-- 1 ftpuser ftpusers 776679 Jul 3 1996 dialr1.exe
+-rw-r--r-- 1 ftpuser ftpusers 1307891 Jul 3 1996 dialr2.exe
+-rw-r--r-- 1 ftpuser ftpusers 1330220 Jul 3 1996 dialr3.exe
+-rw-r--r-- 1 ftpuser ftpusers 62202 Sep 17 1993 distst.exe
+-rw-r--r-- 1 ftpuser ftpusers 133345 Feb 8 2001 dlttape.exe
+-rw-r--r-- 1 ftpuser ftpusers 174566 Dec 13 1995 dr6tid.exe
+-rw-r--r-- 1 ftpuser ftpusers 188110 May 15 15:23 dradpt1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 12654872 Apr 11 10:37 drdt10.exe
+-rw-r--r-- 1 ftpuser ftpusers 7991951 Apr 11 10:50 drnt10.exe
+-rw-r--r-- 1 ftpuser ftpusers 259966 Dec 9 1993 drv2x.exe
+-rw-r--r-- 1 ftpuser ftpusers 366568 Sep 17 1993 drvkit.exe
+-rw-r--r-- 1 ftpuser ftpusers 28773 Dec 2 1998 drvspc.exe
+-rw-r--r-- 1 ftpuser ftpusers 242836 Jul 12 1994 ds310.exe
+-rw-r--r-- 1 ftpuser ftpusers 739008 Dec 13 1999 ds410q.exe
+-rw-r--r-- 1 ftpuser ftpusers 683746 Jun 11 18:01 ds616.exe
+-rw-r--r-- 1 ftpuser ftpusers 1237908 Jul 3 19:58 ds760a.exe
+-rw-r--r-- 1 ftpuser ftpusers 3084809 Jun 12 13:47 ds880d_a.exe
+-rw-r--r-- 1 ftpuser ftpusers 2366484 Jun 7 2000 ds8c.exe
+-rw-r--r-- 1 ftpuser ftpusers 300572 May 31 2000 dsbrowse.exe
+-rw-r--r-- 1 ftpuser ftpusers 425220 Nov 10 1998 dsdiag1.exe
+-rw-r--r-- 1 ftpuser ftpusers 766525 Apr 15 1998 dskdrv.exe
+-rw-r--r-- 1 ftpuser ftpusers 201308 May 2 1997 dsright2.exe
+-rw-r--r-- 1 ftpuser ftpusers 6620 Feb 4 14:26 dsrmenu5.tgz
+-rw-r--r-- 1 ftpuser ftpusers 32671 Jan 11 12:06 dsx86upg.tgz
+-rw-r--r-- 1 ftpuser ftpusers 438327 Nov 22 1999 duprid.exe
+-rw-r--r-- 1 ftpuser ftpusers 366231 Nov 30 1999 dw271i1.exe
+-rw-r--r-- 1 ftpuser ftpusers 6444327 Oct 31 2001 dx1patch.exe
+-rw-r--r-- 1 ftpuser ftpusers 764705 Dec 11 2001 dxjdbc1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 369669 Jul 31 2001 dxnotp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 325977 Jan 11 17:32 dxntp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 6446882 Jan 11 17:11 dxnwp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 27292445 Jan 15 18:08 dxx10a.tgz
+-rw-r--r-- 1 ftpuser ftpusers 420838 Sep 18 1993 e2isa.exe
+-rw-r--r-- 1 ftpuser ftpusers 299227554 May 15 09:35 edir851.exe
+-rw-r--r-- 1 ftpuser ftpusers 13752049 Jun 19 22:20 edir8527.exe
+-rw-r--r-- 1 ftpuser ftpusers 8909701 Jun 18 17:22 edir8527.tgz
+-rw-r--r-- 1 ftpuser ftpusers 35256093 May 23 12:35 edir862.exe
+-rw-r--r-- 1 ftpuser ftpusers 30290896 Mar 7 13:22 edir862.tgz
+-rw-r--r-- 1 ftpuser ftpusers 12405810 Jun 20 11:12 edir862sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 7623982 Jun 20 11:07 edir862sp1a.tgz
+-rw-r--r-- 1 ftpuser ftpusers 178010922 Jun 19 23:26 edirw8527.exe
+-rw-r--r-- 1 ftpuser ftpusers 739976 Aug 1 1995 edvwin.exe
+-rw-r--r-- 1 ftpuser ftpusers 270433 Apr 12 15:32 egdpvr02.exe
+-rw-r--r-- 1 ftpuser ftpusers 6660863 Jan 15 10:28 einstall.exe
+-rw-r--r-- 1 ftpuser ftpusers 19547 Sep 18 1993 els2dt.exe
+-rw-r--r-- 1 ftpuser ftpusers 46872 Sep 18 1993 elsupd.exe
+-rw-r--r-- 1 ftpuser ftpusers 44481 Sep 18 1993 emshdl.exe
+-rw-r--r-- 1 ftpuser ftpusers 171889 Nov 30 2001 es7000.exe
+-rw-r--r-- 1 ftpuser ftpusers 395219 Sep 18 1993 escsi.exe
+-rw-r--r-- 1 ftpuser ftpusers 50164 Nov 1 1995 esdidr.exe
+-rw-r--r-- 1 ftpuser ftpusers 22207 Sep 18 1993 esdifx.exe
+-rw-r--r-- 1 ftpuser ftpusers 162763 Apr 16 2001 etbox7.exe
+-rw-r--r-- 1 ftpuser ftpusers 28262 Sep 18 1993 ethrlk.exe
+-rw-r--r-- 1 ftpuser ftpusers 21776 Sep 18 1993 ethsh.exe
+-rw-r--r-- 1 ftpuser ftpusers 3111638 Oct 13 1999 exchnt2.exe
+-rw-r--r-- 1 ftpuser ftpusers 32615 Mar 20 1995 exprul.exe
+-rw-r--r-- 1 ftpuser ftpusers 19910 Jul 18 1995 facwin.exe
+-rw-r--r-- 1 ftpuser ftpusers 193689 Sep 18 1993 faxdoc.exe
+-rw-r--r-- 1 ftpuser ftpusers 103299 Jul 18 1995 faxsv.exe
+-rw-r--r-- 1 ftpuser ftpusers 566087 Jul 20 1998 fbm21y2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 263164 Jul 27 2000 ffwnt1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 9564485 Jun 5 2000 fgwep1ad.exe
+-rw-r--r-- 1 ftpuser ftpusers 158446 Nov 10 1993 fil376.exe
+-rw-r--r-- 1 ftpuser ftpusers 35376 Sep 18 1993 filehd.exe
+-rw-r--r-- 1 ftpuser ftpusers 64924 Jan 28 1999 filt01a.exe
+-rw-r--r-- 1 ftpuser ftpusers 38027 Sep 18 1993 flgdir.exe
+-rw-r--r-- 1 ftpuser ftpusers 891667 Jun 25 10:26 flsysft7.exe
+-rw-r--r-- 1 ftpuser ftpusers 210958 Jul 20 1994 flx196.exe
+-rw-r--r-- 1 ftpuser ftpusers 23948 Sep 18 1993 fmtps2.exe
+-rw-r--r-- 1 ftpuser ftpusers 265642 Jun 1 1995 fmwin1.exe
+-rw-r--r-- 1 ftpuser ftpusers 44110 Jun 18 1997 fnasi21b.exe
+-rw-r--r-- 1 ftpuser ftpusers 35133 Apr 29 1997 fnwcrns.exe
+-rw-r--r-- 1 ftpuser ftpusers 64944 Jun 18 1997 fnwcss.exe
+-rw-r--r-- 1 ftpuser ftpusers 38169 Jun 18 1997 fnwcx25.exe
+-rw-r--r-- 1 ftpuser ftpusers 18985686 Feb 26 2001 fp3023a.exe
+-rw-r--r-- 1 ftpuser ftpusers 19034903 Feb 26 2001 fp3023s.exe
+-rw-r--r-- 1 ftpuser ftpusers 41401158 Jun 22 2001 fpa353.exe
+-rw-r--r-- 1 ftpuser ftpusers 40072174 Jun 22 2001 fps353.exe
+-rw-r--r-- 1 ftpuser ftpusers 40680 Aug 2 1996 frebld.exe
+-rw-r--r-- 1 ftpuser ftpusers 156117 Jan 30 15:36 ftpservk.exe
+-rw-r--r-- 1 ftpuser ftpusers 1427341 Jun 20 2001 fzd2abnd.exe
+-rw-r--r-- 1 ftpuser ftpusers 121436 May 22 2001 fzd2nal.exe
+-rw-r--r-- 1 ftpuser ftpusers 293122 May 22 2001 fzd2nal1.exe
+-rw-r--r-- 1 ftpuser ftpusers 333581 Dec 18 2001 fzd2nal2.exe
+-rw-r--r-- 1 ftpuser ftpusers 250445 May 23 2001 fzd2zapp.exe
+-rw-r--r-- 1 ftpuser ftpusers 2619032 Oct 10 2001 g32ep3b.exe
+-rw-r--r-- 1 ftpuser ftpusers 26193920 Nov 23 1998 g41c5a41.tar
+-rw-r--r-- 1 ftpuser ftpusers 25907200 Nov 23 1998 g41c5a43.tar
+-rw-r--r-- 1 ftpuser ftpusers 25190400 Nov 23 1998 g41c5dg.tar
+-rw-r--r-- 1 ftpuser ftpusers 27494400 Nov 23 1998 g41c5hp.tar
+-rw-r--r-- 1 ftpuser ftpusers 29337600 Nov 23 1998 g41c5ncr.tar
+-rw-r--r-- 1 ftpuser ftpusers 27146240 Nov 23 1998 g41c5sc5.tar
+-rw-r--r-- 1 ftpuser ftpusers 26982400 Nov 23 1998 g41c5sl5.tar
+-rw-r--r-- 1 ftpuser ftpusers 26961920 Nov 23 1998 g41c5sl6.tar
+-rw-r--r-- 1 ftpuser ftpusers 32808960 Nov 23 1998 g41c5sun.tar
+-rw-r--r-- 1 ftpuser ftpusers 3614720 Nov 23 1998 g41m5a41.tar
+-rw-r--r-- 1 ftpuser ftpusers 3604480 Nov 23 1998 g41m5a43.tar
+-rw-r--r-- 1 ftpuser ftpusers 3481600 Nov 23 1998 g41m5dg.tar
+-rw-r--r-- 1 ftpuser ftpusers 4280320 Nov 23 1998 g41m5hp.tar
+-rw-r--r-- 1 ftpuser ftpusers 4495360 Nov 23 1998 g41m5ncr.tar
+-rw-r--r-- 1 ftpuser ftpusers 5263360 Nov 23 1998 g41m5sc5.tar
+-rw-r--r-- 1 ftpuser ftpusers 4116480 Nov 23 1998 g41m5sl5.tar
+-rw-r--r-- 1 ftpuser ftpusers 4106240 Nov 23 1998 g41m5sl6.tar
+-rw-r--r-- 1 ftpuser ftpusers 5939200 Nov 20 1998 g41m5sun.tar
+-rw-r--r-- 1 ftpuser ftpusers 93137892 Jun 2 2000 g526east.exe
+-rw-r--r-- 1 ftpuser ftpusers 84011178 Jun 2 2000 g526kcc.exe
+-rw-r--r-- 1 ftpuser ftpusers 106015153 Jun 2 2000 g526mult.exe
+-rw-r--r-- 1 ftpuser ftpusers 92474943 Jun 2 2000 g526scan.exe
+-rw-r--r-- 1 ftpuser ftpusers 74449657 Jun 2 2000 g526us.exe
+-rw-r--r-- 1 ftpuser ftpusers 80161031 Jun 2 2000 g526usde.exe
+-rw-r--r-- 1 ftpuser ftpusers 77052636 Jun 2 2000 g526usjp.exe
+-rw-r--r-- 1 ftpuser ftpusers 20712319 Dec 18 1997 g52a1aix.z
+-rw-r--r-- 1 ftpuser ftpusers 17069171 Dec 18 1997 g52a1hp.z
+-rw-r--r-- 1 ftpuser ftpusers 14703356 Dec 18 1997 g52a1sol.z
+-rw-r--r-- 1 ftpuser ftpusers 7595802 Jun 2 2000 g554ar.exe
+-rw-r--r-- 1 ftpuser ftpusers 39304570 Jun 2 2000 g554en.exe
+-rw-r--r-- 1 ftpuser ftpusers 13651283 Jun 2 2000 g554est.exe
+-rw-r--r-- 1 ftpuser ftpusers 7587459 Jun 2 2000 g554he.exe
+-rw-r--r-- 1 ftpuser ftpusers 23317212 Jun 2 2000 g554jp.exe
+-rw-r--r-- 1 ftpuser ftpusers 22871590 Jun 2 2000 g554kcc.exe
+-rw-r--r-- 1 ftpuser ftpusers 30379240 Jun 2 2000 g554mlt.exe
+-rw-r--r-- 1 ftpuser ftpusers 30469595 Jun 2 2000 g554scn.exe
+-rw-r--r-- 1 ftpuser ftpusers 3252251 Aug 31 2000 g5notmb1.exe
+-rw-r--r-- 1 ftpuser ftpusers 1983381 Aug 8 1995 gam10.exe
+-rw-r--r-- 1 ftpuser ftpusers 565411 Jul 20 1998 gbm21y2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 547498 Nov 19 1996 gdsmtp.exe
+-rw-r--r-- 1 ftpuser ftpusers 26760 Oct 21 1996 gdusc1.exe
+-rw-r--r-- 1 ftpuser ftpusers 32876 Sep 18 1993 genbio.exe
+-rw-r--r-- 1 ftpuser ftpusers 4589470 Oct 3 2001 gep3beng.exe
+-rw-r--r-- 1 ftpuser ftpusers 12570112 Aug 16 1999 gm527aen.bin
+-rw-r--r-- 1 ftpuser ftpusers 12556928 Jun 14 2000 gm528aen.bin
+-rw-r--r-- 1 ftpuser ftpusers 12558720 Jun 19 2000 gm528ben.bin
+-rw-r--r-- 1 ftpuser ftpusers 6081664 Dec 21 1996 gmcec3.hqx
+-rw-r--r-- 1 ftpuser ftpusers 6086656 Dec 21 1996 gmcfc3.hqx
+-rw-r--r-- 1 ftpuser ftpusers 6089856 Dec 24 1996 gmesc3.hqx
+-rw-r--r-- 1 ftpuser ftpusers 6087552 Dec 20 1996 gmfrc3.hqx
+-rw-r--r-- 1 ftpuser ftpusers 6084480 Dec 24 1996 gmitc3.hqx
+-rw-r--r-- 1 ftpuser ftpusers 6079872 Dec 19 1996 gmozc3.hqx
+-rw-r--r-- 1 ftpuser ftpusers 6081792 Dec 19 1996 gmukc3.hqx
+-rw-r--r-- 1 ftpuser ftpusers 6079872 Dec 11 1996 gmusc3.hqx
+-rw-r--r-- 1 ftpuser ftpusers 26557 Sep 18 1993 gpierr.exe
+-rw-r--r-- 1 ftpuser ftpusers 189508 Aug 28 1996 gpwrdk.exe
+-rw-r--r-- 1 ftpuser ftpusers 114332 Aug 28 1996 gpwrnl.exe
+-rw-r--r-- 1 ftpuser ftpusers 99491 Sep 3 1996 gpwrru.exe
+-rw-r--r-- 1 ftpuser ftpusers 131835 Aug 28 1996 gpwrsu.exe
+-rw-r--r-- 1 ftpuser ftpusers 170183 Aug 22 1996 gpwrsv.exe
+-rw-r--r-- 1 ftpuser ftpusers 74740 Feb 25 1998 gpwsbr.exe
+-rw-r--r-- 1 ftpuser ftpusers 44964 Feb 25 1998 gpwsde.exe
+-rw-r--r-- 1 ftpuser ftpusers 40264 Feb 25 1998 gpwsfr.exe
+-rw-r--r-- 1 ftpuser ftpusers 39224 Feb 25 1998 gpwsit.exe
+-rw-r--r-- 1 ftpuser ftpusers 47842 Jul 22 1999 groupfix.exe
+-rw-r--r-- 1 ftpuser ftpusers 207875 Oct 19 1995 gsc41.exe
+-rw-r--r-- 1 ftpuser ftpusers 811983 Dec 15 1997 gsc51.exe
+-rw-r--r-- 1 ftpuser ftpusers 9805824 Jun 8 1995 gusmtp.tar
+-rw-r--r-- 1 ftpuser ftpusers 4658880 Jul 28 1999 gw41api.exe
+-rw-r--r-- 1 ftpuser ftpusers 1307103 Nov 17 1999 gw41api2.exe
+-rw-r--r-- 1 ftpuser ftpusers 30983798 Jul 29 1999 gw41aus.exe
+-rw-r--r-- 1 ftpuser ftpusers 86653 Feb 28 1996 gw41qa.exe
+-rw-r--r-- 1 ftpuser ftpusers 20978 Dec 10 1998 gw41sp5.txt
+-rw-r--r-- 1 ftpuser ftpusers 18251583 Jan 8 1998 gw51sp2a.exe
+-rw-r--r-- 1 ftpuser ftpusers 3483616 Mar 10 1998 gw51w16a.exe
+-rw-r--r-- 1 ftpuser ftpusers 1931948 Jan 9 2001 gw52ch6.exe
+-rw-r--r-- 1 ftpuser ftpusers 479758 Jun 26 2000 gw52sp6.exe
+-rw-r--r-- 1 ftpuser ftpusers 35836761 Feb 28 16:19 gw555cck.exe
+-rw-r--r-- 1 ftpuser ftpusers 26614908 Feb 28 16:34 gw555ee.exe
+-rw-r--r-- 1 ftpuser ftpusers 372421 May 31 2000 gw55bk.exe
+-rw-r--r-- 1 ftpuser ftpusers 109887 Feb 3 2000 gw55bp.exe
+-rw-r--r-- 1 ftpuser ftpusers 847939 Jun 19 2000 gw55dutl.exe
+-rw-r--r-- 1 ftpuser ftpusers 58548675 Aug 14 2001 gw55ep3a.exe
+-rw-r--r-- 1 ftpuser ftpusers 2497895 Jun 25 1999 gw55inst.exe
+-rw-r--r-- 1 ftpuser ftpusers 3742457 Jun 27 2000 gw55ol2.exe
+-rw-r--r-- 1 ftpuser ftpusers 219963 Apr 18 2001 gw55puma.exe
+-rw-r--r-- 1 ftpuser ftpusers 19376 Mar 1 1999 gw55rc.exe
+-rw-r--r-- 1 ftpuser ftpusers 45201 Dec 18 1998 gw55sp1u.exe
+-rw-r--r-- 1 ftpuser ftpusers 21311033 Feb 28 16:08 gw55sp5a.exe
+-rw-r--r-- 1 ftpuser ftpusers 52764291 Feb 19 17:56 gw55sp5e.exe
+-rw-r--r-- 1 ftpuser ftpusers 21300984 Feb 28 16:13 gw55sp5h.exe
+-rw-r--r-- 1 ftpuser ftpusers 43933605 Feb 19 18:03 gw55sp5m.exe
+-rw-r--r-- 1 ftpuser ftpusers 44001516 Feb 28 16:03 gw55sp5s.exe
+-rw-r--r-- 1 ftpuser ftpusers 5867520 Mar 9 1999 gw55uagb.tar
+-rw-r--r-- 1 ftpuser ftpusers 20446033 Apr 23 1997 gw5img.exe
+-rw-r--r-- 1 ftpuser ftpusers 313843533 Nov 21 2001 gw6sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 313466368 Nov 20 2001 gw6sp1fr.exe
+-rw-r--r-- 1 ftpuser ftpusers 26705047 Mar 13 18:35 gw6tomcat_nt.exe
+-rw-r--r-- 1 ftpuser ftpusers 318278 Oct 15 2001 gw6wasf.exe
+-rw-r--r-- 1 ftpuser ftpusers 493803 Jan 22 1997 gwadm.exe
+-rw-r--r-- 1 ftpuser ftpusers 1900719 Jul 26 2000 gwafe510.exe
+-rw-r--r-- 1 ftpuser ftpusers 469618 Nov 2 1999 gwanlzr1.exe
+-rw-r--r-- 1 ftpuser ftpusers 479013 Jun 19 2000 gwata417.exe
+-rw-r--r-- 1 ftpuser ftpusers 1731751 Jun 19 2000 gwata517.exe
+-rw-r--r-- 1 ftpuser ftpusers 168008 Aug 12 1996 gwbr41.exe
+-rw-r--r-- 1 ftpuser ftpusers 17881984 Aug 31 1998 gwbrc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 194213 Aug 26 1997 gwbupaus.exe
+-rw-r--r-- 1 ftpuser ftpusers 885247 Jun 15 2000 gwca55.exe
+-rw-r--r-- 1 ftpuser ftpusers 902786 Jun 29 2000 gwca55us.exe
+-rw-r--r-- 1 ftpuser ftpusers 2398720 Aug 17 1999 gwccarch.exe
+-rw-r--r-- 1 ftpuser ftpusers 19751754 Aug 27 1998 gwcec5.exe
+-rw-r--r-- 1 ftpuser ftpusers 18095569 Dec 1 1998 gwcfc5a.exe
+-rw-r--r-- 1 ftpuser ftpusers 499022 Jan 22 1997 gwclint.exe
+-rw-r--r-- 1 ftpuser ftpusers 274618 Jun 19 2000 gwclust.exe
+-rw-r--r-- 1 ftpuser ftpusers 18704283 Aug 31 1998 gwczc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 18602662 Aug 28 1998 gwdec5.exe
+-rw-r--r-- 1 ftpuser ftpusers 577392 Jan 22 1997 gwdirsnc.exe
+-rw-r--r-- 1 ftpuser ftpusers 18044524 Aug 31 1998 gwdkc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 2064976 Aug 16 2001 gwe2mlfx.exe
+-rw-r--r-- 1 ftpuser ftpusers 220287 Apr 18 2001 gweppuma.exe
+-rw-r--r-- 1 ftpuser ftpusers 106411074 Feb 19 17:38 gwepsp4e.exe
+-rw-r--r-- 1 ftpuser ftpusers 105412358 Feb 19 17:48 gwepsp4m.exe
+-rw-r--r-- 1 ftpuser ftpusers 211359 Oct 15 2001 gwepwasf.exe
+-rw-r--r-- 1 ftpuser ftpusers 18156006 Aug 31 1998 gwesc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 2278400 Aug 20 1999 gwexarch.exe
+-rw-r--r-- 1 ftpuser ftpusers 18094284 Sep 2 1998 gwfrc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 14809111 Feb 5 12:22 gwia6sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 47599 Dec 24 1998 gwip.exe
+-rw-r--r-- 1 ftpuser ftpusers 2103744 Jun 26 2000 gwiru55.exe
+-rw-r--r-- 1 ftpuser ftpusers 18176506 Aug 31 1998 gwitc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 1643991 May 20 1997 gwjpc3.exe
+-rw-r--r-- 1 ftpuser ftpusers 2689024 Aug 24 1999 gwlnarch.exe
+-rw-r--r-- 1 ftpuser ftpusers 18450385 Aug 31 1998 gwmac5.exe
+-rw-r--r-- 1 ftpuser ftpusers 104256 Jun 19 2001 gwmacvew.exe
+-rw-r--r-- 1 ftpuser ftpusers 521879 Jan 22 1997 gwmigrat.exe
+-rw-r--r-- 1 ftpuser ftpusers 2387456 Aug 18 1999 gwmsarch.exe
+-rw-r--r-- 1 ftpuser ftpusers 18442250 Aug 31 1998 gwnlc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 18496070 Aug 31 1998 gwnoc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 18436940 Aug 27 1998 gwozc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 735542 Aug 29 2001 gwpdchk.exe
+-rw-r--r-- 1 ftpuser ftpusers 29521018 Aug 28 2001 gwpdlk56.exe
+-rw-r--r-- 1 ftpuser ftpusers 29520686 Aug 14 2001 gwpdlock.exe
+-rw-r--r-- 1 ftpuser ftpusers 18696898 Aug 31 1998 gwplc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 1388969 Mar 5 1996 gwpoc.exe
+-rw-r--r-- 1 ftpuser ftpusers 17738497 Aug 31 1998 gwpoc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 10400450 Jan 22 16:48 gwport32.exe
+-rw-r--r-- 1 ftpuser ftpusers 18492682 Aug 31 1998 gwruc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 18154021 Aug 31 1998 gwsuc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 17958220 Aug 31 1998 gwsvc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 536848 Jan 16 09:41 gwsyclo.exe
+-rw-r--r-- 1 ftpuser ftpusers 78740 Nov 9 1999 gwtps1v2.exe
+-rw-r--r-- 1 ftpuser ftpusers 18432206 Aug 28 1998 gwukc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 18544901 Aug 27 1998 gwusc5.exe
+-rw-r--r-- 1 ftpuser ftpusers 210542 Oct 18 1995 gwusr1.exe
+-rw-r--r-- 1 ftpuser ftpusers 1404401 Oct 18 1995 gwusr2.exe
+-rw-r--r-- 1 ftpuser ftpusers 2467040 Mar 28 1997 gwusr3.exe
+-rw-r--r-- 1 ftpuser ftpusers 767611 Oct 1 1997 gwwa4p1.exe
+-rw-r--r-- 1 ftpuser ftpusers 2092781 Mar 4 1998 gwwebcgi.z
+-rw-r--r-- 1 ftpuser ftpusers 345006 Aug 4 1999 gwy195.exe
+-rw-r--r-- 1 ftpuser ftpusers 102293 Oct 9 2001 hdir501c.exe
+-rw-r--r-- 1 ftpuser ftpusers 1138106 Aug 21 1998 highutl1.exe
+-rw-r--r-- 1 ftpuser ftpusers 567026 Mar 28 1995 hpt004.exe
+-rw-r--r-- 1 ftpuser ftpusers 64329 Mar 9 1995 hpt005.exe
+-rw-r--r-- 1 ftpuser ftpusers 602958 Aug 27 1996 hpt006.exe
+-rw-r--r-- 1 ftpuser ftpusers 497382 Mar 9 1995 hpt007.exe
+-rw-r--r-- 1 ftpuser ftpusers 510029 Mar 9 1995 hpt008.exe
+-rw-r--r-- 1 ftpuser ftpusers 596667 Mar 13 1995 hpt009.exe
+-rw-r--r-- 1 ftpuser ftpusers 942798 Nov 20 1995 hpt011.exe
+-rw-r--r-- 1 ftpuser ftpusers 176332 Aug 11 1995 hpt013.exe
+-rw-r--r-- 1 ftpuser ftpusers 1070543 Mar 16 1999 hstdev.exe
+-rw-r--r-- 1 ftpuser ftpusers 246782 Apr 5 14:51 httpstk1.exe
+-rw-r--r-- 1 ftpuser ftpusers 262791 Apr 19 2000 i2odrv5.exe
+-rw-r--r-- 1 ftpuser ftpusers 565749 Jul 20 1998 ibm21y2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 24735 Sep 18 1993 ibmmem.exe
+-rw-r--r-- 1 ftpuser ftpusers 60883 Sep 18 1993 ibmrt.exe
+-rw-r--r-- 1 ftpuser ftpusers 2621963 Jul 11 2001 ic15fp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 2905716 Feb 8 16:39 ic15fp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 9581302 Apr 4 2001 ic15sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 1585498 Dec 14 2001 ic20fp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 4520778 Jan 14 09:32 ic20fp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 4777958 May 30 15:01 ic20sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 142010 Mar 28 17:46 ichcdump.exe
+-rw-r--r-- 1 ftpuser ftpusers 36043 Sep 20 1994 ide.exe
+-rw-r--r-- 1 ftpuser ftpusers 24552 Sep 18 1993 ide286.exe
+-rw-r--r-- 1 ftpuser ftpusers 27300 Sep 18 1993 ide386.exe
+-rw-r--r-- 1 ftpuser ftpusers 105249 Jun 9 2000 ideata5a.exe
+-rw-r--r-- 1 ftpuser ftpusers 1356133 Apr 17 2000 ihp232.exe
+-rw-r--r-- 1 ftpuser ftpusers 93664 Mar 8 15:40 imspmfix.exe
+-rw-r--r-- 1 ftpuser ftpusers 7338542 Jul 23 1998 in42sp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 430410 Nov 8 1995 ind41.exe
+-rw-r--r-- 1 ftpuser ftpusers 63751 Mar 20 1997 inetcs.exe
+-rw-r--r-- 1 ftpuser ftpusers 60414 Mar 20 1997 inetct.exe
+-rw-r--r-- 1 ftpuser ftpusers 69792 Apr 28 1997 inetha.exe
+-rw-r--r-- 1 ftpuser ftpusers 1094896 Oct 18 1995 inf1.exe
+-rw-r--r-- 1 ftpuser ftpusers 798379 Oct 18 1995 inff1.exe
+-rw-r--r-- 1 ftpuser ftpusers 151877 Jan 9 2002 installa.exe
+-rw-r--r-- 1 ftpuser ftpusers 836804 Jun 9 1995 instll.exe
+-rw-r--r-- 1 ftpuser ftpusers 101582 Oct 9 2000 instp5x.exe
+-rw-r--r-- 1 ftpuser ftpusers 39511 Sep 18 1993 int215.exe
+-rw-r--r-- 1 ftpuser ftpusers 19521 Sep 18 1993 intfix.exe
+-rw-r--r-- 1 ftpuser ftpusers 35521 Sep 18 1993 intrud.exe
+-rw-r--r-- 1 ftpuser ftpusers 5594188 Dec 4 1997 inwc2enh.exe
+-rw-r--r-- 1 ftpuser ftpusers 69340 Sep 18 1993 ipc212.exe
+-rw-r--r-- 1 ftpuser ftpusers 24423 Sep 18 1993 ipcfg.exe
+-rw-r--r-- 1 ftpuser ftpusers 593463 Aug 13 2001 ipcost.exe
+-rw-r--r-- 1 ftpuser ftpusers 131414 Jun 24 1999 ipg4201a.exe
+-rw-r--r-- 1 ftpuser ftpusers 617600 Jun 30 2000 ipgc07a.exe
+-rw-r--r-- 1 ftpuser ftpusers 233838 Feb 11 2000 ipgsb06.exe
+-rw-r--r-- 1 ftpuser ftpusers 107564 Oct 2 1999 ipgsn10a.exe
+-rw-r--r-- 1 ftpuser ftpusers 44888 Nov 15 1999 ipgwdoc.exe
+-rw-r--r-- 1 ftpuser ftpusers 65876 Sep 18 1993 ipt112.exe
+-rw-r--r-- 1 ftpuser ftpusers 842325 Sep 23 1998 ipx660.exe
+-rw-r--r-- 1 ftpuser ftpusers 37227 Dec 1 1995 ipxspx.exe
+-rw-r--r-- 1 ftpuser ftpusers 22904 Sep 18 1993 isa30.exe
+-rw-r--r-- 1 ftpuser ftpusers 31546 Sep 18 1993 isa311.exe
+-rw-r--r-- 1 ftpuser ftpusers 24391 Sep 18 1993 isarem.exe
+-rw-r--r-- 1 ftpuser ftpusers 49650 Apr 9 1997 iwsbp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 6073482 Nov 21 2000 jbm30sp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 109173 Oct 19 1995 jcon.exe
+-rw-r--r-- 1 ftpuser ftpusers 185167 Aug 16 2001 jr08993.exe
+-rw-r--r-- 1 ftpuser ftpusers 54187 Aug 15 2001 jr10449.exe
+-rw-r--r-- 1 ftpuser ftpusers 51804 Aug 15 2001 jr10470.exe
+-rw-r--r-- 1 ftpuser ftpusers 105466 May 29 2001 jr10490.exe
+-rw-r--r-- 1 ftpuser ftpusers 17936 Oct 16 2000 jr10662.exe
+-rw-r--r-- 1 ftpuser ftpusers 51421 Oct 16 2000 jr10803.exe
+-rw-r--r-- 1 ftpuser ftpusers 884373 Aug 15 2001 jr10823.exe
+-rw-r--r-- 1 ftpuser ftpusers 1909 Aug 15 2001 jr10923.zip
+-rw-r--r-- 1 ftpuser ftpusers 53610 Oct 16 2000 jr11209.exe
+-rw-r--r-- 1 ftpuser ftpusers 272210 Oct 16 2000 jr11213.exe
+-rw-r--r-- 1 ftpuser ftpusers 32984 May 27 2001 jr11223.exe
+-rw-r--r-- 1 ftpuser ftpusers 45200 Oct 16 2000 jr11409.exe
+-rw-r--r-- 1 ftpuser ftpusers 488829 May 27 2001 jr12054.exe
+-rw-r--r-- 1 ftpuser ftpusers 17761 Aug 15 2001 jr12089.exe
+-rw-r--r-- 1 ftpuser ftpusers 245833 May 27 2001 jr12125.exe
+-rw-r--r-- 1 ftpuser ftpusers 242650 Aug 15 2001 jr12129.exe
+-rw-r--r-- 1 ftpuser ftpusers 144543 May 27 2001 jr12229.exe
+-rw-r--r-- 1 ftpuser ftpusers 23194 May 27 2001 jr12349.exe
+-rw-r--r-- 1 ftpuser ftpusers 158924 Aug 15 2001 jr12415.exe
+-rw-r--r-- 1 ftpuser ftpusers 39844 Oct 16 2000 jr12518.exe
+-rw-r--r-- 1 ftpuser ftpusers 42015 Oct 16 2000 jr12676.exe
+-rw-r--r-- 1 ftpuser ftpusers 42090 May 27 2001 jr12692.exe
+-rw-r--r-- 1 ftpuser ftpusers 41998 May 29 2001 jr12705.exe
+-rw-r--r-- 1 ftpuser ftpusers 21903 Oct 16 2000 jr12706.exe
+-rw-r--r-- 1 ftpuser ftpusers 75818 Oct 16 2000 jr12765.exe
+-rw-r--r-- 1 ftpuser ftpusers 245898 Aug 15 2001 jr12768.exe
+-rw-r--r-- 1 ftpuser ftpusers 144542 Oct 16 2000 jr12773.exe
+-rw-r--r-- 1 ftpuser ftpusers 144542 May 29 2001 jr12775.exe
+-rw-r--r-- 1 ftpuser ftpusers 144543 Aug 15 2001 jr12776.exe
+-rw-r--r-- 1 ftpuser ftpusers 44352 Oct 16 2000 jr12777.exe
+-rw-r--r-- 1 ftpuser ftpusers 44355 May 27 2001 jr12778.exe
+-rw-r--r-- 1 ftpuser ftpusers 43721 Aug 15 2001 jr12828.exe
+-rw-r--r-- 1 ftpuser ftpusers 52823 May 27 2001 jr12890.exe
+-rw-r--r-- 1 ftpuser ftpusers 52824 Oct 16 2000 jr12947.exe
+-rw-r--r-- 1 ftpuser ftpusers 74323 Oct 16 2000 jr12978.exe
+-rw-r--r-- 1 ftpuser ftpusers 74323 May 27 2001 jr12979.exe
+-rw-r--r-- 1 ftpuser ftpusers 74326 May 29 2001 jr12987.exe
+-rw-r--r-- 1 ftpuser ftpusers 16573256 May 27 2001 jr13042.exe
+-rw-r--r-- 1 ftpuser ftpusers 16586769 Aug 15 2001 jr13046.exe
+-rw-r--r-- 1 ftpuser ftpusers 170632 Aug 15 2001 jr13047.exe
+-rw-r--r-- 1 ftpuser ftpusers 55210 Aug 15 2001 jr13105.exe
+-rw-r--r-- 1 ftpuser ftpusers 124966 Aug 15 2001 jr13147.exe
+-rw-r--r-- 1 ftpuser ftpusers 43318 Oct 16 2000 jr13259.exe
+-rw-r--r-- 1 ftpuser ftpusers 33183 Oct 16 2000 jr13461.exe
+-rw-r--r-- 1 ftpuser ftpusers 84700 May 27 2001 jr13554.exe
+-rw-r--r-- 1 ftpuser ftpusers 84649 Oct 16 2000 jr13555.exe
+-rw-r--r-- 1 ftpuser ftpusers 52564 May 27 2001 jr13557.exe
+-rw-r--r-- 1 ftpuser ftpusers 52161 Oct 16 2000 jr13558.exe
+-rw-r--r-- 1 ftpuser ftpusers 52167 May 29 2001 jr13559.exe
+-rw-r--r-- 1 ftpuser ftpusers 54942 May 27 2001 jr13616.exe
+-rw-r--r-- 1 ftpuser ftpusers 54947 Oct 16 2000 jr13617.exe
+-rw-r--r-- 1 ftpuser ftpusers 56424 Aug 15 2001 jr13619.exe
+-rw-r--r-- 1 ftpuser ftpusers 71827 Sep 17 1999 jr13627.exe
+-rw-r--r-- 1 ftpuser ftpusers 83182 Oct 16 2000 jr13637.exe
+-rw-r--r-- 1 ftpuser ftpusers 108483 May 29 2001 jr13722.exe
+-rw-r--r-- 1 ftpuser ftpusers 170173 Aug 15 2001 jr13734.exe
+-rw-r--r-- 1 ftpuser ftpusers 641941 Aug 15 2001 jr13748.exe
+-rw-r--r-- 1 ftpuser ftpusers 641950 May 29 2001 jr13749.exe
+-rw-r--r-- 1 ftpuser ftpusers 579521 May 29 2001 jr13886.exe
+-rw-r--r-- 1 ftpuser ftpusers 126491 Aug 15 2001 jr13891.exe
+-rw-r--r-- 1 ftpuser ftpusers 109292 May 27 2001 jr14132.exe
+-rw-r--r-- 1 ftpuser ftpusers 109181 Aug 15 2001 jr14134.exe
+-rw-r--r-- 1 ftpuser ftpusers 39830 May 29 2001 jr14185.exe
+-rw-r--r-- 1 ftpuser ftpusers 72780 Aug 15 2001 jr14278.exe
+-rw-r--r-- 1 ftpuser ftpusers 345689 Aug 15 2001 jr14358.exe
+-rw-r--r-- 1 ftpuser ftpusers 642240 May 27 2001 jr14359.exe
+-rw-r--r-- 1 ftpuser ftpusers 642388 Oct 16 2000 jr14360.exe
+-rw-r--r-- 1 ftpuser ftpusers 313078 May 27 2001 jr14367.exe
+-rw-r--r-- 1 ftpuser ftpusers 109587 May 27 2001 jr14402.exe
+-rw-r--r-- 1 ftpuser ftpusers 71603 Aug 15 2001 jr14457.exe
+-rw-r--r-- 1 ftpuser ftpusers 567270 Aug 15 2001 jr14500.exe
+-rw-r--r-- 1 ftpuser ftpusers 157611 Aug 15 2001 jr14523.exe
+-rw-r--r-- 1 ftpuser ftpusers 161290 Aug 15 2001 jr14556.exe
+-rw-r--r-- 1 ftpuser ftpusers 161439 May 27 2001 jr14585.exe
+-rw-r--r-- 1 ftpuser ftpusers 161435 Oct 16 2000 jr14586.exe
+-rw-r--r-- 1 ftpuser ftpusers 186037 Oct 16 2000 jr14840.exe
+-rw-r--r-- 1 ftpuser ftpusers 368604 Oct 16 2000 jr14936.exe
+-rw-r--r-- 1 ftpuser ftpusers 115132 Aug 15 2001 jr15013.exe
+-rw-r--r-- 1 ftpuser ftpusers 568164 Aug 15 2001 jr15133.exe
+-rw-r--r-- 1 ftpuser ftpusers 217169 Aug 15 2001 jr15338.exe
+-rw-r--r-- 1 ftpuser ftpusers 362664 Aug 15 2001 jr15396.exe
+-rw-r--r-- 1 ftpuser ftpusers 104143 Aug 15 2001 jr15509.exe
+-rw-r--r-- 1 ftpuser ftpusers 473822 Aug 15 2001 jr15544.exe
+-rw-r--r-- 1 ftpuser ftpusers 484196 Jul 25 2001 jssl11d.exe
+-rw-r--r-- 1 ftpuser ftpusers 36251555 Jul 20 2001 jvm122.exe
+-rw-r--r-- 1 ftpuser ftpusers 49007010 Feb 28 08:06 jvm131.exe
+-rw-r--r-- 1 ftpuser ftpusers 48672254 Mar 28 2001 jzfd3sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 66469 Jul 17 1997 killq.exe
+-rw-r--r-- 1 ftpuser ftpusers 202716 Mar 1 1994 l11f01.exe
+-rw-r--r-- 1 ftpuser ftpusers 202878 Mar 1 1994 l11g01.exe
+-rw-r--r-- 1 ftpuser ftpusers 202460 Mar 1 1994 l11i01.exe
+-rw-r--r-- 1 ftpuser ftpusers 23583 Jan 6 1994 l11p06.exe
+-rw-r--r-- 1 ftpuser ftpusers 202249 Mar 1 1994 l11s01.exe
+-rw-r--r-- 1 ftpuser ftpusers 30533 Nov 24 1993 l11u05.exe
+-rw-r--r-- 1 ftpuser ftpusers 206616 Apr 20 1999 lanchk.exe
+-rw-r--r-- 1 ftpuser ftpusers 341280 Oct 21 1996 landr9.exe
+-rw-r--r-- 1 ftpuser ftpusers 4610909 May 14 1998 landrv.exe
+-rw-r--r-- 1 ftpuser ftpusers 24799 Sep 10 1996 lanwcs.exe
+-rw-r--r-- 1 ftpuser ftpusers 37088 Sep 4 1996 lanwct.exe
+-rw-r--r-- 1 ftpuser ftpusers 42514 Sep 4 1996 lanwes.exe
+-rw-r--r-- 1 ftpuser ftpusers 42417 Sep 11 1996 lanwfr.exe
+-rw-r--r-- 1 ftpuser ftpusers 36855 Sep 10 1996 lanwha.exe
+-rw-r--r-- 1 ftpuser ftpusers 42397 Sep 4 1996 lanwit.exe
+-rw-r--r-- 1 ftpuser ftpusers 16012931 Jan 31 16:00 lanwp02.exe
+-rw-r--r-- 1 ftpuser ftpusers 342390 Dec 16 1996 lat002.exe
+-rw-r--r-- 1 ftpuser ftpusers 133326 Sep 18 1993 ld401a.exe
+-rw-r--r-- 1 ftpuser ftpusers 166765 Feb 7 2000 ldr312ft.exe
+-rw-r--r-- 1 ftpuser ftpusers 26450 Sep 18 1993 leap.exe
+-rw-r--r-- 1 ftpuser ftpusers 180540 Jun 9 1994 lg4084.exe
+-rw-r--r-- 1 ftpuser ftpusers 91840 Dec 14 1995 lg42l4.exe
+-rw-r--r-- 1 ftpuser ftpusers 72061 Oct 11 1995 li3pre.exe
+-rw-r--r-- 1 ftpuser ftpusers 258605 Jun 2 1998 lib311b.exe
+-rw-r--r-- 1 ftpuser ftpusers 273268 Sep 20 1999 lib312d.exe
+-rw-r--r-- 1 ftpuser ftpusers 977416 Feb 23 2000 libupj4.exe
+-rw-r--r-- 1 ftpuser ftpusers 111269 Jun 26 1995 lo30a2.exe
+-rw-r--r-- 1 ftpuser ftpusers 94927 Jun 26 1995 lo30t1.exe
+-rw-r--r-- 1 ftpuser ftpusers 105128 Sep 18 1993 load.exe
+-rw-r--r-- 1 ftpuser ftpusers 111722 Aug 26 1998 loaddll1.exe
+-rw-r--r-- 1 ftpuser ftpusers 20810 Sep 18 1993 locins.exe
+-rw-r--r-- 1 ftpuser ftpusers 74768 Mar 9 1995 log376.exe
+-rw-r--r-- 1 ftpuser ftpusers 269333 Sep 15 1997 log410a.exe
+-rw-r--r-- 1 ftpuser ftpusers 99524 Feb 23 2000 longnam.exe
+-rw-r--r-- 1 ftpuser ftpusers 1563061 Mar 5 1997 lpo51a.exe
+-rw-r--r-- 1 ftpuser ftpusers 115601 Mar 14 1997 lpo51b.exe
+-rw-r--r-- 1 ftpuser ftpusers 373114 Jun 12 1995 lw42w2.exe
+-rw-r--r-- 1 ftpuser ftpusers 986579 Sep 20 1996 lw50w1.exe
+-rw-r--r-- 1 ftpuser ftpusers 79276 Aug 21 1996 lwg50a.exe
+-rw-r--r-- 1 ftpuser ftpusers 115527 Aug 18 1998 lwp001.exe
+-rw-r--r-- 1 ftpuser ftpusers 54951 Aug 20 1998 lwp002.exe
+-rw-r--r-- 1 ftpuser ftpusers 447982 May 6 1996 lwp413.exe
+-rw-r--r-- 1 ftpuser ftpusers 231591 Nov 30 1994 lwp423.exe
+-rw-r--r-- 1 ftpuser ftpusers 26516 May 18 1998 lwp501.exe
+-rw-r--r-- 1 ftpuser ftpusers 27895 May 15 1998 lwp511.exe
+-rw-r--r-- 1 ftpuser ftpusers 21913 Sep 18 1993 lwpo30.exe
+-rw-r--r-- 1 ftpuser ftpusers 47334 Sep 3 1997 lwpping.exe
+-rw-r--r-- 1 ftpuser ftpusers 356846 Aug 9 1999 lzfw01c.exe
+-rw-r--r-- 1 ftpuser ftpusers 33252 Oct 18 1993 lzfwdi.exe
+-rw-r--r-- 1 ftpuser ftpusers 1083871 Jul 14 1999 lzfwlf.exe
+-rw-r--r-- 1 ftpuser ftpusers 29057 Jun 16 1995 lzfwqa.exe
+-rw-r--r-- 1 ftpuser ftpusers 26848 Sep 7 1994 lzw001.exe
+-rw-r--r-- 1 ftpuser ftpusers 29431 May 16 1995 lzw002.exe
+-rw-r--r-- 1 ftpuser ftpusers 151295 Sep 18 1993 lzw40.exe
+-rw-r--r-- 1 ftpuser ftpusers 29379 Sep 18 1993 m30pat.exe
+-rw-r--r-- 1 ftpuser ftpusers 122720 Jul 24 1996 macfil.exe
+-rw-r--r-- 1 ftpuser ftpusers 347278 Jul 10 1997 macpt3d.exe
+-rw-r--r-- 1 ftpuser ftpusers 193792 May 29 1996 mactsa.bin
+-rw-r--r-- 1 ftpuser ftpusers 232349 Jul 23 1996 mactsa.exe
+-rw-r--r-- 1 ftpuser ftpusers 210004 Feb 21 1996 mailcl.exe
+-rw-r--r-- 1 ftpuser ftpusers 48964 Mar 13 1995 map312.exe
+-rw-r--r-- 1 ftpuser ftpusers 144574 Nov 24 1997 map410b.exe
+-rw-r--r-- 1 ftpuser ftpusers 127956 Oct 10 2001 masv_sp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 266084 Feb 28 2001 mbcmnup1.exe
+-rw-r--r-- 1 ftpuser ftpusers 508288 Aug 13 1998 mclupd6a.bin
+-rw-r--r-- 1 ftpuser ftpusers 22803 Sep 18 1993 mcmfm.exe
+-rw-r--r-- 1 ftpuser ftpusers 37710 Feb 11 1994 mdf178.exe
+-rw-r--r-- 1 ftpuser ftpusers 87520 Sep 18 1993 menu34.exe
+-rw-r--r-- 1 ftpuser ftpusers 20214 Nov 15 1993 menuhi.exe
+-rw-r--r-- 1 ftpuser ftpusers 91376 Sep 18 1993 menus.exe
+-rw-r--r-- 1 ftpuser ftpusers 5040875 Aug 15 2001 mgt22010.exe
+-rw-r--r-- 1 ftpuser ftpusers 683946 Nov 3 1993 mhs173.exe
+-rw-r--r-- 1 ftpuser ftpusers 656047 Feb 14 1994 mhs183.exe
+-rw-r--r-- 1 ftpuser ftpusers 664789 Feb 7 1994 mhs184.exe
+-rw-r--r-- 1 ftpuser ftpusers 85281 Nov 3 1997 mhsmcu.exe
+-rw-r--r-- 1 ftpuser ftpusers 54627 Sep 18 1993 mhsmd.exe
+-rw-r--r-- 1 ftpuser ftpusers 604103 Aug 16 1994 mhsslt.exe
+-rw-r--r-- 1 ftpuser ftpusers 132603 Jun 30 1995 mhsvr1.exe
+-rw-r--r-- 1 ftpuser ftpusers 449605 Aug 1 1996 migrat.exe
+-rw-r--r-- 1 ftpuser ftpusers 33708 Sep 18 1993 mirrem.exe
+-rw-r--r-- 1 ftpuser ftpusers 27044 Jan 5 2000 mixmod6.exe
+-rw-r--r-- 1 ftpuser ftpusers 96673 Sep 18 1993 mkuser.exe
+-rw-r--r-- 1 ftpuser ftpusers 68504 Sep 18 1995 mon176.exe
+-rw-r--r-- 1 ftpuser ftpusers 66024 May 18 1995 monsft.exe
+-rw-r--r-- 1 ftpuser ftpusers 424897 Sep 18 1993 morebk.exe
+-rw-r--r-- 1 ftpuser ftpusers 37818 Sep 18 1993 mountr.exe
+-rw-r--r-- 1 ftpuser ftpusers 19452 Sep 18 1993 mouse.exe
+-rw-r--r-- 1 ftpuser ftpusers 32801 Feb 3 1994 mpr182.exe
+-rw-r--r-- 1 ftpuser ftpusers 125166 Jul 15 1994 mpr199.exe
+-rw-r--r-- 1 ftpuser ftpusers 1066126 Jun 4 1996 mpr31a.exe
+-rw-r--r-- 1 ftpuser ftpusers 1082729 Oct 28 1996 mpr31b.exe
+-rw-r--r-- 1 ftpuser ftpusers 31245 Sep 23 1994 mprper.exe
+-rw-r--r-- 1 ftpuser ftpusers 38997 Mar 24 1995 mprul3.exe
+-rw-r--r-- 1 ftpuser ftpusers 122440 Oct 11 1995 mprx25.exe
+-rw-r--r-- 1 ftpuser ftpusers 328085 Aug 2 1996 msml21.exe
+-rw-r--r-- 1 ftpuser ftpusers 5876316 Oct 5 1998 msmlos21.exe
+-rw-r--r-- 1 ftpuser ftpusers 70822 Aug 2 1999 msmpcu.exe
+-rw-r--r-- 1 ftpuser ftpusers 6355314 May 31 2000 mw26sp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 119531 Jul 31 2000 mw26trd1.exe
+-rw-r--r-- 1 ftpuser ftpusers 3054719 Nov 13 2000 mw27sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 27173 Nov 23 1999 mw5mcal1.exe
+-rw-r--r-- 1 ftpuser ftpusers 253007 May 17 2000 mwhp01b.exe
+-rw-r--r-- 1 ftpuser ftpusers 255066 Jan 25 11:47 mwhp01c.exe
+-rw-r--r-- 1 ftpuser ftpusers 9813556 Sep 1 2000 mwinoc1k.exe
+-rw-r--r-- 1 ftpuser ftpusers 8298211 Sep 1 2000 mwinoc2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 141530 Feb 20 14:35 mwipgrop.exe
+-rw-r--r-- 1 ftpuser ftpusers 566807 Oct 9 1996 mwmis01.exe
+-rw-r--r-- 1 ftpuser ftpusers 1070535 Jan 26 1999 mwnma26.exe
+-rw-r--r-- 1 ftpuser ftpusers 265545 Oct 16 1998 mwnma3a.exe
+-rw-r--r-- 1 ftpuser ftpusers 300304 Oct 16 1998 mwnma4a.exe
+-rw-r--r-- 1 ftpuser ftpusers 2180810 Apr 12 2001 mwnmaupd.exe
+-rw-r--r-- 1 ftpuser ftpusers 154598 Jan 12 2000 mwnxp26.exe
+-rw-r--r-- 1 ftpuser ftpusers 339201 Apr 9 2001 mwnxpfix.exe
+-rw-r--r-- 1 ftpuser ftpusers 1502706 Aug 20 1999 mwzen01.exe
+-rw-r--r-- 1 ftpuser ftpusers 58460632 Mar 28 2001 mzfd3sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 2407200 May 24 2001 n51_nis1.exe
+-rw-r--r-- 1 ftpuser ftpusers 6840962 May 16 2000 n8slinux.01
+-rw-r--r-- 1 ftpuser ftpusers 217465 Feb 18 1998 na4nty2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 48510 Sep 18 1993 nacs2.exe
+-rw-r--r-- 1 ftpuser ftpusers 64238 May 28 1996 nadhep.exe
+-rw-r--r-- 1 ftpuser ftpusers 1777018 Mar 23 1999 nal201p2.exe
+-rw-r--r-- 1 ftpuser ftpusers 38276 Oct 29 1996 nam312.exe
+-rw-r--r-- 1 ftpuser ftpusers 199571 Jun 6 2000 nam41d.exe
+-rw-r--r-- 1 ftpuser ftpusers 104382 May 24 15:12 nat600d.exe
+-rw-r--r-- 1 ftpuser ftpusers 322806 Sep 18 1993 nbckup.exe
+-rw-r--r-- 1 ftpuser ftpusers 21328 Jan 10 1997 nbora.exe
+-rw-r--r-- 1 ftpuser ftpusers 18843 Aug 12 1997 nc1tip.txt
+-rw-r--r-- 1 ftpuser ftpusers 838367 Jun 3 09:30 nccutl10.exe
+-rw-r--r-- 1 ftpuser ftpusers 7725859 Oct 24 2000 nce8slr1.z
+-rw-r--r-- 1 ftpuser ftpusers 77251 Sep 18 1993 nconfg.exe
+-rw-r--r-- 1 ftpuser ftpusers 19889 Oct 10 1997 ncpec.exe
+-rw-r--r-- 1 ftpuser ftpusers 144892 Sep 15 1997 ncpy410a.exe
+-rw-r--r-- 1 ftpuser ftpusers 136962 Nov 21 2000 ncs3.exe
+-rw-r--r-- 1 ftpuser ftpusers 704205 Oct 1 1996 ncv201.exe
+-rw-r--r-- 1 ftpuser ftpusers 811853 Oct 1 1996 ncv202.exe
+-rw-r--r-- 1 ftpuser ftpusers 489774 Apr 21 1998 ncv20y2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 142314 Nov 12 2001 ndb410q.exe
+-rw-r--r-- 1 ftpuser ftpusers 820712 Feb 21 13:36 ndp21p3c.exe
+-rw-r--r-- 1 ftpuser ftpusers 853818 Jun 21 12:06 ndp21p4.exe
+-rw-r--r-- 1 ftpuser ftpusers 1008445 Oct 17 2001 ndp2xp7.exe
+-rw-r--r-- 1 ftpuser ftpusers 530101 Feb 21 13:53 ndpcnw6.exe
+-rw-r--r-- 1 ftpuser ftpusers 909348 Feb 21 13:48 ndpcsp3a.exe
+-rw-r--r-- 1 ftpuser ftpusers 94047 Jul 17 2001 ndpsinf.exe
+-rw-r--r-- 1 ftpuser ftpusers 11673051 Oct 4 2001 ndpsw2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 59495 Sep 18 1993 ndr345.exe
+-rw-r--r-- 1 ftpuser ftpusers 112722 Feb 2 2000 nds4ntp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 507960 Aug 17 2000 nds4ntu3.exe
+-rw-r--r-- 1 ftpuser ftpusers 3437308 Oct 27 2000 nds8lnx1.gz
+-rw-r--r-- 1 ftpuser ftpusers 14133762 Jul 17 2001 ndsas3s1.exe
+-rw-r--r-- 1 ftpuser ftpusers 24182 Sep 18 1993 ndscsi.exe
+-rw-r--r-- 1 ftpuser ftpusers 41652 Sep 18 1993 ndspx.exe
+-rw-r--r-- 1 ftpuser ftpusers 6712 Jul 20 2000 ndssch.gz
+-rw-r--r-- 1 ftpuser ftpusers 20023 Sep 18 1993 ndstac.exe
+-rw-r--r-- 1 ftpuser ftpusers 211239 Sep 18 1993 ne286.exe
+-rw-r--r-- 1 ftpuser ftpusers 5894979 Oct 24 2000 ned8slr1.z
+-rw-r--r-- 1 ftpuser ftpusers 82148198 May 3 2000 nesn451a.exe
+-rw-r--r-- 1 ftpuser ftpusers 1157470 Dec 20 2000 nesn51b.exe
+-rw-r--r-- 1 ftpuser ftpusers 866140 Nov 28 2001 nesn51c.exe
+-rw-r--r-- 1 ftpuser ftpusers 865375 Mar 5 06:54 nesn51d.exe
+-rw-r--r-- 1 ftpuser ftpusers 138202 Mar 16 1999 netarng3.exe
+-rw-r--r-- 1 ftpuser ftpusers 73822 Feb 4 1998 netfr.exe
+-rw-r--r-- 1 ftpuser ftpusers 306211 Mar 12 1996 netusr.exe
+-rw-r--r-- 1 ftpuser ftpusers 74054 Feb 4 1998 netwbr.exe
+-rw-r--r-- 1 ftpuser ftpusers 56229 Feb 4 1998 netwde.exe
+-rw-r--r-- 1 ftpuser ftpusers 27699 Aug 28 1996 netwdk.exe
+-rw-r--r-- 1 ftpuser ftpusers 67776 Feb 2 1998 netwes.exe
+-rw-r--r-- 1 ftpuser ftpusers 59210 Feb 12 1998 netwit.exe
+-rw-r--r-- 1 ftpuser ftpusers 28000 Aug 28 1996 netwno.exe
+-rw-r--r-- 1 ftpuser ftpusers 53501 Sep 10 1996 netwru.exe
+-rw-r--r-- 1 ftpuser ftpusers 27741 Aug 23 1996 netwsv.exe
+-rw-r--r-- 1 ftpuser ftpusers 1539054 Mar 18 15:27 nfap1sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 290090 Aug 22 1994 nfs193.exe
+-rw-r--r-- 1 ftpuser ftpusers 2266015 Dec 30 1997 nfs203.exe
+-rw-r--r-- 1 ftpuser ftpusers 2007873 Nov 23 1998 nfs205.exe
+-rw-r--r-- 1 ftpuser ftpusers 6472548 Jul 20 2001 nfs30sp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 1310460 Mar 6 15:56 nfs30sp3a.exe
+-rw-r--r-- 1 ftpuser ftpusers 1186381 May 29 14:59 nfs3nwci.exe
+-rw-r--r-- 1 ftpuser ftpusers 5440307 Aug 28 2001 nfs3sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 1280002 Feb 2 2001 nfsadmn2.exe
+-rw-r--r-- 1 ftpuser ftpusers 38114 Jan 20 1998 nfsmlaup.exe
+-rw-r--r-- 1 ftpuser ftpusers 35803 Aug 2 1999 nfsnam23.exe
+-rw-r--r-- 1 ftpuser ftpusers 245015 Sep 18 1993 ngm121.exe
+-rw-r--r-- 1 ftpuser ftpusers 1240500 Sep 18 1993 ngm137.exe
+-rw-r--r-- 1 ftpuser ftpusers 145298 Sep 18 1993 ngm138.exe
+-rw-r--r-- 1 ftpuser ftpusers 145010 Sep 18 1993 ngm139.exe
+-rw-r--r-- 1 ftpuser ftpusers 781292 Oct 28 1993 ngm170.exe
+-rw-r--r-- 1 ftpuser ftpusers 202093 Dec 3 1993 ngm175.exe
+-rw-r--r-- 1 ftpuser ftpusers 201248 Dec 6 1993 ngm176.exe
+-rw-r--r-- 1 ftpuser ftpusers 279862 May 26 1994 ngm192.exe
+-rw-r--r-- 1 ftpuser ftpusers 945888 Dec 20 1996 ngm211.exe
+-rw-r--r-- 1 ftpuser ftpusers 1403369 Aug 5 1995 ngwadm.exe
+-rw-r--r-- 1 ftpuser ftpusers 1810533 Aug 13 1996 ngwaup.exe
+-rw-r--r-- 1 ftpuser ftpusers 106862 Oct 31 1995 ngwmfc.exe
+-rw-r--r-- 1 ftpuser ftpusers 662953 Mar 15 1995 ngwsnc.exe
+-rw-r--r-- 1 ftpuser ftpusers 27283 Sep 18 1993 ni5010.exe
+-rw-r--r-- 1 ftpuser ftpusers 786223 Jul 10 2001 nicid157.exe
+-rw-r--r-- 1 ftpuser ftpusers 761229 Jul 10 2001 nicie157.exe
+-rw-r--r-- 1 ftpuser ftpusers 59300 Jan 15 11:38 nicimig.tgz
+-rw-r--r-- 1 ftpuser ftpusers 6802379 Jan 17 09:35 nims265.tgz
+-rw-r--r-- 1 ftpuser ftpusers 2526415 Jan 31 10:19 nims265.zip
+-rw-r--r-- 1 ftpuser ftpusers 121765 Jan 31 11:14 nims265a.zip
+-rw-r--r-- 1 ftpuser ftpusers 4894646 Jan 14 16:09 nims26l.tgz
+-rw-r--r-- 1 ftpuser ftpusers 2492982 Jan 14 16:05 nims26n.zip
+-rw-r--r-- 1 ftpuser ftpusers 5385381 Feb 27 16:49 nims26sb.z
+-rw-r--r-- 1 ftpuser ftpusers 343052 Nov 8 1999 nims2_1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 12495019 Apr 15 15:54 nims303.tar.z
+-rw-r--r-- 1 ftpuser ftpusers 7563916 Apr 15 15:53 nims303.tgz
+-rw-r--r-- 1 ftpuser ftpusers 7696073 Apr 15 15:54 nims303.zip
+-rw-r--r-- 1 ftpuser ftpusers 1252720 May 23 1997 nip202.exe
+-rw-r--r-- 1 ftpuser ftpusers 1180104 Oct 23 1998 nip203.exe
+-rw-r--r-- 1 ftpuser ftpusers 6212358 Apr 19 1996 nip22b.exe
+-rw-r--r-- 1 ftpuser ftpusers 555990 Jul 9 1996 nip318.exe
+-rw-r--r-- 1 ftpuser ftpusers 69020 Jul 9 1996 nip319.exe
+-rw-r--r-- 1 ftpuser ftpusers 2489203 Nov 2 2001 nipp10a.exe
+-rw-r--r-- 1 ftpuser ftpusers 3753117 Sep 19 2000 nipt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 6369467 Mar 5 1996 nipw22.exe
+-rw-r--r-- 1 ftpuser ftpusers 42316 May 29 1996 nipw2x.exe
+-rw-r--r-- 1 ftpuser ftpusers 4286209 Jun 7 2000 njcl5a.exe
+-rw-r--r-- 1 ftpuser ftpusers 102325 Jun 10 1998 nls212.exe
+-rw-r--r-- 1 ftpuser ftpusers 155414 Jul 24 2000 nlsdll.exe
+-rw-r--r-- 1 ftpuser ftpusers 16952278 May 25 2001 nlslsp6.exe
+-rw-r--r-- 1 ftpuser ftpusers 215729 Jan 4 2000 nlsty2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 1462112 Nov 28 1995 nms002.exe
+-rw-r--r-- 1 ftpuser ftpusers 48618 Mar 8 1994 nmsddf.exe
+-rw-r--r-- 1 ftpuser ftpusers 434841 Nov 15 1994 nmsxp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 28499 Sep 18 1993 nnscpt.exe
+-rw-r--r-- 1 ftpuser ftpusers 88964 Sep 18 1993 nnst40.exe
+-rw-r--r-- 1 ftpuser ftpusers 89092 Sep 18 1993 nnstll.exe
+-rw-r--r-- 1 ftpuser ftpusers 32483 Jul 25 1995 not131.exe
+-rw-r--r-- 1 ftpuser ftpusers 6707094 Oct 12 1998 notes41.exe
+-rw-r--r-- 1 ftpuser ftpusers 4556171 Jun 8 2000 notes51.exe
+-rw-r--r-- 1 ftpuser ftpusers 24900 Sep 18 1993 novadf.exe
+-rw-r--r-- 1 ftpuser ftpusers 30691 Sep 18 1993 np600a.exe
+-rw-r--r-- 1 ftpuser ftpusers 17097790 Aug 2 1999 nppb_1.exe
+-rw-r--r-- 1 ftpuser ftpusers 17097771 Aug 2 1999 nppb_2.exe
+-rw-r--r-- 1 ftpuser ftpusers 633317 Mar 15 16:33 nps15dpa.exe
+-rw-r--r-- 1 ftpuser ftpusers 31183790 Jun 28 09:08 nps15sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 8200267 Sep 10 2001 npsgad01.exe
+-rw-r--r-- 1 ftpuser ftpusers 114902 Apr 12 2001 npsnsapi.exe
+-rw-r--r-- 1 ftpuser ftpusers 615863 Feb 11 15:57 nptr95b.exe
+-rw-r--r-- 1 ftpuser ftpusers 22915 Jun 30 1997 nrsbuild.exe
+-rw-r--r-- 1 ftpuser ftpusers 793469 Jun 23 1997 nrsnt.exe
+-rw-r--r-- 1 ftpuser ftpusers 53586091 Jun 18 1998 nsbgwsp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 455182 Mar 22 1994 nsd004.exe
+-rw-r--r-- 1 ftpuser ftpusers 1964329 Aug 21 1998 nsr511n.zip
+-rw-r--r-- 1 ftpuser ftpusers 1935353 Jun 24 1996 nsrtr51n.zip
+-rw-r--r-- 1 ftpuser ftpusers 93785 Feb 13 13:36 nsschk1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 116845 Jul 30 1997 nsync1.exe
+-rw-r--r-- 1 ftpuser ftpusers 10933860 Sep 16 1999 nt411b.exe
+-rw-r--r-- 1 ftpuser ftpusers 1084753 Oct 26 1998 nt411p1.exe
+-rw-r--r-- 1 ftpuser ftpusers 744586 Apr 6 1999 nt430p2.exe
+-rw-r--r-- 1 ftpuser ftpusers 834534 Jun 22 1999 nt451p1.exe
+-rw-r--r-- 1 ftpuser ftpusers 920405 Mar 23 2000 nt46pt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 4017917 Oct 3 1999 nt46sp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 765887 Aug 11 2000 nt471pt2.exe
+-rw-r--r-- 1 ftpuser ftpusers 448015 Jun 13 2000 nt47pt3.exe
+-rw-r--r-- 1 ftpuser ftpusers 1081217 May 9 07:26 nt480pt5.exe
+-rw-r--r-- 1 ftpuser ftpusers 898400 Nov 6 2001 nt481pt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 291026 Jun 14 14:07 nt483pt2.exe
+-rw-r--r-- 1 ftpuser ftpusers 150230 Nov 19 1998 ntprint.exe
+-rw-r--r-- 1 ftpuser ftpusers 114593 Jul 18 1995 ntwin.exe
+-rw-r--r-- 1 ftpuser ftpusers 28138 Sep 18 1993 nver30.exe
+-rw-r--r-- 1 ftpuser ftpusers 28798 Jan 7 1997 nw3dfs.exe
+-rw-r--r-- 1 ftpuser ftpusers 24257 Jan 7 1997 nw4dfs.exe
+-rw-r--r-- 1 ftpuser ftpusers 80377034 Nov 13 2000 nw4sp9.exe
+-rw-r--r-- 1 ftpuser ftpusers 866224 Aug 27 2001 nw4wsock.exe
+-rw-r--r-- 1 ftpuser ftpusers 158210659 Dec 20 2000 nw50sp6a.exe
+-rw-r--r-- 1 ftpuser ftpusers 490599 Jul 23 2001 nw51fs1.exe
+-rw-r--r-- 1 ftpuser ftpusers 684981 Feb 17 2000 nw51inst.exe
+-rw-r--r-- 1 ftpuser ftpusers 513640 Aug 21 2001 nw51nrm1.exe
+-rw-r--r-- 1 ftpuser ftpusers 294037836 Jul 24 2001 nw51sp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 300006242 Feb 25 11:26 nw51sp4.exe
+-rw-r--r-- 1 ftpuser ftpusers 332610 Apr 27 2000 nw51upd1.exe
+-rw-r--r-- 1 ftpuser ftpusers 3250529 Jun 24 14:54 nw56up1.exe
+-rw-r--r-- 1 ftpuser ftpusers 38435 Sep 9 1999 nw5nss.exe
+-rw-r--r-- 1 ftpuser ftpusers 251511 Feb 17 2000 nw5nwip.exe
+-rw-r--r-- 1 ftpuser ftpusers 169896 May 16 2000 nw5psrv2.exe
+-rw-r--r-- 1 ftpuser ftpusers 378831 Jun 20 2000 nw5tcp.exe
+-rw-r--r-- 1 ftpuser ftpusers 1533365 Mar 22 16:33 nw6nss1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 633339 Oct 22 2001 nw6sms1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 237785656 Mar 6 17:15 nw6sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 568253661 Mar 11 12:19 nw6sp1ef.exe
+-rw-r--r-- 1 ftpuser ftpusers 567439767 Mar 11 12:59 nw6sp1ef56.exe
+-rw-r--r-- 1 ftpuser ftpusers 566604272 Mar 22 12:23 nw6sp1eg.exe
+-rw-r--r-- 1 ftpuser ftpusers 566458792 Mar 22 13:02 nw6sp1ei.exe
+-rw-r--r-- 1 ftpuser ftpusers 566528467 Mar 11 10:57 nw6sp1ep.exe
+-rw-r--r-- 1 ftpuser ftpusers 567333526 Mar 22 16:05 nw6sp1er.exe
+-rw-r--r-- 1 ftpuser ftpusers 565955338 Mar 13 16:55 nw6sp1es.exe
+-rw-r--r-- 1 ftpuser ftpusers 1344552 Mar 23 1999 nwadmnp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 478371 May 10 1995 nwc001.exe
+-rw-r--r-- 1 ftpuser ftpusers 251557 Feb 24 1995 nwc002.exe
+-rw-r--r-- 1 ftpuser ftpusers 1598884 Jan 31 1996 nwc201.exe
+-rw-r--r-- 1 ftpuser ftpusers 1524102 Nov 22 1995 nwc202.exe
+-rw-r--r-- 1 ftpuser ftpusers 1328082 Jan 22 1998 nwc206.exe
+-rw-r--r-- 1 ftpuser ftpusers 1382188 Nov 18 1996 nwc207.exe
+-rw-r--r-- 1 ftpuser ftpusers 547655 Oct 24 1996 nwc208.exe
+-rw-r--r-- 1 ftpuser ftpusers 29587 Aug 12 1997 nwc2tp.txt
+-rw-r--r-- 1 ftpuser ftpusers 21386 Sep 18 1993 nwc386.exe
+-rw-r--r-- 1 ftpuser ftpusers 102446 Oct 5 1994 nwcdll.exe
+-rw-r--r-- 1 ftpuser ftpusers 33443 Feb 27 1996 nwcinf.exe
+-rw-r--r-- 1 ftpuser ftpusers 22331 Sep 11 1998 nwcmod.exe
+-rw-r--r-- 1 ftpuser ftpusers 71514 Sep 20 1995 nwcncs.exe
+-rw-r--r-- 1 ftpuser ftpusers 37424 Jul 11 1997 nwcppp.exe
+-rw-r--r-- 1 ftpuser ftpusers 36603464 Mar 13 2000 nwcssp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 170397 Mar 23 2000 nwcsupd1.exe
+-rw-r--r-- 1 ftpuser ftpusers 367734 Feb 14 1995 nwcwin.exe
+-rw-r--r-- 1 ftpuser ftpusers 367002 May 22 1998 nwcwrt.exe
+-rw-r--r-- 1 ftpuser ftpusers 77941 Dec 16 1996 nwda01.exe
+-rw-r--r-- 1 ftpuser ftpusers 147838 May 8 12:21 nwftpd6.exe
+-rw-r--r-- 1 ftpuser ftpusers 128211 Jan 29 15:30 nwipadm4.exe
+-rw-r--r-- 1 ftpuser ftpusers 571623 Nov 1 1995 nwl11e.exe
+-rw-r--r-- 1 ftpuser ftpusers 579046 Nov 1 1995 nwl11f.exe
+-rw-r--r-- 1 ftpuser ftpusers 585907 Nov 1 1995 nwl11g.exe
+-rw-r--r-- 1 ftpuser ftpusers 576676 Nov 1 1995 nwl11i.exe
+-rw-r--r-- 1 ftpuser ftpusers 579137 Nov 1 1995 nwl11s.exe
+-rw-r--r-- 1 ftpuser ftpusers 184137 Dec 13 1995 nwltid.exe
+-rw-r--r-- 1 ftpuser ftpusers 13639159 Apr 9 1999 nwmac.exe
+-rw-r--r-- 1 ftpuser ftpusers 2264037 Mar 23 1999 nwmp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 16902888 Jun 15 2001 nwovly2.exe
+-rw-r--r-- 1 ftpuser ftpusers 2536221 Apr 2 1997 nwpa300.exe
+-rw-r--r-- 1 ftpuser ftpusers 155727 May 7 2001 nwpa5.exe
+-rw-r--r-- 1 ftpuser ftpusers 254835 Dec 7 2001 nwpapt2a.exe
+-rw-r--r-- 1 ftpuser ftpusers 26440 Nov 15 1993 nwparr.exe
+-rw-r--r-- 1 ftpuser ftpusers 1341903 Jun 9 1999 nwpaup1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 7763041 Feb 27 1997 nws25b.exe
+-rw-r--r-- 1 ftpuser ftpusers 73306 Mar 11 1999 nwsaahpr.exe
+-rw-r--r-- 1 ftpuser ftpusers 12091868 Feb 29 2000 nwsb41wa.exe
+-rw-r--r-- 1 ftpuser ftpusers 38819 Aug 11 1999 nwsp2aai.exe
+-rw-r--r-- 1 ftpuser ftpusers 287681 Feb 4 2000 nwsso.exe
+-rw-r--r-- 1 ftpuser ftpusers 112641 Feb 24 2000 nwtape1.exe
+-rw-r--r-- 1 ftpuser ftpusers 66111 Nov 15 1993 nwtlg.exe
+-rw-r--r-- 1 ftpuser ftpusers 126883 Jun 16 1995 o31mci.exe
+-rw-r--r-- 1 ftpuser ftpusers 73911 Jul 25 1995 o4crtl.exe
+-rw-r--r-- 1 ftpuser ftpusers 4957532 Apr 27 1999 odbcbeta.exe
+-rw-r--r-- 1 ftpuser ftpusers 6488080 Nov 8 2001 odemandb.exe
+-rw-r--r-- 1 ftpuser ftpusers 671132 Jul 28 1999 odi33g.exe
+-rw-r--r-- 1 ftpuser ftpusers 409920 Jul 30 1997 odiwan1.exe
+-rw-r--r-- 1 ftpuser ftpusers 48296 Jul 18 1995 of31pt.exe
+-rw-r--r-- 1 ftpuser ftpusers 111219 Sep 18 1993 os2p1.exe
+-rw-r--r-- 1 ftpuser ftpusers 610164 Dec 18 1998 os2pt2.exe
+-rw-r--r-- 1 ftpuser ftpusers 896477 Nov 26 1996 os2u1.exe
+-rw-r--r-- 1 ftpuser ftpusers 4229434 May 30 2000 os4pt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 4227811 Mar 2 2001 os5pt2a.exe
+-rw-r--r-- 1 ftpuser ftpusers 216072 Sep 18 1993 othdrv.exe
+-rw-r--r-- 1 ftpuser ftpusers 66394 Dec 4 1996 ovvmdl.exe
+-rw-r--r-- 1 ftpuser ftpusers 26153 Oct 25 1996 p1000.exe
+-rw-r--r-- 1 ftpuser ftpusers 242785 Jan 3 1995 p10g05.exe
+-rw-r--r-- 1 ftpuser ftpusers 242514 Jan 3 1995 p10i05.exe
+-rw-r--r-- 1 ftpuser ftpusers 242647 Jan 3 1995 p10s05.exe
+-rw-r--r-- 1 ftpuser ftpusers 33893 May 12 1995 p2scsi.exe
+-rw-r--r-- 1 ftpuser ftpusers 659891 May 11 1999 pager1.exe
+-rw-r--r-- 1 ftpuser ftpusers 50002 Sep 18 1993 pat301.exe
+-rw-r--r-- 1 ftpuser ftpusers 50015 Sep 18 1993 pat303.exe
+-rw-r--r-- 1 ftpuser ftpusers 49975 Sep 18 1993 pat304.exe
+-rw-r--r-- 1 ftpuser ftpusers 49878 Sep 18 1993 pat306.exe
+-rw-r--r-- 1 ftpuser ftpusers 29863 Sep 18 1993 pat311.exe
+-rw-r--r-- 1 ftpuser ftpusers 49888 Sep 18 1993 pat312.exe
+-rw-r--r-- 1 ftpuser ftpusers 49823 Sep 18 1993 pat314.exe
+-rw-r--r-- 1 ftpuser ftpusers 33034 Sep 18 1993 pat315.exe
+-rw-r--r-- 1 ftpuser ftpusers 49900 Sep 18 1993 pat317.exe
+-rw-r--r-- 1 ftpuser ftpusers 49858 Sep 18 1993 pat321.exe
+-rw-r--r-- 1 ftpuser ftpusers 49901 Sep 18 1993 pat323.exe
+-rw-r--r-- 1 ftpuser ftpusers 50232 Sep 18 1993 pat326.exe
+-rw-r--r-- 1 ftpuser ftpusers 49842 Sep 18 1993 pat334.exe
+-rw-r--r-- 1 ftpuser ftpusers 49930 Sep 18 1993 pat354.exe
+-rw-r--r-- 1 ftpuser ftpusers 30322 Sep 18 1993 patman.exe
+-rw-r--r-- 1 ftpuser ftpusers 35789 Sep 18 1993 paudfx.exe
+-rw-r--r-- 1 ftpuser ftpusers 565974 Jul 20 1998 pbm21y2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 63237 Jun 15 1994 pburst.exe
+-rw-r--r-- 1 ftpuser ftpusers 35522 Sep 18 1993 pcn22x.exe
+-rw-r--r-- 1 ftpuser ftpusers 25266 Sep 18 1993 pcn23x.exe
+-rw-r--r-- 1 ftpuser ftpusers 46823 Sep 18 1993 pcn2pa.exe
+-rw-r--r-- 1 ftpuser ftpusers 30816 Sep 18 1993 pcnscs.exe
+-rw-r--r-- 1 ftpuser ftpusers 22801 Sep 18 1993 pdf.exe
+-rw-r--r-- 1 ftpuser ftpusers 38018 Sep 18 1993 pdf311.exe
+-rw-r--r-- 1 ftpuser ftpusers 8552350 Aug 27 2001 pdlckcmp.exe
+-rw-r--r-- 1 ftpuser ftpusers 699150 Jan 22 1997 perfectf.exe
+-rw-r--r-- 1 ftpuser ftpusers 214597 Jun 7 2000 pfar6.exe
+-rw-r--r-- 1 ftpuser ftpusers 26618 Sep 18 1993 pfix1.exe
+-rw-r--r-- 1 ftpuser ftpusers 26734 Sep 18 1993 pfix3.exe
+-rw-r--r-- 1 ftpuser ftpusers 23435 Jul 18 1995 pifoff.exe
+-rw-r--r-- 1 ftpuser ftpusers 70799 Aug 26 1999 pkernel.exe
+-rw-r--r-- 1 ftpuser ftpusers 252312 Aug 12 1999 pkis.pdf
+-rw-r--r-- 1 ftpuser ftpusers 772450 Feb 8 2000 pkisnmas.exe
+-rw-r--r-- 1 ftpuser ftpusers 63891 Sep 11 1995 plpd8.exe
+-rw-r--r-- 1 ftpuser ftpusers 212389 Mar 28 12:17 plpdsoc2.exe
+-rw-r--r-- 1 ftpuser ftpusers 181777 Dec 13 1995 pnwtid.exe
+-rw-r--r-- 1 ftpuser ftpusers 186437 Nov 17 1995 pnxtfx.exe
+-rw-r--r-- 1 ftpuser ftpusers 4463887 Jan 3 2001 preds8a.exe
+-rw-r--r-- 1 ftpuser ftpusers 75026 Sep 18 1993 pro10.exe
+-rw-r--r-- 1 ftpuser ftpusers 28781 Nov 1 1995 prog.exe
+-rw-r--r-- 1 ftpuser ftpusers 23802 Sep 18 1993 propth.exe
+-rw-r--r-- 1 ftpuser ftpusers 25129 Jan 29 1996 prt312.exe
+-rw-r--r-- 1 ftpuser ftpusers 31193 Sep 18 1993 prtime.exe
+-rw-r--r-- 1 ftpuser ftpusers 130827 Jul 20 1995 prupc.exe
+-rw-r--r-- 1 ftpuser ftpusers 34893 Sep 18 1993 ps110.exe
+-rw-r--r-- 1 ftpuser ftpusers 25963 Sep 18 1993 ps2286.exe
+-rw-r--r-- 1 ftpuser ftpusers 24576 Sep 18 1993 ps22is.exe
+-rw-r--r-- 1 ftpuser ftpusers 42925 Sep 18 1993 ps2311.exe
+-rw-r--r-- 1 ftpuser ftpusers 29867 Sep 18 1993 ps2386.exe
+-rw-r--r-- 1 ftpuser ftpusers 28205 Sep 18 1993 ps2cmb.exe
+-rw-r--r-- 1 ftpuser ftpusers 23372 Sep 18 1993 ps2esd.exe
+-rw-r--r-- 1 ftpuser ftpusers 24336 Sep 18 1993 ps2fx.exe
+-rw-r--r-- 1 ftpuser ftpusers 76207 Sep 18 1993 ps2isa.exe
+-rw-r--r-- 1 ftpuser ftpusers 23955 Sep 18 1993 ps2m57.exe
+-rw-r--r-- 1 ftpuser ftpusers 36351 Dec 14 1993 ps2opt.exe
+-rw-r--r-- 1 ftpuser ftpusers 162367 Jun 30 1995 ps3x02.exe
+-rw-r--r-- 1 ftpuser ftpusers 85566 Jan 23 1996 ps4x03.exe
+-rw-r--r-- 1 ftpuser ftpusers 172677 Oct 24 2001 psrvr112.exe
+-rw-r--r-- 1 ftpuser ftpusers 52324 Sep 18 1993 ptf286.exe
+-rw-r--r-- 1 ftpuser ftpusers 112633 Sep 18 1993 ptf350.exe
+-rw-r--r-- 1 ftpuser ftpusers 48074 Sep 18 1993 ptf374.exe
+-rw-r--r-- 1 ftpuser ftpusers 39025 Sep 18 1993 ptf378.exe
+-rw-r--r-- 1 ftpuser ftpusers 30600 Sep 18 1993 ptf380.exe
+-rw-r--r-- 1 ftpuser ftpusers 525519 Mar 25 1994 ptf410.exe
+-rw-r--r-- 1 ftpuser ftpusers 501986 Sep 29 1993 ptf411.exe
+-rw-r--r-- 1 ftpuser ftpusers 350294 Sep 29 1993 ptf412.exe
+-rw-r--r-- 1 ftpuser ftpusers 473981 Sep 29 1993 ptf413.exe
+-rw-r--r-- 1 ftpuser ftpusers 480777 Sep 29 1993 ptf414.exe
+-rw-r--r-- 1 ftpuser ftpusers 488223 Sep 29 1993 ptf415.exe
+-rw-r--r-- 1 ftpuser ftpusers 147005 Oct 22 1993 ptf424.exe
+-rw-r--r-- 1 ftpuser ftpusers 109320 Aug 14 1995 ptf425.exe
+-rw-r--r-- 1 ftpuser ftpusers 109064 Oct 18 1993 ptf426.exe
+-rw-r--r-- 1 ftpuser ftpusers 292097 Oct 7 1994 ptf437.exe
+-rw-r--r-- 1 ftpuser ftpusers 464842 Apr 12 1994 ptf569.exe
+-rw-r--r-- 1 ftpuser ftpusers 453054 Nov 16 1994 pu3x01.exe
+-rw-r--r-- 1 ftpuser ftpusers 553603 May 2 1995 pu4x03.exe
+-rw-r--r-- 1 ftpuser ftpusers 280505 May 29 17:29 pwdsnc1.exe
+-rw-r--r-- 1 ftpuser ftpusers 758411 May 31 11:45 pxy031.exe
+-rw-r--r-- 1 ftpuser ftpusers 785651 Aug 31 2000 pxyauth.exe
+-rw-r--r-- 1 ftpuser ftpusers 25270 Nov 1 1995 qa.exe
+-rw-r--r-- 1 ftpuser ftpusers 22674 Jul 25 1995 qaos2.exe
+-rw-r--r-- 1 ftpuser ftpusers 21421 Jul 18 1995 qkinst.exe
+-rw-r--r-- 1 ftpuser ftpusers 390862 Dec 4 1995 qlfix.exe
+-rw-r--r-- 1 ftpuser ftpusers 21028 Oct 5 1995 quest.exe
+-rw-r--r-- 1 ftpuser ftpusers 13847723 Nov 23 1998 r16524br.exe
+-rw-r--r-- 1 ftpuser ftpusers 15367885 Nov 23 1998 r16524ce.exe
+-rw-r--r-- 1 ftpuser ftpusers 13974046 Nov 23 1998 r16524cf.exe
+-rw-r--r-- 1 ftpuser ftpusers 14636368 Nov 23 1998 r16524cs.exe
+-rw-r--r-- 1 ftpuser ftpusers 14606815 Nov 23 1998 r16524ct.exe
+-rw-r--r-- 1 ftpuser ftpusers 14396472 Nov 23 1998 r16524cz.exe
+-rw-r--r-- 1 ftpuser ftpusers 14526983 Nov 23 1998 r16524de.exe
+-rw-r--r-- 1 ftpuser ftpusers 13996151 Nov 23 1998 r16524dk.exe
+-rw-r--r-- 1 ftpuser ftpusers 14083999 Nov 24 1998 r16524es.exe
+-rw-r--r-- 1 ftpuser ftpusers 14036283 Nov 24 1998 r16524fr.exe
+-rw-r--r-- 1 ftpuser ftpusers 14168496 Nov 24 1998 r16524it.exe
+-rw-r--r-- 1 ftpuser ftpusers 15194180 Nov 30 1998 r16524jp.exe
+-rw-r--r-- 1 ftpuser ftpusers 14717983 Nov 24 1998 r16524kr.exe
+-rw-r--r-- 1 ftpuser ftpusers 13957605 Nov 24 1998 r16524ma.exe
+-rw-r--r-- 1 ftpuser ftpusers 13018097 Nov 24 1998 r16524nl.exe
+-rw-r--r-- 1 ftpuser ftpusers 14282386 Nov 24 1998 r16524no.exe
+-rw-r--r-- 1 ftpuser ftpusers 14592999 Nov 24 1998 r16524oz.exe
+-rw-r--r-- 1 ftpuser ftpusers 14683051 Nov 24 1998 r16524pl.exe
+-rw-r--r-- 1 ftpuser ftpusers 13868667 Nov 24 1998 r16524ru.exe
+-rw-r--r-- 1 ftpuser ftpusers 14075816 Nov 24 1998 r16524su.exe
+-rw-r--r-- 1 ftpuser ftpusers 14090792 Nov 24 1998 r16524sv.exe
+-rw-r--r-- 1 ftpuser ftpusers 14598010 Nov 24 1998 r16524uk.exe
+-rw-r--r-- 1 ftpuser ftpusers 14633171 Nov 23 1998 r16524us.exe
+-rw-r--r-- 1 ftpuser ftpusers 13892746 Oct 8 1999 r16525br.exe
+-rw-r--r-- 1 ftpuser ftpusers 15412960 Oct 8 1999 r16525ce.exe
+-rw-r--r-- 1 ftpuser ftpusers 14019075 Oct 8 1999 r16525cf.exe
+-rw-r--r-- 1 ftpuser ftpusers 14681320 Oct 8 1999 r16525cs.exe
+-rw-r--r-- 1 ftpuser ftpusers 14651741 Oct 8 1999 r16525ct.exe
+-rw-r--r-- 1 ftpuser ftpusers 14443408 Oct 8 1999 r16525cz.exe
+-rw-r--r-- 1 ftpuser ftpusers 14572069 Aug 24 1999 r16525de.exe
+-rw-r--r-- 1 ftpuser ftpusers 14041141 Oct 8 1999 r16525dk.exe
+-rw-r--r-- 1 ftpuser ftpusers 14129003 Oct 8 1999 r16525es.exe
+-rw-r--r-- 1 ftpuser ftpusers 14081224 Oct 8 1999 r16525fr.exe
+-rw-r--r-- 1 ftpuser ftpusers 14213472 Oct 8 1999 r16525it.exe
+-rw-r--r-- 1 ftpuser ftpusers 15239217 Oct 8 1999 r16525jp.exe
+-rw-r--r-- 1 ftpuser ftpusers 14762877 Oct 8 1999 r16525kr.exe
+-rw-r--r-- 1 ftpuser ftpusers 14004580 Oct 8 1999 r16525ma.exe
+-rw-r--r-- 1 ftpuser ftpusers 14520305 Oct 8 1999 r16525nl.exe
+-rw-r--r-- 1 ftpuser ftpusers 14327373 Oct 8 1999 r16525no.exe
+-rw-r--r-- 1 ftpuser ftpusers 14638087 Oct 8 1999 r16525oz.exe
+-rw-r--r-- 1 ftpuser ftpusers 14730025 Oct 8 1999 r16525pl.exe
+-rw-r--r-- 1 ftpuser ftpusers 13915653 Oct 8 1999 r16525ru.exe
+-rw-r--r-- 1 ftpuser ftpusers 14120807 Oct 8 1999 r16525su.exe
+-rw-r--r-- 1 ftpuser ftpusers 14135776 Oct 8 1999 r16525sv.exe
+-rw-r--r-- 1 ftpuser ftpusers 14643087 Oct 8 1999 r16525uk.exe
+-rw-r--r-- 1 ftpuser ftpusers 14678258 Aug 24 1999 r16525us.exe
+-rw-r--r-- 1 ftpuser ftpusers 34195974 Nov 20 1998 r524east.exe
+-rw-r--r-- 1 ftpuser ftpusers 29934184 Nov 21 1998 r524kcc.exe
+-rw-r--r-- 1 ftpuser ftpusers 40546603 Nov 21 1998 r524mult.exe
+-rw-r--r-- 1 ftpuser ftpusers 33377124 Nov 21 1998 r524scan.exe
+-rw-r--r-- 1 ftpuser ftpusers 17133749 Nov 21 1998 r524us.exe
+-rw-r--r-- 1 ftpuser ftpusers 20919099 Nov 21 1998 r524usde.exe
+-rw-r--r-- 1 ftpuser ftpusers 21776910 Dec 21 1998 r524usjp.exe
+-rw-r--r-- 1 ftpuser ftpusers 33695357 Oct 11 1999 r525east.exe
+-rw-r--r-- 1 ftpuser ftpusers 29387389 Oct 11 1999 r525kcc.exe
+-rw-r--r-- 1 ftpuser ftpusers 39896412 Oct 11 1999 r525mult.exe
+-rw-r--r-- 1 ftpuser ftpusers 32843372 Oct 11 1999 r525scan.exe
+-rw-r--r-- 1 ftpuser ftpusers 18205814 Oct 11 1999 r525us.exe
+-rw-r--r-- 1 ftpuser ftpusers 20711743 Oct 11 1999 r525usde.exe
+-rw-r--r-- 1 ftpuser ftpusers 19744627 Oct 14 1999 r525usjp.exe
+-rw-r--r-- 1 ftpuser ftpusers 21883384 Feb 25 1999 r551en.exe
+-rw-r--r-- 1 ftpuser ftpusers 38653860 Feb 26 1999 r551mult.exe
+-rw-r--r-- 1 ftpuser ftpusers 38136537 Feb 25 1999 r551scan.exe
+-rw-r--r-- 1 ftpuser ftpusers 37890181 Oct 19 1999 r552mult.exe
+-rw-r--r-- 1 ftpuser ftpusers 37404535 Oct 19 1999 r552scan.exe
+-rw-r--r-- 1 ftpuser ftpusers 22183381 Feb 11 2000 r553aen.exe
+-rw-r--r-- 1 ftpuser ftpusers 32216751 Feb 11 2000 r553aest.exe
+-rw-r--r-- 1 ftpuser ftpusers 24925427 Feb 11 2000 r553ajp.exe
+-rw-r--r-- 1 ftpuser ftpusers 27749699 Feb 11 2000 r553akcc.exe
+-rw-r--r-- 1 ftpuser ftpusers 38006860 Feb 11 2000 r553amlt.exe
+-rw-r--r-- 1 ftpuser ftpusers 37454601 Feb 11 2000 r553ascn.exe
+-rw-r--r-- 1 ftpuser ftpusers 87518 Apr 6 1998 rad102.exe
+-rw-r--r-- 1 ftpuser ftpusers 260651 Nov 23 1998 rad104.exe
+-rw-r--r-- 1 ftpuser ftpusers 118100 Mar 4 16:09 radatr4.exe
+-rw-r--r-- 1 ftpuser ftpusers 575303 Feb 28 1997 ramac.exe
+-rw-r--r-- 1 ftpuser ftpusers 66500 Jun 7 1995 rbuild.exe
+-rw-r--r-- 1 ftpuser ftpusers 23539 Feb 27 1998 rdmsg0.exe
+-rw-r--r-- 1 ftpuser ftpusers 91403 Apr 3 2000 revfhrft.exe
+-rw-r--r-- 1 ftpuser ftpusers 138359 Jul 27 2001 rinstall.exe
+-rw-r--r-- 1 ftpuser ftpusers 211615 Nov 4 1993 ripsap.exe
+-rw-r--r-- 1 ftpuser ftpusers 192641 Sep 18 1993 rlit92.exe
+-rw-r--r-- 1 ftpuser ftpusers 155252 Sep 18 1993 rlit93.exe
+-rw-r--r-- 1 ftpuser ftpusers 780218 Jul 18 1995 rofwin.exe
+-rw-r--r-- 1 ftpuser ftpusers 36120 Sep 18 1993 routez.exe
+-rw-r--r-- 1 ftpuser ftpusers 96684 Sep 18 1993 routfx.exe
+-rw-r--r-- 1 ftpuser ftpusers 141605 Oct 5 1998 rplkt5.exe
+-rw-r--r-- 1 ftpuser ftpusers 72596 May 11 1994 rsync1.exe
+-rw-r--r-- 1 ftpuser ftpusers 23294 Sep 18 1993 rxnet.exe
+-rw-r--r-- 1 ftpuser ftpusers 48534006 Mar 28 2001 rzfd3sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 39313 Jun 16 1994 saa005.exe
+-rw-r--r-- 1 ftpuser ftpusers 534003 Aug 16 2001 saa008.exe
+-rw-r--r-- 1 ftpuser ftpusers 80219 Aug 11 1994 saa010.exe
+-rw-r--r-- 1 ftpuser ftpusers 142620 Sep 1 1994 saa012.exe
+-rw-r--r-- 1 ftpuser ftpusers 943059 Aug 16 2001 saa023.exe
+-rw-r--r-- 1 ftpuser ftpusers 154805 Dec 24 1996 saa031.exe
+-rw-r--r-- 1 ftpuser ftpusers 4659719 Aug 16 2001 saa20040.exe
+-rw-r--r-- 1 ftpuser ftpusers 2550556 Aug 16 2001 saa21030.exe
+-rw-r--r-- 1 ftpuser ftpusers 63688405 Aug 15 2001 saa22010.exe
+-rw-r--r-- 1 ftpuser ftpusers 9396094 Aug 15 2001 saa2210e.exe
+-rw-r--r-- 1 ftpuser ftpusers 10338946 Aug 15 2001 saa30020.exe
+-rw-r--r-- 1 ftpuser ftpusers 9315931 Aug 15 2001 saa40020.exe
+-rw-r--r-- 1 ftpuser ftpusers 169062 Jun 29 2000 saa4pt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 20269 Jun 27 1995 saamic.exe
+-rw-r--r-- 1 ftpuser ftpusers 1646 Jun 3 1998 saapatch.txt
+-rw-r--r-- 1 ftpuser ftpusers 32233 Nov 30 1995 saarot.exe
+-rw-r--r-- 1 ftpuser ftpusers 29347 Aug 3 1995 saaupg.exe
+-rw-r--r-- 1 ftpuser ftpusers 282396 Jun 26 1996 sback6.exe
+-rw-r--r-- 1 ftpuser ftpusers 376293 Jun 7 2001 sbcon1.exe
+-rw-r--r-- 1 ftpuser ftpusers 564045 Jul 20 1998 sbm21y2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 8341393 Mar 2 2001 sbs5pt2a.exe
+-rw-r--r-- 1 ftpuser ftpusers 244604 Dec 5 1997 schcmp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 151673 Aug 12 1999 scmddoc.exe
+-rw-r--r-- 1 ftpuser ftpusers 167290 May 4 2001 scmdflt.exe
+-rw-r--r-- 1 ftpuser ftpusers 40595 Sep 18 1993 sec286.exe
+-rw-r--r-- 1 ftpuser ftpusers 29661 May 25 1994 secdoc.exe
+-rw-r--r-- 1 ftpuser ftpusers 310609 Sep 18 1993 secdos.exe
+-rw-r--r-- 1 ftpuser ftpusers 7039614 May 26 2000 secexp64.01
+-rw-r--r-- 1 ftpuser ftpusers 5016153 Aug 10 2000 secexp64.z
+-rw-r--r-- 1 ftpuser ftpusers 167904 Nov 15 1993 seclog.exe
+-rw-r--r-- 1 ftpuser ftpusers 632669 Sep 18 1993 secnns.exe
+-rw-r--r-- 1 ftpuser ftpusers 449590 Sep 18 1993 secprn.exe
+-rw-r--r-- 1 ftpuser ftpusers 322007 Sep 18 1993 secsys.exe
+-rw-r--r-- 1 ftpuser ftpusers 7351040 May 26 2000 secus64.01
+-rw-r--r-- 1 ftpuser ftpusers 5457221 Aug 10 2000 secus64.z
+-rw-r--r-- 1 ftpuser ftpusers 510733 Sep 18 1993 secut1.exe
+-rw-r--r-- 1 ftpuser ftpusers 556873 Sep 18 1993 secut2.exe
+-rw-r--r-- 1 ftpuser ftpusers 431691 Sep 18 1993 secut3.exe
+-rw-r--r-- 1 ftpuser ftpusers 134525 Aug 29 2001 servinst.exe
+-rw-r--r-- 1 ftpuser ftpusers 367009 May 25 1996 setdoc.exe
+-rw-r--r-- 1 ftpuser ftpusers 24541 Sep 18 1993 setfx.exe
+-rw-r--r-- 1 ftpuser ftpusers 56904 Sep 18 1993 setupc.exe
+-rw-r--r-- 1 ftpuser ftpusers 75076 Jul 21 1997 sftpt2.exe
+-rw-r--r-- 1 ftpuser ftpusers 67817 Sep 18 1993 sftutl.exe
+-rw-r--r-- 1 ftpuser ftpusers 49345 Sep 2 1999 showenv1.exe
+-rw-r--r-- 1 ftpuser ftpusers 25774 Nov 6 1997 silent.exe
+-rw-r--r-- 1 ftpuser ftpusers 181878 Apr 23 09:38 slp107g.exe
+-rw-r--r-- 1 ftpuser ftpusers 184680 Aug 28 2001 slpinsp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 59254 Sep 18 1993 smfsel.exe
+-rw-r--r-- 1 ftpuser ftpusers 2747104 Jan 31 1997 smsup6.exe
+-rw-r--r-- 1 ftpuser ftpusers 131884 Sep 25 1996 smt121.exe
+-rw-r--r-- 1 ftpuser ftpusers 105031 Nov 10 1993 smt171.exe
+-rw-r--r-- 1 ftpuser ftpusers 1764462 May 24 1996 smtos2.exe
+-rw-r--r-- 1 ftpuser ftpusers 322954 Oct 11 1996 smtp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 441783 May 19 1997 smtp2.exe
+-rw-r--r-- 1 ftpuser ftpusers 2862615 Sep 19 1997 smtp3.exe
+-rw-r--r-- 1 ftpuser ftpusers 2882529 Jul 14 1998 smtp4.exe
+-rw-r--r-- 1 ftpuser ftpusers 53164 Aug 1 1995 smtslp.exe
+-rw-r--r-- 1 ftpuser ftpusers 298148 Jun 4 1996 sna31a.exe
+-rw-r--r-- 1 ftpuser ftpusers 148302 Mar 7 10:28 snmpfix.exe
+-rw-r--r-- 1 ftpuser ftpusers 147265 Jul 20 1995 snupd2.exe
+-rw-r--r-- 1 ftpuser ftpusers 163195 Jul 20 1995 snupdu.exe
+-rw-r--r-- 1 ftpuser ftpusers 12675957 Jul 14 2000 sp1_ce.02
+-rw-r--r-- 1 ftpuser ftpusers 9547499 Apr 25 2000 sp1_edir.02
+-rw-r--r-- 1 ftpuser ftpusers 230035 Sep 20 1999 sp3to3a.exe
+-rw-r--r-- 1 ftpuser ftpusers 74372 Feb 25 1998 spanish.exe
+-rw-r--r-- 1 ftpuser ftpusers 5323860 May 23 1996 srapi.exe
+-rw-r--r-- 1 ftpuser ftpusers 38967 Nov 8 1996 srout4.exe
+-rw-r--r-- 1 ftpuser ftpusers 812158 Jul 24 2000 srvinst.exe
+-rw-r--r-- 1 ftpuser ftpusers 54912 Aug 23 1996 srvmn1.exe
+-rw-r--r-- 1 ftpuser ftpusers 38078 Jun 30 1995 stampd.exe
+-rw-r--r-- 1 ftpuser ftpusers 126042 Feb 21 11:15 strmft1.exe
+-rw-r--r-- 1 ftpuser ftpusers 250945 Aug 23 2000 strtl8a.exe
+-rw-r--r-- 1 ftpuser ftpusers 36114 Mar 8 1999 stufkey5.exe
+-rw-r--r-- 1 ftpuser ftpusers 52344 Feb 11 1998 stylbr.exe
+-rw-r--r-- 1 ftpuser ftpusers 50098 Apr 14 1997 stylct.exe
+-rw-r--r-- 1 ftpuser ftpusers 35645 Feb 11 1998 styles.exe
+-rw-r--r-- 1 ftpuser ftpusers 37446 Feb 11 1998 stylfr.exe
+-rw-r--r-- 1 ftpuser ftpusers 77671 Apr 14 1997 stylha.exe
+-rw-r--r-- 1 ftpuser ftpusers 36626 Feb 12 1998 stylit.exe
+-rw-r--r-- 1 ftpuser ftpusers 55674 Apr 16 1997 stylsc.exe
+-rw-r--r-- 1 ftpuser ftpusers 37297 Dec 12 1995 supwin.exe
+-rw-r--r-- 1 ftpuser ftpusers 186171 Sep 18 1993 sys233.exe
+-rw-r--r-- 1 ftpuser ftpusers 159178 Sep 18 1993 sys368.exe
+-rw-r--r-- 1 ftpuser ftpusers 161608 May 10 1995 sys376.exe
+-rw-r--r-- 1 ftpuser ftpusers 61914 Sep 18 1993 syschk.exe
+-rw-r--r-- 1 ftpuser ftpusers 81300 Sep 18 1993 syslod.exe
+-rw-r--r-- 1 ftpuser ftpusers 418576 Jul 14 1997 tabnd2a.exe
+-rw-r--r-- 1 ftpuser ftpusers 9831871 Jan 13 1997 tambt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 172843 May 4 1998 tback3.exe
+-rw-r--r-- 1 ftpuser ftpusers 58235 Sep 1 1998 tbox7.exe
+-rw-r--r-- 1 ftpuser ftpusers 174964 May 4 1998 tcopy2.exe
+-rw-r--r-- 1 ftpuser ftpusers 781603 May 18 1998 tcp312.exe
+-rw-r--r-- 1 ftpuser ftpusers 1223056 Aug 1 2001 tcp542u.exe
+-rw-r--r-- 1 ftpuser ftpusers 1124221 Apr 10 08:49 tcp553v.exe
+-rw-r--r-- 1 ftpuser ftpusers 1221375 May 24 16:03 tcp590s.exe
+-rw-r--r-- 1 ftpuser ftpusers 315088 Apr 15 10:50 tcp604m.exe
+-rw-r--r-- 1 ftpuser ftpusers 1118361 May 7 11:27 tcp604s.exe
+-rw-r--r-- 1 ftpuser ftpusers 6902826 Feb 9 1998 tel01a.exe
+-rw-r--r-- 1 ftpuser ftpusers 97084 Jan 21 1998 tel40d.exe
+-rw-r--r-- 1 ftpuser ftpusers 33888 Sep 18 1993 tim286.exe
+-rw-r--r-- 1 ftpuser ftpusers 20453 Sep 18 1993 tim386.exe
+-rw-r--r-- 1 ftpuser ftpusers 105037 Nov 2 1998 timefx.exe
+-rw-r--r-- 1 ftpuser ftpusers 31521 Mar 29 1994 tokws.exe
+-rw-r--r-- 1 ftpuser ftpusers 123321 Jan 25 2001 trpmon.exe
+-rw-r--r-- 1 ftpuser ftpusers 26100 Sep 18 1993 trxnet.exe
+-rw-r--r-- 1 ftpuser ftpusers 88579 Aug 21 1996 tsa410.exe
+-rw-r--r-- 1 ftpuser ftpusers 724997 Jun 25 10:29 tsa5up9.exe
+-rw-r--r-- 1 ftpuser ftpusers 127632 Jan 12 2000 tsands.exe
+-rw-r--r-- 1 ftpuser ftpusers 20771 Nov 2 1999 ttsy2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 19933 Sep 22 1995 ttyncs.exe
+-rw-r--r-- 1 ftpuser ftpusers 834048 Aug 3 1994 tux001.tar
+-rw-r--r-- 1 ftpuser ftpusers 845824 Aug 3 1994 tux002.tar
+-rw-r--r-- 1 ftpuser ftpusers 1034240 Aug 3 1994 tux003.tar
+-rw-r--r-- 1 ftpuser ftpusers 2764800 Aug 3 1994 tux004.tar
+-rw-r--r-- 1 ftpuser ftpusers 2836480 Aug 3 1994 tux005.tar
+-rw-r--r-- 1 ftpuser ftpusers 1252352 Aug 3 1994 tux006.tar
+-rw-r--r-- 1 ftpuser ftpusers 1355264 Aug 3 1994 tux007.tar
+-rw-r--r-- 1 ftpuser ftpusers 1710080 Aug 3 1994 tux008.tar
+-rw-r--r-- 1 ftpuser ftpusers 3502080 Aug 3 1994 tux009.tar
+-rw-r--r-- 1 ftpuser ftpusers 3573760 Aug 3 1994 tux010.tar
+-rw-r--r-- 1 ftpuser ftpusers 258236 Aug 4 1994 tux011.exe
+-rw-r--r-- 1 ftpuser ftpusers 258250 Aug 4 1994 tux012.exe
+-rw-r--r-- 1 ftpuser ftpusers 304451 Aug 4 1994 tux013.exe
+-rw-r--r-- 1 ftpuser ftpusers 602748 Aug 4 1994 tux014.exe
+-rw-r--r-- 1 ftpuser ftpusers 351070 Aug 4 1994 tux015.exe
+-rw-r--r-- 1 ftpuser ftpusers 460026 Aug 4 1994 tux016.exe
+-rw-r--r-- 1 ftpuser ftpusers 34077 Sep 18 1993 ucpy.exe
+-rw-r--r-- 1 ftpuser ftpusers 103354 Sep 18 1993 udf355.exe
+-rw-r--r-- 1 ftpuser ftpusers 6994 Feb 22 12:49 unixinf1.tgz
+-rw-r--r-- 1 ftpuser ftpusers 107260 May 8 14:56 unixins2.tgz
+-rw-r--r-- 1 ftpuser ftpusers 25508 Sep 18 1993 unld.exe
+-rw-r--r-- 1 ftpuser ftpusers 30830 Sep 18 1993 unps2.exe
+-rw-r--r-- 1 ftpuser ftpusers 34857 Sep 18 1993 up215c.exe
+-rw-r--r-- 1 ftpuser ftpusers 509794 Jan 6 1994 upd311.exe
+-rw-r--r-- 1 ftpuser ftpusers 24330 Sep 18 1993 ups.exe
+-rw-r--r-- 1 ftpuser ftpusers 20837 Sep 18 1993 ups22.exe
+-rw-r--r-- 1 ftpuser ftpusers 45537 Sep 18 1993 upsm70.exe
+-rw-r--r-- 1 ftpuser ftpusers 43743 Jul 22 1997 upsnlm.exe
+-rw-r--r-- 1 ftpuser ftpusers 28519 Oct 13 1998 userhlp.exe
+-rw-r--r-- 1 ftpuser ftpusers 134247 Sep 18 1993 ut1192.exe
+-rw-r--r-- 1 ftpuser ftpusers 1632088 Jan 14 1998 uxp203.exe
+-rw-r--r-- 1 ftpuser ftpusers 1389072 Nov 19 1998 uxp205.exe
+-rw-r--r-- 1 ftpuser ftpusers 1341347 Jun 6 2001 uxp23j.exe
+-rw-r--r-- 1 ftpuser ftpusers 1098502 Nov 2 1995 uxpsft.exe
+-rw-r--r-- 1 ftpuser ftpusers 58761 Nov 1 1995 v2014.exe
+-rw-r--r-- 1 ftpuser ftpusers 40944 Sep 18 1993 v286ol.exe
+-rw-r--r-- 1 ftpuser ftpusers 95133 Jun 8 2001 v_nfs914.exe
+-rw-r--r-- 1 ftpuser ftpusers 34278 Sep 18 1993 vapvol.exe
+-rw-r--r-- 1 ftpuser ftpusers 38035 Sep 18 1993 vgetsc.exe
+-rw-r--r-- 1 ftpuser ftpusers 52323 Sep 18 1993 volinf.exe
+-rw-r--r-- 1 ftpuser ftpusers 2444080 May 3 2001 vpn35e.exe
+-rw-r--r-- 1 ftpuser ftpusers 3838701 Feb 13 14:50 vpn36d.exe
+-rw-r--r-- 1 ftpuser ftpusers 3837285 Feb 13 14:48 vpn36e.exe
+-rw-r--r-- 1 ftpuser ftpusers 96158 Aug 31 1999 vpnbs01.exe
+-rw-r--r-- 1 ftpuser ftpusers 49835 Sep 18 1993 vrepfa.exe
+-rw-r--r-- 1 ftpuser ftpusers 86326 Sep 18 1993 vrp215.exe
+-rw-r--r-- 1 ftpuser ftpusers 59336 Jul 31 1997 vrp386.exe
+-rw-r--r-- 1 ftpuser ftpusers 43438 Jul 31 1997 vrpa286.exe
+-rw-r--r-- 1 ftpuser ftpusers 486274 Sep 18 1993 vrpels.exe
+-rw-r--r-- 1 ftpuser ftpusers 103958 Sep 18 1993 vrpps2.exe
+-rw-r--r-- 1 ftpuser ftpusers 699367 Sep 9 1999 w2n213.exe
+-rw-r--r-- 1 ftpuser ftpusers 771404 Sep 25 2000 w2ny2k.exe
+-rw-r--r-- 1 ftpuser ftpusers 240179 Jun 4 1996 wan31a.exe
+-rw-r--r-- 1 ftpuser ftpusers 135592 Jun 16 1995 wanx02.exe
+-rw-r--r-- 1 ftpuser ftpusers 79254744 Jul 20 2001 was351.exe
+-rw-r--r-- 1 ftpuser ftpusers 28100 Sep 18 1993 watch.exe
+-rw-r--r-- 1 ftpuser ftpusers 7884641 Apr 23 10:17 waview71.exe
+-rw-r--r-- 1 ftpuser ftpusers 182961 Jul 9 2001 wbdav51.exe
+-rw-r--r-- 1 ftpuser ftpusers 53418 Aug 21 1996 web002.exe
+-rw-r--r-- 1 ftpuser ftpusers 182219 Mar 1 2001 webdv51.exe
+-rw-r--r-- 1 ftpuser ftpusers 2574191 Oct 5 1999 weblsp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 3589741 Jun 22 1998 webser31.exe
+-rw-r--r-- 1 ftpuser ftpusers 27063 Nov 1 1995 welcom.exe
+-rw-r--r-- 1 ftpuser ftpusers 1887450 Apr 23 2001 winntwms.exe
+-rw-r--r-- 1 ftpuser ftpusers 28104 Jul 17 1997 wkstrk.exe
+-rw-r--r-- 1 ftpuser ftpusers 52547 Jul 20 1995 wpca31.exe
+-rw-r--r-- 1 ftpuser ftpusers 89314 Jul 20 1995 wpfm31.exe
+-rw-r--r-- 1 ftpuser ftpusers 41008 Sep 11 1995 wpmdm2.exe
+-rw-r--r-- 1 ftpuser ftpusers 36824 Jul 18 1995 wpofus.exe
+-rw-r--r-- 1 ftpuser ftpusers 51398 Jul 20 1995 wprp31.exe
+-rw-r--r-- 1 ftpuser ftpusers 21092 Jul 18 1995 wpvwin.exe
+-rw-r--r-- 1 ftpuser ftpusers 52738 Mar 15 1994 wrkdoc.exe
+-rw-r--r-- 1 ftpuser ftpusers 683395 May 29 1997 ws250c.exe
+-rw-r--r-- 1 ftpuser ftpusers 765234 May 29 1997 ws251c.exe
+-rw-r--r-- 1 ftpuser ftpusers 212586 May 9 1997 ws3tk2b.exe
+-rw-r--r-- 1 ftpuser ftpusers 371 Mar 7 12:40 ws_ftp.log
+-rw-r--r-- 1 ftpuser ftpusers 1507075 Jun 29 1999 wtmc1.exe
+-rw-r--r-- 1 ftpuser ftpusers 32697 Jun 16 1995 x400fx.exe
+-rw-r--r-- 1 ftpuser ftpusers 660700 Jun 9 1999 x400nlm1.exe
+-rw-r--r-- 1 ftpuser ftpusers 1134477 Aug 5 1999 x400os21.exe
+-rw-r--r-- 1 ftpuser ftpusers 156483 Jan 30 17:09 xconss9f.exe
+-rw-r--r-- 1 ftpuser ftpusers 49801 Sep 18 1993 xld386.exe
+-rw-r--r-- 1 ftpuser ftpusers 1043685 Jul 27 2001 zd2dmi1.exe
+-rw-r--r-- 1 ftpuser ftpusers 365016 Dec 19 2001 zd2dstfx.exe
+-rw-r--r-- 1 ftpuser ftpusers 338947 Jul 20 2001 zd2scan.exe
+-rw-r--r-- 1 ftpuser ftpusers 24341430 Mar 1 09:27 zd322k1.exe
+-rw-r--r-- 1 ftpuser ftpusers 24350056 Mar 1 09:35 zd322k2.exe
+-rw-r--r-- 1 ftpuser ftpusers 95330 Mar 14 18:03 zd32dupw.exe
+-rw-r--r-- 1 ftpuser ftpusers 26945103 Mar 1 09:16 zd32nw.exe
+-rw-r--r-- 1 ftpuser ftpusers 26937023 Mar 1 09:21 zd32nw4.exe
+-rw-r--r-- 1 ftpuser ftpusers 26944994 Feb 5 12:18 zd32nw5.exe
+-rw-r--r-- 1 ftpuser ftpusers 24349972 Jul 29 2001 zd32p2k1.exe
+-rw-r--r-- 1 ftpuser ftpusers 24349896 Jul 29 2001 zd32p2k2.exe
+-rw-r--r-- 1 ftpuser ftpusers 26936865 Jul 29 2001 zd32pnw4.exe
+-rw-r--r-- 1 ftpuser ftpusers 26944944 Jul 29 2001 zd32pnw5.exe
+-rw-r--r-- 1 ftpuser ftpusers 128456 Jan 29 14:50 zd3awsr1.exe
+-rw-r--r-- 1 ftpuser ftpusers 1242985 Dec 19 2001 zd3ccpp.exe
+-rw-r--r-- 1 ftpuser ftpusers 304923 Dec 19 2001 zd3dac.exe
+-rw-r--r-- 1 ftpuser ftpusers 537680 Feb 22 15:31 zd3dupws.exe
+-rw-r--r-- 1 ftpuser ftpusers 142260 Nov 8 2001 zd3dxsnp.exe
+-rw-r--r-- 1 ftpuser ftpusers 94250 Dec 4 2001 zd3idnt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 1443132 Jan 2 2002 zd3ntmsi.exe
+-rw-r--r-- 1 ftpuser ftpusers 15512136 Dec 20 2001 zd3o8i1.exe
+-rw-r--r-- 1 ftpuser ftpusers 15575094 Dec 19 2001 zd3o8i2.exe
+-rw-r--r-- 1 ftpuser ftpusers 204858 May 24 10:03 zd3rosnp.exe
+-rw-r--r-- 1 ftpuser ftpusers 298505 Jan 9 2002 zd3scn.exe
+-rw-r--r-- 1 ftpuser ftpusers 149726 Dec 18 2001 zd3wm95.exe
+-rw-r--r-- 1 ftpuser ftpusers 180523 Jan 9 2002 zd3wminv.exe
+-rw-r--r-- 1 ftpuser ftpusers 166988 Dec 18 2001 zd3wmsch.exe
+-rw-r--r-- 1 ftpuser ftpusers 195447 Dec 19 2001 zd3wsmg.exe
+-rw-r--r-- 1 ftpuser ftpusers 381437 Mar 19 14:21 zd3xwsrg.exe
+-rw-r--r-- 1 ftpuser ftpusers 125036 Apr 18 15:53 zd3xwuol.exe
+-rw-r--r-- 1 ftpuser ftpusers 180429 Apr 18 16:30 zd3xzisw.exe
+-rw-r--r-- 1 ftpuser ftpusers 226961 Mar 14 10:01 zd3zpol.exe
+-rw-r--r-- 1 ftpuser ftpusers 1274878 May 1 17:41 zenintg.exe
+-rw-r--r-- 1 ftpuser ftpusers 1865 May 9 2001 zenstart.txt
+-rw-r--r-- 1 ftpuser ftpusers 2408726 Feb 23 2001 zfd2pt3b.exe
+-rw-r--r-- 1 ftpuser ftpusers 62396652 Mar 21 2000 zfd2sp1.exe
+-rw-r--r-- 1 ftpuser ftpusers 293221 May 22 2001 zfd2tsfx.exe
+-rw-r--r-- 1 ftpuser ftpusers 97309 Oct 20 2000 zfd3site.exe
+-rw-r--r-- 1 ftpuser ftpusers 46890033 Nov 23 2001 zfd3sp1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 31452136 Aug 10 2000 zfn101.exe
+-rw-r--r-- 1 ftpuser ftpusers 1647316 Nov 23 2001 zfs2jvm.exe
+-rw-r--r-- 1 ftpuser ftpusers 215046 Dec 18 2001 zfs2pt1.exe
+-rw-r--r-- 1 ftpuser ftpusers 262640 Dec 20 2001 zfs2sel.exe
+-rw-r--r-- 1 ftpuser ftpusers 54876346 Jan 18 14:59 zfs2sp1a.exe
+-rw-r--r-- 1 ftpuser ftpusers 1903657 Feb 5 2001 zfsdbpb.exe
+-rw-r--r-- 1 ftpuser ftpusers 96356 Oct 11 2000 zisclr.exe
+-rw-r--r-- 1 ftpuser ftpusers 94293 Dec 19 2001 zs2dbbk.exe
+-rw-r--r-- 1 ftpuser ftpusers 141307 Dec 20 2001 zs2ipg.exe
+-rw-r--r-- 1 ftpuser ftpusers 1173802 Dec 19 2001 zs2mibs.exe
+-rw-r--r-- 1 ftpuser ftpusers 943931 Jan 23 08:51 zs2ndst1.exe
+-rw-r--r-- 1 ftpuser ftpusers 516401 Jun 4 13:23 zs2rbs.exe
+-rw-r--r-- 1 ftpuser ftpusers 1095584 Mar 13 11:41 zs2smtp.exe
+-rw-r--r-- 1 ftpuser ftpusers 981014 Dec 5 2001 zs2util2.exe
+-rw-r--r-- 1 ftpuser ftpusers 92151 Jun 6 11:14 zs3sch.exe
+-rw-r--r-- 1 ftpuser ftpusers 1039314 Oct 13 1998 zw100p1.exe
+-rw-r--r-- 1 ftpuser ftpusers 194420 Nov 6 1998 zw101p1.exe
+-rw-r--r-- 1 ftpuser ftpusers 1065727 Nov 22 1999 zw110p3.exe
+226 Listing completed.
+ftp> close
+221-Thank you and have a nice day.
+221
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-ncFTPd.out b/netwerk/test/gtest/parse-ftp/U-ncFTPd.out
new file mode 100644
index 0000000000..6e3bac46f0
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-ncFTPd.out
@@ -0,0 +1,1377 @@
+<!-- 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/. -->
+
+01-01-1997 00:00:00 2419 Readme
+07-10-2002 11:03:00 <DIR> incoming
+07-10-2002 10:18:00 <DIR> outgoing
+05-10-2002 10:16:00 <DIR> priv
+07-10-2002 08:12:00 <DIR> pub
+07-08-2002 19:20:00 <DIR> allupdates
+01-01-1997 00:00:00 <DIR> netwire
+07-09-2002 19:20:00 <DIR> support
+01-10-2002 00:00:00 <JUNCTION> updates -> allupdates
+07-27-1999 00:00:00 19448 0dsb.exe
+09-17-1993 00:00:00 49351 215mir.exe
+09-17-1993 00:00:00 32586 215sec.exe
+09-17-1993 00:00:00 136344 21fix.exe
+09-17-1993 00:00:00 57276 223200.exe
+11-01-1995 00:00:00 119616 22bkup.exe
+10-13-1995 00:00:00 19820 22dos5.exe
+11-01-1995 00:00:00 32980 22nd2f.exe
+05-09-2002 11:30:00 92151 236779.exe
+01-17-2001 00:00:00 273958 242234.exe
+07-10-2001 00:00:00 283462 243798.exe
+12-18-2001 00:00:00 160893 251000.exe
+12-18-2001 00:00:00 205531 252143.exe
+12-18-2001 00:00:00 183262 253720.exe
+11-06-2001 00:00:00 231638 260624.exe
+06-21-2001 00:00:00 250545 264837.exe
+02-21-2002 16:33:00 589722 265058a.exe
+11-07-2001 00:00:00 336586 269308.exe
+11-06-2001 00:00:00 345275 270050.exe
+11-06-2001 00:00:00 103027 270410.exe
+05-09-2002 07:13:00 341460 275382.exe
+05-09-2002 11:23:00 365835 275436.exe
+10-09-2001 00:00:00 230063 275520.exe
+10-02-2001 00:00:00 285953 275820.exe
+11-16-2001 00:00:00 156517 277412.exe
+12-19-2001 00:00:00 839272 278415.exe
+12-19-2001 00:00:00 130983 282848.exe
+09-17-1993 00:00:00 61891 286dwn.exe
+05-09-2002 07:18:00 136529 290254.exe
+04-12-2002 17:07:00 96694 290261.exe
+05-09-2002 07:22:00 230377 291158.exe
+06-27-2002 12:20:00 114329 295137.exe
+09-17-1993 00:00:00 84885 2xto3x.exe
+09-17-1993 00:00:00 60861 300pt1.exe
+09-17-1993 00:00:00 180279 310pt1.exe
+11-11-1996 00:00:00 178076 311ptg.exe
+04-29-1996 00:00:00 188572 312du1.exe
+03-18-1998 00:00:00 168258 312ptd.exe
+08-25-1999 00:00:00 436629 312y2kp2.exe
+06-29-2001 00:00:00 2365264 33sp3.exe
+09-17-1993 00:00:00 28881 386dcb.exe
+09-17-1993 00:00:00 33111 3cboot.exe
+11-10-1995 00:00:00 27583 400pt1.exe
+10-23-1995 00:00:00 79295 401pt6.exe
+08-26-1994 00:00:00 42873 402pa1.exe
+03-28-1995 00:00:00 50737 402pt1.exe
+06-08-1998 00:00:00 548398 410pt8b.exe
+08-25-1999 00:00:00 285471 410y2kp2.exe
+07-23-1999 00:00:00 538544 411y2kp2.exe
+04-29-1996 00:00:00 370469 41filr.exe
+01-02-1997 00:00:00 58965 41migutl.exe
+08-29-1995 00:00:00 173978 41ndir.exe
+11-24-1997 00:00:00 42101 41rem1.exe
+07-09-1996 00:00:00 855292 41rtr2.exe
+07-23-1999 00:00:00 212785 42y2kp1.exe
+07-03-2001 00:00:00 3043701 48sp3.exe
+05-22-2001 00:00:00 308856 4pent.exe
+04-06-1998 00:00:00 1072023 4xmigr2.exe
+11-17-1995 00:00:00 125457 4xrep1.exe
+07-06-1994 00:00:00 29001 50z70.exe
+11-01-1995 00:00:00 23248 55sx60.exe
+12-04-1998 00:00:00 647818 95220p1.exe
+03-25-1999 00:00:00 905243 95250p2.exe
+06-21-1999 00:00:00 694344 9530p1.exe
+06-13-2000 00:00:00 794454 9531pt2.exe
+10-03-1999 00:00:00 4380134 9531sp2.exe
+11-16-2000 00:00:00 1306298 95321pt5.exe
+06-13-2000 00:00:00 494394 9532pt3.exe
+11-06-2001 00:00:00 483405 95331pt1.exe
+06-02-2000 00:00:00 19588899 a526aix.z
+06-02-2000 00:00:00 17196628 a526hp.z
+06-02-2000 00:00:00 14813432 a526sol.z
+07-09-1999 00:00:00 238005 accupg1b.exe
+09-17-1993 00:00:00 19472 aceclp.exe
+06-19-2001 00:00:00 2061142 acmgtcl.exe
+12-17-1996 00:00:00 52792 actkey.exe
+11-08-1996 00:00:00 1026928 adde1.exe
+09-10-1997 00:00:00 476094 adm32_22.exe
+01-10-1997 00:00:00 4204451 adm4113x.exe
+01-10-1997 00:00:00 3813257 adm41195.exe
+01-10-1997 00:00:00 5377426 adm411nt.exe
+05-23-2001 00:00:00 130826 admattrs.exe
+05-23-2001 00:00:00 3291925 admn519f.exe
+07-15-1997 00:00:00 273404 adtus3.exe
+09-17-1993 00:00:00 25475 afix1.exe
+09-17-1993 00:00:00 25929 afix2.exe
+09-17-1993 00:00:00 26184 afix4.exe
+04-10-2001 00:00:00 116034 afnwcgi1.exe
+01-28-2002 13:43:00 175949 afp100j.exe
+07-12-1999 00:00:00 90415 afp11.exe
+11-01-1995 00:00:00 513677 aiodrv.exe
+08-12-1995 00:00:00 26752 aiotrm.exe
+02-08-2000 00:00:00 113328 alx311cm.exe
+12-11-2001 00:00:00 202594 am210pt2.exe
+12-10-2001 00:00:00 1126900 am210snp.exe
+12-11-2001 00:00:00 267218 amsammg.exe
+11-29-2001 00:00:00 4394406 amw2ksp1.exe
+11-06-1996 00:00:00 34959 anlmde.exe
+11-20-1996 00:00:00 70315 antde.exe
+12-10-1997 00:00:00 2778036 apinlm.exe
+04-05-1994 00:00:00 47772 apinst.exe
+12-10-1997 00:00:00 3367826 apios2.exe
+09-17-1993 00:00:00 44662 apsvap.exe
+10-05-1998 00:00:00 1507519 async1.exe
+07-25-1995 00:00:00 431852 asyq4a.exe
+09-17-1993 00:00:00 68700 atalk.exe
+09-17-1993 00:00:00 22944 atdisk.exe
+01-29-1996 00:00:00 222222 atk307.exe
+09-24-1999 00:00:00 259359 atmdrv04.exe
+06-14-1996 00:00:00 22012 atok31.exe
+09-17-1993 00:00:00 25152 atps1.exe
+09-17-1993 00:00:00 25812 atps2.exe
+09-17-1993 00:00:00 206226 atsup.exe
+09-15-1997 00:00:00 249262 audit410.exe
+07-25-1995 00:00:00 27058 autoda.exe
+03-28-2001 00:00:00 53955568 azfd3sp1.exe
+03-30-2000 00:00:00 1267891 bacl105.exe
+04-24-1998 00:00:00 564407 bm21y2k.exe
+12-09-1999 00:00:00 64354 bm2ncs2.exe
+11-13-2000 00:00:00 5025837 bm30sp3.exe
+03-27-2002 10:48:00 118425 bm35adm6.exe
+09-25-2001 00:00:00 8950758 bm35sp3.exe
+05-31-2002 15:43:00 1560521 bm36c02.exe
+11-06-2001 00:00:00 1995053 bm36nsp1.exe
+01-30-2002 13:44:00 4187534 bm36sp1a.exe
+04-19-2002 13:52:00 146884 bm37flt.exe
+04-19-2002 13:54:00 3958423 bm37vpn1.exe
+06-16-2000 00:00:00 2192048 bm3cp3.exe
+03-27-2000 00:00:00 521873 bm3licfx.exe
+01-21-1999 00:00:00 550905 bm3netad.exe
+10-08-1999 00:00:00 28435 bm3pcfg.exe
+10-20-1999 00:00:00 30429 bm3rmv3.exe
+09-02-1999 00:00:00 4865777 bm3sp2.exe
+01-11-2000 00:00:00 3934644 bm3sp2j.exe
+01-16-2001 00:00:00 105579 bm3sso2.exe
+11-23-1998 00:00:00 114564 bmas203.exe
+07-27-2000 00:00:00 185953 bmas204.exe
+05-29-2001 00:00:00 227934 bmas3x01.exe
+04-14-1998 00:00:00 2409166 bmnwntb.exe
+10-07-1999 00:00:00 235512 bmp114.exe
+08-25-2000 00:00:00 114828 bmsamp1.exe
+02-05-2001 00:00:00 7822377 bmsp2d.exe
+05-09-2001 00:00:00 177276 bmvpn3y.exe
+07-16-1997 00:00:00 57666 bndfx4.exe
+09-26-1997 00:00:00 22178 brdrem1.exe
+09-17-1993 00:00:00 140225 brgcom.exe
+03-17-1998 00:00:00 64130 bwcc.exe
+05-10-2000 00:00:00 106576 c112brj.exe
+05-09-2000 00:00:00 107820 c112crcj.exe
+05-10-2000 00:00:00 106834 c112crj.exe
+03-05-2002 13:14:00 35687507 c1_132.exe
+02-27-2001 00:00:00 188379 c1unx85a.exe
+06-02-2000 00:00:00 24246977 c526aix.z
+06-02-2000 00:00:00 39823205 c526hp.z
+06-02-2000 00:00:00 31630789 c526sol.z
+12-04-1996 00:00:00 39967 ccmdll.exe
+06-21-1999 00:00:00 3532557 ccmln1.exe
+04-21-2000 00:00:00 3610648 ccmln2.exe
+10-30-1998 00:00:00 7242383 ccmlo1.exe
+03-06-1997 00:00:00 71189 cdisc.exe
+08-19-1998 00:00:00 298109 cdup5a.exe
+10-14-1998 00:00:00 1554357 cfgrd6b.exe
+09-17-1993 00:00:00 30799 chk375.exe
+06-16-1997 00:00:00 85538 chtree1.exe
+12-08-1999 00:00:00 28171 clibaux1.exe
+09-08-2000 00:00:00 2819 clients.txt
+09-11-2000 00:00:00 16820824 clntaot.exe
+01-05-1999 00:00:00 7269162 clos2d1.exe
+06-24-1996 00:00:00 2960384 clt511.bin
+03-24-1999 00:00:00 195429 clty2kp1.exe
+11-22-1993 00:00:00 76117 comchk.exe
+11-01-1995 00:00:00 76738 comsub.exe
+08-16-1996 00:00:00 74759 comx.exe
+02-22-2001 00:00:00 102496 comx218.exe
+12-05-2000 00:00:00 117584 confg9.exe
+09-17-1993 00:00:00 27438 conlog.exe
+09-17-1993 00:00:00 20051 cpuchk.exe
+01-07-2000 00:00:00 96755 cron5.exe
+07-21-2001 00:00:00 22439431 cs1sp2.exe
+02-19-2002 16:08:00 12643202 cs1sp3.exe
+02-28-2001 00:00:00 2395980 cs2ep2.exe
+02-17-2000 00:00:00 97982 csatpxy2.exe
+01-30-1997 00:00:00 888262 csserv.exe
+01-30-1997 00:00:00 888092 ctserv.exe
+09-20-1999 00:00:00 1195718 ctsv20_1.pdf
+08-30-2000 00:00:00 97050 cvsbind.exe
+01-05-1996 00:00:00 1040603 d70f15.exe
+01-05-1996 00:00:00 1046550 d70g15.exe
+01-05-1996 00:00:00 1041138 d70i15.exe
+01-05-1996 00:00:00 1042404 d70s15.exe
+01-05-1996 00:00:00 1031373 d70u15.exe
+10-31-1995 00:00:00 309903 d72pnw.exe
+08-17-1995 00:00:00 26322 daishm.exe
+01-17-2002 09:55:00 92347 decrenfx.exe
+11-24-1997 00:00:00 32573 devmon.exe
+11-23-1999 00:00:00 225697 dhcp21r.exe
+07-27-1994 00:00:00 65667 diag.exe
+07-03-1996 00:00:00 776679 dialr1.exe
+07-03-1996 00:00:00 1307891 dialr2.exe
+07-03-1996 00:00:00 1330220 dialr3.exe
+09-17-1993 00:00:00 62202 distst.exe
+02-08-2001 00:00:00 133345 dlttape.exe
+12-13-1995 00:00:00 174566 dr6tid.exe
+05-15-2002 15:23:00 188110 dradpt1a.exe
+04-11-2002 10:37:00 12654872 drdt10.exe
+04-11-2002 10:50:00 7991951 drnt10.exe
+12-09-1993 00:00:00 259966 drv2x.exe
+09-17-1993 00:00:00 366568 drvkit.exe
+12-02-1998 00:00:00 28773 drvspc.exe
+07-12-1994 00:00:00 242836 ds310.exe
+12-13-1999 00:00:00 739008 ds410q.exe
+06-11-2002 18:01:00 683746 ds616.exe
+07-03-2002 19:58:00 1237908 ds760a.exe
+06-12-2002 13:47:00 3084809 ds880d_a.exe
+06-07-2000 00:00:00 2366484 ds8c.exe
+05-31-2000 00:00:00 300572 dsbrowse.exe
+11-10-1998 00:00:00 425220 dsdiag1.exe
+04-15-1998 00:00:00 766525 dskdrv.exe
+05-02-1997 00:00:00 201308 dsright2.exe
+02-04-2002 14:26:00 6620 dsrmenu5.tgz
+01-11-2002 12:06:00 32671 dsx86upg.tgz
+11-22-1999 00:00:00 438327 duprid.exe
+11-30-1999 00:00:00 366231 dw271i1.exe
+10-31-2001 00:00:00 6444327 dx1patch.exe
+12-11-2001 00:00:00 764705 dxjdbc1a.exe
+07-31-2001 00:00:00 369669 dxnotp1.exe
+01-11-2002 17:32:00 325977 dxntp1.exe
+01-11-2002 17:11:00 6446882 dxnwp1.exe
+01-15-2002 18:08:00 27292445 dxx10a.tgz
+09-18-1993 00:00:00 420838 e2isa.exe
+05-15-2002 09:35:00 299227554 edir851.exe
+06-19-2002 22:20:00 13752049 edir8527.exe
+06-18-2002 17:22:00 8909701 edir8527.tgz
+05-23-2002 12:35:00 35256093 edir862.exe
+03-07-2002 13:22:00 30290896 edir862.tgz
+06-20-2002 11:12:00 12405810 edir862sp1.exe
+06-20-2002 11:07:00 7623982 edir862sp1a.tgz
+06-19-2002 23:26:00 178010922 edirw8527.exe
+08-01-1995 00:00:00 739976 edvwin.exe
+04-12-2002 15:32:00 270433 egdpvr02.exe
+01-15-2002 10:28:00 6660863 einstall.exe
+09-18-1993 00:00:00 19547 els2dt.exe
+09-18-1993 00:00:00 46872 elsupd.exe
+09-18-1993 00:00:00 44481 emshdl.exe
+11-30-2001 00:00:00 171889 es7000.exe
+09-18-1993 00:00:00 395219 escsi.exe
+11-01-1995 00:00:00 50164 esdidr.exe
+09-18-1993 00:00:00 22207 esdifx.exe
+04-16-2001 00:00:00 162763 etbox7.exe
+09-18-1993 00:00:00 28262 ethrlk.exe
+09-18-1993 00:00:00 21776 ethsh.exe
+10-13-1999 00:00:00 3111638 exchnt2.exe
+03-20-1995 00:00:00 32615 exprul.exe
+07-18-1995 00:00:00 19910 facwin.exe
+09-18-1993 00:00:00 193689 faxdoc.exe
+07-18-1995 00:00:00 103299 faxsv.exe
+07-20-1998 00:00:00 566087 fbm21y2k.exe
+07-27-2000 00:00:00 263164 ffwnt1a.exe
+06-05-2000 00:00:00 9564485 fgwep1ad.exe
+11-10-1993 00:00:00 158446 fil376.exe
+09-18-1993 00:00:00 35376 filehd.exe
+01-28-1999 00:00:00 64924 filt01a.exe
+09-18-1993 00:00:00 38027 flgdir.exe
+06-25-2002 10:26:00 891667 flsysft7.exe
+07-20-1994 00:00:00 210958 flx196.exe
+09-18-1993 00:00:00 23948 fmtps2.exe
+06-01-1995 00:00:00 265642 fmwin1.exe
+06-18-1997 00:00:00 44110 fnasi21b.exe
+04-29-1997 00:00:00 35133 fnwcrns.exe
+06-18-1997 00:00:00 64944 fnwcss.exe
+06-18-1997 00:00:00 38169 fnwcx25.exe
+02-26-2001 00:00:00 18985686 fp3023a.exe
+02-26-2001 00:00:00 19034903 fp3023s.exe
+06-22-2001 00:00:00 41401158 fpa353.exe
+06-22-2001 00:00:00 40072174 fps353.exe
+08-02-1996 00:00:00 40680 frebld.exe
+01-30-2002 15:36:00 156117 ftpservk.exe
+06-20-2001 00:00:00 1427341 fzd2abnd.exe
+05-22-2001 00:00:00 121436 fzd2nal.exe
+05-22-2001 00:00:00 293122 fzd2nal1.exe
+12-18-2001 00:00:00 333581 fzd2nal2.exe
+05-23-2001 00:00:00 250445 fzd2zapp.exe
+10-10-2001 00:00:00 2619032 g32ep3b.exe
+11-23-1998 00:00:00 26193920 g41c5a41.tar
+11-23-1998 00:00:00 25907200 g41c5a43.tar
+11-23-1998 00:00:00 25190400 g41c5dg.tar
+11-23-1998 00:00:00 27494400 g41c5hp.tar
+11-23-1998 00:00:00 29337600 g41c5ncr.tar
+11-23-1998 00:00:00 27146240 g41c5sc5.tar
+11-23-1998 00:00:00 26982400 g41c5sl5.tar
+11-23-1998 00:00:00 26961920 g41c5sl6.tar
+11-23-1998 00:00:00 32808960 g41c5sun.tar
+11-23-1998 00:00:00 3614720 g41m5a41.tar
+11-23-1998 00:00:00 3604480 g41m5a43.tar
+11-23-1998 00:00:00 3481600 g41m5dg.tar
+11-23-1998 00:00:00 4280320 g41m5hp.tar
+11-23-1998 00:00:00 4495360 g41m5ncr.tar
+11-23-1998 00:00:00 5263360 g41m5sc5.tar
+11-23-1998 00:00:00 4116480 g41m5sl5.tar
+11-23-1998 00:00:00 4106240 g41m5sl6.tar
+11-20-1998 00:00:00 5939200 g41m5sun.tar
+06-02-2000 00:00:00 93137892 g526east.exe
+06-02-2000 00:00:00 84011178 g526kcc.exe
+06-02-2000 00:00:00 106015153 g526mult.exe
+06-02-2000 00:00:00 92474943 g526scan.exe
+06-02-2000 00:00:00 74449657 g526us.exe
+06-02-2000 00:00:00 80161031 g526usde.exe
+06-02-2000 00:00:00 77052636 g526usjp.exe
+12-18-1997 00:00:00 20712319 g52a1aix.z
+12-18-1997 00:00:00 17069171 g52a1hp.z
+12-18-1997 00:00:00 14703356 g52a1sol.z
+06-02-2000 00:00:00 7595802 g554ar.exe
+06-02-2000 00:00:00 39304570 g554en.exe
+06-02-2000 00:00:00 13651283 g554est.exe
+06-02-2000 00:00:00 7587459 g554he.exe
+06-02-2000 00:00:00 23317212 g554jp.exe
+06-02-2000 00:00:00 22871590 g554kcc.exe
+06-02-2000 00:00:00 30379240 g554mlt.exe
+06-02-2000 00:00:00 30469595 g554scn.exe
+08-31-2000 00:00:00 3252251 g5notmb1.exe
+08-08-1995 00:00:00 1983381 gam10.exe
+07-20-1998 00:00:00 565411 gbm21y2k.exe
+11-19-1996 00:00:00 547498 gdsmtp.exe
+10-21-1996 00:00:00 26760 gdusc1.exe
+09-18-1993 00:00:00 32876 genbio.exe
+10-03-2001 00:00:00 4589470 gep3beng.exe
+08-16-1999 00:00:00 12570112 gm527aen.bin
+06-14-2000 00:00:00 12556928 gm528aen.bin
+06-19-2000 00:00:00 12558720 gm528ben.bin
+12-21-1996 00:00:00 6081664 gmcec3.hqx
+12-21-1996 00:00:00 6086656 gmcfc3.hqx
+12-24-1996 00:00:00 6089856 gmesc3.hqx
+12-20-1996 00:00:00 6087552 gmfrc3.hqx
+12-24-1996 00:00:00 6084480 gmitc3.hqx
+12-19-1996 00:00:00 6079872 gmozc3.hqx
+12-19-1996 00:00:00 6081792 gmukc3.hqx
+12-11-1996 00:00:00 6079872 gmusc3.hqx
+09-18-1993 00:00:00 26557 gpierr.exe
+08-28-1996 00:00:00 189508 gpwrdk.exe
+08-28-1996 00:00:00 114332 gpwrnl.exe
+09-03-1996 00:00:00 99491 gpwrru.exe
+08-28-1996 00:00:00 131835 gpwrsu.exe
+08-22-1996 00:00:00 170183 gpwrsv.exe
+02-25-1998 00:00:00 74740 gpwsbr.exe
+02-25-1998 00:00:00 44964 gpwsde.exe
+02-25-1998 00:00:00 40264 gpwsfr.exe
+02-25-1998 00:00:00 39224 gpwsit.exe
+07-22-1999 00:00:00 47842 groupfix.exe
+10-19-1995 00:00:00 207875 gsc41.exe
+12-15-1997 00:00:00 811983 gsc51.exe
+06-08-1995 00:00:00 9805824 gusmtp.tar
+07-28-1999 00:00:00 4658880 gw41api.exe
+11-17-1999 00:00:00 1307103 gw41api2.exe
+07-29-1999 00:00:00 30983798 gw41aus.exe
+02-28-1996 00:00:00 86653 gw41qa.exe
+12-10-1998 00:00:00 20978 gw41sp5.txt
+01-08-1998 00:00:00 18251583 gw51sp2a.exe
+03-10-1998 00:00:00 3483616 gw51w16a.exe
+01-09-2001 00:00:00 1931948 gw52ch6.exe
+06-26-2000 00:00:00 479758 gw52sp6.exe
+02-28-2002 16:19:00 35836761 gw555cck.exe
+02-28-2002 16:34:00 26614908 gw555ee.exe
+05-31-2000 00:00:00 372421 gw55bk.exe
+02-03-2000 00:00:00 109887 gw55bp.exe
+06-19-2000 00:00:00 847939 gw55dutl.exe
+08-14-2001 00:00:00 58548675 gw55ep3a.exe
+06-25-1999 00:00:00 2497895 gw55inst.exe
+06-27-2000 00:00:00 3742457 gw55ol2.exe
+04-18-2001 00:00:00 219963 gw55puma.exe
+03-01-1999 00:00:00 19376 gw55rc.exe
+12-18-1998 00:00:00 45201 gw55sp1u.exe
+02-28-2002 16:08:00 21311033 gw55sp5a.exe
+02-19-2002 17:56:00 52764291 gw55sp5e.exe
+02-28-2002 16:13:00 21300984 gw55sp5h.exe
+02-19-2002 18:03:00 43933605 gw55sp5m.exe
+02-28-2002 16:03:00 44001516 gw55sp5s.exe
+03-09-1999 00:00:00 5867520 gw55uagb.tar
+04-23-1997 00:00:00 20446033 gw5img.exe
+11-21-2001 00:00:00 313843533 gw6sp1.exe
+11-20-2001 00:00:00 313466368 gw6sp1fr.exe
+03-13-2002 18:35:00 26705047 gw6tomcat_nt.exe
+10-15-2001 00:00:00 318278 gw6wasf.exe
+01-22-1997 00:00:00 493803 gwadm.exe
+07-26-2000 00:00:00 1900719 gwafe510.exe
+11-02-1999 00:00:00 469618 gwanlzr1.exe
+06-19-2000 00:00:00 479013 gwata417.exe
+06-19-2000 00:00:00 1731751 gwata517.exe
+08-12-1996 00:00:00 168008 gwbr41.exe
+08-31-1998 00:00:00 17881984 gwbrc5.exe
+08-26-1997 00:00:00 194213 gwbupaus.exe
+06-15-2000 00:00:00 885247 gwca55.exe
+06-29-2000 00:00:00 902786 gwca55us.exe
+08-17-1999 00:00:00 2398720 gwccarch.exe
+08-27-1998 00:00:00 19751754 gwcec5.exe
+12-01-1998 00:00:00 18095569 gwcfc5a.exe
+01-22-1997 00:00:00 499022 gwclint.exe
+06-19-2000 00:00:00 274618 gwclust.exe
+08-31-1998 00:00:00 18704283 gwczc5.exe
+08-28-1998 00:00:00 18602662 gwdec5.exe
+01-22-1997 00:00:00 577392 gwdirsnc.exe
+08-31-1998 00:00:00 18044524 gwdkc5.exe
+08-16-2001 00:00:00 2064976 gwe2mlfx.exe
+04-18-2001 00:00:00 220287 gweppuma.exe
+02-19-2002 17:38:00 106411074 gwepsp4e.exe
+02-19-2002 17:48:00 105412358 gwepsp4m.exe
+10-15-2001 00:00:00 211359 gwepwasf.exe
+08-31-1998 00:00:00 18156006 gwesc5.exe
+08-20-1999 00:00:00 2278400 gwexarch.exe
+09-02-1998 00:00:00 18094284 gwfrc5.exe
+02-05-2002 12:22:00 14809111 gwia6sp1.exe
+12-24-1998 00:00:00 47599 gwip.exe
+06-26-2000 00:00:00 2103744 gwiru55.exe
+08-31-1998 00:00:00 18176506 gwitc5.exe
+05-20-1997 00:00:00 1643991 gwjpc3.exe
+08-24-1999 00:00:00 2689024 gwlnarch.exe
+08-31-1998 00:00:00 18450385 gwmac5.exe
+06-19-2001 00:00:00 104256 gwmacvew.exe
+01-22-1997 00:00:00 521879 gwmigrat.exe
+08-18-1999 00:00:00 2387456 gwmsarch.exe
+08-31-1998 00:00:00 18442250 gwnlc5.exe
+08-31-1998 00:00:00 18496070 gwnoc5.exe
+08-27-1998 00:00:00 18436940 gwozc5.exe
+08-29-2001 00:00:00 735542 gwpdchk.exe
+08-28-2001 00:00:00 29521018 gwpdlk56.exe
+08-14-2001 00:00:00 29520686 gwpdlock.exe
+08-31-1998 00:00:00 18696898 gwplc5.exe
+03-05-1996 00:00:00 1388969 gwpoc.exe
+08-31-1998 00:00:00 17738497 gwpoc5.exe
+01-22-2002 16:48:00 10400450 gwport32.exe
+08-31-1998 00:00:00 18492682 gwruc5.exe
+08-31-1998 00:00:00 18154021 gwsuc5.exe
+08-31-1998 00:00:00 17958220 gwsvc5.exe
+01-16-2002 09:41:00 536848 gwsyclo.exe
+11-09-1999 00:00:00 78740 gwtps1v2.exe
+08-28-1998 00:00:00 18432206 gwukc5.exe
+08-27-1998 00:00:00 18544901 gwusc5.exe
+10-18-1995 00:00:00 210542 gwusr1.exe
+10-18-1995 00:00:00 1404401 gwusr2.exe
+03-28-1997 00:00:00 2467040 gwusr3.exe
+10-01-1997 00:00:00 767611 gwwa4p1.exe
+03-04-1998 00:00:00 2092781 gwwebcgi.z
+08-04-1999 00:00:00 345006 gwy195.exe
+10-09-2001 00:00:00 102293 hdir501c.exe
+08-21-1998 00:00:00 1138106 highutl1.exe
+03-28-1995 00:00:00 567026 hpt004.exe
+03-09-1995 00:00:00 64329 hpt005.exe
+08-27-1996 00:00:00 602958 hpt006.exe
+03-09-1995 00:00:00 497382 hpt007.exe
+03-09-1995 00:00:00 510029 hpt008.exe
+03-13-1995 00:00:00 596667 hpt009.exe
+11-20-1995 00:00:00 942798 hpt011.exe
+08-11-1995 00:00:00 176332 hpt013.exe
+03-16-1999 00:00:00 1070543 hstdev.exe
+04-05-2002 14:51:00 246782 httpstk1.exe
+04-19-2000 00:00:00 262791 i2odrv5.exe
+07-20-1998 00:00:00 565749 ibm21y2k.exe
+09-18-1993 00:00:00 24735 ibmmem.exe
+09-18-1993 00:00:00 60883 ibmrt.exe
+07-11-2001 00:00:00 2621963 ic15fp2.exe
+02-08-2002 16:39:00 2905716 ic15fp3.exe
+04-04-2001 00:00:00 9581302 ic15sp1.exe
+12-14-2001 00:00:00 1585498 ic20fp1.exe
+01-14-2002 09:32:00 4520778 ic20fp2.exe
+05-30-2002 15:01:00 4777958 ic20sp1.exe
+03-28-2002 17:46:00 142010 ichcdump.exe
+09-20-1994 00:00:00 36043 ide.exe
+09-18-1993 00:00:00 24552 ide286.exe
+09-18-1993 00:00:00 27300 ide386.exe
+06-09-2000 00:00:00 105249 ideata5a.exe
+04-17-2000 00:00:00 1356133 ihp232.exe
+03-08-2002 15:40:00 93664 imspmfix.exe
+07-23-1998 00:00:00 7338542 in42sp2.exe
+11-08-1995 00:00:00 430410 ind41.exe
+03-20-1997 00:00:00 63751 inetcs.exe
+03-20-1997 00:00:00 60414 inetct.exe
+04-28-1997 00:00:00 69792 inetha.exe
+10-18-1995 00:00:00 1094896 inf1.exe
+10-18-1995 00:00:00 798379 inff1.exe
+01-09-2002 00:00:00 151877 installa.exe
+06-09-1995 00:00:00 836804 instll.exe
+10-09-2000 00:00:00 101582 instp5x.exe
+09-18-1993 00:00:00 39511 int215.exe
+09-18-1993 00:00:00 19521 intfix.exe
+09-18-1993 00:00:00 35521 intrud.exe
+12-04-1997 00:00:00 5594188 inwc2enh.exe
+09-18-1993 00:00:00 69340 ipc212.exe
+09-18-1993 00:00:00 24423 ipcfg.exe
+08-13-2001 00:00:00 593463 ipcost.exe
+06-24-1999 00:00:00 131414 ipg4201a.exe
+06-30-2000 00:00:00 617600 ipgc07a.exe
+02-11-2000 00:00:00 233838 ipgsb06.exe
+10-02-1999 00:00:00 107564 ipgsn10a.exe
+11-15-1999 00:00:00 44888 ipgwdoc.exe
+09-18-1993 00:00:00 65876 ipt112.exe
+09-23-1998 00:00:00 842325 ipx660.exe
+12-01-1995 00:00:00 37227 ipxspx.exe
+09-18-1993 00:00:00 22904 isa30.exe
+09-18-1993 00:00:00 31546 isa311.exe
+09-18-1993 00:00:00 24391 isarem.exe
+04-09-1997 00:00:00 49650 iwsbp1.exe
+11-21-2000 00:00:00 6073482 jbm30sp3.exe
+10-19-1995 00:00:00 109173 jcon.exe
+08-16-2001 00:00:00 185167 jr08993.exe
+08-15-2001 00:00:00 54187 jr10449.exe
+08-15-2001 00:00:00 51804 jr10470.exe
+05-29-2001 00:00:00 105466 jr10490.exe
+10-16-2000 00:00:00 17936 jr10662.exe
+10-16-2000 00:00:00 51421 jr10803.exe
+08-15-2001 00:00:00 884373 jr10823.exe
+08-15-2001 00:00:00 1909 jr10923.zip
+10-16-2000 00:00:00 53610 jr11209.exe
+10-16-2000 00:00:00 272210 jr11213.exe
+05-27-2001 00:00:00 32984 jr11223.exe
+10-16-2000 00:00:00 45200 jr11409.exe
+05-27-2001 00:00:00 488829 jr12054.exe
+08-15-2001 00:00:00 17761 jr12089.exe
+05-27-2001 00:00:00 245833 jr12125.exe
+08-15-2001 00:00:00 242650 jr12129.exe
+05-27-2001 00:00:00 144543 jr12229.exe
+05-27-2001 00:00:00 23194 jr12349.exe
+08-15-2001 00:00:00 158924 jr12415.exe
+10-16-2000 00:00:00 39844 jr12518.exe
+10-16-2000 00:00:00 42015 jr12676.exe
+05-27-2001 00:00:00 42090 jr12692.exe
+05-29-2001 00:00:00 41998 jr12705.exe
+10-16-2000 00:00:00 21903 jr12706.exe
+10-16-2000 00:00:00 75818 jr12765.exe
+08-15-2001 00:00:00 245898 jr12768.exe
+10-16-2000 00:00:00 144542 jr12773.exe
+05-29-2001 00:00:00 144542 jr12775.exe
+08-15-2001 00:00:00 144543 jr12776.exe
+10-16-2000 00:00:00 44352 jr12777.exe
+05-27-2001 00:00:00 44355 jr12778.exe
+08-15-2001 00:00:00 43721 jr12828.exe
+05-27-2001 00:00:00 52823 jr12890.exe
+10-16-2000 00:00:00 52824 jr12947.exe
+10-16-2000 00:00:00 74323 jr12978.exe
+05-27-2001 00:00:00 74323 jr12979.exe
+05-29-2001 00:00:00 74326 jr12987.exe
+05-27-2001 00:00:00 16573256 jr13042.exe
+08-15-2001 00:00:00 16586769 jr13046.exe
+08-15-2001 00:00:00 170632 jr13047.exe
+08-15-2001 00:00:00 55210 jr13105.exe
+08-15-2001 00:00:00 124966 jr13147.exe
+10-16-2000 00:00:00 43318 jr13259.exe
+10-16-2000 00:00:00 33183 jr13461.exe
+05-27-2001 00:00:00 84700 jr13554.exe
+10-16-2000 00:00:00 84649 jr13555.exe
+05-27-2001 00:00:00 52564 jr13557.exe
+10-16-2000 00:00:00 52161 jr13558.exe
+05-29-2001 00:00:00 52167 jr13559.exe
+05-27-2001 00:00:00 54942 jr13616.exe
+10-16-2000 00:00:00 54947 jr13617.exe
+08-15-2001 00:00:00 56424 jr13619.exe
+09-17-1999 00:00:00 71827 jr13627.exe
+10-16-2000 00:00:00 83182 jr13637.exe
+05-29-2001 00:00:00 108483 jr13722.exe
+08-15-2001 00:00:00 170173 jr13734.exe
+08-15-2001 00:00:00 641941 jr13748.exe
+05-29-2001 00:00:00 641950 jr13749.exe
+05-29-2001 00:00:00 579521 jr13886.exe
+08-15-2001 00:00:00 126491 jr13891.exe
+05-27-2001 00:00:00 109292 jr14132.exe
+08-15-2001 00:00:00 109181 jr14134.exe
+05-29-2001 00:00:00 39830 jr14185.exe
+08-15-2001 00:00:00 72780 jr14278.exe
+08-15-2001 00:00:00 345689 jr14358.exe
+05-27-2001 00:00:00 642240 jr14359.exe
+10-16-2000 00:00:00 642388 jr14360.exe
+05-27-2001 00:00:00 313078 jr14367.exe
+05-27-2001 00:00:00 109587 jr14402.exe
+08-15-2001 00:00:00 71603 jr14457.exe
+08-15-2001 00:00:00 567270 jr14500.exe
+08-15-2001 00:00:00 157611 jr14523.exe
+08-15-2001 00:00:00 161290 jr14556.exe
+05-27-2001 00:00:00 161439 jr14585.exe
+10-16-2000 00:00:00 161435 jr14586.exe
+10-16-2000 00:00:00 186037 jr14840.exe
+10-16-2000 00:00:00 368604 jr14936.exe
+08-15-2001 00:00:00 115132 jr15013.exe
+08-15-2001 00:00:00 568164 jr15133.exe
+08-15-2001 00:00:00 217169 jr15338.exe
+08-15-2001 00:00:00 362664 jr15396.exe
+08-15-2001 00:00:00 104143 jr15509.exe
+08-15-2001 00:00:00 473822 jr15544.exe
+07-25-2001 00:00:00 484196 jssl11d.exe
+07-20-2001 00:00:00 36251555 jvm122.exe
+02-28-2002 08:06:00 49007010 jvm131.exe
+03-28-2001 00:00:00 48672254 jzfd3sp1.exe
+07-17-1997 00:00:00 66469 killq.exe
+03-01-1994 00:00:00 202716 l11f01.exe
+03-01-1994 00:00:00 202878 l11g01.exe
+03-01-1994 00:00:00 202460 l11i01.exe
+01-06-1994 00:00:00 23583 l11p06.exe
+03-01-1994 00:00:00 202249 l11s01.exe
+11-24-1993 00:00:00 30533 l11u05.exe
+04-20-1999 00:00:00 206616 lanchk.exe
+10-21-1996 00:00:00 341280 landr9.exe
+05-14-1998 00:00:00 4610909 landrv.exe
+09-10-1996 00:00:00 24799 lanwcs.exe
+09-04-1996 00:00:00 37088 lanwct.exe
+09-04-1996 00:00:00 42514 lanwes.exe
+09-11-1996 00:00:00 42417 lanwfr.exe
+09-10-1996 00:00:00 36855 lanwha.exe
+09-04-1996 00:00:00 42397 lanwit.exe
+01-31-2002 16:00:00 16012931 lanwp02.exe
+12-16-1996 00:00:00 342390 lat002.exe
+09-18-1993 00:00:00 133326 ld401a.exe
+02-07-2000 00:00:00 166765 ldr312ft.exe
+09-18-1993 00:00:00 26450 leap.exe
+06-09-1994 00:00:00 180540 lg4084.exe
+12-14-1995 00:00:00 91840 lg42l4.exe
+10-11-1995 00:00:00 72061 li3pre.exe
+06-02-1998 00:00:00 258605 lib311b.exe
+09-20-1999 00:00:00 273268 lib312d.exe
+02-23-2000 00:00:00 977416 libupj4.exe
+06-26-1995 00:00:00 111269 lo30a2.exe
+06-26-1995 00:00:00 94927 lo30t1.exe
+09-18-1993 00:00:00 105128 load.exe
+08-26-1998 00:00:00 111722 loaddll1.exe
+09-18-1993 00:00:00 20810 locins.exe
+03-09-1995 00:00:00 74768 log376.exe
+09-15-1997 00:00:00 269333 log410a.exe
+02-23-2000 00:00:00 99524 longnam.exe
+03-05-1997 00:00:00 1563061 lpo51a.exe
+03-14-1997 00:00:00 115601 lpo51b.exe
+06-12-1995 00:00:00 373114 lw42w2.exe
+09-20-1996 00:00:00 986579 lw50w1.exe
+08-21-1996 00:00:00 79276 lwg50a.exe
+08-18-1998 00:00:00 115527 lwp001.exe
+08-20-1998 00:00:00 54951 lwp002.exe
+05-06-1996 00:00:00 447982 lwp413.exe
+11-30-1994 00:00:00 231591 lwp423.exe
+05-18-1998 00:00:00 26516 lwp501.exe
+05-15-1998 00:00:00 27895 lwp511.exe
+09-18-1993 00:00:00 21913 lwpo30.exe
+09-03-1997 00:00:00 47334 lwpping.exe
+08-09-1999 00:00:00 356846 lzfw01c.exe
+10-18-1993 00:00:00 33252 lzfwdi.exe
+07-14-1999 00:00:00 1083871 lzfwlf.exe
+06-16-1995 00:00:00 29057 lzfwqa.exe
+09-07-1994 00:00:00 26848 lzw001.exe
+05-16-1995 00:00:00 29431 lzw002.exe
+09-18-1993 00:00:00 151295 lzw40.exe
+09-18-1993 00:00:00 29379 m30pat.exe
+07-24-1996 00:00:00 122720 macfil.exe
+07-10-1997 00:00:00 347278 macpt3d.exe
+05-29-1996 00:00:00 193792 mactsa.bin
+07-23-1996 00:00:00 232349 mactsa.exe
+02-21-1996 00:00:00 210004 mailcl.exe
+03-13-1995 00:00:00 48964 map312.exe
+11-24-1997 00:00:00 144574 map410b.exe
+10-10-2001 00:00:00 127956 masv_sp3.exe
+02-28-2001 00:00:00 266084 mbcmnup1.exe
+08-13-1998 00:00:00 508288 mclupd6a.bin
+09-18-1993 00:00:00 22803 mcmfm.exe
+02-11-1994 00:00:00 37710 mdf178.exe
+09-18-1993 00:00:00 87520 menu34.exe
+11-15-1993 00:00:00 20214 menuhi.exe
+09-18-1993 00:00:00 91376 menus.exe
+08-15-2001 00:00:00 5040875 mgt22010.exe
+11-03-1993 00:00:00 683946 mhs173.exe
+02-14-1994 00:00:00 656047 mhs183.exe
+02-07-1994 00:00:00 664789 mhs184.exe
+11-03-1997 00:00:00 85281 mhsmcu.exe
+09-18-1993 00:00:00 54627 mhsmd.exe
+08-16-1994 00:00:00 604103 mhsslt.exe
+06-30-1995 00:00:00 132603 mhsvr1.exe
+08-01-1996 00:00:00 449605 migrat.exe
+09-18-1993 00:00:00 33708 mirrem.exe
+01-05-2000 00:00:00 27044 mixmod6.exe
+09-18-1993 00:00:00 96673 mkuser.exe
+09-18-1995 00:00:00 68504 mon176.exe
+05-18-1995 00:00:00 66024 monsft.exe
+09-18-1993 00:00:00 424897 morebk.exe
+09-18-1993 00:00:00 37818 mountr.exe
+09-18-1993 00:00:00 19452 mouse.exe
+02-03-1994 00:00:00 32801 mpr182.exe
+07-15-1994 00:00:00 125166 mpr199.exe
+06-04-1996 00:00:00 1066126 mpr31a.exe
+10-28-1996 00:00:00 1082729 mpr31b.exe
+09-23-1994 00:00:00 31245 mprper.exe
+03-24-1995 00:00:00 38997 mprul3.exe
+10-11-1995 00:00:00 122440 mprx25.exe
+08-02-1996 00:00:00 328085 msml21.exe
+10-05-1998 00:00:00 5876316 msmlos21.exe
+08-02-1999 00:00:00 70822 msmpcu.exe
+05-31-2000 00:00:00 6355314 mw26sp3.exe
+07-31-2000 00:00:00 119531 mw26trd1.exe
+11-13-2000 00:00:00 3054719 mw27sp1.exe
+11-23-1999 00:00:00 27173 mw5mcal1.exe
+05-17-2000 00:00:00 253007 mwhp01b.exe
+01-25-2002 11:47:00 255066 mwhp01c.exe
+09-01-2000 00:00:00 9813556 mwinoc1k.exe
+09-01-2000 00:00:00 8298211 mwinoc2k.exe
+02-20-2002 14:35:00 141530 mwipgrop.exe
+10-09-1996 00:00:00 566807 mwmis01.exe
+01-26-1999 00:00:00 1070535 mwnma26.exe
+10-16-1998 00:00:00 265545 mwnma3a.exe
+10-16-1998 00:00:00 300304 mwnma4a.exe
+04-12-2001 00:00:00 2180810 mwnmaupd.exe
+01-12-2000 00:00:00 154598 mwnxp26.exe
+04-09-2001 00:00:00 339201 mwnxpfix.exe
+08-20-1999 00:00:00 1502706 mwzen01.exe
+03-28-2001 00:00:00 58460632 mzfd3sp1.exe
+05-24-2001 00:00:00 2407200 n51_nis1.exe
+05-16-2000 00:00:00 6840962 n8slinux.01
+02-18-1998 00:00:00 217465 na4nty2k.exe
+09-18-1993 00:00:00 48510 nacs2.exe
+05-28-1996 00:00:00 64238 nadhep.exe
+03-23-1999 00:00:00 1777018 nal201p2.exe
+10-29-1996 00:00:00 38276 nam312.exe
+06-06-2000 00:00:00 199571 nam41d.exe
+05-24-2002 15:12:00 104382 nat600d.exe
+09-18-1993 00:00:00 322806 nbckup.exe
+01-10-1997 00:00:00 21328 nbora.exe
+08-12-1997 00:00:00 18843 nc1tip.txt
+06-03-2002 09:30:00 838367 nccutl10.exe
+10-24-2000 00:00:00 7725859 nce8slr1.z
+09-18-1993 00:00:00 77251 nconfg.exe
+10-10-1997 00:00:00 19889 ncpec.exe
+09-15-1997 00:00:00 144892 ncpy410a.exe
+11-21-2000 00:00:00 136962 ncs3.exe
+10-01-1996 00:00:00 704205 ncv201.exe
+10-01-1996 00:00:00 811853 ncv202.exe
+04-21-1998 00:00:00 489774 ncv20y2k.exe
+11-12-2001 00:00:00 142314 ndb410q.exe
+02-21-2002 13:36:00 820712 ndp21p3c.exe
+06-21-2002 12:06:00 853818 ndp21p4.exe
+10-17-2001 00:00:00 1008445 ndp2xp7.exe
+02-21-2002 13:53:00 530101 ndpcnw6.exe
+02-21-2002 13:48:00 909348 ndpcsp3a.exe
+07-17-2001 00:00:00 94047 ndpsinf.exe
+10-04-2001 00:00:00 11673051 ndpsw2k.exe
+09-18-1993 00:00:00 59495 ndr345.exe
+02-02-2000 00:00:00 112722 nds4ntp1.exe
+08-17-2000 00:00:00 507960 nds4ntu3.exe
+10-27-2000 00:00:00 3437308 nds8lnx1.gz
+07-17-2001 00:00:00 14133762 ndsas3s1.exe
+09-18-1993 00:00:00 24182 ndscsi.exe
+09-18-1993 00:00:00 41652 ndspx.exe
+07-20-2000 00:00:00 6712 ndssch.gz
+09-18-1993 00:00:00 20023 ndstac.exe
+09-18-1993 00:00:00 211239 ne286.exe
+10-24-2000 00:00:00 5894979 ned8slr1.z
+05-03-2000 00:00:00 82148198 nesn451a.exe
+12-20-2000 00:00:00 1157470 nesn51b.exe
+11-28-2001 00:00:00 866140 nesn51c.exe
+03-05-2002 06:54:00 865375 nesn51d.exe
+03-16-1999 00:00:00 138202 netarng3.exe
+02-04-1998 00:00:00 73822 netfr.exe
+03-12-1996 00:00:00 306211 netusr.exe
+02-04-1998 00:00:00 74054 netwbr.exe
+02-04-1998 00:00:00 56229 netwde.exe
+08-28-1996 00:00:00 27699 netwdk.exe
+02-02-1998 00:00:00 67776 netwes.exe
+02-12-1998 00:00:00 59210 netwit.exe
+08-28-1996 00:00:00 28000 netwno.exe
+09-10-1996 00:00:00 53501 netwru.exe
+08-23-1996 00:00:00 27741 netwsv.exe
+03-18-2002 15:27:00 1539054 nfap1sp1.exe
+08-22-1994 00:00:00 290090 nfs193.exe
+12-30-1997 00:00:00 2266015 nfs203.exe
+11-23-1998 00:00:00 2007873 nfs205.exe
+07-20-2001 00:00:00 6472548 nfs30sp2.exe
+03-06-2002 15:56:00 1310460 nfs30sp3a.exe
+05-29-2002 14:59:00 1186381 nfs3nwci.exe
+08-28-2001 00:00:00 5440307 nfs3sp1.exe
+02-02-2001 00:00:00 1280002 nfsadmn2.exe
+01-20-1998 00:00:00 38114 nfsmlaup.exe
+08-02-1999 00:00:00 35803 nfsnam23.exe
+09-18-1993 00:00:00 245015 ngm121.exe
+09-18-1993 00:00:00 1240500 ngm137.exe
+09-18-1993 00:00:00 145298 ngm138.exe
+09-18-1993 00:00:00 145010 ngm139.exe
+10-28-1993 00:00:00 781292 ngm170.exe
+12-03-1993 00:00:00 202093 ngm175.exe
+12-06-1993 00:00:00 201248 ngm176.exe
+05-26-1994 00:00:00 279862 ngm192.exe
+12-20-1996 00:00:00 945888 ngm211.exe
+08-05-1995 00:00:00 1403369 ngwadm.exe
+08-13-1996 00:00:00 1810533 ngwaup.exe
+10-31-1995 00:00:00 106862 ngwmfc.exe
+03-15-1995 00:00:00 662953 ngwsnc.exe
+09-18-1993 00:00:00 27283 ni5010.exe
+07-10-2001 00:00:00 786223 nicid157.exe
+07-10-2001 00:00:00 761229 nicie157.exe
+01-15-2002 11:38:00 59300 nicimig.tgz
+01-17-2002 09:35:00 6802379 nims265.tgz
+01-31-2002 10:19:00 2526415 nims265.zip
+01-31-2002 11:14:00 121765 nims265a.zip
+01-14-2002 16:09:00 4894646 nims26l.tgz
+01-14-2002 16:05:00 2492982 nims26n.zip
+02-27-2002 16:49:00 5385381 nims26sb.z
+11-08-1999 00:00:00 343052 nims2_1a.exe
+04-15-2002 15:54:00 12495019 nims303.tar.z
+04-15-2002 15:53:00 7563916 nims303.tgz
+04-15-2002 15:54:00 7696073 nims303.zip
+05-23-1997 00:00:00 1252720 nip202.exe
+10-23-1998 00:00:00 1180104 nip203.exe
+04-19-1996 00:00:00 6212358 nip22b.exe
+07-09-1996 00:00:00 555990 nip318.exe
+07-09-1996 00:00:00 69020 nip319.exe
+11-02-2001 00:00:00 2489203 nipp10a.exe
+09-19-2000 00:00:00 3753117 nipt1.exe
+03-05-1996 00:00:00 6369467 nipw22.exe
+05-29-1996 00:00:00 42316 nipw2x.exe
+06-07-2000 00:00:00 4286209 njcl5a.exe
+06-10-1998 00:00:00 102325 nls212.exe
+07-24-2000 00:00:00 155414 nlsdll.exe
+05-25-2001 00:00:00 16952278 nlslsp6.exe
+01-04-2000 00:00:00 215729 nlsty2k.exe
+11-28-1995 00:00:00 1462112 nms002.exe
+03-08-1994 00:00:00 48618 nmsddf.exe
+11-15-1994 00:00:00 434841 nmsxp1.exe
+09-18-1993 00:00:00 28499 nnscpt.exe
+09-18-1993 00:00:00 88964 nnst40.exe
+09-18-1993 00:00:00 89092 nnstll.exe
+07-25-1995 00:00:00 32483 not131.exe
+10-12-1998 00:00:00 6707094 notes41.exe
+06-08-2000 00:00:00 4556171 notes51.exe
+09-18-1993 00:00:00 24900 novadf.exe
+09-18-1993 00:00:00 30691 np600a.exe
+08-02-1999 00:00:00 17097790 nppb_1.exe
+08-02-1999 00:00:00 17097771 nppb_2.exe
+03-15-2002 16:33:00 633317 nps15dpa.exe
+06-28-2002 09:08:00 31183790 nps15sp1.exe
+09-10-2001 00:00:00 8200267 npsgad01.exe
+04-12-2001 00:00:00 114902 npsnsapi.exe
+02-11-2002 15:57:00 615863 nptr95b.exe
+06-30-1997 00:00:00 22915 nrsbuild.exe
+06-23-1997 00:00:00 793469 nrsnt.exe
+06-18-1998 00:00:00 53586091 nsbgwsp3.exe
+03-22-1994 00:00:00 455182 nsd004.exe
+08-21-1998 00:00:00 1964329 nsr511n.zip
+06-24-1996 00:00:00 1935353 nsrtr51n.zip
+02-13-2002 13:36:00 93785 nsschk1a.exe
+07-30-1997 00:00:00 116845 nsync1.exe
+09-16-1999 00:00:00 10933860 nt411b.exe
+10-26-1998 00:00:00 1084753 nt411p1.exe
+04-06-1999 00:00:00 744586 nt430p2.exe
+06-22-1999 00:00:00 834534 nt451p1.exe
+03-23-2000 00:00:00 920405 nt46pt1.exe
+10-03-1999 00:00:00 4017917 nt46sp2.exe
+08-11-2000 00:00:00 765887 nt471pt2.exe
+06-13-2000 00:00:00 448015 nt47pt3.exe
+05-09-2002 07:26:00 1081217 nt480pt5.exe
+11-06-2001 00:00:00 898400 nt481pt1.exe
+06-14-2002 14:07:00 291026 nt483pt2.exe
+11-19-1998 00:00:00 150230 ntprint.exe
+07-18-1995 00:00:00 114593 ntwin.exe
+09-18-1993 00:00:00 28138 nver30.exe
+01-07-1997 00:00:00 28798 nw3dfs.exe
+01-07-1997 00:00:00 24257 nw4dfs.exe
+11-13-2000 00:00:00 80377034 nw4sp9.exe
+08-27-2001 00:00:00 866224 nw4wsock.exe
+12-20-2000 00:00:00 158210659 nw50sp6a.exe
+07-23-2001 00:00:00 490599 nw51fs1.exe
+02-17-2000 00:00:00 684981 nw51inst.exe
+08-21-2001 00:00:00 513640 nw51nrm1.exe
+07-24-2001 00:00:00 294037836 nw51sp3.exe
+02-25-2002 11:26:00 300006242 nw51sp4.exe
+04-27-2000 00:00:00 332610 nw51upd1.exe
+06-24-2002 14:54:00 3250529 nw56up1.exe
+09-09-1999 00:00:00 38435 nw5nss.exe
+02-17-2000 00:00:00 251511 nw5nwip.exe
+05-16-2000 00:00:00 169896 nw5psrv2.exe
+06-20-2000 00:00:00 378831 nw5tcp.exe
+03-22-2002 16:33:00 1533365 nw6nss1a.exe
+10-22-2001 00:00:00 633339 nw6sms1a.exe
+03-06-2002 17:15:00 237785656 nw6sp1.exe
+03-11-2002 12:19:00 568253661 nw6sp1ef.exe
+03-11-2002 12:59:00 567439767 nw6sp1ef56.exe
+03-22-2002 12:23:00 566604272 nw6sp1eg.exe
+03-22-2002 13:02:00 566458792 nw6sp1ei.exe
+03-11-2002 10:57:00 566528467 nw6sp1ep.exe
+03-22-2002 16:05:00 567333526 nw6sp1er.exe
+03-13-2002 16:55:00 565955338 nw6sp1es.exe
+03-23-1999 00:00:00 1344552 nwadmnp1.exe
+05-10-1995 00:00:00 478371 nwc001.exe
+02-24-1995 00:00:00 251557 nwc002.exe
+01-31-1996 00:00:00 1598884 nwc201.exe
+11-22-1995 00:00:00 1524102 nwc202.exe
+01-22-1998 00:00:00 1328082 nwc206.exe
+11-18-1996 00:00:00 1382188 nwc207.exe
+10-24-1996 00:00:00 547655 nwc208.exe
+08-12-1997 00:00:00 29587 nwc2tp.txt
+09-18-1993 00:00:00 21386 nwc386.exe
+10-05-1994 00:00:00 102446 nwcdll.exe
+02-27-1996 00:00:00 33443 nwcinf.exe
+09-11-1998 00:00:00 22331 nwcmod.exe
+09-20-1995 00:00:00 71514 nwcncs.exe
+07-11-1997 00:00:00 37424 nwcppp.exe
+03-13-2000 00:00:00 36603464 nwcssp1.exe
+03-23-2000 00:00:00 170397 nwcsupd1.exe
+02-14-1995 00:00:00 367734 nwcwin.exe
+05-22-1998 00:00:00 367002 nwcwrt.exe
+12-16-1996 00:00:00 77941 nwda01.exe
+05-08-2002 12:21:00 147838 nwftpd6.exe
+01-29-2002 15:30:00 128211 nwipadm4.exe
+11-01-1995 00:00:00 571623 nwl11e.exe
+11-01-1995 00:00:00 579046 nwl11f.exe
+11-01-1995 00:00:00 585907 nwl11g.exe
+11-01-1995 00:00:00 576676 nwl11i.exe
+11-01-1995 00:00:00 579137 nwl11s.exe
+12-13-1995 00:00:00 184137 nwltid.exe
+04-09-1999 00:00:00 13639159 nwmac.exe
+03-23-1999 00:00:00 2264037 nwmp2.exe
+06-15-2001 00:00:00 16902888 nwovly2.exe
+04-02-1997 00:00:00 2536221 nwpa300.exe
+05-07-2001 00:00:00 155727 nwpa5.exe
+12-07-2001 00:00:00 254835 nwpapt2a.exe
+11-15-1993 00:00:00 26440 nwparr.exe
+06-09-1999 00:00:00 1341903 nwpaup1a.exe
+02-27-1997 00:00:00 7763041 nws25b.exe
+03-11-1999 00:00:00 73306 nwsaahpr.exe
+02-29-2000 00:00:00 12091868 nwsb41wa.exe
+08-11-1999 00:00:00 38819 nwsp2aai.exe
+02-04-2000 00:00:00 287681 nwsso.exe
+02-24-2000 00:00:00 112641 nwtape1.exe
+11-15-1993 00:00:00 66111 nwtlg.exe
+06-16-1995 00:00:00 126883 o31mci.exe
+07-25-1995 00:00:00 73911 o4crtl.exe
+04-27-1999 00:00:00 4957532 odbcbeta.exe
+11-08-2001 00:00:00 6488080 odemandb.exe
+07-28-1999 00:00:00 671132 odi33g.exe
+07-30-1997 00:00:00 409920 odiwan1.exe
+07-18-1995 00:00:00 48296 of31pt.exe
+09-18-1993 00:00:00 111219 os2p1.exe
+12-18-1998 00:00:00 610164 os2pt2.exe
+11-26-1996 00:00:00 896477 os2u1.exe
+05-30-2000 00:00:00 4229434 os4pt1.exe
+03-02-2001 00:00:00 4227811 os5pt2a.exe
+09-18-1993 00:00:00 216072 othdrv.exe
+12-04-1996 00:00:00 66394 ovvmdl.exe
+10-25-1996 00:00:00 26153 p1000.exe
+01-03-1995 00:00:00 242785 p10g05.exe
+01-03-1995 00:00:00 242514 p10i05.exe
+01-03-1995 00:00:00 242647 p10s05.exe
+05-12-1995 00:00:00 33893 p2scsi.exe
+05-11-1999 00:00:00 659891 pager1.exe
+09-18-1993 00:00:00 50002 pat301.exe
+09-18-1993 00:00:00 50015 pat303.exe
+09-18-1993 00:00:00 49975 pat304.exe
+09-18-1993 00:00:00 49878 pat306.exe
+09-18-1993 00:00:00 29863 pat311.exe
+09-18-1993 00:00:00 49888 pat312.exe
+09-18-1993 00:00:00 49823 pat314.exe
+09-18-1993 00:00:00 33034 pat315.exe
+09-18-1993 00:00:00 49900 pat317.exe
+09-18-1993 00:00:00 49858 pat321.exe
+09-18-1993 00:00:00 49901 pat323.exe
+09-18-1993 00:00:00 50232 pat326.exe
+09-18-1993 00:00:00 49842 pat334.exe
+09-18-1993 00:00:00 49930 pat354.exe
+09-18-1993 00:00:00 30322 patman.exe
+09-18-1993 00:00:00 35789 paudfx.exe
+07-20-1998 00:00:00 565974 pbm21y2k.exe
+06-15-1994 00:00:00 63237 pburst.exe
+09-18-1993 00:00:00 35522 pcn22x.exe
+09-18-1993 00:00:00 25266 pcn23x.exe
+09-18-1993 00:00:00 46823 pcn2pa.exe
+09-18-1993 00:00:00 30816 pcnscs.exe
+09-18-1993 00:00:00 22801 pdf.exe
+09-18-1993 00:00:00 38018 pdf311.exe
+08-27-2001 00:00:00 8552350 pdlckcmp.exe
+01-22-1997 00:00:00 699150 perfectf.exe
+06-07-2000 00:00:00 214597 pfar6.exe
+09-18-1993 00:00:00 26618 pfix1.exe
+09-18-1993 00:00:00 26734 pfix3.exe
+07-18-1995 00:00:00 23435 pifoff.exe
+08-26-1999 00:00:00 70799 pkernel.exe
+08-12-1999 00:00:00 252312 pkis.pdf
+02-08-2000 00:00:00 772450 pkisnmas.exe
+09-11-1995 00:00:00 63891 plpd8.exe
+03-28-2002 12:17:00 212389 plpdsoc2.exe
+12-13-1995 00:00:00 181777 pnwtid.exe
+11-17-1995 00:00:00 186437 pnxtfx.exe
+01-03-2001 00:00:00 4463887 preds8a.exe
+09-18-1993 00:00:00 75026 pro10.exe
+11-01-1995 00:00:00 28781 prog.exe
+09-18-1993 00:00:00 23802 propth.exe
+01-29-1996 00:00:00 25129 prt312.exe
+09-18-1993 00:00:00 31193 prtime.exe
+07-20-1995 00:00:00 130827 prupc.exe
+09-18-1993 00:00:00 34893 ps110.exe
+09-18-1993 00:00:00 25963 ps2286.exe
+09-18-1993 00:00:00 24576 ps22is.exe
+09-18-1993 00:00:00 42925 ps2311.exe
+09-18-1993 00:00:00 29867 ps2386.exe
+09-18-1993 00:00:00 28205 ps2cmb.exe
+09-18-1993 00:00:00 23372 ps2esd.exe
+09-18-1993 00:00:00 24336 ps2fx.exe
+09-18-1993 00:00:00 76207 ps2isa.exe
+09-18-1993 00:00:00 23955 ps2m57.exe
+12-14-1993 00:00:00 36351 ps2opt.exe
+06-30-1995 00:00:00 162367 ps3x02.exe
+01-23-1996 00:00:00 85566 ps4x03.exe
+10-24-2001 00:00:00 172677 psrvr112.exe
+09-18-1993 00:00:00 52324 ptf286.exe
+09-18-1993 00:00:00 112633 ptf350.exe
+09-18-1993 00:00:00 48074 ptf374.exe
+09-18-1993 00:00:00 39025 ptf378.exe
+09-18-1993 00:00:00 30600 ptf380.exe
+03-25-1994 00:00:00 525519 ptf410.exe
+09-29-1993 00:00:00 501986 ptf411.exe
+09-29-1993 00:00:00 350294 ptf412.exe
+09-29-1993 00:00:00 473981 ptf413.exe
+09-29-1993 00:00:00 480777 ptf414.exe
+09-29-1993 00:00:00 488223 ptf415.exe
+10-22-1993 00:00:00 147005 ptf424.exe
+08-14-1995 00:00:00 109320 ptf425.exe
+10-18-1993 00:00:00 109064 ptf426.exe
+10-07-1994 00:00:00 292097 ptf437.exe
+04-12-1994 00:00:00 464842 ptf569.exe
+11-16-1994 00:00:00 453054 pu3x01.exe
+05-02-1995 00:00:00 553603 pu4x03.exe
+05-29-2002 17:29:00 280505 pwdsnc1.exe
+05-31-2002 11:45:00 758411 pxy031.exe
+08-31-2000 00:00:00 785651 pxyauth.exe
+11-01-1995 00:00:00 25270 qa.exe
+07-25-1995 00:00:00 22674 qaos2.exe
+07-18-1995 00:00:00 21421 qkinst.exe
+12-04-1995 00:00:00 390862 qlfix.exe
+10-05-1995 00:00:00 21028 quest.exe
+11-23-1998 00:00:00 13847723 r16524br.exe
+11-23-1998 00:00:00 15367885 r16524ce.exe
+11-23-1998 00:00:00 13974046 r16524cf.exe
+11-23-1998 00:00:00 14636368 r16524cs.exe
+11-23-1998 00:00:00 14606815 r16524ct.exe
+11-23-1998 00:00:00 14396472 r16524cz.exe
+11-23-1998 00:00:00 14526983 r16524de.exe
+11-23-1998 00:00:00 13996151 r16524dk.exe
+11-24-1998 00:00:00 14083999 r16524es.exe
+11-24-1998 00:00:00 14036283 r16524fr.exe
+11-24-1998 00:00:00 14168496 r16524it.exe
+11-30-1998 00:00:00 15194180 r16524jp.exe
+11-24-1998 00:00:00 14717983 r16524kr.exe
+11-24-1998 00:00:00 13957605 r16524ma.exe
+11-24-1998 00:00:00 13018097 r16524nl.exe
+11-24-1998 00:00:00 14282386 r16524no.exe
+11-24-1998 00:00:00 14592999 r16524oz.exe
+11-24-1998 00:00:00 14683051 r16524pl.exe
+11-24-1998 00:00:00 13868667 r16524ru.exe
+11-24-1998 00:00:00 14075816 r16524su.exe
+11-24-1998 00:00:00 14090792 r16524sv.exe
+11-24-1998 00:00:00 14598010 r16524uk.exe
+11-23-1998 00:00:00 14633171 r16524us.exe
+10-08-1999 00:00:00 13892746 r16525br.exe
+10-08-1999 00:00:00 15412960 r16525ce.exe
+10-08-1999 00:00:00 14019075 r16525cf.exe
+10-08-1999 00:00:00 14681320 r16525cs.exe
+10-08-1999 00:00:00 14651741 r16525ct.exe
+10-08-1999 00:00:00 14443408 r16525cz.exe
+08-24-1999 00:00:00 14572069 r16525de.exe
+10-08-1999 00:00:00 14041141 r16525dk.exe
+10-08-1999 00:00:00 14129003 r16525es.exe
+10-08-1999 00:00:00 14081224 r16525fr.exe
+10-08-1999 00:00:00 14213472 r16525it.exe
+10-08-1999 00:00:00 15239217 r16525jp.exe
+10-08-1999 00:00:00 14762877 r16525kr.exe
+10-08-1999 00:00:00 14004580 r16525ma.exe
+10-08-1999 00:00:00 14520305 r16525nl.exe
+10-08-1999 00:00:00 14327373 r16525no.exe
+10-08-1999 00:00:00 14638087 r16525oz.exe
+10-08-1999 00:00:00 14730025 r16525pl.exe
+10-08-1999 00:00:00 13915653 r16525ru.exe
+10-08-1999 00:00:00 14120807 r16525su.exe
+10-08-1999 00:00:00 14135776 r16525sv.exe
+10-08-1999 00:00:00 14643087 r16525uk.exe
+08-24-1999 00:00:00 14678258 r16525us.exe
+11-20-1998 00:00:00 34195974 r524east.exe
+11-21-1998 00:00:00 29934184 r524kcc.exe
+11-21-1998 00:00:00 40546603 r524mult.exe
+11-21-1998 00:00:00 33377124 r524scan.exe
+11-21-1998 00:00:00 17133749 r524us.exe
+11-21-1998 00:00:00 20919099 r524usde.exe
+12-21-1998 00:00:00 21776910 r524usjp.exe
+10-11-1999 00:00:00 33695357 r525east.exe
+10-11-1999 00:00:00 29387389 r525kcc.exe
+10-11-1999 00:00:00 39896412 r525mult.exe
+10-11-1999 00:00:00 32843372 r525scan.exe
+10-11-1999 00:00:00 18205814 r525us.exe
+10-11-1999 00:00:00 20711743 r525usde.exe
+10-14-1999 00:00:00 19744627 r525usjp.exe
+02-25-1999 00:00:00 21883384 r551en.exe
+02-26-1999 00:00:00 38653860 r551mult.exe
+02-25-1999 00:00:00 38136537 r551scan.exe
+10-19-1999 00:00:00 37890181 r552mult.exe
+10-19-1999 00:00:00 37404535 r552scan.exe
+02-11-2000 00:00:00 22183381 r553aen.exe
+02-11-2000 00:00:00 32216751 r553aest.exe
+02-11-2000 00:00:00 24925427 r553ajp.exe
+02-11-2000 00:00:00 27749699 r553akcc.exe
+02-11-2000 00:00:00 38006860 r553amlt.exe
+02-11-2000 00:00:00 37454601 r553ascn.exe
+04-06-1998 00:00:00 87518 rad102.exe
+11-23-1998 00:00:00 260651 rad104.exe
+03-04-2002 16:09:00 118100 radatr4.exe
+02-28-1997 00:00:00 575303 ramac.exe
+06-07-1995 00:00:00 66500 rbuild.exe
+02-27-1998 00:00:00 23539 rdmsg0.exe
+04-03-2000 00:00:00 91403 revfhrft.exe
+07-27-2001 00:00:00 138359 rinstall.exe
+11-04-1993 00:00:00 211615 ripsap.exe
+09-18-1993 00:00:00 192641 rlit92.exe
+09-18-1993 00:00:00 155252 rlit93.exe
+07-18-1995 00:00:00 780218 rofwin.exe
+09-18-1993 00:00:00 36120 routez.exe
+09-18-1993 00:00:00 96684 routfx.exe
+10-05-1998 00:00:00 141605 rplkt5.exe
+05-11-1994 00:00:00 72596 rsync1.exe
+09-18-1993 00:00:00 23294 rxnet.exe
+03-28-2001 00:00:00 48534006 rzfd3sp1.exe
+06-16-1994 00:00:00 39313 saa005.exe
+08-16-2001 00:00:00 534003 saa008.exe
+08-11-1994 00:00:00 80219 saa010.exe
+09-01-1994 00:00:00 142620 saa012.exe
+08-16-2001 00:00:00 943059 saa023.exe
+12-24-1996 00:00:00 154805 saa031.exe
+08-16-2001 00:00:00 4659719 saa20040.exe
+08-16-2001 00:00:00 2550556 saa21030.exe
+08-15-2001 00:00:00 63688405 saa22010.exe
+08-15-2001 00:00:00 9396094 saa2210e.exe
+08-15-2001 00:00:00 10338946 saa30020.exe
+08-15-2001 00:00:00 9315931 saa40020.exe
+06-29-2000 00:00:00 169062 saa4pt1.exe
+06-27-1995 00:00:00 20269 saamic.exe
+06-03-1998 00:00:00 1646 saapatch.txt
+11-30-1995 00:00:00 32233 saarot.exe
+08-03-1995 00:00:00 29347 saaupg.exe
+06-26-1996 00:00:00 282396 sback6.exe
+06-07-2001 00:00:00 376293 sbcon1.exe
+07-20-1998 00:00:00 564045 sbm21y2k.exe
+03-02-2001 00:00:00 8341393 sbs5pt2a.exe
+12-05-1997 00:00:00 244604 schcmp2.exe
+08-12-1999 00:00:00 151673 scmddoc.exe
+05-04-2001 00:00:00 167290 scmdflt.exe
+09-18-1993 00:00:00 40595 sec286.exe
+05-25-1994 00:00:00 29661 secdoc.exe
+09-18-1993 00:00:00 310609 secdos.exe
+05-26-2000 00:00:00 7039614 secexp64.01
+08-10-2000 00:00:00 5016153 secexp64.z
+11-15-1993 00:00:00 167904 seclog.exe
+09-18-1993 00:00:00 632669 secnns.exe
+09-18-1993 00:00:00 449590 secprn.exe
+09-18-1993 00:00:00 322007 secsys.exe
+05-26-2000 00:00:00 7351040 secus64.01
+08-10-2000 00:00:00 5457221 secus64.z
+09-18-1993 00:00:00 510733 secut1.exe
+09-18-1993 00:00:00 556873 secut2.exe
+09-18-1993 00:00:00 431691 secut3.exe
+08-29-2001 00:00:00 134525 servinst.exe
+05-25-1996 00:00:00 367009 setdoc.exe
+09-18-1993 00:00:00 24541 setfx.exe
+09-18-1993 00:00:00 56904 setupc.exe
+07-21-1997 00:00:00 75076 sftpt2.exe
+09-18-1993 00:00:00 67817 sftutl.exe
+09-02-1999 00:00:00 49345 showenv1.exe
+11-06-1997 00:00:00 25774 silent.exe
+04-23-2002 09:38:00 181878 slp107g.exe
+08-28-2001 00:00:00 184680 slpinsp3.exe
+09-18-1993 00:00:00 59254 smfsel.exe
+01-31-1997 00:00:00 2747104 smsup6.exe
+09-25-1996 00:00:00 131884 smt121.exe
+11-10-1993 00:00:00 105031 smt171.exe
+05-24-1996 00:00:00 1764462 smtos2.exe
+10-11-1996 00:00:00 322954 smtp1.exe
+05-19-1997 00:00:00 441783 smtp2.exe
+09-19-1997 00:00:00 2862615 smtp3.exe
+07-14-1998 00:00:00 2882529 smtp4.exe
+08-01-1995 00:00:00 53164 smtslp.exe
+06-04-1996 00:00:00 298148 sna31a.exe
+03-07-2002 10:28:00 148302 snmpfix.exe
+07-20-1995 00:00:00 147265 snupd2.exe
+07-20-1995 00:00:00 163195 snupdu.exe
+07-14-2000 00:00:00 12675957 sp1_ce.02
+04-25-2000 00:00:00 9547499 sp1_edir.02
+09-20-1999 00:00:00 230035 sp3to3a.exe
+02-25-1998 00:00:00 74372 spanish.exe
+05-23-1996 00:00:00 5323860 srapi.exe
+11-08-1996 00:00:00 38967 srout4.exe
+07-24-2000 00:00:00 812158 srvinst.exe
+08-23-1996 00:00:00 54912 srvmn1.exe
+06-30-1995 00:00:00 38078 stampd.exe
+02-21-2002 11:15:00 126042 strmft1.exe
+08-23-2000 00:00:00 250945 strtl8a.exe
+03-08-1999 00:00:00 36114 stufkey5.exe
+02-11-1998 00:00:00 52344 stylbr.exe
+04-14-1997 00:00:00 50098 stylct.exe
+02-11-1998 00:00:00 35645 styles.exe
+02-11-1998 00:00:00 37446 stylfr.exe
+04-14-1997 00:00:00 77671 stylha.exe
+02-12-1998 00:00:00 36626 stylit.exe
+04-16-1997 00:00:00 55674 stylsc.exe
+12-12-1995 00:00:00 37297 supwin.exe
+09-18-1993 00:00:00 186171 sys233.exe
+09-18-1993 00:00:00 159178 sys368.exe
+05-10-1995 00:00:00 161608 sys376.exe
+09-18-1993 00:00:00 61914 syschk.exe
+09-18-1993 00:00:00 81300 syslod.exe
+07-14-1997 00:00:00 418576 tabnd2a.exe
+01-13-1997 00:00:00 9831871 tambt1.exe
+05-04-1998 00:00:00 172843 tback3.exe
+09-01-1998 00:00:00 58235 tbox7.exe
+05-04-1998 00:00:00 174964 tcopy2.exe
+05-18-1998 00:00:00 781603 tcp312.exe
+08-01-2001 00:00:00 1223056 tcp542u.exe
+04-10-2002 08:49:00 1124221 tcp553v.exe
+05-24-2002 16:03:00 1221375 tcp590s.exe
+04-15-2002 10:50:00 315088 tcp604m.exe
+05-07-2002 11:27:00 1118361 tcp604s.exe
+02-09-1998 00:00:00 6902826 tel01a.exe
+01-21-1998 00:00:00 97084 tel40d.exe
+09-18-1993 00:00:00 33888 tim286.exe
+09-18-1993 00:00:00 20453 tim386.exe
+11-02-1998 00:00:00 105037 timefx.exe
+03-29-1994 00:00:00 31521 tokws.exe
+01-25-2001 00:00:00 123321 trpmon.exe
+09-18-1993 00:00:00 26100 trxnet.exe
+08-21-1996 00:00:00 88579 tsa410.exe
+06-25-2002 10:29:00 724997 tsa5up9.exe
+01-12-2000 00:00:00 127632 tsands.exe
+11-02-1999 00:00:00 20771 ttsy2k.exe
+09-22-1995 00:00:00 19933 ttyncs.exe
+08-03-1994 00:00:00 834048 tux001.tar
+08-03-1994 00:00:00 845824 tux002.tar
+08-03-1994 00:00:00 1034240 tux003.tar
+08-03-1994 00:00:00 2764800 tux004.tar
+08-03-1994 00:00:00 2836480 tux005.tar
+08-03-1994 00:00:00 1252352 tux006.tar
+08-03-1994 00:00:00 1355264 tux007.tar
+08-03-1994 00:00:00 1710080 tux008.tar
+08-03-1994 00:00:00 3502080 tux009.tar
+08-03-1994 00:00:00 3573760 tux010.tar
+08-04-1994 00:00:00 258236 tux011.exe
+08-04-1994 00:00:00 258250 tux012.exe
+08-04-1994 00:00:00 304451 tux013.exe
+08-04-1994 00:00:00 602748 tux014.exe
+08-04-1994 00:00:00 351070 tux015.exe
+08-04-1994 00:00:00 460026 tux016.exe
+09-18-1993 00:00:00 34077 ucpy.exe
+09-18-1993 00:00:00 103354 udf355.exe
+02-22-2002 12:49:00 6994 unixinf1.tgz
+05-08-2002 14:56:00 107260 unixins2.tgz
+09-18-1993 00:00:00 25508 unld.exe
+09-18-1993 00:00:00 30830 unps2.exe
+09-18-1993 00:00:00 34857 up215c.exe
+01-06-1994 00:00:00 509794 upd311.exe
+09-18-1993 00:00:00 24330 ups.exe
+09-18-1993 00:00:00 20837 ups22.exe
+09-18-1993 00:00:00 45537 upsm70.exe
+07-22-1997 00:00:00 43743 upsnlm.exe
+10-13-1998 00:00:00 28519 userhlp.exe
+09-18-1993 00:00:00 134247 ut1192.exe
+01-14-1998 00:00:00 1632088 uxp203.exe
+11-19-1998 00:00:00 1389072 uxp205.exe
+06-06-2001 00:00:00 1341347 uxp23j.exe
+11-02-1995 00:00:00 1098502 uxpsft.exe
+11-01-1995 00:00:00 58761 v2014.exe
+09-18-1993 00:00:00 40944 v286ol.exe
+06-08-2001 00:00:00 95133 v_nfs914.exe
+09-18-1993 00:00:00 34278 vapvol.exe
+09-18-1993 00:00:00 38035 vgetsc.exe
+09-18-1993 00:00:00 52323 volinf.exe
+05-03-2001 00:00:00 2444080 vpn35e.exe
+02-13-2002 14:50:00 3838701 vpn36d.exe
+02-13-2002 14:48:00 3837285 vpn36e.exe
+08-31-1999 00:00:00 96158 vpnbs01.exe
+09-18-1993 00:00:00 49835 vrepfa.exe
+09-18-1993 00:00:00 86326 vrp215.exe
+07-31-1997 00:00:00 59336 vrp386.exe
+07-31-1997 00:00:00 43438 vrpa286.exe
+09-18-1993 00:00:00 486274 vrpels.exe
+09-18-1993 00:00:00 103958 vrpps2.exe
+09-09-1999 00:00:00 699367 w2n213.exe
+09-25-2000 00:00:00 771404 w2ny2k.exe
+06-04-1996 00:00:00 240179 wan31a.exe
+06-16-1995 00:00:00 135592 wanx02.exe
+07-20-2001 00:00:00 79254744 was351.exe
+09-18-1993 00:00:00 28100 watch.exe
+04-23-2002 10:17:00 7884641 waview71.exe
+07-09-2001 00:00:00 182961 wbdav51.exe
+08-21-1996 00:00:00 53418 web002.exe
+03-01-2001 00:00:00 182219 webdv51.exe
+10-05-1999 00:00:00 2574191 weblsp1.exe
+06-22-1998 00:00:00 3589741 webser31.exe
+11-01-1995 00:00:00 27063 welcom.exe
+04-23-2001 00:00:00 1887450 winntwms.exe
+07-17-1997 00:00:00 28104 wkstrk.exe
+07-20-1995 00:00:00 52547 wpca31.exe
+07-20-1995 00:00:00 89314 wpfm31.exe
+09-11-1995 00:00:00 41008 wpmdm2.exe
+07-18-1995 00:00:00 36824 wpofus.exe
+07-20-1995 00:00:00 51398 wprp31.exe
+07-18-1995 00:00:00 21092 wpvwin.exe
+03-15-1994 00:00:00 52738 wrkdoc.exe
+05-29-1997 00:00:00 683395 ws250c.exe
+05-29-1997 00:00:00 765234 ws251c.exe
+05-09-1997 00:00:00 212586 ws3tk2b.exe
+03-07-2002 12:40:00 371 ws_ftp.log
+06-29-1999 00:00:00 1507075 wtmc1.exe
+06-16-1995 00:00:00 32697 x400fx.exe
+06-09-1999 00:00:00 660700 x400nlm1.exe
+08-05-1999 00:00:00 1134477 x400os21.exe
+01-30-2002 17:09:00 156483 xconss9f.exe
+09-18-1993 00:00:00 49801 xld386.exe
+07-27-2001 00:00:00 1043685 zd2dmi1.exe
+12-19-2001 00:00:00 365016 zd2dstfx.exe
+07-20-2001 00:00:00 338947 zd2scan.exe
+03-01-2002 09:27:00 24341430 zd322k1.exe
+03-01-2002 09:35:00 24350056 zd322k2.exe
+03-14-2002 18:03:00 95330 zd32dupw.exe
+03-01-2002 09:16:00 26945103 zd32nw.exe
+03-01-2002 09:21:00 26937023 zd32nw4.exe
+02-05-2002 12:18:00 26944994 zd32nw5.exe
+07-29-2001 00:00:00 24349972 zd32p2k1.exe
+07-29-2001 00:00:00 24349896 zd32p2k2.exe
+07-29-2001 00:00:00 26936865 zd32pnw4.exe
+07-29-2001 00:00:00 26944944 zd32pnw5.exe
+01-29-2002 14:50:00 128456 zd3awsr1.exe
+12-19-2001 00:00:00 1242985 zd3ccpp.exe
+12-19-2001 00:00:00 304923 zd3dac.exe
+02-22-2002 15:31:00 537680 zd3dupws.exe
+11-08-2001 00:00:00 142260 zd3dxsnp.exe
+12-04-2001 00:00:00 94250 zd3idnt1.exe
+01-02-2002 00:00:00 1443132 zd3ntmsi.exe
+12-20-2001 00:00:00 15512136 zd3o8i1.exe
+12-19-2001 00:00:00 15575094 zd3o8i2.exe
+05-24-2002 10:03:00 204858 zd3rosnp.exe
+01-09-2002 00:00:00 298505 zd3scn.exe
+12-18-2001 00:00:00 149726 zd3wm95.exe
+01-09-2002 00:00:00 180523 zd3wminv.exe
+12-18-2001 00:00:00 166988 zd3wmsch.exe
+12-19-2001 00:00:00 195447 zd3wsmg.exe
+03-19-2002 14:21:00 381437 zd3xwsrg.exe
+04-18-2002 15:53:00 125036 zd3xwuol.exe
+04-18-2002 16:30:00 180429 zd3xzisw.exe
+03-14-2002 10:01:00 226961 zd3zpol.exe
+05-01-2002 17:41:00 1274878 zenintg.exe
+05-09-2001 00:00:00 1865 zenstart.txt
+02-23-2001 00:00:00 2408726 zfd2pt3b.exe
+03-21-2000 00:00:00 62396652 zfd2sp1.exe
+05-22-2001 00:00:00 293221 zfd2tsfx.exe
+10-20-2000 00:00:00 97309 zfd3site.exe
+11-23-2001 00:00:00 46890033 zfd3sp1a.exe
+08-10-2000 00:00:00 31452136 zfn101.exe
+11-23-2001 00:00:00 1647316 zfs2jvm.exe
+12-18-2001 00:00:00 215046 zfs2pt1.exe
+12-20-2001 00:00:00 262640 zfs2sel.exe
+01-18-2002 14:59:00 54876346 zfs2sp1a.exe
+02-05-2001 00:00:00 1903657 zfsdbpb.exe
+10-11-2000 00:00:00 96356 zisclr.exe
+12-19-2001 00:00:00 94293 zs2dbbk.exe
+12-20-2001 00:00:00 141307 zs2ipg.exe
+12-19-2001 00:00:00 1173802 zs2mibs.exe
+01-23-2002 08:51:00 943931 zs2ndst1.exe
+06-04-2002 13:23:00 516401 zs2rbs.exe
+03-13-2002 11:41:00 1095584 zs2smtp.exe
+12-05-2001 00:00:00 981014 zs2util2.exe
+06-06-2002 11:14:00 92151 zs3sch.exe
+10-13-1998 00:00:00 1039314 zw100p1.exe
+11-06-1998 00:00:00 194420 zw101p1.exe
+11-22-1999 00:00:00 1065727 zw110p3.exe
diff --git a/netwerk/test/gtest/parse-ftp/U-no_ug.in b/netwerk/test/gtest/parse-ftp/U-no_ug.in
new file mode 100644
index 0000000000..aedd9cff46
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-no_ug.in
@@ -0,0 +1,84 @@
+ftp> open casper.cs.uct.ac.za
+Connected to casper.cs.uct.ac.za.
+220 casper.cs.uct.ac.za FTP server (Version 6.00LS) ready.
+Name (ftp.cs.uct.ac.za:cyp):
+331 Guest login ok, send your email address as password.
+230- Welcome to
+230- __ _ _
+230- / _| |_ _ __ ___ ___ _ _ ___| |_ __ _ ___ ______ _
+230- | |_| __| '_ \ / __/ __|| | | |/ __| __| / _` |/ __| |_ / _` |
+230- | _| |_| |_) | (__\__ \| |_| | (__| |_ | (_| | (__ _ / / (_| |
+230- |_| \__| .__(_)___|___(_)__,_|\___|\__(_)__,_|\___(_)___\__,_|
+230- |_|
+230-
+230- Publicly available downloads can be found in /pub.
+230-
+230- Do not put anything in /incoming unless it is by prior arrangement.
+230- If we do not know what it is, it will be deleted.
+230-
+230- A complete listing of available files can be found in /pub/ls-lR.gz
+230- and /pub/ls-lR. This list is updated daily at 02:00 SAST.
+230-
+230- Contents of /pub:
+230- CVC/ - Collaborative Visual Computing Laboratory
+230- DB/ - Database Laboratory
+230- DNA/ - The Data Network Architectures Laboratory
+230- FreeBSD/ - The FreeBSD Operating System
+230- distfiles/ - ports source tarball's
+230- releases/ - self-made releases
+230- OpenBSD/ - The OpenBSD Operating System
+230- windows/ - Software for Microsoft Windows
+230- ssh/ - secure shell clients
+230-
+230- This FTP site is also searchable via archie,
+230- and the web: http://ftp.cs.uct.ac.za:8000/ftpsearch
+230-
+230- UCT/UNINET users should also peruse the following
+230- anonymous FTP servers for additional resources:
+230-
+230- ftp://ftp.leg.uct.ac.za/ [ http://www.leg.uct.ac.za/ ]
+230- ftp://ftp.adamastor.ac.za/ [ http://ftp.adamastor.ac.za/ ]
+230- ftp://cabbagewrath.its.uct.ac.za/ [ don't ask about the name ]
+230-
+230- --
+230- ftp-admin@cs.uct.ac.za
+230 Guest login ok, access restrictions apply.
+Remote system type is UNIX.
+Using binary mode to transfer files.
+ftp> syst
+215 UNIX Type: L8 Version: BSD-199506
+ftp> ls
+200 PORT command successful.
+150 Opening ASCII mode data connection for '/bin/ls'.
+total 1092
+drwxr-xr-x 2 0 0 512 May 28 22:17 etc
+drwx-wx-wt 2 0 0 512 Jul 1 02:15 incoming
+drwx--x--x 2 0 0 512 Jul 3 12:19 private
+drwxr-xr-x 9 0 0 512 Jul 11 01:02 pub
+drwxr-xr-x 2 0 5 512 May 28 22:24 CVC
+drwxr-xr-x 2 0 5 512 Jul 31 2000 DB
+drwxr-xr-x 5 0 5 512 May 28 22:24 DNA
+drwxr-xr-x 4 0 0 512 Jun 12 22:13 FreeBSD
+drwxr-xr-x 3 0 5 512 May 28 22:24 OpenBSD
+drwxr-xr-x 2 0 5 512 Jun 3 15:51 Solaris
+-rw-r--r-- 1 0 0 158918 Jul 11 01:02 ls-lR
+-rw-r--r-- 1 0 0 26569 Jul 11 01:02 ls-lR.gz
+drwxr-xr-x 3 0 5 512 May 28 22:24 windows
+lrwx------ 1 0 0 25 Jun 12 22:10 4.6-RELEASE -> releases/i386/4.6-RELEASE
+lrwx------ 1 0 0 24 Jun 12 22:13 ISO-IMAGES -> releases/i386/ISO-IMAGES
+-rw-r--r-- 1 0 5 157 May 28 22:27 README.TXT
+-rw-r--r-- 1 0 5 872048 Sep 23 2001 cvsup-16.1e.tgz
+lrwxr-xr-x 1 0 0 15 May 28 22:26 distfiles -> ports/distfiles
+lrwxr-xr-x 1 0 0 14 Jun 6 17:12 packages -> ports/packages
+drwxr-xr-x 5 0 0 512 Jun 23 18:47 ports
+drwxr-xr-x 3 0 0 512 May 28 22:27 releases
+-rw-r--r-- 1 0 0 1538 Mar 15 2001 ftpmotd
+ftp> cd incoming
+250 CWD command successful.
+ftp> ls
+200 PORT command successful.
+150 Opening ASCII mode data connection for '/bin/ls'.
+ftpd: .: Permission denied
+226 Transfer complete.
+ftp> close
+221 Goodbye.
diff --git a/netwerk/test/gtest/parse-ftp/U-no_ug.out b/netwerk/test/gtest/parse-ftp/U-no_ug.out
new file mode 100644
index 0000000000..5200a9b0e1
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-no_ug.out
@@ -0,0 +1,26 @@
+<!-- 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/. -->
+
+05-28-2002 22:17:00 <DIR> etc
+07-01-2002 02:15:00 <DIR> incoming
+07-03-2002 12:19:00 <DIR> private
+07-11-2002 01:02:00 <DIR> pub
+05-28-2002 22:24:00 <DIR> CVC
+07-31-2000 00:00:00 <DIR> DB
+05-28-2002 22:24:00 <DIR> DNA
+06-12-2002 22:13:00 <DIR> FreeBSD
+05-28-2002 22:24:00 <DIR> OpenBSD
+06-03-2002 15:51:00 <DIR> Solaris
+07-11-2002 01:02:00 158918 ls-lR
+07-11-2002 01:02:00 26569 ls-lR.gz
+05-28-2002 22:24:00 <DIR> windows
+06-12-2002 22:10:00 <JUNCTION> 4.6-RELEASE -> releases/i386/4.6-RELEASE
+06-12-2002 22:13:00 <JUNCTION> ISO-IMAGES -> releases/i386/ISO-IMAGES
+05-28-2002 22:27:00 157 README.TXT
+09-23-2001 00:00:00 872048 cvsup-16.1e.tgz
+05-28-2002 22:26:00 <JUNCTION> distfiles -> ports/distfiles
+06-06-2002 17:12:00 <JUNCTION> packages -> ports/packages
+06-23-2002 18:47:00 <DIR> ports
+05-28-2002 22:27:00 <DIR> releases
+03-15-2001 00:00:00 1538 ftpmotd
diff --git a/netwerk/test/gtest/parse-ftp/U-nogid.in b/netwerk/test/gtest/parse-ftp/U-nogid.in
new file mode 100644
index 0000000000..15f77d1ee3
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-nogid.in
@@ -0,0 +1,82 @@
+ftp> open export.lcs.mit.edu
+Connected to ftp.x.org.
+220-Welcome to the ftp.x.org server.
+220-
+220-This server is provided and supported by The Open Group.
+220-
+220 ftp.x.org FTP server (Version wu-2.6.2(2) Mon Dec 17 13:03:41 GMT 2001) ready.
+Name (export.lcs.mit.edu:cyp):
+331 Guest login ok, send your complete e-mail address as password.
+230-
+230-Welcome to ftp.x.org, the X11 anonymous FTP archive of X.Org.
+230-
+230-PLEASE NOTE THE INCOMING FACILITY IS PRESENTLY UNAVAILABLE
+230-
+230-All activity is logged with your host name and email address.
+230-
+230-REPORTING PROBLEMS - Please report all problems to xorg_info@x.org.
+230-
+230-LOGIN PROBLEMS - If your FTP client crashes or hangs shortly after
+230-login, try using a dash (-) as the first character of your password.
+230-This turns off the informational messages that may be confusing
+230-your ftp client.
+230-
+230-
+230-Please read the file README
+230- it was last modified on Tue Apr 24 15:33:13 2001 - 444 days ago
+230 User ftp logged in. Access restrictions apply.
+Remote system type is UNIX.
+Using binary mode to transfer files.
+ftp> ls
+200 PORT command successful.
+150 Opening ASCII mode data connection for /bin/ls.
+total 5106
+-rw-r--r-- 1 X.Org 91 May 7 2001 .banner
+---------- 1 X.Org 0 May 30 2000 .notar
+-rw-r--r-- 1 X.Org 885 May 27 1999 .welcome
+-rw-r--r-- 1 X.Org 61 Jul 20 2001 30_days_changes
+-rw-r--r-- 1 X.Org 61 Jul 20 2001 7_days_changes
+-rw-r--r-- 1 X.Org 1456 Jul 20 2001 90_days_changes
+-rw-r--r-- 1 X.Org 3075 Oct 7 1998 GettingBroadway
+-rw-r--r-- 1 X.Org 3075 Oct 7 1998 GettingR6.3
+-rw-r--r-- 1 X.Org 1847 Feb 1 1999 GettingR6.4
+-rw-r--r-- 1 X.Org 1378 Aug 24 2000 GettingR6.5.1
+-rw-r--r-- 1 X.Org 1229 Apr 24 2001 GettingR6.6
+-rw-r--r-- 1 X.Org 194 Mar 11 1997 MIRROR.README
+drwxr-xr-x 56 X.Org 22016 May 4 2001 R5contrib
+-r--r--r-- 1 X.Org 1314 Apr 24 2001 README
+-rw-r--r-- 2 X.Org 479 Nov 6 2001 banner2
+lrwxrwxrwx 1 X.Org 7 Aug 8 2001 bin -> usr/bin
+drwxr-xr-x 34 X.Org 1024 Nov 6 2001 contrib
+d--x--x--x 2 X.Org 512 Aug 8 2001 dev
+drwxr-xr-x 2 X.Org 512 Oct 12 1998 digest
+d--x--x--x 3 X.Org 512 Aug 8 2001 etc
+-rw-r--r-- 1 X.Org 2135632 Jul 20 2001 ls-lR
+-rw-r--r-- 1 X.Org 376221 May 8 2001 ls-lR.Z
+drwxr-xr-x 2 X.Org 512 Sep 29 1998 private
+drwxr-xr-x 17 X.Org 512 May 4 2001 pub
+drwxr-xr-x 2 X.Org 512 May 4 2001 rcsfaq
+d--x--x--x 5 X.Org 512 Aug 8 2001 usr
+-rw-r--r-- 2 X.Org 479 Nov 6 2001 welcome.msg
+drwxr-xr-x 2 X.Org 512 May 4 2001 10R3
+drwxr-xr-x 2 X.Org 512 May 4 2001 10R4
+-rw-r--r-- 1 X.Org 9740 Mar 2 1999 Contrib.howto
+drwxr-xr-x 9 X.Org 512 Jun 2 2001 DOCS
+drwxr-xr-x 2 X.Org 512 May 4 2001 R1
+drwxr-xr-x 2 X.Org 512 May 4 2001 R2
+drwxr-xr-x 2 X.Org 512 May 4 2001 R3
+drwxr-xr-x 7 X.Org 512 May 4 2001 R4
+drwxr-xr-x 4 X.Org 512 May 4 2001 R5
+drwxr-xr-x 4 X.Org 512 May 4 2001 R6
+drwxr-xr-x 5 X.Org 512 May 4 2001 R6.1
+drwxr-xr-x 6 X.Org 512 May 4 2001 R6.3
+drwxr-xr-x 8 X.Org 512 Aug 10 2001 R6.4
+drwxr-xr-x 7 X.Org 512 Aug 9 2001 R6.5.1
+drwxr-xr-x 8 X.Org 512 May 2 2001 R6.6
+drwxr-xr-x 10 X.Org 512 May 4 2001 unsupported
+226 Transfer complete.
+ftp> close
+221-You have transferred 0 bytes in 0 files.
+221-Total traffic for this session was 2686 bytes in 1 transfers.
+221-Thank you for using the FTP service on ftp.x.org.
+221 Goodbye.
diff --git a/netwerk/test/gtest/parse-ftp/U-nogid.out b/netwerk/test/gtest/parse-ftp/U-nogid.out
new file mode 100644
index 0000000000..9a31407c8f
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-nogid.out
@@ -0,0 +1,47 @@
+<!-- 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/. -->
+
+05-07-2001 00:00:00 91 .banner
+05-30-2000 00:00:00 0 .notar
+05-27-1999 00:00:00 885 .welcome
+07-20-2001 00:00:00 61 30_days_changes
+07-20-2001 00:00:00 61 7_days_changes
+07-20-2001 00:00:00 1456 90_days_changes
+10-07-1998 00:00:00 3075 GettingBroadway
+10-07-1998 00:00:00 3075 GettingR6.3
+02-01-1999 00:00:00 1847 GettingR6.4
+08-24-2000 00:00:00 1378 GettingR6.5.1
+04-24-2001 00:00:00 1229 GettingR6.6
+03-11-1997 00:00:00 194 MIRROR.README
+05-04-2001 00:00:00 <DIR> R5contrib
+04-24-2001 00:00:00 1314 README
+11-06-2001 00:00:00 479 banner2
+08-08-2001 00:00:00 <JUNCTION> bin -> usr/bin
+11-06-2001 00:00:00 <DIR> contrib
+08-08-2001 00:00:00 <DIR> dev
+10-12-1998 00:00:00 <DIR> digest
+08-08-2001 00:00:00 <DIR> etc
+07-20-2001 00:00:00 2135632 ls-lR
+05-08-2001 00:00:00 376221 ls-lR.Z
+09-29-1998 00:00:00 <DIR> private
+05-04-2001 00:00:00 <DIR> pub
+05-04-2001 00:00:00 <DIR> rcsfaq
+08-08-2001 00:00:00 <DIR> usr
+11-06-2001 00:00:00 479 welcome.msg
+05-04-2001 00:00:00 <DIR> 10R3
+05-04-2001 00:00:00 <DIR> 10R4
+03-02-1999 00:00:00 9740 Contrib.howto
+06-02-2001 00:00:00 <DIR> DOCS
+05-04-2001 00:00:00 <DIR> R1
+05-04-2001 00:00:00 <DIR> R2
+05-04-2001 00:00:00 <DIR> R3
+05-04-2001 00:00:00 <DIR> R4
+05-04-2001 00:00:00 <DIR> R5
+05-04-2001 00:00:00 <DIR> R6
+05-04-2001 00:00:00 <DIR> R6.1
+05-04-2001 00:00:00 <DIR> R6.3
+08-10-2001 00:00:00 <DIR> R6.4
+08-09-2001 00:00:00 <DIR> R6.5.1
+05-02-2001 00:00:00 <DIR> R6.6
+05-04-2001 00:00:00 <DIR> unsupported
diff --git a/netwerk/test/gtest/parse-ftp/U-proftpd.in b/netwerk/test/gtest/parse-ftp/U-proftpd.in
new file mode 100644
index 0000000000..0f8aa138da
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-proftpd.in
@@ -0,0 +1,21 @@
+ftp> open ftp.netmanage.com
+Connected to ftp.netmanage.com.
+220 ProFTPD 1.2.4 Server (Netmanage FTP Server) [156.27.8.3]
+Name (ftp.netmanage.com:cyp):
+331 Anonymous login ok, send your complete email address as your password.
+230 Anonymous access granted, restrictions apply.
+Remote system type is UNIX.
+Using binary mode to transfer files.
+ftp> ls
+200 PORT command successful.
+150 Opening ASCII mode data connection for file list.
+drwxr-xr-x 13 ftp ftp 344 Oct 17 2001 pub
+drwxrwxr-x 7 ftp support 304 May 14 16:56 support
+-rw-r--r-- 1 ftp ftp 508 Aug 19 1998 welcome.msg
+226-Transfer complete.
+226 Quotas off
+ftp> syst
+215 UNIX Type: L8
+ftp> close
+221 Goodbye.
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-proftpd.out b/netwerk/test/gtest/parse-ftp/U-proftpd.out
new file mode 100644
index 0000000000..02d7a18432
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-proftpd.out
@@ -0,0 +1,7 @@
+<!-- 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/. -->
+
+10-17-2001 00:00:00 <DIR> pub
+05-14-2002 16:56:00 <DIR> support
+08-19-1998 00:00:00 508 welcome.msg
diff --git a/netwerk/test/gtest/parse-ftp/U-wu.in b/netwerk/test/gtest/parse-ftp/U-wu.in
new file mode 100644
index 0000000000..e4a822a093
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-wu.in
@@ -0,0 +1,71 @@
+ftp> open sunsite.unc.edu
+Connected to sunsite.unc.edu.
+220 divahouse.metalab.unc.edu FTP server (Version wu-2.6.1(4) Thu Nov 29 23:05:07 EST 2001) ready.
+Name (sunsite.unc.edu:cyp):
+331 Guest login ok, send your complete e-mail address as password.
+230-
+230- Welcome to ibiblio.org's FTP archives!
+230- formerly known as MetaLab.unc.edu
+230-
+230-
+230-For more information about services offered by ibiblio.org,
+230-browse to http://ibiblio.org/faq
+230-
+230-You can access this archive via HTTP with the same URL.
+230-
+230-example: ftp://ibiblio.org/pub/Linux/ becomes
+230- http://ibiblio.org/pub/Linux/, but we prefer you use FTP.
+230-
+230-You can get tarred directories if you issue a "get dirname.tar"
+230-You can also get gzipped or compressed tarred directories by following
+230-the .tar with .gz or .Z, respectively. Please don't issue either of
+230-these commands to get Linux distributions. They are already compressed,
+230-so this only generates unnecessary CPU overhead for us.
+230-
+230-************************************************************************
+230-
+230-Please use LSM documentation when submitting to the linux archive.
+230-Anything submitted without an LSM will be rejected! You'll get an
+230-email form letter about it if we can figure out who you are.
+230-
+230-To learn more about submitting an LSM,
+230-see: http://www.ibiblio.org/pub/Linux/howtosubmit.html
+230-or ftp://www.ibiblio.org/pub/Linux/HOW.TO.SUBMIT
+230-
+230-***********************************************************************
+230-
+230-If you mirror a site on ibiblio, please subscribe to our mirror list:
+230-http://lists.ibiblio.org/mailman/listinfo/ibiblio-mirrors
+230-
+230-Have suggestions or questions? Please mail ftpkeeper@ibiblio.org.
+230-
+230-
+230-Please read the file README
+230- it was last modified on Tue Feb 19 09:46:53 2002 - 140 days ago
+230 Guest login ok, access restrictions apply.
+Remote system type is UNIX.
+Using binary mode to transfer files.
+ftp> syst
+215 UNIX Type: L8
+ftp> ls
+200 PORT command successful.
+150 Opening ASCII mode data connection for /bin/ls.
+total 78744
+-r--r--r-- 1 root other 80507411 Jul 9 06:09 IAFA-LISTINGS
+-rw-r--r-- 1 root root 1393 Feb 19 14:46 README
+dr-xr-xr-x 2 root other 4096 Mar 27 2001 bin
+dr-xr-xr-x 2 root other 4096 Jul 16 1997 dev
+dr-xr-xr-x 2 root other 4096 May 30 14:35 etc
+drwxrwxrwx 18 ftp 20 4096 Jun 10 13:05 incoming
+drwxr-xr-x 2 root root 4096 Mar 27 2001 lib
+lrwxrwxrwx 1 root other 13 Mar 16 2001 ls-lR -> IAFA-LISTINGS
+dr-xr-xr-x 18 root root 4096 May 31 19:46 pub
+dr-xr-xr-x 3 root other 4096 Jun 26 2000 unc
+dr-xr-xr-x 5 root other 4096 Jul 16 1997 usr
+226 Transfer complete.
+ftp> close
+221-You have transferred 0 bytes in 0 files.
+221-Total traffic for this session was 2777 bytes in 1 transfers.
+221-Thank you for using the FTP service on divahouse.metalab.unc.edu.
+221 Goodbye.
+ftp> \ No newline at end of file
diff --git a/netwerk/test/gtest/parse-ftp/U-wu.out b/netwerk/test/gtest/parse-ftp/U-wu.out
new file mode 100644
index 0000000000..1ffbf23eb2
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/U-wu.out
@@ -0,0 +1,15 @@
+<!-- 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/. -->
+
+07-09-2002 06:09:00 80507411 IAFA-LISTINGS
+02-19-2002 14:46:00 1393 README
+03-27-2001 00:00:00 <DIR> bin
+07-16-1997 00:00:00 <DIR> dev
+05-30-2002 14:35:00 <DIR> etc
+06-10-2002 13:05:00 <DIR> incoming
+03-27-2001 00:00:00 <DIR> lib
+03-16-2001 00:00:00 <JUNCTION> ls-lR -> IAFA-LISTINGS
+05-31-2002 19:46:00 <DIR> pub
+06-26-2000 00:00:00 <DIR> unc
+07-16-1997 00:00:00 <DIR> usr
diff --git a/netwerk/test/gtest/parse-ftp/V-MultiNet.in b/netwerk/test/gtest/parse-ftp/V-MultiNet.in
new file mode 100644
index 0000000000..04e66774e6
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/V-MultiNet.in
@@ -0,0 +1,34 @@
+Connected to acavax.lynchburg.edu.
+220 acavax.lynchburg.edu MultiNet FTP Server Process V4.0(15) at Mon 1-Jul-02 10:51AM-EDT
+Name (acavax.lynchburg.edu:cyp): 331 anonymous user ok. Send real ident as password.
+230-Guest User FOO@BAR.COM logged into ACA:[ANONYMOUS] at Mon 1-Jul-02 10:51AM-EDT, job 2b69.
+230 Access restrictions apply
+Remote system type is VMS.
+ftp> passive
+Passive mode on.
+ftp> pwd
+257 "ACA:[ANONYMOUS]" is current directory.
+ftp> ls
+227 Entering passive mode; use PORT 161,115,147,1,10,31
+150 List started.
+
+ACA:[ANONYMOUS]
+
+AUTOEXEC.BAT;1 %RMS-E-PRV, insufficient privilege or file protection violation
+BOURNE.DIR;1 1 28-OCT-1994 10:05 [ANONYMOUS] (RWE,RWE,RE,RWE)
+FTP_SERVER.LOG;8171 0 1-JUL-2002 10:51 [ANONYMOUS] (RWED,RWED,,)
+LOGIN.COM;2 1 4-NOV-1994 14:09 [ANONYMOUS] (RWE,RWE,,)
+NICELY.DIR;1 1 14-NOV-1994 14:17 [501,120] (RWED,RWED,RE,RE)
+NWLINK.386;1 66 7-AUG-1995 14:32 [ANONYMOUS] (RWED,RWED,,RE)
+PUB.DIR;1 1 27-JAN-1994 14:46 [ANONYMOUS] (RWE,RWE,RE,RWE)
+README.FTP;1 %RMS-E-PRV, insufficient privilege or file protection violation
+ROUSSOS.DIR;1 1 27-JAN-1994 14:48 [CS,ROUSSOS] (RWE,RWE,RE,R)
+S67-50903.JPG;1 328 22-SEP-1998 16:19 [ANONYMOUS] (RWED,RWED,,)
+S71-43543.JPG;1 310 22-SEP-1998 16:20 [ANONYMOUS] (RWED,RWED,,)
+TEAGUE.DIR;1 1 1-JUL-1995 12:23 [ANONYMOUS] (RWE,RWE,RE,RE)
+
+
+Total of 710 blocks in 12 files.
+226 Transfer completed.
+ftp> quit
+221 QUIT command received. Goodbye.
diff --git a/netwerk/test/gtest/parse-ftp/V-MultiNet.out b/netwerk/test/gtest/parse-ftp/V-MultiNet.out
new file mode 100644
index 0000000000..a6cddd6191
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/V-MultiNet.out
@@ -0,0 +1,14 @@
+<!-- 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/. -->
+
+10-28-1994 10:05:00 <DIR> BOURNE
+07-01-2002 10:51:00 0 FTP_SERVER.LOG
+11-04-1994 14:09:00 512 LOGIN.COM
+11-14-1994 14:17:00 <DIR> NICELY
+08-07-1995 14:32:00 33792 NWLINK.386
+01-27-1994 14:46:00 <DIR> PUB
+01-27-1994 14:48:00 <DIR> ROUSSOS
+09-22-1998 16:19:00 167936 S67-50903.JPG
+09-22-1998 16:20:00 158720 S71-43543.JPG
+07-01-1995 12:23:00 <DIR> TEAGUE
diff --git a/netwerk/test/gtest/parse-ftp/V-VMS-mix.in b/netwerk/test/gtest/parse-ftp/V-VMS-mix.in
new file mode 100644
index 0000000000..07ebd7bbac
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/V-VMS-mix.in
@@ -0,0 +1,22 @@
+This is a composite of 'difficult' VMS (MultiNet/UCX/CMU) LIST lines.
+CAUTION WHILE EDITING - lines may have dangling CRs! (intentional)
+
+
+Directory DISK$VOL:[DIR1.DIR2]
+DISK$VOL:
+ACA:[ANONYMOUS]
+
+AUTOEXEC.BAT;1 %RMS-E-PRV, insufficient privilege or file protection violation
+README.FTP;1 insufficient privilege or file protection violation
+LOGIN.COM;2 1 4-NOV-1994 14:09 [ANONYMOUS] (RWE,RWE,,)
+CII-MANUAL.TEX;1 213/216 29-JAN-1996 03:33:12 [ANONYMOU,ANONYMOUS] (RWED,RWED,,)
+THIS-IS-A-LONG-VMS-FILENAME.WITH-CR-TO-NEXT-LINE 213/216 29-JAN-1996 03:33:12 [ANONYMOU,ANONYMOUS] (RWED,RWED,,)
+ANOTHER-LONG-VMS-FILENAME.WITH-LF-TO-NEXT-LINE
+ 213 29-JAN-1996 03:33 [ANONYMOU,ANONYMOUS] (RWED,RWED,,)
+[A.DIR]CMU-VMS-IP-FTP-FILE;1 1/3 5-MAR-1993 18:09
+MAX_FILESIZE.FILE;1 2199023255040/4294967295 5-MAR-1993 18:09
+
+Total of 710 blocks in 12 files.
+226 Transfer completed.
+ftp> quit
+221 QUIT command received. Goodbye.
diff --git a/netwerk/test/gtest/parse-ftp/V-VMS-mix.out b/netwerk/test/gtest/parse-ftp/V-VMS-mix.out
new file mode 100644
index 0000000000..b8192f5ef9
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/V-VMS-mix.out
@@ -0,0 +1,10 @@
+<!-- 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/. -->
+
+11-04-1994 14:09:00 512 LOGIN.COM
+01-29-1996 03:33:12 109056 CII-MANUAL.TEX
+01-29-1996 03:33:12 109056 THIS-IS-A-LONG-VMS-FILENAME.WITH-CR-TO-NEXT-LINE
+01-29-1996 03:33:00 109056 ANOTHER-LONG-VMS-FILENAME.WITH-LF-TO-NEXT-LINE
+03-05-1993 18:09:00 512 CMU-VMS-IP-FTP-FILE
+03-05-1993 18:09:00 2199023255040 MAX_FILESIZE.FILE
diff --git a/netwerk/test/gtest/parse-ftp/moz.build b/netwerk/test/gtest/parse-ftp/moz.build
new file mode 100644
index 0000000000..04961f33f5
--- /dev/null
+++ b/netwerk/test/gtest/parse-ftp/moz.build
@@ -0,0 +1,68 @@
+# -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
+# vim: set filetype=python:
+# 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/.
+
+UNIFIED_SOURCES += [
+ "TestParseFTPList.cpp",
+]
+
+TEST_HARNESS_FILES.gtest += [
+ "3-guess.in",
+ "3-guess.out",
+ "C-VMold.in",
+ "C-VMold.out",
+ "C-zVM.in",
+ "C-zVM.out",
+ "D-WinNT.in",
+ "D-WinNT.out",
+ "E-EPLF.in",
+ "E-EPLF.out",
+ "O-guess.in",
+ "O-guess.out",
+ "R-dls.in",
+ "R-dls.out",
+ "U-HellSoft.in",
+ "U-HellSoft.out",
+ "U-hethmon.in",
+ "U-hethmon.out",
+ "U-murksw.in",
+ "U-murksw.out",
+ "U-ncFTPd.in",
+ "U-ncFTPd.out",
+ "U-NetPresenz.in",
+ "U-NetPresenz.out",
+ "U-NetWare.in",
+ "U-NetWare.out",
+ "U-no_ug.in",
+ "U-no_ug.out",
+ "U-nogid.in",
+ "U-nogid.out",
+ "U-Novonyx.in",
+ "U-Novonyx.out",
+ "U-proftpd.in",
+ "U-proftpd.out",
+ "U-Surge.in",
+ "U-Surge.out",
+ "U-WarFTPd.in",
+ "U-WarFTPd.out",
+ "U-WebStar.in",
+ "U-WebStar.out",
+ "U-WinNT.in",
+ "U-WinNT.out",
+ "U-wu.in",
+ "U-wu.out",
+ "V-MultiNet.in",
+ "V-MultiNet.out",
+ "V-VMS-mix.in",
+ "V-VMS-mix.out",
+]
+
+include("/ipc/chromium/chromium-config.mozbuild")
+
+LOCAL_INCLUDES += [
+ "/netwerk/streamconv/converters",
+]
+
+FINAL_LIBRARY = "xul-gtest"
diff --git a/netwerk/test/gtest/urltestdata-orig.json b/netwerk/test/gtest/urltestdata-orig.json
new file mode 100644
index 0000000000..5565c938fd
--- /dev/null
+++ b/netwerk/test/gtest/urltestdata-orig.json
@@ -0,0 +1,6148 @@
+[
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/script-tests/segments.js",
+ {
+ "input": "http://example\t.\norg",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://user:pass@foo:21/bar;par?b#c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://user:pass@foo:21/bar;par?b#c",
+ "origin": "http://foo:21",
+ "protocol": "http:",
+ "username": "user",
+ "password": "pass",
+ "host": "foo:21",
+ "hostname": "foo",
+ "port": "21",
+ "pathname": "/bar;par",
+ "search": "?b",
+ "hash": "#c"
+ },
+ {
+ "input": "https://test:@test",
+ "base": "about:blank",
+ "href": "https://test@test/",
+ "origin": "https://test",
+ "protocol": "https:",
+ "username": "test",
+ "password": "",
+ "host": "test",
+ "hostname": "test",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https://:@test",
+ "base": "about:blank",
+ "href": "https://test/",
+ "origin": "https://test",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "test",
+ "hostname": "test",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://test:@test/x",
+ "base": "about:blank",
+ "href": "non-special://test@test/x",
+ "origin": "null",
+ "protocol": "non-special:",
+ "username": "test",
+ "password": "",
+ "host": "test",
+ "hostname": "test",
+ "port": "",
+ "pathname": "/x",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://:@test/x",
+ "base": "about:blank",
+ "href": "non-special://test/x",
+ "origin": "null",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "test",
+ "hostname": "test",
+ "port": "",
+ "pathname": "/x",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:foo.com",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/foo.com",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/foo.com",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "\t :foo.com \n",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:foo.com",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:foo.com",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": " foo.com ",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/foo.com",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/foo.com",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "a:\t foo.com",
+ "base": "http://example.org/foo/bar",
+ "href": "a: foo.com",
+ "origin": "null",
+ "protocol": "a:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": " foo.com",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:21/ b ? d # e ",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f:21/%20b%20?%20d%20# e",
+ "origin": "http://f:21",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f:21",
+ "hostname": "f",
+ "port": "21",
+ "pathname": "/%20b%20",
+ "search": "?%20d%20",
+ "hash": "# e"
+ },
+ {
+ "input": "lolscheme:x x#x x",
+ "base": "about:blank",
+ "href": "lolscheme:x x#x x",
+ "protocol": "lolscheme:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "x x",
+ "search": "",
+ "hash": "#x x"
+ },
+ {
+ "input": "http://f:/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f/c",
+ "origin": "http://f",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f",
+ "hostname": "f",
+ "port": "",
+ "pathname": "/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:0/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f:0/c",
+ "origin": "http://f:0",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f:0",
+ "hostname": "f",
+ "port": "0",
+ "pathname": "/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:00000000000000/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f:0/c",
+ "origin": "http://f:0",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f:0",
+ "hostname": "f",
+ "port": "0",
+ "pathname": "/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:00000000000000000000080/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f/c",
+ "origin": "http://f",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f",
+ "hostname": "f",
+ "port": "",
+ "pathname": "/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:b/c",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://f: /c",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://f:\n/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f/c",
+ "origin": "http://f",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f",
+ "hostname": "f",
+ "port": "",
+ "pathname": "/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:fifty-two/c",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://f:999999/c",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "non-special://f:999999/c",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://f: 21 / b ? d # e ",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": " \t",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":foo.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:foo.com/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:foo.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":foo.com\\",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:foo.com/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:foo.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":a",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:a",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:a",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":\\",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":#",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:#",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "#",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar#",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "#/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar#/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": "#/"
+ },
+ {
+ "input": "#\\",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar#\\",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": "#\\"
+ },
+ {
+ "input": "#;?",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar#;?",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": "#;?"
+ },
+ {
+ "input": "?",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar?",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":23",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:23",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:23",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/:23",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/:23",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/:23",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "::",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/::",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/::",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "::23",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/::23",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/::23",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo://",
+ "base": "http://example.org/foo/bar",
+ "href": "foo:///",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://a:b@c:29/d",
+ "base": "http://example.org/foo/bar",
+ "href": "http://a:b@c:29/d",
+ "origin": "http://c:29",
+ "protocol": "http:",
+ "username": "a",
+ "password": "b",
+ "host": "c:29",
+ "hostname": "c",
+ "port": "29",
+ "pathname": "/d",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http::@c:29",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:@c:29",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:@c:29",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://&a:foo(b]c@d:2/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://&a:foo(b%5Dc@d:2/",
+ "origin": "http://d:2",
+ "protocol": "http:",
+ "username": "&a",
+ "password": "foo(b%5Dc",
+ "host": "d:2",
+ "hostname": "d",
+ "port": "2",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://::@c@d:2",
+ "base": "http://example.org/foo/bar",
+ "href": "http://:%3A%40c@d:2/",
+ "origin": "http://d:2",
+ "protocol": "http:",
+ "username": "",
+ "password": "%3A%40c",
+ "host": "d:2",
+ "hostname": "d",
+ "port": "2",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo.com:b@d/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo.com:b@d/",
+ "origin": "http://d",
+ "protocol": "http:",
+ "username": "foo.com",
+ "password": "b",
+ "host": "d",
+ "hostname": "d",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo.com/\\@",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo.com//@",
+ "origin": "http://foo.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo.com",
+ "hostname": "foo.com",
+ "port": "",
+ "pathname": "//@",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:\\\\foo.com\\",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo.com/",
+ "origin": "http://foo.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo.com",
+ "hostname": "foo.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:\\\\a\\b:c\\d@foo.com\\",
+ "base": "http://example.org/foo/bar",
+ "href": "http://a/b:c/d@foo.com/",
+ "origin": "http://a",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "a",
+ "hostname": "a",
+ "port": "",
+ "pathname": "/b:c/d@foo.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo:/",
+ "base": "http://example.org/foo/bar",
+ "href": "foo:/",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo:/bar.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "foo:/bar.com/",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/bar.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo://///////",
+ "base": "http://example.org/foo/bar",
+ "href": "foo://///////",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "///////",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo://///////bar.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "foo://///////bar.com/",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "///////bar.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo:////://///",
+ "base": "http://example.org/foo/bar",
+ "href": "foo:////://///",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "//://///",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "c:/foo",
+ "base": "http://example.org/foo/bar",
+ "href": "c:/foo",
+ "origin": "null",
+ "protocol": "c:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//foo/bar",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo/bar",
+ "origin": "http://foo",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo/path;a??e#f#g",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo/path;a??e#f#g",
+ "origin": "http://foo",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/path;a",
+ "search": "??e",
+ "hash": "#f#g"
+ },
+ {
+ "input": "http://foo/abcd?efgh?ijkl",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo/abcd?efgh?ijkl",
+ "origin": "http://foo",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/abcd",
+ "search": "?efgh?ijkl",
+ "hash": ""
+ },
+ {
+ "input": "http://foo/abcd#foo?bar",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo/abcd#foo?bar",
+ "origin": "http://foo",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/abcd",
+ "search": "",
+ "hash": "#foo?bar"
+ },
+ {
+ "input": "[61:24:74]:98",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/[61:24:74]:98",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/[61:24:74]:98",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:[61:27]/:foo",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/[61:27]/:foo",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/[61:27]/:foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[1::2]:3:4",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://2001::1",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://2001::1]",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://2001::1]:80",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://[2001::1]",
+ "base": "http://example.org/foo/bar",
+ "href": "http://[2001::1]/",
+ "origin": "http://[2001::1]",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[2001::1]",
+ "hostname": "[2001::1]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[::127.0.0.1]",
+ "base": "http://example.org/foo/bar",
+ "href": "http://[::7f00:1]/",
+ "origin": "http://[::7f00:1]",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[::7f00:1]",
+ "hostname": "[::7f00:1]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[0:0:0:0:0:0:13.1.68.3]",
+ "base": "http://example.org/foo/bar",
+ "href": "http://[::d01:4403]/",
+ "origin": "http://[::d01:4403]",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[::d01:4403]",
+ "hostname": "[::d01:4403]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[2001::1]:80",
+ "base": "http://example.org/foo/bar",
+ "href": "http://[2001::1]/",
+ "origin": "http://[2001::1]",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[2001::1]",
+ "hostname": "[2001::1]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/example.com/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ftp://example.com/",
+ "origin": "ftp://example.com",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "https://example.com/",
+ "origin": "https://example.com",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "madeupscheme:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "madeupscheme:/example.com/",
+ "origin": "null",
+ "protocol": "madeupscheme:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "file:///example.com/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://example:1/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "file://example:test/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "file://example%/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "file://[example]/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "ftps:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ftps:/example.com/",
+ "origin": "null",
+ "protocol": "ftps:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "gopher://example.com/",
+ "origin": "gopher://example.com",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ws://example.com/",
+ "origin": "ws://example.com",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "wss://example.com/",
+ "origin": "wss://example.com",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "data:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "data:/example.com/",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "javascript:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "javascript:/example.com/",
+ "origin": "null",
+ "protocol": "javascript:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "mailto:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "mailto:/example.com/",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/example.com/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ftp://example.com/",
+ "origin": "ftp://example.com",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "https://example.com/",
+ "origin": "https://example.com",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "madeupscheme:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "madeupscheme:example.com/",
+ "origin": "null",
+ "protocol": "madeupscheme:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftps:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ftps:example.com/",
+ "origin": "null",
+ "protocol": "ftps:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "gopher://example.com/",
+ "origin": "gopher://example.com",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ws://example.com/",
+ "origin": "ws://example.com",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "wss://example.com/",
+ "origin": "wss://example.com",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "data:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "data:example.com/",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "javascript:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "javascript:example.com/",
+ "origin": "null",
+ "protocol": "javascript:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "mailto:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "mailto:example.com/",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/a/b/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/a/b/c",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/a/b/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/a/ /c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/a/%20/c",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/a/%20/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/a%2fc",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/a%2fc",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/a%2fc",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/a/%2f/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/a/%2f/c",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/a/%2f/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "#β",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar#%CE%B2",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": "#%CE%B2"
+ },
+ {
+ "input": "data:text/html,test#test",
+ "base": "http://example.org/foo/bar",
+ "href": "data:text/html,test#test",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "text/html,test",
+ "search": "",
+ "hash": "#test"
+ },
+ {
+ "input": "tel:1234567890",
+ "base": "http://example.org/foo/bar",
+ "href": "tel:1234567890",
+ "origin": "null",
+ "protocol": "tel:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "1234567890",
+ "search": "",
+ "hash": ""
+ },
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/file.html",
+ {
+ "input": "file:c:\\foo\\bar.html",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///c:/foo/bar.html",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/c:/foo/bar.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": " File:c|////foo\\bar.html",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///c:////foo/bar.html",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/c:////foo/bar.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|/foo/bar",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///C:/foo/bar",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/C|\\foo\\bar",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///C:/foo/bar",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//C|/foo/bar",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///C:/foo/bar",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//server/file",
+ "base": "file:///tmp/mock/path",
+ "href": "file://server/file",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "server",
+ "hostname": "server",
+ "port": "",
+ "pathname": "/file",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "\\\\server\\file",
+ "base": "file:///tmp/mock/path",
+ "href": "file://server/file",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "server",
+ "hostname": "server",
+ "port": "",
+ "pathname": "/file",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/\\server/file",
+ "base": "file:///tmp/mock/path",
+ "href": "file://server/file",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "server",
+ "hostname": "server",
+ "port": "",
+ "pathname": "/file",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:///foo/bar.txt",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///foo/bar.txt",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/foo/bar.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:///home/me",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///home/me",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/home/me",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "///",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "///test",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://test",
+ "base": "file:///tmp/mock/path",
+ "href": "file://test/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "test",
+ "hostname": "test",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://localhost",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://localhost/",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://localhost/test",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "test",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///tmp/mock/test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/tmp/mock/test",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:test",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///tmp/mock/test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/tmp/mock/test",
+ "search": "",
+ "hash": ""
+ },
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/script-tests/path.js",
+ {
+ "input": "http://example.com/././foo",
+ "base": "about:blank",
+ "href": "http://example.com/foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/./.foo",
+ "base": "about:blank",
+ "href": "http://example.com/.foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/.foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/.",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/./",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar/..",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar/../",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/..bar",
+ "base": "about:blank",
+ "href": "http://example.com/foo/..bar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/..bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar/../ton",
+ "base": "about:blank",
+ "href": "http://example.com/foo/ton",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/ton",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar/../ton/../../a",
+ "base": "about:blank",
+ "href": "http://example.com/a",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/a",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/../../..",
+ "base": "about:blank",
+ "href": "http://example.com/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/../../../ton",
+ "base": "about:blank",
+ "href": "http://example.com/ton",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/ton",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/%2e",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/%2e%2",
+ "base": "about:blank",
+ "href": "http://example.com/foo/%2e%2",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/%2e%2",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/%2e./%2e%2e/.%2e/%2e.bar",
+ "base": "about:blank",
+ "href": "http://example.com/%2e.bar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%2e.bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com////../..",
+ "base": "about:blank",
+ "href": "http://example.com//",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "//",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar//../..",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar//..",
+ "base": "about:blank",
+ "href": "http://example.com/foo/bar/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/bar/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo",
+ "base": "about:blank",
+ "href": "http://example.com/foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/%20foo",
+ "base": "about:blank",
+ "href": "http://example.com/%20foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%20foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%",
+ "base": "about:blank",
+ "href": "http://example.com/foo%",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%2",
+ "base": "about:blank",
+ "href": "http://example.com/foo%2",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%2",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%2zbar",
+ "base": "about:blank",
+ "href": "http://example.com/foo%2zbar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%2zbar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%2©zbar",
+ "base": "about:blank",
+ "href": "http://example.com/foo%2%C3%82%C2%A9zbar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%2%C3%82%C2%A9zbar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%41%7a",
+ "base": "about:blank",
+ "href": "http://example.com/foo%41%7a",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%41%7a",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo\t\u0091%91",
+ "base": "about:blank",
+ "href": "http://example.com/foo%C2%91%91",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%C2%91%91",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%00%51",
+ "base": "about:blank",
+ "href": "http://example.com/foo%00%51",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%00%51",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/(%28:%3A%29)",
+ "base": "about:blank",
+ "href": "http://example.com/(%28:%3A%29)",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/(%28:%3A%29)",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/%3A%3a%3C%3c",
+ "base": "about:blank",
+ "href": "http://example.com/%3A%3a%3C%3c",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%3A%3a%3C%3c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo\tbar",
+ "base": "about:blank",
+ "href": "http://example.com/foobar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foobar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com\\\\foo\\\\bar",
+ "base": "about:blank",
+ "href": "http://example.com//foo//bar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "//foo//bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/%7Ffp3%3Eju%3Dduvgw%3Dd",
+ "base": "about:blank",
+ "href": "http://example.com/%7Ffp3%3Eju%3Dduvgw%3Dd",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%7Ffp3%3Eju%3Dduvgw%3Dd",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/@asdf%40",
+ "base": "about:blank",
+ "href": "http://example.com/@asdf%40",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/@asdf%40",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/你好你好",
+ "base": "about:blank",
+ "href": "http://example.com/%E4%BD%A0%E5%A5%BD%E4%BD%A0%E5%A5%BD",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%E4%BD%A0%E5%A5%BD%E4%BD%A0%E5%A5%BD",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/‥/foo",
+ "base": "about:blank",
+ "href": "http://example.com/%E2%80%A5/foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%E2%80%A5/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com//foo",
+ "base": "about:blank",
+ "href": "http://example.com/%EF%BB%BF/foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%EF%BB%BF/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/‮/foo/‭/bar",
+ "base": "about:blank",
+ "href": "http://example.com/%E2%80%AE/foo/%E2%80%AD/bar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%E2%80%AE/foo/%E2%80%AD/bar",
+ "search": "",
+ "hash": ""
+ },
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/script-tests/relative.js",
+ {
+ "input": "http://www.google.com/foo?bar=baz#",
+ "base": "about:blank",
+ "href": "http://www.google.com/foo?bar=baz#",
+ "origin": "http://www.google.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.google.com",
+ "hostname": "www.google.com",
+ "port": "",
+ "pathname": "/foo",
+ "search": "?bar=baz",
+ "hash": ""
+ },
+ {
+ "input": "http://www.google.com/foo?bar=baz# »",
+ "base": "about:blank",
+ "href": "http://www.google.com/foo?bar=baz# %C2%BB",
+ "origin": "http://www.google.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.google.com",
+ "hostname": "www.google.com",
+ "port": "",
+ "pathname": "/foo",
+ "search": "?bar=baz",
+ "hash": "# %C2%BB"
+ },
+ {
+ "input": "data:test# »",
+ "base": "about:blank",
+ "href": "data:test# %C2%BB",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "test",
+ "search": "",
+ "hash": "# %C2%BB"
+ },
+ {
+ "input": "http://www.google.com",
+ "base": "about:blank",
+ "href": "http://www.google.com/",
+ "origin": "http://www.google.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.google.com",
+ "hostname": "www.google.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://192.0x00A80001",
+ "base": "about:blank",
+ "href": "http://192.168.0.1/",
+ "origin": "http://192.168.0.1",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.0.1",
+ "hostname": "192.168.0.1",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://www/foo%2Ehtml",
+ "base": "about:blank",
+ "href": "http://www/foo%2Ehtml",
+ "origin": "http://www",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www",
+ "hostname": "www",
+ "port": "",
+ "pathname": "/foo%2Ehtml",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://www/foo/%2E/html",
+ "base": "about:blank",
+ "href": "http://www/foo/html",
+ "origin": "http://www",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www",
+ "hostname": "www",
+ "port": "",
+ "pathname": "/foo/html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://user:pass@/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://%25DOMAIN:foobar@foodomain.com/",
+ "base": "about:blank",
+ "href": "http://%25DOMAIN:foobar@foodomain.com/",
+ "origin": "http://foodomain.com",
+ "protocol": "http:",
+ "username": "%25DOMAIN",
+ "password": "foobar",
+ "host": "foodomain.com",
+ "hostname": "foodomain.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:\\\\www.google.com\\foo",
+ "base": "about:blank",
+ "href": "http://www.google.com/foo",
+ "origin": "http://www.google.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.google.com",
+ "hostname": "www.google.com",
+ "port": "",
+ "pathname": "/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo:80/",
+ "base": "about:blank",
+ "href": "http://foo/",
+ "origin": "http://foo",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo:81/",
+ "base": "about:blank",
+ "href": "http://foo:81/",
+ "origin": "http://foo:81",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo:81",
+ "hostname": "foo",
+ "port": "81",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "httpa://foo:80/",
+ "base": "about:blank",
+ "href": "httpa://foo:80/",
+ "origin": "null",
+ "protocol": "httpa:",
+ "username": "",
+ "password": "",
+ "host": "foo:80",
+ "hostname": "foo",
+ "port": "80",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo:-80/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://foo:443/",
+ "base": "about:blank",
+ "href": "https://foo/",
+ "origin": "https://foo",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https://foo:80/",
+ "base": "about:blank",
+ "href": "https://foo:80/",
+ "origin": "https://foo:80",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "foo:80",
+ "hostname": "foo",
+ "port": "80",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp://foo:21/",
+ "base": "about:blank",
+ "href": "ftp://foo/",
+ "origin": "ftp://foo",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp://foo:80/",
+ "base": "about:blank",
+ "href": "ftp://foo:80/",
+ "origin": "ftp://foo:80",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "foo:80",
+ "hostname": "foo",
+ "port": "80",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher://foo:70/",
+ "base": "about:blank",
+ "href": "gopher://foo/",
+ "origin": "gopher://foo",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher://foo:443/",
+ "base": "about:blank",
+ "href": "gopher://foo:443/",
+ "origin": "gopher://foo:443",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "foo:443",
+ "hostname": "foo",
+ "port": "443",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws://foo:80/",
+ "base": "about:blank",
+ "href": "ws://foo/",
+ "origin": "ws://foo",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws://foo:81/",
+ "base": "about:blank",
+ "href": "ws://foo:81/",
+ "origin": "ws://foo:81",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "foo:81",
+ "hostname": "foo",
+ "port": "81",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws://foo:443/",
+ "base": "about:blank",
+ "href": "ws://foo:443/",
+ "origin": "ws://foo:443",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "foo:443",
+ "hostname": "foo",
+ "port": "443",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws://foo:815/",
+ "base": "about:blank",
+ "href": "ws://foo:815/",
+ "origin": "ws://foo:815",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "foo:815",
+ "hostname": "foo",
+ "port": "815",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss://foo:80/",
+ "base": "about:blank",
+ "href": "wss://foo:80/",
+ "origin": "wss://foo:80",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "foo:80",
+ "hostname": "foo",
+ "port": "80",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss://foo:81/",
+ "base": "about:blank",
+ "href": "wss://foo:81/",
+ "origin": "wss://foo:81",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "foo:81",
+ "hostname": "foo",
+ "port": "81",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss://foo:443/",
+ "base": "about:blank",
+ "href": "wss://foo/",
+ "origin": "wss://foo",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss://foo:815/",
+ "base": "about:blank",
+ "href": "wss://foo:815/",
+ "origin": "wss://foo:815",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "foo:815",
+ "hostname": "foo",
+ "port": "815",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/example.com/",
+ "base": "about:blank",
+ "href": "http://example.com/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp:/example.com/",
+ "base": "about:blank",
+ "href": "ftp://example.com/",
+ "origin": "ftp://example.com",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https:/example.com/",
+ "base": "about:blank",
+ "href": "https://example.com/",
+ "origin": "https://example.com",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "madeupscheme:/example.com/",
+ "base": "about:blank",
+ "href": "madeupscheme:/example.com/",
+ "origin": "null",
+ "protocol": "madeupscheme:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:/example.com/",
+ "base": "about:blank",
+ "href": "file:///example.com/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftps:/example.com/",
+ "base": "about:blank",
+ "href": "ftps:/example.com/",
+ "origin": "null",
+ "protocol": "ftps:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher:/example.com/",
+ "base": "about:blank",
+ "href": "gopher://example.com/",
+ "origin": "gopher://example.com",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws:/example.com/",
+ "base": "about:blank",
+ "href": "ws://example.com/",
+ "origin": "ws://example.com",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss:/example.com/",
+ "base": "about:blank",
+ "href": "wss://example.com/",
+ "origin": "wss://example.com",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "data:/example.com/",
+ "base": "about:blank",
+ "href": "data:/example.com/",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "javascript:/example.com/",
+ "base": "about:blank",
+ "href": "javascript:/example.com/",
+ "origin": "null",
+ "protocol": "javascript:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "mailto:/example.com/",
+ "base": "about:blank",
+ "href": "mailto:/example.com/",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:example.com/",
+ "base": "about:blank",
+ "href": "http://example.com/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp:example.com/",
+ "base": "about:blank",
+ "href": "ftp://example.com/",
+ "origin": "ftp://example.com",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https:example.com/",
+ "base": "about:blank",
+ "href": "https://example.com/",
+ "origin": "https://example.com",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "madeupscheme:example.com/",
+ "base": "about:blank",
+ "href": "madeupscheme:example.com/",
+ "origin": "null",
+ "protocol": "madeupscheme:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftps:example.com/",
+ "base": "about:blank",
+ "href": "ftps:example.com/",
+ "origin": "null",
+ "protocol": "ftps:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher:example.com/",
+ "base": "about:blank",
+ "href": "gopher://example.com/",
+ "origin": "gopher://example.com",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws:example.com/",
+ "base": "about:blank",
+ "href": "ws://example.com/",
+ "origin": "ws://example.com",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss:example.com/",
+ "base": "about:blank",
+ "href": "wss://example.com/",
+ "origin": "wss://example.com",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "data:example.com/",
+ "base": "about:blank",
+ "href": "data:example.com/",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "javascript:example.com/",
+ "base": "about:blank",
+ "href": "javascript:example.com/",
+ "origin": "null",
+ "protocol": "javascript:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "mailto:example.com/",
+ "base": "about:blank",
+ "href": "mailto:example.com/",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/segments-userinfo-vs-host.html",
+ {
+ "input": "http:@www.example.com",
+ "base": "about:blank",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/@www.example.com",
+ "base": "about:blank",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://@www.example.com",
+ "base": "about:blank",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:a:b@www.example.com",
+ "base": "about:blank",
+ "href": "http://a:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/a:b@www.example.com",
+ "base": "about:blank",
+ "href": "http://a:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://a:b@www.example.com",
+ "base": "about:blank",
+ "href": "http://a:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://@pple.com",
+ "base": "about:blank",
+ "href": "http://pple.com/",
+ "origin": "http://pple.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "pple.com",
+ "hostname": "pple.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http::b@www.example.com",
+ "base": "about:blank",
+ "href": "http://:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/:b@www.example.com",
+ "base": "about:blank",
+ "href": "http://:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://:b@www.example.com",
+ "base": "about:blank",
+ "href": "http://:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/:@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://user@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:/@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https:@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:a:b@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:/a:b@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://a:b@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http::@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:a:@www.example.com",
+ "base": "about:blank",
+ "href": "http://a@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/a:@www.example.com",
+ "base": "about:blank",
+ "href": "http://a@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://a:@www.example.com",
+ "base": "about:blank",
+ "href": "http://a@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://www.@pple.com",
+ "base": "about:blank",
+ "href": "http://www.@pple.com/",
+ "origin": "http://pple.com",
+ "protocol": "http:",
+ "username": "www.",
+ "password": "",
+ "host": "pple.com",
+ "hostname": "pple.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:@:www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:/@:www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://@:www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://:@www.example.com",
+ "base": "about:blank",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "# Others",
+ {
+ "input": "/",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ".",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "..",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "./test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "../test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "../aaa/test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/aaa/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/aaa/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "../../test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "中/test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/%E4%B8%AD/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/%E4%B8%AD/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://www.example2.com",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example2.com/",
+ "origin": "http://www.example2.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example2.com",
+ "hostname": "www.example2.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//www.example2.com",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example2.com/",
+ "origin": "http://www.example2.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example2.com",
+ "hostname": "www.example2.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:...",
+ "base": "http://www.example.com/test",
+ "href": "file:///...",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/...",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:..",
+ "base": "http://www.example.com/test",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:a",
+ "base": "http://www.example.com/test",
+ "href": "file:///a",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/a",
+ "search": "",
+ "hash": ""
+ },
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/host.html",
+ "Basic canonicalization, uppercase should be converted to lowercase",
+ {
+ "input": "http://ExAmPlE.CoM",
+ "base": "http://other.com/",
+ "href": "http://example.com/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example example.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://Goo%20 goo%7C|.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[:]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "U+3000 is mapped to U+0020 (space) which is disallowed",
+ {
+ "input": "http://GOO\u00a0\u3000goo.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "Other types of space (no-break, zero-width, zero-width-no-break) are name-prepped away to nothing. U+200B, U+2060, and U+FEFF, are ignored",
+ {
+ "input": "http://GOO\u200b\u2060\ufeffgoo.com",
+ "base": "http://other.com/",
+ "href": "http://googoo.com/",
+ "origin": "http://googoo.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "googoo.com",
+ "hostname": "googoo.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Leading and trailing C0 control or space",
+ {
+ "input": "\u0000\u001b\u0004\u0012 http://example.com/\u001f \u000d ",
+ "base": "about:blank",
+ "href": "http://example.com/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Ideographic full stop (full-width period for Chinese, etc.) should be treated as a dot. U+3002 is mapped to U+002E (dot)",
+ {
+ "input": "http://www.foo。bar.com",
+ "base": "http://other.com/",
+ "href": "http://www.foo.bar.com/",
+ "origin": "http://www.foo.bar.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.foo.bar.com",
+ "hostname": "www.foo.bar.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Invalid unicode characters should fail... U+FDD0 is disallowed; %ef%b7%90 is U+FDD0",
+ {
+ "input": "http://\ufdd0zyx.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "This is the same as previous but escaped",
+ {
+ "input": "http://%ef%b7%90zyx.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "U+FFFD",
+ {
+ "input": "https://\ufffd",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://%EF%BF%BD",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://x/\ufffd?\ufffd#\ufffd",
+ "base": "about:blank",
+ "href": "https://x/%EF%BF%BD?%EF%BF%BD#%EF%BF%BD",
+ "origin": "https://x",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "x",
+ "hostname": "x",
+ "port": "",
+ "pathname": "/%EF%BF%BD",
+ "search": "?%EF%BF%BD",
+ "hash": "#%EF%BF%BD"
+ },
+ "Test name prepping, fullwidth input should be converted to ASCII and NOT IDN-ized. This is 'Go' in fullwidth UTF-8/UTF-16.",
+ {
+ "input": "http://Go.com",
+ "base": "http://other.com/",
+ "href": "http://go.com/",
+ "origin": "http://go.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "go.com",
+ "hostname": "go.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "URL spec forbids the following. https://www.w3.org/Bugs/Public/show_bug.cgi?id=24257",
+ {
+ "input": "http://%41.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://%ef%bc%85%ef%bc%94%ef%bc%91.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "...%00 in fullwidth should fail (also as escaped UTF-8 input)",
+ {
+ "input": "http://%00.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://%ef%bc%85%ef%bc%90%ef%bc%90.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "Basic IDN support, UTF-8 and UTF-16 input should be converted to IDN",
+ {
+ "input": "http://你好你好",
+ "base": "http://other.com/",
+ "href": "http://xn--6qqa088eba/",
+ "origin": "http://xn--6qqa088eba",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "xn--6qqa088eba",
+ "hostname": "xn--6qqa088eba",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https://faß.ExAmPlE/",
+ "base": "about:blank",
+ "href": "https://xn--fa-hia.example/",
+ "origin": "https://xn--fa-hia.example",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "xn--fa-hia.example",
+ "hostname": "xn--fa-hia.example",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "sc://faß.ExAmPlE/",
+ "base": "about:blank",
+ "href": "sc://fa%C3%9F.ExAmPlE/",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "fa%C3%9F.ExAmPlE",
+ "hostname": "fa%C3%9F.ExAmPlE",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Invalid escaped characters should fail and the percents should be escaped. https://www.w3.org/Bugs/Public/show_bug.cgi?id=24191",
+ {
+ "input": "http://%zz%66%a.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "If we get an invalid character that has been escaped.",
+ {
+ "input": "http://%25",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://hello%00",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "Escaped numbers should be treated like IP addresses if they are.",
+ {
+ "input": "http://%30%78%63%30%2e%30%32%35%30.01",
+ "base": "http://other.com/",
+ "href": "http://192.168.0.1/",
+ "origin": "http://192.168.0.1",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.0.1",
+ "hostname": "192.168.0.1",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://%30%78%63%30%2e%30%32%35%30.01%2e",
+ "base": "http://other.com/",
+ "href": "http://192.168.0.1/",
+ "origin": "http://192.168.0.1",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.0.1",
+ "hostname": "192.168.0.1",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://192.168.0.257",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "Invalid escaping in hosts causes failure",
+ {
+ "input": "http://%3g%78%63%30%2e%30%32%35%30%2E.01",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "A space in a host causes failure",
+ {
+ "input": "http://192.168.0.1 hello",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "https://x x:12",
+ "base": "about:blank",
+ "failure": true
+ },
+ "Fullwidth and escaped UTF-8 fullwidth should still be treated as IP",
+ {
+ "input": "http://0Xc0.0250.01",
+ "base": "http://other.com/",
+ "href": "http://192.168.0.1/",
+ "origin": "http://192.168.0.1",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.0.1",
+ "hostname": "192.168.0.1",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Domains with empty labels",
+ {
+ "input": "http://./",
+ "base": "about:blank",
+ "href": "http://./",
+ "origin": "http://.",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": ".",
+ "hostname": ".",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://../",
+ "base": "about:blank",
+ "href": "http://../",
+ "origin": "http://..",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "..",
+ "hostname": "..",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://0..0x300/",
+ "base": "about:blank",
+ "href": "http://0..0x300/",
+ "origin": "http://0..0x300",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "0..0x300",
+ "hostname": "0..0x300",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Broken IPv6",
+ {
+ "input": "http://[www.google.com]/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://[google.com]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[::1.2.3.4x]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[::1.2.3.]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[::1.2.]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[::1.]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "Misc Unicode",
+ {
+ "input": "http://foo:💩@example.com/bar",
+ "base": "http://other.com/",
+ "href": "http://foo:%F0%9F%92%A9@example.com/bar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "foo",
+ "password": "%F0%9F%92%A9",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/bar",
+ "search": "",
+ "hash": ""
+ },
+ "# resolving a fragment against any scheme succeeds",
+ {
+ "input": "#",
+ "base": "test:test",
+ "href": "test:test#",
+ "origin": "null",
+ "protocol": "test:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "test",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "#x",
+ "base": "mailto:x@x.com",
+ "href": "mailto:x@x.com#x",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "x@x.com",
+ "search": "",
+ "hash": "#x"
+ },
+ {
+ "input": "#x",
+ "base": "data:,",
+ "href": "data:,#x",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": ",",
+ "search": "",
+ "hash": "#x"
+ },
+ {
+ "input": "#x",
+ "base": "about:blank",
+ "href": "about:blank#x",
+ "origin": "null",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": "#x"
+ },
+ {
+ "input": "#",
+ "base": "test:test?test",
+ "href": "test:test?test#",
+ "origin": "null",
+ "protocol": "test:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "test",
+ "search": "?test",
+ "hash": ""
+ },
+ "# multiple @ in authority state",
+ {
+ "input": "https://@test@test@example:800/",
+ "base": "http://doesnotmatter/",
+ "href": "https://%40test%40test@example:800/",
+ "origin": "https://example:800",
+ "protocol": "https:",
+ "username": "%40test%40test",
+ "password": "",
+ "host": "example:800",
+ "hostname": "example",
+ "port": "800",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https://@@@example",
+ "base": "http://doesnotmatter/",
+ "href": "https://%40%40@example/",
+ "origin": "https://example",
+ "protocol": "https:",
+ "username": "%40%40",
+ "password": "",
+ "host": "example",
+ "hostname": "example",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "non-az-09 characters",
+ {
+ "input": "http://`{}:`{}@h/`{}?`{}",
+ "base": "http://doesnotmatter/",
+ "href": "http://%60%7B%7D:%60%7B%7D@h/%60%7B%7D?`{}",
+ "origin": "http://h",
+ "protocol": "http:",
+ "username": "%60%7B%7D",
+ "password": "%60%7B%7D",
+ "host": "h",
+ "hostname": "h",
+ "port": "",
+ "pathname": "/%60%7B%7D",
+ "search": "?`{}",
+ "hash": ""
+ },
+ "# Credentials in base",
+ {
+ "input": "/some/path",
+ "base": "http://user@example.org/smth",
+ "href": "http://user@example.org/some/path",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "user",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/some/path",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "",
+ "base": "http://user:pass@example.org:21/smth",
+ "href": "http://user:pass@example.org:21/smth",
+ "origin": "http://example.org:21",
+ "protocol": "http:",
+ "username": "user",
+ "password": "pass",
+ "host": "example.org:21",
+ "hostname": "example.org",
+ "port": "21",
+ "pathname": "/smth",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/some/path",
+ "base": "http://user:pass@example.org:21/smth",
+ "href": "http://user:pass@example.org:21/some/path",
+ "origin": "http://example.org:21",
+ "protocol": "http:",
+ "username": "user",
+ "password": "pass",
+ "host": "example.org:21",
+ "hostname": "example.org",
+ "port": "21",
+ "pathname": "/some/path",
+ "search": "",
+ "hash": ""
+ },
+ "# a set of tests designed by zcorpan for relative URLs with unknown schemes",
+ {
+ "input": "i",
+ "base": "sc:sd",
+ "failure": true
+ },
+ {
+ "input": "i",
+ "base": "sc:sd/sd",
+ "failure": true
+ },
+ {
+ "input": "i",
+ "base": "sc:/pa/pa",
+ "href": "sc:/pa/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/i",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "i",
+ "base": "sc://ho/pa",
+ "href": "sc://ho/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "ho",
+ "hostname": "ho",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "i",
+ "base": "sc:///pa/pa",
+ "href": "sc:///pa/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/i",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "../i",
+ "base": "sc:sd",
+ "failure": true
+ },
+ {
+ "input": "../i",
+ "base": "sc:sd/sd",
+ "failure": true
+ },
+ {
+ "input": "../i",
+ "base": "sc:/pa/pa",
+ "href": "sc:/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "../i",
+ "base": "sc://ho/pa",
+ "href": "sc://ho/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "ho",
+ "hostname": "ho",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "../i",
+ "base": "sc:///pa/pa",
+ "href": "sc:///i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/i",
+ "base": "sc:sd",
+ "failure": true
+ },
+ {
+ "input": "/i",
+ "base": "sc:sd/sd",
+ "failure": true
+ },
+ {
+ "input": "/i",
+ "base": "sc:/pa/pa",
+ "href": "sc:/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/i",
+ "base": "sc://ho/pa",
+ "href": "sc://ho/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "ho",
+ "hostname": "ho",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/i",
+ "base": "sc:///pa/pa",
+ "href": "sc:///i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "?i",
+ "base": "sc:sd",
+ "failure": true
+ },
+ {
+ "input": "?i",
+ "base": "sc:sd/sd",
+ "failure": true
+ },
+ {
+ "input": "?i",
+ "base": "sc:/pa/pa",
+ "href": "sc:/pa/pa?i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/pa",
+ "search": "?i",
+ "hash": ""
+ },
+ {
+ "input": "?i",
+ "base": "sc://ho/pa",
+ "href": "sc://ho/pa?i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "ho",
+ "hostname": "ho",
+ "port": "",
+ "pathname": "/pa",
+ "search": "?i",
+ "hash": ""
+ },
+ {
+ "input": "?i",
+ "base": "sc:///pa/pa",
+ "href": "sc:///pa/pa?i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/pa",
+ "search": "?i",
+ "hash": ""
+ },
+ {
+ "input": "#i",
+ "base": "sc:sd",
+ "href": "sc:sd#i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "sd",
+ "search": "",
+ "hash": "#i"
+ },
+ {
+ "input": "#i",
+ "base": "sc:sd/sd",
+ "href": "sc:sd/sd#i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "sd/sd",
+ "search": "",
+ "hash": "#i"
+ },
+ {
+ "input": "#i",
+ "base": "sc:/pa/pa",
+ "href": "sc:/pa/pa#i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/pa",
+ "search": "",
+ "hash": "#i"
+ },
+ {
+ "input": "#i",
+ "base": "sc://ho/pa",
+ "href": "sc://ho/pa#i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "ho",
+ "hostname": "ho",
+ "port": "",
+ "pathname": "/pa",
+ "search": "",
+ "hash": "#i"
+ },
+ {
+ "input": "#i",
+ "base": "sc:///pa/pa",
+ "href": "sc:///pa/pa#i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/pa",
+ "search": "",
+ "hash": "#i"
+ },
+ "# make sure that relative URL logic works on known typically non-relative schemes too",
+ {
+ "input": "about:/../",
+ "base": "about:blank",
+ "href": "about:/",
+ "origin": "null",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "data:/../",
+ "base": "about:blank",
+ "href": "data:/",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "javascript:/../",
+ "base": "about:blank",
+ "href": "javascript:/",
+ "origin": "null",
+ "protocol": "javascript:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "mailto:/../",
+ "base": "about:blank",
+ "href": "mailto:/",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "# unknown schemes and their hosts",
+ {
+ "input": "sc://ñ.test/",
+ "base": "about:blank",
+ "href": "sc://%C3%B1.test/",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "%C3%B1.test",
+ "hostname": "%C3%B1.test",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "sc://\u001F!\"$&'()*+,-.;<=>^_`{|}~/",
+ "base": "about:blank",
+ "href": "sc://%1F!\"$&'()*+,-.;<=>^_`{|}~/",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "%1F!\"$&'()*+,-.;<=>^_`{|}~",
+ "hostname": "%1F!\"$&'()*+,-.;<=>^_`{|}~",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "sc://\u0000/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "sc:// /",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "sc://%/",
+ "base": "about:blank",
+ "href": "sc://%/",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "%",
+ "hostname": "%",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "sc://[/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "sc://\\/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "sc://]/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "x",
+ "base": "sc://ñ",
+ "href": "sc://%C3%B1/x",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "%C3%B1",
+ "hostname": "%C3%B1",
+ "port": "",
+ "pathname": "/x",
+ "search": "",
+ "hash": ""
+ },
+ "# unknown schemes and backslashes",
+ {
+ "input": "sc:\\../",
+ "base": "about:blank",
+ "href": "sc:\\../",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "\\../",
+ "search": "",
+ "hash": ""
+ },
+ "# unknown scheme with path looking like a password",
+ {
+ "input": "sc::a@example.net",
+ "base": "about:blank",
+ "href": "sc::a@example.net",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": ":a@example.net",
+ "search": "",
+ "hash": ""
+ },
+ "# unknown scheme with bogus percent-encoding",
+ {
+ "input": "wow:%NBD",
+ "base": "about:blank",
+ "href": "wow:%NBD",
+ "origin": "null",
+ "protocol": "wow:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "%NBD",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wow:%1G",
+ "base": "about:blank",
+ "href": "wow:%1G",
+ "origin": "null",
+ "protocol": "wow:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "%1G",
+ "search": "",
+ "hash": ""
+ },
+ "# Hosts and percent-encoding",
+ {
+ "input": "ftp://example.com%80/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "ftp://example.com%A0/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://example.com%80/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://example.com%A0/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "ftp://%e2%98%83",
+ "base": "about:blank",
+ "href": "ftp://xn--n3h/",
+ "origin": "ftp://xn--n3h",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "xn--n3h",
+ "hostname": "xn--n3h",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https://%e2%98%83",
+ "base": "about:blank",
+ "href": "https://xn--n3h/",
+ "origin": "https://xn--n3h",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "xn--n3h",
+ "hostname": "xn--n3h",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "# tests from jsdom/whatwg-url designed for code coverage",
+ {
+ "input": "http://127.0.0.1:10100/relative_import.html",
+ "base": "about:blank",
+ "href": "http://127.0.0.1:10100/relative_import.html",
+ "origin": "http://127.0.0.1:10100",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "127.0.0.1:10100",
+ "hostname": "127.0.0.1",
+ "port": "10100",
+ "pathname": "/relative_import.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://facebook.com/?foo=%7B%22abc%22",
+ "base": "about:blank",
+ "href": "http://facebook.com/?foo=%7B%22abc%22",
+ "origin": "http://facebook.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "facebook.com",
+ "hostname": "facebook.com",
+ "port": "",
+ "pathname": "/",
+ "search": "?foo=%7B%22abc%22",
+ "hash": ""
+ },
+ {
+ "input": "https://localhost:3000/jqueryui@1.2.3",
+ "base": "about:blank",
+ "href": "https://localhost:3000/jqueryui@1.2.3",
+ "origin": "https://localhost:3000",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "localhost:3000",
+ "hostname": "localhost",
+ "port": "3000",
+ "pathname": "/jqueryui@1.2.3",
+ "search": "",
+ "hash": ""
+ },
+ "# tab/LF/CR",
+ {
+ "input": "h\tt\nt\rp://h\to\ns\rt:9\t0\n0\r0/p\ta\nt\rh?q\tu\ne\rry#f\tr\na\rg",
+ "base": "about:blank",
+ "href": "http://host:9000/path?query#frag",
+ "origin": "http://host:9000",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "host:9000",
+ "hostname": "host",
+ "port": "9000",
+ "pathname": "/path",
+ "search": "?query",
+ "hash": "#frag"
+ },
+ "# Stringification of URL.searchParams",
+ {
+ "input": "?a=b&c=d",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar?a=b&c=d",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "?a=b&c=d",
+ "searchParams": "a=b&c=d",
+ "hash": ""
+ },
+ {
+ "input": "??a=b&c=d",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar??a=b&c=d",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "??a=b&c=d",
+ "searchParams": "%3Fa=b&c=d",
+ "hash": ""
+ },
+ "# Scheme only",
+ {
+ "input": "http:",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "searchParams": "",
+ "hash": ""
+ },
+ {
+ "input": "http:",
+ "base": "https://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "sc:",
+ "base": "https://example.org/foo/bar",
+ "href": "sc:",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "",
+ "search": "",
+ "searchParams": "",
+ "hash": ""
+ },
+ "# Percent encoding of fragments",
+ {
+ "input": "http://foo.bar/baz?qux#foo\bbar",
+ "base": "about:blank",
+ "href": "http://foo.bar/baz?qux#foo%08bar",
+ "origin": "http://foo.bar",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo.bar",
+ "hostname": "foo.bar",
+ "port": "",
+ "pathname": "/baz",
+ "search": "?qux",
+ "searchParams": "qux=",
+ "hash": "#foo%08bar"
+ },
+ "# IPv4 parsing (via https://github.com/nodejs/node/pull/10317)",
+ {
+ "input": "http://192.168.257",
+ "base": "http://other.com/",
+ "href": "http://192.168.1.1/",
+ "origin": "http://192.168.1.1",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.1.1",
+ "hostname": "192.168.1.1",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://192.168.257.com",
+ "base": "http://other.com/",
+ "href": "http://192.168.257.com/",
+ "origin": "http://192.168.257.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.257.com",
+ "hostname": "192.168.257.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://256",
+ "base": "http://other.com/",
+ "href": "http://0.0.1.0/",
+ "origin": "http://0.0.1.0",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "0.0.1.0",
+ "hostname": "0.0.1.0",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://256.com",
+ "base": "http://other.com/",
+ "href": "http://256.com/",
+ "origin": "http://256.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "256.com",
+ "hostname": "256.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://999999999",
+ "base": "http://other.com/",
+ "href": "http://59.154.201.255/",
+ "origin": "http://59.154.201.255",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "59.154.201.255",
+ "hostname": "59.154.201.255",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://999999999.com",
+ "base": "http://other.com/",
+ "href": "http://999999999.com/",
+ "origin": "http://999999999.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "999999999.com",
+ "hostname": "999999999.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://10000000000",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://10000000000.com",
+ "base": "http://other.com/",
+ "href": "http://10000000000.com/",
+ "origin": "http://10000000000.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "10000000000.com",
+ "hostname": "10000000000.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://4294967295",
+ "base": "http://other.com/",
+ "href": "http://255.255.255.255/",
+ "origin": "http://255.255.255.255",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "255.255.255.255",
+ "hostname": "255.255.255.255",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://4294967296",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://0xffffffff",
+ "base": "http://other.com/",
+ "href": "http://255.255.255.255/",
+ "origin": "http://255.255.255.255",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "255.255.255.255",
+ "hostname": "255.255.255.255",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://0xffffffff1",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://256.256.256.256",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://256.256.256.256.256",
+ "base": "http://other.com/",
+ "href": "http://256.256.256.256.256/",
+ "origin": "http://256.256.256.256.256",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "256.256.256.256.256",
+ "hostname": "256.256.256.256.256",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https://0x.0x.0",
+ "base": "about:blank",
+ "href": "https://0.0.0.0/",
+ "origin": "https://0.0.0.0",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "0.0.0.0",
+ "hostname": "0.0.0.0",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "More IPv4 parsing (via https://github.com/jsdom/whatwg-url/issues/92)",
+ {
+ "input": "https://256.0.0.1/test",
+ "base": "about:blank",
+ "failure": true
+ },
+ "# file URLs containing percent-encoded Windows drive letters (shouldn't work)",
+ {
+ "input": "file:///C%3A/",
+ "base": "about:blank",
+ "href": "file:///C%3A/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C%3A/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:///C%7C/",
+ "base": "about:blank",
+ "href": "file:///C%7C/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C%7C/",
+ "search": "",
+ "hash": ""
+ },
+ "# file URLs relative to other file URLs (via https://github.com/jsdom/whatwg-url/pull/60)",
+ {
+ "input": "pix/submit.gif",
+ "base": "file:///C:/Users/Domenic/Dropbox/GitHub/tmpvar/jsdom/test/level2/html/files/anchor.html",
+ "href": "file:///C:/Users/Domenic/Dropbox/GitHub/tmpvar/jsdom/test/level2/html/files/pix/submit.gif",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/Users/Domenic/Dropbox/GitHub/tmpvar/jsdom/test/level2/html/files/pix/submit.gif",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "..",
+ "base": "file:///C:/",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "..",
+ "base": "file:///",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "# More file URL tests by zcorpan and annevk",
+ {
+ "input": "/",
+ "base": "file:///C:/a/b",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//d:",
+ "base": "file:///C:/a/b",
+ "href": "file:///d:",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/d:",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//d:/..",
+ "base": "file:///C:/a/b",
+ "href": "file:///d:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/d:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "..",
+ "base": "file:///ab:/",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "..",
+ "base": "file:///1:/",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "",
+ "base": "file:///test?test#test",
+ "href": "file:///test?test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?test",
+ "hash": ""
+ },
+ {
+ "input": "file:",
+ "base": "file:///test?test#test",
+ "href": "file:///test?test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?test",
+ "hash": ""
+ },
+ {
+ "input": "?x",
+ "base": "file:///test?test#test",
+ "href": "file:///test?x",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?x",
+ "hash": ""
+ },
+ {
+ "input": "file:?x",
+ "base": "file:///test?test#test",
+ "href": "file:///test?x",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?x",
+ "hash": ""
+ },
+ {
+ "input": "#x",
+ "base": "file:///test?test#test",
+ "href": "file:///test?test#x",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?test",
+ "hash": "#x"
+ },
+ {
+ "input": "file:#x",
+ "base": "file:///test?test#test",
+ "href": "file:///test?test#x",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?test",
+ "hash": "#x"
+ },
+ "# File URLs and many (back)slashes",
+ {
+ "input": "file:///localhost//cat",
+ "base": "about:blank",
+ "href": "file:///localhost//cat",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/localhost//cat",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "\\//pig",
+ "base": "file://lion/",
+ "href": "file:///pig",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pig",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://",
+ "base": "file://ape/",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "# Windows drive letter handling with the 'file:' base URL",
+ {
+ "input": "C|#",
+ "base": "file://host/dir/file",
+ "href": "file:///C:#",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|?",
+ "base": "file://host/dir/file",
+ "href": "file:///C:?",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|/",
+ "base": "file://host/dir/file",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|\n/",
+ "base": "file://host/dir/file",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|\\",
+ "base": "file://host/dir/file",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C",
+ "base": "file://host/dir/file",
+ "href": "file://host/dir/C",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "host",
+ "hostname": "host",
+ "port": "",
+ "pathname": "/dir/C",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|a",
+ "base": "file://host/dir/file",
+ "href": "file://host/dir/C|a",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "host",
+ "hostname": "host",
+ "port": "",
+ "pathname": "/dir/C|a",
+ "search": "",
+ "hash": ""
+ },
+ "# Windows drive letter quirk in the file slash state",
+ {
+ "input": "/c:/foo/bar",
+ "base": "file://host/path",
+ "href": "file:///c:/foo/bar",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/c:/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ "# Windows drive letter quirk (no host)",
+ {
+ "input": "file:/C|/",
+ "base": "about:blank",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://C|/",
+ "base": "about:blank",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ "# Windows drive letter quirk with not empty host",
+ {
+ "input": "file://example.net/C:/",
+ "base": "about:blank",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://1.2.3.4/C:/",
+ "base": "about:blank",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://[1::8]/C:/",
+ "base": "about:blank",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ "# file URLs without base URL by Rimas Misevičius",
+ {
+ "input": "file:",
+ "base": "about:blank",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:?q=v",
+ "base": "about:blank",
+ "href": "file:///?q=v",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "?q=v",
+ "hash": ""
+ },
+ {
+ "input": "file:#frag",
+ "base": "about:blank",
+ "href": "file:///#frag",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": "#frag"
+ },
+ "# IPv6 tests",
+ {
+ "input": "http://[1:0::]",
+ "base": "http://example.net/",
+ "href": "http://[1::]/",
+ "origin": "http://[1::]",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[1::]",
+ "hostname": "[1::]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[0:1:2:3:4:5:6:7:8]",
+ "base": "http://example.net/",
+ "failure": true
+ },
+ {
+ "input": "https://[0::0::0]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:.0]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:0:]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:1:2:3:4:5:6:7.0.0.0.1]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:1.00.0.0.0]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:1.290.0.0.0]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:1.23.23]",
+ "base": "about:blank",
+ "failure": true
+ },
+ "# Empty host",
+ {
+ "input": "http://?",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://#",
+ "base": "about:blank",
+ "failure": true
+ },
+ "Port overflow (2^32 + 81)",
+ {
+ "input": "http://f:4294967377/c",
+ "base": "http://example.org/",
+ "failure": true
+ },
+ "Port overflow (2^64 + 81)",
+ {
+ "input": "http://f:18446744073709551697/c",
+ "base": "http://example.org/",
+ "failure": true
+ },
+ "Port overflow (2^128 + 81)",
+ {
+ "input": "http://f:340282366920938463463374607431768211537/c",
+ "base": "http://example.org/",
+ "failure": true
+ },
+ "# Non-special-URL path tests",
+ {
+ "input": "///",
+ "base": "sc://x/",
+ "href": "sc:///",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "tftp://foobar.com/someconfig;mode=netascii",
+ "base": "about:blank",
+ "href": "tftp://foobar.com/someconfig;mode=netascii",
+ "origin": "null",
+ "protocol": "tftp:",
+ "username": "",
+ "password": "",
+ "host": "foobar.com",
+ "hostname": "foobar.com",
+ "port": "",
+ "pathname": "/someconfig;mode=netascii",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "telnet://user:pass@foobar.com:23/",
+ "base": "about:blank",
+ "href": "telnet://user:pass@foobar.com:23/",
+ "origin": "null",
+ "protocol": "telnet:",
+ "username": "user",
+ "password": "pass",
+ "host": "foobar.com:23",
+ "hostname": "foobar.com",
+ "port": "23",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ut2004://10.10.10.10:7777/Index.ut2",
+ "base": "about:blank",
+ "href": "ut2004://10.10.10.10:7777/Index.ut2",
+ "origin": "null",
+ "protocol": "ut2004:",
+ "username": "",
+ "password": "",
+ "host": "10.10.10.10:7777",
+ "hostname": "10.10.10.10",
+ "port": "7777",
+ "pathname": "/Index.ut2",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "redis://foo:bar@somehost:6379/0?baz=bam&qux=baz",
+ "base": "about:blank",
+ "href": "redis://foo:bar@somehost:6379/0?baz=bam&qux=baz",
+ "origin": "null",
+ "protocol": "redis:",
+ "username": "foo",
+ "password": "bar",
+ "host": "somehost:6379",
+ "hostname": "somehost",
+ "port": "6379",
+ "pathname": "/0",
+ "search": "?baz=bam&qux=baz",
+ "hash": ""
+ },
+ {
+ "input": "rsync://foo@host:911/sup",
+ "base": "about:blank",
+ "href": "rsync://foo@host:911/sup",
+ "origin": "null",
+ "protocol": "rsync:",
+ "username": "foo",
+ "password": "",
+ "host": "host:911",
+ "hostname": "host",
+ "port": "911",
+ "pathname": "/sup",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "git://github.com/foo/bar.git",
+ "base": "about:blank",
+ "href": "git://github.com/foo/bar.git",
+ "origin": "null",
+ "protocol": "git:",
+ "username": "",
+ "password": "",
+ "host": "github.com",
+ "hostname": "github.com",
+ "port": "",
+ "pathname": "/foo/bar.git",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "irc://myserver.com:6999/channel?passwd",
+ "base": "about:blank",
+ "href": "irc://myserver.com:6999/channel?passwd",
+ "origin": "null",
+ "protocol": "irc:",
+ "username": "",
+ "password": "",
+ "host": "myserver.com:6999",
+ "hostname": "myserver.com",
+ "port": "6999",
+ "pathname": "/channel",
+ "search": "?passwd",
+ "hash": ""
+ },
+ {
+ "input": "dns://fw.example.org:9999/foo.bar.org?type=TXT",
+ "base": "about:blank",
+ "href": "dns://fw.example.org:9999/foo.bar.org?type=TXT",
+ "origin": "null",
+ "protocol": "dns:",
+ "username": "",
+ "password": "",
+ "host": "fw.example.org:9999",
+ "hostname": "fw.example.org",
+ "port": "9999",
+ "pathname": "/foo.bar.org",
+ "search": "?type=TXT",
+ "hash": ""
+ },
+ {
+ "input": "ldap://localhost:389/ou=People,o=JNDITutorial",
+ "base": "about:blank",
+ "href": "ldap://localhost:389/ou=People,o=JNDITutorial",
+ "origin": "null",
+ "protocol": "ldap:",
+ "username": "",
+ "password": "",
+ "host": "localhost:389",
+ "hostname": "localhost",
+ "port": "389",
+ "pathname": "/ou=People,o=JNDITutorial",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "git+https://github.com/foo/bar",
+ "base": "about:blank",
+ "href": "git+https://github.com/foo/bar",
+ "origin": "null",
+ "protocol": "git+https:",
+ "username": "",
+ "password": "",
+ "host": "github.com",
+ "hostname": "github.com",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "urn:ietf:rfc:2648",
+ "base": "about:blank",
+ "href": "urn:ietf:rfc:2648",
+ "origin": "null",
+ "protocol": "urn:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "ietf:rfc:2648",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "tag:joe@example.org,2001:foo/bar",
+ "base": "about:blank",
+ "href": "tag:joe@example.org,2001:foo/bar",
+ "origin": "null",
+ "protocol": "tag:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "joe@example.org,2001:foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ "# percent encoded hosts in non-special-URLs",
+ {
+ "input": "non-special://%E2%80%A0/",
+ "base": "about:blank",
+ "href": "non-special://%E2%80%A0/",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "%E2%80%A0",
+ "hostname": "%E2%80%A0",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://H%4fSt/path",
+ "base": "about:blank",
+ "href": "non-special://H%4fSt/path",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "H%4fSt",
+ "hostname": "H%4fSt",
+ "port": "",
+ "pathname": "/path",
+ "search": "",
+ "hash": ""
+ },
+ "# IPv6 in non-special-URLs",
+ {
+ "input": "non-special://[1:2:0:0:5:0:0:0]/",
+ "base": "about:blank",
+ "href": "non-special://[1:2:0:0:5::]/",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "[1:2:0:0:5::]",
+ "hostname": "[1:2:0:0:5::]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://[1:2:0:0:0:0:0:3]/",
+ "base": "about:blank",
+ "href": "non-special://[1:2::3]/",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "[1:2::3]",
+ "hostname": "[1:2::3]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://[1:2::3]:80/",
+ "base": "about:blank",
+ "href": "non-special://[1:2::3]:80/",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "[1:2::3]:80",
+ "hostname": "[1:2::3]",
+ "port": "80",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://[:80/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "blob:https://example.com:443/",
+ "base": "about:blank",
+ "href": "blob:https://example.com:443/",
+ "protocol": "blob:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "https://example.com:443/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "blob:d3958f5c-0777-0845-9dcf-2cb28783acaf",
+ "base": "about:blank",
+ "href": "blob:d3958f5c-0777-0845-9dcf-2cb28783acaf",
+ "protocol": "blob:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "d3958f5c-0777-0845-9dcf-2cb28783acaf",
+ "search": "",
+ "hash": ""
+ },
+ "Invalid IPv4 radix digits",
+ {
+ "input": "http://0177.0.0.0189",
+ "base": "about:blank",
+ "href": "http://0177.0.0.0189/",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "0177.0.0.0189",
+ "hostname": "0177.0.0.0189",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://0x7f.0.0.0x7g",
+ "base": "about:blank",
+ "href": "http://0x7f.0.0.0x7g/",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "0x7f.0.0.0x7g",
+ "hostname": "0x7f.0.0.0x7g",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://0X7F.0.0.0X7G",
+ "base": "about:blank",
+ "href": "http://0x7f.0.0.0x7g/",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "0x7f.0.0.0x7g",
+ "hostname": "0x7f.0.0.0x7g",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Invalid IPv4 portion of IPv6 address",
+ {
+ "input": "http://[::127.0.0.0.1]",
+ "base": "about:blank",
+ "failure": true
+ },
+ "Uncompressed IPv6 addresses with 0",
+ {
+ "input": "http://[0:1:0:1:0:1:0:1]",
+ "base": "about:blank",
+ "href": "http://[0:1:0:1:0:1:0:1]/",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[0:1:0:1:0:1:0:1]",
+ "hostname": "[0:1:0:1:0:1:0:1]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[1:0:1:0:1:0:1:0]",
+ "base": "about:blank",
+ "href": "http://[1:0:1:0:1:0:1:0]/",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[1:0:1:0:1:0:1:0]",
+ "hostname": "[1:0:1:0:1:0:1:0]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Percent-encoded query and fragment",
+ {
+ "input": "http://example.org/test?\u0022",
+ "base": "about:blank",
+ "href": "http://example.org/test?%22",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%22",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?\u0023",
+ "base": "about:blank",
+ "href": "http://example.org/test?#",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?\u003C",
+ "base": "about:blank",
+ "href": "http://example.org/test?%3C",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%3C",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?\u003E",
+ "base": "about:blank",
+ "href": "http://example.org/test?%3E",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%3E",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?\u2323",
+ "base": "about:blank",
+ "href": "http://example.org/test?%E2%8C%A3",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%E2%8C%A3",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?%23%23",
+ "base": "about:blank",
+ "href": "http://example.org/test?%23%23",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%23%23",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?%GH",
+ "base": "about:blank",
+ "href": "http://example.org/test?%GH",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%GH",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?a#%EF",
+ "base": "about:blank",
+ "href": "http://example.org/test?a#%EF",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?a",
+ "hash": "#%EF"
+ },
+ {
+ "input": "http://example.org/test?a#%GH",
+ "base": "about:blank",
+ "href": "http://example.org/test?a#%GH",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?a",
+ "hash": "#%GH"
+ },
+ "Bad bases",
+ {
+ "input": "test-a.html",
+ "base": "a",
+ "failure": true
+ },
+ {
+ "input": "test-a-slash.html",
+ "base": "a/",
+ "failure": true
+ },
+ {
+ "input": "test-a-slash-slash.html",
+ "base": "a//",
+ "failure": true
+ },
+ {
+ "input": "test-a-colon.html",
+ "base": "a:",
+ "failure": true
+ },
+ {
+ "input": "test-a-colon-slash.html",
+ "base": "a:/",
+ "href": "a:/test-a-colon-slash.html",
+ "protocol": "a:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test-a-colon-slash.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "test-a-colon-slash-slash.html",
+ "base": "a://",
+ "href": "a:///test-a-colon-slash-slash.html",
+ "protocol": "a:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test-a-colon-slash-slash.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "test-a-colon-b.html",
+ "base": "a:b",
+ "failure": true
+ },
+ {
+ "input": "test-a-colon-slash-b.html",
+ "base": "a:/b",
+ "href": "a:/test-a-colon-slash-b.html",
+ "protocol": "a:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test-a-colon-slash-b.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "test-a-colon-slash-slash-b.html",
+ "base": "a://b",
+ "href": "a://b/test-a-colon-slash-slash-b.html",
+ "protocol": "a:",
+ "username": "",
+ "password": "",
+ "host": "b",
+ "hostname": "b",
+ "port": "",
+ "pathname": "/test-a-colon-slash-slash-b.html",
+ "search": "",
+ "hash": ""
+ },
+ "Null code point in fragment",
+ {
+ "input": "http://example.org/test?a#b\u0000c",
+ "base": "about:blank",
+ "href": "http://example.org/test?a#bc",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?a",
+ "hash": "#bc"
+ }
+]
diff --git a/netwerk/test/gtest/urltestdata.json b/netwerk/test/gtest/urltestdata.json
new file mode 100644
index 0000000000..b093656ff4
--- /dev/null
+++ b/netwerk/test/gtest/urltestdata.json
@@ -0,0 +1,6480 @@
+[
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/script-tests/segments.js",
+ {
+ "input": "http://example\t.\norg",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://user:pass@foo:21/bar;par?b#c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://user:pass@foo:21/bar;par?b#c",
+ "origin": "http://foo:21",
+ "protocol": "http:",
+ "username": "user",
+ "password": "pass",
+ "host": "foo:21",
+ "hostname": "foo",
+ "port": "21",
+ "pathname": "/bar;par",
+ "search": "?b",
+ "hash": "#c"
+ },
+ {
+ "input": "https://test:@test",
+ "base": "about:blank",
+ "href": "https://test@test/",
+ "origin": "https://test",
+ "protocol": "https:",
+ "username": "test",
+ "password": "",
+ "host": "test",
+ "hostname": "test",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https://:@test",
+ "base": "about:blank",
+ "href": "https://test/",
+ "origin": "https://test",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "test",
+ "hostname": "test",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://test:@test/x",
+ "base": "about:blank",
+ "href": "non-special://test@test/x",
+ "origin": "null",
+ "protocol": "non-special:",
+ "username": "test",
+ "password": "",
+ "host": "test",
+ "hostname": "test",
+ "port": "",
+ "pathname": "/x",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://:@test/x",
+ "base": "about:blank",
+ "href": "non-special://test/x",
+ "origin": "null",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "test",
+ "hostname": "test",
+ "port": "",
+ "pathname": "/x",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:foo.com",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/foo.com",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/foo.com",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "\t :foo.com \n",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:foo.com",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:foo.com",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": " foo.com ",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/foo.com",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/foo.com",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "a:\t foo.com",
+ "base": "http://example.org/foo/bar",
+ "href": "a: foo.com",
+ "origin": "null",
+ "protocol": "a:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": " foo.com",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:21/ b ? d # e ",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f:21/%20b%20?%20d%20# e",
+ "origin": "http://f:21",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f:21",
+ "hostname": "f",
+ "port": "21",
+ "pathname": "/%20b%20",
+ "search": "?%20d%20",
+ "hash": "# e"
+ },
+ {
+ "input": "lolscheme:x x#x x",
+ "base": "about:blank",
+ "href": "lolscheme:x x#x x",
+ "protocol": "lolscheme:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "x x",
+ "search": "",
+ "hash": "#x x"
+ },
+ {
+ "input": "http://f:/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f/c",
+ "origin": "http://f",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f",
+ "hostname": "f",
+ "port": "",
+ "pathname": "/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:0/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f:0/c",
+ "origin": "http://f:0",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f:0",
+ "hostname": "f",
+ "port": "0",
+ "pathname": "/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:00000000000000/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f:0/c",
+ "origin": "http://f:0",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f:0",
+ "hostname": "f",
+ "port": "0",
+ "pathname": "/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:00000000000000000000080/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f/c",
+ "origin": "http://f",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f",
+ "hostname": "f",
+ "port": "",
+ "pathname": "/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:b/c",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://f: /c",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://f:\n/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://f/c",
+ "origin": "http://f",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "f",
+ "hostname": "f",
+ "port": "",
+ "pathname": "/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://f:fifty-two/c",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://f:999999/c",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "non-special://f:999999/c",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://f: 21 / b ? d # e ",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": " \t",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":foo.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:foo.com/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:foo.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":foo.com\\",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:foo.com/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:foo.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":a",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:a",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:a",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":\\",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":#",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:#",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "#",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar#",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "#/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar#/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": "#/"
+ },
+ {
+ "input": "#\\",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar#\\",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": "#\\"
+ },
+ {
+ "input": "#;?",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar#;?",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": "#;?"
+ },
+ {
+ "input": "?",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar?",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ":23",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:23",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:23",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/:23",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/:23",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/:23",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "::",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/::",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/::",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "::23",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/::23",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/::23",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo://",
+ "base": "http://example.org/foo/bar",
+ "href": "foo:///",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://a:b@c:29/d",
+ "base": "http://example.org/foo/bar",
+ "href": "http://a:b@c:29/d",
+ "origin": "http://c:29",
+ "protocol": "http:",
+ "username": "a",
+ "password": "b",
+ "host": "c:29",
+ "hostname": "c",
+ "port": "29",
+ "pathname": "/d",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http::@c:29",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/:@c:29",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/:@c:29",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://&a:foo(b]c@d:2/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://&a:foo(b%5Dc@d:2/",
+ "origin": "http://d:2",
+ "protocol": "http:",
+ "username": "&a",
+ "password": "foo(b%5Dc",
+ "host": "d:2",
+ "hostname": "d",
+ "port": "2",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://::@c@d:2",
+ "base": "http://example.org/foo/bar",
+ "href": "http://:%3A%40c@d:2/",
+ "origin": "http://d:2",
+ "protocol": "http:",
+ "username": "",
+ "password": "%3A%40c",
+ "host": "d:2",
+ "hostname": "d",
+ "port": "2",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo.com:b@d/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo.com:b@d/",
+ "origin": "http://d",
+ "protocol": "http:",
+ "username": "foo.com",
+ "password": "b",
+ "host": "d",
+ "hostname": "d",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo.com/\\@",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo.com//@",
+ "origin": "http://foo.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo.com",
+ "hostname": "foo.com",
+ "port": "",
+ "pathname": "//@",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:\\\\foo.com\\",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo.com/",
+ "origin": "http://foo.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo.com",
+ "hostname": "foo.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:\\\\a\\b:c\\d@foo.com\\",
+ "base": "http://example.org/foo/bar",
+ "href": "http://a/b:c/d@foo.com/",
+ "origin": "http://a",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "a",
+ "hostname": "a",
+ "port": "",
+ "pathname": "/b:c/d@foo.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo:/",
+ "base": "http://example.org/foo/bar",
+ "href": "foo:/",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo:/bar.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "foo:/bar.com/",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/bar.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo://///////",
+ "base": "http://example.org/foo/bar",
+ "href": "foo://///////",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "///////",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo://///////bar.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "foo://///////bar.com/",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "///////bar.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "foo:////://///",
+ "base": "http://example.org/foo/bar",
+ "href": "foo:////://///",
+ "origin": "null",
+ "protocol": "foo:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "//://///",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "c:/foo",
+ "base": "http://example.org/foo/bar",
+ "href": "c:/foo",
+ "origin": "null",
+ "protocol": "c:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//foo/bar",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo/bar",
+ "origin": "http://foo",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo/path;a??e#f#g",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo/path;a??e#f#g",
+ "origin": "http://foo",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/path;a",
+ "search": "??e",
+ "hash": "#f#g"
+ },
+ {
+ "input": "http://foo/abcd?efgh?ijkl",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo/abcd?efgh?ijkl",
+ "origin": "http://foo",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/abcd",
+ "search": "?efgh?ijkl",
+ "hash": ""
+ },
+ {
+ "input": "http://foo/abcd#foo?bar",
+ "base": "http://example.org/foo/bar",
+ "href": "http://foo/abcd#foo?bar",
+ "origin": "http://foo",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/abcd",
+ "search": "",
+ "hash": "#foo?bar"
+ },
+ {
+ "input": "[61:24:74]:98",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/[61:24:74]:98",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/[61:24:74]:98",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:[61:27]/:foo",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/[61:27]/:foo",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/[61:27]/:foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[1::2]:3:4",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://2001::1",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://2001::1]",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://2001::1]:80",
+ "base": "http://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "http://[2001::1]",
+ "base": "http://example.org/foo/bar",
+ "href": "http://[2001::1]/",
+ "origin": "http://[2001::1]",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[2001::1]",
+ "hostname": "[2001::1]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[::127.0.0.1]",
+ "base": "http://example.org/foo/bar",
+ "href": "http://[::7f00:1]/",
+ "origin": "http://[::7f00:1]",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[::7f00:1]",
+ "hostname": "[::7f00:1]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[0:0:0:0:0:0:13.1.68.3]",
+ "base": "http://example.org/foo/bar",
+ "href": "http://[::d01:4403]/",
+ "origin": "http://[::d01:4403]",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[::d01:4403]",
+ "hostname": "[::d01:4403]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[2001::1]:80",
+ "base": "http://example.org/foo/bar",
+ "href": "http://[2001::1]/",
+ "origin": "http://[2001::1]",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[2001::1]",
+ "hostname": "[2001::1]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/example.com/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ftp://example.com/",
+ "origin": "ftp://example.com",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "https://example.com/",
+ "origin": "https://example.com",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "madeupscheme:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "madeupscheme:/example.com/",
+ "origin": "null",
+ "protocol": "madeupscheme:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "file:///example.com/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://example:1/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "file://example:test/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "file://example%/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "file://[example]/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "ftps:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ftps:/example.com/",
+ "origin": "null",
+ "protocol": "ftps:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "gopher://example.com/",
+ "origin": "null",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ws://example.com/",
+ "origin": "ws://example.com",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "wss://example.com/",
+ "origin": "wss://example.com",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "data:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "data:/example.com/",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ {
+ "input": "javascript:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "javascript:/example.com/",
+ "origin": "null",
+ "protocol": "javascript:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "mailto:/example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "mailto:/example.com/",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/example.com/",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ftp://example.com/",
+ "origin": "ftp://example.com",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "https://example.com/",
+ "origin": "https://example.com",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "madeupscheme:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "madeupscheme:example.com/",
+ "origin": "null",
+ "protocol": "madeupscheme:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftps:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ftps:example.com/",
+ "origin": "null",
+ "protocol": "ftps:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "gopher://example.com/",
+ "origin": "null",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "ws://example.com/",
+ "origin": "ws://example.com",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "wss://example.com/",
+ "origin": "wss://example.com",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "data:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "data:example.com/",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ {
+ "input": "javascript:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "javascript:example.com/",
+ "origin": "null",
+ "protocol": "javascript:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "mailto:example.com/",
+ "base": "http://example.org/foo/bar",
+ "href": "mailto:example.com/",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/a/b/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/a/b/c",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/a/b/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/a/ /c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/a/%20/c",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/a/%20/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/a%2fc",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/a%2fc",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/a%2fc",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/a/%2f/c",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/a/%2f/c",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/a/%2f/c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "#β",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar#%CE%B2",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": "#%CE%B2"
+ },
+ {
+ "input": "data:text/html,test#test",
+ "base": "http://example.org/foo/bar",
+ "href": "data:text/html,test#test",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "text/html,test",
+ "search": "",
+ "hash": "#test"
+ },
+ {
+ "input": "tel:1234567890",
+ "base": "http://example.org/foo/bar",
+ "href": "tel:1234567890",
+ "origin": "null",
+ "protocol": "tel:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "1234567890",
+ "search": "",
+ "hash": ""
+ },
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/file.html",
+ {
+ "input": "file:c:\\foo\\bar.html",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///c:/foo/bar.html",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/c:/foo/bar.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": " File:c|////foo\\bar.html",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///c:////foo/bar.html",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/c:////foo/bar.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|/foo/bar",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///C:/foo/bar",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/C|\\foo\\bar",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///C:/foo/bar",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//C|/foo/bar",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///C:/foo/bar",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//server/file",
+ "base": "file:///tmp/mock/path",
+ "href": "file://server/file",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "server",
+ "hostname": "server",
+ "port": "",
+ "pathname": "/file",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "\\\\server\\file",
+ "base": "file:///tmp/mock/path",
+ "href": "file://server/file",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "server",
+ "hostname": "server",
+ "port": "",
+ "pathname": "/file",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/\\server/file",
+ "base": "file:///tmp/mock/path",
+ "href": "file://server/file",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "server",
+ "hostname": "server",
+ "port": "",
+ "pathname": "/file",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:///foo/bar.txt",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///foo/bar.txt",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/foo/bar.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:///home/me",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///home/me",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/home/me",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "///",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "///test",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://test",
+ "base": "file:///tmp/mock/path",
+ "href": "file://test/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "test",
+ "hostname": "test",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://localhost",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://localhost/",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://localhost/test",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "test",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///tmp/mock/test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/tmp/mock/test",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:test",
+ "base": "file:///tmp/mock/path",
+ "href": "file:///tmp/mock/test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/tmp/mock/test",
+ "search": "",
+ "hash": ""
+ },
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/script-tests/path.js",
+ {
+ "input": "http://example.com/././foo",
+ "base": "about:blank",
+ "href": "http://example.com/foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/./.foo",
+ "base": "about:blank",
+ "href": "http://example.com/.foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/.foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/.",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/./",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar/..",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar/../",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/..bar",
+ "base": "about:blank",
+ "href": "http://example.com/foo/..bar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/..bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar/../ton",
+ "base": "about:blank",
+ "href": "http://example.com/foo/ton",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/ton",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar/../ton/../../a",
+ "base": "about:blank",
+ "href": "http://example.com/a",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/a",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/../../..",
+ "base": "about:blank",
+ "href": "http://example.com/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/../../../ton",
+ "base": "about:blank",
+ "href": "http://example.com/ton",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/ton",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/%2e",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/%2e%2",
+ "base": "about:blank",
+ "href": "http://example.com/foo/%2e%2",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/%2e%2",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/%2e./%2e%2e/.%2e/%2e.bar",
+ "base": "about:blank",
+ "href": "http://example.com/%2e.bar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%2e.bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com////../..",
+ "base": "about:blank",
+ "href": "http://example.com//",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "//",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar//../..",
+ "base": "about:blank",
+ "href": "http://example.com/foo/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo/bar//..",
+ "base": "about:blank",
+ "href": "http://example.com/foo/bar/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo/bar/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo",
+ "base": "about:blank",
+ "href": "http://example.com/foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/%20foo",
+ "base": "about:blank",
+ "href": "http://example.com/%20foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%20foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%",
+ "base": "about:blank",
+ "href": "http://example.com/foo%",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%2",
+ "base": "about:blank",
+ "href": "http://example.com/foo%2",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%2",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%2zbar",
+ "base": "about:blank",
+ "href": "http://example.com/foo%2zbar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%2zbar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%2©zbar",
+ "base": "about:blank",
+ "href": "http://example.com/foo%2%C3%82%C2%A9zbar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%2%C3%82%C2%A9zbar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%41%7a",
+ "base": "about:blank",
+ "href": "http://example.com/foo%41%7a",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%41%7a",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo\t\u0091%91",
+ "base": "about:blank",
+ "href": "http://example.com/foo%C2%91%91",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%C2%91%91",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo%00%51",
+ "base": "about:blank",
+ "href": "http://example.com/foo%00%51",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foo%00%51",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/(%28:%3A%29)",
+ "base": "about:blank",
+ "href": "http://example.com/(%28:%3A%29)",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/(%28:%3A%29)",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/%3A%3a%3C%3c",
+ "base": "about:blank",
+ "href": "http://example.com/%3A%3a%3C%3c",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%3A%3a%3C%3c",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/foo\tbar",
+ "base": "about:blank",
+ "href": "http://example.com/foobar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/foobar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com\\\\foo\\\\bar",
+ "base": "about:blank",
+ "href": "http://example.com//foo//bar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "//foo//bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/%7Ffp3%3Eju%3Dduvgw%3Dd",
+ "base": "about:blank",
+ "href": "http://example.com/%7Ffp3%3Eju%3Dduvgw%3Dd",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%7Ffp3%3Eju%3Dduvgw%3Dd",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/@asdf%40",
+ "base": "about:blank",
+ "href": "http://example.com/@asdf%40",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/@asdf%40",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/你好你好",
+ "base": "about:blank",
+ "href": "http://example.com/%E4%BD%A0%E5%A5%BD%E4%BD%A0%E5%A5%BD",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%E4%BD%A0%E5%A5%BD%E4%BD%A0%E5%A5%BD",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/‥/foo",
+ "base": "about:blank",
+ "href": "http://example.com/%E2%80%A5/foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%E2%80%A5/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com//foo",
+ "base": "about:blank",
+ "href": "http://example.com/%EF%BB%BF/foo",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%EF%BB%BF/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.com/‮/foo/‭/bar",
+ "base": "about:blank",
+ "href": "http://example.com/%E2%80%AE/foo/%E2%80%AD/bar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/%E2%80%AE/foo/%E2%80%AD/bar",
+ "search": "",
+ "hash": ""
+ },
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/script-tests/relative.js",
+ {
+ "input": "http://www.google.com/foo?bar=baz#",
+ "base": "about:blank",
+ "href": "http://www.google.com/foo?bar=baz#",
+ "origin": "http://www.google.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.google.com",
+ "hostname": "www.google.com",
+ "port": "",
+ "pathname": "/foo",
+ "search": "?bar=baz",
+ "hash": ""
+ },
+ {
+ "input": "http://www.google.com/foo?bar=baz# »",
+ "base": "about:blank",
+ "href": "http://www.google.com/foo?bar=baz# %C2%BB",
+ "origin": "http://www.google.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.google.com",
+ "hostname": "www.google.com",
+ "port": "",
+ "pathname": "/foo",
+ "search": "?bar=baz",
+ "hash": "# %C2%BB"
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "data:test# »",
+ "base": "about:blank",
+ "href": "data:test# %C2%BB",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "test",
+ "search": "",
+ "hash": "# %C2%BB",
+ "skip": true
+ },
+ {
+ "input": "http://www.google.com",
+ "base": "about:blank",
+ "href": "http://www.google.com/",
+ "origin": "http://www.google.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.google.com",
+ "hostname": "www.google.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://192.0x00A80001",
+ "base": "about:blank",
+ "href": "http://192.168.0.1/",
+ "origin": "http://192.168.0.1",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.0.1",
+ "hostname": "192.168.0.1",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://www/foo%2Ehtml",
+ "base": "about:blank",
+ "href": "http://www/foo%2Ehtml",
+ "origin": "http://www",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www",
+ "hostname": "www",
+ "port": "",
+ "pathname": "/foo%2Ehtml",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://www/foo/%2E/html",
+ "base": "about:blank",
+ "href": "http://www/foo/html",
+ "origin": "http://www",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www",
+ "hostname": "www",
+ "port": "",
+ "pathname": "/foo/html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://user:pass@/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://%25DOMAIN:foobar@foodomain.com/",
+ "base": "about:blank",
+ "href": "http://%25DOMAIN:foobar@foodomain.com/",
+ "origin": "http://foodomain.com",
+ "protocol": "http:",
+ "username": "%25DOMAIN",
+ "password": "foobar",
+ "host": "foodomain.com",
+ "hostname": "foodomain.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:\\\\www.google.com\\foo",
+ "base": "about:blank",
+ "href": "http://www.google.com/foo",
+ "origin": "http://www.google.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.google.com",
+ "hostname": "www.google.com",
+ "port": "",
+ "pathname": "/foo",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo:80/",
+ "base": "about:blank",
+ "href": "http://foo/",
+ "origin": "http://foo",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo:81/",
+ "base": "about:blank",
+ "href": "http://foo:81/",
+ "origin": "http://foo:81",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo:81",
+ "hostname": "foo",
+ "port": "81",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "httpa://foo:80/",
+ "base": "about:blank",
+ "href": "httpa://foo:80/",
+ "origin": "null",
+ "protocol": "httpa:",
+ "username": "",
+ "password": "",
+ "host": "foo:80",
+ "hostname": "foo",
+ "port": "80",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://foo:-80/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://foo:443/",
+ "base": "about:blank",
+ "href": "https://foo/",
+ "origin": "https://foo",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https://foo:80/",
+ "base": "about:blank",
+ "href": "https://foo:80/",
+ "origin": "https://foo:80",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "foo:80",
+ "hostname": "foo",
+ "port": "80",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp://foo:21/",
+ "base": "about:blank",
+ "href": "ftp://foo/",
+ "origin": "ftp://foo",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp://foo:80/",
+ "base": "about:blank",
+ "href": "ftp://foo:80/",
+ "origin": "ftp://foo:80",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "foo:80",
+ "hostname": "foo",
+ "port": "80",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher://foo:70/",
+ "base": "about:blank",
+ "href": "gopher://foo/",
+ "origin": "null",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher://foo:443/",
+ "base": "about:blank",
+ "href": "gopher://foo:443/",
+ "origin": "null",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "foo:443",
+ "hostname": "foo",
+ "port": "443",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws://foo:80/",
+ "base": "about:blank",
+ "href": "ws://foo/",
+ "origin": "ws://foo",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws://foo:81/",
+ "base": "about:blank",
+ "href": "ws://foo:81/",
+ "origin": "ws://foo:81",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "foo:81",
+ "hostname": "foo",
+ "port": "81",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws://foo:443/",
+ "base": "about:blank",
+ "href": "ws://foo:443/",
+ "origin": "ws://foo:443",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "foo:443",
+ "hostname": "foo",
+ "port": "443",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws://foo:815/",
+ "base": "about:blank",
+ "href": "ws://foo:815/",
+ "origin": "ws://foo:815",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "foo:815",
+ "hostname": "foo",
+ "port": "815",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss://foo:80/",
+ "base": "about:blank",
+ "href": "wss://foo:80/",
+ "origin": "wss://foo:80",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "foo:80",
+ "hostname": "foo",
+ "port": "80",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss://foo:81/",
+ "base": "about:blank",
+ "href": "wss://foo:81/",
+ "origin": "wss://foo:81",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "foo:81",
+ "hostname": "foo",
+ "port": "81",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss://foo:443/",
+ "base": "about:blank",
+ "href": "wss://foo/",
+ "origin": "wss://foo",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "foo",
+ "hostname": "foo",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss://foo:815/",
+ "base": "about:blank",
+ "href": "wss://foo:815/",
+ "origin": "wss://foo:815",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "foo:815",
+ "hostname": "foo",
+ "port": "815",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/example.com/",
+ "base": "about:blank",
+ "href": "http://example.com/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp:/example.com/",
+ "base": "about:blank",
+ "href": "ftp://example.com/",
+ "origin": "ftp://example.com",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https:/example.com/",
+ "base": "about:blank",
+ "href": "https://example.com/",
+ "origin": "https://example.com",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "madeupscheme:/example.com/",
+ "base": "about:blank",
+ "href": "madeupscheme:/example.com/",
+ "origin": "null",
+ "protocol": "madeupscheme:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:/example.com/",
+ "base": "about:blank",
+ "href": "file:///example.com/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftps:/example.com/",
+ "base": "about:blank",
+ "href": "ftps:/example.com/",
+ "origin": "null",
+ "protocol": "ftps:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher:/example.com/",
+ "base": "about:blank",
+ "href": "gopher://example.com/",
+ "origin": "null",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws:/example.com/",
+ "base": "about:blank",
+ "href": "ws://example.com/",
+ "origin": "ws://example.com",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss:/example.com/",
+ "base": "about:blank",
+ "href": "wss://example.com/",
+ "origin": "wss://example.com",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "data:/example.com/",
+ "base": "about:blank",
+ "href": "data:/example.com/",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ {
+ "input": "javascript:/example.com/",
+ "base": "about:blank",
+ "href": "javascript:/example.com/",
+ "origin": "null",
+ "protocol": "javascript:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "mailto:/example.com/",
+ "base": "about:blank",
+ "href": "mailto:/example.com/",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:example.com/",
+ "base": "about:blank",
+ "href": "http://example.com/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftp:example.com/",
+ "base": "about:blank",
+ "href": "ftp://example.com/",
+ "origin": "ftp://example.com",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https:example.com/",
+ "base": "about:blank",
+ "href": "https://example.com/",
+ "origin": "https://example.com",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "madeupscheme:example.com/",
+ "base": "about:blank",
+ "href": "madeupscheme:example.com/",
+ "origin": "null",
+ "protocol": "madeupscheme:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ftps:example.com/",
+ "base": "about:blank",
+ "href": "ftps:example.com/",
+ "origin": "null",
+ "protocol": "ftps:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "gopher:example.com/",
+ "base": "about:blank",
+ "href": "gopher://example.com/",
+ "origin": "null",
+ "protocol": "gopher:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ws:example.com/",
+ "base": "about:blank",
+ "href": "ws://example.com/",
+ "origin": "ws://example.com",
+ "protocol": "ws:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wss:example.com/",
+ "base": "about:blank",
+ "href": "wss://example.com/",
+ "origin": "wss://example.com",
+ "protocol": "wss:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "data:example.com/",
+ "base": "about:blank",
+ "href": "data:example.com/",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ {
+ "input": "javascript:example.com/",
+ "base": "about:blank",
+ "href": "javascript:example.com/",
+ "origin": "null",
+ "protocol": "javascript:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "mailto:example.com/",
+ "base": "about:blank",
+ "href": "mailto:example.com/",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "example.com/",
+ "search": "",
+ "hash": ""
+ },
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/segments-userinfo-vs-host.html",
+ {
+ "input": "http:@www.example.com",
+ "base": "about:blank",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/@www.example.com",
+ "base": "about:blank",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://@www.example.com",
+ "base": "about:blank",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:a:b@www.example.com",
+ "base": "about:blank",
+ "href": "http://a:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/a:b@www.example.com",
+ "base": "about:blank",
+ "href": "http://a:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://a:b@www.example.com",
+ "base": "about:blank",
+ "href": "http://a:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://@pple.com",
+ "base": "about:blank",
+ "href": "http://pple.com/",
+ "origin": "http://pple.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "pple.com",
+ "hostname": "pple.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "http::b@www.example.com",
+ "base": "about:blank",
+ "href": "http://:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ {
+ "input": "http:/:b@www.example.com",
+ "base": "about:blank",
+ "href": "http://:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://:b@www.example.com",
+ "base": "about:blank",
+ "href": "http://:b@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "b",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/:@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://user@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:/@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https:@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:a:b@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:/a:b@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://a:b@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http::@/www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:a:@www.example.com",
+ "base": "about:blank",
+ "href": "http://a@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:/a:@www.example.com",
+ "base": "about:blank",
+ "href": "http://a@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://a:@www.example.com",
+ "base": "about:blank",
+ "href": "http://a@www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "a",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://www.@pple.com",
+ "base": "about:blank",
+ "href": "http://www.@pple.com/",
+ "origin": "http://pple.com",
+ "protocol": "http:",
+ "username": "www.",
+ "password": "",
+ "host": "pple.com",
+ "hostname": "pple.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http:@:www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http:/@:www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://@:www.example.com",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://:@www.example.com",
+ "base": "about:blank",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "# Others",
+ {
+ "input": "/",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": ".",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "..",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "./test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "../test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "../aaa/test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/aaa/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/aaa/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "../../test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "中/test.txt",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example.com/%E4%B8%AD/test.txt",
+ "origin": "http://www.example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example.com",
+ "hostname": "www.example.com",
+ "port": "",
+ "pathname": "/%E4%B8%AD/test.txt",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://www.example2.com",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example2.com/",
+ "origin": "http://www.example2.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example2.com",
+ "hostname": "www.example2.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//www.example2.com",
+ "base": "http://www.example.com/test",
+ "href": "http://www.example2.com/",
+ "origin": "http://www.example2.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.example2.com",
+ "hostname": "www.example2.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:...",
+ "base": "http://www.example.com/test",
+ "href": "file:///...",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/...",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:..",
+ "base": "http://www.example.com/test",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:a",
+ "base": "http://www.example.com/test",
+ "href": "file:///a",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/a",
+ "search": "",
+ "hash": ""
+ },
+ "# Based on http://trac.webkit.org/browser/trunk/LayoutTests/fast/url/host.html",
+ "Basic canonicalization, uppercase should be converted to lowercase",
+ {
+ "input": "http://ExAmPlE.CoM",
+ "base": "http://other.com/",
+ "href": "http://example.com/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example example.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://Goo%20 goo%7C|.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[:]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "U+3000 is mapped to U+0020 (space) which is disallowed",
+ {
+ "input": "http://GOO\u00a0\u3000goo.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "Other types of space (no-break, zero-width, zero-width-no-break) are name-prepped away to nothing. U+200B, U+2060, and U+FEFF, are ignored",
+ {
+ "input": "http://GOO\u200b\u2060\ufeffgoo.com",
+ "base": "http://other.com/",
+ "href": "http://googoo.com/",
+ "origin": "http://googoo.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "googoo.com",
+ "hostname": "googoo.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Leading and trailing C0 control or space",
+ {
+ "input": "\u0000\u001b\u0004\u0012 http://example.com/\u001f \u000d ",
+ "base": "about:blank",
+ "href": "http://example.com/",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Ideographic full stop (full-width period for Chinese, etc.) should be treated as a dot. U+3002 is mapped to U+002E (dot)",
+ {
+ "input": "http://www.foo。bar.com",
+ "base": "http://other.com/",
+ "href": "http://www.foo.bar.com/",
+ "origin": "http://www.foo.bar.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "www.foo.bar.com",
+ "hostname": "www.foo.bar.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Invalid unicode characters should fail... U+FDD0 is disallowed; %ef%b7%90 is U+FDD0",
+ {
+ "input": "http://\ufdd0zyx.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "This is the same as previous but escaped",
+ {
+ "input": "http://%ef%b7%90zyx.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "U+FFFD",
+ {
+ "input": "https://\ufffd",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://%EF%BF%BD",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://x/\ufffd?\ufffd#\ufffd",
+ "base": "about:blank",
+ "href": "https://x/%EF%BF%BD?%EF%BF%BD#%EF%BF%BD",
+ "origin": "https://x",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "x",
+ "hostname": "x",
+ "port": "",
+ "pathname": "/%EF%BF%BD",
+ "search": "?%EF%BF%BD",
+ "hash": "#%EF%BF%BD"
+ },
+ "Test name prepping, fullwidth input should be converted to ASCII and NOT IDN-ized. This is 'Go' in fullwidth UTF-8/UTF-16.",
+ {
+ "input": "http://Go.com",
+ "base": "http://other.com/",
+ "href": "http://go.com/",
+ "origin": "http://go.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "go.com",
+ "hostname": "go.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "URL spec forbids the following. https://www.w3.org/Bugs/Public/show_bug.cgi?id=24257",
+ {
+ "input": "http://%41.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://%ef%bc%85%ef%bc%94%ef%bc%91.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "...%00 in fullwidth should fail (also as escaped UTF-8 input)",
+ {
+ "input": "http://%00.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://%ef%bc%85%ef%bc%90%ef%bc%90.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "Basic IDN support, UTF-8 and UTF-16 input should be converted to IDN",
+ {
+ "input": "http://你好你好",
+ "base": "http://other.com/",
+ "href": "http://xn--6qqa088eba/",
+ "origin": "http://xn--6qqa088eba",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "xn--6qqa088eba",
+ "hostname": "xn--6qqa088eba",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Origin computed by MozURL is wrong",
+ {
+ "input": "https://faß.ExAmPlE/",
+ "base": "about:blank",
+ "href": "https://xn--fa-hia.example/",
+ "origin": "https://xn--fa-hia.example",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "xn--fa-hia.example",
+ "hostname": "xn--fa-hia.example",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ {
+ "input": "sc://faß.ExAmPlE/",
+ "base": "about:blank",
+ "href": "sc://fa%C3%9F.ExAmPlE/",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "fa%C3%9F.ExAmPlE",
+ "hostname": "fa%C3%9F.ExAmPlE",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Invalid escaped characters should fail and the percents should be escaped. https://www.w3.org/Bugs/Public/show_bug.cgi?id=24191",
+ {
+ "input": "http://%zz%66%a.com",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "If we get an invalid character that has been escaped.",
+ {
+ "input": "http://%25",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://hello%00",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "Escaped numbers should be treated like IP addresses if they are.",
+ {
+ "input": "http://%30%78%63%30%2e%30%32%35%30.01",
+ "base": "http://other.com/",
+ "href": "http://192.168.0.1/",
+ "origin": "http://192.168.0.1",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.0.1",
+ "hostname": "192.168.0.1",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://%30%78%63%30%2e%30%32%35%30.01%2e",
+ "base": "http://other.com/",
+ "href": "http://192.168.0.1/",
+ "origin": "http://192.168.0.1",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.0.1",
+ "hostname": "192.168.0.1",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://192.168.0.257",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "Invalid escaping in hosts causes failure",
+ {
+ "input": "http://%3g%78%63%30%2e%30%32%35%30%2E.01",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "A space in a host causes failure",
+ {
+ "input": "http://192.168.0.1 hello",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "https://x x:12",
+ "base": "about:blank",
+ "failure": true
+ },
+ "Fullwidth and escaped UTF-8 fullwidth should still be treated as IP",
+ {
+ "input": "http://0Xc0.0250.01",
+ "base": "http://other.com/",
+ "href": "http://192.168.0.1/",
+ "origin": "http://192.168.0.1",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.0.1",
+ "hostname": "192.168.0.1",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Domains with empty labels",
+ {
+ "input": "http://./",
+ "base": "about:blank",
+ "href": "http://./",
+ "origin": "http://.",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": ".",
+ "hostname": ".",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://../",
+ "base": "about:blank",
+ "href": "http://../",
+ "origin": "http://..",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "..",
+ "hostname": "..",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://0..0x300/",
+ "base": "about:blank",
+ "href": "http://0..0x300/",
+ "origin": "http://0..0x300",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "0..0x300",
+ "hostname": "0..0x300",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Broken IPv6",
+ {
+ "input": "http://[www.google.com]/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://[google.com]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[::1.2.3.4x]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[::1.2.3.]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[::1.2.]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://[::1.]",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ "Misc Unicode",
+ {
+ "input": "http://foo:💩@example.com/bar",
+ "base": "http://other.com/",
+ "href": "http://foo:%F0%9F%92%A9@example.com/bar",
+ "origin": "http://example.com",
+ "protocol": "http:",
+ "username": "foo",
+ "password": "%F0%9F%92%A9",
+ "host": "example.com",
+ "hostname": "example.com",
+ "port": "",
+ "pathname": "/bar",
+ "search": "",
+ "hash": ""
+ },
+ "# resolving a fragment against any scheme succeeds",
+ {
+ "input": "#",
+ "base": "test:test",
+ "href": "test:test#",
+ "origin": "null",
+ "protocol": "test:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "test",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "#x",
+ "base": "mailto:x@x.com",
+ "href": "mailto:x@x.com#x",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "x@x.com",
+ "search": "",
+ "hash": "#x"
+ },
+ {
+ "input": "#x",
+ "base": "data:,",
+ "href": "data:,#x",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": ",",
+ "search": "",
+ "hash": "#x"
+ },
+ {
+ "input": "#x",
+ "base": "about:blank",
+ "href": "about:blank#x",
+ "origin": "null",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": "#x"
+ },
+ {
+ "input": "#",
+ "base": "test:test?test",
+ "href": "test:test?test#",
+ "origin": "null",
+ "protocol": "test:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "test",
+ "search": "?test",
+ "hash": ""
+ },
+ "# multiple @ in authority state",
+ {
+ "input": "https://@test@test@example:800/",
+ "base": "http://doesnotmatter/",
+ "href": "https://%40test%40test@example:800/",
+ "origin": "https://example:800",
+ "protocol": "https:",
+ "username": "%40test%40test",
+ "password": "",
+ "host": "example:800",
+ "hostname": "example",
+ "port": "800",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https://@@@example",
+ "base": "http://doesnotmatter/",
+ "href": "https://%40%40@example/",
+ "origin": "https://example",
+ "protocol": "https:",
+ "username": "%40%40",
+ "password": "",
+ "host": "example",
+ "hostname": "example",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "non-az-09 characters",
+ {
+ "input": "http://`{}:`{}@h/`{}?`{}",
+ "base": "http://doesnotmatter/",
+ "href": "http://%60%7B%7D:%60%7B%7D@h/%60%7B%7D?`{}",
+ "origin": "http://h",
+ "protocol": "http:",
+ "username": "%60%7B%7D",
+ "password": "%60%7B%7D",
+ "host": "h",
+ "hostname": "h",
+ "port": "",
+ "pathname": "/%60%7B%7D",
+ "search": "?`{}",
+ "hash": ""
+ },
+ "# Credentials in base",
+ {
+ "input": "/some/path",
+ "base": "http://user@example.org/smth",
+ "href": "http://user@example.org/some/path",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "user",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/some/path",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "",
+ "base": "http://user:pass@example.org:21/smth",
+ "href": "http://user:pass@example.org:21/smth",
+ "origin": "http://example.org:21",
+ "protocol": "http:",
+ "username": "user",
+ "password": "pass",
+ "host": "example.org:21",
+ "hostname": "example.org",
+ "port": "21",
+ "pathname": "/smth",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "/some/path",
+ "base": "http://user:pass@example.org:21/smth",
+ "href": "http://user:pass@example.org:21/some/path",
+ "origin": "http://example.org:21",
+ "protocol": "http:",
+ "username": "user",
+ "password": "pass",
+ "host": "example.org:21",
+ "hostname": "example.org",
+ "port": "21",
+ "pathname": "/some/path",
+ "search": "",
+ "hash": ""
+ },
+ "# a set of tests designed by zcorpan for relative URLs with unknown schemes",
+ {
+ "input": "i",
+ "base": "sc:sd",
+ "failure": true
+ },
+ {
+ "input": "i",
+ "base": "sc:sd/sd",
+ "failure": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "i",
+ "base": "sc:/pa/pa",
+ "href": "sc:/pa/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/i",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "i",
+ "base": "sc://ho/pa",
+ "href": "sc://ho/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "ho",
+ "hostname": "ho",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "i",
+ "base": "sc:///pa/pa",
+ "href": "sc:///pa/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/i",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ {
+ "input": "../i",
+ "base": "sc:sd",
+ "failure": true
+ },
+ {
+ "input": "../i",
+ "base": "sc:sd/sd",
+ "failure": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "../i",
+ "base": "sc:/pa/pa",
+ "href": "sc:/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "../i",
+ "base": "sc://ho/pa",
+ "href": "sc://ho/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "ho",
+ "hostname": "ho",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "../i",
+ "base": "sc:///pa/pa",
+ "href": "sc:///i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ {
+ "input": "/i",
+ "base": "sc:sd",
+ "failure": true
+ },
+ {
+ "input": "/i",
+ "base": "sc:sd/sd",
+ "failure": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "/i",
+ "base": "sc:/pa/pa",
+ "href": "sc:/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "/i",
+ "base": "sc://ho/pa",
+ "href": "sc://ho/i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "ho",
+ "hostname": "ho",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "/i",
+ "base": "sc:///pa/pa",
+ "href": "sc:///i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/i",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ {
+ "input": "?i",
+ "base": "sc:sd",
+ "failure": true
+ },
+ {
+ "input": "?i",
+ "base": "sc:sd/sd",
+ "failure": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "?i",
+ "base": "sc:/pa/pa",
+ "href": "sc:/pa/pa?i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/pa",
+ "search": "?i",
+ "hash": "",
+ "skip": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "?i",
+ "base": "sc://ho/pa",
+ "href": "sc://ho/pa?i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "ho",
+ "hostname": "ho",
+ "port": "",
+ "pathname": "/pa",
+ "search": "?i",
+ "hash": "",
+ "skip": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "skip": true,
+ "input": "?i",
+ "base": "sc:///pa/pa",
+ "href": "sc:///pa/pa?i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/pa",
+ "search": "?i",
+ "hash": ""
+ },
+ {
+ "input": "#i",
+ "base": "sc:sd",
+ "href": "sc:sd#i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "sd",
+ "search": "",
+ "hash": "#i"
+ },
+ {
+ "input": "#i",
+ "base": "sc:sd/sd",
+ "href": "sc:sd/sd#i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "sd/sd",
+ "search": "",
+ "hash": "#i"
+ },
+ {
+ "input": "#i",
+ "base": "sc:/pa/pa",
+ "href": "sc:/pa/pa#i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/pa",
+ "search": "",
+ "hash": "#i"
+ },
+ {
+ "input": "#i",
+ "base": "sc://ho/pa",
+ "href": "sc://ho/pa#i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "ho",
+ "hostname": "ho",
+ "port": "",
+ "pathname": "/pa",
+ "search": "",
+ "hash": "#i"
+ },
+ {
+ "input": "#i",
+ "base": "sc:///pa/pa",
+ "href": "sc:///pa/pa#i",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pa/pa",
+ "search": "",
+ "hash": "#i"
+ },
+ "# make sure that relative URL logic works on known typically non-relative schemes too",
+ "Origin computed by MozURL is wrong",
+ {
+ "input": "about:/../",
+ "base": "about:blank",
+ "href": "about:/",
+ "origin": "about:/../",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "data:/../",
+ "base": "about:blank",
+ "href": "data:/",
+ "origin": "null",
+ "protocol": "data:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ {
+ "input": "javascript:/../",
+ "base": "about:blank",
+ "href": "javascript:/",
+ "origin": "null",
+ "protocol": "javascript:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "mailto:/../",
+ "base": "about:blank",
+ "href": "mailto:/",
+ "origin": "null",
+ "protocol": "mailto:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "# unknown schemes and their hosts",
+ {
+ "input": "sc://ñ.test/",
+ "base": "about:blank",
+ "href": "sc://%C3%B1.test/",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "%C3%B1.test",
+ "hostname": "%C3%B1.test",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "sc://\u001F!\"$&'()*+,-.;<=>^_`{|}~/",
+ "base": "about:blank",
+ "href": "sc://%1F!\"$&'()*+,-.;<=>^_`{|}~/",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "%1F!\"$&'()*+,-.;<=>^_`{|}~",
+ "hostname": "%1F!\"$&'()*+,-.;<=>^_`{|}~",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "sc://\u0000/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "sc:// /",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "sc://%/",
+ "base": "about:blank",
+ "href": "sc://%/",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "%",
+ "hostname": "%",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "sc://[/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "sc://\\/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "sc://]/",
+ "base": "about:blank",
+ "failure": true
+ },
+ "NS_NewURI for given input and base fails",
+ {
+ "input": "x",
+ "base": "sc://ñ",
+ "href": "sc://%C3%B1/x",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "%C3%B1",
+ "hostname": "%C3%B1",
+ "port": "",
+ "pathname": "/x",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ "# unknown schemes and backslashes",
+ {
+ "input": "sc:\\../",
+ "base": "about:blank",
+ "href": "sc:\\../",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "\\../",
+ "search": "",
+ "hash": ""
+ },
+ "# unknown scheme with path looking like a password",
+ {
+ "input": "sc::a@example.net",
+ "base": "about:blank",
+ "href": "sc::a@example.net",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": ":a@example.net",
+ "search": "",
+ "hash": ""
+ },
+ "# unknown scheme with bogus percent-encoding",
+ {
+ "input": "wow:%NBD",
+ "base": "about:blank",
+ "href": "wow:%NBD",
+ "origin": "null",
+ "protocol": "wow:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "%NBD",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "wow:%1G",
+ "base": "about:blank",
+ "href": "wow:%1G",
+ "origin": "null",
+ "protocol": "wow:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "%1G",
+ "search": "",
+ "hash": ""
+ },
+ "# Hosts and percent-encoding",
+ {
+ "input": "ftp://example.com%80/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "ftp://example.com%A0/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://example.com%80/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://example.com%A0/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "ftp://%e2%98%83",
+ "base": "about:blank",
+ "href": "ftp://xn--n3h/",
+ "origin": "ftp://xn--n3h",
+ "protocol": "ftp:",
+ "username": "",
+ "password": "",
+ "host": "xn--n3h",
+ "hostname": "xn--n3h",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "https://%e2%98%83",
+ "base": "about:blank",
+ "href": "https://xn--n3h/",
+ "origin": "https://xn--n3h",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "xn--n3h",
+ "hostname": "xn--n3h",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "# tests from jsdom/whatwg-url designed for code coverage",
+ {
+ "input": "http://127.0.0.1:10100/relative_import.html",
+ "base": "about:blank",
+ "href": "http://127.0.0.1:10100/relative_import.html",
+ "origin": "http://127.0.0.1:10100",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "127.0.0.1:10100",
+ "hostname": "127.0.0.1",
+ "port": "10100",
+ "pathname": "/relative_import.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://facebook.com/?foo=%7B%22abc%22",
+ "base": "about:blank",
+ "href": "http://facebook.com/?foo=%7B%22abc%22",
+ "origin": "http://facebook.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "facebook.com",
+ "hostname": "facebook.com",
+ "port": "",
+ "pathname": "/",
+ "search": "?foo=%7B%22abc%22",
+ "hash": ""
+ },
+ {
+ "input": "https://localhost:3000/jqueryui@1.2.3",
+ "base": "about:blank",
+ "href": "https://localhost:3000/jqueryui@1.2.3",
+ "origin": "https://localhost:3000",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "localhost:3000",
+ "hostname": "localhost",
+ "port": "3000",
+ "pathname": "/jqueryui@1.2.3",
+ "search": "",
+ "hash": ""
+ },
+ "# tab/LF/CR",
+ {
+ "input": "h\tt\nt\rp://h\to\ns\rt:9\t0\n0\r0/p\ta\nt\rh?q\tu\ne\rry#f\tr\na\rg",
+ "base": "about:blank",
+ "href": "http://host:9000/path?query#frag",
+ "origin": "http://host:9000",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "host:9000",
+ "hostname": "host",
+ "port": "9000",
+ "pathname": "/path",
+ "search": "?query",
+ "hash": "#frag"
+ },
+ "# Stringification of URL.searchParams",
+ {
+ "input": "?a=b&c=d",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar?a=b&c=d",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "?a=b&c=d",
+ "searchParams": "a=b&c=d",
+ "hash": ""
+ },
+ {
+ "input": "??a=b&c=d",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar??a=b&c=d",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "??a=b&c=d",
+ "searchParams": "%3Fa=b&c=d",
+ "hash": ""
+ },
+ "# Scheme only",
+ {
+ "input": "http:",
+ "base": "http://example.org/foo/bar",
+ "href": "http://example.org/foo/bar",
+ "origin": "http://example.org",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "searchParams": "",
+ "hash": ""
+ },
+ {
+ "input": "http:",
+ "base": "https://example.org/foo/bar",
+ "failure": true
+ },
+ {
+ "input": "sc:",
+ "base": "https://example.org/foo/bar",
+ "href": "sc:",
+ "origin": "null",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "",
+ "search": "",
+ "searchParams": "",
+ "hash": ""
+ },
+ "# Percent encoding of fragments",
+ {
+ "input": "http://foo.bar/baz?qux#foo\bbar",
+ "base": "about:blank",
+ "href": "http://foo.bar/baz?qux#foo%08bar",
+ "origin": "http://foo.bar",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "foo.bar",
+ "hostname": "foo.bar",
+ "port": "",
+ "pathname": "/baz",
+ "search": "?qux",
+ "searchParams": "qux=",
+ "hash": "#foo%08bar"
+ },
+ "# IPv4 parsing (via https://github.com/nodejs/node/pull/10317)",
+ {
+ "input": "http://192.168.257",
+ "base": "http://other.com/",
+ "href": "http://192.168.1.1/",
+ "origin": "http://192.168.1.1",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.1.1",
+ "hostname": "192.168.1.1",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://192.168.257.com",
+ "base": "http://other.com/",
+ "href": "http://192.168.257.com/",
+ "origin": "http://192.168.257.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "192.168.257.com",
+ "hostname": "192.168.257.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://256",
+ "base": "http://other.com/",
+ "href": "http://0.0.1.0/",
+ "origin": "http://0.0.1.0",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "0.0.1.0",
+ "hostname": "0.0.1.0",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://256.com",
+ "base": "http://other.com/",
+ "href": "http://256.com/",
+ "origin": "http://256.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "256.com",
+ "hostname": "256.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://999999999",
+ "base": "http://other.com/",
+ "href": "http://59.154.201.255/",
+ "origin": "http://59.154.201.255",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "59.154.201.255",
+ "hostname": "59.154.201.255",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://999999999.com",
+ "base": "http://other.com/",
+ "href": "http://999999999.com/",
+ "origin": "http://999999999.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "999999999.com",
+ "hostname": "999999999.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://10000000000",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://10000000000.com",
+ "base": "http://other.com/",
+ "href": "http://10000000000.com/",
+ "origin": "http://10000000000.com",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "10000000000.com",
+ "hostname": "10000000000.com",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://4294967295",
+ "base": "http://other.com/",
+ "href": "http://255.255.255.255/",
+ "origin": "http://255.255.255.255",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "255.255.255.255",
+ "hostname": "255.255.255.255",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://4294967296",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://0xffffffff",
+ "base": "http://other.com/",
+ "href": "http://255.255.255.255/",
+ "origin": "http://255.255.255.255",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "255.255.255.255",
+ "hostname": "255.255.255.255",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://0xffffffff1",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://256.256.256.256",
+ "base": "http://other.com/",
+ "failure": true
+ },
+ {
+ "input": "http://256.256.256.256.256",
+ "base": "http://other.com/",
+ "href": "http://256.256.256.256.256/",
+ "origin": "http://256.256.256.256.256",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "256.256.256.256.256",
+ "hostname": "256.256.256.256.256",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Origin computed by MozURL is wrong",
+ {
+ "input": "https://0x.0x.0",
+ "base": "about:blank",
+ "href": "https://0.0.0.0/",
+ "origin": "https://0x.0x.0",
+ "protocol": "https:",
+ "username": "",
+ "password": "",
+ "host": "0.0.0.0",
+ "hostname": "0.0.0.0",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": "",
+ "skip": true
+ },
+ "More IPv4 parsing (via https://github.com/jsdom/whatwg-url/issues/92)",
+ {
+ "input": "https://256.0.0.1/test",
+ "base": "about:blank",
+ "failure": true
+ },
+ "# file URLs containing percent-encoded Windows drive letters (shouldn't work)",
+ {
+ "input": "file:///C%3A/",
+ "base": "about:blank",
+ "href": "file:///C%3A/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C%3A/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:///C%7C/",
+ "base": "about:blank",
+ "href": "file:///C%7C/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C%7C/",
+ "search": "",
+ "hash": ""
+ },
+ "# file URLs relative to other file URLs (via https://github.com/jsdom/whatwg-url/pull/60)",
+ {
+ "input": "pix/submit.gif",
+ "base": "file:///C:/Users/Domenic/Dropbox/GitHub/tmpvar/jsdom/test/level2/html/files/anchor.html",
+ "href": "file:///C:/Users/Domenic/Dropbox/GitHub/tmpvar/jsdom/test/level2/html/files/pix/submit.gif",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/Users/Domenic/Dropbox/GitHub/tmpvar/jsdom/test/level2/html/files/pix/submit.gif",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "..",
+ "base": "file:///C:/",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "..",
+ "base": "file:///",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "# More file URL tests by zcorpan and annevk",
+ {
+ "input": "/",
+ "base": "file:///C:/a/b",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//d:",
+ "base": "file:///C:/a/b",
+ "href": "file:///d:",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/d:",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "//d:/..",
+ "base": "file:///C:/a/b",
+ "href": "file:///d:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/d:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "..",
+ "base": "file:///ab:/",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "..",
+ "base": "file:///1:/",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "",
+ "base": "file:///test?test#test",
+ "href": "file:///test?test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?test",
+ "hash": ""
+ },
+ {
+ "input": "file:",
+ "base": "file:///test?test#test",
+ "href": "file:///test?test",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?test",
+ "hash": ""
+ },
+ {
+ "input": "?x",
+ "base": "file:///test?test#test",
+ "href": "file:///test?x",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?x",
+ "hash": ""
+ },
+ {
+ "input": "file:?x",
+ "base": "file:///test?test#test",
+ "href": "file:///test?x",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?x",
+ "hash": ""
+ },
+ {
+ "input": "#x",
+ "base": "file:///test?test#test",
+ "href": "file:///test?test#x",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?test",
+ "hash": "#x"
+ },
+ {
+ "input": "file:#x",
+ "base": "file:///test?test#test",
+ "href": "file:///test?test#x",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test",
+ "search": "?test",
+ "hash": "#x"
+ },
+ "# File URLs and many (back)slashes",
+ {
+ "input": "file:///localhost//cat",
+ "base": "about:blank",
+ "href": "file:///localhost//cat",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/localhost//cat",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "\\//pig",
+ "base": "file://lion/",
+ "href": "file:///pig",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/pig",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://",
+ "base": "file://ape/",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "# Windows drive letter handling with the 'file:' base URL",
+ {
+ "input": "C|#",
+ "base": "file://host/dir/file",
+ "href": "file:///C:#",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|?",
+ "base": "file://host/dir/file",
+ "href": "file:///C:?",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|/",
+ "base": "file://host/dir/file",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|\n/",
+ "base": "file://host/dir/file",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|\\",
+ "base": "file://host/dir/file",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C",
+ "base": "file://host/dir/file",
+ "href": "file://host/dir/C",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "host",
+ "hostname": "host",
+ "port": "",
+ "pathname": "/dir/C",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "C|a",
+ "base": "file://host/dir/file",
+ "href": "file://host/dir/C|a",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "host",
+ "hostname": "host",
+ "port": "",
+ "pathname": "/dir/C|a",
+ "search": "",
+ "hash": ""
+ },
+ "# Windows drive letter quirk in the file slash state",
+ {
+ "input": "/c:/foo/bar",
+ "base": "file://host/path",
+ "href": "file:///c:/foo/bar",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/c:/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ "# Windows drive letter quirk (no host)",
+ {
+ "input": "file:/C|/",
+ "base": "about:blank",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://C|/",
+ "base": "about:blank",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ "# Windows drive letter quirk with not empty host",
+ {
+ "input": "file://example.net/C:/",
+ "base": "about:blank",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://1.2.3.4/C:/",
+ "base": "about:blank",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file://[1::8]/C:/",
+ "base": "about:blank",
+ "href": "file:///C:/",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/C:/",
+ "search": "",
+ "hash": ""
+ },
+ "# file URLs without base URL by Rimas Misevičius",
+ {
+ "input": "file:",
+ "base": "about:blank",
+ "href": "file:///",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:?q=v",
+ "base": "about:blank",
+ "href": "file:///?q=v",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "?q=v",
+ "hash": ""
+ },
+ {
+ "input": "file:#frag",
+ "base": "about:blank",
+ "href": "file:///#frag",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": "#frag"
+ },
+ "# IPv6 tests",
+ {
+ "input": "http://[1:0::]",
+ "base": "http://example.net/",
+ "href": "http://[1::]/",
+ "origin": "http://[1::]",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[1::]",
+ "hostname": "[1::]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[0:1:2:3:4:5:6:7:8]",
+ "base": "http://example.net/",
+ "failure": true
+ },
+ {
+ "input": "https://[0::0::0]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:.0]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:0:]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:1:2:3:4:5:6:7.0.0.0.1]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:1.00.0.0.0]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:1.290.0.0.0]",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "https://[0:1.23.23]",
+ "base": "about:blank",
+ "failure": true
+ },
+ "# Empty host",
+ {
+ "input": "http://?",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "http://#",
+ "base": "about:blank",
+ "failure": true
+ },
+ "Port overflow (2^32 + 81)",
+ {
+ "input": "http://f:4294967377/c",
+ "base": "http://example.org/",
+ "failure": true
+ },
+ "Port overflow (2^64 + 81)",
+ {
+ "input": "http://f:18446744073709551697/c",
+ "base": "http://example.org/",
+ "failure": true
+ },
+ "Port overflow (2^128 + 81)",
+ {
+ "input": "http://f:340282366920938463463374607431768211537/c",
+ "base": "http://example.org/",
+ "failure": true
+ },
+ "# Non-special-URL path tests",
+ {
+ "input": "///",
+ "base": "sc://x/",
+ "href": "sc:///",
+ "protocol": "sc:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "tftp://foobar.com/someconfig;mode=netascii",
+ "base": "about:blank",
+ "href": "tftp://foobar.com/someconfig;mode=netascii",
+ "origin": "null",
+ "protocol": "tftp:",
+ "username": "",
+ "password": "",
+ "host": "foobar.com",
+ "hostname": "foobar.com",
+ "port": "",
+ "pathname": "/someconfig;mode=netascii",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "telnet://user:pass@foobar.com:23/",
+ "base": "about:blank",
+ "href": "telnet://user:pass@foobar.com:23/",
+ "origin": "null",
+ "protocol": "telnet:",
+ "username": "user",
+ "password": "pass",
+ "host": "foobar.com:23",
+ "hostname": "foobar.com",
+ "port": "23",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "ut2004://10.10.10.10:7777/Index.ut2",
+ "base": "about:blank",
+ "href": "ut2004://10.10.10.10:7777/Index.ut2",
+ "origin": "null",
+ "protocol": "ut2004:",
+ "username": "",
+ "password": "",
+ "host": "10.10.10.10:7777",
+ "hostname": "10.10.10.10",
+ "port": "7777",
+ "pathname": "/Index.ut2",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "redis://foo:bar@somehost:6379/0?baz=bam&qux=baz",
+ "base": "about:blank",
+ "href": "redis://foo:bar@somehost:6379/0?baz=bam&qux=baz",
+ "origin": "null",
+ "protocol": "redis:",
+ "username": "foo",
+ "password": "bar",
+ "host": "somehost:6379",
+ "hostname": "somehost",
+ "port": "6379",
+ "pathname": "/0",
+ "search": "?baz=bam&qux=baz",
+ "hash": ""
+ },
+ {
+ "input": "rsync://foo@host:911/sup",
+ "base": "about:blank",
+ "href": "rsync://foo@host:911/sup",
+ "origin": "null",
+ "protocol": "rsync:",
+ "username": "foo",
+ "password": "",
+ "host": "host:911",
+ "hostname": "host",
+ "port": "911",
+ "pathname": "/sup",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "git://github.com/foo/bar.git",
+ "base": "about:blank",
+ "href": "git://github.com/foo/bar.git",
+ "origin": "null",
+ "protocol": "git:",
+ "username": "",
+ "password": "",
+ "host": "github.com",
+ "hostname": "github.com",
+ "port": "",
+ "pathname": "/foo/bar.git",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "irc://myserver.com:6999/channel?passwd",
+ "base": "about:blank",
+ "href": "irc://myserver.com:6999/channel?passwd",
+ "origin": "null",
+ "protocol": "irc:",
+ "username": "",
+ "password": "",
+ "host": "myserver.com:6999",
+ "hostname": "myserver.com",
+ "port": "6999",
+ "pathname": "/channel",
+ "search": "?passwd",
+ "hash": ""
+ },
+ {
+ "input": "dns://fw.example.org:9999/foo.bar.org?type=TXT",
+ "base": "about:blank",
+ "href": "dns://fw.example.org:9999/foo.bar.org?type=TXT",
+ "origin": "null",
+ "protocol": "dns:",
+ "username": "",
+ "password": "",
+ "host": "fw.example.org:9999",
+ "hostname": "fw.example.org",
+ "port": "9999",
+ "pathname": "/foo.bar.org",
+ "search": "?type=TXT",
+ "hash": ""
+ },
+ {
+ "input": "ldap://localhost:389/ou=People,o=JNDITutorial",
+ "base": "about:blank",
+ "href": "ldap://localhost:389/ou=People,o=JNDITutorial",
+ "origin": "null",
+ "protocol": "ldap:",
+ "username": "",
+ "password": "",
+ "host": "localhost:389",
+ "hostname": "localhost",
+ "port": "389",
+ "pathname": "/ou=People,o=JNDITutorial",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "git+https://github.com/foo/bar",
+ "base": "about:blank",
+ "href": "git+https://github.com/foo/bar",
+ "origin": "null",
+ "protocol": "git+https:",
+ "username": "",
+ "password": "",
+ "host": "github.com",
+ "hostname": "github.com",
+ "port": "",
+ "pathname": "/foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "urn:ietf:rfc:2648",
+ "base": "about:blank",
+ "href": "urn:ietf:rfc:2648",
+ "origin": "null",
+ "protocol": "urn:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "ietf:rfc:2648",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "tag:joe@example.org,2001:foo/bar",
+ "base": "about:blank",
+ "href": "tag:joe@example.org,2001:foo/bar",
+ "origin": "null",
+ "protocol": "tag:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "joe@example.org,2001:foo/bar",
+ "search": "",
+ "hash": ""
+ },
+ "# percent encoded hosts in non-special-URLs",
+ {
+ "input": "non-special://%E2%80%A0/",
+ "base": "about:blank",
+ "href": "non-special://%E2%80%A0/",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "%E2%80%A0",
+ "hostname": "%E2%80%A0",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://H%4fSt/path",
+ "base": "about:blank",
+ "href": "non-special://H%4fSt/path",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "H%4fSt",
+ "hostname": "H%4fSt",
+ "port": "",
+ "pathname": "/path",
+ "search": "",
+ "hash": ""
+ },
+ "# IPv6 in non-special-URLs",
+ {
+ "input": "non-special://[1:2:0:0:5:0:0:0]/",
+ "base": "about:blank",
+ "href": "non-special://[1:2:0:0:5::]/",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "[1:2:0:0:5::]",
+ "hostname": "[1:2:0:0:5::]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://[1:2:0:0:0:0:0:3]/",
+ "base": "about:blank",
+ "href": "non-special://[1:2::3]/",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "[1:2::3]",
+ "hostname": "[1:2::3]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://[1:2::3]:80/",
+ "base": "about:blank",
+ "href": "non-special://[1:2::3]:80/",
+ "protocol": "non-special:",
+ "username": "",
+ "password": "",
+ "host": "[1:2::3]:80",
+ "hostname": "[1:2::3]",
+ "port": "80",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "non-special://[:80/",
+ "base": "about:blank",
+ "failure": true
+ },
+ {
+ "input": "blob:https://example.com:443/",
+ "base": "about:blank",
+ "href": "blob:https://example.com:443/",
+ "protocol": "blob:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "https://example.com:443/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "blob:d3958f5c-0777-0845-9dcf-2cb28783acaf",
+ "base": "about:blank",
+ "href": "blob:d3958f5c-0777-0845-9dcf-2cb28783acaf",
+ "protocol": "blob:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "d3958f5c-0777-0845-9dcf-2cb28783acaf",
+ "search": "",
+ "hash": ""
+ },
+ "Invalid IPv4 radix digits",
+ {
+ "input": "http://0177.0.0.0189",
+ "base": "about:blank",
+ "href": "http://0177.0.0.0189/",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "0177.0.0.0189",
+ "hostname": "0177.0.0.0189",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://0x7f.0.0.0x7g",
+ "base": "about:blank",
+ "href": "http://0x7f.0.0.0x7g/",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "0x7f.0.0.0x7g",
+ "hostname": "0x7f.0.0.0x7g",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://0X7F.0.0.0X7G",
+ "base": "about:blank",
+ "href": "http://0x7f.0.0.0x7g/",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "0x7f.0.0.0x7g",
+ "hostname": "0x7f.0.0.0x7g",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Invalid IPv4 portion of IPv6 address",
+ {
+ "input": "http://[::127.0.0.0.1]",
+ "base": "about:blank",
+ "failure": true
+ },
+ "Uncompressed IPv6 addresses with 0",
+ {
+ "input": "http://[0:1:0:1:0:1:0:1]",
+ "base": "about:blank",
+ "href": "http://[0:1:0:1:0:1:0:1]/",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[0:1:0:1:0:1:0:1]",
+ "hostname": "[0:1:0:1:0:1:0:1]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://[1:0:1:0:1:0:1:0]",
+ "base": "about:blank",
+ "href": "http://[1:0:1:0:1:0:1:0]/",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "[1:0:1:0:1:0:1:0]",
+ "hostname": "[1:0:1:0:1:0:1:0]",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ "Percent-encoded query and fragment",
+ {
+ "input": "http://example.org/test?\u0022",
+ "base": "about:blank",
+ "href": "http://example.org/test?%22",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%22",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?\u0023",
+ "base": "about:blank",
+ "href": "http://example.org/test?#",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?\u003C",
+ "base": "about:blank",
+ "href": "http://example.org/test?%3C",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%3C",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?\u003E",
+ "base": "about:blank",
+ "href": "http://example.org/test?%3E",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%3E",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?\u2323",
+ "base": "about:blank",
+ "href": "http://example.org/test?%E2%8C%A3",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%E2%8C%A3",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?%23%23",
+ "base": "about:blank",
+ "href": "http://example.org/test?%23%23",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%23%23",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?%GH",
+ "base": "about:blank",
+ "href": "http://example.org/test?%GH",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?%GH",
+ "hash": ""
+ },
+ {
+ "input": "http://example.org/test?a#%EF",
+ "base": "about:blank",
+ "href": "http://example.org/test?a#%EF",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?a",
+ "hash": "#%EF"
+ },
+ {
+ "input": "http://example.org/test?a#%GH",
+ "base": "about:blank",
+ "href": "http://example.org/test?a#%GH",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?a",
+ "hash": "#%GH"
+ },
+ "Bad bases",
+ {
+ "input": "test-a.html",
+ "base": "a",
+ "failure": true
+ },
+ {
+ "input": "test-a-slash.html",
+ "base": "a/",
+ "failure": true
+ },
+ {
+ "input": "test-a-slash-slash.html",
+ "base": "a//",
+ "failure": true
+ },
+ {
+ "input": "test-a-colon.html",
+ "base": "a:",
+ "failure": true
+ },
+ {
+ "input": "test-a-colon-slash.html",
+ "base": "a:/",
+ "href": "a:/test-a-colon-slash.html",
+ "protocol": "a:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test-a-colon-slash.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "test-a-colon-slash-slash.html",
+ "base": "a://",
+ "href": "a:///test-a-colon-slash-slash.html",
+ "protocol": "a:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test-a-colon-slash-slash.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "test-a-colon-b.html",
+ "base": "a:b",
+ "failure": true
+ },
+ {
+ "input": "test-a-colon-slash-b.html",
+ "base": "a:/b",
+ "href": "a:/test-a-colon-slash-b.html",
+ "protocol": "a:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/test-a-colon-slash-b.html",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "test-a-colon-slash-slash-b.html",
+ "base": "a://b",
+ "href": "a://b/test-a-colon-slash-slash-b.html",
+ "protocol": "a:",
+ "username": "",
+ "password": "",
+ "host": "b",
+ "hostname": "b",
+ "port": "",
+ "pathname": "/test-a-colon-slash-slash-b.html",
+ "search": "",
+ "hash": ""
+ },
+ "Null code point in fragment",
+ {
+ "input": "http://example.org/test?a#b\u0000c",
+ "base": "about:blank",
+ "href": "http://example.org/test?a#bc",
+ "protocol": "http:",
+ "username": "",
+ "password": "",
+ "host": "example.org",
+ "hostname": "example.org",
+ "port": "",
+ "pathname": "/test",
+ "search": "?a",
+ "hash": "#bc"
+ },
+ "New tests",
+ {
+ "input": "file:///foo/bar.html",
+ "base": "about:blank",
+ "href": "file:///foo/bar.html",
+ "origin": "file:///foo/bar.html",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:///foo/bar.html?x=y",
+ "base": "about:blank",
+ "href": "file:///foo/bar.html?x=y",
+ "origin": "file:///foo/bar.html",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "file:///foo/bar.html#bla",
+ "base": "about:blank",
+ "href": "file:///foo/bar.html#bla",
+ "origin": "file:///foo/bar.html",
+ "protocol": "file:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "/",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "about:blank",
+ "base": "about:blank",
+ "href": "about:blank",
+ "origin": "null",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "about:home",
+ "base": "about:blank",
+ "href": "about:home",
+ "origin": "about:home",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "about:home#x",
+ "base": "about:blank",
+ "href": "about:home#x",
+ "origin": "about:home",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "about:home?x=y",
+ "base": "about:blank",
+ "href": "about:home?x=y",
+ "origin": "about:home",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "moz-safe-about:home",
+ "base": "about:blank",
+ "href": "moz-safe-about:home",
+ "origin": "moz-safe-about:home",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "moz-safe-about:home#x",
+ "base": "about:blank",
+ "href": "moz-safe-about:home#x",
+ "origin": "moz-safe-about:home",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "moz-safe-about:home?x=y",
+ "base": "about:blank",
+ "href": "moz-safe-about:home?x=y",
+ "origin": "moz-safe-about:home",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "indexeddb://fx-devtools",
+ "base": "about:blank",
+ "href": "indexeddb://fx-devtools/",
+ "origin": "indexeddb://fx-devtools",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "indexeddb://fx-devtools/",
+ "base": "about:blank",
+ "href": "indexeddb://fx-devtools/",
+ "origin": "indexeddb://fx-devtools",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "indexeddb://fx-devtools/foo",
+ "base": "about:blank",
+ "href": "indexeddb://fx-devtools/foo",
+ "origin": "indexeddb://fx-devtools",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "indexeddb://fx-devtools#x",
+ "base": "about:blank",
+ "href": "indexeddb://fx-devtools#x",
+ "origin": "indexeddb://fx-devtools",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "indexeddb://fx-devtools/#x",
+ "base": "about:blank",
+ "href": "indexeddb://fx-devtools/#x",
+ "origin": "indexeddb://fx-devtools",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "moz-extension://53711a8f-65ed-e742-9671-1f02e267c0bc/foo/bar.html",
+ "base": "about:blank",
+ "href": "moz-extension://53711a8f-65ed-e742-9671-1f02e267c0bc/foo/bar.html",
+ "origin": "moz-extension://53711a8f-65ed-e742-9671-1f02e267c0bc",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "moz-extension://53711a8f-65ed-e742-9671-1f02e267c0bc:123/foo/bar.html",
+ "base": "about:blank",
+ "href": "moz-extension://53711a8f-65ed-e742-9671-1f02e267c0bc:123/foo/bar.html",
+ "origin": "moz-extension://53711a8f-65ed-e742-9671-1f02e267c0bc:123",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "resource://foo/bar.html",
+ "base": "about:blank",
+ "href": "resource://foo/bar.html",
+ "origin": "resource://foo",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ },
+ {
+ "input": "resource://foo:123/bar.html",
+ "base": "about:blank",
+ "href": "resource://foo:123/bar.html",
+ "origin": "resource://foo:123",
+ "protocol": "about:",
+ "username": "",
+ "password": "",
+ "host": "",
+ "hostname": "",
+ "port": "",
+ "pathname": "blank",
+ "search": "",
+ "hash": ""
+ }
+]