使用 C 开始使用 wpa_supplicant
Posted
技术标签:
【中文标题】使用 C 开始使用 wpa_supplicant【英文标题】:Getting started with wpa_supplicant using C 【发布时间】:2016-11-08 00:02:36 【问题描述】:在人们妄下结论说这是重复的帖子之前,我想指出我已经浏览了有关此主题的其他帖子,但确实没有找到解决方案。
我需要什么
我的目标是从 C 程序访问 wpa_supplicant 以执行以下操作:
-
查看活动连接
检测接口何时关闭
连接AP/设置AP等
我发现了什么
如果我需要编写一个 C 程序来与 wpa_supplicant 通信,我不需要 DBus 只需将这些文件包含在我的项目目录中,我就可以使用wpa_ctrl.h
中的功能
以下是我找到的与此问题相关的一些链接。 1, 2, 3
我还浏览了official documentation,它讨论了使用wpa_ctrl.c
的外部程序
为什么上述方法并不能真正解决问题
我在 SO 和其他相关网站上找到的大多数关于此问题的帖子都指向官方文档等资源,这些资源很好但不能解决问题 在许多此类帖子中,人们已经放弃了这一点,或者已经制定了解决方案,但尚未将其发布到网上。 对于本主题的新手,如果可以发布一个工作示例——wpa_supplicant 的“hello world”,将会很有帮助。到目前为止我做了什么
从this 链接,我将wpa_supplicant-2.5/src/common/wpa_ctrl.h
复制到wpa_supplicant-2.5/src/utils
目录中(因为common.h
有很多依赖项)。然后我在同一目录中编写了一个简单的 C 程序hostapd_cli.c
,如下所示。 我收到未定义的“wpa_ctrl_open”引用错误
#include "includes.h"
#include <dirent.h>
#include "wpa_ctrl.h"
#include "common.h"
static struct wpa_ctrl *ctrl_conn;
static int hostapd_cli_quit = 0;
static int hostapd_cli_attached = 0;
static const char *ctrl_iface_dir = "/var/run/wpa_supplicant";
static char *ctrl_ifname = NULL;
static int ping_interval = 5;
int main()
ctrl_conn = wpa_ctrl_open(ctrl_iface_dir);
if (!ctrl_conn)
printf("Could not get ctrl interface!\n");
return -1;
return 0;
生成文件
C=gcc
CFLAGS=-lpthread
DEPS = includes.h wpa_ctrl.h common.h
OBJ = wpa_ctrl.o hostapd_cli.o
%.o: %.c $(DEPS)
$(CC) -c -o $@ $< $(CFLAGS)
main: $(OBJ)
gcc -o $@ $^ $(CFLAGS)
.PHONY: clean
clean:
rm -f *.o *~ core $(INCDIR)/*~
构建日志
gcc -o main wpa_ctrl.o hostapd_cli.o -lpthread
hostapd_cli.o: In function `main':
hostapd_cli.c:(.text+0xf): undefined reference to `wpa_ctrl_open'
collect2: error: ld returned 1 exit status
Makefile:10: recipe for target 'main' failed
make: *** [main] Error 1
关于如何使用这些文件并将其集成到外部项目或如何编译它的材料不多,我有点无能为力。任何有关如何进行的帮助将不胜感激。
编辑 1:更正错字并添加构建日志
【问题讨论】:
来自您链接的官方文档,参考wpa_ctrl.c
:“外部程序可以将此文件链接到其中”。也就是说,您需要复制该文件,对其进行编译并将其链接到您的程序中。
这是否意味着,在我的 makefile 中我添加了 wpa_ctrl.c?在我的makefile中,OBJ = wpa_ctrl.c testProg.c
是的。除了它应该列出 .o
文件而不是 .c
文件。
是的。对不起,那是一个错字。包含正确的.o
文件仍然会产生同样的错误。
也许你的 Makeifile 还是有问题。如果您需要帮助,则需要显示更新后的 Makefile 和构建日志。
【参考方案1】:
对于 OP 来说,这个答案来得太晚了,但它可能会帮助其他遇到同样问题的人。
在 wpa_supplicant-2.9 中,您不需要使用自己的源文件编译 wpa_ctrl.c
。相反,首先从 wpa_supplicant 来源构建libwpa_client.so
(或libwpa_client.a
):$make -C wpa_supplicant libwpa_client.so
然后,将共享库链接到构建您自己的程序。您还需要添加包含路径。例如)$gcc main.c -Iwpa_supplicant-2.9/src/common -I.wpa_supplicant2-9/src/utils -lwpa_client
【讨论】:
【参考方案2】:对 `wpa_ctrl_open' 的未定义引用
这是一个链接器错误。如果是命令,
$ nm wpa_ctrl.o
显示它定义了 wpa_ctrl_open,那么您的直接问题可能只是命令行命令。试试:
gcc -o main hostapd_cli.o wpa_ctrl.o -lpthread
因为hostapd_cli
引用了wpa_ctrl.o
中的符号。否则,您需要找到定义该符号的源代码,以便链接到它。
编辑:显然你需要define a couple of symbols。
HTH。
【讨论】:
我不认为它是链接器问题。我想我没有正确的文件。wpa_ctrl.c
没有定义 wpa_ctrl_open()
方法。这是令人困惑的部分,因为官方文档说任何外部文档都可以链接wpa_ctrl.c
并使用wpa_ctrl_open()
已定义。请参阅我的编辑和w1.fi/cgit/hostap/tree/src/common/wpa_ctrl.c 的第 86 行。
我认为这还不够清楚,也不是独立的。 wpa_ctrl.c
定义了两个 wpa_ctrl_open 函数,但定义由宏控制。答案中“定义几个符号”下的链接显示,对于典型的 Linux 使用,您需要在编译 wpa_ctrl.c
时定义 CONFIG_CTRL_IFACE
和 CONFIG_CTRL_IFACE_UNIX
宏以获得在 Linux 上有用的功能。相同的文件适用于具有不同宏的 Windows。恕我直言,答案可以显示此信息并具有参考链接以显示信息的来源。
我可以交叉编译库(用于 arm、raspberry)并通过定义这两个宏来使其工作。对于常规编译(在 X86-64 上运行),没有必要定义它们。【参考方案3】:
好的,所以我让它在我的树莓派上工作。所有功劳归于树莓派论坛上的 Gyph(链接:https://www.raspberrypi.org/forums/viewtopic.php?t=42949)。
需要的文件
in wpa_supplicant/src/common :
wpa_ctrl.h
wpa_ctrl.c
in wpa_supplicant/src/utils :
build_config.h
common.h
includes.h
os.h
os_unix.c
wpabuf.h
wpa_debug.h
your own file
运行以下命令进行编译:
gcc -Wall -Wextra -I ./ -MMD -c -g -o wpa_ctrl.o wpa_ctrl.c -D CONFIG_CTRL_IFACE -D CONFIG_CTRL_IFACE_UNIX
gcc -Wall -Wextra -I ./ -MMD -c -g -o os_unix.o os_unix.c -D CONFIG_CTRL_IFACE -D CONFIG_CTRL_IFACE_UNIX
gcc -Wall -Wextra -o your_file your_file.c os_unix.o wpa_ctrol.o
要使用 wpa_supplicant,我发现复制 hostapd_cli 并根据我的需要进行调整是最简单的。请注意,如果您使用的是 wpa_supplicant 而不是 hostapd,则必须调整 ctrl_iface_dir 变量。 (对我来说是“/var/run/wpa_supplicant”)。
【讨论】:
以上是关于使用 C 开始使用 wpa_supplicant的主要内容,如果未能解决你的问题,请参考以下文章