【问题标题】:What security issues should I look out for in PHP我应该在 PHP 中注意哪些安全问题
【发布时间】:2010-11-12 23:55:12
【问题描述】:

我刚开始学习 PHP,我已经在 ASP.Net 中开发 Web 应用程序很长时间了。我想知道是否有任何我应该注意的特定于 PHP 的安全错误。

那么,我的问题是每个 PHP 开发人员都应该知道的最重要的安全提示是什么?

请为每个答案保留一个提示,以便人们可以有效地投票赞成/反对。

【问题讨论】:

    标签: php security


    【解决方案1】:

    (排名不分先后)

    1. 始终检查register globals 是否处于关闭状态
    2. 始终检查magic quotes 是否关闭
    3. 确保你理解SQL injection attacks
    4. 在生产中关闭error reporting

    编辑:对于那里的“新手”来说,这是一个基本的原因(因为我有时间解释这一点):

    1. 注册全局变量是一种异常。这是有史以来的终极安全漏洞。例如,如果 register_globals 打开,则 url http://www.yourdomain.com/foo.php?isAdmin=1 将声明 $isAdmin 为全局变量,无需任何代码。我不知道为什么这个“功能”会成为 PHP 的方式,但是 这背后的人应该在他们的额头上纹上以下纹身:“我发明了 PHP Register Globals”,这样我们就可以像害虫一样逃离它们了看看他们!

    2. 魔术引号是另一个愚蠢的想法,它已经成为 PHP 的方式。基本上,当 ON PHP 将自动转义引号('成为\'和“成为\”)以帮助进行 SQL 注入攻击。这个概念还不错(有助于避免注入攻击),但是转义 all GET、POST 和 COOKIE 值会使您的代码非常复杂(例如,每次显示和数据时都必须取消转义)。另外,如果有一天您关闭此设置而不对您的代码进行任何更改,那么您的所有代码和/或数据都会被破坏并且(甚至更)容易受到注入攻击(是的,即使您很容易受到攻击)。

    3. 您的数据库数据是您网站上最有价值的东西。您不希望人们惹恼它,因此请保护好自己并阅读有关它的内容牢记这一点。

    4. 同样,这可能会导致安全问题。错误消息可以为黑客提供有关您的代码如何工作的提示。此外,这些消息对您的访问者没有任何意义,那么为什么要显示它们呢?

    【讨论】:

      【解决方案2】:

      避免使用register_globals

      警告:此功能自 PHP 5.3.0 起已弃用,自 PHP 5.4.0 起已移除。

      【讨论】:

      • 不难,默认禁用,在 PHP6 中被移除。
      【解决方案3】:

      【讨论】:

      • -1 用于密码中的 md5。过于简单的答案,如果您使用 session_start(),会话固定不是问题。但你只是像巨魔一样链接到谷歌。
      • @Michael,我曾在哪里推荐过使用 MD5 做任何事情?更重要的是,考虑到可能出现的无数潜在问题,更值得的是,我试图在一个 SO 答案中复制数百份文档和数千人年的研究,或者链接到足够的资源让你开始正确的关键字?此外,我还链接到我写的一篇巨大的手写文章,以及麻省理工学院的一篇文章。关于客户端身份验证的论文,因为它们是更具体的来源,而不仅仅是针对各自主题的谷歌。
      • 请阅读您所说的内容:如果您使用session_start(),会话固定不是问题吗?你知道 PHP 的会话模型是如何工作的吗?这正是它的问题所在。也许你在想session_regenerate_id()?尽管如此,这也会在可能同时触发多个请求的环境中引入竞争条件(例如 AJAX)。我质疑你关于“只使用session_start()”的建议是本周在 PHP 安全方面“过于简单”的答案!
      • 您的密码存储模型明显错误。河豚真的很老了,用双鱼。不应将分组密码用于密码,因为它违反了 CWE-257 cwe.mitre.org/data/definitions/257.html。目前唯一通过 NIST 认证的密码消息摘要函数是 sha2 系列。 Sha256 是个不错的选择。
      • 并不是session_start() 本身就很弱,而是会话 ID 可以通过各种方式“固定”(查询字符串、发布参数,或者如果您可以控制 cookie),这可以提供恶意攻击者完全访问经过身份验证的系统。采取措施防止这种情况(例如,不允许通过 POST 和 GET 设置会话 ID,在某些事件(如登录和购买)上轮换会话 ID)是防止此类攻击的简单方法。我的问题是,session_start() 在什么世界里没有其他会话固定保护被认为是足够的保护?
      【解决方案4】:

      这里是良好 PHP 安全编程实践的链接。

      http://phpsec.org/

      大多数安全问题都围绕着用户输入(自然而然),并确保他们不会把你搞砸。始终确保验证您的输入。

      http://htmlfixit.com/cgi-tutes/tutorial_PHP_Security_Issues.php

      【讨论】:

      • 非常好。您可以阅读英语、法语、罗马尼亚语和塞尔维亚语的安全指南。
      • 问题:phpsec.org 最近有什么成果吗? (2008,9)
      【解决方案5】:
      1. 始终清理和验证从页面传递的数据
      2. 结合 #1,始终正确地转义您的输出
      3. 在生产环境中始终关闭 display_errors
      4. 如果使用 DB 后端,请使用支持/模拟预准备语句的驱动程序,并且不带偏见地使用 :-)

      【讨论】:

      • XSRF 与转义无关。如果你做了这份清单上的所有事情,你仍然会流泪。
      • @Michael:我没有说这是所有列表的全部内容,也没有特别提到有关 XSRF 的任何内容。事实上,到目前为止,此列表中的每个推荐都有很好的信息和警告。
      • 是的,你在我的书中获得了一些参数化查询的分数。但是这个问题的每一个答案都过于简单化了。所有人都想到的就是 xss 和 sqli,这真的让我很烦恼。
      【解决方案6】:

      不要使用“注册全局变量”并过滤用户输入以进行 xss 和注入

      【讨论】:

        【解决方案7】:

        语言与程序员。您可以编写最严重的漏洞,并且不会收到警告或错误消息。漏洞可以像在代码中添加或删除 2 个字符一样简单。有数百种不同类型的漏洞会影响 PHP 应用程序。大多数人会想到 XSS 和 Sql 注入,因为它们是最流行的。

        阅读OWASP top 10

        【讨论】:

          【解决方案8】:

          如果您使用的是 mysql 数据库,请确保在向数据库发送数据时调用 mysql_real_escape_string

          【讨论】:

          • 有趣的名字,有没有 mysql_imaginary_escape_string 函数?
          • mysql_phantasmal_escapist_wormhole 已被弃用,如果这就是您的想法...
          【解决方案9】:

          有很多安全预防措施。我可以推荐一本书 Chris Shiflett:PHP 和 Web 应用程序安全。

          http://phpsecurity.org/

          【讨论】:

            【解决方案10】:
            【解决方案11】:

            PHPSec Guide 提供了很好的概述。

            【讨论】:

              【解决方案12】:

              与 PHP 相关的大多数安全问题都来自使用未解析的“外部”(GET/POST/COOKIE) 变量。人们将这种数据直接放入文件路径或sql查询中,导致文件泄漏或sql注入。

              【讨论】:

                【解决方案13】:

                OWASP 提供了对当今应用程序中最大问题的安全问题的深入了解。很高兴看到他们有一个 PHP 专用页面可用

                http://www.owasp.org/index.php/PHP_Top_5

                【讨论】:

                  【解决方案14】:
                  1. 始终关闭 SQL 连接。
                  2. 始终发布 SQL 结果。
                  3. 始终清理您放入数据库的所有变量。
                  4. 从 sql 中删除或删除时使用限制 1 以防万一。
                  5. 在开发时,请确保您已锁定事物以防止不受欢迎的事物进入。如果它打开并且您知道现在不要加载该页面,因为它可能会破坏某些内容,但这并不意味着其他人会这样做。
                  6. 切勿使用 Admin 或 Root 作为您的服务器登录名。

                  【讨论】:

                    【解决方案15】:

                    尽可能使用准备好的语句(tutorial。在处理用户输入时几乎是必须的(我说“几乎”是因为在一些用例中它们不起作用),甚至在不处理时也是如此输入,它们让你养成习惯。更不用说它们可以带来更好的性能,而且一旦你开始做事情,它们比零敲碎打要容易得多。

                    【讨论】:

                      【解决方案16】:

                      通常介绍性教程根本不讨论检查用户数据。像所有编程环境一样,永远不要相信您从用户那里获得的数据。学习使用is_numeric()isset()mysql_real_escape_string() 等功能来保护您的系统。

                      还有一些功能可以让您访问远程文件和其他有创意的东西。在您充分了解它们的工作方式和时间之前,我会避免使用它们(出于安全原因,它们通常被禁用)。

                      【讨论】:

                      • is_numeric() 不应该被使用,因为像1.234 这样的值会漏掉,这几乎总是不是你想要的,因为你大部分时间都将在 SQL 查询中使用这些值。相反,请参阅this 答案。
                      【解决方案17】:

                      使用 POST 方法将数据从一个页面传递到另一个页面。

                      在获取trim($_POST) 之类的数据时使用修剪。 此外,在传递到查询之前,请使用 strip_tags 作为变量。

                      我建议你使用任何框架链接 Codeigniter、Laravel、YII、Cake PHP,因为它们为所有证券提供了框架

                      我建议将 Codeigniter 用于小型项目,将 Laravel 用于大型项目。

                      【讨论】:

                        【解决方案18】:

                        对重要数据始终使用 POST 而不是 GET...

                        【讨论】:

                        • 它能确保什么样的安全性?
                        • 使用 post 时看不到数据,但使用 get 时用户可以轻松操作数据...
                        • 这对所有语言都是通用的。 PHP 有什么特别之处?
                        猜你喜欢
                        • 1970-01-01
                        • 2011-02-20
                        • 2010-12-16
                        • 1970-01-01
                        • 1970-01-01
                        • 1970-01-01
                        • 2011-01-07
                        • 1970-01-01
                        • 1970-01-01
                        相关资源
                        最近更新 更多