From f22bb53aa8dbbde510ab866c6eb779126e4f5725 Mon Sep 17 00:00:00 2001 From: Nikos Gorogiannis Date: Fri, 11 May 2018 03:10:53 -0700 Subject: [PATCH] [starvation] Treat Service (but not IntentService) subclasses as on UI thread Reviewed By: jvillard Differential Revision: D7952150 fbshipit-source-id: 22ea0e0 --- infer/src/concurrency/RacerDConfig.ml | 3 ++ .../java/starvation/ServiceOnUIThread.java | 49 +++++++++++++++++++ .../codetoanalyze/java/starvation/issues.exp | 2 + 3 files changed, 54 insertions(+) create mode 100644 infer/tests/codetoanalyze/java/starvation/ServiceOnUIThread.java diff --git a/infer/src/concurrency/RacerDConfig.ml b/infer/src/concurrency/RacerDConfig.ml index 8c2a59b49..df0e4eeb8 100644 --- a/infer/src/concurrency/RacerDConfig.ml +++ b/infer/src/concurrency/RacerDConfig.ml @@ -519,6 +519,9 @@ module Models = struct match get_current_class_and_annotated_superclasses Annotations.ia_is_ui_thread tenv pname with | Some (_, _ :: _) -> true + | Some (current_class, _) -> + PatternMatch.is_subtype_of_str tenv current_class "android.app.Service" + && not (PatternMatch.is_subtype_of_str tenv current_class "android.app.IntentService") | _ -> false diff --git a/infer/tests/codetoanalyze/java/starvation/ServiceOnUIThread.java b/infer/tests/codetoanalyze/java/starvation/ServiceOnUIThread.java new file mode 100644 index 000000000..729867d85 --- /dev/null +++ b/infer/tests/codetoanalyze/java/starvation/ServiceOnUIThread.java @@ -0,0 +1,49 @@ +/* + * Copyright (c) 2018 - present Facebook, Inc. + * All rights reserved. + * + * This source code is licensed under the BSD style license found in the + * LICENSE file in the root directory of this source tree. An additional grant + * of patent rights can be found in the PATENTS file in the same directory. + */ + +import android.os.IBinder; +import android.content.Intent; +import android.app.Service; +import android.app.IntentService; +import android.os.RemoteException; + +class ServiceOnUIThread extends Service { + private final IBinder mBinder = null; + + @Override + public IBinder onBind(Intent intent) { + transactBad(); + return mBinder; + } + + void transactBad() { + try { + mBinder.transact(0, null, null, 0); + } catch (RemoteException e) {} + } +} + +class IntentServiceNotOnUIThread extends IntentService { + private final IBinder mBinder = null; + + public IntentServiceNotOnUIThread() { + super("Intent service"); + } + + @Override + public void onHandleIntent(Intent intent) { + transactOk(); + } + + void transactOk() { + try { + mBinder.transact(0, null, null, 0); + } catch (RemoteException e) {} + } +} diff --git a/infer/tests/codetoanalyze/java/starvation/issues.exp b/infer/tests/codetoanalyze/java/starvation/issues.exp index 9218d3876..a2391a66b 100644 --- a/infer/tests/codetoanalyze/java/starvation/issues.exp +++ b/infer/tests/codetoanalyze/java/starvation/issues.exp @@ -18,6 +18,8 @@ codetoanalyze/java/starvation/Interproc.java, void Interproc.interproc1Bad(Inter codetoanalyze/java/starvation/Intraproc.java, void Intraproc.intraBad(IntraprocA), 11, DEADLOCK, ERROR, [[Trace 1] void Intraproc.intraBad(IntraprocA),locks `this` in class `Intraproc*`,locks `o` in class `IntraprocA*`,[Trace 2] void IntraprocA.intraBad(Intraproc),locks `this` in class `IntraprocA*`,locks `o` in class `Intraproc*`] codetoanalyze/java/starvation/JavaIO.java, void JavaIO.fileReadBad(), 32, STARVATION, ERROR, [ void JavaIO.fileReadBad(),Method call: int JavaIO.doFileRead(),calls int InputStreamReader.read() from int JavaIO.doFileRead()] codetoanalyze/java/starvation/JavaIO.java, void JavaIO.streamReadBad(), 37, STARVATION, ERROR, [ void JavaIO.streamReadBad(),Method call: String JavaIO.doStreamRead(),calls String DataInputStream.readUTF() from String JavaIO.doStreamRead()] +codetoanalyze/java/starvation/ServiceOnUIThread.java, IBinder ServiceOnUIThread.onBind(Intent), 20, STARVATION, ERROR, [ IBinder ServiceOnUIThread.onBind(Intent),Method call: void ServiceOnUIThread.transactBad(),calls boolean IBinder.transact(int,Parcel,Parcel,int) from void ServiceOnUIThread.transactBad()] +codetoanalyze/java/starvation/ServiceOnUIThread.java, void ServiceOnUIThread.transactBad(), 25, STARVATION, ERROR, [ void ServiceOnUIThread.transactBad(),calls boolean IBinder.transact(int,Parcel,Parcel,int) from void ServiceOnUIThread.transactBad()] codetoanalyze/java/starvation/StaticLock.java, void StaticLock.lockOtherClassOneWayBad(), 24, DEADLOCK, ERROR, [[Trace 1] void StaticLock.lockOtherClassOneWayBad(),locks `StaticLock$0` in class `java.lang.Class*`,locks `this` in class `StaticLock*`,[Trace 2] void StaticLock.lockOtherClassAnotherWayNad(),locks `this` in class `StaticLock*`,Method call: void StaticLock.staticSynced(),locks `StaticLock$0` in class `java.lang.Class*`] codetoanalyze/java/starvation/UIDeadlock.java, void UIDeadlock.onUIThreadBad(), 28, DEADLOCK, ERROR, [[Trace 1] void UIDeadlock.onUIThreadBad(),locks `this` in class `UIDeadlock*`,locks `this.UIDeadlock.lockB` in class `UIDeadlock*`,[Trace 2] void UIDeadlock.notOnUIThreadBad(),locks `this.UIDeadlock.lockB` in class `UIDeadlock*`,locks `this` in class `UIDeadlock*`] codetoanalyze/java/starvation/VisDispFrame.java, void VisDispFrame.callsGetVisibleDisplayFrameOnUiThreadBad(), 19, STARVATION, ERROR, [ void VisDispFrame.callsGetVisibleDisplayFrameOnUiThreadBad(),calls void View.getWindowVisibleDisplayFrame(Rect) from void VisDispFrame.callsGetVisibleDisplayFrameOnUiThreadBad()]