Android Bluetooth Address

蓝牙地址的NV项是447项,蓝牙地址一般从NV读取,所以连接上QXDM,修改NV447项就可以修改蓝牙的MAC地址。Android修改NV 447项之后,发现修改不起作用。原来Android的蓝牙地址可以从/persist/.bt_nv.bin读,也可以从NV447读,关键就看一个 vendor/.../bt/hci_qcomm_init/Android.mk的设置 如果要从nv447读, 则
BT_QSOC_GET_ITEMS_FROM_NV = 1
BT_QSOC_GET_ITEMS_FROM_PERSIST = 1
BT_QSOC_GET_ITEMS_FROM_PERSIST_THEN_NV = 1

将BT_QSOC_GET_ITEMS_FROM_PERSIST_THEN_NV注释掉,如果从.bt_nv.bin读就取消注释。
读取蓝牙地址的代码在同一目录下的 bthci_qcomm_linux.cpp,修改了Android.mk文件后,要保证 bthci_qcomm_linux.cpp能被重新编译下修改才能起作用 。获得蓝牙地址代码如下:

boolean bt_hci_qcomm_pfal_get_bdaddress ( uint8 *pCmdBuffer )
 {
  boolean bd_set = FALSE;

  if (verbose > 2)
  {
    fprintf (stderr, "get_bdaddr: before: 0x%02x.0x%02x.0x%02x.0x%02x.0x%02x.0x%02x\n",
             BD_addr[0], BD_addr[1], BD_addr[2], BD_addr[3], BD_addr[4], BD_addr[5]);
  }

  if (BD_addr_string != NULL) /* BD_ADDR was passed in as -b arg */
  {
    /* convert ASCII HEX representation to 48 bits */
    /* BD_addr is little-endian, but string is as printed */
    BD_addr[5] = strtol (&BD_addr_string[ 0], 0, 16);
    BD_addr[4] = strtol (&BD_addr_string[ 3], 0, 16);
    BD_addr[3] = strtol (&BD_addr_string[ 6], 0, 16);
    BD_addr[2] = strtol (&BD_addr_string[ 9], 0, 16);
    BD_addr[1] = strtol (&BD_addr_string[12], 0, 16);
    BD_addr[0] = strtol (&BD_addr_string[15], 0, 16);
    bd_set = TRUE;

  }
  else /* get BD_ADDR from NV or set it to RANDOM */
  {
#if defined(BT_QSOC_GET_ITEMS_FROM_PERSIST_THEN_NV)
    static nv_persist_item_type my_nv_persist_item; /* nv_bd_addr_type */
    static nv_persist_stat_enum_type persistcmd_result;

    persistcmd_result = (nv_persist_stat_enum_type)bt_nv_cmd(NV_PERSIST_READ_F,  NV_PERSIST_BD_ADDR_I, &my_nv_persist_item);

    if (NV_PERSIST_SUCCESS  != persistcmd_result)
    {
        if (verbose > 0)
        {
            fprintf (stderr, "bt_nv_cmd failed to get BD_ADDR from NV, code %d\n", persistcmd_result);
        }

        static nv_item_type my_nv_item; /* nv_bd_addr_type */
        static nv_stat_enum_type cmd_result;       
        if (nv_available)
        {
          cmd_result = nv_cmd_remote(NV_READ_F,  NV_BD_ADDR_I, &my_nv_item);
        }
        else
        {
          cmd_result = NV_FAIL_S;
        }

        if (NV_DONE_S != cmd_result)
        {
          if (verbose > 0)
          {
             fprintf (stderr, "nv_cmd_remote failed to get BD_ADDR from NV, code %d\n", cmd_result);
          }
        }
        else
        {
          /* copy bytes */
          BD_addr[5] = my_nv_item.bd_addr.bd_addr[5];
          BD_addr[4] = my_nv_item.bd_addr.bd_addr[4];
          BD_addr[3] = my_nv_item.bd_addr.bd_addr[3];
          BD_addr[2] = my_nv_item.bd_addr.bd_addr[2];
          BD_addr[1] = my_nv_item.bd_addr.bd_addr[1];
          BD_addr[0] = my_nv_item.bd_addr.bd_addr[0];
          bd_set = TRUE;
        }

    }
    else
    {
        /* copy bytes */
        BD_addr[5] = my_nv_persist_item.bd_addr[5];
        BD_addr[4] = my_nv_persist_item.bd_addr[4];
        BD_addr[3] = my_nv_persist_item.bd_addr[3];
        BD_addr[2] = my_nv_persist_item.bd_addr[2];
        BD_addr[1] = my_nv_persist_item.bd_addr[1];
        BD_addr[0] = my_nv_persist_item.bd_addr[0];
        bd_set = TRUE;
    }

#else
#if defined(BT_QSOC_GET_ITEMS_FROM_NV)

    static nv_item_type my_nv_persist_item; /* nv_bd_addr_type */
    static nv_stat_enum_type persistcmd_result;

    if (nv_available)
    {
      persistcmd_result = nv_cmd_remote(NV_READ_F,  NV_BD_ADDR_I, &my_nv_persist_item);
    }
    else
    {
      persistcmd_result = NV_FAIL_S;
    }

    if (NV_DONE_S != persistcmd_result)
    {
      if (verbose > 0)
      {
         fprintf (stderr, "nv_cmd_remote failed to get BD_ADDR from NV, code %d\n", persistcmd_result);
      }
    }
    else
    {
      /* copy bytes */
      BD_addr[5] = my_nv_persist_item.bd_addr.bd_addr[5];
      BD_addr[4] = my_nv_persist_item.bd_addr.bd_addr[4];
      BD_addr[3] = my_nv_persist_item.bd_addr.bd_addr[3];
      BD_addr[2] = my_nv_persist_item.bd_addr.bd_addr[2];
      BD_addr[1] = my_nv_persist_item.bd_addr.bd_addr[1];
      BD_addr[0] = my_nv_persist_item.bd_addr.bd_addr[0];
      bd_set = TRUE;
    }
#elif defined(BT_QSOC_GET_ITEMS_FROM_PERSIST)

    static nv_persist_item_type my_nv_persist_item; /* nv_bd_addr_type */
    static nv_persist_stat_enum_type persistcmd_result;

    persistcmd_result = (nv_persist_stat_enum_type)bt_nv_cmd(NV_PERSIST_READ_F,  NV_PERSIST_BD_ADDR_I, &my_nv_persist_item);

    if (NV_PERSIST_SUCCESS  != persistcmd_result)
    {
        if (verbose > 0)
        {
            fprintf (stderr, "bt_nv_cmd failed to get BD_ADDR from NV, code %d\n", cmd_result);
        }
    }
    else
    {
        /* copy bytes */
        BD_addr[5] = my_nv_persist_item.bd_addr[5];
        BD_addr[4] = my_nv_persist_item.bd_addr[4];
        BD_addr[3] = my_nv_persist_item.bd_addr[3];
        BD_addr[2] = my_nv_persist_item.bd_addr[2];
        BD_addr[1] = my_nv_persist_item.bd_addr[1];
        BD_addr[0] = my_nv_persist_item.bd_addr[0];
        bd_set = TRUE;
    }

#else /* not BT_QSOC_GET_ITEMS_FROM_NV - running on PC not MSM */

    /* then set the non-manufacturer part to random */
    BTHCI_QCOMM_TRACE ("bt_hci_qcomm_pfal_get_bdaddress: BD_ADDR not avialable from NV.\n");

#endif /* not on PC */
#endif
  }

  if (!bd_set)
  {
   int seed;
   struct timespec sTime;

   if (-1 == clock_gettime (CLOCK_REALTIME, &sTime))
   {
	perror ("clock_gettime\n" );
	return (FALSE);
   }

   seed = sTime.tv_nsec;
   srand ((unsigned int) seed);

   BD_addr[0] = (rand() & 0x0FF00000) >> 20;
   BD_addr[1] = (rand() & 0x0FF00000) >> 20;
   BD_addr[2] = (rand() & 0x0FF00000) >> 20;
  }

  memcpy( pCmdBuffer, BD_addr, sizeof(BD_addr) );

  if (verbose > 2)
  {
    fprintf (stderr, "get_bdaddr: after: %02x.%02x.%02x.%02x.%02x.%02x\n",
             BD_addr[0], BD_addr[1], BD_addr[2], BD_addr[3], BD_addr[4], BD_addr[5]);
  }
  return TRUE; /* for now -- need error checking? */
}


BT_QSOC_GET_ITEMS_FROM_PERSIST_THEN_NV不仅控制蓝牙地址,在bt_hci_qcomm_pfal_is_refclock_19P2MHz和bt_hci_qcomm_pfal_is_clocksharing_enabled这两个函数中也有用到。不过不用担心这个注释会影响蓝牙的时钟读取,时钟信息都是写死在芯片里,不用从NV或者配置文件获得。

 

你可能感兴趣的:(Bluetooth)