summaryrefslogtreecommitdiffstats
path: root/openpgp-ffi
diff options
context:
space:
mode:
authorNeal H. Walfield <neal@pep.foundation>2020-01-31 14:20:53 +0100
committerNeal H. Walfield <neal@pep.foundation>2020-01-31 15:59:16 +0100
commita464ce819ccd1fa07ff8c6d0be74cff5eec5cf34 (patch)
tree31ed9d18b9c7802a93b4e4c8e6e85d1121b201d8 /openpgp-ffi
parentb9b6533bd5394cd5cdb6b91b5c5ca7a02e3ea199 (diff)
openpgp: Add a policy object.
- Change all functions that need to evaluate the validity of a signature (either directly or indirectly to take a policy object. - Use the policy object to allow the user to place additional constraints on a signature's validity. - This addresses the first half of #274 (it introduces the policy object, but does not yet implement any policy).
Diffstat (limited to 'openpgp-ffi')
-rw-r--r--openpgp-ffi/examples/decrypt-with.c4
-rw-r--r--openpgp-ffi/examples/encrypt-for.c4
-rw-r--r--openpgp-ffi/include/sequoia/openpgp.h82
-rw-r--r--openpgp-ffi/include/sequoia/openpgp/types.h10
-rw-r--r--openpgp-ffi/src/cert.rs54
-rw-r--r--openpgp-ffi/src/common.rs1
-rw-r--r--openpgp-ffi/src/parse/stream.rs26
-rw-r--r--openpgp-ffi/src/policy.rs36
8 files changed, 178 insertions, 39 deletions
diff --git a/openpgp-ffi/examples/decrypt-with.c b/openpgp-ffi/examples/decrypt-with.c
index 3f98c574..e288efbf 100644
--- a/openpgp-ffi/examples/decrypt-with.c
+++ b/openpgp-ffi/examples/decrypt-with.c
@@ -203,6 +203,7 @@ main (int argc, char **argv)
pgp_reader_t plaintext;
uint8_t buf[1024];
ssize_t nread;
+ pgp_policy_t policy = pgp_standard_policy ();
if (argc != 2)
error (1, 0, "Usage: %s <keyfile> <cipher >plain", argv[0]);
@@ -218,7 +219,7 @@ main (int argc, char **argv)
.key = cert,
.decrypt_called = 0,
};
- plaintext = pgp_decryptor_new (&err, source,
+ plaintext = pgp_decryptor_new (&err, policy, source,
get_public_keys_cb, decrypt_cb,
check_cb, NULL, &cookie, 0);
if (! plaintext)
@@ -233,5 +234,6 @@ main (int argc, char **argv)
pgp_reader_free (plaintext);
pgp_reader_free (source);
pgp_cert_free (cert);
+ pgp_policy_free (policy);
return 0;
}
diff --git a/openpgp-ffi/examples/encrypt-for.c b/openpgp-ffi/examples/encrypt-for.c
index aeb4dea4..27a7a585 100644
--- a/openpgp-ffi/examples/encrypt-for.c
+++ b/openpgp-ffi/examples/encrypt-for.c
@@ -28,6 +28,7 @@ main (int argc, char **argv)
pgp_cert_t cert;
pgp_writer_t sink;
pgp_writer_stack_t writer = NULL;
+ pgp_policy_t policy = pgp_standard_policy ();
if (argc != 2)
error (1, 0, "Usage: %s <keyfile> <plain >cipher", argv[0]);
@@ -36,7 +37,7 @@ main (int argc, char **argv)
if (cert == NULL)
error (1, 0, "pgp_cert_from_file: %s", pgp_error_to_string (err));
- pgp_cert_valid_key_iter_t iter = pgp_cert_valid_key_iter (cert, 0);
+ pgp_cert_valid_key_iter_t iter = pgp_cert_valid_key_iter (cert, policy, 0);
pgp_cert_valid_key_iter_alive (iter);
pgp_cert_valid_key_iter_revoked (iter, false);
pgp_cert_valid_key_iter_for_storage_encryption (iter);
@@ -91,5 +92,6 @@ main (int argc, char **argv)
pgp_recipient_free (recipients[i]);
free (recipients);
pgp_cert_free (cert);
+ pgp_policy_free (policy);
return 0;
}
diff --git a/openpgp-ffi/include/sequoia/openpgp.h b/openpgp-ffi/include/sequoia/openpgp.h
index 405cd2c6..d15749d9 100644
--- a/openpgp-ffi/include/sequoia/openpgp.h
+++ b/openpgp-ffi/include/sequoia/openpgp.h
@@ -590,7 +590,8 @@ char *pgp_user_id_binding_user_id (pgp_user_id_binding_t binding);
/*/
/// Returns a reference to the self-signature, if any.
/*/
-pgp_signature_t pgp_user_id_binding_selfsig(pgp_user_id_binding_t binding);
+pgp_signature_t pgp_user_id_binding_selfsig(pgp_user_id_binding_t binding,
+ pgp_policy_t policy);
/* openpgp::cert::UserIDBindingIter. */
@@ -628,7 +629,7 @@ void pgp_cert_key_iter_unencrypted_secret (pgp_cert_key_iter_t iter);
/// Note: you may not call this function after starting to iterate.
/*/
pgp_cert_valid_key_iter_t pgp_cert_key_iter_policy
- (pgp_cert_key_iter_t iter, time_t when);
+ (pgp_cert_key_iter_t iter, pgp_policy_t policy, time_t when);
/*/
/// Returns a reference to the next key. Returns NULL if there are no
@@ -703,15 +704,14 @@ void pgp_cert_valid_key_iter_for_transport_encryption (pgp_cert_valid_key_iter_t
void pgp_cert_valid_key_iter_alive (pgp_cert_valid_key_iter_t iter);
/*/
-/// Changes the iterator to only return keys whose revocation status
-/// matches `revoked`.
+/// Changes the iterator to only return keys that are revoked.
///
/// Note: you may not call this function after starting to iterate.
/*/
void pgp_cert_valid_key_iter_revoked (pgp_cert_valid_key_iter_t iter, bool revoked);
/*/
-/// Changes the iterator to only return keys that have secret keys.
+/// Changes the iterator to only return keys that are not revoked.
///
/// Note: you may not call this function after starting to iterate.
/*/
@@ -877,7 +877,8 @@ pgp_key_t pgp_cert_primary_key (pgp_cert_t cert);
/// If `when` is 0, then returns the Cert's revocation status as of the
/// time of the call.
/*/
-pgp_revocation_status_t pgp_cert_revoked (pgp_cert_t cert, time_t when);
+pgp_revocation_status_t pgp_cert_revoked (pgp_cert_t cert,
+ pgp_policy_t policy, time_t when);
/*/
/// Writes a revocation certificate to the writer.
@@ -906,7 +907,8 @@ pgp_cert_t pgp_cert_revoke_in_place (pgp_error_t *errp,
///
/// If `when` is 0, then the current time is used.
/*/
-pgp_status_t pgp_cert_alive(pgp_error_t *errp, pgp_cert_t cert, time_t when);
+pgp_status_t pgp_cert_alive(pgp_error_t *errp, pgp_cert_t cert,
+ pgp_policy_t policy, time_t when);
/*/
/// Changes the Cert's expiration.
@@ -917,9 +919,10 @@ pgp_status_t pgp_cert_alive(pgp_error_t *errp, pgp_cert_t cert, time_t when);
/// This function consumes `cert` and returns a new `Cert`.
/*/
pgp_cert_t pgp_cert_set_expiry(pgp_error_t *errp,
- pgp_cert_t cert,
- pgp_signer_t signer,
- uint32_t expiry);
+ pgp_cert_t cert,
+ pgp_policy_t policy,
+ pgp_signer_t signer,
+ uint32_t expiry);
/*/
/// Returns whether the Cert includes any secret key material.
@@ -946,12 +949,13 @@ pgp_cert_key_iter_t pgp_cert_key_iter (pgp_cert_t cert);
/// subkeys that are valid (i.e., have a self-signature at time
/// `when`).
/*/
-pgp_cert_valid_key_iter_t pgp_cert_valid_key_iter (pgp_cert_t cert, time_t when);
+pgp_cert_valid_key_iter_t pgp_cert_valid_key_iter
+ (pgp_cert_t cert, pgp_policy_t policy, time_t when);
/*/
/// Returns the Cert's primary user id (if any).
/*/
-char *pgp_cert_primary_user_id(pgp_cert_t cert);
+char *pgp_cert_primary_user_id(pgp_cert_t cert, pgp_policy_t policy);
/*/
/// Returns a CertParser.
@@ -1740,7 +1744,9 @@ bool pgp_verification_result_error (pgp_verification_result_t,
///
/// Note: all of the parameters are required; none may be NULL.
/*/
-pgp_reader_t pgp_decryptor_new (pgp_error_t *errp, pgp_reader_t input,
+pgp_reader_t pgp_decryptor_new (pgp_error_t *errp,
+ pgp_policy_t policy,
+ pgp_reader_t input,
pgp_decryptor_get_public_keys_cb_t get_public_keys,
pgp_decryptor_decrypt_cb_t decrypt,
pgp_decryptor_check_cb_t check,
@@ -1753,18 +1759,64 @@ pgp_reader_t pgp_decryptor_new (pgp_error_t *errp, pgp_reader_t input,
/// No attempt is made to decrypt any encryption packets. These are
/// treated as opaque containers.
/*/
-pgp_reader_t pgp_verifier_new (pgp_error_t *errp, pgp_reader_t input,
+pgp_reader_t pgp_verifier_new (pgp_error_t *errp,
+ pgp_policy_t policy,
+ pgp_reader_t input,
pgp_decryptor_get_public_keys_cb_t get_public_keys,
pgp_decryptor_check_cb_t check,
void *cookie, time_t time);
/*/
-/// Verifies a detached OpenPGP signature.
+/// Verifies a detached OpenPGP signature.///
+/// A Certificate (see [RFC 4880, section 11.1]) can be used to verify
+/// signatures and encrypt data. It can be stored in a keystore and
+/// uploaded to keyservers.
+///
+/// [RFC 4880, section 11.1]: https://tools.ietf.org/html/rfc4880#section-11.1
+
/*/
pgp_reader_t pgp_detached_verifier_new (pgp_error_t *errp,
+ pgp_policy_t policy,
pgp_reader_t signature_input, pgp_reader_t input,
pgp_decryptor_get_public_keys_cb_t get_public_keys,
pgp_decryptor_check_cb_t check,
void *cookie, time_t time);
+/*/
+/// Returns a new standard policy.
+/*/
+pgp_policy_t pgp_standard_policy ();
+
+/*/
+/// Clones the object.
+/*/
+pgp_policy_t pgp_standard_policy_clone (pgp_standard_policy_t);
+
+/*/
+/// Frees this object.
+/*/
+void pgp_standard_policy_free (pgp_standard_policy_t);
+
+/*/
+/// Returns a human readable description of this object suitable for
+/// debugging.
+/*/
+char *pgp_standard_policy_debug (const pgp_standard_policy_t);
+
+/*/
+/// Clones the object.
+/*/
+pgp_policy_t pgp_policy_clone (pgp_policy_t);
+
+/*/
+/// Frees this object.
+/*/
+void pgp_policy_free (pgp_policy_t);
+
+/*/
+/// Returns a human readable description of this object suitable for
+/// debugging.
+/*/
+char *pgp_policy_debug (const pgp_policy_t);
+
#endif
diff --git a/openpgp-ffi/include/sequoia/openpgp/types.h b/openpgp-ffi/include/sequoia/openpgp/types.h
index e9bbc1b7..7a8eb83a 100644
--- a/openpgp-ffi/include/sequoia/openpgp/types.h
+++ b/openpgp-ffi/include/sequoia/openpgp/types.h
@@ -520,4 +520,14 @@ typedef pgp_status_t (*pgp_decryptor_check_cb_t) (void *,
typedef pgp_status_t (*pgp_decryptor_inspect_cb_t) (void *,
pgp_packet_parser_t);
+/*/
+/// An OpenPGP policy.
+/*/
+typedef struct pgp_policy *pgp_policy_t;
+
+/*/
+/// A standard OpenPGP policy.
+/*/
+typedef struct pgp_standard_policy *pgp_standard_policy_t;
+
#endif
diff --git a/openpgp-ffi/src/cert.rs b/openpgp-ffi/src/cert.rs
index 65c56f9f..e2a58c03 100644
--- a/openpgp-ffi/src/cert.rs
+++ b/openpgp-ffi/src/cert.rs
@@ -41,6 +41,7 @@ use super::packet::signature::Signature;
use super::packet_pile::PacketPile;
use super::tsk::TSK;
use super::revocation_status::RevocationStatus;
+use super::policy::Policy;
use crate::Maybe;
use crate::RefRaw;
@@ -168,10 +169,13 @@ fn pgp_cert_primary_key(cert: *const Cert) -> *const Key {
/// If `when` is 0, then returns the Cert's revocation status as of the
/// time of the call.
#[::sequoia_ffi_macros::extern_fn] #[no_mangle] pub extern "C"
-fn pgp_cert_revoked(cert: *const Cert, when: time_t)
+fn pgp_cert_revoked(cert: *const Cert, policy: *const Policy, when: time_t)
-> *mut RevocationStatus<'static>
{
- cert.ref_raw().revoked(maybe_time(when)).move_into_raw()
+ let policy = &**policy.ref_raw();
+ cert.ref_raw()
+ .revoked(policy, maybe_time(when))
+ .move_into_raw()
}
fn int_to_reason_for_revocation(code: c_int) -> ReasonForRevocation {
@@ -203,6 +207,7 @@ fn int_to_reason_for_revocation(code: c_int) -> ReasonForRevocation {
/// pgp_key_t primary_key;
/// pgp_key_pair_t primary_keypair;
/// pgp_signer_t primary_signer;
+/// pgp_policy_t policy = pgp_standard_policy ();
///
/// builder = pgp_cert_builder_new ();
/// pgp_cert_builder_set_cipher_suite (&builder, PGP_CERT_CIPHER_SUITE_CV25519);
@@ -227,11 +232,12 @@ fn int_to_reason_for_revocation(code: c_int) -> ReasonForRevocation {
/// cert = pgp_cert_merge_packets (NULL, cert, &packet, 1);
/// assert (cert);
///
-/// pgp_revocation_status_t rs = pgp_cert_revoked (cert, 0);
+/// pgp_revocation_status_t rs = pgp_cert_revoked (cert, policy, 0);
/// assert (pgp_revocation_status_variant (rs) == PGP_REVOCATION_STATUS_REVOKED);
/// pgp_revocation_status_free (rs);
///
/// pgp_cert_free (cert);
+/// pgp_policy_free (policy);
/// ```
#[::sequoia_ffi_macros::extern_fn] #[no_mangle] pub extern "C"
fn pgp_cert_revoke(errp: Option<&mut *mut crate::error::Error>,
@@ -273,6 +279,7 @@ fn pgp_cert_revoke(errp: Option<&mut *mut crate::error::Error>,
/// pgp_key_t primary_key;
/// pgp_key_pair_t primary_keypair;
/// pgp_signer_t primary_signer;
+/// pgp_policy_t policy = pgp_standard_policy ();
///
/// builder = pgp_cert_builder_new ();
/// pgp_cert_builder_set_cipher_suite (&builder, PGP_CERT_CIPHER_SUITE_CV25519);
@@ -293,11 +300,12 @@ fn pgp_cert_revoke(errp: Option<&mut *mut crate::error::Error>,
/// pgp_signer_free (primary_signer);
/// pgp_key_pair_free (primary_keypair);
///
-/// pgp_revocation_status_t rs = pgp_cert_revoked (cert, 0);
+/// pgp_revocation_status_t rs = pgp_cert_revoked (cert, policy, 0);
/// assert (pgp_revocation_status_variant (rs) == PGP_REVOCATION_STATUS_REVOKED);
/// pgp_revocation_status_free (rs);
///
/// pgp_cert_free (cert);
+/// pgp_policy_free (policy);
/// ```
#[::sequoia_ffi_macros::extern_fn] #[no_mangle] pub extern "C"
fn pgp_cert_revoke_in_place(errp: Option<&mut *mut crate::error::Error>,
@@ -324,9 +332,12 @@ fn pgp_cert_revoke_in_place(errp: Option<&mut *mut crate::error::Error>,
/// If `when` is 0, then the current time is used.
#[::sequoia_ffi_macros::extern_fn] #[no_mangle] pub extern "C"
fn pgp_cert_alive(errp: Option<&mut *mut crate::error::Error>,
- cert: *const Cert, when: time_t) -> Status {
+ cert: *const Cert, policy: *const Policy, when: time_t)
+ -> Status
+{
+ let policy = &**policy.ref_raw();
ffi_make_fry_from_errp!(errp);
- ffi_try_status!(cert.ref_raw().alive(maybe_time(when)))
+ ffi_try_status!(cert.ref_raw().alive(policy, maybe_time(when)))
}
/// Changes the Cert's expiration.
@@ -338,14 +349,17 @@ fn pgp_cert_alive(errp: Option<&mut *mut crate::error::Error>,
#[::sequoia_ffi_macros::extern_fn] #[no_mangle] pub extern "C"
fn pgp_cert_set_expiry(errp: Option<&mut *mut crate::error::Error>,
cert: *mut Cert,
+ policy: *const Policy,
primary_signer: *mut Box<dyn crypto::Signer>,
expiry: u32)
- -> Maybe<Cert> {
+ -> Maybe<Cert>
+{
+ let policy = &**policy.ref_raw();
let cert = cert.move_from_raw();
let signer = ffi_param_ref_mut!(primary_signer);
- cert.set_expiry(signer.as_mut(),
- Some(std::time::Duration::new(expiry as u64, 0)))
+ cert.set_expiry(policy, signer.as_mut(),
+ Some(std::time::Duration::new(expiry as u64, 0)))
.move_into_raw(errp)
}
@@ -359,11 +373,12 @@ fn pgp_cert_is_tsk(cert: *const Cert)
/// Returns an iterator over the Cert's user id bindings.
#[::sequoia_ffi_macros::extern_fn] #[no_mangle] pub extern "C"
-fn pgp_cert_primary_user_id(cert: *const Cert)
+fn pgp_cert_primary_user_id(cert: *const Cert, policy: *const Policy)
-> *mut c_char
{
let cert = cert.ref_raw();
- if let Some(binding) = cert.primary_userid(None) {
+ let policy = &**policy.ref_raw();
+ if let Some(binding) = cert.primary_userid(policy, None) {
ffi_return_string!(binding.userid().value())
} else {
ptr::null_mut()
@@ -392,11 +407,13 @@ pub extern "C" fn pgp_user_id_binding_user_id(
/// Returns a reference to the self-signature, if any.
#[::sequoia_ffi_macros::extern_fn] #[no_mangle]
pub extern "C" fn pgp_user_id_binding_selfsig(
- binding: *const UserIDBinding)
+ binding: *const UserIDBinding,
+ policy: *const Policy)
-> Maybe<Signature>
{
let binding = ffi_param_ref!(binding);
- binding.binding_signature(None).move_into_raw()
+ let policy = &**policy.ref_raw();
+ binding.binding_signature(policy, None).move_into_raw()
}
@@ -505,9 +522,11 @@ pub extern "C" fn pgp_cert_key_iter_unencrypted_secret<'a>(
#[::sequoia_ffi_macros::extern_fn] #[no_mangle]
pub extern "C" fn pgp_cert_key_iter_policy<'a>(
iter_wrapper: *mut KeyIterWrapper<'a>,
+ policy: *const Policy,
when: time_t)
-> *mut ValidKeyIterWrapper<'static>
{
+ let policy = policy.ref_raw();
let iter_wrapper = ffi_param_ref_mut!(iter_wrapper);
if iter_wrapper.next_called {
panic!("Can't change KeyIter filter after iterating.");
@@ -517,7 +536,9 @@ pub extern "C" fn pgp_cert_key_iter_policy<'a>(
let tmp = mem::replace(&mut iter_wrapper.iter, unsafe { mem::zeroed() });
box_raw!(ValidKeyIterWrapper {
- iter: unsafe { std::mem::transmute(tmp.policy(maybe_time(when))) },
+ iter: unsafe {
+ std::mem::transmute(tmp.set_policy(&**policy, maybe_time(when)))
+ },
next_called: false,
})
}
@@ -561,7 +582,8 @@ pub struct ValidKeyIterWrapper<'a> {
/// subkeys that are valid (i.e., have a self-signature at time
/// `when`).
#[::sequoia_ffi_macros::extern_fn] #[no_mangle]
-pub extern "C" fn pgp_cert_valid_key_iter(cert: *const Cert, when: time_t)
+pub extern "C" fn pgp_cert_valid_key_iter(cert: *const Cert,
+ policy: *const Policy, when: time_t)
-> *mut ValidKeyIterWrapper<'static>
{
let cert = cert.ref_raw();
@@ -570,7 +592,7 @@ pub extern "C" fn pgp_cert_valid_key_iter(cert: *const Cert, when: time_t)
next_called: false,
});
- pgp_cert_key_iter_policy(iter, when)
+ pgp_cert_key_iter_policy(iter, policy, when)
}
/// Frees a pgp_cert_key_iter_t.
diff --git a/openpgp-ffi/src/common.rs b/openpgp-ffi/src/common.rs
index c22e5c9e..592c4776 100644
--- a/openpgp-ffi/src/common.rs
+++ b/openpgp-ffi/src/common.rs
@@ -342,3 +342,4 @@ pub mod serialize;
pub mod cert;
pub mod tsk;
pub mod revocation_status;
+pub mod policy;
diff --git a/openpgp-ffi/src/parse/stream.rs b/openpgp-ffi/src/parse/stream.rs
index e0a5e7c4..0fb0bec9 100644
--- a/openpgp-ffi/src/parse/stream.rs
+++ b/openpgp-ffi/src/parse/stream.rs
@@ -50,6 +50,7 @@ use super::super::{
packet::signature::Signature,
packet::key::Key,
parse::PacketParser,
+ policy::Policy,
revocation_status::RevocationStatus,
};
@@ -509,6 +510,7 @@ impl VerificationHelper for VHelper {
/// pgp_reader_t plaintext;
/// uint8_t buf[128];
/// ssize_t nread;
+/// pgp_policy_t policy = pgp_standard_policy ();
///
/// cert = pgp_cert_from_file (NULL, "../openpgp/tests/data/keys/testy.pgp");
/// assert(cert);
@@ -520,7 +522,7 @@ impl VerificationHelper for VHelper {
/// struct verify_cookie cookie = {
/// .key = cert, /* Move. */
/// };
-/// plaintext = pgp_verifier_new (NULL, source,
+/// plaintext = pgp_verifier_new (NULL, policy, source,
/// get_public_keys_cb, check_cb,
/// &cookie, 1554542219);
/// assert (source);
@@ -532,11 +534,13 @@ impl VerificationHelper for VHelper {
///
/// pgp_reader_free (plaintext);
/// pgp_reader_free (source);
+/// pgp_policy_free (policy);
/// return 0;
/// }
/// ```
#[::sequoia_ffi_macros::extern_fn] #[no_mangle] pub extern "C"
fn pgp_verifier_new<'a>(errp: Option<&mut *mut crate::error::Error>,
+ policy: *const Policy,
input: *mut io::Reader,
get_public_keys: GetPublicKeysCallback,
check: CheckCallback,
@@ -544,9 +548,10 @@ fn pgp_verifier_new<'a>(errp: Option<&mut *mut crate::error::Error>,
time: time_t)
-> Maybe<io::Reader>
{
+ let policy = policy.ref_raw().as_ref();
let helper = VHelper::new(get_public_keys, check, cookie);
- Verifier::from_reader(input.ref_mut_raw(), helper, maybe_time(time))
+ Verifier::from_reader(policy, input.ref_mut_raw(), helper, maybe_time(time))
.map(|r| io::ReaderKind::Generic(Box::new(r)))
.move_into_raw(errp)
}
@@ -620,6 +625,7 @@ fn pgp_verifier_new<'a>(errp: Option<&mut *mut crate::error::Error>,
/// pgp_reader_t plaintext;
/// uint8_t buf[128];
/// ssize_t nread;
+/// pgp_policy_t policy = pgp_standard_policy ();
///
/// cert = pgp_cert_from_file (NULL,
/// "../openpgp/tests/data/keys/emmelie-dorothea-dina-samantha-awina-ed25519.pgp");
@@ -637,7 +643,7 @@ fn pgp_verifier_new<'a>(errp: Option<&mut *mut crate::error::Error>,
/// struct verify_cookie cookie = {
/// .key = cert, /* Move. */
/// };
-/// plaintext = pgp_detached_verifier_new (NULL, signature, source,
+/// plaintext = pgp_detached_verifier_new (NULL, policy, signature, source,
/// get_public_keys_cb, check_cb,
/// &cookie, 1554542219);
/// assert (source);
@@ -650,11 +656,13 @@ fn pgp_verifier_new<'a>(errp: Option<&mut *mut crate::error::Error>,
/// pgp_reader_free (plaintext);
/// pgp_reader_free (source);
/// pgp_reader_free (signature);
+/// pgp_policy_free (policy);
/// return 0;
/// }
/// ```
#[::sequoia_ffi_macros::extern_fn] #[no_mangle] pub extern "C"
fn pgp_detached_verifier_new<'a>(errp: Option<&mut *mut crate::error::Error>,
+ policy: *const Policy,
signature_input: *mut io::Reader,
input: *mut io::Reader,
get_public_keys: GetPublicKeysCallback,
@@ -663,9 +671,11 @@ fn pgp_detached_verifier_new<'a>(errp: Option<&mut *mut crate::error::Error>,
time: time_t)
-> Maybe<io::Reader>
{
+ let policy = policy.ref_raw().as_ref();
+
let helper = VHelper::new(get_public_keys, check, cookie);
- DetachedVerifier::from_reader(signature_input.ref_mut_raw(),
+ DetachedVerifier::from_reader(policy, signature_input.ref_mut_raw(),
input.ref_mut_raw(), helper, maybe_time(time))
.map(|r| io::ReaderKind::Generic(Box::new(r)))
.move_into_raw(errp)
@@ -897,6 +907,7 @@ impl DecryptionHelper for DHelper {
/// pgp_reader_t plaintext;
/// uint8_t buf[128];
/// ssize_t nread;
+/// pgp_policy_t policy = pgp_standard_policy ();
///
/// cert = pgp_cert_from_file (
/// NULL, "../openpgp/tests/data/keys/testy-private.pgp");
@@ -910,7 +921,7 @@ impl DecryptionHelper for DHelper {
/// .key = cert,
/// .decrypt_called = 0,
/// };
-/// plaintext = pgp_decryptor_new (NULL, source,
+/// plaintext = pgp_decryptor_new (NULL, policy, source,
/// get_public_keys_cb, decrypt_cb,
/// check_cb, NULL, &cookie, 1554542219);
/// assert (plaintext);
@@ -923,11 +934,13 @@ impl DecryptionHelper for DHelper {
/// pgp_reader_free (plaintext);
/// pgp_reader_free (source);
/// pgp_cert_free (cert);
+/// pgp_policy_free (policy);
/// return 0;
/// }
/// ```
#[::sequoia_ffi_macros::extern_fn] #[no_mangle] pub extern "C"
fn pgp_decryptor_new<'a>(errp: Option<&mut *mut crate::error::Error>,
+ policy: *const Policy,
input: *mut io::Reader,
get_public_keys: GetPublicKeysCallback,
decrypt: DecryptCallback,
@@ -937,10 +950,11 @@ fn pgp_decryptor_new<'a>(errp: Option<&mut *mut crate::error::Error>,
time: time_t)
-> Maybe<io::Reader>
{
+ let policy = policy.ref_raw().as_ref();
let helper = DHelper::new(
get_public_keys, decrypt, check, inspect, cookie);
- Decryptor::from_reader(input.ref_mut_raw(), helper, maybe_time(time))
+ Decryptor::from_reader(policy, input.ref_mut_raw(), helper, maybe_time(time))
.map(|r| io::ReaderKind::Generic(Box::new(r)))
.move_into_raw(errp)
}
diff --git a/openpgp-ffi/src/policy.rs b/openpgp-ffi/src/policy.rs
new file mode 100644
index 00000000..2c00ae52
--- /dev/null
+++ b/openpgp-ffi/src/policy.rs
@@ -0,0 +1,36 @@
+//! Policy objects.
+//!
+//! This module allows the caller to specify low-level policy like
+//! what algorithms are allowed.
+//!
+//! Wraps the policy object functions, see
+//! [`sequoia-openpgp::policy`].
+//!
+//! [`sequoia-openpgp::policy`]: ../../sequoia_openpgp/policy/index.html
+
+extern crate sequoia_openpgp as openpgp;
+
+use crate::MoveIntoRaw;
+
+use self::openpgp::policy;
+
+/// A policy object.
+#[crate::ffi_wrapper_type(
+ prefix = "pgp_",
+ derive = "Clone, Debug")]
+pub struct Policy(Box<policy::Policy>);
+
+/// A StandardPolicy object.
+#[crate::ffi_wrapper_type(
+ prefix = "pgp_",
+ derive = "Clone, Debug")]
+pub struct StandardPolicy(policy::StandardPolicy);
+
+/// Returns a new standard policy.
+#[::sequoia_ffi_macros::extern_fn] #[no_mangle]
+pub extern "C" fn pgp_standard_policy()
+ -> *mut Policy
+{
+ let p : Box<policy::Policy> = Box::new(policy::StandardPolicy::new());
+ p.move_into_raw()
+}