예제 #1
0
파일: Gossiper.java 프로젝트: Jashinta/570
  /** Start the gossiper with the generation # retrieved from the System table */
  public void start(InetAddress localEndpoint, int generationNbr) {
    localEndpoint_ = localEndpoint;
    /* Get the seeds from the config and initialize them. */
    Set<InetAddress> seedHosts = DatabaseDescriptor.getSeeds();
    for (InetAddress seed : seedHosts) {
      if (seed.equals(localEndpoint)) continue;
      seeds_.add(seed);
    }

    /* initialize the heartbeat state for this localEndpoint */
    EndpointState localState = endpointStateMap_.get(localEndpoint_);
    if (localState == null) {
      HeartBeatState hbState = new HeartBeatState(generationNbr);
      localState = new EndpointState(hbState);
      localState.isAlive(true);
      localState.isAGossiper(true);
      endpointStateMap_.put(localEndpoint_, localState);
    }

    // notify snitches that Gossiper is about to start
    DatabaseDescriptor.getEndpointSnitch().gossiperStarting();

    scheduledGossipTask =
        StorageService.scheduledTasks.scheduleWithFixedDelay(
            new GossipTask(),
            Gossiper.intervalInMillis_,
            Gossiper.intervalInMillis_,
            TimeUnit.MILLISECONDS);
  }
 public void validate(String name) {
   // Attempt to instantiate the ARS, which will throw a ConfigurationException if the options
   // aren't valid.
   TokenMetadata tmd = StorageService.instance.getTokenMetadata();
   IEndpointSnitch eps = DatabaseDescriptor.getEndpointSnitch();
   AbstractReplicationStrategy.validateReplicationStrategy(name, klass, tmd, eps, options);
 }
예제 #3
0
  private List<String> getKeyLocations(ByteBuffer key) {
    List<InetAddress> endpoints = StorageService.instance.getLiveNaturalEndpoints(cfsKeyspace, key);
    DatabaseDescriptor.getEndpointSnitch()
        .sortByProximity(FBUtilities.getLocalAddress(), endpoints);

    List<String> hosts = new ArrayList<String>(endpoints.size());

    for (InetAddress endpoint : endpoints) {
      hosts.add(endpoint.getHostName());
    }

    return hosts;
  }
예제 #4
0
    /** Stores current DC/rack assignment for ep */
    protected void addEndpoint(InetAddress ep) {
      IEndpointSnitch snitch = DatabaseDescriptor.getEndpointSnitch();
      String dc = snitch.getDatacenter(ep);
      String rack = snitch.getRack(ep);
      Pair<String, String> current = currentLocations.get(ep);
      if (current != null) {
        if (current.left.equals(dc) && current.right.equals(rack)) return;
        dcRacks.get(current.left).remove(current.right, ep);
        dcEndpoints.remove(current.left, ep);
      }

      dcEndpoints.put(dc, ep);

      if (!dcRacks.containsKey(dc)) dcRacks.put(dc, HashMultimap.<String, InetAddress>create());
      dcRacks.get(dc).put(rack, ep);

      currentLocations.put(ep, Pair.create(dc, rack));
    }
  public void validate(ClientState state) throws RequestValidationException {
    KSMetaData ksm = Schema.instance.getKSMetaData(name);
    if (ksm == null) throw new InvalidRequestException("Unknown keyspace " + name);
    if (ksm.name.equalsIgnoreCase(Keyspace.SYSTEM_KS))
      throw new InvalidRequestException("Cannot alter system keyspace");

    attrs.validate();

    if (attrs.getReplicationStrategyClass() == null && !attrs.getReplicationOptions().isEmpty()) {
      throw new ConfigurationException("Missing replication strategy class");
    } else if (attrs.getReplicationStrategyClass() != null) {
      // The strategy is validated through KSMetaData.validate() in announceKeyspaceUpdate below.
      // However, for backward compatibility with thrift, this doesn't validate unexpected options
      // yet,
      // so doing proper validation here.
      AbstractReplicationStrategy.validateReplicationStrategy(
          name,
          AbstractReplicationStrategy.getClass(attrs.getReplicationStrategyClass()),
          StorageService.instance.getTokenMetadata(),
          DatabaseDescriptor.getEndpointSnitch(),
          attrs.getReplicationOptions());
    }
  }
public class OutboundTcpConnectionPool {
  private final IEndpointSnitch snitch = DatabaseDescriptor.getEndpointSnitch();
  // pointer for the real Address.
  private final InetAddress id;
  public final OutboundTcpConnection cmdCon;
  public final OutboundTcpConnection ackCon;
  // pointer to the reseted Address.
  private InetAddress resetedEndpoint;
  private ConnectionMetrics metrics;

  OutboundTcpConnectionPool(InetAddress remoteEp) {
    id = remoteEp;
    cmdCon = new OutboundTcpConnection(this);
    cmdCon.start();
    ackCon = new OutboundTcpConnection(this);
    ackCon.start();

    metrics = new ConnectionMetrics(id, this);
  }

  /**
   * returns the appropriate connection based on message type. returns null if a connection could
   * not be established.
   */
  OutboundTcpConnection getConnection(MessageOut msg) {
    Stage stage = msg.getStage();
    return stage == Stage.REQUEST_RESPONSE
            || stage == Stage.INTERNAL_RESPONSE
            || stage == Stage.GOSSIP
        ? ackCon
        : cmdCon;
  }

  void reset() {
    for (OutboundTcpConnection conn : new OutboundTcpConnection[] {cmdCon, ackCon})
      conn.closeSocket(false);
  }

  public void resetToNewerVersion(int version) {
    for (OutboundTcpConnection conn : new OutboundTcpConnection[] {cmdCon, ackCon}) {
      if (version > conn.getTargetVersion()) conn.softCloseSocket();
    }
  }

  /**
   * reconnect to @param remoteEP (after the current message backlog is exhausted). Used by
   * Ec2MultiRegionSnitch to force nodes in the same region to communicate over their private IPs.
   *
   * @param remoteEP
   */
  public void reset(InetAddress remoteEP) {
    resetedEndpoint = remoteEP;
    for (OutboundTcpConnection conn : new OutboundTcpConnection[] {cmdCon, ackCon})
      conn.softCloseSocket();

    // release previous metrics and create new one with reset address
    metrics.release();
    metrics = new ConnectionMetrics(resetedEndpoint, this);
  }

  public long getTimeouts() {
    return metrics.timeouts.count();
  }

  public long getRecentTimeouts() {
    return metrics.getRecentTimeout();
  }

  public void incrementTimeout() {
    metrics.timeouts.mark();
  }

  public Socket newSocket() throws IOException {
    // zero means 'bind on any available port.'
    if (isEncryptedChannel()) {
      if (Config.getOutboundBindAny())
        return SSLFactory.getSocket(
            DatabaseDescriptor.getServerEncryptionOptions(),
            endPoint(),
            DatabaseDescriptor.getSSLStoragePort());
      else
        return SSLFactory.getSocket(
            DatabaseDescriptor.getServerEncryptionOptions(),
            endPoint(),
            DatabaseDescriptor.getSSLStoragePort(),
            FBUtilities.getLocalAddress(),
            0);
    } else {
      Socket socket =
          SocketChannel.open(new InetSocketAddress(endPoint(), DatabaseDescriptor.getStoragePort()))
              .socket();
      if (Config.getOutboundBindAny() && !socket.isBound())
        socket.bind(new InetSocketAddress(FBUtilities.getLocalAddress(), 0));
      return socket;
    }
  }

  InetAddress endPoint() {
    return resetedEndpoint == null ? id : resetedEndpoint;
  }

  boolean isEncryptedChannel() {
    switch (DatabaseDescriptor.getServerEncryptionOptions().internode_encryption) {
      case none:
        return false; // if nothing needs to be encrypted then return immediately.
      case all:
        break;
      case dc:
        if (snitch
            .getDatacenter(id)
            .equals(snitch.getDatacenter(FBUtilities.getBroadcastAddress()))) return false;
        break;
      case rack:
        // for rack then check if the DC's are the same.
        if (snitch.getRack(id).equals(snitch.getRack(FBUtilities.getBroadcastAddress()))
            && snitch
                .getDatacenter(id)
                .equals(snitch.getDatacenter(FBUtilities.getBroadcastAddress()))) return false;
        break;
    }
    return true;
  }

  public void close() {
    // these null guards are simply for tests
    if (ackCon != null) ackCon.closeSocket(true);
    if (cmdCon != null) cmdCon.closeSocket(true);
    metrics.release();
  }
}
예제 #7
0
public class OutboundTcpConnectionPool {
  private IEndpointSnitch snitch = DatabaseDescriptor.getEndpointSnitch();
  // pointer for the real Address.
  private final InetAddress id;
  public final OutboundTcpConnection cmdCon;
  public final OutboundTcpConnection ackCon;
  // pointer to the reseted Address.
  private InetAddress resetedEndpoint;

  OutboundTcpConnectionPool(InetAddress remoteEp) {
    id = remoteEp;
    cmdCon = new OutboundTcpConnection(this);
    cmdCon.start();
    ackCon = new OutboundTcpConnection(this);
    ackCon.start();
  }

  /**
   * returns the appropriate connection based on message type. returns null if a connection could
   * not be established.
   */
  OutboundTcpConnection getConnection(Message msg) {
    Stage stage = msg.getMessageType();
    return stage == Stage.REQUEST_RESPONSE
            || stage == Stage.INTERNAL_RESPONSE
            || stage == Stage.GOSSIP
        ? ackCon
        : cmdCon;
  }

  synchronized void reset() {
    for (OutboundTcpConnection con : new OutboundTcpConnection[] {cmdCon, ackCon})
      con.closeSocket();
  }

  /**
   * reconnect to @param remoteEP (after the current message backlog is exhausted). Used by
   * Ec2MultiRegionSnitch to force nodes in the same region to communicate over their private IPs.
   *
   * @param remoteEP
   */
  public void reset(InetAddress remoteEP) {
    resetedEndpoint = remoteEP;
    for (OutboundTcpConnection con : new OutboundTcpConnection[] {cmdCon, ackCon})
      con.softCloseSocket();
  }

  public Socket newSocket() throws IOException {
    // zero means 'bind on any available port.'
    if (isEncryptedChannel()) {
      if (Config.getOutboundBindAny())
        return SSLFactory.getSocket(
            DatabaseDescriptor.getEncryptionOptions(),
            endPoint(),
            DatabaseDescriptor.getSSLStoragePort());
      else
        return SSLFactory.getSocket(
            DatabaseDescriptor.getEncryptionOptions(),
            endPoint(),
            DatabaseDescriptor.getSSLStoragePort(),
            FBUtilities.getLocalAddress(),
            0);
    } else {
      if (Config.getOutboundBindAny())
        return new Socket(endPoint(), DatabaseDescriptor.getStoragePort());
      else
        return new Socket(
            endPoint(), DatabaseDescriptor.getStoragePort(), FBUtilities.getLocalAddress(), 0);
    }
  }

  InetAddress endPoint() {
    return resetedEndpoint == null ? id : resetedEndpoint;
  }

  boolean isEncryptedChannel() {
    switch (DatabaseDescriptor.getEncryptionOptions().internode_encryption) {
      case none:
        return false; // if nothing needs to be encrypted then return immediately.
      case all:
        break;
      case dc:
        if (snitch
            .getDatacenter(id)
            .equals(snitch.getDatacenter(FBUtilities.getBroadcastAddress()))) return false;
        break;
      case rack:
        // for rack then check if the DC's are the same.
        if (snitch.getRack(id).equals(snitch.getRack(FBUtilities.getBroadcastAddress()))
            && snitch
                .getDatacenter(id)
                .equals(snitch.getDatacenter(FBUtilities.getBroadcastAddress()))) return false;
        break;
    }
    return true;
  }
}