Little-Endian 字节顺序(iOS,BLE 扫描响应)

Posted

技术标签:

【中文标题】Little-Endian 字节顺序(iOS,BLE 扫描响应)【英文标题】:Little-Endian Byte Order (iOS, BLE scan response) 【发布时间】:2017-09-30 15:12:38 【问题描述】:

基本上,我将 nativescript 用于跨平台应用程序。此应用程序与 BLE 设备交互。 BLE 设备在广告数据包之后发送扫描响应,我可以在 ios 端将其作为 NSData 对象检索。

这是描述属性的(伪)输出:。

输出代表外设的硬件地址。

硬件人员告诉我这是 little-endian,我知道它是 48 位字符串。它来自外围设备,其固件是用 C 语言编写的。

我已经尝试了几天将其转换为字符串(具有正确的字节顺序),以便我可以将硬件地址存储在我们的后端,但我无法提出一个优雅的解决方案。

我提出的一个解决方案是读取 NSData 对象的 :description 属性,然后手动(在 javascript 中)“解码”它。我只是觉得这个解决方案对于生产环境来说不够合适,我想改用本机实用程序。

我尝试过使用:

NSString.alloc().initWithDataEncoding(mac, NSUTF8StringEncoding);

..使用文档THIS 页面中的每种编码类型。我要么得到 nil 作为回报,要么是不正确的字符。

正如我之前所说,这是用 NativeScript 编写的;但是,我对目标 C 有很好的理解,所以我应该能够转换以该语言提供的任何示例。

任何意见将不胜感激。提前致谢!

【问题讨论】:

【参考方案1】:

CRD 的答案是正确的,但我猜这不是您要的。您想要一个看起来像“54:fc:a2:67:0b:00”(蓝牙/MAC 地址)的结果,对吗?这是一种简单的蛮力方法(您可以在循环等中执行此操作,但不值得 IMO)。

// Just for testing; you already have data.
uint8_t address[6] =  0x54, 0xfc, 0xa2, 0x67, 0x0b, 0x00 ;
NSData *data = [NSData dataWithBytes:address length:6];

// Check the length before proceeding (maybe return an error rather than crash :D)
assert([data length] == 6);

// Grab the bytes
const uint8_t *bytes = data.bytes;

// Format them
NSString *addressString = [NSString stringWithFormat:@"%02x:%02x:%02x:%02x:%02x:%02x",
                           bytes[0], bytes[1], bytes[2], bytes[3], bytes[4], bytes[5]];

// 3. Profit
NSLog(@"%@", addressString);

但是……

我不太确定工程师在这里所说的“小端”是什么意思。 54:fc:a2 不是指定的制造商代码。通常,我会假设“little-endian”意味着他们已经对 16 位字进行了字节交换(我在 CSR 平台上遇到过),所以这应该是 fc:54:67,但没有分配任何一个。将整个事情视为完全向后给我们00:0b:67,它被分配给制造蓝牙相机的TopView,所以我敢打赌这就是“小端”的意思(这是有道理的,因为在线路上写入 MAC 地址的正常方式正好相反,是“大端”)。

所以这会将代码更改为:

NSString *addressString = [NSString stringWithFormat:@"%02x:%02x:%02x:%02x:%02x:%02x",
                           bytes[5], bytes[4], bytes[3], bytes[2], bytes[1], bytes[0]];

地址是00:b0:67:a2:fc:54吗?

【讨论】:

地址正确,我很抱歉。 OUI 应该注册到 si-labs。 Rob,你能看看这个问题吗:***.com/questions/46518084/… 如果我在 obj-c 中工作,你的解决方案将是黄金!话虽如此,由于 NativeScript(可能的)限制,我无法实现 stringWithFormat 方法。【参考方案2】:

您似乎有一个包含 6 个字节的 NSData 对象,第一个字节是最不重要的字节(小端序)。不要尝试使用字符表示,这是二进制数据,就这样处理吧。

使用NSDatabytes 属性获取指向第一个字节的指针并将其保存到Byte * 变量,例如bPtr。现在只需依次索引字节并将它们按顺序插入到 64 位无符号整数变量中。您可以通过对整数进行位移并在下一个字节中进行或运算来做到这一点 - 从 bPtr[5] 开始向下到 bPtr[0] 并将整数每次向左移动 8。

HTH

【讨论】:

以上是关于Little-Endian 字节顺序(iOS,BLE 扫描响应)的主要内容,如果未能解决你的问题,请参考以下文章

小端格式和大端格式(Little-Endian&Big-Endian)

小端格式和大端格式(Little-Endian&Big-Endian)

字节存储顺序问题

字节序

数据在内存中存放的顺序之字节序(附图解判断本机大小端程序及例题)建议收藏食用

Little-Endian小字节序