/** * Creates a OFPacketOut with the OFPacketIn data that is flooded on all ports unless the port is * blocked, in which case the packet will be dropped. * * @param sw The switch that receives the OFPacketIn * @param pi The OFPacketIn that came to the switch * @param cntx The FloodlightContext associated with this OFPacketIn */ @LogMessageDoc( level = "ERROR", message = "Failure writing PacketOut " + "switch={switch} packet-in={packet-in} " + "packet-out={packet-out}", explanation = "An I/O error occured while writing a packet " + "out message to the switch", recommendation = LogMessageDoc.CHECK_SWITCH) protected void doFlood(IOFSwitch sw, OFPacketIn pi, FloodlightContext cntx) { if (topology.isIncomingBroadcastAllowed(sw.getId(), pi.getInPort()) == false) { if (log.isTraceEnabled()) { log.trace( "doFlood, drop broadcast packet, pi={}, " + "from a blocked port, srcSwitch=[{},{}], linkInfo={}", new Object[] {pi, sw.getId(), pi.getInPort()}); } return; } // Set Action to flood OFPacketOut po = (OFPacketOut) floodlightProvider.getOFMessageFactory().getMessage(OFType.PACKET_OUT); List<OFAction> actions = new ArrayList<OFAction>(); if (sw.hasAttribute(IOFSwitch.PROP_SUPPORTS_OFPP_FLOOD)) { actions.add(new OFActionOutput(OFPort.OFPP_FLOOD.getValue(), (short) 0xFFFF)); } else { actions.add(new OFActionOutput(OFPort.OFPP_ALL.getValue(), (short) 0xFFFF)); } po.setActions(actions); po.setActionsLength((short) OFActionOutput.MINIMUM_LENGTH); // set buffer-id, in-port and packet-data based on packet-in short poLength = (short) (po.getActionsLength() + OFPacketOut.MINIMUM_LENGTH); po.setBufferId(pi.getBufferId()); po.setInPort(pi.getInPort()); if (pi.getBufferId() == OFPacketOut.BUFFER_ID_NONE) { byte[] packetData = pi.getPacketData(); poLength += packetData.length; po.setPacketData(packetData); } po.setLength(poLength); try { if (log.isTraceEnabled()) { log.trace( "Writing flood PacketOut switch={} packet-in={} packet-out={}", new Object[] {sw, pi, po}); } messageDamper.write(sw, po, cntx); } catch (IOException e) { log.error( "Failure writing PacketOut switch={} packet-in={} packet-out={}", new Object[] {sw, pi, po}, e); } return; }
/** * TODO This method must be moved to a layer below forwarding so that anyone can use it. * * @param packetData * @param sw * @param ports * @param cntx */ @LogMessageDoc( level = "ERROR", message = "Failed to clear all flows on switch {switch}", explanation = "An I/O error occured while trying send " + "topology discovery packet", recommendation = LogMessageDoc.CHECK_SWITCH) public void doMultiActionPacketOut( byte[] packetData, IOFSwitch sw, Set<Short> ports, FloodlightContext cntx) { if (ports == null) return; if (packetData == null || packetData.length <= 0) return; OFPacketOut po = (OFPacketOut) floodlightProvider.getOFMessageFactory().getMessage(OFType.PACKET_OUT); List<OFAction> actions = new ArrayList<OFAction>(); for (short p : ports) { actions.add(new OFActionOutput(p, (short) 0)); } // set actions po.setActions(actions); // set action length po.setActionsLength((short) (OFActionOutput.MINIMUM_LENGTH * ports.size())); // set buffer-id to BUFFER_ID_NONE po.setBufferId(OFPacketOut.BUFFER_ID_NONE); // set in-port to OFPP_NONE po.setInPort(OFPort.OFPP_NONE.getValue()); // set packet data po.setPacketData(packetData); // compute and set packet length. short poLength = (short) (OFPacketOut.MINIMUM_LENGTH + po.getActionsLength() + packetData.length); po.setLength(poLength); try { // counterStore.updatePktOutFMCounterStore(sw, po); if (log.isTraceEnabled()) { log.trace( "write broadcast packet on switch-id={} " + "interaces={} packet-data={} packet-out={}", new Object[] {sw.getId(), ports, packetData, po}); } sw.write(po, cntx); } catch (IOException e) { log.error("Failure writing packet out", e); } }
/** * Write packetout message to sw with output actions to one or more output ports with * inPort/outPorts passed in. * * @param packetData * @param sw * @param inPort * @param ports * @param cntx */ public void packetOutMultiPort( byte[] packetData, IOFSwitch sw, short inPort, Set<Integer> outPorts, FloodlightContext cntx) { // setting actions List<OFAction> actions = new ArrayList<OFAction>(); Iterator<Integer> j = outPorts.iterator(); while (j.hasNext()) { actions.add(new OFActionOutput(j.next().shortValue(), (short) 0)); } OFPacketOut po = (OFPacketOut) floodlightProvider.getOFMessageFactory().getMessage(OFType.PACKET_OUT); po.setActions(actions); po.setActionsLength((short) (OFActionOutput.MINIMUM_LENGTH * outPorts.size())); // set buffer-id to BUFFER_ID_NONE, and set in-port to OFPP_NONE po.setBufferId(OFPacketOut.BUFFER_ID_NONE); po.setInPort(inPort); // data (note buffer_id is always BUFFER_ID_NONE) and length short poLength = (short) (po.getActionsLength() + OFPacketOut.MINIMUM_LENGTH); poLength += packetData.length; po.setPacketData(packetData); po.setLength(poLength); try { counterStore.updatePktOutFMCounterStoreLocal(sw, po); if (log.isTraceEnabled()) { log.trace( "write broadcast packet on switch-id={} " + "interfaces={} packet-out={}", new Object[] {sw.getId(), outPorts, po}); } messageDamper.write(sw, po, cntx); } catch (IOException e) { log.error("Failure writing packet out", e); } }