#!/usr/bin/perl
#
# Copyright 2002,2005 Greg Kroah-Hartman <greg@kroah.com>
# Copyright 2005 Ryan Anderson <ryan@michonline.com>
#
# GPL v2 (See COPYING)
#
# Ported to support git "mbox" format files by Ryan Anderson <ryan@michonline.com>
#
# Sends a collection of emails to the given email addresses, disturbingly fast.
#
# Supports two formats:
# 1. mbox format files (ignoring most headers and MIME formatting - this is designed for sending patches)
# 2. The original format support by Greg's script:
#    first line of the message is who to CC,
#    and second line is the subject of the message.
#

require v5.26;
use strict;
use warnings $ENV{GIT_PERL_FATAL_WARNINGS} ? qw(FATAL all) : ();
use Getopt::Long;
use Git::LoadCPAN::Error qw(:try);
use Git;
use Git::I18N;
use Encode qw(find_encoding);

Getopt::Long::Configure qw/ pass_through /;

sub usage {
	print <<EOT;
git send-email [<options>] <file|directory>
git send-email [<options>] <format-patch options>
git send-email --dump-aliases
git send-email --translate-aliases

  Composing:
    --from                  <str>  * Email From:
    --[no-]to               <str>  * Email To:
    --[no-]cc               <str>  * Email Cc:
    --[no-]bcc              <str>  * Email Bcc:
    --subject               <str>  * Email "Subject:"
    --reply-to              <str>  * Email "Reply-To:"
    --in-reply-to           <str>  * Email "In-Reply-To:"
    --[no-]outlook-id-fix          * The SMTP host is an Outlook server that munges the
                                     Message-ID. Retrieve it from the server.
    --[no-]xmailer                 * Add "X-Mailer:" header (default).
    --[no-]annotate                * Review each patch that will be sent in an editor.
    --compose                      * Open an editor for introduction.
    --compose-encoding      <str>  * Encoding to assume for introduction.
    --8bit-encoding         <str>  * Encoding to assume 8bit mails if undeclared
    --transfer-encoding     <str>  * Transfer encoding to use (quoted-printable, 8bit, base64)
    --[no-]mailmap                 * Use mailmap file to map all email addresses to canonical
                                     real names and email addresses.

  Sending:
    --envelope-sender       <str>  * Email envelope sender.
    --sendmail-cmd          <str>  * Command to run to send email.
    --smtp-server       <str:int>  * Outgoing SMTP server to use. The port
                                     is optional. Default 'localhost'.
    --smtp-server-option    <str>  * Outgoing SMTP server option to use.
    --smtp-server-port      <int>  * Outgoing SMTP server port.
    --smtp-user             <str>  * Username for SMTP-AUTH.
    --smtp-pass             <str>  * Password for SMTP-AUTH; not necessary.
    --smtp-encryption       <str>  * tls or ssl; anything else disables.
    --smtp-ssl                     * Deprecated. Use `--smtp-encryption ssl`.
    --smtp-ssl-cert-path    <str>  * Path to ca-certificates (either directory or file).
                                     Pass an empty string to disable certificate
                                     verification.
    --smtp-ssl-client-cert  <str>  * Path to the client certificate file
    --smtp-ssl-client-key   <str>  * Path to the private key file for the client certificate
    --smtp-domain           <str>  * The domain name sent to HELO/EHLO handshake
    --smtp-auth             <str>  * Space-separated list of allowed AUTH mechanisms, or
                                     "none" to disable authentication.
                                     This setting forces to use one of the listed mechanisms.
    --no-smtp-auth                 * Disable SMTP authentication. Shorthand for
                                     `--smtp-auth=none`
    --smtp-debug            <0|1>  * Disable, enable Net::SMTP debug.
    --imap-sent-folder      <str>  * IMAP folder where a copy of the emails should be sent.
                                     Make sure `git imap-send` is set up to use this feature.
    --[no-]use-imap-only           * Only copy emails to the IMAP folder specified by
                                     `--imap-sent-folder` instead of actually sending them.

    --batch-size            <int>  * send max <int> message per connection.
    --relogin-delay         <int>  * delay <int> seconds between two successive login.
                                     This option can only be used with --batch-size

  Automating:
    --identity              <str>  * Use the sendemail.<id> options.
    --to-cmd                <str>  * Email To: via `<str> \$patch_path`.
    --cc-cmd                <str>  * Email Cc: via `<str> \$patch_path`.
    --header-cmd            <str>  * Add headers via `<str> \$patch_path`.
    --no-header-cmd                * Disable any header command in use.
    --suppress-cc           <str>  * author, self, sob, cc, cccmd, body, bodycc, misc-by, all.
    --[no-]cc-cover                * Email Cc: addresses in the cover letter.
    --[no-]to-cover                * Email To: addresses in the cover letter.
    --[no-]signed-off-by-cc        * Send to Signed-off-by: addresses. Default on.
    --[no-]suppress-from           * Send to self. Default off.
    --[no-]chain-reply-to          * Chain In-Reply-To: fields. Default off.
    --[no-]thread                  * Use In-Reply-To: field. Default on.

  Administering:
    --confirm               <str>  * Confirm recipients before sending;
                                     auto, cc, compose, always, or never.
    --quiet                        * Output one line of info per email.
    --dry-run                      * Don't actually send the emails.
    --[no-]validate                * Perform patch sanity checks. Default on.
    --[no-]format-patch            * understand any non optional arguments as
                                     `git format-patch` ones.
    --force                        * Send even if safety checks would prevent it.

  Information:
    --dump-aliases                 * Dump configured aliases and exit.
    --translate-aliases            * Translate aliases read from standard
                                     input according to the configured email
                                     alias file(s), outputting the result to
                                     standard output.

EOT
	exit(1);
}

sub uniq {
	my %seen;
	grep !$seen{$_}++, @_;
}

sub completion_helper {
	my ($original_opts) = @_;
	my %not_for_completion = (
		"git-completion-helper" => undef,
		"h" => undef,
	);
	my @send_email_opts = ();

	foreach my $key (keys %$original_opts) {
		unless (exists $not_for_completion{$key}) {
			my $negatable = ($key =~ s/!$//);

			if ($key =~ /[:=][si]$/) {
				$key =~ s/[:=][si]$//;
				push (@send_email_opts, "--$_=") foreach (split (/\|/, $key));
			} else {
				push (@send_email_opts, "--$_") foreach (split (/\|/, $key));
				if ($negatable) {
					push (@send_email_opts, "--no-$_") foreach (split (/\|/, $key));
				}
			}
		}
	}

	my @format_patch_opts = split(/ /, Git::command('format-patch', '--git-completion-helper'));
	my @opts = (@send_email_opts, @format_patch_opts);
	@opts = uniq (grep !/^$/, @opts);
	# There's an implicit '\n' here already, no need to add an explicit one.
	print "@opts";
	exit(0);
}

# most mail servers generate the Date: header, but not all...
sub format_2822_time {
	my ($time) = @_;
	my @localtm = localtime($time);
	my @gmttm = gmtime($time);
	my $localmin = $localtm[1] + $localtm[2] * 60;
	my $gmtmin = $gmttm[1] + $gmttm[2] * 60;
	if ($localtm[0] != $gmttm[0]) {
		die __("local zone differs from GMT by a non-minute interval\n");
	}
	if ((($gmttm[6] + 1) % 7) == $localtm[6]) {
		$localmin += 1440;
	} elsif ((($gmttm[6] - 1) % 7) == $localtm[6]) {
		$localmin -= 1440;
	} elsif ($gmttm[6] != $localtm[6]) {
		die __("local time offset greater than or equal to 24 hours\n");
	}
	my $offset = $localmin - $gmtmin;
	my $offhour = $offset / 60;
	my $offmin = abs($offset % 60);
	if (abs($offhour) >= 24) {
		die __("local time offset greater than or equal to 24 hours\n");
	}

	return sprintf("%s, %2d %s %d %02d:%02d:%02d %s%02d%02d",
		       qw(Sun Mon Tue Wed Thu Fri Sat)[$localtm[6]],
		       $localtm[3],
		       qw(Jan Feb Mar Apr May Jun
			  Jul Aug Sep Oct Nov Dec)[$localtm[4]],
		       $localtm[5]+1900,
		       $localtm[2],
		       $localtm[1],
		       $localtm[0],
		       ($offset >= 0) ? '+' : '-',
		       abs($offhour),
		       $offmin,
		       );
}

my $smtp;
my $auth;
my $num_sent = 0;

# Regexes for RFC 2047 productions.
my $re_token = qr/[^][()<>@,;:\\"\/?.= \000-\037\177-\377]+/;
my $re_encoded_text = qr/[^? \000-\037\177-\377]+/;
my $re_encoded_word = qr/=\?($re_token)\?($re_token)\?($re_encoded_text)\?=/;

# Variables we fill in automatically, or via prompting:
my (@to,@cc,@xh,$envelope_sender,
	$initial_in_reply_to,$reply_to,$initial_subject,@files,@imap_copy,
	$author,$sender,$smtp_authpass,$annotate,$compose,$time);
# Things we either get from config, *or* are overridden on the
# command-line.
my ($no_cc, $no_to, $no_bcc, $no_identity, $no_header_cmd);
my (@config_to, @getopt_to);
my (@config_cc, @getopt_cc);
my (@config_bcc, @getopt_bcc);

# Example reply to:
#$initial_in_reply_to = ''; #<20050203173208.GA23964@foobar.com>';

my $repo = eval { Git->repository() };
my @repo = $repo ? ($repo) : ();

# Behavior modification variables
my ($quiet, $dry_run) = (0, 0);
my $format_patch;
my $compose_filename;
my $force = 0;
my $dump_aliases = 0;
my $translate_aliases = 0;

# Variables to prevent short format-patch options from being captured
# as abbreviated send-email options
my $reroll_count;

# Handle interactive edition of files.
my $multiedit;
my $editor;

sub system_or_msg {
	my ($args, $msg, $cmd_name) = @_;
	system(@$args);
	my $signalled = $? & 127;
	my $exit_code = $? >> 8;
	return unless $signalled or $exit_code;

	my @sprintf_args = ($cmd_name ? $cmd_name : $args->[0], $exit_code);
	if (defined $msg) {
		# Quiet the 'redundant' warning category, except we
		# need to support down to Perl 5.8.1, so we can't do a
		# "no warnings 'redundant'", since that category was
		# introduced in perl 5.22, and asking for it will die
		# on older perls.
		no warnings;
		return sprintf($msg, @sprintf_args);
	}
	return sprintf(__("fatal: command '%s' died with exit code %d"),
		       @sprintf_args);
}

sub system_or_die {
	my $msg = system_or_msg(@_);
	die $msg if $msg;
}

sub do_edit {
	if (!defined($editor)) {
		$editor = Git::command_oneline('var', 'GIT_EDITOR');
	}
	my $die_msg = __("the editor exited uncleanly, aborting everything");
	if (defined($multiedit) && !$multiedit) {
		system_or_die(['sh', '-c', $editor.' "$@"', $editor, $_], $die_msg) for @_;
	} else {
		system_or_die(['sh', '-c', $editor.' "$@"', $editor, @_], $die_msg);
	}
}

# Variables with corresponding config settings
my ($suppress_from, $signed_off_by_cc);
my ($cover_cc, $cover_to);
my ($to_cmd, $cc_cmd, $header_cmd);
my ($smtp_server, $smtp_server_port, @smtp_server_options);
my ($smtp_authuser, $smtp_encryption, $smtp_ssl_cert_path);
my ($smtp_ssl_client_cert, $smtp_ssl_client_key);
my ($batch_size, $relogin_delay);
my ($identity, $aliasfiletype, @alias_files, $smtp_domain, $smtp_auth);
my ($imap_sent_folder);
my ($confirm);
my (@suppress_cc);
my ($auto_8bit_encoding);
my ($compose_encoding);
my ($sendmail_cmd);
my ($mailmap_file, $mailmap_blob);
# Variables with corresponding config settings & hardcoded defaults
my ($debug_net_smtp) = 0;		# Net::SMTP, see send_message()
my $thread = 1;
my $chain_reply_to = 0;
my $use_xmailer = 1;
my $validate = 1;
my $mailmap = 0;
my $target_xfer_encoding = 'auto';
my $forbid_sendmail_variables = 1;
my $outlook_id_fix = 'auto';
my $use_imap_only = 0;

my %config_bool_settings = (
    "thread" => \$thread,
    "chainreplyto" => \$chain_reply_to,
    "suppressfrom" => \$suppress_from,
    "signedoffbycc" => \$signed_off_by_cc,
    "cccover" => \$cover_cc,
    "tocover" => \$cover_to,
    "signedoffcc" => \$signed_off_by_cc,
    "validate" => \$validate,
    "multiedit" => \$multiedit,
    "annotate" => \$annotate,
    "xmailer" => \$use_xmailer,
    "forbidsendmailvariables" => \$forbid_sendmail_variables,
    "mailmap" => \$mailmap,
    "outlookidfix" => \$outlook_id_fix,
    "useimaponly" => \$use_imap_only,
);

my %config_settings = (
    "smtpencryption" => \$smtp_encryption,
    "smtpserver" => \$smtp_server,
    "smtpserverport" => \$smtp_server_port,
    "smtpserveroption" => \@smtp_server_options,
    "smtpuser" => \$smtp_authuser,
    "smtppass" => \$smtp_authpass,
    "smtpdomain" => \$smtp_domain,
    "smtpauth" => \$smtp_auth,
    "smtpbatchsize" => \$batch_size,
    "smtprelogindelay" => \$relogin_delay,
    "imapsentfolder" => \$imap_sent_folder,
    "to" => \@config_to,
    "tocmd" => \$to_cmd,
    "cc" => \@config_cc,
    "cccmd" => \$cc_cmd,
    "headercmd" => \$header_cmd,
    "aliasfiletype" => \$aliasfiletype,
    "bcc" => \@config_bcc,
    "suppresscc" => \@suppress_cc,
    "envelopesender" => \$envelope_sender,
    "confirm"   => \$confirm,
    "from" => \$sender,
    "assume8bitencoding" => \$auto_8bit_encoding,
    "composeencoding" => \$compose_encoding,
    "transferencoding" => \$target_xfer_encoding,
    "sendmailcmd" => \$sendmail_cmd,
);

my %config_path_settings = (
    "aliasesfile" => \@alias_files,
    "smtpsslcertpath" => \$smtp_ssl_cert_path,
    "smtpsslclientcert" => \$smtp_ssl_client_cert,
    "smtpsslclientkey" => \$smtp_ssl_client_key,
    "mailmap.file" => \$mailmap_file,
    "mailmap.blob" => \$mailmap_blob,
);

# Handle Uncouth Termination
sub signal_handler {
	# Make text normal
	require Term::ANSIColor;
	print Term::ANSIColor::color("reset"), "\n";

	# SMTP password masked
	system "stty echo";

	# tmp files from --compose
	if (defined $compose_filename) {
		if (-e $compose_filename) {
			printf __("'%s' contains an intermediate version ".
				  "of the email you were composing.\n"),
				  $compose_filename;
		}
		if (-e ($compose_filename . ".final")) {
			printf __("'%s.final' contains the composed email.\n"),
				  $compose_filename;
		}
	}

	exit;
};

$SIG{TERM} = \&signal_handler;
$SIG{INT}  = \&signal_handler;

# Read our sendemail.* config
sub read_config {
	my ($known_keys, $configured, $prefix) = @_;

	foreach my $setting (keys %config_bool_settings) {
		my $target = $config_bool_settings{$setting};
		my $key = "$prefix.$setting";
		next unless exists $known_keys->{$key};
		my $v = (@{$known_keys->{$key}} == 1 &&
			 (defined $known_keys->{$key}->[0] &&
			  $known_keys->{$key}->[0] =~ /^(?:true|false)$/s))
			? $known_keys->{$key}->[0] eq 'true'
			: Git::config_bool(@repo, $key);
		next unless defined $v;
		next if $configured->{$setting}++;
		$$target = $v;
	}

	foreach my $setting (keys %config_path_settings) {
		my $target = $config_path_settings{$setting};
		my $key = "$prefix.$setting";
		next unless exists $known_keys->{$key};
		if (ref($target) eq "ARRAY") {
			my @values = Git::config_path(@repo, $key);
			next unless @values;
			next if $configured->{$setting}++;
			@$target = @values;
		}
		else {
			my $v = Git::config_path(@repo, "$prefix.$setting");
			next unless defined $v;
			next if $configured->{$setting}++;
			$$target = $v;
		}
	}

	foreach my $setting (keys %config_settings) {
		my $target = $config_settings{$setting};
		my $key = "$prefix.$setting";
		next unless exists $known_keys->{$key};
		if (ref($target) eq "ARRAY") {
			my @values = @{$known_keys->{$key}};
			@values = grep { defined } @values;
			next if $configured->{$setting}++;
			@$target = @values;
		}
		else {
			my $v = $known_keys->{$key}->[-1];
			next unless defined $v;
			next if $configured->{$setting}++;
			$$target = $v;
		}
	}
}

sub config_regexp {
	my ($regex) = @_;
	my @ret;
	eval {
		my $ret = Git::command(
			'config',
			'--null',
			'--get-regexp',
			$regex,
		);
		@ret = map {
			# We must always return ($k, $v) here, since
			# empty config values will be just "key\0",
			# not "key\nvalue\0".
			my ($k, $v) = split /\n/, $_, 2;
			($k, $v);
		} split /\0/, $ret;
		1;
	} or do {
		# If we have no keys we're OK, otherwise re-throw
		die $@ if $@->value != 1;
	};
	return @ret;
}

# Save ourselves a lot of work of shelling out to 'git config' (it
# parses 'bool' etc.) by only doing so for config keys that exist.
my %known_config_keys;
{
	my @kv = config_regexp("^sende?mail[.]");
	while (my ($k, $v) = splice @kv, 0, 2) {
		push @{$known_config_keys{$k}} => $v;
	}
}

# sendemail.identity yields to --identity. We must parse this
# special-case first before the rest of the config is read.
{
	my $key = "sendemail.identity";
	$identity = Git::config(@repo, $key) if exists $known_config_keys{$key};
}
my %identity_options = (
	"identity=s" => \$identity,
	"no-identity" => \$no_identity,
);
my $rc = GetOptions(%identity_options);
usage() unless $rc;
undef $identity if $no_identity;

# Now we know enough to read the config
{
    my %configured;
    read_config(\%known_config_keys, \%configured, "sendemail.$identity") if defined $identity;
    read_config(\%known_config_keys, \%configured, "sendemail");
}

# Begin by accumulating all the variables (defined above), that we will end up
# needing, first, from the command line:

my $help;
my $git_completion_helper;
my %dump_aliases_options = (
	"h" => \$help,
	"dump-aliases" => \$dump_aliases,
	"translate-aliases" => \$translate_aliases,
);
$rc = GetOptions(%dump_aliases_options);
usage() unless $rc;
die __("--dump-aliases incompatible with other options\n")
    if !$help and ($dump_aliases or $translate_aliases) and @ARGV;
die __("--dump-aliases and --translate-aliases are mutually exclusive\n")
    if !$help and $dump_aliases and $translate_aliases;
my %options = (
		    "sender|from=s" => \$sender,
		    "in-reply-to=s" => \$initial_in_reply_to,
		    "reply-to=s" => \$reply_to,
		    "subject=s" => \$initial_subject,
		    "to=s" => \@getopt_to,
		    "to-cmd=s" => \$to_cmd,
		    "no-to" => \$no_to,
		    "cc=s" => \@getopt_cc,
		    "no-cc" => \$no_cc,
		    "bcc=s" => \@getopt_bcc,
		    "no-bcc" => \$no_bcc,
		    "chain-reply-to!" => \$chain_reply_to,
		    "sendmail-cmd=s" => \$sendmail_cmd,
		    "smtp-server=s" => \$smtp_server,
		    "smtp-server-option=s" => \@smtp_server_options,
		    "smtp-server-port=s" => \$smtp_server_port,
		    "smtp-user=s" => \$smtp_authuser,
		    "smtp-pass:s" => \$smtp_authpass,
		    "smtp-ssl" => sub { $smtp_encryption = 'ssl' },
		    "smtp-encryption=s" => \$smtp_encryption,
		    "smtp-ssl-cert-path=s" => \$smtp_ssl_cert_path,
		    "smtp-ssl-client-cert=s" => \$smtp_ssl_client_cert,
		    "smtp-ssl-client-key=s" => \$smtp_ssl_client_key,
		    "smtp-debug:i" => \$debug_net_smtp,
		    "smtp-domain:s" => \$smtp_domain,
		    "smtp-auth=s" => \$smtp_auth,
		    "no-smtp-auth" => sub {$smtp_auth = 'none'},
		    "imap-sent-folder=s" => \$imap_sent_folder,
		    "use-imap-only!" => \$use_imap_only,
		    "annotate!" => \$annotate,
		    "compose" => \$compose,
		    "quiet" => \$quiet,
		    "cc-cmd=s" => \$cc_cmd,
		    "header-cmd=s" => \$header_cmd,
		    "no-header-cmd" => \$no_header_cmd,
		    "suppress-from!" => \$suppress_from,
		    "suppress-cc=s" => \@suppress_cc,
		    "signed-off-cc|signed-off-by-cc!" => \$signed_off_by_cc,
		    "cc-cover!" => \$cover_cc,
		    "to-cover!" => \$cover_to,
		    "confirm=s" => \$confirm,
		    "dry-run" => \$dry_run,
		    "envelope-sender=s" => \$envelope_sender,
		    "thread!" => \$thread,
		    "validate!" => \$validate,
		    "transfer-encoding=s" => \$target_xfer_encoding,
		    "mailmap!" => \$mailmap,
		    "use-mailmap!" => \$mailmap,
		    "format-patch!" => \$format_patch,
		    "8bit-encoding=s" => \$auto_8bit_encoding,
		    "compose-encoding=s" => \$compose_encoding,
		    "force" => \$force,
		    "xmailer!" => \$use_xmailer,
		    "batch-size=i" => \$batch_size,
		    "relogin-delay=i" => \$relogin_delay,
		    "git-completion-helper" => \$git_completion_helper,
		    "v=s" => \$reroll_count,
		    "outlook-id-fix!" => \$outlook_id_fix,
);
$rc = GetOptions(%options);

# Munge any "either config or getopt, not both" variables
my @initial_to = @getopt_to ? @getopt_to : ($no_to ? () : @config_to);
my @initial_cc = @getopt_cc ? @getopt_cc : ($no_cc ? () : @config_cc);
my @initial_bcc = @getopt_bcc ? @getopt_bcc : ($no_bcc ? () : @config_bcc);

usage() if $help;
my %all_options = (%options, %dump_aliases_options, %identity_options);
completion_helper(\%all_options) if $git_completion_helper;
unless ($rc) {
    usage();
}

if ($forbid_sendmail_variables && grep { /^sendmail/s } keys %known_config_keys) {
	die __("fatal: found configuration options for 'sendmail'\n" .
		"git-send-email is configured with the sendemail.* options - note the 'e'.\n" .
		"Set sendemail.forbidSendmailVariables to false to disable this check.\n");
}

die __("Cannot run git format-patch from outside a repository\n")
	if $format_patch and not $repo;

die __("`batch-size` and `relogin` must be specified together " .
	"(via command-line or configuration option)\n")
	if defined $relogin_delay and not defined $batch_size;

# 'default' encryption is none -- this only prevents a warning
$smtp_encryption = '' unless (defined $smtp_encryption);

# Set CC suppressions
my(%suppress_cc);
if (@suppress_cc) {
	foreach my $entry (@suppress_cc) {
		# Please update $__git_send_email_suppresscc_options
		# in git-completion.bash when you add new options.
		die sprintf(__("Unknown --suppress-cc field: '%s'\n"), $entry)
			unless $entry =~ /^(?:all|cccmd|cc|author|self|sob|body|bodycc|misc-by)$/;
		$suppress_cc{$entry} = 1;
	}
}

if ($suppress_cc{'all'}) {
	foreach my $entry (qw (cccmd cc author self sob body bodycc misc-by)) {
		$suppress_cc{$entry} = 1;
	}
	delete $suppress_cc{'all'};
}

# If explicit old-style ones are specified, they trump --suppress-cc.
$suppress_cc{'self'} = $suppress_from if defined $suppress_from;
$suppress_cc{'sob'} = !$signed_off_by_cc if defined $signed_off_by_cc;

if ($suppress_cc{'body'}) {
	foreach my $entry (qw (sob bodycc misc-by)) {
		$suppress_cc{$entry} = 1;
	}
	delete $suppress_cc{'body'};
}

# Set confirm's default value
my $confirm_unconfigured = !defined $confirm;
if ($confirm_unconfigured) {
	$confirm = scalar %suppress_cc ? 'compose' : 'auto';
};
# Please update $__git_send_email_confirm_options in
# git-completion.bash when you add new options.
die sprintf(__("Unknown --confirm setting: '%s'\n"), $confirm)
	unless $confirm =~ /^(?:auto|cc|compose|always|never)/;

# Debugging, print out the suppressions.
if (0) {
	print "suppressions:\n";
	foreach my $entry (keys %suppress_cc) {
		printf "  %-5s -> $suppress_cc{$entry}\n", $entry;
	}
}

my ($repoauthor, $repocommitter);
{
	my %cache;
	my ($author, $committer);
	my $common = sub {
		my ($what) = @_;
		return $cache{$what} if exists $cache{$what};
		($cache{$what}) = Git::ident_person(@repo, $what);
		return $cache{$what};
	};
	$repoauthor = sub { $common->('author') };
	$repocommitter = sub { $common->('committer') };
}

sub parse_address_line {
	require Git::LoadCPAN::Mail::Address;
	return map { $_->format } Mail::Address->parse($_[0]);
}

sub split_addrs {
	require Text::ParseWords;
	return Text::ParseWords::quotewords('\s*,\s*', 1, @_);
}

my %aliases;

sub parse_sendmail_alias {
	local $_ = shift;
	if (/"/) {
		printf STDERR __("warning: sendmail alias with quotes is not supported: %s\n"), $_;
	} elsif (/:include:/) {
		printf STDERR __("warning: `:include:` not supported: %s\n"), $_;
	} elsif (/[\/|]/) {
		printf STDERR __("warning: `/file` or `|pipe` redirection not supported: %s\n"), $_;
	} elsif (/^(\S+?)\s*:\s*(.+)$/) {
		my ($alias, $addr) = ($1, $2);
		$aliases{$alias} = [ split_addrs($addr) ];
	} else {
		printf STDERR __("warning: sendmail line is not recognized: %s\n"), $_;
	}
}

sub parse_sendmail_aliases {
	my $fh = shift;
	my $s = '';
	while (<$fh>) {
		chomp;
		next if /^\s*$/ || /^\s*#/;
		$s .= $_, next if $s =~ s/\\$// || s/^\s+//;
		parse_sendmail_alias($s) if $s;
		$s = $_;
	}
	$s =~ s/\\$//; # silently tolerate stray '\' on last line
	parse_sendmail_alias($s) if $s;
}

my %parse_alias = (
	# multiline formats can be supported in the future
	mutt => sub { my $fh = shift; while (<$fh>) {
		if (/^\s*alias\s+(?:-group\s+\S+\s+)*(\S+)\s+(.*)$/) {
			my ($alias, $addr) = ($1, $2);
			$addr =~ s/#.*$//; # mutt allows # comments
			# commas delimit multiple addresses
			my @addr = split_addrs($addr);

			# quotes may be escaped in the file,
			# unescape them so we do not double-escape them later.
			s/\\"/"/g foreach @addr;
			$aliases{$alias} = \@addr
		}}},
	mailrc => sub {	my $fh = shift; while (<$fh>) {
		if (/^alias\s+(\S+)\s+(.*?)\s*$/) {
			require Text::ParseWords;
			# spaces delimit multiple addresses
			$aliases{$1} = [ Text::ParseWords::quotewords('\s+', 0, $2) ];
		}}},
	pine => sub { my $fh = shift; my $f='\t[^\t]*';
	        for (my $x = ''; defined($x); $x = $_) {
			chomp $x;
		        $x .= $1 while(defined($_ = <$fh>) && /^ +(.*)$/);
			$x =~ /^(\S+)$f\t\(?([^\t]+?)\)?(:?$f){0,2}$/ or next;
			$aliases{$1} = [ split_addrs($2) ];
		}},
	elm => sub  { my $fh = shift;
		      while (<$fh>) {
			  if (/^(\S+)\s+=\s+[^=]+=\s(\S+)/) {
			      my ($alias, $addr) = ($1, $2);
			       $aliases{$alias} = [ split_addrs($addr) ];
			  }
		      } },
	sendmail => \&parse_sendmail_aliases,
	gnus => sub { my $fh = shift; while (<$fh>) {
		if (/\(define-mail-alias\s+"(\S+?)"\s+"(\S+?)"\)/) {
			$aliases{$1} = [ $2 ];
		}}}
	# Please update _git_config() in git-completion.bash when you
	# add new MUAs.
);

if (@alias_files and $aliasfiletype and defined $parse_alias{$aliasfiletype}) {
	foreach my $file (@alias_files) {
		open my $fh, '<', $file or die "opening $file: $!\n";
		$parse_alias{$aliasfiletype}->($fh);
		close $fh;
	}
}

if ($dump_aliases) {
    print "$_\n" for (sort keys %aliases);
    exit(0);
}

if ($translate_aliases) {
	while (<STDIN>) {
		my @addr_list = parse_address_line($_);
		@addr_list = expand_aliases(@addr_list);
		@addr_list = sanitize_address_list(@addr_list);
		print "$_\n" for @addr_list;
	}
	exit(0);
}

# is_format_patch_arg($f) returns 0 if $f names a patch, or 1 if
# $f is a revision list specification to be passed to format-patch.
sub is_format_patch_arg {
	return unless $repo;
	my $f = shift;
	try {
		$repo->command('rev-parse', '--verify', '--quiet', $f);
		if (defined($format_patch)) {
			return $format_patch;
		}
		die sprintf(__(<<EOF), $f, $f);
File '%s' exists but it could also be the range of commits
to produce patches for.  Please disambiguate by...

    * Saying "./%s" if you mean a file; or
    * Giving --format-patch option if you mean a range.
EOF
	} catch Git::Error::Command with {
		# Not a valid revision.  Treat it as a filename.
		return 0;
	}
}

# Now that all the defaults are set, process the rest of the command line
# arguments and collect up the files that need to be processed.
my @rev_list_opts;
while (defined(my $f = shift @ARGV)) {
	if ($f eq "--") {
		push @rev_list_opts, "--", @ARGV;
		@ARGV = ();
	} elsif (-d $f and !is_format_patch_arg($f)) {
		opendir my $dh, $f
			or die sprintf(__("Failed to opendir %s: %s"), $f, $!);

		require File::Spec;
		push @files, grep { -f $_ } map { File::Spec->catfile($f, $_) }
				sort readdir $dh;
		closedir $dh;
	} elsif ((-f $f or -p $f) and !is_format_patch_arg($f)) {
		push @files, $f;
	} else {
		push @rev_list_opts, $f;
	}
}

if (@rev_list_opts) {
	die __("Cannot run git format-patch from outside a repository\n")
		unless $repo;
	require File::Temp;
	push @files, $repo->command('format-patch', '-o', File::Temp::tempdir(CLEANUP => 1),
				    defined $reroll_count ? ('-v', $reroll_count) : (),
				    @rev_list_opts);
}

if (defined $sender) {
	$sender =~ s/^\s+|\s+$//g;
	($sender) = expand_aliases($sender);
} else {
	$sender = $repoauthor->() || $repocommitter->() || '';
}

# $sender could be an already sanitized address
# (e.g. sendemail.from could be manually sanitized by user).
# But it's a no-op to run sanitize_address on an already sanitized address.
$sender = sanitize_address($sender);

$time = time - scalar $#files;

@files = handle_backup_files(@files);

if (@files) {
	unless ($quiet) {
		print $_,"\n" for (@files);
	}
} else {
	print STDERR __("\nNo patch files specified!\n\n");
	usage();
}

sub get_patch_subject {
	my $fn = shift;
	open (my $fh, '<', $fn);
	while (my $line = <$fh>) {
		next unless ($line =~ /^Subject: (.*)$/);
		close $fh;
		return "GIT: $1\n";
	}
	close $fh;
	die sprintf(__("No subject line in %s?"), $fn);
}

if ($compose) {
	# Note that this does not need to be secure, but we will make a small
	# effort to have it be unique
	require File::Temp;
	$compose_filename = ($repo ?
		File::Temp::tempfile(".gitsendemail.msg.XXXXXX", DIR => $repo->repo_path()) :
		File::Temp::tempfile(".gitsendemail.msg.XXXXXX", DIR => "."))[1];
	open my $c, ">", $compose_filename
		or die sprintf(__("Failed to open for writing %s: %s"), $compose_filename, $!);


	my $tpl_sender = $sender || $repoauthor->() || $repocommitter->() || '';
	my $tpl_subject = $initial_subject || '';
	my $tpl_in_reply_to = $initial_in_reply_to || '';
	my $tpl_reply_to = $reply_to || '';
	my $tpl_to = join(',', @initial_to);
	my $tpl_cc = join(',', @initial_cc);
	my $tpl_bcc = join(', ', @initial_bcc);

	print $c <<EOT1, Git::prefix_lines("GIT: ", __(<<EOT2)), <<EOT3;
From $tpl_sender # This line is ignored.
EOT1
Lines beginning in "GIT:" will be removed.
Consider including an overall diffstat or table of contents
for the patch you are writing.

Clear the body content if you don't wish to send a summary.
EOT2
From: $tpl_sender
To: $tpl_to
Cc: $tpl_cc
Bcc: $tpl_bcc
Reply-To: $tpl_reply_to
Subject: $tpl_subject
In-Reply-To: $tpl_in_reply_to

EOT3
	for my $f (@files) {
		print $c get_patch_subject($f);
	}
	close $c;

	if ($annotate) {
		do_edit($compose_filename, @files);
	} else {
		do_edit($compose_filename);
	}

	open my $c2, ">", $compose_filename . ".final"
		or die sprintf(__("Failed to open %s.final: %s"), $compose_filename, $!);

	open $c, "<", $compose_filename
		or die sprintf(__("Failed to open %s: %s"), $compose_filename, $!);

	my $need_8bit_cte = file_has_nonascii($compose_filename);
	my $in_body = 0;
	my $summary_empty = 1;
	if (!defined $compose_encoding) {
		$compose_encoding = "UTF-8";
	}
	while(<$c>) {
		next if m/^GIT:/;
		if ($in_body) {
			$summary_empty = 0 unless (/^\n$/);
		} elsif (/^\n$/) {
			$in_body = 1;
			if ($need_8bit_cte) {
				print $c2 "MIME-Version: 1.0\n",
					 "Content-Type: text/plain; ",
					   "charset=$compose_encoding\n",
					 "Content-Transfer-Encoding: 8bit\n";
			}
		} elsif (/^MIME-Version:/i) {
			$need_8bit_cte = 0;
		} elsif (/^Subject:\s*(.+)\s*$/i) {
			$initial_subject = $1;
			my $subject = $initial_subject;
			$_ = "Subject: " .
				quote_subject($subject, $compose_encoding) .
				"\n";
		} elsif (/^In-Reply-To:\s*(.+)\s*$/i) {
			$initial_in_reply_to = $1;
			next;
		} elsif (/^Reply-To:\s*(.+)\s*$/i) {
			$reply_to = $1;
		} elsif (/^From:\s*(.+)\s*$/i) {
			$sender = $1;
			next;
		} elsif (/^To:\s*(.+)\s*$/i) {
			@initial_to = parse_address_line($1);
			next;
		} elsif (/^Cc:\s*(.+)\s*$/i) {
			@initial_cc = parse_address_line($1);
			next;
		} elsif (/^Bcc:/i) {
			@initial_bcc = parse_address_line($1);
			next;
		}
		print $c2 $_;
	}
	close $c;
	close $c2;

	if ($summary_empty) {
		print __("Summary email is empty, skipping it\n");
		$compose = -1;
	}
} elsif ($annotate) {
	do_edit(@files);
}

{
	# Only instantiate one $term per program run, since some
	# Term::ReadLine providers refuse to create a second instance.
	my $term;
	sub term {
		require Term::ReadLine;
		if (!defined $term) {
			$term = $ENV{"GIT_SEND_EMAIL_NOTTY"}
				? Term::ReadLine->new('git-send-email', \*STDIN, \*STDOUT)
				: Term::ReadLine->new('git-send-email');
		}
		return $term;
	}
}

sub ask {
	my ($prompt, %arg) = @_;
	my $valid_re = $arg{valid_re};
	my $default = $arg{default};
	my $confirm_only = $arg{confirm_only};
	my $resp;
	my $i = 0;
	my $term = term();
	return defined $default ? $default : undef
		unless defined $term->IN and defined fileno($term->IN) and
		       defined $term->OUT and defined fileno($term->OUT);
	while ($i++ < 10) {
		$resp = $term->readline($prompt);
		if (!defined $resp) { # EOF
			print "\n";
			return defined $default ? $default : undef;
		}
		if ($resp eq '' and defined $default) {
			return $default;
		}
		if (!defined $valid_re or $resp =~ /$valid_re/) {
			return $resp;
		}
		if ($confirm_only) {
			my $yesno = $term->readline(
				# TRANSLATORS: please keep [y/N] as is.
				sprintf(__("Are you sure you want to use <%s> [y/N]? "), $resp));
			if (defined $yesno && $yesno =~ /y/i) {
				return $resp;
			}
		}
	}
	return;
}

my %broken_encoding;

sub file_declares_8bit_cte {
	my $fn = shift;
	open (my $fh, '<', $fn);
	while (my $line = <$fh>) {
		last if ($line =~ /^$/);
		return 1 if ($line =~ /^Content-Transfer-Encoding: .*8bit.*$/);
	}
	close $fh;
	return 0;
}

foreach my $f (@files) {
	next unless (body_or_subject_has_nonascii($f)
		     && !file_declares_8bit_cte($f));
	$broken_encoding{$f} = 1;
}

if (!defined $auto_8bit_encoding && scalar %broken_encoding) {
	print __("The following files are 8bit, but do not declare " .
		 "a Content-Transfer-Encoding.\n");
	foreach my $f (sort keys %broken_encoding) {
		print "    $f\n";
	}
	while (1) {
		my $encoding = ask(
			__("Declare which 8bit encoding to use [default: UTF-8]? "),
			valid_re => qr/^\S+$/,
			default  => "UTF-8");
		next unless defined $encoding;
		if (find_encoding($encoding)) {
			$auto_8bit_encoding = $encoding;
			last;
		}
		my $yesno = ask(
			sprintf(
			__("'%s' does not appear to be a valid charset name. Use it anyway [y/N]? "),
			$encoding),
			valid_re => qr/^(?:y|n)/i,
			default => "n");
		if (defined $yesno && $yesno =~ /^y/i) {
			$auto_8bit_encoding = $encoding;
			last;
		}
	}
}

if (!$force) {
	for my $f (@files) {
		if (get_patch_subject($f) =~ /\Q*** SUBJECT HERE ***\E/) {
			die sprintf(__("Refusing to send because the patch\n\t%s\n"
				. "has the template subject '*** SUBJECT HERE ***'. "
				. "Pass --force if you really want to send.\n"), $f);
		}
	}
}

my $to_whom = __("To whom should the emails be sent (if anyone)?");
my $prompting = 0;
if (!@initial_to && !defined $to_cmd) {
	my $to = ask("$to_whom ",
		     default => "",
		     valid_re => qr/\@.*\./, confirm_only => 1);
	push @initial_to, parse_address_line($to) if defined $to; # sanitized/validated later
	$prompting++;
}

sub expand_aliases {
	return map { expand_one_alias($_) } @_;
}

my %EXPANDED_ALIASES;
sub expand_one_alias {
	my $alias = shift;
	if ($EXPANDED_ALIASES{$alias}) {
		die sprintf(__("fatal: alias '%s' expands to itself\n"), $alias);
	}
	local $EXPANDED_ALIASES{$alias} = 1;
	return $aliases{$alias} ? expand_aliases(@{$aliases{$alias}}) : $alias;
}

@initial_to = process_address_list(@initial_to);
@initial_cc = process_address_list(@initial_cc);
@initial_bcc = process_address_list(@initial_bcc);

if ($thread && !defined $initial_in_reply_to && $prompting) {
	$initial_in_reply_to = ask(
		__("Message-ID to be used as In-Reply-To for the first email (if any)? "),
		default => "",
		valid_re => qr/\@.*\./, confirm_only => 1);
}
if (defined $initial_in_reply_to) {
	$initial_in_reply_to =~ s/^\s*<?//;
	$initial_in_reply_to =~ s/>?\s*$//;
	$initial_in_reply_to = "<$initial_in_reply_to>" if $initial_in_reply_to ne '';
}

if (defined $reply_to) {
	$reply_to =~ s/^\s+|\s+$//g;
	($reply_to) = expand_aliases($reply_to);
	$reply_to = sanitize_address($reply_to);
}

if (!defined $sendmail_cmd && !defined $smtp_server) {
	my @sendmail_paths = qw( /usr/sbin/sendmail /usr/lib/sendmail );
	push @sendmail_paths, map {"$_/sendmail"} split /:/, $ENV{PATH};
	foreach (@sendmail_paths) {
		if (-x $_) {
			$sendmail_cmd = $_;
			last;
		}
	}

	if (!defined $sendmail_cmd) {
		$smtp_server = 'localhost'; # could be 127.0.0.1, too... *shrug*
	}
}

if ($compose && $compose > 0) {
	@files = ($compose_filename . ".final", @files);
}

# Variables we set as part of the loop over files
our ($message_id, %mail, $subject, $in_reply_to, $references, $message,
	$needs_confirm, $message_num, $ask_default);

sub mailmap_address_list {
	return @_ unless @_ and $mailmap;
	my @options = ();
	push(@options, "--mailmap-file=$mailmap_file") if $mailmap_file;
	push(@options, "--mailmap-blob=$mailmap_blob") if $mailmap_blob;
	my @addr_list = Git::command('check-mailmap', @options, @_);
	s/^<(.*)>$/$1/ for @addr_list;
	return @addr_list;
}

sub extract_valid_address {
	my $address = shift;
	my $local_part_regexp = qr/[^<>"\s@]+/;
	my $domain_regexp = qr/[^.<>"\s@]+(?:\.[^.<>"\s@]+)+/;

	# check for a local address:
	return $address if ($address =~ /^($local_part_regexp)$/);

	$address =~ s/^\s*<(.*)>\s*$/$1/;
	my $have_email_valid = eval { require Email::Valid; 1 };
	if ($have_email_valid) {
		return scalar Email::Valid->address($address);
	}

	# less robust/correct than the monster regexp in Email::Valid,
	# but still does a 99% job, and one less dependency
	return $1 if $address =~ /($local_part_regexp\@$domain_regexp)/;
	return;
}

sub extract_valid_address_or_die {
	my $address = shift;
	my $valid_address = extract_valid_address($address);
	die sprintf(__("error: unable to extract a valid address from: %s\n"), $address)
		if !$valid_address;
	return $valid_address;
}

sub validate_address {
	my $address = shift;
	while (!extract_valid_address($address)) {
		printf STDERR __("error: unable to extract a valid address from: %s\n"), $address;
		# TRANSLATORS: Make sure to include [q] [d] [e] in your
		# translation. The program will only accept English input
		# at this point.
		$_ = ask(__("What to do with this address? ([q]uit|[d]rop|[e]dit): "),
			valid_re => qr/^(?:quit|q|drop|d|edit|e)/i,
			default => 'q');
		if (/^d/i) {
			return undef;
		} elsif (/^q/i) {
			cleanup_compose_files();
			exit(0);
		}
		$address = ask("$to_whom ",
			default => "",
			valid_re => qr/\@.*\./, confirm_only => 1);
	}
	return $address;
}

sub validate_address_list {
	return (grep { defined $_ }
		map { validate_address($_) } @_);
}

# Usually don't need to change anything below here.

# we make a "fake" message id by taking the current number
# of seconds since the beginning of Unix time and tacking on
# a random number to the end, in case we are called quicker than
# 1 second since the last time we were called.

# We'll setup a template for the message id, using the "from" address:

my ($message_id_stamp, $message_id_serial);
sub make_message_id {
	my $uniq;
	if (!defined $message_id_stamp) {
		require POSIX;
		$message_id_stamp = POSIX::strftime("%Y%m%d%H%M%S.$$", gmtime(time));
		$message_id_serial = 0;
	}
	$message_id_serial++;
	$uniq = "$message_id_stamp-$message_id_serial";

	my $du_part;
	for ($sender, $repocommitter->(), $repoauthor->()) {
		$du_part = extract_valid_address(sanitize_address($_));
		last if (defined $du_part and $du_part ne '');
	}
	if (not defined $du_part or $du_part eq '') {
		require Sys::Hostname;
		$du_part = 'user@' . Sys::Hostname::hostname();
	}
	my $message_id_template = "<%s-%s>";
	$message_id = sprintf($message_id_template, $uniq, $du_part);
	#print "new message id = $message_id\n"; # Was useful for debugging
}

sub unquote_rfc2047 {
	local ($_) = @_;
	my $charset;
	my $sep = qr/[ \t]+/;
	s{$re_encoded_word(?:$sep$re_encoded_word)*}{
		my @words = split $sep, $&;
		foreach (@words) {
			m/$re_encoded_word/;
			$charset = $1;
			my $encoding = $2;
			my $text = $3;
			if ($encoding eq 'q' || $encoding eq 'Q') {
				$_ = $text;
				s/_/ /g;
				s/=([0-9A-F]{2})/chr(hex($1))/egi;
			} else {
				# other encodings not supported yet
			}
		}
		join '', @words;
	}eg;
	return wantarray ? ($_, $charset) : $_;
}

sub quote_rfc2047 {
	local $_ = shift;
	my $encoding = shift || 'UTF-8';
	s/([^-a-zA-Z0-9!*+\/])/sprintf("=%02X", ord($1))/eg;
	s/(.*)/=\?$encoding\?q\?$1\?=/;
	return $_;
}

sub is_rfc2047_quoted {
	my $s = shift;
	length($s) <= 75 &&
	$s =~ m/^(?:"[[:ascii:]]*"|$re_encoded_word)$/o;
}

sub subject_needs_rfc2047_quoting {
	my $s = shift;

	return ($s =~ /[^[:ascii:]]/) || ($s =~ /=\?/);
}

sub quote_subject {
	local $subject = shift;
	my $encoding = shift || 'UTF-8';

	if (subject_needs_rfc2047_quoting($subject)) {
		return quote_rfc2047($subject, $encoding);
	}
	return $subject;
}

# use the simplest quoting being able to handle the recipient
sub sanitize_address {
	my ($recipient) = @_;

	# remove garbage after email address
	$recipient =~ s/(.*>).*$/$1/;

	my ($recipient_name, $recipient_addr) = ($recipient =~ /^(.*?)\s*(<.*)/);

	if (not $recipient_name) {
		return $recipient;
	}

	# if recipient_name is already quoted, do nothing
	if (is_rfc2047_quoted($recipient_name)) {
		return $recipient;
	}

	# remove non-escaped quotes
	$recipient_name =~ s/(^|[^\\])"/$1/g;

	# rfc2047 is needed if a non-ascii char is included
	if ($recipient_name =~ /[^[:ascii:]]/) {
		$recipient_name = quote_rfc2047($recipient_name);
	}

	# double quotes are needed if specials or CTLs are included
	elsif ($recipient_name =~ /[][()<>@,;:\\".\000-\037\177]/) {
		$recipient_name =~ s/([\\\r])/\\$1/g;
		$recipient_name = qq["$recipient_name"];
	}

	return "$recipient_name $recipient_addr";

}

sub strip_garbage_one_address {
	my ($addr) = @_;
	chomp $addr;
	if ($addr =~ /^(("[^"]*"|[^"<]*)? *<[^>]*>).*/) {
		# "Foo Bar" <foobar@example.com> [possibly garbage here]
		# Foo Bar <foobar@example.com> [possibly garbage here]
		return $1;
	}
	if ($addr =~ /^(<[^>]*>).*/) {
		# <foo@example.com> [possibly garbage here]
		# if garbage contains other addresses, they are ignored.
		return $1;
	}
	if ($addr =~ /^([^"#,\s]*)/) {
		# address without quoting: remove anything after the address
		return $1;
	}
	return $addr;
}

sub sanitize_address_list {
	return (map { sanitize_address($_) } @_);
}

sub process_address_list {
	my @addr_list = map { parse_address_line($_) } @_;
	@addr_list = expand_aliases(@addr_list);
	@addr_list = sanitize_address_list(@addr_list);
	@addr_list = validate_address_list(@addr_list);
	@addr_list = mailmap_address_list(@addr_list);
	return @addr_list;
}

# Returns the local Fully Qualified Domain Name (FQDN) if available.
#
# Tightly configured MTAa require that a caller sends a real DNS
# domain name that corresponds the IP address in the HELO/EHLO
# handshake. This is used to verify the connection and prevent
# spammers from trying to hide their identity. If the DNS and IP don't
# match, the receiving MTA may deny the connection.
#
# Here is a deny example of Net::SMTP with the default "localhost.localdomain"
#
# Net::SMTP=GLOB(0x267ec28)>>> EHLO localhost.localdomain
# Net::SMTP=GLOB(0x267ec28)<<< 550 EHLO argument does not match calling host
#
# This maildomain*() code is based on ideas in Perl library Test::Reporter
# /usr/share/perl5/Test/Reporter/Mail/Util.pm ==> sub _maildomain ()

sub valid_fqdn {
	my $domain = shift;
	my $subdomain = '(?!-)[A-Za-z0-9-]{1,63}(?<!-)';
	return defined $domain && !($^O eq 'darwin' && $domain =~ /\.local$/)
		&& $domain  =~ /^$subdomain(?:\.$subdomain)*$/;
}

sub maildomain_net {
	my $maildomain;

	require Net::Domain;
	my $domain = Net::Domain::domainname();
	$maildomain = $domain if valid_fqdn($domain);

	return $maildomain;
}

sub maildomain_mta {
	my $maildomain;

	for my $host (qw(mailhost localhost)) {
		require Net::SMTP;
		my $smtp = Net::SMTP->new($host);
		if (defined $smtp) {
			my $domain = $smtp->domain;
			$smtp->quit;

			$maildomain = $domain if valid_fqdn($domain);

			last if $maildomain;
		}
	}

	return $maildomain;
}

sub maildomain_hostname_command {
	my $maildomain;

	if ($^O eq 'linux' || $^O eq 'darwin') {
		my $domain = `(hostname -f) 2>/dev/null`;
		if (!$?) {
			chomp($domain);
			$maildomain = $domain if valid_fqdn($domain);
		}
	}
	return $maildomain;
}

sub maildomain {
	return maildomain_net() || maildomain_mta() ||
		maildomain_hostname_command || 'localhost.localdomain';
}

sub smtp_host_string {
	if (defined $smtp_server_port) {
		return "$smtp_server:$smtp_server_port";
	} else {
		return $smtp_server;
	}
}

# Returns 1 if authentication succeeded or was not necessary
# (smtp_user was not specified), and 0 otherwise.

sub smtp_auth_maybe {
	if (!defined $smtp_authuser || $auth || (defined $smtp_auth && $smtp_auth eq "none")) {
		return 1;
	}

	# Workaround AUTH PLAIN/LOGIN interaction defect
	# with Authen::SASL::Cyrus
	eval {
		require Authen::SASL;
		Authen::SASL->import(qw(Perl));
	};

	# Check mechanism naming as defined in:
	# https://tools.ietf.org/html/rfc4422#page-8
	if ($smtp_auth && $smtp_auth !~ /^(\b[A-Z0-9-_]{1,20}\s*)*$/) {
		die "invalid smtp auth: '${smtp_auth}'";
	}

	# Authentication may fail not because credentials were
	# invalid but due to other reasons, in which we should not
	# reject credentials.
	$auth = Git::credential({
		'protocol' => 'smtp',
		'host' => smtp_host_string(),
		'username' => $smtp_authuser,
		# if there's no password, "git credential fill" will
		# give us one, otherwise it'll just pass this one.
		'password' => $smtp_authpass
	}, sub {
		my $cred = shift;
		my $result;
		my $error;

		# catch all SMTP auth error in a unified eval block
		eval {
			if ($smtp_auth) {
				my $sasl = Authen::SASL->new(
					mechanism => $smtp_auth,
					callback => {
						user     => $cred->{'username'},
						pass     => $cred->{'password'},
						authname => $cred->{'username'},
						host     => $smtp_server,
						(defined $smtp_server_port ? (port => $smtp_server_port) : ()),
					}
				);
				$result = $smtp->auth($sasl);
			} else {
				$result = $smtp->auth($cred->{'username'}, $cred->{'password'});
			}
			1; # ensure true value is returned if no exception is thrown
		} or do {
			$error = $@ || 'Unknown error';
		};

		return ($error
			? handle_smtp_error($error)
			: ($result ? 1 : 0));
	});

	return $auth;
}

sub handle_smtp_error {
	my ($error) = @_;

	# Parse SMTP status code from error message in:
	# https://www.rfc-editor.org/rfc/rfc5321.html
	if ($error =~ /\b(\d{3})\b/) {
		my $status_code = $1;
		if ($status_code =~ /^4/) {
			# 4yz: Transient Negative Completion reply
			warn "SMTP transient error (status code $status_code): $error";
			return 1;
		} elsif ($status_code =~ /^5/) {
			# 5yz: Permanent Negative Completion reply
			warn "SMTP permanent error (status code $status_code): $error";
			return 0;
		}
		# If no recognized status code is found, treat as transient error
		warn "SMTP unknown error: $error. Treating as transient failure.";
		return 1;
	}

	# If no status code is found, treat as transient error
	warn "SMTP generic error: $error";
	return 1;
}

sub ssl_verify_params {
	my %ret = ();

	eval {
		require IO::Socket::SSL;
		IO::Socket::SSL->import(qw/SSL_VERIFY_PEER SSL_VERIFY_NONE/);
	};
	if ($@) {
		print STDERR "Not using SSL_VERIFY_PEER due to out-of-date IO::Socket::SSL.\n";
		return;
	}

	if (!defined $smtp_ssl_cert_path) {
		# use the OpenSSL defaults
		$ret{SSL_verify_mode} = SSL_VERIFY_PEER();
	}
	else {
		if ($smtp_ssl_cert_path eq "") {
			$ret{SSL_verify_mode} = SSL_VERIFY_NONE();
		} elsif (-d $smtp_ssl_cert_path) {
			$ret{SSL_verify_mode} = SSL_VERIFY_PEER();
			$ret{SSL_ca_path} = $smtp_ssl_cert_path;
		} elsif (-f $smtp_ssl_cert_path) {
			$ret{SSL_verify_mode} = SSL_VERIFY_PEER();
			$ret{SSL_ca_file} = $smtp_ssl_cert_path;
		} else {
			die sprintf(__("CA path \"%s\" does not exist"), $smtp_ssl_cert_path);
		}
	}

	if (defined $smtp_ssl_client_cert) {
		$ret{SSL_cert_file} = $smtp_ssl_client_cert;
	}
	if (defined $smtp_ssl_client_key) {
		if (!defined $smtp_ssl_client_cert) {
			# Accept the client key only when a certificate is given.
			# We die here because this case is a user error.
			die sprintf(__("Only client key \"%s\" specified"),
				    $smtp_ssl_client_key);
		}
		$ret{SSL_key_file} = $smtp_ssl_client_key;
	}

	return %ret;
}

sub file_name_is_absolute {
	my ($path) = @_;

	# msys does not grok DOS drive-prefixes
	if ($^O eq 'msys') {
		return ($path =~ m#^/# || $path =~ m#^[a-zA-Z]\:#)
	}

	require File::Spec::Functions;
	return File::Spec::Functions::file_name_is_absolute($path);
}

sub gen_header {
	my @recipients = unique_email_list(@to);
	@cc = (grep { my $cc = extract_valid_address_or_die($_);
		      not grep { $cc eq $_ || $_ =~ /<\Q${cc}\E>$/ } @recipients
		    }
	       @cc);
	my $to = join (",\n\t", @recipients);
	@recipients = unique_email_list(@recipients,@cc,@initial_bcc);
	@recipients = (map { extract_valid_address_or_die($_) } @recipients);
	my $date = format_2822_time($time++);
	my $gitversion = '@GIT_VERSION@';
	if ($gitversion =~ m/..GIT_VERSION../) {
	    $gitversion = Git::version();
	}

	my $cc = join(",\n\t", unique_email_list(@cc));
	my $ccline = "";
	if ($cc ne '') {
		$ccline = "\nCc: $cc";
	}
	make_message_id() unless defined($message_id);

	my $header = "From: $sender
To: $to${ccline}
Subject: $subject
Date: $date
Message-ID: $message_id
";
	if ($use_xmailer) {
		$header .= "X-Mailer: git-send-email $gitversion\n";
	}
	if ($in_reply_to) {

		$header .= "In-Reply-To: $in_reply_to\n";
		$header .= "References: $references\n";
	}
	if ($reply_to) {
		$header .= "Reply-To: $reply_to\n";
	}
	if (@xh) {
		$header .= join("\n", @xh) . "\n";
	}
	my $recipients_ref = \@recipients;
	return ($recipients_ref, $to, $date, $gitversion, $cc, $ccline, $header);
}

sub is_outlook {
	my ($host) = @_;
	if ($outlook_id_fix eq 'auto') {
		$outlook_id_fix =
			($host eq 'smtp.office365.com' ||
			 $host eq 'smtp-mail.outlook.com') ? 1 : 0;
	}
	return $outlook_id_fix;
}

# Prepares the email, then asks the user what to do.
#
# If the user chooses to send the email, it's sent and 1 is returned.
# If the user chooses not to send the email, 0 is returned.
# If the user decides they want to make further edits, -1 is returned and the
# caller is expected to call send_message again after the edits are performed.
#
# If an error occurs sending the email, this just dies.

sub send_message {
	my ($recipients_ref, $to, $date, $gitversion, $cc, $ccline, $header) = gen_header();
	my @recipients = @$recipients_ref;

	my @sendmail_parameters = ('-i', @recipients);
	my $raw_from = $sender;
	if (defined $envelope_sender && $envelope_sender ne "auto") {
		$raw_from = $envelope_sender;
	}
	$raw_from = extract_valid_address($raw_from);
	unshift (@sendmail_parameters,
			'-f', $raw_from) if(defined $envelope_sender);

	if ($needs_confirm && !$dry_run) {
		print "\n$header\n";
		if ($needs_confirm eq "inform") {
			$confirm_unconfigured = 0; # squelch this message for the rest of this run
			$ask_default = "y"; # assume yes on EOF since user hasn't explicitly asked for confirmation
			print __ <<EOF ;
    The Cc list above has been expanded by additional
    addresses found in the patch commit message. By default
    send-email prompts before sending whenever this occurs.
    This behavior is controlled by the sendemail.confirm
    configuration setting.

    For additional information, run 'git send-email --help'.
    To retain the current behavior, but squelch this message,
    run 'git config --global sendemail.confirm auto'.

EOF
		}
		# TRANSLATORS: Make sure to include [y] [n] [e] [q] [a] in your
		# translation. The program will only accept English input
		# at this point.
		$_ = ask(__("Send this email? ([y]es|[n]o|[e]dit|[q]uit|[a]ll): "),
		         valid_re => qr/^(?:yes|y|no|n|edit|e|quit|q|all|a)/i,
		         default => $ask_default);
		die __("Send this email reply required") unless defined $_;
		if (/^n/i) {
			# If we are skipping a message, we should make sure that
			# the next message is treated as the successor to the
			# previously sent message, and not the skipped message.
			$message_num--;
			return 0;
		} elsif (/^e/i) {
			# Since the same message will be sent again, we need to
			# decrement the message number to the previous message.
			# Otherwise, the edited message will be treated as a
			# different message sent after the original non-edited
			# message.
			$message_num--;
			return -1;
		} elsif (/^q/i) {
			cleanup_compose_files();
			exit(0);
		} elsif (/^a/i) {
			$confirm = 'never';
		}
	}

	unshift (@sendmail_parameters, @smtp_server_options);

	if ($dry_run) {
		# We don't want to send the email.
	} elsif ($use_imap_only) {
		die __("The destination IMAP folder is not properly defined.") if !defined $imap_sent_folder;
	} elsif (defined $sendmail_cmd || file_name_is_absolute($smtp_server)) {
		my $pid = open my $sm, '|-';
		defined $pid or die $!;
		if (!$pid) {
			if (defined $sendmail_cmd) {
				exec ("sh", "-c", "$sendmail_cmd \"\$@\"", "-", @sendmail_parameters)
					or die $!;
			} else {
				exec ($smtp_server, @sendmail_parameters)
					or die $!;
			}
		}
		print $sm "$header\n$message";
		close $sm or die $!;
	} else {

		if (!defined $smtp_server) {
			die __("The required SMTP server is not properly defined.")
		}

		require Net::SMTP;
		my $use_net_smtp_ssl = version->parse($Net::SMTP::VERSION) < version->parse("2.34");
		$smtp_domain ||= maildomain();

		if ($smtp_encryption eq 'ssl') {
			$smtp_server_port ||= 465; # ssmtp
			require IO::Socket::SSL;

			# Suppress "variable accessed once" warning.
			{
				no warnings 'once';
				$IO::Socket::SSL::DEBUG = 1;
			}

			# Net::SMTP::SSL->new() does not forward any SSL options
			IO::Socket::SSL::set_client_defaults(
				ssl_verify_params());

			if ($use_net_smtp_ssl) {
				require Net::SMTP::SSL;
				$smtp ||= Net::SMTP::SSL->new($smtp_server,
							      Hello => $smtp_domain,
							      Port => $smtp_server_port,
							      Debug => $debug_net_smtp);
			}
			else {
				$smtp ||= Net::SMTP->new($smtp_server,
							 Hello => $smtp_domain,
							 Port => $smtp_server_port,
							 Debug => $debug_net_smtp,
							 SSL => 1);
			}
		}
		elsif (!$smtp) {
			$smtp_server_port ||= 25;
			$smtp ||= Net::SMTP->new($smtp_server,
						 Hello => $smtp_domain,
						 Debug => $debug_net_smtp,
						 Port => $smtp_server_port);
			if ($smtp_encryption eq 'tls' && $smtp) {
				if ($use_net_smtp_ssl) {
					$smtp->command('STARTTLS');
					$smtp->response();
					if ($smtp->code != 220) {
						die sprintf(__("Server does not support STARTTLS! %s"), $smtp->message);
					}
					require Net::SMTP::SSL;
					$smtp = Net::SMTP::SSL->start_SSL($smtp,
									  ssl_verify_params())
						or die sprintf(__("STARTTLS failed! %s"), IO::Socket::SSL::errstr());
				}
				else {
					$smtp->starttls(ssl_verify_params())
						or die sprintf(__("STARTTLS failed! %s"), IO::Socket::SSL::errstr());
				}
				# Send EHLO again to receive fresh
				# supported commands
				$smtp->hello($smtp_domain);
			}
		}

		if (!$smtp) {
			die __("Unable to initialize SMTP properly. Check config and use --smtp-debug."),
			    " VALUES: server=$smtp_server ",
			    "encryption=$smtp_encryption ",
			    "hello=$smtp_domain",
			    defined $smtp_server_port ? " port=$smtp_server_port" : "";
		}

		smtp_auth_maybe or die $smtp->message;

		$smtp->mail( $raw_from ) or die $smtp->message;
		$smtp->to( @recipients ) or die $smtp->message;
		$smtp->data or die $smtp->message;
		$smtp->datasend("$header\n") or die $smtp->message;
		my @lines = split /^/, $message;
		foreach my $line (@lines) {
			$smtp->datasend("$line") or die $smtp->message;
		}
		$smtp->dataend() or die $smtp->message;

		# Outlook discards the Message-ID header we set while sending the email
		# and generates a new random Message-ID. So in order to avoid breaking
		# threads, we simply retrieve the Message-ID from the server response
		# and assign it to the $message_id variable, which will then be
		# assigned to $in_reply_to by the caller when the next message is sent
		# as a response to this message.
		if (is_outlook($smtp_server)) {
			if ($smtp->message =~ /<([^>]+)>/) {
				$message_id = "<$1>";
				$header =~ s/^(Message-ID:\s*).*\n/${1}$message_id\n/m;
				printf __("Outlook reassigned Message-ID to: %s\n"), $message_id if $smtp->debug;
			} else {
				warn __("Warning: Could not retrieve Message-ID from server response.\n");
			}
		}

		$smtp->code =~ /250|200/ or die sprintf(__("Failed to send %s\n"), $subject).$smtp->message;
	}
	if ($quiet) {
		printf($dry_run ? __("Dry-Sent %s") : __("Sent %s"), $subject);
		print "\n";
	} else {
		print($dry_run ? __("Dry-OK. Log says:") : __("OK. Log says:"));
		print "\n";
		if (!defined $sendmail_cmd && !file_name_is_absolute($smtp_server)) {
			print "Server: $smtp_server\n";
			print "MAIL FROM:<$raw_from>\n";
			foreach my $entry (@recipients) {
			    print "RCPT TO:<$entry>\n";
			}
		} else {
			my $sm;
			if (defined $sendmail_cmd) {
				$sm = $sendmail_cmd;
			} else {
				$sm = $smtp_server;
			}

			print "Sendmail: $sm ".join(' ',@sendmail_parameters)."\n";
		}
		print $header, "\n";
		if ($smtp) {
			print __("Result: "), $smtp->code, ' ',
				($smtp->message =~ /\n([^\n]+\n)$/s);
		} else {
			print __("Result: OK");
		}
		print "\n";
	}

	if ($imap_sent_folder && !$dry_run) {
		my $imap_header = $header;
		if (@initial_bcc) {
			# Bcc is not a part of $header, so we add it here.
			# This is only for the IMAP copy, not for the actual email
			# sent to the recipients.
			$imap_header .= "Bcc: " . join(", ", @initial_bcc) . "\n";
		}
		push @imap_copy, "From git-send-email\n$imap_header\n$message";
	}

	return 1;
}

sub pre_process_file {
	my ($t, $quiet) = @_;

	open my $fh, "<", $t or die sprintf(__("can't open file %s"), $t);

	my $author = undef;
	my $sauthor = undef;
	my $author_encoding;
	my $has_content_type;
	my $body_encoding;
	my $xfer_encoding;
	my $has_mime_version;
	@to = ();
	@cc = ();
	@xh = ();
	my $input_format = undef;
	my @header = ();
	$subject = $initial_subject;
	$message = "";
	$message_num++;
	undef $message_id;
	# Retrieve and unfold header fields.
	my @header_lines = ();
	while(<$fh>) {
		last if /^\s*$/;
		push(@header_lines, $_);
	}
	@header = unfold_headers(@header_lines);
	# Add computed headers, if applicable.
	unless ($no_header_cmd || ! $header_cmd) {
		push @header, invoke_header_cmd($header_cmd, $t);
	}
	# Now parse the header
	foreach(@header) {
		if (/^From /) {
			$input_format = 'mbox';
			next;
		}
		chomp;
		if (!defined $input_format && /^[-A-Za-z]+:\s/) {
			$input_format = 'mbox';
		}

		if (defined $input_format && $input_format eq 'mbox') {
			if (/^Subject:\s+(.*)$/i) {
				$subject = $1;
			}
			elsif (/^From:\s+(.*)$/i) {
				($author, $author_encoding) = unquote_rfc2047($1);
				$sauthor = sanitize_address($author);
				next if $suppress_cc{'author'};
				next if $suppress_cc{'self'} and $sauthor eq $sender;
				printf(__("(mbox) Adding cc: %s from line '%s'\n"),
					$1, $_) unless $quiet;
				push @cc, $1;
			}
			elsif (/^To:\s+(.*)$/i) {
				foreach my $addr (parse_address_line($1)) {
					printf(__("(mbox) Adding to: %s from line '%s'\n"),
						$addr, $_) unless $quiet;
					push @to, $addr;
				}
			}
			elsif (/^Cc:\s+(.*)$/i) {
				foreach my $addr (parse_address_line($1)) {
					my $qaddr = unquote_rfc2047($addr);
					my $saddr = sanitize_address($qaddr);
					if ($saddr eq $sender) {
						next if ($suppress_cc{'self'});
					} else {
						next if ($suppress_cc{'cc'});
					}
					printf(__("(mbox) Adding cc: %s from line '%s'\n"),
						$addr, $_) unless $quiet;
					push @cc, $addr;
				}
			}
			elsif (/^Content-type:/i) {
				$has_content_type = 1;
				if (/charset="?([^ "]+)/) {
					$body_encoding = $1;
				}
				push @xh, $_;
			}
			elsif (/^MIME-Version/i) {
				$has_mime_version = 1;
				push @xh, $_;
			}
			elsif (/^Message-ID: (.*)/i) {
				$message_id = $1;
			}
			elsif (/^Content-Transfer-Encoding: (.*)/i) {
				$xfer_encoding = $1 if not defined $xfer_encoding;
			}
			elsif (/^In-Reply-To: (.*)/i) {
				if (!$initial_in_reply_to || $thread) {
					$in_reply_to = $1;
				}
			}
			elsif (/^Reply-To: (.*)/i) {
				$reply_to = $1;
			}
			elsif (/^References: (.*)/i) {
				if (!$initial_in_reply_to || $thread) {
					$references = $1;
				}
			}
			elsif (!/^Date:\s/i && /^[-A-Za-z]+:\s+\S/) {
				push @xh, $_;
			}
		} else {
			# In the traditional
			# "send lots of email" format,
			# line 1 = cc
			# line 2 = subject
			# So let's support that, too.
			$input_format = 'lots';
			if (@cc == 0 && !$suppress_cc{'cc'}) {
				printf(__("(non-mbox) Adding cc: %s from line '%s'\n"),
					$_, $_) unless $quiet;
				push @cc, $_;
			} elsif (!defined $subject) {
				$subject = $_;
			}
		}
	}
	# Now parse the message body
	while(<$fh>) {
		$message .=  $_;
		if (/^([a-z][a-z-]*-by|Cc): (.*)/i) {
			chomp;
			my ($what, $c) = ($1, $2);
			# strip garbage for the address we'll use:
			$c = strip_garbage_one_address($c);
			# sanitize a bit more to decide whether to suppress the address:
			my $sc = sanitize_address($c);
			if ($sc eq $sender) {
				next if ($suppress_cc{'self'});
			} else {
				if ($what =~ /^Signed-off-by$/i) {
					next if $suppress_cc{'sob'};
				} elsif ($what =~ /-by$/i) {
					next if $suppress_cc{'misc-by'};
				} elsif ($what =~ /Cc/i) {
					next if $suppress_cc{'bodycc'};
				}
			}
			if ($c !~ /.+@.+|<.+>/) {
				printf("(body) Ignoring %s from line '%s'\n",
					$what, $_) unless $quiet;
				next;
			}
			push @cc, $sc;
			printf(__("(body) Adding cc: %s from line '%s'\n"),
				$sc, $_) unless $quiet;
		}
	}
	close $fh;

	push @to, recipients_cmd("to-cmd", "to", $to_cmd, $t, $quiet)
		if defined $to_cmd;
	push @cc, recipients_cmd("cc-cmd", "cc", $cc_cmd, $t, $quiet)
		if defined $cc_cmd && !$suppress_cc{'cccmd'};

	if ($broken_encoding{$t} && !$has_content_type) {
		$xfer_encoding = '8bit' if not defined $xfer_encoding;
		$has_content_type = 1;
		push @xh, "Content-Type: text/plain; charset=$auto_8bit_encoding";
		$body_encoding = $auto_8bit_encoding;
	}

	if ($broken_encoding{$t} && !is_rfc2047_quoted($subject)) {
		$subject = quote_subject($subject, $auto_8bit_encoding);
	}

	if (defined $sauthor and $sauthor ne $sender) {
		$message = "From: $author\n\n$message";
		if (defined $author_encoding) {
			if ($has_content_type) {
				if ($body_encoding eq $author_encoding) {
					# ok, we already have the right encoding
				}
				else {
					# uh oh, we should re-encode
				}
			}
			else {
				$xfer_encoding = '8bit' if not defined $xfer_encoding;
				$has_content_type = 1;
				push @xh,
				  "Content-Type: text/plain; charset=$author_encoding";
			}
		}
	}
	$xfer_encoding = '8bit' if not defined $xfer_encoding;
	($message, $xfer_encoding) = apply_transfer_encoding(
		$message, $xfer_encoding, $target_xfer_encoding);
	push @xh, "Content-Transfer-Encoding: $xfer_encoding";
	unshift @xh, 'MIME-Version: 1.0' unless $has_mime_version;

	$needs_confirm = (
		$confirm eq "always" or
		($confirm =~ /^(?:auto|cc)$/ && @cc) or
		($confirm =~ /^(?:auto|compose)$/ && $compose && $message_num == 1));
	$needs_confirm = "inform" if ($needs_confirm && $confirm_unconfigured && @cc);

	@to = process_address_list(@to);
	@cc = process_address_list(@cc);

	@to = (@initial_to, @to);
	@cc = (@initial_cc, @cc);

	if ($message_num == 1) {
		if (defined $cover_cc and $cover_cc) {
			@initial_cc = @cc;
		}
		if (defined $cover_to and $cover_to) {
			@initial_to = @to;
		}
	}
}

# Prepares the email, prompts the user, and sends it out
# Returns 0 if an edit was done and the function should be called again, or 1
# on the email being successfully sent out.
sub process_file {
	my ($t) = @_;

        pre_process_file($t, $quiet);

	my $message_was_sent = send_message();
	if ($message_was_sent == -1) {
		do_edit($t);
		return 0;
	}

	# set up for the next message
	if ($thread) {
		if ($message_was_sent &&
		  ($chain_reply_to || !defined $in_reply_to || length($in_reply_to) == 0 ||
		  $message_num == 1)) {
			$in_reply_to = $message_id;
			if (length $references > 0) {
				$references .= "\n $message_id";
			} else {
				$references = "$message_id";
			}
		}
	} elsif (!defined $initial_in_reply_to) {
		# --thread and --in-reply-to manage the "In-Reply-To" header and by
		# extension the "References" header. If these commands are not used, reset
		# the header values to their defaults.
		$in_reply_to = undef;
		$references = '';
	}
	$message_id = undef;
	$num_sent++;
	if (defined $batch_size && $num_sent == $batch_size) {
		$num_sent = 0;
		$smtp->quit if defined $smtp;
		undef $smtp;
		undef $auth;
		sleep($relogin_delay) if defined $relogin_delay;
	}

	return 1;
}

sub initialize_modified_loop_vars {
	$in_reply_to = $initial_in_reply_to;
	$references = $initial_in_reply_to || '';
	$message_num = 0;
}

if ($validate) {
	# FIFOs can only be read once, exclude them from validation.
	my @real_files = ();
	foreach my $f (@files) {
		unless (-p $f) {
			push(@real_files, $f);
		}
	}

	# Validate the SMTP server port, if provided.
	if (defined $smtp_server_port) {
		my $port = Git::port_num($smtp_server_port);
		if ($port) {
			$smtp_server_port = $port;
		} else  {
			die sprintf(__("error: invalid SMTP port '%s'\n"),
				    $smtp_server_port);
		}
	}

	# Run the loop once again to avoid gaps in the counter due to FIFO
	# arguments provided by the user.
	my $num = 1;
	my $num_files = scalar @real_files;
	$ENV{GIT_SENDEMAIL_FILE_TOTAL} = "$num_files";
	initialize_modified_loop_vars();
	foreach my $r (@real_files) {
		$ENV{GIT_SENDEMAIL_FILE_COUNTER} = "$num";
		pre_process_file($r, 1);
		validate_patch($r, $target_xfer_encoding);
		$num += 1;
	}
	delete $ENV{GIT_SENDEMAIL_FILE_COUNTER};
	delete $ENV{GIT_SENDEMAIL_FILE_TOTAL};
}

initialize_modified_loop_vars();
foreach my $t (@files) {
	while (!process_file($t)) {
		# user edited the file
	}
}

# Execute a command and return its output lines as an array.  Blank
# lines which do not appear at the end of the output are reported as
# errors.
sub execute_cmd {
	my ($prefix, $cmd, $file) = @_;
	my @lines = ();
	my $seen_blank_line = 0;
	open my $fh, "-|", "$cmd \Q$file\E"
		or die sprintf(__("(%s) Could not execute '%s'"), $prefix, $cmd);
	while (my $line = <$fh>) {
		die sprintf(__("(%s) Malformed output from '%s'"), $prefix, $cmd)
		    if $seen_blank_line;
		if ($line =~ /^$/) {
			$seen_blank_line = $line =~ /^$/;
			next;
		}
		push @lines, $line;
	}
	close $fh
	    or die sprintf(__("(%s) failed to close pipe to '%s'"), $prefix, $cmd);
	return @lines;
}

# Process headers lines, unfolding multiline headers as defined by RFC
# 2822.
sub unfold_headers {
	my @headers;
	foreach(@_) {
		last if /^\s*$/;
		if (/^\s+\S/ and @headers) {
			chomp($headers[$#headers]);
			s/^\s+/ /;
			$headers[$#headers] .= $_;
		} else {
			push(@headers, $_);
		}
	}
	return @headers;
}

# Invoke the provided CMD with FILE as an argument, which should
# output RFC 2822 email headers. Fold multiline headers and return the
# headers as an array.
sub invoke_header_cmd {
	my ($cmd, $file) = @_;
	my @lines = execute_cmd("header-cmd", $header_cmd, $file);
	return unfold_headers(@lines);
}

# Execute a command (e.g. $to_cmd) to get a list of email addresses
# and return a results array
sub recipients_cmd {
	my ($prefix, $what, $cmd, $file, $quiet) = @_;
	my @lines = ();
	my @addresses = ();

	@lines = execute_cmd($prefix, $cmd, $file);
	for my $address (@lines) {
		$address =~ s/^\s*//g;
		$address =~ s/\s*$//g;
		$address = sanitize_address($address);
		next if ($address eq $sender and $suppress_cc{'self'});
		push @addresses, $address;
		printf(__("(%s) Adding %s: %s from: '%s'\n"),
		       $prefix, $what, $address, $cmd) unless $quiet;
		}
	return @addresses;
}

cleanup_compose_files();

sub cleanup_compose_files {
	unlink($compose_filename, $compose_filename . ".final") if $compose;
}

$smtp->quit if $smtp;

if ($imap_sent_folder && @imap_copy && !$dry_run) {
	my $imap_input = join("\n", @imap_copy);
	eval {
		print "\nStarting git imap-send...\n";
		my ($fh, $ctx) = Git::command_input_pipe(['imap-send', '-f', $imap_sent_folder]);
		print $fh $imap_input;
		Git::command_close_pipe($fh, $ctx);
		1;
	} or do {
		warn "Warning: failed to send messages to IMAP folder $imap_sent_folder: $@";
	};
}

sub apply_transfer_encoding {
	my $message = shift;
	my $from = shift;
	my $to = shift;

	return ($message, $to) if ($from eq $to and $from ne '7bit');

	require MIME::QuotedPrint;
	require MIME::Base64;

	$message = MIME::QuotedPrint::decode($message)
		if ($from eq 'quoted-printable');
	$message = MIME::Base64::decode($message)
		if ($from eq 'base64');

	$to = ($message =~ /(?:.{999,}|\r)/) ? 'quoted-printable' : '8bit'
		if $to eq 'auto';

	die __("cannot send message as 7bit")
		if ($to eq '7bit' and $message =~ /[^[:ascii:]]/);
	return ($message, $to)
		if ($to eq '7bit' or $to eq '8bit');
	return (MIME::QuotedPrint::encode($message, "\n", 0), $to)
		if ($to eq 'quoted-printable');
	return (MIME::Base64::encode($message, "\n"), $to)
		if ($to eq 'base64');
	die __("invalid transfer encoding");
}

sub unique_email_list {
	my %seen;
	my @emails;

	foreach my $entry (@_) {
		my $clean = extract_valid_address_or_die($entry);
		$seen{$clean} ||= 0;
		next if $seen{$clean}++;
		push @emails, $entry;
	}
	return @emails;
}

sub validate_patch {
	my ($fn, $xfer_encoding) = @_;

	if ($repo) {
		my $hook_name = 'sendemail-validate';
		my $hooks_path = $repo->command_oneline('rev-parse', '--git-path', 'hooks');
		require File::Spec;
		my $validate_hook = File::Spec->catfile($hooks_path, $hook_name);
		my $hook_error;
		if (-x $validate_hook) {
			require Cwd;
			my $target = Cwd::abs_path($fn);
			# The hook needs a correct cwd and GIT_DIR.
			my $cwd_save = Cwd::getcwd();
			chdir($repo->wc_path() or $repo->repo_path())
				or die("chdir: $!");
			local $ENV{"GIT_DIR"} = $repo->repo_path();

			my ($recipients_ref, $to, $date, $gitversion, $cc, $ccline, $header) = gen_header();

			require File::Temp;
			my ($header_filehandle, $header_filename) = File::Temp::tempfile(
                            TEMPLATE => ".gitsendemail.header.XXXXXX",
                            DIR => $repo->repo_path(),
                            UNLINK => 1,
                        );
			print $header_filehandle $header;

			my @cmd = ("git", "hook", "run", "--ignore-missing",
				    $hook_name, "--");
			my @cmd_msg = (@cmd, "<patch>", "<header>");
			my @cmd_run = (@cmd, $target, $header_filename);
			$hook_error = system_or_msg(\@cmd_run, undef, "@cmd_msg");
			chdir($cwd_save) or die("chdir: $!");
		}
		if ($hook_error) {
			$hook_error = sprintf(
			    __("fatal: %s: rejected by %s hook\n%s\nwarning: no patches were sent\n"),
			    $fn, $hook_name, $hook_error);
			die $hook_error;
		}
	}

	# Any long lines will be automatically fixed if we use a suitable transfer
	# encoding.
	unless ($xfer_encoding =~ /^(?:auto|quoted-printable|base64)$/) {
		open(my $fh, '<', $fn)
			or die sprintf(__("unable to open %s: %s\n"), $fn, $!);
		while (my $line = <$fh>) {
			if (length($line) > 998) {
				die sprintf(__("fatal: %s:%d is longer than 998 characters\n" .
					       "warning: no patches were sent\n"), $fn, $.);
			}
		}
	}
	return;
}

sub handle_backup {
	my ($last, $lastlen, $file, $known_suffix) = @_;
	my ($suffix, $skip);

	$skip = 0;
	if (defined $last &&
	    ($lastlen < length($file)) &&
	    (substr($file, 0, $lastlen) eq $last) &&
	    ($suffix = substr($file, $lastlen)) !~ /^[a-z0-9]/i) {
		if (defined $known_suffix && $suffix eq $known_suffix) {
			printf(__("Skipping %s with backup suffix '%s'.\n"), $file, $known_suffix);
			$skip = 1;
		} else {
			# TRANSLATORS: please keep "[y|N]" as is.
			my $answer = ask(sprintf(__("Do you really want to send %s? [y|N]: "), $file),
					 valid_re => qr/^(?:y|n)/i,
					 default => 'n');
			$skip = ($answer ne 'y');
			if ($skip) {
				$known_suffix = $suffix;
			}
		}
	}
	return ($skip, $known_suffix);
}

sub handle_backup_files {
	my @file = @_;
	my ($last, $lastlen, $known_suffix, $skip, @result);
	for my $file (@file) {
		($skip, $known_suffix) = handle_backup($last, $lastlen,
						       $file, $known_suffix);
		push @result, $file unless $skip;
		$last = $file;
		$lastlen = length($file);
	}
	return @result;
}

sub file_has_nonascii {
	my $fn = shift;
	open(my $fh, '<', $fn)
		or die sprintf(__("unable to open %s: %s\n"), $fn, $!);
	while (my $line = <$fh>) {
		return 1 if $line =~ /[^[:ascii:]]/;
	}
	return 0;
}

sub body_or_subject_has_nonascii {
	my $fn = shift;
	open(my $fh, '<', $fn)
		or die sprintf(__("unable to open %s: %s\n"), $fn, $!);
	while (my $line = <$fh>) {
		last if $line =~ /^$/;
		return 1 if $line =~ /^Subject.*[^[:ascii:]]/;
	}
	while (my $line = <$fh>) {
		return 1 if $line =~ /[^[:ascii:]]/;
	}
	return 0;
}
