[libsoup] SoupServer: fix to not allow smuggling ".." into path



commit 150c7f6743924cb5d6f2dec85c6248620b8f4e4a
Author: Ignacio Casal Quinteiro <qignacio amazon com>
Date:   Mon Aug 26 12:54:09 2019 +0200

    SoupServer: fix to not allow smuggling ".." into path
    
    This was already fixed for Unix like systems but it was still
    possible to smuggle .. into a windows like server.

 libsoup/soup-server.c | 10 +++++++-
 tests/server-test.c   | 66 +++++++++++++++++++++++++++++++++++++++++++++++++++
 2 files changed, 75 insertions(+), 1 deletion(-)
---
diff --git a/libsoup/soup-server.c b/libsoup/soup-server.c
index 0bb30626..3411f67a 100644
--- a/libsoup/soup-server.c
+++ b/libsoup/soup-server.c
@@ -1368,7 +1368,15 @@ got_headers (SoupMessage *msg, SoupClientContext *client)
                decoded_path = soup_uri_decode (uri->path);
 
                if (strstr (decoded_path, "/../") ||
-                   g_str_has_suffix (decoded_path, "/..")) {
+                   g_str_has_suffix (decoded_path, "/..")
+#ifdef G_OS_WIN32
+                   ||
+                   strstr (decoded_path, "\\..\\") ||
+                   strstr (decoded_path, "/..\\") ||
+                   strstr (decoded_path, "\\../") ||
+                   g_str_has_suffix (decoded_path, "\\..")
+#endif
+                   ) {
                        /* Introducing new ".." segments is not allowed */
                        g_free (decoded_path);
                        soup_message_set_status (msg, SOUP_STATUS_BAD_REQUEST);
diff --git a/tests/server-test.c b/tests/server-test.c
index cf132b33..8976103e 100644
--- a/tests/server-test.c
+++ b/tests/server-test.c
@@ -275,6 +275,72 @@ do_dot_dot_test (ServerData *sd, gconstpointer test_data)
        soup_test_assert_message_status (msg, SOUP_STATUS_BAD_REQUEST);
        g_object_unref (msg);
 
+       uri = soup_uri_new_with_base (sd->base_uri, "/%2e%2e%2ftest");
+       msg = soup_message_new_from_uri ("GET", uri);
+       soup_uri_free (uri);
+
+       soup_session_send_message (session, msg);
+       soup_test_assert_message_status (msg, SOUP_STATUS_BAD_REQUEST);
+       g_object_unref (msg);
+
+#ifdef G_OS_WIN32
+       uri = soup_uri_new_with_base (sd->base_uri, "\\..%5Ctest");
+       msg = soup_message_new_from_uri ("GET", uri);
+       soup_uri_free (uri);
+
+       soup_session_send_message (session, msg);
+       soup_test_assert_message_status (msg, SOUP_STATUS_BAD_REQUEST);
+       g_object_unref (msg);
+
+       uri = soup_uri_new_with_base (sd->base_uri, "\\../test");
+       msg = soup_message_new_from_uri ("GET", uri);
+       soup_uri_free (uri);
+
+       soup_session_send_message (session, msg);
+       soup_test_assert_message_status (msg, SOUP_STATUS_BAD_REQUEST);
+       g_object_unref (msg);
+
+       uri = soup_uri_new_with_base (sd->base_uri, "%5C..%2ftest");
+       msg = soup_message_new_from_uri ("GET", uri);
+       soup_uri_free (uri);
+
+       soup_session_send_message (session, msg);
+       soup_test_assert_message_status (msg, SOUP_STATUS_BAD_REQUEST);
+       g_object_unref (msg);
+
+       uri = soup_uri_new_with_base (sd->base_uri, "/..\\test");
+       msg = soup_message_new_from_uri ("GET", uri);
+       soup_uri_free (uri);
+
+       soup_session_send_message (session, msg);
+       soup_test_assert_message_status (msg, SOUP_STATUS_BAD_REQUEST);
+       g_object_unref (msg);
+
+       uri = soup_uri_new_with_base (sd->base_uri, "%2f..%5Ctest");
+       msg = soup_message_new_from_uri ("GET", uri);
+       soup_uri_free (uri);
+
+       soup_session_send_message (session, msg);
+       soup_test_assert_message_status (msg, SOUP_STATUS_BAD_REQUEST);
+       g_object_unref (msg);
+
+       uri = soup_uri_new_with_base (sd->base_uri, "\\%2e%2e%5ctest");
+       msg = soup_message_new_from_uri ("GET", uri);
+       soup_uri_free (uri);
+
+       soup_session_send_message (session, msg);
+       soup_test_assert_message_status (msg, SOUP_STATUS_BAD_REQUEST);
+       g_object_unref (msg);
+
+       uri = soup_uri_new_with_base (sd->base_uri, "\\..%%35%63..%%35%63test");
+       msg = soup_message_new_from_uri ("GET", uri);
+       soup_uri_free (uri);
+
+       soup_session_send_message (session, msg);
+       soup_test_assert_message_status (msg, SOUP_STATUS_BAD_REQUEST);
+       g_object_unref (msg);
+#endif
+
        soup_test_session_abort_unref (session);
 }
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]