Use compareAndSet() instead of locking.

This commit is contained in:
akwizgran
2016-09-16 10:49:41 +01:00
committed by Ernir Erlingsson
parent 2d59b9095c
commit 33795e7046

View File

@@ -67,7 +67,8 @@ public class ForumControllerImpl extends DbControllerImpl
protected volatile IdentityManager identityManager; protected volatile IdentityManager identityManager;
private final Map<MessageId, byte[]> bodyCache = new ConcurrentHashMap<>(); private final Map<MessageId, byte[]> bodyCache = new ConcurrentHashMap<>();
private volatile AtomicLong newestTimeStamp = new AtomicLong(); private final AtomicLong newestTimeStamp = new AtomicLong();
private volatile LocalAuthor localAuthor = null; private volatile LocalAuthor localAuthor = null;
private volatile Forum forum = null; private volatile Forum forum = null;
@@ -109,15 +110,12 @@ public class ForumControllerImpl extends DbControllerImpl
if (e instanceof ForumPostReceivedEvent) { if (e instanceof ForumPostReceivedEvent) {
final ForumPostReceivedEvent pe = (ForumPostReceivedEvent) e; final ForumPostReceivedEvent pe = (ForumPostReceivedEvent) e;
if (pe.getGroupId().equals(forum.getId())) { if (pe.getGroupId().equals(forum.getId())) {
LOG.info("Forum Post received, adding..."); LOG.info("Forum post received, adding...");
final ForumPostHeader fph = pe.getForumPostHeader(); final ForumPostHeader fph = pe.getForumPostHeader();
updateNewestTimestamp(fph.getTimestamp());
activity.runOnUiThread(new Runnable() { activity.runOnUiThread(new Runnable() {
@Override @Override
public void run() { public void run() {
synchronized (this) {
if (fph.getTimestamp() > newestTimeStamp.get())
newestTimeStamp.set(fph.getTimestamp());
}
listener.onExternalEntryAdded(fph); listener.onExternalEntryAdded(fph);
} }
}); });
@@ -147,8 +145,7 @@ public class ForumControllerImpl extends DbControllerImpl
forum = forumManager.getForum(groupId); forum = forumManager.getForum(groupId);
long duration = System.currentTimeMillis() - now; long duration = System.currentTimeMillis() - now;
if (LOG.isLoggable(INFO)) if (LOG.isLoggable(INFO))
LOG.info("Loading forum took " + duration + LOG.info("Loading forum took " + duration + " ms");
" ms");
// Get First Identity // Get First Identity
now = System.currentTimeMillis(); now = System.currentTimeMillis();
@@ -157,8 +154,7 @@ public class ForumControllerImpl extends DbControllerImpl
.next(); .next();
duration = System.currentTimeMillis() - now; duration = System.currentTimeMillis() - now;
if (LOG.isLoggable(INFO)) if (LOG.isLoggable(INFO))
LOG.info("Loading author took " + duration + LOG.info("Loading author took " + duration + " ms");
" ms");
} }
/** /**
@@ -210,11 +206,9 @@ public class ForumControllerImpl extends DbControllerImpl
return entries; return entries;
} }
private synchronized void checkNewestTimeStamp( private void updateNewestTimeStamp(Collection<ForumPostHeader> headers) {
Collection<ForumPostHeader> headers) {
for (ForumPostHeader h : headers) { for (ForumPostHeader h : headers) {
if (h.getTimestamp() > newestTimeStamp.get()) updateNewestTimestamp(h.getTimestamp());
newestTimeStamp.set(h.getTimestamp());
} }
} }
@@ -224,15 +218,14 @@ public class ForumControllerImpl extends DbControllerImpl
runOnDbThread(new Runnable() { runOnDbThread(new Runnable() {
@Override @Override
public void run() { public void run() {
if (LOG.isLoggable(INFO)) LOG.info("Loading forum...");
LOG.info("Loading forum...");
try { try {
if (forum == null) { if (forum == null) {
loadForum(groupId); loadForum(groupId);
} }
// Get Forum Posts and Bodies // Get Forum Posts and Bodies
Collection<ForumPostHeader> headers = loadHeaders(); Collection<ForumPostHeader> headers = loadHeaders();
checkNewestTimeStamp(headers); updateNewestTimeStamp(headers);
loadBodies(headers); loadBodies(headers);
resultHandler.onResult(buildForumEntries(headers)); resultHandler.onResult(buildForumEntries(headers));
} catch (DbException e) { } catch (DbException e) {
@@ -328,14 +321,9 @@ public class ForumControllerImpl extends DbControllerImpl
cryptoExecutor.execute(new Runnable() { cryptoExecutor.execute(new Runnable() {
@Override @Override
public void run() { public void run() {
if (LOG.isLoggable(INFO)) LOG.info("Create post...");
LOG.info("create post..");
long timestamp = System.currentTimeMillis(); long timestamp = System.currentTimeMillis();
// FIXME next two lines Synchronized ? timestamp = Math.max(timestamp, newestTimeStamp.get());
// Only reading the atomic value, and even if it is changed
// between the first and second get, the condition will hold
if (timestamp < newestTimeStamp.get())
timestamp = newestTimeStamp.get();
ForumPost p; ForumPost p;
try { try {
KeyParser keyParser = crypto.getSignatureKeyParser(); KeyParser keyParser = crypto.getSignatureKeyParser();
@@ -353,20 +341,19 @@ public class ForumControllerImpl extends DbControllerImpl
}); });
} }
@Override
public void storePost(final ForumPost p, public void storePost(final ForumPost p,
final ResultHandler<ForumEntry> resultHandler) { final ResultHandler<ForumEntry> resultHandler) {
runOnDbThread(new Runnable() { runOnDbThread(new Runnable() {
@Override @Override
public void run() { public void run() {
try { try {
if (LOG.isLoggable(INFO)) LOG.info("Store post...");
LOG.info("Store post...");
long now = System.currentTimeMillis(); long now = System.currentTimeMillis();
forumManager.addLocalPost(p); forumManager.addLocalPost(p);
long duration = System.currentTimeMillis() - now; long duration = System.currentTimeMillis() - now;
if (LOG.isLoggable(INFO)) if (LOG.isLoggable(INFO))
LOG.info( LOG.info("Storing message took " + duration + " ms");
"Storing message took " + duration + " ms");
ForumPostHeader h = ForumPostHeader h =
new ForumPostHeader(p.getMessage().getId(), new ForumPostHeader(p.getMessage().getId(),
@@ -386,4 +373,11 @@ public class ForumControllerImpl extends DbControllerImpl
}); });
} }
private void updateNewestTimestamp(long update) {
long newest = newestTimeStamp.get();
while (newest < update) {
if (newestTimeStamp.compareAndSet(newest, update)) return;
newest = newestTimeStamp.get();
}
}
} }