merge in ics-release history after reset to master
diff --git a/chips/src/com/android/ex/chips/RecipientEditTextView.java b/chips/src/com/android/ex/chips/RecipientEditTextView.java
index e38b489..efee160 100644
--- a/chips/src/com/android/ex/chips/RecipientEditTextView.java
+++ b/chips/src/com/android/ex/chips/RecipientEditTextView.java
@@ -675,8 +675,13 @@
         if (mValidator != null && !mValidator.isValid(token)) {
             // Try fixing up the entry using the validator.
             token = mValidator.fixText(token).toString();
-            if (tokens != null && tokens.length > 0) {
-                token = Rfc822Tokenizer.tokenize(token)[0].getAddress();
+            if (!TextUtils.isEmpty(token)) {
+                // protect against the case of a validator with a null domain,
+                // which doesn't add a domain to the token
+                Rfc822Token[] tokenized = Rfc822Tokenizer.tokenize(token);
+                if (tokenized.length > 0) {
+                    token = tokenized[0].getAddress();
+                }
             }
         }
         return RecipientEntry.constructFakeEntry(token);
diff --git a/common/java/com/android/common/Rfc822Validator.java b/common/java/com/android/common/Rfc822Validator.java
index 1b4a268..2db00ff 100644
--- a/common/java/com/android/common/Rfc822Validator.java
+++ b/common/java/com/android/common/Rfc822Validator.java
@@ -36,6 +36,7 @@
  *             a full understanding of the syntax it claims to correct.
  * @hide
  */
+@Deprecated
 public class Rfc822Validator implements AutoCompleteTextView.Validator {
     /*
      * Regex.EMAIL_ADDRESS_PATTERN hardcodes the TLD that we accept, but we
@@ -48,6 +49,7 @@
             Pattern.compile("[^\\s@]+@([^\\s@\\.]+\\.)+[a-zA-z][a-zA-Z][a-zA-Z]*");
 
     private String mDomain;
+    private boolean mRemoveInvalid = false;
 
     /**
      * Constructs a new validator that uses the specified domain name as
@@ -69,6 +71,18 @@
     }
 
     /**
+     * Specify if the validator should remove invalid tokens instead of trying
+     * to fix them. This can be used to strip results of incorrectly formatted
+     * tokens.
+     *
+     * @param remove true to remove tokens with the wrong format, false to
+     *            attempt to fix them
+     */
+    public void setRemoveInvalid(boolean remove) {
+        mRemoveInvalid = remove;
+    }
+
+    /**
      * @return a string in which all the characters that are illegal for the username
      * or the domain name part of the email address have been removed.
      */
@@ -112,15 +126,29 @@
 
         for (int i = 0; i < tokens.length; i++) {
             String text = tokens[i].getAddress();
+
+            if (mRemoveInvalid && !isValid(text)) {
+                continue;
+            }
             int index = text.indexOf('@');
             if (index < 0) {
-                // If there is no @, just append the domain of the account
-                tokens[i].setAddress(removeIllegalCharacters(text) + "@" + mDomain);
+                // append the domain of the account if it exists
+                if (mDomain != null) {
+                    tokens[i].setAddress(removeIllegalCharacters(text) + "@" + mDomain);
+                }
             } else {
                 // Otherwise, remove the illegal characters on both sides of the '@'
                 String fix = removeIllegalCharacters(text.substring(0, index));
+                if (TextUtils.isEmpty(fix)) {
+                    // if the address is empty after removing invalid chars
+                    // don't use it
+                    continue;
+                }
                 String domain = removeIllegalCharacters(text.substring(index + 1));
-                tokens[i].setAddress(fix + "@" + (domain.length() != 0 ? domain : mDomain));
+                boolean emptyDomain = domain.length() == 0;
+                if (!emptyDomain || mDomain != null) {
+                    tokens[i].setAddress(fix + "@" + (!emptyDomain ? domain : mDomain));
+                }
             }
 
             sb.append(tokens[i].toString());
diff --git a/common/tests/src/com/android/common/Rfc822ValidatorTest.java b/common/tests/src/com/android/common/Rfc822ValidatorTest.java
index 5118146..cbcc812 100644
--- a/common/tests/src/com/android/common/Rfc822ValidatorTest.java
+++ b/common/tests/src/com/android/common/Rfc822ValidatorTest.java
@@ -49,6 +49,38 @@
         fixes.put("a", "<a@gmail.com>");
         fixes.put("a b", "<ab@gmail.com>");
         fixes.put("a@b", "<a@b>");
+        fixes.put("()~><@not.work", "");
+
+        for (Map.Entry<String, String> e : fixes.entrySet()) {
+            assertEquals(e.getValue(), validator.fixText(e.getKey()).toString());
+        }
+    }
+
+    @SmallTest
+    public void testEmailValidatorNullDomain() {
+        Rfc822Validator validator = new Rfc822Validator(null);
+
+        Map<String, String> fixes = new HashMap<String, String>();
+        fixes.put("a", "<a>");
+        fixes.put("a b", "<a b>");
+        fixes.put("a@b", "<a@b>");
+        fixes.put("a@b.com", "<a@b.com>"); // this one is correct
+
+        for (Map.Entry<String, String> e : fixes.entrySet()) {
+            assertEquals(e.getValue(), validator.fixText(e.getKey()).toString());
+        }
+    }
+
+    @SmallTest
+    public void testEmailValidatorRemoveInvalid() {
+        Rfc822Validator validator = new Rfc822Validator("google.com");
+        validator.setRemoveInvalid(true);
+
+        Map<String, String> fixes = new HashMap<String, String>();
+        fixes.put("a", "");
+        fixes.put("a b", "");
+        fixes.put("a@b", "");
+        fixes.put("a@b.com", "<a@b.com>"); // this one is correct
 
         for (Map.Entry<String, String> e : fixes.entrySet()) {
             assertEquals(e.getValue(), validator.fixText(e.getKey()).toString());