From: Mu-Woong Lee Date: Tue, 1 Aug 2017 11:44:54 +0000 (+0900) Subject: Add defence code to handle socket read failure X-Git-Tag: accepted/tizen/unified/20170904.144519^2~7 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=97a36ac553b22894aabc0c308b9e35cdb793011e;p=platform%2Fcore%2Fcontext%2Fcontext-service.git Add defence code to handle socket read failure Change-Id: Ic8e1f638d900c7d29804a93bcc1c09a80fde7f45 Signed-off-by: Mu-Woong Lee --- diff --git a/src/agent/AgentSocket.cpp b/src/agent/AgentSocket.cpp index e8d45b9..f9d6fb5 100644 --- a/src/agent/AgentSocket.cpp +++ b/src/agent/AgentSocket.cpp @@ -14,6 +14,7 @@ * limitations under the License. */ +#include #include #include #include @@ -152,27 +153,43 @@ bool AgentSocket::__readCommand(int msgsock) { uint16_t id = 0; uint8_t length = 0; - int rval = 0; - char buf[CTX_AGENT_COMMAND_LIMIT] = {0}; - - rval = read(msgsock, &id, sizeof(id)); - IF_FAIL_RETURN_TAG(rval == sizeof(id), false, _E, "read() failed"); + char command[CTX_AGENT_COMMAND_LIMIT] = {0}; + + auto safeRead = [&msgsock](char* buf, size_t count)->bool { + do { + int rc = read(msgsock, buf, count); + if (rc < 0) { + if (errno == EAGAIN) { + continue; + } else { + _E("Socket read error: %d", errno); + return false; + } + } + count -= rc; + buf += rc; + } while (count > 0); + return true; + }; + + bool success; + + success = safeRead(reinterpret_cast(&id), sizeof(id)); + IF_FAIL_RETURN(success, false); if (id == TERM_MSG_ID) { _D("Stop listening..."); return false; } - rval = read(msgsock, &length, sizeof(length)); - IF_FAIL_RETURN_TAG(rval == sizeof(length), false, _E, "read() failed"); - - rval = read(msgsock, buf, length); - IF_FAIL_RETURN_TAG(rval == static_cast(length), false, _E, "read() failed"); - + success = safeRead(reinterpret_cast(&length), sizeof(length)); + IF_FAIL_RETURN(success, false); + IF_FAIL_RETURN_TAG(length > 0 && length <= CTX_AGENT_COMMAND_LIMIT, false, _E, "Invalid command"); - buf[length] = '\0'; + success = safeRead(command, length); + IF_FAIL_RETURN(success, false); - CommandInfo* info = new CommandInfo(&__pluginLoader, id, length, buf); + CommandInfo* info = new CommandInfo(&__pluginLoader, id, length, command); g_idle_add(__send_command, info); return true;