Подключите Android и Pi 3 через сетевой разъем, используя Pi 3 в качестве точки доступа - PullRequest
0 голосов
/ 01 октября 2018

Мой план здесь состоит в том, чтобы создать точку доступа на Pi 3 с использованием интерфейса wlan0, который был настроен с использованием hostapd.Я запускаю команду hostapd /etc/hostapd/hostapd.conf, чтобы запустить сеть, а затем хочу подключиться к ней с помощью Android и настроить сокет.

В настоящее время сеть включается на Pi 3 без проблем, но создается сокетна андроид выкидывает

java.net.ConnectException: failed to connect to /192.168.42.1 (port 80) after 500ms: connect failed: ENETUNREACH (Network is unreachable).

Я использую IP-адрес Pi's wlan0, чтобы создать мой сокет, как вы можете видеть (на коде Android).Я опубликую вывод скрипта Python Pi, а также некоторую информацию о сети.

У меня есть следующий код Python 3 на моем Pi 3 (сервере):

import socket
import os

os.system('hostapd /etc/hostapd/hostapd.conf &')
print('started access point service')

serversocket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
serversocket.bind(('192.168.42.1', 80))
serversocket.listen(1)

connection, address = serversocket.accept()

b = connection.recv(1024)
print(b)

serversocket.close()
connection.shutdown(socket.SHUT_WR)
connection.close()

Androidкод, касающийся подключения к разъему Wi-Fi (клиент).Присоединяется к сети, используя ее SSID:

        // enable Wifi
        wifiManager.setWifiEnabled(true);

        // connect to the network access point created by the Pi 3
        WifiConfiguration wifiConfiguration = new WifiConfiguration();
        wifiConfiguration.SSID = "\"" + blackBoxSSID + "\"";
        wifiConfiguration.preSharedKey = "\"" + blackBoxNetworkPassword + "\"";
        wifiConfiguration.status = WifiConfiguration.Status.ENABLED;
        wifiConfiguration.allowedProtocols.set(WifiConfiguration.Protocol.WPA);
        wifiConfiguration.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK);

        int netID = wifiManager.addNetwork(wifiConfiguration);
        if (netID == -1) {
            netID = getExistingNetworkID(wifiConfiguration.SSID);
        }

        wifiManager.disconnect();
        wifiManager.enableNetwork(netID, true);
        wifiManager.reconnect();

        WifiInfo wifiInfo = wifiManager.getConnectionInfo();

        Log.d(TAG, "current netID " + netID + ", current SSID " + wifiInfo.getSSID());
        Log.d(TAG, "current IP of wifi device: " + wifiInfo.getIpAddress() + ", HW address: " + wifiInfo.getMacAddress());

        // start the server socket process
        startServerSocket();

Вспомогательные функции:

    private void startServerSocket() {
            Log.i(TAG, "Starting server socket thread");
            Thread serverSocketThread = new Thread(new Runnable() {
                @Override
                public void run() {
                    try {
                        Socket socket = new Socket();
                        socket.bind(null);
                        socket.connect(new InetSocketAddress("192.168.42.1", 80), 500);
                        DataOutputStream dataOutputStream = new DataOutputStream(socket.getOutputStream());
                        dataOutputStream.writeBytes("Hello black box");
                        dataOutputStream.writeBytes("Hello black box");
                        dataOutputStream.writeBytes("Hello black box");
                        dataOutputStream.writeBytes("Hello black box");
                        dataOutputStream.writeBytes("Hello black box");
                        dataOutputStream.writeBytes("Hello black box");
                        socket.close();
                    } catch (IOException e) {
                        Log.e(TAG, "Error creating ServerSocket and Socket object:", e);
                    }
                }
            });
            serverSocketThread.start();
            Log.d(TAG, "started server socket thread");
        }

и

private int getExistingNetworkID(String SSID) {
        WifiManager wifiManager = (WifiManager) mContext.getApplicationContext().getSystemService(Context.WIFI_SERVICE);
        List<WifiConfiguration> configuredNetworks = wifiManager.getConfiguredNetworks();
        if (configuredNetworks != null) {
            for (WifiConfiguration existingConfig : configuredNetworks) {
                if (existingConfig.SSID.equals(SSID)) {
                    return existingConfig.networkId;
                }
            }
        }
        return -1;
    }

, вот файл манифеста:

<!-- Wifi/Internet-related permissions -->
    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
    <uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
    <uses-permission android:name="android.permission.CHANGE_WIFI_STATE"/>
    <uses-permission android:name="android.permission.INTERNET"/>

Код Android возвращает

current netID 617, current SSID "NetworkName" current IP of wifi device: 0, HW address: <hw address of something but not wlan0>, что означает, что правильная сеть подключена без проблем.

Код Python возвращает

started access point service
Configuration file: /etc/hostapd/hostapd.conf
Failed to create interface mon.wlan0: -95 (Operation not supported)
wlan0: interface state UNINITIALIZED->COUNTRY_UPDATE
wlan0: Could not connect to kernel driver
Using interface wlan0 with hwaddr <wlan0 hw address> and ssid "NetworkName"
listening on port 80
wlan0: interface state COUNTRY_UPDATE->ENABLED
wlan0: AP-ENABLED 

и все устройства Wi-FiЯ могу видеть сеть и подключиться, используя пароль.

Для получения дополнительной информации вот файл hostapd.conf:

interface=wlan0
#driver=nl80211
ssid=Coriolis
country_code=CA
hw_mode=g
channel=6
wmm_enabled=0
macaddr_acl=0
auth_algs=1
ignore_broadcast_ssid=0
wpa=2
wpa_passphrase=password123
wpa_key_mgmt=WPA-PSK
wpa_group_rekey=86400
ieee80211n=1
wpa_pairwise=TKIP
rsn_pairwise=CCMP
wme_enabled=1

извините за отступ внутри некоторых фрагментов кода, используякнопка {} code вставляет это, и я не могу избавиться от этого, не удалив форматирование кода.

Редактировать:

Вот содержимое /etc/dnsmasq.conf:

interface=wlan0 dhcp-range=192.168.42.2,192.168.42.4,255.255.255.0,24h

dnsmasq и hostapd службы оба active (running)

Если я вручную захожу и выбираю Wi-Fi, затем подключаюсь с помощью пароля WPA, устройство связывает затемразъединяется с Pi 3, затем читает AP-STA-CONNECTED с pairwise key handshake completed (RSN).Ясно, что мой код Android делает что-то странное.Но при этом происходит сбой приложения с RuntimeException; unable to instantiate receiver (wifiReceiver - which doesn't exist) и ClassNotFoundException: didn't find class (wifiReceiver) on path: DexPathList.Похоже, что это также полностью внутренний вызов, нет никаких обратных ссылок на мой фактический код.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...