void ConnectionHandler::start(const FieldTable& /*serverProps*/, const Array& mechanisms, const Array& /*locales*/)
{
    checkState(NOT_STARTED, INVALID_STATE_START);
    setState(NEGOTIATING);
    sasl = SaslFactory::getInstance().create( username,
                                              password,
                                              service,
                                              host,
                                              minSsf,
                                              maxSsf
                                            );

    std::vector<std::string> mechlist;
    mechlist.reserve(mechanisms.size());
    if (mechanism.empty()) {
        //mechlist is simply what the server offers
        std::transform(mechanisms.begin(), mechanisms.end(), std::back_inserter(mechlist), Array::get<std::string, Array::ValuePtr>);
    } else {
        //mechlist is the intersection of those indicated by user and
        //those supported by server, in the order listed by user
        std::vector<std::string> allowed = split(mechanism, " ");
        std::vector<std::string> supported(mechanisms.size());
        std::transform(mechanisms.begin(), mechanisms.end(), std::back_inserter(supported), Array::get<std::string, Array::ValuePtr>);
        intersection(allowed, supported, mechlist);
        if (mechlist.empty()) {
            throw Exception(QPID_MSG("Desired mechanism(s) not valid: " << mechanism << " (supported: " << join(supported) << ")"));
        }
    }

    if (sasl.get()) {
        std::string response;
        if (sasl->start(join(mechlist), response, getSecuritySettings ? getSecuritySettings() : 0)) {
            proxy.startOk(properties, sasl->getMechanism(), response, locale);
        } else {
            //response was null
            ConnectionStartOkBody body;
            body.setClientProperties(properties);
            body.setMechanism(sasl->getMechanism());
            //Don't set response, as none was given
            body.setLocale(locale);
            proxy.send(body);
        }
    } else {
        //TODO: verify that desired mechanism and locale are supported
        std::string response = ((char)0) + username + ((char)0) + password;
        proxy.startOk(properties, mechanism, response, locale);
    }
}
Beispiel #2
0
void ConnectionHandler::Handler::start(const FieldTable& serverProperties,
                                       const framing::Array& supportedMechanisms,
                                       const framing::Array& /*locales*/)
{
    string requestedMechanism = connection.getAuthMechanism();

    std::string username = connection.getUsername();

    std::string password = connection.getPassword();
    std::string host     = connection.getHost();
    std::string service("qpidd");

    if ( connection.getBroker().isAuthenticating() ) {
        sasl = SaslFactory::getInstance().create( username,
                                                  password,
                                                  service,
                                                  host,
                                                  0,   // TODO -- mgoulish Fri Sep 24 2010
                                                  256,
                                                  false ); // disallow interaction
    }
    std::string supportedMechanismsList;
    Array::const_iterator i;

    /*
      If no specific mechanism has been requested, just make
      a list of all of them, and assert that the one the caller
      requested is there.  ( If *any* are supported! )
    */
    if ( requestedMechanism.empty() ) {
        for ( i = supportedMechanisms.begin(); i != supportedMechanisms.end(); ++i) {
            if (i != supportedMechanisms.begin())
                supportedMechanismsList += SPACE;
            supportedMechanismsList += (*i)->get<std::string>();
        }
    }
    else {
        /*
          The caller has requested a mechanism.  If it's available,
          make sure it ends up at the head of the list.
        */
        for ( i = supportedMechanisms.begin(); i != supportedMechanisms.end(); ++i) {
            string currentMechanism = (*i)->get<std::string>();

            if ( requestedMechanism == currentMechanism ) {
                supportedMechanismsList = currentMechanism + SPACE + supportedMechanismsList;
            } else {
                if (i != supportedMechanisms.begin())
                    supportedMechanismsList += SPACE;
                supportedMechanismsList += currentMechanism;
            }
        }
    }

    if (serverProperties.isSet(QPID_FED_TAG)) {
        connection.setFederationPeerTag(serverProperties.getAsString(QPID_FED_TAG));
    }

    FieldTable ft = connection.getBroker().getLinkClientProperties();
    ft.setInt(QPID_FED_LINK,1);
    ft.setString(QPID_FED_TAG, connection.getBroker().getFederationTag());

    string response;
    if (sasl.get()) {
        const qpid::sys::SecuritySettings& ss = connection.getExternalSecuritySettings();
        if (sasl->start ( requestedMechanism.empty()
                          ? supportedMechanismsList
                          : requestedMechanism,
                          response,
                          & ss )) {
            proxy.startOk ( ft, sasl->getMechanism(), response, en_US );
        } else {
            //response was null
            ConnectionStartOkBody body;
            body.setClientProperties(ft);
            body.setMechanism(sasl->getMechanism());
            //Don't set response, as none was given
            body.setLocale(en_US);
            proxy.send(body);
        }
    }
    else {
        response = ((char)0) + username + ((char)0) + password;
        proxy.startOk ( ft, requestedMechanism, response, en_US );
    }

}