10000 gleichzeitige Verbindung mit Java NIO

Ich habe einen Server geschrieben (ähnlich einemHie) undClient code mit Java nio.

Ich versuche so viele Verbindungen wie möglich herzustellen. Aufgrund früherer Vorschläge habe ich den Prozess der Client-Erstellung verlangsamt und dem Betriebssystem (Windows 8) genügend Zeit eingeräumt, um die Anforderungen zu bearbeiten.

Ich habe den Client-Code auf einem anderen Computer ausgeführt, sodass der Server über den gesamten verfügbaren Speicherplatz verfügt.

Wenn ich versuche, 10.000 Verbindungen herzustellen, werden rund 8500 Verbindungen hergestellt, und der Rest wird für die Verbindung abgelehnt, und die Ablehnung der Verbindung für Clients (Threads im Client-Code) geschieht mehr, die später erstellt werden (für die Schleife im Client-Code).

Meine CPU- und Speicherauslastung steigt drastisch an. Ich habe ein Profil erstellt, um zu sehen, dass die meisten (48% des gesamten CPU-Verbrauchs) nach einer Auswahlmethode verbraucht werden (Rest meistens durch GUI-Ereignisse). Liegt es an so vielen Kunden? Ich habe auch einige Leute gesehen, die sich über diesen Fehler in JRE7 beschwert haben und vorgeschlagen haben, JRE6 zu verwenden.

Memory Usage sind 2000+ MB fürjavaw.exe -Prozesse. (Ich bemerkte 1 Prozess, der wenig Arbeitsspeicher verbrauchte, aber eine hohe CPU-Auslastung aufwies.) Die Gesamtauslastung lag bei 98%, wenn alle rund 8500 Clients verbunden waren. Das System blieb auch viele Male hängen, wurde aber weiterhin gewartet. Während des Vorgangs wurde die Speichernutzung ohne Seitenpool von 178 MB auf 310 MB erhöht (was ist das maximale Limit?). Liegt es daran, dass wir auf Sockets ohne Seiten schreiben Poolspeicher wird verwendet?

Kann jemand bitte sagen, an welche Grenzen ich stoßen könnte, damit die 10.000 erfolgreichen Verbindungen nicht möglich sind? (Socket pro Prozesslimit?) (Nicht ausgelagerter Speicher?) (Backlog-Warteschlange erneut?) Optimierungen, mit denen möglicherweise Limits verschoben werden können? (Windows-Maschine)

ch verwende Windows 8 auf einem 4-GB-Syste

`

public class Server implements Runnable  {

public final static String ADDRESS = "192.168.2.14";

public final static int PORT = 8511;

public final static long TIMEOUT = 10000;

public int clients;

ByteBuffer readBuffer = ByteBuffer.allocate(1024);

private ServerSocketChannel serverChannel;

private Selector selector;

private Map<SocketChannel,byte[]> dataTracking = new HashMap<SocketChannel, byte[]>();

public Server(){
    init();
}

private void init(){
    System.out.println("initializing server");

    if (selector != null) return;
    if (serverChannel != null) return;

    try {
        selector = Selector.open();
        serverChannel = ServerSocketChannel.open();
        serverChannel.configureBlocking(false);
        serverChannel.socket().bind(new InetSocketAddress(ADDRESS, PORT));
        serverChannel.register(selector, SelectionKey.OP_ACCEPT);
    } catch (IOException e) {
        e.printStackTrace();
    }
}

@Override
public void run() {
    System.out.println("Now accepting connections...");
    try{
        while (!Thread.currentThread().isInterrupted()){

            int ready = selector.select();
            if(ready==0)
                continue;
            Iterator<SelectionKey> keys = selector.selectedKeys().iterator();

            while (keys.hasNext()){
                SelectionKey key = keys.next();
                keys.remove();
                if (!key.isValid()){
                    continue;
                }

                if (key.isAcceptable()){
                    System.out.println("Accepting connection");
                    accept(key);
                }

                if (key.isWritable()){
                    System.out.println("Writing...");
                    write(key);
                }

                if (key.isReadable()){
                    System.out.println("Reading connection");
                    read(key);
                }
            }
        }
    } catch (IOException e){
        e.printStackTrace();
    } finally{
        closeConnection();
    }

}

private void write(SelectionKey key) throws IOException{

    SocketChannel channel = (SocketChannel) key.channel();
    byte[] data = dataTracking.get(channel);
    dataTracking.remove(channel);
    **int count = channel.write(ByteBuffer.wrap(data));
    if(count == 0)
    {
        key.interestOps(SelectionKey.OP_WRITE);
        return;
    }
    else if(count > 0)
    {
        key.interestOps(0);
        key.interestOps(SelectionKey.OP_READ);  
    }** 
}

private void closeConnection(){

    System.out.println("Closing server down");
    if (selector != null){
        try {
            selector.close();
            serverChannel.socket().close();
            serverChannel.close();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

private void accept(SelectionKey key) throws IOException{
    ServerSocketChannel serverSocketChannel = (ServerSocketChannel) key.channel();
    SocketChannel socketChannel = serverSocketChannel.accept();
    if(socketChannel == null)
    {
        throw new IOException();
    }
    socketChannel.configureBlocking(false);
     clients++;
    **//socketChannel.register(selector, SelectionKey.OP_WRITE|SelectionKey.OP_READ);
    SelectionKey skey = socketChannel.register(selector, SelectionKey.OP_READ);**

    byte[] hello = new String("Hello from server").getBytes();
    dataTracking.put(socketChannel, hello);
}

private void read(SelectionKey key) throws IOException{
    SocketChannel channel = (SocketChannel) key.channel();
    readBuffer.clear();
    int length;
    try {
        length = channel.read(readBuffer);
    } catch (IOException e) {
        System.out.println("Reading problem, closing connection");
        System.out.println("No of clients :"+clients);
        key.cancel();
        channel.close();
        return;
    }
    if (length == -1){
        System.out.println("Nothing was there to be read, closing connection");
        channel.close();
        key.cancel();
        return;
    }

    readBuffer.flip();
    byte[] data = new byte[1000];
    readBuffer.get(data, 0, length);
    String fromclient = new String(data,0,length,"UTF-8");
    System.out.println("Received: "+fromclient);
    String dat = fromclient+channel.getRemoteAddress();
    data= dat.getBytes();
    echo(key,data);
}

private void echo(SelectionKey key, byte[] data) throws IOException{
    SocketChannel socketChannel = (SocketChannel) key.channel();
    dataTracking.put(socketChannel, data);
    **//key.interestOps(SelectionKey.OP_WRITE);
    try
    {
        write(key);
    }
    catch(IOException e)
    {
        System.out.println("Problem in echo"+e);
        e.printStackTrace();
    }
}
public static void main(String [] args)
{
    Thread serv = new Thread(new Server());
    serv.start();
}

}

Antworten auf die Frage(2)

Ihre Antwort auf die Frage