summaryrefslogtreecommitdiffstats
path: root/core/java/android
diff options
context:
space:
mode:
Diffstat (limited to 'core/java/android')
-rw-r--r--core/java/android/app/Activity.java2
-rw-r--r--core/java/android/app/Service.java10
-rw-r--r--core/java/android/content/ContentProvider.java178
-rw-r--r--core/java/android/content/Context.java1
-rw-r--r--core/java/android/database/sqlite/SQLiteOpenHelper.java39
-rw-r--r--core/java/android/net/DownloadManager.java2
-rw-r--r--core/java/android/net/NetworkInfo.java126
-rw-r--r--core/java/android/os/StrictMode.java2
8 files changed, 242 insertions, 118 deletions
diff --git a/core/java/android/app/Activity.java b/core/java/android/app/Activity.java
index 61fd5f3..142c325 100644
--- a/core/java/android/app/Activity.java
+++ b/core/java/android/app/Activity.java
@@ -2059,7 +2059,7 @@ public class Activity extends ContextThemeWrapper
* removed. Otherwise, all entries up to but not including that entry
* will be removed
*/
- static final int POP_BACK_STACK_INCLUSIVE = 1<<0;
+ public static final int POP_BACK_STACK_INCLUSIVE = 1<<0;
/**
* Pop the top state off the back stack. Returns true if there was one
diff --git a/core/java/android/app/Service.java b/core/java/android/app/Service.java
index 697a987..b7a750b 100644
--- a/core/java/android/app/Service.java
+++ b/core/java/android/app/Service.java
@@ -400,7 +400,15 @@ public abstract class Service extends ContextWrapper implements ComponentCallbac
*
* {@sample development/samples/ApiDemos/src/com/example/android/apis/app/ForegroundService.java
* start_compatibility}
- *
+ *
+ * <p class="caution">Note that the system calls this on your
+ * service's main thread. A service's main thread is the same
+ * thread where UI operations place for Activities running in the
+ * same process. You should always avoid stalling the main
+ * thread's event loop. When doing long-running operations,
+ * network calls, or heavy disk I/O, you should kick off a new
+ * thread, or use {@link android.os.AsyncTask}.</p>
+ *
* @param intent The Intent supplied to {@link android.content.Context#startService},
* as given. This may be null if the service is being restarted after
* its process has gone away, and it had previously returned anything
diff --git a/core/java/android/content/ContentProvider.java b/core/java/android/content/ContentProvider.java
index 5fb2aae..40108c3 100644
--- a/core/java/android/content/ContentProvider.java
+++ b/core/java/android/content/ContentProvider.java
@@ -57,6 +57,7 @@ import java.util.ArrayList;
*
* <p>The primary methods that need to be implemented are:
* <ul>
+ * <li>{@link #onCreate} which is called to initialize the provider</li>
* <li>{@link #query} which returns data to the caller</li>
* <li>{@link #insert} which inserts new data into the content provider</li>
* <li>{@link #update} which updates existing data in the content provider</li>
@@ -64,8 +65,15 @@ import java.util.ArrayList;
* <li>{@link #getType} which returns the MIME type of data in the content provider</li>
* </ul></p>
*
- * <p>This class takes care of cross process calls so subclasses don't have to worry about which
- * process a request is coming from.</p>
+ * <p class="caution">Data access methods (such as {@link #insert} and
+ * {@link #update}) may be called from many threads at once, and must be thread-safe.
+ * Other methods (such as {@link #onCreate}) are only called from the application
+ * main thread, and must avoid performing lengthy operations. See the method
+ * descriptions for their expected thread behavior.</p>
+ *
+ * <p>Requests to {@link ContentResolver} are automatically forwarded to the appropriate
+ * ContentProvider instance, so subclasses don't have to worry about the details of
+ * cross-process calls.</p>
*/
public abstract class ContentProvider implements ComponentCallbacks {
/*
@@ -81,6 +89,21 @@ public abstract class ContentProvider implements ComponentCallbacks {
private Transport mTransport = new Transport();
+ /**
+ * Construct a ContentProvider instance. Content providers must be
+ * <a href="{@docRoot}guide/topics/manifest/provider-element.html">declared
+ * in the manifest</a>, accessed with {@link ContentResolver}, and created
+ * automatically by the system, so applications usually do not create
+ * ContentProvider instances directly.
+ *
+ * <p>At construction time, the object is uninitialized, and most fields and
+ * methods are unavailable. Subclasses should initialize themselves in
+ * {@link #onCreate}, not the constructor.
+ *
+ * <p>Content providers are created on the application main thread at
+ * application launch time. The constructor must not perform lengthy
+ * operations, or application startup will be delayed.
+ */
public ContentProvider() {
}
@@ -328,8 +351,8 @@ public abstract class ContentProvider implements ComponentCallbacks {
/**
- * Retrieve the Context this provider is running in. Only available once
- * onCreate(Map icicle) has been called -- this will be null in the
+ * Retrieves the Context this provider is running in. Only available once
+ * {@link #onCreate} has been called -- this will return null in the
* constructor.
*/
public final Context getContext() {
@@ -403,23 +426,59 @@ public abstract class ContentProvider implements ComponentCallbacks {
}
/**
- * Called when the provider is being started.
+ * Implement this to initialize your content provider on startup.
+ * This method is called for all registered content providers on the
+ * application main thread at application launch time. It must not perform
+ * lengthy operations, or application startup will be delayed.
+ *
+ * <p>You should defer nontrivial initialization (such as opening,
+ * upgrading, and scanning databases) until the content provider is used
+ * (via {@link #query}, {@link #insert}, etc). Deferred initialization
+ * keeps application startup fast, avoids unnecessary work if the provider
+ * turns out not to be needed, and stops database errors (such as a full
+ * disk) from halting application launch.
+ *
+ * <p>For SQL databases, {@link android.database.sqlite.SQLiteOpenHelper}
+ * is a helpful utility class that makes it easy to manage databases,
+ * and will automatically defer opening until first use. If you do use
+ * SQLiteOpenHelper, make sure to avoid calling
+ * {@link android.database.sqlite.SQLiteOpenHelper#getReadableDatabase} or
+ * {@link android.database.sqlite.SQLiteOpenHelper#getWritableDatabase}
+ * from this method. (Instead, override
+ * {@link android.database.sqlite.SQLiteOpenHelper#onOpen} to initialize the
+ * database when it is first opened.)
*
* @return true if the provider was successfully loaded, false otherwise
*/
public abstract boolean onCreate();
+ /**
+ * {@inheritDoc}
+ * This method is always called on the application main thread, and must
+ * not perform lengthy operations.
+ *
+ * <p>The default content provider implementation does nothing.
+ * Override this method to take appropriate action.
+ * (Content providers do not usually care about things like screen
+ * orientation, but may want to know about locale changes.)
+ */
public void onConfigurationChanged(Configuration newConfig) {
}
-
+
+ /**
+ * {@inheritDoc}
+ * This method is always called on the application main thread, and must
+ * not perform lengthy operations.
+ *
+ * <p>The default content provider implementation does nothing.
+ * Subclasses may override this method to take appropriate action.
+ */
public void onLowMemory() {
}
/**
- * Receives a query request from a client in a local process, and
- * returns a Cursor. This is called internally by the {@link ContentResolver}.
- * This method can be called from multiple
- * threads, as described in
+ * Implement this to handle query requests from clients.
+ * This method can be called from multiple threads, as described in
* <a href="{@docRoot}guide/topics/fundamentals.html#procthread">Application Fundamentals:
* Processes and Threads</a>.
* <p>
@@ -476,11 +535,11 @@ public abstract class ContentProvider implements ComponentCallbacks {
String selection, String[] selectionArgs, String sortOrder);
/**
- * Return the MIME type of the data at the given URI. This should start with
+ * Implement this to handle requests for the MIME type of the data at the
+ * given URI. The returned MIME type should start with
* <code>vnd.android.cursor.item</code> for a single record,
* or <code>vnd.android.cursor.dir/</code> for multiple items.
- * This method can be called from multiple
- * threads, as described in
+ * This method can be called from multiple threads, as described in
* <a href="{@docRoot}guide/topics/fundamentals.html#procthread">Application Fundamentals:
* Processes and Threads</a>.
*
@@ -490,11 +549,10 @@ public abstract class ContentProvider implements ComponentCallbacks {
public abstract String getType(Uri uri);
/**
- * Implement this to insert a new row.
+ * Implement this to handle requests to insert a new row.
* As a courtesy, call {@link ContentResolver#notifyChange(android.net.Uri ,android.database.ContentObserver) notifyChange()}
* after inserting.
- * This method can be called from multiple
- * threads, as described in
+ * This method can be called from multiple threads, as described in
* <a href="{@docRoot}guide/topics/fundamentals.html#procthread">Application Fundamentals:
* Processes and Threads</a>.
* @param uri The content:// URI of the insertion request.
@@ -504,12 +562,12 @@ public abstract class ContentProvider implements ComponentCallbacks {
public abstract Uri insert(Uri uri, ContentValues values);
/**
- * Implement this to insert a set of new rows, or the default implementation will
- * iterate over the values and call {@link #insert} on each of them.
+ * Override this to handle requests to insert a set of new rows, or the
+ * default implementation will iterate over the values and call
+ * {@link #insert} on each of them.
* As a courtesy, call {@link ContentResolver#notifyChange(android.net.Uri ,android.database.ContentObserver) notifyChange()}
* after inserting.
- * This method can be called from multiple
- * threads, as described in
+ * This method can be called from multiple threads, as described in
* <a href="{@docRoot}guide/topics/fundamentals.html#procthread">Application Fundamentals:
* Processes and Threads</a>.
*
@@ -526,13 +584,12 @@ public abstract class ContentProvider implements ComponentCallbacks {
}
/**
- * A request to delete one or more rows. The selection clause is applied when performing
- * the deletion, allowing the operation to affect multiple rows in a
- * directory.
+ * Implement this to handle requests to delete one or more rows.
+ * The implementation should apply the selection clause when performing
+ * deletion, allowing the operation to affect multiple rows in a directory.
* As a courtesy, call {@link ContentResolver#notifyChange(android.net.Uri ,android.database.ContentObserver) notifyDelete()}
* after deleting.
- * This method can be called from multiple
- * threads, as described in
+ * This method can be called from multiple threads, as described in
* <a href="{@docRoot}guide/topics/fundamentals.html#procthread">Application Fundamentals:
* Processes and Threads</a>.
*
@@ -549,13 +606,12 @@ public abstract class ContentProvider implements ComponentCallbacks {
public abstract int delete(Uri uri, String selection, String[] selectionArgs);
/**
- * Update a content URI. All rows matching the optionally provided selection
- * will have their columns listed as the keys in the values map with the
- * values of those keys.
+ * Implement this to update one or more rows.
+ * The implementation should update all rows matching the selection
+ * to set the columns according to the provided values map.
* As a courtesy, call {@link ContentResolver#notifyChange(android.net.Uri ,android.database.ContentObserver) notifyChange()}
* after updating.
- * This method can be called from multiple
- * threads, as described in
+ * This method can be called from multiple threads, as described in
* <a href="{@docRoot}guide/topics/fundamentals.html#procthread">Application Fundamentals:
* Processes and Threads</a>.
*
@@ -570,18 +626,15 @@ public abstract class ContentProvider implements ComponentCallbacks {
String[] selectionArgs);
/**
- * Open a file blob associated with a content URI.
- * This method can be called from multiple
- * threads, as described in
+ * Override this to open a file blob associated with a content URI.
+ * The default implementation always throws {@link FileNotFoundException}.
+ * This method can be called from multiple threads, as described in
* <a href="{@docRoot}guide/topics/fundamentals.html#procthread">Application Fundamentals:
* Processes and Threads</a>.
- *
- * <p>Returns a
- * ParcelFileDescriptor, from which you can obtain a
- * {@link java.io.FileDescriptor} for use with
- * {@link java.io.FileInputStream}, {@link java.io.FileOutputStream}, etc.
- * This can be used to store large data (such as an image) associated with
- * a particular piece of content.
+ *
+ * <p>Returns a ParcelFileDescriptor, which is returned directly to the
+ * caller. This way large data (such as images and documents) can be
+ * returned without copying the content.
*
* <p>The returned ParcelFileDescriptor is owned by the caller, so it is
* their responsibility to close it when done. That is, the implementation
@@ -599,31 +652,35 @@ public abstract class ContentProvider implements ComponentCallbacks {
* no file associated with the given URI or the mode is invalid.
* @throws SecurityException Throws SecurityException if the caller does
* not have permission to access the file.
- *
+ *
* @see #openAssetFile(Uri, String)
* @see #openFileHelper(Uri, String)
- */
+ */
public ParcelFileDescriptor openFile(Uri uri, String mode)
throws FileNotFoundException {
throw new FileNotFoundException("No files supported by provider at "
+ uri);
}
-
+
/**
* This is like {@link #openFile}, but can be implemented by providers
* that need to be able to return sub-sections of files, often assets
- * inside of their .apk. Note that when implementing this your clients
- * must be able to deal with such files, either directly with
- * {@link ContentResolver#openAssetFileDescriptor
- * ContentResolver.openAssetFileDescriptor}, or by using the higher-level
+ * inside of their .apk.
+ * This method can be called from multiple threads, as described in
+ * <a href="{@docRoot}guide/topics/fundamentals.html#procthread">Application Fundamentals:
+ * Processes and Threads</a>.
+ *
+ * <p>If you implement this, your clients must be able to deal with such
+ * files, either directly with
+ * {@link ContentResolver#openAssetFileDescriptor}, or by using the higher-level
* {@link ContentResolver#openInputStream ContentResolver.openInputStream}
* or {@link ContentResolver#openOutputStream ContentResolver.openOutputStream}
* methods.
- *
- * <p><em>Note: if you are implementing this to return a full file, you
+ *
+ * <p class="note">If you are implementing this to return a full file, you
* should create the AssetFileDescriptor with
* {@link AssetFileDescriptor#UNKNOWN_LENGTH} to be compatible with
- * applications that can not handle sub-sections of files.</em></p>
+ * applications that can not handle sub-sections of files.</p>
*
* @param uri The URI whose file is to be opened.
* @param mode Access mode for the file. May be "r" for read-only access,
@@ -735,17 +792,20 @@ public abstract class ContentProvider implements ComponentCallbacks {
}
/**
- * Applies each of the {@link ContentProviderOperation} objects and returns an array
- * of their results. Passes through OperationApplicationException, which may be thrown
- * by the call to {@link ContentProviderOperation#apply}.
- * If all the applications succeed then a {@link ContentProviderResult} array with the
- * same number of elements as the operations will be returned. It is implementation-specific
- * how many, if any, operations will have been successfully applied if a call to
- * apply results in a {@link OperationApplicationException}.
+ * Override this to perform a batch of operations, or the default
+ * implementation will {@link ContentProviderOperation#apply} each of the
+ * {@link ContentProviderOperation} objects. If the apply calls all succeed
+ * then a {@link ContentProviderResult} array with the same number of
+ * elements as the operations will be returned. If any of the apply calls
+ * fail, it is up to the implementation how many of the others take effect.
+ * This method can be called from multiple threads, as described in
+ * <a href="{@docRoot}guide/topics/fundamentals.html#procthread">Application Fundamentals:
+ * Processes and Threads</a>.
+ *
* @param operations the operations to apply
* @return the results of the applications
- * @throws OperationApplicationException thrown if an application fails.
- * See {@link ContentProviderOperation#apply} for more information.
+ * @throws OperationApplicationException thrown if any operation fails.
+ * @see ContentProviderOperation#apply
*/
public ContentProviderResult[] applyBatch(ArrayList<ContentProviderOperation> operations)
throws OperationApplicationException {
diff --git a/core/java/android/content/Context.java b/core/java/android/content/Context.java
index 3d64984..b5ec633 100644
--- a/core/java/android/content/Context.java
+++ b/core/java/android/content/Context.java
@@ -1566,7 +1566,6 @@ public abstract class Context {
* {@link android.net.DownloadManager} for requesting HTTP downloads.
*
* @see #getSystemService
- * @hide (TODO) for now
*/
public static final String DOWNLOAD_SERVICE = "download";
diff --git a/core/java/android/database/sqlite/SQLiteOpenHelper.java b/core/java/android/database/sqlite/SQLiteOpenHelper.java
index 0f2e872..d8cce21 100644
--- a/core/java/android/database/sqlite/SQLiteOpenHelper.java
+++ b/core/java/android/database/sqlite/SQLiteOpenHelper.java
@@ -24,10 +24,16 @@ import android.util.Log;
/**
* A helper class to manage database creation and version management.
- * You create a subclass implementing {@link #onCreate}, {@link #onUpgrade} and
+ *
+ * <p>You create a subclass implementing {@link #onCreate}, {@link #onUpgrade} and
* optionally {@link #onOpen}, and this class takes care of opening the database
* if it exists, creating it if it does not, and upgrading it as necessary.
* Transactions are used to make sure the database is always in a sensible state.
+ *
+ * <p>This class makes it easy for {@link android.content.ContentProvider}
+ * implementations to defer opening and upgrading the database until first use,
+ * to avoid blocking application startup with long-running database upgrades.
+ *
* <p>For an example, see the NotePadProvider class in the NotePad sample application,
* in the <em>samples/</em> directory of the SDK.</p>
*
@@ -51,8 +57,9 @@ public abstract class SQLiteOpenHelper {
/**
* Create a helper object to create, open, and/or manage a database.
- * The database is not actually created or opened until one of
- * {@link #getWritableDatabase} or {@link #getReadableDatabase} is called.
+ * This method always returns very quickly. The database is not actually
+ * created or opened until one of {@link #getWritableDatabase} or
+ * {@link #getReadableDatabase} is called.
*
* @param context to use to open or create the database
* @param name of the database file, or null for an in-memory database
@@ -96,13 +103,20 @@ public abstract class SQLiteOpenHelper {
/**
* Create and/or open a database that will be used for reading and writing.
- * Once opened successfully, the database is cached, so you can call this
- * method every time you need to write to the database. Make sure to call
- * {@link #close} when you no longer need it.
+ * The first time this is called, the database will be opened and
+ * {@link #onCreate}, {@link #onUpgrade} and/or {@link #onOpen} will be
+ * called.
*
- * <p>Errors such as bad permissions or a full disk may cause this operation
+ * <p>Once opened successfully, the database is cached, so you can
+ * call this method every time you need to write to the database.
+ * (Make sure to call {@link #close} when you no longer need the database.)
+ * Errors such as bad permissions or a full disk may cause this method
* to fail, but future attempts may succeed if the problem is fixed.</p>
*
+ * <p class="caution">Database upgrade may take a long time, you
+ * should not call this method from the application main thread, including
+ * from {@link android.content.ContentProvider#onCreate ContentProvider.onCreate()}.
+ *
* @throws SQLiteException if the database cannot be opened for writing
* @return a read/write database object valid until {@link #close} is called
*/
@@ -183,6 +197,11 @@ public abstract class SQLiteOpenHelper {
* database object will be closed and the read/write object will be returned
* in the future.
*
+ * <p class="caution">Like {@link #getWritableDatabase}, this method may
+ * take a long time to return, so you should not call it from the
+ * application main thread, including from
+ * {@link android.content.ContentProvider#onCreate ContentProvider.onCreate()}.
+ *
* @throws SQLiteException if the database cannot be opened
* @return a database object valid until {@link #getWritableDatabase}
* or {@link #close} is called.
@@ -262,9 +281,9 @@ public abstract class SQLiteOpenHelper {
public abstract void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion);
/**
- * Called when the database has been opened.
- * Override method should check {@link SQLiteDatabase#isReadOnly} before
- * updating the database.
+ * Called when the database has been opened. The implementation
+ * should check {@link SQLiteDatabase#isReadOnly} before updating the
+ * database.
*
* @param db The database.
*/
diff --git a/core/java/android/net/DownloadManager.java b/core/java/android/net/DownloadManager.java
index 455bd36..1d88c18 100644
--- a/core/java/android/net/DownloadManager.java
+++ b/core/java/android/net/DownloadManager.java
@@ -42,8 +42,6 @@ import java.util.Set;
* Instances of this class should be obtained through
* {@link android.content.Context#getSystemService(String)} by passing
* {@link android.content.Context#DOWNLOAD_SERVICE}.
- *
- * @hide
*/
public class DownloadManager {
/**
diff --git a/core/java/android/net/NetworkInfo.java b/core/java/android/net/NetworkInfo.java
index 21f711c..5f5e11c 100644
--- a/core/java/android/net/NetworkInfo.java
+++ b/core/java/android/net/NetworkInfo.java
@@ -97,7 +97,7 @@ public class NetworkInfo implements Parcelable {
stateMap.put(DetailedState.DISCONNECTED, State.DISCONNECTED);
stateMap.put(DetailedState.FAILED, State.DISCONNECTED);
}
-
+
private int mNetworkType;
private int mSubtype;
private String mTypeName;
@@ -144,7 +144,9 @@ public class NetworkInfo implements Parcelable {
* @return the network type
*/
public int getType() {
- return mNetworkType;
+ synchronized (this) {
+ return mNetworkType;
+ }
}
/**
@@ -153,12 +155,16 @@ public class NetworkInfo implements Parcelable {
* @return the network subtype
*/
public int getSubtype() {
- return mSubtype;
+ synchronized (this) {
+ return mSubtype;
+ }
}
void setSubtype(int subtype, String subtypeName) {
- mSubtype = subtype;
- mSubtypeName = subtypeName;
+ synchronized (this) {
+ mSubtype = subtype;
+ mSubtypeName = subtypeName;
+ }
}
/**
@@ -167,7 +173,9 @@ public class NetworkInfo implements Parcelable {
* @return the name of the network type
*/
public String getTypeName() {
- return mTypeName;
+ synchronized (this) {
+ return mTypeName;
+ }
}
/**
@@ -175,7 +183,9 @@ public class NetworkInfo implements Parcelable {
* @return the name of the network subtype
*/
public String getSubtypeName() {
- return mSubtypeName;
+ synchronized (this) {
+ return mSubtypeName;
+ }
}
/**
@@ -188,7 +198,9 @@ public class NetworkInfo implements Parcelable {
* of being established, {@code false} otherwise.
*/
public boolean isConnectedOrConnecting() {
- return mState == State.CONNECTED || mState == State.CONNECTING;
+ synchronized (this) {
+ return mState == State.CONNECTED || mState == State.CONNECTING;
+ }
}
/**
@@ -197,7 +209,9 @@ public class NetworkInfo implements Parcelable {
* @return {@code true} if network connectivity exists, {@code false} otherwise.
*/
public boolean isConnected() {
- return mState == State.CONNECTED;
+ synchronized (this) {
+ return mState == State.CONNECTED;
+ }
}
/**
@@ -213,7 +227,9 @@ public class NetworkInfo implements Parcelable {
* @return {@code true} if the network is available, {@code false} otherwise
*/
public boolean isAvailable() {
- return mIsAvailable;
+ synchronized (this) {
+ return mIsAvailable;
+ }
}
/**
@@ -223,7 +239,9 @@ public class NetworkInfo implements Parcelable {
* @hide
*/
public void setIsAvailable(boolean isAvailable) {
- mIsAvailable = isAvailable;
+ synchronized (this) {
+ mIsAvailable = isAvailable;
+ }
}
/**
@@ -234,7 +252,9 @@ public class NetworkInfo implements Parcelable {
* otherwise.
*/
public boolean isFailover() {
- return mIsFailover;
+ synchronized (this) {
+ return mIsFailover;
+ }
}
/**
@@ -244,7 +264,9 @@ public class NetworkInfo implements Parcelable {
* @hide
*/
public void setFailover(boolean isFailover) {
- mIsFailover = isFailover;
+ synchronized (this) {
+ mIsFailover = isFailover;
+ }
}
/**
@@ -254,11 +276,15 @@ public class NetworkInfo implements Parcelable {
* @return {@code true} if roaming is in effect, {@code false} otherwise.
*/
public boolean isRoaming() {
- return mIsRoaming;
+ synchronized (this) {
+ return mIsRoaming;
+ }
}
void setRoaming(boolean isRoaming) {
- mIsRoaming = isRoaming;
+ synchronized (this) {
+ mIsRoaming = isRoaming;
+ }
}
/**
@@ -266,7 +292,9 @@ public class NetworkInfo implements Parcelable {
* @return the coarse-grained state
*/
public State getState() {
- return mState;
+ synchronized (this) {
+ return mState;
+ }
}
/**
@@ -274,7 +302,9 @@ public class NetworkInfo implements Parcelable {
* @return the fine-grained state
*/
public DetailedState getDetailedState() {
- return mDetailedState;
+ synchronized (this) {
+ return mDetailedState;
+ }
}
/**
@@ -287,10 +317,12 @@ public class NetworkInfo implements Parcelable {
* @hide
*/
public void setDetailedState(DetailedState detailedState, String reason, String extraInfo) {
- this.mDetailedState = detailedState;
- this.mState = stateMap.get(detailedState);
- this.mReason = reason;
- this.mExtraInfo = extraInfo;
+ synchronized (this) {
+ this.mDetailedState = detailedState;
+ this.mState = stateMap.get(detailedState);
+ this.mReason = reason;
+ this.mExtraInfo = extraInfo;
+ }
}
/**
@@ -299,7 +331,9 @@ public class NetworkInfo implements Parcelable {
* @return the reason for failure, or null if not available
*/
public String getReason() {
- return mReason;
+ synchronized (this) {
+ return mReason;
+ }
}
/**
@@ -309,20 +343,24 @@ public class NetworkInfo implements Parcelable {
* @return the extra information, or null if not available
*/
public String getExtraInfo() {
- return mExtraInfo;
+ synchronized (this) {
+ return mExtraInfo;
+ }
}
@Override
public String toString() {
- StringBuilder builder = new StringBuilder("NetworkInfo: ");
- builder.append("type: ").append(getTypeName()).append("[").append(getSubtypeName()).
- append("], state: ").append(mState).append("/").append(mDetailedState).
- append(", reason: ").append(mReason == null ? "(unspecified)" : mReason).
- append(", extra: ").append(mExtraInfo == null ? "(none)" : mExtraInfo).
- append(", roaming: ").append(mIsRoaming).
- append(", failover: ").append(mIsFailover).
- append(", isAvailable: ").append(mIsAvailable);
- return builder.toString();
+ synchronized (this) {
+ StringBuilder builder = new StringBuilder("NetworkInfo: ");
+ builder.append("type: ").append(getTypeName()).append("[").append(getSubtypeName()).
+ append("], state: ").append(mState).append("/").append(mDetailedState).
+ append(", reason: ").append(mReason == null ? "(unspecified)" : mReason).
+ append(", extra: ").append(mExtraInfo == null ? "(none)" : mExtraInfo).
+ append(", roaming: ").append(mIsRoaming).
+ append(", failover: ").append(mIsFailover).
+ append(", isAvailable: ").append(mIsAvailable);
+ return builder.toString();
+ }
}
/**
@@ -338,17 +376,19 @@ public class NetworkInfo implements Parcelable {
* @hide
*/
public void writeToParcel(Parcel dest, int flags) {
- dest.writeInt(mNetworkType);
- dest.writeInt(mSubtype);
- dest.writeString(mTypeName);
- dest.writeString(mSubtypeName);
- dest.writeString(mState.name());
- dest.writeString(mDetailedState.name());
- dest.writeInt(mIsFailover ? 1 : 0);
- dest.writeInt(mIsAvailable ? 1 : 0);
- dest.writeInt(mIsRoaming ? 1 : 0);
- dest.writeString(mReason);
- dest.writeString(mExtraInfo);
+ synchronized (this) {
+ dest.writeInt(mNetworkType);
+ dest.writeInt(mSubtype);
+ dest.writeString(mTypeName);
+ dest.writeString(mSubtypeName);
+ dest.writeString(mState.name());
+ dest.writeString(mDetailedState.name());
+ dest.writeInt(mIsFailover ? 1 : 0);
+ dest.writeInt(mIsAvailable ? 1 : 0);
+ dest.writeInt(mIsRoaming ? 1 : 0);
+ dest.writeString(mReason);
+ dest.writeString(mExtraInfo);
+ }
}
/**
diff --git a/core/java/android/os/StrictMode.java b/core/java/android/os/StrictMode.java
index dc92590..d4b0500 100644
--- a/core/java/android/os/StrictMode.java
+++ b/core/java/android/os/StrictMode.java
@@ -97,7 +97,7 @@ public final class StrictMode {
* via Parcel.writeNoException() (amusingly) where the caller can
* choose how to react.
*/
- private static ThreadLocal<ArrayList<ApplicationErrorReport.CrashInfo>> gatheredViolations =
+ private static final ThreadLocal<ArrayList<ApplicationErrorReport.CrashInfo>> gatheredViolations =
new ThreadLocal<ArrayList<ApplicationErrorReport.CrashInfo>>() {
@Override protected ArrayList<ApplicationErrorReport.CrashInfo> initialValue() {
// Starts null to avoid unnecessary allocations when