【问题标题】:undefined reference to clock_gettime in contiki osContiki os中对clock_gettime的未定义引用
【发布时间】:2021-11-01 18:45:37
【问题描述】:

我需要在 C 中生成一个随机数,我使用 srand() 和 rand() 函数完成了它。当我在普通编译器中运行它时它工作正常,但是当我尝试在 Contiki OS 中编译文件时,它会抛出一个“未定义的时钟获取时间引用”错误。

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <time.h>
int a;
srand(time(NULL));
a=rand() % 10000 + 2;
char *str = (char*)malloc(a);
int i=0;
for(i=0; i<a-1;i++){
  str[i]='s';
}
str[i] = '\0';
strcat(str,"Hello %d from the client ");
sprintf(buf,str, seq_id);

有人可以帮我解决这个问题吗?

【问题讨论】:

  • main() 函数在哪里?您不能在函数之外拥有所有这些代码
  • strcat 调用会导致缓冲区溢出。
  • 欢迎来到 *!请拨打tour 并阅读“How to Ask”以了解本网站的运作方式。 -- 请不要发布代码或文本的图像。逐字复制。 -- 请查阅 Contiki 的文档,您可能需要提供该错过的功能才能调用time()。可以去掉time()的调用,使用rand()内部预定义或未定义的初始值。
  • @rturrado - 不太可能提供帮助。目标嵌入在 MSP430 MCU 中 - 甚至没有给定它具有使用时间源的 RTC。这必须由 BSP 或用户提供。除了这里的要求是获得合适的 PRNG 种子,而不是实际获得时钟时间。这个平台有更合适的方法。
  • @rturrado :这很公平,尤其是问题被错误标记为“Ubuntu”并且从未提及目标。 MSP430 仅在屏幕截图中可见。我不确定“更彻底” - 我在嵌入式系统方面拥有 30 多年的经验,并且正在做出有根据的猜测。我从未使用过 Contiki——据我所知,使用 Newlib 而不是 glibc,这对于 Contiki 所针对的资源受限的嵌入式系统来说是有意义的。

标签: c embedded msp430 contiki srand


【解决方案1】:

我认为“普通编译器”是指主机系统的本机编译器?在这种情况下,开发主机是带有操作系统的标准硬件,该操作系统通过最终从 RTC 或 NTP 获取时间的操作服务提供“挂钟”时间。

在嵌入式系统中,标准库是通用的,需要重新定位到您的平台。通常 I/O、堆管理和时间服务需要重定向。在这种情况下,您需要定义 clock_gettime() 来解析链接(或简单地重新定义 time() 的覆盖 - 如 here 所述)。您如何实现它取决于您的特定硬件。通常,您会从 RTC 获得时间,但如果您的硬件缺少 RTC 晶体及其备用电池,那么它几乎没有用处。时间必须来自某个地方,图书馆无法确定您的特定硬件的位置。

如果您实际上从不需要挂钟时间并且只是遵循使用time(NULL) 作为随机数生成器种子的常见习惯用法,而不是完全支持您不需要的time() 函数;考虑另一种生成种子的方法,例如Application Note 中描述的方法,它使用两个独立的时钟源(VLO 和 DCO)来生成随机位序列。该方法非常耗时,因此您通常会执行一次,然后通过srand() 将其用作标准 PRNG 的种子。

https://github.com/0/msp430-rng/blob/master/rand.c 有一个应用笔记算法的实现,但它是作为标准rand() 的替代实现的。我建议你重命名为generate_seed(),然后调用:

srand( generate_seed() ) ;

【讨论】:

    【解决方案2】:

    我的建议是使用工厂预编程的 TLV 内存中的芯片唯一值。每个芯片都将包含唯一值(例如校准数据),因此只需对所有 TLV 内存进行哈希处理以得出种子值,然后将其插入 rand() 函数。如果您手边没有散列函数,那么只需对所有字节使用任何 CRC32 计算。

    请参阅this code,例如如何从 TLV 内存中读取。请记住,每个 MSP430 系列都不同,因此请查阅器件数据表以了解确切的存储器位置。

    如果您的应用程序初始化每个 MSP430 芯片内的实时时钟 (RTC) 硬件(并通过电源循环对其进行更新),那么您可以将其添加到哈希结果中。只需使用 RTC 日期和时间寄存器为您的种子值继续哈希(或 CRC32)。

    【讨论】: