/* * Created by Andrey Cherkashin (acherkashin) * http://acherkashin.me * * License * Copyright (c) 2015 Andrey Cherkashin * The project released under the MIT license: http://opensource.org/licenses/MIT */ package ragefist.core.network; import java.io.IOException; import java.net.ConnectException; import java.nio.ByteBuffer; import java.nio.charset.Charset; import java.util.ArrayList; import java.util.List; /** * * @author acherkashin */ public class SocketStrategyDefault implements ISocketStrategy { private static final Charset _charset = Charset.defaultCharset(); private final static ISocketStrategy _instance = new SocketStrategyDefault(); public static final ISocketStrategy getInstance() { return _instance; } @Override public byte[][] readPackets(SocketClient socket, ByteBuffer readBuffer) throws IOException { PacketBufferDefault packetBuffer = (PacketBufferDefault)socket.getPacketBuffer(PacketBufferDefault.class); List<byte[]> packets = new ArrayList<>(); int bytesRead; while ((bytesRead = socket.read(readBuffer)) > 0) { readBuffer.flip(); while(readBuffer.remaining() > 0) { // No header yet if (packetBuffer.hasHeader() == false) { // Can't read header - need to put 4 bytes into the buffer if (packetBuffer.canReadHeader() == false) { packetBuffer.put(readBuffer, 0, Math.min(4, readBuffer.remaining())); if (readBuffer.remaining() == 0) { break; } } // Can read header - its already in a packet buffer if (packetBuffer.canReadHeader()) { packetBuffer.readHeader(); } } // Packet header is already exist if (packetBuffer.hasHeader()) { int bytesToWrite = packetBuffer.getBytesToFinishPacket(); if (bytesToWrite > 0) { packetBuffer.put(readBuffer, 0, Math.min(bytesToWrite, readBuffer.remaining())); } if (packetBuffer.hasPacket()) { packets.add(packetBuffer.readPacket()); } } } readBuffer.clear(); } if (bytesRead < 0) { throw new ConnectException(); } byte[][] array = new byte[packets.size()][]; for(int i = 0; i < array.length; i++) { byte[] byteArray = packets.get(i); array[i] = byteArray; } return array; } @Override public int writePacket(SocketClient socket, String packet) throws IOException { return socket.write(_charset.encode(packet)); } @Override public int writePacket(SocketClient socket, byte[] bytes) throws IOException { ByteBuffer buffer = ByteBuffer.allocate(bytes.length + 4); // 4 bytes for length buffer.putInt((int)bytes.length); buffer.put(bytes); buffer.flip(); return socket.write(buffer); } }