Live data from Hacker News

Dyad: Minimal, portable async networking library for C

github.com

31–40 of 47 posts

Re: Dyad: Minimal, portable async networking library for C

#31

Earlier quoted context omitted.

How are you supposed to do socket programming without select?

I think the only viable (in terms of portability) alternative is poll. There's a pretty good comparison of the two written by the author of cURL [0]. But essentially it's the same speed and doesn't have a hard-coded FD limit, but it runs on fewer platforms. [0] http://daniel.haxx.se/docs/poll-vs-select.html

I like epoll over poll because you don't need a central point in your application that knows about all FDs, each component can manage it's own FDs registration with the OS.

Re: Dyad: Minimal, portable async networking library for C

#32
post #19
post #17

Earlier quoted context omitted.

"Context switching is expensive. My rule of thumb is that it'll cost you about 30µs of CPU overhead. This seems to be a good worst-case approximation. Applications that create too many threads that are constantly fighting for CPU time (such as Apache's HTTPd or many Java applications) can waste considerable amounts of CPU cycles just to switch back and forth between different threads." http://blog.tsunanet.net/2010/1…

I don't trust those measurements. They never fully explored what is due to cache effects and what is due to context switching. You'd have heavy cache effects if you switched data between client contexts after select returns, too. So just because spinning on a futex show a max 30us wasted CPU doesn't mean you won't waste that with select as well. Also in case of an IO bound thread, they are not just spinning on a fute…

In those cases I like the coroutines/user-space-threading. It gives you the reduced cost of having a single or a few threads without the heavy toll of callbacks.

Re: Dyad: Minimal, portable async networking library for C

#33
post #16
post #15

Earlier quoted context omitted.

You need select or a select-like function to know which sockets are readable/writable without tying up one thread per socket

I know what select/epoll and friends are for. What's wrong with tying up one thread per socket?

Probably nothing. {taking aside performance issues when you run into the thousands of parallel connections}

I personally prefer the old-school async approach, because there you are forced to explicitly manage your connections' state, and the application/process-wide data access is inherently race-condition free. I'd use this as far as possible.

If you let your OS schedule threads, obviously you have to be careful that shared data is correctly locked/only atomically changed, but you get parallelism (especially for CPU heavy tasks) for free. If you are used to do these chores (I'm not), perfect! And your connections state (or the state of required computations) can be arbitrarily complex (ugly?) and still quite elegantly hidden in your threads's stack.

So, I don't see that one approach is better than the other. For me the extremes are probably clear in favor of one or the other, with a large grey area in between.

Re: Dyad: Minimal, portable async networking library for C

#35

Earlier quoted context omitted.

How are you supposed to do socket programming without select?

poll is fairly portable, but still has scaling problems. To get beyond scaling problems, you usually need something OS-specific, such as epoll (Linux), kqueue (BSDs of some kind), etc. One of the things I'd expect of a cross-platform networking library would be to use the best available abstraction, especially on major platforms such as linux, and perhaps fall back to select on odd platforms. Of course, your docs nee…

Plus kqueue gives you ways to wait for other events (timeouts, signals etc), and epoll+other linux specific calls does too. This simplifies your code a lot.

Re: Dyad: Minimal, portable async networking library for C

#36
post #32
post #19

Earlier quoted context omitted.

I don't trust those measurements. They never fully explored what is due to cache effects and what is due to context switching. You'd have heavy cache effects if you switched data between client contexts after select returns, too. So just because spinning on a futex show a max 30us wasted CPU doesn't mean you won't waste that with select as well. Also in case of an IO bound thread, they are not just spinning on a fute…

In those cases I like the coroutines/user-space-threading. It gives you the reduced cost of having a single or a few threads without the heavy toll of callbacks.

Just to expand on the timing and cost argument:

When you have 10,000 tasks and about 8 cores (give or take a few) the number of context switches is very large. Switching in the kernel will happen mostly in the system call boundary of blocking IOs and require the scheduler to make a decision on what thread to wake up next and then change the running process.

This can be seen in function context_switch inhttps://github.com/torvalds/linux/blob/master/kernel/sched/c... without the arch dependent components and can hardly be compared in complexity and effort to switching between 4 and 8 registers in user-space.

The above still doesn't include any changes to the TLB and memory protection tables as I assume the OS optimized those away when it switched between two threads of the same program. An optimization I'm not sure that happens normally.

Re: Dyad: Minimal, portable async networking library for C

#37
Is it just me that wants to have complete control over stuff? I mean if you really have the need to use a library like libevent you most likely know why and could do your own handling rather easily.

I'm not saying there's not a need for libraries like libevent, but IMO it's not needed for most applications. I might be biased because I want complete control and know what happens, I think that's important. I don't want to use a library before I know what happens in the "background". When I know that and know what I need, only then it might be appropriate to use a library.

Re: Dyad: Minimal, portable async networking library for C

#38
post #37

Is it just me that wants to have complete control over stuff? I mean if you really have the need to use a library like libevent you most likely know why and could do your own handling rather easily. I'm not saying there's not a need for libraries like libevent, but IMO it's not needed for most applications. I might be biased because I want complete control and know what happens, I think that's important. I don't want…

I'm curious what you mean by "complete control"? Does that mean less abstraction? Or do you want to avoid inversion of control? That is, you want to avoid using callback-based libraries?

Re: Dyad: Minimal, portable async networking library for C

#39
post #37

Is it just me that wants to have complete control over stuff? I mean if you really have the need to use a library like libevent you most likely know why and could do your own handling rather easily. I'm not saying there's not a need for libraries like libevent, but IMO it's not needed for most applications. I might be biased because I want complete control and know what happens, I think that's important. I don't want…

For me, libevent just provides the boiler plate but I'd be writing too often for fd registration and timeouts.

I could do it myself, but it would just end up looking more and more like libevent each time I did it.

Re: Dyad: Minimal, portable async networking library for C

#40

Earlier quoted context omitted.

How are you supposed to do socket programming without select?

I think the only viable (in terms of portability) alternative is poll. There's a pretty good comparison of the two written by the author of cURL [0]. But essentially it's the same speed and doesn't have a hard-coded FD limit, but it runs on fewer platforms. [0] http://daniel.haxx.se/docs/poll-vs-select.html

I sent patches in for curl about 10 years ago to switch from select to poll to get around the 1024 FD limit (which was a problem for multi-threaded servers that handled many sockets).
Post reply on HN