From 135c918861ce17baec8a12727e76b569be97cecd Mon Sep 17 00:00:00 2001 From: Tae-Jeong Lee Date: Fri, 28 Jun 2013 21:04:56 +0900 Subject: [PATCH] Implementation of IPC Asynchronous Message Support. - sendAsyncMessageToUiProcess() - ignoreAsyncMessageReply() [Issue#] N/A [Problem] Requirement from webapi team. [Cause] N/A [Solution] Add IPC Asynchronous Message Support Feature. Change-Id: I158eebfd5690e6f1e0828da785cac3568f1f9017 --- src/plugins-ipc-message/ipc_message_support.cpp | 140 +++++++++++++++++++++++- src/plugins-ipc-message/ipc_message_support.h | 46 ++++++++ src/standards/W3C/Widget/CMakeLists.txt | 2 + 3 files changed, 184 insertions(+), 4 deletions(-) diff --git a/src/plugins-ipc-message/ipc_message_support.cpp b/src/plugins-ipc-message/ipc_message_support.cpp index 5d2f290..547efae 100644 --- a/src/plugins-ipc-message/ipc_message_support.cpp +++ b/src/plugins-ipc-message/ipc_message_support.cpp @@ -36,7 +36,7 @@ namespace { const char* const TIZEN_GET_WINDOW_HANDLE = "tizen://getWindowHandle"; const char* const TIZEN_CLEAR_ALL_COOKIES = "tizen://clearAllCookies"; -std::string toString(WKStringRef str) +static std::string toString(WKStringRef str) { if (WKStringIsEmpty(str)) { return std::string(); @@ -47,7 +47,7 @@ std::string toString(WKStringRef str) return buffer; } -std::string sendSyncMessage(const char* name, const char* body) +static std::string sendSyncMessage(const char* name, const char* body) { WKStringRef nameWKString = WKStringCreateWithUTF8CString(name); WKStringRef bodyWKString = NULL; @@ -72,7 +72,7 @@ std::string sendSyncMessage(const char* name, const char* body) } } -void sendAsyncMessage(const char* name, const char* body) +static void sendPostMessage(const char* name, const char* body) { WKStringRef nameWKString = WKStringCreateWithUTF8CString(name); WKStringRef bodyWKString = NULL; @@ -88,8 +88,79 @@ void sendAsyncMessage(const char* name, const char* body) WKRelease(bodyWKString); } } + +static int sendAsyncMessage(const char* name, const char* body, AsyncReplyCallback replyCallback, void* data) +{ + using namespace IPCMessageSupport; + + int handle = AsyncConnectionManager::instance().addConnection(AsyncConnectionPtr(new AsyncConnection(replyCallback, data))); + + std::string strBody = body; + std::stringstream ss; + + ss << handle; + strBody = ss.str() + "_" + strBody; + + sendPostMessage(name, strBody.c_str()); + + return handle; +} + +} // namespace + + +namespace IPCMessageSupport { + +AsyncConnectionManager::~AsyncConnectionManager() +{ + m_connectionMap.clear(); +} + +AsyncConnectionManager &AsyncConnectionManager::instance() +{ + static AsyncConnectionManager instance; + + return instance; +} + +int AsyncConnectionManager::addConnection(AsyncConnectionPtr connection) +{ + static int latestHandle = -1; + int newHandle; + + latestHandle++; + if (latestHandle < 0) latestHandle = 0; + + newHandle = latestHandle; + + m_connectionMap.insert(AsyncConnectionMap::value_type(newHandle, connection)); + + return newHandle; +} + +bool AsyncConnectionManager::removeConnection(int handle) +{ + bool ret = (m_connectionMap.erase(handle) == 1); + + return ret; +} + +AsyncConnectionPtr AsyncConnectionManager::getConnection(int handle) +{ + AsyncConnectionMap::iterator iter = m_connectionMap.find(handle); + + if (iter != m_connectionMap.end()) + { + return iter->second; + } + + return AsyncConnectionPtr(); } + +} // namespace IPCMessageSupport + + void IPCMessageSupport::setWKBundleRef(WKBundleRef bundleRef) { LogDebug("setWKBundleRef called"); @@ -134,9 +205,70 @@ const char* IPCMessageSupport::sendMessageToUiProcess( // tizen://clearAllCookies if (!strcmp(name, TIZEN_CLEAR_ALL_COOKIES)) { - sendAsyncMessage(name, body); + sendPostMessage(name, body); return NULL; } return NULL; } + +int IPCMessageSupport::sendAsyncMessageToUiProcess(const char* name, const char* body, AsyncReplyCallback replyCallback, void* data) +{ + LogDebug("sendAsyncMessageToUiProcess called"); + + if (s_injectedBundleRef == NULL) + { + LogError("UI Process information isn't set"); + return -1; + } + + if (name == NULL) + { + LogError("msg name is null!"); + return -1; + } + + if (body == NULL) + { + body = ""; + } + + LogDebug("name = [" << name << "]"); + LogDebug("body = [" << body << "]"); + + return sendAsyncMessage(name, body, replyCallback, data); +} + +void* IPCMessageSupport::ignoreAsyncMessageReply(int handle) +{ + LogDebug("ignoreAsyncMessageReply called"); + + AsyncConnectionPtr connection = AsyncConnectionManager::instance().getConnection(handle); + + if (!connection) + { + return NULL; + } + + AsyncConnectionManager::instance().removeConnection(handle); + + return connection->data; +} + +void IPCMessageSupport::replyAsyncMessageToWebProcess(Ewk_Context* ewkContext, int handle, const char* body) +{ + LogDebug("replyAsyncMessageToWebProcess called"); + + if (ewkContext == NULL) + { + return; + } + + std::string strBody = (body) ? (body) : ""; + std::stringstream ss; + ss << handle; + + strBody = ss.str() + "_" + strBody; + + ewk_context_message_post_to_injected_bundle(ewkContext, REPLY_ASYNC, strBody.c_str()); +} diff --git a/src/plugins-ipc-message/ipc_message_support.h b/src/plugins-ipc-message/ipc_message_support.h index fa96e3f..d2c5384 100644 --- a/src/plugins-ipc-message/ipc_message_support.h +++ b/src/plugins-ipc-message/ipc_message_support.h @@ -22,13 +22,59 @@ #ifndef WRT_SRC_IPC_MESSAGE_SUPPORT #define WRT_SRC_IPC_MESSAGE_SUPPORT +#include +#include #include #include +#include + +typedef void (*AsyncReplyCallback)(unsigned int, void*, const char*); namespace IPCMessageSupport { + +static const char * const REPLY_ASYNC = "ToInjectedBundle::REPLY_ASYNC"; +static const char * const TIZEN_CHANGE_USERAGENT = "tizen://changeUA"; +static const char * const TIZEN_DELETE_ALL_COOKIES = "tizen://deleteAllCookies"; + +class AsyncConnection +{ + public: + AsyncReplyCallback replyCallback; + void* data; + + AsyncConnection(AsyncReplyCallback r, void* d) : + replyCallback(r), + data(d) + { + } +}; + +typedef std::shared_ptr AsyncConnectionPtr; +typedef std::map AsyncConnectionMap; + +class AsyncConnectionManager +{ + private: + AsyncConnectionMap m_connectionMap; + + public: + ~AsyncConnectionManager(); + + // Singleton + static AsyncConnectionManager &instance(); + + int addConnection(AsyncConnectionPtr connection); + bool removeConnection(int handle); + AsyncConnectionPtr getConnection(int handle); + +}; + void setWKBundleRef(WKBundleRef bundleRef); void setXwindowHandle(unsigned int handle); const char* sendMessageToUiProcess(const char* name, const char* body); +int sendAsyncMessageToUiProcess(const char* name, const char* body, AsyncReplyCallback replyCallback, void* data); +void* ignoreAsyncMessageReply(int handle); +void replyAsyncMessageToWebProcess(Ewk_Context* ewkContext, int handle, const char* body); } #endif // WRT_SRC_IPC_MESSAGE_SUPPORT \ No newline at end of file diff --git a/src/standards/W3C/Widget/CMakeLists.txt b/src/standards/W3C/Widget/CMakeLists.txt index 231e6a6..537cd64 100644 --- a/src/standards/W3C/Widget/CMakeLists.txt +++ b/src/standards/W3C/Widget/CMakeLists.txt @@ -29,6 +29,7 @@ include_directories( ${API_WIDGET_PATH} ${webkit2_INCLUDE_DIRS} ${plugin-types_INCLUDE_DIRS} + ${PLUGINS_IPC_MESSAGE_DIRS} ) add_library(${TARGET_NAME} SHARED ${SRCS}) @@ -41,6 +42,7 @@ target_link_libraries(${TARGET_NAME} wrt-plugins-localstorage wrt-plugins-storageevent wrt-dispatch-event + wrt-plugins-ipc-message ) INSTALL(TARGETS ${TARGET_NAME} LIBRARY DESTINATION ${LIB_INSTALL_DIR}/wrt-plugins/w3c-widget-interface) -- 2.7.4