私のコンピューターには、UDP パケットを 10 ミリ秒ごとにブロードキャストするように記述した 802.3 有線送信機アプリケーションがあります。各ブロードキャスト パケットには、特定のパケットに固有の 4 バイトの整数値が含まれています。これにより、受信側でドロップされたパケットの数を正確に把握できます。
送信機が Wireshark で動作することを確認しました。同じネットワーク上に 4 台の 802.11 受信機 (Android フォン 2 台とラップトップ コンピューター 2 台) をセットアップしました。ラップトップは UDP ブロードキャスト パケットの 95% を受信しました。1 台の電話で 89% が受信されました。もう一方の電話は 40% を受け取りました。
なんで?
これが私のAndroidレシーバーコードの一部です:
public class NetThread extends Thread {
int[] pkt_nums;
int p;
NetThread(int[] pkt_nums)
{
this.pkt_nums = pkt_nums;
for (int i=0; i<pkt_nums.length; i++)
{
pkt_nums[i]=0;
}
p = 0;
}
@Override
public void run()
{
receiveData();
}
public void receiveData()
{
// request permission to do network operations in manifest file...done
// start the network side of things
DatagramSocket sock = null;
DatagramPacket pkt = null;
try
{
byte[] data = new byte[C.PAYLOAD_MAX];
sock = new DatagramSocket(C.NET_PORT);
sock.setSoTimeout(C.NET_SO_TIMEOUT);
pkt = new DatagramPacket(data, 0, C.PAYLOAD_MAX);
while (true)
{
Thread.sleep(0); // allow for an interrupt
try
{
sock.receive(pkt);
int length = pkt.getLength();
boolean success = writeToBuffer(pkt.getData(), length);
if (!success) break;
}
catch (InterruptedIOException e)
{
// thrown when a timeout occurs
Log.d(C.DTAG, "net: no packets yet");
}
}
Log.d(C.DTAG, "buffer is full. done receiving.");
if (sock != null) sock.close();
}
catch (InterruptedException x)
{
Log.d(C.DTAG, "net: was interrupted.");
}
catch (SocketException e)
{
Log.d(C.DTAG, "net: SocketException");
e.printStackTrace();
}
catch (IOException e)
{
Log.d(C.DTAG, "net: IOException");
e.printStackTrace();
}
if (sock != null) sock.close();
}
public boolean writeToBuffer(byte[] data, int length)
{
// each packet should have exactly 4 bytes - a number
int pkt_num = data[0] & 0x000000FF | data[1]<<8 & 0x0000FF00 | data[2]<<16 & 0x00FF0000 | data[3]<<24 & 0xFF000000;
if (p < pkt_nums.length)
{
pkt_nums[p++] = pkt_num;
return true; // success
}
else
{
return false;
}
}
}
メイン アクティビティで上記のクラスを次のように宣言します。
mNetThrd = new NetThread(pkt_nums);
mNetThrd.setDaemon(true);
mNetThrd.start();
スレッドの優先順位を上げてみますが、何か間違っている気がします。アプリケーションの UDP ブロードキャスト パケットの少なくとも 95% を取得する必要があります。
詳細: ラップトップと電話は、ルーターから 30 フィート離れた場所に隣接して配置されており、見通しの良い場所にあります。ラップトップ 1 は 95% のパケットを受信しました。ラップトップ 2 は 94% を受け取りました。電話 1 は 89% を受け取りました。電話 2 は 40% を受け取りました。どちらも同じアプリを実行しました。その他のネットワーク トラフィックは最小限です。 Android でのドロップ パケットは、通常、一度に 20 ~ 50 のグループで発生します。 802.11 にはクリーン チャネルがあります。各パケットには 4 バイトのペイロードが含まれます。
レシーバー コードに何か根本的な問題があるのでしょうか、それともまったく別の問題なのでしょうか?