Skip to content

Instantly share code, notes, and snippets.

View llgruff's full-sized avatar
🎯
🐱

Roman Krokhmalyuk llgruff

🎯
🐱
View GitHub Profile

Understanding Comparative Benchmarks

I'm going to do something that I don't normally do, which is to say I'm going to talk about comparative benchmarks. In general, I try to confine performance discussion to absolute metrics as much as possible, or comparisons to other well-defined neutral reference points. This is precisely why Cats Effect's readme mentions a comparison to a fixed thread pool, rather doing comparisons with other asynchronous runtimes like Akka or ZIO. Comparisons in general devolve very quickly into emotional marketing.

But, just once, today we're going to talk about the emotional marketing. In particular, we're going to look at Cats Effect 3 and ZIO 2. Now, for context, as of this writing ZIO 2 has released their first milestone; they have not released a final 2.0 version. This implies straight off the bat that we're comparing apples to oranges a bit, since Cats Effect 3 has been out and in production for months. However, there has been a post going around which cites various compar

A Study in Multi-Point Deadlocks

Deadlocks are extremely difficult to reason about sometimes. We are used to thinking about them in terms of contention over shared resources, with the pair of exclusive locks being a good and relatively canonical example of this phenomenon. However, sometimes you can find yourself in deadlock scenarios which are caused not so much by an improper sequencing of exclusivity, but rather by insufficient buffer capacity!

These kinds of scenarios are a lot rarer and much more difficult to diagnose and describe, which is why I found this particular puzzle so incredibly fascinating. The following is a screenshot from Cities Skylines (I added textual markers and arrows to make things easier to follow). All vehicles pictured are stationary and unable to move, indefinitely:

Do you see the deadlock? It took me a bit to understand it, but this situation can and does arise in software resource contention where it is dramatically harder to conc

Fibers

Fibers are an abstraction over sequential computation, similar to threads but at a higher level. There are two ways to think about this model: by example, and abstractly from first principles. We'll start with the example.

(credit here is very much due to Fabio Labella, who's incredible Scala World talk describes these ideas far better than I can)

Callback Sequentialization

Consider the following three functions

Schedulers

As Cats Effect is a runtime system, it ultimately must deal with the problem of how best to execute the programs which are defined using its concrete implementation (IO). Fibers are an incredibly powerful model, but they don't map 1:1 or even 1:n with any JVM or JavaScript construct, which means that some interpretation is required. The fashion in which this is achieved has a profound impact on the performance and elasticity of programs written using IO.

This is true across both the JVM and JavaScript, and while it seems intuitive that JavaScript scheduling would be a simpler problem (due to its single-threaded nature), there are still some significant subtleties which become relevant in real-world applications.

JVM

IO programs and fibers are ultimately executed on JVM threads, which are themselves mapped directly to kernel threads and, ultimately (when scheduled), to processors. Determining the optimal method of mapping a real-world, concurrent application down to kernel-level thr

@Hakky54
Hakky54 / openssl_commands.md
Last active May 8, 2025 12:37 — forked from p3t3r67x0/openssl_commands.md
OpenSSL Cheat Sheet

OpenSSL Cheat Sheet 🔐

Install

Install the OpenSSL on Debian based systems

sudo apt-get install openssl
@Hakky54
Hakky54 / java_keytool_cheat_sheet.md
Last active May 2, 2025 10:15
Keytool Cheat Sheet

Keytool CheatSheet 🔐

Some history

This cheat sheet came into life when I started working on a tutorial of setting up one way tls and two way tls, which can be found here: GitHub - Mutual TLS SSL

Creation and importing

Generate a Java keystore and key pair

keytool -genkeypair -keyalg RSA -keysize 2048 -keystore keystore.jks -alias server -validity 3650
@jdegoes
jdegoes / fpmax.scala
Created July 13, 2018 03:18
FP to the Max — Code Examples
package fpmax
import scala.util.Try
import scala.io.StdIn.readLine
object App0 {
def main: Unit = {
println("What is your name?")
val name = readLine()

Quick Tips for Fast Code on the JVM

I was talking to a coworker recently about general techniques that almost always form the core of any effort to write very fast, down-to-the-metal hot path code on the JVM, and they pointed out that there really isn't a particularly good place to go for this information. It occurred to me that, really, I had more or less picked up all of it by word of mouth and experience, and there just aren't any good reference sources on the topic. So… here's my word of mouth.

This is by no means a comprehensive gist. It's also important to understand that the techniques that I outline in here are not 100% absolute either. Performance on the JVM is an incredibly complicated subject, and while there are rules that almost always hold true, the "almost" remains very salient. Also, for many or even most applications, there will be other techniques that I'm not mentioning which will have a greater impact. JMH, Java Flight Recorder, and a good profiler are your very best friend! Mea

Thread Pools

Thread pools on the JVM should usually be divided into the following three categories:

  1. CPU-bound
  2. Blocking IO
  3. Non-blocking IO polling

Each of these categories has a different optimal configuration and usage pattern.