PHP的mail()函数是否存在注入风险?
我想知道以下代码是否存在任何潜在的安全风险。我在我的博客上使用此功能,每当用户提交评论时,它都会向我发送一条短信:
mail('[email protected]', '',
"Comment posted by $name: $comment",
"From: [email protected]");
其中 $name
和 $comment
是用户输入的值,但还没有确实以任何方式进行了消毒。用户是否有可能在这里做任何恶意的事情? mail() 文档对此没有任何说明,但是将用户输入的值直接粘贴到字符串中感觉是错误的。是否存在任何真正的风险,或者我只是偏执?
I am wondering if there is any potential security risk from the following code. I use this on my blog whenever a user submits a comment, it will send me a text message:
mail('[email protected]', '',
"Comment posted by $name: $comment",
"From: [email protected]");
Where $name
and $comment
are user-entered values that haven't really been sanitized in any way. Is there any possibility that a user could do anything malicious here? The mail() documentation doesn't say anything about this, but it just feels wrong to stick user-entered values directly into a string. Is there any real risk or am I just being paranoid?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
只要我将所有用户资料保存在邮件正文中,就不会有注入的风险。
然而,一旦用户可以影响邮件标头,他们就可以注入额外的标头并执行诸如使用它向任意电子邮件地址发送垃圾邮件或包含完全不同的消息(包括附件)之类的操作。
如果您检查影响标题的部分中的换行符,并在出现时拒绝换行符,那么这就足够了。 SMTP 标准使用 CRLF 来分隔标题行,但据我所知,许多基于 Unix 的服务器希望您仅使用 LF (因为这是这些系统上的本机行分隔符)。然后,邮件中继器在向上游发送时对其进行转换。
As long as all user-stuff i's kept in the mail body, then there is no risk of injection.
However, as soon as a user can affect mail headers, then they can inject extra headers and do things like use it to spam arbitrary e-mail addresses or include a completely different message - including attachments.
If you check for newlines in the parts that affect the headers, and reject if it appears, then that should be enough. The SMTP standard uses CRLF to separate the header lines, but AFAIK, many Unix-based servers want you to only use LF (because that's the native line separator on those systems). The mail relayer then converts it when sending it further upstream.
请注意名称中的换行符。两个连续的(呃……请原谅我的英语,两个接一个的换行符)换行符在 SMTP 中意味着“标头结束”。
另外,序列“\n.\n”(仅带句点的空行)表示“消息结束”。
编辑:是的,存在垃圾邮件发送者的风险!如果 $name 实际上包含:(
即注入更多标头的内容)怎么办?
EDIT2:没有注意到“名称”和“评论”都在消息的正文部分中。那么我关于垃圾邮件发送者的想法是无效的。
Be aware of the newline character inside the name. Two consequent (erm.. pardon my English, two newlines one after another) newlines mean "end of headers" in SMTP.
Also, the sequence `\n.\n' (empty line with only a period) means "end of message".
EDIT: Yes, there is a risk of spammers! What if the $name actually contains:
(i.e. something to inject more headers)?
EDIT2: didn't notice that "name" and "comment" were both in the body part of the message. Then my idea about spammers is not valid.
PHP 充满了不安全的东西,但我不确定这里是否存在很多风险。
当然,太长的注释可能会超出您对消息大小的限制。这可能不会伤害你。
PHP 的
$XXX
语法扩展了字符串,但不会对XXX
进行任何进一步的评估,不是吗?如果$XXX
的工作方式类似于某种eval()
,那么您将进入远程代码执行的世界,但我认为情况并非如此。如果这是在内部执行 SMTP,那么一行上的
.
后跟一个空行将表示邮件的结束,理论上攻击者可以在连续行中使用更多文本来劫持您的邮件邮件程序将其他消息邮寄给其他人。如果 PHP 一开始就无法识别并转义这样的字符串的话。这是我要调查的事情。PHP is full of unsafe stuff, but I'm not sure there's a lot of risk here.
Certainly a too-long comment could overflow whatever limit you might have on message size. That probably won't hurt you.
PHP's
$XXX
syntax expands the string, but doesn't do any further evaluation of theXXX
does it? If$XXX
worked like some kind ofeval()
, you'd be in for a world of remote code execution, but I don't think that's the case.If this is inwardly doing SMTP, then a
.
on one line followed by a blank line would signal the end of a mail, and theoretically an attacker could follow that up with more text in successive lines to hijack your mailer to mail some other message to someone else. That's if PHP doesn't recognize and escape such a string in the first place. This is something I'd look into.