bool authpgsql_connection::getuserinfo(authpgsql_userinfo &uiret, const char *username, const char *service) { std::string querybuf; if (!do_connect()) return false; if (config_file.select_clause.empty()) { std::ostringstream o; o << "SELECT " << config_file.login_field << ", " << config_file.crypt_field << ", " << config_file.clear_field << ", " << config_file.uid_field << ", " << config_file.gid_field << ", " << config_file.home_field << ", " << (strcmp(service, "courier") == 0 ? config_file.defaultdelivery_field :config_file.maildir_field) << ", " << config_file.quota_field << ", " << config_file.name_field << ", " << config_file.options_field << " FROM " << config_file.user_table << " WHERE " << config_file.login_field << " = '" << escape_username(username) << "' AND (" << config_file.where_clause << ")"; querybuf=o.str(); } else { std::map<std::string, std::string> parameters; parameters["service"]=service; querybuf=config_file .parse_custom_query(config_file.select_clause, escape(username), config_file.defdomain, parameters); } DPRINTF("SQL query: %s", querybuf.c_str()); result res1(*this, querybuf); if (res1) return getuserinfo(uiret, res1); disconnect(); if (do_connect()) { result res2(*this, querybuf); if (res2) return getuserinfo(uiret, res2); } return false; }
static JabberSaslState scram_start(JabberStream *js, PurpleXmlNode *mechanisms, PurpleXmlNode **out, char **error) { PurpleXmlNode *reply; JabberScramData *data; guint64 cnonce; #ifdef CHANNEL_BINDING gboolean binding_supported = TRUE; #endif gchar *dec_out, *enc_out; gchar *prepped_node, *tmp; gchar *prepped_pass; prepped_node = jabber_saslprep(js->user->node); if (!prepped_node) { *error = g_strdup(_("Unable to canonicalize username")); return JABBER_SASL_STATE_FAIL; } tmp = escape_username(prepped_node); g_free(prepped_node); prepped_node = tmp; prepped_pass = jabber_saslprep(purple_connection_get_password(js->gc)); if (!prepped_pass) { g_free(prepped_node); *error = g_strdup(_("Unable to canonicalize password")); return JABBER_SASL_STATE_FAIL; } data = js->auth_mech_data = g_new0(JabberScramData, 1); data->hash = mech_to_hash(js->auth_mech->name); data->password = prepped_pass; #ifdef CHANNEL_BINDING if (strstr(js->auth_mech_name, "-PLUS")) data->channel_binding = TRUE; #endif cnonce = ((guint64)g_random_int() << 32) | g_random_int(); data->cnonce = purple_base64_encode((guchar *)&cnonce, sizeof(cnonce)); data->auth_message = g_string_new(NULL); g_string_printf(data->auth_message, "n=%s,r=%s", prepped_node, data->cnonce); g_free(prepped_node); data->step = 1; reply = purple_xmlnode_new("auth"); purple_xmlnode_set_namespace(reply, NS_XMPP_SASL); purple_xmlnode_set_attrib(reply, "mechanism", js->auth_mech->name); /* TODO: Channel binding */ dec_out = g_strdup_printf("%c,,%s", 'n', data->auth_message->str); enc_out = purple_base64_encode((guchar *)dec_out, strlen(dec_out)); purple_debug_misc("jabber", "initial SCRAM message '%s'\n", dec_out); purple_xmlnode_insert_data(reply, enc_out, -1); g_free(enc_out); g_free(dec_out); *out = reply; return JABBER_SASL_STATE_CONTINUE; }