gboolean ssi_auth_action(HybridSslConnection *isc, gpointer user_data) { gchar *password; gchar no_url[URL_LENGTH]; gchar verify_url[URL_LENGTH]; gchar ssl_buf[BUF_LENGTH]; gint pass_type; fetion_account *ac = (fetion_account*)user_data; hybrid_account_set_connection_string(ac->account, _("Start SSI authentication...")); hybrid_debug_info("fetion", "ssi authencating"); password = hash_password_v4(ac->userid, ac->password); if (ac->mobileno) { g_snprintf(no_url, sizeof(no_url) - 1, "mobileno=%s", ac->mobileno); } else { g_snprintf(no_url, sizeof(no_url) - 1, "sid=%s", ac->sid); } *verify_url = '\0'; /** * if the verification is not NULL ,it means we need to add the * confirm code in the request url. */ if (ac->verification != NULL && ac->verification->code != NULL) { g_snprintf(verify_url, sizeof(verify_url) - 1, "&pid=%s&pic=%s&algorithm=%s", ac->verification->guid, ac->verification->code, ac->verification->algorithm); } fetion_verification_destroy(ac->verification); ac->verification = NULL; pass_type = (ac->userid == NULL || *(ac->userid) == '\0' ? 1 : 2); g_snprintf(ssl_buf, sizeof(ssl_buf) - 1, "GET /ssiportal/SSIAppSignInV4.aspx?%s" "&domains=fetion.com.cn%s&v4digest-type=%d&v4digest=%s\r\n" "User-Agent: IIC2.0/pc "PROTO_VERSION"\r\n" "Host: %s\r\n" "Cache-Control: private\r\n" "Connection: Keep-Alive\r\n\r\n", no_url, verify_url, pass_type, password, SSI_SERVER); g_free(password); hybrid_debug_info("fetion", "send:\n%s", ssl_buf); /* write the request to ssl connection, and a callback function * to handle the read event. */ hybrid_ssl_write(isc, ssl_buf, strlen(ssl_buf)); hybrid_ssl_event_add(isc, ssi_auth_cb, ac); return FALSE; }
gboolean Ssi_cb(gpointer sodata, PurpleSslConnection * gsc, gint con) { gchar *head; struct fetion_account_data *sip; // Modified from codes of open-fetion char noUri[128]; char verifyUri[256]; char *password; int passwordType; sip = sodata; purple_debug_info("Fetion:", "Ssi_cb\n"); /*purple_debug_info("Fetion:", "Initialize ssi authentication action\n");*/ password = hash_password_v4(NULL , sip->password); /*password = hash_password_v4(sip->userId , sip->password);*/ memset(noUri, 0, sizeof(noUri)); if(sip->mobileno != NULL) sprintf(noUri , "mobileno=%s" , sip->mobileno); else sprintf(noUri , "sid=%s" , sip->username); memset(verifyUri, 0, sizeof(verifyUri)); /*if(user->verification != NULL && user->verification->code != NULL)*/ /*{*/ /*sprintf(verifyUri , "&pid=%s&pic=%s&algorithm=%s"*/ /*, user->verification->guid*/ /*, user->verification->code*/ /*, user->verification->algorithm);*/ /*}*/ /*passwordType = (strlen(sip->userId) == 0 ? 1 : 2);*/ passwordType = 1; head = g_strdup_printf( "GET /ssiportal/SSIAppSignInV4.aspx?%s" "&domains=fetion.com.cn%s&v4digest-type=%d&v4digest=%s\r\n" "User-Agent: IIC2.0/pc "PROTO_VERSION"\r\n" "Host: %s\r\n" "Cache-Control: private\r\n" "Connection: Keep-Alive\r\n\r\n", noUri , verifyUri , passwordType , password , "uid.fetion.com.cn"); /*if (sip->mobileno != NULL) {*/ /*head =*/ /*g_strdup_printf*/ /*("GET /ssiportal/SSIAppSignIn.aspx?mobileno=%s&pwd=%s HTTP/1.1\r\n"*/ /*"User-Agent: IIC2.0/pc 3.3.0370\r\n" "Host: %s\r\n"*/ /*"Connection: Keep-Alive\r\n\r\n", sip->mobileno,*/ /*sip->password, sip->SsicServer);*/ /*} else {*/ /*head =*/ /*g_strdup_printf*/ /*("GET /ssiportal/SSIAppSignIn.aspx?sid=%s&pwd=%s HTTP/1.1\r\n"*/ /*"User-Agent: IIC2.0/pc 3.3.0370\r\n" "Host: %s\r\n"*/ /*"Connection: Keep-Alive\r\n\r\n", sip->username,*/ /*sip->password, sip->SsicServer);*/ /*}*/ purple_ssl_write(gsc, head, strlen(head)); purple_ssl_input_add(gsc, (PurpleSslInputFunction) read_cookie, sip); return TRUE; }
static gchar* generate_response(const gchar *nouce, const gchar *userid, const gchar *password, const gchar *publickey, const gchar *aeskey_raw) { gchar *psdhex = hash_password_v4(userid, password); gchar modulus[257]; gchar exponent[7]; gint ret, flen; BIGNUM *bnn, *bne; guchar *out; guchar *nonce, *aeskey, *psd, *res; gint nonce_len, aeskey_len, psd_len; RSA *r = RSA_new(); memset(modulus, 0, sizeof(modulus)); memset(exponent, 0, sizeof(exponent)); memcpy(modulus, publickey, 256); memcpy(exponent, publickey + 256, 6); nonce = (guchar*)g_malloc0(strlen(nouce) + 1); memcpy(nonce, (guchar*)nouce, strlen(nouce)); nonce_len = strlen(nouce); psd = strtohex(psdhex, &psd_len); aeskey = strtohex(aeskey_raw, &aeskey_len); res = (guchar*)g_malloc0(nonce_len + aeskey_len + psd_len + 1); memcpy(res, nonce, nonce_len); memcpy(res + nonce_len, psd, psd_len); memcpy(res + nonce_len + psd_len, aeskey, aeskey_len); bnn = BN_new(); bne = BN_new(); BN_hex2bn(&bnn, modulus); BN_hex2bn(&bne, exponent); r->n = bnn; r->e = bne; r->d = NULL; RSA_print_fp(stdout, r, 5); flen = RSA_size(r); out = (guchar*)g_malloc0(flen); hybrid_debug_info("fetion", "start encrypting response"); ret = RSA_public_encrypt(nonce_len + aeskey_len + psd_len, res, out, r, RSA_PKCS1_PADDING); if (ret < 0) { hybrid_debug_info("fetion", "encrypt response failed!"); g_free(res); g_free(aeskey); g_free(psd); g_free(nonce); return NULL; } RSA_free(r); hybrid_debug_info("fetion", "encrypting reponse success"); g_free(res); g_free(aeskey); g_free(psd); g_free(nonce); return hextostr(out , ret); }