/* * Copyright 2011 Future Systems * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.krakenapps.logdb.pcap.impl; import java.io.File; import java.io.IOException; import java.util.Date; import org.krakenapps.logdb.LogQueryCommand; import org.krakenapps.pcap.Protocol; import org.krakenapps.pcap.decoder.ethernet.EthernetFrame; import org.krakenapps.pcap.decoder.ethernet.EthernetProcessor; import org.krakenapps.pcap.decoder.http.HttpDecoder; import org.krakenapps.pcap.decoder.http.HttpProcessor; import org.krakenapps.pcap.decoder.http.HttpRequest; import org.krakenapps.pcap.decoder.http.HttpResponse; import org.krakenapps.pcap.decoder.tcp.TcpDirection; import org.krakenapps.pcap.decoder.tcp.TcpSegment; import org.krakenapps.pcap.decoder.tcp.TcpSegmentCallback; import org.krakenapps.pcap.decoder.tcp.TcpSession; import org.krakenapps.pcap.decoder.udp.UdpPacket; import org.krakenapps.pcap.decoder.udp.UdpProcessor; import org.krakenapps.pcap.packet.PacketHeader; import org.krakenapps.pcap.util.Buffer; import org.krakenapps.pcap.util.PcapFileRunner; import org.slf4j.Logger; import org.slf4j.LoggerFactory; public class PcapCommand extends LogQueryCommand { private final Logger logger = LoggerFactory.getLogger(PcapCommand.class.getName()); private PcapFileRunner runner; public PcapCommand(File f) { headerColumn.put("date", "_time"); runner = new PcapFileRunner(f); runner.getEthernetDecoder().register(new EthernetProcessor() { @Override public void process(EthernetFrame frame) { LogMap m = new LogMap(); PacketHeader h = frame.getPcapPacket().getPacketHeader(); Date date = new Date(h.getTsSec() * 1000L + h.getTsUsec()); m.put("_time", date); m.put("proto", "eth"); m.put("ether_type", frame.getType()); m.put("frame_size", frame.getData().readableBytes()); m.put("dst", frame.getDestination().toString()); m.put("src", frame.getSource().toString()); write(m); } }); runner.getTcpDecoder().registerSegmentCallback(new TcpSegmentCallback() { @Override public void onReceive(TcpSession session, TcpSegment segment) { if (logger.isDebugEnabled()) logger.debug("kraken logdb pcap: tcp [{}]", session.getKey()); Date date = getDate(segment.getIpPacket().getL2Frame()); LogMap m = new LogMap(); m.put("_time", date); m.put("proto", "tcp"); m.put("src_ip", segment.getSourceAddress().getHostAddress()); m.put("src_port", segment.getSourcePort()); m.put("dst_ip", segment.getDestinationAddress().getHostAddress()); m.put("dst_port", segment.getDestinationPort()); m.put("client_ip", session != null ? session.getKey().getClientIp().getHostAddress() : null); m.put("client_port", session != null ? session.getKey().getClientPort() : null); m.put("server_ip", session != null ? session.getKey().getServerIp().getHostAddress() : null); m.put("server_port", session != null ? session.getKey().getServerPort() : null); m.put("client_state", session != null ? session.getClientState() : null); m.put("server_state", session != null ? session.getServerState() : null); if (segment.getDirection() == TcpDirection.ToServer) { m.put("sent", segment.getData() != null ? segment.getData().readableBytes() : 0); m.put("rcvd", 0); } else { m.put("sent", 0); m.put("rcvd", segment.getData() != null ? segment.getData().readableBytes() : 0); } m.put("seq", segment.getSeq()); m.put("ack", segment.getAck()); write(m); } }); runner.getUdpDecoder().registerUdpProcessor(new UdpProcessor() { @Override public void process(UdpPacket p) { Date date = getDate(p.getIpPacket().getL2Frame()); LogMap m = new LogMap(); m.put("_time", date); m.put("proto", "udp"); m.put("src_ip", p.getSource().getAddress().getHostAddress()); m.put("src_port", p.getSourcePort()); m.put("dst_ip", p.getDestination().getAddress().getHostAddress()); m.put("dst_port", p.getDestinationPort()); m.put("length", p.getLength()); m.put("checksum", p.getChecksum()); write(m); } }); HttpDecoder http = new HttpDecoder(); http.register(new HttpProcessor() { @Override public void onRequest(HttpRequest req) { LogMap m = new LogMap(); m.put("proto", "http"); m.put("type", "request"); m.put("server_ip", req.getLocalAddress().getAddress().getHostAddress()); m.put("client_ip", req.getRemoteAddress().getAddress().getHostAddress()); m.put("method", req.getMethod()); m.put("url", req.getURL().toString()); m.put("version", req.getHttpVersion().toString()); write(m); } @Override public void onResponse(HttpRequest req, HttpResponse resp) { LogMap m = new LogMap(); m.put("proto", "http"); m.put("type", "response"); m.put("server_ip", req.getLocalAddress().getAddress().getHostAddress()); m.put("client_ip", req.getRemoteAddress().getAddress().getHostAddress()); m.put("method", req.getMethod()); m.put("url", req.getURL().toString()); m.put("status_code", resp.getStatusCode()); m.put("status_line", resp.getStatusLine()); write(m); } @Override public void onMultipartData(Buffer buffer) { } }); runner.getTcpDecoder().getProtocolMapper().register(Protocol.HTTP, http); } private Date getDate(Object frame) { Date date = null; if (frame != null && frame instanceof EthernetFrame) { EthernetFrame eth = (EthernetFrame) frame; if (eth.getPcapPacket() != null) date = eth.getPcapPacket().getPacketHeader().getDate(); } return date; } @Override public void start() { status = Status.Running; try { runner.run(); } catch (IOException e) { } finally { eof(); } } @Override public boolean isReducer() { return false; } @Override public void push(LogMap m) { } }