Протокол Ди́ффи — Хе́ллмана (англ. Diffie–Hellman key exchange protocol, DH) — криптографический протокол, позволяющий двум и более сторонам получить общий секретный ключ, используя незащищенный от прослушивания канал связи. Полученный ключ используется для шифрования дальнейшего обмена с помощью алгоритмов симметричного шифрования.
 Схема открытого распределения ключей, предложенная Диффи и Хеллманом, произвела настоящую революцию в мире шифрования, так как снимала основную проблему классической криптографии — проблему распределения ключей.
 В чистом виде алгоритм Диффи — Хеллмана уязвим для модификации данных в канале связи, в том числе для атаки «Man-in-the-middle (человек посередине)», поэтому схемы с его использованием применяют дополнительные методы односторонней или двусторонней аутентификации.
 Передача ключа по открытым каналам была большой проблемой криптографии XX века. Но эту проблему удалось решить после появления алгоритма Диффи — Хеллмана. Данный алгоритм позволил дать ответ на главный вопрос: «Как при обмене зашифрованными посланиями уйти от необходимости передачи секретного кода расшифровки, который, как правило, не меньше самого послания?» Открытое распространение ключей Диффи — Хеллмана позволяет паре пользователей системы выработать общий секретный ключ, не обмениваясь секретными данными.
 Основы криптографии с открытыми ключами были выдвинуты Уитфилдом Диффи (Whitfield Diffie) и Мартином Хеллманом (Martin Hellman), а также независимо от них Ральфом Мерклом (Ralph Merkle).
 Их вкладом в криптографию было утверждение, что ключи можно использовать парами — ключ шифрования и ключ дешифрования — при условии, что исключается возможность определения содержимого ключа расшифровки, исходя из содержимого открыто передаваемого ключа шифрования. Диффи и Хеллман впервые представили эту идею на Национальной компьютерной конференции в 1976 году, а через несколько месяцев была опубликована их основополагающая работа «New Directions in Cryptography» («Новые направления в криптографии»).
 Годом позже был изобретён первый алгоритм асимметричного шифрования RSA, который позволил решить проблему общения через незащищённый канал.
 В 2002 году Мартин Хеллман писал[источник не указан 669 дней]:
 Эта система … с тех пор известна под названием алгоритма Диффи — Хеллмана. Однако, когда система была впервые описана на бумаге Диффи и мной, это была система распространения открытых ключей, концепция которой была выработана Мерклом, и поэтому она должна называться „алгоритмом Диффи — Хеллмана — Меркла“, если её связывают с именами. Я надеюсь, что это небольшое изменение поможет признанию равного вклада Меркла в изобретение криптографии с открытыми ключами. В уже истёкшем патенте U.S. Patent 4 200 770 в качестве создателей данного алгоритма указано три автора: Хеллман, Диффи и Меркл.
 Только в декабре 1997 года появилась обновлённая информация о том, что Малькольм Вильямсон уже в 1974 году изобрёл математический алгоритм, основанный на коммутативности показателей при последовательном возведении в степень (
  
    
      
        (
        
          b
          
            x
          
        
        
          )
          
            y
          
        
        =
        (
        
          b
          
            y
          
        
        
          )
          
            x
          
        
        =
        
          b
          
            x
            y
          
        
      
    
    {\displaystyle (b^{x})^{y}=(b^{y})^{x}=b^{xy}}
  
). Данный метод можно назвать аналогом алгоритма Диффи — Хеллмана.
 Работу алгоритма можно описать следующим образом. Предположим, существует два абонента: Алиса и Боб. Обоим абонентам известны некоторые два числа 
  
    
      
        g
      
    
    {\displaystyle g}
  
 и 
  
    
      
        p
      
    
    {\displaystyle p}
  
, которые не являются секретными и могут быть известны также другим заинтересованным лицам. Для того, чтобы создать неизвестный более никому секретный ключ, оба абонента генерируют большие случайные числа: Алиса — число 
  
    
      
        a
      
    
    {\displaystyle a}
  
, Боб — число 
  
    
      
        b
      
    
    {\displaystyle b}
  
. Затем Алиса вычисляет остаток от деления (1):
 и пересылает его Бобу, а Боб вычисляет остаток от деления (2):
 и передаёт Алисе. Предполагается, что злоумышленник может получить оба этих значения, но не модифицировать их (то есть, у него нет возможности вмешаться в процесс передачи).
 На втором этапе Алиса на основе имеющегося у неё 
  
    
      
        a
      
    
    {\displaystyle a}
  
 и полученного по сети 
  
    
      
        B
      
    
    {\displaystyle B}
  
 вычисляет значение (3):
 Боб на основе имеющегося у него 
  
    
      
        b
      
    
    {\displaystyle b}
  
 и полученного по сети 
  
    
      
        A
      
    
    {\displaystyle A}
  
 вычисляет значение (4):
 Как нетрудно видеть, у Алисы и Боба получилось одно и то же число (5):
 Его они и могут использовать в качестве секретного ключа, поскольку здесь злоумышленник встретится с практически неразрешимой (за разумное время) проблемой вычисления (3) или (4) по перехваченным 
  
    
      
        
          g
          
            a
          
        
        
          mod
          
            p
          
        
      
    
    {\displaystyle g^{a}{\bmod {p}}}
  
 и 
  
    
      
        
          g
          
            b
          
        
        
          mod
          
            p
          
        
      
    
    {\displaystyle g^{b}{\bmod {p}}}
  
, если числа 
  
    
      
        p
      
    
    {\displaystyle p}
  
, 
  
    
      
        a
      
    
    {\displaystyle a}
  
, 
  
    
      
        b
      
    
    {\displaystyle b}
  
 выбраны достаточно большими. Работа алгоритма показана на рисунке.
 При работе алгоритма каждая сторона:
 В практических реализациях для a и b используются числа порядка 10100 и p порядка 10300. Число g не обязано быть большим и обычно имеет значение в пределах первого десятка.
 Ева — криптоаналитик. Она читает пересылку Боба и Алисы, но не изменяет содержимого их сообщений.
 Использование алгоритма Диффи — Хеллмана не ограничивается двумя участниками. Он может быть применен на неограниченное количество пользователей. Рассмотрим ситуацию, когда Алиса, Боб и Кэрол вместе генерируют исходный ключ. В данном случае последовательность действий будет следующая:
 Все вычисления производятся по модулю p
 Если кто-то будет прослушивать канал связи, то он сможет увидеть ga mod p, gb mod p, gc mod p, gab mod p, gac mod p, и gbc mod p, но при этом не сможет воспроизвести gabc mod p используя любые комбинации этих чисел.
 Для того чтобы данный алгоритм был эффективно применен для большой группы людей, необходимо соблюдение двух основных принципов:
 Алгоритм Диффи — Хеллмана также может быть использован при шифровании с открытым ключом. В этом случае общая схема остаётся аналогичной приведённой выше, но с небольшими отличиями. Алиса не передаёт значения p, g и A Бобу напрямую, а публикует их заранее в качестве своего открытого ключа. Боб выполняет свою часть вычислений, после чего шифрует сообщение симметричным алгоритмом, используя K в качестве ключа, и передает шифротекст Алисе вместе со значением B.
 На практике алгоритм Диффи — Хеллмана таким образом не используется. В данной области доминирующим алгоритмом с открытым ключом является RSA. Это обусловлено больше коммерческими соображениями, так как именно компанией RSA Data Security был создан центр сертификации. К тому же алгоритм Диффи — Хеллмана не может быть использован при подписании сертификатов.
 Если имеется сообщество пользователей, каждый из пользователей может опубликовать открытый ключ X=
  
    
      
        
          g
          
            x
          
        
      
    
    {\displaystyle g^{x}}
  
mod n в общей базе данных. Если Алиса хочет установить связь с Бобом, ей надо получить открытый ключ Боба и сгенерировать их общий секретный ключ. Алиса может зашифровать сообщение сгенерированным секретным ключом и послать его Бобу. Боб извлечет открытый ключ Алисы и найдет общий секретный ключ.
 Каждая пара пользователей может использовать свой уникальный секретный ключ, не требуя обмена данными между пользователями. При этом все открытые ключи должны пройти проверку подлинности для того, чтобы исключить «человека посередине».
 Криптографическая стойкость алгоритма Диффи — Хеллмана (то есть сложность вычисления 
  
    
      
        K
        =
        
          g
          
            a
            b
          
        
        
          mod
          
            p
          
        
      
    
    {\displaystyle K=g^{ab}{\bmod {p}}}
  
 по известным p, g, 
  
    
      
        A
        =
        
          g
          
            a
          
        
        
          mod
          
            p
          
        
      
    
    {\displaystyle A=g^{a}{\bmod {p}}}
  
 и 
  
    
      
        B
        =
        
          g
          
            b
          
        
        
          mod
          
            p
          
        
      
    
    {\displaystyle B=g^{b}{\bmod {p}}}
  
) основана на предполагаемой сложности задачи дискретного логарифмирования.
 Протокол Диффи — Хеллмана отлично противостоит пассивному нападению, но в случае реализации атаки «человек посередине» он не устоит. В самом деле, в протоколе ни Алиса, ни Боб не могут достоверно определить, кем является их собеседник, поэтому вполне возможно представить случай, при котором Боб и Алиса установили связь с Меллори, которая Алисе выдает себя за Боба, а Бобу представляется Алисой. И тогда вместо протокола Диффи — Хеллмана получаем что-то похожее на следующее:
 То есть Меллори получает один общий ключ с Алисой (которая считает, что это Боб) и один общий ключ с Бобом (который считает, что это Алиса). А, следовательно, она может получать от Алисы любое сообщение для Боба, расшифровать его ключом, прочитать, зашифровать ключом и передать Бобу. Таким образом, подлог может оставаться незамеченным очень долгое время.
 Стойкость разделенного ключа в протоколе Диффи — Хеллмана обеспечивается вычислением значения 
  
    
      
        
          g
          
            a
            b
          
        
        
          mod
          
            p
          
        
      
    
    {\displaystyle g^{ab}{\bmod {p}}}
  
 по заданным числам 
  
    
      
        
          g
          
            a
          
        
      
    
    {\displaystyle g^{a}}
  
 и 
  
    
      
        
          g
          
            b
          
        
      
    
    {\displaystyle g^{b}}
  
. Эта задача называется вычислительной задачей Диффи — Хеллмана.
 Такая формулировка представляет собой общую постановку задачи в конечном поле 
  
    
      
        
          F
          
            q
          
        
      
    
    {\displaystyle F_{q}}
  
 представляет общий случай, для Диффи — Хеллмана используется специальный случай.
Если бы задачу Диффи — Хеллмана было легко решить, то значение 
  
    
      
        
          g
          
            a
            b
          
        
        
          mod
          
            p
          
        
      
    
    {\displaystyle g^{ab}{\bmod {p}}}
  
 можно было бы найти, зная числа 
  
    
      
        p
      
    
    {\displaystyle p}
  
, 
  
    
      
        g
      
    
    {\displaystyle g}
  
, 
  
    
      
        
          g
          
            a
          
        
      
    
    {\displaystyle g^{a}}
  
 и 
  
    
      
        
          g
          
            b
          
        
      
    
    {\displaystyle g^{b}}
  
, которые являются частью протокола. Предполагая, что противник обладает возможностями перехвата информации, следует предположить, что эти числа не являются для него секретом.
Задача Диффи — Хеллмана опирается на сложность вычисления дискретного логарифма.
 Дискретное логарифмирование аналогично обычному логарифмированию в поле действительных чисел. Однако, в отличие от последней задачи, в которой решение является приближенным, задача о вычислении дискретного логарифма имеет точное решение.
 Как уже стало понятным, в основе современной криптографии лежит теория вычислительной сложности. Это значит, что стойкость криптосистем с открытым ключом является условной и зависит от сложности решения некоторых задач.
Все это приводит к тому, что задача Диффи — Хеллмана и задача дискретного логарифмирования считаются трудноразрешимыми.
 Интуитивно ясно, что сложность решения этих задач зависит как от размера поля Fq, так и от выбора параметров (открытого параметра g и секретных чисел a и b). Очевидно, что небольшие варианты этих задач являются разрешимыми.
Полученные сведения позволяют сформулировать точные предположения о неразрешимости задачи Диффи — Хеллмана и задачи дискретного логарифмирования.
 Предположение 1 — Условия неразрешимости задачи Диффи — Хеллмана
 Алгоритмом решения задачи Диффи — Хеллмана называется вероятностный полиномиальный алгоритм A с преимуществом ε > 0:
 где входные данные А указаны в определении (Вычислительная задача Диффи — Хеллмана) (в конечном поле).
 Пусть IG — генератор вариантов, получающий на вход число 
  
    
      
        
          1
          
            k
          
        
      
    
    {\displaystyle 1^{k}}
  
, время работы которого является полиномом от параметра k, а результатом — 1) desq(
  
    
      
        
          F
          
            q
          
        
      
    
    {\displaystyle F_{q}}
  
), где |q| = k, и 2) порождающий элемент g ∈
  
    
      
        
          F
          
            q
          
          
            ∗
          
        
      
    
    {\displaystyle F_{q}^{*}}
  
.
 Будем говорить, что генератор IG удовлетворяет условиям неразрешимости задачи Диффи — Хеллмана, если для вариантов IG(
  
    
      
        
          1
          
            k
          
        
      
    
    {\displaystyle 1^{k}}
  
) не существует алгоритма решения с преимуществом ε> 0, которое не является пренебрежимо малым по сравнению со всеми достаточно большими числами k.
 Предположение 2 — Условия неразрешимости задачи дискретного логарифмирования
 Алгоритмом решения задачи дискретного логарифмирования называется вероятностный полиномиальный алгоритм A с преимуществом ε > 0:
 где входные данные А указаны в определении (Вычислительная задача Диффи — Хеллмана) (в конечном поле).
 Пусть IG — генератор вариантов, получающий на вход число 
  
    
      
        
          1
          
            k
          
        
      
    
    {\displaystyle 1^{k}}
  
, время работы которого является полиномом от параметра k, а результатом — 1) desq(
  
    
      
        
          F
          
            q
          
        
      
    
    {\displaystyle F_{q}}
  
), где |q| = k, и 2) порождающий элемент g ∈
  
    
      
        
          F
          
            q
          
          
            ∗
          
        
      
    
    {\displaystyle F_{q}^{*}}
  
 и 3) элемент h ∈
  
    
      
        
          F
          
            q
          
          
            ∗
          
        
      
    
    {\displaystyle F_{q}^{*}}
  

 Будем говорить, что генератор IG удовлетворяет условиям неразрешимости задачи Диффи — Хеллмана, если для вариантов IG(
  
    
      
        
          1
          
            k
          
        
      
    
    {\displaystyle 1^{k}}
  
) не существует алгоритма решения с преимуществом ε> 0, которое не является пренебрежимо малым по сравнению со всеми достаточно большими числами k.
 Иначе говоря, здесь предполагается, что почти все достаточно большие варианты указанных задач в конечных полях не имеют эффективного алгоритма решения. Доля слабых вариантов этих задач, поддающихся решению, пренебрежимо мала.
 Для безопасности протокола важным является выбор параметров. Многие реализации используют небольшое количество популярных наборов параметров алгоритма. В 2016 была представлена работа, показавшая возможность по подготовке специальных конечных полей для алгоритма Диффи — Хеллмана (DH). Выбранное исследователями простое число p специального вида (размером 1024 бита) выглядит обычным для пользователей, но упрощает на несколько порядков сложность вычислений по методу SNFS для решения задачи дискретного логарифмирования. Для борьбы с атакой предлагается увеличить размер модуля до 2048 бит.