CMS Deprecated. Next Steps?

The popular Concurrent Mark Sweep (CMS) GC algorithm is deprecated in JDK 9. According to JEP-291, this decision has been made to reduce the maintenance burden of the GC code base and accelerate new development.

Thus, from Java 9 onwards, if you launch the application with -XX:+UseConcMarkSweepGC (an argument which will activate the CMS GC algorithm), you are going to see below WARNING message:

What Are Garbage Collection Logs, Thread Dumps, and Heap Dumps?

Java Virtual Machine (JVM) generates 3 critical artifacts that are useful for optimizing the performance and troubleshooting production problems. Those artifacts are:

  1. Garbage collection (GC) log
  2. Thread Dump
  3. Heap Dump

In this article, let's try to understand these 3 critical artifacts, where to use them, how do they look, how to capture them, how to analyze them, and their differences.

3 GC Techniques to Improve Application Performance

Automated garbage collection (along with the JIT HotSpot Compiler) is one of the most advanced and most valued components of the JVM, but many developers and engineers are far less familiar with Garbage Collection (GC), how it works and how it impacts application performance.

First, what is GC even for? Garbage collection is the memory management process for objects in the heap. As objects are allocated to the heap, they run through a few collection phases – usually rather quickly as the majority of objects in the heap have short lifespans.

JDK 14: CMS GC Is OBE

JDK 14 Early Access Build #23 is now available.

JDK 14 Early Access Build #23 ( 2019/11/13) is now available. One of the more noteworthy changes with this build is the removal of the Concurrent Mark Sweep garbage collector. JEP 291 ["Deprecate the Concurrent Mark Sweep (CMS) Garbage Collector"] deprecated the Concurrent Mark Sweep (CMS) garbage collector back in 2017 with JDK 9 and JEP 363 ["Remove the Concurrent Mark Sweep (CMS) Garbage Collector"] has been targeted for JDK 14 to remove the CMS garbage collector altogether.

The next screen snapshot demonstrates that the CMS garbage collector was still available with JDK 14 Early Access Build #22.

Run Faster, Git: The Story of Git Command Slowdown, Branches, and Garbage Collection

Speed up, Git!

My team uses Git for source control. And since we created a bunch of branches for features on the application, we ended up with a ton of branches on our Git repository. While this is not something we cared about initially, the rising number of branches grew rapidly and soon got out of control. This, in turn, resulted in slowing down our Git commands because Git now had to handle the unused branches.

You may also like: Top 20 Git Commands With Examples

This was a challenge that I was interested in solving. In this post, we assess the problems associated with too many Git branches, problem-solving, and a solution to slow Git commands. Let's get started.

The Best Way to Optimize Garbage Collection Is NOT By Tuning it

The best way to optimize garbage collection is NOT by tuning it.

When asked: "What would you do if your Java app experiences long GC pauses?" — most people would answer: "increase the heap size and/or tune the garbage collector." That works in many but not all situations. The heap may already be close to the total memory available. And GC tuning, beyond a few most obvious and efficient flags, often becomes a black art where each new change brings a smaller improvement. Worse, hyper-tuning GC makes it tightly coupled with your current heap size, number of CPUs, and workload patterns.

Need help choosing the right GC? Check out this post!

If any of these components changes in the future, the GC may suddenly perform much worse. And (what a surprise!) at that point, it may be really hard to remember why each of the flags in the combination like the one below is there, and what its effect was supposed to be: 

Pitfalls in JVM and Docker Defaults

First, there are a lot of articles about JVM and container-awareness:

In this post, I use Java 11, which means the default for garbage collector is supposed to be G1GC! Let's look at the defaults, which are automatically chosen by the JVM depending on memory size and provided CPUs.

How to Tune Garbage Collection in Java

Garbage collection is the mechanism by which the JVM reclaims memory on behalf of the application when it's no longer needed. At a high level, it consists of finding objects that are no longer in use, freeing the memory associated with those objects, and occasionally compacting the heap to prevent memory fragmentation.

The garbage collector performs it's work using one or more threads. But in order to do the job of tracking down object references and moving objects around in memory, it needs to make sure that the application threads are not currently using those objects because if, for example, an application thread is using an object and then the memory location of the object changes due to GC, then bad and unpredictable things could happen. This is why garbage collectors must pause all application threads when performing certain tasks. These pauses are sometimes called Stop-The-World pauses, and the minimization of them is the primary concern of GC tuning, as they can have a huge impact on the performance of a Java application.

The Myth of the Server’s Terrible, Horrible, No Good, Very Bad Day

Have you ever been on call when something had a temporary latency spike that was possibly just a network blip? Or maybe the service was unhappy and went into a GC spiral? Sometimes it just goes away on its own, or sometimes you restart the service and things start to look better. It’s all too common these days to feel like the systems we operate are feeling emotions like “unhappiness” rather than behaving deterministically.

We already know that software is deterministic — it does what you program it to do. So, why do we sometimes feel like it’s not doing its thing? Programs don’t get tired, so why does restarting do anything at all, let alone magically fix it? You wouldn’t expect a Fibonacci generator to just randomly give up or slow down, so why do large distributed systems sometimes seem like they do?