java - Android:BluetoothSocket 连接抛出 IOException

标签 java android sockets bluetooth android-bluetooth

我正在编写一个将从另一台设备接收串行数据的应用程序(不是 Android,如果重要的话它将是 Bluesmirf Silver 模块,但现在我只在我的笔记本电脑蓝牙适配器上尝试)。这是我正在使用的代码:

public class ListenThread extends Thread {
    private BluetoothSocket socket;
    private InputStream istream;
    private Handler handler;
    private BluetoothAdapter adapter;

    public ListenThread(BluetoothAdapter adapter, Handler handler) {
        Log.v(TAG, "creating ListenThread");
        this.adapter = adapter;
        this.handler = handler;

        if (adapter.isDiscovering()) {
            adapter.cancelDiscovery();
        }
    }

    public void run() {
        if (running == false) {
            // Thread is cancelled
            Log.v(TAG, "run(): running == false");
            return;
        }

        if (adapter == null) {
            // No BT adapter supplied
            Log.v(TAG, "run(): adapter == null");
            return;
        }

        if (btDevice == null) {
            // No btDevice is paired
            Log.v(TAG, "run(): btDevice == null");
            return;
        }

        try {

            socket = device.createRfcommSocketToServiceRecord(UUID.fromString("00001101-0000-1000-8000-00805F9B34FB"));     
            adapter.cancelDiscovery();
            socket.connect();
            Log.v(TAG, "run(): socket connected");
        } catch (IOException e) {
            Log.v(TAG, "run(): socket not connected");
            Log.v(TAG, "IOException: " + e.toString());
            e.printStackTrace();
            socket = null;
        } 

        if (socket == null) {
            // Connection to device failed
            Log.v(TAG, "run(): socket is null");
            return;
        }

        InputStream tmpIn = null;
        try {
            tmpIn = socket.getInputStream();
        } catch (IOException e) {
            // getInputStream always returns InputStream
            // but operations will throw IOException until
            // the stream is ready
        }
        istream = tmpIn;

        StringBuffer sb = new StringBuffer();
        byte[] buffer = new byte[1024]; // buffer store for the stream
        int bytes;  // bytes returned from the read();
        String message;
        int idx;
        HashMap<String, String> hm;
        String[] chunks;

        Log.v(TAG, "run(): listening loop starting");
        while (true) {
            try {
                // Read from the InputStream
                bytes = istream.read();
                sb.append(new String(buffer, 0, bytes));
                while ((idx = sb.indexOf("\r\n\r\n")) > -1) {
                    message = sb.substring(0, idx);
                    sb.replace(0, idx + 4, "");
                    hm = new HashMap<String, String>();
                    for (String line : message.split("\n")) {
                        chunks = line.trim().split("=", 2);
                        if (chunks.length != 2) continue;
                        hm.put(chunks[0], chunks[1]);
                    }
                    handler.obtainMessage(0x2a, hm).sendToTarget();
                }
            } catch (IOException e) {
                break;
            }
        }
    }

我总是在 socket.connect() 行得到一个 IOException。我尝试了几种建立连接的方法,但没有一种有效,但每种方法都引发了不同的 IO 异常:

方法一:

socket=BluetoothAdapter.getDefaultAdapter().getRemoteDevice(device.getAddress()).createRfcommSocketToServiceRecord(UUID.fromString("00001101-0000-1000-8000-00805F9B34FB"));

方法二:

socket = device.createInsecureRfcommSocketToServiceRecord(UUID.fromString("00001101-0000-1000-8000-00805F9B34FB"));

方法三:

socket = device.createRfcommSocketToServiceRecord(UUID.fromString("00001101-0000-1000-8000-00805F9B34FB"));

我也这样试过:

Method m = device.getClass().getMethod("createRfcommSocket", new Class[] {int.class});
socket = (BluetoothSocket) m.invoke(device, 1);

我总是收到服务发现失败或连接被拒绝的消息。这就是我管理 ListenThread 的方式:

public void startListening() {
    Log.v(TAG, "starting to listen");
    running = true;     
}

public void stopListening() {
    Log.v(TAG, "stoping listening");
    running = false;
}

我在 Google 上进行了搜索,但我发现的只是连接 socket 的不同方法,但正如我所说,它们都不起作用。任何想法?非常感谢!

编辑:

这就是 Log.v(TAG, "IOException: "+ e.toString());和 e.printStackTrace();打印:

    IOException: java.io.IOException: Service discovery failed
    java.io.IOException: Service discovery failed
    W/System.err(8604):     at android.bluetooth.BluetoothSocket$SdpHelper.doSdp(BluetoothSocket.java:397)
    W/System.err(8604):     at android.bluetooth.BluetoothSocket.connect(BluetoothSocket.java:207)
    W/System.err(8604):     at com.ginger.kanarci_android.communication.BluetoothService$ListenThread.run(BluetoothService.java:133)

最佳答案

所以我终于能够解决这个问题。唯一的问题是 UUID。在我发布的代码中,我使用了众所周知的 SPP UUID,但我的笔记本电脑的蓝牙适配器具有不同的 UUID,这就是我认为两者无法连接的原因。

当我配置 Bluesmirf 模块(默认情况下具有 SSP UUID)并尝试从应用程序连接时,它运行良好。

关于java - Android:BluetoothSocket 连接抛出 IOException,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22767989/

相关文章:

android - 如何更改Android中状态栏的颜色?

C - 套接字,分离数据和http header ?

java - 带有 Apache Derby 的 JDBC 抛出 java.sql.SQLNonTransientConnectionException : No current connection

java - 如何配置 Maven 编译器插件以在发生错误时继续并在构建过程结束时显示它们?

java - 比较两个数组中的共同项并返回另一个具有共同项的数组

android - 在 android 4.1 中使用 android L 按钮,例如 google plus app

java - 尝试在android中的AsyncTask中读取文本文件,但我得到空结果

java - Java 中泛型类型的泛型类型?

c - sendto()函数中发送一个结构体——C语言

java - 获取套接字数据后调用单独的线程进行进一步处理?