Esempio n. 1
0
 @Override
 public Future<OFFeaturesReply> querySwitchFeaturesReply() throws IOException {
   OFMessage request =
       floodlightProvider.getOFMessageFactory().getMessage(OFType.FEATURES_REQUEST);
   request.setXid(getNextTransactionId());
   OFFeaturesReplyFuture future = new OFFeaturesReplyFuture(threadPool, this, request.getXid());
   this.featuresFutureMap.put(request.getXid(), future);
   List<OFMessage> msglist = new ArrayList<OFMessage>(1);
   msglist.add(request);
   this.write(msglist);
   return future;
 }
Esempio n. 2
0
 @Override
 public void deliverStatisticsReply(OFMessage reply) {
   OFStatisticsFuture future = this.statsFutureMap.get(reply.getXid());
   if (future != null) {
     future.deliverFuture(this, reply);
     // The future will ultimately unregister itself and call
     // cancelStatisticsReply
     return;
   }
   /* Transaction id was not found in statsFutureMap.check the other map */
   IOFMessageListener caller = this.iofMsgListenersMap.get(reply.getXid());
   if (caller != null) {
     caller.receive(this, reply, null);
   }
 }
Esempio n. 3
0
 @Override
 public void deliverOFFeaturesReply(OFMessage reply) {
   OFFeaturesReplyFuture future = this.featuresFutureMap.get(reply.getXid());
   if (future != null) {
     future.deliverFuture(this, reply);
     // The future will ultimately unregister itself and call
     // cancelFeaturesReply
     return;
   }
   log.error("Switch {}: received unexpected featureReply", this);
 }
Esempio n. 4
0
  /**
   * Handle replies to certain OFMessages, and pass others off to listeners
   *
   * @param sw
   * @param msgs
   * @throws IOException
   */
  @SuppressWarnings("unchecked")
  protected void handleMessages(IOFSwitchExt sw, List<OFMessage> msgs) throws IOException {
    for (OFMessage m : msgs) {
      // If we detect a write failure, break early so we can disconnect
      if (((OFStream) sw.getInputStream()).getWriteFailure()) {
        break;
      }
      // Always handle ECHO REQUESTS, regardless of state
      switch (m.getType()) {
        case ECHO_REQUEST:
          OFMessageInStream in = sw.getInputStream();
          OFMessageOutStream out = sw.getOutputStream();
          OFEchoReply reply = (OFEchoReply) in.getMessageFactory().getMessage(OFType.ECHO_REPLY);
          reply.setXid(m.getXid());
          out.write(reply);
          break;
        case ECHO_REPLY:
          // *Note, ECHO REPLIES need no handling due to last message timestamp
          break;
        case ERROR:
          logError(sw, (OFError) m);
          // fall through intentionally so error can be listened for
        default:
          switch (sw.getState()) {
            case DISCONNECTED:
              log.info("Switch {} in state DISCONNECTED, exiting message processing loop", sw);
              return;
            case HELLO_SENT:
              if (m.getType() == OFType.HELLO) {
                log.debug("HELLO from {}", sw);
                sw.transitionToState(OFSwitchState.FEATURES_REQUEST_SENT);
                // Send initial Features Request
                sw.getOutputStream().write(factory.getMessage(OFType.FEATURES_REQUEST));
              }
              break;
            case FEATURES_REQUEST_SENT:
              if (m.getType() == OFType.FEATURES_REPLY) {
                log.debug("Features Reply from {}", sw);
                sw.setFeaturesReply((OFFeaturesReply) m);

                // Send Description Statistics Request
                OFStatisticsRequest sr = new OFStatisticsRequest();
                sr.setStatisticType(OFStatisticsType.DESC);
                sw.getOutputStream().write(sr);
                sw.transitionToState(OFSwitchState.DESCRIPTION_STATISTICS_REQUEST_SENT);
              }
              break;
            case DESCRIPTION_STATISTICS_REQUEST_SENT:
              if (m.getType() == OFType.STATS_REPLY) {
                OFStatisticsReply sr = (OFStatisticsReply) m;
                if (sr.getStatisticType() == OFStatisticsType.DESC
                    && sr.getStatistics().size() > 0) {
                  OFDescriptionStatistics desc =
                      (OFDescriptionStatistics) sr.getStatistics().get(0);
                  sw.setDescriptionStatistics(desc);
                  log.debug("Description Statistics Reply from {}: {}", sw, desc);

                  // Set config and request to receive the config
                  OFSetConfig config = (OFSetConfig) factory.getMessage(OFType.SET_CONFIG);
                  config.setMissSendLength((short) 0xffff).setLengthU(OFSetConfig.MINIMUM_LENGTH);
                  sw.getOutputStream().write(config);
                  sw.getOutputStream().write(factory.getMessage(OFType.BARRIER_REQUEST));
                  sw.getOutputStream().write(factory.getMessage(OFType.GET_CONFIG_REQUEST));
                  sw.transitionToState(OFSwitchState.GET_CONFIG_REQUEST_SENT);
                }
              }
              break;
            case GET_CONFIG_REQUEST_SENT:
              if (m.getType() == OFType.GET_CONFIG_REPLY) {
                OFGetConfigReply cr = (OFGetConfigReply) m;
                if (cr.getMissSendLength() == (short) 0xffff) {
                  log.debug("Config Reply from {} confirms miss length set to 0xffff", sw);
                  sw.transitionToState(OFSwitchState.INITIALIZING);

                  CopyOnWriteArrayList<IOFInitializerListener> initializers =
                      (CopyOnWriteArrayList<IOFInitializerListener>) initializerList.clone();
                  // Add all existing initializers to the list
                  this.initializerMap.put(sw, initializers);
                  log.debug(
                      "Remaining initializers for switch {}: {}", sw, this.initializerMap.get(sw));

                  // Delete all pre-existing flows
                  if (deletePreExistingFlows) {
                    OFMatch match = new OFMatch().setWildcards(OFMatch.OFPFW_ALL);
                    OFMessage fm =
                        ((OFFlowMod)
                                sw.getInputStream().getMessageFactory().getMessage(OFType.FLOW_MOD))
                            .setMatch(match)
                            .setCommand(OFFlowMod.OFPFC_DELETE)
                            .setOutPort(OFPort.OFPP_NONE)
                            .setLength(U16.t(OFFlowMod.MINIMUM_LENGTH));
                    sw.getOutputStream().write(fm);
                    sw.getOutputStream().write(factory.getMessage(OFType.BARRIER_REQUEST));
                  }

                  if (initializers.size() > 0) queueInitializer(sw, initializers.iterator().next());
                  else advanceInitializers(sw);
                } else {
                  log.error(
                      "Switch {} refused to set miss send length to 0xffff, disconnecting", sw);
                  disconnectSwitch(((OFStream) sw.getInputStream()).getKey(), sw);
                  return;
                }
              }
              break;
            case INITIALIZING:
              CopyOnWriteArrayList<IOFInitializerListener> initializers = initializerMap.get(sw);
              Iterator<IOFInitializerListener> it = initializers.iterator();
              if (it.hasNext()) {
                IOFInitializerListener listener = it.next();
                try {
                  listener.initializerReceive(sw, m);
                } catch (Exception e) {
                  log.error(
                      "Error calling initializer listener: {} on switch: {} for message: {}, removing listener",
                      new Object[] {listener, sw, m});
                  advanceInitializers(sw);
                }
              }
              break;
            case ACTIVE:
              List<IOFMessageListener> listeners = messageListeners.get(m.getType());
              if (listeners != null) {
                for (IOFMessageListener listener : listeners) {
                  try {
                    if (listener instanceof IOFSwitchFilter) {
                      if (!((IOFSwitchFilter) listener).isInterested(sw)) {
                        continue;
                      }
                    }
                    if (Command.STOP.equals(listener.receive(sw, m))) {
                      break;
                    }
                  } catch (Exception e) {
                    log.error(
                        "Failure calling listener ["
                            + listener.toString()
                            + "] with message ["
                            + m.toString()
                            + "]",
                        e);
                  }
                }
              } else {
                log.debug("Unhandled OF Message: {} from {}", m, sw);
              }
              break;
          } // end switch(sw.getState())
      } // end switch(m.getType())
    }
  }