sequoia_openpgp/cert/parser/mod.rs
1use std::io;
2use std::mem;
3use std::vec;
4
5use buffered_reader::BufferedReader;
6use lalrpop_util::ParseError;
7
8use crate::{
9 Error,
10 KeyHandle,
11 packet::Tag,
12 Packet,
13 parse::{
14 Cookie,
15 Parse,
16 PacketParserResult,
17 PacketParser
18 },
19 Result,
20 cert::bundle::ComponentBundle,
21 Cert,
22};
23
24mod low_level;
25use low_level::{
26 Lexer,
27 CertParser as CertLowLevelParser,
28 CertParserError,
29 Token,
30 parse_error_downcast,
31};
32
33const TRACE : bool = false;
34
35/// Whether a packet sequence is a valid keyring.
36///
37/// This is used
38#[derive(Debug)]
39pub(crate) enum KeyringValidity {
40 /// The packet sequence is a valid keyring.
41 Keyring,
42 /// The packet sequence is a valid keyring prefix.
43 KeyringPrefix,
44 /// The packet sequence is definitely not a keyring.
45 Error(anyhow::Error),
46}
47
48#[allow(unused)]
49impl KeyringValidity {
50 /// Returns whether the packet sequence is a valid keyring.
51 ///
52 /// Note: a `KeyringValidator` will only return this after
53 /// `KeyringValidator::finish` has been called.
54 pub fn is_keyring(&self) -> bool {
55 matches!(self, KeyringValidity::Keyring)
56 }
57
58 /// Returns whether the packet sequence is a valid Keyring prefix.
59 ///
60 /// Note: a `KeyringValidator` will only return this before
61 /// `KeyringValidator::finish` has been called.
62 pub fn is_keyring_prefix(&self) -> bool {
63 matches!(self, KeyringValidity::KeyringPrefix)
64 }
65
66 /// Returns whether the packet sequence is definitely not a valid
67 /// keyring.
68 pub fn is_err(&self) -> bool {
69 matches!(self, KeyringValidity::Error(_))
70 }
71}
72
73/// Used to help validate that a packet sequence is a valid keyring.
74#[derive(Debug)]
75pub(crate) struct KeyringValidator {
76 tokens: Vec<Token>,
77 n_keys: usize,
78 n_packets: usize,
79 finished: bool,
80
81 // If we know that the packet sequence is invalid.
82 error: Option<CertParserError>,
83}
84
85impl Default for KeyringValidator {
86 fn default() -> Self {
87 KeyringValidator::new()
88 }
89}
90
91#[allow(unused)]
92impl KeyringValidator {
93 /// Instantiates a new `KeyringValidator`.
94 pub fn new() -> Self {
95 KeyringValidator {
96 tokens: vec![],
97 n_keys: 0,
98 n_packets: 0,
99 finished: false,
100 error: None,
101 }
102 }
103
104 /// Returns whether the packet sequence is a valid keyring.
105 ///
106 /// Note: a `KeyringValidator` will only return this after
107 /// `KeyringValidator::finish` has been called.
108 pub fn is_keyring(&self) -> bool {
109 self.check().is_keyring()
110 }
111
112 /// Returns whether the packet sequence forms a valid keyring
113 /// prefix.
114 ///
115 /// Note: a `KeyringValidator` will only return this before
116 /// `KeyringValidator::finish` has been called.
117 pub fn is_keyring_prefix(&self) -> bool {
118 self.check().is_keyring_prefix()
119 }
120
121 /// Returns whether the packet sequence is definitely not a valid
122 /// keyring.
123 pub fn is_err(&self) -> bool {
124 self.check().is_err()
125 }
126
127 /// Add the token `token` to the token stream.
128 pub fn push_token(&mut self, token: Token) {
129 assert!(!self.finished);
130
131 if self.error.is_some() {
132 return;
133 }
134
135 if let Token::PublicKey(_) | Token::SecretKey(_) = token {
136 self.tokens.clear();
137 self.n_keys += 1;
138 }
139
140 self.n_packets += 1;
141 match (&token, self.tokens.last()) {
142 (Token::Signature(None), Some(Token::Signature(None))) => {
143 // Compress multiple signatures in a row. This is
144 // essential for dealing with flooded keys
145 },
146 _ => self.tokens.push(token),
147 }
148 }
149
150 /// Add a packet of type `tag` to the token stream.
151 pub fn push(&mut self, tag: Tag) {
152 let token = match tag {
153 Tag::PublicKey => Token::PublicKey(None),
154 Tag::SecretKey => Token::SecretKey(None),
155 Tag::PublicSubkey => Token::PublicSubkey(None),
156 Tag::SecretSubkey => Token::SecretSubkey(None),
157 Tag::UserID => Token::UserID(None),
158 Tag::UserAttribute => Token::UserAttribute(None),
159 Tag::Signature => Token::Signature(None),
160 Tag::Trust => Token::Trust(None),
161 Tag::Marker => {
162 // Ignore Marker Packet. RFC4880, section 5.8:
163 //
164 // Such a packet MUST be ignored when received.
165 return;
166 },
167 Tag::Unknown(_) => Token::Unknown(tag, None),
168 Tag::Private(_) => Token::Unknown(tag, None),
169 _ => {
170 // Unknown token.
171 self.error = Some(CertParserError::OpenPGP(
172 Error::MalformedMessage(
173 format!("Invalid Cert: {:?} packet (#{}) not expected",
174 tag, self.n_packets))));
175 self.tokens.clear();
176 return;
177 }
178 };
179
180 self.push_token(token)
181 }
182
183 /// Notes that the entire message has been seen.
184 ///
185 /// This function may only be called once.
186 ///
187 /// Once called, this function will no longer return
188 /// `KeyringValidity::KeyringPrefix`.
189 pub fn finish(&mut self) {
190 assert!(!self.finished);
191 self.finished = true;
192 }
193
194 /// Returns whether the token stream corresponds to a valid
195 /// keyring.
196 ///
197 /// This returns a tri-state: if the packet sequence is a valid
198 /// Keyring, it returns `KeyringValidity::Keyring`, if the packet
199 /// sequence is invalid, then it returns `KeyringValidity::Error`.
200 /// If the packet sequence that has been processed so far is a
201 /// valid prefix, then it returns
202 /// `KeyringValidity::KeyringPrefix`.
203 ///
204 /// Note: if `KeyringValidator::finish()` *hasn't* been called,
205 /// then this function will only ever return either
206 /// `KeyringValidity::KeyringPrefix` or `KeyringValidity::Error`.
207 /// Once `KeyringValidity::finish()` has been called, then it will
208 /// only return either `KeyringValidity::Keyring` or
209 /// `KeyringValidity::Error`.
210 pub fn check(&self) -> KeyringValidity {
211 if let Some(ref err) = self.error {
212 return KeyringValidity::Error((*err).clone().into());
213 }
214
215 let r = CertLowLevelParser::new().parse(
216 Lexer::from_tokens(&self.tokens));
217
218 if self.finished {
219 match r {
220 Ok(_) => KeyringValidity::Keyring,
221 Err(err) =>
222 KeyringValidity::Error(
223 CertParserError::Parser(parse_error_downcast(err)).into()),
224 }
225 } else {
226 match r {
227 Ok(_) => KeyringValidity::KeyringPrefix,
228 Err(ParseError::UnrecognizedEof { .. }) =>
229 KeyringValidity::KeyringPrefix,
230 Err(err) =>
231 KeyringValidity::Error(
232 CertParserError::Parser(parse_error_downcast(err)).into()),
233 }
234 }
235 }
236}
237
238/// Whether a packet sequence is a valid Cert.
239#[derive(Debug)]
240#[allow(unused)]
241pub(crate) enum CertValidity {
242 /// The packet sequence is a valid Cert.
243 Cert,
244 /// The packet sequence is a valid Cert prefix.
245 CertPrefix,
246 /// The packet sequence is definitely not a Cert.
247 Error(anyhow::Error),
248}
249
250#[allow(unused)]
251impl CertValidity {
252 /// Returns whether the packet sequence is a valid Cert.
253 ///
254 /// Note: a `CertValidator` will only return this after
255 /// `CertValidator::finish` has been called.
256 pub fn is_cert(&self) -> bool {
257 matches!(self, CertValidity::Cert)
258 }
259
260 /// Returns whether the packet sequence is a valid Cert prefix.
261 ///
262 /// Note: a `CertValidator` will only return this before
263 /// `CertValidator::finish` has been called.
264 pub fn is_cert_prefix(&self) -> bool {
265 matches!(self, CertValidity::CertPrefix)
266 }
267
268 /// Returns whether the packet sequence is definitely not a valid
269 /// Cert.
270 pub fn is_err(&self) -> bool {
271 matches!(self, CertValidity::Error(_))
272 }
273}
274
275/// Used to help validate that a packet sequence is a valid Cert.
276#[derive(Debug)]
277pub(crate) struct CertValidator(KeyringValidator);
278
279impl Default for CertValidator {
280 fn default() -> Self {
281 CertValidator::new()
282 }
283}
284
285impl CertValidator {
286 /// Instantiates a new `CertValidator`.
287 pub fn new() -> Self {
288 CertValidator(Default::default())
289 }
290
291 /// Add the token `token` to the token stream.
292 #[cfg(test)]
293 pub fn push_token(&mut self, token: Token) {
294 self.0.push_token(token)
295 }
296
297 /// Add a packet of type `tag` to the token stream.
298 pub fn push(&mut self, tag: Tag) {
299 self.0.push(tag)
300 }
301
302 /// Note that the entire message has been seen.
303 ///
304 /// This function may only be called once.
305 ///
306 /// Once called, this function will no longer return
307 /// `CertValidity::CertPrefix`.
308 pub fn finish(&mut self) {
309 self.0.finish()
310 }
311
312 /// Returns whether the token stream corresponds to a valid
313 /// Cert.
314 ///
315 /// This returns a tri-state: if the packet sequence is a valid
316 /// Cert, it returns `CertValidity::Cert`, if the packet sequence
317 /// is invalid, then it returns `CertValidity::Error`. If the
318 /// packet sequence that has been processed so far is a valid
319 /// prefix, then it returns `CertValidity::CertPrefix`.
320 ///
321 /// Note: if `CertValidator::finish()` *hasn't* been called, then
322 /// this function will only ever return either
323 /// `CertValidity::CertPrefix` or `CertValidity::Error`. Once
324 /// `CertValidity::finish()` has been called, then it will only
325 /// return either `CertValidity::Cert` or `CertValidity::Error`.
326 pub fn check(&self) -> CertValidity {
327 if self.0.n_keys > 1 {
328 return CertValidity::Error(Error::MalformedMessage(
329 "More than one key found, this is a keyring".into()).into());
330 }
331
332 match self.0.check() {
333 KeyringValidity::Keyring => CertValidity::Cert,
334 KeyringValidity::KeyringPrefix => CertValidity::CertPrefix,
335 KeyringValidity::Error(e) => CertValidity::Error(e),
336 }
337 }
338}
339
340/// An iterator over a sequence of certificates, i.e., an OpenPGP keyring.
341///
342/// The source of packets is a fallible iterator over [`Packet`]s. In
343/// this way, it is possible to propagate parse errors.
344///
345/// A `CertParser` returns each [`TPK`] or [`TSK`] that it encounters.
346/// Note: if you don't actually need all the certificates, it is
347/// usually faster to use a [`RawCertParser`] and only fully parse and
348/// canonicalize those certificates that are relevant.
349///
350/// [`RawCertParser`]: crate::cert::raw::RawCertParser
351///
352/// A `CertParser`'s behavior can be modeled using a simple state
353/// machine.
354///
355/// In the first and initial state, it looks for the start of a
356/// certificate, a [`Public Key`] packet or a [`Secret Key`] packet.
357/// When it encounters such a packet it buffers it, and transitions to
358/// the second state. Any other packet or an error causes it to emit
359/// an error and stay in the same state. When the source of packets
360/// is exhausted, it enters the `End` state.
361///
362/// In the second state, it looks for packets that belong to a
363/// certificate's body. If it encounters a valid body packet, then it
364/// buffers it and stays in the same state. If it encounters the
365/// start of a certificate, then it emits the buffered certificate,
366/// buffers the packet, and stays in the same state. If it encounters
367/// an invalid packet (e.g., a [`Literal Data`] packet), it emits two
368/// items, the buffered certificate, and an error, and then it
369/// transitions back to the initial state. When the source of packets
370/// is exhausted, it emits the buffered certificate and enters the end
371/// state.
372///
373/// In the end state, it emits `None`.
374///
375/// ```text
376/// Invalid Packet / Error
377/// ,------------------------.
378/// v |
379/// Not a +---------+ +---------+
380/// Start .-> | Looking | -------------> | Looking | <-. Cert
381/// of Cert | | for | Start | for | | Body
382/// Packet | | Start | of Cert | Cert | | Packet
383/// / Error `-- | of Cert | Packet | Body | --'
384/// +---------+ .-> +---------+
385/// | | | |
386/// | `------' |
387/// | Start of Cert Packet |
388/// | |
389/// EOF | +-----+ | EOF
390/// `------> | End | <---------'
391/// +-----+
392/// | ^
393/// `--'
394/// ```
395///
396/// The parser does not recurse into containers, thus when it
397/// encounters a container like a [`Compressed Data`] Packet, it will
398/// return an error even if the container contains a valid
399/// certificate.
400///
401/// The parser considers unknown packets to be valid body packets.
402/// (In a [`Cert`], these show up as [`Unknown`] components.) The
403/// goal is to provide some future compatibility.
404///
405/// [`Packet`]: crate::packet::Packet
406/// [`TPK`]: https://www.rfc-editor.org/rfc/rfc9580.html#section-10.1
407/// [`TSK`]: https://www.rfc-editor.org/rfc/rfc9580.html#section-10.2
408/// [`Public Key`]: super::Packet::PublicKey
409/// [`Secret Key`]: super::Packet::SecretKey
410/// [`Literal Data`]: super::Packet::Literal
411/// [`Compressed Data`]: super::Packet::CompressedData
412/// [`Cert`]: super::Cert
413/// [`Unknown`]: super::Packet::Unknown
414///
415/// # Examples
416///
417/// Print information about all certificates in a keyring:
418///
419/// ```rust
420/// use sequoia_openpgp as openpgp;
421/// # use openpgp::Result;
422/// use openpgp::parse::Parse;
423/// use openpgp::parse::PacketParser;
424/// # use openpgp::serialize::Serialize;
425/// use openpgp::cert::prelude::*;
426///
427/// # fn main() -> Result<()> {
428/// # let (alice, _) =
429/// # CertBuilder::general_purpose(Some("alice@example.org"))
430/// # .generate()?;
431/// # let (bob, _) =
432/// # CertBuilder::general_purpose(Some("bob@example.org"))
433/// # .generate()?;
434/// #
435/// # let mut keyring = Vec::new();
436/// # alice.serialize(&mut keyring)?;
437/// # bob.serialize(&mut keyring)?;
438/// #
439/// # let mut count = 0;
440/// let ppr = PacketParser::from_bytes(&keyring)?;
441/// for certo in CertParser::from(ppr) {
442/// match certo {
443/// Ok(cert) => {
444/// println!("Key: {}", cert.fingerprint());
445/// for ua in cert.userids() {
446/// println!(" User ID: {}", ua.userid());
447/// }
448/// # count += 1;
449/// }
450/// Err(err) => {
451/// eprintln!("Error reading keyring: {}", err);
452/// # unreachable!();
453/// }
454/// }
455/// }
456/// # assert_eq!(count, 2);
457/// # Ok(())
458/// # }
459/// ```
460///
461/// When an invalid packet is encountered, an error is returned and
462/// parsing continues:
463///
464/// ```rust
465/// use sequoia_openpgp as openpgp;
466/// # use openpgp::Result;
467/// # use openpgp::serialize::Serialize;
468/// use openpgp::cert::prelude::*;
469/// use openpgp::packet::prelude::*;
470/// use openpgp::types::DataFormat;
471///
472/// # fn main() -> Result<()> {
473/// let mut lit = Literal::new(DataFormat::Unicode);
474/// lit.set_body(b"test".to_vec());
475///
476/// let (alice, _) =
477/// CertBuilder::general_purpose(Some("alice@example.org"))
478/// .generate()?;
479/// let (bob, _) =
480/// CertBuilder::general_purpose(Some("bob@example.org"))
481/// .generate()?;
482///
483/// let mut packets : Vec<Packet> = Vec::new();
484/// packets.extend(alice.clone().into_packets());
485/// packets.push(lit.clone().into());
486/// packets.push(lit.clone().into());
487/// packets.extend(bob.clone().into_packets());
488///
489/// let r : Vec<Result<Cert>> = CertParser::from(packets).collect();
490/// assert_eq!(r.len(), 4);
491/// assert_eq!(r[0].as_ref().unwrap().fingerprint(), alice.fingerprint());
492/// assert!(r[1].is_err());
493/// assert!(r[2].is_err());
494/// assert_eq!(r[3].as_ref().unwrap().fingerprint(), bob.fingerprint());
495/// # Ok(())
496/// # }
497/// ```
498
499#[derive(Default)]
500pub struct CertParser<'a> {
501 source: Option<Box<dyn Iterator<Item=Result<Packet>> + 'a + Send + Sync>>,
502 packets: Vec<Packet>,
503 queued_error: Option<anyhow::Error>,
504 filter: Vec<Box<dyn Send + Sync + Fn(&Cert, bool) -> bool + 'a>>,
505}
506assert_send_and_sync!(CertParser<'_>);
507
508// When using a `PacketParser`, we never use the `Iter` variant.
509// Nevertheless, we need to provide a concrete type.
510// vec::IntoIter<Packet> is about as good as any other.
511impl<'a> From<PacketParserResult<'a>> for CertParser<'a>
512{
513 /// Initializes a `CertParser` from a `PacketParser`.
514 fn from(ppr: PacketParserResult<'a>) -> Self {
515 use std::io::ErrorKind::UnexpectedEof;
516 let mut parser : Self = Default::default();
517 if let PacketParserResult::Some(pp) = ppr {
518 let mut ppp : Box<Option<PacketParser>> = Box::new(Some(pp));
519 let mut retry_with_reader = Box::new(None);
520 parser.source = Some(
521 Box::new(std::iter::from_fn(move || {
522 tracer!(TRACE, "PacketParserResult::next", 0);
523 if let Some(reader) = retry_with_reader.take() {
524 // Try to find the next (armored) blob.
525 match PacketParser::from_cookie_reader(reader) {
526 Ok(PacketParserResult::Some(pp)) => {
527 // We read at least one packet. Try
528 // to parse the next cert.
529 *ppp = Some(pp);
530 },
531 Ok(PacketParserResult::EOF(_)) =>
532 (), // No dice.
533 Err(err) => {
534 // See if we just reached the end.
535 if let Some(e) = err.downcast_ref::<io::Error>()
536 {
537 if e.kind() == UnexpectedEof {
538 return None;
539 }
540 }
541 return Some(Err(err));
542 },
543 }
544 }
545
546 if let Some(mut pp) = ppp.take() {
547 if let Packet::Unknown(_) = pp.packet {
548 // Buffer unknown packets. This may be a
549 // signature that we don't understand, and
550 // keeping it intact is important.
551 if let Err(e) = pp.buffer_unread_content() {
552 return Some(Err(e));
553 }
554 }
555
556 match pp.next() {
557 Ok((packet, ppr)) => {
558 match ppr {
559 PacketParserResult::Some(pp) =>
560 *ppp = Some(pp),
561 PacketParserResult::EOF(eof) =>
562 *retry_with_reader =
563 Some(eof.into_reader()),
564 }
565 t!("PacketParser::next yielded a {}",
566 packet.tag());
567 Some(Ok(packet))
568 },
569 Err(err) => {
570 t!("PacketParser::next returned an error: {}.",
571 err);
572 Some(Err(err))
573 }
574 }
575 } else {
576 None
577 }
578 })));
579 }
580 parser
581 }
582}
583
584impl<'a> From<Vec<Result<Packet>>> for CertParser<'a> {
585 fn from(p: Vec<Result<Packet>>) -> CertParser<'a> {
586 CertParser::from_iter(p)
587 }
588}
589
590impl<'a> From<Vec<Packet>> for CertParser<'a> {
591 fn from(p: Vec<Packet>) -> CertParser<'a> {
592 CertParser::from_iter(p)
593 }
594}
595
596impl<'a> Parse<'a, CertParser<'a>> for CertParser<'a>
597{
598 /// Initializes a `CertParser` from a `BufferedReader`.
599 fn from_buffered_reader<R>(reader: R) -> Result<CertParser<'a>>
600 where
601 R: BufferedReader<Cookie> + 'a,
602 {
603 Ok(Self::from(PacketParser::from_buffered_reader(reader.into_boxed())?))
604 }
605}
606
607impl<'a> crate::seal::Sealed for CertParser<'a> {}
608
609impl<'a> CertParser<'a> {
610 /// Creates a `CertParser` from a `Result<Packet>` iterator.
611 ///
612 /// Note: because we implement `From<Packet>` for
613 /// `Result<Packet>`, it is possible to pass in an iterator over
614 /// `Packet`s.
615 ///
616 /// # Examples
617 ///
618 /// From a `Vec<Packet>`:
619 ///
620 /// ```rust
621 /// use sequoia_openpgp as openpgp;
622 /// # use openpgp::Result;
623 /// # use openpgp::PacketPile;
624 /// # use openpgp::parse::Parse;
625 /// # use openpgp::serialize::Serialize;
626 /// use openpgp::cert::prelude::*;
627 /// use openpgp::packet::prelude::*;
628 ///
629 /// # fn main() -> Result<()> {
630 /// # let (alice, _) =
631 /// # CertBuilder::general_purpose(Some("alice@example.org"))
632 /// # .generate()?;
633 /// # let (bob, _) =
634 /// # CertBuilder::general_purpose(Some("bob@example.org"))
635 /// # .generate()?;
636 /// #
637 /// # let mut keyring = Vec::new();
638 /// # alice.serialize(&mut keyring)?;
639 /// # bob.serialize(&mut keyring)?;
640 /// #
641 /// # let mut count = 0;
642 /// # let pp = PacketPile::from_bytes(&keyring)?;
643 /// # let packets : Vec<Packet> = pp.into();
644 /// for certo in CertParser::from_iter(packets) {
645 /// match certo {
646 /// Ok(cert) => {
647 /// println!("Key: {}", cert.fingerprint());
648 /// for ua in cert.userids() {
649 /// println!(" User ID: {}", ua.userid());
650 /// }
651 /// # count += 1;
652 /// }
653 /// Err(err) => {
654 /// eprintln!("Error reading keyring: {}", err);
655 /// # unreachable!();
656 /// }
657 /// }
658 /// }
659 /// # assert_eq!(count, 2);
660 /// # Ok(())
661 /// # }
662 /// ```
663 pub fn from_iter<I, J>(iter: I) -> Self
664 where I: 'a + IntoIterator<Item=J>,
665 J: 'a + Into<Result<Packet>>,
666 <I as IntoIterator>::IntoIter: Send + Sync,
667 {
668 Self {
669 source: Some(Box::new(iter.into_iter().map(Into::into))),
670 ..Default::default()
671 }
672 }
673
674 /// Filters the Certs prior to validation.
675 ///
676 /// By default, the `CertParser` only returns valdiated [`Cert`]s.
677 /// Checking that a certificate's self-signatures are valid,
678 /// however, is computationally expensive, and not always
679 /// necessary. For example, when looking for a small number of
680 /// certificates in a large keyring, most certificates can be
681 /// immediately discarded. That is, it is more efficient to
682 /// filter, validate, and double check, than to validate and
683 /// filter. (It is necessary to double-check, because the check
684 /// might have been on an invalid part. For example, if searching
685 /// for a key with a particular Key ID, a matching key might not
686 /// have any self signatures.)
687 ///
688 /// If the `CertParser` gave out unvalidated `Cert`s, and provided
689 /// an interface to validate them, then the caller could implement
690 /// this check-validate-double-check pattern. Giving out
691 /// unvalidated `Cert`s, however, is dangerous: inevitably, a
692 /// `Cert` will be used without having been validated in a context
693 /// where it should have been.
694 ///
695 /// This function avoids this class of bugs while still providing
696 /// a mechanism to filter `Cert`s prior to validation: the caller
697 /// provides a callback that is invoked on the *unvalidated*
698 /// `Cert`. If the callback returns `true`, then the parser
699 /// validates the `Cert`, and invokes the callback *a second time*
700 /// to make sure the `Cert` is really wanted. If the callback
701 /// returns false, then the `Cert` is skipped.
702 ///
703 /// Note: calling this function multiple times on a single
704 /// `CertParser` will not replace the existing filter, but install
705 /// multiple filters.
706 ///
707 /// [`Cert`]: super::Cert
708 ///
709 /// # Examples
710 ///
711 /// ```rust
712 /// use sequoia_openpgp as openpgp;
713 /// # use openpgp::Result;
714 /// # use openpgp::parse::{Parse, PacketParser};
715 /// use openpgp::cert::prelude::*;
716 ///
717 /// # fn main() -> Result<()> {
718 /// # let ppr = PacketParser::from_bytes(b"")?;
719 /// # let some_keyid = "C2B819056C652598".parse()?;
720 /// for certr in CertParser::from(ppr)
721 /// .unvalidated_cert_filter(|cert, _| {
722 /// for component in cert.keys() {
723 /// if component.key().keyid() == some_keyid {
724 /// return true;
725 /// }
726 /// }
727 /// false
728 /// })
729 /// {
730 /// match certr {
731 /// Ok(cert) => {
732 /// // The Cert contains the subkey.
733 /// }
734 /// Err(err) => {
735 /// eprintln!("Error reading keyring: {}", err);
736 /// }
737 /// }
738 /// }
739 /// # Ok(())
740 /// # }
741 /// ```
742 pub fn unvalidated_cert_filter<F>(mut self, filter: F) -> Self
743 where F: 'a + Send + Sync + Fn(&Cert, bool) -> bool
744 {
745 self.filter.push(Box::new(filter));
746 self
747 }
748
749 // Parses the next packet in the packet stream.
750 //
751 // If we complete parsing a Cert, returns the Cert. Otherwise,
752 // returns None.
753 fn parse(&mut self, p: Packet) -> Result<Option<Cert>> {
754 tracer!(TRACE, "CertParser::parse", 0);
755 match p {
756 Packet::Marker(_) => {
757 // Ignore Marker Packet. RFC4880, section 5.8:
758 //
759 // Such a packet MUST be ignored when received.
760 return Ok(None);
761 },
762 Packet::Padding(_) => {
763 // "[Padding packets] MUST be ignored when received.",
764 // section 5.14 of RFC 9580.
765 return Ok(None);
766 },
767 p if Cert::valid_packet(&p).is_err()
768 && ! p.tag().is_critical() =>
769 {
770 // "Unknown, non-critical packets MUST be ignored when
771 // received.", section 4.3 of RFC 9580.
772 return Ok(None);
773 },
774 _ => {},
775 }
776
777 if !self.packets.is_empty() {
778 if self.packets.len() == 1 {
779 if let Err(err) = Cert::valid_start(&self.packets[0]) {
780 t!("{}", err);
781 return self.cert(Some(p));
782 }
783 }
784
785 if Cert::valid_start(&p).is_ok() {
786 t!("Encountered the start of a new certificate ({}), \
787 finishing buffered certificate", p.tag());
788 return self.cert(Some(p));
789 } else if let Err(err) = Cert::valid_packet(&p) {
790 t!("Encountered an invalid packet ({}), \
791 finishing buffered certificate: {}",
792 p.tag(), err);
793 return self.cert(Some(p));
794 }
795 }
796
797 self.packets.push(p);
798 Ok(None)
799 }
800
801 // Resets the parser so that it starts parsing a new cert.
802 //
803 // Returns the old state. Note: the packet iterator is preserved.
804 fn reset(&mut self) -> Self {
805 // We need to preserve `source` and `filter`.
806 let mut orig = mem::take(self);
807 self.source = orig.source.take();
808 mem::swap(&mut self.filter, &mut orig.filter);
809 orig
810 }
811
812 // Finalizes the current Cert and returns it. Sets the parser up to
813 // begin parsing the next Cert.
814 //
815 // `pk` is buffered for the next certificate.
816 fn cert(&mut self, pk: Option<Packet>) -> Result<Option<Cert>> {
817 tracer!(TRACE, "CertParser::cert", 0);
818 let orig = self.reset();
819
820 if let Some(pk) = pk {
821 self.packets.push(pk);
822 }
823
824 let n_packets = orig.packets.len();
825 t!("Finalizing certificate with {} packets", n_packets);
826
827 // Convert to tokens, but preserve packets if it fails.
828 let mut failed = false;
829 let mut packets: Vec<Packet> = Vec::with_capacity(0);
830 let mut tokens: Vec<Token> = Vec::with_capacity(n_packets);
831 for p in orig.packets {
832 if failed {
833 // Just stash the packet.
834 packets.push(p);
835 } else {
836 match p.try_into() {
837 Ok(t) => tokens.push(t),
838 Err(p) => {
839 // Conversion failed. Revert the whole process.
840 packets.reserve(n_packets);
841 for t in tokens.drain(..) {
842 packets.push({
843 let p: Option<Packet> = t.into();
844 p.expect("token created with packet")
845 });
846 }
847 packets.push(p);
848 failed = true;
849 },
850 }
851 }
852 }
853
854 if failed {
855 // There was at least one packet that doesn't belong in a
856 // Cert. Fail now.
857 let err = Error::UnsupportedCert(
858 "Packet sequence includes non-Cert packets.".into(),
859 packets);
860 t!("Invalid certificate: {}", err);
861 return Err(err.into());
862 }
863 t!("{} tokens: {:?}", tokens.len(), tokens);
864
865 let certo = match CertLowLevelParser::new()
866 .parse(Lexer::from_tokens(&tokens))
867 {
868 Ok(certo) => certo,
869 Err(err) => {
870 let err = low_level::parse_error_to_openpgp_error(
871 low_level::parse_error_downcast(err));
872 t!("Low level parser: {}", err);
873 return Err(err.into());
874 }
875 }.and_then(|cert| {
876 for filter in &self.filter {
877 if !filter(&cert, true) {
878 t!("Rejected by filter");
879 return None;
880 }
881 }
882
883 Some(cert)
884 }).and_then(|mut cert| {
885 let primary_fp: KeyHandle = cert.key_handle();
886
887 // The parser puts all the signatures on the
888 // certifications field. Split them now.
889
890 split_sigs(&primary_fp, &mut cert.primary);
891
892 for b in cert.userids.iter_mut() {
893 split_sigs(&primary_fp, b);
894 }
895 for b in cert.user_attributes.iter_mut() {
896 split_sigs(&primary_fp, b);
897 }
898 for b in cert.subkeys.iter_mut() {
899 split_sigs(&primary_fp, b);
900 }
901
902 let cert = cert.canonicalize();
903
904 // Make sure it is still wanted.
905 for filter in &self.filter {
906 if !filter(&cert, true) {
907 t!("Rejected by filter");
908 return None;
909 }
910 }
911
912 Some(cert)
913 });
914
915 t!("Returning {:?}, constructed from {} packets",
916 certo.as_ref().map(|c| c.fingerprint()),
917 n_packets);
918
919 Ok(certo)
920 }
921}
922
923/// Splits the signatures in b.certifications into the correct
924/// vectors.
925fn split_sigs<C>(primary: &KeyHandle, b: &mut ComponentBundle<C>)
926{
927 debug_assert!(b.self_signatures.is_empty());
928 debug_assert!(b.self_revocations.is_empty());
929 debug_assert!(b.other_revocations.is_empty());
930
931 for sig in mem::replace(&mut b.certifications, Vec::with_capacity(0)) {
932 let typ = sig.typ();
933
934 let issuers = sig.get_issuers();
935 let is_selfsig =
936 issuers.is_empty()
937 || issuers.iter().any(|kh| kh.aliases(primary));
938
939 use crate::SignatureType::*;
940 if typ == CertificationApproval {
941 b.attestations.push(sig);
942 } else if typ == KeyRevocation
943 || typ == SubkeyRevocation
944 || typ == CertificationRevocation
945 {
946 if is_selfsig {
947 b.self_revocations.push(sig);
948 } else {
949 b.other_revocations.push(sig);
950 }
951 } else if is_selfsig {
952 b.self_signatures.push(sig);
953 } else {
954 b.certifications.push(sig);
955 }
956 }
957}
958
959impl<'a> Iterator for CertParser<'a> {
960 type Item = Result<Cert>;
961
962 fn next(&mut self) -> Option<Self::Item> {
963 tracer!(TRACE, "CertParser::next", 0);
964 if let Some(err) = self.queued_error.take() {
965 t!("Returning queued error: {}", err);
966 return Some(Err(err));
967 }
968
969 loop {
970 match self.source.take() {
971 None => {
972 t!("EOF.");
973
974 if self.packets.is_empty() {
975 return None;
976 }
977 match self.cert(None) {
978 Ok(Some(cert)) => return Some(Ok(cert)),
979 Ok(None) => return None,
980 Err(err) => return Some(Err(err)),
981 }
982 },
983 Some(mut iter) => {
984 let r = match iter.next() {
985 Some(Ok(packet)) => {
986 t!("Got packet #{} ({}{})",
987 self.packets.len(), packet.tag(),
988 match &packet {
989 Packet::PublicKey(k) =>
990 Some(k.fingerprint().to_hex()),
991 Packet::SecretKey(k) =>
992 Some(k.fingerprint().to_hex()),
993 Packet::PublicSubkey(k) =>
994 Some(k.fingerprint().to_hex()),
995 Packet::SecretSubkey(k) =>
996 Some(k.fingerprint().to_hex()),
997 Packet::UserID(u) =>
998 Some(String::from_utf8_lossy(u.value())
999 .into()),
1000 Packet::Signature(s) =>
1001 Some(format!("{}", s.typ())),
1002 _ => None,
1003 }
1004 .map(|s| format!(", {}", s))
1005 .unwrap_or_else(|| "".into())
1006 );
1007 self.source = Some(iter);
1008 self.parse(packet)
1009 }
1010 Some(Err(err)) => {
1011 self.source = Some(iter);
1012
1013 t!("Error getting packet: {}", err);
1014
1015 if ! self.packets.is_empty() {
1016 // Returned any queued certificate first.
1017 match self.cert(None) {
1018 Ok(Some(cert)) => {
1019 self.queued_error = Some(err);
1020 return Some(Ok(cert));
1021 }
1022 Ok(None) => {
1023 return Some(Err(err));
1024 }
1025 Err(err2) => {
1026 // Return the first error,
1027 // queue the second error.
1028 self.queued_error = Some(err2);
1029 return Some(Err(err));
1030 }
1031 }
1032 } else {
1033 return Some(Err(err));
1034 }
1035 }
1036 None if self.packets.is_empty() => {
1037 t!("Packet iterator was empty");
1038 Ok(None)
1039 }
1040 None => {
1041 t!("Packet iterator exhausted after {} packets",
1042 self.packets.len());
1043 self.cert(None)
1044 }
1045 };
1046
1047 match r {
1048 Ok(Some(cert)) => {
1049 t!(" => {}", cert.fingerprint());
1050 return Some(Ok(cert));
1051 }
1052 Ok(None) => (),
1053 Err(err) => return Some(Err(err)),
1054 }
1055 },
1056 }
1057 }
1058 }
1059}
1060
1061#[cfg(test)]
1062mod test {
1063 use super::*;
1064
1065 use std::collections::HashSet;
1066 use std::iter::FromIterator;
1067
1068 use crate::Fingerprint;
1069 use crate::cert::prelude::*;
1070 use crate::packet::prelude::*;
1071 use crate::parse::RECOVERY_THRESHOLD;
1072 use crate::serialize::Serialize;
1073 use crate::types::DataFormat;
1074
1075 use crate::tests;
1076
1077 #[test]
1078 fn push_tokens() {
1079 use crate::cert::parser::low_level::lexer::{Token, Lexer};
1080 use crate::cert::parser::low_level::lexer::Token::*;
1081 use crate::cert::parser::low_level::CertParser;
1082
1083 struct TestVector<'a> {
1084 s: &'a [Token],
1085 result: bool,
1086 }
1087
1088 let test_vectors = [
1089 TestVector {
1090 s: &[ PublicKey(None) ],
1091 result: true,
1092 },
1093 TestVector {
1094 s: &[ SecretKey(None) ],
1095 result: true,
1096 },
1097 TestVector {
1098 s: &[ PublicKey(None), Signature(None) ],
1099 result: true,
1100 },
1101 TestVector {
1102 s: &[ PublicKey(None), Signature(None), Signature(None) ],
1103 result: true,
1104 },
1105
1106 TestVector {
1107 s: &[ PublicKey(None), Signature(None), Signature(None),
1108 UserID(None) ],
1109 result: true,
1110 },
1111 TestVector {
1112 s: &[ PublicKey(None), Signature(None), Signature(None),
1113 UserID(None), Signature(None) ],
1114 result: true,
1115 },
1116 TestVector {
1117 s: &[ PublicKey(None), Signature(None), Signature(None),
1118 UserAttribute(None) ],
1119 result: true,
1120 },
1121 TestVector {
1122 s: &[ PublicKey(None), Signature(None), Signature(None),
1123 UserAttribute(None), Signature(None) ],
1124 result: true,
1125 },
1126 TestVector {
1127 s: &[ PublicKey(None), Signature(None), Signature(None),
1128 PublicSubkey(None) ],
1129 result: true,
1130 },
1131 TestVector {
1132 s: &[ PublicKey(None), Signature(None), Signature(None),
1133 PublicSubkey(None), Signature(None) ],
1134 result: true,
1135 },
1136 TestVector {
1137 s: &[ PublicKey(None), Signature(None), Signature(None),
1138 SecretSubkey(None) ],
1139 result: true,
1140 },
1141 TestVector {
1142 s: &[ PublicKey(None), Signature(None), Signature(None),
1143 SecretSubkey(None), Signature(None) ],
1144 result: true,
1145 },
1146
1147 TestVector {
1148 s: &[ PublicKey(None), Signature(None), Signature(None),
1149 SecretSubkey(None), Signature(None),
1150 SecretSubkey(None), Signature(None),
1151 SecretSubkey(None), Signature(None),
1152 SecretSubkey(None), Signature(None),
1153 SecretSubkey(None), Signature(None),
1154 UserID(None), Signature(None),
1155 Signature(None), Signature(None),
1156 SecretSubkey(None), Signature(None),
1157 UserAttribute(None), Signature(None),
1158 Signature(None), Signature(None),
1159 SecretSubkey(None), Signature(None),
1160 UserID(None),
1161 UserAttribute(None), Signature(None),
1162 Signature(None), Signature(None),
1163 ],
1164 result: true,
1165 },
1166
1167 TestVector {
1168 s: &[ PublicKey(None), Signature(None), Signature(None),
1169 PublicKey(None), Signature(None), Signature(None),
1170 ],
1171 result: false,
1172 },
1173 TestVector {
1174 s: &[ PublicKey(None), Signature(None), Signature(None),
1175 SecretKey(None), Signature(None), Signature(None),
1176 ],
1177 result: false,
1178 },
1179 TestVector {
1180 s: &[ SecretKey(None), Signature(None), Signature(None),
1181 SecretKey(None), Signature(None), Signature(None),
1182 ],
1183 result: false,
1184 },
1185 TestVector {
1186 s: &[ SecretKey(None), Signature(None), Signature(None),
1187 PublicKey(None), Signature(None), Signature(None),
1188 ],
1189 result: false,
1190 },
1191 TestVector {
1192 s: &[ SecretSubkey(None), Signature(None), Signature(None),
1193 PublicSubkey(None), Signature(None), Signature(None),
1194 ],
1195 result: false,
1196 },
1197 TestVector {
1198 s: &[ SecretKey(None), Signature(None),
1199 UserID(None), Signature(None),
1200 SecretSubkey(None), Signature(None),
1201 SecretSubkey(None), Signature(None),
1202 Unknown(Tag::Private(61), None),
1203 ],
1204 result: true,
1205 },
1206 ];
1207
1208 for v in &test_vectors {
1209 if v.result {
1210 let mut l = CertValidator::new();
1211 for token in v.s.into_iter() {
1212 l.push_token((*token).clone());
1213 assert_match!(CertValidity::CertPrefix = l.check());
1214 }
1215
1216 l.finish();
1217 assert_match!(CertValidity::Cert = l.check());
1218 }
1219
1220 match CertParser::new().parse(Lexer::from_tokens(v.s)) {
1221 Ok(r) => assert!(v.result, "Parsing: {:?} => {:?}", v.s, r),
1222 Err(e) => assert!(! v.result, "Parsing: {:?} => {:?}", v.s, e),
1223 }
1224 }
1225 }
1226
1227 #[test]
1228 fn push_tags() {
1229 use Tag::*;
1230
1231 struct TestVector<'a> {
1232 s: &'a [Tag],
1233 result: bool,
1234 }
1235
1236 let test_vectors = [
1237 TestVector {
1238 s: &[ PublicKey ],
1239 result: true,
1240 },
1241 TestVector {
1242 s: &[ SecretKey, Signature,
1243 UserID, Signature,
1244 SecretSubkey, Signature,
1245 SecretSubkey, Signature,
1246 Tag::Private(61),
1247 ],
1248 result: true,
1249 },
1250 TestVector {
1251 s: &[ SecretKey, Signature,
1252 UserID, Signature,
1253 SecretSubkey, Signature,
1254 SecretSubkey, Signature,
1255 Tag::Unknown(61),
1256 ],
1257 result: true,
1258 },
1259 TestVector {
1260 s: &[ SecretKey, Signature,
1261 UserID, Signature,
1262 SecretSubkey, Signature,
1263 SecretSubkey, Signature,
1264 Tag::Unknown(61),
1265 SecretKey, Signature,
1266 UserID, Signature,
1267 SecretSubkey, Signature,
1268 SecretSubkey, Signature,
1269 ],
1270 // This is a keyring, not a cert.
1271 result: false,
1272 },
1273 ];
1274
1275 for v in &test_vectors {
1276 if v.result {
1277 let mut l = CertValidator::new();
1278 for &tag in v.s.into_iter() {
1279 l.push(tag.clone());
1280 assert_match!(CertValidity::CertPrefix = l.check());
1281 }
1282
1283 l.finish();
1284 assert_match!(CertValidity::Cert = l.check());
1285 }
1286 }
1287 }
1288
1289 #[test]
1290 fn marker_packet_ignored() {
1291 use crate::serialize::Serialize;
1292 let mut testy_with_marker = Vec::new();
1293 Packet::Marker(Default::default())
1294 .serialize(&mut testy_with_marker).unwrap();
1295 testy_with_marker.extend_from_slice(crate::tests::key("testy.pgp"));
1296 CertParser::from(
1297 PacketParser::from_bytes(&testy_with_marker).unwrap())
1298 .next().unwrap().unwrap();
1299
1300 let mut testy_with_marker = Vec::new();
1301 testy_with_marker.extend_from_slice(crate::tests::key("testy.pgp"));
1302 Packet::Marker(Default::default())
1303 .serialize(&mut testy_with_marker).unwrap();
1304 CertParser::from(
1305 PacketParser::from_bytes(&testy_with_marker).unwrap())
1306 .next().unwrap().unwrap();
1307 }
1308
1309 #[test]
1310 fn invalid_packets() -> Result<()> {
1311 tracer!(TRACE, "invalid_packets", 0);
1312
1313 fn cert_cmp(a: &Result<Cert>, b: &Vec<Packet>)
1314 {
1315 let a =
1316 a.as_ref().unwrap().clone().into_packets().collect::<Vec<_>>();
1317
1318 for (i, (a, b)) in a.iter().zip(b).enumerate() {
1319 if a != b {
1320 panic!("Differ at element #{}:\n {:?}\n {:?}",
1321 i, a, b);
1322 }
1323 }
1324 if a.len() != b.len() {
1325 panic!("Different lengths (common prefix identical): {} vs. {}",
1326 a.len(), b.len());
1327 }
1328 }
1329
1330 let (cert, _) =
1331 CertBuilder::general_purpose(Some("alice@example.org"))
1332 .generate()?;
1333 let cert = cert.into_packets().collect::<Vec<_>>();
1334
1335 // A userid packet.
1336 let userid : Packet = cert.clone()
1337 .into_iter()
1338 .filter(|p| p.tag() == Tag::UserID)
1339 .next()
1340 .unwrap();
1341
1342 // An unknown packet.
1343 let tag = Tag::Private(61);
1344 let unknown : Packet
1345 = Unknown::new(tag, Error::UnsupportedPacketType(tag).into())
1346 .into();
1347
1348 // A literal packet. (This is a valid OpenPGP Message.)
1349 let mut lit = Literal::new(DataFormat::Unicode);
1350 lit.set_body(b"test".to_vec());
1351 let lit = Packet::from(lit);
1352
1353 // A compressed data packet containing a literal data packet.
1354 // (This is a valid OpenPGP Message.)
1355 let cd = {
1356 use crate::types::CompressionAlgorithm;
1357 use crate::packet;
1358 use crate::PacketPile;
1359 use crate::serialize::Serialize;
1360 use crate::parse::Parse;
1361
1362 let mut cd = CompressedData::new(
1363 CompressionAlgorithm::Uncompressed);
1364 let mut body = Vec::new();
1365 lit.serialize(&mut body)?;
1366 cd.set_body(packet::Body::Processed(body));
1367 let cd = Packet::from(cd);
1368
1369 // Make sure we created the message correctly: serialize,
1370 // parse it, and then check its form.
1371 let mut bytes = Vec::new();
1372 cd.serialize(&mut bytes)?;
1373
1374 let pp = PacketPile::from_bytes(&bytes[..])?;
1375
1376 assert_eq!(pp.descendants().count(), 2);
1377 assert_eq!(pp.path_ref(&[ 0 ]).unwrap().tag(),
1378 packet::Tag::CompressedData);
1379 assert_eq!(pp.path_ref(&[ 0, 0 ]), Some(&lit));
1380
1381 cd
1382 };
1383
1384 t!("A single cert.");
1385 let cp = CertParser::from_iter(cert.clone()).collect::<Vec<_>>();
1386 assert_eq!(cp.len(), 1);
1387 cert_cmp(&cp[0], &cert);
1388
1389 t!("Two certificates.");
1390 let cp = CertParser::from_iter(
1391 cert.clone().into_iter().chain(cert.clone())).collect::<Vec<_>>();
1392 assert_eq!(cp.len(), 2);
1393 cert_cmp(&cp[0], &cert);
1394 cert_cmp(&cp[1], &cert);
1395
1396 fn interleave(cert: &Vec<Packet>, p: &Packet) {
1397 t!("A certificate, a {}.", p.tag());
1398 let cp = CertParser::from_iter(
1399 cert.clone().into_iter()
1400 .chain(p.clone()))
1401 .collect::<Vec<_>>();
1402 assert_eq!(cp.len(), 2);
1403 cert_cmp(&cp[0], cert);
1404 assert!(cp[1].is_err());
1405
1406 t!("A certificate, two {}.", p.tag());
1407 let cp = CertParser::from_iter(
1408 cert.clone().into_iter()
1409 .chain(p.clone())
1410 .chain(p.clone()))
1411 .collect::<Vec<_>>();
1412 assert_eq!(cp.len(), 3);
1413 cert_cmp(&cp[0], cert);
1414 assert!(cp[1].is_err());
1415 assert!(cp[2].is_err());
1416
1417 t!("A {}, a certificate.", p.tag());
1418 let cp = CertParser::from_iter(
1419 p.clone().into_iter()
1420 .chain(cert.clone()))
1421 .collect::<Vec<_>>();
1422 assert_eq!(cp.len(), 2);
1423 assert!(cp[0].is_err());
1424 cert_cmp(&cp[1], cert);
1425
1426 t!("Two {}, a certificate.", p.tag());
1427 let cp = CertParser::from_iter(
1428 p.clone().into_iter()
1429 .chain(p.clone())
1430 .chain(cert.clone()))
1431 .collect::<Vec<_>>();
1432 assert_eq!(cp.len(), 3);
1433 assert!(cp[0].is_err());
1434 assert!(cp[1].is_err());
1435 cert_cmp(&cp[2], cert);
1436
1437 t!("Two {}, a certificate, two {}.", p.tag(), p.tag());
1438 let cp = CertParser::from_iter(
1439 p.clone().into_iter()
1440 .chain(p.clone())
1441 .chain(cert.clone())
1442 .chain(p.clone())
1443 .chain(p.clone()))
1444 .collect::<Vec<_>>();
1445 assert_eq!(cp.len(), 5);
1446 assert!(cp[0].is_err());
1447 assert!(cp[1].is_err());
1448 cert_cmp(&cp[2], cert);
1449 assert!(cp[3].is_err());
1450 assert!(cp[4].is_err());
1451
1452 t!("Two {}, two certificates, two {}, a certificate.");
1453 let cp = CertParser::from_iter(
1454 p.clone().into_iter()
1455 .chain(p.clone())
1456 .chain(cert.clone())
1457 .chain(cert.clone())
1458 .chain(p.clone())
1459 .chain(p.clone())
1460 .chain(cert.clone()))
1461 .collect::<Vec<_>>();
1462 assert_eq!(cp.len(), 7);
1463 assert!(cp[0].is_err());
1464 assert!(cp[1].is_err());
1465 cert_cmp(&cp[2], cert);
1466 cert_cmp(&cp[3], cert);
1467 assert!(cp[4].is_err());
1468 assert!(cp[5].is_err());
1469 cert_cmp(&cp[6], cert);
1470 }
1471
1472 interleave(&cert, &lit);
1473 // The certificate parser shouldn't recurse into containers.
1474 // So, the compressed data packets should show up as a single
1475 // error.
1476 interleave(&cert, &cd);
1477
1478
1479 // The certificate parser should treat unknown packets as
1480 // valid certificate components.
1481 let mut cert_plus = cert.clone();
1482 cert_plus.push(unknown.clone());
1483
1484 t!("A certificate, an unknown.");
1485 let cp = CertParser::from_iter(
1486 cert.clone().into_iter()
1487 .chain(unknown.clone()))
1488 .collect::<Vec<_>>();
1489 assert_eq!(cp.len(), 1);
1490 cert_cmp(&cp[0], &cert_plus);
1491
1492 t!("An unknown, a certificate.");
1493 let cp = CertParser::from_iter(
1494 unknown.clone().into_iter()
1495 .chain(cert.clone()))
1496 .collect::<Vec<_>>();
1497 assert_eq!(cp.len(), 2);
1498 assert!(cp[0].is_err());
1499 cert_cmp(&cp[1], &cert);
1500
1501 t!("A certificate, two unknowns.");
1502 let cp = CertParser::from_iter(
1503 cert.clone().into_iter()
1504 .chain(unknown.clone())
1505 .chain(unknown.clone()))
1506 .collect::<Vec<_>>();
1507 assert_eq!(cp.len(), 1);
1508 cert_cmp(&cp[0], &cert_plus);
1509
1510 t!("A certificate, an unknown, a certificate.");
1511 let cp = CertParser::from_iter(
1512 cert.clone().into_iter()
1513 .chain(unknown.clone())
1514 .chain(cert.clone()))
1515 .collect::<Vec<_>>();
1516 assert_eq!(cp.len(), 2);
1517 cert_cmp(&cp[0], &cert_plus);
1518 cert_cmp(&cp[1], &cert);
1519
1520
1521 t!("A Literal, two User IDs");
1522 let cp = CertParser::from_iter(
1523 lit.clone().into_iter()
1524 .chain(userid.clone())
1525 .chain(userid.clone()))
1526 .collect::<Vec<_>>();
1527 assert_eq!(cp.len(), 3);
1528 assert!(cp[0].is_err());
1529 assert!(cp[1].is_err());
1530 assert!(cp[2].is_err());
1531
1532 t!("A User ID, a certificate");
1533 let cp = CertParser::from_iter(
1534 userid.clone().into_iter()
1535 .chain(cert.clone()))
1536 .collect::<Vec<_>>();
1537 assert_eq!(cp.len(), 2);
1538 assert!(cp[0].is_err());
1539 cert_cmp(&cp[1], &cert);
1540
1541 t!("Two User IDs, a certificate");
1542 let cp = CertParser::from_iter(
1543 userid.clone().into_iter()
1544 .chain(userid.clone())
1545 .chain(cert.clone()))
1546 .collect::<Vec<_>>();
1547 assert_eq!(cp.len(), 3);
1548 assert!(cp[0].is_err());
1549 assert!(cp[1].is_err());
1550 cert_cmp(&cp[2], &cert);
1551
1552 Ok(())
1553 }
1554
1555 #[test]
1556 fn concatenated_armored_certs() -> Result<()> {
1557 let mut keyring = Vec::new();
1558 keyring.extend_from_slice(b"some\ntext\n");
1559 keyring.extend_from_slice(crate::tests::key("testy.asc"));
1560 keyring.extend_from_slice(crate::tests::key("testy.asc"));
1561 keyring.extend_from_slice(b"some\ntext\n");
1562 keyring.extend_from_slice(crate::tests::key("testy.asc"));
1563 keyring.extend_from_slice(b"some\ntext\n");
1564 let certs = CertParser::from_bytes(&keyring)?.collect::<Vec<_>>();
1565 assert_eq!(certs.len(), 3);
1566 assert!(certs.iter().all(|c| c.is_ok()));
1567 Ok(())
1568 }
1569
1570 fn parse_test(n: usize, literal: bool, bad: usize) -> Result<()> {
1571 tracer!(TRACE, "t", 0);
1572
1573 // Parses keyrings with different numbers of keys and
1574 // different errors.
1575
1576 // n: number of keys
1577 // literal: whether to interleave literal packets.
1578 // bad: whether to insert invalid data (NUL bytes where
1579 // the start of a certificate is expected).
1580 let nulls = vec![ 0; bad ];
1581
1582 t!("n: {}, literals: {}, bad data: {}",
1583 n, literal, bad);
1584
1585 let mut data = Vec::new();
1586
1587 let mut certs_orig = vec![];
1588 for i in 0..n {
1589 let (cert, _) =
1590 CertBuilder::general_purpose(
1591 Some(format!("{}@example.org", i)))
1592 .generate()?;
1593
1594 cert.as_tsk().serialize(&mut data)?;
1595 certs_orig.push(cert);
1596
1597 if literal {
1598 let mut lit = Literal::new(DataFormat::Unicode);
1599 lit.set_body(b"data".to_vec());
1600
1601 Packet::from(lit).serialize(&mut data)?;
1602 }
1603 // Push some NUL bytes.
1604 data.extend(&nulls[..bad]);
1605 }
1606 if n == 0 {
1607 // Push some NUL bytes even if we didn't add any packets.
1608 data.extend(&nulls[..bad]);
1609 }
1610 assert_eq!(certs_orig.len(), n);
1611
1612 t!("Start of data: {} {}",
1613 if let Some(x) = data.get(0) {
1614 format!("{:02X}", x)
1615 } else {
1616 "XX".into()
1617 },
1618 if let Some(x) = data.get(1) {
1619 format!("{:02X}", x)
1620 } else {
1621 "XX".into()
1622 });
1623
1624 let certs_parsed = CertParser::from_bytes(&data);
1625
1626 let certs_parsed = if n == 0 && bad > 0 {
1627 // Junk at the beginning of the file results in an
1628 // immediate parse error.
1629 assert!(certs_parsed.is_err());
1630 return Ok(());
1631 } else {
1632 certs_parsed.expect("Valid init")
1633 };
1634 let certs_parsed: Vec<_> = certs_parsed.collect();
1635
1636 certs_parsed.iter().enumerate().for_each(|(i, r)| {
1637 t!("{}. {}",
1638 i,
1639 match r {
1640 Ok(c) => c.fingerprint().to_string(),
1641 Err(err) => err.to_string(),
1642 });
1643 });
1644
1645 let n = if bad > RECOVERY_THRESHOLD {
1646 // We stop once we see the junk.
1647 certs_orig.drain(1..);
1648 std::cmp::min(n, 1)
1649 } else {
1650 n
1651 };
1652
1653 let modulus = if literal && bad > 0 {
1654 3
1655 } else {
1656 2
1657 };
1658 let certs_parsed: Vec<Cert> = certs_parsed.into_iter()
1659 .enumerate()
1660 .filter_map(|(i, c)| {
1661 if literal && i % modulus == 1 {
1662 // Literals should be errors.
1663 assert!(c.is_err());
1664 None
1665 } else if bad > 0 && n == 0 && i == 0 {
1666 // The first byte in the input is the NUL
1667 // byte.
1668 assert!(c.is_err());
1669 None
1670 } else if bad > 0 && i % modulus == modulus - 1 {
1671 // NUL bytes are inserted after the
1672 // certificate / literal data packet. So the
1673 // second element will be the parse error.
1674 assert!(c.is_err());
1675 None
1676 } else {
1677 Some(c.unwrap())
1678 }
1679 })
1680 .collect();
1681
1682 assert_eq!(certs_orig.len(), certs_parsed.len(),
1683 "number of parsed certificates: expected vs. got");
1684
1685 let fpr_orig = certs_orig.iter()
1686 .map(|c| {
1687 c.fingerprint()
1688 })
1689 .collect::<Vec<_>>();
1690 let fpr_parsed = certs_parsed.iter()
1691 .map(|c| {
1692 c.fingerprint()
1693 })
1694 .collect::<Vec<_>>();
1695 if fpr_orig != fpr_parsed {
1696 t!("{} certificates in orig; {} is parsed",
1697 fpr_orig.len(), fpr_parsed.len());
1698
1699 let fpr_set_orig: HashSet<&Fingerprint>
1700 = HashSet::from_iter(fpr_orig.iter());
1701 let fpr_set_parsed = HashSet::from_iter(fpr_parsed.iter());
1702 t!("Only in orig:\n {}",
1703 fpr_set_orig.difference(&fpr_set_parsed)
1704 .map(|f| f.to_string())
1705 .collect::<Vec<_>>()
1706 .join(",\n "));
1707 t!("Only in parsed:\n {}",
1708 fpr_set_parsed.difference(&fpr_set_orig)
1709 .map(|f| f.to_string())
1710 .collect::<Vec<_>>()
1711 .join(",\n "));
1712
1713 assert_eq!(fpr_orig, fpr_parsed);
1714 }
1715
1716 // Go packet by packet. (This makes finding an error a
1717 // lot easier.)
1718 for (i, (c_orig, c_parsed)) in
1719 certs_orig
1720 .into_iter()
1721 .zip(certs_parsed.into_iter())
1722 .enumerate()
1723 {
1724 let ps_orig: Vec<Packet> =
1725 c_orig.as_tsk().into_packets().collect();
1726 let ps_parsed: Vec<Packet> =
1727 c_parsed.as_tsk().into_packets().collect();
1728 assert_eq!(ps_orig.len(), ps_parsed.len(),
1729 "number of packets: expected vs. got");
1730
1731 for (j, (p_orig, p_parsed)) in
1732 ps_orig
1733 .into_iter()
1734 .zip(ps_parsed.into_iter())
1735 .enumerate()
1736 {
1737 assert_eq!(p_orig, p_parsed,
1738 "Cert {}, packet: {}", i, j);
1739 }
1740 }
1741
1742 Ok(())
1743 }
1744
1745 #[test]
1746 fn parse_keyring_simple() -> Result<()> {
1747 for n in [1, 100, 0].iter() {
1748 parse_test(*n, false, 0)?;
1749 }
1750
1751 Ok(())
1752 }
1753
1754 #[test]
1755 fn parse_keyring_interleaved_literals() -> Result<()> {
1756 for n in [1, 100, 0].iter() {
1757 parse_test(*n, true, 0)?;
1758 }
1759
1760 Ok(())
1761 }
1762
1763 #[test]
1764 fn parse_keyring_interleaved_small_junk() -> Result<()> {
1765 for n in [1, 100, 0].iter() {
1766 parse_test(*n, false, 1)?;
1767 }
1768
1769 Ok(())
1770 }
1771
1772 #[test]
1773 fn parse_keyring_interleaved_unrecoverable_junk() -> Result<()> {
1774 // PacketParser is pretty good at recovering from junk in the
1775 // middle: it will search the next RECOVERY_THRESHOLD bytes
1776 // for a valid packet. If it finds it, it will turn the junk
1777 // into a reserved packet and resume. Insert a lot of NULs to
1778 // prevent the recovery mechanism from working.
1779 for n in [1, 100, 0].iter() {
1780 parse_test(*n, false, 2 * RECOVERY_THRESHOLD)?;
1781 }
1782
1783 Ok(())
1784 }
1785
1786 #[test]
1787 fn parse_keyring_interleaved_literal_and_small_junk() -> Result<()> {
1788 for n in [1, 100, 0].iter() {
1789 parse_test(*n, true, 1)?;
1790 }
1791
1792 Ok(())
1793 }
1794
1795 #[test]
1796 fn parse_keyring_interleaved_literal_and_unrecoverable_junk() -> Result<()> {
1797 for n in [1, 100, 0].iter() {
1798 parse_test(*n, true, 2 * RECOVERY_THRESHOLD)?;
1799 }
1800
1801 Ok(())
1802 }
1803
1804 #[test]
1805 fn parse_keyring_no_public_key() -> Result<()> {
1806 tracer!(TRACE, "parse_keyring_no_public_key", 0);
1807
1808 // The first few packets are not the valid start of a
1809 // certificate. Each of those should return in an Error.
1810 // But, that shouldn't stop us from parsing the rest of the
1811 // keyring.
1812
1813 let (cert_1, _) =
1814 CertBuilder::general_purpose(
1815 Some("ea@example.org"))
1816 .generate()?;
1817 let cert_1_packets: Vec<Packet>
1818 = cert_1.into_packets().collect();
1819
1820 let (cert_2, _) =
1821 CertBuilder::general_purpose(
1822 Some("eb@example.org"))
1823 .generate()?;
1824
1825 for n in 1..cert_1_packets.len() {
1826 t!("n: {}", n);
1827
1828 let mut data = Vec::new();
1829
1830 for i in n..cert_1_packets.len() {
1831 cert_1_packets[i].serialize(&mut data)?;
1832 }
1833
1834 cert_2.as_tsk().serialize(&mut data)?;
1835
1836
1837 let certs_parsed = CertParser::from_bytes(&data)
1838 .expect("Valid parse");
1839
1840 let mut iter = certs_parsed;
1841 for _ in n..cert_1_packets.len() {
1842 assert!(iter.next().unwrap().is_err());
1843 }
1844 assert_eq!(iter.next().unwrap().as_ref().unwrap(), &cert_2);
1845 assert!(iter.next().is_none());
1846 assert!(iter.next().is_none());
1847 }
1848
1849 Ok(())
1850 }
1851
1852 #[test]
1853 fn filter() {
1854 let fp = Fingerprint::from_hex(
1855 "CBCD8F030588653EEDD7E2659B7DD433F254904A",
1856 ).unwrap();
1857
1858 let cp = CertParser::from_bytes(tests::key("bad-subkey-keyring.pgp"))
1859 .unwrap()
1860 .unvalidated_cert_filter(|cert, _| {
1861 cert.fingerprint() == fp
1862 });
1863 let certs = cp.collect::<Result<Vec<Cert>>>().unwrap();
1864 assert_eq!(certs.len(), 1);
1865 assert!(certs[0].fingerprint() == fp);
1866 }
1867
1868 #[test]
1869 fn packet_source_includes_an_error() -> Result<()> {
1870 let mut ppr
1871 = PacketParser::from_bytes(crate::tests::key("testy.pgp"))?;
1872 let mut testy = Vec::new();
1873 while let PacketParserResult::Some(pp) = ppr {
1874 let (packet, ppr_) = pp.next()?;
1875 testy.push(packet);
1876 ppr = ppr_;
1877 }
1878
1879 // A cert, two errors, another cert.
1880 let mut packets: Vec<Result<Packet>> = Vec::new();
1881 for p in testy.iter() {
1882 packets.push(Ok(p.clone()));
1883 }
1884 packets.push(Err(anyhow::anyhow!("An error")));
1885 packets.push(Err(anyhow::anyhow!("Another error")));
1886 for p in testy.iter() {
1887 packets.push(Ok(p.clone()));
1888 }
1889
1890 let certs = CertParser::from(packets).collect::<Vec<Result<Cert>>>();
1891 assert_eq!(certs.len(), 4);
1892 assert!(certs[0].is_ok());
1893 assert!(certs[1].is_err());
1894 assert!(certs[2].is_err());
1895 assert!(certs[3].is_ok());
1896
1897 Ok(())
1898 }
1899}