Ldd(1) and Untrusted Binaries (2023)

(jmmv.dev)

40 points | by 3np 5 days ago ago

17 comments

  • omoikane 2 hours ago ago

    Coincidentally, `ldd` has the same caveat on Cygwin, although there it's implemented as an executable instead of a shell script:

        ldd invokes the Windows loader on the file specified, then uses the Windows debugging interface to report DLLs loaded, and (for executables) to attempt to stop execution before the entrypoint. Thus, you should never use ldd on an untrusted file.
    
    https://cygwin.com/cygwin-ug-net/ldd.html
    • userbinator 4 minutes ago ago

      I wonder why they implemented it that way, since dynamic linking on Windows is much less of a mess than on *nix systems. dumpbin /imports and Depends have been the standard there for a long time.

  • krosaen 30 minutes ago ago

    I have found libtree to be nicer, sounds like it doesn’t suffer the same risk. But there is the added inconvenience of installing it - but usually mild given prebuilt binaries for common distributions.

  • ReleaseCandidat 3 hours ago ago

    Each Elf executable can have its own "interpreter" (loader, which as default is `ld-linux. so`), so without calling the configured interpreter ldd can't know about the dependencies of such "special" executables. And the configured interpreter can be any program, AFAIK there are no limititations in the ELF format.

    • quotemstr 2 hours ago ago

      Yes, but in the vast majority of cases the interpreter is ld-linux.so (or the Buonic/Musl equivalent) and a safe binary inspection tool can know for sure what that interpreter will do. It's okay for that tool to say "I don't know" 0.0001% of the time.

      • ReleaseCandidat 2 hours ago ago

        It wasn't meant as an argument against not loading the interpreter, but an explanation why it is "normal" - but if course insecure - behavior for ldd to execute the configured interpreter.

  • aleden 3 hours ago ago

    Disentangling who loads what without actually running the app, i.e. allowing a sequence of dlopen() calls to succeed, seems impossible to accomplish in the presence of binary code which cannot be effectively scrutinized.

    • ReleaseCandidat 3 hours ago ago

      It's not about calling the app itself - that doesn't happen with ldd. ldd does not know about dlopened libraries.

      • aleden 3 hours ago ago

        I guess I wasn't sure that DT_NEEDED entries covered everything. Sometimes you have stuff that happens in DT_INIT constructors.

        • ReleaseCandidat 3 hours ago ago

          Dynamic dlopen calls do not appear in the ELF at all, these are "normal" function calls.

          • sim7c00 2 hours ago ago

            correct. you cam call dlopen anywhere so loading it into memory or even executing all easy to reach paths wont guarantee you'd get that. you might do full symbolic execution but your 'ldd' might take days or weeks :'D

  • quotemstr 2 hours ago ago

    ldd's shortcomings have been well known for years, but here we are. Same with strncpy. It's remarkable how sticky some tools are in people's muscle memory and how hard it is to eradicate these bad tools even when drop in alternatives are within reach. Habit is powerful.

    • ReleaseCandidat 2 hours ago ago

      > strncpy

      strncpy had been touted the "safe strcpy alternative" for years.

  • anthk 2 hours ago ago

                  objdump -x /path/to/binary | grep NEEDED
    • ReleaseCandidat 2 hours ago ago

      It's not same, as ldd does print transitive dependencies too. libtree is comparable to ldd

  • blueflow 3 hours ago ago

    Why do people a) have these preconceptions, b) have them be accurate enough to work at all, and c) get away with shouting "but POLA" when they don't work out?

    • juped 2 hours ago ago

      I'm astonished that this melted sand performs computations, but Shockley closed my CVE "not a bug"