This email list is read-only. Emails sent to this list will be discarded ---------------------------------- AUTHORS | 3 + client/pbap.c | 916 ++++++++++++++++++++++++++++++++++++++++++++++++++-- client/pbap.h | 10 +- client/session.c | 23 +- client/session.h | 1 + doc/client-api.txt | 4 +- src/pbap.c | 5 +- 7 files changed, 926 insertions(+), 36 deletions(-)
New commits: commit 148b31f8ac3812b0c7438f899013df0cd9decebb Author: Raymond Liu <[email protected]> Date: Thu Dec 18 17:12:11 2008 +0800 Add SetFilters and remove AddFilter, RemoveFilter for PBAP client commit 3d217b3f324ae6f2bb807100f4e63c6317304a8f Merge: e753bed6e064648f7fcc924d631b199d24eb0682 675c6788eeea184a1764a8602f64513cab259c10 Author: Marcel Holtmann <[email protected]> Date: Thu Dec 18 08:57:23 2008 +0100 Merge branch 'fix' of http://git.moblin.org/repos/users/raymond/obexd commit 675c6788eeea184a1764a8602f64513cab259c10 Author: Raymond Liu <[email protected]> Date: Thu Dec 18 14:11:08 2008 +0800 Bug fix on session_get, do not register transfer twice commit e753bed6e064648f7fcc924d631b199d24eb0682 Author: Raymond Liu <[email protected]> Date: Thu Dec 18 13:43:14 2008 +0800 Minor bug fix on Pull Search Function commit 8b0cc6951a3b3bd2a39ddc62bd6475a2db7ac515 Author: Raymond Liu <[email protected]> Date: Thu Dec 18 11:24:44 2008 +0800 Implement Filter related function for PBAP client commit 70cc605c9fe4d97df4f8b9385f112c183472dc82 Author: Raymond Liu <[email protected]> Date: Wed Dec 17 10:28:04 2008 +0800 Implement List and Search function for PBAP client commit 27d147846694bef39814d435f7f1c9bb21c9c154 Author: Raymond Liu <[email protected]> Date: Tue Dec 16 17:11:55 2008 +0800 add Pull function for PBAP client commit 3e151ac60d30b00db6177f94755dc8463b8ff049 Author: Raymond Liu <[email protected]> Date: Tue Dec 16 16:12:45 2008 +0800 add GetSize function for PBAP client commit 5479e11e5609f48603d35200bc39a82d8ce34fbd Author: Raymond Liu <[email protected]> Date: Tue Dec 16 13:30:22 2008 +0800 add PullAll function for PBAP client commit b75a2e700c5493dc0c11d31a4d0b7d9238160cdc Author: Raymond Liu <[email protected]> Date: Tue Dec 16 09:50:38 2008 +0800 Add SetFormat and SetOrder function for PBAP client commit f3e500353065abaed38d8e4856f397a0c69b9c63 Author: Raymond Liu <[email protected]> Date: Mon Dec 15 13:57:38 2008 +0800 Implement Select function for PBAP Client commit 29650a6ddf2adcdf9e0c47fa1a13de045f0f39d5 Author: Marcel Holtmann <[email protected]> Date: Mon Dec 15 23:30:32 2008 +0100 Update list of contributors commit cd0bf89a5307c394dbcc797156396d757e0effda Author: Forrest Zhao <[email protected]> Date: Mon Dec 15 08:21:21 2008 +0800 fix a bug in pbap_setpath() when session->current_folder is NULL Diff in this email is a maximum of 400 lines. diff --git a/AUTHORS b/AUTHORS index 785ff52..10a3130 100644 --- a/AUTHORS +++ b/AUTHORS @@ -1,4 +1,7 @@ Marcel Holtmann <[email protected]> Johan Hedberg <[email protected]> Claudio Takahasi <[email protected]> +Luiz Augusto von Dentz <[email protected]> Vinicius Costa Gomes <[email protected]> +Forrest Zhao <[email protected]> +Raymond Liu <[email protected]> diff --git a/client/pbap.c b/client/pbap.c index e29d3c9..46cc09f 100644 --- a/client/pbap.c +++ b/client/pbap.c @@ -26,61 +26,931 @@ #include <config.h> #endif +#include <errno.h> #include <glib.h> #include <gdbus.h> #include "session.h" #include "pbap.h" -static DBusMessage *pbap_pull_phonebook(DBusConnection *connection, - DBusMessage *message, void *user_data) +#define ERROR_INF PBAP_INTERFACE ".Error" + +#define FORMAT_VCARD21 0x0 +#define FORMAT_VCARD30 0x1 + +#define ORDER_INDEXED 0x0 +#define ORDER_ALPHANUMERIC 0x1 +#define ORDER_PHONETIC 0x2 + +#define ATTRIB_NAME 0x0 +#define ATTRIB_NUMBER 0x1 +#define ATTRIB_SOUND 0x2 + +#define DEFAULT_COUNT 65535 +#define DEFAULT_OFFSET 0 + +#define PULLPHONEBOOK 0x1 +#define GETPHONEBOOKSIZE 0x2 + +#define ORDER_TAG 0x01 +#define SEARCHVALUE_TAG 0x02 +#define SEARCHATTRIB_TAG 0x03 +#define MAXLISTCOUNT_TAG 0x04 +#define LISTSTARTOFFSET_TAG 0x05 +#define FILTER_TAG 0x06 +#define FORMAT_TAG 0X07 +#define PHONEBOOKSIZE_TAG 0X08 +#define NEWMISSEDCALLS_TAG 0X09 + +/* The following length is in the unit of byte */ +#define ORDER_LEN 1 +#define SEARCHATTRIB_LEN 1 +#define MAXLISTCOUNT_LEN 2 +#define LISTSTARTOFFSET_LEN 2 +#define FILTER_LEN 8 +#define FORMAT_LEN 1 +#define PHONEBOOKSIZE_LEN 2 +#define NEWMISSEDCALLS_LEN 1 + +#define get_be16(val) GUINT16_FROM_BE(bt_get_unaligned((guint16 *) val)) + +static const char *filter_list[] = { + "VERSION", + "FN", + "N", + "PHOTO", + "BDAY", + "ADR", + "LABEL", + "TEL", + "EMAIL", + "MAILER", + "TZ", + "GEO", + "TITLE", + "ROLE", + "LOGO", + "AGENT", + "ORG", + "NOTE", + "REV", + "SOUND", + "URL", + "UID", + "KEY", + "NICKNAME", + "CATEGORIES", + "PROID", + "CLASS", + "SORT-STRING", + "X-IRMC-CALL-DATETIME", + NULL +}; + +#define FILTER_BIT_MAX 63 +#define FILTER_ALL 0xFFFFFFFFFFFFFFFFULL + +struct pullphonebook_apparam { + uint8_t filter_tag; + uint8_t filter_len; + uint64_t filter; + uint8_t format_tag; + uint8_t format_len; + uint8_t format; + uint8_t maxlistcount_tag; + uint8_t maxlistcount_len; + uint16_t maxlistcount; + uint8_t liststartoffset_tag; + uint8_t liststartoffset_len; + uint16_t liststartoffset; +} __attribute__ ((packed)); + +struct pullvcardentry_apparam { + uint8_t filter_tag; + uint8_t filter_len; + uint64_t filter; + uint8_t format_tag; + uint8_t format_len; + uint8_t format; +} __attribute__ ((packed)); + +struct apparam_hdr { + uint8_t tag; + uint8_t len; + uint8_t val[0]; +} __attribute__ ((packed)); + +#define APPARAM_HDR_SIZE 2 + +static void listing_element(GMarkupParseContext *ctxt, + const gchar *element, + const gchar **names, + const gchar **values, + gpointer user_data, + GError **gerr) { - return NULL; + DBusMessageIter *item = user_data, entry; + gchar **key; + const gchar *handle = NULL, *vcardname = NULL; + + if (g_str_equal(element, "card") != TRUE) + return; + + for (key = (gchar **) names; *key; key++, values++) { + if (g_str_equal(*key, "handle") == TRUE) + handle = *values; + else if (g_str_equal(*key, "name") == TRUE) + vcardname = *values; + } + + if (!handle || !vcardname) + return; + + dbus_message_iter_open_container(item, DBUS_TYPE_STRUCT, NULL, &entry); + dbus_message_iter_append_basic(&entry, DBUS_TYPE_STRING, &handle); + dbus_message_iter_append_basic(&entry, DBUS_TYPE_STRING, &vcardname); + dbus_message_iter_close_container(item, &entry); +} + +static const GMarkupParser listing_parser = { + listing_element, + NULL, + NULL, + NULL, + NULL +}; +static gchar *build_phonebook_path(const char *location, const char *item) +{ + gchar *path = NULL, *tmp, *tmp1; + + if (!g_ascii_strcasecmp(location, "INT") || + !g_ascii_strcasecmp(location, "INTERNAL")) + path = g_strdup("telecom"); + else if (!g_ascii_strncasecmp(location, "SIM", 3)) { + if (strlen(location) == 3) + tmp = g_strdup("SIM1"); + else + tmp = g_ascii_strup(location, 4); + + path = g_build_filename(tmp, "telecom", NULL); + g_free(tmp); + } else + return NULL; + + if (!g_ascii_strcasecmp(item, "PB") || + !g_ascii_strcasecmp(item, "ICH") || + !g_ascii_strcasecmp(item, "OCH") || + !g_ascii_strcasecmp(item, "MCH") || + !g_ascii_strcasecmp(item, "CCH")) { + tmp = path; + tmp1 = g_ascii_strdown(item, -1); + path = g_build_filename(tmp, tmp1, NULL); + g_free(tmp); + g_free(tmp1); + } else { + g_free(path); + return NULL; + } + + return path; +} + +/* should only be called inside pbap_set_path */ +static void pbap_reset_path(struct session_data *session) +{ + int err = 0; + char **paths = NULL, **item; + struct pbap_data *pbapdata = session->pbapdata; + + if (!pbapdata->path) + return; + + gw_obex_chdir(session->obex, "", &err); + + paths = g_strsplit(pbapdata->path, "/", 3); + + for (item = paths; *item; item++) + gw_obex_chdir(session->obex, *item, &err); + + g_strfreev(paths); } -static DBusMessage *pbap_set_phonebook(DBusConnection *connection, - DBusMessage *message, void *user_data) +static gint pbap_set_path(struct session_data *session, const char *path) { + int err = 0; + char **paths = NULL, **item; + struct pbap_data *pbapdata = session->pbapdata; + + if (!path) + return OBEX_RSP_BAD_REQUEST; + + if (pbapdata->path != NULL && g_str_equal(pbapdata->path, path)) + return 0; + + if (gw_obex_chdir(session->obex, "", &err) == FALSE) { + if (err == OBEX_RSP_NOT_IMPLEMENTED) + goto done; + goto fail; + } + + paths = g_strsplit(path, "/", 3); + for (item = paths; *item; item++) { + if (gw_obex_chdir(session->obex, *item, &err) == FALSE) { + /* we need to reset the path to the saved one on fail*/ + pbap_reset_path(session); + goto fail; + } + } + + g_strfreev(paths); + +done: + g_free(pbapdata->path); + pbapdata->path = g_strdup(path); + return 0; + +fail: + if (paths) + g_strfreev(paths); + + return err; +} + +static void read_return_apparam(struct session_data *session, + guint16 *phone_book_size, guint8 *new_missed_calls) +{ + GwObexXfer *xfer = session->xfer; + unsigned char *buf; + size_t size = 0; + + *phone_book_size = 0; + *new_missed_calls = 0; + + if (xfer == NULL) + return; + + buf = gw_obex_xfer_object_apparam(xfer, &size); + + if (size < APPARAM_HDR_SIZE) + return; + + while (size > APPARAM_HDR_SIZE) { + struct apparam_hdr *hdr = (struct apparam_hdr *) buf; + + if (hdr->len > size - APPARAM_HDR_SIZE) { + fprintf(stderr, "Unexpected PBAP pullphonebook app" + " length, tag %d, len %d\n", + hdr->tag, hdr->len); + return; + } + + switch (hdr->tag) { + case PHONEBOOKSIZE_TAG: + if (hdr->len == PHONEBOOKSIZE_LEN) + *phone_book_size = get_be16(hdr->val); + break; + case NEWMISSEDCALLS_TAG: + if (hdr->len == NEWMISSEDCALLS_LEN) + *new_missed_calls = hdr->val[0]; + break; + default: + fprintf(stderr, "Unexpected PBAP pullphonebook app" + " parameter, tag %d, len %d\n", + hdr->tag, hdr->len); + } + + buf += APPARAM_HDR_SIZE + hdr->len; + size -= APPARAM_HDR_SIZE + hdr->len; + } +} + +static void pull_phonebook_callback(struct session_data *session, + void *user_data) +{ + DBusMessage *reply; + char *buf = ""; + + reply = dbus_message_new_method_return(session->msg); + + if (session->filled > 0) + buf = session->buffer; + + dbus_message_append_args(reply, + DBUS_TYPE_STRING, &buf, + DBUS_TYPE_INVALID); + + session->filled = 0; + g_dbus_send_message(session->conn, reply); + dbus_message_unref(session->msg); + session->msg = NULL; +} + +static void phonebook_size_callback(struct session_data *session, + void *user_data) +{ + DBusMessage *reply; + guint16 phone_book_size; + guint8 new_missed_calls; + + reply = dbus_message_new_method_return(session->msg); + + read_return_apparam(session, &phone_book_size, &new_missed_calls); + + dbus_message_append_args(reply, + DBUS_TYPE_UINT16, &phone_book_size, + DBUS_TYPE_INVALID); + + session->filled = 0; + g_dbus_send_message(session->conn, reply); + dbus_message_unref(session->msg); + session->msg = NULL; +} + +static void pull_vcard_listing_callback(struct session_data *session, + void *user_data) +{ + GMarkupParseContext *ctxt; + DBusMessage *reply; + DBusMessageIter iter, array; + int i; + + reply = dbus_message_new_method_return(session->msg); + + if (session->filled == 0) + goto done; + + for (i = session->filled - 1; i > 0; i--) { + if (session->buffer[i] != '\0') + break; + + session->filled--; + } + + dbus_message_iter_init_append(reply, &iter); + dbus_message_iter_open_container(&iter, DBUS_TYPE_ARRAY, + DBUS_STRUCT_BEGIN_CHAR_AS_STRING + DBUS_TYPE_STRING_AS_STRING DBUS_TYPE_STRING_AS_STRING + DBUS_STRUCT_END_CHAR_AS_STRING, &array); + ctxt = g_markup_parse_context_new(&listing_parser, 0, &array, NULL); + g_markup_parse_context_parse(ctxt, session->buffer, + session->filled, NULL); + g_markup_parse_context_free(ctxt); + dbus_message_iter_close_container(&iter, &array); + + session->filled = 0; + +done: + g_dbus_send_message(session->conn, reply); _______________________________________________ Commits mailing list [email protected] https://lists.moblin.org/mailman/listinfo/commits
