#include <stdio.h>
#include <errno.h>
#include <unistd.h>
#include <alloca.h>
#include <stdlib.h>
#include <stdbool.h>
#include <poll.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <syslog.h>
#include <pthread.h>

#include <bluetooth/bluetooth.h>
#include <bluetooth/hci.h>
#include <bluetooth/hci_lib.h>
#include <bluetooth/l2cap.h>

#include "src/shared/mainloop.h"
#include "src/shared/mgmt.h"
#include "src/shared/util.h"
#include "lib/mgmt.h"
#include "lib/sdp.h"

#include "dy_utils/dy_mqtt.h"
#include "dy_utils/dy_list.h"
#include "dy_utils/dy_common.h"
#include "dy_utils/dy_pp.h"
#include "dy_utils/dy_db.h"
#include "dy_utils/dy_ipc.h"

typedef enum
{
    HCI_STATE_NONE = 0,
    HCI_STATE_OPEN = 2,
    HCI_STATE_SCANNING = 3,
    HCI_STATE_FILTERING = 4,
} hci_state;

#define EIR_FLAGS 0X01
#define EIR_NAME_SHORT 0x08
#define EIR_NAME_COMPLETE 0x09
#define EIR_MANUFACTURE_SPECIFIC 0xFF

typedef struct ble_dev_s
{
    int dev_id;
    int scan_fd;
    struct mgmt *mgmt;
    struct hci_dev_info *di;
    hci_state state;
} ble_dev_t;

typedef struct _ble_var_s
{
    mqtt_session_t *session; //内部broker的MQTT session，用于进程间通信
    int ble_cnt;
    ble_dev_t *dev;
} ble_var_t;

extern void start_hci_scan(ble_dev_t *current_hci_state);
extern int l2cap_le_att_connect(int dev_id, char *dst, uint8_t dst_type,
								int sec, uint16_t mtu);
extern int l2cap_le_att_listen_and_accept(int dev_id, int sec,
								   uint8_t src_type, uint16_t mtu);

extern unsigned int send_cmd(struct mgmt *mgmt, uint16_t op, uint16_t id,
                             uint16_t len, const void *param,
                             void (*cb)(uint16_t id, uint16_t op,
                                        uint8_t status, uint16_t len,
                                        const void *param));
extern void setting_rsp(uint16_t op, uint16_t id, uint8_t status, uint16_t len,
                        const void *param);
extern int l2cap_le_att_advertise(int dev_id, uint32_t flags, uuid_t UUIDs[], int uuid_cnt,
                           uint8_t *adv_data, uint8_t adv_len,
                           uint8_t *scan_rsp, uint8_t scan_rsp_len,
                           uint16_t timeout, uint16_t duration, int instance);
