Skip to content

Instantly share code, notes, and snippets.

@Olegas
Last active August 29, 2015 14:22
Show Gist options
  • Select an option

  • Save Olegas/a6a03c65ed533e89a9a9 to your computer and use it in GitHub Desktop.

Select an option

Save Olegas/a6a03c65ed533e89a9a9 to your computer and use it in GitHub Desktop.
Race condition in cluster RR scheduling

Starting from createServer: https://github.com/nodejs/io.js/blob/master/lib/net.js#L884

Adding subscription to ‘connection’ event: https://github.com/nodejs/io.js/blob/master/lib/net.js#L1066

When listen is called, we are going here: https://github.com/nodejs/io.js/blob/master/lib/net.js#L1353

Cause’ we are worker, we’ll request a server: https://github.com/nodejs/io.js/blob/master/lib/net.js#L1254

_getServer is sending a message to master https://github.com/nodejs/io.js/blob/master/lib/cluster.js#L542

Master accepts and handles server creation here: https://github.com/nodejs/io.js/blob/master/lib/cluster.js#L437

It creates a RoundRobinHandle

Handle itself creates a server (It is in master process!) https://github.com/nodejs/io.js/blob/master/lib/cluster.js#L104, and starts listening.

When connection is received on this server, it is distributed to some worker: https://github.com/nodejs/io.js/blob/master/lib/cluster.js#L116

Requesting workers is added to newly created RoundRobinHandle. On addition, we’ll wait server listening and then send a reply.

Reply is sent here: https://github.com/nodejs/io.js/blob/master/lib/cluster.js#L472

Handle is received https://github.com/nodejs/io.js/blob/master/lib/cluster.js#L545 Worker realize there are no handle and create a faux-one.

The server is successfully created at this point.

In a master process, ‘listening’ event is emitted on worker and we creating connection to it's server: https://github.com/nodejs/io.js/blob/master/test/parallel/test-cluster-worker-wait-server-close.js#L23 Interesting moment: technicall, master connects to itself now!

Then connection is established client (master's client side) fires connection handler, which, in turn, disconnects a worker: https://github.com/nodejs/io.js/blob/master/test/parallel/test-cluster-worker-wait-server-close.js#L25 (remember, there is no setTimeout now). This will send a disconnect message to worker.

Lets’ go back to the point where server is accepting connection (it is in master as of round robin scheduling policy). It leads to a handoff call https://github.com/nodejs/io.js/blob/master/lib/cluster.js#L169

It will send a newconn message to worker using process.send https://github.com/nodejs/io.js/blob/master/lib/cluster.js#L180 and wait for an answer from it.

Then disconnect is received, worker closes all it’s handles and waits for close is finished. It triggers immediately and worker is doing process.disconnect();

NO DISCONNECT EVENT AT MASTER!!!! WHY?????

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment