On Tuesday 24 of February 2015 13:05:59 Szymon Janc wrote: > This adds fake L2CAP based service that adds SDP records required > for passing SDP qualification tests. > > L2CAP sockets are currently not used in Android so it should be safe > to use it. > --- > android/socket.c | 118 > ++++++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 117 > insertions(+), 1 deletion(-) > > diff --git a/android/socket.c b/android/socket.c > index ec78dcd..15e1bfc 100644 > --- a/android/socket.c > +++ b/android/socket.c > @@ -98,6 +98,10 @@ static GList *connections = NULL; > > static struct rfcomm_channel servers[RFCOMM_CHANNEL_MAX + 1]; > > +static uint32_t test_sdp_record_uuid16 = 0; > +static uint32_t test_sdp_record_uuid32 = 0; > +static uint32_t test_sdp_record_uuid128 = 0; > + > static int rfsock_set_buffer(struct rfcomm_sock *rfsock) > { > socklen_t len = sizeof(int); > @@ -878,6 +882,113 @@ failed: > return HAL_STATUS_FAILED; > } > > +static uint32_t add_test_record(uuid_t *uuid) > +{ > + sdp_record_t *record; > + sdp_list_t *svclass_id; > + sdp_list_t *seq, *pbg_seq, *proto_seq, *ap_seq; > + sdp_list_t *proto, *proto1, *aproto; > + uuid_t l2cap_uuid, pbg_uuid, ap_uuid; > + > + record = sdp_record_alloc(); > + if (!record) > + return 0; > + > + record->handle = sdp_next_handle(); > + > + svclass_id = sdp_list_append(NULL, uuid); > + sdp_set_service_classes(record, svclass_id); > + > + sdp_uuid16_create(&l2cap_uuid, L2CAP_UUID); > + proto = sdp_list_append(NULL, &l2cap_uuid); > + seq = sdp_list_append(NULL, proto); > + > + proto_seq = sdp_list_append(NULL, seq); > + sdp_set_access_protos(record, proto_seq); > + > + sdp_uuid16_create(&pbg_uuid, PUBLIC_BROWSE_GROUP); > + pbg_seq = sdp_list_append(NULL, &pbg_uuid); > + sdp_set_browse_groups(record, pbg_seq); > + > + /* Additional Protocol Descriptor List */ > + sdp_uuid16_create(&ap_uuid, L2CAP_UUID); > + proto1 = sdp_list_append(NULL, &ap_uuid); > + ap_seq = sdp_list_append(NULL, proto1); > + aproto = sdp_list_append(NULL, ap_seq); > + sdp_set_add_access_protos(record, aproto); > + > + sdp_set_service_id(record, *uuid); > + sdp_set_record_state(record, 0); > + sdp_set_service_ttl(record, 0); > + sdp_set_service_avail(record, 0); > + sdp_set_url_attr(record, "http://www.bluez.org", > + "http://www.bluez.org", "http://www.bluez.org"); > + > + sdp_list_free(proto, NULL); > + sdp_list_free(seq, NULL); > + sdp_list_free(proto_seq, NULL); > + sdp_list_free(pbg_seq, NULL); > + sdp_list_free(svclass_id, NULL); > + > + if (bt_adapter_add_record(record, 0) < 0) { > + sdp_record_free(record); > + return 0; > + } > + > + return record->handle; > +} > + > +static void test_sdp_cleanup(void) > +{ > + if (test_sdp_record_uuid16) { > + bt_adapter_remove_record(test_sdp_record_uuid16); > + test_sdp_record_uuid16 = 0; > + } > + > + if (test_sdp_record_uuid32) { > + bt_adapter_remove_record(test_sdp_record_uuid32); > + test_sdp_record_uuid32 = 0; > + } > + > + if (test_sdp_record_uuid128) { > + bt_adapter_remove_record(test_sdp_record_uuid128); > + test_sdp_record_uuid128 = 0; > + } > +} > + > +static void test_sdp_init(void) > +{ > + char uuid128[] = {0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, > + 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff}; > + uuid_t u; > + > + sdp_uuid16_create(&u, 0xffff); > + test_sdp_record_uuid16 = add_test_record(&u); > + > + sdp_uuid32_create(&u, 0xffffffff); > + test_sdp_record_uuid32 = add_test_record(&u); > + > + sdp_uuid128_create(&u, uuid128); > + test_sdp_record_uuid128 = add_test_record(&u); > +} > + > +static uint8_t l2cap_listen(int chan, const uint8_t *name, const uint8_t > *uuid, + uint8_t flags, int *hal_sock) > +{ > + /* TODO be more strict here? */ > + if (strcmp("BlueZ", (const char *) name)) { > + error("socket: Only SDP test supported on L2CAP"); > + return HAL_STATUS_UNSUPPORTED; > + } > + > + test_sdp_cleanup(); > + test_sdp_init(); > + > + *hal_sock = -1; > + > + return HAL_STATUS_SUCCESS; > +} > + > static void handle_listen(const void *buf, uint16_t len) > { > const struct hal_cmd_socket_listen *cmd = buf; > @@ -889,8 +1000,11 @@ static void handle_listen(const void *buf, uint16_t > len) status = rfcomm_listen(cmd->channel, cmd->name, cmd->uuid, > cmd->flags, &hal_sock); > break; > - case HAL_SOCK_SCO: > case HAL_SOCK_L2CAP: > + status = l2cap_listen(cmd->channel, cmd->name, cmd->uuid, > + cmd->flags, &hal_sock); > + break; > + case HAL_SOCK_SCO: > status = HAL_STATUS_UNSUPPORTED; > break; > default: > @@ -1193,6 +1307,8 @@ void bt_socket_unregister(void) > > DBG(""); > > + test_sdp_cleanup(); > + > g_list_free_full(connections, cleanup_rfsock); > > for (ch = 0; ch <= RFCOMM_CHANNEL_MAX; ch++) Applied. -- BR Szymon Janc -- To unsubscribe from this list: send the line "unsubscribe linux-bluetooth" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html