Discussion:
Preloading libraries to override BSD IPC function symbols and recursion
(too old to reply)
Matthew Mondor
2018-03-23 16:12:24 UTC
Permalink
Lately while doing a test, I noticed that if a library overrides
socket(2) and attempts to call the original socket(2) function from
libc, a recursive loop fills the stack causing a segmentation fault in
wrapped applications using socket(2).

I then remembered that some wrappers such as tsocks and proxychains
also occasionally crashed with some programs. Tsocks doesn't seem to
override socket(2) but it overrides select(2) and connect(2). Some
applications work fine, others crash with select()/__select50() calling
eachother recursively.

Using nm(1) on /usr/pkg/lib/libtsocks.so:

000000000000226b T connect
0000000000207480 b realconnect
0000000000002751 T __select50
0000000000207478 b realselect

Using nm(1) on test /usr/local/lib/nonet-unix.so:

0000000000000953 T __socket30
0000000000200f70 b real_socket

If in my nonet test I dlsym(3) "__socket30" instead of "socket", it
works fine. Which begs the question: how are those programs expected
to know which symbol to use (they expect the standard symbol name).
Some tricks can be used to discover it, of course.

But is there a better solution to always get this right?

Thanks,
--
Matt

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Joerg Sonnenberger
2018-03-23 19:32:51 UTC
Permalink
Post by Matthew Mondor
But is there a better solution to always get this right?
I'm not aware of any compiler intrinsic to get the linker name of a
given variable or function. Neither exists for symbol versioning.

Joerg

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Matthew Mondor
2018-03-23 20:06:37 UTC
Permalink
On Fri, 23 Mar 2018 20:32:51 +0100
Post by Joerg Sonnenberger
Post by Matthew Mondor
But is there a better solution to always get this right?
I'm not aware of any compiler intrinsic to get the linker name of a
given variable or function. Neither exists for symbol versioning.
Thanks. Do you think that it could be feasible (i.e. in a future
NetBSD release) to always use/present the official symbols and have
them mapped transparently by the kernel/compat modules depending on
version information from the ELF header rather than using public
versioned linker names (or was it previously done this way and changed
for a reason)? I assume (possibly wrongly), that these versioned
symbols are used for binary compatibility?

Thanks again,
--
Matt

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Joerg Sonnenberger
2018-03-23 20:39:46 UTC
Permalink
Post by Matthew Mondor
On Fri, 23 Mar 2018 20:32:51 +0100
Post by Joerg Sonnenberger
Post by Matthew Mondor
But is there a better solution to always get this right?
I'm not aware of any compiler intrinsic to get the linker name of a
given variable or function. Neither exists for symbol versioning.
Thanks. Do you think that it could be feasible (i.e. in a future
NetBSD release) to always use/present the official symbols and have
them mapped transparently by the kernel/compat modules depending on
version information from the ELF header rather than using public
versioned linker names (or was it previously done this way and changed
for a reason)? I assume (possibly wrongly), that these versioned
symbols are used for binary compatibility?
Frankly, I don't think symbol versioning will give you the expected
behavior either. It just works most of the time since people rarely keep
such binaries around long enough for the next versioning round.

Joerg

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Taylor R Campbell
2018-03-23 21:34:30 UTC
Permalink
Date: Fri, 23 Mar 2018 12:12:24 -0400
If in my nonet test I dlsym(3) "__socket30" instead of "socket", it
works fine. Which begs the question: how are those programs expected
to know which symbol to use (they expect the standard symbol name).
Some tricks can be used to discover it, of course.
But is there a better solution to always get this right?
Not really. Overriding symbols is a black art in the first place, of
course... I'll leave further discussion of symbol versioning and ELF
to experts on the subject like joerg, but here's the patch I sent to
torsocks to fix the same issue:

https://trac.torproject.org/projects/tor/ticket/16432

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Matthew Mondor
2018-03-23 22:45:22 UTC
Permalink
On Fri, 23 Mar 2018 21:34:30 +0000
Post by Taylor R Campbell
Date: Fri, 23 Mar 2018 12:12:24 -0400
If in my nonet test I dlsym(3) "__socket30" instead of "socket", it
works fine. Which begs the question: how are those programs
expected to know which symbol to use (they expect the standard
symbol name). Some tricks can be used to discover it, of course.
But is there a better solution to always get this right?
Not really. Overriding symbols is a black art in the first place, of
course... I'll leave further discussion of symbol versioning and ELF
to experts on the subject like joerg, but here's the patch I sent to
https://trac.torproject.org/projects/tor/ticket/16432
Thanks again to both of you; I'll consider this part to be OS+version
specific then.
--
Matt

--
Posted automagically by a mail2news gateway at muc.de e.V.
Please direct questions, flames, donations, etc. to news-***@muc.de
Loading...