summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIngo Huerner <ingo.huerner@xse.de>2013-03-27 14:17:43 +0100
committerIngo Huerner <ingo.huerner@xse.de>2013-03-27 14:17:43 +0100
commit9b1db7aadd4e326a24c35a7b2408b8e1d3958026 (patch)
treeeede6ccecbcc07cbe9aad180c450b55ae6fad9e1
parent1e9bbac24b54622b43c3ed04a639506cdb905252 (diff)
downloadpersistence-client-library-9b1db7aadd4e326a24c35a7b2408b8e1d3958026.tar.gz
Implemented changed notification for shared data; persistence_client_library_dbus_test.c has beend used for receiving notifications
-rw-r--r--README11
-rw-r--r--include/persistence_client_library_key.h33
-rw-r--r--include_protected/persistence_client_library_data_organization.h6
-rw-r--r--include_protected/persistence_client_library_db_access.h4
-rw-r--r--src/persistence_client_library_data_organization.c2
-rw-r--r--src/persistence_client_library_db_access.c74
-rw-r--r--src/persistence_client_library_dbus_service.c61
-rw-r--r--src/persistence_client_library_key.c14
-rw-r--r--src/persistence_client_library_pas_interface.c34
-rw-r--r--test/data/Data.tar.gzbin98914 -> 131411 bytes
-rw-r--r--test/persistence_client_library_dbus_test.c24
-rw-r--r--test/persistence_client_library_test.c31
-rw-r--r--test/persistence_lifeCycle_mockup.c7
13 files changed, 257 insertions, 44 deletions
diff --git a/README b/README
index e0bfa5d..8d4307b 100644
--- a/README
+++ b/README
@@ -1,6 +1,7 @@
Environment
The Persistence Client Library has been developed using Ubuntu 11.10
+
Required packages
* automotive-dlt: available via GENIVI projects ==> http://git.projects.genivi.org/?p=dlt-daemon.git;a=summary
* Itzam/C: download from here ==> http://www.coyotegulch.com/products/itzam/c/index.html
@@ -8,6 +9,7 @@ Required packages
* autotools: install via Synaptic Package Manger or use apt-get
* GNU c compiler: install via Synaptic Package Manger or use apt-get
+
Known issues:
* Patch Itzam/C configure.ac file:
- replace in the Itzam/C configure.ac GENERIC_LIBRARY_NAME=libitzam with GENERIC_LIBRARY_NAME=itzam
@@ -20,3 +22,12 @@ To build the client library perform the following steps:
* "autoreconf -vi"
* "./configure --enable-tests"
* "make"
+
+
+How to run:
+After building the client library and the test code the test data needs to be copied to the appropriate place.
+The test data is located in the test subdirectory test/data/Data.tar.gz and needs be extracted to the root/Data folder.
+
+
+
+
diff --git a/include/persistence_client_library_key.h b/include/persistence_client_library_key.h
index 72acf65..876d951 100644
--- a/include/persistence_client_library_key.h
+++ b/include/persistence_client_library_key.h
@@ -34,7 +34,34 @@ extern "C" {
#define PERSIST_KEYVALUEAPI_INTERFACE_VERSION (0x03000000U)
+/**
+* status returned in notification structure
+*/
+typedef enum _PersistenceNotifyStatus_e
+{
+ pclNotifyStatus_no_changed = 0,
+ pclNotifyStatus_created,
+ pclNotifyStatus_changed,
+ pclNotifyStatus_deleted,
+ /* insert new_ entries here .. */
+ pclNotifyStatus_lastEntry
+} PersistenceNotifyStatus_e;
+
+
+/**
+* structure to return in case of notification
+*/
+typedef struct _PersistenceNotification_s
+{
+ PersistenceNotifyStatus_e pclKeyNotify_Status;
+ unsigned int ldbid;
+ const char * resource_id;
+ unsigned int user_no;
+ unsigned int seat_no;
+} PersistenceNotification_s;
+
+typedef int(* changeNotifyCallback_t)(PersistenceNotification_s * notifyStruct);
/**
* @brief delete persistent data
@@ -120,10 +147,11 @@ int pclKeyHandleReadData(int key_handle, unsigned char* buffer, int buffer_size)
* @brief register a change notification for persistent data
*
* @param key_handle key value handle return by key_handle_open()
+ * @param callback notification callback
*
* @return positive value: registration OK; On error a negative value will be returned with th follwoing error codes:
*/
-int pclKeyHandleRegisterNotifyOnChange(int key_handle);
+int pclKeyHandleRegisterNotifyOnChange(int key_handle, changeNotifyCallback_t callback);
@@ -164,10 +192,11 @@ int pclKeyReadData(unsigned int ldbid, const char* resource_id, unsigned int use
* @param resource_id the resource ID
* @param user_no the user ID; user_no=0 can not be used as user-ID beacause ‘0’ is defined as System/node
* @param seat_no the seat number
+ * @param callback notification callback
*
* @return positive value: registration OK; On error a negative value will be returned with th follwoing error codes:
*/
-int pclKeyRegisterNotifyOnChange(unsigned int ldbid, const char* resource_id, unsigned int user_no, unsigned int seat_no);
+int pclKeyRegisterNotifyOnChange(unsigned int ldbid, const char* resource_id, unsigned int user_no, unsigned int seat_no, changeNotifyCallback_t callback);
diff --git a/include_protected/persistence_client_library_data_organization.h b/include_protected/persistence_client_library_data_organization.h
index ca28be8..6151aa4 100644
--- a/include_protected/persistence_client_library_data_organization.h
+++ b/include_protected/persistence_client_library_data_organization.h
@@ -27,6 +27,8 @@ extern "C" {
#define PERSIST_CLIENT_LIBRARY_DATA_ORGANIZATION_INTERFACE_VERSION (0x01000000U)
#include "../include/persistence_client_library_error_def.h"
+#include "../include/persistence_client_library_key.h"
+
#include <string.h>
#include <stdio.h>
@@ -127,6 +129,10 @@ extern char gAppId[MaxAppNameLen];
/// max key value data size
extern int gMaxKeyValDataSize;
+
+extern int(* gChangeNotifyCallback)(PersistenceNotification_s * notifyStruct);
+
+
#ifdef __cplusplus
}
#endif
diff --git a/include_protected/persistence_client_library_db_access.h b/include_protected/persistence_client_library_db_access.h
index 7e7c0aa..1958b0a 100644
--- a/include_protected/persistence_client_library_db_access.h
+++ b/include_protected/persistence_client_library_db_access.h
@@ -29,6 +29,7 @@ extern "C" {
#include "persistence_client_library_data_organization.h"
#include "persistence_client_library_rc_table.h"
+#include "persistence_client_library_key.h"
@@ -116,7 +117,8 @@ void pers_db_close_all();
*
* @return 0 of registration was successfull; -1 if registration failes
*/
-int persistence_reg_notify_on_change(char* dbPath, char* key);
+int persistence_reg_notify_on_change(char* dbPath, char* key, unsigned int ldbid, unsigned int user_no, unsigned int seat_no,
+ changeNotifyCallback_t callback);
diff --git a/src/persistence_client_library_data_organization.c b/src/persistence_client_library_data_organization.c
index b53d15f..f88becb 100644
--- a/src/persistence_client_library_data_organization.c
+++ b/src/persistence_client_library_data_organization.c
@@ -77,6 +77,6 @@ char gAppId[MaxAppNameLen];
int gMaxKeyValDataSize = defaultMaxKeyValDataSize;
-
+int(* gChangeNotifyCallback)(PersistenceNotification_s * notifyStruct);
diff --git a/src/persistence_client_library_db_access.c b/src/persistence_client_library_db_access.c
index 778cd03..5fdb09b 100644
--- a/src/persistence_client_library_db_access.c
+++ b/src/persistence_client_library_db_access.c
@@ -22,6 +22,9 @@
#include "persistence_client_library_custom_loader.h"
#include "persistence_client_library_itzam_errors.h"
+#include "persistence_client_library_dbus_service.h"
+
+#include <dbus/dbus.h>
#include <string.h>
#include <stdio.h>
#include <stdlib.h>
@@ -219,8 +222,8 @@ int pers_db_write_key(char* dbPath, char* key, PersistenceInfo_s* info, unsigned
{
int write_size = -1;
- if( PersistenceStorage_shared == info->configKey.storage
- || PersistenceStorage_local == info->configKey.storage)
+ if( PersistenceStorage_local == info->configKey.storage
+ || PersistenceStorage_shared == info->configKey.storage )
{
write_size = buffer_size;
itzam_btree* btree = NULL;
@@ -260,6 +263,46 @@ int pers_db_write_key(char* dbPath, char* key, PersistenceInfo_s* info, unsigned
fprintf(stderr, "\npersistence_set_data ==> Insert Itzam problem: %s\n", STATE_MESSAGES[state]);
write_size = EPERS_DB_ERROR_INTERNAL;
}
+
+ if(PersistenceStorage_shared == info->configKey.storage)
+ {
+ // send changed notification
+ DBusMessage* message;
+ char ldbid_array[12];
+ char user_array[12];
+ char seat_array[12];
+ const char* ldbid_ptr = ldbid_array;
+ const char* user_ptr = user_array;
+ const char* seat_ptr = seat_array;
+
+ memset(ldbid_array, 0, 12);
+ memset(user_array, 0, 12);
+ memset(seat_array, 0, 12);
+
+ // dbus_bus_add_match is used for the notification mechanism,
+ // and this works only for type DBUS_TYPE_STRING as message arguments
+ // this is the reason to use string instead of integer types directly
+ snprintf(ldbid_array, 12, "%d", info->context.ldbid);
+ snprintf(user_array, 12, "%d", info->context.user_no);
+ snprintf(seat_array, 12, "%d", info->context.seat_no);
+
+ message = dbus_message_new_signal("/org/genivi/persistence/adminconsumer", // const char *path,
+ "org.genivi.persistence.adminconsumer", // const char *interface,
+ "PersistenceValueChanged" ); // const char *name
+
+ dbus_message_append_args(message,
+ DBUS_TYPE_STRING, &key,
+ DBUS_TYPE_STRING, &ldbid_ptr,
+ DBUS_TYPE_STRING, &user_ptr,
+ DBUS_TYPE_STRING, &seat_ptr,
+ DBUS_TYPE_INVALID);
+
+ // Send the signal
+ dbus_connection_send(get_dbus_connection(), message, NULL);
+
+ // Free the signal now we have finished with it
+ dbus_message_unref(message);
+ }
}
else
{
@@ -422,9 +465,34 @@ int pers_db_delete_key(char* dbPath, char* dbKey, PersistenceInfo_s* info)
}
-int persistence_reg_notify_on_change(char* dbPath, char* key)
+int persistence_reg_notify_on_change(char* dbPath, char* key, unsigned int ldbid, unsigned int user_no, unsigned int seat_no,
+ changeNotifyCallback_t callback)
{
int rval = -1;
+ DBusError error;
+ dbus_error_init (&error);
+ char rule[300];
+ char ldbid_array[12];
+ char user_array[12];
+ char seat_array[12];
+
+ memset(ldbid_array, 0, 12);
+ memset(user_array, 0, 12);
+ memset(seat_array, 0, 12);
+
+ // assign callback
+ gChangeNotifyCallback = callback;
+
+ // dbus_bus_add_match works only for type DBUS_TYPE_STRING as message arguments
+ // this is the reason to use string instead of integer types directly
+ snprintf(ldbid_array, 12, "%d", ldbid);
+ snprintf(user_array, 12, "%d", user_no);
+ snprintf(seat_array, 12, "%d", seat_no);
+
+ snprintf(rule, 256, "type='signal',interface='org.genivi.persistence.adminconsumer',member='PersistenceValueChanged',path='/org/genivi/persistence/adminconsumer',arg0='%s',arg1='%s',arg2='%s',arg3='%s'",
+ key, ldbid_array, user_array, seat_array);
+
+ dbus_bus_add_match(get_dbus_connection(), rule, &error);
return rval;
}
diff --git a/src/persistence_client_library_dbus_service.c b/src/persistence_client_library_dbus_service.c
index fd24232..d82d2e7 100644
--- a/src/persistence_client_library_dbus_service.c
+++ b/src/persistence_client_library_dbus_service.c
@@ -20,6 +20,7 @@
#include "persistence_client_library_dbus_service.h"
#include "persistence_client_library_lc_interface.h"
#include "persistence_client_library_pas_interface.h"
+#include "../include_protected/persistence_client_library_data_organization.h"
#include <stdio.h>
#include <errno.h>
@@ -63,7 +64,6 @@ typedef struct SPollInfo
/// polling information
static tPollInfo gPollInfo;
-
/// dbus connection
DBusConnection* gDbusConn = NULL;
@@ -107,7 +107,7 @@ static DBusHandlerResult handleObjectPathMessageFallback(DBusConnection * connec
// org.genivi.persistence.admin S I G N A L
if((0==strcmp("org.genivi.persistence.admin", dbus_message_get_interface(message))))
{
- // printf("checkPersAdminSignalInterface '%s' -> '%s'\n", dbus_message_get_interface(message), dbus_message_get_member(message));
+ printf("checkPersAdminSignalInterface '%s' -> '%s'\n", dbus_message_get_interface(message), dbus_message_get_member(message));
if(dbus_message_get_type(message) == DBUS_MESSAGE_TYPE_SIGNAL)
{
printf(" checkPersAdminSignal signal\n");
@@ -123,7 +123,64 @@ static DBusHandlerResult handleObjectPathMessageFallback(DBusConnection * connec
}
}
}
+ // org.genivi.persistence.admin S I G N A L
+ else if((0==strcmp("org.genivi.persistence.adminconsumer", dbus_message_get_interface(message))))
+ {
+ printf("checkPersAdminconsumerSignalInterface '%s' -> '%s'\n", dbus_message_get_interface(message), dbus_message_get_member(message));
+ if(dbus_message_get_type(message) == DBUS_MESSAGE_TYPE_SIGNAL)
+ {
+ if((0==strcmp("PersistenceValueChanged", dbus_message_get_member(message))))
+ {
+ DBusError error;
+ DBusMessage *reply;
+ dbus_error_init (&error);
+ char* ldbid;
+ char* user_no;
+ char* seat_no;
+
+ printf("PersistenceValueChanged signal\n");
+ // to do handle signal
+ PersistenceNotification_s notifyStruct;
+ notifyStruct.pclKeyNotify_Status = pclNotifyStatus_changed;
+
+ if (!dbus_message_get_args (message, &error, DBUS_TYPE_STRING, &notifyStruct.resource_id,
+ DBUS_TYPE_STRING, &ldbid,
+ DBUS_TYPE_STRING, &user_no,
+ DBUS_TYPE_STRING, &seat_no,
+ DBUS_TYPE_INVALID))
+ {
+ reply = dbus_message_new_error(message, error.name, error.message);
+
+ if (reply == 0)
+ {
+ //DLT_LOG(mgrContext, DLT_LOG_ERROR, DLT_STRING("DBus No memory"));
+ printf("DBus No memory\n");
+ }
+ if (!dbus_connection_send(connection, reply, 0))
+ {
+ //DLT_LOG(mgrContext, DLT_LOG_ERROR, DLT_STRING("DBus No memory"));
+ printf("DBus No memory\n");
+ }
+
+ result = DBUS_HANDLER_RESULT_NOT_YET_HANDLED;;
+ dbus_message_unref(reply);
+ }
+ else
+ {
+ notifyStruct.ldbid = atoi(ldbid);
+ notifyStruct.user_no = atoi(user_no);
+ notifyStruct.seat_no = atoi(seat_no);
+
+ // call the registered callback function
+ gChangeNotifyCallback(&notifyStruct);
+
+ result = DBUS_HANDLER_RESULT_HANDLED;
+ }
+ dbus_connection_flush(connection);
+ }
+ }
+ }
// org.genivi.persistence.admin P R O P E R T Y
else if((0==strcmp("org.freedesktop.DBus.Properties", dbus_message_get_interface(message))))
{
diff --git a/src/persistence_client_library_key.c b/src/persistence_client_library_key.c
index 7a3df3f..291c6c8 100644
--- a/src/persistence_client_library_key.c
+++ b/src/persistence_client_library_key.c
@@ -204,7 +204,7 @@ int pclKeyHandleReadData(int key_handle, unsigned char* buffer, int buffer_size)
-int pclKeyHandleRegisterNotifyOnChange(int key_handle)
+int pclKeyHandleRegisterNotifyOnChange(int key_handle, changeNotifyCallback_t callback)
{
int rval = -1;
@@ -470,7 +470,7 @@ int pclKeyWriteData(unsigned int ldbid, const char* resource_id, unsigned int us
// status: TODO implement register on change
-int pclKeyRegisterNotifyOnChange(unsigned int ldbid, const char* resource_id, unsigned int user_no, unsigned int seat_no)
+int pclKeyRegisterNotifyOnChange(unsigned int ldbid, const char* resource_id, unsigned int user_no, unsigned int seat_no, changeNotifyCallback_t callback)
{
int rval = 0;
PersistenceInfo_s dbContext;
@@ -490,10 +490,14 @@ int pclKeyRegisterNotifyOnChange(unsigned int ldbid, const char* resource_id, un
rval = get_db_context(&dbContext, resource_id, ResIsNoFile, dbKey, dbPath);
// registration is only on shared key possible
- if( (PersistenceStorage_shared == rval)
- && (dbContext.configKey.type == PersistenceResourceType_key) )
+ if( (dbContext.configKey.storage == PersistenceStorage_shared)
+ && (dbContext.configKey.type == PersistenceResourceType_key) )
{
- rval = persistence_reg_notify_on_change(dbPath, dbKey);
+ rval = persistence_reg_notify_on_change(dbPath, dbKey, ldbid, user_no, seat_no, callback);
+ }
+ else
+ {
+ printf("pclKeyRegisterNotifyOnChange: error - resource is not a shared resource or resource is not a key\n");
}
return rval;
diff --git a/src/persistence_client_library_pas_interface.c b/src/persistence_client_library_pas_interface.c
index 7d5292d..e2db17e 100644
--- a/src/persistence_client_library_pas_interface.c
+++ b/src/persistence_client_library_pas_interface.c
@@ -156,6 +156,7 @@ DBusHandlerResult msg_persAdminRequest(DBusConnection *connection, DBusMessage *
return DBUS_HANDLER_RESULT_HANDLED;
}
+
int signal_persModeChange(DBusConnection *connection, DBusMessage *message)
{
int persistenceMode = 0;
@@ -213,35 +214,6 @@ int signal_persModeChange(DBusConnection *connection, DBusMessage *message)
return DBUS_HANDLER_RESULT_HANDLED;
}
-/*
-DBusHandlerResult checkPersAdminSignal(DBusConnection *connection, DBusMessage *message, void *user_data)
-{
- DBusHandlerResult result = DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
-
- printf("checkPersAdminSignalInterface '%s' -> '%s'\n", dbus_message_get_interface(message), dbus_message_get_member(message));
-
- if((0==strcmp("org.genivi.persistence.admin", dbus_message_get_interface(message))))
- {
- if(dbus_message_get_type(message) == DBUS_MESSAGE_TYPE_SIGNAL)
- {
- printf("checkPersAdminSignal signal\n");
- if((0==strcmp("PersistenceModeChanged", dbus_message_get_member(message))))
- {
- printf("checkPersAdminSignal signal\n");
- // to do handle signal
- result = signal_persModeChange(connection, message);
- }
- else
- {
- printf("checkPersAdminMsg -> unknown signal '%s'\n", dbus_message_get_interface(message));
- }
- }
- }
-
- return result;
-}
-*/
-
DBusHandlerResult checkPersAdminMsg(DBusConnection * connection, DBusMessage * message, void * user_data)
{
@@ -259,6 +231,10 @@ DBusHandlerResult checkPersAdminMsg(DBusConnection * connection, DBusMessage * m
printf("checkPersAdminMsg -> unknown message '%s'\n", dbus_message_get_interface(message));
}
}
+ else
+ {
+ printf("checkPersAdminMsg ELSE -> unknown message '%s'\n", dbus_message_get_interface(message));
+ }
return result;
}
diff --git a/test/data/Data.tar.gz b/test/data/Data.tar.gz
index dab24c2..64f0d92 100644
--- a/test/data/Data.tar.gz
+++ b/test/data/Data.tar.gz
Binary files differ
diff --git a/test/persistence_client_library_dbus_test.c b/test/persistence_client_library_dbus_test.c
index f30d5c5..f276caf 100644
--- a/test/persistence_client_library_dbus_test.c
+++ b/test/persistence_client_library_dbus_test.c
@@ -23,15 +23,37 @@
#include <stdio.h>
+
+
+int myChangeCallback(PersistenceNotification_s * notifyStruct)
+{
+ printf(" ==> * - * myChangeCallback * - *\n");
+ printf("Notification received ==> lbid: %d | resource_id: %s | seat: %d | user: %d \n", notifyStruct->ldbid,
+ notifyStruct->resource_id,
+ notifyStruct->seat_no,
+ notifyStruct->user_no );
+ printf(" <== * - * myChangeCallback * - *\n");
+
+ return 1;
+}
+
+
int main(int argc, char *argv[])
{
int ret = 0;
+ PersistenceNotification_s notifyValue;
+
printf("Dbus interface test application\n");
printf("Press a key to end application\n");
ret = pclKeyHandleOpen(0xFF, "posHandle/last_position", 0, 0);
- getchar();
+ printf("Register for change notification\n");
+ ret = pclKeyRegisterNotifyOnChange(0x84, "links/last_link2", 2/*user_no*/, 1/*seat_no*/, &myChangeCallback);
+ //ret = pclKeyRegisterNotifyOnChange(0x84, "links/last_link3", 3/*user_no*/, 2/*seat_no*/, &myChangeCallback);
+ ret = pclKeyRegisterNotifyOnChange(0x84, "links/last_link4", 4/*user_no*/, 1/*seat_no*/, &myChangeCallback);
+
+ getchar();
printf("By\n");
return ret;
diff --git a/test/persistence_client_library_test.c b/test/persistence_client_library_test.c
index d7d1375..96b7ef5 100644
--- a/test/persistence_client_library_test.c
+++ b/test/persistence_client_library_test.c
@@ -282,6 +282,37 @@ START_TEST(test_SetData)
fail_unless(ret == strlen(write2), "Wrong write size");
+ /*******************************************************************************************************************************************/
+ /* used for changed notification testing */
+ /*******************************************************************************************************************************************/
+ /**
+ * Logical DB ID: 0x84 with user 2 and seat 1
+ * ==> shared user value accessible by A GROUP (user 2 and seat 1)
+ *
+ * ==> used for shared testing
+ */
+ printf("Write data to trigger change notification\n");
+ ret = pclKeyWriteData(0x84, "links/last_link2", 2, 1, (unsigned char*)"Test notify shared data", strlen("Test notify shared data"));
+
+ /**
+ * Logical DB ID: 0x84 with user 2 and seat 1
+ * ==> shared user value accessible by A GROUP (user 2 and seat 1)
+ *
+ * ==> used for shared testing
+ */
+ printf("Write data to trigger change notification\n");
+ ret = pclKeyWriteData(0x84, "links/last_link3", 3, 2, (unsigned char*)"Test notify shared data", strlen("Test notify shared data"));
+
+ /**
+ * Logical DB ID: 0x84 with user 2 and seat 1
+ * ==> shared user value accessible by A GROUP (user 2 and seat 1)
+ *
+ * ==> used for shared testing
+ */
+ printf("Write data to trigger change notification\n");
+ ret = pclKeyWriteData(0x84, "links/last_link4", 4, 1, (unsigned char*)"Test notify shared data", strlen("Test notify shared data"));
+ /*******************************************************************************************************************************************/
+ /*******************************************************************************************************************************************/
/*
* now read the data written in the previous steps to the keys
diff --git a/test/persistence_lifeCycle_mockup.c b/test/persistence_lifeCycle_mockup.c
index 14a6ca3..f6a1458 100644
--- a/test/persistence_lifeCycle_mockup.c
+++ b/test/persistence_lifeCycle_mockup.c
@@ -176,6 +176,13 @@ DBusHandlerResult checkPersAdminMsg(DBusConnection * connection, DBusMessage * m
result = checkAdminMsg(connection, message);
}
+ else if((0==strcmp("LifecycleRequestComplete", dbus_message_get_member(message))))
+ {
+ printf(" ==> org.genivi.NodeStateManager.Consumer - received - ==> LifecycleRequestComplete \n");
+
+ result = checkAdminMsg(connection, message);
+ }
+
else
{
printf(" ==> org.genivi.NodeStateManager.Consumer - received U N KN O W N-'%s'\n", dbus_message_get_interface(message));