Change EAS request implementation to use LinkedBlockingQueue
* Make sure that requests added during sync() aren't missed
Change-Id: I20a7788f3695ef6a99642240230f0d004f034f44
diff --git a/src/com/android/exchange/AbstractSyncService.java b/src/com/android/exchange/AbstractSyncService.java
index b750113..c676cce 100644
--- a/src/com/android/exchange/AbstractSyncService.java
+++ b/src/com/android/exchange/AbstractSyncService.java
@@ -29,7 +29,7 @@
import android.os.Bundle;
import android.util.Log;
-import java.util.ArrayList;
+import java.util.concurrent.LinkedBlockingQueue;
/**
* Base class for all protocol services SyncManager (extends Service, implements
@@ -70,7 +70,7 @@
protected Object mSynchronizer = new Object();
protected volatile long mRequestTime = 0;
- protected ArrayList<Request> mRequests = new ArrayList<Request>();
+ protected LinkedBlockingQueue<Request> mRequestQueue = new LinkedBlockingQueue<Request>();
protected PartRequest mPendingRequest = null;
/**
@@ -294,15 +294,15 @@
*/
public void addRequest(Request req) {
- synchronized (mRequests) {
- mRequests.add(req);
- mRequestTime = System.currentTimeMillis();
- }
+ mRequestQueue.offer(req);
}
public void removeRequest(Request req) {
- synchronized (mRequests) {
- mRequests.remove(req);
- }
+ mRequestQueue.remove(req);
}
+
+ public boolean hasPendingRequests() {
+ return !mRequestQueue.isEmpty();
+}
+
}
diff --git a/src/com/android/exchange/EasSyncService.java b/src/com/android/exchange/EasSyncService.java
index 988fb75..740616a 100644
--- a/src/com/android/exchange/EasSyncService.java
+++ b/src/com/android/exchange/EasSyncService.java
@@ -2028,7 +2028,7 @@
boolean moreAvailable = true;
int loopingCount = 0;
- while (!mStop && moreAvailable) {
+ while (!mStop && (moreAvailable || hasPendingRequests())) {
// If we have no connectivity, just exit cleanly. SyncManager will start us up again
// when connectivity has returned
if (!hasConnectivity()) {
@@ -2046,12 +2046,11 @@
// Now, handle various requests
while (true) {
Request req = null;
- synchronized (mRequests) {
- if (mRequests.isEmpty()) {
- break;
- } else {
- req = mRequests.get(0);
- }
+
+ if (mRequestQueue.isEmpty()) {
+ break;
+ } else {
+ req = mRequestQueue.peek();
}
// Our two request types are PartRequest (loading attachment) and
@@ -2064,9 +2063,12 @@
// If there's an exception handling the request, we'll throw it
// Otherwise, we remove the request
- synchronized(mRequests) {
- mRequests.remove(req);
- }
+ mRequestQueue.remove();
+ }
+
+ // Don't sync if we've got nothing to do
+ if (!moreAvailable) {
+ continue;
}
Serializer s = new Serializer();
@@ -2134,7 +2136,6 @@
if (header != null && header.getValue().equals("0")) {
// If this happens, exit cleanly, and change the interval from push to ping
// if necessary
- mExitStatus = EXIT_DONE;
userLog("Empty sync response; finishing");
if (mMailbox.mSyncInterval == Mailbox.CHECK_INTERVAL_PUSH) {
userLog("Changing mailbox from push to ping");
@@ -2144,7 +2145,12 @@
ContentUris.withAppendedId(Mailbox.CONTENT_URI, mMailbox.mId), cv,
null, null);
}
- return;
+ if (mRequestQueue.isEmpty()) {
+ mExitStatus = EXIT_DONE;
+ return;
+ } else {
+ continue;
+ }
}
InputStream is = resp.getEntity().getContent();
if (is != null) {
diff --git a/src/com/android/exchange/SyncManager.java b/src/com/android/exchange/SyncManager.java
index a015a7f..8503f2e 100644
--- a/src/com/android/exchange/SyncManager.java
+++ b/src/com/android/exchange/SyncManager.java
@@ -2368,7 +2368,7 @@
int exitStatus = svc.mExitStatus;
switch (exitStatus) {
case AbstractSyncService.EXIT_DONE:
- if (!svc.mRequests.isEmpty()) {
+ if (svc.hasPendingRequests()) {
// TODO Handle this case
}
errorMap.remove(mailboxId);