]> git.ipfire.org Git - thirdparty/freeswitch.git/commitdiff
FS-9952: Big commit, first registered jsonrpc echo call successful, lots of cleanup...
authorShane Bryldt <astaelan@gmail.com>
Tue, 7 Mar 2017 18:45:52 +0000 (18:45 +0000)
committerMike Jerris <mike@jerris.com>
Wed, 22 Mar 2017 21:42:50 +0000 (17:42 -0400)
25 files changed:
libs/libblade/Makefile.am
libs/libblade/src/blade_connection.c
libs/libblade/src/blade_method.c [new file with mode: 0644]
libs/libblade/src/blade_module_wss.c
libs/libblade/src/blade_protocol.c
libs/libblade/src/blade_rpcproto.c [deleted file]
libs/libblade/src/blade_session.c
libs/libblade/src/blade_space.c [new file with mode: 0644]
libs/libblade/src/blade_stack.c
libs/libblade/src/bpcp.c [deleted file]
libs/libblade/src/include/blade.h
libs/libblade/src/include/blade_method.h [moved from libs/libblade/src/include/bpcp.h with 79% similarity]
libs/libblade/src/include/blade_protocol.h
libs/libblade/src/include/blade_rpcproto.h [deleted file]
libs/libblade/src/include/blade_session.h
libs/libblade/src/include/blade_space.h [moved from libs/libks/src/include/ks_rpcmessage.h with 52% similarity]
libs/libblade/src/include/blade_stack.h
libs/libblade/src/include/blade_types.h
libs/libblade/test/Makefile.am
libs/libblade/test/testrpcproto.c [deleted file]
libs/libks/Makefile.am
libs/libks/src/include/ks.h
libs/libks/src/ks_rpcmessage.c [deleted file]
libs/libks/test/Makefile.am
libs/libks/test/testmessages.c [deleted file]

index 46e751405f747438ab1ed8ac7b512fae768808f3..9346c3249a855abe9b694e099c95bab512b87411 100644 (file)
@@ -11,23 +11,20 @@ libunqlite_la_CFLAGS    = -DUNQLITE_ENABLE_THREADS
 libunqlite_la_LIBADD    = -lpthread
 
 lib_LTLIBRARIES                = libblade.la
-libblade_la_SOURCES     = src/blade.c src/blade_stack.c src/bpcp.c src/blade_datastore.c
-libblade_la_SOURCES    += src/blade_rpcproto.c
-libblade_la_SOURCES    += src/blade_identity.c src/blade_module.c src/blade_connection.c src/blade_module_wss.c
-libblade_la_SOURCES    += src/blade_session.c src/blade_protocol.c
+libblade_la_SOURCES     = src/blade.c src/blade_stack.c
+libblade_la_SOURCES    += src/blade_datastore.c
+libblade_la_SOURCES    += src/blade_identity.c src/blade_module.c src/blade_connection.c
+libblade_la_SOURCES    += src/blade_session.c src/blade_protocol.c src/blade_space.c src/blade_method.c
+libblade_la_SOURCES    += src/blade_module_wss.c
 libblade_la_CFLAGS     = $(AM_CFLAGS) $(AM_CPPFLAGS)
 libblade_la_LDFLAGS     = -version-info 0:1:0 -lncurses -lpthread -lm -lconfig $(AM_LDFLAGS)
 libblade_la_LIBADD      = libunqlite.la
 library_includedir     = $(prefix)/include
 library_include_HEADERS = src/include/blade.h src/include/blade_types.h src/include/blade_stack.h
-library_include_HEADERS += src/include/bpcp.h src/include/blade_datastore.h src/include/blade_rpcproto.h
-library_include_HEADERS += src/include/blade_identity.h src/include/blade_module.h src/include/blade_connection.h 
-library_include_HEADERS += src/include/blade_session.h src/include/blade_protocol.h 
+library_include_HEADERS += src/include/blade_datastore.h
+library_include_HEADERS += src/include/blade_identity.h src/include/blade_module.h src/include/blade_connection.h
+library_include_HEADERS += src/include/blade_session.h src/include/blade_protocol.h src/include/blade_space.h src/include/blade_method.h
 library_include_HEADERS += src/include/unqlite.h test/tap.h
 
 tests: libblade.la
        $(MAKE) -C test tests
-
-
-
-
index 6816d61db930cc9b7afe37d911ab97ffc4e44289..f8cfaead545e2d7674a74576813892994f2e7920 100644 (file)
@@ -495,6 +495,7 @@ ks_status_t blade_connection_state_on_ready(blade_connection_t *bc)
        blade_transport_state_callback_t callback = NULL;
        blade_connection_state_hook_t hook = BLADE_CONNECTION_STATE_HOOK_SUCCESS;
        cJSON *json = NULL;
+       blade_session_t *bs = NULL;
        ks_bool_t done = KS_FALSE;
 
        ks_assert(bc);
@@ -514,14 +515,18 @@ ks_status_t blade_connection_state_on_ready(blade_connection_t *bc)
                        blade_connection_disconnect(bc);
                        break;
                }
+
                if (!(done = (json == NULL))) {
-                       blade_session_t *bs = blade_handle_sessions_get(bc->handle, bc->session);
-                       ks_assert(bs);
+                       if (!bs) {
+                               bs = blade_handle_sessions_get(bc->handle, bc->session);
+                               ks_assert(bs);
+                       }
                        blade_session_receiving_push(bs, json);
                        cJSON_Delete(json);
                        json = NULL;
                }
        }
+       if (bs) blade_session_read_unlock(bs);
 
        callback = blade_connection_state_callback_lookup(bc, BLADE_CONNECTION_STATE_READY);
        if (callback) hook = callback(bc, BLADE_CONNECTION_STATE_CONDITION_POST);
diff --git a/libs/libblade/src/blade_method.c b/libs/libblade/src/blade_method.c
new file mode 100644 (file)
index 0000000..ac09c0d
--- /dev/null
@@ -0,0 +1,118 @@
+/*
+ * Copyright (c) 2017, Shane Bryldt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * * Neither the name of the original author; nor the names of any contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER
+ * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "blade.h"
+
+struct blade_method_s {
+       blade_handle_t *handle;
+       ks_pool_t *pool;
+
+       blade_space_t *space;
+       const char *name;
+
+       blade_request_callback_t callback;
+       // @todo more fun descriptive information about the call for remote registrations
+};
+
+
+KS_DECLARE(ks_status_t) blade_method_create(blade_method_t **bmP, blade_space_t *bs, const char *name, blade_request_callback_t callback)
+{
+       blade_handle_t *bh = NULL;
+       blade_method_t *bm = NULL;
+       ks_pool_t *pool = NULL;
+
+       ks_assert(bmP);
+       ks_assert(bs);
+       ks_assert(name);
+
+       bh = blade_space_handle_get(bs);
+       ks_assert(bh);
+
+       pool = blade_handle_pool_get(bh);
+       ks_assert(pool);
+
+       bm = ks_pool_alloc(pool, sizeof(blade_method_t));
+       bm->handle = bh;
+       bm->pool = pool;
+       bm->space = bs;
+       bm->name = name; // @todo dup and keep copy? should mostly be literals
+       bm->callback = callback;
+
+       *bmP = bm;
+
+    ks_log(KS_LOG_DEBUG, "Method Created: %s.%s\n", blade_space_path_get(bs), name);
+
+       return KS_STATUS_SUCCESS;
+}
+
+KS_DECLARE(ks_status_t) blade_method_destroy(blade_method_t **bmP)
+{
+       blade_method_t *bm = NULL;
+
+       ks_assert(bmP);
+       ks_assert(*bmP);
+
+       bm = *bmP;
+
+    ks_log(KS_LOG_DEBUG, "Method Destroyed: %s.%s\n", blade_space_path_get(bm->space), bm->name);
+
+       ks_pool_free(bm->pool, bmP);
+
+       return KS_STATUS_SUCCESS;
+}
+
+KS_DECLARE(const char *) blade_method_name_get(blade_method_t *bm)
+{
+       ks_assert(bm);
+
+       return bm->name;
+}
+
+KS_DECLARE(blade_request_callback_t) blade_method_callback_get(blade_method_t *bm)
+{
+       ks_assert(bm);
+
+       return bm->callback;
+}
+
+
+/* For Emacs:
+ * Local Variables:
+ * mode:c
+ * indent-tabs-mode:t
+ * tab-width:4
+ * c-basic-offset:4
+ * End:
+ * For VIM:
+ * vim:set softtabstop=4 shiftwidth=4 tabstop=4 noet:
+ */
index ae5c5e1f961a5a1ab5885971801c61fb16bf30de..dc1118cb957118339be459a2fc4d521dce7025fd 100644 (file)
@@ -111,8 +111,10 @@ blade_connection_state_hook_t blade_transport_wss_on_state_connect_inbound(blade
 blade_connection_state_hook_t blade_transport_wss_on_state_connect_outbound(blade_connection_t *bc, blade_connection_state_condition_t condition);
 blade_connection_state_hook_t blade_transport_wss_on_state_attach_inbound(blade_connection_t *bc, blade_connection_state_condition_t condition);
 blade_connection_state_hook_t blade_transport_wss_on_state_attach_outbound(blade_connection_t *bc, blade_connection_state_condition_t condition);
-blade_connection_state_hook_t blade_transport_wss_on_state_detach(blade_connection_t *bc, blade_connection_state_condition_t condition);
-blade_connection_state_hook_t blade_transport_wss_on_state_ready(blade_connection_t *bc, blade_connection_state_condition_t condition);
+blade_connection_state_hook_t blade_transport_wss_on_state_detach_inbound(blade_connection_t *bc, blade_connection_state_condition_t condition);
+blade_connection_state_hook_t blade_transport_wss_on_state_detach_outbound(blade_connection_t *bc, blade_connection_state_condition_t condition);
+blade_connection_state_hook_t blade_transport_wss_on_state_ready_inbound(blade_connection_t *bc, blade_connection_state_condition_t condition);
+blade_connection_state_hook_t blade_transport_wss_on_state_ready_outbound(blade_connection_t *bc, blade_connection_state_condition_t condition);
 
 
 
@@ -120,6 +122,9 @@ ks_status_t blade_transport_wss_init_create(blade_transport_wss_init_t **bt_wssi
 ks_status_t blade_transport_wss_init_destroy(blade_transport_wss_init_t **bt_wssiP);
 
 
+ks_bool_t blade_test_echo_request_handler(blade_request_t *breq);
+ks_bool_t blade_test_echo_response_handler(blade_response_t *bres);
+
 
 static blade_module_callbacks_t g_module_wss_callbacks =
 {
@@ -144,10 +149,10 @@ static blade_transport_callbacks_t g_transport_wss_callbacks =
        blade_transport_wss_on_state_connect_outbound,
        blade_transport_wss_on_state_attach_inbound,
        blade_transport_wss_on_state_attach_outbound,
-       blade_transport_wss_on_state_detach,
-       blade_transport_wss_on_state_detach,
-       blade_transport_wss_on_state_ready,
-       blade_transport_wss_on_state_ready,
+       blade_transport_wss_on_state_detach_inbound,
+       blade_transport_wss_on_state_detach_outbound,
+       blade_transport_wss_on_state_ready_inbound,
+       blade_transport_wss_on_state_ready_outbound,
 };
 
 
@@ -385,6 +390,8 @@ ks_status_t blade_module_wss_config(blade_module_wss_t *bm_wss, config_setting_t
 KS_DECLARE(ks_status_t) blade_module_wss_on_startup(blade_module_t *bm, config_setting_t *config)
 {
        blade_module_wss_t *bm_wss = NULL;
+       blade_space_t *space = NULL;
+       blade_method_t *method = NULL;
 
        ks_assert(bm);
        ks_assert(config);
@@ -419,6 +426,17 @@ KS_DECLARE(ks_status_t) blade_module_wss_on_startup(blade_module_t *bm, config_s
 
        blade_handle_transport_register(bm_wss->handle, bm, BLADE_MODULE_WSS_TRANSPORT_NAME, bm_wss->transport_callbacks);
 
+
+       blade_space_create(&space, bm_wss->handle, "blade.test");
+       ks_assert(space);
+
+       blade_method_create(&method, space, "echo", blade_test_echo_request_handler);
+       ks_assert(method);
+
+       blade_space_methods_add(space, method);
+
+       blade_handle_space_register(space);
+
        ks_log(KS_LOG_DEBUG, "Started\n");
 
        return KS_STATUS_SUCCESS;
@@ -428,6 +446,7 @@ KS_DECLARE(ks_status_t) blade_module_wss_on_shutdown(blade_module_t *bm)
 {
        blade_module_wss_t *bm_wss = NULL;
        blade_connection_t *bc = NULL;
+       ks_bool_t stopped = KS_FALSE;
 
        ks_assert(bm);
 
@@ -440,6 +459,7 @@ KS_DECLARE(ks_status_t) blade_module_wss_on_shutdown(blade_module_t *bm)
                ks_thread_join(bm_wss->listeners_thread);
                ks_pool_free(bm_wss->pool, &bm_wss->listeners_thread);
                bm_wss->shutdown = KS_FALSE;
+               stopped = KS_TRUE;
        }
 
        for (int32_t index = 0; index < bm_wss->listeners_count; ++index) {
@@ -461,7 +481,7 @@ KS_DECLARE(ks_status_t) blade_module_wss_on_shutdown(blade_module_t *bm)
                while (list_size(&bm_wss->connected) > 0) ks_sleep_ms(100);
        }
 
-       ks_log(KS_LOG_DEBUG, "Stopped\n");
+       if (stopped) ks_log(KS_LOG_DEBUG, "Stopped\n");
 
        return KS_STATUS_SUCCESS;
 }
@@ -751,7 +771,6 @@ ks_status_t blade_transport_wss_write(blade_transport_wss_t *bt_wss, cJSON *json
 
 ks_status_t blade_transport_wss_on_send(blade_connection_t *bc, cJSON *json)
 {
-       ks_status_t ret = KS_STATUS_SUCCESS;
        blade_transport_wss_t *bt_wss = NULL;
 
        ks_assert(bc);
@@ -759,11 +778,7 @@ ks_status_t blade_transport_wss_on_send(blade_connection_t *bc, cJSON *json)
 
        bt_wss = (blade_transport_wss_t *)blade_connection_transport_get(bc);
 
-       ret = blade_transport_wss_write(bt_wss, json);
-
-       cJSON_Delete(json);
-
-       return ret;
+       return blade_transport_wss_write(bt_wss, json);
 }
 
 ks_status_t blade_transport_wss_read(blade_transport_wss_t *bt_wss, cJSON **json)
@@ -814,6 +829,29 @@ ks_status_t blade_transport_wss_on_receive(blade_connection_t *bc, cJSON **json)
        return blade_transport_wss_read(bt_wss, json);
 }
 
+ks_status_t blade_transport_wss_rpc_error_send(blade_connection_t *bc, const char *id, int32_t code, const char *message)
+{
+       ks_status_t ret = KS_STATUS_SUCCESS;
+       blade_transport_wss_t *bt_wss = NULL;
+       cJSON *json = NULL;
+
+       ks_assert(bc);
+       ks_assert(id);
+       ks_assert(message);
+
+       bt_wss = (blade_transport_wss_t *)blade_connection_transport_get(bc);
+
+       blade_rpc_error_create(blade_connection_pool_get(bc), &json, NULL, id, code, message);
+
+    if (blade_transport_wss_write(bt_wss, json) != KS_STATUS_SUCCESS) {
+               ks_log(KS_LOG_DEBUG, "Failed to write error message\n");
+               ret = KS_STATUS_FAIL;
+       }
+
+       cJSON_Delete(json);
+       return ret;
+}
+
 blade_connection_state_hook_t blade_transport_wss_on_state_disconnect(blade_connection_t *bc, blade_connection_state_condition_t condition)
 {
        blade_transport_wss_t *bt_wss = NULL;
@@ -924,10 +962,11 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_inbound(blade_
 {
        blade_connection_state_hook_t ret = BLADE_CONNECTION_STATE_HOOK_SUCCESS;
        blade_transport_wss_t *bt_wss = NULL;
+       ks_pool_t *pool = NULL;
        cJSON *json_req = NULL;
        cJSON *json_res = NULL;
-       cJSON *params = NULL;
-       cJSON *result = NULL;
+       cJSON *json_params = NULL;
+       cJSON *json_result = NULL;
        //cJSON *error = NULL;
        blade_session_t *bs = NULL;
        blade_handle_t *bh = NULL;
@@ -948,6 +987,8 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_inbound(blade_
 
        bt_wss = (blade_transport_wss_t *)blade_connection_transport_get(bc);
 
+       pool = blade_connection_pool_get(bc);
+
        // @todo very temporary, really need monotonic clock and get timeout delay and sleep delay from config
        timeout = ks_time_now() + (5 * KS_USEC_PER_SEC);
        while (blade_transport_wss_read(bt_wss, &json_req) == KS_STATUS_SUCCESS) {
@@ -958,6 +999,7 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_inbound(blade_
 
        if (!json_req) {
                ks_log(KS_LOG_DEBUG, "Failed to receive message before timeout\n");
+               blade_transport_wss_rpc_error_send(bc, NULL, -32600, "Timeout while expecting request");
                ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
                goto done;
        }
@@ -966,7 +1008,7 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_inbound(blade_
        jsonrpc = cJSON_GetObjectCstr(json_req, "jsonrpc"); // @todo check for definitions of these keys and fixed values
        if (!jsonrpc || strcmp(jsonrpc, "2.0")) {
                ks_log(KS_LOG_DEBUG, "Received message is not the expected protocol\n");
-               // @todo send error response before disconnecting, code = -32600 (invalid request)
+               blade_transport_wss_rpc_error_send(bc, NULL, -32600, "Invalid request, missing 'jsonrpc' field");
                ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
                goto done;
        }
@@ -974,7 +1016,7 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_inbound(blade_
        id = cJSON_GetObjectCstr(json_req, "id"); // @todo switch to number if we are not using a uuid for message id
        if (!id) {
                ks_log(KS_LOG_DEBUG, "Received message is missing 'id'\n");
-               // @todo send error response before disconnecting, code = -32600 (invalid request)
+               blade_transport_wss_rpc_error_send(bc, NULL, -32600, "Invalid request, missing 'id' field");
                ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
                goto done;
        }
@@ -982,14 +1024,14 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_inbound(blade_
        method = cJSON_GetObjectCstr(json_req, "method");
        if (!method || strcasecmp(method, "blade.session.attach")) {
                ks_log(KS_LOG_DEBUG, "Received message is missing 'method' or is an unexpected method\n");
-               // @todo send error response before disconnecting, code = -32601 (method not found)
+               blade_transport_wss_rpc_error_send(bc, id, -32601, "Missing or unexpected 'method' field");
                ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
                goto done;
        }
 
-       params = cJSON_GetObjectItem(json_req, "params");
-       if (params) {
-               sid = cJSON_GetObjectCstr(params, "session-id");
+       json_params = cJSON_GetObjectItem(json_req, "params");
+       if (json_params) {
+               sid = cJSON_GetObjectCstr(json_params, "session-id");
                if (sid) {
                        // @todo validate uuid format by parsing, not currently available in uuid functions, send -32602 (invalid params) if invalid
                        ks_log(KS_LOG_DEBUG, "Session (%s) requested\n", sid);
@@ -1019,7 +1061,7 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_inbound(blade_
 
                if (blade_session_startup(bs) != KS_STATUS_SUCCESS) {
                        ks_log(KS_LOG_DEBUG, "Session (%s) startup failed\n", blade_session_id_get(bs));
-                       // @todo send error response before disconnecting, code = -32603 (internal error)
+                       blade_transport_wss_rpc_error_send(bc, id, -32603, "Internal error, session could not be started");
                        blade_session_read_unlock(bs);
                        blade_session_destroy(&bs);
                        ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
@@ -1030,17 +1072,14 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_inbound(blade_
        }
 
        // @todo wrapper to generate request and response
-       json_res = cJSON_CreateObject();
-       cJSON_AddStringToObject(json_res, "jsonrpc", "2.0");
-       cJSON_AddStringToObject(json_res, "id", id);
+       blade_rpc_response_create(pool, &json_res, &json_result, id);
+       ks_assert(json_res);
 
-       result = cJSON_CreateObject();
-       cJSON_AddStringToObject(result, "session-id", blade_session_id_get(bs));
-       cJSON_AddItemToObject(json_res, "result", result);
+       cJSON_AddStringToObject(json_result, "session-id", blade_session_id_get(bs));
 
        // @todo send response
        if (blade_transport_wss_write(bt_wss, json_res) != KS_STATUS_SUCCESS) {
-               ks_log(KS_LOG_DEBUG, "Failed to write message\n");
+               ks_log(KS_LOG_DEBUG, "Failed to write response message\n");
                ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
                goto done;
        }
@@ -1064,14 +1103,14 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_outbound(blade
        blade_transport_wss_init_t *bt_wss_init = NULL;
        ks_pool_t *pool = NULL;
        cJSON *json_req = NULL;
+       cJSON *json_params = NULL;
        cJSON *json_res = NULL;
-       uuid_t msgid;
        const char *mid = NULL;
        ks_time_t timeout;
        const char *jsonrpc = NULL;
        const char *id = NULL;
-       cJSON *error = NULL;
-       cJSON *result = NULL;
+       cJSON *json_error = NULL;
+       cJSON *json_result = NULL;
        const char *sid = NULL;
        blade_session_t *bs = NULL;
 
@@ -1087,25 +1126,15 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_outbound(blade
        pool = blade_connection_pool_get(bc);
 
 
-       // @todo wrapper to build a request and response/error
-       json_req = cJSON_CreateObject();
-       cJSON_AddStringToObject(json_req, "jsonrpc", "2.0");
-       cJSON_AddStringToObject(json_req, "method", "blade.session.attach");
+       blade_rpc_request_create(pool, &json_req, &json_params, &mid, "blade.session.attach");
+       ks_assert(json_req);
 
-       ks_uuid(&msgid);
-       mid = ks_uuid_str(pool, &msgid);
-       cJSON_AddStringToObject(json_req, "id", mid);
-
-       if (bt_wss_init->session_id) {
-               cJSON *params = cJSON_CreateObject();
-               cJSON_AddStringToObject(params, "session-id", bt_wss_init->session_id);
-               cJSON_AddItemToObject(json_req, "params", params);
-       }
+       if (bt_wss_init->session_id) cJSON_AddStringToObject(json_params, "session-id", bt_wss_init->session_id);
 
        ks_log(KS_LOG_DEBUG, "Session (%s) requested\n", (bt_wss_init->session_id ? bt_wss_init->session_id : "none"));
 
        if (blade_transport_wss_write(bt_wss, json_req) != KS_STATUS_SUCCESS) {
-               ks_log(KS_LOG_DEBUG, "Failed to write message\n");
+               ks_log(KS_LOG_DEBUG, "Failed to write request message\n");
                ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
                goto done;
        }
@@ -1134,26 +1163,26 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_outbound(blade
 
        id = cJSON_GetObjectCstr(json_res, "id"); // @todo switch to number if we are not using a uuid for message id
        if (!id || strcasecmp(mid, id)) {
-               ks_log(KS_LOG_DEBUG, "Received message is missing 'id'\n");
+               ks_log(KS_LOG_DEBUG, "Received message has missing or unexpected 'id'\n");
                ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
                goto done;
        }
 
-       error = cJSON_GetObjectItem(json_res, "error");
-       if (error) {
+       json_error = cJSON_GetObjectItem(json_res, "error");
+       if (json_error) {
                ks_log(KS_LOG_DEBUG, "Error message ... add the details\n");
                ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
                goto done;
        }
 
-       result = cJSON_GetObjectItem(json_res, "result");
-       if (!result) {
+       json_result = cJSON_GetObjectItem(json_res, "result");
+       if (!json_result) {
                ks_log(KS_LOG_DEBUG, "Received message is missing 'result'\n");
                ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
                goto done;
        }
 
-       sid = cJSON_GetObjectCstr(result, "session-id");
+       sid = cJSON_GetObjectCstr(json_result, "session-id");
        if (!sid) {
                ks_log(KS_LOG_DEBUG, "Received message 'result' is missing 'session-id'\n");
                ret = BLADE_CONNECTION_STATE_HOOK_DISCONNECT;
@@ -1192,13 +1221,21 @@ blade_connection_state_hook_t blade_transport_wss_on_state_attach_outbound(blade
        blade_connection_session_set(bc, blade_session_id_get(bs));
 
  done:
-       if (mid) ks_pool_free(pool, &mid);
        if (json_req) cJSON_Delete(json_req);
        if (json_res) cJSON_Delete(json_res);
        return ret;
 }
 
-blade_connection_state_hook_t blade_transport_wss_on_state_detach(blade_connection_t *bc, blade_connection_state_condition_t condition)
+blade_connection_state_hook_t blade_transport_wss_on_state_detach_inbound(blade_connection_t *bc, blade_connection_state_condition_t condition)
+{
+       ks_assert(bc);
+
+       ks_log(KS_LOG_DEBUG, "State Callback: %d\n", (int32_t)condition);
+
+       return BLADE_CONNECTION_STATE_HOOK_SUCCESS;
+}
+
+blade_connection_state_hook_t blade_transport_wss_on_state_detach_outbound(blade_connection_t *bc, blade_connection_state_condition_t condition)
 {
        ks_assert(bc);
 
@@ -1207,7 +1244,7 @@ blade_connection_state_hook_t blade_transport_wss_on_state_detach(blade_connecti
        return BLADE_CONNECTION_STATE_HOOK_SUCCESS;
 }
 
-blade_connection_state_hook_t blade_transport_wss_on_state_ready(blade_connection_t *bc, blade_connection_state_condition_t condition)
+blade_connection_state_hook_t blade_transport_wss_on_state_ready_inbound(blade_connection_t *bc, blade_connection_state_condition_t condition)
 {
        ks_assert(bc);
 
@@ -1217,6 +1254,60 @@ blade_connection_state_hook_t blade_transport_wss_on_state_ready(blade_connectio
        return BLADE_CONNECTION_STATE_HOOK_SUCCESS;
 }
 
+blade_connection_state_hook_t blade_transport_wss_on_state_ready_outbound(blade_connection_t *bc, blade_connection_state_condition_t condition)
+{
+       ks_assert(bc);
+
+       ks_log(KS_LOG_DEBUG, "State Callback: %d\n", (int32_t)condition);
+
+       if (condition == BLADE_CONNECTION_STATE_CONDITION_PRE) {
+               blade_session_t *bs = NULL;
+               cJSON *req = NULL;
+
+               bs = blade_handle_sessions_get(blade_connection_handle_get(bc), blade_connection_session_get(bc));
+               ks_assert(bs);
+
+               blade_rpc_request_create(blade_connection_pool_get(bc), &req, NULL, NULL, "blade.test.echo");
+               blade_session_send(bs, req, blade_test_echo_response_handler);
+
+               blade_session_read_unlock(bs);
+       }
+
+       ks_sleep_ms(1000);
+       return BLADE_CONNECTION_STATE_HOOK_SUCCESS;
+}
+
+
+
+ks_bool_t blade_test_echo_request_handler(blade_request_t *breq)
+{
+       blade_session_t *bs = NULL;
+       cJSON *res = NULL;
+
+       ks_assert(breq);
+
+       ks_log(KS_LOG_DEBUG, "Request Received!\n");
+
+       bs = blade_handle_sessions_get(breq->handle, breq->session_id);
+       ks_assert(bs);
+
+       blade_rpc_response_create(breq->pool, &res, NULL, breq->message_id);
+       blade_session_send(bs, res, NULL);
+
+       blade_session_read_unlock(bs);
+
+       return KS_FALSE;
+}
+
+ks_bool_t blade_test_echo_response_handler(blade_response_t *bres)
+{
+       ks_assert(bres);
+
+       ks_log(KS_LOG_DEBUG, "Response Received!\n");
+
+       return KS_FALSE;
+}
+
 /* For Emacs:
  * Local Variables:
  * mode:c
index 830be262f0c860b15c86a4022c200c9b4d1a3d0d..092c31f23786fa4b49a5071c2273c1cd5821c5ec 100644 (file)
 
 #include "blade.h"
 
-KS_DECLARE(ks_status_t) blade_request_create(blade_request_t **breqP, blade_handle_t *bh, const char *session_id, cJSON *json)
+KS_DECLARE(ks_status_t) blade_request_create(blade_request_t **breqP,
+                                                                                        blade_handle_t *bh,
+                                                                                        const char *session_id,
+                                                                                        cJSON *json,
+                                                                                        blade_response_callback_t callback)
 {
        blade_request_t *breq = NULL;
        ks_pool_t *pool = NULL;
@@ -50,8 +54,9 @@ KS_DECLARE(ks_status_t) blade_request_create(blade_request_t **breqP, blade_hand
        breq->handle = bh;
        breq->pool = pool;
        breq->session_id = ks_pstrdup(pool, session_id);
-       breq->message = json;
+       breq->message = cJSON_Duplicate(json, 1);
        breq->message_id = cJSON_GetObjectCstr(json, "id");
+       breq->callback = callback;
 
        *breqP = breq;
 
@@ -95,7 +100,7 @@ KS_DECLARE(ks_status_t) blade_response_create(blade_response_t **bresP, blade_ha
        bres->pool = pool;
        bres->session_id = ks_pstrdup(pool, session_id);
        bres->request = breq;
-       bres->message = json;
+       bres->message = cJSON_Duplicate(json, 1);
 
        *bresP = bres;
 
@@ -120,6 +125,88 @@ KS_DECLARE(ks_status_t) blade_response_destroy(blade_response_t **bresP)
        return KS_STATUS_SUCCESS;
 }
 
+KS_DECLARE(ks_status_t) blade_rpc_request_create(ks_pool_t *pool, cJSON **json, cJSON **params, const char **id, const char *method)
+{
+       cJSON *root = NULL;
+       cJSON *p = NULL;
+       uuid_t msgid;
+       const char *mid = NULL;
+
+       ks_assert(pool);
+       ks_assert(json);
+       ks_assert(method);
+
+       root = cJSON_CreateObject();
+
+       cJSON_AddStringToObject(root, "jsonrpc", "2.0");
+
+       ks_uuid(&msgid);
+       mid = ks_uuid_str(pool, &msgid);
+       cJSON_AddStringToObject(root, "id", mid);
+       ks_pool_free(pool, &mid);
+
+       cJSON_AddStringToObject(root, "method", method);
+
+       p = cJSON_CreateObject();
+       cJSON_AddItemToObject(root, "params", p);
+
+       *json = root;
+       if (params) *params = p;
+       if (id) *id = cJSON_GetObjectCstr(root, "id");
+
+       return KS_STATUS_SUCCESS;
+}
+
+KS_DECLARE(ks_status_t) blade_rpc_response_create(ks_pool_t *pool, cJSON **json, cJSON **result, const char *id)
+{
+       cJSON *root = NULL;
+       cJSON *r = NULL;
+
+       ks_assert(pool);
+       ks_assert(json);
+       ks_assert(id);
+
+       root = cJSON_CreateObject();
+
+       cJSON_AddStringToObject(root, "jsonrpc", "2.0");
+
+       cJSON_AddStringToObject(root, "id", id);
+
+       r = cJSON_CreateObject();
+       cJSON_AddItemToObject(root, "result", r);
+
+       *json = root;
+       if (result) *result = r;
+
+       return KS_STATUS_SUCCESS;
+}
+
+KS_DECLARE(ks_status_t) blade_rpc_error_create(ks_pool_t *pool, cJSON **json, cJSON **error, const char *id, int32_t code, const char *message)
+{
+       cJSON *root = NULL;
+       cJSON *e = NULL;
+
+       ks_assert(pool);
+       ks_assert(json);
+       ks_assert(id);
+       ks_assert(message);
+
+       root = cJSON_CreateObject();
+
+       cJSON_AddStringToObject(root, "jsonrpc", "2.0");
+
+       cJSON_AddStringToObject(root, "id", id);
+
+       e = cJSON_CreateObject();
+       cJSON_AddNumberToObject(e, "code", code);
+       cJSON_AddStringToObject(e, "message", message);
+       cJSON_AddItemToObject(root, "error", e);
+
+       *json = root;
+       if (error) *error = e;
+
+       return KS_STATUS_SUCCESS;
+}
 
 /* For Emacs:
  * Local Variables:
diff --git a/libs/libblade/src/blade_rpcproto.c b/libs/libblade/src/blade_rpcproto.c
deleted file mode 100644 (file)
index bedfd1c..0000000
+++ /dev/null
@@ -1,1178 +0,0 @@
-/*
- * Copyright (c) 2017 FreeSWITCH Solutions LLC
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * * Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * * Neither the name of the original author; nor the names of any contributors
- * may be used to endorse or promote products derived from this software
- * without specific prior written permission.
- *
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER
- * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
- * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
- * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#pragma GCC optimize ("O0")
-
-#include <blade_rpcproto.h>
-
-/* 
- * internal shared structure grounded in global 
- */
-typedef struct blade_rpc_handle_ex {
-
-    ks_hash_t  *namespace_hash;      /* hash to namespace methods */
-       ks_hash_t  *template_hash;               /* hash to template methods */
-
-    ks_hash_t  *peer_hash;           /* hash to peer structure */
-       
-       ks_q_t     *event_queue;
-       ks_bool_t   isactive;
-       ks_pool_t  *pool; 
-
-} blade_rpc_handle_ex_t;
-
-
-typedef struct blade_rpc_namespace_s {
-
-       char       name[KS_RPCMESSAGE_NAMESPACE_LENGTH+1];
-       char       version[KS_RPCMESSAGE_VERSION_LENGTH+1];   /* nnn.nn.nn */
-    ks_hash_t *method_hash;      /* hash to namespace methods */
-
-} blade_rpc_namespace_t;
-
-
-
-
-blade_rpc_handle_ex_t *g_handle = NULL;
-
-
-/*
- * callbacks - from blade_rpc_handle_ex->method_hash
- */
-
-typedef struct blade_rpc_custom_callbackpair_s
-{
-    jrpc_func_t  prefix_request_func;
-    jrpc_func_t  postfix_request_func;
-
-    jrpc_func_t  prefix_response_func;
-    jrpc_func_t  postfix_response_func;
-
-} blade_rpc_custom_callbackpair_t;
-
-
-
-typedef struct blade_rpc_callbackpair_s
-{
-    jrpc_func_t         request_func;
-
-    jrpc_func_t         response_func;
-
-       blade_rpc_custom_callbackpair_t* custom;
-
-       ks_mutex_t               *lock; 
-
-    uint16_t         command_length;
-    char             command[1];
-
-} blade_rpc_callbackpair_t;
-
-
-
-
-
-static void blade_rpc_make_fqcommand(const char* namespace, const char *command, char *fscommand)
-{
-    memset(fscommand, 0, KS_RPCMESSAGE_FQCOMMAND_LENGTH);
-       sprintf(fscommand, "%s.%s", namespace, command);
-
-       return;
-}
-
-static void blade_rpc_parse_fqcommand(const char* fscommand, char *namespace, char *command)
-{
-    memset(command, 0, KS_RPCMESSAGE_COMMAND_LENGTH);
-    memset(namespace, 0, KS_RPCMESSAGE_NAMESPACE_LENGTH);
-
-       uint32_t len = strlen(fscommand);
-
-       assert(len <=  KS_RPCMESSAGE_FQCOMMAND_LENGTH); 
-       ks_bool_t dotfound = KS_FALSE;
-
-       for(int i=0, x=0; i<len; ++i, ++x)  {
-
-               if (fscommand[i] == '.' && dotfound == KS_FALSE) {
-                       dotfound = KS_TRUE;
-                       x = -1;
-               }
-               else if (dotfound == KS_FALSE) {
-                       namespace[x] = fscommand[i];    
-               }
-               else {
-                       command[x] = fscommand[i];
-               }
-
-       }
-
-       return;
-}
-
-
-KS_DECLARE(ks_status_t) blade_rpc_init(ks_pool_t *pool)
-{
-       if (g_handle == NULL) {
-               g_handle = ks_pool_alloc(pool, sizeof(blade_rpc_handle_ex_t));
-           ks_hash_create(&g_handle->namespace_hash,
-                    KS_HASH_MODE_CASE_SENSITIVE,
-                    KS_HASH_FLAG_RWLOCK + KS_HASH_FLAG_DUP_CHECK,       // + KS_HASH_FLAG_FREE_VALUE,
-                    pool);
-
-        ks_hash_create(&g_handle->template_hash,
-                    KS_HASH_MODE_CASE_SENSITIVE,
-                    KS_HASH_FLAG_RWLOCK + KS_HASH_FLAG_DUP_CHECK,       // + KS_HASH_FLAG_FREE_VALUE,
-                    pool);
-                                       
-               ks_q_create(&g_handle->event_queue, pool, 1024);        
-
-               g_handle->pool = pool;
-
-               /* initialize rpc messaging mechanism */
-               ks_rpcmessage_init(pool);
-
-               g_handle->isactive = KS_TRUE;
-       }       
-       return KS_STATUS_SUCCESS;
-}
-
-
-//KS_DECLARE(ks_status_t) blade_rpc_onconnect(ks_pool_t *pool, blade_peer_t* peer)
-//{
-//
-//
-//     return KS_STATUS_FAIL;
-//}
-//
-//KS_DECLARE(ks_status_t) blade_rpc_disconnect(blade_peer_t* peer)
-//{
-//
-//     return KS_STATUS_FAIL;
-//}
-
-
-
-/*
- * namespace setup
- */
-
-/*
- *  function/callback functions
- */
-static blade_rpc_callbackpair_t *blade_rpc_find_callbacks_locked(char *namespace, char *command)
-{
-       blade_rpc_callbackpair_t *callbacks = NULL;
-
-    blade_rpc_namespace_t *n =  ks_hash_search(g_handle->namespace_hash, namespace, KS_UNLOCKED);
-       if (n) {
-
-               ks_hash_read_lock(n->method_hash);
-
-        callbacks = ks_hash_search(n->method_hash, command, KS_UNLOCKED);
-
-               if (callbacks) {
-                       ks_mutex_lock(callbacks->lock);
-               }
-
-               ks_hash_read_unlock(n->method_hash);
-       }
-
-    return callbacks;
-}
-
-static blade_rpc_callbackpair_t *blade_rpc_find_template_locked(char *name, char *command)
-{
-    blade_rpc_callbackpair_t *callbacks = NULL;
-
-    blade_rpc_namespace_t *n =  ks_hash_search(g_handle->template_hash, name, KS_UNLOCKED);
-    if (n) {
-
-        ks_hash_read_lock(n->method_hash);
-        callbacks = ks_hash_search(n->method_hash, command, KS_UNLOCKED);
-
-               if (callbacks) {
-                       ks_mutex_lock(callbacks->lock);
-               }
-
-        ks_hash_read_unlock(n->method_hash);
-    }
-
-    return callbacks;
-}
-
-
-
-
-static blade_rpc_callbackpair_t *blade_rpc_find_callbacks_locked_fq(char *fqcommand)
-{
-    blade_rpc_callbackpair_t *callbacks = NULL;
-
-       char command[KS_RPCMESSAGE_COMMAND_LENGTH+1];
-    char namespace[KS_RPCMESSAGE_NAMESPACE_LENGTH+1];
-
-       blade_rpc_parse_fqcommand(fqcommand, namespace, command);
-
-    blade_rpc_namespace_t *n =  ks_hash_search(g_handle->namespace_hash, namespace, KS_UNLOCKED);
-    if (n) {
-        blade_rpc_make_fqcommand(namespace, command, fqcommand);
-               ks_hash_read_lock(n->method_hash);
-
-        callbacks = ks_hash_search(n->method_hash, fqcommand, KS_UNLOCKED);
-
-               if (callbacks) {
-                       ks_mutex_lock(callbacks->lock);
-               }
-
-               ks_hash_read_unlock(n->method_hash);
-    }
-
-    return callbacks;
-}
-
-
-KS_DECLARE(jrpc_func_t) blade_rpc_find_request_function(char *fqcommand)
-{
-
-    blade_rpc_callbackpair_t* callbacks = blade_rpc_find_callbacks_locked_fq(fqcommand);
-
-    if (!callbacks) {
-        return NULL;
-    }
-
-    jrpc_func_t f = callbacks->request_func;
-
-    ks_mutex_unlock(callbacks->lock);
-
-    return f;
-}
-
-KS_DECLARE(jrpc_func_t) blade_rpc_find_requestprefix_function(char *fqcommand)
-{
-
-    blade_rpc_callbackpair_t* callbacks = blade_rpc_find_callbacks_locked_fq(fqcommand);
-
-    if (!callbacks || !callbacks->custom) {
-        return NULL;
-    }
-
-    jrpc_func_t f = callbacks->custom->prefix_request_func;
-
-    ks_mutex_unlock(callbacks->lock);
-
-    return f;
-}
-
-KS_DECLARE(jrpc_func_t) blade_rpc_find_response_function(char *fqcommand)
-{
-
-    blade_rpc_callbackpair_t* callbacks = blade_rpc_find_callbacks_locked_fq(fqcommand);
-
-       if (!callbacks) {
-               return NULL;
-       }
-               
-    jrpc_func_t f = callbacks->response_func;
-
-       ks_mutex_unlock(callbacks->lock);
-
-       return f;
-}
-
-KS_DECLARE(jrpc_func_t) blade_rpc_find_responseprefix_function(char *fqcommand)
-{
-
-    blade_rpc_callbackpair_t* callbacks = blade_rpc_find_callbacks_locked_fq(fqcommand);
-
-    if (!callbacks || !callbacks->custom) {
-        return NULL;
-    }
-
-    jrpc_func_t f = callbacks->custom->prefix_response_func;
-
-    ks_mutex_unlock(callbacks->lock);
-
-    return f;
-}
-
-
-KS_DECLARE(ks_status_t) blade_rpc_declare_namespace(char* namespace, const char* version)
-{
-
-       /* find/insert to namespace hash as needed */
-       ks_hash_write_lock(g_handle->namespace_hash);
-       blade_rpc_namespace_t *n =  ks_hash_search(g_handle->namespace_hash, namespace, KS_UNLOCKED);
-       if (n == NULL) {
-               n = ks_pool_alloc(g_handle->pool, sizeof (blade_rpc_namespace_t) + strlen(namespace) + 1);
-               strncpy(n->name, namespace, KS_RPCMESSAGE_NAMESPACE_LENGTH);
-               strncpy(n->version, version, KS_RPCMESSAGE_VERSION_LENGTH);
-               ks_hash_create(&n->method_hash,
-                                       KS_HASH_MODE_CASE_SENSITIVE,
-                                       KS_HASH_FLAG_RWLOCK + KS_HASH_FLAG_DUP_CHECK + KS_HASH_FLAG_FREE_VALUE,
-                                       g_handle->pool);
-               ks_hash_insert(g_handle->namespace_hash, n->name, n);
-       }
-       ks_hash_write_unlock(g_handle->namespace_hash);
-
-    ks_log(KS_LOG_DEBUG, "Setting message namespace value %s, version %s\n", namespace, version);
-
-    return KS_STATUS_SUCCESS;
-}
-
-
-KS_DECLARE(ks_status_t)blade_rpc_register_function(char *namespace, 
-                                                char *command,
-                                                jrpc_func_t func,
-                                                jrpc_func_t respfunc)
-{
-    if (!func && !respfunc) {
-        return KS_STATUS_FAIL;
-    }
-
-       char nskey[KS_RPCMESSAGE_NAMESPACE_LENGTH+1];
-       memset(nskey, 0, sizeof(nskey));
-       strcpy(nskey, namespace);
-
-    char fqcommand[KS_RPCMESSAGE_FQCOMMAND_LENGTH];
-    memset(fqcommand, 0, sizeof(fqcommand));
-
-//    strcpy(fqcommand, namespace);
-//    strcpy(fqcommand, ".");
-    strcat(fqcommand, command);
-
-    int lkey = strlen(command)+1;
-
-    if (lkey < 16) {
-        lkey = 16;
-    }
-
-    ks_hash_read_lock(g_handle->namespace_hash);    /* lock namespace hash */
-
-    blade_rpc_namespace_t *n =  ks_hash_search(g_handle->namespace_hash, nskey, KS_UNLOCKED);
-
-    if (n == NULL) {
-        ks_hash_read_unlock(g_handle->namespace_hash);
-        ks_log(KS_LOG_ERROR, "Unable to find %s namespace\n", namespace);
-        return KS_STATUS_FAIL;
-    }
-
-       blade_rpc_callbackpair_t* callbacks = blade_rpc_find_callbacks_locked(nskey, command);
-
-       /* just ignore attempt to re register callbacks */
-       /* @todo :  should this be smarter, allow override ? */
-       if (callbacks != NULL) {
-               ks_mutex_unlock(callbacks->lock);
-        ks_hash_read_unlock(g_handle->namespace_hash);
-        ks_log(KS_LOG_ERROR, "Callbacks already registered for %s namespace\n", namespace);
-        return KS_STATUS_FAIL;
-       }
-
-    callbacks =
-            (blade_rpc_callbackpair_t*)ks_pool_alloc(g_handle->pool, lkey + sizeof(blade_rpc_callbackpair_t));
-
-    strcpy(callbacks->command, command);
-    callbacks->command_length = lkey;
-    callbacks->request_func   = func;
-    callbacks->response_func  = respfunc;
-       ks_mutex_create(&callbacks->lock, KS_MUTEX_FLAG_DEFAULT, g_handle->pool);
-
-    ks_hash_write_lock(n->method_hash);             /* lock method hash */
-
-    ks_hash_insert(n->method_hash, callbacks->command, (void *) callbacks);
-
-    ks_hash_write_unlock(n->method_hash);           /* unlock method hash */
-       ks_hash_read_unlock(g_handle->namespace_hash);  /* unlock namespace hash */
-
-    ks_log(KS_LOG_DEBUG, "Message %s %s registered\n", namespace, command);
-
-    return KS_STATUS_SUCCESS;
-
-}
-
-
-KS_DECLARE(ks_status_t)blade_rpc_register_custom_request_function(char *namespace, 
-                                                                                                       char *command,
-                                                                                                       jrpc_func_t prefix_func,
-                                                                                                       jrpc_func_t postfix_func)
-{
-       ks_status_t s = KS_STATUS_FAIL;
-
-    char fqcommand[KS_RPCMESSAGE_FQCOMMAND_LENGTH];
-    memset(fqcommand, 0, sizeof(fqcommand));
-    strcat(fqcommand, command);
-
-    ks_hash_write_lock(g_handle->namespace_hash);
-       blade_rpc_callbackpair_t* callbacks = blade_rpc_find_callbacks_locked(namespace, fqcommand);
-
-    if (callbacks) {
-
-               if (!callbacks->custom) {
-                       callbacks->custom = 
-                               (blade_rpc_custom_callbackpair_t *)ks_pool_alloc(g_handle->pool, sizeof(blade_rpc_custom_callbackpair_t));
-               }
-
-               callbacks->custom->prefix_request_func  = prefix_func;
-               callbacks->custom->postfix_request_func = postfix_func;
-               ks_mutex_unlock(callbacks->lock);
-               s = KS_STATUS_SUCCESS;
-       }
-
-       ks_hash_write_unlock(g_handle->namespace_hash);
-       return  s;
-}
-
-KS_DECLARE(ks_status_t)blade_rpc_register_custom_response_function(char* namespace, 
-                                                                                                       char *command,
-                                                                                                       jrpc_func_t prefix_func,
-                                                                                                       jrpc_func_t postfix_func)
-{
-       ks_status_t s = KS_STATUS_FAIL;
-
-    char fqcommand[KS_RPCMESSAGE_FQCOMMAND_LENGTH];
-    memset(fqcommand, 0, sizeof(fqcommand));
-    strcat(fqcommand, command);
-       
-       ks_hash_write_lock(g_handle->namespace_hash);
-    blade_rpc_callbackpair_t *callbacks = blade_rpc_find_callbacks_locked(namespace, fqcommand);
-
-    if (callbacks) {
-
-               if (!callbacks->custom) {
-                       callbacks->custom = 
-                               (blade_rpc_custom_callbackpair_t *)ks_pool_alloc(g_handle->pool, sizeof(blade_rpc_custom_callbackpair_t));
-               }
-
-        callbacks->custom->prefix_response_func  = prefix_func;
-        callbacks->custom->postfix_response_func = postfix_func;
-               ks_mutex_unlock(callbacks->lock);
-        s = KS_STATUS_SUCCESS;
-    }
-
-    ks_hash_write_unlock(g_handle->namespace_hash);
-    return  s;
-}
-
-KS_DECLARE(void) blade_rpc_remove_namespace(char* namespace)
-{
-    char nskey[KS_RPCMESSAGE_NAMESPACE_LENGTH];
-    memset(nskey, 0, sizeof(nskey));
-    strcat(nskey, namespace);
-
-    ks_hash_write_lock(g_handle->namespace_hash);
-
-       blade_rpc_namespace_t *n =  ks_hash_search(g_handle->namespace_hash, nskey, KS_UNLOCKED);
-
-       ks_hash_iterator_t* it = ks_hash_first(n->method_hash, KS_HASH_FLAG_RWLOCK);
-
-       while (it) {
-
-               const void *key; 
-               void *value;
-               ks_ssize_t len = strlen(key);
-
-               ks_hash_this(it, &key, &len, &value);
-               blade_rpc_callbackpair_t *callbacks = (blade_rpc_callbackpair_t *)value;
-
-               ks_mutex_lock(callbacks->lock);
-
-               if (callbacks->custom) {
-                       ks_pool_free(g_handle->pool, callbacks->custom);
-               }
-
-               it = ks_hash_next(&it);
-               ks_hash_remove(n->method_hash, (void *)key);
-       }               
-
-       ks_hash_write_unlock(g_handle->namespace_hash);
-
-       return;
-}
-
-
-/*
- * template functions
- *
- */
-
-KS_DECLARE(ks_status_t) blade_rpc_declare_template(char* templatename, const char* version)
-{
-    char nskey[KS_RPCMESSAGE_NAMESPACE_LENGTH];
-    memset(nskey, 0, sizeof(nskey));
-    strcat(nskey, templatename);
-
-
-    /* find/insert to namespace hash as needed */
-    ks_hash_write_lock(g_handle->template_hash);
-    blade_rpc_namespace_t *n =  ks_hash_search(g_handle->template_hash, nskey, KS_UNLOCKED);
-
-    if (n == NULL) {
-        n = ks_pool_alloc(g_handle->pool, sizeof (blade_rpc_namespace_t) + strlen(templatename) + 1);
-        strncpy(n->name, templatename, KS_RPCMESSAGE_NAMESPACE_LENGTH);
-               strncpy(n->version, version, KS_RPCMESSAGE_VERSION_LENGTH);
-               ks_hash_create(&n->method_hash,
-                                       KS_HASH_MODE_CASE_SENSITIVE,
-                    KS_HASH_FLAG_RWLOCK + KS_HASH_FLAG_DUP_CHECK + KS_HASH_FLAG_FREE_VALUE,
-                    g_handle->pool);
-        ks_hash_insert(g_handle->template_hash, n->name, n);
-    }
-    ks_hash_write_unlock(g_handle->template_hash);
-
-    ks_log(KS_LOG_DEBUG, "Declaring application template namespace %s, version %s\n", templatename, version);
-
-    return KS_STATUS_SUCCESS;
-}
-
-KS_DECLARE(ks_status_t)blade_rpc_register_template_function(char *name,
-                                                char *command,
-                                                jrpc_func_t func,
-                                                jrpc_func_t respfunc)
-{
-       (void)blade_rpc_find_template_locked;   //remove
-
-    if (!func && !respfunc) {
-        return KS_STATUS_FAIL;
-    }
-
-    char nskey[KS_RPCMESSAGE_NAMESPACE_LENGTH];
-    memset(nskey, 0, sizeof(nskey));
-    strcat(nskey, name);
-
-    char fqcommand[KS_RPCMESSAGE_FQCOMMAND_LENGTH];
-    memset(fqcommand, 0, sizeof(fqcommand));
-    strcat(fqcommand, command);
-
-    int lkey = strlen(fqcommand)+1;
-
-    if (lkey < 16) {
-        lkey = 16;
-    }
-
-    ks_hash_read_lock(g_handle->template_hash);    /* lock template hash */
-
-    blade_rpc_namespace_t *n =  ks_hash_search(g_handle->template_hash, nskey, KS_UNLOCKED);
-
-    if (n == NULL) {
-        ks_hash_read_unlock(g_handle->template_hash);
-        ks_log(KS_LOG_ERROR, "Unable to find %s template\n", name);
-        return KS_STATUS_FAIL;
-    }
-
-       ks_hash_read_lock(n->method_hash);
-    blade_rpc_callbackpair_t* callbacks = ks_hash_search(n->method_hash, fqcommand, KS_UNLOCKED);
-    ks_hash_read_unlock(n->method_hash);
-
-    /* just ignore attempt to re register callbacks */
-    /* as the template may already be in use leading to confusion */
-
-    if (callbacks != NULL) {
-        ks_mutex_unlock(callbacks->lock);
-        ks_hash_read_unlock(g_handle->template_hash);
-        ks_log(KS_LOG_ERROR, "Callbacks already registered for %s template\n", name);
-        return KS_STATUS_FAIL;
-    }
-
-    callbacks =
-            (blade_rpc_callbackpair_t*)ks_pool_alloc(g_handle->pool, lkey + sizeof(blade_rpc_callbackpair_t));
-
-    strcpy(callbacks->command, command);
-    callbacks->command_length = lkey;
-    callbacks->request_func   = func;
-    callbacks->response_func  = respfunc;
-
-    ks_mutex_create(&callbacks->lock, KS_MUTEX_FLAG_DEFAULT, g_handle->pool);
-
-    ks_hash_write_lock(n->method_hash);             /* lock method hash */
-
-    ks_hash_insert(n->method_hash, callbacks->command, (void *) callbacks);
-
-    ks_hash_write_unlock(n->method_hash);           /* unlock method hash */
-    ks_hash_read_unlock(g_handle->template_hash);  /* unlock namespace hash */
-
-    ks_log(KS_LOG_DEBUG, "Template message %s %s registered\n", name, command);
-
-    return KS_STATUS_SUCCESS;
-
-}
-
-KS_DECLARE(ks_status_t)blade_rpc_inherit_template(char *namespace, char* template)
-{
-       ks_hash_read_lock(g_handle->template_hash);
-
-       char tkey[KS_RPCMESSAGE_NAMESPACE_LENGTH+1];
-       memset(tkey, 0, sizeof(tkey));
-       strcpy(tkey, template);
-
-    char nskey[KS_RPCMESSAGE_NAMESPACE_LENGTH+1];
-    memset(nskey, 0, sizeof(tkey));
-    strcpy(nskey, namespace);
-
-       blade_rpc_namespace_t *n =  ks_hash_search(g_handle->template_hash, tkey, KS_UNLOCKED);
-
-       if (!n) {
-               ks_hash_read_unlock(g_handle->template_hash);
-               ks_log(KS_LOG_ERROR, "Unable to locate template %s\n", template);
-               return KS_STATUS_FAIL;
-       }
-
-       ks_hash_read_lock(g_handle->namespace_hash);
-
-       blade_rpc_namespace_t *ns =  ks_hash_search(g_handle->namespace_hash, nskey, KS_UNLOCKED);
-
-    if (!ns) {
-        ks_hash_read_unlock(g_handle->template_hash);
-               ks_hash_read_unlock(g_handle->namespace_hash);
-        ks_log(KS_LOG_ERROR, "Unable to locate namespace %s\n", namespace);
-        return KS_STATUS_FAIL;
-    }
-
-       ks_hash_write_lock(ns->method_hash);
-
-    ks_hash_iterator_t* it = ks_hash_first(n->method_hash, KS_HASH_FLAG_RWLOCK);
-
-       while (it) {
-
-        const void *key;
-        void *value;
-        ks_ssize_t len = strlen(key);
-
-        ks_hash_this(it, &key, &len, &value);
-        blade_rpc_callbackpair_t *t_callback = (blade_rpc_callbackpair_t *)value;
-
-        ks_mutex_lock(t_callback->lock);
-
-               int lkey = t_callback->command_length;
-
-               blade_rpc_callbackpair_t *callbacks =
-                               (blade_rpc_callbackpair_t*)ks_pool_alloc(g_handle->pool, lkey + sizeof(blade_rpc_callbackpair_t));
-
-               strcat(callbacks->command, template);
-               strcat(callbacks->command, ".");
-               strcat(callbacks->command, t_callback->command);
-               
-               callbacks->command_length = lkey;
-               callbacks->request_func   = t_callback->request_func;
-               callbacks->response_func  = t_callback->response_func;
-               ks_mutex_create(&callbacks->lock, KS_MUTEX_FLAG_DEFAULT, g_handle->pool);
-
-               ks_hash_insert(ns->method_hash, callbacks->command, (void *) callbacks);                
-
-               ks_mutex_unlock(t_callback->lock);
-
-               it = ks_hash_next(&it);
-       }
-       
-
-       ks_hash_write_lock(ns->method_hash);
-
-       ks_hash_read_unlock(g_handle->namespace_hash);
-       ks_hash_read_unlock(g_handle->template_hash);
-
-       return KS_STATUS_SUCCESS;
-}
-               
-
-/*
- * create a request message
- */
-KS_DECLARE(ks_rpcmessageid_t) blade_rpc_create_request(char *namespace,
-                                                    char *method,
-                                                    blade_rpc_fields_t* fields,
-                                                    cJSON **paramsP,
-                                                    cJSON **requestP)
-{
-       cJSON *jversion = NULL;
-       blade_rpc_callbackpair_t* callbacks = NULL;
-
-       *requestP = NULL;
-
-    ks_hash_read_lock(g_handle->namespace_hash);
-    blade_rpc_namespace_t *n =  ks_hash_search(g_handle->namespace_hash, namespace, KS_UNLOCKED);
-
-       if (n) {
-               ks_hash_read_lock(n->method_hash);
-               callbacks = ks_hash_search(n->method_hash, method, KS_UNLOCKED);                                
-               if (callbacks) {
-                       jversion = cJSON_CreateString(n->version);
-               }
-               ks_hash_read_unlock(n->method_hash);
-       }
-
-       ks_hash_read_unlock(g_handle->namespace_hash);
-
-       if (!n) {
-               ks_log(KS_LOG_ERROR, "No namespace %s found\n", namespace);
-               return 0;
-       }       
-
-       if (!callbacks) {
-        ks_log(KS_LOG_ERROR, "No method %s.%s found\n", namespace, method);
-        return 0;
-       }
-
-       ks_rpcmessageid_t msgid = ks_rpcmessage_create_request(namespace, method, paramsP, requestP);
-       
-       if (!msgid || *requestP == NULL) {
-               ks_log(KS_LOG_ERROR, "Unable to create rpc message for method %s.%s\n", namespace, method);
-               return 0;               
-       }
-  
-       cJSON *jfields = cJSON_CreateObject();
-
-       cJSON_AddItemToObject(jfields, "version", jversion);
-
-       if (fields->to) {
-               cJSON_AddStringToObject(jfields, "to", fields->to);
-       }
-
-       if (fields->from) {
-               cJSON_AddStringToObject(jfields, "from", fields->from);
-       }
-
-    if (fields->token) {
-        cJSON_AddStringToObject(jfields, "token", fields->token);
-    }
-
-        cJSON_AddItemToObject(*requestP, "blade", jfields);
-
-       return msgid;
-}
-
-KS_DECLARE(ks_rpcmessageid_t) blade_rpc_create_response(cJSON *request,
-                                                    cJSON **replyP,
-                                                    cJSON **responseP)
-{
-       cJSON *jfields = cJSON_GetObjectItem(request, "blade");
-
-       if (!jfields) {
-               ks_log(KS_LOG_ERROR, "No blade routing info found.  Unable to create response\n");
-               return 0;       
-       }
-
-       ks_rpcmessageid_t msgid = ks_rpcmessage_create_response(request, replyP, responseP);
-
-       if (!msgid || *responseP == NULL) {
-               ks_log(KS_LOG_ERROR, "Unable to create rpc response message\n");  //TODO : Add namespace, method from request 
-               return 0;
-       }
-
-       const char *to =    cJSON_GetObjectCstr(jfields, "to");
-       const char *from =  cJSON_GetObjectCstr(jfields, "from");
-       const char *token = cJSON_GetObjectCstr(jfields, "token");
-       const char *version =  cJSON_GetObjectCstr(jfields, "version");
-
-       cJSON *blade = cJSON_CreateObject(); 
-
-       if (to) {
-        cJSON_AddStringToObject(blade, "to", from);
-    }
-
-       if (from) {
-               cJSON_AddStringToObject(blade, "from", to);
-       }
-
-       if (token) {
-               cJSON_AddStringToObject(blade, "token", token);
-       }
-
-    if (version) {
-        cJSON_AddStringToObject(blade, "version", version);
-    }
-
-       cJSON_AddItemToObject(*responseP, "blade", blade);
-
-       return msgid;
-}
-
-KS_DECLARE(ks_rpcmessageid_t) blade_rpc_create_errorresponse(cJSON *request,
-                                                    cJSON **errorP,
-                                                    cJSON **responseP)
-{
-       ks_rpcmessageid_t msgid = blade_rpc_create_response(request, NULL, responseP);
-
-       if (msgid) {
-
-               if      (errorP) {
-
-                       if (*errorP) {
-                               cJSON_AddItemToObject(*responseP, "error", *errorP);
-                       }
-                       else {
-                               cJSON *error = cJSON_CreateObject();
-                               cJSON_AddItemToObject(*responseP, "error", error);
-                               *errorP = error;
-                       }
-               }       
-       }       
-       
-       return msgid;   
-}
-
-
-const char BLADE_JRPC_METHOD[] = "method";
-const char BLADE_JRPC_ID[]     = "id";
-const char BLADE_JRPC_FIELDS[] = "blade";
-const char BLADE_JRPC_TO[]     = "to";
-const char BLADE_JRPC_FROM[]   = "from";
-const char BLADE_JRPC_TOKEN[]  = "token";
-const char BLADE_JRPC_VERSION[] = "version";
-
-KS_DECLARE(ks_status_t) blade_rpc_parse_message(cJSON *message,
-                                                                                                       char **namespaceP,
-                                                                                                       char **methodP,
-                                                                                                       char **versionP,
-                                                                                                       uint32_t *idP,
-                                                                                                       blade_rpc_fields_t **fieldsP)
-{
-       const char *m = cJSON_GetObjectCstr(message, BLADE_JRPC_METHOD);
-       cJSON *blade  = cJSON_GetObjectItem(message, BLADE_JRPC_FIELDS);
-       cJSON *jid    = cJSON_GetObjectItem(message, BLADE_JRPC_ID);
-
-       *fieldsP    = NULL;
-       *namespaceP = NULL;
-       *versionP   = NULL;
-       *methodP    = NULL;
-       *idP        = 0;
-
-       if (jid) {
-               *idP = jid->valueint; 
-       }
-
-       if (!m || !blade) {
-               const char *buffer = cJSON_PrintUnformatted(message);
-               ks_log(KS_LOG_ERROR, "Unable to locate necessary fields in message:\n%s\n", buffer);
-               ks_pool_free(g_handle->pool, buffer);
-               return KS_STATUS_FAIL;  
-       }
-
-    cJSON *jto    = cJSON_GetObjectItem(blade, BLADE_JRPC_TO);
-    cJSON *jfrom  = cJSON_GetObjectItem(blade, BLADE_JRPC_FROM);
-    cJSON *jtoken = cJSON_GetObjectItem(blade, BLADE_JRPC_TOKEN);
-
-
-       ks_size_t len = KS_RPCMESSAGE_COMMAND_LENGTH   + 1 + 
-                                       KS_RPCMESSAGE_NAMESPACE_LENGTH + 1 +
-                                       KS_RPCMESSAGE_VERSION_LENGTH   + 1 +
-                                       sizeof(blade_rpc_fields_t) + 1;
-
-       uint32_t lento = 0;
-       uint32_t lenfrom = 0;
-       uint32_t lentoken = 0;
-
-       if (jto) {
-               lento = strlen(jto->valuestring) + 1;
-               len += lento;
-       }
-
-       if (jfrom) {
-               lenfrom += strlen(jfrom->valuestring) + 1;
-               len += lenfrom;
-       }
-
-       if (jtoken) {
-               lentoken += strlen(jtoken->valuestring) + 1;
-               len += lentoken;
-       }
-
-       blade_rpc_fields_t *fields =  (blade_rpc_fields_t *)ks_pool_alloc(g_handle->pool, len);
-
-    char *namespace = (char*)fields + sizeof(blade_rpc_fields_t);
-    char *command   = namespace + KS_RPCMESSAGE_NAMESPACE_LENGTH + 1;
-    char *version   = command + KS_RPCMESSAGE_COMMAND_LENGTH + 1;
-       
-       char *ptr = version + KS_RPCMESSAGE_VERSION_LENGTH + 1;
-
-       if (jto) {
-               strcpy(ptr, jto->valuestring);
-               fields->to = ptr;
-               ptr += strlen(jto->valuestring) + 1;
-       }
-
-       if (jfrom) {
-               strcpy(ptr, jfrom->valuestring);
-               fields->from = ptr;
-               ptr += strlen(jfrom->valuestring) + 1;
-       }
-
-       if (jtoken) {
-               strcpy(ptr, jtoken->valuestring);
-               fields->token = ptr;
-               ptr += strlen(jtoken->valuestring) + 1;
-    }
-
-    blade_rpc_parse_fqcommand(m, namespace, command);
-       
-       strcpy(version, cJSON_GetObjectCstr(blade, BLADE_JRPC_VERSION));
-
-       *fieldsP    = fields;   
-       *namespaceP = namespace;
-       *methodP    = command;
-       *versionP   = version;
-
-       return KS_STATUS_SUCCESS;
-}
-
-
-/*
- * send message
- * ------------
- */
-
-KS_DECLARE(ks_status_t) blade_rpc_write_data(char *sessionid, char* data, uint32_t size)
-{
-
-       ks_status_t s = KS_STATUS_FAIL;
-
-    // convert to json
-       cJSON *msg = cJSON_Parse(data);
-
-       if (msg) {
-
-               // ks_status_t blade_peer_message_push(blade_peer_t *peer, void *data, int32_t data_length);
-
-               s = KS_STATUS_SUCCESS;
-       }
-       else {
-               ks_log(KS_LOG_ERROR, "Unable to format outbound message\n");
-       }
-       
-
-    // ks_rpc_write_json
-       // ks_status_t blade_peer_message_push(blade_peer_t *peer, void *data, int32_t data_length);
-       return s;
-}
-
-
-KS_DECLARE(ks_status_t) blade_rpc_write_json(cJSON* json)
-{
-    // just push the messages onto the communication manager
-    // synchronization etc, taken care of by the transport api'
-       char *data = cJSON_PrintUnformatted(json);
-       if (data) {
-               ks_log(KS_LOG_DEBUG, "%s\n", data);
-           //return blade_rpc_write_data(sessionid, data, strlen(data));
-               return KS_STATUS_SUCCESS;
-       }
-       ks_log(KS_LOG_ERROR, "Unable to parse json\n");
-       return KS_STATUS_FAIL;
-}
-
-
-
-
-/*
- * Transport layer callbacks follow below
- *
-*/
-
-
-
-
-/*
- * rpc message processing
- */
-static ks_status_t blade_rpc_process_jsonmessage_all(cJSON *request)
-{
-       const char *fqcommand = cJSON_GetObjectCstr(request, "method");
-       cJSON *error = NULL;
-       cJSON *response = NULL;
-       cJSON *responseP = NULL;
-
-       if (!fqcommand) {
-               error = cJSON_CreateObject();
-               cJSON_AddStringToObject(error, "errormessage", "Command not specified");
-        ks_rpcmessage_create_request("rpcprotocol", "unknowncommand", &error, &responseP);
-               blade_rpc_write_json(responseP);
-        return KS_STATUS_FAIL;
-       }
-
-
-       char namespace[KS_RPCMESSAGE_NAMESPACE_LENGTH];
-       char command[KS_RPCMESSAGE_COMMAND_LENGTH];
-
-    blade_rpc_parse_fqcommand(fqcommand, namespace, command);
-    blade_rpc_callbackpair_t* callbacks = blade_rpc_find_callbacks_locked(namespace, command);
-
-    if (!callbacks) {
-               error = cJSON_CreateObject();
-               cJSON_AddStringToObject(error, "errormessage", "Command not supported");
-        ks_rpcmessage_create_response(request, &error, &responseP);
-           blade_rpc_write_json(responseP);
-        return  KS_STATUS_FAIL;
-    }
-
-       //todo - add more checks ? 
-
-       ks_bool_t isrequest = ks_rpcmessage_isrequest(request);
-
-       enum jrpc_status_t jrcs = 0;
-       
-       if (isrequest && callbacks->request_func) {
-
-               cJSON *responseP = NULL;
-       
-               if (callbacks->custom && callbacks->custom->prefix_request_func) {
-                       jrcs = callbacks->custom->prefix_request_func(request, &responseP);
-                       if ( (jrcs & JRPC_SEND) && responseP) {
-                               blade_rpc_write_json(responseP);
-                               cJSON_Delete(responseP);
-                               responseP = NULL;
-                       }
-               }
-
-               if ( !(jrcs & JRPC_EXIT) && jrcs != JRPC_ERROR) {
-                       jrcs =  callbacks->request_func(request, &responseP);
-                       if ((jrcs & JRPC_SEND) && responseP) {
-                               blade_rpc_write_json(responseP);
-                               cJSON_Delete(responseP);
-                               responseP = NULL;
-                       }
-               }
-
-               if (  !(jrcs & JRPC_EXIT) && jrcs != JRPC_ERROR && callbacks->custom && callbacks->custom->postfix_request_func) {
-                       jrcs =  callbacks->custom->postfix_request_func(request, &responseP);
-                       if ( (jrcs & JRPC_SEND) && responseP) {
-                               blade_rpc_write_json(responseP);
-                               cJSON_Delete(responseP);
-                               responseP = NULL;
-                       }
-               }
-
-               ks_mutex_unlock(callbacks->lock);
-
-               if (jrcs == JRPC_ERROR) {
-                       return KS_STATUS_FAIL;
-               }
-
-               return KS_STATUS_SUCCESS;
-       }
-    else if (!isrequest && callbacks->response_func) {
-
-        if (callbacks->custom && callbacks->custom->prefix_response_func) {
-            jrcs = callbacks->custom->prefix_response_func(response, &responseP);
-            if ( (jrcs & JRPC_SEND) && responseP) {
-                blade_rpc_write_json(responseP);
-                cJSON_Delete(responseP);
-                responseP = NULL;
-            }
-               }
-
-               if ( !(jrcs & JRPC_EXIT) && jrcs != JRPC_ERROR) {
-                       jrcs =  callbacks->response_func(response, &responseP);
-            if ( (jrcs & JRPC_SEND) && responseP) {
-                blade_rpc_write_json(responseP);
-                cJSON_Delete(responseP);
-                responseP = NULL;
-            }
-               }
-
-               if ( !(jrcs & JRPC_EXIT) && jrcs != JRPC_ERROR && callbacks->custom &&  callbacks->custom->postfix_response_func) {
-                       jrcs =  callbacks->custom->postfix_response_func(response, &responseP);
-                       if ( (jrcs & JRPC_SEND) && responseP) {
-                               blade_rpc_write_json(responseP);
-                               cJSON_Delete(responseP);
-                               responseP = NULL;
-                       }
-               }
-
-               ks_mutex_unlock(callbacks->lock);
-
-               if (jrcs == JRPC_ERROR) {
-                       return KS_STATUS_FAIL;
-               }
-
-        return KS_STATUS_SUCCESS;
-       }
-
-       ks_log(KS_LOG_ERROR, "Unable to find message handler for %s\n", command);
-       
-       return KS_STATUS_FAIL;
-}
-
-/*
- *
-*/
-KS_DECLARE(ks_status_t) blade_rpc_process_jsonmessage(cJSON *request)
-{
-       ks_status_t respstatus = blade_rpc_process_jsonmessage_all(request);
-       return respstatus;
-}
-
-KS_DECLARE(ks_status_t) blade_rpc_process_data(const uint8_t *data,
-                                                        ks_size_t size)
-{
-       
-       cJSON *json = cJSON_Parse((const char*)data);
-       if (json != NULL) {
-               ks_log( KS_LOG_ERROR, "Unable to parse message\n");
-               return KS_STATUS_FAIL;
-       }
-
-       /* deal with rpc message */
-       if (ks_rpcmessage_isrpc(json)) {
-               ks_status_t respstatus = blade_rpc_process_jsonmessage_all(json);
-               return respstatus;
-       }
-       
-       ks_log(KS_LOG_ERROR, "Unable to identify message type\n");
-       
-       return KS_STATUS_FAIL;
-}
-
-//KS_DECLARE(ks_status_t) blade_rpc_process_blademessage(blade_message_t *message)
-//{
-//     uint8_t* data = NULL;
-//     ks_size_t size = 0;
-//
-//     blade_message_get(message, (void **)&data, &size);
-//
-//     if (data && size>0) {
-//             ks_status_t s = blade_rpc_process_data(data, size);
-//             blade_message_discard(&message);
-//             return s;
-//     } 
-//     
-//     ks_log(KS_LOG_ERROR, "Message read failed\n");
-//     return KS_STATUS_FAIL;
-//
-//}
-
-
-/* For Emacs:
- * Local Variables:
- * mode:c
- * indent-tabs-mode:t
- * tab-width:4
- * c-basic-offset:4
- * End:
- * For VIM:
- * vim:set softtabstop=4 shiftwidth=4 tabstop=4 noet:
- */
-
index 58c9b323d15ef1ebd3d7c95712a05daa4700cf8d..048baec18328f604ff0dd804a880aad064225c56 100644 (file)
@@ -430,6 +430,7 @@ ks_status_t blade_session_state_on_destroy(blade_session_t *bs)
        ks_assert(bs);
 
        ks_log(KS_LOG_DEBUG, "Session (%s) state destroy\n", bs->id);
+
        blade_handle_sessions_remove(bs);
        blade_session_destroy(&bs);
 
@@ -483,21 +484,31 @@ ks_status_t blade_session_state_on_ready(blade_session_t *bs)
 }
 
 
-KS_DECLARE(ks_status_t) blade_session_send(blade_session_t *bs, cJSON *json)
+KS_DECLARE(ks_status_t) blade_session_send(blade_session_t *bs, cJSON *json, blade_response_callback_t callback)
 {
        blade_request_t *request = NULL;
        const char *method = NULL;
+       const char *id = NULL;
 
        ks_assert(bs);
        ks_assert(json);
 
        method = cJSON_GetObjectCstr(json, "method");
+       id = cJSON_GetObjectCstr(json, "id");
        if (method) {
-               blade_request_create(&request, bs->handle, bs->id, json);
+               // @note This is scenario 1
+               // 1) Sending a request (client: method caller or consumer)
+               ks_log(KS_LOG_DEBUG, "Session (%s) sending request (%s) for %s\n", bs->id, id, method);
+
+               blade_request_create(&request, bs->handle, bs->id, json, callback);
                ks_assert(request);
 
                // @todo set request TTL and figure out when requests are checked for expiration (separate thread in the handle?)
                blade_handle_requests_add(request);
+       } else {
+               // @note This is scenario 3
+               // 3) Sending a response or error (server: method callee or provider)
+               ks_log(KS_LOG_DEBUG, "Session (%s) sending response (%s)\n", bs->id, id);
        }
 
        if (list_empty(&bs->connections)) {
@@ -516,20 +527,18 @@ KS_DECLARE(ks_status_t) blade_session_send(blade_session_t *bs, cJSON *json)
 
 ks_status_t blade_session_process(blade_session_t *bs, cJSON *json)
 {
-       ks_status_t ret = KS_STATUS_SUCCESS;
        blade_request_t *breq = NULL;
        blade_response_t *bres = NULL;
        const char *jsonrpc = NULL;
        const char *id = NULL;
        const char *method = NULL;
+       ks_bool_t disconnect = KS_FALSE;
 
        ks_assert(bs);
        ks_assert(json);
 
        ks_log(KS_LOG_DEBUG, "Session (%s) processing\n", bs->id);
 
-       // @todo teardown the message, convert into a blade_request_t or blade_response_t
-       // @todo validate the jsonrpc fields
 
        jsonrpc = cJSON_GetObjectCstr(json, "jsonrpc");
        if (!jsonrpc || strcmp(jsonrpc, "2.0")) {
@@ -549,13 +558,50 @@ ks_status_t blade_session_process(blade_session_t *bs, cJSON *json)
 
        method = cJSON_GetObjectCstr(json, "method");
        if (method) {
-               // @todo use method to find RPC callbacks
+               // @note This is scenario 2
+               // 2) Receiving a request (server: method callee or provider)
+               blade_space_t *tmp_space = NULL;
+               blade_method_t *tmp_method = NULL;
+               blade_request_callback_t callback = NULL;
+               char *space_name = ks_pstrdup(bs->pool, method);
+               char *method_name = strrchr(space_name, '.');
+
+               ks_log(KS_LOG_DEBUG, "Session (%s) receiving request (%s) for %s\n", bs->id, id, method);
+
+               if (!method_name || method_name == space_name) {
+                       ks_pool_free(bs->pool, (void **)&space_name);
+                       // @todo send error response, code = -32601 (method not found)
+                       // @todo hangup session entirely?
+                       return KS_STATUS_FAIL;
+               }
+               *method_name = '\0';
+               method_name++; // @todo check if can be postfixed safely on previous assignment, can't recall
+
+               tmp_space = blade_handle_space_lookup(bs->handle, space_name);
+               if (tmp_space) tmp_method = blade_space_methods_get(tmp_space, method_name);
+
+               ks_pool_free(bs->pool, (void **)&space_name);
 
-               blade_request_create(&breq, bs->handle, bs->id, json);
+               if (!tmp_method) {
+                       // @todo send error response, code = -32601 (method not found)
+                       // @todo hangup session entirely?
+                       return KS_STATUS_FAIL;
+               }
+               callback = blade_method_callback_get(tmp_method);
+               ks_assert(callback);
+
+               blade_request_create(&breq, bs->handle, bs->id, json, NULL);
                ks_assert(breq);
 
-               // @todo call request callback handler
+               disconnect = callback(breq);
+
+               blade_request_destroy(&breq);
        } else {
+               // @note This is scenario 4
+               // 4) Receiving a response or error (client: method caller or consumer)
+
+               ks_log(KS_LOG_DEBUG, "Session (%s) receiving response (%s)\n", bs->id, id);
+
                breq = blade_handle_requests_get(bs->handle, id);
                if (!breq) {
                        // @todo hangup session entirely?
@@ -563,18 +609,20 @@ ks_status_t blade_session_process(blade_session_t *bs, cJSON *json)
                }
                blade_handle_requests_remove(breq);
 
-               method = cJSON_GetObjectCstr(breq->message, "method");
-               ks_assert(method);
-
-               // @todo use method to find RPC callbacks
-
                blade_response_create(&bres, bs->handle, bs->id, breq, json);
                ks_assert(bres);
 
-               // @todo call response callback handler
+               disconnect = breq->callback(bres);
+
+               blade_response_destroy(&bres);
        }
 
-       return ret;
+       if (disconnect) {
+               // @todo hangup session entirely?
+               return KS_STATUS_FAIL;
+       }
+
+       return KS_STATUS_SUCCESS;
 }
 
 /* For Emacs:
diff --git a/libs/libblade/src/blade_space.c b/libs/libblade/src/blade_space.c
new file mode 100644 (file)
index 0000000..09a8574
--- /dev/null
@@ -0,0 +1,176 @@
+/*
+ * Copyright (c) 2017, Shane Bryldt
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *
+ * * Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * * Neither the name of the original author; nor the names of any contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER
+ * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "blade.h"
+
+struct blade_space_s {
+       blade_handle_t *handle;
+       ks_pool_t *pool;
+
+       const char *path;
+       ks_hash_t *methods;
+};
+
+
+KS_DECLARE(ks_status_t) blade_space_create(blade_space_t **bsP, blade_handle_t *bh, const char *path)
+{
+       blade_space_t *bs = NULL;
+       ks_pool_t *pool = NULL;
+
+       ks_assert(bsP);
+       ks_assert(bh);
+       ks_assert(path);
+
+       pool = blade_handle_pool_get(bh);
+
+       bs = ks_pool_alloc(pool, sizeof(blade_space_t));
+       bs->handle = bh;
+       bs->pool = pool;
+       bs->path = path; // @todo dup and keep copy? should mostly be literals
+       ks_hash_create(&bs->methods, KS_HASH_MODE_CASE_INSENSITIVE, KS_HASH_FLAG_NOLOCK | KS_HASH_FLAG_DUP_CHECK, bs->pool);
+       ks_assert(bs);
+
+       *bsP = bs;
+
+       ks_log(KS_LOG_DEBUG, "Space Created: %s\n", path);
+
+       return KS_STATUS_SUCCESS;
+}
+
+KS_DECLARE(ks_status_t) blade_space_destroy(blade_space_t **bsP)
+{
+       blade_space_t *bs = NULL;
+       ks_hash_iterator_t *it = NULL;
+
+       ks_assert(bsP);
+       ks_assert(*bsP);
+
+       bs = *bsP;
+
+       for (it = ks_hash_first(bs->methods, KS_UNLOCKED); it; it = ks_hash_next(&it)) {
+        void *key = NULL;
+               blade_method_t *value = NULL;
+
+               ks_hash_this(it, (const void **)&key, NULL, (void **)&value);
+               blade_method_destroy(&value);
+       }
+
+       ks_hash_destroy(&bs->methods);
+
+       ks_log(KS_LOG_DEBUG, "Space Destroyed: %s\n", bs->path);
+
+       ks_pool_free(bs->pool, bsP);
+
+       return KS_STATUS_SUCCESS;
+}
+
+KS_DECLARE(blade_handle_t *) blade_space_handle_get(blade_space_t *bs)
+{
+       ks_assert(bs);
+
+       return bs->handle;
+}
+
+KS_DECLARE(const char *) blade_space_path_get(blade_space_t *bs)
+{
+       ks_assert(bs);
+
+       return bs->path;
+}
+
+KS_DECLARE(ks_status_t) blade_space_methods_add(blade_space_t *bs, blade_method_t *bm)
+{
+       ks_status_t ret = KS_STATUS_SUCCESS;
+       const char *name = NULL;
+       blade_method_t *bm_old = NULL;
+
+       ks_assert(bs);
+       ks_assert(bm);
+
+       name = blade_method_name_get(bm);
+       ks_assert(name);
+
+       ks_hash_write_lock(bs->methods);
+       bm_old = ks_hash_search(bs->methods, (void *)name, KS_UNLOCKED);
+       if (bm_old) ks_hash_remove(bs->methods, (void *)name);
+       ret = ks_hash_insert(bs->methods, (void *)name, (void *)bm);
+       ks_hash_write_unlock(bs->methods);
+
+       if (bm_old) blade_method_destroy(&bm_old);
+
+       return ret;
+}
+
+KS_DECLARE(ks_status_t) blade_space_methods_remove(blade_space_t *bs, blade_method_t *bm)
+{
+       ks_status_t ret = KS_STATUS_SUCCESS;
+       const char *name = NULL;
+
+       ks_assert(bs);
+       ks_assert(bm);
+
+       name = blade_method_name_get(bm);
+       ks_assert(name);
+
+       ks_hash_write_lock(bs->methods);
+       ks_hash_remove(bs->methods, (void *)name);
+       ks_hash_write_unlock(bs->methods);
+
+       return ret;
+}
+
+KS_DECLARE(blade_method_t *) blade_space_methods_get(blade_space_t *bs, const char *name)
+{
+       blade_method_t *bm = NULL;
+
+       ks_assert(bs);
+       ks_assert(name);
+
+       ks_hash_read_lock(bs->methods);
+       bm = ks_hash_search(bs->methods, (void *)name, KS_UNLOCKED);
+       ks_hash_read_unlock(bs->methods);
+
+       return bm;
+}
+
+
+/* For Emacs:
+ * Local Variables:
+ * mode:c
+ * indent-tabs-mode:t
+ * tab-width:4
+ * c-basic-offset:4
+ * End:
+ * For VIM:
+ * vim:set softtabstop=4 shiftwidth=4 tabstop=4 noet:
+ */
index 56357344ced5cf1c1942e93e762b2d719e8c8a08..697a8d9feb38ab7d21295db8ff3e4eb7b5058b23 100644 (file)
@@ -48,6 +48,7 @@ struct blade_handle_s {
        config_setting_t *config_datastore;
 
        ks_hash_t *transports; // registered transports exposed by modules, NOT active connections
+       ks_hash_t *spaces; // registered method spaces exposed by modules
 
        //blade_identity_t *identity;
        blade_datastore_t *datastore;
@@ -69,6 +70,7 @@ struct blade_handle_transport_registration_s {
        blade_transport_callbacks_t *callbacks;
 };
 
+
 KS_DECLARE(ks_status_t) blade_handle_transport_registration_create(blade_handle_transport_registration_t **bhtrP,
                                                                                                                                   ks_pool_t *pool,
                                                                                                                                   blade_module_t *module,
@@ -133,6 +135,8 @@ KS_DECLARE(ks_status_t) blade_handle_create(blade_handle_t **bhP, ks_pool_t *poo
 
        ks_hash_create(&bh->transports, KS_HASH_MODE_CASE_INSENSITIVE, KS_HASH_FLAG_NOLOCK | KS_HASH_FLAG_DUP_CHECK, bh->pool);
        ks_assert(bh->transports);
+       ks_hash_create(&bh->spaces, KS_HASH_MODE_CASE_INSENSITIVE, KS_HASH_FLAG_NOLOCK | KS_HASH_FLAG_DUP_CHECK, bh->pool);
+       ks_assert(bh->spaces);
 
        ks_hash_create(&bh->connections, KS_HASH_MODE_CASE_INSENSITIVE, KS_HASH_FLAG_NOLOCK | KS_HASH_FLAG_DUP_CHECK, bh->pool);
        ks_assert(bh->connections);
@@ -144,6 +148,8 @@ KS_DECLARE(ks_status_t) blade_handle_create(blade_handle_t **bhP, ks_pool_t *poo
 
        *bhP = bh;
 
+       ks_log(KS_LOG_DEBUG, "Created\n");
+
        return KS_STATUS_SUCCESS;
 }
 
@@ -168,10 +174,13 @@ KS_DECLARE(ks_status_t) blade_handle_destroy(blade_handle_t **bhP)
        ks_hash_destroy(&bh->requests);
        ks_hash_destroy(&bh->sessions);
        ks_hash_destroy(&bh->connections);
+       ks_hash_destroy(&bh->spaces);
        ks_hash_destroy(&bh->transports);
 
     if (bh->tpool && (flags & BH_MYTPOOL)) ks_thread_pool_destroy(&bh->tpool);
 
+       ks_log(KS_LOG_DEBUG, "Destroyed\n");
+
        ks_pool_free(bh->pool, &bh);
 
        if (pool && (flags & BH_MYPOOL)) {
@@ -249,13 +258,22 @@ KS_DECLARE(ks_status_t) blade_handle_shutdown(blade_handle_t *bh)
                blade_session_t *value = NULL;
 
                ks_hash_this(it, (const void **)&key, NULL, (void **)&value);
-               ks_hash_remove(bh->requests, key);
+               //ks_hash_remove(bh->sessions, key);
 
                blade_session_hangup(value);
        }
        while (ks_hash_count(bh->sessions) > 0) ks_sleep_ms(100);
 
-       // @todo call onshutdown and onunload callbacks for modules from DSOs, which will unregister transports and disconnect remaining unattached connections
+       // @todo call onshutdown and onunload callbacks for modules from DSOs, which will unregister transports and spaces, and will disconnect remaining
+       // unattached connections
+
+       for (it = ks_hash_first(bh->spaces,  KS_UNLOCKED); it; it = ks_hash_next(&it)) {
+               void *key = NULL;
+               blade_space_t *value = NULL;
+
+               ks_hash_this(it, (const void **)&key, NULL, (void **)&value);
+               blade_handle_space_unregister(value);
+       }
 
        // @todo unload DSOs
 
@@ -316,11 +334,81 @@ KS_DECLARE(ks_status_t) blade_handle_transport_unregister(blade_handle_t *bh, co
        if (bhtr) ks_hash_remove(bh->transports, (void *)name);
        ks_hash_write_unlock(bh->transports);
 
-       if (bhtr) blade_handle_transport_registration_destroy(&bhtr);
+       if (bhtr) {
+               blade_handle_transport_registration_destroy(&bhtr);
+               ks_log(KS_LOG_DEBUG, "Transport Unregistered: %s\n", name);
+       }
+
+       return KS_STATUS_SUCCESS;
+}
+
+KS_DECLARE(ks_status_t) blade_handle_space_register(blade_space_t *bs)
+{
+       blade_handle_t *bh = NULL;
+       const char *path = NULL;
+       blade_space_t *bs_old = NULL;
+
+       ks_assert(bs);
+
+       bh = blade_space_handle_get(bs);
+       ks_assert(bh);
+
+       path = blade_space_path_get(bs);
+       ks_assert(path);
+
+       ks_hash_write_lock(bh->spaces);
+       bs_old = ks_hash_search(bh->spaces, (void *)path, KS_UNLOCKED);
+       if (bs_old) ks_hash_remove(bh->spaces, (void *)path);
+       ks_hash_insert(bh->spaces, (void *)path, bs);
+       ks_hash_write_unlock(bh->spaces);
+
+       if (bs_old) blade_space_destroy(&bs_old);
+
+       ks_log(KS_LOG_DEBUG, "Space Registered: %s\n", path);
 
        return KS_STATUS_SUCCESS;
 }
 
+KS_DECLARE(ks_status_t) blade_handle_space_unregister(blade_space_t *bs)
+{
+       blade_handle_t *bh = NULL;
+       const char *path = NULL;
+
+       ks_assert(bs);
+
+       bh = blade_space_handle_get(bs);
+       ks_assert(bh);
+
+       path = blade_space_path_get(bs);
+       ks_assert(path);
+
+       ks_hash_write_lock(bh->spaces);
+       bs = ks_hash_search(bh->spaces, (void *)path, KS_UNLOCKED);
+       if (bs) ks_hash_remove(bh->spaces, (void *)path);
+       ks_hash_write_unlock(bh->spaces);
+
+       if (bs) {
+               blade_space_destroy(&bs);
+               ks_log(KS_LOG_DEBUG, "Space Unregistered: %s\n", path);
+       }
+
+       return KS_STATUS_SUCCESS;
+}
+
+KS_DECLARE(blade_space_t *) blade_handle_space_lookup(blade_handle_t *bh, const char *path)
+{
+       blade_space_t *bs = NULL;
+
+       ks_assert(bh);
+       ks_assert(path);
+
+       ks_hash_read_lock(bh->spaces);
+       bs = ks_hash_search(bh->spaces, (void *)path, KS_UNLOCKED);
+       ks_hash_read_unlock(bh->spaces);
+
+       return bs;
+}
+
 KS_DECLARE(ks_status_t) blade_handle_connect(blade_handle_t *bh, blade_connection_t **bcP, blade_identity_t *target, const char *session_id)
 {
        ks_status_t ret = KS_STATUS_SUCCESS;
diff --git a/libs/libblade/src/bpcp.c b/libs/libblade/src/bpcp.c
deleted file mode 100644 (file)
index f61180a..0000000
+++ /dev/null
@@ -1,108 +0,0 @@
-/*
- * Copyright (c) 2007-2014, Anthony Minessale II
- * All rights reserved.
- * 
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 
- * * Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- * 
- * * Neither the name of the original author; nor the names of any contributors
- * may be used to endorse or promote products derived from this software
- * without specific prior written permission.
- * 
- * 
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER
- * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
- * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
- * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "blade.h"
-
-
-/*
-
-Find bootstrap addr.
-Make a WSS connection to get validated and get group keys.
-Broadcast/Announce existence.
-
-
-HEADER
-
- 0                   1                   2                   3
- 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-| Ver   |r|R|U|U|  Channel no   |   Packet Length               |
-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-|                          SEQ                                  |
-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-|   PAYLOAD  ......                                             |
-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-
-r = IS Response
-R = IS Retransmission
-U = Unused
-
-PAYLOAD
-
- 0                   1                   2                   3
- 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-|  Instruction | Datatype      |      Length                    |
-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-|   PAYLOAD .....                                               |
-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
-
-
- */
-
-
-typedef struct bpcp_header_s {
-       uint32_t header;
-       uint64_t seq;
-} bpcp_header_t;
-
-typedef struct bpcp_channel_nfo_s {
-       char *channel_name;
-       unsigned char key[crypto_generichash_BYTES];
-       uint32_t ttl;
-} bpcp_channel_nfo_t;
-
-typedef struct bpcp_handle_s {
-       ks_socket_t sock;
-       ks_sockaddr_t local_addr;
-       ks_sockaddr_t bootstrap_addr;
-       ks_hash_t *channel_nfo_hash;
-} bpcp_handle_t;
-
-KS_DECLARE(ks_status_t) bpcp_create(bpcp_handle_t **handle,
-                                                                       const char *local_addr, ks_port_t local_port,
-                                                                       const char *bootstrap_addr, ks_port_t bootstrap_port)
-{
-       return KS_STATUS_SUCCESS;
-}
-
-/* For Emacs:
- * Local Variables:
- * mode:c
- * indent-tabs-mode:t
- * tab-width:4
- * c-basic-offset:4
- * End:
- * For VIM:
- * vim:set softtabstop=4 shiftwidth=4 tabstop=4 noet:
- */
index 54d744657a26396913d7848d10e86bc7e49aa740..c94c08551106cc17df3996ca33164419cabf5893 100644 (file)
@@ -1,23 +1,23 @@
 /*
  * Copyright (c) 2007-2014, Anthony Minessale II
  * All rights reserved.
- * 
+ *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
  * are met:
- * 
+ *
  * * Redistributions of source code must retain the above copyright
  * notice, this list of conditions and the following disclaimer.
- * 
+ *
  * * Redistributions in binary form must reproduce the above copyright
  * notice, this list of conditions and the following disclaimer in the
  * documentation and/or other materials provided with the distribution.
- * 
+ *
  * * Neither the name of the original author; nor the names of any contributors
  * may be used to endorse or promote products derived from this software
  * without specific prior written permission.
- * 
- * 
+ *
+ *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
@@ -46,7 +46,8 @@
 #include "blade_session.h"
 #include "blade_protocol.h"
 #include "blade_datastore.h"
-#include "bpcp.h"
+#include "blade_space.h"
+#include "blade_method.h"
 
 KS_BEGIN_EXTERN_C
 
similarity index 79%
rename from libs/libblade/src/include/bpcp.h
rename to libs/libblade/src/include/blade_method.h
index 46a648abbe8da744844a32eb88b16b4a3838ad78..74bf87d13f91ab13aefc6d43b5776d563ca2d99a 100644 (file)
@@ -1,23 +1,23 @@
 /*
- * Copyright (c) 2007-2014, Anthony Minessale II
+ * Copyright (c) 2017, Shane Bryldt
  * All rights reserved.
- * 
+ *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
  * are met:
- * 
+ *
  * * Redistributions of source code must retain the above copyright
  * notice, this list of conditions and the following disclaimer.
- * 
+ *
  * * Redistributions in binary form must reproduce the above copyright
  * notice, this list of conditions and the following disclaimer in the
  * documentation and/or other materials provided with the distribution.
- * 
+ *
  * * Neither the name of the original author; nor the names of any contributors
  * may be used to endorse or promote products derived from this software
  * without specific prior written permission.
- * 
- * 
+ *
+ *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
-#ifndef _BPCP_H_
-#define _BPCP_H_
+#ifndef _BLADE_METHOD_H_
+#define _BLADE_METHOD_H_
 #include <blade.h>
 
 KS_BEGIN_EXTERN_C
-
+KS_DECLARE(ks_status_t) blade_method_create(blade_method_t **bmP, blade_space_t *bs, const char *name, blade_request_callback_t callback);
+KS_DECLARE(ks_status_t) blade_method_destroy(blade_method_t **bmP);
+KS_DECLARE(const char *) blade_method_name_get(blade_method_t *bm);
+KS_DECLARE(blade_request_callback_t) blade_method_callback_get(blade_method_t *bm);
 KS_END_EXTERN_C
 
 #endif
index ddc4a3cdee4088d6876cb626d41077e326d2dffc..0d3b4c772f0f071c3fdc156aaa25a64d7e58185d 100644 (file)
 #include <blade.h>
 
 KS_BEGIN_EXTERN_C
-KS_DECLARE(ks_status_t) blade_request_create(blade_request_t **breqP, blade_handle_t *bh, const char *session_id, cJSON *json);
+KS_DECLARE(ks_status_t) blade_request_create(blade_request_t **breqP,
+                                                                                        blade_handle_t *bh,
+                                                                                        const char *session_id,
+                                                                                        cJSON *json,
+                                                                                        blade_response_callback_t callback);
 KS_DECLARE(ks_status_t) blade_request_destroy(blade_request_t **breqP);
 KS_DECLARE(ks_status_t) blade_response_create(blade_response_t **bresP, blade_handle_t *bh, const char *session_id, blade_request_t *breq, cJSON *json);
 KS_DECLARE(ks_status_t) blade_response_destroy(blade_response_t **bresP);
+KS_DECLARE(ks_status_t) blade_rpc_request_create(ks_pool_t *pool, cJSON **json, cJSON **params, const char **id, const char *method);
+KS_DECLARE(ks_status_t) blade_rpc_response_create(ks_pool_t *pool, cJSON **json, cJSON **result, const char *id);
+KS_DECLARE(ks_status_t) blade_rpc_error_create(ks_pool_t *pool, cJSON **json, cJSON **error, const char *id, int32_t code, const char *message);
 KS_END_EXTERN_C
 
 #endif
diff --git a/libs/libblade/src/include/blade_rpcproto.h b/libs/libblade/src/include/blade_rpcproto.h
deleted file mode 100644 (file)
index f108c98..0000000
+++ /dev/null
@@ -1,166 +0,0 @@
-/*
- * Copyright (c) 2017, FreeSWITCH LLC
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * * Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * * Neither the name of the original author; nor the names of any contributors
- * may be used to endorse or promote products derived from this software
- * without specific prior written permission.
- *
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER
- * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
- * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
- * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef _BLADE_RPCPROTO_H_
-#define _BLADE_RPCPROTO_H_
-
-#include <ks_rpcmessage.h>
-#include <blade_types.h>
-
-// temp typedefs to get compile going 
-//typedef struct blade_peer_s  blade_peer_t;
-//typedef struct blade_event_s blade_event_t;
-
-#define KS_RPCMESSAGE_NAMESPACE_LENGTH 16
-#define KS_RPCMESSAGE_COMMAND_LENGTH  238
-#define KS_RPCMESSAGE_FQCOMMAND_LENGTH  (KS_RPCMESSAGE_NAMESPACE_LENGTH+KS_RPCMESSAGE_COMMAND_LENGTH+1)
-#define KS_RPCMESSAGE_VERSION_LENGTH 9
-
-
-/* 
- *  contents to add to the "blade" field in rpc
- */
-
-typedef struct blade_rpc_fields_s {
-
-       const char *to;
-       const char *from;
-       const char *token;
-
-}  blade_rpc_fields_t;
-
-
-
-enum jrpc_status_t { 
-       JRPC_PASS = (1 << 0), 
-       JRPC_SEND = (1 << 1),
-       JRPC_EXIT = (1 << 2),
-       JRPC_SEND_EXIT = JRPC_SEND + JRPC_EXIT, 
-       JRPC_ERROR =  (1 << 3)
-};
-
-
-typedef enum jrpc_status_t (*jrpc_func_t)  (cJSON *request, cJSON **replyP);
-
-
-/*
- *  setup
- *  -----
- */
-
-KS_DECLARE(ks_status_t) blade_rpc_init(ks_pool_t *pool);
-
-
-/* 
- *  namespace and call back registration 
- *  ------------------------------------
- */
-KS_DECLARE(ks_status_t) blade_rpc_declare_namespace(char* namespace, const char* version);
-KS_DECLARE(ks_status_t) blade_rpc_register_function(char* namespace, 
-                                                                                                               char *command,
-                                                                                                               jrpc_func_t func,
-                                                                                                               jrpc_func_t respfunc);
-KS_DECLARE(ks_status_t) blade_rpc_register_custom_request_function(char* namespace,   
-                                                                                                               char *command,
-                                                                                                               jrpc_func_t prefix_func,
-                                                                                                               jrpc_func_t postfix_func);
-KS_DECLARE(ks_status_t) blade_rpc_register_custom_response_function(char *namespace,   
-                                                                                                               char *command,
-                                                                                                               jrpc_func_t prefix_func,
-                                                                                                               jrpc_func_t postfix_func);
-KS_DECLARE(void) blade_rpc_remove_namespace(char* namespace);
-
-/*
- * template registration and inheritance
- * -------------------------------------
- */
-KS_DECLARE(ks_status_t) blade_rpc_declare_template(char* templatename, const char* version);
-
-KS_DECLARE(ks_status_t)blade_rpc_register_template_function(char *name,
-                                                char *command,
-                                                jrpc_func_t func,
-                                                jrpc_func_t respfunc);
-
-KS_DECLARE(ks_status_t)blade_rpc_inherit_template(char *namespace, char* template);
-
-
-/*
- * create a request message
- */
-KS_DECLARE(ks_rpcmessageid_t) blade_rpc_create_request(char *namespace,
-                                                                                                       char *method,
-                                                                                                       blade_rpc_fields_t* fields,
-                                                                                                       cJSON **paramsP,
-                                                                                                       cJSON **requestP);
-
-KS_DECLARE(ks_rpcmessageid_t) blade_rpc_create_response(cJSON *request,
-                                                                                                       cJSON **reply,
-                                                                                                       cJSON **response);
-
-KS_DECLARE(ks_rpcmessageid_t) blade_rpc_create_errorresponse(cJSON *request,
-                                                                                                       cJSON **reply,
-                                                                                                       cJSON **response);
-
-KS_DECLARE(ks_status_t) blade_rpc_parse_message(cJSON *message,
-                                                                                                       char **namespace,
-                                                                                                       char **method,
-                                                                                                       char **version,
-                                                                                                       uint32_t *idP,  
-                                                                                                       blade_rpc_fields_t **fieldsP);
-
-/*
- * peer create/destroy
- * -------------------
- */
-//KS_DECLARE(ks_status_t) blade_rpc_onconnect(ks_pool_t *pool, blade_peer_t* peer);
-//KS_DECLARE(ks_status_t) blade_rpc_disconnect(blade_peer_t* peer);
-
-/* 
- * send message
- * ------------
- */
-KS_DECLARE(ks_status_t) blade_rpc_write(char *sessionid, char* data, uint32_t size);  //uuid_t ?
-KS_DECLARE(ks_status_t) blade_rpc_write_json(cJSON* json);
-
-
-/*
- * process inbound message
- * -----------------------
- */
-KS_DECLARE(ks_status_t) blade_rpc_process_data(const uint8_t *data, ks_size_t size);
-
-KS_DECLARE(ks_status_t) blade_rpc_process_jsonmessage(cJSON *request);
-
-
-#endif
-
index f4e92775b36f4ea7adc44ebbb4e3d77d50571a6e..e79fbf34b0846d9579f93ecf5b89bda07c45bf52 100644 (file)
@@ -1,23 +1,23 @@
 /*
  * Copyright (c) 2017, Shane Bryldt
  * All rights reserved.
- * 
+ *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
  * are met:
- * 
+ *
  * * Redistributions of source code must retain the above copyright
  * notice, this list of conditions and the following disclaimer.
- * 
+ *
  * * Redistributions in binary form must reproduce the above copyright
  * notice, this list of conditions and the following disclaimer in the
  * documentation and/or other materials provided with the distribution.
- * 
+ *
  * * Neither the name of the original author; nor the names of any contributors
  * may be used to endorse or promote products derived from this software
  * without specific prior written permission.
- * 
- * 
+ *
+ *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
@@ -52,7 +52,7 @@ KS_DECLARE(void) blade_session_hangup(blade_session_t *bs);
 KS_DECLARE(ks_bool_t) blade_session_terminating(blade_session_t *bs);
 KS_DECLARE(ks_status_t) blade_session_connections_add(blade_session_t *bs, const char *id);
 KS_DECLARE(ks_status_t) blade_session_connections_remove(blade_session_t *bs, const char *id);
-KS_DECLARE(ks_status_t) blade_session_send(blade_session_t *bs, cJSON *json);
+KS_DECLARE(ks_status_t) blade_session_send(blade_session_t *bs, cJSON *json, blade_response_callback_t callback);
 KS_DECLARE(ks_status_t) blade_session_sending_push(blade_session_t *bs, cJSON *json);
 KS_DECLARE(ks_status_t) blade_session_sending_pop(blade_session_t *bs, cJSON **json);
 KS_DECLARE(ks_status_t) blade_session_receiving_push(blade_session_t *bs, cJSON *json);
similarity index 52%
rename from libs/libks/src/include/ks_rpcmessage.h
rename to libs/libblade/src/include/blade_space.h
index da2157e9d09aa50b0efa4fbf11b9692356668eb3..65664fdba51cdcb895dbc5bbbf307ac192307c0e 100644 (file)
@@ -1,23 +1,23 @@
 /*
- * Copyright (c) 2017, FreeSWITCH Solutions LLC 
+ * Copyright (c) 2017, Shane Bryldt
  * All rights reserved.
- * 
+ *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
  * are met:
- * 
+ *
  * * Redistributions of source code must retain the above copyright
  * notice, this list of conditions and the following disclaimer.
- * 
+ *
  * * Redistributions in binary form must reproduce the above copyright
  * notice, this list of conditions and the following disclaimer in the
  * documentation and/or other materials provided with the distribution.
- * 
+ *
  * * Neither the name of the original author; nor the names of any contributors
  * may be used to endorse or promote products derived from this software
  * without specific prior written permission.
- * 
- * 
+ *
+ *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
-
-#ifndef _KS_RPCMESSAGE_H_
-#define _KS_RPCMESSAGE_H_
-
-#include "ks.h"
+#ifndef _BLADE_SPACE_H_
+#define _BLADE_SPACE_H_
+#include <blade.h>
 
 KS_BEGIN_EXTERN_C
-
-#define KS_RPCMESSAGE_NAMESPACE_LENGTH 16
-#define KS_RPCMESSAGE_COMMAND_LENGTH  238
-#define KS_RPCMESSAGE_FQCOMMAND_LENGTH  (KS_RPCMESSAGE_NAMESPACE_LENGTH+KS_RPCMESSAGE_COMMAND_LENGTH+1)
-#define KS_RPCMESSAGE_VERSION_LENGTH 9
-
-
-typedef uint32_t ks_rpcmessageid_t;
-
-
-KS_DECLARE(void) ks_rpcmessage_init(ks_pool_t *pool);
-
-KS_DECLARE(void*) ks_json_pool_alloc(ks_size_t size);
-KS_DECLARE(void) ks_json_pool_free(void *ptr);
-
-
-KS_DECLARE(ks_rpcmessageid_t) ks_rpcmessage_create_request(char *namespace, 
-                                                                                       char *method,
-                                                                                       cJSON **paramsP,
-                                                                                       cJSON **requestP);
-
-KS_DECLARE(ks_size_t) ks_rpc_create_buffer(char *namespace,
-                                            char *method,
-                                            cJSON **paramsP,
-                                            ks_buffer_t *buffer);
-
-KS_DECLARE(ks_rpcmessageid_t) ks_rpcmessage_create_response( 
-                                                                                       const cJSON *request, 
-                                                                                       cJSON **resultP, 
-                                                                                       cJSON **responseP);
-
-KS_DECLARE(ks_rpcmessageid_t) ks_rpcmessage_create_errorresponse(
-                                            const cJSON *request,
-                                            cJSON **errorP,
-                                            cJSON **responseP);
-
-KS_DECLARE(ks_bool_t) ks_rpcmessage_isrequest(cJSON *msg);
-
-KS_DECLARE(ks_bool_t) ks_rpcmessage_isrpc(cJSON *msg);
-
+KS_DECLARE(ks_status_t) blade_space_create(blade_space_t **bsP, blade_handle_t *bh, const char *path);
+KS_DECLARE(ks_status_t) blade_space_destroy(blade_space_t **bsP);
+KS_DECLARE(blade_handle_t *) blade_space_handle_get(blade_space_t *bs);
+KS_DECLARE(const char *) blade_space_path_get(blade_space_t *bs);
+KS_DECLARE(ks_status_t) blade_space_methods_add(blade_space_t *bs, blade_method_t *bm);
+KS_DECLARE(ks_status_t) blade_space_methods_remove(blade_space_t *bs, blade_method_t *bm);
+KS_DECLARE(blade_method_t *) blade_space_methods_get(blade_space_t *bs, const char *name);
 KS_END_EXTERN_C
 
-#endif                                                 /* defined(_KS_RPCMESSAGE_H_) */
+#endif
 
 /* For Emacs:
  * Local Variables:
index ff86af388e4c44c49b48b1a3a537ff3944cec0c5..27b45bf93f2a873783075a9102dbf84cc7425e25 100644 (file)
@@ -50,6 +50,11 @@ KS_DECLARE(ks_thread_pool_t *) blade_handle_tpool_get(blade_handle_t *bh);
 
 KS_DECLARE(ks_status_t) blade_handle_transport_register(blade_handle_t *bh, blade_module_t *bm, const char *name, blade_transport_callbacks_t *callbacks);
 KS_DECLARE(ks_status_t) blade_handle_transport_unregister(blade_handle_t *bh, const char *name);
+
+KS_DECLARE(ks_status_t) blade_handle_space_register(blade_space_t *bs);
+KS_DECLARE(ks_status_t) blade_handle_space_unregister(blade_space_t *bs);
+KS_DECLARE(blade_space_t *) blade_handle_space_lookup(blade_handle_t *bh, const char *path);
+
 KS_DECLARE(ks_status_t) blade_handle_connect(blade_handle_t *bh, blade_connection_t **bcP, blade_identity_t *target, const char *session_id);
 
 KS_DECLARE(blade_connection_t *) blade_handle_connections_get(blade_handle_t *bh, const char *cid);
index 295217979dd0b69a9d82019c5014e6545567b87a..14c908f8573c919f3913c899c3020f4b3e4799dd 100644 (file)
@@ -47,6 +47,12 @@ typedef struct blade_connection_s blade_connection_t;
 typedef struct blade_session_s blade_session_t;
 typedef struct blade_request_s blade_request_t;
 typedef struct blade_response_s blade_response_t;
+typedef struct blade_space_s blade_space_t;
+typedef struct blade_method_s blade_method_t;
+
+
+typedef ks_bool_t (*blade_request_callback_t)(blade_request_t *breq);
+typedef ks_bool_t (*blade_response_callback_t)(blade_response_t *bres);
 
 typedef struct blade_datastore_s blade_datastore_t;
 
@@ -147,6 +153,7 @@ struct blade_request_s {
 
        cJSON *message;
        const char *message_id; // pulled from message for easier keying
+       blade_response_callback_t callback;
        // @todo ttl to wait for response before injecting an error response locally
        // @todo rpc response callback
 };
index e6c8c3902fe6b92ae8bc9524d6d7c6fc9f41cb7c..328a71ef250507c637a68f807f796861a040760e 100644 (file)
@@ -1,13 +1,8 @@
-AM_CFLAGS += -I$(abs_top_srcdir)/src/include -g -ggdb -O0 
+AM_CFLAGS += -I$(abs_top_srcdir)/src/include -g -ggdb -O0
 TEST_LDADD = $(abs_top_builddir)/libblade.la -lconfig -lm -lpthread
 check_PROGRAMS =
 
 
-check_PROGRAMS += testrpcproto
-testrpcproto_SOURCES = testrpcproto.c tap.c
-testrpcproto_CFLAGS = $(AM_CFLAGS)
-testrpcproto_LDADD = $(TEST_LDADD)
-
 check_PROGRAMS += testbuild
 testbuild_SOURCES = testbuild.c tap.c
 testbuild_CFLAGS = $(AM_CFLAGS)
diff --git a/libs/libblade/test/testrpcproto.c b/libs/libblade/test/testrpcproto.c
deleted file mode 100644 (file)
index 2b5f282..0000000
+++ /dev/null
@@ -1,724 +0,0 @@
-#pragma GCC diagnostic ignored "-Wunused-but-set-variable"
-#pragma GCC diagnostic ignored "-Wunused-variable"
-#pragma GCC diagnostic ignored "-Wunused-function"
-
-
-#include <blade_rpcproto.h>
-
-#pragma GCC optimize ("O0")
-
-
-ks_pool_t *pool;
-ks_thread_pool_t *tpool;
-
-
-static ks_thread_t *threads[10];
-
-static char idbuffer[51];
-
-
-
-static enum jrpc_status_t  process_widget(cJSON *msg, cJSON **response)
-{
-    printf("entering process_widget\n");
-
-    char *b0 = cJSON_PrintUnformatted(msg);
-    printf("Request: %s\n", b0);
-    ks_pool_free(pool, &b0);
-
-    cJSON *resp = cJSON_CreateObject();
-    cJSON_AddNumberToObject(resp, "code", 199);
-
-    //ks_rpcmessageid_t msgid = ks_rpcmessage_create_response(msg, &resp, response);
-       ks_rpcmessageid_t msgid = blade_rpc_create_response(msg, &resp, response);
-
-    char *b1 = cJSON_PrintUnformatted(*response);   //(*response);
-    printf("Response: msgid %d\n%s\n", msgid, b1);
-    ks_pool_free(pool, &b1);
-
-    printf("exiting process_wombat\n");
-
-    return JRPC_SEND;
-}
-
-
-static enum jrpc_status_t  process_widget_response(cJSON *request, cJSON **msg)
-{
-       printf("entering process_widget_response\n");
-       printf("exiting process_widget_response\n");
-       return JRPC_PASS;
-}
-
-
-
-static enum jrpc_status_t  process_wombat(cJSON *msg, cJSON **replyP)
-{
-       printf("entering process_wombat\n");
-       
-       char *b0 = cJSON_PrintUnformatted(msg);
-       printf("\nRequest: %s\n\n", b0);
-       ks_pool_free(pool, &b0);
-
-       cJSON *result = cJSON_CreateObject();
-       cJSON_AddNumberToObject(result, "code", 99);
-       cJSON *response;
-
-//    ks_rpcmessageid_t msgid = ks_rpcmessage_create_response(msg, &result, &response);
-       ks_rpcmessageid_t msgid = blade_rpc_create_response(msg, &result, &response);
-
-       cJSON *response_copy = cJSON_Duplicate(response, 1);
-    blade_rpc_process_jsonmessage(response_copy);
-
-    if (msgid != 0) {
-           char *b1 = cJSON_PrintUnformatted(response);   //(*response);
-           printf("\nResponse: msgid %d\n%s\n\n", msgid, b1);
-        blade_rpc_write_json(response);
-               ks_pool_free(pool, &b1);
-    }
-    else {
-        printf("process_wombat: unable to create response \n");
-        return JRPC_ERROR;
-    }
-
-       blade_rpc_fields_t *r_fields;
-
-       char *r_method;
-       char *r_namespace;
-       char *r_version;
-       uint32_t r_id;
-
-       ks_status_t s1 = blade_rpc_parse_message(msg, &r_namespace, &r_method, &r_version, &r_id, &r_fields);
-
-       if (s1 == KS_STATUS_FAIL) {
-               printf("process_wombat:  blade_rpc_parse_message failed\n");
-               return JRPC_ERROR;
-       }
-       
-       printf("\nprocess_wombat:  blade_rpc_parse_message namespace %s,  method %s, id %d,  version %s,  to %s, from %s,  token %s\n\n",
-                                                                                       r_namespace, r_method, r_id, r_version,
-                                                                                       r_fields->to, r_fields->from, r_fields->token);
-
-       cJSON *parms2 = NULL;
-
-    char to[] = "tony@freeswitch.com/laptop?transport=wss&host=server1.freeswitch.com&port=1234";
-    char from[] = "colm@freeswitch.com/laptop?transport=wss&host=server2.freeswitch.com&port=4321";
-    char token[] = "abcdefhgjojklmnopqrst";
-
-    blade_rpc_fields_t  fields;
-    fields.to = to;
-    fields.from = from;
-    fields.token = token;
-
-//     msgid = ks_rpcmessage_create_request("app1", "widget", &parms2, replyP);
-       msgid = blade_rpc_create_request(r_namespace, r_method, &fields, NULL, replyP);
-
-       if (!msgid) {
-               printf("process wombat:  create of next request failed\n");
-               return  JRPC_ERROR;
-       }
-
-       b0 = cJSON_PrintUnformatted(*replyP);
-       
-       if (!b0) {      
-        printf("process wombat:  create of next request cannot be formatted\n");
-        return  JRPC_ERROR;
-    }
-
-
-       printf("\nprocess wombat: next request\n%s\n\n", b0);    
-       
-
-    printf("\n\nexiting process_wombat with a reply to send\n");
-
-       return JRPC_SEND; 
-}
-
-static enum jrpc_status_t  process_wombat_prerequest(cJSON *request, cJSON **msg)
-{
-    printf("entering process_wombat_prerequest\n");
-    printf("exiting process_wombat_prerequest\n");
-    return JRPC_SEND;
-}
-
-static enum jrpc_status_t  process_wombat_postrequest(cJSON *request, cJSON **msg)
-{
-    printf("entering process_wombat_postrequest\n");
-    printf("exiting process_wombat_postrequest\n");
-    return JRPC_PASS;
-}
-
-
-
-static enum jrpc_status_t  process_wombat_response(cJSON *request, cJSON **msg)
-{
-       printf("entering process_wombat_response\n");
-       printf("exiting process_wombat_response\n");
-       return JRPC_PASS;
-}
-
-static enum jrpc_status_t  process_wombat_preresponse(cJSON *request, cJSON **msg)
-{
-
-    printf("entering process_wombat_preresponse\n");
-
-       cJSON *response = NULL;
-       cJSON *result = NULL;
-
-       cJSON *parms2 = NULL;
-
-       //ks_rpcmessageid_t msgid = ks_rpcmessage_create_request("app1", "widget", &parms2, msg);       
-
-    printf("exiting process_wombat_preresponse\n");
-    return JRPC_SEND;
-}
-
-static enum jrpc_status_t  process_wombat_postresponse(cJSON *request, cJSON **msg)
-{
-    printf("entering process_postwombat_response\n");
-    printf("exiting process_postwombat_response\n");
-    return JRPC_PASS;
-}
-
-
-
-
-static enum jrpc_status_t  process_badbunny( cJSON *msg, cJSON **response)
-{
-    printf("entering process_badbunny\n");
-
-    char *b0 = cJSON_PrintUnformatted(msg);
-    printf("\nRequest: %s\n\n", b0);
-    ks_pool_free(pool, &b0);
-
-    cJSON *respvalue;
-
-    ks_rpcmessageid_t msgid = ks_rpcmessage_create_errorresponse(msg, &respvalue, response);
-
-    char *b2 = cJSON_PrintUnformatted(*response);
-    printf("\nRequest: msgid %d\n%s\n\n", msgid, b2);
-    ks_pool_free(pool, &b2);
-
-       //cJSON *respvalue = cJSON_CreateNumber(1);
-       
-
-    char *b1 = cJSON_PrintUnformatted(*response);   //(*response);
-    printf("\nResponse: %s\n\n", b1);
-    ks_pool_free(pool, &b1);
-
-    printf("exiting process_badbunny\n");
-
-
-    return JRPC_SEND;
-}
-
-
-void test01()
-{
-       printf("**** testrpcmessages - test01 start\n"); fflush(stdout);
-
-       blade_rpc_declare_template("temp1", "1.0");
-
-       blade_rpc_register_template_function("temp1", "widget", process_widget, process_widget_response); 
-
-    blade_rpc_declare_namespace("app1", "1.0");
-
-       blade_rpc_register_function("app1", "wombat", process_wombat, process_wombat_response); 
-
-    blade_rpc_register_custom_request_function("app1", "wombat", process_wombat_prerequest, process_wombat_postresponse);
-    blade_rpc_register_custom_response_function("app1", "wombat", process_wombat_preresponse, process_wombat_postresponse);
-
-
-       /* message 1 */
-       /* --------- */
-    cJSON* request1 = NULL;
-    cJSON* parms1   = NULL;
-
-       printf("\n\n\n - test01 message1 - basic message\n\n\n");
-
-       ks_rpcmessageid_t msgid = ks_rpcmessage_create_request("app1", "wombat", &parms1, &request1);
-       if (msgid == 0) {
-               printf("test01.1: unable to create message 1\n");
-               return;
-       }       
-
-       if (!request1) {
-               printf("test01.1: No json returned from create request 1\n");
-               return;
-       }
-
-    cJSON_AddStringToObject(parms1, "hello", "cruel world");
-
-       char *pdata = cJSON_PrintUnformatted(request1);
-
-       if (!pdata) {
-               printf("test01.1: unable to parse cJSON object\n");
-               return;
-       }
-
-       printf("test01 request:\n%s\n", pdata);
-
-
-       blade_rpc_process_jsonmessage(request1);
-
-       cJSON_Delete(request1);
-
-       ks_pool_free(pool, &pdata);
-
-       printf("\ntest01.1 complete\n");
-
-       
-       /* message 2 */
-       /* --------- */
-
-    printf("\n\n\n test01 - message2 - test inherit\n\n\n");
-
-       blade_rpc_inherit_template("app1", "temp1");
-
-    cJSON* request2 = NULL;
-    cJSON* parms2   = cJSON_CreateObject();
-
-    cJSON_AddStringToObject(parms2, "hello2", "cruel world once again");
-
-    msgid = ks_rpcmessage_create_request("app1", "temp1.widget", &parms2, &request2); 
-       if (msgid == 0) {
-               printf("test01.2: failed to create a wombat\n");
-               return;
-       }
-
-    if (!request2) {
-        printf("test01.2: No json returned from create request 1\n");
-        return;
-    }
-
-    pdata = cJSON_PrintUnformatted(request2);
-
-       if (!pdata) {
-               printf("test01.2: unable to parse cJSON object\n");
-               return;
-       }
-
-    printf("\ntest01 request:\n%s\n\n\n", pdata);
-
-    blade_rpc_process_jsonmessage(request2);
-
-    cJSON_Delete(request2);
-    ks_pool_free(pool, &pdata);
-
-    printf("\ntest01.2 complete\n");
-
-       return;
-
-}
-
-void test02()
-{
-       printf("**** testrpcmessages - test02 start\n"); fflush(stdout);
-
-    blade_rpc_declare_namespace("app2", "1.0");
-
-    blade_rpc_register_function("app2", "wombat", process_wombat, process_wombat_response);
-
-    blade_rpc_inherit_template("app2", "temp1");
-
-    blade_rpc_register_custom_request_function("app2", "wombat", process_wombat_prerequest, process_wombat_postresponse);
-    blade_rpc_register_custom_response_function("app2", "wombat", process_wombat_preresponse, process_wombat_postresponse);
-
-    blade_rpc_register_function("app2", "bunny", process_badbunny, NULL);
-
-       char to[] = "tony@freeswitch.com/laptop?transport=wss&host=server1.freeswitch.com&port=1234";
-       char from[] = "colm@freeswitch.com/laptop?transport=wss&host=server2.freeswitch.com&port=4321";
-       char token[] = "abcdefhgjojklmnopqrst";
-
-       blade_rpc_fields_t  fields;
-       fields.to = to;
-       fields.from = from;
-       fields.token = token;
-
-
-       /* test the 4 different ways to handle param messages */
-
-       cJSON *params1 = NULL;
-       cJSON *request1;
-
-       ks_rpcmessageid_t msgid =  blade_rpc_create_request("app2", "temp1.widget2", &fields, &params1, &request1); 
-
-       if (!msgid) {
-                printf("test02.1: create_request failed\n");
-               return;
-       }
-
-    cJSON_AddStringToObject(params1, "hello", "cruel world");
-
-    char *pdata = cJSON_PrintUnformatted(request1);
-
-    if (!pdata) {
-        printf("test02.1: unable to parse cJSON object\n");
-        return;
-    }
-
-       printf("\ntest02.1 request:\n\n%s\n\n\n", pdata);
-
-       printf("\n\n -----------------------------------------\n\n");
-
-       ks_status_t s1 = blade_rpc_process_jsonmessage(request1);
-       if (s1 == KS_STATUS_FAIL) {
-               printf("test02.1:  process request1 failed\n");
-               return;
-       }
-       printf(" -----------------------------------------\n\n\n\n");
-
-       ks_pool_free(pool, &pdata);
-
-       cJSON *reply1 = NULL;
-       cJSON *response1 = NULL;
-
-       ks_rpcmessageid_t msgid2 = blade_rpc_create_response(request1, &reply1, &response1);
-
-       if (!msgid2) {
-               printf("test02.1: create_response failed\n");
-               return;
-       }
-
-       cJSON_AddNumberToObject(reply1, "code", 10);
-       cJSON_AddStringToObject(reply1, "farewell", "cruel server");
-
-       pdata = cJSON_PrintUnformatted(response1);
-
-       if (!pdata) {
-        printf("test02.1: unable to parse cJSON response object\n");
-        return;
-       }
-
-    printf("\ntest02.1 response:\n\n%s\n\n\n", pdata);
-
-    printf("\n\n -----------------------------------------\n\n");
-
-    s1 = blade_rpc_process_jsonmessage(response1);
-    if (s1 == KS_STATUS_FAIL) {
-        printf("test02.1:  process request1 failed\n");
-        return;
-    }
-
-    printf(" -----------------------------------------\n\n\n\n");
-
-
-       ks_pool_free(pool, &pdata);
-
-       printf("****  testrpcmessages - test02 finished\n"); fflush(stdout);
-
-       return;
-}
-
-
-void test02a()
-{
-       printf("**** testrpcmessages - test02a start\n"); fflush(stdout);
-
-       char to[] = "tony@freeswitch.com/laptop?transport=wss&host=server1.freeswitch.com&port=1234";
-       char from[] = "colm@freeswitch.com/laptop?transport=wss&host=server2.freeswitch.com&port=4321";
-       char token[] = "abcdefhgjojklmnopqrst";
-
-       blade_rpc_fields_t  fields;
-       fields.to = to;
-       fields.from = from;
-       fields.token = token;
-
-
-       /* test the 4 different ways to handle param messages */
-
-       cJSON *request1;
-
-       ks_rpcmessageid_t msgid =  blade_rpc_create_request("app2", "wombat", &fields, NULL, &request1);
-
-       if (!msgid) {
-               printf("test02.1: create_request failed\n");
-               return;
-       }
-
-       char *pdata = cJSON_PrintUnformatted(request1);
-
-       if (!pdata) {
-               printf("test02.1: unable to parse cJSON object\n");
-               return;
-       }
-
-       printf("\ntest02.1 request:\n\n%s\n\n\n", pdata);
-
-    printf("\n\n -----------------------------------------\n\n");
-
-    ks_status_t s1 = blade_rpc_process_jsonmessage(request1);
-    if (s1 == KS_STATUS_FAIL) {
-        printf("test02.1:  process request1 failed\n");
-        return;
-    }
-
-    printf(" -----------------------------------------\n\n\n\n");
-
-
-
-       
-       ks_pool_free(pool, &pdata);
-
-       cJSON *response1 = NULL;
-
-       ks_rpcmessageid_t msgid2 = blade_rpc_create_response(request1, NULL, &response1);
-
-       if (!msgid2) {
-               printf("test02.1: create_response failed\n");
-               return;
-       }
-
-       pdata = cJSON_PrintUnformatted(response1);
-
-       printf("\ntest02.1 response:\n\n%s\n\n\n", pdata);
-
-       ks_pool_free(pool, &pdata);
-
-       printf("****  testrpcmessages - test02a finished\n\n\n"); fflush(stdout);
-
-       return;
-}
-
-
-void test02b()
-{
-    printf("**** testrpcmessages - test02b start\n"); fflush(stdout);
-
-    char to[] = "tony@freeswitch.com/laptop?transport=wss&host=server1.freeswitch.com&port=1234";
-    char from[] = "colm@freeswitch.com/laptop?transport=wss&host=server2.freeswitch.com&port=4321";
-    char token[] = "abcdefhgjojklmnopqrst";
-
-    blade_rpc_fields_t  fields;
-    fields.to = to;
-    fields.from = from;
-    fields.token = token;
-
-
-    /* test the 4 different ways to handle param messages */
-
-    cJSON *params1 = cJSON_CreateNumber(4321);
-    cJSON *request1;
-
-    ks_rpcmessageid_t msgid =  blade_rpc_create_request("app2", "temp1.widget", &fields, &params1, &request1);
-
-    if (!msgid) {
-         printf("test02.1: create_request failed\n");
-        return;
-    }
-
-    char *pdata = cJSON_PrintUnformatted(request1);
-
-    if (!pdata) {
-        printf("test02.1: unable to parse cJSON object\n");
-        return;
-    }
-
-    printf("\ntest02.1 request:\n\n%s\n\n\n", pdata);
-       
-           ks_pool_free(pool, &pdata);
-
-    cJSON *reply1 = cJSON_CreateString("successful");
-    cJSON *response1 = NULL;
-
-    ks_rpcmessageid_t msgid2 = blade_rpc_create_response(request1, &reply1, &response1);
-
-    if (!msgid2) {
-        printf("test02.1: create_response failed\n");
-        return;
-    }
-
-     pdata = cJSON_PrintUnformatted(response1);
-
-    printf("\ntest02.1 response:\n\n%s\n\n\n", pdata);
-
-    ks_pool_free(pool, &pdata);
-
-    printf("****  testrpcmessages - test02b finished\n"); fflush(stdout);
-
-    return;
-}
-
-
-void test02c() 
-{
-
-    printf("**** testrpcmessages - test02c start\n"); fflush(stdout);
-
-    char to[] = "tony@freeswitch.com/laptop?transport=wss&host=server1.freeswitch.com&port=1234";
-    char from[] = "colm@freeswitch.com/laptop?transport=wss&host=server2.freeswitch.com&port=4321";
-    char token[] = "abcdefhgjojklmnopqrst";
-
-    blade_rpc_fields_t  fields;
-    fields.to    = to;
-    fields.from  = from;
-    fields.token = token;
-
-
-    /* test the 4 different ways to handle param messages */
-
-    cJSON *params1 = cJSON_CreateObject();
-
-       cJSON_AddStringToObject(params1, "string1", "here is a string");
-       cJSON_AddNumberToObject(params1, "number1", 4242);
-
-    cJSON *request1;
-
-    ks_rpcmessageid_t msgid =  blade_rpc_create_request("app2", "bunny", &fields, &params1, &request1);
-
-    if (!msgid) {
-         printf("test02.1: create_request failed\n");
-        return;
-    }
-
-    cJSON_AddStringToObject(params1, "hello", "cruel world");
-
-    char *pdata = cJSON_PrintUnformatted(request1);
-
-    if (!pdata) {
-        printf("test02.1: unable to parse cJSON object\n");
-        return;
-    }
-
-    printf("\ntest02.1 request:\n\n%s\n\n\n", pdata);
-       
-           ks_pool_free(pool, &pdata);
-
-
-    cJSON *reply1 = cJSON_CreateObject();
-    cJSON_AddNumberToObject(reply1, "code", 10);
-    cJSON_AddStringToObject(reply1, "farewell", "cruel server");
-
-
-    cJSON *response1 = NULL;
-
-    ks_rpcmessageid_t msgid2 = blade_rpc_create_response(request1, &reply1, &response1);
-
-    if (!msgid2) {
-        printf("test02.1: create_response failed\n");
-        return;
-    }
-
-
-     pdata = cJSON_PrintUnformatted(response1);
-
-    printf("\ntest02.1 response:\n\n%s\n\n\n", pdata);
-
-    ks_pool_free(pool, &pdata);
-
-    printf("****  testrpcmessages - test02c finished\n"); fflush(stdout);
-
-    return;
-}
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-/* test06  */
-/* ------  */
-
-static void *testnodelocking_ex1(ks_thread_t *thread, void *data)
-{
-       return NULL;
-}
-
-static void *testnodelocking_ex2(ks_thread_t *thread, void *data)
-{
-       return NULL;
-}
-
-
-void test06()
-{
-       printf("**** testmessages - test06 start\n"); fflush(stdout);
-
-       ks_thread_t *t0;
-       ks_thread_create(&t0, testnodelocking_ex1, NULL, pool);
-
-       ks_thread_t *t1;
-       ks_thread_create(&t1, testnodelocking_ex2, NULL, pool);
-
-       ks_thread_join(t1);
-       ks_thread_join(t0);
-
-       printf("\n\n* **testmessages - test06 -- threads complete\n\n"); fflush(stdout);
-
-       printf("**** testmessages - test06 start\n"); fflush(stdout);
-
-       return;
-}
-
-
-
-int main(int argc, char *argv[]) {
-
-       printf("testmessages - start\n");
-
-       int tests[100];
-       if (argc == 0) {
-               tests[0] = 1;
-               tests[1] = 2;
-               tests[2] = 3;
-               tests[3] = 4;
-               tests[4] = 5;
-       }
-       else {
-               for(int tix=1; tix<100 && tix<argc; ++tix) {
-                       long i = strtol(argv[tix], NULL, 0);
-                       tests[tix] = i;
-               }
-       }
-
-       ks_init();
-       ks_global_set_default_logger(7);
-
-
-       ks_status_t status;
-
-       status = ks_pool_open(&pool);
-
-       blade_rpc_init(pool);
-
-    blade_rpc_declare_template("temp1", "1.0");
-
-    blade_rpc_register_template_function("temp1", "widget", process_widget, process_widget_response);
-    blade_rpc_register_template_function("temp1", "widget2", process_widget, process_widget_response);
-    blade_rpc_register_template_function("temp1", "widget3", process_widget, process_widget_response);
-
-
-       for (int tix=0; tix<argc; ++tix) {
-
-
-               if (tests[tix] == 1) {
-                       test01();
-                       continue;
-               }
-
-               if (tests[tix] == 2) {
-                       test02();
-                       printf("\n\n");
-                       test02a();
-            printf("\n\n");
-                       test02b();
-            printf("\n\n");
-                       test02c();
-            printf("\n\n");
-                       continue;
-               }
-
-       }
-
-       return 0;
-}
index 57538f236b684a739e708656c0632ed25e9beb69..5a4bb8c850b325a8790d4474b64bd9deb3e8671c 100644 (file)
@@ -10,13 +10,13 @@ lib_LTLIBRARIES       = libks.la
 libks_la_SOURCES  = src/ks.c src/ks_string.c src/ks_json.c src/cJSON.c src/cJSON_Utils.c src/ks_thread.c src/ks_thread_pool.c src/ks_mutex.c src/ks_config.c
 libks_la_SOURCES += src/ks_log.c src/ks_socket.c src/ks_buffer.c src/ks_pool.c src/simclist.c
 libks_la_SOURCES += src/ks_time.c src/ks_printf.c src/ks_hash.c src/ks_q.c src/ks_dso.c # src/ks_dht.c
-libks_la_SOURCES += src/ks_ssl.c src/kws.c src/ks_rng.c src/ks_rpcmessage.c src/ks_base64.c
+libks_la_SOURCES += src/ks_ssl.c src/kws.c src/ks_rng.c src/ks_base64.c
 libks_la_SOURCES += src/utp/utp_api.cpp src/utp/utp_callbacks.cpp src/utp/utp_hash.cpp src/utp/utp_internal.cpp
 libks_la_SOURCES += src/utp/utp_packedsockaddr.cpp src/utp/utp_utils.cpp src/ks_bencode.c
 libks_la_SOURCES += src/dht/ks_dht.c src/dht/ks_dht_datagram.c src/dht/ks_dht_endpoint.c src/dht/ks_dht_message.c src/dht/ks_dht_transaction.c
 libks_la_SOURCES += src/dht/ks_dht_job.c src/dht/ks_dht_search.c src/dht/ks_dht_publish.c src/dht/ks_dht_distribute.c src/dht/ks_dht_storageitem.c
 libks_la_SOURCES += src/dht/ks_dht_bucket.c
-libks_la_SOURCES += crypt/aeskey.c crypt/aestab.c crypt/sha2.c crypt/twofish.c crypt/aes_modes.c crypt/aescrypt.c crypt/twofish_cfb.c 
+libks_la_SOURCES += crypt/aeskey.c crypt/aestab.c crypt/sha2.c crypt/twofish.c crypt/aes_modes.c crypt/aescrypt.c crypt/twofish_cfb.c
 #aes.h aescpp.h brg_endian.h aesopt.h aestab.h brg_types.h sha2.h twofish.h
 libks_la_SOURCES += src/ks_acl.c
 
@@ -29,14 +29,10 @@ library_include_HEADERS = src/include/ks_config.h src/include/ks.h src/include/k
 library_include_HEADERS += src/include/ks_thread_pool.h src/include/ks_cJSON.h src/include/ks_cJSON_Utils.h
 library_include_HEADERS += src/include/ks_pool.h src/include/simclist.h src/include/ks_time.h src/include/ks_q.h src/include/ks_socket.h
 library_include_HEADERS += src/include/ks_dso.h src/include/ks_platform.h src/include/ks_types.h # src/include/ks_rng.h src/include/ks_dht.h
-library_include_HEADERS += src/include/ks_printf.h src/include/ks_hash.h src/include/ks_ssl.h src/include/kws.h 
-library_include_HEADERS += src/include/ks_rpcmessage.h src/include/ks_base64.h
+library_include_HEADERS += src/include/ks_printf.h src/include/ks_hash.h src/include/ks_ssl.h src/include/kws.h
+library_include_HEADERS += src/include/ks_base64.h
 library_include_HEADERS += src/utp/utp_internal.h src/utp/utp.h src/utp/utp_types.h src/utp/utp_callbacks.h src/utp/utp_templates.h
 library_include_HEADERS += src/utp/utp_hash.h src/utp/utp_packedsockaddr.h src/utp/utp_utils.h src/include/ks_utp.h src/include/ks_acl.h
 
 tests: libks.la
        $(MAKE) -C test tests
-
-
-
-
index 9f0e511ba441ba8568f5984817929884da6ffe0d..f7b88d002d74722cf17595c4ec2f596b81e463bc 100644 (file)
@@ -1,23 +1,23 @@
 /*
  * Copyright (c) 2007-2014, Anthony Minessale II
  * All rights reserved.
- * 
+ *
  * Redistribution and use in source and binary forms, with or without
  * modification, are permitted provided that the following conditions
  * are met:
- * 
+ *
  * * Redistributions of source code must retain the above copyright
  * notice, this list of conditions and the following disclaimer.
- * 
+ *
  * * Redistributions in binary form must reproduce the above copyright
  * notice, this list of conditions and the following disclaimer in the
  * documentation and/or other materials provided with the distribution.
- * 
+ *
  * * Neither the name of the original author; nor the names of any contributors
  * may be used to endorse or promote products derived from this software
  * without specific prior written permission.
- * 
- * 
+ *
+ *
  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
@@ -137,7 +137,6 @@ KS_DECLARE(void) ks_random_string(char *buf, uint16_t len, char *set);
 #include "ks_bencode.h"
 #include "ks_rng.h"
 #include "ks_acl.h"
-#include "ks_rpcmessage.h"
 #include "ks_base64.h"
 
 KS_END_EXTERN_C
diff --git a/libs/libks/src/ks_rpcmessage.c b/libs/libks/src/ks_rpcmessage.c
deleted file mode 100644 (file)
index e950c69..0000000
+++ /dev/null
@@ -1,317 +0,0 @@
-/*
- * Copyright (c) 2017 FreeSWITCH Solutions LLC
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- *
- * * Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * * Neither the name of the original author; nor the names of any contributors
- * may be used to endorse or promote products derived from this software
- * without specific prior written permission.
- *
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER
- * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
- * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
- * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
- * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
- * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
- * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#pragma GCC optimize ("O0")
-
-
-#include <ks.h>
-#include <ks_rpcmessage.h>
-#include <ks_buffer.h>
-
-struct 
-{
-
-    ks_mutex_t *id_mutex;
-    uint32_t   message_id;
-
-    ks_pool_t  *pool;
-
-} handle = {NULL, 0, NULL};
-
-const char PROTOCOL[] = "jsonrpc";
-const char PROTOCOL_VERSION[] = "2.0";
-const char ID[]      = "id";
-const char METHOD[]  = "method";
-const char PARAMS[]  = "params";
-const char ERROR[]   = "error";
-const char RESULT[]  = "result";
-
-
-
-KS_DECLARE(void*) ks_json_pool_alloc(ks_size_t size)
-{
-       return ks_pool_alloc(handle.pool, size);
-}
-
-KS_DECLARE(void) ks_json_pool_free(void *ptr)
-{
-    ks_pool_free(handle.pool, &ptr);
-}
-
-
-KS_DECLARE(void) ks_rpcmessage_init(ks_pool_t* pool)
-{
-       if (!handle.id_mutex) {
-               ks_mutex_create(&handle.id_mutex, KS_MUTEX_FLAG_DEFAULT, pool);
-           handle.pool = pool;
-
-               cJSON_Hooks hooks;
-               hooks.malloc_fn = ks_json_pool_alloc;
-               hooks.free_fn   = ks_json_pool_free;
-               cJSON_InitHooks(&hooks);
-       }
-       return;
-}
-
-static uint32_t ks_rpcmessage_next_id()
-{
-    uint32_t message_id;
-
-    ks_mutex_lock(handle.id_mutex);
-
-    ++handle.message_id;
-
-    if (!handle.message_id) {
-                ++handle.message_id;
-       }
-
-       message_id = handle.message_id;
-
-    ks_mutex_unlock(handle.id_mutex);
-
-    return message_id;
-}
-
-
-static cJSON *ks_rpcmessage_new(uint32_t id)
-{
-    cJSON *obj = cJSON_CreateObject();
-    cJSON_AddItemToObject(obj, PROTOCOL, cJSON_CreateString(PROTOCOL_VERSION));
-
-    if (id) {
-        cJSON_AddItemToObject(obj, ID, cJSON_CreateNumber(id));
-    }
-
-    return obj;
-}
-
-static cJSON *ks_rpcmessage_dup(cJSON *msgid)
-{
-    cJSON *obj = cJSON_CreateObject();
-    cJSON_AddItemToObject(obj, PROTOCOL, cJSON_CreateString(PROTOCOL_VERSION));
-
-    if (msgid) {
-        cJSON_AddItemToObject(obj, ID,  cJSON_Duplicate(msgid, 0));
-    }
-
-    return obj;
-}
-
-KS_DECLARE(ks_bool_t) ks_rpcmessage_isrequest(cJSON *msg)
-{
-    cJSON *result = cJSON_GetObjectItem(msg, RESULT);
-    cJSON *error  = cJSON_GetObjectItem(msg, ERROR);
-
-       if (result || error) {
-               return  KS_FALSE;
-       }
-
-    return KS_TRUE;
-}
-
-KS_DECLARE(ks_bool_t) ks_rpcmessage_isrpc(cJSON *msg)
-{
-    cJSON *rpc = cJSON_GetObjectItem(msg, PROTOCOL);
-
-    if (rpc) {
-        return  KS_FALSE;
-    }
-
-    return KS_TRUE;
-}
-
-
-
-
-KS_DECLARE(ks_rpcmessageid_t) ks_rpcmessage_create_request(char *namespace,
-                                                                                               char *command,
-                                                                                               cJSON **paramsP,
-                                                                                               cJSON **requestP)
-{
-    cJSON *msg, *params = NULL;
-       *requestP = NULL;
-
-       ks_rpcmessageid_t msgid = ks_rpcmessage_next_id();
-    msg = ks_rpcmessage_new(msgid);
-
-    if (paramsP) {
-
-               if (*paramsP) {   /* parameters have been passed */
-                       params = *paramsP;
-               }
-               else {
-                       params = cJSON_CreateObject();
-                       *paramsP = params;
-               }
-
-               cJSON_AddItemToObject(msg, PARAMS, params);
-    }
-
-    char fqcommand[KS_RPCMESSAGE_FQCOMMAND_LENGTH];
-    memset(fqcommand, 0, sizeof(fqcommand));
-
-       sprintf(fqcommand, "%s.%s", namespace, command);
-
-    cJSON_AddItemToObject(msg, METHOD, cJSON_CreateString(fqcommand));
-
-       *requestP = msg;
-    return msgid;
-}
-
-KS_DECLARE(ks_size_t) ks_rpc_create_buffer(char *namespace,
-                                            char *method,
-                                            cJSON **params,
-                                            ks_buffer_t *buffer)
-{
-
-       cJSON *message;
-
-       ks_rpcmessageid_t msgid = ks_rpcmessage_create_request(namespace, method, params, &message);
-
-       if (!msgid) {
-               return 0;
-       }
-
-       if ( (*params)->child == NULL) {
-               cJSON_AddNullToObject(*params, "bladenull");
-       }
-
-       const char* b = cJSON_PrintUnformatted(message);
-       ks_size_t size = strlen(b);
-
-       ks_buffer_write(buffer, b, size);
-       cJSON_Delete(message);
-
-       return size;    
-}
-
-
-static ks_rpcmessageid_t ks_rpcmessage_get_messageid(const cJSON *msg, cJSON **cmsgidP)
-{
-       ks_rpcmessageid_t msgid = 0;
-
-       cJSON *cmsgid = cJSON_GetObjectItem(msg, ID);
-
-       if (cmsgid->type == cJSON_Number) {
-               msgid = (ks_rpcmessageid_t) cmsgid->valueint;
-       }
-       
-       *cmsgidP = cmsgid;      
-
-       return msgid;
-} 
-
-
-static ks_rpcmessageid_t ks_rpcmessage_new_response(
-                                                const cJSON *request,
-                                                cJSON **result,
-                                                cJSON **pmsg)
-{
-    cJSON *respmsg = NULL;
-    cJSON *cmsgid  = NULL;
-
-    cJSON *command = cJSON_GetObjectItem(request, METHOD);
-
-       ks_rpcmessageid_t msgid = ks_rpcmessage_get_messageid(request, &cmsgid );
-
-    if (!msgid || !command) {
-        return 0;
-    }
-
-    *pmsg = respmsg = ks_rpcmessage_dup(cmsgid);
-
-    cJSON_AddItemToObject(respmsg, METHOD, cJSON_Duplicate(command, 0));
-
-    if (result && *result) {
-        cJSON_AddItemToObject(respmsg, RESULT, *result);
-    }
-
-    return msgid;
-}
-
-
-KS_DECLARE(ks_rpcmessageid_t) ks_rpcmessage_create_response(
-                                                                                               const cJSON *request,
-                                                                                               cJSON **resultP,
-                                                                                               cJSON **responseP)
-{
-       ks_rpcmessageid_t msgid = ks_rpcmessage_new_response(request, resultP, responseP);
-
-       cJSON *respmsg = *responseP;
-
-    if (msgid) {
-
-               if (resultP && *resultP == NULL) {
-                       cJSON *result = cJSON_CreateObject();
-                       *resultP = result;
-                       cJSON_AddItemToObject(respmsg, RESULT, result);
-               }
-       }
-
-    return msgid;
-}
-
-KS_DECLARE(ks_rpcmessageid_t) ks_rpcmessage_create_errorresponse( 
-                                                                                               const cJSON *request, 
-                                                                                               cJSON **errorP, 
-                                                                                               cJSON **responseP)
-{
-       ks_rpcmessageid_t msgid = ks_rpcmessage_new_response(request, NULL, responseP);
-       cJSON *respmsg = *responseP;
-
-       if (msgid) { 
-
-               if (errorP && *errorP == NULL) {
-                       cJSON *error = cJSON_CreateObject();
-                       *errorP = error;
-                       cJSON_AddItemToObject(respmsg, ERROR, error);
-               }
-               else if (errorP && *errorP) {
-                       cJSON_AddItemToObject(*responseP, ERROR, *errorP);      
-               }
-       }
-
-    return msgid;
-}
-
-
-/* For Emacs:
- * Local Variables:
- * mode:c
- * indent-tabs-mode:t
- * tab-width:4
- * c-basic-offset:4
- * End:
- * For VIM:
- * vim:set softtabstop=4 shiftwidth=4 tabstop=4 noet:
- */
index 0b85a468c4fa375f8036472bf26ba29340b878ec..cffc18bdcdd5f81f9a9e8a30d88585b906e5603d 100644 (file)
@@ -1,14 +1,9 @@
 AM_CFLAGS += -I$(abs_top_srcdir)/src/include -g -ggdb -O0 $(openssl_CFLAGS)
 TEST_LDADD = $(abs_top_builddir)/libks.la $(openssl_LIBS)
-check_PROGRAMS = 
+check_PROGRAMS =
 
 EXTRA_DIST = tap.h
 
-check_PROGRAMS += testmessages
-testmessages_SOURCES = testmessages.c tap.c
-testmessages_CFLAGS = $(AM_CFLAGS)
-testmessages_LDADD = $(TEST_LDADD)
-
 check_PROGRAMS += testbuckets
 testbuckets_SOURCES = testbuckets.c tap.c
 testbuckets_CFLAGS = $(AM_CFLAGS)
@@ -96,7 +91,7 @@ nodeidgen_LDADD = $(TEST_LDADD)
 
 #check_PROGRAMS += libtorrent_example
 #libtorrent_example_SOURCES = libtorrent-example.c
-#libtorrent_example_CFLAGS = $(AM_CFLAGS) 
+#libtorrent_example_CFLAGS = $(AM_CFLAGS)
 #libtorrent_example_LDADD = $(abs_top_builddir)/libks.la $(abs_top_builddir)/test/libtorrent.so /usr/lib/x86_64-linux-gnu/libboost_system.a $(openssl_LIBS) -ledit -lpthread -ltorrent-rasterbar -lstdc++
 
 TESTS=$(check_PROGRAMS)
@@ -108,4 +103,3 @@ $(abs_top_builddir)/test/libtorrent.so: $(abs_top_builddir)/test/libtorrent.o
 
 $(abs_top_builddir)/test/libtorrent.o: $(abs_top_builddir)/test/libtorrent.cpp
        g++ -c -fPIC -o $(abs_top_builddir)/test/libtorrent.o -I$(abs_top_builddir)/test/ $(abs_top_builddir)/test/libtorrent.cpp
-
diff --git a/libs/libks/test/testmessages.c b/libs/libks/test/testmessages.c
deleted file mode 100644 (file)
index 7609cf6..0000000
+++ /dev/null
@@ -1,124 +0,0 @@
-#pragma GCC diagnostic ignored "-Wunused-but-set-variable"
-#pragma GCC diagnostic ignored "-Wunused-variable"
-#pragma GCC diagnostic ignored "-Wunused-function"
-
-#include "../src/include/ks_rpcmessage.h"
-
-#pragma GCC optimize ("O0")
-
-
-ks_pool_t *pool;
-
-
-void test01()
-{
-       printf("**** testrpcmessages - test01 start\n\n"); fflush(stdout);
-
-       cJSON* request1  = NULL;
-       cJSON* parms1    = NULL;
-    cJSON* response1 = NULL;
-
-                                                                                                                /*namespace, method,  params, **request */     
-       ks_rpcmessageid_t msgid = ks_rpcmessage_create_request("app1",     "func1", &parms1, &request1);
-       if (msgid == 0) {
-               printf("message create failed %d\n", msgid);
-       }       
-       
-       cJSON_AddStringToObject(parms1, "hello", "cruel world");
-       char* data = cJSON_PrintUnformatted(request1);  
-       
-       printf("test01 request1: %d\n%s\n\n", msgid, data);
-    ks_json_pool_free(data);
-
-
-       /* convert to buffer */
-       cJSON* parms2  = NULL;
-       ks_buffer_t *buffer;
-
-       ks_buffer_create(&buffer, 256, 256, 1024);
-
-    ks_size_t n = ks_rpc_create_buffer("app2", "func2", &parms2, buffer);
-
-       ks_size_t size =  ks_buffer_len(buffer);
-       char *b = (char *)ks_pool_alloc(pool, size+1);
-       ks_buffer_read(buffer, b, size); 
-       
-       printf("test01 request2: %zd %zd  from ks_buffer\n%s\n\n\n", n, size, b); 
-       
-
-       /* create message 3 */
-       
-       cJSON *parms3 = cJSON_CreateNumber(1);
-    cJSON *request3  = NULL;
-
-    msgid = ks_rpcmessage_create_request("app1", "badbunny",  &parms3, &request3);
-       data = cJSON_PrintUnformatted(request3);
-       printf("\ntest01i request: %d\n%s\n\n", msgid, data);
-
-       cJSON *response3 = NULL;
-
-       ks_rpcmessage_create_response(request3,  NULL, &response3);  
-
-       data = cJSON_PrintUnformatted(response3);
-    printf("\ntest01 response3: %d\n%s\n\n", msgid, data);
-    ks_json_pool_free(data);
-    cJSON_Delete(request3);
-    cJSON_Delete(response3);
-       
-       printf("**** testrpcmessages - test01 complete\n\n\n"); fflush(stdout);
-}
-
-void test02()
-{
-       printf("**** testmessages - test02 start\n"); fflush(stdout);
-
-       printf("****  testmessages - test02 finished\n"); fflush(stdout);
-
-       return;
-}
-
-
-
-int main(int argc, char *argv[]) {
-
-       printf("testmessages - start\n");
-
-       int tests[100];
-       if (argc == 1) {
-               tests[0] = 1;
-       }
-       else {
-               for(int tix=1; tix<100 && tix<argc; ++tix) {
-                       long i = strtol(argv[tix], NULL, 0);
-                       tests[tix] = i;
-               }
-       }
-
-       ks_init();
-       ks_global_set_default_logger(7);
-
-
-       ks_status_t status;
-
-       status = ks_pool_open(&pool);
-
-
-       for (int tix=0; tix<argc; ++tix) {
-
-               if (tests[tix] == 1) {
-                       ks_rpcmessage_init(pool);
-                       test01();
-                       continue;
-               }
-
-               if (tests[tix] == 2) {
-                       ks_rpcmessage_init(pool);
-                       test02();
-                       continue;
-               }
-
-       }
-
-       return 0;
-}