You can subscribe to this list here.
2005 |
Jan
|
Feb
|
Mar
(56) |
Apr
(109) |
May
(15) |
Jun
(3) |
Jul
(37) |
Aug
(96) |
Sep
(40) |
Oct
(4) |
Nov
(54) |
Dec
|
---|---|---|---|---|---|---|---|---|---|---|---|---|
2006 |
Jan
(47) |
Feb
(30) |
Mar
(102) |
Apr
(120) |
May
(68) |
Jun
(54) |
Jul
(53) |
Aug
(122) |
Sep
(190) |
Oct
(71) |
Nov
(85) |
Dec
(108) |
2007 |
Jan
(72) |
Feb
(190) |
Mar
(53) |
Apr
(101) |
May
(145) |
Jun
(148) |
Jul
(167) |
Aug
(143) |
Sep
(23) |
Oct
(198) |
Nov
(223) |
Dec
(195) |
2008 |
Jan
(100) |
Feb
(129) |
Mar
(79) |
Apr
(77) |
May
(34) |
Jun
(95) |
Jul
(112) |
Aug
(160) |
Sep
(82) |
Oct
(124) |
Nov
(199) |
Dec
(355) |
2009 |
Jan
(436) |
Feb
(89) |
Mar
(298) |
Apr
(189) |
May
(33) |
Jun
(88) |
Jul
(105) |
Aug
(44) |
Sep
(181) |
Oct
(87) |
Nov
(75) |
Dec
(1) |
2010 |
Jan
(63) |
Feb
(21) |
Mar
(3) |
Apr
(1) |
May
(1) |
Jun
(3) |
Jul
(26) |
Aug
(37) |
Sep
(26) |
Oct
(15) |
Nov
(13) |
Dec
|
From: <svn...@op...> - 2009-10-16 13:48:41
|
Author: bellmich Date: Fri Oct 16 15:48:26 2009 New Revision: 1334 URL: http://libsyncml.opensync.org/changeset/1334 Log: fixed handling of committed delete commands Modified: trunk/tools/syncml-ds-tool.c Modified: trunk/tools/syncml-ds-tool.c ============================================================================== --- trunk/tools/syncml-ds-tool.c Fri Oct 16 15:21:13 2009 (r1333) +++ trunk/tools/syncml-ds-tool.c Fri Oct 16 15:48:26 2009 (r1334) @@ -1583,7 +1583,8 @@ if (!digest && *error) goto error; - g_key_file_set_string(datastore->index, "committed_index", key, digest); + if (sml_data_sync_change_item_get_action(item) != SML_CHANGE_DELETE) + g_key_file_set_string(datastore->index, "committed_index", key, digest); if (!g_key_file_remove_key(datastore->index, "change_index", key, error)) goto error; |
From: <svn...@op...> - 2009-10-16 13:21:29
|
Author: bellmich Date: Fri Oct 16 15:21:13 2009 New Revision: 1333 URL: http://libsyncml.opensync.org/changeset/1333 Log: Every send change is now announced. Modified: trunk/tools/syncml-ds-tool.c Modified: trunk/tools/syncml-ds-tool.c ============================================================================== --- trunk/tools/syncml-ds-tool.c Fri Oct 16 15:04:32 2009 (r1332) +++ trunk/tools/syncml-ds-tool.c Fri Oct 16 15:21:13 2009 (r1333) @@ -999,6 +999,7 @@ SmlDsToolLocationType *datastore = o->data; if (!datastore->directory) continue; + printf("Sending all changes of directory %s ...\n", datastore->directory); smlTrace(TRACE_INTERNAL, "%s: checking %s", __func__, VA_STRING(sml_data_sync_data_store_get_local_uri(datastore->object))); GDir *dir = g_dir_open(datastore->directory, 0, error); @@ -1047,6 +1048,7 @@ if (strcmp(digest, original)) { /* changed item */ + printf("\tItem %s was locally changed.\n", filename); changeType = SML_CHANGE_REPLACE; g_key_file_set_string(datastore->index, "change_index", filename, digest); if (!g_key_file_remove_key(datastore->index, "last_index", filename, error)) @@ -1060,6 +1062,7 @@ } } else { /* new item */ + printf("\tItem %s was locally added.\n", filename); changeType = SML_CHANGE_ADD; g_key_file_set_string(datastore->index, "change_index", filename, digest); } @@ -1097,6 +1100,8 @@ gsize i = 0; for (; i < count; i++) { + printf("\tItem %s was locally deleted.\n", keys[i]); + /* fix indexes */ char *digest = g_key_file_get_string(datastore->index, "last_index", keys[i], error); |
From: <svn...@op...> - 2009-10-16 13:04:52
|
Author: bellmich Date: Fri Oct 16 15:04:32 2009 New Revision: 1332 URL: http://libsyncml.opensync.org/changeset/1332 Log: - anchor callbacks make only sense if the anchors can be persisted - handle one more error Modified: trunk/tools/syncml-ds-tool.c Modified: trunk/tools/syncml-ds-tool.c ============================================================================== --- trunk/tools/syncml-ds-tool.c Fri Oct 16 12:23:28 2009 (r1331) +++ trunk/tools/syncml-ds-tool.c Fri Oct 16 15:04:32 2009 (r1332) @@ -477,8 +477,6 @@ sml_data_sync_data_store_register_get_alert_type_callback(datastore->object, smlDsToolRecvAlertTypeCallback, datastore); sml_data_sync_data_store_register_change_callback(datastore->object, smlDsToolRecvChangeCallback, datastore); sml_data_sync_data_store_register_change_status_callback(datastore->object, smlDsToolRecvChangeStatusCallback, datastore); - sml_data_sync_data_store_register_get_anchor_callback(datastore->object, smlDsToolGetAnchorCallback, datastore); - sml_data_sync_data_store_register_set_anchor_callback(datastore->object, smlDsToolSetAnchorCallback, datastore); /* sync type */ @@ -542,6 +540,9 @@ goto error; } g_free(data); + /* anchors are only managed if they can be cached */ + sml_data_sync_data_store_register_get_anchor_callback(datastore->object, smlDsToolGetAnchorCallback, datastore); + sml_data_sync_data_store_register_set_anchor_callback(datastore->object, smlDsToolSetAnchorCallback, datastore); } else { datastore->directory = NULL; } @@ -971,6 +972,8 @@ gchar *filename = g_strdup_printf("%s/%s.INDEX", datastore->directory, STATUS_FILENAME); gsize length = 0; gchar *data = g_key_file_to_data(datastore->index, &length, &error); + if (!data && error) + goto error; if (!g_file_set_contents(filename, data, length, &error)) goto error; g_free(filename); |
From: <svn...@op...> - 2009-10-16 10:23:41
|
Author: bellmich Date: Fri Oct 16 12:23:28 2009 New Revision: 1331 URL: http://libsyncml.opensync.org/changeset/1331 Log: - fixed status management in index file - added error handling for changes Modified: trunk/tools/syncml-ds-tool.c trunk/tools/syncml-ds-tool_internals.c trunk/tools/syncml-ds-tool_internals.h Modified: trunk/tools/syncml-ds-tool.c ============================================================================== --- trunk/tools/syncml-ds-tool.c Fri Oct 16 12:02:45 2009 (r1330) +++ trunk/tools/syncml-ds-tool.c Fri Oct 16 12:23:28 2009 (r1331) @@ -939,6 +939,7 @@ static void writeSyncStatus(gboolean success) { + GError *error = NULL; SmlDsToolLocationType *datastore = NULL; GList *o = datastores; for(;o;o = o->next) { @@ -946,22 +947,32 @@ if (datastore->directory) { char *absolute = g_strdup_printf("%s/%s", datastore->directory, STATUS_FILENAME); if (success) { - GError *error = NULL; - if (!g_file_set_contents(absolute, "DONE", 4, &error)) { - g_warning("Cannot write data to %s. %s", - absolute, error->message); - g_error_free(error); + if (!g_file_set_contents(absolute, "Okay.", 5, &error)) + goto error; + + /* migrate all entries from committed_index to last_index */ + gsize count = 0; + char **keys = g_key_file_get_keys(datastore->index, "committed_index", NULL, NULL); + int pos = 0; + while (keys[pos] != NULL) + { + char *digest = g_key_file_get_string(datastore->index, "committed_index", keys[pos], &error); + if (!digest && error) + goto error; + if (!g_key_file_remove_key(datastore->index, "committed_index", keys[pos], &error)) + goto error; + g_key_file_set_string(datastore->index, "last_index", keys[pos], digest); + smlSafeCFree(&digest); + pos++; } + g_strfreev(keys); /* dump index */ gchar *filename = g_strdup_printf("%s/%s.INDEX", datastore->directory, STATUS_FILENAME); gsize length = 0; gchar *data = g_key_file_to_data(datastore->index, &length, &error); if (!g_file_set_contents(filename, data, length, &error)) - { - g_warning("The index file %s cannot be written.", filename); - g_error_free(error); - } + goto error; g_free(filename); } else { g_unlink(STATUS_FILENAME); @@ -969,6 +980,9 @@ smlSafeCFree(&absolute); } } + return; +error: + g_error("%s", error->message); } gboolean @@ -1204,7 +1218,6 @@ { smlTrace(TRACE_ENTRY, "%s(%p, %p, %p, %p)", __func__, session, item, userdata, error); char *absolute_uid = NULL; - char *absolute_status = NULL; /* find the appropriate datasoure */ SmlDsToolLocationType *datastore = userdata; @@ -1225,7 +1238,6 @@ char *safeUID = getSafeFilename(orgUID); printf("Writing item %s to directory %s.\n", safeUID, datastore->directory); absolute_uid = g_strdup_printf("%s/%s", datastore->directory, safeUID); - absolute_status = g_strdup_printf("%s/%s", datastore->directory, STATUS_FILENAME); /* sanity check for uid */ if (!strncmp(safeUID, STATUS_FILENAME, strlen(STATUS_FILENAME))) { @@ -1513,7 +1525,6 @@ /* cleanup UIDs */ smlSafeCFree(&safeUID); smlSafeCFree(&absolute_uid); - smlSafeCFree(&absolute_status); } else { /* print received change */ printf("-----BEGIN CHANGE-----\n"); @@ -1529,8 +1540,6 @@ error: if (absolute_uid) smlSafeCFree(&absolute_uid); - if (absolute_status) - smlSafeCFree(&absolute_status); smlTrace(TRACE_EXIT_ERROR, "%s - %s", __func__, (*error)->message); return FALSE; } @@ -1544,6 +1553,13 @@ { smlTrace(TRACE_ENTRY, "%s(%p, %p, %d, %p, %p)", __func__, session, item, code, userdata, error); + /* If there is an error then the whole operation must be aborted. */ + if (sml_error_get_class(code) != SML_ERRORCLASS_SUCCESS) + { + g_set_error(error, TOOL_ERROR, code, smlErrorTypeGetMessage(code)); + goto error; + } + /* find the appropriate datasoure */ SmlDsToolLocationType *datastore = userdata; if (!datastore) @@ -1555,7 +1571,7 @@ SmlLocation *loc = sml_data_sync_change_item_get_location(item); const char *key = sml_location_get_uri(loc); - const char *digest = g_key_file_get_string(datastore->index, "last_index", key, error); + const char *digest = g_key_file_get_string(datastore->index, "change_index", key, error); if (!digest && *error) goto error; @@ -1606,6 +1622,21 @@ datastore->slow = TRUE; if (datastore->slow) type = SML_ALERT_SLOW_SYNC; + char *status = g_strdup_printf("%s/%s", datastore->directory, STATUS_FILENAME); + if (!g_file_test(status, G_FILE_TEST_EXISTS)) + { + /* directory is out-of-sync => enforce slow sync */ + datastore->slow = TRUE; + type = SML_ALERT_SLOW_SYNC; + } + smlSafeCFree(&status); + + if (type == SML_ALERT_SLOW_SYNC) + { + g_message("\t%s => SLOW SYNC.", sml_data_sync_data_store_get_local_uri(datastore->object)); + } else { + g_message("\t%s => NORMAL SYNC.", sml_data_sync_data_store_get_local_uri(datastore->object)); + } smlTrace(TRACE_EXIT, "%s - slow == %d", __func__, datastore->slow); return type; @@ -1702,6 +1733,7 @@ if (!sml_data_sync_initialize(dsObject, &error)) goto error; + g_message("Starting data sync ..."); /* run the sync */ checkpoint = time(NULL); Modified: trunk/tools/syncml-ds-tool_internals.c ============================================================================== --- trunk/tools/syncml-ds-tool_internals.c Fri Oct 16 12:02:45 2009 (r1330) +++ trunk/tools/syncml-ds-tool_internals.c Fri Oct 16 12:23:28 2009 (r1331) @@ -19,3 +19,4 @@ */ #include <libsyncml/sml_support.h> +#include <libsyncml/sml_error_internals.h> Modified: trunk/tools/syncml-ds-tool_internals.h ============================================================================== --- trunk/tools/syncml-ds-tool_internals.h Fri Oct 16 12:02:45 2009 (r1330) +++ trunk/tools/syncml-ds-tool_internals.h Fri Oct 16 12:23:28 2009 (r1331) @@ -31,6 +31,8 @@ void smlSafeFree (gpointer *address); void smlSafeCFree (gchar **address); +const char *smlErrorTypeGetMessage(SmlErrorType type); + /** Solaris g_strdup_vprintf crashes on NULL strings. * Therefore a macro was introduced to sanitize string parameters. */ |
From: <svn...@op...> - 2009-10-16 10:02:58
|
Author: bellmich Date: Fri Oct 16 12:02:45 2009 New Revision: 1330 URL: http://libsyncml.opensync.org/changeset/1330 Log: comment for another patch from Jim Radford Modified: trunk/ChangeLog Modified: trunk/ChangeLog ============================================================================== --- trunk/ChangeLog Fri Oct 16 12:02:09 2009 (r1329) +++ trunk/ChangeLog Fri Oct 16 12:02:45 2009 (r1330) @@ -2,8 +2,10 @@ * server can handle now several sessions at once * transport cleanup is now much more robust * map fragmentation is supported - * Jim Radford <ra...@bl...> supplied a fix for some hangs on - 64 bit machines because of mixed data types (r1285). + * Jim Radford <ra...@bl...> supplied some patches: + * a fix for some hangs on 64 bit machines because of mixed data + types (r1285) + * added a forgotten change type in syncml-ds-tool (r1326) 2009-06-04 Michael Bell <mic...@we...> * Released 0.5.4 |
From: <svn...@op...> - 2009-10-16 10:02:22
|
Author: bellmich Date: Fri Oct 16 12:02:09 2009 New Revision: 1329 URL: http://libsyncml.opensync.org/changeset/1329 Log: The DS API has a callback which returns only an error code. This makes it necessary that the error code can be directly handled. Modified: trunk/libsyncml/sml_error.c trunk/libsyncml/sml_error.h Modified: trunk/libsyncml/sml_error.c ============================================================================== --- trunk/libsyncml/sml_error.c Fri Oct 16 10:48:49 2009 (r1328) +++ trunk/libsyncml/sml_error.c Fri Oct 16 12:02:09 2009 (r1329) @@ -395,15 +395,22 @@ * @returns The error class * */ -SmlErrorClass smlErrorGetClass(GError **error) +SmlErrorClass +smlErrorGetClass (GError **error) { if (!error || *error == NULL) return SML_ERRORCLASS_SUCCESS; - if ((*error)->code == SML_NO_ERROR) + return sml_error_get_class((*error)->code); +} + +SmlErrorClass +sml_error_get_class (SmlErrorType code) +{ + if (code == SML_NO_ERROR) return SML_ERRORCLASS_SUCCESS; - return (int)((*error)->code / 100); + return (int)(code / 100); } /*@}*/ Modified: trunk/libsyncml/sml_error.h ============================================================================== --- trunk/libsyncml/sml_error.h Fri Oct 16 10:48:49 2009 (r1328) +++ trunk/libsyncml/sml_error.h Fri Oct 16 12:02:09 2009 (r1329) @@ -114,5 +114,6 @@ } SmlErrorType; SmlErrorClass smlErrorGetClass(GError **error); +SmlErrorClass sml_error_get_class(SmlErrorType code); #endif //_SML_ERROR_H_ |
From: <svn...@op...> - 2009-10-16 08:49:05
|
Author: bellmich Date: Fri Oct 16 10:48:49 2009 New Revision: 1328 URL: http://libsyncml.opensync.org/changeset/1328 Log: This is the first implementation of a real index database. Please note that only the initial slow sync with an empty directory and a filled remote device is test. The following stuff is fully untested: - remote changes with normal sync - local changes with normal sync - local items during initial slow sync - existing index database during initial slow sync Yes, this is real ALPHA software. Modified: trunk/tools/syncml-ds-tool.c Modified: trunk/tools/syncml-ds-tool.c ============================================================================== --- trunk/tools/syncml-ds-tool.c Mon Oct 12 13:13:32 2009 (r1327) +++ trunk/tools/syncml-ds-tool.c Fri Oct 16 10:48:49 2009 (r1328) @@ -238,7 +238,7 @@ gboolean slow; /* char *contentType; */ char *directory; - GHashTable *remoteHash; + GKeyFile *index; } SmlDsToolLocationType; GList *datastores = NULL; @@ -401,11 +401,12 @@ #endif -static gboolean smlDsToolRecvDevInfCallback (SmlDataSyncSession *self, SmlDevInf *devinf, void *userdata, GError **error); -static SmlAlertType smlDsToolRecvAlertTypeCallback (SmlDataSyncDataStoreSession *self, SmlAlertType type, void *userdata, GError **error); -static gboolean smlDsToolRecvChangeCallback (SmlDataSyncDataStoreSession *self, SmlDataSyncChangeItem *item, void *userdata, GError **error); -static gchar* smlDsToolGetAnchorCallback (SmlDataSyncDataStoreSession *self, gboolean remote, void *userdata, GError **error); -static gboolean smlDsToolSetAnchorCallback (SmlDataSyncDataStoreSession *self, gboolean remote, const gchar* anchor, void *userdata, GError **error); +static gboolean smlDsToolRecvDevInfCallback (SmlDataSyncSession *self, SmlDevInf *devinf, void *userdata, GError **error); +static SmlAlertType smlDsToolRecvAlertTypeCallback (SmlDataSyncDataStoreSession *self, SmlAlertType type, void *userdata, GError **error); +static gboolean smlDsToolRecvChangeCallback (SmlDataSyncDataStoreSession *self, SmlDataSyncChangeItem *item, void *userdata, GError **error); +static gboolean smlDsToolRecvChangeStatusCallback (SmlDataSyncDataStoreSession *self, SmlDataSyncChangeItem *item, SmlErrorType code, void *userdata, GError **error); +static gchar* smlDsToolGetAnchorCallback (SmlDataSyncDataStoreSession *self, gboolean remote, void *userdata, GError **error); +static gboolean smlDsToolSetAnchorCallback (SmlDataSyncDataStoreSession *self, gboolean remote, const gchar* anchor, void *userdata, GError **error); SmlTransportType getTransportType(int argc, char *argv[]) { @@ -475,6 +476,7 @@ datastore->object = sml_data_sync_data_store_new(); sml_data_sync_data_store_register_get_alert_type_callback(datastore->object, smlDsToolRecvAlertTypeCallback, datastore); sml_data_sync_data_store_register_change_callback(datastore->object, smlDsToolRecvChangeCallback, datastore); + sml_data_sync_data_store_register_change_status_callback(datastore->object, smlDsToolRecvChangeStatusCallback, datastore); sml_data_sync_data_store_register_get_anchor_callback(datastore->object, smlDsToolGetAnchorCallback, datastore); sml_data_sync_data_store_register_set_anchor_callback(datastore->object, smlDsToolSetAnchorCallback, datastore); @@ -519,15 +521,31 @@ datastore->directory, errno); goto error; } + /* load the index if available */ + gchar *filename = g_strdup_printf("%s/%s.INDEX", datastore->directory, STATUS_FILENAME); + gsize length = 0; + gchar *data = NULL; + if (g_file_test(filename, G_FILE_TEST_EXISTS) && + !g_file_get_contents(filename, &data, &length, error)) + { + g_set_error(error, TOOL_ERROR, SML_ERROR_INTERNAL_MISCONFIGURATION, + "The index file %s cannot be loaded.", + filename); + g_free(filename); + goto error; + } + g_free(filename); + datastore->index = g_key_file_new(); + if (data && length && + !g_key_file_load_from_data(datastore->index, data, length, 0, error)) { + g_free(data); + goto error; + } + g_free(data); } else { datastore->directory = NULL; } - /* init uid hash table if it is an OMA DS server */ - - if (sessionType == SML_SESSION_TYPE_SERVER) - datastore->remoteHash = g_hash_table_new(g_str_hash, g_str_equal); - /* register datastore */ if (!sml_data_sync_add_data_store( dsObject, @@ -934,6 +952,17 @@ absolute, error->message); g_error_free(error); } + + /* dump index */ + gchar *filename = g_strdup_printf("%s/%s.INDEX", datastore->directory, STATUS_FILENAME); + gsize length = 0; + gchar *data = g_key_file_to_data(datastore->index, &length, &error); + if (!g_file_set_contents(filename, data, length, &error)) + { + g_warning("The index file %s cannot be written.", filename); + g_error_free(error); + } + g_free(filename); } else { g_unlink(STATUS_FILENAME); } @@ -942,103 +971,6 @@ } } -SmlChangeType getChangeType( - SmlDsToolLocationType *datastore, - const char *filename, - GError **error) -{ - smlTrace(TRACE_ENTRY, "%s(%p, %s, %p)", __func__, datastore, VA_STRING(filename), error); - struct stat fdata; - struct stat fstatus; - char *absolute_status = NULL; - - /* does the file exist */ - if (g_stat(filename, &fdata) != 0) { - g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, - "Cannot stat file %s (%d).", - filename, errno); - goto error; - } - - /* was the file touched after the checkpoint */ - if (fdata.st_mtime >= checkpoint) { - if (sessionType == SML_SESSION_TYPE_CLIENT) { - g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, - "Someone accessed the file %s after the synchronization started.", - filename); - goto error; - } else { - /* this can be an error but it is not sure */ - smlTrace(TRACE_EXIT, "%s: changed after checkpoint (%d >= %d)", - __func__, fdata.st_mtime, checkpoint); - return SML_CHANGE_UNKNOWN; - } - } - - /* is there a status file from an earlier sync */ - absolute_status = g_strdup_printf("%s/%s", datastore->directory, STATUS_FILENAME); - if (!g_file_test(absolute_status, G_FILE_TEST_EXISTS)) { - if (!datastore->slow) { - g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, - "Status file %s is missing but it is no SLOW-SYNC.", - absolute_status); - goto error; - } else { - smlSafeCFree(&absolute_status); - smlTrace(TRACE_EXIT, "%s: %d", __func__, SML_CHANGE_ADD); - return SML_CHANGE_ADD; - } - } - - /* read the stat from the status file */ - if (g_stat(absolute_status, &fstatus) != 0) { - /* this is a general error */ - g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, - "Cannot stat file %s (%d).", - absolute_status, errno); - goto error; - } - smlSafeCFree(&absolute_status); - - /* check if it was added after the last sync */ - if (fdata.st_mtime <= fstatus.st_mtime) { - if (datastore->slow) { - if (sessionType == SML_SESSION_TYPE_SERVER && - g_hash_table_lookup(datastore->remoteHash, filename)) { - smlTrace(TRACE_EXIT, "%s: %d (old known item but slowsync)", - __func__, SML_CHANGE_REPLACE); - return SML_CHANGE_REPLACE; - } else { - smlTrace(TRACE_EXIT, "%s: %d (old item but slowsync)", - __func__, SML_CHANGE_ADD); - return SML_CHANGE_ADD; - } - } else { - smlTrace(TRACE_EXIT, "%s: %d (old item and no slowsync)", - __func__, SML_CHANGE_UNKNOWN); - return SML_CHANGE_UNKNOWN; - } - } else { - /* ctime cannot be used - to unreliable */ - /* normal sync does not work reliable therefore */ - if (sessionType == SML_SESSION_TYPE_SERVER && - g_hash_table_lookup(datastore->remoteHash, filename)) { - smlTrace(TRACE_EXIT, "%s: %d (new but known)", - __func__, SML_CHANGE_REPLACE); - return SML_CHANGE_REPLACE; - } else { - smlTrace(TRACE_EXIT, "%s: %d (new)", - __func__, SML_CHANGE_ADD); - return SML_CHANGE_ADD; - } - } -error: - if (absolute_status) - smlSafeCFree(&absolute_status); - smlTrace(TRACE_EXIT_ERROR, "%s - %s", __func__, (*error)->message); - return SML_CHANGE_UNKNOWN; -} - gboolean sendAllChanges (SmlDataSyncSession *session, GError **error) @@ -1061,23 +993,23 @@ if (!datastore->session) goto error; + /* handle all required ADD and REPLACE commands + * + * The INDEX file includes a group called last_index. + * last_index includes a hash of every known item. + * So every found file will be checked. + * 1. If it is new or changed + * then the item will be migrated to the change_index. + * 2. If the file is already known + * then the item will be migrated to the committed_index. + */ for (;filename; filename = g_dir_read_name(dir)) { smlTrace(TRACE_INTERNAL, "%s: checking %s", __func__, VA_STRING(filename)); if (!strncmp(filename, STATUS_FILENAME, strlen(STATUS_FILENAME))) continue; char *absolute = g_strdup_printf("%s/%s", datastore->directory, filename); - SmlChangeType changeType = getChangeType(datastore, absolute, error); - if (changeType == SML_CHANGE_UNKNOWN) { - /* error or ignorable file */ - smlSafeCFree(&absolute); - if (*error) { - goto error; - } else { - continue; - } - } - /* all time checks succeeded, so send sync */ - smlTrace(TRACE_INTERNAL, "%s: sending %s", __func__, VA_STRING(absolute)); + + /* load data */ gsize length; char *data = NULL; if (!g_file_get_contents(absolute, &data, &length, error)) { @@ -1086,6 +1018,39 @@ } smlSafeCFree(&absolute); + /* calculate and load checksum */ + char *digest = g_compute_checksum_for_data(G_CHECKSUM_SHA256, data, length); + char *original = g_key_file_get_string(datastore->index, "last_index", filename, NULL); + + /* fix indexes */ + SmlChangeType changeType = SML_CHANGE_UNKNOWN; + if (original) + { + /* potentially changed item */ + if (strcmp(digest, original)) + { + /* changed item */ + changeType = SML_CHANGE_REPLACE; + g_key_file_set_string(datastore->index, "change_index", filename, digest); + if (!g_key_file_remove_key(datastore->index, "last_index", filename, error)) + goto error; + } else { + /* nothing to do */ + g_key_file_set_string(datastore->index, "committed_index", filename, digest); + if (!g_key_file_remove_key(datastore->index, "last_index", filename, error)) + goto error; + continue; + } + } else { + /* new item */ + changeType = SML_CHANGE_ADD; + g_key_file_set_string(datastore->index, "change_index", filename, digest); + } + + /* add change */ + + smlTrace(TRACE_INTERNAL, "%s: sending %s", __func__, VA_STRING(filename)); + SmlDataSyncChangeItem *item = sml_data_sync_change_item_new(); sml_data_sync_change_item_set_action(item, changeType); @@ -1103,6 +1068,40 @@ } g_dir_close(dir); dir = NULL; + + /* All items which are still in last_index must be deleted. + * Those items will be written to delete_index. + */ + + gsize count = 0; + char **keys = g_key_file_get_keys(datastore->index, "last_index", &count, error); + if (*error) + goto error; + gsize i = 0; + for (; i < count; i++) + { + /* fix indexes */ + + char *digest = g_key_file_get_string(datastore->index, "last_index", keys[i], error); + if (!digest && *error) + goto error; + g_key_file_set_string(datastore->index, "change_index", keys[i], digest); + if (!g_key_file_remove_key(datastore->index, "last_index", keys[i], error)) + goto error; + + /* add change */ + + SmlDataSyncChangeItem *item = sml_data_sync_change_item_new(); + sml_data_sync_change_item_set_action(item, SML_CHANGE_DELETE); + + SmlLocation *uid = sml_location_new(); + sml_location_set_uri(uid, keys[i]); + if (!sml_data_sync_change_item_set_location(item, uid, error)) + goto error; + + if (!sml_data_sync_data_store_session_add_change(datastore->session, item, NULL, error)) + goto error; + } } smlTrace(TRACE_EXIT, "%s", __func__); return sml_data_sync_session_send_changes(session, error); @@ -1218,14 +1217,17 @@ /* handle the item */ if (datastore->directory) { - /* prepare absolute filenames */ + + /* prepare UIDs and absolute filenames */ + SmlLocation *uid = sml_data_sync_change_item_get_location(item); - char *safeUID = getSafeFilename(sml_location_get_uri(uid)); + const char *orgUID = sml_location_get_uri(uid); + char *safeUID = getSafeFilename(orgUID); printf("Writing item %s to directory %s.\n", safeUID, datastore->directory); absolute_uid = g_strdup_printf("%s/%s", datastore->directory, safeUID); absolute_status = g_strdup_printf("%s/%s", datastore->directory, STATUS_FILENAME); /* sanity check for uid */ - if (!strcmp(safeUID, STATUS_FILENAME)) + if (!strncmp(safeUID, STATUS_FILENAME, strlen(STATUS_FILENAME))) { g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, "The filename %s cannot be used as UID. This is a potential attack.", @@ -1235,76 +1237,281 @@ STATUS_FILENAME); goto error; } - smlSafeCFree(&safeUID); + SmlChangeType action = sml_data_sync_change_item_get_action(item); + + /* load digest information */ - /* cache that the remote device knows the uid */ - if (datastore->remoteHash) { - g_hash_table_insert(datastore->remoteHash, g_strdup(absolute_uid), (char *)"1"); + char *index_digest = NULL; + char *item_digest = NULL; + char *file_digest = NULL; + index_digest = g_key_file_get_string(datastore->index, "last_index", safeUID, NULL); + const char *data = sml_data_sync_change_item_get_data(item); + if (data) + item_digest = g_compute_checksum_for_data(G_CHECKSUM_SHA256, data, strlen(data)); + if (g_file_test(absolute_uid, G_FILE_TEST_EXISTS)) + { + char *file_data = NULL; + gsize file_length = 0; + if (!g_file_get_contents(absolute_uid, &file_data, &file_length, error)) + goto error; + file_digest = g_compute_checksum_for_data(G_CHECKSUM_SHA256, file_data, file_length); + smlSafeCFree(&file_data); } - /* the directory is checked by scanArguments */ + + /* determine the action */ + gboolean doWrite = FALSE; - if (!doWrite && !g_file_test(absolute_uid, G_FILE_TEST_EXISTS)) - doWrite = TRUE; - if (!doWrite && sessionType == SML_SESSION_TYPE_CLIENT) - doWrite = TRUE; - if (!doWrite && !localWinsConflicts) - doWrite = TRUE; - if (!doWrite && - g_file_test(absolute_status, G_FILE_TEST_EXISTS)) + switch(action) { - if (datastore->slow) - { - /* We have to check the content. - * If the content is identical - * then we simply touch the file - * to commit it. The file will - * not be uploaded because of the - * new timestamp. - */ - const gchar* data = sml_data_sync_change_item_get_data(item); - char *remoteData = NULL; - gsize remoteSize = 0; - if (g_file_get_contents(absolute_uid, &remoteData, &remoteSize, NULL) && - remoteSize == strlen(data) && - !strncmp(data, remoteData, strlen(data))) - g_file_set_contents(absolute_uid, data, strlen(data), NULL); - } else { //!datastore->slow - /* let's check if there is a local change */ - struct stat fdata; - struct stat status; - if (g_stat(absolute_uid, &fdata) != 0) { - g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, - "Cannot stat uid file %s (%d).", - absolute_uid, errno); - goto error; + case SML_CHANGE_ADD: + if (g_file_test(absolute_uid, G_FILE_TEST_EXISTS)) + { + if (datastore->slow) + { + if (strcmp(file_digest, item_digest) == 0) + { + /* nothing to do - items identical */ + g_key_file_set_string(datastore->index, "last_index", safeUID, file_digest); + printf("\tIdentical items detected.\n"); + } else { + /* The items do not match. + * This is a classical conflict. + */ + if (localWinsConflicts) + { + printf("\tConflict: Remote add command is ignored.\n"); + printf("\tConflict: Local item wins conflict.\n"); + g_key_file_set_string(datastore->index, "last_index", safeUID, file_digest); + } else { + printf("\tConflict: Local item is ignored.\n"); + printf("\tConflict: Remote add command wins conflict.\n"); + doWrite = TRUE; + } + } + } else { + /* This should be a new remote item. + * The entry must be duplicated. + */ + doWrite = TRUE; + while (g_file_test(absolute_uid, G_FILE_TEST_EXISTS)) + { + char *new = g_strdup_printf("%s%s", safeUID, "_dup"); + smlSafeCFree(&safeUID); + smlSafeCFree(&absolute_uid); + safeUID = new; + absolute_uid = g_strdup_printf("%s/%s", datastore->directory, safeUID); + } + SmlMapItem *map = sml_map_item_new(); + if (!sml_map_item_set_remote(map, uid, error)) + goto error; + SmlLocation *local = sml_location_new(); + sml_location_set_uri(local, safeUID); + if (!sml_map_item_set_local(map, local, error)) + goto error; + if (!sml_data_sync_data_store_session_add_mapping(session, map, NULL, error)) + goto error; + g_object_unref(map); + g_object_unref(local); + g_key_file_set_string(datastore->index, "map", safeUID, orgUID); + g_key_file_set_string(datastore->index, "reverse_map", orgUID, safeUID); + printf("\tItem %s will be duplicated.\n", safeUID); + } + } else { + if (index_digest && strcmp(index_digest, item_digest) == 0) + { + /* the item was locally deleted => ignore add */ + printf("\tThe item was already locally deleted.\n"); + g_key_file_remove_key(datastore->index, "last_index", safeUID, NULL); + } else if (!index_digest) + { + /* normal add */ + printf("\tThe item is new.\n"); + doWrite = TRUE; + SmlMapItem *map = sml_map_item_new(); + if (!sml_map_item_set_remote(map, uid, error)) + goto error; + SmlLocation *local = sml_location_new(); + sml_location_set_uri(local, safeUID); + if (!sml_map_item_set_local(map, local, error)) + goto error; + if (!sml_data_sync_data_store_session_add_mapping(session, map, NULL, error)) + goto error; + g_object_unref(map); + g_object_unref(local); + g_key_file_set_string(datastore->index, "map", safeUID, orgUID); + g_key_file_set_string(datastore->index, "reverse_map", orgUID, safeUID); + } else { + /* The item was locally different + * but it was already deleted. + * This is a classical conflict. + */ + if (localWinsConflicts) + { + printf("\tConflict: Remote add command is ignored.\n"); + printf("\tConflict: Local deletion wins conflict.\n"); + g_key_file_remove_key(datastore->index, "last_index", safeUID, NULL); + } else { + printf("\tConflict: Local deletion is ignored.\n"); + printf("\tConflict: Remote add command wins conflict.\n"); + doWrite = TRUE; + SmlMapItem *map = sml_map_item_new(); + if (!sml_map_item_set_remote(map, uid, error)) + goto error; + SmlLocation *local = sml_location_new(); + sml_location_set_uri(local, safeUID); + if (!sml_map_item_set_local(map, local, error)) + goto error; + if (!sml_data_sync_data_store_session_add_mapping(session, map, NULL, error)) + goto error; + g_object_unref(map); + g_object_unref(local); + g_key_file_set_string(datastore->index, "map", safeUID, orgUID); + g_key_file_set_string(datastore->index, "reverse_map", orgUID, safeUID); + } + } } - if (g_stat(absolute_status, &status) != 0) { - g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, - "Cannot stat status file %s (%d).", - absolute_status, errno); - goto error; + break; + case SML_CHANGE_REPLACE: + if (g_file_test(absolute_uid, G_FILE_TEST_EXISTS)) + { + if (strcmp(file_digest, item_digest) == 0) + { + /* nothing to do - items identical */ + printf("\tIdentical items detected.\n"); + g_key_file_set_string(datastore->index, "last_index", safeUID, file_digest); + } else if (strcmp(index_digest, item_digest) == 0) + { + /* nothing to do - the change is already known */ + printf("\tOld change detected.\n"); + } else { + /* The items do not match and the change is unknown. + * This is a classical conflict. + */ + if (localWinsConflicts) + { + printf("\tConflict: Remote replace command is ignored.\n"); + printf("\tConflict: Local changed item wins conflict.\n"); + } else { + printf("\tConflict: Local changed item is ignored.\n"); + printf("\tConflict: Remote replace command wins conflict.\n"); + doWrite = TRUE; + } + } + } else { + /* The item was locally deleted. */ + if (index_digest && strcmp(index_digest, item_digest) == 0) + { + /* The change was locally known + * but the item is away. + */ + printf("\tThe item was already locally deleted.\n"); + g_key_file_remove_key(datastore->index, "last_index", safeUID, NULL); + } else { + /* The item was locally different + * but it was already deleted. + * This is a classical conflict. + */ + if (localWinsConflicts) + { + printf("\tConflict: Remote replace command is ignored.\n"); + printf("\tConflict: Local deletion wins conflict.\n"); + g_key_file_remove_key(datastore->index, "last_index", safeUID, NULL); + } else { + printf("\tConflict: Local deletion is ignored.\n"); + printf("\tConflict: Remote replace command wins conflict.\n"); + doWrite = TRUE; + SmlMapItem *map = sml_map_item_new(); + if (!sml_map_item_set_remote(map, uid, error)) + goto error; + SmlLocation *local = sml_location_new(); + sml_location_set_uri(local, safeUID); + if (!sml_map_item_set_local(map, local, error)) + goto error; + if (!sml_data_sync_data_store_session_add_mapping(session, map, NULL, error)) + goto error; + g_object_unref(map); + g_object_unref(local); + g_key_file_set_string(datastore->index, "map", safeUID, orgUID); + g_key_file_set_string(datastore->index, "reverse_map", orgUID, safeUID); + } + } } - if (status.st_mtime > fdata.st_mtime) - doWrite = TRUE; - } + break; + case SML_CHANGE_DELETE: + if (g_file_test(absolute_uid, G_FILE_TEST_EXISTS)) + { + if (strcmp(file_digest, index_digest) == 0) + { + /* All local changes are synchronized. + * So the deletion can be executed. + */ + printf("\tThe item will be deleted.\n"); + doWrite = TRUE; + } else { + /* The item is not synchronized + * but the item should be deleted. + * This is a classical conflict. + */ + if (localWinsConflicts) + { + printf("\tConflict: Remote delete command is ignored.\n"); + printf("\tConflict: Local changed item wins conflict.\n"); + } else { + printf("\tConflict: Local changed item is ignored.\n"); + printf("\tConflict: Remote delete command wins conflict.\n"); + doWrite = TRUE; + } + } + } else { + /* The item was locally deleted. */ + printf("\tThe item was already locally deleted.\n"); + g_key_file_remove_key(datastore->index, "last_index", safeUID, NULL); + } + break; + default: + g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, + "The change type of %s is not supported.", safeUID); + printf("\t%s\n", (*error)->message); + goto error; } - printf("\tConflicts were checked.\n"); /* write the change */ + if (doWrite) { - if (sml_data_sync_change_item_get_action(item) == SML_CHANGE_DELETE) { - g_unlink(absolute_uid); - printf("\tThe item was successfully deleted.\n"); - } else { - const gchar* data = sml_data_sync_change_item_get_data(item); - if (!g_file_set_contents(absolute_uid, data, strlen(data), error)) + switch(action) + { + case SML_CHANGE_ADD: + case SML_CHANGE_REPLACE: + data = sml_data_sync_change_item_get_data(item); + if (!g_file_set_contents(absolute_uid, data, strlen(data), error)) + goto error; + g_key_file_set_string(datastore->index, "last_index", safeUID, item_digest); + printf("\tThe item was successfully written.\n"); + break; + case SML_CHANGE_DELETE: + if (g_unlink(absolute_uid) != 0) + { + g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, + "The file %s cannot be removed.", + absolute_uid); + goto error; + } + if (!g_key_file_remove_key(datastore->index, "last_index", safeUID, error)) + goto error; + printf("\tThe item was successfully deleted.\n"); + break; + default: + g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, + "The change type of %s is not supported.", safeUID); + printf("\t%s\n", (*error)->message); goto error; - printf("\tThe item was successfully written.\n"); } } else { - printf("\tThe item was not touched.\n"); + printf("\tThe change was ignored.\n"); } - /* free absolute filenames */ + + /* cleanup UIDs */ + smlSafeCFree(&safeUID); smlSafeCFree(&absolute_uid); smlSafeCFree(&absolute_status); } else { @@ -1327,6 +1534,41 @@ smlTrace(TRACE_EXIT_ERROR, "%s - %s", __func__, (*error)->message); return FALSE; } + +static gboolean +smlDsToolRecvChangeStatusCallback (SmlDataSyncDataStoreSession *session, + SmlDataSyncChangeItem *item, + SmlErrorType code, + void *userdata, + GError **error) +{ + smlTrace(TRACE_ENTRY, "%s(%p, %p, %d, %p, %p)", __func__, session, item, code, userdata, error); + + /* find the appropriate datasoure */ + SmlDsToolLocationType *datastore = userdata; + if (!datastore) + { + g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, + "The userdata of the callback %s is missing.", __func__); + goto error; + } + + SmlLocation *loc = sml_data_sync_change_item_get_location(item); + const char *key = sml_location_get_uri(loc); + const char *digest = g_key_file_get_string(datastore->index, "last_index", key, error); + if (!digest && *error) + goto error; + + g_key_file_set_string(datastore->index, "committed_index", key, digest); + if (!g_key_file_remove_key(datastore->index, "change_index", key, error)) + goto error; + + smlTrace(TRACE_EXIT, "%s - TRUE", __func__); + return TRUE; +error: + smlTrace(TRACE_EXIT_ERROR, "%s - %s", __func__, (*error)->message); + return FALSE; +} static gboolean smlDsToolRecvDevInfCallback (SmlDataSyncSession *session, |
From: <svn...@op...> - 2009-10-13 19:35:35
|
Author: henrik Date: Tue Oct 13 21:35:20 2009 New Revision: 5870 URL: http://www.opensync.org/changeset/5870 Log: demerge_xmlformat in xmlformat_merge.c requires capabilities to be sorted. So now we sort them before saving. Fixes bug 1168 Modified: trunk/opensync/capabilities/opensync_capabilities.c Modified: trunk/opensync/capabilities/opensync_capabilities.c ============================================================================== --- trunk/opensync/capabilities/opensync_capabilities.c Tue Oct 13 20:51:22 2009 (r5869) +++ trunk/opensync/capabilities/opensync_capabilities.c Tue Oct 13 21:35:20 2009 (r5870) @@ -195,6 +195,8 @@ osync_assert(capabilities); osync_assert(file); + osync_capabilities_sort(capabilities); + ret = osync_capabilities_assemble(capabilities, &buffer, &size, error); if (!ret) goto error; |
From: <svn...@op...> - 2009-10-13 18:51:42
|
Author: dgollub Date: Tue Oct 13 20:51:22 2009 New Revision: 5869 URL: http://www.opensync.org/changeset/5869 Log: Fix invalid comparsion results. Mixing up the OSyncChange pointers caused that the logical same entries got compared together. This was not obvious due to the cloning. This bug was introduced by r5747 Overwriting pointer change1 too early with clone_change1 caused that the clone_demerge function processed the logical change2, instead of change1. The twist of demerging with capabililtiies of member 1, the change of member 2 and vice-versa, is intended. Report and most of the debugging was done by henrik Modified: trunk/opensync/engine/opensync_obj_engine.c Modified: trunk/opensync/engine/opensync_obj_engine.c ============================================================================== --- trunk/opensync/engine/opensync_obj_engine.c Sat Oct 10 18:28:03 2009 (r5868) +++ trunk/opensync/engine/opensync_obj_engine.c Tue Oct 13 20:51:22 2009 (r5869) @@ -315,7 +315,6 @@ if (!clone_change1) goto error; - change1 = clone_change1; } if (caps2) { @@ -323,9 +322,15 @@ if (!clone_change2) goto error; - change2 = mapping_change; } + + if (clone_change1) + change1 = clone_change1; + + if (clone_change2) + change2 = clone_change2; + tmp_result = osync_change_compare(change1, change2, error); if (caps1) |
From: <svn...@op...> - 2009-10-12 11:13:49
|
Author: bellmich Date: Mon Oct 12 13:13:32 2009 New Revision: 1327 URL: http://libsyncml.opensync.org/changeset/1327 Log: - added support for sync anchors - make use of userdata callback pointer instead of searching the correct data store Modified: trunk/tools/syncml-ds-tool.c Modified: trunk/tools/syncml-ds-tool.c ============================================================================== --- trunk/tools/syncml-ds-tool.c Mon Oct 12 10:30:03 2009 (r1326) +++ trunk/tools/syncml-ds-tool.c Mon Oct 12 13:13:32 2009 (r1327) @@ -404,6 +404,8 @@ static gboolean smlDsToolRecvDevInfCallback (SmlDataSyncSession *self, SmlDevInf *devinf, void *userdata, GError **error); static SmlAlertType smlDsToolRecvAlertTypeCallback (SmlDataSyncDataStoreSession *self, SmlAlertType type, void *userdata, GError **error); static gboolean smlDsToolRecvChangeCallback (SmlDataSyncDataStoreSession *self, SmlDataSyncChangeItem *item, void *userdata, GError **error); +static gchar* smlDsToolGetAnchorCallback (SmlDataSyncDataStoreSession *self, gboolean remote, void *userdata, GError **error); +static gboolean smlDsToolSetAnchorCallback (SmlDataSyncDataStoreSession *self, gboolean remote, const gchar* anchor, void *userdata, GError **error); SmlTransportType getTransportType(int argc, char *argv[]) { @@ -471,8 +473,10 @@ datastores = g_list_append(datastores, datastore); datastore->object = sml_data_sync_data_store_new(); - sml_data_sync_data_store_register_get_alert_type_callback(datastore->object, smlDsToolRecvAlertTypeCallback, NULL); - sml_data_sync_data_store_register_change_callback(datastore->object, smlDsToolRecvChangeCallback, NULL); + sml_data_sync_data_store_register_get_alert_type_callback(datastore->object, smlDsToolRecvAlertTypeCallback, datastore); + sml_data_sync_data_store_register_change_callback(datastore->object, smlDsToolRecvChangeCallback, datastore); + sml_data_sync_data_store_register_get_anchor_callback(datastore->object, smlDsToolGetAnchorCallback, datastore); + sml_data_sync_data_store_register_set_anchor_callback(datastore->object, smlDsToolSetAnchorCallback, datastore); /* sync type */ @@ -1059,7 +1063,7 @@ for (;filename; filename = g_dir_read_name(dir)) { smlTrace(TRACE_INTERNAL, "%s: checking %s", __func__, VA_STRING(filename)); - if (!strcmp(filename, STATUS_FILENAME)) + if (!strncmp(filename, STATUS_FILENAME, strlen(STATUS_FILENAME))) continue; char *absolute = g_strdup_printf("%s/%s", datastore->directory, filename); SmlChangeType changeType = getChangeType(datastore, absolute, error); @@ -1204,121 +1208,113 @@ char *absolute_status = NULL; /* find the appropriate datasoure */ - SmlDsToolLocationType *datastore = NULL; - GList *o = datastores; - while (o) { - datastore = o->data; - if (datastore->session == session) { - /* abort the scan */ - o = NULL; - } else { - datastore = NULL; - } - if (o) o = o->next; + SmlDsToolLocationType *datastore = userdata; + if (!datastore) + { + g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, + "The userdata of the callback %s is missing.", __func__); + goto error; } - smlTrace(TRACE_INTERNAL, "%s: datastores scanned", __func__); /* handle the item */ - if (datastore) { - if (datastore->directory) { - /* prepare absolute filenames */ - SmlLocation *uid = sml_data_sync_change_item_get_location(item); - char *safeUID = getSafeFilename(sml_location_get_uri(uid)); - printf("Writing item %s to directory %s.\n", safeUID, datastore->directory); - absolute_uid = g_strdup_printf("%s/%s", datastore->directory, safeUID); - absolute_status = g_strdup_printf("%s/%s", datastore->directory, STATUS_FILENAME); - /* sanity check for uid */ - if (!strcmp(safeUID, STATUS_FILENAME)) - { - g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, - "The filename %s cannot be used as UID. This is a potential attack.", - STATUS_FILENAME); - printf("\tIllegal filename %s detected.\n", STATUS_FILENAME); - g_warning("Potential attack against status file %s detected.", - STATUS_FILENAME); - goto error; - } - smlSafeCFree(&safeUID); - - /* cache that the remote device knows the uid */ - if (datastore->remoteHash) { - g_hash_table_insert(datastore->remoteHash, g_strdup(absolute_uid), (char *)"1"); - } - /* the directory is checked by scanArguments */ - gboolean doWrite = FALSE; - if (!doWrite && !g_file_test(absolute_uid, G_FILE_TEST_EXISTS)) - doWrite = TRUE; - if (!doWrite && sessionType == SML_SESSION_TYPE_CLIENT) - doWrite = TRUE; - if (!doWrite && !localWinsConflicts) - doWrite = TRUE; - if (!doWrite && - g_file_test(absolute_status, G_FILE_TEST_EXISTS)) + if (datastore->directory) { + /* prepare absolute filenames */ + SmlLocation *uid = sml_data_sync_change_item_get_location(item); + char *safeUID = getSafeFilename(sml_location_get_uri(uid)); + printf("Writing item %s to directory %s.\n", safeUID, datastore->directory); + absolute_uid = g_strdup_printf("%s/%s", datastore->directory, safeUID); + absolute_status = g_strdup_printf("%s/%s", datastore->directory, STATUS_FILENAME); + /* sanity check for uid */ + if (!strcmp(safeUID, STATUS_FILENAME)) + { + g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, + "The filename %s cannot be used as UID. This is a potential attack.", + STATUS_FILENAME); + printf("\tIllegal filename %s detected.\n", STATUS_FILENAME); + g_warning("Potential attack against status file %s detected.", + STATUS_FILENAME); + goto error; + } + smlSafeCFree(&safeUID); + + /* cache that the remote device knows the uid */ + if (datastore->remoteHash) { + g_hash_table_insert(datastore->remoteHash, g_strdup(absolute_uid), (char *)"1"); + } + /* the directory is checked by scanArguments */ + gboolean doWrite = FALSE; + if (!doWrite && !g_file_test(absolute_uid, G_FILE_TEST_EXISTS)) + doWrite = TRUE; + if (!doWrite && sessionType == SML_SESSION_TYPE_CLIENT) + doWrite = TRUE; + if (!doWrite && !localWinsConflicts) + doWrite = TRUE; + if (!doWrite && + g_file_test(absolute_status, G_FILE_TEST_EXISTS)) + { + if (datastore->slow) { - if (datastore->slow) - { - /* We have to check the content. - * If the content is identical - * then we simply touch the file - * to commit it. The file will - * not be uploaded because of the - * new timestamp. - */ - const gchar* data = sml_data_sync_change_item_get_data(item); - char *remoteData = NULL; - gsize remoteSize = 0; - if (g_file_get_contents(absolute_uid, &remoteData, &remoteSize, NULL) && - remoteSize == strlen(data) && - !strncmp(data, remoteData, strlen(data))) - g_file_set_contents(absolute_uid, data, strlen(data), NULL); - } else { //!datastore->slow - /* let's check if there is a local change */ - struct stat fdata; - struct stat status; - if (g_stat(absolute_uid, &fdata) != 0) { - g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, - "Cannot stat uid file %s (%d).", - absolute_uid, errno); - goto error; - } - if (g_stat(absolute_status, &status) != 0) { - g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, - "Cannot stat status file %s (%d).", - absolute_status, errno); - goto error; - } - if (status.st_mtime > fdata.st_mtime) - doWrite = TRUE; + /* We have to check the content. + * If the content is identical + * then we simply touch the file + * to commit it. The file will + * not be uploaded because of the + * new timestamp. + */ + const gchar* data = sml_data_sync_change_item_get_data(item); + char *remoteData = NULL; + gsize remoteSize = 0; + if (g_file_get_contents(absolute_uid, &remoteData, &remoteSize, NULL) && + remoteSize == strlen(data) && + !strncmp(data, remoteData, strlen(data))) + g_file_set_contents(absolute_uid, data, strlen(data), NULL); + } else { //!datastore->slow + /* let's check if there is a local change */ + struct stat fdata; + struct stat status; + if (g_stat(absolute_uid, &fdata) != 0) { + g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, + "Cannot stat uid file %s (%d).", + absolute_uid, errno); + goto error; + } + if (g_stat(absolute_status, &status) != 0) { + g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, + "Cannot stat status file %s (%d).", + absolute_status, errno); + goto error; } + if (status.st_mtime > fdata.st_mtime) + doWrite = TRUE; } + } - printf("\tConflicts were checked.\n"); - /* write the change */ - if (doWrite) { - if (sml_data_sync_change_item_get_action(item) == SML_CHANGE_DELETE) { - g_unlink(absolute_uid); - printf("\tThe item was successfully deleted.\n"); - } else { - const gchar* data = sml_data_sync_change_item_get_data(item); - if (!g_file_set_contents(absolute_uid, data, strlen(data), error)) - goto error; - printf("\tThe item was successfully written.\n"); - } + printf("\tConflicts were checked.\n"); + /* write the change */ + if (doWrite) { + if (sml_data_sync_change_item_get_action(item) == SML_CHANGE_DELETE) { + g_unlink(absolute_uid); + printf("\tThe item was successfully deleted.\n"); } else { - printf("\tThe item was not touched.\n"); + const gchar* data = sml_data_sync_change_item_get_data(item); + if (!g_file_set_contents(absolute_uid, data, strlen(data), error)) + goto error; + printf("\tThe item was successfully written.\n"); } - /* free absolute filenames */ - smlSafeCFree(&absolute_uid); - smlSafeCFree(&absolute_status); } else { - /* print received change */ - printf("-----BEGIN CHANGE-----\n"); - if (sml_data_sync_change_item_get_action(item) == SML_CHANGE_DELETE) - printf("DELETE %s\n", sml_location_get_uri(sml_data_sync_change_item_get_location(item))); - else - printf("%s", sml_data_sync_change_item_get_data(item)); - printf("-----END CHANGE-----\n"); + printf("\tThe item was not touched.\n"); } + /* free absolute filenames */ + smlSafeCFree(&absolute_uid); + smlSafeCFree(&absolute_status); + } else { + /* print received change */ + printf("-----BEGIN CHANGE-----\n"); + if (sml_data_sync_change_item_get_action(item) == SML_CHANGE_DELETE) + printf("DELETE %s\n", sml_location_get_uri(sml_data_sync_change_item_get_location(item))); + else + printf("%s", sml_data_sync_change_item_get_data(item)); + printf("-----END CHANGE-----\n"); } smlTrace(TRACE_EXIT, "%s - TRUE", __func__); @@ -1353,20 +1349,7 @@ { smlTrace(TRACE_ENTRY, "%s(%p, %d, %p, %p)", __func__, session, type, userdata, error); /* find the appropriate datasoure */ - SmlDsToolLocationType *datastore = NULL; - GList *o = datastores; - while (o) { - datastore = o->data; - if (datastore->object == sml_data_sync_data_store_session_get_data_store(session)) { - if (datastore->session == NULL) - datastore->session = session; - /* abort the scan */ - o = NULL; - } else { - datastore = NULL; - } - if (o) o = o->next; - } + SmlDsToolLocationType *datastore = userdata; if (!datastore) { SmlDataSyncDataStore *ds = sml_data_sync_data_store_session_get_data_store(session); g_set_error(error, TOOL_ERROR, SML_ERROR_GENERIC, @@ -1389,6 +1372,68 @@ return SML_ALERT_UNKNOWN; } +/* ***** sync anchor management ***** */ + +static gchar* +smlDsToolGetAnchorCallback (SmlDataSyncDataStoreSession *self, + gboolean remote, + void *userdata, + GError **error) +{ + smlTrace(TRACE_ENTRY, "%s (%p, %d, %p, %p)", __func__, self, remote, userdata, error); + SmlDsToolLocationType *datastore = userdata; + + gchar *filename = g_strdup_printf("%s/%s.%s", datastore->directory, STATUS_FILENAME, remote ? "REMOTE" : "LOCAL"); + + /* does the file exist */ + struct stat fdata; + if (g_stat(filename, &fdata) != 0) { + g_free(filename); + smlTrace(TRACE_EXIT, "%s - There is no such sync anchor.", __func__); + return NULL; + } + + gsize length = 0; + gchar *data = NULL; + if (!g_file_get_contents(filename, &data, &length, error)) + { + g_free(filename); + smlTrace(TRACE_EXIT_ERROR, "%s - %s", __func__, (*error)->message); + return NULL; + } + g_free(filename); + + gchar *result = smlTryMalloc0(length+1, error); + if (!result) { + g_free(data); + smlTrace(TRACE_EXIT_ERROR, "%s - %s", __func__, (*error)->message); + return NULL; + } + memcpy(result, data, length); + g_free(data); + + smlTrace(TRACE_EXIT, "%s - %s", __func__, result); + return result; +} + +static gboolean +smlDsToolSetAnchorCallback (SmlDataSyncDataStoreSession *self, + gboolean remote, + const gchar* anchor, + void *userdata, + GError **error) +{ + smlTrace(TRACE_ENTRY, "%s (%p, %d, %p, %p)", __func__, self, remote, userdata, error); + SmlDsToolLocationType *datastore = userdata; + + gchar *filename = g_strdup_printf("%s/%s.%s", datastore->directory, STATUS_FILENAME, remote ? "REMOTE" : "LOCAL"); + gboolean result = g_file_set_contents(filename, anchor, strlen(anchor), error); + g_free(filename); + + smlTrace(TRACE_EXIT, "%s - %d", __func__, result); + return result; +} + /* ************************************ */ /* ************** TOOL **************** */ /* ************************************ */ |
From: <svn...@op...> - 2009-10-12 08:30:25
|
Author: bellmich Date: Mon Oct 12 10:30:03 2009 New Revision: 1326 URL: http://libsyncml.opensync.org/changeset/1326 Log: committed patch from Jim Radford <radford_at_blackbean_dot_org> Modified: trunk/tools/syncml-ds-tool.c Modified: trunk/tools/syncml-ds-tool.c ============================================================================== --- trunk/tools/syncml-ds-tool.c Fri Oct 9 14:56:32 2009 (r1325) +++ trunk/tools/syncml-ds-tool.c Mon Oct 12 10:30:03 2009 (r1326) @@ -1083,6 +1083,7 @@ smlSafeCFree(&absolute); SmlDataSyncChangeItem *item = sml_data_sync_change_item_new(); + sml_data_sync_change_item_set_action(item, changeType); SmlLocation *uid = sml_location_new(); sml_location_set_uri(uid, filename); |
From: <svn...@op...> - 2009-10-10 16:28:16
|
Author: henrik Date: Sat Oct 10 18:28:03 2009 New Revision: 5868 URL: http://www.opensync.org/changeset/5868 Log: AutoRegister components, just to be on the safe side Modified: plugins/mozilla-sync/trunk/tests/unit_test_xpcom.cpp Modified: plugins/mozilla-sync/trunk/tests/unit_test_xpcom.cpp ============================================================================== --- plugins/mozilla-sync/trunk/tests/unit_test_xpcom.cpp Sat Oct 10 18:27:19 2009 (r5867) +++ plugins/mozilla-sync/trunk/tests/unit_test_xpcom.cpp Sat Oct 10 18:28:03 2009 (r5868) @@ -186,12 +186,16 @@ f=mozilla_startup(szTmp, &fWasStarted, &szError, &logFunction); fail_unless(f, "mozilla_startup failed: %s", szError); + printf("Getting ServiceManager\n"); nsCOMPtr<nsIServiceManager> servMan; rv = NS_GetServiceManager(getter_AddRefs(servMan)); fail_unless(NS_SUCCEEDED(rv), "NS_GetServiceManager returned [0x0%x]", rv); nsCOMPtr<nsIComponentRegistrar> registrar = do_QueryInterface(servMan, &rv); fail_unless(NS_SUCCEEDED(rv), "do_QueryInterface for nsIComponentRegistrar returned [0x0%x]", rv); + printf("AutoRegister components\n"); + registrar->AutoRegister(nsnull); + printf("Enumerating component ContractIDs\n"); nsCOMPtr<nsISimpleEnumerator> e; |
From: <svn...@op...> - 2009-10-10 16:27:31
|
Author: henrik Date: Sat Oct 10 18:27:19 2009 New Revision: 5867 URL: http://www.opensync.org/changeset/5867 Log: Check that GRE_DIR actually exists Modified: plugins/mozilla-sync/trunk/tests/blackbox_test_common.shinc.in Modified: plugins/mozilla-sync/trunk/tests/blackbox_test_common.shinc.in ============================================================================== --- plugins/mozilla-sync/trunk/tests/blackbox_test_common.shinc.in Thu Oct 8 14:48:19 2009 (r5866) +++ plugins/mozilla-sync/trunk/tests/blackbox_test_common.shinc.in Sat Oct 10 18:27:19 2009 (r5867) @@ -176,6 +176,7 @@ GRE_DIR=`grep moz_libdir "${TB_EXE}" | head -1 | cut -s -d "=" -f 2 | tr -d '"'` test -n "${GRE_DIR}" || GRE_DIR=`grep MOZ_DIST_LIB "${TB_EXE}" | head -1 | cut -s -d "=" -f 2 | tr -d '"'` test -n "${GRE_DIR}" || error_exit "Could not find GRE (Gecko Runtime Environment)" 1 + test -d "${GRE_DIR}" || error_exit "Could not find GRE (Gecko Runtime Environment); tried [${GRE_DIR}]" 1 myecho "GRE_DIR [${GRE_DIR}]" # Export the location of the GRE_DIR @@ -204,6 +205,7 @@ GRE_DIR=`grep moz_libdir "${TB_EXE}" | head -1 | cut -s -d "=" -f 2` test -n "${GRE_DIR}" || error_exit "Could not find GRE (Gecko Runtime Environment)" 1 + test -d "${GRE_DIR}" || error_exit "Could not find GRE (Gecko Runtime Environment); tried [${GRE_DIR}]" 1 myecho "GRE_DIR [${GRE_DIR}]" # Export the location of the GRE_DIR |
From: <svn...@op...> - 2009-10-09 12:56:48
|
Author: bellmich Date: Fri Oct 9 14:56:32 2009 New Revision: 1325 URL: http://libsyncml.opensync.org/changeset/1325 Log: fixed some warnings from gcc (which were real bugs) Modified: trunk/libsyncml/parser/sml_xml_parse.c trunk/libsyncml/sml_transport.c Modified: trunk/libsyncml/parser/sml_xml_parse.c ============================================================================== --- trunk/libsyncml/parser/sml_xml_parse.c Fri Oct 9 14:46:54 2009 (r1324) +++ trunk/libsyncml/parser/sml_xml_parse.c Fri Oct 9 14:56:32 2009 (r1325) @@ -3023,15 +3023,16 @@ /* This function was designed to parse one CTCap section */ /* which can include several CTCap definitions */ + SmlDevInfContentType *ct = NULL; + SmlDevInfCTCap *ctcap = NULL; + SmlDevInfProperty *property = NULL; + SmlDevInfPropParam *param = NULL; + if (!_smlXmlParserStep(parser)) { g_set_error(error, SML_ERROR, SML_ERROR_GENERIC, "Missing nodes"); goto error; } - SmlDevInfContentType *ct = NULL; - SmlDevInfCTCap *ctcap = NULL; - SmlDevInfProperty *property = NULL; - SmlDevInfPropParam *param = NULL; char *value = NULL; while (1) { Modified: trunk/libsyncml/sml_transport.c ============================================================================== --- trunk/libsyncml/sml_transport.c Fri Oct 9 14:46:54 2009 (r1324) +++ trunk/libsyncml/sml_transport.c Fri Oct 9 14:56:32 2009 (r1325) @@ -1254,6 +1254,7 @@ smlLinkDeref(link_); smlTrace(TRACE_EXIT, "%s - TRUE", __func__); + return TRUE; } /** @brief Finalizes the transport |
From: <svn...@op...> - 2009-10-09 12:47:06
|
Author: bellmich Date: Fri Oct 9 14:46:54 2009 New Revision: 1324 URL: http://libsyncml.opensync.org/changeset/1324 Log: fixed some warnings from Solaris Modified: trunk/libsyncml/data_sync_api/sml_data_sync_change_item.c trunk/libsyncml/dev_inf_api/sml_dev_inf_ctcap.c trunk/tests/check_data_sync_api_location.c trunk/tests/support.h Modified: trunk/libsyncml/data_sync_api/sml_data_sync_change_item.c ============================================================================== --- trunk/libsyncml/data_sync_api/sml_data_sync_change_item.c Tue Oct 6 17:56:44 2009 (r1323) +++ trunk/libsyncml/data_sync_api/sml_data_sync_change_item.c Fri Oct 9 14:46:54 2009 (r1324) @@ -380,7 +380,7 @@ *size = 0; return TRUE; } - *data = g_base64_decode(self->priv->data, size); + *data = (gchar *) g_base64_decode(self->priv->data, size); sml_return_val_error_if_fail (size != 0, FALSE, error, SML_ERROR_GENERIC, "The base64 decoding failed."); return TRUE; Modified: trunk/libsyncml/dev_inf_api/sml_dev_inf_ctcap.c ============================================================================== --- trunk/libsyncml/dev_inf_api/sml_dev_inf_ctcap.c Tue Oct 6 17:56:44 2009 (r1323) +++ trunk/libsyncml/dev_inf_api/sml_dev_inf_ctcap.c Fri Oct 9 14:46:54 2009 (r1324) @@ -66,7 +66,6 @@ if (SML_DEV_INF_CTCAP (object)->priv->content_type) g_object_unref (SML_DEV_INF_CTCAP (object)->priv->content_type); g_object_ref(SML_DEV_INF_CONTENT_TYPE (value)); - break; SML_DEV_INF_CTCAP (object)->priv->content_type = SML_DEV_INF_CONTENT_TYPE (value); break; case PROP_PROPERTIES: Modified: trunk/tests/check_data_sync_api_location.c ============================================================================== --- trunk/tests/check_data_sync_api_location.c Tue Oct 6 17:56:44 2009 (r1323) +++ trunk/tests/check_data_sync_api_location.c Fri Oct 9 14:46:54 2009 (r1324) @@ -22,6 +22,7 @@ #include "tests/support.h" #include <libsyncml/data_sync_api/sml_location.h> +#include <string.h> START_TEST (location_new) { Modified: trunk/tests/support.h ============================================================================== --- trunk/tests/support.h Tue Oct 6 17:56:44 2009 (r1323) +++ trunk/tests/support.h Fri Oct 9 14:46:54 2009 (r1324) @@ -84,7 +84,7 @@ struct sml_testcase_s { const char *name; - void *func; + TFun func; }; |
From: <svn...@op...> - 2009-10-08 12:48:38
|
Author: henrik Date: Thu Oct 8 14:48:19 2009 New Revision: 5866 URL: http://www.opensync.org/changeset/5866 Log: doxygen documentation brought up-to-date Modified: plugins/mozilla-sync/trunk/src/mozilla-sync.cpp Modified: plugins/mozilla-sync/trunk/src/mozilla-sync.cpp ============================================================================== --- plugins/mozilla-sync/trunk/src/mozilla-sync.cpp Thu Oct 8 13:54:00 2009 (r5865) +++ plugins/mozilla-sync/trunk/src/mozilla-sync.cpp Thu Oct 8 14:48:19 2009 (r5866) @@ -43,7 +43,7 @@ node [fontname="FreeSans.ttf",fontsize=10,shape=record]; n1 [label="mozilla-sync", URL="\ref mozilla-sync.cpp"]; - n11 [label="xml-config", URL="\ref xml-config.cpp"]; + n11 [label="mozilla-config", URL="\ref mozilla-config.cpp"]; n11 -> n1; n12 [label="mozilla-xpcom", URL="\ref mozilla-xpcom.cpp"]; n12 -> n1; @@ -53,6 +53,10 @@ n13 -> n1; n131 [label="ThunderbirdCard", URL="\ref ThunderbirdCard"]; n131 -> n13; + n14 [label="MozillaCalendar",URL="\ref MozillaCalendar"]; + n14 -> n1; + n141 [label="calendar-event", URL="\ref calendar-event.cpp"]; + n141 -> n14; } @enddot @@ -199,11 +203,12 @@ extern "C" { // ---------------------------------------- -/** @brief Report address book changes since last sync into OSyncMozillaDatabase->OSyncHashTable +/** @brief Report address book changes since last sync into the hash-table provided @param pOSyncMozillaDatabase The database we have to report on @param pOSyncPluginInfo On entry we have what we gave in get_sync_info. @param pOSyncContext The context of the connect (e.g. to report error) + @param pHashTable The hash table to report changes into @return TRUE on success; FALSE on error **/ gboolean mozilla_sync_report_addressbook_changes_to_hash( @@ -330,7 +335,7 @@ // ---------------------------------------- -/** @brief Report calendar changes since last sync into OSyncMozillaDatabase->OSyncHashTable +/** @brief Report calendar changes since last sync into the provided hash table @todo mozilla_sync_report_calendar_changes_to_hash and mozilla_sync_report_addressbook_changes_to_hash are quite similar. Could we merge them? @@ -338,6 +343,7 @@ @param pOSyncMozillaDatabase The database we have to report on @param pOSyncPluginInfo On entry we have what we gave in get_sync_info. @param pOSyncContext The context of the connect (e.g. to report error) + @param pHashTable The hash table to report changes into @return TRUE on success; FALSE on error **/ gboolean mozilla_sync_report_calendar_changes_to_hash( @@ -455,8 +461,10 @@ /** @brief Get changes since last sync (or all changes on slow sync) @param data The OSyncMozillaEnv + @param pOSyncObjTypeSink The ObjectType sink we shall get changes for. @param pOSyncPluginInfo On entry we have what we gave in get_sync_info. @param pOSyncContext The context of the connect (e.g. to report error) + @param fSlow True if we are doing a slow sync, meaning we want to get *all* changes **/ static void mozilla_sync_get_changes( OSyncObjTypeSink* pOSyncObjTypeSink, @@ -680,6 +688,7 @@ /** @brief Commit change @param data The OSyncMozillaEnv + @param pOSyncObjTypeSink The ObjectType sink we shall commit the change into. @param pOSyncPluginInfo On entry we have what we gave in get_sync_info. @param pOSyncContext The context of the connect (e.g. to report error) @param pChange The change we shall commit @@ -769,8 +778,9 @@ /** @brief Called when sync is complete @param data The OSyncMozillaEnv + @param pOSyncObjTypeSink The ObjectType sink for which the sync is complete. @param pOSyncPluginInfo On entry we have what we gave in get_sync_info. - @param pOSyncContext The context of the connect (e.g. to report error) + @param pOSyncContext The context (e.g. to report error) **/ static void mozilla_sync_done(OSyncObjTypeSink* pOSyncObjTypeSink, OSyncPluginInfo *pOSyncPluginInfo, @@ -799,6 +809,7 @@ /** @brief Connect to sink @param data The OSyncMozillaEnv + @param pOSyncObjTypeSink The ObjectType sink we shall try to connect to. @param pOSyncPluginInfo On entry we have what we gave in get_sync_info. @param pOSyncContext The context of the connect (e.g. to report error) **/ @@ -871,6 +882,7 @@ /** @brief Disconnect from sink @param data The OSyncMozillaEnv + @param pOSyncObjTypeSink The ObjectType sink we shall disconnect from. @param pOSyncPluginInfo On entry we have what we gave in get_sync_info. @param pOSyncContext The context of the connect (e.g. to report error) **/ |
From: <svn...@op...> - 2009-10-08 11:54:13
|
Author: henrik Date: Thu Oct 8 13:54:00 2009 New Revision: 5865 URL: http://www.opensync.org/changeset/5865 Log: Add possibility to automatically create OSYNC_TRACES by settin environment variable MAKE_OSYNC_TRACE Modified: plugins/mozilla-sync/trunk/tests/blackbox_test_common.shinc.in Modified: plugins/mozilla-sync/trunk/tests/blackbox_test_common.shinc.in ============================================================================== --- plugins/mozilla-sync/trunk/tests/blackbox_test_common.shinc.in Thu Oct 8 13:53:03 2009 (r5864) +++ plugins/mozilla-sync/trunk/tests/blackbox_test_common.shinc.in Thu Oct 8 13:54:00 2009 (r5865) @@ -36,6 +36,11 @@ # e.g export KEEP_TEMP_FILES=1 KEEP_TEMP_FILES=${KEEP_TEMP_FILES:-""} +# Set $MAKE_OSYNC_TRACE before runng the test +# e.g. export MAKE_OSYNC_TRACE=1 +# to get OpenSync trace files for osynctool +MAKE_OSYNC_TRACE=${MAKE_OSYNC_TRACE:-""} + # Array in which we keep file- and directory-names to be removed # when the test exits declare -a PATHS_TO_CLEAN @@ -255,6 +260,14 @@ # ---------------------------------------------------------------------- msync_sync () { GROUP_NAME="$1" + if [ -n "${MAKE_OSYNC_TRACE}" ]; then + export OSYNC_NOPRIVACY=1 + local DIR=`mktemp -dt "OSYNC_TRACE_${GROUP_NAME}.XXXXXX"` || + error_exit "Could not create temporary directory for [${GROUP_NAME}]" 1 + export OSYNC_TRACE="${DIR}" + myecho "Tracing into ${DIR}" + fi + msync --sync "${GROUP_NAME}" --always-accept-forecast --conflict i || error_exit "Synchronization failed for [${STEP}]" $? } |
From: <svn...@op...> - 2009-10-08 11:53:19
|
Author: henrik Date: Thu Oct 8 13:53:03 2009 New Revision: 5864 URL: http://www.opensync.org/changeset/5864 Log: Do not unref objtype_sink as we do not own it Modified: plugins/mozilla-sync/trunk/src/mozilla-sync.cpp Modified: plugins/mozilla-sync/trunk/src/mozilla-sync.cpp ============================================================================== --- plugins/mozilla-sync/trunk/src/mozilla-sync.cpp Wed Sep 30 01:30:16 2009 (r5863) +++ plugins/mozilla-sync/trunk/src/mozilla-sync.cpp Thu Oct 8 13:53:03 2009 (r5864) @@ -1139,7 +1139,6 @@ void freeMozillaDatabase(void* voidOSyncMozillaDatabase, void* notused) { OSyncMozillaDatabase *pDB=(OSyncMozillaDatabase*) voidOSyncMozillaDatabase; - osync_objtype_sink_unref(pDB->pOSyncObjTypeSink); if (pDB->iMozillaDatabaseType==MOZILLA_DATABASE_TYPE_ADDRESSBOOK) { if (pDB->pThunderbirdAddressbook) delete pDB->pThunderbirdAddressbook; } else if (pDB->iMozillaDatabaseType==MOZILLA_DATABASE_TYPE_CALENDAR) { |
From: <svn...@op...> - 2009-10-06 15:57:10
|
Author: bellmich Date: Tue Oct 6 17:56:44 2009 New Revision: 1323 URL: http://libsyncml.opensync.org/changeset/1323 Log: Valgrind 3.5.0 (from Debian) only supports a maximum of 50 callers. CTest actually tries to configure 100 callers. Modified: trunk/CMakeLists.txt Modified: trunk/CMakeLists.txt ============================================================================== --- trunk/CMakeLists.txt Tue Oct 6 17:32:24 2009 (r1322) +++ trunk/CMakeLists.txt Tue Oct 6 17:56:44 2009 (r1323) @@ -185,6 +185,7 @@ ENDIF(CHECK_FOUND) IF(CHECK_FOUND) SET( ENABLE_UNIT_TEST ON ) + SET( MEMORYCHECK_COMMAND_OPTIONS "${MEMORYCHECK_COMMAND_OPTIONS} --num-callers=50" ) SET( MEMORYCHECK_SUPPRESSIONS_FILE "${CMAKE_SOURCE_DIR}/tests/valgrind.supp" CACHE FILEPATH "valgrind.supp" ) INCLUDE( Testing ) ENDIF(CHECK_FOUND) |
From: <svn...@op...> - 2009-10-06 15:32:47
|
Author: bellmich Date: Tue Oct 6 17:32:24 2009 New Revision: 1322 URL: http://libsyncml.opensync.org/changeset/1322 Log: fixed another memory leak in a test Modified: trunk/ChangeLog trunk/tests/check_data_sync_api.c Modified: trunk/ChangeLog ============================================================================== --- trunk/ChangeLog Tue Oct 6 16:24:06 2009 (r1321) +++ trunk/ChangeLog Tue Oct 6 17:32:24 2009 (r1322) @@ -1,5 +1,6 @@ * Only data sync and dev inf API survive API renewal * server can handle now several sessions at once + * transport cleanup is now much more robust * map fragmentation is supported * Jim Radford <ra...@bl...> supplied a fix for some hangs on 64 bit machines because of mixed data types (r1285). Modified: trunk/tests/check_data_sync_api.c ============================================================================== --- trunk/tests/check_data_sync_api.c Tue Oct 6 16:24:06 2009 (r1321) +++ trunk/tests/check_data_sync_api.c Tue Oct 6 17:32:24 2009 (r1322) @@ -315,6 +315,8 @@ sml_fail_unless(sml_map_item_set_remote(map, remote, error), "%s", GET_ERROR_MESSAGE((*error))); sml_fail_unless(sml_map_item_set_local(map, local, error), "%s", GET_ERROR_MESSAGE((*error))); sml_fail_unless(sml_map_item_is_compliant(map, error), "%s", GET_ERROR_MESSAGE((*error))); + g_object_unref(local); + local = NULL; /* add the mapping to the session */ |
From: <svn...@op...> - 2009-10-06 14:24:20
|
Author: bellmich Date: Tue Oct 6 16:24:06 2009 New Revision: 1321 URL: http://libsyncml.opensync.org/changeset/1321 Log: implemented automatic disconnect of open server connections during finalize Modified: trunk/libsyncml/sml_transport.c Modified: trunk/libsyncml/sml_transport.c ============================================================================== --- trunk/libsyncml/sml_transport.c Tue Oct 6 16:09:21 2009 (r1320) +++ trunk/libsyncml/sml_transport.c Tue Oct 6 16:24:06 2009 (r1321) @@ -1236,6 +1236,26 @@ return; } +static gboolean +smlTransportDisconnectLink (gpointer key, + gpointer value, + gpointer userdata) +{ + smlTrace(TRACE_ENTRY, "%s(%p, %p, %p)", __func__, key, value, userdata); + + SmlTransport *tsp = userdata; + SmlLink *link_ = key; + + if (link_->link_data) + { + /* connected */ + tsp->functions.disconnect(tsp->transport_data, link_); + } + smlLinkDeref(link_); + + smlTrace(TRACE_EXIT, "%s - TRUE", __func__); +} + /** @brief Finalizes the transport * * This function will finalize the transport . The transport must be in the state "Initialized" @@ -1329,7 +1349,7 @@ if (smlTransportIsServer(tsp)) { /* All open server connections will now be closed. */ - /* FIXME: TODO */ + g_hash_table_foreach_remove(tsp->links, smlTransportDisconnectLink, tsp); } else { /* This is a client. */ smlTrace(TRACE_INTERNAL, "%s: try automatic disconnect for a client", __func__); |
From: <svn...@op...> - 2009-10-06 14:09:34
|
Author: bellmich Date: Tue Oct 6 16:09:21 2009 New Revision: 1320 URL: http://libsyncml.opensync.org/changeset/1320 Log: - All transport implementations have a disconnect function. - The state management works now too if there is no event callback. This can happen after the SmlManager is stopped. - It is now cleanly checked if the transport is in synchronous or asynchronous mode. Commands can only be send if the transport is at minimum initialized and in asynchronous mode. If the transport is synchronized again then no more commands are allowed. - The finalize function must disconnect all open connections. This is not implemented for server connections yet. Modified: trunk/libsyncml/sml_transport.c trunk/libsyncml/sml_transport_internals.h Modified: trunk/libsyncml/sml_transport.c ============================================================================== --- trunk/libsyncml/sml_transport.c Tue Oct 6 16:04:38 2009 (r1319) +++ trunk/libsyncml/sml_transport.c Tue Oct 6 16:09:21 2009 (r1320) @@ -98,6 +98,12 @@ smlAssert(tsp); smlAssert(data); + if (!tsp->async) + { + g_set_error(error, SML_ERROR, SML_ERROR_GENERIC, "The transport is not in asynchronous mode."); + goto error; + } + if (tsp->cached_error != NULL) { // the most parameters should be NULL because the cached error @@ -155,11 +161,6 @@ tsp->functions.connect(tsp->transport_data); break; case SML_TRANSPORT_CMD_DISCONNECT: - if (!tsp->functions.disconnect) { - smlTransportReceiveEvent(tsp, NULL, SML_TRANSPORT_EVENT_DISCONNECT_DONE, NULL, NULL); - smlTrace(TRACE_INTERNAL, "%s: No disconnect function", __func__); - break; - } /* If there is a disconnect request * but the connection is already down * then an earlier disconnect happened @@ -268,76 +269,79 @@ /* Third we have to send the original event. */ } + } - /* If a connect or disconnect is received without a link - * then this means that this is a new connection or a - * closed connection of a client. If such a constallation - * happens with a server then this is a fatal error. - * - * If a connect is reveived with a link - * then this must be a server and - * the link_data must be set. - * - * If a disconnect is received with a link - * then this must be a server and - * the link_data must not be present - * because the link is down now. - */ + /* If a connect or disconnect is received without a link + * then this means that this is a new connection or a + * closed connection of a client. If such a constallation + * happens with a server then this is a fatal error. + * + * If a connect is reveived with a link + * then this must be a server and + * the link_data must be set. + * + * If a disconnect is received with a link + * then this must be a server and + * the link_data must not be present + * because the link is down now. + */ - if (type == SML_TRANSPORT_EVENT_CONNECT_DONE && !link_) - { - if (smlTransportIsServer(tsp)) - g_error("A connect event without a link was received " \ - "but the transport layer is a server."); - if (tsp->connected) - g_error("A connect event was received " \ - "but the transport layer is already connected."); - smlTrace(TRACE_INTERNAL, "%s: connect + no link", __func__); - tsp->connected = TRUE; - } + if (type == SML_TRANSPORT_EVENT_CONNECT_DONE && !link_) + { + if (smlTransportIsServer(tsp)) + g_error("A connect event without a link was received " \ + "but the transport layer is a server."); + if (tsp->connected) + g_error("A connect event was received " \ + "but the transport layer is already connected."); + smlTrace(TRACE_INTERNAL, "%s: connect + no link", __func__); + tsp->connected = TRUE; + } - if (type == SML_TRANSPORT_EVENT_DISCONNECT_DONE && !link_) - { - if (smlTransportIsServer(tsp)) - g_error("A disconnect event without a link was received " \ - "but the transport layer is a server."); - if (!tsp->connected) - g_error("A disconnect event was received " \ - "but there is no connected transport."); - smlTrace(TRACE_INTERNAL, "%s: disconnect + no link", __func__); - tsp->connected = FALSE; - } + if (type == SML_TRANSPORT_EVENT_DISCONNECT_DONE && !link_) + { + if (smlTransportIsServer(tsp)) + g_error("A disconnect event without a link was received " \ + "but the transport layer is a server."); + if (!tsp->connected) + g_error("A disconnect event was received " \ + "but there is no connected transport."); + smlTrace(TRACE_INTERNAL, "%s: disconnect + no link", __func__); + tsp->connected = FALSE; + } - if (type == SML_TRANSPORT_EVENT_CONNECT_DONE && link_) - { - if (!smlTransportIsServer(tsp)) - g_error("A connect event with a link was received " \ - "but the transport layer is a server."); - if (!link_->link_data) - g_error("A connect event with a link was received " \ - "but the link does not contain the required " \ - "transport environment."); - smlTrace(TRACE_INTERNAL, "%s: connect + link", __func__); - g_mutex_lock(tsp->connections_mutex); - tsp->connections++; - g_mutex_unlock(tsp->connections_mutex); - } + if (type == SML_TRANSPORT_EVENT_CONNECT_DONE && link_) + { + if (!smlTransportIsServer(tsp)) + g_error("A connect event with a link was received " \ + "but the transport layer is a server."); + if (!link_->link_data) + g_error("A connect event with a link was received " \ + "but the link does not contain the required " \ + "transport environment."); + smlTrace(TRACE_INTERNAL, "%s: connect + link", __func__); + g_mutex_lock(tsp->connections_mutex); + tsp->connections++; + g_mutex_unlock(tsp->connections_mutex); + } - if (type == SML_TRANSPORT_EVENT_DISCONNECT_DONE && link_) - { - if (!smlTransportIsServer(tsp)) - g_error("A disconnect event with a link was received " \ - "but the transport layer is not a server."); - if (link_->link_data) - g_error("A disconnect event with a link was received " \ - "but the link still contains the " \ - "transport environment."); - smlTrace(TRACE_INTERNAL, "%s: disconnect + link", __func__); - g_mutex_lock(tsp->connections_mutex); - tsp->connections--; - g_mutex_unlock(tsp->connections_mutex); - } + if (type == SML_TRANSPORT_EVENT_DISCONNECT_DONE && link_) + { + if (!smlTransportIsServer(tsp)) + g_error("A disconnect event with a link was received " \ + "but the transport layer is not a server."); + if (link_->link_data) + g_error("A disconnect event with a link was received " \ + "but the link still contains the " \ + "transport environment."); + smlTrace(TRACE_INTERNAL, "%s: disconnect + link", __func__); + g_mutex_lock(tsp->connections_mutex); + tsp->connections--; + g_mutex_unlock(tsp->connections_mutex); + } + if (tsp->event_callback != NULL) + { /* now execute the callback */ if (!(tsp->cached_error && @@ -383,6 +387,12 @@ CHECK_ERROR_REF smlAssert(tsp); + if (!tsp->async) + { + g_set_error(error, SML_ERROR, SML_ERROR_GENERIC, "The transport is not in asynchronous mode."); + goto error; + } + /* Only clients can actively connect and * a client can only connect once. */ @@ -428,6 +438,12 @@ CHECK_ERROR_REF smlAssert(tsp); + if (!tsp->async) + { + g_set_error(error, SML_ERROR, SML_ERROR_GENERIC, "The transport is not in asynchronous mode."); + goto error; + } + /* The transport must (still) be connected. */ if (!tsp->connected) @@ -782,6 +798,7 @@ tsp->cached_error = NULL; tsp->event_callback = NULL; tsp->context = NULL; + tsp->async = TRUE; switch (type) { #ifdef ENABLE_HTTP @@ -818,6 +835,7 @@ g_set_error(error, SML_ERROR, SML_ERROR_GENERIC, "The transport type must be specified."); goto error; } + smlAssert(tsp->functions.disconnect); tsp->command_queue = smlQueueNew(error); if (!tsp->command_queue) @@ -1095,6 +1113,7 @@ /* start the queue - e.g. to handle errors */ smlQueueSetHandler(tsp->command_queue, (SmlQueueHandler)smlTransportWorkerHandler, tsp); smlQueueAttach(tsp->command_queue, tsp->context); + tsp->async = TRUE; if (tsp->functions.initialize && !tsp->functions.initialize(tsp, error)) goto error_detach; @@ -1245,8 +1264,15 @@ goto error; } + /* mark the transport as synchronous + * + * This means that no more commands are accepted. + */ + + tsp->async = FALSE; + /* smlTransportFinalize is a synchronous function. - * It requires that the transport is no longer disconnected. + * It requires that the transport is no longer connected. * smlTransportDisconnect is an asynchronous function. * This means that the transport must be synchronized. * So before the real checking and finalization starts @@ -1294,28 +1320,26 @@ } } - /* NOTICE: The transport is now synchronized. */ + /* NOTICE: The transport is now synchronized and clean. */ - /* ensure that all client transorts are really disconnected */ + /* All open connections must be disconnected. */ - if (tsp->connected && - !smlTransportIsServer(tsp) && - tsp->state == SML_TRANSPORT_ERROR) - { - /* If this is a crashed client - * then an automatic graceful disconnect is tried. */ - smlTrace(TRACE_INTERNAL, "%s: try disconnect for client in error state", __func__); - if (!tsp->functions.disconnect) { - smlTransportReceiveEvent(tsp, NULL, SML_TRANSPORT_EVENT_DISCONNECT_DONE, NULL, NULL); - smlTrace(TRACE_INTERNAL, "%s: no disconnect function", __func__); + if (tsp->connected) + { + if (smlTransportIsServer(tsp)) + { + /* All open server connections will now be closed. */ + /* FIXME: TODO */ } else { + /* This is a client. */ + smlTrace(TRACE_INTERNAL, "%s: try automatic disconnect for a client", __func__); tsp->functions.disconnect(tsp->transport_data, NULL); - } - if (tsp->connected && !smlTransportIsServer(tsp)) { - g_set_error(error, SML_ERROR, SML_ERROR_GENERIC, - "If a client transport is connected then it cannot be finalized."); - goto error; + if (tsp->connected) { + g_set_error(error, SML_ERROR, SML_ERROR_GENERIC, + "Automatic client disconnect during finalization failed."); + goto error; + } } } Modified: trunk/libsyncml/sml_transport_internals.h ============================================================================== --- trunk/libsyncml/sml_transport_internals.h Tue Oct 6 16:04:38 2009 (r1319) +++ trunk/libsyncml/sml_transport_internals.h Tue Oct 6 16:09:21 2009 (r1320) @@ -92,6 +92,8 @@ GMutex *links_mutex; gsize connections; GMutex *connections_mutex; + + gboolean async; }; struct SmlLink { |
From: <svn...@op...> - 2009-10-06 14:04:56
|
Author: bellmich Date: Tue Oct 6 16:04:38 2009 New Revision: 1319 URL: http://libsyncml.opensync.org/changeset/1319 Log: fixed wrong (duplicated) test port Modified: trunk/tests/check_data_sync_api.c Modified: trunk/tests/check_data_sync_api.c ============================================================================== --- trunk/tests/check_data_sync_api.c Tue Oct 6 14:34:27 2009 (r1318) +++ trunk/tests/check_data_sync_api.c Tue Oct 6 16:04:38 2009 (r1319) @@ -984,7 +984,7 @@ START_TEST (ds_api_max_msg_changes_multi_plus_one) { - test_ds_api_max_msg_changes("17009", "5", 501); + test_ds_api_max_msg_changes("17010", "5", 501); } END_TEST |
From: <svn...@op...> - 2009-10-06 12:34:41
|
Author: bellmich Date: Tue Oct 6 14:34:27 2009 New Revision: 1318 URL: http://libsyncml.opensync.org/changeset/1318 Log: fixed wrong block construction because of poor source code formatting Modified: trunk/libsyncml/sml_transport.c Modified: trunk/libsyncml/sml_transport.c ============================================================================== --- trunk/libsyncml/sml_transport.c Tue Oct 6 14:19:48 2009 (r1317) +++ trunk/libsyncml/sml_transport.c Tue Oct 6 14:34:27 2009 (r1318) @@ -1312,10 +1312,11 @@ tsp->functions.disconnect(tsp->transport_data, NULL); } - if (tsp->connected && !smlTransportIsServer(tsp)) - g_set_error(error, SML_ERROR, SML_ERROR_GENERIC, - "If a client transport is connected then it cannot be finalized."); - goto error; + if (tsp->connected && !smlTransportIsServer(tsp)) { + g_set_error(error, SML_ERROR, SML_ERROR_GENERIC, + "If a client transport is connected then it cannot be finalized."); + goto error; + } } /* stop and finalize the transport */ |
From: <svn...@op...> - 2009-10-06 12:27:18
|
Author: bellmich Date: Tue Oct 6 14:19:48 2009 New Revision: 1317 URL: http://libsyncml.opensync.org/changeset/1317 Log: - better error message - more aggressive error signalling Modified: trunk/libsyncml/data_sync_api/sml_data_sync.c trunk/libsyncml/sml_transport.c Modified: trunk/libsyncml/data_sync_api/sml_data_sync.c ============================================================================== --- trunk/libsyncml/data_sync_api/sml_data_sync.c Tue Oct 6 14:01:22 2009 (r1316) +++ trunk/libsyncml/data_sync_api/sml_data_sync.c Tue Oct 6 14:19:48 2009 (r1317) @@ -130,6 +130,7 @@ if (self->priv->state >= SML_DATA_SYNC_STATE_INITIALIZED && !smlTransportFinalize(self->priv->tsp, &error)) { /* just ignore the error */ + g_warning("%s: %s", __func__, error->message); smlTrace(TRACE_ERROR, "%s: %s", __func__, error->message); g_error_free(error); error = NULL; Modified: trunk/libsyncml/sml_transport.c ============================================================================== --- trunk/libsyncml/sml_transport.c Tue Oct 6 14:01:22 2009 (r1316) +++ trunk/libsyncml/sml_transport.c Tue Oct 6 14:19:48 2009 (r1317) @@ -1241,7 +1241,7 @@ if (tsp->state < SML_TRANSPORT_INITIALIZED) { g_set_error (error, SML_ERROR, SML_ERROR_GENERIC, - "Transport was not in the state \"Initialized\""); + "Transport was never in the state \"Initialized\"."); goto error; } |