对“inotify_init1”的未定义引用
undefined reference to `inotify_init1'
我正在尝试将最新的 version 2.80 of dnsmasq 应用程序集成到我的项目中。该平台是 Linux 2.6.32。
使用交叉编译器 arm-none-linux-gnueabi-gcc 编译会出现此错误:
inotify.o: In function `inotify_dnsmasq_init':
inotify.c:(.text+0x514): undefined reference to `inotify_init1'
这个平台似乎不支持函数 inotify_init1()。
我在想能不能自己写这个函数
int inotify_init1(int flags)
{
int flags1 = 0;
int inotify_fd = inotify_init();
if ((inotify_fd != -1) && (flags != 0))
{
if((flags1 = fcntl(inotify_fd, F_GETFL)) != -1)
{
fcntl(inotify_fd, F_SETFL, flags1 | flags);
}
}
return inotify_fd;
}
这段代码能完成这项工作吗?
更新:
根据 inotify_init man page,inotify_init1() 在 2.9 版中添加到 glibc。我只使用 glibc 2.8 版
另一方面,我看到 inotify_init1 存在于内核中的几个文件中:
1) /fs/notify/inotify/inotify_user.c
/* inotify syscalls */
SYSCALL_DEFINE1(inotify_init1, int, flags)
{
...
}
2) /kernel/sys_ni.c
cond_syscall(sys_inotify_init1);
我知道我遗漏了一些东西,但我不知道是否在 dnsmasq 构建文件上构建或正确链接了适当的库。
谢谢指教。
您的功能看起来不错,应该可以工作。但是我不知道您的应用程序如何定义宏 IN_NONBLOCK 和 IN_CLOEXEC。查看 kernel srcrs 它们的定义应与 O_NONBLOCK 和 O_CLOEXEC 相同。添加 if (flags & ~(IN_CLOEXEC | IN_NONBLOCK)) return -EINVAL;
一些检查也很好。
我会添加一个文件 inotify.h
到您的项目/dnsmasq 源,我会添加到包含路径:
#ifndef MY_INOTIFY_H_
#define MY_INOTIFY_H_
#include_next <inotify.h>
// from https://github.molgen.mpg.de/git-mirror/glibc/blob/glibc-2.9/sysdeps/unix/sysv/linux/sys/inotify.h#L25
/* Flags for the parameter of inotify_init1. */
enum
{
IN_CLOEXEC = 02000000,
#define IN_CLOEXEC IN_CLOEXEC
IN_NONBLOCK = 04000
#define IN_NONBLOCK IN_NONBLOCK
};
extern int inotify_init1 (int flags) __THROW;
// or just int inotify_init1(int flags); ...
#endif
连同它,您在 c 文件中的包装器已添加到编译/链接中。 include_next 用作 glibc inotify.h 的简单覆盖。
如果您的内核支持 inotify_wait1 系统调用并且我认为 it does. You can even check if__NR_inotify_wait1 是在您的 unistd.h 中定义的。您可以:
#define _GNU_SOURCE
#include <unistd.h>
#include <sys/syscall.h>
int inotify_init1(int flags) {
return syscall(332, flags);
}
要进行系统调用,只需调用 syscall() 函数即可。
我正在尝试将最新的 version 2.80 of dnsmasq 应用程序集成到我的项目中。该平台是 Linux 2.6.32。 使用交叉编译器 arm-none-linux-gnueabi-gcc 编译会出现此错误:
inotify.o: In function `inotify_dnsmasq_init':
inotify.c:(.text+0x514): undefined reference to `inotify_init1'
这个平台似乎不支持函数 inotify_init1()。
我在想能不能自己写这个函数
int inotify_init1(int flags)
{
int flags1 = 0;
int inotify_fd = inotify_init();
if ((inotify_fd != -1) && (flags != 0))
{
if((flags1 = fcntl(inotify_fd, F_GETFL)) != -1)
{
fcntl(inotify_fd, F_SETFL, flags1 | flags);
}
}
return inotify_fd;
}
这段代码能完成这项工作吗?
更新: 根据 inotify_init man page,inotify_init1() 在 2.9 版中添加到 glibc。我只使用 glibc 2.8 版
另一方面,我看到 inotify_init1 存在于内核中的几个文件中:
1) /fs/notify/inotify/inotify_user.c
/* inotify syscalls */
SYSCALL_DEFINE1(inotify_init1, int, flags)
{
...
}
2) /kernel/sys_ni.c
cond_syscall(sys_inotify_init1);
我知道我遗漏了一些东西,但我不知道是否在 dnsmasq 构建文件上构建或正确链接了适当的库。
谢谢指教。
您的功能看起来不错,应该可以工作。但是我不知道您的应用程序如何定义宏 IN_NONBLOCK 和 IN_CLOEXEC。查看 kernel srcrs 它们的定义应与 O_NONBLOCK 和 O_CLOEXEC 相同。添加 if (flags & ~(IN_CLOEXEC | IN_NONBLOCK)) return -EINVAL;
一些检查也很好。
我会添加一个文件 inotify.h
到您的项目/dnsmasq 源,我会添加到包含路径:
#ifndef MY_INOTIFY_H_
#define MY_INOTIFY_H_
#include_next <inotify.h>
// from https://github.molgen.mpg.de/git-mirror/glibc/blob/glibc-2.9/sysdeps/unix/sysv/linux/sys/inotify.h#L25
/* Flags for the parameter of inotify_init1. */
enum
{
IN_CLOEXEC = 02000000,
#define IN_CLOEXEC IN_CLOEXEC
IN_NONBLOCK = 04000
#define IN_NONBLOCK IN_NONBLOCK
};
extern int inotify_init1 (int flags) __THROW;
// or just int inotify_init1(int flags); ...
#endif
连同它,您在 c 文件中的包装器已添加到编译/链接中。 include_next 用作 glibc inotify.h 的简单覆盖。
如果您的内核支持 inotify_wait1 系统调用并且我认为 it does. You can even check if__NR_inotify_wait1 是在您的 unistd.h 中定义的。您可以:
#define _GNU_SOURCE
#include <unistd.h>
#include <sys/syscall.h>
int inotify_init1(int flags) {
return syscall(332, flags);
}
要进行系统调用,只需调用 syscall() 函数即可。