ProcessHandle returns ambiguous results - java

I've two Java 11 methods that check whether a process for a given PID is running:
public static final boolean isProcessRunning( final long pid ) {
Optional< ProcessHandle > optionalProcess = ProcessHandle.of( pid );
return optionalProcess.isPresent() && optionalProcess.get().isAlive();
}
public static boolean isProcessRunning2( final long pid ) {
return ProcessHandle.allProcesses()
.filter( p -> p.pid() == pid )
.anyMatch( p -> p.isAlive() );
}
When checking multiple PIDs on Linux clients, I'm getting sometimes different results for certain PIDs, where the first implementation always returns true and the second one always false.
Checking some "false positives" with shell command ps -ef | grep <pid> shows that first implementation seems to be wrong, the OS doesn't know about these processes neither.
Assumably the second implementation is always right but seems to be very inefficient.
What's wrong with the first implementation and how can I fix it?

Having a look at the implementation of ProcessHandleImpl.isAlive() (Java 11 version) it seems that this method might return true if the native method isAlive0(pid) returns 0 - which it does "if the start time cannot be determined". The same native method is also used to determine whether to return an empty optional (returns -1) or not (returns 0 or actual start time). ProcessHandle.allProcesses() on the other hand gets all children of pid 0 and then calls getProcessPids0(...) (another native method) to return the pids and start times.
So it seems to be a difference in the native code of the JVM you're using - or one in your OS (depends on what the native code is doing).
To "fix" your first snippet, you could eliminate the "0" start times by using info().startInstant().isPresent():
public static final boolean isProcessRunning( final long pid, final boolean excludeUnsure ) {
Optional< ProcessHandle > optionalProcess = ProcessHandle.of( pid );
if( excludeUnsure ) {
return optionalProcess.map(ph -> ph.info())
.flatMap(info -> info.startInstant())
.isPresent();
} else {
return optionalProcess.map(ph -> ph.isAlive()).orElse(Boolean.FALSE);
}
}

Related

Log line taking 10's of milliseconds

I am seeing very high latencies when invoking java.util.logging.Logger.log() in some instances, in the following code:
private static Object[] NETWORK_LOG_TOKEN = new Object[] {Integer.valueOf(1)};
private final TimeProbe probe_ = new TimeProbe();
public void onTextMessagesReceived(ArrayList<String> msgs_list) {
final long start_ts = probe_.addTs(); // probe A
// Loop through the messages
for (String msg: msgs_list) {
probe_.addTs(); // probe B
log_.log(Level.INFO, "<-- " + msg, NETWORK_LOG_TOKEN);
probe_.addTs(); // probe C
// Do some work on the message ...
probe_.addTs(); // probe D
}
final long end_ts = probe_.addTs(); // probe E
if (end_ts - start_ts >= 50) {
// If the run was slow (>= 50 millis) we print all the recorded timestamps
log_.info(probe_.print("Slow run with " + msgs_list.size() + " msgs: "));
}
probe_.clear();
}
The probe_ is simply an instance of this very basic class:
public class TimeProbe {
final ArrayList<Long> timestamps_ = new ArrayList<>();
final StringBuilder builder_ = new StringBuilder();
public void addTs() {
final long ts = System.currentTimeMillis();
timestamps_.add(ts);
return ts;
}
public String print(String prefix) {
builder_.setLength(0);
builder_.append(prefix);
for (long ts: timestamps_) {
builder_.append(ts);
builder_.append(", ");
}
builder_.append("in millis");
return builder_.toString();
}
public void clear() {
timestamps_.clear();
}
}
And here is the handler that logs the NETWORK_LOG_TOKEN entries:
final FileHandler network_logger = new FileHandler("/home/users/dummy.logs", true);
network_logger2.setFilter(record -> {
final Object[] params = record.getParameters();
// This filter returns true if the params suggest that the record is a network log
// We use Integer.valueOf(1) as our "network token"
return (params != null && params.length > 0 && params[0] == Integer.valueOf(1));
});
In some cases, I am getting the following ouputs (adding labels with probe A,B,C,D,E to make things more clear):
// A B C D B C D E
slow run with 2 msgs: 1616069594883, 1616069594883, 1616069594956, 1616069594957, 1616069594957, 1616069594957, 1616069594957, 1616069594957
Everything takes less than 1ms, except for the line of code between B and C (during the first iteration of the for loop), which takes a whopping 73 milliseconds. This does not occur every time onTextMessagesReceived() is called, but the fact that it does is big problem. I would welcome any ideas explaining where this lack of predictability comes from.
As a side note, I have checked that my disk IO is super low, and no GC pause occurred around this time. I would think my NETWORK_LOG_TOKEN setup is pretty flimsy at best in terms of design, but I still cannot think of reasons why sometimes, this first log line takes forever. Any pointers or suggestions as to what could be happening would be really appreciated :)!
Things to try:
Enable JVM safepoint logs. VM pauses are not always caused by GC.
If you use JDK < 15, disable Biased Locking: -XX:-UseBiasedLocking. There are many synchronized places in JUL framework. In a multithreaded application, this could cause biased lock revocation, which is a common reason for a safepoint pause.
Run async-profiler in the wall-clock mode with .jfr output. Then, using JMC, you'll be able to find what a thread was exactly doing near the given moment of time.
Try putting a log file onto tmpfs to exclude disk latency, or use MemoryHandler instead of FileHandler to check whether file I/O affects pauses at all.
Everything takes less than 1ms, except for the line of code between B and C (during the first iteration of the for loop), which takes a whopping 73 milliseconds. [snip] ...but I still cannot think of reasons why sometimes, this first log line takes forever.
The first log record that is published to the root logger or its handlers will
trigger lazy loading of the root handlers.
If you don't need to publish to the root logger handlers then call log_.setUseParentHandlers(false) when you add your FileHandler. This will make it so your log records don't travel up to the root logger. It also ensures that you are not publishing to other handlers attached to the parent loggers.
You can also load the root handlers by doing Logger.getLogger("").getHandlers() before you start your loop. You'll pay the price for loading them but at a different time.
log_.log(Level.INFO, "<-- " + msg, NETWORK_LOG_TOKEN);
The string concatenation in this line is going to do array copies and create garbage. Try to do:
log_.log(Level.INFO, msg, NETWORK_LOG_TOKEN);
The default log method will walk the current thread stack. You can avoid that walk by using logp​ methods in tight loops:
public Foo {
private static final String CLASS_NAME = Foo.class.getName();
private static final Logger log_ = Logger.getLogger(CLASS_NAME);
public void onTextMessagesReceived(ArrayList<String> msgs_list) {
String methodName = "onTextMessagesReceived";
// Loop through the messages
for (String msg: msgs_list) {
probe_.addTs(); // probe B
log_.logp(Level.INFO, CLASS_NAME, methodName, msg, NETWORK_LOG_TOKEN);
probe_.addTs(); // probe C
// Do some work on the message ...
probe_.addTs(); // probe D
}
}
}
In your code you are attaching a filter to the FileHandler. Depends on the use case but loggers also accept filters. Sometimes it makes sense to install a filter on the logger instead of the handler if you are targeting a specific message.

Is there a Java built in equivalent to Kotlin's require function?

Kotlin has a require function which can be used like so (copied from the reference documentation):
fun getIndices(count: Int): List<Int> {
require(count >= 0) { "Count must be non-negative, was $count" }
// ...
return List(count) { it + 1 }
}
// getIndices(-1) // will fail with IllegalArgumentException
println(getIndices(3)) // [1, 2, 3]
The function essentially throws an IllegalArgumentException if the value is false.
Obviously this could very easily be implemented in Java - but I was wondering is there something already in the JDK or apache libraries (or any other ubiquitous libraries) which offers a function which does this?
You can use assert function that is equivalent to the Kotlin require method.
assert count >= 0 : "Count must be non-negative, was " + count;
Programming With Assertions
JDK disables assert operations by default. If you want to enable assert operations you must define enabled package or class locations with VM options like -ea:com.example.demo...
Enabling and Disabling Assertions
I prefer Spring Framework's org.springframework.util.Assert class, because there are lots of method for validating parameters.
Simpler way:
Assert.isTrue(count >= 0, "Count must be non-negative, was " + count);
Lazy way (For better performance and same flow like kotlin require function):
Assert.isTrue(count >= 0, () -> "Count must be non-negative, was " + count);
Spring Assert Statements
For Unit tests, you can use, Junit (org.junit.Assert) or Jupiter (org.junit.jupiter.api.Assertions) assertion functions.
There is a method requireNonNull() in java.util.Objects that takes an object reference and checks that for being null.
See the Javadoc here!
But obviously, that is less flexible as the Kotlin version …
Basically, you can write your own version of require() like this:
public static final void require( final boolean predicate, final Supplier<String> messageSupplier )
{
if( !predicate ) throw new IllegalArgumentException( messageSupplier.get() );
}
(Error handling omitted …)
You can use it like this:
…
require( count > 0, () -> String.format( "Count must be non-negative, was %d", count );
…
But this requires that count is effectively final (or constant), otherwise it will not compile.
This can be circumvented when creating require() like this:
public static final void require( final boolean predicate, final Object messageArgument, final Function<Object,String> messageSupplier )
{
if( !predicate ) throw new IllegalArgumentException( messageSupplier.apply( Objects.toString( messageArgument ) );
}
You can use it like this:
…
require( count > 0, count, arg -> String.format( "Count must be non-negative, was %s", arg );
…
But in case of a primitive type, you have to pay the price for the boxing when calling require().
That in turn can be avoided by having a whole family of require() methods, one for each primitive type …
If the main goal is to avoid temporary objects that are not used when the condition of predicate is met, I would assume, you should not use inline closures (() -> …) but method references (this::getMessage) as the Supplier/Function arguments … but I also think that we are here already on the path of premature optimisations.
public class TestAsserts {
public static void main(String[] argv) {
int count = -2;
testCount(count);
}
public static void testCount(int count) {
assert(count >= 0): "Count must be non-negative, was " + count;
}
}
would work the same way. You get to decide if assertions are enabled or not at runtime. To run this you'd need to pass -ea as a Java command line option.
Note the the exception is a bit different too:
Exception in thread "main" java.lang.AssertionError: Count must be non-negative, was -2
at TestAsserts.testCount(TestAsserts.java:12)
at TestAsserts.main(TestAsserts.java:8)
Since Java 1.4 there is the assert Keyword in the JDK, which could be used to do something pretty similar. Oin this case an AsserrionError is thrown.

Edit method return value in a debugger

Given the following Java code, how can I use the IntelliJ or Eclipse debugger to return false from the condition() method?
public boolean condition() {
return (4 == add());
}
public int add() {
return 2 + 2;
}
In Eclipse you can use Force Return.
Just place a breakpoint on return (4 == add()); and type false on the Display view-tab. Then make a selection of your false, right click and hit "Force Return".
In IntelliJ (since IDEA 15 EAP) you can use Force return.
Extract from jetbrains' blog
You can force the return from the current method without executing any more instructions from it:
NB :
If the method returns a value, you’ll have to specify it (smart code completion provided).
If the method has try-finally blocks, you’ll be able to choose whether to execute them or not.
You can first change the code for condition to something like this:
public boolean condition() {
boolean result = (4 == add());
return result;
}
Then, you can set a breakpoint on the return statement. When the breakpoint is hit, you can use the debugger to change the value of result to false.

Is defaulting to an empty lambda better or worse than checking for a potentially null lambda?

I'm working on a small scene graph implementation in Java 8. The basic scene node looks something like this:
public class SceneNode {
private final List<SceneNode> children = new ArrayList<>();
protected Runnable preRender;
protected Runnable postRender;
protected Runnable render;
public final void render() {
preRender.run();
render.run();
for (Renderable child : children) {
child.render();
}
postRender.run();
}
}
This works fine if the Runnables default to () -> {}. However, alternatively I could allow them to be null, but that means that render() method has to look like this:
public final void render() {
if (null != preRender) { preRender.run(); }
if (null != render) { render.run(); }
for (Renderable child : children) {
child.render();
}
if (null != postRender) { postRender.run(); }
}
So my question is, is the implicit cost of the branching introduced by the null check likely to cost more or less than whatever the JVM ends up compiling an empty lambda into? It seems like it should end up costing more to check for null, because a potential branch limits optimization, while presumably the Java compiler or JVM should be smart enough to compile an empty lambda into a no-op.
Interestingly, it seems that checking for null is a little bit faster, than calling an empty lambda or an empty anonymous class, when the JVM is run with the -client argument. When running with -server, the performance is the same for all approaches.
I have done a micro benchmark with Caliper, to test this.
Here is the test class (latest Caliper form git necessary to compile):
#VmOptions("-client")
public class EmptyLambdaTest {
public Runnable emptyLambda = () -> {};
public Runnable emptyAnonymousType = new Runnable() {
#Override
public void run() {}
};
public Runnable nullAbleRunnable;
#Benchmark
public int timeEmptyLambda(int reps){
int dummy = 0;
for (int i = 0; i < reps; i++) {
emptyLambda.run();
dummy |= i;
}
return dummy;
}
#Benchmark
public int timeEmptyAnonymousType(int reps){
int dummy = 0;
for (int i = 0; i < reps; i++) {
emptyAnonymousType.run();
dummy |= i;
}
return dummy;
}
#Benchmark
public int timeNullCheck(int reps){
int dummy = 0;
for (int i = 0; i < reps; i++) {
if (nullAbleRunnable != null) {
nullAbleRunnable.run();
}
dummy |= i;
}
return dummy;
}
}
And here are the benchmark results:
Running with -client
Running with -server
Is defaulting to an empty lambda better or worse than checking for a potentially null lambda?
This is essentially the same as asking if it is better to test for a null String parameter or try to substitute an empty String.
The answer is that it depends on whether you want to treat the null as a programming error ... or not.
My personal opinion is that unexpected nulls should be treated as programming errors, and that you should allow the program to crash with an NPE. That way, the problem will come to your attention earlier and will be easier to track down and fix ... than if you substituted some "make good" value to stop the NPE from being thrown.
But of course, that doesn't apply for expected null values; i.e. when the API javadocs say that a null is a permissible value, and say what it means.
This also relates to how you design your APIs. In this case, the issue is whether your API spec (i.e. the javadoc!) should insist on the programmer providing a no-op lambda, or treat null as meaning the same thing. That boils down to a compromise between:
API client convenience,
API implementor work, and
robustness; e.g. when using the value of an incorrectly initialized variable ...
I'm more concerned about the implications of the runtime performance of using an empty lambda vs using a null and having to do a null check.
My intuition is that testing for null would be faster, but any difference in performance will be small, and that the chances are that it won't be significant to the overall performance of the application.
(UPDATE - Turns out that my intuition is "half right" according to #Balder's micro-benchmarking. For a -client mode JVM, null checking is a bit faster, but not enough to be concerning. For a -server mode JVM, the JIT compiler is apparently optimizing both cases to native code with identical performance.)
I suggest that you treat that you would (or at least should) treat any potential optimization problem:
Put off any optimization until your application is working.
Benchmark the application to see if it is already fast enough
Profile the applications to see where the real hotspots are
Develop and test a putative optimization
Rerun the benchmarks to see if it improved things
Go to step 2.

Evaluate logical expression at runtime

How do I go about evaluating logical expression like "VERB1 OR (VERB2 AND VERB3) OR (VERB4)" entered at runtime. VERB* are placeholder to evaluate certain conditions. For example, VERB1 might mean check for the existence of a record in database.
In expression "VERB1 OR (VERB2 AND VERB3) OR (VERB4)", other verbs should not be executed if VERB1 is true
EDIT: Example described at http://www.alittlemadness.com/2006/06/05/antlr-by-example-part-1-the-language/ seems very similar to what I am trying to do. However, the optimization step (other verbs should not be executed if VERB1 is true) doesn't seem to be there.
If you can use || and && in place of AND and OR, you can just use groovy's missing property methods and the GroovyShell base class setting like so:
import org.codehaus.groovy.control.CompilerConfiguration
// The command to be executes
def command = "VERB1 || (VERB2 && VERB3) || (VERB4)"
// Set a base class for the GroovyShell
new CompilerConfiguration().with { compiler ->
compiler.scriptBaseClass = 'VerbHandlingBaseClass'
new GroovyShell( this.class.classLoader, new Binding(), compiler ).with { shell ->
// and evaluate the command
shell.evaluate( command )
}
}
abstract class VerbHandlingBaseClass extends Script {
boolean VERB1() {
System.out.println( 'CHECK THE DATABASE, RETURN FALSE' )
false
}
boolean VERB2() {
System.out.println( 'WRITE A LOG ENTRY RETURN TRUE' )
true
}
boolean VERB3() {
System.out.println( 'VALIDATE SOMETHING, RETURN TRUE' )
true
}
boolean VERB4() {
System.out.println( 'THIS WONT BE REACHED, AS VERB2 && VERB3 == true' )
true
}
def propertyMissing( String name ) {
"$name"()
}
}
That should print:
CHECK THE DATABASE, RETURN FALSE
WRITE A LOG ENTRY RETURN TRUE
VALIDATE SOMETHING, RETURN TRUE
You mentioned ANTLR in your tags: have you given this a go? You can create a full boolean grammar in ANTLR but it gets much harder when you get down to the level of how to evaluate the verbs.
If there is a small, fixed set of verbs which may be queried you can easily create a mapping between the verbs and the functions.
If there is a larger list of verbs, you may be able to use reflection to call specific methods to evaluate them.
If your verbs can include mathematical comparisons, this all gets a bit harder as you create a mathematical lexer and parser as well.
Without a more specific question and knowledge of what you have tried in ANTLR I'm not sure I can give you much more advice.
EDIT: Based on your comments, I'll add some more.
You can add parsing rules to your grammar:
boolean_or returns [boolean b]
: b1=boolean_and {$b = $b1.b;}
(OR b2=boolean_and {$b = $b || $b2.b;})*
;
boolean_atom returns [boolean b]
:
((numeric_comparison)=> b1=numeric_comparison {$b = $b1.b;}
| TRUE {$b = true;} | FALSE {$b = false;}
| s1=VERB {$b = evalVerb($s1.s);}
| LPAREN b1=boolean_expr RPAREN {$b = $b1.b;}
)
;
Thats a small part of a boolean parser I'm currently using. You can fill in the blanks.
And then call the parser using something like
ANTLRStringStream in = new ANTLRStringStream(booleanString);
ActionLexer lexer = new ActionLexer(in);
CommonTokenStream tokens = new CommonTokenStream(lexer);
BooleanParser parser = new BooleanParser(tokens);
try {
return parser.eval();
} catch (Exception e) {
}
This doesn't account for your requirement of returning early, but I'm sure you can figure out how to do that.
This might not be the best way to do things, but its the way that I've gotten it to work for me in the past. Hope this helps.

Categories

Resources