Hacker News new | ask | show | jobs
by AnimalMuppet 2 days ago
In general, you're right.

The exception that I could think of is a "dump memory" function. You take a pointer to something (who cares what it is), and print out the bytes there. That I could see taking a void*.

But that's a really limited case. In general, yes, you do not want to be dealing with blobs of memory as arguments. You want to be dealing with things that are known to be the right kind of thing as arguments.

1 comments

But parent is right, you have to cast it anyways before reading from it, so might as well take the right type from the beginning.
Anything can be aliased by char, unsigned char, std::byte (as well as signed char in C), and usually uint8_t == unsigned char, thus by extension any valid void pointer can be cast to u8*.

Thus void*+size is usually the right type if ones only care for the memory representation of an object (cstring functions like memcpy, etc.)

Most likely one would have both overloads:

    void Hexdump(const void *p, size_t size); // (1)
    
    template<typename T>  // (2)
    inline void Hexdump(const T &obj) {
         return Hexdump(&obj, sizeof(T));
    }
With (2) being a wrapper to (1) that compilers will almost always inline, avoiding monomorphization costs (and (2) can also accept rvalues as argument).

(1) could also take std::span<const u8>, but (void*, size) is the more common idiom, more convenient to use and to read , as it is unambiguous which overload it is.