Develop and Download Open Source Software

Browse Subversion Repository

Diff of /branches/ssh_chacha20poly1305/ttssh2/ttxssh/ssh.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 2759 by yutakakn, Fri Dec 17 16:52:36 2004 UTC revision 2762 by yutakakn, Wed Dec 22 17:28:14 2004 UTC
# Line 33  SOFTWARE, EVEN IF ADVISED OF THE POSSIBI Line 33  SOFTWARE, EVEN IF ADVISED OF THE POSSIBI
33  #include <openssl/evp.h>  #include <openssl/evp.h>
34  #include <openssl/dh.h>  #include <openssl/dh.h>
35  #include <openssl/engine.h>  #include <openssl/engine.h>
36    #include <openssl/rsa.h>
37    #include <openssl/dsa.h>
38  #include <limits.h>  #include <limits.h>
39  #include <malloc.h>  #include <malloc.h>
40  #include <string.h>  #include <string.h>
# Line 46  SOFTWARE, EVEN IF ADVISED OF THE POSSIBI Line 48  SOFTWARE, EVEN IF ADVISED OF THE POSSIBI
48  #define SSH2_DEBUG  #define SSH2_DEBUG
49  #endif  #endif
50    
51    #define INTBLOB_LEN 20
52    #define SIGBLOB_LEN (2*INTBLOB_LEN)
53    
54  static char ssh_ttymodes[] = "\x01\x03\x02\x1c\x03\x08\x04\x15\x05\x04";  static char ssh_ttymodes[] = "\x01\x03\x02\x1c\x03\x08\x04\x15\x05\x04";
55    
56  static void try_send_credentials(PTInstVar pvar);  static void try_send_credentials(PTInstVar pvar);
# Line 3296  static int ssh_dss_verify( Line 3301  static int ssh_dss_verify(
3301                          DSA *key, u_char *signature, u_int signaturelen,                          DSA *key, u_char *signature, u_int signaturelen,
3302                          u_char *data, u_int datalen)                          u_char *data, u_int datalen)
3303  {  {
 #define INTBLOB_LEN 20  
3304          DSA_SIG *sig;          DSA_SIG *sig;
3305          const EVP_MD *evp_md = EVP_sha1();          const EVP_MD *evp_md = EVP_sha1();
3306          EVP_MD_CTX md;          EVP_MD_CTX md;
# Line 3327  static int ssh_dss_verify( Line 3331  static int ssh_dss_verify(
3331          sigblob = ptr;          sigblob = ptr;
3332          ptr += len;          ptr += len;
3333    
3334          if (len != (2*INTBLOB_LEN)) {          if (len != SIGBLOB_LEN) {
3335                  return -1;                  return -1;
3336          }          }
3337    
# Line 4125  BOOL do_SSH2_userauth(PTInstVar pvar) Line 4129  BOOL do_SSH2_userauth(PTInstVar pvar)
4129          char *s;          char *s;
4130          unsigned char *outmsg;          unsigned char *outmsg;
4131          int len;          int len;
   
 #if 1  
         // TODO: MACの決定  
         {  
4132          int mode;          int mode;
4133    
4134          for (mode = 0 ; mode < MODE_MAX ; mode++) {          for (mode = 0 ; mode < MODE_MAX ; mode++) {
4135                  pvar->ssh2_keys[mode].mac.enabled = 1;                  pvar->ssh2_keys[mode].mac.enabled = 1;
4136          }          }
         }  
 #endif  
4137    
4138          // start user authentication          // start user authentication
4139          msg = buffer_init();          msg = buffer_init();
# Line 4158  BOOL do_SSH2_userauth(PTInstVar pvar) Line 4156  BOOL do_SSH2_userauth(PTInstVar pvar)
4156          return TRUE;          return TRUE;
4157  }  }
4158    
4159    
4160    static char *get_SSH2_keyname(CRYPTKeyPair *keypair)
4161    {
4162            char *s;
4163    
4164            if (keypair->RSA_key != NULL) {
4165                    s = "ssh-rsa";
4166            } else {
4167                    s = "ssh-dss";
4168            }
4169    
4170            return (s);
4171    }
4172    
4173    
4174    static BOOL generate_SSH2_keysign(CRYPTKeyPair *keypair, char **sigptr, int *siglen, char *data, int datalen)
4175    {
4176            buffer_t *msg = NULL;
4177            char *s;
4178    
4179            msg = buffer_init();
4180            if (msg == NULL) {
4181                    // TODO: error check
4182                    return FALSE;
4183            }
4184    
4185            if (keypair->RSA_key != NULL) { // RSA
4186                    const EVP_MD *evp_md;
4187                    EVP_MD_CTX md;
4188                    u_char digest[EVP_MAX_MD_SIZE], *sig;
4189                    u_int slen, dlen, len;
4190                    int ok, nid;
4191    
4192                    nid = NID_sha1;
4193                    if ((evp_md = EVP_get_digestbynid(nid)) == NULL) {
4194                            goto error;
4195                    }
4196    
4197                    // ダイジェスト値の計算
4198                    EVP_DigestInit(&md, evp_md);
4199                    EVP_DigestUpdate(&md, data, datalen);
4200                    EVP_DigestFinal(&md, digest, &dlen);
4201    
4202                    slen = RSA_size(keypair->RSA_key);
4203                    sig = malloc(slen);
4204                    if (sig == NULL)
4205                            goto error;
4206    
4207                    // 電子署名を計算
4208                    ok = RSA_sign(nid, digest, dlen, sig, &len, keypair->RSA_key);
4209                    memset(digest, 'd', sizeof(digest));
4210                    if (ok != 1) { // error
4211                            free(sig);
4212                            goto error;
4213                    }
4214                    // 署名のサイズがバッファより小さい場合、後ろへずらす。先頭はゼロで埋める。
4215                    if (len < slen) {
4216                            u_int diff = slen - len;
4217                            memmove(sig + diff, sig, len);
4218                            memset(sig, 0, diff);
4219    
4220                    } else if (len > slen) {
4221                            free(sig);
4222                            goto error;
4223    
4224                    } else {
4225                            // do nothing
4226    
4227                    }
4228    
4229                    s = get_SSH2_keyname(keypair);
4230                    buffer_put_string(msg, s, strlen(s));
4231                    buffer_append_length(msg, sig, slen);
4232                    len = buffer_len(msg);
4233    
4234                    // setting
4235                    *siglen = len;
4236                    *sigptr = malloc(len);
4237                    if (*sigptr == NULL) {
4238                            free(sig);
4239                            goto error;
4240                    }
4241                    memcpy(*sigptr, buffer_ptr(msg), len);
4242                    free(sig);
4243    
4244            } else { // DSA
4245                    DSA_SIG *sig;
4246                    const EVP_MD *evp_md = EVP_sha1();
4247                    EVP_MD_CTX md;
4248                    u_char digest[EVP_MAX_MD_SIZE], sigblob[SIGBLOB_LEN];
4249                    u_int rlen, slen, len, dlen;
4250    
4251                    // ダイジェストの計算
4252                    EVP_DigestInit(&md, evp_md);
4253                    EVP_DigestUpdate(&md, data, datalen);
4254                    EVP_DigestFinal(&md, digest, &dlen);
4255    
4256                    // DSA電子署名を計算
4257                    sig = DSA_do_sign(digest, dlen, keypair->DSA_key);
4258                    memset(digest, 'd', sizeof(digest));
4259                    if (sig == NULL) {
4260                            goto error;
4261                    }
4262    
4263                    // BIGNUMからバイナリ値への変換
4264                    rlen = BN_num_bytes(sig->r);
4265                    slen = BN_num_bytes(sig->s);
4266                    if (rlen > INTBLOB_LEN || slen > INTBLOB_LEN) {
4267                            DSA_SIG_free(sig);
4268                            goto error;
4269                    }
4270                    memset(sigblob, 0, SIGBLOB_LEN);
4271                    BN_bn2bin(sig->r, sigblob+ SIGBLOB_LEN - INTBLOB_LEN - rlen);
4272                    BN_bn2bin(sig->s, sigblob+ SIGBLOB_LEN - slen);
4273                    DSA_SIG_free(sig);
4274    
4275                    // setting
4276                    s = get_SSH2_keyname(keypair);
4277                    buffer_put_string(msg, s, strlen(s));
4278                    buffer_append_length(msg, sigblob, sizeof(sigblob));
4279                    len = buffer_len(msg);
4280    
4281                    // setting
4282                    *siglen = len;
4283                    *sigptr = malloc(len);
4284                    if (*sigptr == NULL) {
4285                            goto error;
4286                    }
4287                    memcpy(*sigptr, buffer_ptr(msg), len);
4288    
4289            }
4290    
4291            buffer_free(msg);
4292            return TRUE;
4293    
4294    error:
4295            buffer_free(msg);
4296    
4297            return FALSE;
4298    }
4299    
4300    
4301    static BOOL get_SSH2_publickey_blob(PTInstVar pvar, buffer_t **blobptr, int *bloblen)
4302    {
4303            buffer_t *msg = NULL;
4304            CRYPTKeyPair *keypair;
4305            char *s;
4306    
4307            msg = buffer_init();
4308            if (msg == NULL) {
4309                    // TODO: error check
4310                    return FALSE;
4311            }
4312    
4313            keypair = pvar->auth_state.cur_cred.key_pair;
4314    
4315            if (keypair->RSA_key != NULL) { // RSA
4316                    s = get_SSH2_keyname(keypair);
4317                    buffer_put_string(msg, s, strlen(s));
4318                    buffer_put_bignum2(msg, keypair->RSA_key->e); // 公開指数
4319                    buffer_put_bignum2(msg, keypair->RSA_key->n); // p×q
4320    
4321            } else { // DSA
4322                    s = get_SSH2_keyname(keypair);
4323                    buffer_put_string(msg, s, strlen(s));
4324                    buffer_put_bignum2(msg, keypair->DSA_key->p); // 素数
4325                    buffer_put_bignum2(msg, keypair->DSA_key->q); // (p-1)の素因数
4326                    buffer_put_bignum2(msg, keypair->DSA_key->g); // 整数
4327                    buffer_put_bignum2(msg, keypair->DSA_key->pub_key); // 公開鍵
4328    
4329            }
4330    
4331            *blobptr = msg;
4332            *bloblen = buffer_len(msg);
4333    
4334            return TRUE;
4335    }
4336    
4337    
4338    // ユーザ認証パケットの構築
4339  static BOOL handle_SSH2_authrequest(PTInstVar pvar)  static BOOL handle_SSH2_authrequest(PTInstVar pvar)
4340  {  {
4341          buffer_t *msg;          buffer_t *msg = NULL;
4342          char *s;          char *s;
4343          unsigned char *outmsg;          unsigned char *outmsg;
4344          int len;          int len;
4345            char *connect_id = "ssh-connection";
4346    
4347          //              pvar->auth_state.cur_cred.password = password;          //              pvar->auth_state.cur_cred.password = password;
4348          //              pvar->auth_state.user =          //              pvar->auth_state.user =
# Line 4174  static BOOL handle_SSH2_authrequest(PTIn Line 4353  static BOOL handle_SSH2_authrequest(PTIn
4353          }          }
4354    
4355          // ペイロードの構築          // ペイロードの構築
         // TODO:  
4356          if (pvar->ssh2_autologin == 1) { // SSH2自動ログイン          if (pvar->ssh2_autologin == 1) { // SSH2自動ログイン
4357                  s = pvar->ssh2_username;                  s = pvar->ssh2_username;
4358          } else {          } else {
4359                  s = pvar->auth_state.user;  // ユーザ名                  s = pvar->auth_state.user;  // ユーザ名
4360          }          }
   
4361          buffer_put_string(msg, s, strlen(s));          buffer_put_string(msg, s, strlen(s));
         s = "ssh-connection";  
         buffer_put_string(msg, s, strlen(s));  
         s = "password";  
         buffer_put_string(msg, s, strlen(s));  
         buffer_put_char(msg, 0); // 0  
4362    
4363          if (pvar->ssh2_autologin == 1) { // SSH2自動ログイン          if (pvar->auth_state.cur_cred.method == SSH_AUTH_PASSWORD) { // パスワード認証
4364                  s = pvar->ssh2_password;                  s = connect_id;
4365                    buffer_put_string(msg, s, strlen(s));
4366                    s = "password";
4367                    buffer_put_string(msg, s, strlen(s));
4368                    buffer_put_char(msg, 0); // 0
4369    
4370                    if (pvar->ssh2_autologin == 1) { // SSH2自動ログイン
4371                            s = pvar->ssh2_password;
4372                    } else {
4373                            s = pvar->auth_state.cur_cred.password;  // パスワード
4374                    }
4375                    buffer_put_string(msg, s, strlen(s));
4376    
4377    
4378            } else if (pvar->auth_state.cur_cred.method == SSH_AUTH_RSA) { // 公開鍵認証
4379                    buffer_t *signbuf = NULL;
4380                    buffer_t *blob = NULL;
4381                    int bloblen;
4382                    char *signature = NULL;
4383                    int siglen;
4384                    CRYPTKeyPair *keypair = pvar->auth_state.cur_cred.key_pair;
4385    
4386                    if (get_SSH2_publickey_blob(pvar, &blob, &bloblen) == FALSE) {
4387                            goto error;
4388                    }
4389    
4390                    // step1
4391                    signbuf = buffer_init();
4392                    if (signbuf == NULL) {
4393                            buffer_free(blob);
4394                            goto error;
4395                    }
4396                    // セッションID
4397                    buffer_append_length(signbuf, pvar->session_id, pvar->session_id_len);
4398                    buffer_put_char(signbuf, SSH2_MSG_USERAUTH_REQUEST);
4399                    s = pvar->auth_state.user;  // ユーザ名
4400                    buffer_put_string(signbuf, s, strlen(s));
4401                    s = connect_id;
4402                    buffer_put_string(signbuf, s, strlen(s));
4403                    s = "publickey";
4404                    buffer_put_string(signbuf, s, strlen(s));
4405                    buffer_put_char(signbuf, 1); // true
4406                    s = get_SSH2_keyname(keypair); // key typeに応じた文字列を得る
4407                    buffer_put_string(signbuf, s, strlen(s));
4408                    s = buffer_ptr(blob);
4409                    buffer_append_length(signbuf, s, bloblen);
4410    
4411                    // 署名の作成
4412                    if ( generate_SSH2_keysign(keypair, &signature, &siglen, buffer_ptr(signbuf), buffer_len(signbuf)) == FALSE) {
4413                            buffer_free(blob);
4414                            buffer_free(signbuf);
4415                            goto error;
4416                    }
4417    
4418                    // step3
4419                    s = connect_id;
4420                    buffer_put_string(msg, s, strlen(s));
4421                    s = "publickey";
4422                    buffer_put_string(msg, s, strlen(s));
4423                    buffer_put_char(msg, 1); // true
4424                    s = get_SSH2_keyname(keypair); // key typeに応じた文字列を得る
4425                    buffer_put_string(msg, s, strlen(s));
4426                    s = buffer_ptr(blob);
4427                    buffer_append_length(msg, s, bloblen);
4428                    buffer_append_length(msg, signature, siglen);
4429    
4430    
4431                    buffer_free(blob);
4432                    buffer_free(signbuf);
4433                    free(signature);
4434    
4435          } else {          } else {
4436                  s = pvar->auth_state.cur_cred.password;  // パスワード                  goto error;
4437    
4438          }          }
4439          buffer_put_string(msg, s, strlen(s));  
4440    
4441          // パケット送信          // パケット送信
4442          len = buffer_len(msg);          len = buffer_len(msg);
# Line 4208  static BOOL handle_SSH2_authrequest(PTIn Line 4451  static BOOL handle_SSH2_authrequest(PTIn
4451          SSH2_dispatch_add_message(SSH2_MSG_USERAUTH_BANNER);          SSH2_dispatch_add_message(SSH2_MSG_USERAUTH_BANNER);
4452    
4453          return TRUE;          return TRUE;
4454    
4455    error:
4456            buffer_free(msg);
4457    
4458            return FALSE;
4459  }  }
4460    
4461    
# Line 4650  static BOOL handle_SSH2_window_adjust(PT Line 4898  static BOOL handle_SSH2_window_adjust(PT
4898    
4899  /*  /*
4900   * $Log: not supported by cvs2svn $   * $Log: not supported by cvs2svn $
4901     * Revision 1.8  2004/12/17 16:52:36  yutakakn
4902     * KEXにおけるRSAおよびDSSのkey verify処理を追加。
4903     *
4904   * Revision 1.7  2004/12/17 14:28:36  yutakakn   * Revision 1.7  2004/12/17 14:28:36  yutakakn
4905   * メッセージ認証アルゴリズムに HMAC-MD5 を追加。   * メッセージ認証アルゴリズムに HMAC-MD5 を追加。
4906   * TTSSHバージョンダイアログにHMACアルゴリズム表示を追加。   * TTSSHバージョンダイアログにHMACアルゴリズム表示を追加。

Legend:
Removed from v.2759  
changed lines
  Added in v.2762

Back to OSDN">Back to OSDN
ViewVC Help
Powered by ViewVC 1.1.26