Commit 6525d89c authored by Andrew Eikum's avatar Andrew Eikum Committed by Alexandre Julliard

shlwapi: Handle URL_WININET_COMPATIBILITY flag in UrlCanonicalize.

parent 35f8d739
...@@ -123,6 +123,9 @@ static const TEST_URL_CANONICALIZE TEST_CANONICALIZE[] = { ...@@ -123,6 +123,9 @@ static const TEST_URL_CANONICALIZE TEST_CANONICALIZE[] = {
{"http://www.winehq.org/tests/../#example", URL_DONT_SIMPLIFY, S_OK, "http://www.winehq.org/tests/../#example", FALSE}, {"http://www.winehq.org/tests/../#example", URL_DONT_SIMPLIFY, S_OK, "http://www.winehq.org/tests/../#example", FALSE},
{"http://www.winehq.org/tests/foo bar", URL_ESCAPE_SPACES_ONLY| URL_DONT_ESCAPE_EXTRA_INFO , S_OK, "http://www.winehq.org/tests/foo%20bar", FALSE}, {"http://www.winehq.org/tests/foo bar", URL_ESCAPE_SPACES_ONLY| URL_DONT_ESCAPE_EXTRA_INFO , S_OK, "http://www.winehq.org/tests/foo%20bar", FALSE},
{"http://www.winehq.org/tests/foo%20bar", URL_UNESCAPE , S_OK, "http://www.winehq.org/tests/foo bar", FALSE}, {"http://www.winehq.org/tests/foo%20bar", URL_UNESCAPE , S_OK, "http://www.winehq.org/tests/foo bar", FALSE},
{"http://www.winehq.org", 0, S_OK, "http://www.winehq.org/", FALSE},
{"http:///www.winehq.org", 0, S_OK, "http:///www.winehq.org", FALSE},
{"http:////www.winehq.org", 0, S_OK, "http:////www.winehq.org", FALSE},
{"file:///c:/tests/foo%20bar", URL_UNESCAPE , S_OK, "file:///c:/tests/foo bar", FALSE}, {"file:///c:/tests/foo%20bar", URL_UNESCAPE , S_OK, "file:///c:/tests/foo bar", FALSE},
{"file:///c:/tests\\foo%20bar", URL_UNESCAPE , S_OK, "file:///c:/tests/foo bar", FALSE}, {"file:///c:/tests\\foo%20bar", URL_UNESCAPE , S_OK, "file:///c:/tests/foo bar", FALSE},
{"file:///c:/tests/foo%20bar", 0, S_OK, "file:///c:/tests/foo%20bar", FALSE}, {"file:///c:/tests/foo%20bar", 0, S_OK, "file:///c:/tests/foo%20bar", FALSE},
...@@ -137,6 +140,24 @@ static const TEST_URL_CANONICALIZE TEST_CANONICALIZE[] = { ...@@ -137,6 +140,24 @@ static const TEST_URL_CANONICALIZE TEST_CANONICALIZE[] = {
{"file:///c://tests/foo%20bar", URL_FILE_USE_PATHURL, S_OK, "file://c:\\\\tests\\foo bar", FALSE}, {"file:///c://tests/foo%20bar", URL_FILE_USE_PATHURL, S_OK, "file://c:\\\\tests\\foo bar", FALSE},
{"file:///c:\\tests\\foo bar", 0, S_OK, "file:///c:/tests/foo bar", FALSE}, {"file:///c:\\tests\\foo bar", 0, S_OK, "file:///c:/tests/foo bar", FALSE},
{"file:///c:\\tests\\foo bar", URL_DONT_SIMPLIFY, S_OK, "file:///c:/tests/foo bar", FALSE}, {"file:///c:\\tests\\foo bar", URL_DONT_SIMPLIFY, S_OK, "file:///c:/tests/foo bar", FALSE},
{"file:///c:\\tests\\foobar", 0, S_OK, "file:///c:/tests/foobar", FALSE},
{"file:///c:\\tests\\foobar", URL_WININET_COMPATIBILITY, S_OK, "file://c:\\tests\\foobar", FALSE},
{"file://home/user/file", 0, S_OK, "file://home/user/file", FALSE},
{"file:///home/user/file", 0, S_OK, "file:///home/user/file", FALSE},
{"file:////home/user/file", 0, S_OK, "file://home/user/file", FALSE},
{"file://home/user/file", URL_WININET_COMPATIBILITY, S_OK, "file://\\\\home\\user\\file", FALSE},
{"file:///home/user/file", URL_WININET_COMPATIBILITY, S_OK, "file://\\home\\user\\file", FALSE},
{"file:////home/user/file", URL_WININET_COMPATIBILITY, S_OK, "file://\\\\home\\user\\file", FALSE},
{"file://///home/user/file", URL_WININET_COMPATIBILITY, S_OK, "file://\\\\home\\user\\file", FALSE},
{"file://C:/user/file", 0, S_OK, "file:///C:/user/file", FALSE},
{"file://C:/user/file/../asdf", 0, S_OK, "file:///C:/user/asdf", FALSE},
{"file:///C:/user/file", 0, S_OK, "file:///C:/user/file", FALSE},
{"file:////C:/user/file", 0, S_OK, "file:///C:/user/file", FALSE},
{"file://C:/user/file", URL_WININET_COMPATIBILITY, S_OK, "file://C:\\user\\file", FALSE},
{"file:///C:/user/file", URL_WININET_COMPATIBILITY, S_OK, "file://C:\\user\\file", FALSE},
{"file:////C:/user/file", URL_WININET_COMPATIBILITY, S_OK, "file://C:\\user\\file", FALSE},
{"http:///www.winehq.org", 0, S_OK, "http:///www.winehq.org", FALSE},
{"http:///www.winehq.org", URL_WININET_COMPATIBILITY, S_OK, "http:///www.winehq.org", FALSE},
{"http://www.winehq.org/site/about", URL_FILE_USE_PATHURL, S_OK, "http://www.winehq.org/site/about", FALSE}, {"http://www.winehq.org/site/about", URL_FILE_USE_PATHURL, S_OK, "http://www.winehq.org/site/about", FALSE},
{"file_://www.winehq.org/site/about", URL_FILE_USE_PATHURL, S_OK, "file_://www.winehq.org/site/about", FALSE}, {"file_://www.winehq.org/site/about", URL_FILE_USE_PATHURL, S_OK, "file_://www.winehq.org/site/about", FALSE},
{"c:\\dir\\file", 0, S_OK, "file:///c:/dir/file", FALSE}, {"c:\\dir\\file", 0, S_OK, "file:///c:/dir/file", FALSE},
......
...@@ -276,6 +276,7 @@ HRESULT WINAPI UrlCanonicalizeW(LPCWSTR pszUrl, LPWSTR pszCanonicalized, ...@@ -276,6 +276,7 @@ HRESULT WINAPI UrlCanonicalizeW(LPCWSTR pszUrl, LPWSTR pszCanonicalized,
LPWSTR lpszUrlCpy, url, wk2, mp, mp2; LPWSTR lpszUrlCpy, url, wk2, mp, mp2;
INT state; INT state;
DWORD nByteLen, nLen, nWkLen; DWORD nByteLen, nLen, nWkLen;
BOOL is_file_url;
WCHAR slash = '\0'; WCHAR slash = '\0';
static const WCHAR wszFile[] = {'f','i','l','e',':'}; static const WCHAR wszFile[] = {'f','i','l','e',':'};
...@@ -318,14 +319,13 @@ HRESULT WINAPI UrlCanonicalizeW(LPCWSTR pszUrl, LPWSTR pszCanonicalized, ...@@ -318,14 +319,13 @@ HRESULT WINAPI UrlCanonicalizeW(LPCWSTR pszUrl, LPWSTR pszCanonicalized,
return E_OUTOFMEMORY; return E_OUTOFMEMORY;
} }
is_file_url = !strncmpW(wszFile, url, sizeof(wszFile)/sizeof(WCHAR));
if ((nByteLen >= sizeof(wszHttp) && if ((nByteLen >= sizeof(wszHttp) &&
!memcmp(wszHttp, url, sizeof(wszHttp))) || !memcmp(wszHttp, url, sizeof(wszHttp))) || is_file_url)
(nByteLen >= sizeof(wszFile) &&
!memcmp(wszFile, url, sizeof(wszFile))))
slash = '/'; slash = '/';
if((dwFlags & URL_FILE_USE_PATHURL) && nByteLen >= sizeof(wszFile) if((dwFlags & (URL_FILE_USE_PATHURL | URL_WININET_COMPATIBILITY)) && is_file_url)
&& !memcmp(wszFile, url, sizeof(wszFile)))
slash = '\\'; slash = '\\';
if(nByteLen >= sizeof(wszRes) && !memcmp(wszRes, url, sizeof(wszRes))) { if(nByteLen >= sizeof(wszRes) && !memcmp(wszRes, url, sizeof(wszRes))) {
...@@ -351,7 +351,7 @@ HRESULT WINAPI UrlCanonicalizeW(LPCWSTR pszUrl, LPWSTR pszCanonicalized, ...@@ -351,7 +351,7 @@ HRESULT WINAPI UrlCanonicalizeW(LPCWSTR pszUrl, LPWSTR pszCanonicalized,
if(url[1] == ':') { /* Assume path */ if(url[1] == ':') { /* Assume path */
memcpy(wk2, wszFilePrefix, sizeof(wszFilePrefix)); memcpy(wk2, wszFilePrefix, sizeof(wszFilePrefix));
wk2 += sizeof(wszFilePrefix)/sizeof(WCHAR); wk2 += sizeof(wszFilePrefix)/sizeof(WCHAR);
if (dwFlags & URL_FILE_USE_PATHURL) if (dwFlags & (URL_FILE_USE_PATHURL | URL_WININET_COMPATIBILITY))
{ {
slash = '\\'; slash = '\\';
--wk2; --wk2;
...@@ -359,6 +359,7 @@ HRESULT WINAPI UrlCanonicalizeW(LPCWSTR pszUrl, LPWSTR pszCanonicalized, ...@@ -359,6 +359,7 @@ HRESULT WINAPI UrlCanonicalizeW(LPCWSTR pszUrl, LPWSTR pszCanonicalized,
else else
dwFlags |= URL_ESCAPE_UNSAFE; dwFlags |= URL_ESCAPE_UNSAFE;
state = 5; state = 5;
is_file_url = TRUE;
} }
while (*wk1) { while (*wk1) {
...@@ -379,14 +380,47 @@ HRESULT WINAPI UrlCanonicalizeW(LPCWSTR pszUrl, LPWSTR pszCanonicalized, ...@@ -379,14 +380,47 @@ HRESULT WINAPI UrlCanonicalizeW(LPCWSTR pszUrl, LPWSTR pszCanonicalized,
if (*wk1 != '/') {state = 6; break;} if (*wk1 != '/') {state = 6; break;}
*wk2++ = *wk1++; *wk2++ = *wk1++;
if((dwFlags & URL_FILE_USE_PATHURL) && nByteLen >= sizeof(wszLocalhost) if((dwFlags & URL_FILE_USE_PATHURL) && nByteLen >= sizeof(wszLocalhost)
&& !strncmpW(wszFile, url, sizeof(wszFile)/sizeof(WCHAR)) && is_file_url
&& !memcmp(wszLocalhost, wk1, sizeof(wszLocalhost))){ && !memcmp(wszLocalhost, wk1, sizeof(wszLocalhost))){
wk1 += sizeof(wszLocalhost)/sizeof(WCHAR); wk1 += sizeof(wszLocalhost)/sizeof(WCHAR);
while(*wk1 == '\\' && (dwFlags & URL_FILE_USE_PATHURL)) while(*wk1 == '\\' && (dwFlags & URL_FILE_USE_PATHURL))
wk1++; wk1++;
} }
if(*wk1 == '/' && (dwFlags & URL_FILE_USE_PATHURL))
if(*wk1 == '/' && (dwFlags & URL_FILE_USE_PATHURL)){
wk1++; wk1++;
}else if(is_file_url){
const WCHAR *body = wk1;
while(*body == '/')
++body;
if(isalnumW(*body) && *(body+1) == ':'){
if(!(dwFlags & (URL_WININET_COMPATIBILITY | URL_FILE_USE_PATHURL))){
if(slash)
*wk2++ = slash;
else
*wk2++ = '/';
}
}else{
if(dwFlags & URL_WININET_COMPATIBILITY){
if(*wk1 == '/' && *(wk1+1) != '/'){
*wk2++ = '\\';
}else{
*wk2++ = '\\';
*wk2++ = '\\';
}
}else{
if(*wk1 == '/' && *(wk1+1) != '/'){
if(slash)
*wk2++ = slash;
else
*wk2++ = '/';
}
}
}
wk1 = body;
}
state = 4; state = 4;
break; break;
case 3: case 3:
......
...@@ -103,7 +103,7 @@ static void test_InternetCanonicalizeUrlA(void) ...@@ -103,7 +103,7 @@ static void test_InternetCanonicalizeUrlA(void)
res = InternetCanonicalizeUrlA("file:///C:/Program%20Files/Atmel/AVR%20Tools/STK500/STK500.xml", buffer, &dwSize, ICU_DECODE | ICU_NO_ENCODE); res = InternetCanonicalizeUrlA("file:///C:/Program%20Files/Atmel/AVR%20Tools/STK500/STK500.xml", buffer, &dwSize, ICU_DECODE | ICU_NO_ENCODE);
ok(res, "InternetCanonicalizeUrlA failed %u\n", GetLastError()); ok(res, "InternetCanonicalizeUrlA failed %u\n", GetLastError());
ok(dwSize == lstrlenA(buffer), "got %d expected %d\n", dwSize, lstrlenA(buffer)); ok(dwSize == lstrlenA(buffer), "got %d expected %d\n", dwSize, lstrlenA(buffer));
todo_wine ok(!lstrcmpA("file://C:\\Program Files\\Atmel\\AVR Tools\\STK500\\STK500.xml", buffer), ok(!lstrcmpA("file://C:\\Program Files\\Atmel\\AVR Tools\\STK500\\STK500.xml", buffer),
"got %s expected 'file://C:\\Program Files\\Atmel\\AVR Tools\\STK500\\STK500.xml'\n", buffer); "got %s expected 'file://C:\\Program Files\\Atmel\\AVR Tools\\STK500\\STK500.xml'\n", buffer);
/* buffer is larger as the required size */ /* buffer is larger as the required size */
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment