Browse Source

Fixed bug that USR_BASENAME is not defined

In some cases, if the dirname is only "/", the basename will not be
defined (e.g., "/f"). This change fixes this bug.
Tatsuhiro Tsujikawa 12 years ago
parent
commit
247084f9c3
2 changed files with 32 additions and 3 deletions
  1. 3 3
      src/uri_split.c
  2. 29 0
      test/UriSplitTest.cc

+ 3 - 3
src/uri_split.c

@@ -268,7 +268,7 @@ int uri_split(uri_split_result *res, const char *uri)
         state = URI_BEFORE_PORT;
         break;
       case '/':
-        host_last = path_first = p;
+        host_last = path_first = last_slash = p;
         state = URI_PATH;
         break;
       case '?':
@@ -301,7 +301,7 @@ int uri_split(uri_split_result *res, const char *uri)
         state = URI_BEFORE_PORT;
         break;
       case '/':
-        path_first = p;
+        path_first = last_slash = p;
         state = URI_PATH;
         break;
       case '?':
@@ -325,7 +325,7 @@ int uri_split(uri_split_result *res, const char *uri)
     case URI_PORT:
       switch(*p) {
       case '/':
-        path_first = p;
+        path_first = last_slash = p;
         state = URI_PATH;
         break;
       case '?':

+ 29 - 0
test/UriSplitTest.cc

@@ -349,6 +349,35 @@ void UriSplitTest::testUriSplit()
   CPPUNIT_ASSERT_EQUAL(std::string("/f"), mkstr(res, USR_PATH, uri));
   CPPUNIT_ASSERT_EQUAL(std::string("f"), mkstr(res, USR_BASENAME, uri));
 
+  uri = "http://[::1]/f";
+  memset(&res, 0, sizeof(res));
+  CPPUNIT_ASSERT_EQUAL(0, uri_split(&res, uri));
+  CHECK_FIELD_SET(res, (1 << USR_SCHEME) | (1 << USR_HOST) | (1 << USR_PATH) |
+                  (1 << USR_BASENAME));
+  CPPUNIT_ASSERT_EQUAL(std::string("::1"), mkstr(res, USR_HOST, uri));
+  CPPUNIT_ASSERT_EQUAL(std::string("/f"), mkstr(res, USR_PATH, uri));
+  CPPUNIT_ASSERT_EQUAL(std::string("f"), mkstr(res, USR_BASENAME, uri));
+
+  uri = "http://[::1]:8080/f";
+  memset(&res, 0, sizeof(res));
+  CPPUNIT_ASSERT_EQUAL(0, uri_split(&res, uri));
+  CHECK_FIELD_SET(res, (1 << USR_SCHEME) | (1 << USR_HOST) | (1 << USR_PORT) |
+                  (1 << USR_PATH) | (1 << USR_BASENAME));
+  CPPUNIT_ASSERT_EQUAL((uint16_t)8080, res.port);
+  CPPUNIT_ASSERT_EQUAL(std::string("/f"), mkstr(res, USR_PATH, uri));
+  CPPUNIT_ASSERT_EQUAL(std::string("f"), mkstr(res, USR_BASENAME, uri));
+
+  uri = "https://user:pass@host/f";
+  memset(&res, 0, sizeof(res));
+  CPPUNIT_ASSERT_EQUAL(0, uri_split(&res, uri));
+  CHECK_FIELD_SET(res, (1 << USR_SCHEME) | (1 << USR_HOST) |
+                  (1 << USR_USERINFO) | (1 << USR_USER) | (1 << USR_PASSWD) |
+                  (1 << USR_PATH) | (1 << USR_BASENAME));
+  CPPUNIT_ASSERT_EQUAL(std::string("host"), mkstr(res, USR_HOST, uri));
+  CPPUNIT_ASSERT_EQUAL(std::string("user:pass"), mkstr(res, USR_USERINFO, uri));
+  CPPUNIT_ASSERT_EQUAL(std::string("/f"), mkstr(res, USR_PATH, uri));
+  CPPUNIT_ASSERT_EQUAL(std::string("f"), mkstr(res, USR_BASENAME, uri));
+
   uri = "http://aria2/index.html?foo";
   memset(&res, 0, sizeof(res));
   CPPUNIT_ASSERT_EQUAL(0, uri_split(&res, uri));