# Overview

To sign a message under DomainKeys, make the following calls:

1. `lib = dk_init();`
   - initialize an instance of the library
   - this must be done once before any of the other calls are made
   - this needs to be called once when the application is started, but its result can be reused at the start of processing of each message
   - the remaining steps can use the same value of `lib`, even in multiple threads and over multiple messages
2. `dk = dk_sign(lib, ...);`
   - initialize a handle set up for signing the message
   - at this point a canonicalization, signing algorithm and secret key are selected by the caller
3. `stat = dk_header(dk, ...);`
   - pass a header to `libdk`
   - this should be done once for each header that should be included in computation of the signature (currently all of them)
4. `stat = dk_eoh(dk);`
   - notify `libdk` that the end of this message's headers has been reached
5. `stat = dk_body(dk, ...);`
   - pass to `libdk` a chunk of the body that should be included in computation of the signature (currently all of it)
   - repeat for each body chunk that arrives
6. `stat = dk_eom(dk, ...);`
   - notify `libdk` that the end of this message has been reached
   - get back any informational flags of interest from `libdk`
7. `stat = dk_getsig(dk, ...);`
   - compute the base64-encoded signature for the message
   - the signing algorithm was selected in the call to `dk_sign()` above
   - the data returned here coupled with the parameters to the `dk_sign()` call make up the content of the signature that needs to be prepended to the message according to the DomainKeys specification
8. `stat = dk_free(dk);`
   - free resources related to this message
9. `stat = dk_close(dk);`
   - free resources related to this library instance

To verify a message under DomainKeys, make the following calls:

1. `lib = dk_init();`
   - initialize an instance of the library
   - this must be done once before any of the other calls are made
   - this needs to be called once when the application is started, but its result can be reused at the start of processing of each message
   - the remaining steps can use the same value of `lib`, even in multiple threads and over multiple messages
2. `dk = dk_verify(lib, ...);`
   - initialize a handle set up for verifying the message
   - the canonicalization and signing algorithms and public key were selected by the agent that signed the message, and so don't need to be provided here
3. `stat = dk_header(dk, ...);`
   - pass a header to `libdk`
   - this should be done once for each header that should be included in computation of the digest to be verified (currently all of them)
4. `stat = dk_eoh(dk);`
   - notify `libdk` that the end of this message's headers has been reached
5. `stat = dk_body(dk, ...);`
   - pass to `libdk` a chunk of the body that should be included in computation of the digest to be verified (currently all of it)
6. `stat = dk_eom(dk, ...);`
   - notify `libdk` that the end of this message has been reached
   - get back any informational flags of interest from `libdk`
   - see if `stat` is `DK_STAT_OK` (verification OK) or `DK_STAT_BADSIG` (verification failed)
7. `stat = dk_free(dk);`
   - free resources related to this message
8. `stat = dk_close(dk);`
   - free resources related to this library instance

One application, having called `dk_init()` once, can call `dk_sign()` or `dk_verify()` more than once each, and furthermore can have more than one signing/verifying handle in existence at any given time.