Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wine-winehq
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
wine
wine-winehq
Commits
41a76362
Commit
41a76362
authored
Sep 03, 2008
by
Hans Leidekker
Committed by
Alexandre Julliard
Sep 03, 2008
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
winhttp: Handle redirects.
parent
8063f5cb
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
140 additions
and
28 deletions
+140
-28
request.c
dlls/winhttp/request.c
+124
-27
winhttp.c
dlls/winhttp/tests/winhttp.c
+16
-1
No files found.
dlls/winhttp/request.c
View file @
41a76362
...
...
@@ -932,6 +932,108 @@ end:
return
TRUE
;
}
static
BOOL
handle_redirect
(
request_t
*
request
)
{
BOOL
ret
=
FALSE
;
DWORD
size
,
len
;
URL_COMPONENTS
uc
;
connect_t
*
connect
=
request
->
connect
;
INTERNET_PORT
port
;
WCHAR
*
hostname
=
NULL
,
*
location
=
NULL
;
size
=
0
;
query_headers
(
request
,
WINHTTP_QUERY_LOCATION
,
NULL
,
NULL
,
&
size
,
NULL
);
if
(
!
(
location
=
heap_alloc
(
size
)))
return
FALSE
;
if
(
!
query_headers
(
request
,
WINHTTP_QUERY_LOCATION
,
NULL
,
location
,
&
size
,
NULL
))
goto
end
;
send_callback
(
&
request
->
hdr
,
WINHTTP_CALLBACK_STATUS_REDIRECT
,
location
,
size
/
sizeof
(
WCHAR
)
+
1
);
memset
(
&
uc
,
0
,
sizeof
(
uc
)
);
uc
.
dwStructSize
=
sizeof
(
uc
);
uc
.
dwSchemeLength
=
uc
.
dwHostNameLength
=
uc
.
dwUrlPathLength
=
uc
.
dwExtraInfoLength
=
~
0UL
;
if
(
!
(
ret
=
WinHttpCrackUrl
(
location
,
size
/
sizeof
(
WCHAR
),
0
,
&
uc
)))
goto
end
;
if
(
uc
.
nScheme
==
INTERNET_SCHEME_HTTP
&&
request
->
hdr
.
flags
&
WINHTTP_FLAG_SECURE
)
{
TRACE
(
"redirect from secure page to non-secure page
\n
"
);
request
->
hdr
.
flags
&=
~
WINHTTP_FLAG_SECURE
;
}
else
if
(
uc
.
nScheme
==
INTERNET_SCHEME_HTTPS
&&
!
(
request
->
hdr
.
flags
&
WINHTTP_FLAG_SECURE
))
{
TRACE
(
"redirect from non-secure page to secure page
\n
"
);
request
->
hdr
.
flags
|=
WINHTTP_FLAG_SECURE
;
}
len
=
uc
.
dwHostNameLength
;
if
(
!
(
hostname
=
heap_alloc
(
(
len
+
1
)
*
sizeof
(
WCHAR
)
)))
goto
end
;
memcpy
(
hostname
,
uc
.
lpszHostName
,
len
*
sizeof
(
WCHAR
)
);
hostname
[
len
]
=
0
;
port
=
uc
.
nPort
?
uc
.
nPort
:
(
uc
.
nScheme
==
INTERNET_SCHEME_HTTPS
?
443
:
80
);
if
(
strcmpiW
(
connect
->
servername
,
hostname
)
||
connect
->
serverport
!=
port
)
{
heap_free
(
connect
->
servername
);
connect
->
servername
=
hostname
;
connect
->
serverport
=
port
;
netconn_close
(
&
request
->
netconn
);
if
(
!
(
ret
=
netconn_init
(
&
request
->
netconn
,
request
->
hdr
.
flags
&
WINHTTP_FLAG_SECURE
)))
goto
end
;
}
if
(
!
(
ret
=
process_header
(
request
,
attr_host
,
hostname
,
WINHTTP_ADDREQ_FLAG_REPLACE
,
TRUE
)))
goto
end
;
if
(
!
(
ret
=
open_connection
(
request
)))
goto
end
;
heap_free
(
request
->
path
);
request
->
path
=
NULL
;
if
(
uc
.
lpszUrlPath
)
{
len
=
uc
.
dwUrlPathLength
+
uc
.
dwExtraInfoLength
;
if
(
!
(
request
->
path
=
heap_alloc
(
(
len
+
1
)
*
sizeof
(
WCHAR
)
)))
goto
end
;
strcpyW
(
request
->
path
,
uc
.
lpszUrlPath
);
}
ret
=
TRUE
;
end:
if
(
!
ret
)
heap_free
(
hostname
);
heap_free
(
location
);
return
ret
;
}
static
BOOL
read_data
(
request_t
*
request
,
void
*
buffer
,
DWORD
size
,
DWORD
*
read
,
BOOL
async
)
{
DWORD
to_read
;
int
bytes_read
;
to_read
=
min
(
size
,
request
->
content_length
-
request
->
content_read
);
if
(
!
netconn_recv
(
&
request
->
netconn
,
buffer
,
to_read
,
async
?
0
:
MSG_WAITALL
,
&
bytes_read
))
{
if
(
bytes_read
!=
to_read
)
{
ERR
(
"not all data received %d/%d
\n
"
,
bytes_read
,
to_read
);
}
/* always return success, even if the network layer returns an error */
*
read
=
0
;
return
TRUE
;
}
request
->
content_read
+=
bytes_read
;
*
read
=
bytes_read
;
return
TRUE
;
}
/* read any content returned by the server so that the connection can be reused */
static
void
drain_content
(
request_t
*
request
)
{
DWORD
bytes_read
;
char
buffer
[
2048
];
if
(
request
->
content_length
==
~
0UL
)
return
;
for
(;;)
{
if
(
!
read_data
(
request
,
buffer
,
sizeof
(
buffer
),
&
bytes_read
,
FALSE
)
||
!
bytes_read
)
return
;
}
}
/***********************************************************************
* WinHttpReceiveResponse (winhttp.@)
*/
...
...
@@ -939,7 +1041,7 @@ BOOL WINAPI WinHttpReceiveResponse( HINTERNET hrequest, LPVOID reserved )
{
BOOL
ret
=
TRUE
;
request_t
*
request
;
DWORD
size
,
query
;
DWORD
size
,
query
,
status
;
TRACE
(
"%p, %p
\n
"
,
hrequest
,
reserved
);
...
...
@@ -955,12 +1057,28 @@ BOOL WINAPI WinHttpReceiveResponse( HINTERNET hrequest, LPVOID reserved )
return
FALSE
;
}
ret
=
receive_response
(
request
,
TRUE
);
for
(;;)
{
if
(
!
(
ret
=
receive_response
(
request
,
TRUE
)))
break
;
size
=
sizeof
(
DWORD
);
query
=
WINHTTP_QUERY_STATUS_CODE
|
WINHTTP_QUERY_FLAG_NUMBER
;
if
(
!
(
ret
=
query_headers
(
request
,
query
,
NULL
,
&
status
,
&
size
,
NULL
)))
break
;
size
=
sizeof
(
DWORD
);
query
=
WINHTTP_QUERY_CONTENT_LENGTH
|
WINHTTP_QUERY_FLAG_NUMBER
;
if
(
!
query_headers
(
request
,
query
,
NULL
,
&
request
->
content_length
,
&
size
,
NULL
))
request
->
content_length
=
~
0UL
;
size
=
sizeof
(
DWORD
);
query
=
WINHTTP_QUERY_CONTENT_LENGTH
|
WINHTTP_QUERY_FLAG_NUMBER
;
if
(
!
query_headers
(
request
,
query
,
NULL
,
&
request
->
content_length
,
&
size
,
NULL
))
request
->
content_length
=
~
0UL
;
if
(
status
==
200
)
break
;
if
(
status
==
301
||
status
==
302
)
{
if
(
request
->
hdr
.
flags
&
WINHTTP_DISABLE_REDIRECTS
)
break
;
drain_content
(
request
);
if
(
!
(
ret
=
handle_redirect
(
request
)))
break
;
}
ret
=
send_request
(
request
,
NULL
,
0
,
NULL
,
0
,
0
,
0
);
}
release_object
(
&
request
->
hdr
);
return
ret
;
...
...
@@ -994,27 +1112,6 @@ BOOL WINAPI WinHttpQueryDataAvailable( HINTERNET hrequest, LPDWORD available )
return
ret
;
}
static
BOOL
read_data
(
request_t
*
request
,
void
*
buffer
,
DWORD
size
,
DWORD
*
read
,
BOOL
async
)
{
DWORD
to_read
;
int
bytes_read
;
to_read
=
min
(
size
,
request
->
content_length
-
request
->
content_read
);
if
(
!
netconn_recv
(
&
request
->
netconn
,
buffer
,
to_read
,
async
?
0
:
MSG_WAITALL
,
&
bytes_read
))
{
if
(
bytes_read
!=
to_read
)
{
ERR
(
"not all data received %d/%d
\n
"
,
bytes_read
,
to_read
);
}
/* always return success, even if the network layer returns an error */
*
read
=
0
;
return
TRUE
;
}
request
->
content_read
+=
bytes_read
;
*
read
=
bytes_read
;
return
TRUE
;
}
static
DWORD
get_chunk_size
(
const
char
*
buffer
)
{
const
char
*
p
;
...
...
dlls/winhttp/tests/winhttp.c
View file @
41a76362
...
...
@@ -532,7 +532,7 @@ static void test_secure_connection(void)
static
const
WCHAR
google
[]
=
{
'w'
,
'w'
,
'w'
,
'.'
,
'g'
,
'o'
,
'o'
,
'g'
,
'l'
,
'e'
,
'.'
,
'c'
,
'o'
,
'm'
,
0
};
HANDLE
ses
,
con
,
req
;
DWORD
size
;
DWORD
size
,
status
;
BOOL
ret
;
ses
=
WinHttpOpen
(
test_useragent
,
0
,
NULL
,
NULL
,
0
);
...
...
@@ -566,6 +566,10 @@ static void test_secure_connection(void)
ret
=
WinHttpReceiveResponse
(
req
,
NULL
);
ok
(
ret
,
"failed to receive response %u
\n
"
,
GetLastError
());
size
=
sizeof
(
status
);
ret
=
WinHttpQueryHeaders
(
req
,
WINHTTP_QUERY_STATUS_CODE
|
WINHTTP_QUERY_FLAG_NUMBER
,
NULL
,
&
status
,
&
size
,
NULL
);
ok
(
ret
,
"failed unexpectedly %u
\n
"
,
GetLastError
());
size
=
0
;
ret
=
WinHttpQueryHeaders
(
req
,
WINHTTP_QUERY_RAW_HEADERS_CRLF
,
NULL
,
NULL
,
&
size
,
NULL
);
ok
(
!
ret
,
"succeeded unexpectedly
\n
"
);
...
...
@@ -581,6 +585,7 @@ static void test_request_parameter_defaults(void)
static
const
WCHAR
codeweavers
[]
=
{
'c'
,
'o'
,
'd'
,
'e'
,
'w'
,
'e'
,
'a'
,
'v'
,
'e'
,
'r'
,
's'
,
'.'
,
'c'
,
'o'
,
'm'
,
0
};
HANDLE
ses
,
con
,
req
;
DWORD
size
,
status
;
BOOL
ret
;
ses
=
WinHttpOpen
(
test_useragent
,
0
,
NULL
,
NULL
,
0
);
...
...
@@ -598,6 +603,11 @@ static void test_request_parameter_defaults(void)
ret
=
WinHttpReceiveResponse
(
req
,
NULL
);
ok
(
ret
,
"failed to receive response %u
\n
"
,
GetLastError
());
size
=
sizeof
(
status
);
ret
=
WinHttpQueryHeaders
(
req
,
WINHTTP_QUERY_STATUS_CODE
|
WINHTTP_QUERY_FLAG_NUMBER
,
NULL
,
&
status
,
&
size
,
NULL
);
ok
(
ret
,
"failed unexpectedly %u
\n
"
,
GetLastError
());
ok
(
status
==
200
,
"request failed unexpectedly %u
\n
"
,
status
);
WinHttpCloseHandle
(
req
);
req
=
WinHttpOpenRequest
(
con
,
empty
,
empty
,
empty
,
NULL
,
NULL
,
0
);
...
...
@@ -609,6 +619,11 @@ static void test_request_parameter_defaults(void)
ret
=
WinHttpReceiveResponse
(
req
,
NULL
);
ok
(
ret
,
"failed to receive response %u
\n
"
,
GetLastError
());
size
=
sizeof
(
status
);
ret
=
WinHttpQueryHeaders
(
req
,
WINHTTP_QUERY_STATUS_CODE
|
WINHTTP_QUERY_FLAG_NUMBER
,
NULL
,
&
status
,
&
size
,
NULL
);
ok
(
ret
,
"failed unexpectedly %u
\n
"
,
GetLastError
());
ok
(
status
==
200
,
"request failed unexpectedly %u
\n
"
,
status
);
WinHttpCloseHandle
(
req
);
WinHttpCloseHandle
(
con
);
WinHttpCloseHandle
(
ses
);
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment