summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSvet Ganov <svetoslavganov@google.com>2014-10-24 12:53:23 -0700
committerSvet Ganov <svetoslavganov@google.com>2014-10-24 13:01:54 -0700
commit4237c92d850b7fb0fa0be15df94e4d1689e353fc (patch)
tree818d3217037b06dbdc7ac67eab941dd0fa4f1ead
parentbd6fabe2ae535cf5d31fc7a1952e43ad6e653e2e (diff)
downloadframeworks_base-4237c92d850b7fb0fa0be15df94e4d1689e353fc.zip
frameworks_base-4237c92d850b7fb0fa0be15df94e4d1689e353fc.tar.gz
frameworks_base-4237c92d850b7fb0fa0be15df94e4d1689e353fc.tar.bz2
Crash in print spooler if printing app killed from recents.
If the printing app with the print UI on top is killed from recents we get a crash because: 1) the remote print document was not transitioned to a failed state if the printing app dies (this is an unrecoverable failure); 2) the print preview controller was destroyed asyncronosly during which it also asynchronously disconnects from the rendering service which however happens after the system has already cleaned up all connections of the print UI activity as it is being destoryed. bug:18109386 Change-Id: If6200b14a8aa90622228bbb659e9c4962226f561
-rw-r--r--packages/PrintSpooler/src/com/android/printspooler/model/PageContentRepository.java59
-rw-r--r--packages/PrintSpooler/src/com/android/printspooler/model/PrintSpoolerService.java6
-rw-r--r--packages/PrintSpooler/src/com/android/printspooler/model/RemotePrintDocument.java9
-rw-r--r--packages/PrintSpooler/src/com/android/printspooler/ui/PageAdapter.java21
-rw-r--r--packages/PrintSpooler/src/com/android/printspooler/ui/PrintActivity.java10
-rw-r--r--packages/PrintSpooler/src/com/android/printspooler/ui/PrintPreviewController.java25
6 files changed, 51 insertions, 79 deletions
diff --git a/packages/PrintSpooler/src/com/android/printspooler/model/PageContentRepository.java b/packages/PrintSpooler/src/com/android/printspooler/model/PageContentRepository.java
index 85b2490..acc2b69 100644
--- a/packages/PrintSpooler/src/com/android/printspooler/model/PageContentRepository.java
+++ b/packages/PrintSpooler/src/com/android/printspooler/model/PageContentRepository.java
@@ -110,13 +110,12 @@ public final class PageContentRepository {
mRenderer.close(callback);
}
- public void destroy(Runnable callback) {
- throwIfNotClosed();
+ public void destroy() {
mState = STATE_DESTROYED;
if (DEBUG) {
Log.i(LOG_TAG, "STATE_DESTROYED");
}
- doDestroy(callback);
+ mRenderer.destroy();
}
public void startPreload(int firstShownPage, int lastShownPage) {
@@ -163,21 +162,13 @@ public final class PageContentRepository {
try {
if (mState != STATE_DESTROYED) {
mCloseGuard.warnIfOpen();
- doDestroy(null);
+ destroy();
}
} finally {
super.finalize();
}
}
- private void doDestroy(Runnable callback) {
- mState = STATE_DESTROYED;
- if (DEBUG) {
- Log.i(LOG_TAG, "STATE_DESTROYED");
- }
- mRenderer.destroy(callback);
- }
-
private void throwIfNotOpened() {
if (mState != STATE_OPENED) {
throw new IllegalStateException("Not opened");
@@ -428,6 +419,7 @@ public final class PageContentRepository {
private IPdfRenderer mRenderer;
private boolean mBoundToService;
+ private boolean mDestroyed;
public AsyncRenderer(Context context, OnMalformedPdfFileListener malformedPdfFileListener) {
mContext = context;
@@ -441,7 +433,6 @@ public final class PageContentRepository {
@Override
public void onServiceConnected(ComponentName name, IBinder service) {
- mBoundToService = true;
synchronized (mLock) {
mRenderer = IPdfRenderer.Stub.asInterface(service);
mLock.notifyAll();
@@ -465,9 +456,14 @@ public final class PageContentRepository {
new AsyncTask<Void, Void, Integer>() {
@Override
protected void onPreExecute() {
+ if (mDestroyed) {
+ cancel(true);
+ return;
+ }
Intent intent = new Intent(PdfManipulationService.ACTION_GET_RENDERER);
intent.setClass(mContext, PdfManipulationService.class);
mContext.bindService(intent, AsyncRenderer.this, Context.BIND_AUTO_CREATE);
+ mBoundToService = true;
}
@Override
@@ -513,6 +509,14 @@ public final class PageContentRepository {
new AsyncTask<Void, Void, Void>() {
@Override
+ protected void onPreExecute() {
+ if (mDestroyed) {
+ cancel(true);
+ return;
+ }
+ }
+
+ @Override
protected Void doInBackground(Void... params) {
synchronized (mLock) {
try {
@@ -534,27 +538,14 @@ public final class PageContentRepository {
}.executeOnExecutor(AsyncTask.SERIAL_EXECUTOR);
}
- public void destroy(final Runnable callback) {
- new AsyncTask<Void, Void, Void>() {
- @Override
- protected Void doInBackground(Void... params) {
- return null;
- }
-
- @Override
- public void onPostExecute(Void result) {
- if (mBoundToService) {
- mBoundToService = false;
- mContext.unbindService(AsyncRenderer.this);
- }
- mPageContentCache.invalidate();
- mPageContentCache.clear();
- if (callback != null) {
- callback.run();
- }
-
- }
- }.executeOnExecutor(AsyncTask.SERIAL_EXECUTOR);
+ public void destroy() {
+ if (mBoundToService) {
+ mBoundToService = false;
+ mContext.unbindService(AsyncRenderer.this);
+ }
+ mPageContentCache.invalidate();
+ mPageContentCache.clear();
+ mDestroyed = true;
}
public void startPreload(int firstShownPage, int lastShownPage, RenderSpec renderSpec) {
diff --git a/packages/PrintSpooler/src/com/android/printspooler/model/PrintSpoolerService.java b/packages/PrintSpooler/src/com/android/printspooler/model/PrintSpoolerService.java
index 045a2f9..2cc5e04 100644
--- a/packages/PrintSpooler/src/com/android/printspooler/model/PrintSpoolerService.java
+++ b/packages/PrintSpooler/src/com/android/printspooler/model/PrintSpoolerService.java
@@ -78,7 +78,7 @@ public final class PrintSpoolerService extends Service {
private static final boolean DEBUG_PERSISTENCE = false;
- private static final boolean PERSISTNECE_MANAGER_ENABLED = true;
+ private static final boolean PERSISTENCE_MANAGER_ENABLED = true;
private static final long CHECK_ALL_PRINTJOBS_HANDLED_DELAY = 5000;
@@ -728,7 +728,7 @@ public final class PrintSpoolerService extends Service {
}
public void writeStateLocked() {
- if (!PERSISTNECE_MANAGER_ENABLED) {
+ if (!PERSISTENCE_MANAGER_ENABLED) {
return;
}
if (mWriteStateScheduled) {
@@ -935,7 +935,7 @@ public final class PrintSpoolerService extends Service {
}
public void readStateLocked() {
- if (!PERSISTNECE_MANAGER_ENABLED) {
+ if (!PERSISTENCE_MANAGER_ENABLED) {
return;
}
FileInputStream in = null;
diff --git a/packages/PrintSpooler/src/com/android/printspooler/model/RemotePrintDocument.java b/packages/PrintSpooler/src/com/android/printspooler/model/RemotePrintDocument.java
index c53fcad..f6ace41 100644
--- a/packages/PrintSpooler/src/com/android/printspooler/model/RemotePrintDocument.java
+++ b/packages/PrintSpooler/src/com/android/printspooler/model/RemotePrintDocument.java
@@ -137,7 +137,7 @@ public final class RemotePrintDocument {
private final DeathRecipient mDeathRecipient = new DeathRecipient() {
@Override
public void binderDied() {
- notifyPrintingAppDied();
+ onPrintingAppDied();
}
};
@@ -268,7 +268,7 @@ public final class RemotePrintDocument {
mPrintDocumentAdapter.finish();
mState = STATE_FINISHED;
} catch (RemoteException re) {
- Log.e(LOG_TAG, "Error calling finish()", re);
+ Log.e(LOG_TAG, "Error calling finish()");
mState = STATE_FAILED;
}
}
@@ -1108,7 +1108,8 @@ public final class RemotePrintDocument {
}
}
- private void notifyPrintingAppDied() {
+ private void onPrintingAppDied() {
+ mState = STATE_FAILED;
new Handler(mLooper).post(new Runnable() {
@Override
public void run() {
@@ -1129,7 +1130,7 @@ public final class RemotePrintDocument {
public void onDestroy() {
final RemotePrintDocument document = mWeakDocument.get();
if (document != null) {
- document.notifyPrintingAppDied();
+ document.onPrintingAppDied();
}
}
}
diff --git a/packages/PrintSpooler/src/com/android/printspooler/ui/PageAdapter.java b/packages/PrintSpooler/src/com/android/printspooler/ui/PageAdapter.java
index fbf7204..aa79568 100644
--- a/packages/PrintSpooler/src/com/android/printspooler/ui/PageAdapter.java
+++ b/packages/PrintSpooler/src/com/android/printspooler/ui/PageAdapter.java
@@ -484,9 +484,13 @@ public final class PageAdapter extends Adapter implements
return selectedPages;
}
- public void destroy(Runnable callback) {
- throwIfNotClosed();
- doDestroy(callback);
+ public void destroy() {
+ mPageContentRepository.destroy();
+ mCloseGuard.close();
+ mState = STATE_DESTROYED;
+ if (DEBUG) {
+ Log.i(LOG_TAG, "STATE_DESTROYED");
+ }
}
@Override
@@ -494,7 +498,7 @@ public final class PageAdapter extends Adapter implements
try {
if (mState != STATE_DESTROYED) {
mCloseGuard.warnIfOpen();
- doDestroy(null);
+ destroy();
}
} finally {
super.finalize();
@@ -741,15 +745,6 @@ public final class PageAdapter extends Adapter implements
mPageContentRepository.stopPreload();
}
- private void doDestroy(Runnable callback) {
- mPageContentRepository.destroy(callback);
- mCloseGuard.close();
- mState = STATE_DESTROYED;
- if (DEBUG) {
- Log.i(LOG_TAG, "STATE_DESTROYED");
- }
- }
-
private void throwIfNotOpened() {
if (mState != STATE_OPENED) {
throw new IllegalStateException("Not opened");
diff --git a/packages/PrintSpooler/src/com/android/printspooler/ui/PrintActivity.java b/packages/PrintSpooler/src/com/android/printspooler/ui/PrintActivity.java
index 21c8b83..15ea9a7 100644
--- a/packages/PrintSpooler/src/com/android/printspooler/ui/PrintActivity.java
+++ b/packages/PrintSpooler/src/com/android/printspooler/ui/PrintActivity.java
@@ -1616,15 +1616,9 @@ public class PrintActivity extends Activity implements RemotePrintDocument.Updat
mSpoolerProvider.destroy();
mPrintedDocument.finish();
mPrintedDocument.destroy();
- mPrintPreviewController.destroy(new Runnable() {
- @Override
- public void run() {
- finish();
- }
- });
- } else {
- finish();
+ mPrintPreviewController.destroy();
}
+ finish();
}
private final class SpinnerItem<T> {
diff --git a/packages/PrintSpooler/src/com/android/printspooler/ui/PrintPreviewController.java b/packages/PrintSpooler/src/com/android/printspooler/ui/PrintPreviewController.java
index e4eab10..15342ae 100644
--- a/packages/PrintSpooler/src/com/android/printspooler/ui/PrintPreviewController.java
+++ b/packages/PrintSpooler/src/com/android/printspooler/ui/PrintPreviewController.java
@@ -192,15 +192,10 @@ class PrintPreviewController implements MutexFileProvider.OnReleaseRequestCallba
});
}
- public void destroy(Runnable callback) {
- if (mPageAdapter.isOpened()) {
- Message operation = mHandler.obtainMessage(MyHandler.MSG_CLOSE);
- mHandler.enqueueOperation(operation);
- }
-
- Message operation = mHandler.obtainMessage(MyHandler.MSG_DESTROY);
- operation.obj = callback;
- mHandler.enqueueOperation(operation);
+ public void destroy() {
+ mHandler.cancelQueuedOperations();
+ mRecyclerView.setAdapter(null);
+ mPageAdapter.destroy();
}
@Override
@@ -226,7 +221,6 @@ class PrintPreviewController implements MutexFileProvider.OnReleaseRequestCallba
private final class MyHandler extends Handler {
public static final int MSG_OPEN = 1;
public static final int MSG_CLOSE = 2;
- public static final int MSG_DESTROY = 3;
public static final int MSG_UPDATE = 4;
public static final int MSG_START_PRELOAD = 5;
@@ -246,6 +240,10 @@ class PrintPreviewController implements MutexFileProvider.OnReleaseRequestCallba
super(looper, null, false);
}
+ public void cancelQueuedOperations() {
+ mPendingOperations.clear();
+ }
+
public void enqueueOperation(Message message) {
mPendingOperations.add(message);
handleNextOperation();
@@ -294,13 +292,6 @@ class PrintPreviewController implements MutexFileProvider.OnReleaseRequestCallba
});
} break;
- case MSG_DESTROY: {
- Runnable callback = (Runnable) message.obj;
- mRecyclerView.setAdapter(null);
- mPageAdapter.destroy(callback);
- handleNextOperation();
- } break;
-
case MSG_UPDATE: {
SomeArgs args = (SomeArgs) message.obj;
PageRange[] writtenPages = (PageRange[]) args.arg1;