Bug 673969 - System preference for "visible passwords" not followed. r=blassey
authorAlex Pakhotin <alexp@mozilla.com>
Tue, 26 Jul 2011 18:14:52 -0700
changeset 75312 c86cbbb7d0bf14ae7af5be3ebb23af50554b98ec
parent 75311 2630af781762a734ee87c3fda701a471cde94546
child 75313 51c50cf19742ffaf2c014f404739c407857f9ba2
push id2
push userbsmedberg@mozilla.com
push dateFri, 19 Aug 2011 14:38:13 +0000
reviewersblassey
bugs673969
milestone8.0a1
Bug 673969 - System preference for "visible passwords" not followed. r=blassey
dom/ipc/ContentParent.cpp
dom/ipc/ContentParent.h
dom/ipc/PContent.ipdl
embedding/android/GeckoAppShell.java
widget/src/android/AndroidBridge.cpp
widget/src/android/AndroidBridge.h
widget/src/android/nsLookAndFeel.cpp
widget/src/android/nsLookAndFeel.h
--- a/dom/ipc/ContentParent.cpp
+++ b/dom/ipc/ContentParent.cpp
@@ -594,16 +594,29 @@ ContentParent::RecvGetIconForExtension(c
 
     bits->AppendElements(aIconSize * aIconSize * 4);
 
     AndroidBridge::Bridge()->GetIconForExtension(aFileExt, aIconSize, bits->Elements());
 #endif
     return true;
 }
 
+bool
+ContentParent::RecvGetShowPasswordSetting(PRBool* showPassword)
+{
+    // default behavior is to show the last password character
+    *showPassword = PR_TRUE;
+#ifdef ANDROID
+    NS_ASSERTION(AndroidBridge::Bridge() != nsnull, "AndroidBridge is not available");
+    if (AndroidBridge::Bridge() != nsnull)
+        *showPassword = AndroidBridge::Bridge()->GetShowPasswordSetting();
+#endif
+    return true;
+}
+
 NS_IMPL_THREADSAFE_ISUPPORTS4(ContentParent,
                               nsIObserver,
                               nsIThreadObserver,
                               nsIDOMGeoPositionCallback,
                               nsIDeviceMotionListener)
 
 NS_IMETHODIMP
 ContentParent::Observe(nsISupports* aSubject,
--- a/dom/ipc/ContentParent.h
+++ b/dom/ipc/ContentParent.h
@@ -162,16 +162,17 @@ private:
 
     virtual bool RecvSetClipboardText(const nsString& text, const PRInt32& whichClipboard);
     virtual bool RecvGetClipboardText(const PRInt32& whichClipboard, nsString* text);
     virtual bool RecvEmptyClipboard();
     virtual bool RecvClipboardHasText(PRBool* hasText);
 
     virtual bool RecvGetSystemColors(const PRUint32& colorsCount, InfallibleTArray<PRUint32>* colors);
     virtual bool RecvGetIconForExtension(const nsCString& aFileExt, const PRUint32& aIconSize, InfallibleTArray<PRUint8>* bits);
+    virtual bool RecvGetShowPasswordSetting(PRBool* showPassword);
 
     virtual bool RecvStartVisitedQuery(const IPC::URI& uri);
 
     virtual bool RecvVisitURI(const IPC::URI& uri,
                               const IPC::URI& referrer,
                               const PRUint32& flags);
 
     virtual bool RecvSetURITitle(const IPC::URI& uri,
--- a/dom/ipc/PContent.ipdl
+++ b/dom/ipc/PContent.ipdl
@@ -200,15 +200,18 @@ parent:
         returns (PRBool hasText);
 
     sync GetSystemColors(PRUint32 colorsCount)
         returns (PRUint32[] colors);
 
     sync GetIconForExtension(nsCString aFileExt, PRUint32 aIconSize)
         returns (PRUint8[] bits);
 
+    sync GetShowPasswordSetting()
+        returns (PRBool showPassword);
+
 both:
      AsyncMessage(nsString aMessage, nsString aJSON);
 
 };
 
 }
 }
--- a/embedding/android/GeckoAppShell.java
+++ b/embedding/android/GeckoAppShell.java
@@ -57,16 +57,17 @@ import android.content.pm.*;
 import android.graphics.*;
 import android.widget.*;
 import android.hardware.*;
 import android.location.*;
 import android.telephony.*;
 import android.webkit.MimeTypeMap;
 import android.media.MediaScannerConnection;
 import android.media.MediaScannerConnection.MediaScannerConnectionClient;
+import android.provider.Settings;
 
 import android.util.*;
 import android.net.Uri;
 import android.net.ConnectivityManager;
 import android.net.NetworkInfo;
 
 import android.graphics.drawable.*;
 import android.graphics.Bitmap;
@@ -1361,9 +1362,21 @@ public class GeckoAppShell
 
         if (resolveInfo == null)
             return null;
 
         ActivityInfo activityInfo = resolveInfo.activityInfo;
 
         return activityInfo.loadIcon(pm);
     }
+
+    public static boolean getShowPasswordSetting() {
+        try {
+            int showPassword =
+                Settings.System.getInt(GeckoApp.mAppContext.getContentResolver(),
+                                       Settings.System.TEXT_SHOW_PASSWORD);
+            return (showPassword > 0);
+        }
+        catch (Exception e) {
+            return false;
+        }
+    }
 }
--- a/widget/src/android/AndroidBridge.cpp
+++ b/widget/src/android/AndroidBridge.cpp
@@ -143,16 +143,17 @@ AndroidBridge::Init(JNIEnv *jEnv,
     jIsNetworkLinkUp = (jmethodID) jEnv->GetStaticMethodID(jGeckoAppShellClass, "isNetworkLinkUp", "()Z");
     jIsNetworkLinkKnown = (jmethodID) jEnv->GetStaticMethodID(jGeckoAppShellClass, "isNetworkLinkKnown", "()Z");
     jGetNetworkLinkType = (jmethodID) jEnv->GetStaticMethodID(jGeckoAppShellClass, "getNetworkLinkType", "()I");
     jSetSelectedLocale = (jmethodID) jEnv->GetStaticMethodID(jGeckoAppShellClass, "setSelectedLocale", "(Ljava/lang/String;)V");
     jScanMedia = (jmethodID) jEnv->GetStaticMethodID(jGeckoAppShellClass, "scanMedia", "(Ljava/lang/String;Ljava/lang/String;)V");
     jGetSystemColors = (jmethodID) jEnv->GetStaticMethodID(jGeckoAppShellClass, "getSystemColors", "()[I");
     jGetIconForExtension = (jmethodID) jEnv->GetStaticMethodID(jGeckoAppShellClass, "getIconForExtension", "(Ljava/lang/String;I)[B");
     jCreateShortcut = (jmethodID) jEnv->GetStaticMethodID(jGeckoAppShellClass, "createShortcut", "(Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;)V");
+    jGetShowPasswordSetting = (jmethodID) jEnv->GetStaticMethodID(jGeckoAppShellClass, "getShowPasswordSetting", "()Z");
 
     jEGLContextClass = (jclass) jEnv->NewGlobalRef(jEnv->FindClass("javax/microedition/khronos/egl/EGLContext"));
     jEGL10Class = (jclass) jEnv->NewGlobalRef(jEnv->FindClass("javax/microedition/khronos/egl/EGL10"));
     jEGLSurfaceImplClass = (jclass) jEnv->NewGlobalRef(jEnv->FindClass("com/google/android/gles_jni/EGLSurfaceImpl"));
     jEGLContextImplClass = (jclass) jEnv->NewGlobalRef(jEnv->FindClass("com/google/android/gles_jni/EGLContextImpl"));
     jEGLConfigImplClass = (jclass) jEnv->NewGlobalRef(jEnv->FindClass("com/google/android/gles_jni/EGLConfigImpl"));
     jEGLDisplayImplClass = (jclass) jEnv->NewGlobalRef(jEnv->FindClass("com/google/android/gles_jni/EGLDisplayImpl"));
 
@@ -750,16 +751,23 @@ AndroidBridge::GetIconForExtension(const
     PRUint32 bufSize = aIconSize * aIconSize * 4;
     NS_ASSERTION(len == bufSize, "AndroidBridge::GetIconForExtension: Pixels array is incomplete!");
     if (len == bufSize)
         memcpy(aBuf, elements, bufSize);
 
     mJNIEnv->ReleaseByteArrayElements(arr, elements, 0);
 }
 
+bool
+AndroidBridge::GetShowPasswordSetting()
+{
+    ALOG_BRIDGE("AndroidBridge::GetShowPasswordSetting");
+    return mJNIEnv->CallStaticBooleanMethod(mGeckoAppShellClass, jGetShowPasswordSetting);
+}
+
 void
 AndroidBridge::SetSurfaceView(jobject obj)
 {
     mSurfaceView.Init(obj);
 }
 
 void
 AndroidBridge::ShowInputMethodPicker()
@@ -993,9 +1001,8 @@ AndroidBridge::LockBitmap(jobject bitmap
 
 void
 AndroidBridge::UnlockBitmap(jobject bitmap)
 {
     int err;
     if ((err = AndroidBitmap_unlockPixels(JNI(), bitmap)) != 0)
         ALOG_BRIDGE("AndroidBitmap_unlockPixels failed! (error %d)", err);
 }
-
--- a/widget/src/android/AndroidBridge.h
+++ b/widget/src/android/AndroidBridge.h
@@ -207,16 +207,18 @@ public:
     int GetNetworkLinkType();
 
     void SetSelectedLocale(const nsAString&);
 
     void GetSystemColors(AndroidSystemColors *aColors);
 
     void GetIconForExtension(const nsACString& aFileExt, PRUint32 aIconSize, PRUint8 * const aBuf);
 
+    bool GetShowPasswordSetting();
+
     struct AutoLocalJNIFrame {
         AutoLocalJNIFrame(int nEntries = 128) : mEntries(nEntries) {
             // Make sure there is enough space to store a local ref to the
             // exception.  I am not completely sure this is needed, but does
             // not hurt.
             AndroidBridge::Bridge()->JNI()->PushLocalFrame(mEntries + 1);
         }
         // Note! Calling Purge makes all previous local refs created in
@@ -317,16 +319,17 @@ protected:
     jmethodID jIsNetworkLinkUp;
     jmethodID jIsNetworkLinkKnown;
     jmethodID jGetNetworkLinkType;
     jmethodID jSetSelectedLocale;
     jmethodID jScanMedia;
     jmethodID jGetSystemColors;
     jmethodID jGetIconForExtension;
     jmethodID jCreateShortcut;
+    jmethodID jGetShowPasswordSetting;
 
     // stuff we need for CallEglCreateWindowSurface
     jclass jEGLSurfaceImplClass;
     jclass jEGLContextImplClass;
     jclass jEGLConfigImplClass;
     jclass jEGLDisplayImplClass;
     jclass jEGLContextClass;
     jclass jEGL10Class;
--- a/widget/src/android/nsLookAndFeel.cpp
+++ b/widget/src/android/nsLookAndFeel.cpp
@@ -40,19 +40,22 @@
 #include "mozilla/dom/ContentChild.h"
 #include "nsStyleConsts.h"
 #include "nsXULAppAPI.h"
 #include "nsLookAndFeel.h"
 
 using namespace mozilla;
 using mozilla::dom::ContentChild;
 
-PRBool nsLookAndFeel::mInitialized = PR_FALSE;
+PRBool nsLookAndFeel::mInitializedSystemColors = PR_FALSE;
 AndroidSystemColors nsLookAndFeel::mSystemColors;
 
+PRBool nsLookAndFeel::mInitializedShowPassword = PR_FALSE;
+PRBool nsLookAndFeel::mShowPassword = PR_TRUE;
+
 nsLookAndFeel::nsLookAndFeel()
     : nsXPLookAndFeel()
 {
 }
 
 nsLookAndFeel::~nsLookAndFeel()
 {
 }
@@ -63,25 +66,25 @@ nsLookAndFeel::~nsLookAndFeel()
 #define DARK_GRAY_COLOR        NS_RGB(0x40,0x40,0x40)
 #define GRAY_COLOR             NS_RGB(0x80,0x80,0x80)
 #define LIGHT_GRAY_COLOR       NS_RGB(0xa0,0xa0,0xa0)
 #define RED_COLOR              NS_RGB(0xff,0x00,0x00)
 
 nsresult
 nsLookAndFeel::GetSystemColors()
 {
-    if (mInitialized)
+    if (mInitializedSystemColors)
         return NS_OK;
 
     if (!AndroidBridge::Bridge())
         return NS_ERROR_FAILURE;
 
     AndroidBridge::Bridge()->GetSystemColors(&mSystemColors);
 
-    mInitialized = PR_TRUE;
+    mInitializedSystemColors = PR_TRUE;
 
     return NS_OK;
 }
 
 nsresult
 nsLookAndFeel::CallRemoteGetSystemColors()
 {
     // An array has to be used to get data from remote process
@@ -97,27 +100,27 @@ nsLookAndFeel::CallRemoteGetSystemColors
 
     if (colors.Length() < colorsCount)
         colorsCount = colors.Length();
 
     // Array elements correspond to the members of mSystemColors structure,
     // so just copy the memory block
     memcpy(&mSystemColors, colors.Elements(), sizeof(nscolor) * colorsCount);
 
-    mInitialized = PR_TRUE;
+    mInitializedSystemColors = PR_TRUE;
 
     return NS_OK;
 }
 
 nsresult
 nsLookAndFeel::NativeGetColor(const nsColorID aID, nscolor &aColor)
 {
     nsresult rv = NS_OK;
 
-    if (!mInitialized) {
+    if (!mInitializedSystemColors) {
         if (XRE_GetProcessType() == GeckoProcessType_Default)
             rv = GetSystemColors();
         else
             rv = CallRemoteGetSystemColors();
         NS_ENSURE_SUCCESS(rv, rv);
     }
 
     // XXX we'll want to use context.obtainStyledAttributes on the java side to
@@ -455,8 +458,25 @@ nsLookAndFeel::GetMetric(const nsMetricF
 
         default:
             aMetric = -1.0;
             rv = NS_ERROR_FAILURE;
             break;
     }
     return rv;
 }
+
+/*virtual*/
+PRBool nsLookAndFeel::GetEchoPassword()
+{
+    if (!mInitializedShowPassword) {
+        if (XRE_GetProcessType() == GeckoProcessType_Default) {
+            if (AndroidBridge::Bridge())
+                mShowPassword = AndroidBridge::Bridge()->GetShowPasswordSetting();
+            else
+                NS_ASSERTION(AndroidBridge::Bridge() != nsnull, "AndroidBridge is not available!");
+        } else {
+            ContentChild::GetSingleton()->SendGetShowPasswordSetting(&mShowPassword);
+        }
+        mInitializedShowPassword = PR_TRUE;
+    }
+    return mShowPassword;
+}
--- a/widget/src/android/nsLookAndFeel.h
+++ b/widget/src/android/nsLookAndFeel.h
@@ -46,18 +46,21 @@ class nsLookAndFeel: public nsXPLookAndF
 {
 public:
     nsLookAndFeel();
     virtual ~nsLookAndFeel();
 
     nsresult NativeGetColor(const nsColorID aID, nscolor &aColor);
     NS_IMETHOD GetMetric(const nsMetricID aID, PRInt32 & aMetric);
     NS_IMETHOD GetMetric(const nsMetricFloatID aID, float & aMetric);
+    virtual PRBool GetEchoPassword();
 
 protected:
-    static PRBool mInitialized;
+    static PRBool mInitializedSystemColors;
     static mozilla::AndroidSystemColors mSystemColors;
+    static PRBool mInitializedShowPassword;
+    static PRBool mShowPassword;
 
     nsresult GetSystemColors();
     nsresult CallRemoteGetSystemColors();
 };
 
 #endif