Android convertToBytes StringIndexOutOfBoundsException 调试小结

直接将/trunk/frameworks/base/wifi/java/android/net/wifi/WifiSsid.java 中的convertToBytes 拷贝出来调试:

目的:了解这个函数的作用,输入输出分别是什么。

结果:输入参数为\xnn格式的ascii码,当输入参数非法时,由于原生代码写的健壮性不够,很容易发生字串索引越界,导致系统异常。

下面将测试代码贴出来,以作备份。


package com.rockey.test1;


import java.io.ByteArrayOutputStream;


import android.os.Bundle;
import android.R.integer;
import android.app.Activity;
import android.util.Log;
import android.view.Menu;


public class MainActivity extends Activity {
    public ByteArrayOutputStream octets = new ByteArrayOutputStream(32);
    private static final int HEX_RADIX = 16;
private static final String TAG = "ROCKEY";
    public String asciiEncoded;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Log.e(TAG, "octets1:"+octets.toString());
asciiEncoded = "\\x45\\x45\\x45\\x45\\x45\\x45\\x45\\07";
convertToBytes(asciiEncoded);
Log.e(TAG, "octets2:"+octets.toString());

int var = Character.digit('B', HEX_RADIX);
Log.e(TAG, "Character.digit:"+var);
}


@Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}


/* This function is equivalent to printf_decode() at src/utils/common.c in
     * the supplicant */


    private void convertToBytes(String asciiEncoded) {
        int i = 0;
        int val = 0;
        while (i< asciiEncoded.length()) {
            char c = asciiEncoded.charAt(i);
            switch (c) {
                case '\\':
                Log.e(TAG, "dash1,length:"+asciiEncoded.length());
                    i++;
//added for StringIndexOutOfBoundsException by ctv zhangjiqiang
                    if (i >= asciiEncoded.length()) {
                        octets.write('\\');
                        break;
                    }
                    switch(asciiEncoded.charAt(i)) {
                   case '\\':
                    Log.e(TAG, "dash2");
                       octets.write('\\');
                       i++;
                       break;
                   case '"':
                       octets.write('"');
                            i++;
                            break;
                   case 'n':
                       octets.write('\n');
                       i++;
                       break;
                        case 'r':
                       octets.write('\r');
                       i++;
                       break;
                        case 't':
                       octets.write('\t');
                       i++;
                       break;
                        case 'e':
                       octets.write(27); //escape char
                       i++;
                       break;
                   case 'x':
                    Log.e(TAG, "dashx");
                       i++;
                            try {
                            //added for StringIndexOutOfBoundsException by ctv zhangjiqiang delete by liuxiang
//if((i+2)>asciiEncoded.length()){
// val = -1;
//}else{
//add try...catch for StringIndexOutOfBoundsException by ctv liuxiang
try{
                            val = Integer.parseInt(asciiEncoded.substring(i, i + 2), HEX_RADIX);
                           }catch(StringIndexOutOfBoundsException e){
                        e.printStackTrace();
                        break;
                        }
//}
                       } catch (NumberFormatException e) {
                           val = -1;
                       }
                            if (val < 0) {
                            //add try catch for StringIndexOutOfBoundsException by ctv liuxiang
                            try{
                            val = Character.digit(asciiEncoded.charAt(i), HEX_RADIX);
                        }catch(StringIndexOutOfBoundsException e){
                        val = -1;
                        Log.e(TAG, "StringIndexOutOfBoundsException2");
                        }
                           if (val < 0) break;
                           octets.write(val);
                           i++;
                       } else {
                           octets.write(val);
                           i += 2;
                            }
                            break;
                        case '0':
                   case '1':
                   case '2':
                   case '3':
                   case '4':
                   case '5':
                        case '6':
                   case '7':
                    Log.e(TAG, "0~7,i="+i);
                       val = asciiEncoded.charAt(i) - '0';
                       Log.e(TAG, "val1:"+val);
                       i++;
                       try {
                       if (asciiEncoded.charAt(i) >= '0' && asciiEncoded.charAt(i) <= '7') {
                           val = val * 8 + asciiEncoded.charAt(i) - '0';
                           Log.e(TAG, "val2:"+val);
                           i++;
                           }
                       if (asciiEncoded.charAt(i) >= '0' && asciiEncoded.charAt(i) <= '7') {
                           val = val * 8 + asciiEncoded.charAt(i) - '0';
                           Log.e(TAG, "val3:"+val);
                           i++;
                       }
                       } catch (Exception e) {
// TODO: handle exception
                        e.printStackTrace();
                        Log.e(TAG, "StringIndexOutOfBoundsException3");
                        break;
}
                            octets.write(val);
                       break;
                   default:
                       break;
               }
                break;
                default:
                Log.e(TAG, "default");
                    octets.write(c);
                    i++;
                    break;
            }
        }
    }

}


输入为:asciiEncoded = "\\x45\\x45\\x45\\x45\\x45\\x45\\x45\\07";

运行结果:


07-15 15:15:44.216: E/ROCKEY(2757): octets1:
07-15 15:15:44.216: E/ROCKEY(2757): dash1,length:31
07-15 15:15:44.216: E/ROCKEY(2757): dashx
07-15 15:15:44.216: E/ROCKEY(2757): dash1,length:31
07-15 15:15:44.216: E/ROCKEY(2757): dashx
07-15 15:15:44.216: E/ROCKEY(2757): dash1,length:31
07-15 15:15:44.216: E/ROCKEY(2757): dashx
07-15 15:15:44.216: E/ROCKEY(2757): dash1,length:31
07-15 15:15:44.216: E/ROCKEY(2757): dashx
07-15 15:15:44.216: E/ROCKEY(2757): dash1,length:31
07-15 15:15:44.216: E/ROCKEY(2757): dashx
07-15 15:15:44.216: E/ROCKEY(2757): dash1,length:31
07-15 15:15:44.216: E/ROCKEY(2757): dashx
07-15 15:15:44.216: E/ROCKEY(2757): dash1,length:31
07-15 15:15:44.216: E/ROCKEY(2757): dashx
07-15 15:15:44.216: E/ROCKEY(2757): dash1,length:31
07-15 15:15:44.216: E/ROCKEY(2757): 0~7,i=29
07-15 15:15:44.216: E/ROCKEY(2757): val1:0
07-15 15:15:44.216: E/ROCKEY(2757): val2:7
07-15 15:15:44.216: W/System.err(2757): java.lang.StringIndexOutOfBoundsException: length=31; index=31
07-15 15:15:44.216: W/System.err(2757): at com.rockey.test1.MainActivity.convertToBytes(MainActivity.java:133)
07-15 15:15:44.216: W/System.err(2757): at com.rockey.test1.MainActivity.onCreate(MainActivity.java:22)
07-15 15:15:44.216: W/System.err(2757): at android.app.Activity.performCreate(Activity.java:5104)
07-15 15:15:44.216: W/System.err(2757): at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1080)
07-15 15:15:44.216: W/System.err(2757): at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2144)
07-15 15:15:44.216: W/System.err(2757): at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2230)
07-15 15:15:44.216: W/System.err(2757): at android.app.ActivityThread.access$600(ActivityThread.java:141)
07-15 15:15:44.216: W/System.err(2757): at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1234)
07-15 15:15:44.216: W/System.err(2757): at android.os.Handler.dispatchMessage(Handler.java:99)
07-15 15:15:44.216: W/System.err(2757): at android.os.Looper.loop(Looper.java:137)
07-15 15:15:44.216: W/System.err(2757): at android.app.ActivityThread.main(ActivityThread.java:5041)
07-15 15:15:44.220: W/System.err(2757): at java.lang.reflect.Method.invokeNative(Native Method)
07-15 15:15:44.220: W/System.err(2757): at java.lang.reflect.Method.invoke(Method.java:511)
07-15 15:15:44.220: W/System.err(2757): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:829)
07-15 15:15:44.220: W/System.err(2757): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:596)
07-15 15:15:44.220: W/System.err(2757): at dalvik.system.NativeStart.main(Native Method)
07-15 15:15:44.220: E/ROCKEY(2757): StringIndexOutOfBoundsException3
07-15 15:15:44.220: E/ROCKEY(2757): octets2:EEEEEEE
07-15 15:15:44.220: E/ROCKEY(2757): Character.digit:11

你可能感兴趣的:(android,功能分析,convertToBytes)