summaryrefslogtreecommitdiffstats
path: root/core/java
diff options
context:
space:
mode:
Diffstat (limited to 'core/java')
-rw-r--r--core/java/android/app/ActivityThread.java4
-rw-r--r--core/java/android/app/LoadedApk.java14
-rw-r--r--core/java/android/os/Message.java17
-rw-r--r--core/java/android/text/SpannableStringBuilder.java132
-rw-r--r--core/java/android/view/DisplayList.java24
-rw-r--r--core/java/android/view/GLES20Canvas.java7
-rw-r--r--core/java/android/view/GLES20DisplayList.java16
-rw-r--r--core/java/android/view/HardwareCanvas.java12
-rw-r--r--core/java/android/view/HardwareRenderer.java74
-rwxr-xr-xcore/java/android/view/KeyEvent.java28
-rw-r--r--core/java/android/view/View.java91
-rw-r--r--core/java/android/view/WindowManagerImpl.java7
-rw-r--r--core/java/android/webkit/WebViewClassic.java9
-rw-r--r--core/java/android/webkit/WebViewCore.java13
-rw-r--r--core/java/android/widget/RemoteViewsAdapter.java21
-rw-r--r--core/java/com/google/android/mms/pdu/PduPersister.java177
16 files changed, 397 insertions, 249 deletions
diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java
index ab4e73d..98c4e10 100644
--- a/core/java/android/app/ActivityThread.java
+++ b/core/java/android/app/ActivityThread.java
@@ -174,8 +174,10 @@ public final class ActivityThread {
static final ThreadLocal<ActivityThread> sThreadLocal = new ThreadLocal<ActivityThread>();
Instrumentation mInstrumentation;
String mInstrumentationAppDir = null;
+ String mInstrumentationAppLibraryDir = null;
String mInstrumentationAppPackage = null;
String mInstrumentedAppDir = null;
+ String mInstrumentedAppLibraryDir = null;
boolean mSystemThread = false;
boolean mJitEnabled = false;
@@ -3936,8 +3938,10 @@ public final class ActivityThread {
}
mInstrumentationAppDir = ii.sourceDir;
+ mInstrumentationAppLibraryDir = ii.nativeLibraryDir;
mInstrumentationAppPackage = ii.packageName;
mInstrumentedAppDir = data.info.getAppDir();
+ mInstrumentedAppLibraryDir = data.info.getLibDir();
ApplicationInfo instrApp = new ApplicationInfo();
instrApp.packageName = ii.packageName;
diff --git a/core/java/android/app/LoadedApk.java b/core/java/android/app/LoadedApk.java
index 5340fbb..8ab1ed6 100644
--- a/core/java/android/app/LoadedApk.java
+++ b/core/java/android/app/LoadedApk.java
@@ -261,6 +261,7 @@ public final class LoadedApk {
if (mIncludeCode && !mPackageName.equals("android")) {
String zip = mAppDir;
+ String libraryPath = mLibDir;
/*
* The following is a bit of a hack to inject
@@ -273,15 +274,20 @@ public final class LoadedApk {
String instrumentationAppDir =
mActivityThread.mInstrumentationAppDir;
+ String instrumentationAppLibraryDir =
+ mActivityThread.mInstrumentationAppLibraryDir;
String instrumentationAppPackage =
mActivityThread.mInstrumentationAppPackage;
String instrumentedAppDir =
mActivityThread.mInstrumentedAppDir;
+ String instrumentedAppLibraryDir =
+ mActivityThread.mInstrumentedAppLibraryDir;
String[] instrumentationLibs = null;
if (mAppDir.equals(instrumentationAppDir)
|| mAppDir.equals(instrumentedAppDir)) {
zip = instrumentationAppDir + ":" + instrumentedAppDir;
+ libraryPath = instrumentationAppLibraryDir + ":" + instrumentedAppLibraryDir;
if (! instrumentedAppDir.equals(instrumentationAppDir)) {
instrumentationLibs =
getLibrariesFor(instrumentationAppPackage);
@@ -301,7 +307,7 @@ public final class LoadedApk {
*/
if (ActivityThread.localLOGV)
- Slog.v(ActivityThread.TAG, "Class path: " + zip + ", JNI path: " + mLibDir);
+ Slog.v(ActivityThread.TAG, "Class path: " + zip + ", JNI path: " + libraryPath);
// Temporarily disable logging of disk reads on the Looper thread
// as this is early and necessary.
@@ -309,7 +315,7 @@ public final class LoadedApk {
mClassLoader =
ApplicationLoaders.getDefault().getClassLoader(
- zip, mLibDir, mBaseClassLoader);
+ zip, libraryPath, mBaseClassLoader);
initializeJavaContextClassLoader();
StrictMode.setThreadPolicy(oldPolicy);
@@ -442,6 +448,10 @@ public final class LoadedApk {
return mAppDir;
}
+ public String getLibDir() {
+ return mLibDir;
+ }
+
public String getResDir() {
return mResDir;
}
diff --git a/core/java/android/os/Message.java b/core/java/android/os/Message.java
index b816b11..4aa7fe2 100644
--- a/core/java/android/os/Message.java
+++ b/core/java/android/os/Message.java
@@ -16,9 +16,6 @@
package android.os;
-import android.os.Bundle;
-import android.os.Parcel;
-import android.os.Parcelable;
import android.util.TimeUtils;
/**
@@ -368,13 +365,13 @@ public final class Message implements Parcelable {
*
* Asynchronous messages represent interrupts or events that do not require global ordering
* with represent to synchronous messages. Asynchronous messages are not subject to
- * the synchronization barriers introduced by {@link MessageQueue#acquireSyncBarrier()}.
+ * the synchronization barriers introduced by {@link MessageQueue#enqueueSyncBarrier(long)}.
*
* @return True if the message is asynchronous.
*
* @see #setAsynchronous(boolean)
- * @see MessageQueue#acquireSyncBarrier()
- * @see MessageQueue#releaseSyncBarrier()
+ * @see MessageQueue#enqueueSyncBarrier(long)
+ * @see MessageQueue#removeSyncBarrier(int)
*
* @hide
*/
@@ -387,13 +384,13 @@ public final class Message implements Parcelable {
*
* Asynchronous messages represent interrupts or events that do not require global ordering
* with represent to synchronous messages. Asynchronous messages are not subject to
- * the synchronization barriers introduced by {@link MessageQueue#acquireSyncBarrier()}.
+ * the synchronization barriers introduced by {@link MessageQueue#enqueueSyncBarrier(long)}.
*
* @param async True if the message is asynchronous.
*
* @see #isAsynchronous()
- * @see MessageQueue#acquireSyncBarrier()
- * @see MessageQueue#releaseSyncBarrier()
+ * @see MessageQueue#enqueueSyncBarrier(long)
+ * @see MessageQueue#removeSyncBarrier(int)
*
* @hide
*/
@@ -506,7 +503,7 @@ public final class Message implements Parcelable {
Messenger.writeMessengerOrNullToParcel(replyTo, dest);
}
- private final void readFromParcel(Parcel source) {
+ private void readFromParcel(Parcel source) {
what = source.readInt();
arg1 = source.readInt();
arg2 = source.readInt();
diff --git a/core/java/android/text/SpannableStringBuilder.java b/core/java/android/text/SpannableStringBuilder.java
index d0c87c6..f7a7eb8 100644
--- a/core/java/android/text/SpannableStringBuilder.java
+++ b/core/java/android/text/SpannableStringBuilder.java
@@ -262,19 +262,8 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
return append(String.valueOf(text));
}
- private int change(int start, int end, CharSequence tb, int tbstart, int tbend) {
- return change(true, start, end, tb, tbstart, tbend);
- }
-
- private int change(boolean notify, int start, int end,
- CharSequence tb, int tbstart, int tbend) {
+ private void change(int start, int end, CharSequence tb, int tbstart, int tbend) {
checkRange("replace", start, end);
- int ret = tbend - tbstart;
- TextWatcher[] recipients = null;
-
- if (notify) {
- recipients = sendTextWillChange(start, end - start, tbend - tbstart);
- }
for (int i = mSpanCount - 1; i >= 0; i--) {
if ((mSpanFlags[i] & SPAN_PARAGRAPH) == SPAN_PARAGRAPH) {
@@ -338,7 +327,7 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
en = tbend;
if (getSpanStart(spans[i]) < 0) {
- setSpan(true, spans[i],
+ setSpan(false, spans[i],
st - tbstart + start,
en - tbstart + start,
sp.getSpanFlags(spans[i]));
@@ -346,51 +335,37 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
}
}
- // no need for span fixup on pure insertion
- if (tbend > tbstart && end - start == 0) {
- if (notify) {
- sendTextChange(recipients, start, end - start, tbend - tbstart);
- sendTextHasChanged(recipients);
- }
-
- return ret;
- }
-
- boolean atend = (mGapStart + mGapLength == mText.length);
+ if (end > start) {
+ // no need for span fixup on pure insertion
+ boolean atEnd = (mGapStart + mGapLength == mText.length);
- for (int i = mSpanCount - 1; i >= 0; i--) {
- if (mSpanStarts[i] >= start &&
- mSpanStarts[i] < mGapStart + mGapLength) {
- int flag = (mSpanFlags[i] & START_MASK) >> START_SHIFT;
+ for (int i = mSpanCount - 1; i >= 0; i--) {
+ if (mSpanStarts[i] >= start &&
+ mSpanStarts[i] < mGapStart + mGapLength) {
+ int flag = (mSpanFlags[i] & START_MASK) >> START_SHIFT;
- if (flag == POINT || (flag == PARAGRAPH && atend))
+ if (flag == POINT || (flag == PARAGRAPH && atEnd))
mSpanStarts[i] = mGapStart + mGapLength;
else
mSpanStarts[i] = start;
- }
+ }
- if (mSpanEnds[i] >= start &&
- mSpanEnds[i] < mGapStart + mGapLength) {
- int flag = (mSpanFlags[i] & END_MASK);
+ if (mSpanEnds[i] >= start &&
+ mSpanEnds[i] < mGapStart + mGapLength) {
+ int flag = (mSpanFlags[i] & END_MASK);
- if (flag == POINT || (flag == PARAGRAPH && atend))
- mSpanEnds[i] = mGapStart + mGapLength;
- else
- mSpanEnds[i] = start;
- }
+ if (flag == POINT || (flag == PARAGRAPH && atEnd))
+ mSpanEnds[i] = mGapStart + mGapLength;
+ else
+ mSpanEnds[i] = start;
+ }
- // remove 0-length SPAN_EXCLUSIVE_EXCLUSIVE
- if (mSpanEnds[i] < mSpanStarts[i]) {
- removeSpan(i);
+ // remove 0-length SPAN_EXCLUSIVE_EXCLUSIVE
+ if (mSpanEnds[i] < mSpanStarts[i]) {
+ removeSpan(i);
+ }
}
}
-
- if (notify) {
- sendTextChange(recipients, start, end - start, tbend - tbstart);
- sendTextHasChanged(recipients);
- }
-
- return ret;
}
private void removeSpan(int i) {
@@ -425,8 +400,7 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
CharSequence tb, int tbstart, int tbend) {
int filtercount = mFilters.length;
for (int i = 0; i < filtercount; i++) {
- CharSequence repl = mFilters[i].filter(tb, tbstart, tbend,
- this, start, end);
+ CharSequence repl = mFilters[i].filter(tb, tbstart, tbend, this, start, end);
if (repl != null) {
tb = repl;
@@ -435,11 +409,17 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
}
}
- if (end == start && tbstart == tbend) {
+ final int origLen = end - start;
+ final int newLen = tbend - tbstart;
+
+ if (origLen == 0 && newLen == 0) {
return this;
}
- if (end == start || tbstart == tbend) {
+ TextWatcher[] textWatchers = getSpans(start, start + origLen, TextWatcher.class);
+ sendBeforeTextChanged(textWatchers, start, origLen, newLen);
+
+ if (origLen == 0 || newLen == 0) {
change(start, end, tb, tbstart, tbend);
} else {
int selstart = Selection.getSelectionStart(this);
@@ -450,11 +430,6 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
checkRange("replace", start, end);
moveGapTo(end);
- TextWatcher[] recipients;
-
- int origlen = end - start;
-
- recipients = sendTextWillChange(start, origlen, tbend - tbstart);
if (mGapLength < 2)
resizeFor(length() + 1);
@@ -475,9 +450,9 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
new Exception("mGapLength < 1").printStackTrace();
}
- int inserted = change(false, start + 1, start + 1, tb, tbstart, tbend);
- change(false, start, start + 1, "", 0, 0);
- change(false, start + inserted, start + inserted + origlen, "", 0, 0);
+ change(start + 1, start + 1, tb, tbstart, tbend);
+ change(start, start + 1, "", 0, 0);
+ change(start + newLen, start + newLen + origLen, "", 0, 0);
/*
* Special case to keep the cursor in the same position
@@ -490,7 +465,7 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
if (selstart > start && selstart < end) {
long off = selstart - start;
- off = off * inserted / (end - start);
+ off = off * newLen / (end - start);
selstart = (int) off + start;
setSpan(false, Selection.SELECTION_START, selstart, selstart,
@@ -499,15 +474,16 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
if (selend > start && selend < end) {
long off = selend - start;
- off = off * inserted / (end - start);
+ off = off * newLen / (end - start);
selend = (int) off + start;
setSpan(false, Selection.SELECTION_END, selend, selend, Spanned.SPAN_POINT_POINT);
}
- sendTextChange(recipients, start, origlen, inserted);
- sendTextHasChanged(recipients);
}
+ sendTextChanged(textWatchers, start, origLen, newLen);
+ sendAfterTextChanged(textWatchers);
+
return this;
}
@@ -872,30 +848,27 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
return new String(buf);
}
- private TextWatcher[] sendTextWillChange(int start, int before, int after) {
- TextWatcher[] recip = getSpans(start, start + before, TextWatcher.class);
- int n = recip.length;
+ private void sendBeforeTextChanged(TextWatcher[] watchers, int start, int before, int after) {
+ int n = watchers.length;
for (int i = 0; i < n; i++) {
- recip[i].beforeTextChanged(this, start, before, after);
+ watchers[i].beforeTextChanged(this, start, before, after);
}
-
- return recip;
}
- private void sendTextChange(TextWatcher[] recip, int start, int before, int after) {
- int n = recip.length;
+ private void sendTextChanged(TextWatcher[] watchers, int start, int before, int after) {
+ int n = watchers.length;
for (int i = 0; i < n; i++) {
- recip[i].onTextChanged(this, start, before, after);
+ watchers[i].onTextChanged(this, start, before, after);
}
}
- private void sendTextHasChanged(TextWatcher[] recip) {
- int n = recip.length;
+ private void sendAfterTextChanged(TextWatcher[] watchers) {
+ int n = watchers.length;
for (int i = 0; i < n; i++) {
- recip[i].afterTextChanged(this);
+ watchers[i].afterTextChanged(this);
}
}
@@ -1037,8 +1010,7 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
* Don't call this yourself -- exists for Canvas to use internally.
* {@hide}
*/
- public void drawText(Canvas c, int start, int end,
- float x, float y, Paint p) {
+ public void drawText(Canvas c, int start, int end, float x, float y, Paint p) {
checkRange("drawText", start, end);
if (end <= mGapStart) {
@@ -1059,8 +1031,7 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
* Don't call this yourself -- exists for Canvas to use internally.
* {@hide}
*/
- public void drawTextRun(Canvas c, int start, int end,
- int contextStart, int contextEnd,
+ public void drawTextRun(Canvas c, int start, int end, int contextStart, int contextEnd,
float x, float y, int flags, Paint p) {
checkRange("drawTextRun", start, end);
@@ -1262,6 +1233,7 @@ public class SpannableStringBuilder implements CharSequence, GetChars, Spannable
private int[] mSpanFlags;
private int mSpanCount;
+ // TODO These value are tightly related to the public SPAN_MARK/POINT values in {@link Spanned}
private static final int POINT = 2;
private static final int PARAGRAPH = 3;
diff --git a/core/java/android/view/DisplayList.java b/core/java/android/view/DisplayList.java
index e2aafa9..33631b7 100644
--- a/core/java/android/view/DisplayList.java
+++ b/core/java/android/view/DisplayList.java
@@ -16,6 +16,8 @@
package android.view;
+import android.graphics.Matrix;
+
/**
* A display lists records a series of graphics related operation and can replay
* them later. Display lists are usually built by recording operations on a
@@ -117,12 +119,26 @@ public abstract class DisplayList {
public abstract void setClipChildren(boolean clipChildren);
/**
- * Set the application scale on the DisplayList. This scale is incurred by applications that
- * are auto-scaled for compatibility reasons. By default, the value is 1 (unscaled).
+ * Set the static matrix on the DisplayList. This matrix exists if a custom ViewGroup
+ * overrides
+ * {@link ViewGroup#getChildStaticTransformation(View, android.view.animation.Transformation)}
+ * and also has {@link ViewGroup#setStaticTransformationsEnabled(boolean)} set to true.
+ * This matrix will be concatenated with any other matrices in the DisplayList to position
+ * the view appropriately.
+ *
+ * @param matrix The matrix
+ */
+ public abstract void setStaticMatrix(Matrix matrix);
+
+ /**
+ * Set the Animation matrix on the DisplayList. This matrix exists if an Animation is
+ * currently playing on a View, and is set on the DisplayList during at draw() time. When
+ * the Animation finishes, the matrix should be cleared by sending <code>null</code>
+ * for the matrix parameter.
*
- * @param scale The scaling factor
+ * @param matrix The matrix, null indicates that the matrix should be cleared.
*/
- public abstract void setApplicationScale(float scale);
+ public abstract void setAnimationMatrix(Matrix matrix);
/**
* Sets the alpha value for the DisplayList
diff --git a/core/java/android/view/GLES20Canvas.java b/core/java/android/view/GLES20Canvas.java
index 5b0433e..bedafc7 100644
--- a/core/java/android/view/GLES20Canvas.java
+++ b/core/java/android/view/GLES20Canvas.java
@@ -259,6 +259,13 @@ class GLES20Canvas extends HardwareCanvas {
private static native int nCallDrawGLFunction(int renderer, int drawGLFunction);
+ @Override
+ public int invokeFunctors(Rect dirty) {
+ return nInvokeFunctors(mRenderer, dirty);
+ }
+
+ private static native int nInvokeFunctors(int renderer, Rect dirty);
+
///////////////////////////////////////////////////////////////////////////
// Memory
///////////////////////////////////////////////////////////////////////////
diff --git a/core/java/android/view/GLES20DisplayList.java b/core/java/android/view/GLES20DisplayList.java
index 9b4cf21..bc3bce0 100644
--- a/core/java/android/view/GLES20DisplayList.java
+++ b/core/java/android/view/GLES20DisplayList.java
@@ -17,6 +17,7 @@
package android.view;
import android.graphics.Bitmap;
+import android.graphics.Matrix;
import java.util.ArrayList;
@@ -119,9 +120,18 @@ class GLES20DisplayList extends DisplayList {
}
@Override
- public void setApplicationScale(float scale) {
+ public void setStaticMatrix(Matrix matrix) {
try {
- nSetApplicationScale(getNativeDisplayList(), scale);
+ nSetStaticMatrix(getNativeDisplayList(), matrix.native_instance);
+ } catch (IllegalStateException e) {
+ // invalid DisplayList okay: we'll set current values the next time we render to it
+ }
+ }
+
+ @Override
+ public void setAnimationMatrix(Matrix matrix) {
+ try {
+ nSetAnimationMatrix(getNativeDisplayList(), matrix.native_instance);
} catch (IllegalStateException e) {
// invalid DisplayList okay: we'll set current values the next time we render to it
}
@@ -335,6 +345,8 @@ class GLES20DisplayList extends DisplayList {
private static native void nSetTransformationInfo(int displayList, float alpha,
float translationX, float translationY, float rotation, float rotationX,
float rotationY, float scaleX, float scaleY);
+ private static native void nSetStaticMatrix(int displayList, int nativeMatrix);
+ private static native void nSetAnimationMatrix(int displayList, int animationMatrix);
///////////////////////////////////////////////////////////////////////////
diff --git a/core/java/android/view/HardwareCanvas.java b/core/java/android/view/HardwareCanvas.java
index 2636ea2..de8c62d 100644
--- a/core/java/android/view/HardwareCanvas.java
+++ b/core/java/android/view/HardwareCanvas.java
@@ -98,4 +98,16 @@ public abstract class HardwareCanvas extends Canvas {
// Noop - this is done in the display list recorder subclass
return DisplayList.STATUS_DONE;
}
+
+ /**
+ * Invoke all the functors who requested to be invoked during the previous frame.
+ *
+ * @param dirty The region to redraw when the functors return {@link DisplayList#STATUS_DRAW}
+ *
+ * @return One of {@link DisplayList#STATUS_DONE}, {@link DisplayList#STATUS_DRAW} or
+ * {@link DisplayList#STATUS_INVOKE}
+ */
+ public int invokeFunctors(Rect dirty) {
+ return DisplayList.STATUS_DONE;
+ }
}
diff --git a/core/java/android/view/HardwareRenderer.java b/core/java/android/view/HardwareRenderer.java
index be640dc..b100a0c 100644
--- a/core/java/android/view/HardwareRenderer.java
+++ b/core/java/android/view/HardwareRenderer.java
@@ -259,7 +259,14 @@ public abstract class HardwareRenderer {
* @param pw
*/
abstract void dumpGfxInfo(PrintWriter pw);
-
+
+ /**
+ * Outputs the total number of frames rendered (used for fps calculations)
+ *
+ * @return the number of frames rendered
+ */
+ abstract long getFrameCount();
+
/**
* Sets the directory to use as a persistent storage for hardware rendering
* resources.
@@ -495,7 +502,9 @@ public abstract class HardwareRenderer {
static final int SURFACE_STATE_ERROR = 0;
static final int SURFACE_STATE_SUCCESS = 1;
static final int SURFACE_STATE_UPDATED = 2;
-
+
+ static final int FUNCTOR_PROCESS_DELAY = 2;
+
static EGL10 sEgl;
static EGLDisplay sEglDisplay;
static EGLConfig sEglConfig;
@@ -513,7 +522,7 @@ public abstract class HardwareRenderer {
GL mGl;
HardwareCanvas mCanvas;
- int mFrameCount;
+ long mFrameCount;
Paint mDebugPaint;
static boolean sDirtyRegions;
@@ -542,7 +551,9 @@ public abstract class HardwareRenderer {
private boolean mDestroyed;
private final Rect mRedrawClip = new Rect();
+
private final int[] mSurfaceSize = new int[2];
+ private final FunctorsRunnable mFunctorsRunnable = new FunctorsRunnable();
GlRenderer(int glVersion, boolean translucent) {
mGlVersion = glVersion;
@@ -591,6 +602,11 @@ public abstract class HardwareRenderer {
}
}
+ @Override
+ long getFrameCount() {
+ return mFrameCount;
+ }
+
/**
* Indicates whether this renderer instance can track and update dirty regions.
*/
@@ -945,6 +961,24 @@ public abstract class HardwareRenderer {
void onPostDraw() {
}
+ class FunctorsRunnable implements Runnable {
+ View.AttachInfo attachInfo;
+
+ @Override
+ public void run() {
+ final HardwareRenderer renderer = attachInfo.mHardwareRenderer;
+ if (renderer == null || !renderer.isEnabled() || renderer != GlRenderer.this) {
+ return;
+ }
+
+ final int surfaceState = checkCurrent();
+ if (surfaceState != SURFACE_STATE_ERROR) {
+ int status = mCanvas.invokeFunctors(mRedrawClip);
+ handleFunctorStatus(attachInfo, status);
+ }
+ }
+ }
+
@Override
boolean draw(View view, View.AttachInfo attachInfo, HardwareDrawCallbacks callbacks,
Rect dirty) {
@@ -1039,15 +1073,7 @@ public abstract class HardwareRenderer {
}
}
- if (status != DisplayList.STATUS_DONE) {
- if (mRedrawClip.isEmpty()) {
- attachInfo.mViewRootImpl.invalidate();
- } else {
- attachInfo.mViewRootImpl.invalidateChildInParent(
- null, mRedrawClip);
- mRedrawClip.setEmpty();
- }
- }
+ handleFunctorStatus(attachInfo, status);
} else {
// Shouldn't reach here
view.draw(canvas);
@@ -1056,13 +1082,13 @@ public abstract class HardwareRenderer {
callbacks.onHardwarePostDraw(canvas);
canvas.restoreToCount(saveCount);
view.mRecreateDisplayList = false;
-
+ mFrameCount++;
if (mDebugDirtyRegions) {
if (mDebugPaint == null) {
mDebugPaint = new Paint();
mDebugPaint.setColor(0x7fff0000);
}
- if (dirty != null && (mFrameCount++ & 1) == 0) {
+ if (dirty != null && (mFrameCount & 1) == 0) {
canvas.drawRect(dirty, mDebugPaint);
}
}
@@ -1099,6 +1125,26 @@ public abstract class HardwareRenderer {
return false;
}
+ private void handleFunctorStatus(View.AttachInfo attachInfo, int status) {
+ // If the draw flag is set, functors will be invoked while executing
+ // the tree of display lists
+ if ((status & DisplayList.STATUS_DRAW) != 0) {
+ if (mRedrawClip.isEmpty()) {
+ attachInfo.mViewRootImpl.invalidate();
+ } else {
+ attachInfo.mViewRootImpl.invalidateChildInParent(null, mRedrawClip);
+ mRedrawClip.setEmpty();
+ }
+ }
+
+ if ((status & DisplayList.STATUS_INVOKE) != 0) {
+ attachInfo.mHandler.removeCallbacks(mFunctorsRunnable);
+ mFunctorsRunnable.attachInfo = attachInfo;
+ // delay the functor callback by a few ms so it isn't polled constantly
+ attachInfo.mHandler.postDelayed(mFunctorsRunnable, FUNCTOR_PROCESS_DELAY);
+ }
+ }
+
/**
* Ensures the current EGL context is the one we expect.
*
diff --git a/core/java/android/view/KeyEvent.java b/core/java/android/view/KeyEvent.java
index 104ed6a..e4a4a75 100755
--- a/core/java/android/view/KeyEvent.java
+++ b/core/java/android/view/KeyEvent.java
@@ -591,8 +591,24 @@ public class KeyEvent extends InputEvent implements Parcelable {
/** Key code constant: Calculator special function key.
* Used to launch a calculator application. */
public static final int KEYCODE_CALCULATOR = 210;
-
- private static final int LAST_KEYCODE = KEYCODE_CALCULATOR;
+ /** Key code constant: Japanese full-width / half-width key. */
+ public static final int KEYCODE_ZENKAKU_HANKAKU = 211;
+ /** Key code constant: Japanese alphanumeric key. */
+ public static final int KEYCODE_EISU = 212;
+ /** Key code constant: Japanese non-conversion key. */
+ public static final int KEYCODE_MUHENKAN = 213;
+ /** Key code constant: Japanese conversion key. */
+ public static final int KEYCODE_HENKAN = 214;
+ /** Key code constant: Japanese katakana / hiragana key. */
+ public static final int KEYCODE_KATAKANA_HIRAGANA = 215;
+ /** Key code constant: Japanese Yen key. */
+ public static final int KEYCODE_YEN = 216;
+ /** Key code constant: Japanese Ro key. */
+ public static final int KEYCODE_RO = 217;
+ /** Key code constant: Japanese kana key. */
+ public static final int KEYCODE_KANA = 218;
+
+ private static final int LAST_KEYCODE = KEYCODE_KANA;
// NOTE: If you add a new keycode here you must also add it to:
// isSystem()
@@ -825,6 +841,14 @@ public class KeyEvent extends InputEvent implements Parcelable {
names.append(KEYCODE_CALENDAR, "KEYCODE_CALENDAR");
names.append(KEYCODE_MUSIC, "KEYCODE_MUSIC");
names.append(KEYCODE_CALCULATOR, "KEYCODE_CALCULATOR");
+ names.append(KEYCODE_ZENKAKU_HANKAKU, "KEYCODE_ZENKAKU_HANKAKU");
+ names.append(KEYCODE_EISU, "KEYCODE_EISU");
+ names.append(KEYCODE_MUHENKAN, "KEYCODE_MUHENKAN");
+ names.append(KEYCODE_HENKAN, "KEYCODE_HENKAN");
+ names.append(KEYCODE_KATAKANA_HIRAGANA, "KEYCODE_KATAKANA_HIRAGANA");
+ names.append(KEYCODE_YEN, "KEYCODE_YEN");
+ names.append(KEYCODE_RO, "KEYCODE_RO");
+ names.append(KEYCODE_KANA, "KEYCODE_KANA");
};
// Symbolic names of all metakeys in bit order from least significant to most significant.
diff --git a/core/java/android/view/View.java b/core/java/android/view/View.java
index 81f3f6a..18e1697 100644
--- a/core/java/android/view/View.java
+++ b/core/java/android/view/View.java
@@ -1464,7 +1464,7 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
* apps.
* @hide
*/
- public static final boolean USE_DISPLAY_LIST_PROPERTIES = false;
+ public static final boolean USE_DISPLAY_LIST_PROPERTIES = true;
/**
* Map used to store views' tags.
@@ -11529,12 +11529,34 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
displayList.setClipChildren(
(((ViewGroup)mParent).mGroupFlags & ViewGroup.FLAG_CLIP_CHILDREN) != 0);
}
- if (mAttachInfo != null && mAttachInfo.mScalingRequired &&
- mAttachInfo.mApplicationScale != 1.0f) {
- displayList.setApplicationScale(1f / mAttachInfo.mApplicationScale);
+ float alpha = 1;
+ if (mParent instanceof ViewGroup && (((ViewGroup) mParent).mGroupFlags &
+ ViewGroup.FLAG_SUPPORT_STATIC_TRANSFORMATIONS) != 0) {
+ ViewGroup parentVG = (ViewGroup) mParent;
+ final boolean hasTransform =
+ parentVG.getChildStaticTransformation(this, parentVG.mChildTransformation);
+ if (hasTransform) {
+ Transformation transform = parentVG.mChildTransformation;
+ final int transformType = parentVG.mChildTransformation.getTransformationType();
+ if (transformType != Transformation.TYPE_IDENTITY) {
+ if ((transformType & Transformation.TYPE_ALPHA) != 0) {
+ alpha = transform.getAlpha();
+ }
+ if ((transformType & Transformation.TYPE_MATRIX) != 0) {
+ displayList.setStaticMatrix(transform.getMatrix());
+ }
+ }
+ }
}
if (mTransformationInfo != null) {
- displayList.setTransformationInfo(mTransformationInfo.mAlpha,
+ alpha *= mTransformationInfo.mAlpha;
+ if (alpha < 1) {
+ final int multipliedAlpha = (int) (255 * alpha);
+ if (onSetAlpha(multipliedAlpha)) {
+ alpha = 1;
+ }
+ }
+ displayList.setTransformationInfo(alpha,
mTransformationInfo.mTranslationX, mTransformationInfo.mTranslationY,
mTransformationInfo.mRotation, mTransformationInfo.mRotationX,
mTransformationInfo.mRotationY, mTransformationInfo.mScaleX,
@@ -11548,6 +11570,8 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
displayList.setPivotX(getPivotX());
displayList.setPivotY(getPivotY());
}
+ } else if (alpha < 1) {
+ displayList.setAlpha(alpha);
}
}
}
@@ -11580,6 +11604,7 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
if ((flags & ViewGroup.FLAG_CHILDREN_DRAWN_WITH_CACHE) != 0 ||
(flags & ViewGroup.FLAG_ALWAYS_DRAWN_WITH_CACHE) != 0) {
caching = true;
+ // Auto-scaled apps are not hw-accelerated, no need to set scaling flag on DisplayList
if (mAttachInfo != null) scalingRequired = mAttachInfo.mScalingRequired;
} else {
caching = (layerType != LAYER_TYPE_NONE) || hardwareAccelerated;
@@ -11590,7 +11615,8 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
more = drawAnimation(parent, drawingTime, a, scalingRequired);
concatMatrix = a.willChangeTransformationMatrix();
transformToApply = parent.mChildTransformation;
- } else if ((flags & ViewGroup.FLAG_SUPPORT_STATIC_TRANSFORMATIONS) != 0) {
+ } else if (!useDisplayListProperties &&
+ (flags & ViewGroup.FLAG_SUPPORT_STATIC_TRANSFORMATIONS) != 0) {
final boolean hasTransform =
parent.getChildStaticTransformation(this, parent.mChildTransformation);
if (hasTransform) {
@@ -11658,6 +11684,17 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
}
}
useDisplayListProperties &= hasDisplayList;
+ if (useDisplayListProperties) {
+ displayList = getDisplayList();
+ if (!displayList.isValid()) {
+ // Uncommon, but possible. If a view is removed from the hierarchy during the call
+ // to getDisplayList(), the display list will be marked invalid and we should not
+ // try to use it again.
+ displayList = null;
+ hasDisplayList = false;
+ useDisplayListProperties = false;
+ }
+ }
final boolean hasNoCache = cache == null || hasDisplayList;
final boolean offsetForScroll = cache == null && !hasDisplayList &&
@@ -11675,6 +11712,7 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
}
if (scalingRequired) {
if (useDisplayListProperties) {
+ // TODO: Might not need this if we put everything inside the DL
restoreTo = canvas.save();
}
// mAttachInfo cannot be null, otherwise scalingRequired == false
@@ -11684,7 +11722,7 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
}
float alpha = useDisplayListProperties ? 1 : getAlpha();
- if (transformToApply != null || alpha < 1.0f || !hasIdentityMatrix()) {
+ if (transformToApply != null || alpha < 1 || !hasIdentityMatrix()) {
if (transformToApply != null || !childHasIdentityMatrix) {
int transX = 0;
int transY = 0;
@@ -11696,16 +11734,20 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
if (transformToApply != null) {
if (concatMatrix) {
- // Undo the scroll translation, apply the transformation matrix,
- // then redo the scroll translate to get the correct result.
- canvas.translate(-transX, -transY);
- canvas.concat(transformToApply.getMatrix());
- canvas.translate(transX, transY);
+ if (useDisplayListProperties) {
+ displayList.setAnimationMatrix(transformToApply.getMatrix());
+ } else {
+ // Undo the scroll translation, apply the transformation matrix,
+ // then redo the scroll translate to get the correct result.
+ canvas.translate(-transX, -transY);
+ canvas.concat(transformToApply.getMatrix());
+ canvas.translate(transX, transY);
+ }
parent.mGroupFlags |= ViewGroup.FLAG_CLEAR_TRANSFORMATION;
}
float transformAlpha = transformToApply.getAlpha();
- if (transformAlpha < 1.0f) {
+ if (transformAlpha < 1) {
alpha *= transformToApply.getAlpha();
parent.mGroupFlags |= ViewGroup.FLAG_CLEAR_TRANSFORMATION;
}
@@ -11718,7 +11760,7 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
}
}
- if (alpha < 1.0f) {
+ if (alpha < 1) {
parent.mGroupFlags |= ViewGroup.FLAG_CLEAR_TRANSFORMATION;
if (hasNoCache) {
final int multipliedAlpha = (int) (255 * alpha);
@@ -11728,7 +11770,9 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
layerType != LAYER_TYPE_NONE) {
layerFlags |= Canvas.CLIP_TO_LAYER_SAVE_FLAG;
}
- if (layerType == LAYER_TYPE_NONE) {
+ if (useDisplayListProperties) {
+ displayList.setAlpha(alpha * getAlpha());
+ } else if (layerType == LAYER_TYPE_NONE) {
final int scrollX = hasDisplayList ? 0 : sx;
final int scrollY = hasDisplayList ? 0 : sy;
canvas.saveLayerAlpha(scrollX, scrollY, scrollX + mRight - mLeft,
@@ -11758,7 +11802,7 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
}
}
- if (hasDisplayList) {
+ if (!useDisplayListProperties && hasDisplayList) {
displayList = getDisplayList();
if (!displayList.isValid()) {
// Uncommon, but possible. If a view is removed from the hierarchy during the call
@@ -11815,7 +11859,7 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
cachePaint.setDither(false);
parent.mCachePaint = cachePaint;
}
- if (alpha < 1.0f) {
+ if (alpha < 1) {
cachePaint.setAlpha((int) (alpha * 255));
parent.mGroupFlags |= ViewGroup.FLAG_ALPHA_LOWER_THAN_ONE;
} else if ((flags & ViewGroup.FLAG_ALPHA_LOWER_THAN_ONE) != 0) {
@@ -13614,13 +13658,12 @@ public class View implements Drawable.Callback, Drawable.Callback2, KeyEvent.Cal
mPrivateFlags |= FORCE_LAYOUT;
mPrivateFlags |= INVALIDATED;
- if (mParent != null) {
- if (mLayoutParams != null) {
- mLayoutParams.onResolveLayoutDirection(getResolvedLayoutDirection());
- }
- if (!mParent.isLayoutRequested()) {
- mParent.requestLayout();
- }
+ if (mLayoutParams != null) {
+ mLayoutParams.onResolveLayoutDirection(getResolvedLayoutDirection());
+ }
+
+ if (mParent != null && !mParent.isLayoutRequested()) {
+ mParent.requestLayout();
}
}
diff --git a/core/java/android/view/WindowManagerImpl.java b/core/java/android/view/WindowManagerImpl.java
index f2ee9f9..a45a87e 100644
--- a/core/java/android/view/WindowManagerImpl.java
+++ b/core/java/android/view/WindowManagerImpl.java
@@ -510,8 +510,13 @@ public class WindowManagerImpl implements WindowManager {
String name = root.getClass().getName() + '@' +
Integer.toHexString(hashCode());
- pw.printf(" %s: %d views, %.2f kB (display lists)\n",
+ pw.printf(" %s: %d views, %.2f kB (display lists)",
name, info[0], info[1] / 1024.0f);
+ HardwareRenderer renderer = root.getView().mAttachInfo.mHardwareRenderer;
+ if (renderer != null) {
+ pw.printf(", %d frames rendered", renderer.getFrameCount());
+ }
+ pw.printf("\n");
viewsCount += info[0];
displayListsSize += info[1];
diff --git a/core/java/android/webkit/WebViewClassic.java b/core/java/android/webkit/WebViewClassic.java
index 04fa07a..45c5fa0 100644
--- a/core/java/android/webkit/WebViewClassic.java
+++ b/core/java/android/webkit/WebViewClassic.java
@@ -1204,10 +1204,8 @@ public final class WebViewClassic implements WebViewProvider, WebViewProvider.Sc
static final int SHOW_FULLSCREEN = 120;
static final int HIDE_FULLSCREEN = 121;
static final int REPLACE_BASE_CONTENT = 123;
- static final int FORM_DID_BLUR = 124;
static final int UPDATE_MATCH_COUNT = 126;
static final int CENTER_FIT_RECT = 127;
- static final int REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID = 128;
static final int SET_SCROLLBAR_MODES = 129;
static final int SELECTION_STRING_CHANGED = 130;
static final int HIT_TEST_RESULT = 131;
@@ -1274,7 +1272,6 @@ public final class WebViewClassic implements WebViewProvider, WebViewProvider.Sc
"HIDE_FULLSCREEN", // = 121;
"DOM_FOCUS_CHANGED", // = 122;
"REPLACE_BASE_CONTENT", // = 123;
- "FORM_DID_BLUR", // = 124;
"RETURN_LABEL", // = 125;
"UPDATE_MATCH_COUNT", // = 126;
"CENTER_FIT_RECT", // = 127;
@@ -8288,16 +8285,10 @@ public final class WebViewClassic implements WebViewProvider, WebViewProvider.Sc
}
}
break;
- case REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID:
- displaySoftKeyboard(true);
- // fall through to UPDATE_TEXT_SELECTION_MSG_ID
case UPDATE_TEXT_SELECTION_MSG_ID:
updateTextSelectionFromMessage(msg.arg1, msg.arg2,
(WebViewCore.TextSelectionData) msg.obj);
break;
- case FORM_DID_BLUR:
- // TODO: Figure out if this is needed for something (b/6111763)
- break;
case TAKE_FOCUS:
int direction = msg.arg1;
View focusSearch = mWebView.focusSearch(direction);
diff --git a/core/java/android/webkit/WebViewCore.java b/core/java/android/webkit/WebViewCore.java
index 3eba6d7..b4ebc09 100644
--- a/core/java/android/webkit/WebViewCore.java
+++ b/core/java/android/webkit/WebViewCore.java
@@ -325,17 +325,6 @@ public final class WebViewCore {
}
/**
- * Called by JNI. Send a message to the UI thread to hide the soft keyboard
- * if the node pointed to by nodePointer is still in focus.
- * @param nodePointer The node which just blurred.
- */
- private void formDidBlur(int nodePointer) {
- if (mWebViewClassic == null) return;
- Message.obtain(mWebViewClassic.mPrivateHandler, WebViewClassic.FORM_DID_BLUR,
- nodePointer, 0).sendToTarget();
- }
-
- /**
* Called by JNI when the focus node changed.
*/
private void focusNodeChanged(int nodePointer, WebKitHitTest hitTest) {
@@ -2830,7 +2819,7 @@ public final class WebViewCore {
Message.obtain(mWebViewClassic.mPrivateHandler,
WebViewClassic.INIT_EDIT_FIELD, initData).sendToTarget();
Message.obtain(mWebViewClassic.mPrivateHandler,
- WebViewClassic.REQUEST_KEYBOARD_WITH_SELECTION_MSG_ID,
+ WebViewClassic.UPDATE_TEXT_SELECTION_MSG_ID,
initData.mFieldPointer, 0,
new TextSelectionData(start, end, selectionPtr))
.sendToTarget();
diff --git a/core/java/android/widget/RemoteViewsAdapter.java b/core/java/android/widget/RemoteViewsAdapter.java
index 586fdf4..8067435 100644
--- a/core/java/android/widget/RemoteViewsAdapter.java
+++ b/core/java/android/widget/RemoteViewsAdapter.java
@@ -477,8 +477,11 @@ public class RemoteViewsAdapter extends BaseAdapter implements Handler.Callback
private static final String TAG = "FixedSizeRemoteViewsCache";
// The meta data related to all the RemoteViews, ie. count, is stable, etc.
- private RemoteViewsMetaData mMetaData;
- private RemoteViewsMetaData mTemporaryMetaData;
+ // The meta data objects are made final so that they can be locked on independently
+ // of the FixedSizeRemoteViewsCache. If we ever lock on both meta data objects, it is in
+ // the order mTemporaryMetaData followed by mMetaData.
+ private final RemoteViewsMetaData mMetaData;
+ private final RemoteViewsMetaData mTemporaryMetaData;
// The cache/mapping of position to RemoteViewsMetaData. This set is guaranteed to be
// greater than or equal to the set of RemoteViews.
@@ -939,6 +942,10 @@ public class RemoteViewsAdapter extends BaseAdapter implements Handler.Callback
* which wouldn't otherwise be possible.
*/
public void setVisibleRangeHint(int lowerBound, int upperBound) {
+ if (lowerBound < 0 || upperBound < 0) {
+ throw new RuntimeException("Attempted to set invalid range: lowerBound="+lowerBound +
+ "," + "upperBound="+upperBound);
+ }
mVisibleWindowLowerBound = lowerBound;
mVisibleWindowUpperBound = upperBound;
}
@@ -1072,12 +1079,20 @@ public class RemoteViewsAdapter extends BaseAdapter implements Handler.Callback
// Re-request the new metadata (only after the notification to the factory)
updateTemporaryMetaData();
+ int newCount;
+ synchronized(mCache.getTemporaryMetaData()) {
+ newCount = mCache.getTemporaryMetaData().count;
+ }
// Pre-load (our best guess of) the views which are currently visible in the AdapterView.
// This mitigates flashing and flickering of loading views when a widget notifies that
// its data has changed.
for (int i = mVisibleWindowLowerBound; i <= mVisibleWindowUpperBound; i++) {
- updateRemoteViews(i, false, false);
+ // Because temporary meta data is only ever modified from this thread (ie.
+ // mWorkerThread), it is safe to assume that count is a valid representation.
+ if (i < newCount) {
+ updateRemoteViews(i, false, false);
+ }
}
// Propagate the notification back to the base adapter
diff --git a/core/java/com/google/android/mms/pdu/PduPersister.java b/core/java/com/google/android/mms/pdu/PduPersister.java
index 7c937ed..1a8e80f 100644
--- a/core/java/com/google/android/mms/pdu/PduPersister.java
+++ b/core/java/com/google/android/mms/pdu/PduPersister.java
@@ -519,98 +519,99 @@ public class PduPersister {
* @throws MmsException Failed to load some fields of a PDU.
*/
public GenericPdu load(Uri uri) throws MmsException {
- PduCacheEntry cacheEntry;
- synchronized(PDU_CACHE_INSTANCE) {
- if (PDU_CACHE_INSTANCE.isUpdating(uri)) {
- if (LOCAL_LOGV) {
- Log.v(TAG, "load: " + uri + " blocked by isUpdating()");
- }
- try {
- PDU_CACHE_INSTANCE.wait();
- } catch (InterruptedException e) {
- Log.e(TAG, "load: ", e);
- }
- cacheEntry = PDU_CACHE_INSTANCE.get(uri);
- if (cacheEntry != null) {
- return cacheEntry.getPdu();
+ GenericPdu pdu = null;
+ PduCacheEntry cacheEntry = null;
+ int msgBox = 0;
+ long threadId = -1;
+ try {
+ synchronized(PDU_CACHE_INSTANCE) {
+ if (PDU_CACHE_INSTANCE.isUpdating(uri)) {
+ if (LOCAL_LOGV) {
+ Log.v(TAG, "load: " + uri + " blocked by isUpdating()");
+ }
+ try {
+ PDU_CACHE_INSTANCE.wait();
+ } catch (InterruptedException e) {
+ Log.e(TAG, "load: ", e);
+ }
+ cacheEntry = PDU_CACHE_INSTANCE.get(uri);
+ if (cacheEntry != null) {
+ return cacheEntry.getPdu();
+ }
}
+ // Tell the cache to indicate to other callers that this item
+ // is currently being updated.
+ PDU_CACHE_INSTANCE.setUpdating(uri, true);
}
- // Tell the cache to indicate to other callers that this item
- // is currently being updated.
- PDU_CACHE_INSTANCE.setUpdating(uri, true);
- }
- Cursor c = SqliteWrapper.query(mContext, mContentResolver, uri,
- PDU_PROJECTION, null, null, null);
- PduHeaders headers = new PduHeaders();
- Set<Entry<Integer, Integer>> set;
- long msgId = ContentUris.parseId(uri);
- int msgBox;
- long threadId;
+ Cursor c = SqliteWrapper.query(mContext, mContentResolver, uri,
+ PDU_PROJECTION, null, null, null);
+ PduHeaders headers = new PduHeaders();
+ Set<Entry<Integer, Integer>> set;
+ long msgId = ContentUris.parseId(uri);
- try {
- if ((c == null) || (c.getCount() != 1) || !c.moveToFirst()) {
- throw new MmsException("Bad uri: " + uri);
- }
+ try {
+ if ((c == null) || (c.getCount() != 1) || !c.moveToFirst()) {
+ throw new MmsException("Bad uri: " + uri);
+ }
- msgBox = c.getInt(PDU_COLUMN_MESSAGE_BOX);
- threadId = c.getLong(PDU_COLUMN_THREAD_ID);
+ msgBox = c.getInt(PDU_COLUMN_MESSAGE_BOX);
+ threadId = c.getLong(PDU_COLUMN_THREAD_ID);
- set = ENCODED_STRING_COLUMN_INDEX_MAP.entrySet();
- for (Entry<Integer, Integer> e : set) {
- setEncodedStringValueToHeaders(
- c, e.getValue(), headers, e.getKey());
- }
+ set = ENCODED_STRING_COLUMN_INDEX_MAP.entrySet();
+ for (Entry<Integer, Integer> e : set) {
+ setEncodedStringValueToHeaders(
+ c, e.getValue(), headers, e.getKey());
+ }
- set = TEXT_STRING_COLUMN_INDEX_MAP.entrySet();
- for (Entry<Integer, Integer> e : set) {
- setTextStringToHeaders(
- c, e.getValue(), headers, e.getKey());
- }
+ set = TEXT_STRING_COLUMN_INDEX_MAP.entrySet();
+ for (Entry<Integer, Integer> e : set) {
+ setTextStringToHeaders(
+ c, e.getValue(), headers, e.getKey());
+ }
- set = OCTET_COLUMN_INDEX_MAP.entrySet();
- for (Entry<Integer, Integer> e : set) {
- setOctetToHeaders(
- c, e.getValue(), headers, e.getKey());
- }
+ set = OCTET_COLUMN_INDEX_MAP.entrySet();
+ for (Entry<Integer, Integer> e : set) {
+ setOctetToHeaders(
+ c, e.getValue(), headers, e.getKey());
+ }
- set = LONG_COLUMN_INDEX_MAP.entrySet();
- for (Entry<Integer, Integer> e : set) {
- setLongToHeaders(
- c, e.getValue(), headers, e.getKey());
- }
- } finally {
- if (c != null) {
- c.close();
+ set = LONG_COLUMN_INDEX_MAP.entrySet();
+ for (Entry<Integer, Integer> e : set) {
+ setLongToHeaders(
+ c, e.getValue(), headers, e.getKey());
+ }
+ } finally {
+ if (c != null) {
+ c.close();
+ }
}
- }
-
- // Check whether 'msgId' has been assigned a valid value.
- if (msgId == -1L) {
- throw new MmsException("Error! ID of the message: -1.");
- }
- // Load address information of the MM.
- loadAddress(msgId, headers);
-
- int msgType = headers.getOctet(PduHeaders.MESSAGE_TYPE);
- PduBody body = new PduBody();
+ // Check whether 'msgId' has been assigned a valid value.
+ if (msgId == -1L) {
+ throw new MmsException("Error! ID of the message: -1.");
+ }
- // For PDU which type is M_retrieve.conf or Send.req, we should
- // load multiparts and put them into the body of the PDU.
- if ((msgType == PduHeaders.MESSAGE_TYPE_RETRIEVE_CONF)
- || (msgType == PduHeaders.MESSAGE_TYPE_SEND_REQ)) {
- PduPart[] parts = loadParts(msgId);
- if (parts != null) {
- int partsNum = parts.length;
- for (int i = 0; i < partsNum; i++) {
- body.addPart(parts[i]);
+ // Load address information of the MM.
+ loadAddress(msgId, headers);
+
+ int msgType = headers.getOctet(PduHeaders.MESSAGE_TYPE);
+ PduBody body = new PduBody();
+
+ // For PDU which type is M_retrieve.conf or Send.req, we should
+ // load multiparts and put them into the body of the PDU.
+ if ((msgType == PduHeaders.MESSAGE_TYPE_RETRIEVE_CONF)
+ || (msgType == PduHeaders.MESSAGE_TYPE_SEND_REQ)) {
+ PduPart[] parts = loadParts(msgId);
+ if (parts != null) {
+ int partsNum = parts.length;
+ for (int i = 0; i < partsNum; i++) {
+ body.addPart(parts[i]);
+ }
}
}
- }
- GenericPdu pdu = null;
- switch (msgType) {
+ switch (msgType) {
case PduHeaders.MESSAGE_TYPE_NOTIFICATION_IND:
pdu = new NotificationInd(headers);
break;
@@ -657,16 +658,20 @@ public class PduPersister {
default:
throw new MmsException(
"Unrecognized PDU type: " + Integer.toHexString(msgType));
+ }
+ } finally {
+ synchronized(PDU_CACHE_INSTANCE) {
+ if (pdu != null) {
+ assert(PDU_CACHE_INSTANCE.get(uri) == null);
+ // Update the cache entry with the real info
+ cacheEntry = new PduCacheEntry(pdu, msgBox, threadId);
+ PDU_CACHE_INSTANCE.put(uri, cacheEntry);
+ }
+ PDU_CACHE_INSTANCE.setUpdating(uri, false);
+ PDU_CACHE_INSTANCE.notifyAll(); // tell anybody waiting on this entry to go ahead
+ }
}
-
- synchronized(PDU_CACHE_INSTANCE ) {
- assert(PDU_CACHE_INSTANCE.get(uri) == null);
- // Update the cache entry with the real info
- cacheEntry = new PduCacheEntry(pdu, msgBox, threadId);
- PDU_CACHE_INSTANCE.put(uri, cacheEntry);
- PDU_CACHE_INSTANCE.notifyAll(); // tell anybody waiting on this entry to go ahead
- return pdu;
- }
+ return pdu;
}
private void persistAddress(