From: Gaudenz Steinlin <gaudenz@soziologie.ch>
To: sup-devel <sup-devel@rubyforge.org>
Subject: [sup-devel] GPGME fixes
Date: Thu, 17 Feb 2011 15:49:01 +0100 [thread overview]
Message-ID: <1297953902-sup-8049@meteor.durcheinandertal.local> (raw)
[-- Attachment #1.1.1: Type: text/plain, Size: 387 bytes --]
Hi
While reimporting all my messages I encountered a few problemes with
the GPGME code. Please consider the attached fixes.
The second patch depends on the first (error message unification). But
if you don't like the first I can easily produce a standalone version.
Gaudenz
--
Ever tried. Ever failed. No matter.
Try again. Fail again. Fail better.
~ Samuel Beckett ~
[-- Attachment #1.1.2: 0001-Encode-multipart-messages-for-crypt-operations.patch --]
[-- Type: application/octet-stream, Size: 2180 bytes --]
From ca2511220d1f0198a4e73432e87774a8fe30fba9 Mon Sep 17 00:00:00 2001
From: Gaudenz Steinlin <gaudenz@soziologie.ch>
Date: Tue, 12 Oct 2010 23:20:53 +0200
Subject: [PATCH 1/2] Encode multipart messages for crypt operations
Sup crashed when trying to encode a multipart message for crypto
operations. This encodes each part of the message separately. It also
changes the encoding for text/* parts to quoted-printable.
This only concerns the transfer encoding and does not change the charset
in any way.
---
lib/sup/modes/edit-message-mode.rb | 26 ++++++++++++++++++++++++--
1 files changed, 24 insertions(+), 2 deletions(-)
diff --git a/lib/sup/modes/edit-message-mode.rb b/lib/sup/modes/edit-message-mode.rb
index f27eb5c..1bf9378 100644
--- a/lib/sup/modes/edit-message-mode.rb
+++ b/lib/sup/modes/edit-message-mode.rb
@@ -403,8 +403,11 @@ protected
if @crypto_selector && @crypto_selector.val != :none
from_email = Person.from_address(@header["From"]).email
to_email = [@header["To"], @header["Cc"], @header["Bcc"]].flatten.compact.map { |p| Person.from_address(p).email }
- m.header["Content-Transfer-Encoding"] = 'base64'
- m.body = [m.body].pack('m')
+ if m.multipart?
+ m.each_part {|p| p = transfer_encode p}
+ else
+ m = transfer_encode m
+ end
m = CryptoManager.send @crypto_selector.val, from_email, to_email, m
end
@@ -520,6 +523,25 @@ private
[]
end
end
+
+ def transfer_encode msg_part
+ ## return the message unchanged if it's already encoded
+ if (msg_part.header["Content-Transfer-Encoding"] == "base64" ||
+ msg_part.header["Content-Transfer-Encoding"] == "quoted-printable")
+ return msg_part
+ end
+
+ ## encode to quoted-printable for all text/* MIME types,
+ ## use base64 otherwise
+ if msg_part.header["Content-Type"] =~ /text\/.*/
+ msg_part.header["Content-Transfer-Encoding"] = 'quoted-printable'
+ msg_part.body = [msg_part.body].pack('M')
+ else
+ msg_part.header["Content-Transfer-Encoding"] = 'base64'
+ msg_part.body = [msg_part.body].pack('m')
+ end
+ msg_part
+ end
end
end
--
1.7.2.3
[-- Attachment #1.1.3: 0001-Unify-formatting-of-GPGME-error-messages.patch --]
[-- Type: application/octet-stream, Size: 2413 bytes --]
From b52a306ed119715e5dac26f35a406ecdd4c5fb87 Mon Sep 17 00:00:00 2001
From: Gaudenz Steinlin <gaudenz@soziologie.ch>
Date: Thu, 17 Feb 2011 15:09:23 +0100
Subject: [PATCH 1/3] Unify formatting of GPGME error messages
Create a private function to turn a an exception into a "human friendly"
error message and to add a entry to the logfile. Use this function for
all error paths.
---
lib/sup/crypto.rb | 17 ++++++++++-------
1 files changed, 10 insertions(+), 7 deletions(-)
diff --git a/lib/sup/crypto.rb b/lib/sup/crypto.rb
index 2bfb475..a3771bf 100644
--- a/lib/sup/crypto.rb
+++ b/lib/sup/crypto.rb
@@ -75,8 +75,7 @@ EOS
begin
sig = GPGME.detach_sign(format_payload(payload), gpg_opts)
rescue GPGME::Error => exc
- info "Error while running gpg: #{exc.message}"
- raise Error, "GPG command failed. See log for details."
+ raise Error, gpgme_exc_msg(exc.message)
end
envelope = RMail::Message.new
@@ -103,8 +102,7 @@ EOS
begin
cipher = GPGME.encrypt(recipients, format_payload(payload), gpg_opts)
rescue GPGME::Error => exc
- info "Error while running gpg: #{exc.message}"
- raise Error, "GPG command failed. See log for details."
+ raise Error, gpgme_exc_msg(exc.message)
end
encrypted_payload = RMail::Message.new
@@ -183,7 +181,7 @@ EOS
begin
ctx.verify(sig_data, signed_text_data, plain_data)
rescue GPGME::Error => exc
- return unknown_status exc.message
+ return unknown_status [gpgme_exc_msg(exc.message)]
end
self.verified_ok? ctx.verify_result
end
@@ -201,8 +199,7 @@ EOS
begin
ctx.decrypt_verify(cipher_data, plain_data)
rescue GPGME::Error => exc
- info "Error while running gpg: #{exc.message}"
- return Chunk::CryptoNotice.new(:invalid, "This message could not be decrypted", exc.message)
+ return Chunk::CryptoNotice.new(:invalid, "This message could not be decrypted", gpgme_exc_msg(exc.message))
end
sig = self.verified_ok? ctx.verify_result
plain_data.seek(0, IO::SEEK_SET)
@@ -264,6 +261,12 @@ private
["Can't find gpgme gem."]
end
+ def gpgme_exc_msg msg
+ err_msg = "Exception in GPGME call: #{msg}"
+ info err_msg
+ err_msg
+ end
+
## here's where we munge rmail output into the format that signed/encrypted
## PGP/GPG messages should be
def format_payload payload
--
1.7.2.3
[-- Attachment #1.1.4: 0002-Check-for-ArgumentError-on-signature-verification.patch --]
[-- Type: application/octet-stream, Size: 1614 bytes --]
From f86d0bb6c2cc9a1d8ef544a34f9c10f73850767c Mon Sep 17 00:00:00 2001
From: Gaudenz Steinlin <gaudenz@soziologie.ch>
Date: Thu, 17 Feb 2011 15:13:31 +0100
Subject: [PATCH 2/3] Check for ArgumentError on signature verification
Broken signatures can cause a NULL pointer which results in an
ArguementError when calling ctx.verify_result even if the previous call
to ctx.verify does not raise an exception.
The underling cause is probably a bug in GPGME.
---
lib/sup/crypto.rb | 12 ++++++++++--
1 files changed, 10 insertions(+), 2 deletions(-)
diff --git a/lib/sup/crypto.rb b/lib/sup/crypto.rb
index a3771bf..cbd0751 100644
--- a/lib/sup/crypto.rb
+++ b/lib/sup/crypto.rb
@@ -183,7 +183,11 @@ EOS
rescue GPGME::Error => exc
return unknown_status [gpgme_exc_msg(exc.message)]
end
- self.verified_ok? ctx.verify_result
+ begin
+ self.verified_ok? ctx.verify_result
+ rescue ArgumentError => exc
+ return unknown_status [gpgme_exc_msg(exc.message)]
+ end
end
## returns decrypted_message, status, desc, lines
@@ -201,7 +205,11 @@ EOS
rescue GPGME::Error => exc
return Chunk::CryptoNotice.new(:invalid, "This message could not be decrypted", gpgme_exc_msg(exc.message))
end
- sig = self.verified_ok? ctx.verify_result
+ begin
+ sig = self.verified_ok? ctx.verify_result
+ rescue ArgumentError => exc
+ sig = unknown_status [gpgme_exc_msg(exc.message)]
+ end
plain_data.seek(0, IO::SEEK_SET)
output = plain_data.read
output.force_encoding Encoding::ASCII_8BIT if output.respond_to? :force_encoding
--
1.7.2.3
[-- Attachment #1.1.5: 0003-Check-for-valid-signature-before-signature.to_s.patch --]
[-- Type: application/octet-stream, Size: 1290 bytes --]
From 0a242c50f93319a47217dd577089732f4fbf0664 Mon Sep 17 00:00:00 2001
From: Gaudenz Steinlin <gaudenz@soziologie.ch>
Date: Thu, 17 Feb 2011 15:26:41 +0100
Subject: [PATCH 3/3] Check for valid signature before signature.to_s
In some circumstances with broken signatures signature.to_s returns nil.
Check for a valid signature before relying on this string. This avoids
an uncaught exception.
---
lib/sup/crypto.rb | 8 +++++++-
1 files changed, 7 insertions(+), 1 deletions(-)
diff --git a/lib/sup/crypto.rb b/lib/sup/crypto.rb
index cbd0751..9ab8607 100644
--- a/lib/sup/crypto.rb
+++ b/lib/sup/crypto.rb
@@ -292,7 +292,13 @@ private
ctx = GPGME::Ctx.new
begin
from_key = ctx.get_key(signature.fingerprint)
- first_sig = signature.to_s.sub(/from [0-9A-F]{16} /, 'from "') + '"'
+ if GPGME::gpgme_err_code(signature.status) == GPGME::GPG_ERR_GENERAL
+ first_sig = "General error on signature verification for #{signature.fingerprint}"
+ elsif signature.to_s
+ first_sig = signature.to_s.sub(/from [0-9A-F]{16} /, 'from "') + '"'
+ else
+ first_sig = "Unknown error or empty signature"
+ end
rescue EOFError
from_key = nil
first_sig = "No public key available for #{signature.fingerprint}"
--
1.7.2.3
[-- Attachment #1.2: signature.asc --]
[-- Type: application/pgp-signature, Size: 482 bytes --]
[-- Attachment #2: Type: text/plain, Size: 143 bytes --]
_______________________________________________
Sup-devel mailing list
Sup-devel@rubyforge.org
http://rubyforge.org/mailman/listinfo/sup-devel
next reply other threads:[~2011-02-17 15:14 UTC|newest]
Thread overview: 4+ messages / expand[flat|nested] mbox.gz Atom feed top
2011-02-17 14:49 Gaudenz Steinlin [this message]
2011-02-17 18:45 ` Hamish D
2011-02-17 20:44 ` Gaudenz Steinlin
2011-02-17 22:57 ` Hamish D
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=1297953902-sup-8049@meteor.durcheinandertal.local \
--to=gaudenz@soziologie.ch \
--cc=sup-devel@rubyforge.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox