Live data from Hacker News

fork() can fail

rachelbythebay.com

251–260 of 320 posts

Re: fork() can fail

#251
post #228

Earlier quoted context omitted.

Indeed. I like using a VERIFY macro: #ifdef NDEBUG # define VERIFY(x) ((x), 1) #else # define VERIFY(x) assert((x)) #endif Then you can write VERIFY(pthread_mutex_unlock(&lock) == 0); You don't need, however, to consider the possibility of your program continuing to run after pthread_mutex_unlock fails.

Huh? You do realize that the standard assert() macro already is compiled out if NDEBUG is defined, right? Your code could just as well be written as assert(pthread_mutex_unlock(&lock) == 0); which of course has the added benefit of not inventing anything new, i.e. being standard and immediately understood by anyone who knows the language and its libraries reasonably well.

Replying to self since I can't edit: d'oh. Yes, I totally mis-read the original code. I should have relized why the other comment questioning this practice had been down-voted, heh.

Of course not unlocking the mutex in non-debug builds would be a problem.

Thanks, and sorry.

Re: fork() can fail

#252
post #131

Earlier quoted context omitted.

I could argue, however, that in this particular case, it's the user's fault for failing to understand the full and defined behavior of fork() in addition to failing to understand the full and defined behavior of other functions, ...say, kill(). It's just as wrong to feed kill() -1 as it would be to feed it -48585 or "babdkd" (unless that is explicitly your intention). A simple sanity check of if [ "${pid} > "0" ]; is…

Fault is not a rivalrous good. It's the user's fault, and it's the API creator's fault. Is there a reason fork can't be changed to just crash the program on failure? Are situations where a program usefully does something other than crash on fork failure, more or less common than situations where a program fails in the way described in the article?

That should be up to the programmer to decide. If fork() fails, it's almost always a transient situation that can be recovered from by spinning until fork() succeeds. Or one could have jobs doing useful things that can finish up, state saved, etc, for when the process is re-run. Just dropping everything onto the floor is usually the worst option.

Re: fork() can fail

#253
post #213
post #209

When I was young and really didn't understand Unix, my friend and were summer students at NBS (now NIST), and one fine afternoon we wondered what would happen if you ran fork() forever. We didn't know, so we wrote the program and ran it. This was on a PDP-11/45 running v6 or v7 Unix. The printing console (some DECWriter 133 something or other) started burping and spewing stuff about fork failing and other bad things,…

> ...a minute or two later one of the folks who had 'root' ran into the machine room with a panic-stricken look because the system had mostly just locked up. It's kind of weird that, while root has always had e.g. 5% reserved disk space on the rootfs for emergencies, one thing no Unix has ever done is enforce a 5% CPU reservation for root so administrators can "talk over" a cascading failure. I think this is possible…

In theory root could nice all other processes.

Re: fork() can fail

#254

Earlier quoted context omitted.

Exceptions disrupt the program flow at any place, including constructors and destructors. It's not easy to guarantee that you deallocate on destructors exactly the resources that were allocated at the constructor when both of them can stop their execution at any time. Finally clauses are technically enough, but each allocation needs the same level of attention non-memory resources (e.g. connections, files) get on oth…

I'm going to answer for C++, since as far as I know it's the only major language with exceptions and RAII. Correct me if I'm misunderstanding your post. > It's not easy to guarantee that you deallocate on destructors exactly the resources that were allocated at the constructor when both of them can stop their execution at any time. I disagree; let's take this one case at time to keep it simple: 1. Destructors: within…

For a long time, Java suffered from issues when throwing an exception during stack unwind. The second exception is the one that is subsequently propagated, and in modern Java the original exception is available and printed in any stack trace.

It's still not particularly pleasant, but it is at least survivable and no information is lost.

Re: fork() can fail

#255
post #232

Earlier quoted context omitted.

'try' and 'finally' are in C now? Someone should warn the GCC guys they're behind the times. Also, getcwd has a size parameter these days, and of course you want to check if the getcwd actually worked.

The OP said: wrap in a macro having similar properties (ala pseudo code).

Good luck writing a macro in C to express language functionality for which you don't have the primitives. It's not exactly lisp. Think of C macros as a way to save you some typing and lisp macros as a way to extend the language.

Re: fork() can fail

#256
post #233
post #213

Earlier quoted context omitted.

> ...a minute or two later one of the folks who had 'root' ran into the machine room with a panic-stricken look because the system had mostly just locked up. It's kind of weird that, while root has always had e.g. 5% reserved disk space on the rootfs for emergencies, one thing no Unix has ever done is enforce a 5% CPU reservation for root so administrators can "talk over" a cascading failure. I think this is possible…

If you care about such things the normal method is to have a backup ssh running on a different port with realtime priority , it is not used at any other time except when some process had gone runaway and you can't do anything else.

I haven't seen this in action. Do you know of a write up describing this?

Re: fork() can fail

#257
post #253
post #213

Earlier quoted context omitted.

> ...a minute or two later one of the folks who had 'root' ran into the machine room with a panic-stricken look because the system had mostly just locked up. It's kind of weird that, while root has always had e.g. 5% reserved disk space on the rootfs for emergencies, one thing no Unix has ever done is enforce a 5% CPU reservation for root so administrators can "talk over" a cascading failure. I think this is possible…

In theory root could nice all other processes.

On Linux, nice is not an absolute priority system.

In the old days, the Amiga operating system did use static absolute priorities for its multi-tasking. This meant that if a task with a priority of 1 wanted to use as much CPU as it wanted, then all tasks with a priority of 0 or below would be completely starved. This meant that you could boost a certain process (like, say, a CD writer) and get close to real-time behaviour. I was certainly writing coaster-free CDs on a much less powerful Amiga than a Linux box that constantly made coasters from buffer under-runs.

Linux, however, has virtual memory and "nice", which complicates matters. A process with a niceness of 19 will still take a small amount of CPU in the presence of another process with a niceness of -20. In the presence of a fork bomb, you may have a very large number of processes. If they all (by some miracle) have a niceness of 19, you still have very little CPU time left for a process with a normal or negative niceness. Infinity multiplied by a small number is still infinity. Real-time priorities are the only thing that will save you here.

You also have the problem of being able to actually change the processes' nicenesses. That requires CPU time, which you no longer have. You would be better off sending a kill signal. You also have a race condition - you obtain (from the OS) a list of processes that are running that you want to renice or kill. By the time you have iterated through each one renicing or killing them, new processes have appeared.

Re: fork() can fail

#258
post #159

And this is why I think Go-lang and its multi-return is the way of the future. In Go you are required to handle errors. If you want them to go away you have to explicitly use an _ and thats really easy to find in the code and shame the person who did it. Nothing fails silently. Nothing fails via primary return. It is such greatness it is hard to express.

> And this is why I think Go-lang and its multi-return is the way of the future.

Using multiple returns for such situations is terrible, especially doing so in the way Go does.

Re: fork() can fail

#259

Out of "-1 as failure return value", and "-1 to signal all possible processes", at least one is a bad idea.

It's the second one. kill() shouldn't have the kill(-1,...) functionality, there should be a separate syscall for this.

Re: fork() can fail

#260
post #158

Yes, fork can fail and we ran into this a few years ago at MemSQL. The problem was that MemSQL would allocate a lot of memory and linux wouldn't allow to fork such a process. A remedy to that is to create a separate process and talk to it via tcp. This small and low on memory consumption process is responsible for fork/exec paradigm.

Why doesn't it use vfork() for fork+exec? AFAIK vfork() doesn't clone the allocated memory of the parent process and is only useful for calling exec immediately after forking. http://linux.die.net/man/2/vfork
Post reply on HN