Exemple #1
0
    internal void VerifyEmail(Outlook.MailItem mailItem)
    {
      string mail = mailItem.Body;
      Outlook.OlBodyFormat mailType = mailItem.BodyFormat;

      if (mailType != Outlook.OlBodyFormat.olFormatPlain)
      {
        MessageBox.Show(
            "OutlookGnuPG can only verify plain text mails.",
            "Invalid Mail Format",
            MessageBoxButtons.OK,
            MessageBoxIcon.Error);

        return;
      }

      if (Regex.IsMatch(mailItem.Body, _pgpSignedHeader) == false)
      {
        MessageBox.Show(
            "OutlookGnuPG cannot help here.",
            "Mail is not signed",
            MessageBoxButtons.OK,
            MessageBoxIcon.Exclamation);
        return;
      }
      
      // Still no gpg.exe path... Annoy the user once again, maybe he'll get it ;)
      if (string.IsNullOrEmpty(_settings.GnuPgPath))
        Settings();

      // Stubborn, give up
      if (string.IsNullOrEmpty(_settings.GnuPgPath))
      {
        MessageBox.Show(
            "OutlookGnuPG can only verify when you provide a valid gpg.exe path. Please open Settings and configure it.",
            "Invalid GnuPG Executable",
            MessageBoxButtons.OK,
            MessageBoxIcon.Error);

        return;
      }

      string verifyResult = string.Empty;
      string errorResult = string.Empty;
      using (MemoryStream inputStream = new MemoryStream(mail.Length))
      using (MemoryStream outputStream = new MemoryStream())
      using (MemoryStream errorStream = new MemoryStream())
      {
        using (StreamWriter writer = new StreamWriter(inputStream))
        {
          writer.Write(mail);
          writer.Flush();
          inputStream.Position = 0;

          try
          {
            _gnuPg.OutputStatus = true;
            _gnuPg.Verify(inputStream, outputStream, errorStream);
          }
          catch (Exception ex)
          {
            string error = ex.Message;

            // We deal with bad signature later
            if (!error.ToLowerInvariant().Contains("bad signature"))
            {
              MessageBox.Show(
                  error,
                  "GnuPG Error",
                  MessageBoxButtons.OK,
                  MessageBoxIcon.Error);

              return;
            }
          }
        }

        using (StreamReader reader = new StreamReader(outputStream))
        {
          outputStream.Position = 0;
          verifyResult = reader.ReadToEnd();
        }

        using (StreamReader reader = new StreamReader(errorStream))
        {
          errorStream.Position = 0;
          errorResult = reader.ReadToEnd();
        }
      }

      if (verifyResult.Contains("BADSIG"))
      {
        errorResult = RemoveInvalidAka(errorResult.Replace("gpg: ", string.Empty));

        MessageBox.Show(
            errorResult,
            "Invalid Signature",
            MessageBoxButtons.OK,
            MessageBoxIcon.Error);
      }
      else if (verifyResult.Contains("GOODSIG"))
      {
        errorResult = RemoveInvalidAka(errorResult.Replace("gpg: ", string.Empty));

        MessageBox.Show(
            errorResult,
            "Valid Signature",
            MessageBoxButtons.OK,
            MessageBoxIcon.Information);
      }
      else
      {
        errorResult = RemoveInvalidAka(errorResult.Replace("gpg: ", string.Empty));

        MessageBox.Show(
            errorResult,
            "Unknown Signature",
            MessageBoxButtons.OK,
            MessageBoxIcon.Exclamation);
      }
    }
Exemple #2
0
    internal void DecryptEmail(Outlook.MailItem mailItem)
    {
      string mail = mailItem.Body;
      Outlook.OlBodyFormat mailType = mailItem.BodyFormat;

      if (mailType != Outlook.OlBodyFormat.olFormatPlain)
      {
        MessageBox.Show(
            "OutlookGnuPG can only decrypt plain text mails.",
            "Invalid Mail Format",
            MessageBoxButtons.OK,
            MessageBoxIcon.Error);

        return;
      }

      if (Regex.IsMatch(mailItem.Body, _pgpEncryptedHeader) == false)
      {
        MessageBox.Show(
            "OutlookGnuPG cannot help here.",
            "Mail is not encrypted",
            MessageBoxButtons.OK,
            MessageBoxIcon.Exclamation);
        return;
      }

      // Still no gpg.exe path... Annoy the user once again, maybe he'll get it ;)
      if (string.IsNullOrEmpty(_settings.GnuPgPath))
        Settings();

      // Stubborn, give up
      if (string.IsNullOrEmpty(_settings.GnuPgPath))
      {
        MessageBox.Show(
            "OutlookGnuPG can only decrypt when you provide a valid gpg.exe path. Please open Settings and configure it.",
            "Invalid GnuPG Executable",
            MessageBoxButtons.OK,
            MessageBoxIcon.Error);

        return;
      }

      string passphrase = string.Empty;
      string privateKey = string.Empty;

      // Popup UI to select the passphrase and private key.
      Passphrase passphraseDialog = new Passphrase(_settings.DefaultKey, "Decrypt");
      DialogResult passphraseResult = passphraseDialog.ShowDialog();
      if (passphraseResult != DialogResult.OK)
      {
        // The user closed the passphrase dialog, prevent sending the mail
        return;
      }

      passphrase = passphraseDialog.EnteredPassphrase;
      privateKey = passphraseDialog.SelectedKey;
      passphraseDialog.Close();

      if (string.IsNullOrEmpty(privateKey))
      {
        MessageBox.Show(
            "OutlookGnuPG needs a private key for decrypting. No keys were detected.",
            "Invalid Private Key",
            MessageBoxButtons.OK,
            MessageBoxIcon.Error);

        return;
      }

      // Decrypt without fd-status (might already blow up, early out)
      // Decrypt with fd-status and cut out the stdout of normal decrypt (prevents BAD/GOODMC messages in message confusing us)
      string stdOutResult = string.Empty;
      using (MemoryStream inputStream = new MemoryStream(mail.Length))
      using (MemoryStream outputStream = new MemoryStream())
      {
        using (StreamWriter writer = new StreamWriter(inputStream))
        {
          writer.Write(mail);
          writer.Flush();
          inputStream.Position = 0;

          try
          {
            _gnuPg.OutputStatus = false;
            _gnuPg.Passphrase = passphrase;
            _gnuPg.Decrypt(inputStream, outputStream, new MemoryStream());
          }
          catch (Exception ex)
          {
            string error = ex.Message;

            // We deal with bad signature later
            if (!error.ToLowerInvariant().Contains("bad signature"))
            {
              MessageBox.Show(
                  error,
                  "GnuPG Error",
                  MessageBoxButtons.OK,
                  MessageBoxIcon.Error);

              return;
            }
          }
        }

        using (StreamReader reader = new StreamReader(outputStream))
        {
          outputStream.Position = 0;
          stdOutResult = reader.ReadToEnd();
        }
      }

      string verifyResult = string.Empty;
      string errorResult = string.Empty;
      using (MemoryStream inputStream = new MemoryStream(mail.Length))
      using (MemoryStream outputStream = new MemoryStream())
      using (MemoryStream errorStream = new MemoryStream())
      {
        using (StreamWriter writer = new StreamWriter(inputStream))
        {
          writer.Write(mail);
          writer.Flush();
          inputStream.Position = 0;

          try
          {
            _gnuPg.OutputStatus = true;
            _gnuPg.Passphrase = passphrase;
            _gnuPg.Decrypt(inputStream, outputStream, errorStream);
          }
          catch (Exception ex)
          {
            string error = ex.Message;

            // We deal with bad signature later
            if (!error.ToLowerInvariant().Contains("bad signature"))
            {
              MessageBox.Show(
                  error,
                  "GnuPG Error",
                  MessageBoxButtons.OK,
                  MessageBoxIcon.Error);

              return;
            }
          }
        }

        using (StreamReader reader = new StreamReader(outputStream))
        {
          outputStream.Position = 0;
          verifyResult = reader.ReadToEnd();
        }

        using (StreamReader reader = new StreamReader(errorStream))
        {
          errorStream.Position = 0;
          errorResult = reader.ReadToEnd();
        }
      }

      verifyResult = verifyResult.Replace(stdOutResult, string.Empty);

      // Verify: status-fd
      // stdOut: the message
      // error: gpg error/status

      if (verifyResult.Contains("BADMDC"))
      {
        errorResult = RemoveInvalidAka(errorResult.Replace("gpg: ", string.Empty));

        MessageBox.Show(
            errorResult,
            "Invalid Encryption",
            MessageBoxButtons.OK,
            MessageBoxIcon.Error);
      }
      else if (verifyResult.Contains("GOODMDC"))
      {
        // Decrypted OK, check for validsig
        if (verifyResult.Contains("BADSIG"))
        {
          errorResult = RemoveInvalidAka(errorResult.Replace("gpg: ", string.Empty));

          MessageBox.Show(
              errorResult,
              "Invalid Signature",
              MessageBoxButtons.OK,
              MessageBoxIcon.Error);
        }
        else if (verifyResult.Contains("GOODSIG"))
        {
          errorResult = RemoveInvalidAka(errorResult.Replace("gpg: ", string.Empty));

          MessageBox.Show(
              errorResult,
              "Valid Signature",
              MessageBoxButtons.OK,
              MessageBoxIcon.Information);

          // Valid signature!
          mailItem.Body = stdOutResult;
        }
        else
        {
          // No signature?
          mailItem.Body = stdOutResult;
        }
      }
      else
      {
        errorResult = RemoveInvalidAka(errorResult.Replace("gpg: ", string.Empty));
        errorResult = errorResult.Replace("WARNING", Environment.NewLine + "WARNING");

        DialogResult res = MessageBox.Show(
            errorResult + Environment.NewLine + "Decrypt mail anyway?",
            "Unknown Encryption",
            MessageBoxButtons.OKCancel,
            MessageBoxIcon.Exclamation);
        if (res == DialogResult.OK)
          mailItem.Body = stdOutResult;
      }
    }
Exemple #3
0
    private void Application_ItemSend(object Item, ref bool Cancel)
    {
      Outlook.MailItem mailItem = Item as Outlook.MailItem;

      if (mailItem == null)
        return;

#if VS2008
      //var inspector = Application.ActiveInspector();
      var inspector = mailItem.GetInspector;
      var currentRibbons = Globals.Ribbons[inspector];
      var currentRibbon = currentRibbons.GnuPGRibbonCompose;
#else
      GnuPGRibbon currentRibbon = ribbon;
#endif

      if (currentRibbon == null)
        return;

      string mail = mailItem.Body;
      Outlook.OlBodyFormat mailType = mailItem.BodyFormat;
      bool needToEncrypt = currentRibbon.EncryptButton.Checked;
      bool needToSign = currentRibbon.SignButton.Checked;

      // Early out when we don't need to sign/encrypt
      if (!needToEncrypt && !needToSign)
        return;

      if (mailType != Outlook.OlBodyFormat.olFormatPlain)
      {
        MessageBox.Show(
            "OutlookGnuPG can only sign/encrypt plain text mails. Please change the format, or disable signing/encrypting for this mail.",
            "Invalid Mail Format",
            MessageBoxButtons.OK,
            MessageBoxIcon.Error);

        Cancel = true; // Prevent sending the mail
        return;
      }

      // Still no gpg.exe path... Annoy the user once again, maybe he'll get it ;)
      if (string.IsNullOrEmpty(_settings.GnuPgPath))
        Settings();

      // Stubborn, give up
      if (string.IsNullOrEmpty(_settings.GnuPgPath))
      {
        MessageBox.Show(
            "OutlookGnuPG can only sign/encrypt when you provide a valid gpg.exe path. Please open Settings and configure it.",
            "Invalid GnuPG Executable",
            MessageBoxButtons.OK,
            MessageBoxIcon.Error);

        Cancel = true; // Prevent sending the mail
        return;
      }

      string passphrase = string.Empty;
      string privateKey = string.Empty;
      if (needToSign)
      {
        // Popup UI to select the passphrase and private key.
        Passphrase passphraseDialog = new Passphrase(_settings.DefaultKey, "Sign");
        DialogResult passphraseResult = passphraseDialog.ShowDialog();
        if (passphraseResult != DialogResult.OK)
        {
          // The user closed the passphrase dialog, prevent sending the mail
          Cancel = true;
          return;
        }

        passphrase = passphraseDialog.EnteredPassphrase;
        privateKey = passphraseDialog.SelectedKey;
        passphraseDialog.Close();

        if (string.IsNullOrEmpty(privateKey))
        {
          MessageBox.Show(
              "OutlookGnuPG needs a private key for signing. No keys were detected.",
              "Invalid Private Key",
              MessageBoxButtons.OK,
              MessageBoxIcon.Error);

          Cancel = true; // Prevent sending the mail
          return;
        }
      }

#if VS2008
      IList<string> recipients = new List<string> { string.Empty };
#else
      IList<string> recipients = new List<string>();
      recipients.Add(string.Empty);
#endif
      if (needToEncrypt)
      {
        // Popup UI to select the encryption targets 
        List<string> mailRecipients = new List<string>();
        foreach (Outlook.Recipient mailRecipient in mailItem.Recipients)
          mailRecipients.Add(GetAddressCN(((Outlook.Recipient)mailRecipient).Address));

        Recipient recipientDialog = new Recipient(mailRecipients); // Passing in the first addres, maybe it matches
        DialogResult recipientResult = recipientDialog.ShowDialog();

        if (recipientResult != DialogResult.OK)
        {
          // The user closed the recipient dialog, prevent sending the mail
          Cancel = true;
          return;
        }

        recipients = recipientDialog.SelectedKeys;
        recipientDialog.Close();

        if (recipients.Count == 0)
        {
          MessageBox.Show(
              "OutlookGnuPG needs a recipient when encrypting. No keys were detected/selected.",
              "Invalid Recipient Key",
              MessageBoxButtons.OK,
              MessageBoxIcon.Error);

          Cancel = true; // Prevent sending the mail
          return;
        }
      }

      // Sign and encrypt the plaintext mail
      if ((needToSign) && (needToEncrypt))
      {
        mail = SignAndEncryptEmail(mail, privateKey, passphrase, recipients);
      }
      else if (needToSign)
      {
        // Sign the plaintext mail if needed
        mail = SignEmail(mail, privateKey, passphrase);
      }
      else if (needToEncrypt)
      {
        // Encrypt the plaintext mail if needed
        mail = EncryptEmail(mail, passphrase, recipients);
      }

      // Update the new content
      if (mail != _gnuPgErrorString)
        mailItem.Body = mail;
      else
        Cancel = true;
    }