(THRIFT-45) TNonblockingServer (C++): only do one write in responses.
Instead of doing one 4-byte write for the frame length before the write
of the actual message, prepend the frame length to the message buffer
so we can send them both at once.
git-svn-id: https://svn.apache.org/repos/asf/incubator/thrift/trunk@672937 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/lib/cpp/src/server/TNonblockingServer.cpp b/lib/cpp/src/server/TNonblockingServer.cpp
index e376f97..cd7951d 100644
--- a/lib/cpp/src/server/TNonblockingServer.cpp
+++ b/lib/cpp/src/server/TNonblockingServer.cpp
@@ -220,6 +220,10 @@
// and get back some data from the dispatch function
inputTransport_->resetBuffer(readBuffer_, readBufferPos_);
outputTransport_->resetBuffer();
+ // Prepend four bytes of blank space to the buffer so we can
+ // write the frame size there later.
+ outputTransport_->getWritePtr(4);
+ outputTransport_->wroteBytes(4);
if (server_->isThreadPoolProcessing()) {
// We are setting up a Task to do this work and we will wait on it
@@ -293,7 +297,7 @@
// If the function call generated return data, then move into the send
// state and get going
- if (writeBufferSize_ > 0) {
+ if (writeBufferSize_ > 4) {
// Move into write state
writeBufferPos_ = 0;
@@ -301,16 +305,15 @@
if (server_->getFrameResponses()) {
// Put the frame size into the write buffer
- appState_ = APP_SEND_FRAME_SIZE;
- frameSize_ = (int32_t)htonl(writeBufferSize_);
- writeBuffer_ = (uint8_t*)&frameSize_;
- writeBufferSize_ = 4;
+ int32_t frameSize = (int32_t)htonl(writeBufferSize_ - 4);
+ memcpy(writeBuffer_, &frameSize, 4);
} else {
// Go straight into sending the result, do not frame it
- appState_ = APP_SEND_RESULT;
+ writeBufferPos_ = 4;
}
// Socket into write mode
+ appState_ = APP_SEND_RESULT;
setWrite();
// Try to work the socket immediately
@@ -323,21 +326,6 @@
// right back into the read frame header state
goto LABEL_APP_INIT;
- case APP_SEND_FRAME_SIZE:
-
- // Refetch the result of the operation since we put the frame size into
- // writeBuffer_
- outputTransport_->getBuffer(&writeBuffer_, &writeBufferSize_);
- writeBufferPos_ = 0;
-
- // Now in send result state
- appState_ = APP_SEND_RESULT;
-
- // Go to work on the socket right away, probably still writeable
- // workSocket();
-
- return;
-
case APP_SEND_RESULT:
// N.B.: We also intentionally fall through here into the INIT state!
diff --git a/lib/cpp/src/server/TNonblockingServer.h b/lib/cpp/src/server/TNonblockingServer.h
index 3de5b94..9d426fa 100644
--- a/lib/cpp/src/server/TNonblockingServer.h
+++ b/lib/cpp/src/server/TNonblockingServer.h
@@ -211,7 +211,6 @@
APP_READ_FRAME_SIZE,
APP_READ_REQUEST,
APP_WAIT_TASK,
- APP_SEND_FRAME_SIZE,
APP_SEND_RESULT
};
@@ -263,9 +262,6 @@
// How far through writing are we?
uint32_t writeBufferPos_;
- // Frame size
- int32_t frameSize_;
-
// Task handle
int taskHandle_;