RejectedSoftware Forums

Sign up

Task Memory Usage

I just now spotted this website while chatting: http://bitcoinity.org/markets/mtgox/USD
This is a realtime charting website for BTC. It seems to use EventSource/Server Sent Events to push new transactions to all connected clients. Now, currently there are roughly 17000 clients connected and I was asking myself two things:

  1. How easily could we integrate Server Sent Events in the current version of Vibe.d? My guess is that one could use it already using the HttpServerResponse, it doesn't offer a nice API AFAIK though.
  2. How much memory does a Task/Fiber (eg. of libev) use and how many fibers are practically usable?

Greets,
bossfong

Re: Task Memory Usage

Am 27.11.2013 18:30, schrieb Matthew Fong:

I just now spotted this website while chatting: http://bitcoinity.org/markets/mtgox/USD
This is a realtime charting website for BTC. It seems to use EventSource/Server Sent Events to push new transactions to all connected clients. Now, currently there are roughly 17000 clients connected and I was asking myself two things:

  1. How easily could we integrate Server Sent Events in the current version of Vibe.d? My guess is that one could use it already using the HttpServerResponse, it doesn't offer a nice API AFAIK though.

It looks like not much is needed to implement it - just setting
HTTPServerResponse.contentType = "text/event-stream"; and using
HTTPServerResponse.bodyWriter to write successive events, right?

  1. How much memory does a Task/Fiber (eg. of libev) use and how many fibers are practically usable?

A fiber uses a minimum of a single memory page (typically 4k) of
reserved memory and can then scale up to the size set using
setTaskStackSize (16k by default). It will always consume the full
stack size in virtual address space though, so a 64-bit system should be
used.

The 17k connections would thus result in a minimum amount of about 66MB
used for fibers and about the same amount on top for handling the HTTP
request. There is also some additional overhead for libevent and the
message queue that each task has (this should probably rather be created
lazily, but currently isn't). But all in all, everything should fit well
inside sane boundaries.

Re: Task Memory Usage

On Wed, 27 Nov 2013 19:19:15 +0100, Sönke Ludwig wrote:

Am 27.11.2013 18:30, schrieb Matthew Fong:

I just now spotted this website while chatting: http://bitcoinity.org/markets/mtgox/USD
This is a realtime charting website for BTC. It seems to use EventSource/Server Sent Events to push new transactions to all connected clients. Now, currently there are roughly 17000 clients connected and I was asking myself two things:

  1. How easily could we integrate Server Sent Events in the current version of Vibe.d? My guess is that one could use it already using the HttpServerResponse, it doesn't offer a nice API AFAIK though.

It looks like not much is needed to implement it - just setting
HTTPServerResponse.contentType = "text/event-stream"; and using
HTTPServerResponse.bodyWriter to write successive events, right?

  1. How much memory does a Task/Fiber (eg. of libev) use and how many fibers are practically usable?

A fiber uses a minimum of a single memory page (typically 4k) of
reserved memory and can then scale up to the size set using
setTaskStackSize (16k by default). It will always consume the full
stack size in virtual address space though, so a 64-bit system should be
used.

I'v just read that nginx seems to use less memory per connection, quotes from here http://www.aosabook.org/en/nginx.html :

on an idle keepalive connection, nginx spends just 550 bytes of memory. A possible optimization for future releases of nginx would be to reuse and share memory buffers for long-lived connections.

So I wonder, is it possible to optimize and further reduce a fiber's memory usage? or use some share memory buffers in thread local?

The 17k connections would thus result in a minimum amount of about 66MB
used for fibers and about the same amount on top for handling the HTTP
request. There is also some additional overhead for libevent and the
message queue that each task has (this should probably rather be created
lazily, but currently isn't). But all in all, everything should fit well
inside sane boundaries.

Re: Task Memory Usage

Am 29.11.2013 09:19, schrieb zhaopuming:

On Wed, 27 Nov 2013 19:19:15 +0100, Sönke Ludwig wrote:

Am 27.11.2013 18:30, schrieb Matthew Fong:

I just now spotted this website while chatting: http://bitcoinity.org/markets/mtgox/USD
This is a realtime charting website for BTC. It seems to use EventSource/Server Sent Events to push new transactions to all connected clients. Now, currently there are roughly 17000 clients connected and I was asking myself two things:

  1. How easily could we integrate Server Sent Events in the current version of Vibe.d? My guess is that one could use it already using the HttpServerResponse, it doesn't offer a nice API AFAIK though.

It looks like not much is needed to implement it - just setting
HTTPServerResponse.contentType = "text/event-stream"; and using
HTTPServerResponse.bodyWriter to write successive events, right?

  1. How much memory does a Task/Fiber (eg. of libev) use and how many fibers are practically usable?

A fiber uses a minimum of a single memory page (typically 4k) of
reserved memory and can then scale up to the size set using
setTaskStackSize (16k by default). It will always consume the full
stack size in virtual address space though, so a 64-bit system should be
used.

I'v just read that nginx seems to use less memory per connection, quotes from here http://www.aosabook.org/en/nginx.html :

on an idle keepalive connection, nginx spends just 550 bytes of memory. A possible optimization for future releases of nginx would be to reuse and share memory buffers for long-lived connections.

So I wonder, is it possible to optimize and further reduce a fiber's memory usage? or use some share memory buffers in thread local?

It is possible to cut a bit on parts like the message queue and possibly
in the libevent driver on the per connection costs, but a single page
per fiber is the minimum possible amount (well, in theory it would be
possible to store the fiber's stack in a different location while it is
not active, possibly using compression, but that would seriously impair
performance and is probably not really worth the trade-off given the
typical amount of RAM of a server)

Buffers for request handling and other parts are already reused
implicitly because of the free list/pool allocators that are used, so
there shouldn't be much to gain there.

Re: Task Memory Usage

On Fri, 29 Nov 2013 22:09:47 +0100, Sönke Ludwig wrote:

Am 29.11.2013 09:19, schrieb zhaopuming:

On Wed, 27 Nov 2013 19:19:15 +0100, Sönke Ludwig wrote:

Am 27.11.2013 18:30, schrieb Matthew Fong:

I just now spotted this website while chatting: http://bitcoinity.org/markets/mtgox/USD
This is a realtime charting website for BTC. It seems to use EventSource/Server Sent Events to push new transactions to all connected clients. Now, currently there are roughly 17000 clients connected and I was asking myself two things:

  1. How easily could we integrate Server Sent Events in the current version of Vibe.d? My guess is that one could use it already using the HttpServerResponse, it doesn't offer a nice API AFAIK though.

It looks like not much is needed to implement it - just setting
HTTPServerResponse.contentType = "text/event-stream"; and using
HTTPServerResponse.bodyWriter to write successive events, right?

  1. How much memory does a Task/Fiber (eg. of libev) use and how many fibers are practically usable?

A fiber uses a minimum of a single memory page (typically 4k) of
reserved memory and can then scale up to the size set using
setTaskStackSize (16k by default). It will always consume the full
stack size in virtual address space though, so a 64-bit system should be
used.

I'v just read that nginx seems to use less memory per connection, quotes from here http://www.aosabook.org/en/nginx.html :

on an idle keepalive connection, nginx spends just 550 bytes of memory. A possible optimization for future releases of nginx would be to reuse and share memory buffers for long-lived connections.

So I wonder, is it possible to optimize and further reduce a fiber's memory usage? or use some share memory buffers in thread local?

It is possible to cut a bit on parts like the message queue and possibly
in the libevent driver on the per connection costs, but a single page
per fiber is the minimum possible amount (well, in theory it would be
possible to store the fiber's stack in a different location while it is
not active, possibly using compression, but that would seriously impair
performance and is probably not really worth the trade-off given the
typical amount of RAM of a server)

Thanks for the clarification. So the 4k minimum was due to fiber's stack.
I was just wondering why nginx could use less than a single page,
it might be using a different approach, which I have no idea of.

Buffers for request handling and other parts are already reused
implicitly because of the free list/pool allocators that are used, so
there shouldn't be much to gain there.

OK. So this means we are already reaching a very optimized situation regarding memory usage :)

Re: Task Memory Usage

On 2013-11-30 02:46:25 +0000, zhaopuming said:

Thanks for the clarification. So the 4k minimum was due to fiber's stack.

I was just wondering why nginx could use less than a single page,

it might be using a different approach, which I have no idea of.

Nginx doesn't use fibers. I believe it just uses callbacks like node.
These can use much less memory than callbacks at the expensive of being
annoying to program.