谷歌源生bug发现与解决记录

最近发现了谷歌安卓源生的一个bug,在这里记录一下。

操作步骤:

1、进入拨号界面,输入 ##4636## ,然后会进入手机测试界面。
2、点击第三栏 Wi-Fi information 。
3、进入Wi-Fi information 界面后,点击第一栏 Wi-Fi API 。
4、进入Wi-Fi API 界面后,点击 enableNetwork 。这时会弹出一个输入栏,如果你输入为空或者输入为非数字,如何点击 OK ,连续操作俩次,就会显示 Settings keeps stopping。

分析:

从log中可以看到,有地方抛出了异常,追踪代码,发现异常为 java.lang.NumberFormatException 。
并且从log中也可以看出是 WifiAPITest 里出现了问题。另外从现象来看,导致 crash 的操作也是在WifiAPITest 中,那我们看代码。
从代码中可以看到,从 EditText 中输入内容后,要调用 Integer.parseInt() 来把string类型转换为int类型。因为enableNetwork 的参数是网络的ID,是数字。
packages/apps/Settings/src/com/android/settings/wifi/WifiAPITest.java
代码链接

public boolean onPreferenceClick(Preference pref) {
	.......
	} else if (pref == mWifiEnableNetwork) {
	    AlertDialog.Builder alert = new AlertDialog.Builder(getContext());
	    alert.setTitle("Input");
	    alert.setMessage("Enter Network ID");
	    // Set an EditText view to get user input
	    final EditText input = new EditText(getPrefContext());
	    alert.setView(input);
	    alert.setPositiveButton("Ok", new DialogInterface.OnClickListener() {
	            public void onClick(DialogInterface dialog, int whichButton) {
	            Editable value = input.getText();
	            netid =  Integer.parseInt(value.toString());
	            mWifiManager.enableNetwork(netid, false);
	            }
	            });
	    alert.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
	            public void onClick(DialogInterface dialog, int whichButton) {
	            // Canceled.
	            }
	            });
	    alert.show();
	}

/libcore/ojluni/src/main/java/java/lang/Integer.java
看 parseInt 函数,可以看到当数据不符合规范时会抛出异常,比如你输入的是汉字或者十进制的字母,都是无法转换为 int 类型的,所以就会抛出异常。而对于这个异常,Integer 中并没有捕获,所以异常会抛给上层,也就是我们上面看的 WifiAPITest ,很明显 WifiAPITest 也没有处理这个异常。Java中如果异常没有处理,也没有 try catch捕获,会导致程序停止执行的。 所以当我们输入为空或者输入非数字,Settings 就会 crash 。
代码链接

public static int parseInt(String s, int radix)
            throws NumberFormatException
{
    ...........
    if (len > 0) {
        char firstChar = s.charAt(0);
        if (firstChar < '0') { // Possible leading "+" or "-"
            if (firstChar == '-') {
                negative = true;
                limit = Integer.MIN_VALUE;
            } else if (firstChar != '+')
                throw NumberFormatException.forInputString(s);

            if (len == 1) // Cannot have lone "+" or "-"
                throw NumberFormatException.forInputString(s);
            i++;
        }
        multmin = limit / radix;
        while (i < len) {
            // Accumulating negatively avoids surprises near MAX_VALUE
            digit = Character.digit(s.charAt(i++),radix);
            if (digit < 0) {
                throw NumberFormatException.forInputString(s);
            }
            if (result < multmin) {
                throw NumberFormatException.forInputString(s);
            }
            result *= radix;
            if (result < limit + digit) {
                throw NumberFormatException.forInputString(s);
            }
            result -= digit;
        }
    } else {
        throw NumberFormatException.forInputString(s);
    }
    return negative ? result : -result;
}

解决:

谷歌的 pixel 源生机也存在这个问题,但是我用的这个小米手机没有这个问题。其实这个问题不难解决,在调用 Integer.parseInt 的地方,加一个 try catch 语句,将这个异常进行捕获就好了。

发布了67 篇原创文章 · 获赞 62 · 访问量 2万+

猜你喜欢

转载自blog.csdn.net/qq_43804080/article/details/103639389