HADOOP-7729. Merge r1183512 from trunk to 0.23

git-svn-id: https://svn.apache.org/repos/asf/hadoop/common/branches/branch-0.23@1298085 13f79535-47bb-0310-9956-ffa450edef68
This commit is contained in:
Suresh Srinivas 2012-03-07 20:08:52 +00:00
parent e4d3e2ffa3
commit d667cd871b
3 changed files with 45 additions and 2 deletions

View File

@ -288,6 +288,9 @@ Release 0.23.1 - 2012-02-17
HADOOP-7470. Move up to Jackson 1.8.8. (Enis Soztutar via szetszwo) HADOOP-7470. Move up to Jackson 1.8.8. (Enis Soztutar via szetszwo)
HADOOP-7729. Send back valid HTTP response if user hits IPC port with
HTTP GET. (todd)
HADOOP-8027. Visiting /jmx on the daemon web interfaces may print HADOOP-8027. Visiting /jmx on the daemon web interfaces may print
unnecessary error in logs. (atm) unnecessary error in logs. (atm)

View File

@ -110,6 +110,23 @@ public abstract class Server {
*/ */
public static final ByteBuffer HEADER = ByteBuffer.wrap("hrpc".getBytes()); public static final ByteBuffer HEADER = ByteBuffer.wrap("hrpc".getBytes());
/**
* If the user accidentally sends an HTTP GET to an IPC port, we detect this
* and send back a nicer response.
*/
private static final ByteBuffer HTTP_GET_BYTES = ByteBuffer.wrap(
"GET ".getBytes());
/**
* An HTTP response to send back if we detect an HTTP request to our IPC
* port.
*/
static final String RECEIVED_HTTP_REQ_RESPONSE =
"HTTP/1.1 404 Not Found\r\n" +
"Content-type: text/plain\r\n\r\n" +
"It looks like you are making an HTTP request to a Hadoop IPC port. " +
"This is not the correct port for the web interface on this daemon.\r\n";
// 1 : Introduce ping and server does not throw away RPCs // 1 : Introduce ping and server does not throw away RPCs
// 3 : Introduce the protocol into the RPC connection header // 3 : Introduce the protocol into the RPC connection header
// 4 : Introduced SASL security layer // 4 : Introduced SASL security layer
@ -990,6 +1007,7 @@ public abstract class Server {
private ByteArrayOutputStream authFailedResponse = new ByteArrayOutputStream(); private ByteArrayOutputStream authFailedResponse = new ByteArrayOutputStream();
// Fake 'call' for SASL context setup // Fake 'call' for SASL context setup
private static final int SASL_CALLID = -33; private static final int SASL_CALLID = -33;
private final Call saslCall = new Call(SASL_CALLID, null, this); private final Call saslCall = new Call(SASL_CALLID, null, this);
private final ByteArrayOutputStream saslResponse = new ByteArrayOutputStream(); private final ByteArrayOutputStream saslResponse = new ByteArrayOutputStream();
@ -1222,7 +1240,7 @@ public abstract class Server {
if (count < 0 || dataLengthBuffer.remaining() > 0) if (count < 0 || dataLengthBuffer.remaining() > 0)
return count; return count;
} }
if (!rpcHeaderRead) { if (!rpcHeaderRead) {
//Every connection is expected to send the header. //Every connection is expected to send the header.
if (rpcHeaderBuffer == null) { if (rpcHeaderBuffer == null) {
@ -1236,7 +1254,16 @@ public abstract class Server {
byte[] method = new byte[] {rpcHeaderBuffer.get(1)}; byte[] method = new byte[] {rpcHeaderBuffer.get(1)};
authMethod = AuthMethod.read(new DataInputStream( authMethod = AuthMethod.read(new DataInputStream(
new ByteArrayInputStream(method))); new ByteArrayInputStream(method)));
dataLengthBuffer.flip(); dataLengthBuffer.flip();
// Check if it looks like the user is hitting an IPC port
// with an HTTP GET - this is a common error, so we can
// send back a simple string indicating as much.
if (HTTP_GET_BYTES.equals(dataLengthBuffer)) {
setupHttpRequestOnIpcPortResponse();
return -1;
}
if (!HEADER.equals(dataLengthBuffer) || version != CURRENT_VERSION) { if (!HEADER.equals(dataLengthBuffer) || version != CURRENT_VERSION) {
//Warning is ok since this is not supposed to happen. //Warning is ok since this is not supposed to happen.
LOG.warn("Incorrect header or version mismatch from " + LOG.warn("Incorrect header or version mismatch from " +
@ -1355,6 +1382,13 @@ public abstract class Server {
responder.doRespond(fakeCall); responder.doRespond(fakeCall);
} }
} }
private void setupHttpRequestOnIpcPortResponse() throws IOException {
Call fakeCall = new Call(0, null, this);
fakeCall.setResponse(ByteBuffer.wrap(
RECEIVED_HTTP_REQ_RESPONSE.getBytes()));
responder.doRespond(fakeCall);
}
/// Reads the connection header following version /// Reads the connection header following version
private void processHeader(byte[] buf) throws IOException { private void processHeader(byte[] buf) throws IOException {

View File

@ -584,6 +584,12 @@ public class TestIPC {
NetworkTraces.RESPONSE_TO_HADOOP_0_21_0_RPC); NetworkTraces.RESPONSE_TO_HADOOP_0_21_0_RPC);
} }
@Test
public void testHttpGetResponse() throws Exception {
doIpcVersionTest("GET / HTTP/1.0\r\n\r\n".getBytes(),
Server.RECEIVED_HTTP_REQ_RESPONSE.getBytes());
}
private void doIpcVersionTest( private void doIpcVersionTest(
byte[] requestData, byte[] requestData,
byte[] expectedResponse) throws Exception { byte[] expectedResponse) throws Exception {