I'm struggling to understand how I'm supposed to capture the client IP address when using libwebsockets as a server.
在使用libwebsockets作为服务器时,我很难理解我应该如何捕获客户端IP地址。
From what I understand of the documentation, libwebsockets_get_peer_addresses
is only available for use in the LWS_CALLBACK_FILTER_NETWORK_CONNECTION
callback, but at that point the user data struct is seemingly not initialized, so any attempt to store here will segfault.
根据我对文档的理解,libwebsockets_get_peer_addresses仅可用于LWS_CALLBACK_FILTER_NETWORK_CONNECTION回调,但此时用户数据结构似乎未初始化,因此任何在此处存储的尝试都将是段错误。
I would have expected the IP address to be in the request headers, as per other web servers such as Apache or nginx, but in this library it seems to be only available for a certain portion of the request process and is not copied into the headers.
我希望IP地址在请求标头中,如其他Web服务器,如Apache或nginx,但在此库中,它似乎只适用于请求过程的某一部分,不会被复制到标头中。
This is what I'm attempting inside LWS_CALLBACK_FILTER_NETWORK_CONNECTION:
这就是我在LWS_CALLBACK_FILTER_NETWORK_CONNECTION中尝试的内容:
char client_name [IP_SIZE];
char client_ip [IP_SIZE];
libwebsockets_get_peer_addresses(context, wsi, (int)(long)in,
client_name, sizeof(client_name),
client_ip, sizeof(client_ip));
strncpy(pss->ip, client_ip, sizeof(client_ip)); // segfault
I've tested the strncpy
inside another callback (LWS_CALLBACK_HTTP
) so I know that it should work when that pss
has been initialized.
我已经在另一个回调(LWS_CALLBACK_HTTP)中测试了strncpy,所以我知道它应该在pss初始化时起作用。
Any help would be appreciated because I find the documentation for the library very difficult to comprehend.
任何帮助将不胜感激,因为我发现该库的文档很难理解。
2 个解决方案
#1
2
You almost had it.
你几乎拥有它。
If you replace the (int)(long)in
with libwebsocket_get_socket_fd(wsi)
you can use it in other callbacks.
如果用libwebsocket_get_socket_fd(wsi)替换(int)(long),则可以在其他回调中使用它。
switch (reason) {
case LWS_CALLBACK_HTTP:
int IP_SIZE = 50;
char client_name [IP_SIZE];
char client_ip [IP_SIZE];
libwebsockets_get_peer_addresses(context, wsi, libwebsocket_get_socket_fd(wsi),
client_name, sizeof(client_name),
client_ip, sizeof(client_ip));
fprintf(stderr, "Received network connect from %s (%s)\n",
client_name, client_ip);
...
}
Output:
输出:
Received network connect from xxxxxxxx.dip0.t-ipconnect.de (93.208.91.xxx)
从xxxxxxxx.dip0.t-ipconnect.de(93.208.91.xxx)收到网络连接
#2
0
Okay, it appears I can work around this by getting the descriptor using libwebsocket_get_socket_fd
in a later callback (such as LWS_CALLBACK_HTTP
)
好的,似乎我可以通过在稍后的回调中使用libwebsocket_get_socket_fd获取描述符来解决这个问题(例如LWS_CALLBACK_HTTP)
It concerns me that the documentation says " You will not need this unless you are doing something special " regarding this particular function, but it seems to work correctly after running a few tests.
我担心文档会说“除非你正在做一些特殊的事情,否则你不会需要这个特殊功能”,但是在运行一些测试后它似乎正常工作。
I wonder if there's a less obtuse way of doing this.
我想知道是否有一种不那么迟钝的做法。
#1
2
You almost had it.
你几乎拥有它。
If you replace the (int)(long)in
with libwebsocket_get_socket_fd(wsi)
you can use it in other callbacks.
如果用libwebsocket_get_socket_fd(wsi)替换(int)(long),则可以在其他回调中使用它。
switch (reason) {
case LWS_CALLBACK_HTTP:
int IP_SIZE = 50;
char client_name [IP_SIZE];
char client_ip [IP_SIZE];
libwebsockets_get_peer_addresses(context, wsi, libwebsocket_get_socket_fd(wsi),
client_name, sizeof(client_name),
client_ip, sizeof(client_ip));
fprintf(stderr, "Received network connect from %s (%s)\n",
client_name, client_ip);
...
}
Output:
输出:
Received network connect from xxxxxxxx.dip0.t-ipconnect.de (93.208.91.xxx)
从xxxxxxxx.dip0.t-ipconnect.de(93.208.91.xxx)收到网络连接
#2
0
Okay, it appears I can work around this by getting the descriptor using libwebsocket_get_socket_fd
in a later callback (such as LWS_CALLBACK_HTTP
)
好的,似乎我可以通过在稍后的回调中使用libwebsocket_get_socket_fd获取描述符来解决这个问题(例如LWS_CALLBACK_HTTP)
It concerns me that the documentation says " You will not need this unless you are doing something special " regarding this particular function, but it seems to work correctly after running a few tests.
我担心文档会说“除非你正在做一些特殊的事情,否则你不会需要这个特殊功能”,但是在运行一些测试后它似乎正常工作。
I wonder if there's a less obtuse way of doing this.
我想知道是否有一种不那么迟钝的做法。