public MessageProcessorFilter(Layer layer, int arequestTimeout, ByteBufferPool bbPool, AsyncWriteCallbackHandler asyncWriteCallbackHandler) {
this(layer, arequestTimeout, false, bbPool, asyncWriteCallbackHandler);
}
public boolean execute(final Context ctx) throws IOException {
SipServletMessageImpl parsedMessage = null;
Socket s = null;
InetSocketAddress remoteAddress = null;
SipServletMessageImpl _message = null;
boolean invokeNextFilter = true;
final WorkerThread workerThread =
((WorkerThread) Thread.currentThread());
ByteBuffer buffer = workerThread.getByteBuffer();
SipParser _parser = SipParser.getInstance();
final Protocol prot = ctx.getProtocol();
final SelectionKey key = ctx.getSelectionKey();
final SelectorHandler handler = ctx.getSelectorHandler();
final ThreadAttachment currentTA = workerThread.getAttachment();
TargetTuple remote = null;
InetSocketAddress local = null;
X509Certificate[] x509Certs = null;
switch (prot) {
case TCP:
s = ((SocketChannel) key.channel()).socket();
remoteAddress = (InetSocketAddress) s.getRemoteSocketAddress();
remote = new TargetTuple(SipTransports.TCP_PROT, remoteAddress);
local = (InetSocketAddress) s.getLocalSocketAddress();
break;
case UDP:
if (!GrizzlyNetworkManager.useDefaultUDPSelectorHandler){
buffer = (ByteBuffer) ctx.removeAttribute
(GrizzlyNetworkManager.UDP_BUFFER);
} else {
ctx.setKeyRegistrationState(Context.KeyRegistrationState.NONE);
handler.register(key, SelectionKey.OP_READ);
}
DatagramSocket d = ((DatagramChannel) key.channel()).socket();
remoteAddress =
(InetSocketAddress) ctx.getAttribute(ReadFilter.UDP_SOCKETADDRESS);
remote = new TargetTuple(SipTransports.UDP_PROT, remoteAddress);
local = (InetSocketAddress) d.getLocalSocketAddress();
break;
case TLS:
s = ((SocketChannel) key.channel()).socket();
remoteAddress = (InetSocketAddress) s.getRemoteSocketAddress();
remote = new TargetTuple(SipTransports.TLS_PROT, remoteAddress);
local = (InetSocketAddress) s.getLocalSocketAddress();
Object[] certs =
(Object[]) ctx.removeAttribute(GrizzlyNetworkManager.SIP_CERTS);
if ((certs != null) && (certs.length > 0)) {
ArrayList<X509Certificate> al =
new ArrayList<X509Certificate>();
for (int i = 0; i < certs.length; i++) {
if (certs[i] instanceof X509Certificate) {
al.add((X509Certificate) certs[i]);
} else {
logger.log(Level.WARNING,
"sip.network.grizzly.wrong.certs",
new Object[]{certs[i].getClass()});
}
}
x509Certs = al.toArray(new X509Certificate[al.size()]);
}
break;
}
try {
int initialSize = 0;
buffer.flip();
int remaining = buffer.remaining();
while (((remaining > 0) && (initialSize != remaining)) ||
(parsedMessage == null)) {
initialSize = remaining;
if (_message == null) {
skipNewLines(buffer);
}
if (!buffer.hasRemaining()) {
return invokeNextFilter;
}
parsedMessage = _parser.parseMessage(_message, buffer, local,
remote, null);
remaining = buffer.remaining();
if ((parsedMessage != null) &&
parsedMessage.isMessageComplete() && remaining > 0) {
if (isRequestBlocked) {
processMessageBlockedState(parsedMessage);
continue;
}
final SipServletMessageImpl msg = parsedMessage;
parsedMessage = null;
_message = null;
final InetSocketAddress _remoteAddress = remoteAddress;
msg.setCertificate(x509Certs);
SipContainerThreadPool.getInstance().execute(new Callable() {
public Object call() throws Exception {
if (prot == Protocol.TLS) {
if (currentTA != null) {
((WorkerThread) Thread.currentThread()).
setSSLEngine(currentTA.getSSLEngine());
((WorkerThread) Thread.currentThread()).
updateAttachment(Mode.SSL_ENGINE);
} else {
logger.log(Level.WARNING,
"Thread attachment is null");
return null;
}
}
processMessage(msg, key, handler, _remoteAddress,
prot);
return null;
}
});
continue;
}
if ((parsedMessage == null) ||
!parsedMessage.isMessageComplete()) {
// UDP packet are *always* read using a single read, hence
// no need to try another read using a temporary Selector.
if (prot != Protocol.UDP) {
if (logger.isLoggable(Level.FINEST)) {
logger.log(Level.FINEST,
"sip.network.grizzly.incomplete.tcp.request",
new Object[]{buffer.position()});
}
initialSize = remaining;
if (buffer.hasRemaining()) {
buffer.compact();
} else {
buffer.clear();
}
// The thread might block when reading more bytes using
// a temporary Selector.
ByteBufferInputStream inputStream =
new ByteBufferInputStream();
inputStream.setSecure((prot == Protocol.TLS));
inputStream.setSelectionKey(ctx.getSelectionKey());
inputStream.setReadTimeout(requestTimeOut * 1000);
int nRead = inputStream.read(buffer);
if (nRead <= 0) {
logger.log(Level.SEVERE,
"sip.network.grizzly.readtimeout",
new Object[]{requestTimeOut, nRead, buffer});
if (logger.isLoggable(Level.FINE)) {
SocketChannel channel = (SocketChannel) ctx.getSelectionKey().
channel();
logger.log(Level.FINE,
"sip.network.grizzly.readtimeout.channel" +
channel);
}
if (parsedMessage != null) {
logger.log(Level.SEVERE,
"sip.network.grizzly.readtimeout.drop",
new Object[]{parsedMessage.toString()});
} // Do not invoke the next ProtocolFilter, if any.
return false;
}
remaining = buffer.remaining();
_message = parsedMessage;
} else {
return true;
}
}
}
if (parsedMessage != null) {
if (isRequestBlocked) {
processMessageBlockedState(parsedMessage);
return false;
}
parsedMessage.setCertificate(x509Certs);
if (prot == Protocol.UDP) {
processMessage(parsedMessage, key, handler, remoteAddress,
prot);
} else {
if (!finalRequestOnContainerThreadPool) {
/**
* The key has to be registered back here for TCP, because
* the request will be processesd in the same worker thread
* and further requests cannot be read until this request
* is processed by the app.
*/
ctx.setKeyRegistrationState(Context.KeyRegistrationState.NONE);
handler.register(key, SelectionKey.OP_READ);
processMessage(parsedMessage, key, handler,
remoteAddress, prot);
} else {
/**
* This is necessary if we have to ensure (mitigate
* ) that the messages are processed in same order. * TODO : To register the key, the buffer
* has to be copied into another buffer because this buffer
* will be reused when this worker thread is used for processing.
*/