pikesaku’s blog

個人的な勉強メモです。記載内容について一切の責任は持ちません。

Diffie-Hellman key exchangeについて

ポイント

読み方

ディフィー・ヘルマン(ディッフェルと勘違いしてた。。。)

公開鍵暗号の一種

公開鍵暗号 - Wikipedia

暗号化と復号に別個の鍵(手順)を用い、暗号化の鍵を公開できるようにした暗号方式

他にRSAがあり。
公開鍵暗号は、共通鍵暗号の共有鍵の交換で利用される

素数

正の約数が 1 と自分自身のみ

原子根

(3 以上の)素数 p と 1 以上 p 未満の整数 r が以下の性質を満たすとき r を法 p に対する原始根と呼ぶ。
「r,r2,⋯,rp−2 のいずれもが p で割って余り 1 でない」
★よく分からないけど、素数に対し存在する、ある条件に合致する整数と考える。
★一つの素数に対し複数存在することあり。例) 素数7の場合、5,3

送受信者間で交換する情報

f:id:pikesaku:20200503015344p:plain

確認コード

# -*- coding:utf-8 -*-
from sympy import prime
import random
import sym
from sympy.ntheory import is_primitive_root

if __name__ == '__main__':
  # 素数をランダムに設定(100~1100番目の範囲で)
  P = prime(random.randint(101,1101))
  # 選択した素数に対する原始根をランダムに設定
  G = random.choice([i for i in range(1,P) if is_primitive_root(i, P)])
  # 送信者側の乱数設定
  A = random.randint(1,P - 2)
  # 受信者側の乱数設定
  B = random.randint(1,P - 2)
  # 送信者が受信者に以下を通知
  GA_MOD_P = G ** A % P
  # 受信者が送信者に以下を通知
  GB_MOD_P = G ** B % P
  # 送信者が共有鍵を計算
  A_SKEY = GB_MOD_P ** A % P
  # 受信者が共有鍵を計算
  B_SKEY = GA_MOD_P ** B % P
  # 送信者と受信者の共有鍵が同一であることを確認
  if A_SKEY == B_SKEY:
    print('Success!')
  else:
    print('Failure!')

確認コードのポイント

・必ずSuccessになる
・数学の理論として、GB_MOD_P ** A % PとGB_MOD_P ** A % Pが同じになる点を利用し共通鍵を交換
・やりとりする情報は全てephemeral(短命の)=PFS対応
・Opensslの暗号化スイートでDHとDHEがあり。
・DHは証明書のDHパラメタを利用(static DH)
・DHEはDHパラメタを動的に生成

※参考URL
Pythonで数学の勉強:初等整数論 - Qiita
Number Theory — SymPy 1.5.1 documentation
夜でもアッサム: SSL(TLS)のDHとDHEの違い