Skip to content

Commit

Permalink
Make FlightRecorderApplicationStartup thread safe
Browse files Browse the repository at this point in the history
Prior to this commit, in some cases application context startup steps
could be created concurrently, which could cause issues with the current
implementation tracking the parent/child relationship between steps.

This commit ensures that the flight recorder implementation is using
thread safe collection implementations for that.

Fixes spring-projectsgh-26941
  • Loading branch information
bclozel authored and lxbzmy committed Mar 26, 2022
1 parent 21132ba commit 00688d7
Showing 1 changed file with 10 additions and 10 deletions.
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
/*
* Copyright 2002-2020 the original author or authors.
* Copyright 2002-2021 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
Expand All @@ -16,8 +16,9 @@

package org.springframework.core.metrics.jfr;

import java.util.ArrayDeque;
import java.util.Deque;
import java.util.concurrent.ConcurrentLinkedDeque;
import java.util.concurrent.atomic.AtomicLong;

import org.springframework.core.metrics.ApplicationStartup;
import org.springframework.core.metrics.StartupStep;
Expand All @@ -37,24 +38,23 @@
*/
public class FlightRecorderApplicationStartup implements ApplicationStartup {

private long currentSequenceId;
private final AtomicLong currentSequenceId = new AtomicLong(0);

private final Deque<Long> currentSteps;


public FlightRecorderApplicationStartup() {
this.currentSequenceId = 0;
this.currentSteps = new ArrayDeque<>();
this.currentSteps.offerFirst(0L);
this.currentSteps = new ConcurrentLinkedDeque<>();
this.currentSteps.offerFirst(this.currentSequenceId.get());
}


@Override
public StartupStep start(String name) {
FlightRecorderStartupStep step = new FlightRecorderStartupStep(++this.currentSequenceId, name,
this.currentSteps.getFirst(), committedStep -> this.currentSteps.removeFirst());
this.currentSteps.offerFirst(this.currentSequenceId);
return step;
long sequenceId = this.currentSequenceId.incrementAndGet();
this.currentSteps.offerFirst(sequenceId);
return new FlightRecorderStartupStep(sequenceId, name,
this.currentSteps.getFirst(), committedStep -> this.currentSteps.removeFirstOccurrence(sequenceId));
}

}

0 comments on commit 00688d7

Please sign in to comment.