Provided by: libbobcat-dev_6.02.02-1_amd64 bug

NAME

       FBB::ECDH - Elliptic Curve Diffie-Hellman PKI, computing shared keys

SYNOPSIS

       #include <bobcat/ecdh>
       Linking option: -lbobcat -lcrypto

DESCRIPTION

       The  class  FBB::ECDH  computes shared keys (shared secrets) applying elliptic keys to the
       Diffie-Hellman (1976) algorithm. The Diffie-Hellman  algorithm  uses  public  and  private
       information,  providing a public key infrastructure (PKI). The public information consists
       of an elliptic curve specification and a public key, which may  be  shared  over  insecure
       media.

       The  Diffie-Hellman  algorithm is commonly used to compute a shared key which is then used
       to encrypt information sent between two parties.

       One party, which in this man-page is called the initiator, specifies at construction  time
       an  elliptic  curve,  constructs  a  public  and private key, and writes the public key in
       hexadecimal big-endian form, followed by the name of the used elliptic curve to file.  The
       initiator’s  private key is separately written to file, as the private key is required for
       computating the shared key. Encryption may be used when writing the private key to file.

       Next the initiator passes the file containing the initiator’s public key and the  name  of
       the used elliptic curve to the other party, which in this man-page is called the peer.

       The  peer,  having  received  the  initiator’s  (public  key) file constructs an FBB::ECDH
       object. The peer’s ECDH constructor computes the peer’s public and private key, writes the
       peer’s  public key to file, and constructs the shared key. Once the peer’s ECDH object has
       been constructed the peer can write the shared key to file. The  peer’s  private  key  may
       optionally  also be written to file, but that’s optional, as the peer’s private key is not
       required for subsequent computations. Encryption may also be used when writing the  peer’s
       private key to file.

       The  file  containing  the  peer’s  public  key is then sent to the initator. The initator
       constructs an ECDH object specifying the names of the used elliptic  curve,  of  the  file
       containing  the  initiator’s  private  key, and the name of the file containing the peer’s
       public key. Once this ECDH object has been constructed the peer may write the  shared  key
       to file.

       The  initiator  and  peer’s  shared  keys  are  identical  and  can  be used for symmetric
       encryption of sensitive information shared between the initiator and the peer.

       FBB::Exceptions are thrown if the ECDH constructors   or  members  cannot  complete  their
       tasks.

       Perfect Forward Secrecy and Ephemeral Diffie Hellman

       The  initiator  and  peer  may decide not to save their private information once they have
       constructed their shared keys, resulting in Perfect Forward Secrecy and  Ephemeral  Diffie
       Hellman. Here, this procedure is applied as follows:

       o      Initiator  and  peer  have agreed upon and securely exchanged a long-lasting common
              secret, which may be used in combination with, e.g., symmetric encryption methods.

       o      Applying the procedure described in the previous section, the private keys are  not
              saved  on  files,  and the process constructing the initiator’s ECDH object may not
              terminate, but must remain active until the peer’s public key  has  been  received.
              Once  the  initiator’s process has constructed the public key that key is encrypted
              using the common  secret,  and  is  then  sent  to  the  peer.  Alternatively,  the
              initiator’s  private  key  may  temporarily  be  stored  in  shared  memory  or may
              temporarily be stored encrypted on file.

       o      The peer, having received the initiator’s public key, constructs the shared secret,
              encrypts  the  peer’s  public  key,  and  sends  the  encrypted  public  key to the
              initiator.

       o      The initiator upon receipt of the peer’s  public  key,  computes  the  shared  key,
              either   by  continuing  the  temporarily  suspended  construction  process  or  by
              retrieving the shared key from memory or file,  removing  the  storage  (memory  or
              file) thereafter.

       o      Since  the  private  keys  and  the public keys are not stored or kept on files the
              shared keys cannot be reconstructed, while a Man-In-The-Middle attack is  prevented
              by only exchanging encrypted public information.

       o      The shared key can now be used to encrypt a communication session

       Document encryption using Diffie Hellman

       As with PKI in general, the Diffie Hellman key exchange method itself is normally not used
       for encrypting documents. Instead, it is used to obtain a key that is used  for  symmetric
       encryption  methods  like  3DES  or  CBC. These symmetric encryption methods are available
       through, e.g., Bobcats’ ISymCryptStream and OSymCryptStream classes.

NAMESPACE

       FBB
       All constructors, members, operators and manipulators, mentioned  in  this  man-page,  are
       defined in the namespace FBB.

INHERITS FROM

       -

ENUMERATIONS

       The  class ECDH defines two enumerations, each having one defined value. The enumberations
       are used to select specific overloaded versions of the ECDH constructors or set members:

       o      The t(enum TheInitiator) has value Initiator  and  is  used  to  select  overloaded
              versions meant for the initiator;

       o      The  t(enum ThePeer) has value Peer and is used to select overloaded versions meant
              for the peer.

CONSTRUCTORS

       o      ECDH():
              The default constructor is available merely constructing a valid  object.  It  also
              prepares  a  map  of  all  elliptic  curves  predefined  by  openSSL.  As all other
              constructors use default constructor delegation the map  is  also  available  after
              calling the other constructors;

       o      ECDH(TheInitiator   init,   std::string   const   &curveName,   std::string   const
              &initPubFname):
              This constructor  initializes  the  ECDH  object  to  be  used  by  the  initiator,
              constructing  the  initiator’s  private  and  public  keys using the elliptic curve
              specified  by  curveName  (e.g.,  secp384r1,  see  also  operator<<   below).   The
              initiator’s public key (in big-endian hexadecimal format) and curveName are written
              to initPubFname;

              This constructor should be called by the  initiator  to  start  the  Diffie-Hellman
              shared key computation procedure;

       o      ECDH(ThePeer    peer,    std::string   const   &initPubFname,   std::string   const
              &peerPubFname):
              This constructor is used by the peer, having received the initiator’s  public  info
              on the file initPubFname.  It constructs the peer’s private and public keys as well
              as the shared key. The peer’s public key  (in  big-endian  hexadecimal  format)  is
              written to peerPubFname, which file is then be sent to the initiator;

       o      ECDH(std::string  const  &curveName,  std::string  const &peerPubFname, std::string
              const &initSecFname, std::string const passphrase = ""):
              Once the initiator has received the peer’s public key (in  the  file  peerPubFname)
              this  constructor  constructs  the initiator’s version of the shared key. Here, the
              initiator has  previously  saved  the  initiator’s  private  key  to  initSecFname,
              optionally  using  encryption. If encryption was used then the then used passphrase
              must also be specified when using this constructor.

       The move constructor (and move assignment operator) is available.

MEMBER FUNCTIONS

       o      std::string const &curve() const:
              The used elliptic curve is returned;

       o      std::string privKey() const:
              The big-endian hex-formatted private key is returned, prefixed by a line containing
              hex;

       o      void privKey(std::string const &privKeyFname, std::string passphrase) const:
              The  private  private  key is encrypted using the AES-256-GCM encryption algorithm,
              using passphrase passphrase. It is then written to privKeyFname, prefixed by a line
              containing  encrypted.  The  string  passphrase  must  consist  of  at  least  five
              characters, and may contain multiple words;

       o      std::string const &pubKey() const:
              The public key is returned as a big-endian hexadecimal string;

       o      void  set(TheInitiator  init,  std::string  const  &curveName,  std::string   const
              &initPubFname):
              This member should be called by the initiator, constructing the initiator’s private
              and public keys using the elliptic curve specified by  curveName.  The  initiator’s
              public  key  (in  big-endian  hexadecimal  format)  and  curveName  are  written to
              initPubFname.  This member is automatically called by the  constructor  having  the
              same  parameters,  but  it  may  also  explicitly  called  after  using the default
              constructor;

       o      void  set(ThePeer  peer,  std::string  const   &initPubFname,   std::string   const
              &peerPubFname):
              This  member  should  be called by the peer, having received the initiator’s public
              info on the file initPubFname.  It constructs the peer’s private and public keys as
              well as the shared key. The peer’s public key (in big-endian hexadecimal format) is
              written to peerPubFname, which file is then be sent to the initiator.  This  member
              is  automatically  called by the constructor having the same parameters, but it may
              also explicitly called after using the default constructor;

       o      void set(std::string const &curveName, std::string const &peerPubFname, std::string
              const &initSecFname, std::string const passphrase = ""):
              This  member  should be called by the initiator, once the peer’s public key (in the
              file peerPubFname) has been received. It computes the initiator’s  version  of  the
              shared  key.  When  using  this  member  the  initiator  has  previously  saved the
              initiator’s private key to initSecFname, optionally using encryption. If encryption
              was used then the then used passphrase must also be specified as this member’s last
              argument.

       o      std::string const &sharedKey() const:
              This member returns the computed shared key (in big-endian hexadecimal format);

       o      std::string const &sharedKey(std::string const &peerPubFname):
              Instead  of  using  the  set(std::string  const  &curveName,  ...)  member  or  the
              ECDH(std::string  const &curveName, ...) constructor, the initiator may also merely
              call the set(TheInitiator init, ...)  member or the  ECDH(TheInitiator  init,  ...)
              constructor,  suspending  the  process  in  which  they  are  called until the file
              containing the peer’s public key has been received. Then, this member can be called
              by  the constructed ECDH object to obtain the initiator’s shared key. The advantage
              of using this member is that the initiator does not have to  save  the  initiator’s
              private key.

OVERLOADED OPERATOR

       o      std::ostream &operator<<(ostream &out, ECDH const &ecdh):
              The   (alphabetically  ordered)  currently  available  elliptic  curves  and  their
              associated comment is written to out, one elliptic curve on a separate line.

EXAMPLE

       Start the program with one of the following arguments:

       o      curves: show the available elliptic curves on cout;

       o      init: compute the initiator’s public/secret  keys  writing  them  to  init.pub  and
              init.sec;

       o      peer:  compute the peer’s public/secret keys writing them to peer.pub and peer.sec,
              compute the peer’s shared key (peer.shared);

       o      priv: compute the  initiator’s  shared  key  (init.shared)  after  making  peer.pub
              available in a separate process, using a single initiator process.

       o      shared: compute the initiator’s shared key (init.shared) using a separate initiator
              process.

       #include "main.ih"

       int main(int argc, char **argv)
       try
       {
           if (argc == 1)
           {
               usage(path{ argv[0] }.filename().string());
               return 0;
           }

           if ("curves"s == argv[1])           // show supported ECDH curves.
               cout << ECDH{};

           else if ("init"s == argv[1])        // initiator key construction
           {
                                               // write the file containing
                                               // the curve + public key
               ECDH ecdh{ ECDH::Initiator, "secp384r1", "init.pub" };

                                               // save the initiator’s
                                              // private key
               ecdh.privKey("init.sec", "use your passphrase");
                   // not using encryption:
                   // auto initSec = Exception::factory<ofstream>("init.sec");
                   // initSec << ecdh.privKey() << ’\n’;
           }

           else if ("priv"s == argv[1])        // initiator key construction
           {
                                               // write the file containing
                                               // the curve + public key
               ECDH ecdh{ ECDH::Initiator, "secp384r1", "init.pub" };

               cout << "wait for the peer’s public key. "
                       "Press Enter to continue... ";
               cin.ignore(100, ’\n’);
                                                           // written to file
               auto initShared = Exception::factory<ofstream>("init.shared");
               initShared << ecdh.sharedKey("peer.pub") << ’\n’;
           }

           else if ("peer"s == argv[1])        // peer’s key construction
           {
                                               // write the peer’s public key
               ECDH ecdh{ ECDH::Peer, "init.pub", "peer.pub" };

                                               // save the peer’s private
                                               // key (although not needed)
               auto out = Exception::factory<ofstream>("peer.sec");
               out << ecdh.privKey() << ’\n’;

               out = Exception::factory<ofstream>("peer.shared");
               out << ecdh.sharedKey() << ’\n’;
           }

           else if ("shared"s == argv[1])      // the initiator’s shared key
           {                                   // construction
               ECDH ecdh{ "secp384r1", "peer.pub", "init.sec",
                                                   "use your passphrase" };

               auto initShared = Exception::factory<ofstream>("init.shared");
               initShared << ecdh.sharedKey() << ’\n’;     // written to file
           }

           else
           {
               usage(path{ argv[0] }.filename().string());
               return 1;
           }
       }
       catch (exception const &exc)
       {
           cerr << "Error: " << exc.what() << ’\n’;
           return 1;
       }
       catch (...)                     // and handle an unexpected exception
       {
           cerr << "unexpected exception\n";
           return 1;
       }

FILES

       bobcat/ecdh - defines the class interface

SEE ALSO

       bobcat(7),     bigint(3bobcat),     diffiehellman(3bobcat),      isymcryptstream(3bobcat),
       osymcryptstream(3bobcat)

BUGS

       None Reported.

BOBCAT PROJECT FILES

       o      https://fbb-git.gitlab.io/bobcat/: gitlab project page;

       o      bobcat_6.02.02-x.dsc: detached signature;

       o      bobcat_6.02.02-x.tar.gz: source archive;

       o      bobcat_6.02.02-x_i386.changes: change log;

       o      libbobcat1_6.02.02-x_*.deb: debian package containing the libraries;

       o      libbobcat1-dev_6.02.02-x_*.deb:  debian  package  containing the libraries, headers
              and manual pages;

BOBCAT

       Bobcat is an acronym of `Brokken’s Own Base Classes And Templates’.

COPYRIGHT

       This is free software, distributed under the terms  of  the  GNU  General  Public  License
       (GPL).

AUTHOR

       Frank B. Brokken (f.b.brokken@rug.nl).