Re: safe strcpy()?

From: Brandon Erhart (berhart@ErhartGroup.COM)
Date: 01/28/03

  • Next message: Timo Sirainen: "Re: safe strcpy()?"
    Date: Tue, 28 Jan 2003 11:21:19 -0600
    To: Michal Zalewski <lcamtuf@coredump.cx>, Ed Carp <erc@pobox.com>
    From: Brandon Erhart <berhart@ErhartGroup.COM>
    
    

    At 03:14 AM 1/28/2003, you wrote:
    >On Tue, 28 Jan 2003, Ed Carp wrote:
    >
    > > This lef me to go back to my C textbooks (which I hadn't liiked in
    > > almost 20 years!), and start looking for a way to figure out how to
    > > determine how much space was allocated to a string. I was rather
    > > surprised to find that I couldn't find such an animal! Am I missing
    > > something here?
    >
    >Not really. C itself does not provide any built-in mechanism for passing
    >sizes of buffers or other objects. Sizeof() is merely replaced with the
    >storage size of whatever you passed to it during the compilation, and is
    >not a runtime mechanism for determining the size of an object you point
    >to.
    That's the reason I love it :) Although I learned QBasic first while I was
    young and impressionable, I was still able to migrate to C without a
    manifold of problems. It's very powerful.
    > > I'm not interested in manual manipulation of code, or suggestions on
    > > changing coding style - there should be a way in the language to
    > > determine the size of an object at runtime.
    >
    >No. C is a fairly low-level language. There are some versions of C that
    >generate code with range checking and such, but it's not very common (and
    >not always as effective as in other languages).
    >You think what made C co popular?;-) If you write your code in range
    >checked, strong typed language, you get some strange errors all the
    >time... if you write it in C, it runs, *maybe* sometimes behaves strangely
    >because some variable gets overwritten, but hey, good enough to release
    >;-)

    That's the source of a lot of problems, though. Bugs that pop up just NOW
    AND THEN when the stack gets fubar'd by some seemingly innocent code (which
    has happened to me many a time -- hard to find it).

    Semi-Interesting-for-those-who-don't-know: A fellow in #C on EFnet IRC once
    suggested I put a char array w/ a large length as the first variable in the
    block of code I thought it was happening at. I did it, and the bug "went
    away" (the variable was being written into instead of smooshing the stack
    due to lack of size since we had increased it). Not a fix, but a way of
    debugging, just thought I'd share that.

    >For dynamically allocated memory, you might want to use
    >malloc_usable_size() in glibc, or a similar mechanism available for your
    >OS, but that works well only if the buffer is a separate chunk. It's a
    >limited, non-portable and often dangerous approach, and most likely
    >requires some coding style changes anyway, just to keep all buffers in
    >separate chunks.
    >
    >There are several interesting ways to prevent the problem without making
    >major changes to the code, however. One of better ideas I've seen is to
    >register buffer sizes when buffers are created. It takes few more lines
    >when you create an object, but this is the only effort you need to make.
    >Buffers are later deregistered from your own free(), for heap memory - and
    >your own function epilogue, for stack. With some help from the compiler
    >and linker, two last steps involve no changes to your existing code. If
    >your code uses mapped memory, you might also want to cover munmap and
    >such.
    >
    >You just call register_buf() whenever you create an array, a structure or
    >such. Its address, length and element size would be stored, so that you
    >can query for a buffer at any time, and perhaps decide, based on element
    >size, if its suitable for the operation you are about to perform (so that
    >when you have a number of buffers inside an array, and you only added the
    >array to implement index range checking, but forgot to add single buffers,
    >your code would not overwrite other elements when modifying one, but
    >rather bail out because of element size mismatch).
    >
    >The approach is not perfect, but can be quite helpful.
    >
    >--
    >------------------------- bash$ :(){ :|:&};: --
    > Michal Zalewski * [http://lcamtuf.coredump.cx]
    > Did you know that clones never use mirrors?
    >--------------------------- 2003-01-28 00:41 --

    Thank you Michal. I will try it :) Indirectly helping everyone !!

    - Brandon Erhart



    Relevant Pages

    • Re: safe strcpy()?
      ... sizes of buffers or other objects. ... No. C is a fairly low-level language. ... For dynamically allocated memory, ... when you have a number of buffers inside an array, ...
      (SecProg)
    • Re: Garbage Collection Issues in long-standing services
      ... The problem with sockets is the unmanaged memory buffers used by the ... (probably a byte array) ... The result is that, depending of the number of buffers, ... > reference between CS and AP, so I don't explicitly set each reference to ...
      (microsoft.public.dotnet.languages.csharp)
    • Re: Comparing byte arrays
      ... *per byte array* you end up with an extra 6K *in total*. ... Work through the example - you only end up with 4 times as much memory ... You'd either have to loop on each stream to get a full ... buffer, then compare the buffers, or manage two partial buffers, ...
      (microsoft.public.dotnet.general)
    • Re: Vector length in bytes
      ... An array of pointers is likely to be much smaller than the buffers it points to, but that would be the size of the array. ... The buffers OTOH are probably what you want transmit, but if you used a general memory counting algorithm, you'd likely have the size of the array of pointers included. ...
      (comp.lang.java.programmer)
    • Re: Garbage Collection Issues in long-standing services
      ... If your buffers are that small why does your working set grows to ... the pinned array should get unpinned or ... > and remove the reference to my wrapper socket class, ... > class that my wrapper socket class references that contains an ArrayList ...
      (microsoft.public.dotnet.languages.csharp)