- How to let selector that socketchannel key change in java nio
- public synchronized int writeData(EventObject source) {
- int n = 0;
- int count = 0;
- SocketChannel socket = (SocketChannel)source.getSource();
- ByteBuffer buffer = ((WriteEvent)source).getBuffer();
- try {
- write(socket);
- } catch (IOException e1) {
- e1.printStackTrace();
- }
- while (buffer.position()>0) {
- try {
- buffer.flip();
- n = socket.write(buffer);
- if(n == 0) {
- key.interestOps(SelectionKey.OP_WRITE); synchronized (this.pendingData) {
- List<ByteBuffer> queue = (List<ByteBuffer>) this.pendingData.get(socket);
- if(queue == null) {
- queue = new ArrayList<ByteBuffer>();
- this.pendingData.put(socket, queue);
- }
- queue.add(buffer);
- logger.logInfo("queue length:" + queue.size());
- }
- break;
- }
- count += n;
- } catch (IOException e) {
- e.printStackTrace();
- } finally {
- buffer.compact();
- }
- }
- if(buffer.position()==0) {
- key.interestOps(SelectionKey.OP_READ);
- }
- return count;
- }
- public synchronized int write(SocketChannel sc, ByteBuffer wbuf) {
- int n = 0;
- int count = 0;
- SelectionKey key = sc.keyFor(this.dispatcher.getDemultiplexer().getDemux());
- while (wbuf.position()>0) {
- try {
- wbuf.flip();
- n = sc.write(wbuf);
- if(n == 0) {
- key.interestOps(SelectionKey.OP_WRITE);
- synchronized (this.pendingData) {
- List<ByteBuffer> queue = (List<ByteBuffer>) this.pendingData.get(sc);
- if(queue == null) {
- queue = new ArrayList<ByteBuffer>();
- this.pendingData.put(sc, queue);
- }
- queue.add(wbuf);
- }
- break;
- }
- count += n;
- } catch (IOException e) {
- e.printStackTrace();
- } finally {
- wbuf.compact();
- }
- }
- if(wbuf.position()==0) {
- wbuf.clear();
- key.interestOps(SelectionKey.OP_READ);
- }
- return n;
- }
- public void write(SocketChannel socketChannel) throws IOException {
- SelectionKey key = socketChannel.keyFor(this.dispatcher.getDemultiplexer().getDemux());
- synchronized (this.pendingData) {
- List<ByteBuffer> queue = (List<ByteBuffer>) this.pendingData.get(socketChannel);
- if(queue == null || queue.isEmpty()) {
- // We wrote away all data, so we're no longer interested
- // in writing on this socket. Switch back to waiting for data.
- try {
- if (key!=null)
- key.interestOps(SelectionKey.OP_READ);
- } catch(Exception ex) {
- if (key!=null)
- key.cancel();
- }
- }
- // Write until there's not more data ...
- int n = 0;
- while (queue != null && !queue.isEmpty()) {
- ByteBuffer buf = (ByteBuffer) queue.get(0);
- // zero length write, break the loop and wait for next writable time
- n = write(socketChannel, buf);
- logger.logInfo("queue length:" + queue.size() + " used time: " + (t2-t1) + " ms.");
- if(n==0) {
- break;
- }
- queue.remove(0);
- }
- }