Unicode conversion failed: Conversion from character set ‘UTF-16BE‘ to ‘UTF-8‘ is not supported

        在调试蓝牙传输文件时,当电脑连接成功后,发送文件卡住不动,且obexd提示:disconnected: Unicode conversion failed: Conversion from character set 'UTF-16BE' to 'UTF-8' is not supported

 解决方案

         使用buildroot编译bluez时,需要把gconv libs选上,这样额外编译出gconv编码相关库:

         编译完成后,gconv库的位置在output/target/usr/lib/gconv/下面,需要手动拷贝UTF-16.so和gconv-modules到目标板的/usr/lib/gconv/目录,这样obexd运行时才会支持UTF-16编码。

        另外,网上其他文章说打开了gconv配置重新编译bluez会生效,但事实证明这个gconv库与bluez没有关联,如果程序缺库会在运行时报错,但obexd是怎么用到gconv库的呢?为何缺库时只提示不支持编码转换呢?

[wangyb@wangyb-VirtualBox:buildroot-2017.02.3]$ ls output/target/usr/lib/gconv/
ANSI_X3.110.so  CWI.so              GBBIG5.so            IBM1122.so  IBM1162.so   IBM424.so     IBM871.so         INIS.so             ISO8859-5.so          MAC-UK.so
ARMSCII-8.so    DEC-MCS.so          GBGBK.so             IBM1123.so  IBM1163.so   IBM437.so     IBM874.so         ISIRI-3342.so       ISO8859-6.so          MIK.so
ASMO_449.so     EBCDIC-AT-DE-A.so   GBK.so               IBM1124.so  IBM1164.so   IBM4517.so    IBM875.so         ISO_10367-BOX.so    ISO8859-7.so          NATS-DANO.so
BIG5HKSCS.so    EBCDIC-AT-DE.so     gconv-modules        IBM1129.so  IBM1166.so   IBM4899.so    IBM880.so         ISO_11548-1.so      ISO8859-8.so          NATS-SEFI.so
BIG5.so         EBCDIC-CA-FR.so     GEORGIAN-ACADEMY.so  IBM1130.so  IBM1167.so   IBM4909.so    IBM891.so         ISO-2022-CN-EXT.so  ISO8859-9E.so         PT154.so
BRF.so          EBCDIC-DK-NO-A.so   GEORGIAN-PS.so       IBM1132.so  IBM12712.so  IBM4971.so    IBM901.so         ISO-2022-CN.so      ISO8859-9.so          RK1048.so
CP10007.so      EBCDIC-DK-NO.so     GOST_19768-74.so     IBM1133.so  IBM1364.so   IBM500.so     IBM902.so         ISO-2022-JP-3.so    ISO-IR-197.so         SAMI-WS2.so
CP1125.so       EBCDIC-ES-A.so      GREEK7-OLD.so        IBM1137.so  IBM1371.so   IBM5347.so    IBM9030.so        ISO-2022-JP.so      ISO-IR-209.so         SHIFT_JISX0213.so
CP1250.so       EBCDIC-ES.so        GREEK7.so            IBM1140.so  IBM1388.so   IBM803.so     IBM903.so         ISO-2022-KR.so      JOHAB.so              SJIS.so
CP1251.so       EBCDIC-ES-S.so      GREEK-CCITT.so       IBM1141.so  IBM1390.so   IBM850.so     IBM904.so         ISO_2033.so         KOI8-R.so             T.61.so
CP1252.so       EBCDIC-FI-SE-A.so   HP-GREEK8.so         IBM1142.so  IBM1399.so   IBM851.so     IBM905.so         ISO_5427-EXT.so     KOI8-RU.so            TCVN5712-1.so
CP1253.so       EBCDIC-FI-SE.so     HP-ROMAN8.so         IBM1143.so  IBM16804.so  IBM852.so     IBM9066.so        ISO_5427.so         KOI-8.so              TIS-620.so
CP1254.so       EBCDIC-FR.so        HP-ROMAN9.so         IBM1144.so  IBM256.so    IBM855.so     IBM918.so         ISO_5428.so         KOI8-T.so             TSCII.so
CP1255.so       EBCDIC-IS-FRISS.so  HP-THAI8.so          IBM1145.so  IBM273.so    IBM856.so     IBM921.so         ISO646.so           KOI8-U.so             UHC.so
CP1256.so       EBCDIC-IT.so        HP-TURKISH8.so       IBM1146.so  IBM274.so    IBM857.so     IBM922.so         ISO_6937-2.so       LATIN-GREEK-1.so      UNICODE.so
CP1257.so       EBCDIC-PT.so        IBM037.so            IBM1147.so  IBM275.so    IBM860.so     IBM930.so         ISO_6937.so         LATIN-GREEK.so        UTF-16.so
CP1258.so       EBCDIC-UK.so        IBM038.so            IBM1148.so  IBM277.so    IBM861.so     IBM932.so         ISO8859-10.so       libCNS.so             UTF-32.so
CP737.so        EBCDIC-US.so        IBM1004.so           IBM1149.so  IBM278.so    IBM862.so     IBM933.so         ISO8859-11.so       libGB.so              UTF-7.so
CP770.so        ECMA-CYRILLIC.so    IBM1008_420.so       IBM1153.so  IBM280.so    IBM863.so     IBM935.so         ISO8859-13.so       libISOIR165.so        VISCII.so
CP771.so        EUC-CN.so           IBM1008.so           IBM1154.so  IBM281.so    IBM864.so     IBM937.so         ISO8859-14.so       libJIS.so
CP772.so        EUC-JISX0213.so     IBM1025.so           IBM1155.so  IBM284.so    IBM865.so     IBM939.so         ISO8859-15.so       libJISX0213.so
CP773.so        EUC-JP-MS.so        IBM1026.so           IBM1156.so  IBM285.so    IBM866NAV.so  IBM943.so         ISO8859-16.so       libKSC.so
CP774.so        EUC-JP.so           IBM1046.so           IBM1157.so  IBM290.so    IBM866.so     IBM9448.so        ISO8859-1.so        MAC-CENTRALEUROPE.so
CP775.so        EUC-KR.so           IBM1047.so           IBM1158.so  IBM297.so    IBM868.so     IEC_P27-1.so      ISO8859-2.so        MACINTOSH.so
CP932.so        EUC-TW.so           IBM1097.so           IBM1160.so  IBM420.so    IBM869.so     INIS-8.so         ISO8859-3.so        MAC-IS.so
CSN_369103.so   GB18030.so          IBM1112.so           IBM1161.so  IBM423.so    IBM870.so     INIS-CYRILLIC.so  ISO8859-4.so        MAC-SAMI.so

        obexd的RPATH不为空,RPATH全称run-time search path,说明程序运行时会搜索相关的库文件。而RPATH指定的路径下就有gconv库。

[wangyb@wangyb-VirtualBox:bluez5_utils-5.43]$ readelf -d obexd/src/obexd

Dynamic section at offset 0x4b304 contains 28 entries:
  标记        类型                         名称/值
 0x00000001 (NEEDED)                     共享库:[libdbus-1.so.3]
 0x00000001 (NEEDED)                     共享库:[libglib-2.0.so.0]
 0x00000001 (NEEDED)                     共享库:[libdl.so.2]
 0x00000001 (NEEDED)                     共享库:[libc.so.6]
 0x0000000f (RPATH)                      Library rpath: [/buildroot-2017.02.3/output/host/usr/arm-buildroot-linux-gnueabi/sysroot/usr/lib]

         应该是在编译时通过am_lib_libbluetooth_la_rpath = -rpath $(libdir)设置的RPATH。

调试过程【仅记录可忽略】

1、使用-d打开obexd和bluetoothd的debug信息:没看到有用的异常信息。

bluetoothd[19288]: src/adapter.c:connected_callback() hci0 device C0:B5:D7:A3:98:90 connected eir_len 22
bluetoothd[19288]: src/device.c:device_create() dst C0:B5:D7:A3:98:90
bluetoothd[19288]: src/device.c:device_new() address C0:B5:D7:A3:98:90
bluetoothd[19288]: src/device.c:device_new() Creating device /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
bluetoothd[19288]: src/device.c:device_set_class() /org/bluez/hci0/dev_C0_B5_D7_A3_98_90 0x0A0104
bluetoothd[19288]: src/device.c:btd_device_device_set_name() /org/bluez/hci0/dev_C0_B5_D7_A3_98_90 DESKTOP-9TIPO5R
[NEW] Device C0:B5:D7:A3:98:90 DESKTOP-9TIPO5R
[bluetooth]# bluetoothd[19288]: src/adapter.c:user_confirm_request_callback() hci0 C0:B5:D7:A3:98:90 confirm_hint 0
bluetoothd[19288]: src/device.c:new_auth() Requesting agent authentication for C0:B5:D7:A3:98:90
bluetoothd[19288]: src/agent.c:agent_ref() 0xe5180: ref=2
bluetoothd[19288]: src/agent.c:agent_request_confirmation() Calling Agent.RequestConfirmation: name=:1.2, path=/org/bluez/agent, passkey=362723
Request confirmation
[agent] Confirm passkey 362723 (yes/no): yes
[DESKTOP-9TIPO5R]# bluetoothd[19288]: src/agent.c:agent_ref() 0xe5180: ref=3
bluetoothd[19288]: src/adapter.c:btd_adapter_confirm_reply() hci0 addr C0:B5:D7:A3:98:90 success 1
bluetoothd[19288]: src/agent.c:agent_unref() 0xe5180: ref=2
bluetoothd[19288]: src/agent.c:agent_unref() 0xe5180: ref=1
bluetoothd[19288]: src/adapter.c:new_link_key_callback() hci0 new key for C0:B5:D7:A3:98:90 type 5 pin_len 0 store_hint 1
bluetoothd[19288]: src/device.c:device_set_bonded() 
bluetoothd[19288]: src/device.c:btd_device_set_temporary() temporary 0
bluetoothd[19288]: src/device.c:device_bonding_complete() bonding (nil) status 0x00
bluetoothd[19288]: src/device.c:device_bonding_complete() setting timer for reverse service discovery
bluetoothd[19288]: src/adapter.c:resume_discovery() 
bluetoothd[19288]: src/device.c:device_probe_profiles() Probing profiles for device C0:B5:D7:A3:98:90
bluetoothd[19288]: src/profile.c:ext_device_probe() Object Push probed with UUID 00001105-0000-1000-8000-00805f9b34fb
bluetoothd[19288]: src/service.c:change_state() 0xdd4e8: device C0:B5:D7:A3:98:90 profile Object Push state changed: unavailable -> disconnected (0)
bluetoothd[19288]: src/service.c:btd_service_ref() 0xdd4e8: ref=2
bluetoothd[19288]: src/profile.c:ext_connect() Object Push connected to C0:B5:D7:A3:98:90
bluetoothd[19288]: src/service.c:change_state() 0xdd4e8: device C0:B5:D7:A3:98:90 profile Object Push state changed: disconnected -> connecting (0)
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 00001105-0000-1000-8000-00805f9b34fb
[DESKTOP-9TIPO5R]# bluetoothd[19288]: src/service.c:change_state() 0xdd4e8: device C0:B5:D7:A3:98:90 profile Object Push state changed: connecting -> connected (0)
bluetoothd[19288]: src/device.c:device_profile_connected() Object Push Success (0)
bluetoothd[19288]: profiles/audio/avctp.c:avctp_confirm_cb() AVCTP: incoming connect from C0:B5:D7:A3:98:90
bluetoothd[19288]: src/device.c:device_probe_profiles() Probing profiles for device C0:B5:D7:A3:98:90
bluetoothd[19288]: profiles/audio/avrcp.c:avrcp_controller_probe() path /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
bluetoothd[19288]: profiles/audio/control.c:control_init() Registered interface org.bluez.MediaControl1 on path /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
bluetoothd[19288]: src/service.c:btd_service_ref() 0xd92d8: ref=2
bluetoothd[19288]: src/service.c:change_state() 0xd92d8: device C0:B5:D7:A3:98:90 profile avrcp-controller state changed: unavailable -> disconnected (0)
bluetoothd[19288]: src/device.c:device_probe_profiles() Probing profiles for device C0:B5:D7:A3:98:90
bluetoothd[19288]: profiles/audio/avrcp.c:avrcp_target_probe() path /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
bluetoothd[19288]: src/service.c:btd_service_ref() 0xdda28: ref=2
bluetoothd[19288]: src/service.c:change_state() 0xdda28: device C0:B5:D7:A3:98:90 profile audio-avrcp-target state changed: unavailable -> disconnected (0)
bluetoothd[19288]: profiles/audio/avctp.c:avctp_set_state() AVCTP Connecting
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 00001105-0000-1000-8000-00805f9b34fb
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 0000110c-0000-1000-8000-00805f9b34fb
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 0000110e-0000-1000-8000-00805f9b34fb
[DESKTOP-9TIPO5R]# obexd[20498]: CONNECT(0x0), (null)(0xffffffff)
obexd[20498]: CONNECT(0x0), (null)(0x0)
obexd[20498]: disconnected: Unicode conversion failed: Conversion from character set 'UTF-16BE' to 'UTF-8' is not supported【不支持】
[CHG] Device C0:B5:D7:A3:98:90 Modalias: bluetooth:v0006p0001d0A00
[DESKTOP-9TIPO5R]# bluetoothd[19288]: src/device.c:device_probe_profiles() Probing profiles for device C0:B5:D7:A3:98:90
bluetoothd[19288]: profiles/network/connection.c:connection_register() /org/bluez/hci0/dev_C0_B5_D7_A3_98_90 id 4373
bluetoothd[19288]: profiles/network/connection.c:create_peer() Registered interface org.bluez.Network1 on path /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
bluetoothd[19288]: src/service.c:btd_service_ref() 0xfd420: ref=2
bluetoothd[19288]: profiles/network/connection.c:connection_register() id 4373 registered
bluetoothd[19288]: src/service.c:change_state() 0xfd420: device C0:B5:D7:A3:98:90 profile network-panu state changed: unavailable -> disconnected (0)
bluetoothd[19288]: profiles/audio/a2dp.c:a2dp_source_probe() path /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
bluetoothd[19288]: profiles/audio/source.c:source_init() /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
bluetoothd[19288]: src/service.c:btd_service_ref() 0xfd468: ref=2
bluetoothd[19288]: src/service.c:change_state() 0xfd468: device C0:B5:D7:A3:98:90 profile a2dp-source state changed: unavailable -> disconnected (0)
bluetoothd[19288]: profiles/audio/a2dp.c:a2dp_sink_probe() path /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
bluetoothd[19288]: profiles/audio/sink.c:sink_init() /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
bluetoothd[19288]: src/service.c:btd_service_ref() 0xfcb00: ref=2
bluetoothd[19288]: src/service.c:change_state() 0xfcb00: device C0:B5:D7:A3:98:90 profile a2dp-sink state changed: unavailable -> disconnected (0)
bluetoothd[19288]: src/device.c:device_svc_resolved() /org/bluez/hci0/dev_C0_B5_D7_A3_98_90 err 0
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 00001000-0000-1000-8000-00805f9b34fb
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 00001105-0000-1000-8000-00805f9b34fb

[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 0000110a-0000-1000-8000-00805f9b34fb
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 0000110b-0000-1000-8000-00805f9b34fb
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 0000110c-0000-1000-8000-00805f9b34fb
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 0000110e-0000-1000-8000-00805f9b34fb
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 00001115-0000-1000-8000-00805f9b34fb
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 0000111f-0000-1000-8000-00805f9b34fb
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: 00001200-0000-1000-8000-00805f9b34fb
[CHG] Device C0:B5:D7:A3:98:90 UUIDs: c7f94713-891e-496a-a0e7-983a0946126e
[DESKTOP-9TIPO5R]# bluetoothd[19288]: src/agent.c:agent_authorize_service() authorize service request was sent for /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
[CHG] Device C0:B5:D7:A3:98:90 ServicesResolved: yes
[CHG] Device C0:B5:D7:A3:98:90 Paired: yes
Authorize service
Authorize service 0000110e-0000-1000-8000-00805f9b34fb (yes/no): yes 
[DESKTOP-9TIPO5R]# bluetoothd[19288]: src/agent.c:agent_ref() 0xe5180: ref=3
bluetoothd[19288]: src/agent.c:agent_unref() 0xe5180: ref=2
bluetoothd[19288]: src/agent.c:agent_unref() 0xe5180: ref=1
bluetoothd[19288]: profiles/audio/avctp.c:avctp_connect_cb() AVCTP: connected to C0:B5:D7:A3:98:90
--------usb state=0
[  764.996253]{1} input: C0:B5:D7:A3:98:90 as /devices/virtual/input/input1
--------usb state=0
bluetoothd[19288]: profiles/audio/avctp.c:init_uinput() AVRCP: uinput initialized for C0:B5:D7:A3:98:90
bluetoothd[19288]: profiles/audio/avrcp.c:controller_init() 0xfe868 version 0x0106
bluetoothd[19288]: src/service.c:change_state() 0xdda28: device C0:B5:D7:A3:98:90 profile audio-avrcp-target state changed: disconnected -> connected (0)
bluetoothd[19288]: profiles/audio/player.c:media_player_controller_create() /org/bluez/hci0/dev_C0_B5_D7_A3_98_90/player0
bluetoothd[19288]: profiles/audio/avrcp.c:target_init() 0xe6aa0 version 0x0106
bluetoothd[19288]: src/service.c:change_state() 0xd92d8: device C0:B5:D7:A3:98:90 profile avrcp-controller state changed: disconnected -> connected (0)
bluetoothd[19288]: profiles/audio/avctp.c:avctp_set_state() AVCTP Connected
bluetoothd[19288]: profiles/audio/avctp.c:avctp_confirm_cb() AVCTP: incoming connect from C0:B5:D7:A3:98:90
bluetoothd[19288]: profiles/audio/avctp.c:avctp_set_state() AVCTP Browsing Connecting
bluetoothd[19288]: profiles/audio/avrcp.c:handle_vendordep_pdu() AVRCP PDU 0x10, company 0x001958 len 0x0001
bluetoothd[19288]: profiles/audio/avrcp.c:avrcp_handle_get_capabilities() id=3
bluetoothd[19288]: profiles/audio/avctp.c:avctp_connect_browsing_cb() AVCTP Browsing: connected to C0:B5:D7:A3:98:90
bluetoothd[19288]: profiles/audio/avctp.c:avctp_set_state() AVCTP Browsing Connected
bluetoothd[19288]: profiles/audio/avrcp.c:handle_vendordep_pdu() AVRCP PDU 0x31, company 0x001958 len 0x0005
bluetoothd[19288]: profiles/audio/player.c:media_player_set_type() Audio
bluetoothd[19288]: profiles/audio/player.c:media_player_set_subtype() None
bluetoothd[19288]: profiles/audio/player.c:media_player_set_status() stopped
bluetoothd[19288]: profiles/audio/player.c:media_player_set_name() Windows
bluetoothd[19288]: profiles/audio/player.c:media_player_set_setting() Repeat: off
bluetoothd[19288]: profiles/audio/player.c:media_player_set_setting() Shuffle: off
bluetoothd[19288]: profiles/audio/player.c:media_player_set_playlist_item() 18446744073709551615
bluetoothd[19288]: profiles/audio/player.c:media_player_set_metadata() Title: 
bluetoothd[19288]: profiles/audio/player.c:media_player_set_duration() 4294967295
bluetoothd[19288]: profiles/audio/player.c:media_player_set_position() 4294967295
bluetoothd[19288]: profiles/audio/player.c:media_player_set_status() stopped
bluetoothd[19288]: profiles/audio/player.c:media_player_set_duration() 4294967295
bluetoothd[19288]: profiles/audio/player.c:media_player_set_position() 4294967295
bluetoothd[19288]: profiles/audio/player.c:media_player_set_status() stopped

2、打开obexd代码函数调试开关

        obexd代码使用加载环境变量的方式设置debug信息:

GObex *g_obex_new(GIOChannel *io, GObexTransportType transport_type,
					gssize io_rx_mtu, gssize io_tx_mtu)
{
	GObex *obex;
	GIOCondition cond;

	if (gobex_debug == 0) {
		const char *env = g_getenv("GOBEX_DEBUG");

		if (env) {
			gobex_debug = g_parse_debug_string(env, keys, 7);
			g_setenv("G_MESSAGES_DEBUG", "gobex", FALSE);
		} else
			gobex_debug = G_OBEX_DEBUG_NONE;
	}

        debug等级描述:

static GDebugKey keys[] = {
	{ "error",	G_OBEX_DEBUG_ERROR },
	{ "command",	G_OBEX_DEBUG_COMMAND },
	{ "transfer",	G_OBEX_DEBUG_TRANSFER },
	{ "header",	G_OBEX_DEBUG_HEADER },
	{ "packet",	G_OBEX_DEBUG_PACKET },
	{ "data",	G_OBEX_DEBUG_DATA },
	{ "apparam",	G_OBEX_DEBUG_APPARAM },
};

        设置debug等级为header

export GOBEX_DEBUG=header

         出现'UTF-16BE' to 'UTF-8' is not supported打印的函数:使用g_convert转码提示不支持。

GObexHeader *g_obex_header_decode(const void *data, gsize len,
				GObexDataPolicy data_policy, gsize *parsed,
				GError **err)
{
	GObexHeader *header;
	const guint8 *ptr = data;
	guint16 hdr_len;
	gsize str_len;
	GError *conv_err = NULL;

	if (len < 2) {
		if (!err)
			return NULL;
		g_set_error(err, G_OBEX_ERROR, G_OBEX_ERROR_PARSE_ERROR,
						"Too short header in packet");
		g_obex_debug(G_OBEX_DEBUG_ERROR, "%s", (*err)->message);
		return NULL;
	}

	header = g_new0(GObexHeader, 1);

	ptr = get_bytes(&header->id, ptr, sizeof(header->id));

	g_obex_debug(G_OBEX_DEBUG_HEADER, "header 0x%02x",
						G_OBEX_HDR_ENC(header->id));

	switch (G_OBEX_HDR_ENC(header->id)) {
	case G_OBEX_HDR_ENC_UNICODE:
		if (len < 3) {
			g_set_error(err, G_OBEX_ERROR,
				G_OBEX_ERROR_PARSE_ERROR,
				"Not enough data for unicode header (0x%02x)",
				header->id);
			goto failed;
		}
		ptr = get_bytes(&hdr_len, ptr, sizeof(hdr_len));
		hdr_len = g_ntohs(hdr_len);

		if (hdr_len == 3) {
			header->v.string = g_strdup("");
			header->vlen = 0;
			header->hlen = hdr_len;
			*parsed = hdr_len;
			break;
		}

		if (hdr_len > len || hdr_len < 5) {
			g_set_error(err, G_OBEX_ERROR,
				G_OBEX_ERROR_PARSE_ERROR,
				"Invalid unicode header (0x%02x) length (%u)",
				header->id, hdr_len);
			goto failed;
		}

		header->v.string = g_convert((const char *) ptr, hdr_len - 5,
						"UTF-8", "UTF-16BE",
						NULL, &str_len, &conv_err);
		if (header->v.string == NULL) {
			g_set_error(err, G_OBEX_ERROR,
					G_OBEX_ERROR_PARSE_ERROR,
					"Unicode conversion failed: %s",
					conv_err->message);
			g_error_free(conv_err);
			goto failed;
		}

		header->vlen = (gsize) str_len;
		header->hlen = hdr_len;

		*parsed = hdr_len;

		break;

        打印出编码和解码时header的类型:

# obexd[4015]: obexd/plugins/bluetooth.c:profile_new_connection() device /org/bluez/hci0/dev_C0_B5_D7_A3_98_90
obexd[4015]: obexd/src/obex.c:obex_session_start() 
bluetoothd[3493]: src/service.c:change_state() 0xdde18: device C0:B5:D7:A3:98:90 profile Object Push state changed: connecting -> connected (0)
bluetoothd[3493]: src/device.c:device_profile_connected() Object Push Success (0)

(obexd:4015): gobex-DEBUG: gobex/gobex-header.c:g_obex_header_create_list() 
obexd[4015]: obexd/src/obex.c:cmd_connect() 
obexd[4015]: CONNECT(0x0), (null)(0xffffffff)
obexd[4015]: obexd/src/obex.c:cmd_connect() Selected driver: Object Push server

(obexd:4015): gobex-DEBUG: gobex/gobex-header.c:g_obex_header_create_list() 
(obexd:4015): gobex-DEBUG: gobex/gobex-header.c:g_obex_header_new_uint32() header 0xc0
(obexd:4015): gobex-DEBUG: gobex/gobex-header.c:g_obex_header_new_uint32() 1
(obexd:4015): gobex-DEBUG: gobex/gobex-header.c:g_obex_header_get_length() header 0xc0 length 5
obexd[4015]: CONNECT(0x0), (null)(0x0)
(obexd:4015): gobex-DEBUG: gobex/gobex-header.c:g_obex_header_encode() header 0xc0
(obexd:4015): gobex-DEBUG: gobex/gobex-header.c:g_obex_header_free() header 0xc0

(obexd:4015): gobex-DEBUG: gobex/gobex-header.c:g_obex_header_create_list() 
(obexd:4015): gobex-DEBUG: gobex/gobex-header.c:g_obex_header_decode() header 0x00【为何为0了?】【xml和txt,bin相同现象】
(obexd:4015): gobex-DEBUG: gobex/gobex-header.c:g_obex_header_free() header 0x00
obexd[4015]: disconnected: Unicode conversion failed: Conversion from character set 'UTF-16BE' to 'UTF-8' is not supported
obexd[4015]: obexd/src/obex.c:obex_session_destroy() 

        与IMX8平台正常的obexd对比打印:明显看到ecode() header 0x00时就提示转码不支持就停止了运行。说明是收到了数据但转码失败。

root@genvict_imx8qxp:~# 
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_create_list() 
obexd[10342]: CONNECT(0x0), <unknown>(0xff)
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_create_list() 
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_new_uint32() header 0xc0
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_new_uint32() 1
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_length() header 0xc0 length 5
obexd[10342]: CONNECT(0x0), <unknown>(0x0)
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_encode() header 0xc0
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_free() header 0xc0
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_create_list() 
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_decode() header 0x00 
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_decode() header 0xc0	【没有执行这里的流程】	
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_decode() header 0x40
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x00 id 0x01
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0xc0 id 0xc3
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x40 id 0x49
obexd[10342]: PUT(0x2), <unknown>(0xff)
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x00 id 0x01
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0xc0 id 0xc3
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x40 id 0x49
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x00 id 0x01
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0xc0 id 0xc3
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x40 id 0x49
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x00 id 0x01
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0xc0 id 0xc3
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x40 id 0x49
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x00 id 0x01
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_unicode() header 0x00
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_unicode() bt.txt
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x00 id 0x01
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0xc0 id 0xc3
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_uint32() header 0xc0
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_uint32() 7
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x00 id 0x01
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0xc0 id 0xc3
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x40 id 0x49
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x00 id 0x01
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0xc0 id 0xc3
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x40 id 0x49
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x00 id 0x01
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0xc0 id 0xc3
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x40 id 0x49
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x00 id 0x01
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0xc0 id 0xc3
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_id() header 0x40 id 0x49
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_get_bytes() header 0x40
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_create_list() 
obexd[10342]: PUT(0x2), Continue(0x10)
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_free() header 0x00
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_free() header 0xc0
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_free() header 0x40
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_create_list() 
obexd[10342]: DISCONNECT(0x1), <unknown>(0xff)
obexd[10342]: DISCONNECT(0x1), Success(0x20)
(obexd:10342): gobex-DEBUG: ../bluez-5.54/gobex/gobex-header.c:g_obex_header_create_list() 
obexd[10342]: disconnected: Transport got disconnected

3、查看GCONV_LIBS怎么使用

        看编译链中的GCONV配置,toolchain/toolchain.mk,里面描述了如果打开配置,就会编译生成对应的动态库放到/usr/lib/gconv/目录下面。

# Install the gconv modules
ifeq ($(BR2_TOOLCHAIN_GLIBC_GCONV_LIBS_COPY),y)
GCONV_LIBS = $(call qstrip,$(BR2_TOOLCHAIN_GLIBC_GCONV_LIBS_LIST))
define COPY_GCONV_LIBS
    $(Q)found_gconv=no; \
    for d in $(TOOLCHAIN_EXTERNAL_PREFIX) ''; do \
        [ -d "$(STAGING_DIR)/usr/lib/$${d}/gconv" ] || continue; \
        found_gconv=yes; \
        break; \
    done; \
    if [ "$${found_gconv}" = "no" ]; then \
        printf "Unable to find gconv modules\n" >&2; \
        exit 1; \
    fi; \
    if [ -z "$(GCONV_LIBS)" ]; then \
        $(INSTALL) -m 0644 -D $(STAGING_DIR)/usr/lib/$${d}/gconv/gconv-modules \
                      $(TARGET_DIR)/usr/lib/gconv/gconv-modules && \
        $(INSTALL) -m 0644 $(STAGING_DIR)/usr/lib/$${d}/gconv/*.so \
                   $(TARGET_DIR)/usr/lib/gconv \
        || exit 1; \
    else \
        for l in $(GCONV_LIBS); do \
            $(INSTALL) -m 0644 -D $(STAGING_DIR)/usr/lib/$${d}/gconv/$${l}.so \
                          $(TARGET_DIR)/usr/lib/gconv/$${l}.so \
            || exit 1; \
            $(TARGET_READELF) -d $(STAGING_DIR)/usr/lib/$${d}/gconv/$${l}.so |\
            sort -u |\
            sed -e '/.*(NEEDED).*\[\(.*\.so\)\]$$/!d; s//\1/;' |\
            while read lib; do \
                 $(INSTALL) -m 0644 -D $(STAGING_DIR)/usr/lib/$${d}/gconv/$${lib} \
                               $(TARGET_DIR)/usr/lib/gconv/$${lib} \
                 || exit 1; \
            done; \
        done; \
        ./support/scripts/expunge-gconv-modules "$(GCONV_LIBS)" \
            <$(STAGING_DIR)/usr/lib/$${d}/gconv/gconv-modules \
            >$(TARGET_DIR)/usr/lib/gconv/gconv-modules; \
    fi
endef
TOOLCHAIN_TARGET_FINALIZE_HOOKS += COPY_GCONV_LIBS
endif

        对比查看IMX8下面是有/usr/lib/gconv/目录文件的:但由于只用buildroot编译bluez工具,所以没有拷贝/usr/lib/gconv/下面的文件,导致了编码库的缺失,这里确实是一个很隐蔽的bug。

root@genvict_imx8qxp:~# ls /usr/lib/gconv/ -l
total 72
-rwxr-xr-x 1 root root 14184 May 26 22:24 UTF-16.so
-rw-r--r-- 1 root root 56282 May 26 22:05 gconv-modules

        拷贝/usr/lib/gconv/的UTF-16.so和gconv-modules文件,obexd接收文件成功没有报错。

4、obexd  UTF16BE to UTF8编码补丁

        通过Google搜索,发现有ti公司的人发了一个补丁,用于UTF16BE to UTF8编码。

Bluetooth file receive failure

0001-obexd-fix-UTF-conversions.patch

Bluetooth: Receiving files failure

        补丁实现了一个utf16be_to_utf8转换函数,替代g_convert函数,但是由于我的bluez版本是5.43比较高,与补丁函数参数差异较大,没有验证这个补丁的可行性,给有条件的童鞋验证。

-			os->name = g_convert((const char *) hd.bs, hlen,
-					"UTF8", "UTF16BE", NULL, NULL, NULL);
+			os->name = utf16be_to_utf8((const char *) hd.bs, hlen);
		header->v.string = g_convert((const char *) ptr, hdr_len - 5,
						"UTF-8", "UTF-16BE",
						NULL, &str_len, &conv_err);

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值