diff --git a/ext/standard/mail.c b/ext/standard/mail.c index 0243ec897a05e..41e2a02078e78 100644 --- a/ext/standard/mail.c +++ b/ext/standard/mail.c @@ -25,6 +25,10 @@ #include "ext/date/php_date.h" #include "zend_smart_str.h" +#ifdef HAVE_SYS_WAIT_H +#include +#endif + #ifdef HAVE_SYSEXITS_H # include #endif @@ -562,6 +566,7 @@ PHPAPI bool php_mail(const char *to, const char *subject, const char *message, c } if (sendmail) { + int ret; #ifndef PHP_WIN32 if (EACCES == errno) { php_error_docref(NULL, E_WARNING, "Permission denied: unable to execute shell to run mail delivery binary '%s'", sendmail_path); @@ -582,26 +587,47 @@ PHPAPI bool php_mail(const char *to, const char *subject, const char *message, c fprintf(sendmail, "%s%s", hdr, line_sep); } fprintf(sendmail, "%s%s%s", line_sep, message, line_sep); - int ret = pclose(sendmail); +#ifdef PHP_WIN32 + ret = pclose(sendmail); #if PHP_SIGCHILD if (sig_handler) { signal(SIGCHLD, sig_handler); } #endif - -#ifdef PHP_WIN32 - if (ret == -1) #else + int wstatus = pclose(sendmail); +#if PHP_SIGCHILD + if (sig_handler) { + signal(SIGCHLD, sig_handler); + } +#endif + /* Determine the wait(2) exit status */ + if (wstatus == -1) { + php_error_docref(NULL, E_WARNING, "Sendmail pclose failed %d (%s)", errno, strerror(errno)); + MAIL_RET(false); + } else if (WIFSIGNALED(wstatus)) { + php_error_docref(NULL, E_WARNING, "Sendmail killed by signal %d (%s)", WTERMSIG(wstatus), strsignal(WTERMSIG(wstatus))); + MAIL_RET(false); + } else { + if (WIFEXITED(wstatus)) { + ret = WEXITSTATUS(wstatus); + } else { + php_error_docref(NULL, E_WARNING, "Sendmail did not exit"); + MAIL_RET(false); + } + } +#endif + #if defined(EX_TEMPFAIL) if ((ret != EX_OK)&&(ret != EX_TEMPFAIL)) #elif defined(EX_OK) if (ret != EX_OK) #else if (ret != 0) -#endif #endif { + php_error_docref(NULL, E_WARNING, "Sendmail exited with non-zero exit code %d", ret); MAIL_RET(false); } else { MAIL_RET(true); diff --git a/ext/standard/tests/mail/gh10990.phpt b/ext/standard/tests/mail/gh10990.phpt index 4f74c17c22bda..ee28f30313858 100644 --- a/ext/standard/tests/mail/gh10990.phpt +++ b/ext/standard/tests/mail/gh10990.phpt @@ -13,5 +13,6 @@ $from = 'test@example.com'; $headers = ['From' => &$from]; var_dump(mail('test@example.com', 'Test', 'Test', $headers)); ?> ---EXPECT-- +--EXPECTF-- +Warning: mail(): Sendmail exited with non-zero exit code 127 in %sgh10990.php on line %d bool(false) diff --git a/ext/standard/tests/mail/mail_basic5.phpt b/ext/standard/tests/mail/mail_basic5.phpt index b427fbeb670a0..73be1e1eaa1ad 100644 --- a/ext/standard/tests/mail/mail_basic5.phpt +++ b/ext/standard/tests/mail/mail_basic5.phpt @@ -20,7 +20,9 @@ $message = 'A Message'; echo "-- failure --\n"; var_dump( mail($to, $subject, $message) ); ?> ---EXPECT-- +--EXPECTF-- *** Testing mail() : basic functionality *** -- failure -- + +Warning: mail(): Sendmail exited with non-zero exit code 1 in %smail_basic5.php on line %d bool(false) diff --git a/ext/standard/tests/mail/mail_variation1.phpt b/ext/standard/tests/mail/mail_variation1.phpt index 75adc62822358..16779bcf455ee 100644 --- a/ext/standard/tests/mail/mail_variation1.phpt +++ b/ext/standard/tests/mail/mail_variation1.phpt @@ -17,6 +17,8 @@ $subject = 'Test Subject'; $message = 'A Message'; var_dump( mail($to, $subject, $message) ); ?> ---EXPECT-- +--EXPECTF-- *** Testing mail() : variation *** + +Warning: mail(): Sendmail exited with non-zero exit code 127 in %smail_variation1.php on line %d bool(false) diff --git a/ext/standard/tests/mail/mail_variation3.phpt b/ext/standard/tests/mail/mail_variation3.phpt new file mode 100644 index 0000000000000..03908242d88e9 --- /dev/null +++ b/ext/standard/tests/mail/mail_variation3.phpt @@ -0,0 +1,22 @@ +--TEST-- +Test mail() function : variation sendmail temp fail +--INI-- +sendmail_path=exit 75 +--SKIPIF-- + +--FILE-- + +--EXPECT-- +*** Testing mail() : variation *** +bool(true) diff --git a/ext/standard/tests/mail/mail_variation4.phpt b/ext/standard/tests/mail/mail_variation4.phpt new file mode 100644 index 0000000000000..c761e3bdbd199 --- /dev/null +++ b/ext/standard/tests/mail/mail_variation4.phpt @@ -0,0 +1,24 @@ +--TEST-- +Test mail() function : variation sigterm +--INI-- +sendmail_path="kill \$\$" +--SKIPIF-- + +--FILE-- + +--EXPECTF-- +*** Testing mail() : variation *** + +Warning: mail(): Sendmail killed by signal %d (%s) in %smail_variation4.php on line %d +bool(false) diff --git a/ext/standard/tests/mail/mail_variation5.phpt b/ext/standard/tests/mail/mail_variation5.phpt new file mode 100644 index 0000000000000..9e430f40c5dfc --- /dev/null +++ b/ext/standard/tests/mail/mail_variation5.phpt @@ -0,0 +1,24 @@ +--TEST-- +Test mail() function : variation non-zero exit +--INI-- +sendmail_path="exit 123" +--SKIPIF-- + +--FILE-- + +--EXPECTF-- +*** Testing mail() : variation *** + +Warning: mail(): Sendmail exited with non-zero exit code 123 in %smail_variation5.php on line %d +bool(false)