commit e9b776f28b42d6a40a512d15c552c51cafbecb5c
parent 7cfbe0536601ef7c62a450ef354433bc848309d7
Author: Rich Lane <rlane@club.cc.cmu.edu>
Date: Sun, 10 Oct 2010 23:45:30 -0700
Merge branch 'master' into next
Diffstat:
4 files changed, 31 insertions(+), 8 deletions(-)
diff --git a/lib/sup.rb b/lib/sup.rb
@@ -261,7 +261,8 @@ EOS
:email => email,
:alternates => [],
:sendmail => "/usr/sbin/sendmail -oem -ti",
- :signature => File.join(ENV["HOME"], ".signature")
+ :signature => File.join(ENV["HOME"], ".signature"),
+ :gpgkey => ""
}
},
:editor => ENV["EDITOR"] || "/usr/bin/vim -f -c 'setlocal spell spelllang=en_us' -c 'set filetype=mail'",
diff --git a/lib/sup/account.rb b/lib/sup/account.rb
@@ -1,7 +1,7 @@
module Redwood
class Account < Person
- attr_accessor :sendmail, :signature
+ attr_accessor :sendmail, :signature, :gpgkey
def initialize h
raise ArgumentError, "no name for account" unless h[:name]
@@ -9,6 +9,7 @@ class Account < Person
super h[:name], h[:email]
@sendmail = h[:sendmail]
@signature = h[:signature]
+ @gpgkey = h[:gpgkey]
end
# Default sendmail command for bouncing mail,
@@ -46,7 +47,7 @@ class AccountManager
def add_account hash, default=false
raise ArgumentError, "no email specified for account" unless hash[:email]
unless default
- [:name, :sendmail, :signature].each { |k| hash[k] ||= @default_account.send(k) }
+ [:name, :sendmail, :signature, :gpgkey].each { |k| hash[k] ||= @default_account.send(k) }
end
hash[:alternates] ||= []
diff --git a/lib/sup/crypto.rb b/lib/sup/crypto.rb
@@ -45,7 +45,8 @@ EOS
sig_fn = Tempfile.new "redwood.signature"; sig_fn.close
- message = run_gpg "--output #{sig_fn.path} --yes --armor --detach-sign --textmode --digest-algo sha256 --local-user '#{from}' #{payload_fn.path}", :interactive => true
+ sign_user_opts = gen_sign_user_opts from
+ message = run_gpg "--output #{sig_fn.path} --yes --armor --detach-sign --textmode --digest-algo sha256 #{sign_user_opts} #{payload_fn.path}", :interactive => true
unless $?.success?
info "Error while running gpg: #{message}"
raise Error, "GPG command failed. See log for details."
@@ -68,7 +69,8 @@ EOS
encrypted_fn = Tempfile.new "redwood.encrypted"; encrypted_fn.close
recipient_opts = (to + [ from ] ).map { |r| "--recipient '<#{r}>'" }.join(" ")
- sign_opts = sign ? "--sign --local-user '#{from}'" : ""
+ sign_opts = ""
+ sign_opts = "--sign --digest-algo sha256 " + gen_sign_user_opts(from) if sign
message = run_gpg "--output #{encrypted_fn.path} --yes --armor --encrypt --textmode #{sign_opts} #{recipient_opts} #{payload_fn.path}", :interactive => true
unless $?.success?
info "Error while running gpg: #{message}"
@@ -208,6 +210,23 @@ private
payload.to_s.gsub(/(^|[^\r])\n/, "\\1\r\n").gsub(/^MIME-Version: .*\r\n/, "")
end
+ # logic is:
+ # if gpgkey set for this account, then use that
+ # elsif only one account, then leave blank so gpg default will be user
+ # else set --local-user from_email_address
+ def gen_sign_user_opts from
+ account = AccountManager.account_for from
+ if !account.gpgkey.nil?
+ opts = "--local-user '#{account.gpgkey}'"
+ elsif AccountManager.user_emails.length == 1
+ # only one account
+ opts = ""
+ else
+ opts = "--local-user '#{from}'"
+ end
+ opts
+ end
+
def run_gpg args, opts={}
args = HookManager.run("gpg-args", { :args => args }) || args
cmd = "LC_MESSAGES=C #{@cmd} #{args}"
diff --git a/lib/sup/message.rb b/lib/sup/message.rb
@@ -475,10 +475,12 @@ private
end
else
filename =
- ## first, paw through the headers looking for a filename
- if m.header["Content-Disposition"] && m.header["Content-Disposition"] =~ /filename="?(.*?[^\\])("|;|$)/
+ ## first, paw through the headers looking for a filename.
+ ## RFC 2183 (Content-Disposition) specifies that disposition-parms are
+ ## separated by ";". So, we match everything up to " and ; (if present).
+ if m.header["Content-Disposition"] && m.header["Content-Disposition"] =~ /filename="?(.*?[^\\])("|;|\z)/m
$1
- elsif m.header["Content-Type"] && m.header["Content-Type"] =~ /name="?(.*?[^\\])("|;|$)/i
+ elsif m.header["Content-Type"] && m.header["Content-Type"] =~ /name="?(.*?[^\\])("|;|\z)/im
$1
## haven't found one, but it's a non-text message. fake