ecb_ews_get_attach_differences (ECalComponent *oldcomp,
				ECalComponent *newcomp,
				GSList **out_removed_attachment_ids, /* gchar * */
				GSList **out_added_attachments) /* EEwsAttachmentInfo * */
{
	GSList *old_attachments = NULL, *new_attachments = NULL, *link;

	g_return_if_fail (out_removed_attachment_ids != NULL);
	g_return_if_fail (out_added_attachments != NULL);

	*out_removed_attachment_ids = NULL;
	*out_added_attachments = NULL;

	if (!ecb_ews_extract_attachments (e_cal_component_get_icalcomponent (oldcomp), &old_attachments))
		old_attachments = NULL;

	if (!ecb_ews_extract_attachments (e_cal_component_get_icalcomponent (newcomp), &new_attachments))
		new_attachments = NULL;

	for (link = old_attachments; link; link = g_slist_next (link)) {
		EEwsAttachmentInfo *old_nfo = link->data;
		GSList *nlink;

		if (!old_nfo)
			continue;

		for (nlink = new_attachments; nlink; nlink = g_slist_next (nlink)) {
			EEwsAttachmentInfo *new_nfo = nlink->data;
			gboolean same = FALSE;

			if (!new_nfo ||
			    e_ews_attachment_info_get_type (old_nfo) != e_ews_attachment_info_get_type (new_nfo))
				continue;

			if (e_ews_attachment_info_get_type (old_nfo) == E_EWS_ATTACHMENT_INFO_TYPE_INLINED) {
				const gchar *old_data, *new_data;
				gsize old_len = -1, new_len = -1;

				old_data = e_ews_attachment_info_get_inlined_data (old_nfo, &old_len);
				new_data = e_ews_attachment_info_get_inlined_data (new_nfo, &new_len);

				same = old_len == new_len && (old_len == 0 ||
					(old_len > 0 && old_data && new_data && memcmp (old_data, new_data, old_len) == 0));
			} else if (e_ews_attachment_info_get_type (old_nfo) == E_EWS_ATTACHMENT_INFO_TYPE_URI) {
				same = g_strcmp0 (e_ews_attachment_info_get_uri (old_nfo), e_ews_attachment_info_get_uri (new_nfo)) == 0;
			}

			if (same) {
				new_attachments = g_slist_remove (new_attachments, new_nfo);
				e_ews_attachment_info_free (new_nfo);
				break;
			}
		}

		if (!nlink) {
			/* Did not find in the new_attachments, thus it's removed */
			g_warn_if_fail (e_ews_attachment_info_get_id (old_nfo) != NULL);
			*out_removed_attachment_ids = g_slist_prepend (*out_removed_attachment_ids,
				g_strdup (e_ews_attachment_info_get_id (old_nfo)));
		}
	}

	*out_added_attachments = new_attachments;

	g_slist_free_full (old_attachments, (GDestroyNotify) e_ews_attachment_info_free);
}
ecb_ews_get_attach_differences (ECalComponent *oldcomp,
				ECalComponent *newcomp,
				GSList **out_removed_attachment_ids,  
				GSList **out_added_attachments)  
{
	GSList *old_attachments = NULL, *new_attachments = NULL, *link;

	g_return_if_fail (out_removed_attachment_ids != NULL);
	g_return_if_fail (out_added_attachments != NULL);

	*out_removed_attachment_ids = NULL;
	*out_added_attachments = NULL;

	if (!ecb_ews_extract_attachments (e_cal_component_get_icalcomponent (oldcomp), &old_attachments))
		old_attachments = NULL;

	if (!ecb_ews_extract_attachments (e_cal_component_get_icalcomponent (newcomp), &new_attachments))
		new_attachments = NULL;

	for (link = old_attachments; link; link = g_slist_next (link)) {
		EEwsAttachmentInfo *old_nfo = link->data;
		GSList *nlink;

		if (!old_nfo)
			continue;

		for (nlink = new_attachments; nlink; nlink = g_slist_next (nlink)) {
			EEwsAttachmentInfo *new_nfo = nlink->data;
			gboolean same = FALSE;

			if (!new_nfo ||
			    e_ews_attachment_info_get_type (old_nfo) != e_ews_attachment_info_get_type (new_nfo))
				continue;

			if (e_ews_attachment_info_get_type (old_nfo) == E_EWS_ATTACHMENT_INFO_TYPE_INLINED) {
				const gchar *old_data, *new_data;
				gsize old_len = -1, new_len = -1;

				old_data = e_ews_attachment_info_get_inlined_data (old_nfo, &old_len);
				new_data = e_ews_attachment_info_get_inlined_data (new_nfo, &new_len);

				same = old_len == new_len && (old_len == 0 ||
					(old_len > 0 && old_data && new_data && memcmp (old_data, new_data, old_len) == 0));
			} else if (e_ews_attachment_info_get_type (old_nfo) == E_EWS_ATTACHMENT_INFO_TYPE_URI) {
				same = g_strcmp0 (e_ews_attachment_info_get_uri (old_nfo), e_ews_attachment_info_get_uri (new_nfo)) == 0;
			}

			if (same) {
				new_attachments = g_slist_remove (new_attachments, new_nfo);
				e_ews_attachment_info_free (new_nfo);
				break;
			}
		}

		if (!nlink) {
			 
			g_warn_if_fail (e_ews_attachment_info_get_id (old_nfo) != NULL);
			*out_removed_attachment_ids = g_slist_prepend (*out_removed_attachment_ids,
				g_strdup (e_ews_attachment_info_get_id (old_nfo)));
		}
	}

	*out_added_attachments = new_attachments;

	g_slist_free_full (old_attachments, (GDestroyNotify) e_ews_attachment_info_free);
}