为什么getrandom()不能编译?

时间:2017-07-21 12:09:38

标签: c random

愚蠢的问题,我可能错过了一个标题,但是手册页说我只需要#include <linux/random.h>

#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>
#include <linux/random.h>

#define BITS 8192
#define BYTES (BITS >> 3)

int main() {
    uint8_t array[BYTES];

    printf("started...");
    int r = getrandom(array, BYTES, 0);
    if (r) exit(1);

    return 0;
}

错误是:

chris@purple:~/lunch/bitarray$ make && ./bitarray 
clang -g -Wall -Wpedantic -Werror -std=c11 -O2 -save-temps bitarray.c -o bitarray
bitarray.c:13:10: error: implicit declaration of function 'getrandom' is invalid in C99 [-Werror,-Wimplicit-function-declaration]
 int r = getrandom(array, (8192 >> 3), 0);
         ^
1 error generated.
Makefile:10: recipe for target 'bitarray' failed
make: *** [bitarray] Error 1

(在gcc中也失败了。)

chris@purple:~/lunch/bitarray$ cat /etc/lsb-release 
DISTRIB_ID=Ubuntu
DISTRIB_RELEASE=16.04
DISTRIB_CODENAME=xenial
DISTRIB_DESCRIPTION="Ubuntu 16.04.2 LTS"
chris@purple:~/lunch/bitarray$ uname -a
Linux purple 4.4.0-83-generic #106-Ubuntu SMP Mon Jun 26 17:54:43 UTC 2017 x86_64 x86_64 x86_64 GNU/Linux

1 个答案:

答案 0 :(得分:5)

似乎有些Linux系统有getrandom的手册页和正确的系统调用定义,但没有C函数。它确实足以让你创建自己的:

// _GNU_SOURCE should be set before *any* includes.
// Alternatively, pass to compiler with -D, or enable GNU extensions
// with -std=gnu11 (or omit -std completely)
#define _GNU_SOURCE
#include <unistd.h>
#include <sys/syscall.h>

int my_getrandom(void *buf, size_t buflen, unsigned int flags)
{
    return (int)syscall(SYS_getrandom, buf, buflen, flags);
}

// remove this when we have a real getrandom():
#define getrandom  my_getrandom
// and replace it with
// #include <linux/random.h>
#include <stdio.h>
#include <stdint.h>
#include <stdlib.h>

#define BITS 8192
#define BYTES (BITS >> 3)

int main() {
    uint8_t array[BYTES];

    printf("started...\n");
    int r = getrandom(array, sizeof array, 0);
    return r;
}