serval-dna/java/org/servalproject/servaldna/AbstractExternalInterface.java

106 lines
2.8 KiB
Java

package org.servalproject.servaldna;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.channels.DatagramChannel;
import java.nio.channels.SelectableChannel;
import java.nio.channels.SelectionKey;
/**
* Created by jeremy on 8/05/14.
*/
public abstract class AbstractExternalInterface extends ChannelSelector.Handler {
private final ChannelSelector selector;
protected final MdpSocket socket;
private boolean isUp = false;
public AbstractExternalInterface(ChannelSelector selector, int loopbackMdpPort) throws IOException {
this.socket = new MdpSocket(loopbackMdpPort);
this.selector = selector;
selector.register(this);
}
public void close(){
try {
selector.unregister(this);
} catch (IOException e) {
e.printStackTrace();
}
socket.close();
}
private static final int MDP_INTERFACE=4;
private static final int MDP_INTERFACE_UP=0;
private static final int MDP_INTERFACE_DOWN=1;
private static final int MDP_INTERFACE_RECV=2;
public void up(String config) throws IOException {
MdpPacket packet = new MdpPacket();
packet.setRemotePort(MDP_INTERFACE);
packet.payload.put((byte) MDP_INTERFACE_UP);
packet.payload.put(config.getBytes());
packet.payload.flip();
packet.send((DatagramChannel)socket.getChannel());
isUp = true;
}
public void down() throws IOException {
isUp = false;
MdpPacket packet = new MdpPacket();
packet.setRemotePort(MDP_INTERFACE);
packet.payload.put((byte) MDP_INTERFACE_DOWN);
packet.payload.flip();
packet.send((DatagramChannel) socket.getChannel());
}
public void receivedPacket(byte recvaddr[], byte recvbytes[]) throws IOException {
receivedPacket(recvaddr, recvbytes, 0, recvbytes==null?0:recvbytes.length);
}
public void receivedPacket(byte recvaddr[], byte recvbytes[], int offset, int len) throws IOException {
if (!isUp)
return;
MdpPacket packet = new MdpPacket();
packet.setRemotePort(MDP_INTERFACE);
packet.payload.put((byte) MDP_INTERFACE_RECV);
packet.payload.put((byte) recvaddr.length);
packet.payload.put(recvaddr);
if (len>0)
packet.payload.put(recvbytes, offset, len);
packet.payload.flip();
packet.send((DatagramChannel) socket.getChannel());
}
protected abstract void sendPacket(byte addr[], ByteBuffer payload);
@Override
public void read() {
try {
MdpPacket response = new MdpPacket();
socket.receive(response);
if (!isUp)
return;
int addrlen = response.payload.get() & 0xFF;
byte addr[]=null;
if (addrlen>0) {
addr = new byte[addrlen];
response.payload.get(addr);
}
sendPacket(addr, response.payload);
} catch (IOException e) {
e.printStackTrace();
}
}
@Override
public SelectableChannel getChannel() throws IOException {
return socket.getChannel();
}
@Override
public int getInterest() {
return SelectionKey.OP_READ;
}
}