diff --git a/libraries-testing-2/pom.xml b/libraries-testing-2/pom.xml
index f0e9cc19db02..477a40d8ba5f 100644
--- a/libraries-testing-2/pom.xml
+++ b/libraries-testing-2/pom.xml
@@ -190,6 +190,12 @@
javalite-common
${javalite.version}
+
+ com.vmlens
+ api
+ ${vmlens.version}
+ test
+
@@ -218,6 +224,24 @@
+
+ com.vmlens
+ vmlens-maven-plugin
+ ${vmlens.version}
+
+
+ test
+
+ test
+
+
+
+
+
+ **/BankAccountTest.java
+
+
+
@@ -238,5 +262,6 @@
0.32
0.12
1.4.13
+ 1.2.10
\ No newline at end of file
diff --git a/libraries-testing-2/src/main/java/com/baeldung/vmlens/AtomicBankAccount.java b/libraries-testing-2/src/main/java/com/baeldung/vmlens/AtomicBankAccount.java
new file mode 100644
index 000000000000..d8f0037aafb4
--- /dev/null
+++ b/libraries-testing-2/src/main/java/com/baeldung/vmlens/AtomicBankAccount.java
@@ -0,0 +1,17 @@
+package com.baeldung.vmlens;
+
+public class AtomicBankAccount {
+
+ private final Object LOCK = new Object();
+ private volatile int amount;
+
+ public int getAmount() {
+ return amount;
+ }
+
+ public void update(int delta) {
+ synchronized (LOCK) {
+ amount += delta;
+ }
+ }
+}
diff --git a/libraries-testing-2/src/main/java/com/baeldung/vmlens/RegularFieldBankAccount.java b/libraries-testing-2/src/main/java/com/baeldung/vmlens/RegularFieldBankAccount.java
new file mode 100644
index 000000000000..1f0f546c13ac
--- /dev/null
+++ b/libraries-testing-2/src/main/java/com/baeldung/vmlens/RegularFieldBankAccount.java
@@ -0,0 +1,14 @@
+package com.baeldung.vmlens;
+
+public class RegularFieldBankAccount {
+
+ private int amount;
+
+ public int getAmount() {
+ return amount;
+ }
+
+ public void update(int delta) {
+ amount += delta;
+ }
+}
diff --git a/libraries-testing-2/src/main/java/com/baeldung/vmlens/VolatileFieldBankAccount.java b/libraries-testing-2/src/main/java/com/baeldung/vmlens/VolatileFieldBankAccount.java
new file mode 100644
index 000000000000..bb604eb647ad
--- /dev/null
+++ b/libraries-testing-2/src/main/java/com/baeldung/vmlens/VolatileFieldBankAccount.java
@@ -0,0 +1,14 @@
+package com.baeldung.vmlens;
+
+public class VolatileFieldBankAccount {
+
+ private volatile int amount;
+
+ public int getAmount() {
+ return amount;
+ }
+
+ public void update(int delta) {
+ amount += delta;
+ }
+}
diff --git a/libraries-testing-2/src/test/java/com/baeldung/vmlens/BankAccountTest.java b/libraries-testing-2/src/test/java/com/baeldung/vmlens/BankAccountTest.java
new file mode 100644
index 000000000000..017a125d0be2
--- /dev/null
+++ b/libraries-testing-2/src/test/java/com/baeldung/vmlens/BankAccountTest.java
@@ -0,0 +1,63 @@
+package com.baeldung.vmlens;
+
+import static org.hamcrest.CoreMatchers.is;
+import static org.hamcrest.MatcherAssert.assertThat;
+import static org.hamcrest.Matchers.anyOf;
+
+import org.junit.jupiter.api.Test;
+
+import com.vmlens.api.AllInterleavings;
+
+/**
+ * This test tests the different implementations of a concurrent bank account class.+
+ * To see what is wrong with RegularFieldBankAccount and VolatileFieldBankAccount replace
+ * AtomicBankAccount with one of those classes.
+ *
+ */
+
+class BankAccountTest {
+
+ @Test
+ public void whenParallelUpdate_thenAmountSumOfBothUpdates() throws InterruptedException {
+ try (AllInterleavings allInterleavings = new AllInterleavings("bankAccount.updateUpdate")) {
+ while (allInterleavings.hasNext()) {
+ AtomicBankAccount bankAccount = new AtomicBankAccount();
+
+ Thread first = new Thread() {
+ @Override
+ public void run() {
+ bankAccount.update(5);
+ }
+ };
+ first.start();
+ bankAccount.update(10);
+ first.join();
+
+ int amount = bankAccount.getAmount();
+ assertThat(amount, is(15));
+ }
+ }
+ }
+
+ @Test
+ public void whenParallelUpdateAndGet_thenResultEitherAmountBeforeOrAfterUpdate() throws InterruptedException {
+ try (AllInterleavings allInterleavings = new AllInterleavings("bankAccount.updateGetAmount")) {
+ while (allInterleavings.hasNext()) {
+ AtomicBankAccount bankAccount = new AtomicBankAccount();
+
+ Thread first = new Thread() {
+ @Override
+ public void run() {
+ bankAccount.update(5);
+ }
+ };
+ first.start();
+
+ int amount = bankAccount.getAmount();
+
+ assertThat(amount, anyOf(is(0), is(5)));
+ first.join();
+ }
+ }
+ }
+}