Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[JENKINS-39150] expose diagnostics across all the channels #120

Closed
wants to merge 8 commits into from

Conversation

kohsuke
Copy link
Member

@kohsuke kohsuke commented Oct 20, 2016

To be used by support-core, we need to be able to enumerate all active channels. We do this via WeakHashMap so that references get automatically garbage collected.

Unclosed channel will remain in memory forever, which also helps us find those leaks.

@reviewbybees

To be used by support-core, we need to be able to enumerate all active
channels. We do this via WeakHashMap so that references get
automatically garbage collected.

Unclosed channel will remain in memory forever, which also helps us find
those leaks.
Copy link
Member

@oleg-nenashev oleg-nenashev left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🐛 for potential concurrency issues

* When a transport is functioning correctly, {@link #commandsSent} of one side
* and {@link #commandsReceived} of the other side should closely match.
*/
private int commandsReceived;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should be AtomicLong 🐜

@@ -494,6 +519,8 @@ protected Channel(ChannelBuilder settings, CommandTransport transport) throws IO

transport.setup(this, new CommandReceiver() {
public void handle(Command cmd) {
commandsReceived++;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🐛 since handling may potentially happen in different threads

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No, commands are received in serial order, so it is not possible for this to happen in different threads that do not have memory barrier established.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Perhaps you meant reader reading incorrect value when write to normal non-volatile long variable can go in two 32bit writes (JLS). I've added volatile.

Copy link
Member

@oleg-nenashev oleg-nenashev Oct 21, 2016

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes. It's what I've meant. Thanks for addressing it

@@ -1149,6 +1178,20 @@ public void dumpPerformanceCounters(PrintWriter w) throws IOException {
}

/**
* Print the diagnostic information.
*/
public void dumpDiagnostics(PrintWriter w) throws IOException {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🐛 Unsynchronized access to pendingCalls container

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hashtable is synchronized, but deprecated. Conflicts with #109

@@ -163,4 +165,14 @@ public T call() throws RuntimeException {
return t;
}
}

public void testDiagnostics() throws Exception {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice2have: reference the issue

@ghost
Copy link

ghost commented Oct 20, 2016

This pull request originates from a CloudBees employee. At CloudBees, we require that all pull requests be reviewed by other CloudBees employees before we seek to have the change accepted. If you want to learn more about our process please see this explanation.

* Timestamp of the last {@link Command} object sent/received, in
* {@link System#currentTimeMillis()} format.
*/
private long lastCommandSent, lastCommandReceived;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

NIT: not that important because private, I guess, but maybe suffix with At like createdAt to distinguish units here? as for example commandsSent is the number of commands received, when lastCommandSent is actually a date/timestamp.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also, isn't lastCommandReceived redundant with lastHeard?

private volatile long lastHeard;

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You are right! I removed the duplication

... and see how they can be interpreted to aid diagnostics
JLS (http://docs.oracle.com/javase/specs/jls/se7/html/jls-17.html#jls-17.7) states
that a write  to non-volatile long variable can go in 32bit batch, so
without it, read could retrieve a completely bogus value.

There's no risk of writer contention here because that is serialized by
the context in which it gets invoked.
Copy link
Member

@stephenc stephenc left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🐛

* Used for diagnostics.
*/
public static void dumpDiagnosticsForAll(PrintWriter w) throws IOException {
for (Ref ref : ACTIVE_CHANNELS.values()) {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it would be better to use ACTIVE_CHANNELS.values().toArray(new Ref[0]) so that we do not need the lock. You risk CME iterating, e.g. see the javadoc for Collections.synchronizedMap which explicitly states:

It is imperative that the user manually synchronize on the returned map when iterating over any of its collection views

The toArray will give you the shortest lock time

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

resolved

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

makes sense

@kohsuke
Copy link
Member Author

kohsuke commented Oct 21, 2016

All review comments addressed

@stephenc
Copy link
Member

🐝

@oleg-nenashev
Copy link
Member

Would be great to address the last comment from @stephenc and to add @since definitions to Javadoc, but generally it's ready to go. 🐝

@oleg-nenashev
Copy link
Member

@kohsuke By the way, do you need backporting to stable-2.x? Diagnosability improvements IMHO qualify if they are pretty small and get soaked enough.

@kohsuke
Copy link
Member Author

kohsuke commented Oct 21, 2016

Crap, I meant to target this to stable-2.x

@kohsuke
Copy link
Member Author

kohsuke commented Oct 21, 2016

Taken over by #122. See you there.

@kohsuke kohsuke closed this Oct 21, 2016
@kohsuke kohsuke deleted the JENKINS-39150 branch October 21, 2016 13:49
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants