diff options
author | Claudio Takahasi <claudio.takahasi@openbossa.org> | 2006-03-27 17:03:26 +0000 |
---|---|---|
committer | Claudio Takahasi <claudio.takahasi@openbossa.org> | 2006-03-27 17:03:26 +0000 |
commit | 80c5591a3c9323cafdc0f0d0ab753cfdd4fec2f5 (patch) | |
tree | 76c9e8aa57775aa560287aab9d270197ff5a75e8 /hcid | |
parent | c971326c36330393203a4cce0173944fe1cd8efe (diff) |
Added GetRemoteVersion, GetRemoteRevision and GetRemoveManufacturer
Diffstat (limited to 'hcid')
-rw-r--r-- | hcid/dbus-adapter.c | 187 | ||||
-rw-r--r-- | hcid/dbus-api.txt | 19 | ||||
-rw-r--r-- | hcid/dbus.c | 1 |
3 files changed, 184 insertions, 23 deletions
diff --git a/hcid/dbus-adapter.c b/hcid/dbus-adapter.c index 7365a0c1..c0da1d1a 100644 --- a/hcid/dbus-adapter.c +++ b/hcid/dbus-adapter.c @@ -638,6 +638,8 @@ static DBusHandlerResult handle_dev_set_minor_class_req(DBusConnection *conn, DB return error_invalid_arguments(conn, msg); } + /* FIXME: check if the major class is computer. If not, return UnsupportedMajorClass */ + if (!minor) return error_invalid_arguments(conn, msg); @@ -681,7 +683,7 @@ static DBusHandlerResult handle_dev_set_minor_class_req(DBusConnection *conn, DB return error_failed(conn, msg, errno); } - signal = dev_signal_factory(dbus_data->dev_id, "MinorClassChange", + signal = dev_signal_factory(dbus_data->dev_id, "MinorClassChanged", DBUS_TYPE_STRING, &minor, DBUS_TYPE_INVALID); if (signal) { @@ -803,31 +805,168 @@ static DBusHandlerResult handle_dev_set_name_req(DBusConnection *conn, DBusMessa static DBusHandlerResult handle_dev_get_remote_version_req(DBusConnection *conn, DBusMessage *msg, void *data) { - return error_not_implemented(conn, msg); -} + struct hci_dbus_data *dbus_data = data; + DBusMessage *reply; + DBusError err; + char filename[PATH_MAX + 1]; + char addr[18], *addr_ptr, *str; + const char *str_ver; + char info_array[64], *info = info_array; + int compid, ver, subver; + int ecode; + uint8_t features; -static DBusHandlerResult handle_dev_get_remote_revision_req(DBusConnection *conn, DBusMessage *msg, void *data) -{ - return error_not_implemented(conn, msg); + dbus_error_init(&err); + + memset(info_array, 0, 64); + + dbus_message_get_args(msg, &err, + DBUS_TYPE_STRING, &addr_ptr, + DBUS_TYPE_INVALID); + + if (dbus_error_is_set(&err)) { + error("Can't extract message arguments:%s", err.message); + dbus_error_free(&err); + return error_invalid_arguments(conn, msg); + } + + if (check_address(addr_ptr) < 0) + return error_invalid_arguments(conn, msg); + + ecode = get_device_address(dbus_data->dev_id, addr, sizeof(addr)); + if (ecode < 0) + return error_failed(conn, msg, -ecode); + + snprintf(filename, PATH_MAX, "%s/%s/lastseen", STORAGEDIR, addr); + + str = textfile_get(filename, addr_ptr); + if (!str) + return error_unknown_address(conn, msg); + + free(str); + + snprintf(filename, PATH_MAX, "%s/%s/manufacturers", STORAGEDIR, addr); + + str = textfile_get(filename, addr_ptr); + if (!str) + return error_not_available(conn, msg); + + if (sscanf(str, "%d %d %d", &compid, &ver, &subver) != 3) { + /* corrupted file data */ + free(str); + goto failed; + } + + free(str); + + str_ver = lmp_vertostr(ver); + + /* default value */ + snprintf(info, 64, "Bluetooth %s", str_ver); + + snprintf(filename, PATH_MAX, "%s/%s/features", STORAGEDIR, addr); + + str = textfile_get(filename, addr_ptr); + if (!str) + goto failed; + + /* check if the data is not corrupted */ + if (strlen(str) == 16) { + /* Getting the third byte */ + features = ((str[6] - 48) << 4) | (str[7] - 48); + if (features & (LMP_EDR_ACL_2M | LMP_EDR_ACL_3M)) + snprintf(info, 64, "Bluetooth %s + EDR", str_ver); + } + + free(str); + +failed: + + reply = dbus_message_new_method_return(msg); + if (!reply) + return error_out_of_memory(conn, msg); + + dbus_message_append_args(reply, DBUS_TYPE_STRING, &info, + DBUS_TYPE_INVALID); + + return send_reply_and_unref(conn, reply); } -static DBusHandlerResult handle_dev_get_remote_manufacturer_req(DBusConnection *conn, DBusMessage *msg, void *data) +static DBusHandlerResult handle_dev_get_remote_revision_req(DBusConnection *conn, DBusMessage *msg, void *data) { struct hci_dbus_data *dbus_data = data; DBusMessage *reply; DBusError err; char filename[PATH_MAX + 1]; char addr[18], *addr_ptr, *str; - int compid; + char info_array[16], *info = info_array; + int compid, ver, subver; int ecode; + dbus_error_init(&err); + + memset(info_array, 0, 16); + + dbus_message_get_args(msg, &err, + DBUS_TYPE_STRING, &addr_ptr, + DBUS_TYPE_INVALID); + + if (dbus_error_is_set(&err)) { + error("Can't extract message arguments:%s", err.message); + dbus_error_free(&err); + return error_invalid_arguments(conn, msg); + } + + if (check_address(addr_ptr) < 0) + return error_invalid_arguments(conn, msg); + ecode = get_device_address(dbus_data->dev_id, addr, sizeof(addr)); if (ecode < 0) return error_failed(conn, msg, -ecode); + snprintf(filename, PATH_MAX, "%s/%s/lastseen", STORAGEDIR, addr); + + str = textfile_get(filename, addr_ptr); + if (!str) + return error_unknown_address(conn, msg); + + free(str); + snprintf(filename, PATH_MAX, "%s/%s/manufacturers", STORAGEDIR, addr); + str = textfile_get(filename, addr_ptr); + if (!str) + return error_not_available(conn, msg); + + if (sscanf(str, "%d %d %d", &compid, &ver, &subver) == 3) + snprintf(info, 16, "HCI 0x%X", subver); + + free(str); + + reply = dbus_message_new_method_return(msg); + if (!reply) + return error_out_of_memory(conn, msg); + + dbus_message_append_args(reply, DBUS_TYPE_STRING, &info, + DBUS_TYPE_INVALID); + + return send_reply_and_unref(conn, reply); +} + +static DBusHandlerResult handle_dev_get_remote_manufacturer_req(DBusConnection *conn, DBusMessage *msg, void *data) +{ + struct hci_dbus_data *dbus_data = data; + DBusMessage *reply; + DBusError err; + char filename[PATH_MAX + 1]; + char addr[18], *addr_ptr, *str; + char info_array[64], *info = info_array; + int compid, ver, subver; + int ecode; dbus_error_init(&err); + + memset(info_array, 0, 64); + dbus_message_get_args(msg, &err, DBUS_TYPE_STRING, &addr_ptr, DBUS_TYPE_INVALID); @@ -838,21 +977,37 @@ static DBusHandlerResult handle_dev_get_remote_manufacturer_req(DBusConnection * return error_invalid_arguments(conn, msg); } + if (check_address(addr_ptr) < 0) + return error_invalid_arguments(conn, msg); + + ecode = get_device_address(dbus_data->dev_id, addr, sizeof(addr)); + if (ecode < 0) + return error_failed(conn, msg, -ecode); + + snprintf(filename, PATH_MAX, "%s/%s/lastseen", STORAGEDIR, addr); + str = textfile_get(filename, addr_ptr); if (!str) - return error_failed(conn, msg, ENXIO); - - compid = atoi(str); + return error_unknown_address(conn, msg); free(str); - str = bt_compidtostr(compid); + snprintf(filename, PATH_MAX, "%s/%s/manufacturers", STORAGEDIR, addr); + + str = textfile_get(filename, addr_ptr); + if (!str) + return error_not_available(conn, msg); + + if (sscanf(str, "%d %d %d", &compid, &ver, &subver) == 3) + info = bt_compidtostr(compid); + + free(str); reply = dbus_message_new_method_return(msg); if (!reply) return error_out_of_memory(conn, msg); - dbus_message_append_args(reply, DBUS_TYPE_STRING, &str, + dbus_message_append_args(reply, DBUS_TYPE_STRING, &info, DBUS_TYPE_INVALID); return send_reply_and_unref(conn, reply); @@ -1526,9 +1681,11 @@ static DBusHandlerResult handle_dev_remove_bonding_req(DBusConnection *conn, DBu snprintf(filename, PATH_MAX, "%s/%s/linkkeys", STORAGEDIR, addr); - /* Delete the link key from storage */ - textfile_del(filename, addr_ptr); + if (textfile_del(filename, addr_ptr)) { + hci_close_dev(dd); + return error_bonding_does_not_exist(conn, msg); + } str2ba(addr_ptr, &bdaddr); diff --git a/hcid/dbus-api.txt b/hcid/dbus-api.txt index b3c1397b..be07afab 100644 --- a/hcid/dbus-api.txt +++ b/hcid/dbus-api.txt @@ -248,7 +248,7 @@ Methods string GetAddress() Changing this value doesn't set the adapter into discoverable mode. The SetMode method must be used. - Possible errors: org.bluez.Error.Failed + Possible errors: org.bluez.Error.InvalidArguments boolean IsConnectable() @@ -275,7 +275,7 @@ Methods string GetAddress() Return true if the local adapter is connected to the remote device. - Possible errors: none + Possible errors: org.bluez.Error.InvalidArguments array{string} ListConnections() @@ -329,7 +329,8 @@ Methods string GetAddress() If the major class is not "computer" an error should be returned. - Possible errors: org.bluez.Error.UnsupportedMajorClass + Possible errors: org.bluez.Error.InvalidArguments + org.bluez.Error.UnsupportedMajorClass array{string} GetServiceClasses() @@ -375,7 +376,8 @@ Methods string GetAddress() Example: "Bluetooth 2.0 + EDR" - Possible errors: org.bluez.Error.UnknownAddress + Possible errors: org.bluez.Error.InvalidArguments + org.bluez.Error.UnknownAddress org.bluez.Error.NotAvailable string GetRemoteRevision(string address) @@ -387,7 +389,8 @@ Methods string GetAddress() Example: "HCI 19.2" - Possible errors: org.bluez.Error.UnknownAddress + Possible errors: org.bluez.Error.InvalidArguments + org.bluez.Error.UnknownAddress org.bluez.Error.NotAvailable string GetRemoteManufacturer(string address) @@ -396,7 +399,8 @@ Methods string GetAddress() Example: "Nokia Mobile Phones" - Possible errors: org.bluez.Error.UnknownAddress + Possible errors: org.bluez.Error.InvalidArguments + org.bluez.Error.UnknownAddress org.bluez.Error.NotAvailable string GetRemoteCompany(string address) @@ -553,8 +557,7 @@ Methods string GetAddress() After deleting the link key this method will send a BondingRemoved signal. - Possible errors: org.bluez.Error.UnknownAddress - org.bluez.Error.DoesNotExist + Possible errors: org.bluez.Error.DoesNotExist boolean HasBonding(string address) diff --git a/hcid/dbus.c b/hcid/dbus.c index f58697e2..2c159ead 100644 --- a/hcid/dbus.c +++ b/hcid/dbus.c @@ -551,6 +551,7 @@ gboolean hcid_dbus_register_device(uint16_t id) if (ioctl(dd, HCIGETCONNLIST, (void *) cl) < 0) { free(cl); + cl = NULL; goto failed; } |