英文:
Deliver bytes to another application which calls ::recv()
问题
- 有没有可能在不更改调用
::recv()
代码的情况下将处理后的数据包字节传递给第二个应用程序? - 我还想将
::send()
的调用“重定向”到第一个应用程序。我认为可以使用动态库和LD_PRELOAD
来实现这一点,但是否可以通过静态技术来实现?
英文:
I have a userspace C++ application (could be a library) processing packets.
I have a second application (written in C) which obtains bytes via calling ::recv()
.
- Is it possible to "deliver" the processed packet bytes to the second application, without changing the code calling
::recv()
? - I'd also like to "divert" calls from
::send()
to the first application. I think I can do this using a dynamic library andLD_PRELOAD
, but is it possible to do via a static technique?
答案1
得分: 1
根据我的理解,您希望能够以一种特殊模式运行任何未经修改的程序,其中它的所有套接字都连接到模拟网络的您自己的程序,而不是实际网络。这是为了帮助开发一些自定义网络代码。
也许最简单的方法是使用LD_PRELOAD - 这是经常用于覆盖标准库函数的机制。
您可以创建一个共享库,其中包含像recv
和send
等函数名称,以及您需要覆盖的其他任何函数,然后在运行第二个程序时设置环境变量LD_PRELOAD=my_socket_library.so
(将其更改为实际的文件名)。加载器将会将recv
和send
的调用链接到您的函数,而不是libc中的函数,因为LD_PRELOAD库具有优先级。如果您希望调用原始函数,可以使用dlsym
与RTLD_NEXT
来获取指向它们的指针(超出范围,请搜索更多信息)。
另外,您可能更喜欢将它变成一个真正的套接字,连接到您的网络程序。您的网络程序将侦听某个端口(使用内核网络系统),并且您的共享库将覆盖connect
函数,使其连接到网络程序侦听的端口,然后告诉网络程序地址。除非程序使用getpeername
来查看它连接到的地址(大多数程序不这样做,因为它们已经知道它们连接到哪个地址),否则它不会察觉到任何差异,但由于它是一个真正的套接字,它将适用于程序执行的任何套接字操作。
英文:
As I understand, you want to be able to run any unmodified program in a special mode where all its sockets get connected to your own program which emulates the network, instead of the actual network. This is to help develop some custom networking code.
Perhaps the simplest way to do this is with LD_PRELOAD - a mechanism that is often used for overriding standard library functions.
You can make a shared library with function names like recv
and send
, and anything else you need to override, and then set the environment variable LD_PRELOAD=my_socket_library.so
(change it to the actual filename) when running the second program. The loader will link recv
and send
calls to your functions instead of the ones in libc, because LD_PRELOAD libraries take priority. If you want to call the original functions you can use dlsym
iwth RTLD_NEXT
to get pointers to them (out of scope; Google for more information).
Alternatively, you might prefer to make it a real socket, connected to your networking program. Your networking program would listen on some port (using the kernel networking system) and your shared library would override the connect
function so it connects to the port where the networking program was listening, then tells the networking program the address. Unless the program uses getpeername
to see the address it's connected to (and most programs don't, because they already know which address they connected to) it won't know the difference, but since it's a real socket it would work no matter what socket stuff the the program did.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论