From cb0b6665f7884b43f6984d0545d1fd38c8333118 Mon Sep 17 00:00:00 2001 From: woodser Date: Thu, 20 Jun 2024 11:53:15 -0400 Subject: [PATCH] add and remove offers on user thread to fix illegal state #1031 --- .../haveno/core/offer/OfferBookService.java | 42 ++++++++++--------- .../offerbook/OfferBookChartViewModel.java | 12 ++++-- 2 files changed, 30 insertions(+), 24 deletions(-) diff --git a/core/src/main/java/haveno/core/offer/OfferBookService.java b/core/src/main/java/haveno/core/offer/OfferBookService.java index 0df2de483f..7698aeb1ca 100644 --- a/core/src/main/java/haveno/core/offer/OfferBookService.java +++ b/core/src/main/java/haveno/core/offer/OfferBookService.java @@ -115,6 +115,7 @@ public class OfferBookService { p2PService.addHashSetChangedListener(new HashMapChangedListener() { @Override public void onAdded(Collection protectedStorageEntries) { + UserThread.execute(() -> { protectedStorageEntries.forEach(protectedStorageEntry -> { if (protectedStorageEntry.getProtectedStoragePayload() instanceof OfferPayload) { OfferPayload offerPayload = (OfferPayload) protectedStorageEntry.getProtectedStoragePayload(); @@ -128,22 +129,25 @@ public class OfferBookService { } } }); + }); } @Override public void onRemoved(Collection protectedStorageEntries) { - protectedStorageEntries.forEach(protectedStorageEntry -> { - if (protectedStorageEntry.getProtectedStoragePayload() instanceof OfferPayload) { - OfferPayload offerPayload = (OfferPayload) protectedStorageEntry.getProtectedStoragePayload(); - maybeInitializeKeyImagePoller(); - keyImagePoller.removeKeyImages(offerPayload.getReserveTxKeyImages()); - Offer offer = new Offer(offerPayload); - offer.setPriceFeedService(priceFeedService); - setReservedFundsSpent(offer); - synchronized (offerBookChangedListeners) { - offerBookChangedListeners.forEach(listener -> listener.onRemoved(offer)); + UserThread.execute(() -> { + protectedStorageEntries.forEach(protectedStorageEntry -> { + if (protectedStorageEntry.getProtectedStoragePayload() instanceof OfferPayload) { + OfferPayload offerPayload = (OfferPayload) protectedStorageEntry.getProtectedStoragePayload(); + maybeInitializeKeyImagePoller(); + keyImagePoller.removeKeyImages(offerPayload.getReserveTxKeyImages()); + Offer offer = new Offer(offerPayload); + offer.setPriceFeedService(priceFeedService); + setReservedFundsSpent(offer); + synchronized (offerBookChangedListeners) { + offerBookChangedListeners.forEach(listener -> listener.onRemoved(offer)); + } } - } + }); }); } }); @@ -278,9 +282,11 @@ public class OfferBookService { keyImagePoller.addListener(new XmrKeyImageListener() { @Override public void onSpentStatusChanged(Map spentStatuses) { - for (String keyImage : spentStatuses.keySet()) { - updateAffectedOffers(keyImage); - } + UserThread.execute(() -> { + for (String keyImage : spentStatuses.keySet()) { + updateAffectedOffers(keyImage); + } + }); } }); @@ -301,12 +307,8 @@ public class OfferBookService { if (offer.getOfferPayload().getReserveTxKeyImages().contains(keyImage)) { synchronized (offerBookChangedListeners) { offerBookChangedListeners.forEach(listener -> { - - // notify off thread to avoid deadlocking - new Thread(() -> { - listener.onRemoved(offer); - listener.onAdded(offer); - }).start(); + listener.onRemoved(offer); + listener.onAdded(offer); }); } } diff --git a/desktop/src/main/java/haveno/desktop/main/market/offerbook/OfferBookChartViewModel.java b/desktop/src/main/java/haveno/desktop/main/market/offerbook/OfferBookChartViewModel.java index 8073351a9b..fa0bcbd0bb 100644 --- a/desktop/src/main/java/haveno/desktop/main/market/offerbook/OfferBookChartViewModel.java +++ b/desktop/src/main/java/haveno/desktop/main/market/offerbook/OfferBookChartViewModel.java @@ -19,6 +19,8 @@ package haveno.desktop.main.market.offerbook; import com.google.common.math.LongMath; import com.google.inject.Inject; + +import haveno.common.UserThread; import haveno.core.account.witness.AccountAgeWitnessService; import haveno.core.locale.CurrencyUtil; import haveno.core.locale.GlobalSettings; @@ -135,10 +137,12 @@ class OfferBookChartViewModel extends ActivatableViewModel { currenciesUpdatedListener = (observable, oldValue, newValue) -> { if (!isAnyPriceAbsent()) { - offerBook.fillOfferBookListItems(); - updateChartData(); - var self = this; - priceFeedService.updateCounterProperty().removeListener(self.currenciesUpdatedListener); + UserThread.execute(() -> { + offerBook.fillOfferBookListItems(); + updateChartData(); + var self = this; + priceFeedService.updateCounterProperty().removeListener(self.currenciesUpdatedListener); + }); } };