Live data from Hacker News

How do I deal with memory leaks? (2022)

stroustrup.com

51–60 of 76 posts

Re: How do I deal with memory leaks? (2022)

#51
post #5

Good arguments. But for some reason there are still strange people, who prefer calling malloc/free (or new/delete or something similar) manually. Some of them even invent languages with manual-only memory management (like Zig or Odin).

One reason is that c++ still hasn't gotten 'trivial relocatability' right - i.e being able to memcpy/memmove and not have to call constructors/destructors when growing your vector class.

std::is_trivially_copyable says hi

Re: How do I deal with memory leaks? (2022)

#52
post #21

Earlier quoted context omitted.

I think it's a reasonable price to have your own containers (vector/unique_ptr replacements), if you wish to use a non-standard approach for memory allocation. Many people do this, like Qt with QVector. But do you really need arenas? Does doing allocations in a traditional way creates a bottleneck in your specific use-case? Or you just want to justify broad manual memory management (with its bugs and secure vulnerabi…

Respectfully, you do not seem to understand this topic well. If the C++ standard library design abstracted memory allocation correctly, you’d still be able to use containers and algorithms and not even notice that their allocation strategy uses the heap, stack, a bump allocator, a pool, etc

Would that even work? If you use std::vector within an arena, you allocate twice as much memory as you need to, since the old arrays can't be deallocated. You might want to use std::deque instead. Memory management is not independent from data structures - std allocators smell to me like another failed experiment, like auto_ptr mentioned in another comment.

Also, with allocators you can replace new and delete, but you can't implement anything that doesn't fit into the new/delete paradigm, like any allocation strategy that requires moving objects.

Re: How do I deal with memory leaks? (2022)

#53
post #21

Earlier quoted context omitted.

Respectfully, you do not seem to understand this topic well. If the C++ standard library design abstracted memory allocation correctly, you’d still be able to use containers and algorithms and not even notice that their allocation strategy uses the heap, stack, a bump allocator, a pool, etc

I understand how C++ standard containers are designed. They are designed in such a way, so that they don't store a pointer to an allocator instance inside. This allows to save memory in the most cases (where the standard allocator is used). Overriding an allocator is possible, but only with some another global allocator (via a template argument), with no possibility to specify a per-object allocator. As I know in new…

Each container stores an allocator instance inside, not a pointer to one. If you need shared state, it's up to you to make each allocator instance contain a pointer to the shared state.

Re: How do I deal with memory leaks? (2022)

#54
post #33

Earlier quoted context omitted.

All of this is false. 1) An allocated memory chunk cannot outlive its arena (leaks are impossible). You probably mean a stale reference? The arena is put at such a level in the memory hierarchy that this bug becomes impossible. The bug here would be that the allocation was done in the wrong arena. In C this would be avoided by putting temporary arenas in a local function scope by passing them as parameters. Fool proo…

1) In practice, this is not true, especially if you implement unwinding in your arena. You probably don't want to have an Arena in main, and you do all of your allocations from there, for example. That "just" leaks everything. Here's a classic Arena-with-rewind bug: { Arena a; avec v(a); { RewindMark rm(a); v.push(1); v.push(1); // Trigger resize } v[2] // Oh no! The underlying data array has been deallocated }

Thanks. This is a good illustration of how data structures aren't cleanly separable from memory management strategies.

Re: How do I deal with memory leaks? (2022)

#55
post #44

Earlier quoted context omitted.

Would you say Rust is more complicated than C++, or just harder to write? I think that complication a la C++ where there are too many features for the language's own good is a different problem than being a clean language but with higher order features that require a bit more, I don't know, focus?

I think there are certainly different complications in Rust than C++. The RAII can be roughly the same in the naive sense, but there's having to worry about Send and Sync and Pin and fighting with the borrow checker and all that fun stuff. Gauging how "complicated" a language is somewhat subjective, so it's kind of hard for me to give a straightforward answer. I think it's certainly easier to be (some definition of)…

> having to worry about Send and Sync and Pin and fighting with the borrow checker and all that fun stuff.

To be fair, the alternative to having to worry about Send/Sync/Pin is not "not worrying about Send/Sync/Pin". It's having to worry about correctly enforcing the constraints they describe on your own, without any kind of mechanical help. E.g., not moving data to another thread that shouldn't be and not accessing data from multiple threads that shouldn't be. This stuff is intrinsic.

In this sense the Rust mental model is simpler, because failing to uphold these constraints is no longer "your fault", it's Rust's fault.

Re: How do I deal with memory leaks? (2022)

#56
post #19

Earlier quoted context omitted.

I actually don't know (at least I don't think I do) the full story here, can you elaborate?

auto_ptr was so misdesigned, they erased it from the language in a later standard. The problem was that the assignment operator “T x = y;” is supposed to have copy semantics, but auto_ptr gave it move semantics by overwriting the source to destroy that reference. This broke all sorts of code that rightfully assumed assignment is done by copying. Therefore all kinda of algorithms like sort broke, as well as resource m…

Holy shit, I didn't know that.

Circa 2004 I was in college and took a C++ class. I spent an entire week trying to get my final project working and couldn't for the life of me figure out what was wrong. It was only a few hundred lines and was like an employee record type demo. I spent about 3 hours one on one with the professor trying to figure it out. I remember that removing the auto_ptr stuff and using regular pointers would make it work (because the problem has to be with the pointer stuff right?), but part of the requirements was that I had to use auto_ptr because it was safer or whatever.

We tried compiling it on different systems and nothing would get it to work. He ended up giving me a C on the project admitting "it should work, but that doesn't cut it in the business world" or something to that effect which really pissed me off.

I just had a chat with GPT about this and that was almost certainly what was causing my program to segfault.

std::auto_ptr a(new int(5));

std::auto_ptr b = a; // a becomes null

Wild.

Re: How do I deal with memory leaks? (2022)

#57
post #44

Earlier quoted context omitted.

Would you say Rust is more complicated than C++, or just harder to write? I think that complication a la C++ where there are too many features for the language's own good is a different problem than being a clean language but with higher order features that require a bit more, I don't know, focus?

I think there are certainly different complications in Rust than C++. The RAII can be roughly the same in the naive sense, but there's having to worry about Send and Sync and Pin and fighting with the borrow checker and all that fun stuff. Gauging how "complicated" a language is somewhat subjective, so it's kind of hard for me to give a straightforward answer. I think it's certainly easier to be (some definition of)…

> I do sometimes miss how utterly simple and dumb C is

You can make an argument that the K&R C "is" an utterly simple and dumb language, but if it was it's long gone and it's also irrelevant for modern hardware.

Today because C only has a single kind of reference, the raw pointer, that means if you want references at all (which you do) you need pointers, and to get decent performance from this sort of language you need pointer provenance, and so now all your reference types involve understanding compiler internals minutiae. Bad luck though, those aren't specified in the C language standard, that's a TODO item from the turn of the century. The committee agrees that C pointers do have provenance but declines to explain how that could possibly work.

Re: How do I deal with memory leaks? (2022)

#59
post #44

Earlier quoted context omitted.

I think there are certainly different complications in Rust than C++. The RAII can be roughly the same in the naive sense, but there's having to worry about Send and Sync and Pin and fighting with the borrow checker and all that fun stuff. Gauging how "complicated" a language is somewhat subjective, so it's kind of hard for me to give a straightforward answer. I think it's certainly easier to be (some definition of)…

> have to understand everything, because if you don't do it in the "Rust way", it often won't compile I confess I haven't dug into it much yet, but this reminds me of how Haskell was. By the time you got a program to compile your project was more or less done.

Rust is similar. I don't have a link handy, but I've read a few articles noting experience with programming in rust where a program that compiles works. Provided the logic is correct, of course.

Re: How do I deal with memory leaks? (2022)

#60
post #44

Earlier quoted context omitted.

I think there are certainly different complications in Rust than C++. The RAII can be roughly the same in the naive sense, but there's having to worry about Send and Sync and Pin and fighting with the borrow checker and all that fun stuff. Gauging how "complicated" a language is somewhat subjective, so it's kind of hard for me to give a straightforward answer. I think it's certainly easier to be (some definition of)…

> have to understand everything, because if you don't do it in the "Rust way", it often won't compile I confess I haven't dug into it much yet, but this reminds me of how Haskell was. By the time you got a program to compile your project was more or less done.

In some senses I actually find Rust a bit harder than Haskell. With Haskell the types are immutable and as such they can be happily shared everywhere. That required basically no rewiring in my brain.

With Rust, I had to get used to single ownership or explicit cloning. There's an argument that this is "better", but I found it a bit harder to learn.

Post reply on HN