[Adapt: HAL] Add support for LE Advertising 34/119834/1
authorAnupam Roy <anupam.r@samsung.com>
Mon, 20 Mar 2017 08:32:28 +0000 (14:02 +0530)
committerAnupam Roy <anupam.r@samsung.com>
Mon, 20 Mar 2017 08:32:28 +0000 (14:02 +0530)
Change-Id: I8bc283e632a0bce274508712c5f24de1eed975be
Signed-off-by: Anupam Roy <anupam.r@samsung.com>
17 files changed:
bt-oal/bluez_hal/CMakeLists.txt
bt-oal/bluez_hal/hardware/bt_gatt.h [new file with mode: 0644]
bt-oal/bluez_hal/hardware/bt_gatt_client.h [new file with mode: 0644]
bt-oal/bluez_hal/hardware/bt_gatt_server.h [new file with mode: 0644]
bt-oal/bluez_hal/hardware/bt_gatt_types.h [new file with mode: 0644]
bt-oal/bluez_hal/inc/bt-hal-msg.h
bt-oal/bluez_hal/inc/bt-hal-utils.h
bt-oal/bluez_hal/src/bt-hal-adapter-le.c [new file with mode: 0644]
bt-oal/bluez_hal/src/bt-hal-adapter-le.h [new file with mode: 0644]
bt-oal/bluez_hal/src/bt-hal-bluetooth.c
bt-oal/bluez_hal/src/bt-hal-dbus-common-utils.h
bt-oal/bluez_hal/src/bt-hal-event-receiver.c
bt-oal/bluez_hal/src/bt-hal-gatt-client.c [new file with mode: 0644]
bt-oal/bluez_hal/src/bt-hal-gatt-server.c [new file with mode: 0644]
bt-oal/bluez_hal/src/bt-hal-gatt-server.h [new file with mode: 0644]
bt-oal/bluez_hal/src/bt-hal-gatt.c [new file with mode: 0644]
bt-oal/bluez_hal/src/bt-hal-gatt.h [new file with mode: 0644]

index 7d19a95..e337977 100644 (file)
@@ -4,6 +4,7 @@ PROJECT(bluetooth.default C)
 SET(SRCS
 ./src/bt-hal-bluetooth.c
 ./src/bt-hal-adapter-dbus-handler.c
+./src/bt-hal-adapter-le.c
 ./src/bt-hal-device-dbus-handler.c
 ./src/bt-hal-dbus-common-utils.c
 ./src/bt-hal-event-receiver.c
@@ -26,6 +27,9 @@ SET(SRCS
 ./src/bt-hal-rfcomm-dbus-handler.c
 ./src/bt-hal-hdp.c
 ./src/bt-hal-hdp-dbus-handler.c
+./src/bt-hal-gatt.c
+./src/bt-hal-gatt-server.c
+./src/bt-hal-gatt-client.c
 )
 
 SET(PREFIX ${CMAKE_INSTALL_PREFIX})
@@ -42,6 +46,7 @@ INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/src/)
 INCLUDE_DIRECTORIES(${CMAKE_CURRENT_SOURCE_DIR}/inc/)
 
 SET(PKG_MODULES
+       vconf
         dbus-glib-1
        glib-2.0
         gio-2.0
@@ -86,5 +91,6 @@ TARGET_LINK_LIBRARIES(${PROJECT_NAME} -ldbus-1)
 TARGET_LINK_LIBRARIES(${PROJECT_NAME} -lgobject-2.0)
 TARGET_LINK_LIBRARIES(${PROJECT_NAME} -lsyspopup_caller)
 TARGET_LINK_LIBRARIES(${PROJECT_NAME} -lbundle)
+TARGET_LINK_LIBRARIES(${PROJECT_NAME} -lvconf)
 
 INSTALL(TARGETS ${PROJECT_NAME} DESTINATION ${LIBDIR} COMPONENT RuntimeLibraries)
diff --git a/bt-oal/bluez_hal/hardware/bt_gatt.h b/bt-oal/bluez_hal/hardware/bt_gatt.h
new file mode 100644 (file)
index 0000000..42e14c2
--- /dev/null
@@ -0,0 +1,61 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+
+#ifndef ANDROID_INCLUDE_BT_GATT_H
+#define ANDROID_INCLUDE_BT_GATT_H
+
+#include <stdint.h>
+#include "bt_gatt_client.h"
+#include "bt_gatt_server.h"
+
+__BEGIN_DECLS
+
+/** BT-GATT callbacks */
+typedef struct {
+    /** Set to sizeof(btgatt_callbacks_t) */
+    size_t size;
+
+    /** GATT Client callbacks */
+    const btgatt_client_callbacks_t* client;
+
+    /** GATT Server callbacks */
+    const btgatt_server_callbacks_t* server;
+} btgatt_callbacks_t;
+
+/** Represents the standard Bluetooth GATT interface. */
+typedef struct {
+    /** Set to sizeof(btgatt_interface_t) */
+    size_t          size;
+
+    /**
+     * Initializes the interface and provides callback routines
+     */
+    bt_status_t (*init)( const btgatt_callbacks_t* callbacks );
+
+    /** Closes the interface */
+    void (*cleanup)( void );
+
+    /** Pointer to the GATT client interface methods.*/
+    const btgatt_client_interface_t* client;
+
+    /** Pointer to the GATT server interface methods.*/
+    const btgatt_server_interface_t* server;
+} btgatt_interface_t;
+
+__END_DECLS
+
+#endif /* ANDROID_INCLUDE_BT_GATT_H */
diff --git a/bt-oal/bluez_hal/hardware/bt_gatt_client.h b/bt-oal/bluez_hal/hardware/bt_gatt_client.h
new file mode 100644 (file)
index 0000000..31ec30d
--- /dev/null
@@ -0,0 +1,364 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ * Copyright (C) 2009-2014 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+
+#ifndef ANDROID_INCLUDE_BT_GATT_CLIENT_H
+#define ANDROID_INCLUDE_BT_GATT_CLIENT_H
+
+#include <stdint.h>
+#include "bt_gatt_types.h"
+
+__BEGIN_DECLS
+
+/** Buffer type for unformatted reads/writes */
+typedef struct
+{
+    uint8_t             value[BTGATT_MAX_ATTR_LEN];
+    uint16_t            len;
+} btgatt_unformatted_value_t;
+
+/** Parameters for GATT read operations */
+typedef struct
+{
+    btgatt_srvc_id_t    srvc_id;
+    btgatt_gatt_id_t    char_id;
+    btgatt_gatt_id_t    descr_id;
+    btgatt_unformatted_value_t value;
+    uint16_t            value_type;
+    uint8_t             status;
+} btgatt_read_params_t;
+
+/** Parameters for GATT write operations */
+typedef struct
+{
+    btgatt_srvc_id_t    srvc_id;
+    btgatt_gatt_id_t    char_id;
+    btgatt_gatt_id_t    descr_id;
+    uint8_t             status;
+} btgatt_write_params_t;
+
+/** Attribute change notification parameters */
+typedef struct
+{
+    uint8_t             value[BTGATT_MAX_ATTR_LEN];
+    bt_bdaddr_t         bda;
+    btgatt_srvc_id_t    srvc_id;
+    btgatt_gatt_id_t    char_id;
+    uint16_t            len;
+    uint8_t             is_notify;
+} btgatt_notify_params_t;
+
+typedef struct
+{
+    bt_bdaddr_t        *bda1;
+    bt_uuid_t          *uuid1;
+    uint16_t            u1;
+    uint16_t            u2;
+    uint16_t            u3;
+    uint16_t            u4;
+    uint16_t            u5;
+} btgatt_test_params_t;
+
+/** BT-GATT Client callback structure. */
+
+/** Callback invoked in response to register_client */
+typedef void (*register_client_callback)(int status, int client_if,
+                bt_uuid_t *app_uuid);
+
+/** Callback for scan results */
+typedef void (*scan_result_callback)(bt_bdaddr_t* bda, int rssi, uint8_t* adv_data);
+
+/** GATT open callback invoked in response to open */
+typedef void (*connect_callback)(int conn_id, int status, int client_if, bt_bdaddr_t* bda);
+
+/** Callback invoked in response to close */
+typedef void (*disconnect_callback)(int conn_id, int status,
+                int client_if, bt_bdaddr_t* bda);
+
+/**
+ * Invoked in response to search_service when the GATT service search
+ * has been completed.
+ */
+typedef void (*search_complete_callback)(int conn_id, int status);
+
+/** Reports GATT services on a remote device */
+typedef void (*search_result_callback)( int conn_id, btgatt_srvc_id_t *srvc_id);
+
+/** GATT characteristic enumeration result callback */
+typedef void (*get_characteristic_callback)(int conn_id, int status,
+                btgatt_srvc_id_t *srvc_id, btgatt_gatt_id_t *char_id,
+                int char_prop);
+
+/** GATT descriptor enumeration result callback */
+typedef void (*get_descriptor_callback)(int conn_id, int status,
+                btgatt_srvc_id_t *srvc_id, btgatt_gatt_id_t *char_id,
+                btgatt_gatt_id_t *descr_id);
+
+/** GATT included service enumeration result callback */
+typedef void (*get_included_service_callback)(int conn_id, int status,
+                btgatt_srvc_id_t *srvc_id, btgatt_srvc_id_t *incl_srvc_id);
+
+/** Callback invoked in response to [de]register_for_notification */
+typedef void (*register_for_notification_callback)(int conn_id,
+                int registered, int status, btgatt_srvc_id_t *srvc_id,
+                btgatt_gatt_id_t *char_id);
+
+/**
+ * Remote device notification callback, invoked when a remote device sends
+ * a notification or indication that a client has registered for.
+ */
+typedef void (*notify_callback)(int conn_id, btgatt_notify_params_t *p_data);
+
+/** Reports result of a GATT read operation */
+typedef void (*read_characteristic_callback)(int conn_id, int status,
+                btgatt_read_params_t *p_data);
+
+/** GATT write characteristic operation callback */
+typedef void (*write_characteristic_callback)(int conn_id, int status,
+                btgatt_write_params_t *p_data);
+
+/** GATT execute prepared write callback */
+typedef void (*execute_write_callback)(int conn_id, int status);
+
+/** Callback invoked in response to read_descriptor */
+typedef void (*read_descriptor_callback)(int conn_id, int status,
+                btgatt_read_params_t *p_data);
+
+/** Callback invoked in response to write_descriptor */
+typedef void (*write_descriptor_callback)(int conn_id, int status,
+                btgatt_write_params_t *p_data);
+
+/** Callback triggered in response to read_remote_rssi */
+typedef void (*read_remote_rssi_callback)(int client_if, bt_bdaddr_t* bda,
+                                          int rssi, int status);
+
+/** Callback invoked when the MTU for a given connection changes */
+typedef void (*configure_mtu_callback)(int conn_id, int status, int mtu);
+
+/** Callback invoked when a scan filter configuration command has completed */
+typedef void (*scan_filter_cfg_callback)(int action, int client_if, int status, int filt_type,
+                                         int avbl_space);
+
+/** Callback invoked when scan param has been added, cleared, or deleted */
+typedef void (*scan_filter_param_callback)(int action, int client_if, int status,
+                                         int avbl_space);
+
+/** Callback invoked when a scan filter configuration command has completed */
+typedef void (*scan_filter_status_callback)(int enable, int client_if, int status);
+
+/**
+ * Callback notifying an application that a remote device connection is currently congested
+ * and cannot receive any more data. An application should avoid sending more data until
+ * a further callback is received indicating the congestion status has been cleared.
+ */
+typedef void (*congestion_callback)(int conn_id, bool congested);
+/** Callback invoked when batchscan storage config operation has completed */
+typedef void (*batchscan_cfg_storage_callback)(int client_if, int status);
+
+/** Callback invoked when batchscan enable / disable operation has completed */
+typedef void (*batchscan_enable_disable_callback)(int action, int client_if, int status);
+
+/** Callback invoked when batchscan reports are obtained */
+typedef void (*batchscan_reports_callback)(int client_if, int status, int report_format,
+                                           int num_records, int data_len, uint8_t* rep_data);
+
+/** Callback invoked when batchscan storage threshold limit is crossed */
+typedef void (*batchscan_threshold_callback)(int client_if);
+
+/** Track ADV VSE callback invoked when tracked device is found or lost */
+typedef void (*track_adv_event_callback)(int client_if, int filt_index, int addr_type,
+                                             bt_bdaddr_t* bda, int adv_state);
+typedef struct {
+       register_client_callback            register_client_cb;
+       scan_result_callback                scan_result_cb;
+       connect_callback                    open_cb;
+       disconnect_callback                 close_cb;
+       search_complete_callback            search_complete_cb;
+       search_result_callback              search_result_cb;
+       get_characteristic_callback         get_characteristic_cb;
+       get_descriptor_callback             get_descriptor_cb;
+       get_included_service_callback       get_included_service_cb;
+       register_for_notification_callback  register_for_notification_cb;
+       notify_callback                     notify_cb;
+       read_characteristic_callback        read_characteristic_cb;
+       write_characteristic_callback       write_characteristic_cb;
+       read_descriptor_callback            read_descriptor_cb;
+       write_descriptor_callback           write_descriptor_cb;
+       execute_write_callback              execute_write_cb;
+       read_remote_rssi_callback           read_remote_rssi_cb;
+       configure_mtu_callback              configure_mtu_cb;
+       scan_filter_cfg_callback            scan_filter_cfg_cb;
+       scan_filter_param_callback          scan_filter_param_cb;
+       scan_filter_status_callback         scan_filter_status_cb;
+       congestion_callback                 congestion_cb;
+       batchscan_cfg_storage_callback      batchscan_cfg_storage_cb;
+       batchscan_enable_disable_callback   batchscan_enb_disable_cb;
+       batchscan_reports_callback          batchscan_reports_cb;
+       batchscan_threshold_callback        batchscan_threshold_cb;
+       track_adv_event_callback            track_adv_event_cb;
+} btgatt_client_callbacks_t;
+
+/** Represents the standard BT-GATT client interface. */
+
+typedef struct {
+    /** Registers a GATT client application with the stack */
+    bt_status_t (*register_client)( bt_uuid_t *uuid );
+
+    /** Unregister a client application from the stack */
+    bt_status_t (*unregister_client)(int client_if );
+
+    /** Start or stop LE device scanning */
+    bt_status_t (*scan)( int client_if, bool start );
+
+    /** Create a connection to a remote LE or dual-mode device */
+    bt_status_t (*connect)( int client_if, const bt_bdaddr_t *bd_addr,
+                         bool is_direct );
+
+    /** Disconnect a remote device or cancel a pending connection */
+    bt_status_t (*disconnect)( int client_if, const bt_bdaddr_t *bd_addr,
+                    int conn_id);
+
+    /** Clear the attribute cache for a given device */
+    bt_status_t (*refresh)( int client_if, const bt_bdaddr_t *bd_addr );
+
+    /**
+     * Enumerate all GATT services on a connected device.
+     * Optionally, the results can be filtered for a given UUID.
+     */
+    bt_status_t (*search_service)(int conn_id, bt_uuid_t *filter_uuid );
+
+    /**
+     * Enumerate included services for a given service.
+     * Set start_incl_srvc_id to NULL to get the first included service.
+     */
+    bt_status_t (*get_included_service)( int conn_id, btgatt_srvc_id_t *srvc_id,
+                                         btgatt_srvc_id_t *start_incl_srvc_id);
+
+    /**
+     * Enumerate characteristics for a given service.
+     * Set start_char_id to NULL to get the first characteristic.
+     */
+    bt_status_t (*get_characteristic)( int conn_id,
+                    btgatt_srvc_id_t *srvc_id, btgatt_gatt_id_t *start_char_id);
+
+    /**
+     * Enumerate descriptors for a given characteristic.
+     * Set start_descr_id to NULL to get the first descriptor.
+     */
+    bt_status_t (*get_descriptor)( int conn_id,
+                    btgatt_srvc_id_t *srvc_id, btgatt_gatt_id_t *char_id,
+                    btgatt_gatt_id_t *start_descr_id);
+
+    /** Read a characteristic on a remote device */
+    bt_status_t (*read_characteristic)( int conn_id,
+                    btgatt_srvc_id_t *srvc_id, btgatt_gatt_id_t *char_id,
+                    int auth_req );
+
+    /** Write a remote characteristic */
+    bt_status_t (*write_characteristic)(int conn_id,
+                    btgatt_srvc_id_t *srvc_id, btgatt_gatt_id_t *char_id,
+                    int write_type, int len, int auth_req,
+                    char* p_value);
+
+    /** Read the descriptor for a given characteristic */
+    bt_status_t (*read_descriptor)(int conn_id,
+                    btgatt_srvc_id_t *srvc_id, btgatt_gatt_id_t *char_id,
+                    btgatt_gatt_id_t *descr_id, int auth_req);
+
+    /** Write a remote descriptor for a given characteristic */
+    bt_status_t (*write_descriptor)( int conn_id,
+                    btgatt_srvc_id_t *srvc_id, btgatt_gatt_id_t *char_id,
+                    btgatt_gatt_id_t *descr_id, int write_type, int len,
+                    int auth_req, char* p_value);
+
+    /** Execute a prepared write operation */
+    bt_status_t (*execute_write)(int conn_id, int execute);
+
+    /**
+     * Register to receive notifications or indications for a given
+     * characteristic
+     */
+    bt_status_t (*register_for_notification)( int client_if,
+                    const bt_bdaddr_t *bd_addr, btgatt_srvc_id_t *srvc_id,
+                    btgatt_gatt_id_t *char_id);
+
+    /** Deregister a previous request for notifications/indications */
+    bt_status_t (*deregister_for_notification)( int client_if,
+                    const bt_bdaddr_t *bd_addr, btgatt_srvc_id_t *srvc_id,
+                    btgatt_gatt_id_t *char_id);
+
+    /** Request RSSI for a given remote device */
+    bt_status_t (*read_remote_rssi)( int client_if, const bt_bdaddr_t *bd_addr);
+
+    /** OTA firmware download */
+    bt_status_t (*ota_fw_update)(int client_if, int conn_id, const bt_bdaddr_t *bd_addr, char* path);
+
+    /** Determine the type of the remote device (LE, BR/EDR, Dual-mode) */
+    int (*get_device_type)( const bt_bdaddr_t *bd_addr );
+
+    /** Request a connection parameter update */
+    bt_status_t (*conn_parameter_update)(bt_bdaddr_t *bd, int min_int, int max_int, int latency, int timeout);
+
+    /** Test mode interface */
+    bt_status_t (*test_command)( int command, btgatt_test_params_t* params);
+
+    /** MTU Exchange request from client */
+    bt_status_t (*configure_mtu)( int conn_id, int mtu);
+
+       /** Setup scan filter params */
+    bt_status_t (*scan_filter_param_setup)(int client_if, int action, int filt_index, int feat_seln,
+                                      int list_logic_type, int filt_logic_type, int rssi_high_thres,
+                                      int rssi_low_thres, int dely_mode, int found_timeout,
+                                      int lost_timeout, int found_timeout_cnt);
+
+
+    /** Configure a scan filter condition  */
+    bt_status_t (*scan_filter_add_remove)(int client_if, int action, int filt_type,
+                                   int filt_index, int company_id,
+                                   int company_id_mask, const bt_uuid_t *p_uuid,
+                                   const bt_uuid_t *p_uuid_mask, const bt_bdaddr_t *bd_addr,
+                                   char addr_type, int data_len, char* p_data, int mask_len,
+                                   char* p_mask);
+
+    /** Clear all scan filter conditions for specific filter index*/
+    bt_status_t (*scan_filter_clear)(int client_if, int filt_index);
+
+    /** Enable / disable scan filter feature*/
+    bt_status_t (*scan_filter_enable)(int client_if, bool enable);
+
+    /** Sets the LE scan interval and window in units of N*0.625 msec */
+    bt_status_t (*set_scan_parameters)(int scan_interval, int scan_window);
+
+    /* Configure the batchscan storage */
+    bt_status_t (*batchscan_cfg_storage)(int client_if, int batch_scan_full_max,
+        int batch_scan_trunc_max, int batch_scan_notify_threshold);
+
+    /* Enable batchscan */
+    bt_status_t (*batchscan_enb_batch_scan)(int client_if, int scan_mode,
+        int scan_interval, int scan_window, int addr_type, int discard_rule);
+
+    /* Disable batchscan */
+    bt_status_t (*batchscan_dis_batch_scan)(int client_if);
+
+    /* Read out batchscan reports */
+    bt_status_t (*batchscan_read_reports)(int client_if, int scan_mode);
+
+} btgatt_client_interface_t;
+
+__END_DECLS
+
+#endif /* ANDROID_INCLUDE_BT_GATT_CLIENT_H */
diff --git a/bt-oal/bluez_hal/hardware/bt_gatt_server.h b/bt-oal/bluez_hal/hardware/bt_gatt_server.h
new file mode 100644 (file)
index 0000000..8bb0ac6
--- /dev/null
@@ -0,0 +1,256 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+
+#ifndef ANDROID_INCLUDE_BT_GATT_SERVER_H
+#define ANDROID_INCLUDE_BT_GATT_SERVER_H
+
+#include <stdint.h>
+
+#include "bt_gatt_types.h"
+
+__BEGIN_DECLS
+
+/** GATT value type used in response to remote read requests */
+typedef struct
+{
+       uint8_t           value[BTGATT_MAX_ATTR_LEN];
+       uint16_t          handle;
+       uint16_t          offset;
+       uint16_t          len;
+       uint8_t           auth_req;
+} btgatt_value_t;
+
+/** GATT remote read request response type */
+typedef union
+{
+       btgatt_value_t attr_value;
+       uint16_t            handle;
+} btgatt_response_t;
+
+typedef struct {
+       uint8_t  server_if;
+       bool     set_scan_rsp;
+       bool     include_name;
+       bool     include_txpower;
+       uint16_t  appearance;
+       char*    manufacturer_data;
+       uint16_t manufacturer_data_len;
+       char*    service_data;
+       uint16_t service_data_len;
+       char*    service_uuid;
+       uint16_t service_uuid_len;
+       char*    solicit_uuid;
+       uint16_t solicit_uuid_len;
+       uint16_t  min_interval;
+       uint16_t  max_interval;
+       uint8_t  adv_type;
+       uint8_t  chnl_map;
+       uint8_t  tx_power;
+       uint8_t  timeout_s;
+} btgatt_adv_param_setup_t;
+
+
+/** BT-GATT Server callback structure. */
+
+/** Callback invoked in response to register_server */
+typedef void (*register_server_callback)(int status, int server_if,
+               bt_uuid_t *app_uuid);
+
+/** Callback indicating that a remote device has connected or been disconnected */
+typedef void (*connection_callback)(int conn_id, int server_if, int connected,
+               bt_bdaddr_t *bda);
+
+/** Callback invoked in response to create_service */
+typedef void (*service_added_callback)(int status, int server_if,
+               btgatt_srvc_id_t *srvc_id, int srvc_handle);
+
+/** Callback indicating that an included service has been added to a service */
+typedef void (*included_service_added_callback)(int status, int server_if,
+               int srvc_handle, int incl_srvc_handle);
+
+/** Callback invoked when a characteristic has been added to a service */
+typedef void (*characteristic_added_callback)(int status, int server_if,
+               bt_uuid_t *uuid, int srvc_handle, int char_handle);
+
+/** Callback invoked when a descriptor has been added to a characteristic */
+typedef void (*descriptor_added_callback)(int status, int server_if,
+               bt_uuid_t *uuid, int srvc_handle, int descr_handle);
+
+/** Callback invoked in response to start_service */
+typedef void (*service_started_callback)(int status, int server_if,
+               int srvc_handle);
+
+/** Callback invoked in response to stop_service */
+typedef void (*service_stopped_callback)(int status, int server_if,
+               int srvc_handle);
+
+/** Callback triggered when a service has been deleted */
+typedef void (*service_deleted_callback)(int status, int server_if,
+               int srvc_handle);
+
+/**
+ * Callback invoked when indication confirmation
+ */
+typedef void (*indication_confirmation_callback) ( int conn_id, int trans_id, int attr_handle, bt_bdaddr_t *bda);
+
+/**
+ * Callback invoked when a remote device has requested to read a characteristic
+ * or descriptor. The application must respond by calling send_response
+ */
+typedef void (*request_read_callback)(int conn_id, int trans_id, bt_bdaddr_t *bda,
+               int attr_handle, int offset, bool is_long);
+
+/**
+ * Callback invoked when a remote device has requested to write to a
+ * characteristic or descriptor.
+ */
+typedef void (*request_write_callback)(int conn_id, int trans_id, bt_bdaddr_t *bda,
+               int attr_handle, int offset, int length,
+               bool need_rsp, bool is_prep, uint8_t* value);
+
+/** Callback invoked when a previously prepared write is to be executed */
+typedef void (*request_exec_write_callback)(int conn_id, int trans_id,
+               bt_bdaddr_t *bda, int exec_write);
+
+/**
+ * Callback triggered in response to send_response if the remote device
+ * sends a confirmation.
+ */
+typedef void (*response_confirmation_callback)(int status, int handle);
+
+/**
+ * Callback indicationg the status of a listen() operation
+ */
+typedef void (*listen_callback)(int status, int server_if);
+
+/** Callback invoked when multi-adv enable operation has completed */
+typedef void (*multi_adv_enable_callback)(int server_if, int status);
+
+/** Callback invoked when multi-adv param update operation has completed */
+typedef void (*multi_adv_update_callback)(int server_if, int status);
+
+/** Callback invoked when multi-adv instance data set operation has completed */
+typedef void (*multi_adv_data_callback)(int server_if, int status);
+
+/** Callback invoked when multi-adv disable operation has completed */
+typedef void (*multi_adv_disable_callback)(int server_if, int status);
+
+/** Callback invoked when the MTU for a given connection changes */
+typedef void (*mtu_changed_callback)(int conn_id, int mtu);
+
+typedef struct {
+       register_server_callback        register_server_cb;
+       connection_callback             connection_cb;
+       service_added_callback          service_added_cb;
+       included_service_added_callback included_service_added_cb;
+       characteristic_added_callback   characteristic_added_cb;
+       descriptor_added_callback       descriptor_added_cb;
+       service_started_callback        service_started_cb;
+       service_stopped_callback        service_stopped_cb;
+       service_deleted_callback        service_deleted_cb;
+       indication_confirmation_callback indication_confirmation_cb;
+       request_read_callback           request_read_cb;
+       request_write_callback          request_write_cb;
+       request_exec_write_callback     request_exec_write_cb;
+       response_confirmation_callback  response_confirmation_cb;
+       listen_callback                 listen_cb;
+       multi_adv_enable_callback       multi_adv_enable_cb;
+       multi_adv_update_callback       multi_adv_update_cb;
+       multi_adv_data_callback         multi_adv_data_cb;
+       multi_adv_disable_callback      multi_adv_disable_cb;
+       mtu_changed_callback            mtu_changed_cb;
+} btgatt_server_callbacks_t;
+
+/** Represents the standard BT-GATT server interface. */
+typedef struct {
+       /** Registers a GATT server application with the stack */
+       bt_status_t (*register_server)( bt_uuid_t *uuid );
+
+       /** Unregister a server application from the stack */
+       bt_status_t (*unregister_server)(int server_if );
+
+       /** Create a connection to a remote peripheral */
+       bt_status_t (*connect)(int server_if, const bt_bdaddr_t *bd_addr, bool is_direct );
+
+       /** Disconnect an established connection or cancel a pending one */
+       bt_status_t (*disconnect)(int server_if, const bt_bdaddr_t *bd_addr,
+                       int conn_id );
+
+       /** Create a new service */
+       bt_status_t (*add_service)( int server_if, btgatt_srvc_id_t *srvc_id, int num_handles);
+
+       /** Assign an included service to it's parent service */
+       bt_status_t (*add_included_service)( int server_if, int service_handle, int included_handle);
+
+       /** Add a characteristic to a service */
+       bt_status_t (*add_characteristic)( int server_if,
+                       int service_handle, bt_uuid_t *uuid,
+                       int properties, int permissions);
+
+       /** Add a descriptor to a given service */
+       bt_status_t (*add_descriptor)(int server_if, int service_handle,
+                       bt_uuid_t *uuid, int permissions);
+
+       /** Starts a local service */
+       bt_status_t (*start_service)(int server_if, int service_handle,
+                       int transport);
+
+       /** Stops a local service */
+       bt_status_t (*stop_service)(int server_if, int service_handle);
+
+       /** Delete a local service */
+       bt_status_t (*delete_service)(int server_if, int service_handle);
+
+       /** Send value indication to a remote device */
+       bt_status_t (*send_indication)(int server_if, int attribute_handle,
+                       int conn_id, int len, int confirm,
+                       char* p_value);
+
+       /** Send a response to a read/write operation */
+       bt_status_t (*send_response)(int conn_id, int trans_id,
+                       int status, btgatt_response_t *response);
+
+       /** Start or stop advertisements to listen for incoming connections */
+       bt_status_t (*listen)(int server_if, bool start);
+
+       /** Set the advertising data or scan response data */
+       bt_status_t (*set_adv_data)(int server_if, bool set_scan_rsp, bool include_name,
+                       bool include_txpower, int min_interval, int max_interval, int appearance,
+                       uint16_t manufacturer_len, char* manufacturer_data,
+                       uint16_t service_data_len, char* service_data,
+                       uint16_t service_uuid_len, char* service_uuid);
+
+       /* Setup the parameters as per spec, user manual specified values and enable multi ADV */
+       bt_status_t (*multi_adv_enable)(int server_if);
+
+       /* Update the parameters as per spec, user manual specified values and restart multi ADV */
+       bt_status_t (*multi_adv_update)(int server_if, int min_interval,int max_interval,int adv_type,
+                       int chnl_map, int tx_power, int timeout_s);
+
+       /* Setup the data for the specified instance */
+       bt_status_t (*multi_adv_set_inst_data)(btgatt_adv_param_setup_t adv_param_setup);
+
+       /* Disable the multi adv instance */
+       bt_status_t (*multi_adv_disable)(int server_if);
+
+       /* Get current att mtu size of active connection */
+       bt_status_t (*get_att_mtu)(int conn_id, int *mtu_size);
+} btgatt_server_interface_t;
+
+__END_DECLS
+
+#endif /* ANDROID_INCLUDE_BT_GATT_SERVER_H */
diff --git a/bt-oal/bluez_hal/hardware/bt_gatt_types.h b/bt-oal/bluez_hal/hardware/bt_gatt_types.h
new file mode 100644 (file)
index 0000000..2c1f2c4
--- /dev/null
@@ -0,0 +1,62 @@
+/*
+ * Copyright (C) 2013 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+
+#ifndef ANDROID_INCLUDE_BT_GATT_TYPES_H
+#define ANDROID_INCLUDE_BT_GATT_TYPES_H
+
+#include <stdint.h>
+#include <stdbool.h>
+
+__BEGIN_DECLS
+
+/**
+ * Buffer sizes for maximum attribute length and maximum read/write
+ * operation buffer size.
+ */
+#define BTGATT_MAX_ATTR_LEN 600
+
+/**
+ * GATT Service types
+ */
+#define BTGATT_SERVICE_TYPE_PRIMARY 0
+#define BTGATT_SERVICE_TYPE_SECONDARY 1
+
+/** GATT ID adding instance id tracking to the UUID */
+typedef struct
+{
+    bt_uuid_t           uuid;
+    uint8_t             inst_id;
+} btgatt_gatt_id_t;
+
+/** GATT Service ID also identifies the service type (primary/secondary) */
+typedef struct
+{
+    btgatt_gatt_id_t    id;
+    uint8_t             is_primary;
+} btgatt_srvc_id_t;
+
+/** Preferred physical Transport for GATT connection */
+typedef enum
+{
+    GATT_TRANSPORT_AUTO,
+    GATT_TRANSPORT_BREDR,
+    GATT_TRANSPORT_LE
+} btgatt_transport_t;
+
+__END_DECLS
+
+#endif /* ANDROID_INCLUDE_BT_GATT_TYPES_H */
index 526c433..81c44c0 100644 (file)
@@ -438,4 +438,42 @@ struct hal_ev_avrcp_tg_player_property {
        uint8_t value;
 } __attribute__((packed));
 
+/* LE-GATT */
+#define HAL_EV_SERVER_INSTANCE_INITIALIZED     0xA4
+struct hal_ev_server_instance_registered {
+        uint32_t status;
+        uint32_t server_instance;
+        uint8_t app_uuid[16];
+} __attribute__((packed));
+
+#define HAL_EV_MULTI_ADV_DATA_SET              0xA5
+struct hal_ev_multi_adv_data_set {
+        uint8_t status;
+        uint8_t server_instance;
+} __attribute__((packed));
+
+#define HAL_EV_MULTI_ADV_ENABLE                        0xA6
+struct hal_ev_multi_adv_enable {
+        uint32_t status;
+        uint32_t server_instance;
+} __attribute__((packed));
+
+#define HAL_EV_MULTI_ADV_DISABLE               0xA7
+struct hal_ev_multi_adv_disable {
+        uint32_t status;
+        uint32_t server_instance;
+} __attribute__((packed));
+
+#define HAL_EV_MULTI_ADV_UPDATE                        0xA8
+struct hal_ev_multi_adv_update {
+        uint32_t status;
+        uint32_t server_instance;
+} __attribute__((packed));
+
+#define HAL_EV_LEGACY_ADV_ENABLE               0xA9
+struct hal_ev_legacy_adv_status {
+        uint32_t status;
+        uint32_t server_instance;
+} __attribute__((packed));
+
 #endif //_BT_HAL_MSG_H_
index 35ae780..1408187 100644 (file)
 #define HAL_UUID_LEN           16
 #define MAX_ADDR_STR_LEN       18
 
-static const char BT_BASE_UUID[] = {
+#define BT_HAL_UUID_16     2
+#define BT_HAL_UUID_32     4
+#define BT_HAL_UUID_128    16
+
+static const char BT_BASE_UUID[BT_HAL_UUID_128] = {
        0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00,
        0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb
 };
 
+static const char BASE_UUID_CONVERTED[BT_HAL_UUID_128] = {
+    0xfb, 0x34, 0x9b, 0x5f, 0x80, 0x00, 0x00, 0x80,
+    0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00
+};
+
 /** BT Profile Service UUID's */
 #define BT_HAL_HFP_AUDIO_GATEWAY_UUID "0000111f-0000-1000-8000-00805f9b34fb"
 #define BT_HAL_HSP_AUDIO_GATEWAY_UUID "00001112-0000-1000-8000-00805f9b34fb"
diff --git a/bt-oal/bluez_hal/src/bt-hal-adapter-le.c b/bt-oal/bluez_hal/src/bt-hal-adapter-le.c
new file mode 100644 (file)
index 0000000..a69e050
--- /dev/null
@@ -0,0 +1,702 @@
+/*
+ * Copyright (c) 2011 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *             http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#include <glib.h>
+
+#include <hardware/bluetooth.h>
+#include <hardware/bt_gatt.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <string.h>
+#include <gio/gio.h>
+#include <glib.h>
+#include <dlog.h>
+#include <vconf.h>
+#include <vconf-keys.h>
+#include <vconf-internal-radio-keys.h>
+#include <stdbool.h>
+#include <stddef.h>
+#include <string.h>
+
+#include "bt-hal.h"
+#include "bt-hal-log.h"
+#include "bt-hal-msg.h"
+#include "bt-hal-utils.h"
+
+#include <bt-hal-adapter-dbus-handler.h>
+#include <bt-hal-dbus-common-utils.h>
+
+#include "bt-hal-gatt-server.h"
+
+typedef struct {
+        int adv_inst_max;
+        int rpa_offloading;
+        int max_filter;
+} bt_adapter_le_feature_info_t;
+
+typedef struct {
+       int initialized;
+       gboolean is_multi_adv; /* To be removed once we complete descope Legacy Adv */
+        int adv_handle;
+        gboolean is_advertising;
+        guint hold_timer_id;
+       bt_uuid_t app_uuid;
+} bt_adapter_le_adv_slot_t;
+
+static bt_adapter_le_feature_info_t le_feature_info = { 1, 0, 0 };
+static bt_adapter_le_adv_slot_t *le_adv_slot = NULL;
+
+typedef struct {
+       uint8_t event;
+        int server_if;
+        uint8_t status;
+        uint8_t data[31];
+} bt_hal_adv_event_data_t;
+
+/* Macros */
+#define BT_HAL_ADV_CONNECTABLE  0x00 /* ADV_IND */
+#define BT_HAL_ADV_CONNECTABLE_DIRECT_HIGH  0x01 /* ADV_DIRECT_IND, high duty cycle */
+#define BT_HAL_ADV_SCANNABLE 0x02 /* ADV_SCAN_IND */
+#define BT_HAL_ADV_NON_CONNECTABLE  0x03 /* ADV_NONCOND_IND */
+#define BT_HAL_ADV_CONNECTABLE_DIRECT_LOW  0x04 /* ADV_DIRECT_IND, low duty cycle */
+
+#define BT_HAL_ADV_INTERVAL_MIN 20 /* msec */
+#define BT_HAL_ADV_INTERVAL_MAX 10240
+#define BT_HAL_ADV_INTERVAL_SPLIT 0.625
+#define BT_HAL_DEFAULT_ADV_MIN_INTERVAL 500
+#define BT_HAL_DEFAULT_ADV_MAX_INTERVAL 500
+#define BT_HAL_ADV_FILTER_POLICY_DEFAULT    0x00
+#define BT_HAL_ADV_TYPE_DEFAULT     0x00
+#define BT_HAL_ADV_FILTER_POLICY_ALLOW_SCAN_CONN_WL_ONLY    0x03
+#define BT_HAL_ADV_MULTI_MAX   16
+
+/* Multi Advertisement callback event */
+#define BT_HAL_MULTI_ADV_ENB_EVT           1
+#define BT_HAL_MULTI_ADV_DISABLE_EVT       2
+#define BT_HAL_MULTI_ADV_PARAM_EVT         3
+#define BT_HAL_MULTI_ADV_DATA_EVT          4
+#define BT_HAL_MULTI_ADV_UPDATE_EVT        5
+#define BT_HAL_LEGACY_ADV_STATUS           6
+
+/* Forward declarations */
+static gboolean __bt_hal_is_factory_test_mode(void);
+static void __bt_hal_free_le_adv_slot(void);
+static gboolean __bt_hal_adv_event_cb(gpointer param);
+
+static void __bt_hal_free_le_adv_slot(void)
+{
+       int i;
+
+       if (le_adv_slot == NULL)
+               return;
+
+       for (i = 0; i < le_feature_info.adv_inst_max; i++) {
+               memset(&le_adv_slot[i], 0x00, sizeof(bt_adapter_le_adv_slot_t));
+       }
+       g_free(le_adv_slot);
+       le_adv_slot = NULL;
+}
+
+int _bt_hal_get_adv_slot_adv_handle(int slot_id)
+{
+       if (le_adv_slot == NULL)
+               return 0;
+
+       return le_adv_slot[slot_id].adv_handle;
+}
+
+void _bt_hal_set_advertising_status(int slot_id, gboolean mode)
+{
+
+       DBG("Advertising enabled [%s] slot [%d]",  mode? "TRUE": "FALSE", slot_id);
+       bt_hal_adv_event_data_t *event;
+
+       if (le_adv_slot == NULL)
+               return;
+
+       le_adv_slot[slot_id].is_advertising = mode;
+
+       event = g_malloc0(sizeof(bt_hal_adv_event_data_t));
+       event->event = mode? BT_HAL_MULTI_ADV_ENB_EVT: BT_HAL_MULTI_ADV_DISABLE_EVT;
+       event->server_if = slot_id;
+       event->status = BT_STATUS_SUCCESS;
+       /* To be removed later when we completely descope Legacy Adv concept */
+       DBG("Is multi ? [%d]", le_adv_slot[slot_id].is_multi_adv);
+       if (le_adv_slot[slot_id].is_multi_adv == FALSE)
+               event->event = BT_HAL_LEGACY_ADV_STATUS;
+
+       __bt_hal_adv_event_cb((gpointer)event);
+}
+
+gboolean _bt_hal_is_advertising(void)
+{
+       gboolean status = FALSE;
+       int i;
+
+       for (i = 0; i < le_feature_info.adv_inst_max; i++) {
+               if (le_adv_slot[i].is_advertising == TRUE)
+                       status = TRUE;
+       }
+
+       return status;
+}
+
+gboolean _bt_hal_update_le_feature_support(const char *item, const char *value)
+{
+       if (item == NULL || value == NULL)
+               return FALSE;
+
+       if (g_strcmp0(item, "adv_inst_max") == 0) {
+               int slot_num;
+
+               slot_num = atoi(value);
+               if (slot_num < 0 || slot_num > BT_HAL_ADV_MULTI_MAX) {
+                       ERR("ERR:Advertising MAX instance [%d]", slot_num);
+                       return FALSE;
+               }
+
+               if (slot_num != le_feature_info.adv_inst_max) {
+                       __bt_hal_free_le_adv_slot();
+                       le_feature_info.adv_inst_max = slot_num;
+                       INFO("Advertising instance max : %d", le_feature_info.adv_inst_max);
+                       le_adv_slot = g_malloc0(sizeof(bt_adapter_le_adv_slot_t) * le_feature_info.adv_inst_max);
+               }
+       } else if (g_strcmp0(item, "rpa_offloading") == 0) {
+               le_feature_info.rpa_offloading = atoi(value);
+               INFO("RPA offloading : %d", le_feature_info.rpa_offloading);
+       } else if (g_strcmp0(item, "max_filter") == 0) {
+               le_feature_info.max_filter = atoi(value);
+               INFO("BLE Scan max filter : %d", le_feature_info.max_filter);
+       } else {
+               DBG("No registered item");
+               return FALSE;
+       }
+
+       return TRUE;
+}
+
+void _bt_hal_free_server_slot(int slot_id)
+{
+       if (le_adv_slot == NULL)
+               return;
+       memset(&le_adv_slot[slot_id], 0x00, sizeof(bt_adapter_le_adv_slot_t));
+}
+
+int _bt_hal_get_available_adv_slot_id(bt_uuid_t *uuid)
+{
+       int i;
+
+       if (le_adv_slot == NULL) {
+               ERR("le_adv_slot is NULL");
+               return -1;
+       }
+
+       DBG("adv_inst_max : %d", le_feature_info.adv_inst_max);
+
+       for (i = 0; i < le_feature_info.adv_inst_max; i++) {
+               if (le_adv_slot[i].initialized == 0)
+                       continue;
+               if (memcmp(uuid->uu, le_adv_slot[i].app_uuid.uu, sizeof(bt_uuid_t)) == 0) {
+                       DBG("UUID [%s] matched, return slot [%d]", btuuid2str(uuid->uu), i);
+                       return i;
+               }
+       }
+
+       for (i = 0; i < le_feature_info.adv_inst_max; i++) {
+               if (le_adv_slot[i].initialized == 0) {
+                       DBG("Slot to be allocated [%d] UUID to be registered [%s]",
+                               i, btuuid2str(uuid->uu));
+                       le_adv_slot[i].initialized = 1;
+                       memcpy(&le_adv_slot[i].app_uuid.uu, &uuid->uu, sizeof(bt_uuid_t));
+                       return i;
+               }
+       }
+
+       return -1;
+}
+
+gboolean _bt_is_advertising(void)
+{
+       return FALSE;
+}
+
+int _bt_set_advertising(const char *sender, int adv_handle,
+                       gboolean enable, gboolean use_reserved_slot)
+{
+       DBG("+");
+       return BT_STATUS_UNSUPPORTED;
+}
+
+static int __bt_hal_uuid_type(uint8_t* p_uuid)
+{
+       int i = 0;
+       int match = 0;
+       int all_zero = 1;
+
+       for (i = 0; i != 16; ++i) {
+               if (i == 12 || i == 13)
+                       continue;
+
+               if (p_uuid[i] == BASE_UUID_CONVERTED[i])
+                       ++match;
+
+               if (p_uuid[i] != 0)
+                       all_zero = 0;
+       }
+       if (all_zero)
+               return 0;
+       if (match == 12)
+               return BT_HAL_UUID_32;
+       if (match == 14)
+               return BT_HAL_UUID_16;
+       return BT_HAL_UUID_128;
+}
+
+static void __bt_hal_parse_uuid(int len, char *src, uint8_t *dest, int *length, int is_solicit)
+{
+       DBG("+");
+       int prev_byte_len = 0;
+       /* dest[index] will contain the length followed by AD Type
+          Move length only when different byte_len is found Ex) 2->4, 2->16, 4->16 etc */
+       int index = 0;
+
+       while (len >= 16) {
+
+               /* Create Local buffer & copy source 16 bytes in sequence */
+               int byte_len;
+               bt_uuid_t uuid;
+               memset(&uuid, 0, sizeof(bt_uuid_t));
+               memcpy(&uuid.uu, src, 16);
+
+               /* Compute current UUID's byte length */
+               byte_len = __bt_hal_uuid_type(uuid.uu);
+
+               switch (byte_len) {
+               case 2: {
+                       if (prev_byte_len == byte_len) {
+                               memcpy(&(dest[dest[index] + 1]), &src[12], byte_len);
+                               *length += 2;
+                               dest[index] += 2;
+                       } else {
+                               if (dest[index] != 0)
+                                       index = dest[index] +1;
+                               dest[index] = byte_len + 1;
+                               if (is_solicit)
+                                       dest[index+1] = 0x14; /* AD Type */
+                               else
+                                       dest[index+1] = 0x02; /* AD Type */
+                               memcpy(&(dest[index + 2]), &src[12], byte_len);
+                               *length += 4;
+                       }
+
+                       /* Update current type */
+                       prev_byte_len = byte_len;
+                       break;
+               }
+               case 4: {
+                       if (prev_byte_len == byte_len) {
+                               memcpy(&(dest[dest[index] + 1]), &src[12], byte_len);;
+                               *length += 4;
+                               dest[index] += 4;
+                       } else {
+                               if (dest[index] != 0)
+                                       index = dest[index] +1;
+                               dest[index] = byte_len + 1;
+                               if (is_solicit)
+                                       dest[index+1] = 0x1F; /* AD Type */
+                               else
+                                       dest[index+1] = 0x04; /* AD Type */
+                               memcpy(&(dest[index + 2]), &src[12], byte_len);
+                               *length += 6;
+                       }
+                       /* Update current type */
+                       prev_byte_len = byte_len;
+                       break;
+               }
+               case 16: {
+                       if (dest[index] != 0)
+                               index = dest[index] +1;
+                       dest[index] = byte_len + 1;
+                       if (is_solicit)
+                               dest[index+1] = 0x15; /* AD Type */
+                       else
+                               dest[index+1] = 0x06; /* AD Type */
+                       memcpy(&(dest[index + 2]), &src[12], byte_len);
+                       /* Update current type */
+                        prev_byte_len = byte_len;
+                       *length += 18;
+                       break;
+               }
+               default: {
+                       ERR("Abnormal Byte len [%d]", byte_len);
+                       break;
+               }
+               }
+
+               /* Process Next 16 bytes of MW UUID */
+               src += 16;
+               len -= 16;
+       }
+       DBG("-");
+}
+
+static gboolean __bt_hal_is_factory_test_mode(void)
+{
+        int mode = 0;
+
+        if (vconf_get_bool(VCONFKEY_BT_DUT_MODE, &mode)) {
+                ERR("Get the DUT Mode fail");
+                return TRUE;
+        }
+
+        if (mode != FALSE) {
+                INFO("DUT Test Mode !!");
+                return TRUE;
+        }
+
+        return FALSE;
+}
+
+static gboolean __bt_hal_adv_event_cb(gpointer param)
+{
+       handle_stack_msg event_cb;
+       bt_hal_adv_event_data_t *event = (bt_hal_adv_event_data_t*)param;
+       DBG("+");
+
+       if (!event)
+               return FALSE;
+
+       event_cb = _bt_hal_get_gatt_event();
+       if (!event_cb) {
+               ERR("GATT event callback not registered!!!");
+               return FALSE;
+       }
+
+       switch(event->event) {
+       case BT_HAL_MULTI_ADV_ENB_EVT: {
+               struct hal_ev_multi_adv_enable ev;
+               memset(&ev, 0, sizeof(struct hal_ev_multi_adv_enable));
+               ev.status = event->status;
+               ev.server_instance = event->server_if;
+               event_cb(HAL_EV_MULTI_ADV_ENABLE, (void *)&ev, sizeof(ev));
+               INFO("BLE Advertising enabled slot [%d]", event->server_if);
+               break;
+       }
+       case BT_HAL_MULTI_ADV_DISABLE_EVT: {
+               struct hal_ev_multi_adv_disable ev;
+               memset(&ev, 0, sizeof(struct hal_ev_multi_adv_disable));
+               ev.status = event->status;
+               ev.server_instance = event->server_if;
+               event_cb(HAL_EV_MULTI_ADV_DISABLE, (void *)&ev, sizeof(ev));
+               INFO("BLE Advertising disabled slot [%d]", event->server_if);
+               break;
+       }
+       case BT_HAL_MULTI_ADV_PARAM_EVT: {
+               INFO("Unhandled event slot [%d]", event->server_if);
+               break;
+       }
+       case BT_HAL_MULTI_ADV_UPDATE_EVT: {
+               struct hal_ev_multi_adv_update ev;
+               memset(&ev, 0, sizeof(struct hal_ev_multi_adv_update));
+               ev.status = event->status;
+               ev.server_instance = event->server_if;
+               event_cb(HAL_EV_MULTI_ADV_UPDATE, (void *)&ev, sizeof(ev));
+               INFO("BLE Advertising Param update slot [%d]", event->server_if);
+               break;
+       }
+       case BT_HAL_MULTI_ADV_DATA_EVT: {
+               INFO("BLE Advertising data set slot [%d]", event->server_if);
+               struct hal_ev_multi_adv_data_set ev_data_set;
+               /* Copy data */
+               memset(&ev_data_set, 0, sizeof(struct hal_ev_multi_adv_data_set));
+               ev_data_set.status = event->status;
+               ev_data_set.server_instance = event->server_if;
+               event_cb(HAL_EV_MULTI_ADV_DATA_SET, (void *)&ev_data_set, sizeof(ev_data_set));
+               break;
+       }
+       case BT_HAL_LEGACY_ADV_STATUS: {
+               INFO("BLE Legacy Advertising [%d]", event->server_if);
+               struct hal_ev_legacy_adv_status ev;
+               /* Copy data */
+               memset(&ev, 0, sizeof(struct hal_ev_legacy_adv_status));
+               ev.status = event->status;
+               ev.server_instance = event->server_if;
+               event_cb(HAL_EV_LEGACY_ADV_ENABLE, (void *)&ev, sizeof(ev));
+               break;
+       }
+       default:
+               ERR("Unknown event");
+               break;
+       }
+
+       g_free(event);
+
+       DBG("-");
+       return FALSE;
+}
+
+int _bt_hal_enable_advertising(int server_if, bool enable, bool is_multi_adv)
+{
+       DBG("+");
+       GError *error = NULL;
+       GVariant *ret;
+       GDBusProxy *proxy;
+
+       proxy = _bt_get_adapter_proxy();
+       if (proxy == NULL)
+               return BT_STATUS_FAIL;
+
+       if (le_adv_slot[server_if].is_advertising == TRUE && enable == TRUE)
+               return BT_STATUS_BUSY;
+
+       if (le_adv_slot[server_if].initialized == TRUE &&
+                       le_adv_slot[server_if].is_advertising == FALSE &&
+                       enable == FALSE)
+               return BT_STATUS_DONE;
+
+       if (le_adv_slot[server_if].hold_timer_id > 0) {
+               g_source_remove(le_adv_slot[server_if].hold_timer_id);
+               le_adv_slot[server_if].hold_timer_id = 0;
+       }
+
+       ret = g_dbus_proxy_call_sync(proxy, "SetAdvertising",
+                       g_variant_new("(bi)", enable, server_if),
+                       G_DBUS_CALL_FLAGS_NONE,
+                       -1,
+                       NULL,
+                       &error);
+
+       if (error) {
+               ERR("SetAdvertising Fail: %s", error->message);
+               g_clear_error(&error);
+               return BT_STATUS_FAIL;
+       }
+
+       INFO("Enable advertising [%d] SLot Id [%d] Is Multi? [%d]", enable, server_if, is_multi_adv);
+       if (ret)
+               g_variant_unref(ret);
+
+       le_adv_slot[server_if].is_multi_adv = is_multi_adv;
+       return BT_STATUS_SUCCESS;
+}
+
+int _bt_hal_set_advertising_params(int server_if, int min_interval,
+               int max_interval,int adv_type,
+                int chnl_map, int tx_power, int timeout_s)
+{
+       DBG("+");
+       GDBusProxy *proxy;
+        GVariant *ret;
+        GError *error = NULL;
+        guint32 min = 0;
+        guint32 max = 0;
+       bt_hal_adv_event_data_t *event;
+
+
+       proxy = _bt_get_adapter_proxy();
+        if (proxy == NULL)
+               return BT_STATUS_FAIL;
+
+       if (min_interval > max_interval ||
+                        min_interval < BT_HAL_ADV_INTERVAL_MIN ||
+                        max_interval > BT_HAL_ADV_INTERVAL_MAX)
+               return BT_STATUS_PARM_INVALID;
+
+
+       if (adv_type  == BT_HAL_ADV_CONNECTABLE_DIRECT_HIGH ||
+                        adv_type == BT_HAL_ADV_CONNECTABLE_DIRECT_LOW ||
+                        adv_type == BT_HAL_ADV_NON_CONNECTABLE)
+                return BT_STATUS_UNSUPPORTED;
+
+
+       min = min_interval / BT_HAL_ADV_INTERVAL_SPLIT;
+        max = max_interval / BT_HAL_ADV_INTERVAL_SPLIT;
+
+       ret = g_dbus_proxy_call_sync(proxy, "SetAdvertisingParameters",
+                        g_variant_new("(uuuui)", min, max,
+                        BT_HAL_ADV_FILTER_POLICY_DEFAULT, adv_type,
+                        server_if), G_DBUS_CALL_FLAGS_NONE,
+                        -1, NULL, &error);
+       if (error) {
+                ERR("SetAdvertisingParameters Fail: %s", error->message);
+                g_clear_error(&error);
+               return BT_STATUS_FAIL;
+        }
+
+       INFO("Set advertising data");
+        if (ret)
+                g_variant_unref(ret);
+
+       /*
+         * As we need to provide async callback to user from HAL, simply schedule a
+         * callback method which will carry actual result
+         */
+       event = g_malloc0(sizeof(bt_hal_adv_event_data_t));
+       event->event  = BT_HAL_MULTI_ADV_DATA_EVT;
+       event->server_if = server_if;
+       event->status = BT_STATUS_SUCCESS;
+        g_idle_add(__bt_hal_adv_event_cb, (gpointer)event);
+
+       return BT_STATUS_SUCCESS;
+}
+
+/* Takes care of both Scan Response and Advertising data */
+int _bt_hal_set_advertising_data(btgatt_adv_param_setup_t adv_param_setup)
+{
+       DBG("+");
+       uint8_t adv_data[31];
+       int index = 0;
+       GDBusProxy *proxy;
+        GError *error = NULL;
+        GVariant *ret = NULL;
+        GVariant *temp = NULL;
+        GVariantBuilder *builder;
+       bt_hal_adv_event_data_t *event;
+       int length = 0;
+        int i;
+
+       /* Parse data according to Bluez Interface */
+       if (__bt_hal_is_factory_test_mode()) {
+                ERR("Unable to set advertising data in factory binary !!");
+                return BT_STATUS_UNSUPPORTED;
+        }
+
+       /* TODO: Check adapter and LE adapter status */
+       proxy = _bt_get_adapter_proxy();
+        if (proxy == NULL)
+               return BT_STATUS_FAIL;
+
+       memset(&adv_data, 0, 31);
+
+       /* Service UUID */
+       DBG("Service UUID length [%d]", adv_param_setup.service_uuid_len);
+       if (adv_param_setup.service_uuid_len > 0) {
+               __bt_hal_parse_uuid(adv_param_setup.service_uuid_len,
+                               adv_param_setup.service_uuid, &adv_data[index], &length, FALSE);
+               index = length;
+               DBG("After Service UUID:Index [%d]", index);
+       }
+
+       /* Solicit UUID */
+       DBG("Solicit UUID length [%d]", adv_param_setup.solicit_uuid_len);
+       if (adv_param_setup.solicit_uuid_len > 0) {
+               __bt_hal_parse_uuid(adv_param_setup.solicit_uuid_len,
+                               adv_param_setup.solicit_uuid, &adv_data[index], &length, TRUE);
+               index = length;
+               DBG("After Solicit UUID: Index [%d]", index);
+       }
+
+       /* Service Data  UUID*/
+       DBG("Service Data length [%d]", adv_param_setup.service_data_len);
+       if (adv_param_setup.service_data_len > 0) {
+               adv_data[index] = 1 + adv_param_setup.service_data_len;
+               adv_data[index+1] = 0x16; /* Fixed */
+               memcpy(&adv_data[index+2], adv_param_setup.service_data, adv_param_setup.service_data_len);
+               index += (2 + adv_param_setup.service_data_len);
+               length += (2 + adv_param_setup.service_data_len);
+               DBG("After Service data: Index [%d]", index);
+       }
+
+       /* Set Apperance */
+       if (adv_param_setup.appearance > 0) {
+               adv_data[index] = 0x03;
+               adv_data[index+1] = 0x19;
+               adv_data[index+2] = (uint8_t) (adv_param_setup.appearance & 0xFF);
+               adv_data[index+3] = (uint8_t) ((adv_param_setup.appearance  >> 8) & 0xFF);
+               index += 4;
+               length += 4;
+               DBG("After Apperance: Index [%d]", index);
+       }
+
+       /* TX Power */
+       if (adv_param_setup.include_txpower != 0) {
+               adv_data[index] = 0x01;
+               adv_data[index+1] = 0x0A;
+               index += 2;
+               length += 2;
+               DBG("After TX Power: Index [%d]", index);
+       }
+
+       /* Device Name */
+       if (adv_param_setup.include_name != 0) {
+               adv_data[index] = 0x01;
+               adv_data[index+1] = 0x09;
+               index += 2;
+               length += 2;
+               DBG("After Name: Index [%d]", index);
+       }
+
+       /* Manufacturer data */
+       if (adv_param_setup.manufacturer_data_len > 0) {
+               adv_data[index] = 1 + adv_param_setup.manufacturer_data_len;
+               adv_data[index+1] = 0xFF;
+               memcpy(&adv_data[index+2], adv_param_setup.manufacturer_data, adv_param_setup.manufacturer_data_len);
+               index += (2 + adv_param_setup.manufacturer_data_len);
+               length += (2 + adv_param_setup.manufacturer_data_len);
+               DBG("After Manuf Data: Index [%d]", index);
+       }
+
+       /* Create Builder */
+       builder = g_variant_builder_new(G_VARIANT_TYPE("ay"));
+        for (i = 0; i < length; i++)
+                g_variant_builder_add(builder, "y", adv_data[i]);
+
+        temp = g_variant_new("ay", builder);
+        g_variant_builder_unref(builder);
+
+        DBG("####Adv data length [%d] Index [%d]", length, index);
+        for (i = 0; i < length; i++)
+                DBG("##Data[%d] [0x%x]", i, adv_data[i]);
+
+       if (adv_param_setup.set_scan_rsp == 0) {
+               /* Set Advertising data to stack */
+               ret = g_dbus_proxy_call_sync(proxy, "SetAdvertisingData",
+                               g_variant_new("(@ayi)", temp, adv_param_setup.server_if),
+                               G_DBUS_CALL_FLAGS_NONE,
+                               -1, NULL, &error);
+       } else {
+               /* Set Scan response data to stack */
+               ret = g_dbus_proxy_call_sync(proxy, "SetScanRespData",
+                               g_variant_new("(@ayi)", temp, adv_param_setup.server_if),
+                               G_DBUS_CALL_FLAGS_NONE,
+                               -1, NULL, &error);
+       }
+
+        if (error) {
+                ERR("SetAdvertisingData Fail: %s", error->message);
+                g_clear_error(&error);
+                return BT_STATUS_FAIL;
+        }
+
+       INFO("Set advertising data");
+        if (ret)
+                g_variant_unref(ret);
+
+       /*
+         * As we need to provide async callback to user from HAL, simply schedule a
+         * callback method which will carry actual result
+         */
+       event = g_malloc0(sizeof(bt_hal_adv_event_data_t));
+       event->event  = BT_HAL_MULTI_ADV_DATA_EVT;
+       event->server_if = adv_param_setup.server_if;
+       event->status = BT_STATUS_SUCCESS;
+       memcpy(&event->data, adv_data, 31);
+        g_idle_add(__bt_hal_adv_event_cb, (gpointer)event);
+
+        return BT_STATUS_SUCCESS;
+}
diff --git a/bt-oal/bluez_hal/src/bt-hal-adapter-le.h b/bt-oal/bluez_hal/src/bt-hal-adapter-le.h
new file mode 100644 (file)
index 0000000..6430abc
--- /dev/null
@@ -0,0 +1,57 @@
+/*
+ * BLUETOOOTH HAL
+ *
+ * Copyright (c) 2015 - 2016 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Contact:  Anupam Roy <anupam.r@samsung.com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *              http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#ifndef _BT_HAL_ADAPTER_LE_H_
+#define _BT_HAL_ADAPTER_LE_H_
+
+#include <glib.h>
+#include <sys/types.h>
+
+#include <hardware/bt_gatt_server.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+gboolean _bt_hal_update_le_feature_support(const char *item, const char *value);
+
+int _bt_hal_get_available_adv_slot_id(bt_uuid_t *uuid);
+
+int _bt_hal_get_adv_slot_adv_handle(int slot_id);
+
+void _bt_hal_set_advertising_status(int slot_id, gboolean mode);
+
+gboolean _bt_hal_is_advertising(void);
+
+void _bt_hal_free_server_slot(int slot_id);
+
+int _bt_hal_set_advertising_data(btgatt_adv_param_setup_t adv_param_setup);
+
+int _bt_hal_set_advertising_params(int server_if, int min_interval,
+                int max_interval, int adv_type,
+               int chnl_map, int tx_power, int timeout_s);
+
+int _bt_hal_enable_advertising(int server_if, bool enable, bool is_multi_adv);
+
+#ifdef __cplusplus
+}
+#endif /* __cplusplus */
+#endif /*_BT_HAL_ADAPTER_LE_H_*/
index bd94537..f5980eb 100644 (file)
@@ -40,6 +40,7 @@
 #include <bt-hal-a2dp-sink.h>
 #include <bt-hal-avrcp-tg.h>
 #include <bt-hal-avrcp-ctrl.h>
+#include <bt-hal-gatt.h>
 
 #define enum_prop_to_hal(prop, hal_prop, type) do { \
        static type e; \
@@ -234,7 +235,7 @@ static const void *get_profile_interface(const char *profile_id)
                return bt_get_hf_interface();
 
        if (!strcmp(profile_id, BT_PROFILE_GATT_ID))
-               return NULL;
+               return bt_get_gatt_interface();
 
        if (!strcmp(profile_id, BT_PROFILE_HEALTH_ID))
                return bt_get_hl_interface();
index 347421a..14276c2 100644 (file)
@@ -64,6 +64,9 @@ extern "C" {
 #define BT_HAL_LOWER_ADDRESS_LENGTH 9
 #define BT_HAL_AGENT_NEW_LINE "\r\n"
 
+#define BT_HAL_HARDWARE_ERROR "HardwareError"
+#define BT_HAL_TX_TIMEOUT_ERROR "TxTimeoutError"
+
 #define BT_HAL_VERSION_LENGTH_MAX       30 /**< This specifies bluetooth device version length */
 #define BT_HAL_INTERFACE_NAME_LENGTH        16
 #define BT_HAL_DEVICE_NAME_LENGTH_MAX       248 /**< This specifies maximum device name length */
index 40ace13..9ffbb73 100644 (file)
@@ -38,6 +38,7 @@
 #include "bt-hal-event-receiver.h"
 #include "bt-hal-dbus-common-utils.h"
 #include "bt-hal-agent.h"
+#include "bt-hal-adapter-le.h"
 
 #define BASELEN_PROP_CHANGED (sizeof(struct hal_ev_adapter_props_changed) \
                + sizeof(struct hal_property))
@@ -57,7 +58,17 @@ static handle_stack_msg avrcp_ctrl_event_cb = NULL;
 static handle_stack_msg avrcp_tg_event_cb = NULL;
 static guint event_id;
 
+
+typedef struct {
+       gchar* sender_name;
+       gchar* object_path;
+      gchar* interface_name;
+       gchar* signal_name;
+       GVariant *parameters;
+} bt_hal_main_event_data_t;
+
 /* Forward declarations */
+static gboolean __bt_hal_event_manager(gpointer param);
 static int __bt_hal_register_service_event(GDBusConnection *g_conn, int event_type);
 static int __bt_hal_register_manager_subscribe_signal(GDBusConnection *conn, int subscribe);
 static int __bt_hal_register_device_subscribe_signal(GDBusConnection *conn, int subscribe);
@@ -370,6 +381,21 @@ static void __bt_hal_adapter_property_changed_event(GVariant *msg)
                        DBG("##Adapter ModAlias [%s]", modalias);
                } else if (!g_strcmp0(key, "SupportedLEFeatures")) {
                        DBG("##LE Supported features");
+                       char *name = NULL;
+                       char *val = NULL;
+                       GVariantIter *iter = NULL;
+                       g_variant_get(value, "as", &iter);
+
+                       if (iter == NULL)
+                               return;
+                       while (g_variant_iter_loop(iter, "s", &name)) {
+                               DBG("name = %s", name);
+                               g_variant_iter_loop(iter, "s", &val);
+                               DBG("Value = %s", val);
+                               if (FALSE == _bt_hal_update_le_feature_support(name, val))
+                                       INFO("Fail to update LE feature info");
+                       }
+                       g_variant_iter_free(iter);
                } else if (!g_strcmp0(key, "IpspInitStateChanged")) {
                        g_variant_get(value, "b" ,&ipsp_initialized);
                        DBG("##IPSP Initialized = %d", ipsp_initialized);
@@ -393,6 +419,41 @@ static void __bt_hal_adapter_property_changed_event(GVariant *msg)
        DBG("-");
 }
 
+void _bt_hal_handle_adapter_event(GVariant *msg, const char *member)
+{
+       DBG("+");
+
+       if (member == NULL)
+               return;
+
+       if (strcasecmp(member, "DeviceCreated") == 0) {
+               DBG("DeviceCreated: Unhandled");
+       } else if (strcasecmp(member, "InterfacesRemoved") == 0) {
+               DBG("InterfacesRemoved: Unhandled");
+       } else if (strcasecmp(member, "AdvertisingEnabled") == 0) {
+               DBG("AdvertisingEnabled");
+               DBG("Advertising Enabled");
+               int slot_id;
+               gboolean status = FALSE;
+               g_variant_get(msg, "(ib)", &slot_id, &status);
+               DBG("Advertising Enabled : slot_id [%d]  status [%d]", slot_id, status);
+               /* Send event to application */
+               _bt_hal_set_advertising_status(slot_id, status);
+       } else if (strcasecmp(member, "RssiEnabled") == 0) {
+               DBG("RssiEnabled: Unhandled");
+       } else if (strcasecmp(member, "RssiAlert") == 0) {
+               DBG("RssiAlert: Unhandled");
+       } else if (strcasecmp(member, "RawRssi") == 0) {
+               DBG("RawRssi: Unhandled");
+       } else if (strcasecmp(member, BT_HAL_HARDWARE_ERROR) == 0) {
+               DBG("BT Hardware Error: Unhandled");
+       } else if (strcasecmp(member, BT_HAL_TX_TIMEOUT_ERROR) == 0) {
+               DBG("BT TX Timeout Error: Unhandled");
+
+       }
+       DBG("-");
+}
+
 static gboolean __bt_hal_parse_device_properties(GVariant *item)
 {
        GVariantIter iter;
@@ -709,27 +770,19 @@ static gboolean __bt_hal_parse_interface(GVariant *msg)
        return FALSE;
 }
 
-static  void __bt_hal_manager_event_filter(GDBusConnection *connection,
-               const gchar *sender_name,
-               const gchar *object_path,
-               const gchar *interface_name,
-               const gchar *signal_name,
-               GVariant *parameters,
-               gpointer user_data)
+static gboolean __bt_hal_event_manager(gpointer data)
 {
        bt_hal_event_type_t bt_event = 0x00;
        GVariant *value;
        char *obj_path = NULL;
 
-       if (signal_name == NULL)
-               return;
-
-       if (strcasecmp(signal_name, "InterfacesAdded") == 0) {
+       bt_hal_main_event_data_t *param = (bt_hal_main_event_data_t*)data;
+       if (strcasecmp(param->signal_name, "InterfacesAdded") == 0) {
 
                /*TODO: Handle Interfaces Added Signal from stack */
                DBG("Manager Event: Signal Name: InterfacesAdded");
 
-               g_variant_get(parameters, "(&o@a{sa{sv}})", &obj_path, &value);
+               g_variant_get(param->parameters, "(&o@a{sa{sv}})", &obj_path, &value);
 
                if (strcasecmp(obj_path, BT_HAL_BLUEZ_HCI_PATH) == 0) {
                        /* TODO: Handle adapter added */
@@ -738,70 +791,99 @@ static  void __bt_hal_manager_event_filter(GDBusConnection *connection,
                        bt_event = __bt_hal_parse_event(value);
                        if (bt_event == BT_HAL_DEVICE_EVENT) {
                                DBG("Device path : %s ", obj_path);
-                               __bt_hal_handle_device_event(value, parameters);
+                               __bt_hal_handle_device_event(value, param->parameters);
                        } else if (bt_event == BT_HAL_AVRCP_CONTROL_EVENT) {
                                /*TODO: Handle AVRCP control events from BlueZ */
                        }
                }
                g_variant_unref(value);
 
-       } else if (strcasecmp(signal_name, "InterfacesRemoved") == 0) {
+       } else if (strcasecmp(param->signal_name, "InterfacesRemoved") == 0) {
                /*TODO: Handle Interfaces Removed Signal from stack */
                DBG("Manager Event: Signal Name: InterfacesRemoved");
-       } else if (strcasecmp(signal_name, "NameOwnerChanged") == 0) {
+       } else if (strcasecmp(param->signal_name, "NameOwnerChanged") == 0) {
                char *name = NULL;
                char *previous = NULL;
                char *current = NULL;
 
                /* TODO: Handle Name Owener changed Signal */
-               if (__bt_hal_get_owner_info(parameters, &name, &previous, &current)) {
+               if (__bt_hal_get_owner_info(param->parameters, &name, &previous, &current)) {
                        DBG("Fail to get the owner info");
-                       return;
+                       return FALSE;
                }
                if (current && *current != '\0') {
                        g_free(name);
                        g_free(previous);
                        g_free(current);
-                       return;
+                       return FALSE;
                }
                if (strcasecmp(name, BT_HAL_BLUEZ_NAME) == 0) {
                        DBG("Bluetoothd is terminated");
 
                        /* TODO: Handle Bluetoothd terminating scenario */
                }
-
                g_free(name);
                g_free(previous);
                g_free(current);
 
-       } else if (g_strcmp0(interface_name, BT_HAL_PROPERTIES_INTERFACE) == 0) {
-               __bt_hal_handle_property_changed_event(parameters, object_path);
-       } else if (g_strcmp0(interface_name, BT_HAL_ADAPTER_INTERFACE) == 0) {
-               /* TODO: Handle Adapter events from stack */
+       } else if (g_strcmp0(param->interface_name, BT_HAL_PROPERTIES_INTERFACE) == 0) {
+               __bt_hal_handle_property_changed_event(param->parameters, param->object_path);
+       } else if (g_strcmp0(param->interface_name, BT_HAL_ADAPTER_INTERFACE) == 0) {
                DBG("Manager Event: Interface Name: BT_HAL_ADAPTER_INTERFACE");
-       } else if (g_strcmp0(interface_name, BT_HAL_INPUT_INTERFACE) == 0) {
+               _bt_hal_handle_adapter_event(param->parameters, param->signal_name);
+       } else if (g_strcmp0(param->interface_name, BT_HAL_INPUT_INTERFACE) == 0) {
                DBG("Manager Event: Interface Name: BT_HAL_INPUT_INTERFACE");
-               __bt_hal_handle_input_event(parameters, object_path);
-       } else if (g_strcmp0(interface_name, BT_HAL_NETWORK_SERVER_INTERFACE) == 0) {
+               __bt_hal_handle_input_event(param->parameters, param->object_path);
+       } else if (g_strcmp0(param->interface_name, BT_HAL_NETWORK_SERVER_INTERFACE) == 0) {
                /* TODO: Handle Network Server events from stack */
                DBG("Manager Event: Interface Name: BT_HAL_NETWORK_SERVER_INTERFACE");
-       } else if (g_strcmp0(interface_name, BT_HAL_HEADSET_INTERFACE) == 0) {
+       } else if (g_strcmp0(param->interface_name, BT_HAL_HEADSET_INTERFACE) == 0) {
                DBG("Manager Event: Interface Name: BT_HAL_HEADSET_INTERFACE");
-                __bt_hal_handle_headset_events(parameters, signal_name, object_path);
-       } else if (g_strcmp0(interface_name, BT_HAL_SINK_INTERFACE) == 0) {
+               __bt_hal_handle_headset_events(param->parameters, param->signal_name, param->object_path);
+       } else if (g_strcmp0(param->interface_name, BT_HAL_SINK_INTERFACE) == 0) {
                /* TODO: Handle Sink interface events from stack */
                DBG("Manager Event: Interface Name:BT_HAL_SINK_INTERFACE");
-       } else if (g_strcmp0(interface_name, BT_HAL_AGENT_INTERFACE) == 0) {
+       } else if (g_strcmp0(param->interface_name, BT_HAL_AGENT_INTERFACE) == 0) {
                /* TODO: Handle Agent events from stack */
                DBG("Manager Event: Interface Name:BT_HAL_AGENT_INTERFACE");
-       } else if (g_strcmp0(interface_name, BT_HAL_DEVICE_INTERFACE) == 0) {
+       } else if (g_strcmp0(param->interface_name, BT_HAL_DEVICE_INTERFACE) == 0) {
                DBG("Manager Event: Interface Name:BT_HAL_DEVICE_INTERFACE");
-               __bt_hal_handle_device_specific_events(parameters, signal_name, object_path);
-       } else if (g_strcmp0(interface_name, BT_HAL_PLAYER_CONTROL_INTERFACE) == 0) {
-               DBG("Manager Event: Interface Name: BT_HAL_PLAYER_CONTROL_INTERFACE");
-               __bt_hal_handle_avrcp_ctrl_events(parameters, signal_name, object_path);
-       }
+               __bt_hal_handle_device_specific_events(param->parameters, param->signal_name, param->object_path);
+       } else if (g_strcmp0(param->interface_name, BT_HAL_PLAYER_CONTROL_INTERFACE) == 0) {
+                DBG("Manager Event: Interface Name: BT_HAL_PLAYER_CONTROL_INTERFACE");
+                __bt_hal_handle_avrcp_ctrl_events(param->parameters, param->signal_name, param->object_path);
+        }
+
+       /* Free data */
+       g_free(param->sender_name);
+       g_free(param->object_path);
+       g_free(param->interface_name);
+       g_free(param->signal_name);
+       g_variant_unref(param->parameters);
+
+       return FALSE;
+}
 
+static  void __bt_hal_manager_event_filter(GDBusConnection *connection,
+                const gchar *sender_name,
+                const gchar *object_path,
+                const gchar *interface_name,
+                const gchar *signal_name,
+                GVariant *parameters,
+                gpointer user_data)
+{
+       if (signal_name == NULL)
+               return;
+
+       bt_hal_main_event_data_t *param = g_new0(bt_hal_main_event_data_t, 1);
+       param->sender_name = g_strdup(sender_name);
+       param->object_path = g_strdup(object_path);
+       param->interface_name = g_strdup(interface_name);
+       param->signal_name = g_strdup(signal_name);
+       param->parameters = g_variant_ref(parameters);
+
+       DBG("Switch Context to Main thread for event");
+       g_idle_add(__bt_hal_event_manager, (gpointer)param);
        return;
 }
 
@@ -1990,4 +2072,4 @@ void _bt_hal_register_avrcp_tg_event_handler_cb(handle_stack_msg cb)
 void _bt_hal_unregister_avrcp_tg_event_handler_cb()
 {
        avrcp_tg_event_cb = NULL;
-}
\ No newline at end of file
+}
diff --git a/bt-oal/bluez_hal/src/bt-hal-gatt-client.c b/bt-oal/bluez_hal/src/bt-hal-gatt-client.c
new file mode 100644 (file)
index 0000000..c625c39
--- /dev/null
@@ -0,0 +1,63 @@
+/*
+ * BLUETOOOTH HAL
+ *
+ * Copyright (c) 2015 - 2016 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Contact:  Anupam Roy <anupam.r@samsung.com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *              http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#include <hardware/bluetooth.h>
+#include <hardware/bt_gatt.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <string.h>
+
+/*TODO*/
+const btgatt_client_interface_t btgatt_client_interface = {
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+       NULL,
+};
diff --git a/bt-oal/bluez_hal/src/bt-hal-gatt-server.c b/bt-oal/bluez_hal/src/bt-hal-gatt-server.c
new file mode 100644 (file)
index 0000000..fa5cfb4
--- /dev/null
@@ -0,0 +1,287 @@
+/*
+ * BLUETOOOTH HAL
+ *
+ * Copyright (c) 2015 - 2016 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Contact:  Anupam Roy <anupam.r@samsung.com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *              http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#include <hardware/bluetooth.h>
+#include <hardware/bt_gatt.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <string.h>
+#include <gio/gio.h>
+#include <glib.h>
+#include <dlog.h>
+#include <vconf.h>
+#include <stdbool.h>
+#include <stddef.h>
+#include <string.h>
+
+#include "bt-hal.h"
+#include "bt-hal-log.h"
+#include "bt-hal-msg.h"
+#include "bt-hal-utils.h"
+
+#include "bt-hal-adapter-le.h"
+#include "bt-hal-event-receiver.h"
+
+/************************************************************************************
+ **  Static variables
+ ************************************************************************************/
+extern const btgatt_callbacks_t *bt_gatt_callbacks;
+
+static handle_stack_msg event_cb = NULL;
+
+typedef struct {
+       uint32_t instance_data;
+       bt_uuid_t uuid;
+} hal_register_server_data;
+
+#define CHECK_BTGATT_INIT() if (bt_gatt_callbacks == NULL)\
+{\
+       ERR("%s: BTGATT not initialized", __FUNCTION__);\
+       return BT_STATUS_NOT_READY;\
+} else {\
+       DBG("%s", __FUNCTION__);\
+}
+
+/* To send stack event to hal-av handler */
+void _bt_hal_register_gatt_server_handler_cb(handle_stack_msg cb)
+{
+        event_cb = cb;
+}
+
+handle_stack_msg _bt_hal_get_gatt_event(void)
+{
+       return event_cb;
+}
+
+static gboolean __bt_hal_register_slot_id_cb(gpointer user_data)
+{
+       struct hal_ev_server_instance_registered ev;
+       hal_register_server_data *data = (hal_register_server_data*) user_data;
+
+       /* Prepare to send AV connecting event */
+       memset(&ev, 0, sizeof(ev));
+       ev.status = BT_STATUS_SUCCESS;
+       ev.server_instance = data->instance_data;
+       memcpy(ev.app_uuid, data->uuid.uu, sizeof(ev.app_uuid));
+
+       if (!event_cb)
+               ERR("GATT Register Server Instance Callback not registered");
+       else {
+               DBG("Server Instance is registered!! server if [%d]", data->instance_data);
+               event_cb(HAL_EV_SERVER_INSTANCE_INITIALIZED, (void *)&ev, sizeof(ev));
+
+       }
+
+       g_free(data);
+       return FALSE;
+}
+
+static bt_status_t gatt_server_register_app(bt_uuid_t *uuid)
+{
+       CHECK_BTGATT_INIT();
+       int status = BT_STATUS_FAIL;
+       int server_if;
+       DBG("Register server instance request");
+       hal_register_server_data *user_data = g_malloc0(sizeof(hal_register_server_data));
+
+       /* Check if slot available */
+       server_if = _bt_hal_get_available_adv_slot_id(uuid);
+
+       if (server_if == -1) {
+               ERR("Allocation of server instance failed");
+               g_free(user_data);
+               return status;
+       } else {
+               user_data->instance_data = server_if;
+               DBG("Allocated new Advertising slot with Stack [%d]", user_data->instance_data);
+       }
+
+       /*
+         * As we need to provide async callback to user from HAL, simply schedule a
+         * callback method which will carry actual result
+         */
+       memcpy(user_data->uuid.uu, uuid->uu, sizeof(bt_uuid_t));
+        g_idle_add(__bt_hal_register_slot_id_cb, (gpointer)user_data);
+
+       /* If available, then return success, else return error */
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_unregister_app(int server_if)
+{
+       CHECK_BTGATT_INIT();
+       DBG("Un-Register server instance request [%d]", server_if);
+       _bt_hal_free_server_slot(server_if);
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_open(int server_if, const bt_bdaddr_t *bd_addr, bool is_direct)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_close(int server_if, const bt_bdaddr_t *bd_addr, int conn_id)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_add_service(int server_if, btgatt_srvc_id_t *srvc_id,
+               int num_handles)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_add_included_service(int server_if, int service_handle,
+               int included_handle)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_add_characteristic(int server_if, int service_handle,
+               bt_uuid_t *uuid, int properties,
+               int permissions)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_add_descriptor(int server_if, int service_handle, bt_uuid_t *uuid,
+               int permissions)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_start_service(int server_if, int service_handle, int transport)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_stop_service(int server_if, int service_handle)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_delete_service(int server_if, int service_handle)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_send_indication(int server_if, int attribute_handle, int conn_id,
+               int len, int confirm, char* p_value)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_send_response(int conn_id, int trans_id,
+               int status, btgatt_response_t *response)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_listen(int server_if, bool start)
+{
+       CHECK_BTGATT_INIT();
+       /* Send Data to LE Module */
+       return _bt_hal_enable_advertising(server_if, start, FALSE);
+}
+
+static bt_status_t gatt_server_set_adv_data(int server_if, bool set_scan_rsp, bool include_name,
+               bool include_txpower, int min_interval, int max_interval, int appearance,
+               uint16_t manufacturer_len, char* manufacturer_data,
+               uint16_t service_data_len, char* service_data,
+               uint16_t service_uuid_len, char* service_uuid)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_multi_adv_enable(int server_if)
+{
+       CHECK_BTGATT_INIT();
+       /* Send Data to LE Module */
+       return _bt_hal_enable_advertising(server_if, TRUE, TRUE);
+       return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t gatt_server_multi_adv_update(int server_if, int min_interval,int max_interval,int adv_type,
+               int chnl_map, int tx_power, int timeout_s)
+{
+       CHECK_BTGATT_INIT();
+       DBG("+");
+       /* Send Advertising parameters to LE Module */
+       return _bt_hal_set_advertising_params(server_if, min_interval, max_interval, adv_type,
+                chnl_map, tx_power, timeout_s);
+}
+
+static bt_status_t gatt_server_multi_adv_set_inst_data(btgatt_adv_param_setup_t adv_param_setup)
+{
+       CHECK_BTGATT_INIT();
+       DBG("+");
+       /* Send Data to LE Module */
+       return _bt_hal_set_advertising_data(adv_param_setup);
+}
+
+static bt_status_t gatt_server_multi_adv_disable(int server_if)
+{
+       CHECK_BTGATT_INIT();
+       /* Send Data to LE Module */
+       return _bt_hal_enable_advertising(server_if, FALSE, TRUE);
+}
+
+static bt_status_t gatt_server_get_mtu_size(int conn_id, int *mtu_size)
+{
+       CHECK_BTGATT_INIT();
+       return BT_STATUS_SUCCESS;
+}
+
+const btgatt_server_interface_t btgatt_server_interface = {
+       gatt_server_register_app,
+       gatt_server_unregister_app,
+       gatt_server_open,
+       gatt_server_close,
+       gatt_server_add_service,
+       gatt_server_add_included_service,
+       gatt_server_add_characteristic,
+       gatt_server_add_descriptor,
+       gatt_server_start_service,
+       gatt_server_stop_service,
+       gatt_server_delete_service,
+       gatt_server_send_indication,
+       gatt_server_send_response,
+       gatt_server_listen,
+       gatt_server_set_adv_data,
+       gatt_server_multi_adv_enable,
+       gatt_server_multi_adv_update,
+       gatt_server_multi_adv_set_inst_data,
+       gatt_server_multi_adv_disable,
+       gatt_server_get_mtu_size
+};
diff --git a/bt-oal/bluez_hal/src/bt-hal-gatt-server.h b/bt-oal/bluez_hal/src/bt-hal-gatt-server.h
new file mode 100644 (file)
index 0000000..03a27d0
--- /dev/null
@@ -0,0 +1,45 @@
+/*
+ * BLUETOOOTH HAL
+ *
+ * Copyright (c) 2015 - 2016 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Contact:  Anupam Roy <anupam.r@samsung.com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *              http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#ifndef _BT_HAL_GATT_SERVER_H_
+#define _BT_HAL_GATT_SERVER_H_
+
+#include <glib.h>
+#include <sys/types.h>
+
+#include "bt-hal.h"
+#include "bt-hal-log.h"
+#include "bt-hal-msg.h"
+
+#include "bt-hal-event-receiver.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+void _bt_hal_register_gatt_server_handler_cb(handle_stack_msg cb);
+
+handle_stack_msg _bt_hal_get_gatt_event(void);
+
+#ifdef __cplusplus
+}
+#endif /* __cplusplus */
+#endif /*_BT_HAL_GATT_SERVER_H_*/
diff --git a/bt-oal/bluez_hal/src/bt-hal-gatt.c b/bt-oal/bluez_hal/src/bt-hal-gatt.c
new file mode 100644 (file)
index 0000000..440d374
--- /dev/null
@@ -0,0 +1,199 @@
+/*
+ * BLUETOOOTH HAL
+ *
+ * Copyright (c) 2015 - 2016 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Contact:  Anupam Roy <anupam.r@samsung.com>
+ *
+ *  Licensed under the Apache License, Version 2.0 (the "License");
+ *  you may not use this file except in compliance with the License.
+ *  You may obtain a copy of the License at:
+ *
+ *  http://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing, software
+ *  distributed under the License is distributed on an "AS IS" BASIS,
+ *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ *  See the License for the specific language governing permissions and
+ *  limitations under the License.
+ *
+ */
+
+
+/*******************************************************************************
+ *
+ *  Filename:      btif_gatt.c
+ *
+ *  Description:   GATT Profile Bluetooth Interface
+ *
+ *******************************************************************************/
+
+#include <hardware/bluetooth.h>
+#include <hardware/bt_gatt.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <errno.h>
+#include <string.h>
+#include <dlog.h>
+
+#include "bt-hal.h"
+#include "bt-hal-log.h"
+#include "bt-hal-msg.h"
+#include "bt-hal-utils.h"
+
+#include "bt-hal-gatt-server.h"
+
+const btgatt_callbacks_t *bt_gatt_callbacks = NULL;
+
+extern btgatt_client_interface_t btgatt_client_interface;
+extern btgatt_server_interface_t btgatt_server_interface;
+
+static bool interface_ready(void)
+{
+        return bt_gatt_callbacks != NULL;
+}
+
+static void __bt_hal_handle_server_instance_initialized(void *buf, uint16_t len)
+{
+       struct hal_ev_server_instance_registered *ev = buf;
+
+       if (bt_gatt_callbacks->server->register_server_cb)
+               bt_gatt_callbacks->server->register_server_cb(ev->status, ev->server_instance, (bt_uuid_t*)&ev->app_uuid);
+}
+
+static void __bt_hal_handle_multi_adv_data_set(void *buf, uint16_t len)
+{
+       struct hal_ev_multi_adv_data_set *ev = buf;
+
+       if (bt_gatt_callbacks->server->multi_adv_data_cb)
+               bt_gatt_callbacks->server->multi_adv_data_cb(ev->server_instance, ev->status);
+}
+
+static void __bt_hal_handle_multi_adv_data_update(void *buf, uint16_t len)
+{
+       struct hal_ev_multi_adv_update *ev = buf;
+
+       if (bt_gatt_callbacks->server->multi_adv_update_cb)
+               bt_gatt_callbacks->server->multi_adv_update_cb(ev->server_instance, ev->status);
+}
+
+static void __bt_hal_handle_multi_adv_enable(void *buf, uint16_t len)
+{
+       struct hal_ev_multi_adv_enable *ev = buf;
+
+       if (bt_gatt_callbacks->server->multi_adv_enable_cb)
+               bt_gatt_callbacks->server->multi_adv_enable_cb(ev->server_instance, ev->status);
+}
+
+static void __bt_hal_handle_multi_adv_disable(void *buf, uint16_t len)
+{
+       struct hal_ev_multi_adv_disable *ev = buf;
+
+       if (bt_gatt_callbacks->server->multi_adv_disable_cb)
+               bt_gatt_callbacks->server->multi_adv_disable_cb(ev->server_instance, ev->status);
+}
+
+/* Same callback for both Enable and DIsable */
+static void __bt_hal_handle_legacy_adv_status(void *buf, uint16_t len)
+{
+       struct hal_ev_legacy_adv_status *ev = buf;
+
+       if (bt_gatt_callbacks->server->listen_cb)
+               bt_gatt_callbacks->server->listen_cb(ev->status, ev->server_instance);
+}
+
+static void __bt_hal_gatt_events(int message, void *buf, uint16_t len)
+{
+       DBG("+");
+       /* Check if GATT interface is Ready */
+       if (!interface_ready())
+               return;
+
+       switch(message) {
+       case HAL_EV_SERVER_INSTANCE_INITIALIZED: {
+               __bt_hal_handle_server_instance_initialized(buf, len);
+               break;
+       }
+       case HAL_EV_MULTI_ADV_ENABLE: {
+               __bt_hal_handle_multi_adv_enable(buf, len);
+               break;
+       }
+       case HAL_EV_MULTI_ADV_DISABLE: {
+               __bt_hal_handle_multi_adv_disable(buf, len);
+               break;
+       }
+       case HAL_EV_MULTI_ADV_DATA_SET: {
+               __bt_hal_handle_multi_adv_data_set(buf, len);
+               break;
+       }
+       case HAL_EV_MULTI_ADV_UPDATE: {
+               __bt_hal_handle_multi_adv_data_update(buf, len);
+               break;
+       }
+       case HAL_EV_LEGACY_ADV_ENABLE: {
+               __bt_hal_handle_legacy_adv_status(buf, len);
+               break;
+       }
+       default:
+               DBG("Event Currently not handled!!");
+               break;
+       }
+       DBG("-");
+}
+
+/*******************************************************************************
+**
+** Function         gatt_init
+**
+** Description      Initializes the GATT interface
+**
+** Returns          bt_status_t
+**
+*******************************************************************************/
+static bt_status_t gatt_init(const btgatt_callbacks_t* callbacks )
+{
+       bt_gatt_callbacks = callbacks;
+       DBG("Register A2DP Src events callback function");
+       _bt_hal_register_gatt_server_handler_cb(__bt_hal_gatt_events);
+
+       return BT_STATUS_SUCCESS;
+}
+
+/*******************************************************************************
+**
+** Function         gatt_cleanup
+**
+** Description      Closes the GATT interface
+**
+** Returns          void
+**
+*******************************************************************************/
+static void  gatt_cleanup(void)
+{
+    if (bt_gatt_callbacks)
+        bt_gatt_callbacks = NULL;
+}
+
+static const btgatt_interface_t btgatt_interface = {
+    sizeof(btgatt_interface),
+
+    gatt_init,
+    gatt_cleanup,
+
+    &btgatt_client_interface,
+    &btgatt_server_interface,
+};
+
+/*******************************************************************************
+**
+** Function         bt_get_gatt_interface
+**
+** Description      Get the gatt callback interface
+**
+** Returns          btgatt_interface_t
+**
+*******************************************************************************/
+const btgatt_interface_t *bt_get_gatt_interface()
+{
+    return &btgatt_interface;
+}
diff --git a/bt-oal/bluez_hal/src/bt-hal-gatt.h b/bt-oal/bluez_hal/src/bt-hal-gatt.h
new file mode 100644 (file)
index 0000000..aab1df2
--- /dev/null
@@ -0,0 +1,34 @@
+/*
+ * BLUETOOTH HAL
+ *
+ * Copyright (c) 2015 - 2016 Samsung Electronics Co., Ltd. All rights reserved.
+ *
+ * Contact:  Anupam Roy <anupam.r@samsung.com>
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *             http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ */
+
+#ifndef __BT_HAL_GATT_H__
+#define __BT_HAL_GATT_H__
+
+#include <stdint.h>
+#include <glib.h>
+#include <unistd.h>
+#include <dlog.h>
+#include <stdio.h>
+#include <hardware/bt_gatt.h>
+
+btgatt_interface_t *bt_get_gatt_interface(void);
+
+#endif //__BT_HAL_GATT_H__