Every web developer knows how to make a GET redirect, in fact they've probably done it numerous times. However very few people know the same can be done for POST requests, in some instances completely transparently to the user. This by itself make not seem like an issue, but when you combine it with XSS it can be a very powerful to used to scam users.
Consider the following scenario. A user goes to a trusted site where XSS had modified the action field of the login POST form, pointing it to http://p0wn3d.com/post.php. When user submits a request it goes to a 3rd party site, which captures the login credentials and then redirects the POST data to the original site. In the end to the user has no clue something sinister had happened because they never see p0wn3d.com. In fact the everything appears to have worked as intended.
So how does this work. Ability to redirect POST comes as a courtesy of the little known
307 redirect code. Which in PHP can be forced in the following manner:
PHP:
<?php
header("Location: URL", TRUE, 307);
?>
Now, according to the RFC
"If the 307 status code is received in response to a request other than GET or HEAD, the user agent MUST NOT automatically redirect the request unless it can be confirmed by the user, since this might change the conditions under which the request was issued."
Alas, unlike the Opera and FireFox developers, the IE developers have never read the spec, and even the latest, most secure IE7 will redirect the POST request from domain A to domain B without any warnings or confirmation dialogs! Safari also acts in an interesting manner, while it does not raise a confirmation dialog and performs the redirect, it throws away the POST data, effectively changing 307 redirect into the more common 302.