{"thread":{"id":"11811","subject":"[PATCH] git-send-email: ssh/login style password requests","startedAt":"2008-02-01T04:59:14Z","lastAt":"2008-02-04T00:53:58Z","messageCount":16,"participants":["Michael Witten","Junio C Hamano"],"isPatch":true,"patchVersion":1,"patchTotal":null},"messages":[{"id":"67005","messageId":"1201841954-17949-1-git-send-email-mfwitten@mit.edu","threadId":"11811","inReplyTo":null,"subject":"[PATCH] git-send-email: ssh/login style password requests","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-01T04:59:14Z","receivedAt":"2008-02-01T04:59:14Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"Whilst convenient, it is most unwise to record passwords\nin any place but one's brain. Moreover, it is especially\nfoolish to store them in configuration files, even with\naccess permissions set accordingly.\n\ngit-send-email has been amended, so that if it detects\nan smtp username without a password, it promptly prompts\nfor the password and masks the input for privacy.\n\nFurthermore, the argument to --smtp-pass has been rendered\noptional.\n\nThe documentation has been updated to reflect these changes.\n\nSigned-off-by: Michael Witten <mfwitten@mit.edu>\n---\n\n\tThis was sent with the updated git-send-email ;-)\n\n Documentation/git-send-email.txt |   19 +++++++++++++++----\n git-send-email.perl              |   23 +++++++++++++++++++----\n 2 files changed, 34 insertions(+), 8 deletions(-)\n\ndiff --git a/Documentation/git-send-email.txt b/Documentation/git-send-email.txt\nindex 0554f2b..6d5abf4 100644\n--- a/Documentation/git-send-email.txt\n+++ b/Documentation/git-send-email.txt\n@@ -96,12 +96,23 @@ The --cc option must be repeated for each user you want on the cc list.\n \tservers typically listen to smtp port 25 and ssmtp port\n \t465).\n \n---smtp-user, --smtp-pass::\n-\tUsername and password for SMTP-AUTH. Defaults are the values of\n-\tthe configuration values 'sendemail.smtpuser' and\n-\t'sendemail.smtppass', but see also 'sendemail.identity'.\n+--smtp-user::\n+\tUsername for SMTP-AUTH. The default value can be specified\n+\twith the configuration variable 'sendemail.smtpuser' or\n+\tsendemail.<identity>.smtpuser (see sendemail.identity).\n \tIf not set, authentication is not attempted.\n \n+--smtp-pass::\n+\tPassword for SMTP-AUTH. The default value can be specified\n+\twith the configuration variable 'sendemail.smtppass' or\n+\tsendemail.<identity>.smtppass (see sendemail.identity).\n+\tThe argument is optional: If no argument is specified, then\n+\tthe password is assumed to be the empty string.\n+\tIf a username has been set, but no password has been set,\n+\tthe user is prompted for a password with masked input for\n+\tprivacy; passwords need not be recorded in configuration\n+\tfiles.\n+\n --smtp-ssl::\n \tIf set, connects to the SMTP server using SSL.\n \tDefault is the value of the 'sendemail.smtpssl' configuration value;\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex a1a9d14..ed0a473 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -157,7 +157,7 @@ my $compose_filename = \".msg.$$\";\n \n # Variables we fill in automatically, or via prompting:\n my (@to,@cc,@initial_cc,@bcclist,@xh,\n-\t$initial_reply_to,$initial_subject,@files,$author,$sender,$compose,$time);\n+\t$initial_reply_to,$initial_subject,@files,$author,$sender,$smtp_authpass,$compose,$time);\n \n my $envelope_sender;\n \n@@ -177,7 +177,7 @@ my ($quiet, $dry_run) = (0, 0);\n \n # Variables with corresponding config settings\n my ($thread, $chain_reply_to, $suppress_from, $signed_off_cc, $cc_cmd);\n-my ($smtp_server, $smtp_server_port, $smtp_authuser, $smtp_authpass, $smtp_ssl);\n+my ($smtp_server, $smtp_server_port, $smtp_authuser, $smtp_ssl);\n my ($identity, $aliasfiletype, @alias_files, @smtp_host_parts);\n my ($no_validate);\n \n@@ -214,7 +214,7 @@ my $rc = GetOptions(\"sender|from=s\" => \\$sender,\n \t\t    \"smtp-server=s\" => \\$smtp_server,\n \t\t    \"smtp-server-port=s\" => \\$smtp_server_port,\n \t\t    \"smtp-user=s\" => \\$smtp_authuser,\n-\t\t    \"smtp-pass=s\" => \\$smtp_authpass,\n+\t\t    \"smtp-pass:s\" => \\$smtp_authpass,\n \t\t    \"smtp-ssl!\" => \\$smtp_ssl,\n \t\t    \"identity=s\" => \\$identity,\n \t\t    \"compose\" => \\$compose,\n@@ -647,9 +647,24 @@ X-Mailer: git-send-email $gitversion\n \t\t\tdie \"Unable to initialize SMTP properly.  Is there something wrong with your config?\";\n \t\t}\n \n-\t\tif ((defined $smtp_authuser) && (defined $smtp_authpass)) {\n+\t\tif (defined $smtp_authuser) {\n+\n+\t\t\tif (!defined $smtp_authpass) {\n+\t\t\t\t\n+\t\t\t\tsystem \"stty -echo\";\n+\n+\t\t\t\tdo {\n+\t\t\t\t\t$_ = $term->readline(\"Password: \");\n+\t\t\t\t} while (!defined $_);\n+\n+\t\t\t\tsystem \"stty echo\";\n+\n+\t\t\t\t$smtp_authpass = $_ if ($_);\n+\t\t\t}\n+\n \t\t\t$auth ||= $smtp->auth( $smtp_authuser, $smtp_authpass ) or die $smtp->message;\n \t\t}\n+\n \t\t$smtp->mail( $raw_from ) or die $smtp->message;\n \t\t$smtp->to( @recipients ) or die $smtp->message;\n \t\t$smtp->data or die $smtp->message;\n-- \n1.5.4.rc5.17.g536ee\n"},{"id":"67021","messageId":"7vodb19edp.fsf@gitster.siamese.dyndns.org","threadId":"11811","inReplyTo":"1201841954-17949-1-git-send-email-mfwitten@mit.edu","subject":"Re: [PATCH] git-send-email: ssh/login style password requests","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2008-02-01T10:09:54Z","receivedAt":"2008-02-01T10:09:54Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Michael Witten <mfwitten@MIT.EDU> writes:\n\n> +--smtp-pass::\n> +\tPassword for SMTP-AUTH. The default value can be specified\n> +\twith the configuration variable 'sendemail.smtppass' or\n> +\tsendemail.<identity>.smtppass (see sendemail.identity).\n> +\tThe argument is optional: If no argument is specified, then\n> +\tthe password is assumed to be the empty string.\n> +\tIf a username has been set, but no password has been set,\n> +\tthe user is prompted for a password with masked input for\n> +\tprivacy; passwords need not be recorded in configuration\n> +\tfiles.\n\nI am a bit puzzled about the above description, though.  It is\nnot clear if there is any difference between \"the empty string\"\npassword, and \"no password has been set\".  It makes me wonder\nwhat the possible cases are.\n\n (1) no *.smtppass configuration present; no --smtp-pass parameter\n     is given on the command line.\n\n (2) *.smtppass configuration present but is an empty string; no\n     --smtp-pass parameter is given on the command line.\n\n (3) *.smtppass configuration present with a non-empty string; no\n     --smtp-pass parameter is given on the command line.\n\n (4) parameter is given with an empty string (i.e. \"--smtp-pass=\")\n     on the command line.\n\n (5) parameter is given with a non-empty string (i.e. \"--smtp-pass=foo\")\n     on the command line.\n\nMy _guess_ is that command line always trump configuration so\nin cases (4) and (5) it does not matter what you have (or do not\nhave) in *.smtppass configuration.  In other cases, lack of *.smtppass\nand having *.smtppass with an empty string as its value are equivalent.\nAnd in any case, an empty string (or lack of specification) results\nin prompting.\n\nBut you shouldn't make _me_ guess.  You certainly would be\nforcing many other people to guess with this.\n\n> +\t\tif (defined $smtp_authuser) {\n> +\n> +\t\t\tif (!defined $smtp_authpass) {\n> +\t\t\t\t\n> +\t\t\t\tsystem \"stty -echo\";\n> +\n> +\t\t\t\tdo {\n> +\t\t\t\t\t$_ = $term->readline(\"Password: \");\n> +\t\t\t\t} while (!defined $_);\n> +\n> +\t\t\t\tsystem \"stty echo\";\n> +\n> +\t\t\t\t$smtp_authpass = $_ if ($_);\n> +\t\t\t}\n> +\n\nI like what the patch tries to do, but the system() there feels\na tad ugly.  In addition it makes me wonder (1) what happens if\nyou ^C out from this while loop, and (2) $term->readline()\ninterface might already have a method to turn echo off.\n\nWe luckily have people handy at Perl on the list, so I'll wait\nfor our resident Perl experts to suggest a better alterantive.\n\nWe are not in a hurry, so I expect a polished resubmit after\n1.5.4.  Thanks.\n"},{"id":"67038","messageId":"FE992810-2B2E-4C23-A7D3-AD4C39D925ED@MIT.EDU","threadId":"11811","inReplyTo":"7vodb19edp.fsf@gitster.siamese.dyndns.org","subject":"Re: [PATCH] git-send-email: ssh/login style password requests","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-01T18:38:47Z","receivedAt":"2008-02-01T18:38:47Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"\nOn 1 Feb 2008, at 5:09 AM, Junio C Hamano wrote:\n\n> Michael Witten <mfwitten@MIT.EDU> writes:\n>\n>> +--smtp-pass::\n>> +\tPassword for SMTP-AUTH. The default value can be specified\n>> +\twith the configuration variable 'sendemail.smtppass' or\n>> +\tsendemail.<identity>.smtppass (see sendemail.identity).\n>> +\tThe argument is optional: If no argument is specified, then\n>> +\tthe password is assumed to be the empty string.\n>> +\tIf a username has been set, but no password has been set,\n>> +\tthe user is prompted for a password with masked input for\n>> +\tprivacy; passwords need not be recorded in configuration\n>> +\tfiles.\n>\n> I am a bit puzzled about the above description, though.  It is\n> not clear if there is any difference between \"the empty string\"\n> password, and \"no password has been set\".  It makes me wonder\n> what the possible cases are.\n\nHow are these descriptions:\n\n\thttp://web.mit.edu/mfwitten/git-send-email.html\n\nI've attempted to keep them short, but complete. Also, the\nresulting man page versions are formatted similarly (though\nat the expense of some ASCIIdoc readability).\n\n> In other cases, lack of *.smtppass\n> and having *.smtppass with an empty string as its value are  \n> equivalent.\n> And in any case, an empty string (or lack of specification) results\n> in prompting.\n\nActually, a lack of *.smtp<user|pass> results in variables without\ndefinition rather than with empty-string values; the original code,\ntoo, makes use of this fact. Consequently, an empty string for\n*.smtppass does not result in prompting, as tested.\n\n>> +\t\tif (defined $smtp_authuser) {\n>> +\n>> +\t\t\tif (!defined $smtp_authpass) {\n>> +\t\t\t\t\n>> +\t\t\t\tsystem \"stty -echo\";\n>> +\n>> +\t\t\t\tdo {\n>> +\t\t\t\t\t$_ = $term->readline(\"Password: \");\n>> +\t\t\t\t} while (!defined $_);\n>> +\n>> +\t\t\t\tsystem \"stty echo\";\n>> +\n>> +\t\t\t\t$smtp_authpass = $_ if ($_);\n>> +\t\t\t}\n>> +\n>\n> I like what the patch tries to do, but the system() there feels\n> a tad ugly.  In addition it makes me wonder (1) what happens if\n> you ^C out from this while loop\n\nGood question! Though I'm not sure you can handle this any other\nway than to intercept the signal.\n\n> (2) $term->readline() interface might already have a method to turn  \n> echo off.\n\nI have very limited knowledge of these things, especially of Perl's  \ninterfaces,\nbut this is what `perldoc -q password` has to say about it:\n\n> \tThere's an example of this in \"crypt\" in perlfunc).\n> \tFirst, you put the terminal into \"no echo\" mode,\n> \tthen just read the password normally.  You may do\n> \tthis with an old-style ioctl() function, POSIX\n> \tterminal control (see POSIX or its documentation\n> \tthe Camel Book), or a call to the stty program,\n> \twith varying degrees of portability.\n> \t\n> \tYou can also do this for most systems using the\n> \tTerm::ReadKey module from CPAN, which is easier\n> \tto use and in theory more portable.\n> \t\n> \t   use Term::ReadKey;\n> \t\n> \t   ReadMode('noecho');\n> \t   $password = ReadLine(0);\n\nMy code is from the \"crypt\" version. The other versions require\nextra module dependencies, and the portability doesn't extend\nimmediately to Windows with any of these methods.\n\n> We are not in a hurry, so I expect a polished resubmit after\n> 1.5.4.  Thanks.\n\nGreat!\n\nSincerely,\nMichael Witten\n"},{"id":"67044","messageId":"5F77BB5B-8D2B-42FD-A805-7195757B14EE@mit.edu","threadId":"11811","inReplyTo":"FE992810-2B2E-4C23-A7D3-AD4C39D925ED@MIT.EDU","subject":"Re: [PATCH] git-send-email: ssh/login style password requests","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-01T22:42:12Z","receivedAt":"2008-02-01T22:42:12Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"\nOn 1 Feb 2008, at 1:38 PM, Michael Witten wrote:\n\n>> I like what the patch tries to do, but the system() there feels\n>> a tad ugly.  In addition it makes me wonder (1) what happens if\n>> you ^C out from this while loop\n>\n> Good question! Though I'm not sure you can handle this any other\n> way than to intercept the signal.\n\nIt turns out that --compose will also leave some temporary files\nbehind if git-send-email is terminated out of course.\n\nShould I establish a general handler for SIGTERM and SIGINT?\n\nMichael Witten\n"},{"id":"67050","messageId":"7v4pcs8d4z.fsf@gitster.siamese.dyndns.org","threadId":"11811","inReplyTo":"5F77BB5B-8D2B-42FD-A805-7195757B14EE@mit.edu","subject":"Re: [PATCH] git-send-email: ssh/login style password requests","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2008-02-01T23:34:20Z","receivedAt":"2008-02-01T23:34:20Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Michael Witten <mfwitten@MIT.EDU> writes:\n\n> It turns out that --compose will also leave some temporary files\n> behind if git-send-email is terminated out of course.\n>\n> Should I establish a general handler for SIGTERM and SIGINT?\n\nI was mostly worried about ^C leaving the terminal in a funny\nstate with your system(stty).\n\nI do not think you should lose the message the user carefully\ncomposed using an editor upon seeing ^C.  The user may start to\ncompose, edit the message, and then at some later time decide to\nstop the mail-sending procedure by ^C-ing out.  The user would\nthank you if you somehow left an escape hatch to allow salvaging\nthe message, instead of having it to be re-typed from scratch.\n"},{"id":"67051","messageId":"E83D03C8-5D96-4110-A047-B7B5F7582F3B@MIT.EDU","threadId":"11811","inReplyTo":"7v4pcs8d4z.fsf@gitster.siamese.dyndns.org","subject":"Re: [PATCH] git-send-email: ssh/login style password requests","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-01T23:42:30Z","receivedAt":"2008-02-01T23:42:30Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"\nOn 1 Feb 2008, at 6:34 PM, Junio C Hamano wrote:\n\n> Michael Witten <mfwitten@MIT.EDU> writes:\n>\n>> It turns out that --compose will also leave some temporary files\n>> behind if git-send-email is terminated out of course.\n>>\n>> Should I establish a general handler for SIGTERM and SIGINT?\n>\n> I was mostly worried about ^C leaving the terminal in a funny\n> state with your system(stty).\n>\n> I do not think you should lose the message the user carefully\n> composed using an editor upon seeing ^C.  The user may start to\n> compose, edit the message, and then at some later time decide to\n> stop the mail-sending procedure by ^C-ing out.  The user would\n> thank you if you somehow left an escape hatch to allow salvaging\n> the message, instead of having it to be re-typed from scratch.\n\nIndeed. How about a message stating that these files exist?\n\nIn any case, I'm looking for your endorsement of a signal handler\nas the means to solve the main problem.\n"},{"id":"67060","messageId":"7vve586tbz.fsf@gitster.siamese.dyndns.org","threadId":"11811","inReplyTo":"E83D03C8-5D96-4110-A047-B7B5F7582F3B@MIT.EDU","subject":"Re: [PATCH] git-send-email: ssh/login style password requests","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2008-02-02T01:27:28Z","receivedAt":"2008-02-02T01:27:28Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Michael Witten <mfwitten@MIT.EDU> writes:\n\n> In any case, I'm looking for your endorsement of a signal handler\n> as the means to solve the main problem.\n\nHeh, unfortunately I am not \"the resident Perl expert on the\nlist\", so I would be waiting for suggestions from them.\n"},{"id":"67077","messageId":"1201925161-9864-1-git-send-email-mfwitten@mit.edu","threadId":"11811","inReplyTo":"7vve586tbz.fsf@gitster.siamese.dyndns.org","subject":"[PATCH 1/2][Perlers?] git-send-email: ssh/login style password requests","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-02T04:06:00Z","receivedAt":"2008-02-02T04:06:00Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"Whilst convenient, it is most unwise to record passwords\nin any place but one's brain. Moreover, it is especially\nfoolish to store them in configuration files, even with\naccess permissions set accordingly.\n\ngit-send-email has been amended, so that if it detects\nan smtp username without a password, it promptly prompts\nfor the password and masks the input for privacy.\n\nFurthermore, the argument to --smtp-pass has been rendered\noptional.\n\nThe documentation has been updated to reflect these changes.\n\nSigned-off-by: Michael Witten <mfwitten@mit.edu>\n---\n\n\tPerlers, please comment.\n\t\n\tBecause AsciiDoc is a nuisance, the modifications\n\tbelow are somewhat difficult to discern. Please\n\ttake look here:\n\t\n\t\thttp://web.mit.edu/mfwitten/git-send-email.html\n\t\n\tAlso, I have quoted the man page text below:\n\t\n>\t--smtp-user\n>\t   Username for SMTP-AUTH. In place of this option, the following\n>\t   configuration variables can be specified:\n>\t\n>\t   o  sendemail.smtpuser\n>\t\n>\t   o  sendemail.<identity>.smtpuser (see sendemail.identity).\n>\t\n>\t   However, --smtp-user always overrides these variables.\n>\t\n>\t   If a username is not specified (with --smtp-user or a configuration\n>\t   variable), then authentication is not attempted.\n>\t\n>\t--smtp-pass\n>\t   Password for SMTP-AUTH. The argument is optional: If no argument is\n>\t   specified, then the empty string is used as the password.\n>\t\n>\t   In place of this option, the following configuration variables can\n>\t   be specified:\n>\t\n>\t   o  sendemail.smtppass\n>\t\n>\t   o  sendemail.<identity>.smtppass (see sendemail.identity).\n>\t\n>\t   However, --smtp-pass always overrides these variables.\n>\t\n>\t   Furthermore, passwords need not be specified in configuration files\n>\t   or on the command line. If a username has been specified (with\n>\t   --smtp-user or a configuration variable), but no password has been\n>\t   specified (with --smtp-pass or a configuration variable), then the\n>\t   user is prompted for a password while the input is masked for\n>\t   privacy.\n\n Documentation/git-send-email.txt |   39 +++++++++++++++++++++++++++++++++----\n git-send-email.perl              |   23 ++++++++++++++++++---\n 2 files changed, 53 insertions(+), 9 deletions(-)\n\ndiff --git a/Documentation/git-send-email.txt b/Documentation/git-send-email.txt\nindex 0554f2b..4f4caa4 100644\n--- a/Documentation/git-send-email.txt\n+++ b/Documentation/git-send-email.txt\n@@ -96,11 +96,40 @@ The --cc option must be repeated for each user you want on the cc list.\n \tservers typically listen to smtp port 25 and ssmtp port\n \t465).\n \n---smtp-user, --smtp-pass::\n-\tUsername and password for SMTP-AUTH. Defaults are the values of\n-\tthe configuration values 'sendemail.smtpuser' and\n-\t'sendemail.smtppass', but see also 'sendemail.identity'.\n-\tIf not set, authentication is not attempted.\n+--smtp-user::\n+\tUsername for SMTP-AUTH. In place of this option, the following\n+\tconfiguration variables can be specified:\n++\n+--\n+\t\t* sendemail.smtpuser\n+\t\t* sendemail.<identity>.smtpuser (see sendemail.identity).\n+--\n++\n+However, --smtp-user always overrides these variables.\n++\n+If a username is not specified (with --smtp-user or a\n+configuration variable), then authentication is not attempted.\n+\n+--smtp-pass::\n+\tPassword for SMTP-AUTH. The argument is optional: If no\n+\targument is specified, then the empty string is used as\n+\tthe password.\n++\n+In place of this option, the following configuration variables\n+can be specified:\n++\n+--\n+\t\t* sendemail.smtppass\n+\t\t* sendemail.<identity>.smtppass (see sendemail.identity).\n+--\n++\n+However, --smtp-pass always overrides these variables.\n++\n+Furthermore, passwords need not be specified in configuration files\n+or on the command line. If a username has been specified (with\n+--smtp-user or a configuration variable), but no password has been\n+specified (with --smtp-pass or a configuration variable), then the\n+user is prompted for a password while the input is masked for privacy.\n \n --smtp-ssl::\n \tIf set, connects to the SMTP server using SSL.\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex a1a9d14..ed0a473 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -157,7 +157,7 @@ my $compose_filename = \".msg.$$\";\n \n # Variables we fill in automatically, or via prompting:\n my (@to,@cc,@initial_cc,@bcclist,@xh,\n-\t$initial_reply_to,$initial_subject,@files,$author,$sender,$compose,$time);\n+\t$initial_reply_to,$initial_subject,@files,$author,$sender,$smtp_authpass,$compose,$time);\n \n my $envelope_sender;\n \n@@ -177,7 +177,7 @@ my ($quiet, $dry_run) = (0, 0);\n \n # Variables with corresponding config settings\n my ($thread, $chain_reply_to, $suppress_from, $signed_off_cc, $cc_cmd);\n-my ($smtp_server, $smtp_server_port, $smtp_authuser, $smtp_authpass, $smtp_ssl);\n+my ($smtp_server, $smtp_server_port, $smtp_authuser, $smtp_ssl);\n my ($identity, $aliasfiletype, @alias_files, @smtp_host_parts);\n my ($no_validate);\n \n@@ -214,7 +214,7 @@ my $rc = GetOptions(\"sender|from=s\" => \\$sender,\n \t\t    \"smtp-server=s\" => \\$smtp_server,\n \t\t    \"smtp-server-port=s\" => \\$smtp_server_port,\n \t\t    \"smtp-user=s\" => \\$smtp_authuser,\n-\t\t    \"smtp-pass=s\" => \\$smtp_authpass,\n+\t\t    \"smtp-pass:s\" => \\$smtp_authpass,\n \t\t    \"smtp-ssl!\" => \\$smtp_ssl,\n \t\t    \"identity=s\" => \\$identity,\n \t\t    \"compose\" => \\$compose,\n@@ -647,9 +647,24 @@ X-Mailer: git-send-email $gitversion\n \t\t\tdie \"Unable to initialize SMTP properly.  Is there something wrong with your config?\";\n \t\t}\n \n-\t\tif ((defined $smtp_authuser) && (defined $smtp_authpass)) {\n+\t\tif (defined $smtp_authuser) {\n+\n+\t\t\tif (!defined $smtp_authpass) {\n+\t\t\t\t\n+\t\t\t\tsystem \"stty -echo\";\n+\n+\t\t\t\tdo {\n+\t\t\t\t\t$_ = $term->readline(\"Password: \");\n+\t\t\t\t} while (!defined $_);\n+\n+\t\t\t\tsystem \"stty echo\";\n+\n+\t\t\t\t$smtp_authpass = $_ if ($_);\n+\t\t\t}\n+\n \t\t\t$auth ||= $smtp->auth( $smtp_authuser, $smtp_authpass ) or die $smtp->message;\n \t\t}\n+\n \t\t$smtp->mail( $raw_from ) or die $smtp->message;\n \t\t$smtp->to( @recipients ) or die $smtp->message;\n \t\t$smtp->data or die $smtp->message;\n-- \n1.5.4.rc5.17.g8ca921-dirty\n"},{"id":"67076","messageId":"1201925161-9864-2-git-send-email-mfwitten@mit.edu","threadId":"11811","inReplyTo":"1201925161-9864-1-git-send-email-mfwitten@mit.edu","subject":"[PATCH 2/2][Perlers?] git-send-email: SIG{TERM,INT} handlers","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-02T04:06:01Z","receivedAt":"2008-02-02T04:06:01Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"A single signal handler is used for both SIGTERM\nand SIGINT in order to clean up after an uncouth\ntermination of git-send-email.\n\nIn particular, the handler resets the text color\n(this cleanup was already present), turns on tty\nechoing (in case termination occurrs during a\nmasked Password prompt), and informs the user of\nof any temporary files created by --compose.\n\nSigned-off-by: Michael Witten <mfwitten@mit.edu>\n---\n\n\tPerlers, please comment.\n\n git-send-email.perl |   25 +++++++++++++++++++++++--\n 1 files changed, 23 insertions(+), 2 deletions(-)\n\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex ed0a473..a0c9e8f 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -24,8 +24,6 @@ use Data::Dumper;\n use Term::ANSIColor;\n use Git;\n \n-$SIG{INT} = sub { print color(\"reset\"), \"\\n\"; exit };\n-\n package FakeTerm;\n sub new {\n \tmy ($class, $reason) = @_;\n@@ -201,6 +199,29 @@ my %config_settings = (\n     \"aliasesfile\" => \\@alias_files,\n );\n \n+# Handle Uncouth Termination\n+sub signal_handler{\n+\t\n+\t# Make text normal\n+\tprint color(\"reset\"), \"\\n\";\n+\n+\t# SMTP password masked\n+\tsystem \"stty echo\";\n+\n+\t# tmp files from --compose\n+\tif (-e $compose_filename) {\n+\t\tprint \"'$compose_filename' contains an intermediate version of the email you were composing.\\n\";\n+\t}\n+\tif (-e ($compose_filename . \".final\")) {\n+\t\tprint \"'$compose_filename.final' contains the composed email.\\n\"\n+\t}\n+\n+\texit;\n+};\n+\n+$SIG{TERM} = \\&signal_handler;\n+$SIG{INT}  = \\&signal_handler;\n+\n # Begin by accumulating all the variables (defined above), that we will end up\n # needing, first, from the command line:\n \n-- \n1.5.4.rc5.17.g8ca921-dirty\n"},{"id":"67160","messageId":"7vve5711wa.fsf@gitster.siamese.dyndns.org","threadId":"11811","inReplyTo":"1201925161-9864-1-git-send-email-mfwitten@mit.edu","subject":"Re: [PATCH 1/2][Perlers?] git-send-email: ssh/login style password requests","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2008-02-02T21:31:17Z","receivedAt":"2008-02-02T21:31:17Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Michael Witten <mfwitten@MIT.EDU> writes:\n\n>  2 files changed, 53 insertions(+), 9 deletions(-)\n\nDocumentation part looks very clear.  Thanks.\n\n> +\t\tif (defined $smtp_authuser) {\n> +\n> +\t\t\tif (!defined $smtp_authpass) {\n> +\t\t\t\t\n> +\t\t\t\tsystem \"stty -echo\";\n> +\n> +\t\t\t\tdo {\n> +\t\t\t\t\t$_ = $term->readline(\"Password: \");\n> +\t\t\t\t} while (!defined $_);\n> +\n> +\t\t\t\tsystem \"stty echo\";\n> +\n> +\t\t\t\t$smtp_authpass = $_ if ($_);\n> +\t\t\t}\n> +\n\nAnother example which appears in PerlFAQ #8 uses ReadKey with\nits ReadLine, like this:\n\n    use Term::ReadKey;\n    ReadMode('noecho');\n    $password = ReadLine(0);\n\nwhich is different from Term::ReadLine's \"ReadLine\".  An earlier\nexample you cited from perlfunc.pod's crypt() entry does:\n\n    system \"stty -echo\";\n    print \"Password: \";\n    chomp($word = <STDIN>);\n    print \"\\n\";\n    system \"stty echo\";\n\nIn either case, I was worried about the interaction between the\nTerm::ReadLine backend implementation and \"stty\".\n\nActually, I just tried this myself:\n\n    #!/usr/bin/perl -w\n\n    use Term::ReadLine;\n    my $term = new Term::ReadLine 'foobar';\n\n    my ($user, $password);\n    while (!defined $user) {\n            $user = $term->readline(\"User: \");\n    }\n    system 'stty -echo';\n    while (!defined $password) {\n            $password = $term->readline(\"Password: \");\n    }\n    system 'stty echo';\n    print \"You said <$user><$password>\\n\";\n    print \"ReadLine backend used was \", $term->ReadLine, \"\\n\";\n\nIn my case, the backend was \"Term::ReadLine::Perl\".  A few\nproblems:\n\n * After typing \"junio <Enter>\" to \"User:\", an extra newline is\n   left before \"Password:\" prompt;\n\n * \"Password:\" prompt still echoed password \"abc\".  There was no\n   extra newline before \"You said <junio><abc>\".\n\n * In either case, typing <Enter> returns an empty string from\n   $term->readline() so the \"while (!defined)\" loop does not buy\n   us anything.\n\n\n \n"},{"id":"67161","messageId":"7vprvf11vv.fsf@gitster.siamese.dyndns.org","threadId":"11811","inReplyTo":"1201925161-9864-2-git-send-email-mfwitten@mit.edu","subject":"Re: [PATCH 2/2][Perlers?] git-send-email: SIG{TERM,INT} handlers","fromName":"Junio C Hamano","fromEmail":"gitster@pobox.com","sentAt":"2008-02-02T21:31:32Z","receivedAt":"2008-02-02T21:31:32Z","isPatch":true,"sender":{"key":"gitster@pobox.com","avatar":"https://avatars.githubusercontent.com/u/54884?v=4"},"body":"Michael Witten <mfwitten@MIT.EDU> writes:\n\n> +# Handle Uncouth Termination\n> +sub signal_handler{\n> +\t\n> +\t# Make text normal\n> +\tprint color(\"reset\"), \"\\n\";\n> +\n> +\t# SMTP password masked\n> +\tsystem \"stty echo\";\n> +\n> +\t# tmp files from --compose\n> +\tif (-e $compose_filename) {\n> +\t\tprint \"'$compose_filename' contains an intermediate version of the email you were composing.\\n\";\n> +\t}\n> +\tif (-e ($compose_filename . \".final\")) {\n> +\t\tprint \"'$compose_filename.final' contains the composed email.\\n\"\n> +\t}\n> +\n> +\texit;\n> +};\n> +\n> +$SIG{TERM} = \\&signal_handler;\n> +$SIG{INT}  = \\&signal_handler;\n> +\n>  # Begin by accumulating all the variables (defined above), that we will end up\n>  # needing, first, from the command line:\n\nNow I think this patch (except the part about \"stty echo\") makes\nsense, although I did not try killing a send-email session with\nsignals myself.\n\nSuccess stories, people?\n"},{"id":"67243","messageId":"87CDEC9F-8153-48D0-AD1C-A3B3CEF6FDAE@MIT.EDU","threadId":"11811","inReplyTo":"7vve5711wa.fsf@gitster.siamese.dyndns.org","subject":"Re: [PATCH 1/2][Perlers?] git-send-email: ssh/login style password requests","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-03T17:59:21Z","receivedAt":"2008-02-03T17:59:21Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"The crux of my conclusion comes after the ---------------------------- .\n\nOn 2 Feb 2008, at 4:31 PM, Junio C Hamano wrote:\n\n> Actually, I just tried this myself:\n>\n>    #!/usr/bin/perl -w\n>\n>    use Term::ReadLine;\n>    my $term = new Term::ReadLine 'foobar';\n>\n>    my ($user, $password);\n>    while (!defined $user) {\n>            $user = $term->readline(\"User: \");\n>    }\n>    system 'stty -echo';\n>    while (!defined $password) {\n>            $password = $term->readline(\"Password: \");\n>    }\n>    system 'stty echo';\n>    print \"You said <$user><$password>\\n\";\n>    print \"ReadLine backend used was \", $term->ReadLine, \"\\n\";\n>\n> In my case, the backend was \"Term::ReadLine::Perl\".  A few\n> problems:\n>\n> * After typing \"junio <Enter>\" to \"User:\", an extra newline is\n>   left before \"Password:\" prompt;\n\nI didn't have this problem.\n\n> * \"Password:\" prompt still echoed password \"abc\".  There was no\n>   extra newline before \"You said <junio><abc>\".\n\nIndeed. I tested your code and my git-send-email code with all three\nbackend implementations (Term::ReadLine::Stub, Term::ReadLine::Gnu, and\nTerm::ReadLine::Perl). The problem with echoing seems to be a fault of\nthe Term::ReadLine::Perl implementation.\n\n> * In either case, typing <Enter> returns an empty string from\n>   $term->readline() so the \"while (!defined)\" loop does not buy\n>   us anything.\n\nFrankly, I wrote that readline code according to the other uses of  \nreadline,\nas I am not well versed in these things.\n\nBecause all other uses of readline are wrapped in such while loops, I  \nassume\nthat they are meant to cover systems with non-blocking (unbuffered)  \nIO, rather\nthan to continue to prompt the user due to empty strings.\n\nShould empty-string passwords not be allowed?\n\n-------------------------------------------------\n\n> Another example which appears in PerlFAQ #8 uses ReadKey with\n> its ReadLine, like this:\n>\n>    use Term::ReadKey;\n>    ReadMode('noecho');\n>    $password = ReadLine(0);\n>\n> which is different from Term::ReadLine's \"ReadLine\".  An earlier\n> example you cited from perlfunc.pod's crypt() entry does:\n>\n>    system \"stty -echo\";\n>    print \"Password: \";\n>    chomp($word = <STDIN>);\n>    print \"\\n\";\n>    system \"stty echo\";\n>\n> In either case, I was worried about the interaction between the\n> Term::ReadLine backend implementation and \"stty\".\n\nThis got me thinking: At first I wanted to use readline for the  \npassword prompt,\nbecause I figured it would allow the user better editing facilities,  \nespecially\nwith regard to the arrow keys. However, it occurred to me that perhaps  \nthis should\nnot be the case; perhaps arrow keys are meant to be useable in  \npasswords, etc.\n\nWell, this turns out to be the case! (which may not be a surprise to  \nmost people,\nbut it was to me). Passwords can actually contain some of the keycodes  \nthat read-\nline converts into editing commands (now you know which characters you  \ndon't have\nto test when cracking my password). Therefore, we shouldn't even  \nbother using the\nreadline backend for password prompting; neither passwd nor ssh use  \nreadline, for\nexample.\n\nI support the 'crypt' method, because the Term::ReadKey approach  \nrequires another\nmodule dependency.\n\nSincerely,\nMichael Witten\n"},{"id":"67257","messageId":"5C100A3B-0B4A-4D4E-B68B-1A54674A795A@mit.edu","threadId":"11811","inReplyTo":"87CDEC9F-8153-48D0-AD1C-A3B3CEF6FDAE@MIT.EDU","subject":"Re: [PATCH 1/2][Perlers?] git-send-email: ssh/login style password requests","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-03T20:59:14Z","receivedAt":"2008-02-03T20:59:14Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"\nOn 3 Feb 2008, at 12:59 PM, Michael Witten wrote:\n\n>> * \"Password:\" prompt still echoed password \"abc\".  There was no\n>>  extra newline before \"You said <junio><abc>\".\n>\n> Indeed. I tested your code and my git-send-email code with all three\n> backend implementations (Term::ReadLine::Stub, Term::ReadLine::Gnu,  \n> and\n> Term::ReadLine::Perl). The problem with echoing seems to be a fault of\n> the Term::ReadLine::Perl implementation.\n\nYiarg!\n\nIt would appear that Term::ReadLine::Gnu's implementation (of at least\nreadline) delays signal handling, so that ^c (C-d) doesn't do anything  \nwhile\nthe prompt is up; I suppose this is an artifact of of this:\n\n\thttp://perldoc.perl.org/perlipc.html#Deferred-Signals-(Safe-Signals)\n\nFor instance:\n\n\tWhat subject should the initial email start with?<^c><ENTER>\n\nOnly after <ENTER> is the handler invoked.\n\n>> * In either case, typing <Enter> returns an empty string from\n>>  $term->readline() so the \"while (!defined)\" loop does not buy\n>>  us anything.\n>\n> Frankly, I wrote that readline code according to the other uses of  \n> readline,\n> as I am not well versed in these things.\n>\n> Because all other uses of readline are wrapped in such while loops,  \n> I assume\n> that they are meant to cover systems with non-blocking (unbuffered)  \n> IO, rather\n> than to continue to prompt the user due to empty strings.\n>\n> Should empty-string passwords not be allowed?\n\n\nPerhaps these loops are meant to handle ^d (C-d; VEOF). This is  \nbecause issuing\nEOF causes input operators/functions to return undefined; in fact,  \nusing just the\n'crypt' method, ^d is unhandled, causing a runtime error. Is there a  \nway to setup\na signal handler for this control character rather than using checks?\n\nMichael Witten\n"},{"id":"67298","messageId":"1202086438-16251-1-git-send-email-mfwitten@mit.edu","threadId":"11811","inReplyTo":"5C100A3B-0B4A-4D4E-B68B-1A54674A795A@mit.edu","subject":"[PATCH 1/3][V.2] git-send-email: ssh/login style password requests","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-04T00:53:56Z","receivedAt":"2008-02-04T00:53:56Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"Whilst convenient, it is most unwise to record passwords\nin any place but one's brain. Moreover, it is especially\nfoolish to store them in configuration files, even with\naccess permissions set accordingly.\n\ngit-send-email has been amended, so that if it detects\nan smtp username without a password, it promptly prompts\nfor the password and masks the input for privacy.\n\nFurthermore, the argument to --smtp-pass has been rendered\noptional.\n\nThe documentation has been updated to reflect these changes.\n\nSigned-off-by: Michael Witten <mfwitten@mit.edu>\n---\n\n\tThe backend ambiguity of Term:ReadLine is avoided, and EOF\n\tis handled for the Password Prompt.\n\n Documentation/git-send-email.txt |   39 +++++++++++++++++++++++++++++++++----\n git-send-email.perl              |   25 ++++++++++++++++++++---\n 2 files changed, 55 insertions(+), 9 deletions(-)\n\ndiff --git a/Documentation/git-send-email.txt b/Documentation/git-send-email.txt\nindex 0554f2b..4f4caa4 100644\n--- a/Documentation/git-send-email.txt\n+++ b/Documentation/git-send-email.txt\n@@ -96,11 +96,40 @@ The --cc option must be repeated for each user you want on the cc list.\n \tservers typically listen to smtp port 25 and ssmtp port\n \t465).\n \n---smtp-user, --smtp-pass::\n-\tUsername and password for SMTP-AUTH. Defaults are the values of\n-\tthe configuration values 'sendemail.smtpuser' and\n-\t'sendemail.smtppass', but see also 'sendemail.identity'.\n-\tIf not set, authentication is not attempted.\n+--smtp-user::\n+\tUsername for SMTP-AUTH. In place of this option, the following\n+\tconfiguration variables can be specified:\n++\n+--\n+\t\t* sendemail.smtpuser\n+\t\t* sendemail.<identity>.smtpuser (see sendemail.identity).\n+--\n++\n+However, --smtp-user always overrides these variables.\n++\n+If a username is not specified (with --smtp-user or a\n+configuration variable), then authentication is not attempted.\n+\n+--smtp-pass::\n+\tPassword for SMTP-AUTH. The argument is optional: If no\n+\targument is specified, then the empty string is used as\n+\tthe password.\n++\n+In place of this option, the following configuration variables\n+can be specified:\n++\n+--\n+\t\t* sendemail.smtppass\n+\t\t* sendemail.<identity>.smtppass (see sendemail.identity).\n+--\n++\n+However, --smtp-pass always overrides these variables.\n++\n+Furthermore, passwords need not be specified in configuration files\n+or on the command line. If a username has been specified (with\n+--smtp-user or a configuration variable), but no password has been\n+specified (with --smtp-pass or a configuration variable), then the\n+user is prompted for a password while the input is masked for privacy.\n \n --smtp-ssl::\n \tIf set, connects to the SMTP server using SSL.\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex a1a9d14..fec55ea 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -157,7 +157,7 @@ my $compose_filename = \".msg.$$\";\n \n # Variables we fill in automatically, or via prompting:\n my (@to,@cc,@initial_cc,@bcclist,@xh,\n-\t$initial_reply_to,$initial_subject,@files,$author,$sender,$compose,$time);\n+\t$initial_reply_to,$initial_subject,@files,$author,$sender,$smtp_authpass,$compose,$time);\n \n my $envelope_sender;\n \n@@ -177,7 +177,7 @@ my ($quiet, $dry_run) = (0, 0);\n \n # Variables with corresponding config settings\n my ($thread, $chain_reply_to, $suppress_from, $signed_off_cc, $cc_cmd);\n-my ($smtp_server, $smtp_server_port, $smtp_authuser, $smtp_authpass, $smtp_ssl);\n+my ($smtp_server, $smtp_server_port, $smtp_authuser, $smtp_ssl);\n my ($identity, $aliasfiletype, @alias_files, @smtp_host_parts);\n my ($no_validate);\n \n@@ -214,7 +214,7 @@ my $rc = GetOptions(\"sender|from=s\" => \\$sender,\n \t\t    \"smtp-server=s\" => \\$smtp_server,\n \t\t    \"smtp-server-port=s\" => \\$smtp_server_port,\n \t\t    \"smtp-user=s\" => \\$smtp_authuser,\n-\t\t    \"smtp-pass=s\" => \\$smtp_authpass,\n+\t\t    \"smtp-pass:s\" => \\$smtp_authpass,\n \t\t    \"smtp-ssl!\" => \\$smtp_ssl,\n \t\t    \"identity=s\" => \\$identity,\n \t\t    \"compose\" => \\$compose,\n@@ -647,9 +647,26 @@ X-Mailer: git-send-email $gitversion\n \t\t\tdie \"Unable to initialize SMTP properly.  Is there something wrong with your config?\";\n \t\t}\n \n-\t\tif ((defined $smtp_authuser) && (defined $smtp_authpass)) {\n+\t\tif (defined $smtp_authuser) {\n+\n+\t\t\tif (!defined $smtp_authpass) {\n+\n+\t\t\t\tsystem \"stty -echo\";\n+\n+\t\t\t\tdo {\n+\t\t\t\t\tprint \"Password: \";\n+\t\t\t\t\t$_ = <STDIN>;\n+\t\t\t\t\tprint \"\\n\";\n+\t\t\t\t} while (!defined $_);\n+\n+\t\t\t\tchomp($smtp_authpass = $_);\n+\n+\t\t\t\tsystem \"stty echo\";\n+\t\t\t}\n+\n \t\t\t$auth ||= $smtp->auth( $smtp_authuser, $smtp_authpass ) or die $smtp->message;\n \t\t}\n+\n \t\t$smtp->mail( $raw_from ) or die $smtp->message;\n \t\t$smtp->to( @recipients ) or die $smtp->message;\n \t\t$smtp->data or die $smtp->message;\n-- \n1.5.4.9.gcc769-dirty\n"},{"id":"67300","messageId":"1202086438-16251-2-git-send-email-mfwitten@mit.edu","threadId":"11811","inReplyTo":"1202086438-16251-1-git-send-email-mfwitten@mit.edu","subject":"[PATCH 2/3][V.2] git-send-email: SIG{TERM,INT} handlers","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-04T00:53:57Z","receivedAt":"2008-02-04T00:53:57Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"A single signal handler is used for both SIGTERM\nand SIGINT in order to clean up after an uncouth\ntermination of git-send-email.\n\nIn particular, the handler resets the text color\n(this cleanup was already present), turns on tty\nechoing (in case termination occurrs during a\nmasked Password prompt), and informs the user of\nof any temporary files created by --compose.\n\nSigned-off-by: Michael Witten <mfwitten@mit.edu>\n---\n git-send-email.perl |   25 +++++++++++++++++++++++--\n 1 files changed, 23 insertions(+), 2 deletions(-)\n\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex fec55ea..14268fc 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -24,8 +24,6 @@ use Data::Dumper;\n use Term::ANSIColor;\n use Git;\n \n-$SIG{INT} = sub { print color(\"reset\"), \"\\n\"; exit };\n-\n package FakeTerm;\n sub new {\n \tmy ($class, $reason) = @_;\n@@ -201,6 +199,29 @@ my %config_settings = (\n     \"aliasesfile\" => \\@alias_files,\n );\n \n+# Handle Uncouth Termination\n+sub signal_handler {\n+\n+\t# Make text normal\n+\tprint color(\"reset\"), \"\\n\";\n+\n+\t# SMTP password masked\n+\tsystem \"stty echo\";\n+\n+\t# tmp files from --compose\n+\tif (-e $compose_filename) {\n+\t\tprint \"'$compose_filename' contains an intermediate version of the email you were composing.\\n\";\n+\t}\n+\tif (-e ($compose_filename . \".final\")) {\n+\t\tprint \"'$compose_filename.final' contains the composed email.\\n\"\n+\t}\n+\n+\texit;\n+};\n+\n+$SIG{TERM} = \\&signal_handler;\n+$SIG{INT}  = \\&signal_handler;\n+\n # Begin by accumulating all the variables (defined above), that we will end up\n # needing, first, from the command line:\n \n-- \n1.5.4.9.gcc769-dirty\n"},{"id":"67297","messageId":"1202086438-16251-3-git-send-email-mfwitten@mit.edu","threadId":"11811","inReplyTo":"1202086438-16251-2-git-send-email-mfwitten@mit.edu","subject":"[PATCH 3/3][V.2] git-send-email: Better handling of EOF [^D]","fromName":"Michael Witten","fromEmail":"mfwitten@mit.edu","sentAt":"2008-02-04T00:53:58Z","receivedAt":"2008-02-04T00:53:58Z","isPatch":true,"sender":{"key":"mfwitten@gmail.com","avatar":"https://avatars.githubusercontent.com/u/597101?v=4"},"body":"Before, when the user sent the EOF control character,\nthe prompts would be repeated on the same line as the\nprevious prompt.\n\nNow, repeat prompts display on separate lines.\n\nSigned-off-by: Michael Witten <mfwitten@mit.edu>\n---\n git-send-email.perl |   46 +++++++++++++++++++++++++++++-----------------\n 1 files changed, 29 insertions(+), 17 deletions(-)\n\ndiff --git a/git-send-email.perl b/git-send-email.perl\nindex 14268fc..6724810 100755\n--- a/git-send-email.perl\n+++ b/git-send-email.perl\n@@ -376,9 +376,12 @@ if (@files) {\n my $prompting = 0;\n if (!defined $sender) {\n \t$sender = $repoauthor || $repocommitter;\n-\tdo {\n+\n+\twhile (1) {\n \t\t$_ = $term->readline(\"Who should the emails appear to be from? [$sender] \");\n-\t} while (!defined $_);\n+\t\tlast if defined $_;\n+\t\tprint \"\\n\";\n+\t}\n \n \t$sender = $_ if ($_);\n \tprint \"Emails will be sent from: \", $sender, \"\\n\";\n@@ -386,10 +389,14 @@ if (!defined $sender) {\n }\n \n if (!@to) {\n-\tdo {\n-\t\t$_ = $term->readline(\"Who should the emails be sent to? \",\n-\t\t\t\t\"\");\n-\t} while (!defined $_);\n+\n+\n+\twhile (1) {\n+\t\t$_ = $term->readline(\"Who should the emails be sent to? \", \"\");\n+\t\tlast if defined $_;\n+\t\tprint \"\\n\";\n+\t}\n+\n \tmy $to = $_;\n \tpush @to, split /,/, $to;\n \t$prompting++;\n@@ -411,20 +418,23 @@ sub expand_aliases {\n @bcclist = expand_aliases(@bcclist);\n \n if (!defined $initial_subject && $compose) {\n-\tdo {\n-\t\t$_ = $term->readline(\"What subject should the initial email start with? \",\n-\t\t\t$initial_subject);\n-\t} while (!defined $_);\n+\twhile (1) {\n+\t\t$_ = $term->readline(\"What subject should the initial email start with? \", $initial_subject);\n+\t\tlast if defined $_;\n+\t\tprint \"\\n\";\n+\t}\n+\n \t$initial_subject = $_;\n \t$prompting++;\n }\n \n if ($thread && !defined $initial_reply_to && $prompting) {\n-\tdo {\n-\t\t$_= $term->readline(\"Message-ID to be used as In-Reply-To for the first email? \",\n-\t\t\t$initial_reply_to);\n-\t} while (!defined $_);\n-\n+\twhile (1) {\n+\t\t$_= $term->readline(\"Message-ID to be used as In-Reply-To for the first email? \", $initial_reply_to);\n+\t\tlast if defined $_;\n+\t\tprint \"\\n\";\n+\t}\n+\t\n \t$initial_reply_to = $_;\n }\n if (defined $initial_reply_to && $_ ne \"\") {\n@@ -474,9 +484,11 @@ EOT\n \tclose(C);\n \tclose(C2);\n \n-\tdo {\n+\twhile (1) {\n \t\t$_ = $term->readline(\"Send this email? (y|n) \");\n-\t} while (!defined $_);\n+\t\tlast if defined $_;\n+\t\tprint \"\\n\";\n+\t}\n \n \tif (uc substr($_,0,1) ne 'Y') {\n \t\tcleanup_compose_files();\n-- \n1.5.4.9.gcc769-dirty\n"}]}