cvs: phpdoc-ru /features cookies.xml /security apache.xml cgi-bin.xml current.xml database.xml errors.xml filesystem.xml general.xml globals.xml
hiding.xml index.xml intro.xml variables.xml
| From: | Antony Dovgal | Date: | Thu, 18 Mar 2004 14:32:29 +0000 |
| Subject: | cvs: phpdoc-ru /features cookies.xml /security apache.xml cgi-bin.xml current.xml database.xml errors.xml filesystem.xml general.xml globals.xml hiding.xml index.xml intro.xml variables.xml |
||
| Groups: | php.doc.ru | ||
| Request: | Send a blank email to doc-ru+get-247@lists.php.net to get a copy of this message | ||
tony2001 Thu Mar 18 09:32:29 2004 EDT
Added files:
/phpdoc-ru/features cookies.xml
/phpdoc-ru/security apache.xml cgi-bin.xml current.xml database.xml
errors.xml filesystem.xml general.xml
globals.xml hiding.xml index.xml intro.xml
variables.xml
Log:
add files translated by Alexander
http://cvs.php.net/co.php/phpdoc-ru/features/cookies.xml?r=1.1&p=1 Index: phpdoc-ru/features/cookies.xml +++ phpdoc-ru/features/cookies.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <chapter id="features.cookies"> <title>Cookies</title> <para> PHP ïðîçðà÷íî ïîääåðæèâàåò HTTP cookies. Cookies ýòî ìåõàíèçì õðàíåíèÿ äàííûõ áðîóçåðîì óäàëåííîé ìàøèíû äëÿ îòñëåæèâàíèÿ èëè èäåíòèôèêàöèè âîçâðàùàþùèõñÿ ïîñåòèòåëåé. Âû ìîæåòå óñòàíîâèòü cookies ïðè ïîìîùè ôóíêöèé <function>setcookie</function> èëè <function>setrawcookie</function>. Cookies ÿâëÿþòñÿ ÷àñòüþ HTTP-çàãîëîâêà, ïîýòîìó <function>setcookie</function> äîëæíà âûçûâàòüñÿ äî ëþáîãî âûâîäà äàííûõ â áðîóçåð. Ýòî òî æå ñàìîå îãðàíè÷åíèå, êîòîðîå èìååò ôóíêöèÿ <function>header</function>. Âû ìîæåòå èñïîëüçîâàòü <link linkend="ref.outcontrol">ôóíêöèè áóôåðèçàöèè âûâîäà</link>, ÷òîáû çàäåðæàòü âûâîä ðåçóëüòàòîâ ðàáîòû ñêðèïòà äî òîãî ìîìåíòà, êîãäà áóäåò èçâåñòíî, ïîíàäîáèòñÿ ëè óñòàíîâêà cookies èëè äðóãèõ HTTP-çàãîëîâêîâ. </para> <para> Ëþáûå cookies, îòïðàâëåííûå ñåðâåðó áðîóçåðîì êëèåíòà, áóäóò àâòîìàòè÷åñêè ïðåîáðàçîâàíû â ïåðåìåííûå PHP, ïîäîáíî äàííûì ìåòîäîâ GET è POST. Íà ýòîò ïðîöåññ âëèÿþò êîíôèãóðàöèîííûå äèðåêòèâû <literal>register_globals</literal> è <literal>variables_order</literal>. Äëÿ íàçíà÷åíèÿ íåñêîëüêèõ çíà÷åíèé îäíîé cookie, ïðîñòî äîáàâüòå <literal>[]</literal> ê å¸ èìåíè. </para> <para>  PHP 4.1.0 è âûøå, ãëîáàëüíûé ìàññèâ <varname>$_COOKIE</varname> âñåãäà àâòîìàòè÷åñêè çàïîëíÿåòñÿ çíà÷åíèÿìè ïîëó÷åííûõ cookies.  áîëåå ðàííèõ âåðñèÿõ îïðåäåëÿåòñÿ ìàññèâ <varname>$HTTP_COOKIE_VARS</varname> íî òîëüêî êîãäà âêëþ÷åíà äèðåêòèâà <literal>track_vars</literal>. (Ýòà äèðåêòèâà âñåãäà âêëþ÷åíà íà÷èíàÿ ñ PHP 4.0.3.) </para> <para> Äîïîëíèòåëüíàÿ èíôîðìàöèÿ, â òîì ÷èñëå è îá îñîáåííîñòÿõ ðåàëèçàöèè áðîóçåðîâ, ïðèâåäåíà â îïèñàíèè ôóíêöèé <function>setcookie</function> è <function>setrawcookie</function>. </para> </chapter> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/apache.xml?r=1.1&p=1 Index: phpdoc-ru/security/apache.xml +++ phpdoc-ru/security/apache.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.apache"> <title>Åñëè PHP óñòàíîâëåí êàê ìîäóëü Apache</title> <simpara> Êîãäà PHP èñïîëüçóåòñÿ êàê ìîäóëü Apache, îí íàñëåäóåò ïðàâà ïîëüçîâàòåëÿ, ñ êîòîðûìè áûë çàïóùåí âåá-ñåðâåð (îáû÷íî ýòî ïîëüçîâàòåëü 'nobody'). Ýòî âëèÿåò íà îáåñïå÷åíèå áåçîïàñíîñòè è ðåàëèçàöèþ àâòîðèçàöèè. Íàïðèìåð, åñëè âû èñïîëüçóåòå áàçó äàííûõ, êîòîðàÿ íå èìååò âñòðîåííîãî ìåõàíèçìà ðàçãðàíè÷åíèÿ äîñòóïà, âàì ïðèéäåòñÿ îáåñïå÷èòü äîñòóï ê ÁÄ äëÿ ïîëüçîâàòåëÿ 'nobody'.  òàêîì ñëó÷àå çëîâðåäíûé ñêðèïò ìîæåò ïîëó÷èòü äîñòóï ê áàçå äàííûõ è ìîäèôèöèðîâàòü åå, äàæå íå çíàÿ ëîãèíà è ïàðîëÿ. Âïîëíå âîçìîæíà ñèòóàöèÿ, êîãäà âåá-ïàóê íåâåðíûìè çàïðîñàìè ñòðàíèöû àäìèíèñòðàòîðà áàçû äàííûõ óíè÷òîæèò âñå äàííûå èëè äàæå ñòðóêòóðó ÁÄ. Âû ìîæåòå èçáåæàòü òàêîé ñèòóàöèè ïðè ïîìîùè àâòîðèçàöèè Apache èëè ðàçðàáîòàâ ñîáñòâåííóþ ìîäåëü äîñòóïà, èñïîëüçóÿ LDAP, ôàéëû &htaccess; èëè ëþáûå äðóãèå òåõíîëîãèè, âíåäðÿÿ ñîîòâåòñòâóþùèé êîä â âàøè ñêðèïòû. </simpara> <simpara> Äîñòàòî÷íî ÷àñòî èñïîëüçóþòñÿ òàêèå íàñòðîéêè áåçîïàñíîñòè, ïðè êîòîðûõ PHP (èìååòñÿ ââèäó ïîëüçîâàòåëü, ñ ïðàâàìè êîòîðîãî âûïîëíÿåòñÿ Apache) èìååò ìèíèìàëüíûå ïðèâåëåãèè, íàïðèìåð îòñóòñòâóåò âîçìîæíîñòü çàïèñè â ïîëüçîâàòåëüñêèå äèðåêòîðèè. Èëè, íàïðèìåð, îòñóòñòâóåò âîçìîæíîñòü ðàáîòàòü ñ áàçîé äàííûõ. Ïðè ýòîì ñèñòåìà áåçîïàñíîñòè íå ïîçâîëÿåò çàïèñûâàòü êàê "õîðîøèå", òàê è "ïëîõèå" ôàéëû, àíàëîãè÷íî ïîçâîëÿåò ïðîèçâîäèòü êàê "õîðîøèå", òàê è "ïëîõèå" òðàíçàêöèè. </simpara> <simpara> Ðàñïðîñòðàíåííîé îøèáêîé ÿâëÿåòñÿ çàïóñê Apache ñ ïðàâàìè ñóïåðïîëüçîâàòåëÿ èëè ëþáîå äðóãîå ðàñøèðåíèå ïîëíîìî÷èé âåá-ñåðâåðà. </simpara> <simpara> Ðàñøèðåíèå ïðèâèëåãèé âåá-ñåðâåðà äî ïîëíîìî÷èé óãðîæàåò ðàáîòîñïîñîáíîñòè âñåé ñèñòåìû, òàêèå êîìàíäû, êàê sudo, chroot äîëæíû âûïîëíÿòüñÿ èñêëþ÷èòåëüíî òåìè, êòî ñ÷èòàåò ñåáÿ ïðîôåññèîíàëàìè â âîïðîñàõ áåçîïàñíîñòè. </simpara> <simpara> Ñóùåñòâóåò íåñêîëüêî ïðîñòûõ ðåøåíèé. Èñïîëüçóÿ <link linkend="ini.open-basedir">open_basedir</link>, âû ìîæåòå îãðàíè÷èòü äåðåâî äîñòóïíûõ äèðåêòîðèé äëÿ PHP. Âû òàê æå ìîæåòå îïðåäåëèòü îáëàñòü äîñòóïà Apache, îãðàíè÷èâ âñå âåá-ñåðâèñû íå-ïîëüçîâàòåëüñêèìè èëè íå-ñèñòåìíûìè ôàéëàìè. </simpara> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/cgi-bin.xml?r=1.1&p=1 Index: phpdoc-ru/security/cgi-bin.xml +++ phpdoc-ru/security/cgi-bin.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.cgi-bin"> <title>Åñëè PHP óñòàíîâëåí êàê CGI</title> <sect2 id="security.cgi-bin.attacks"> <title>Âîçìîæíûå àòàêè</title> <simpara> Èñïîëüçîâàíèå PHP êàê áèíàðíîãî <acronym>CGI</acronym>-ïðèëîæåíèÿ ÿâëÿåòñÿ îäíèì èç âàðèàíòîâ, êîãäà ïî êàêèì-ëèáî ïðè÷èíàì íåæåëàòåëüíî èíòåãðèðîâàòü PHP â âåá-ñåðâåð (íàïðèìåð Apache) â êà÷åñòâå ìîäóëÿ, ëèáî ïðåäïîëàãàåòñÿ èñïîëüçîâàíèå òàêèõ óòèëèò, êàê chroot è setuid äëÿ îðãàíèçàöèè áåçîïàñíîãî îêðóæåíèÿ âî âðåìÿ ðàáîòû ñêðèïòîâ. Òàêàÿ óñòàíîâêà îáû÷íî ñîïðîâîæäàåòñÿ êîïèðîâàíèåì èñïîëíÿåìîãî ôàéëà PHP â äèðåêòîðèþ cgi-bin âåá-ñåðâåðà. CERT (îðãàíèçàöèÿ, ñëåäÿùàÿ çà óãðîçàìè áåçîïàñíîñòè) <ulink url="&url.cert;">CA-96.11</ulink> ðåêîìåíäóåò íå ïîìåùàòü êàêèå-ëèáî èíòåðïðåòàòîðû â êàòàëîã cgi-bin. Äàæå åñëè PHP èñïîëüçóåòñÿ êàê ñàìîñòîÿòåëüíûé èíòåðïðêòàòîð, îí ñïðîåêòèðîâàí òàê, ÷òîáû ïðåäîòâðàòèòü âîçìîæíîñòü ñëåäóþùèõ àòàê: </simpara> <itemizedlist> <listitem> <simpara> Äîñòóï ê ñèñòåìíûì ôàéëàì: <filename role="url">http://my.host/cgi-bin/php?/etc/passwd</filename> </simpara> <simpara> Äàííûå, ââåäåííûå â ñòðîêå çàïðîñà (URL) ïîñëå âîïðîñèòåëüíîãî çíàêà, ïåðåäàþòñÿ èíòåðïðåòàòîðó êàê àðãóìåíòû êîìàíäíîé ñòðîêè ñîãëàñíî CGI ïðîòîêîëó. Îáû÷íî èíòåðïðåòàòîðû îòêðûâàþò è èñïîëíÿþò ôàéë, óêàçàííûé â êà÷åñòâå ïåðâîãî àðãóìåíòà. </simpara> <simpara>  ñëó÷àå èñïîëüçîâàíèÿ PHP ïîñðåäñòâîì CGI-ïðîòîêîëà îí íå ñòàíåò èíòåðïðåòèðîâàòü àðãóìåíòû êîìàíäíîé ñòðîêè. </simpara> </listitem> <listitem> <simpara> Äîñòóï ê ïðîèçâîëüíîìó äîêóìåíòó íà ñåðâåðå: <filename role="url">http://my.host/cgi-bin/php/secret/doc.html</filename> </simpara> <simpara> Ñîãëàñíî îáùåïðèíÿòîìó ñîãëàøåíèþ ÷àñòü ïóòè â çàïðîøåííîé ñòðàíèöå, êîòîðàÿ ðàñïîëîæåíà ïîñëå èìåíè âûïîëíÿåìîãî ìîäóëÿ PHP, <filename role="uri">/secret/doc.html</filename>, èñïîëüçóåòñÿ äëÿ óêàçàíèÿ ôàéëà, êîòîðûé áóäåò èíòåðïðåòèðîâàí êàê <acronym>CGI</acronym>-ïðîãðàììà Îáû÷íî, íåêîòîðûå êîíôèãóðàöèîííûå îïöèè âåá-ñåðåâåðà (íàïðèìåð, Action äëÿ ñåðâåðà Apache) èñïîëüçóþòñÿ äëÿ ïåðåíàïðàâëåíèÿ äîêóìåíòà, ê ïðèìåðó, äëÿ ïåðåíàïðàâëåíèÿ çàïðîñîâ âèäà <filename role="url">http://my.host/secret/script.php</filename> èíòåðïðåòàòîðó PHP.  òàêîì ñëó÷àå âåá-ñåðâåð âíà÷àëå ïðîâåðÿåò ïðàâà äîñòóïà ê äèðåêòîðèè <filename role="uri">/secret</filename>, è ïîñëå ýòîãî ñîçäàåò ïåðåíàïðàâëåííûé çàïðîñ <filename role="url">http://my.host/cgi-bin/php/secret/script.php</filename>. Ê ñîæàëåíèþ, åñëè çàïðîñ èçíà÷àëüíî çàäàí â ïîëíîì âèäå, ïðîâåðêà íà íàëè÷èå ïðàâ äëÿ ôàéëà <filename role="uri">/secret/script.php</filename> íå âûïîëíÿåòñÿ, îíà ïðîèñõîäèò òîëüêî äëÿ ôàéëà <filename role="uri">/cgi-bin/php</filename>. Òàêèì îáðàçîì, ïîëüçîâàòåëü èìååò âîçìîæíîñòü îáðàòèòüñÿ ê <filename role="uri">/cgi-bin/php</filename>, è, êàê ñëåäñòâèå, ê ëþáîìó çàùèùåííîìó äîêóìåíòó íà ñåðâåðå. </simpara> <simpara>  PHP, óêàçûâàÿ âî âðåìÿ êîìïèëÿöèè îïöèþ <link linkend="install.configure.enable-force-cgi-redirect">--enable-force-cgi-redirect</link>, à òàêå îïöèè <link linkend="ini.doc-root">doc_root</link> è <link linkend="ini.user-dir">user_dir</link> âî âðåìÿ âûïîëíåíèÿ ñêðèïòà, ìîæíî ïðåäîòâðàòèòü ïîäîáíûå àòàêè äëÿ äèðåêòîðèé ñ îãðàíè÷åííûì äîñòóïîì. Áîëåå äåòàëüíî ïðèâåäåííûå îïöèè, à òàêæå èõ êîìáèíàöèè áóäóò ðàññìîòðåíû íèæå. </simpara> </listitem> </itemizedlist> </sect2> <sect2 id="security.cgi-bin.default"> <title>Âàðèàíò 1: îáñëóæèâàþòñÿ òîëüêî îáùåäîñòóïíûå ôàéëû</title> <simpara>  ñëó÷àå, åñëè íà âàøåì ñåðâåðå îòñóòñòâóþò ôàéëû, äîñòóï ê êîòîðûì îãðàíè÷åí ïàðîëåì ëèáî ôèëüòðîì ïî IP-àäðåñàì, íåò íèêàêîé íåîáõîäèìîñòè èñïîëüçîâàòü äàííûå îïöèè. Åñëè âàø âåá-ñåðâåð íå ðàçðåøàåò âûïîëíÿòü ïåðåíàïðàâëåíèÿ ëèáî íå èìååò âîçìîæíîñòè âçàèìîäåéñòâîâàòü ñ èñïîëíÿåìûì PHP-ìîäóëåì íà íåîáõîäèìîì óðîâíå áåçîïàñíîñòè, âû ìîæåòå èñïîëüçîâàòü îïöèþ <link linkend="install.configure.enable-force-cgi-redirect">--enable-force-cgi-redirect</link> âî âðåìÿ ñáîðêè PHP. Íî ïðè ýòîì âû äîëæíû óáåäèòüñÿ, ÷òî àëüòåðíàòèâíûå ñïîñîáû âûçîâà ñêðèïòà, òàêèå êàê íåïîñðåäñòâåííî âûçîâ <filename role="php">http://my.host/cgi-bin/php/dir/script.php</filename> ëèáî ñ ïåðåàäðåñàöèåé <filename role="php">http://my.host/dir/script.php</filename>, íåäîñòóïíû. </simpara> <simpara>  âåá-ñåðâåðå Apache ïåðåíàïðàâëåíèå ìîæåò áûòü ñêîíôèãóðèðîâàíî ïðè ïîìîùè äèðåêòèâ AddHandler è Action (îïèñàíî íèæå). </simpara> </sect2> <sect2 id="security.cgi-bin.force-redirect"> <title>Âàðèàíò 2: èñïîëüçîâàíèå --enable-force-cgi-redirect</title> <simpara> Ýòà îïöèÿ, óêàçûâàåìàÿ âî âðåìÿ ñáîðêè PHP, ïðåäîòâðàùàåò âûçîâ ñêðèïòîâ íåïîñðåäñòâåííî ïî àäðåñó âèäà <filename role="php">http://my.host/cgi-bin/php/secretdir/script.php</filename>. Âìåñòî ýòîãî, PHP áóäåò îáðàáàòûâàòü ïðèøåäøèé çàïðîñ òîëüêî â òîì ñëó÷àå, åñëè îí áûë ïåðåíàïðàâëåí âåá-ñåðâåðîì. </simpara> <simpara> Îáû÷íî ïåðåíàïðàâëåíèå â âåá-ñåðâåðå Apache íàñòðàèâàåòñÿ ïðè ïîìîùè ñëåäóþùèõ îïöèé: </simpara> <programlisting role="apache-conf"> <![CDATA[ Action php-script /cgi-bin/php AddHandler php-script .php ]]> </programlisting> <simpara> Ýòà îïöèÿ ïðîâåðåíà òîëüêî äëÿ âåá-ñåðâåðà Apache, åå ðàáîòà îñíîâûâàåòñÿ íà óñòàíîâêå â ñëó÷àå ïåðåíàïðàâëåíèÿ íåñòàíäàðòíîé ïåðåìåííîé <envar>REDIRECT_STATUS</envar>, íàõîäÿùåéñÿ â CGI-îêðóæåíèè.  ñëó÷àå, åñëè âàø âåá-ñåðâåð íå ïðåäîñòàâëÿåò âîçìîæíîñòè îäíîçíà÷íî èäåíòèôèöèðîâàòü, ÿâëÿåòñÿ ëè äàííûé çàïðîñ ïåðåíàïðàâëåííûì, âû íå ìîæåòå èñïîëüçîâàòü îïèñûâàåìóþ â äàííîì ðàçäåëå îïöèþ è äîëæíû âîñïîëüçîâàòüñÿ ëþáûì äðóãèì ìåòîäîì ðàáîòû ñ CGI-ïðèëîæåíèÿìè. </simpara> </sect2> <sect2 id="security.cgi-bin.doc-root"> <title>Âàðèàíò 3: èñïîëüçîâàíèå îïöèé doc_root è user_dir</title> <simpara> Ðàçìåùåíèå äèíàìè÷åñêîãî êîíòåíòà, òàêîãî êàê ñêðèïòû ëèáî ëþáûå äðóãèå èñïîëíÿåìûå ôàéëû, â äèðåêòîðèè âåá-ñåðâåðà äåëàåò åãî ïîòåíöèàëüíî îïàñíûì.  ñëó÷àå, åñëè â êîíôèãóðàöèè ñåðâåðà äîïóùåíà îøèáêà, âîçìîæíà ñèòóàöèÿ, êîãäà ñêðèïòû íå âûïîëíÿþòñÿ, à îòîáðàæàþòñÿ â áðàóçåðå, êàê îáû÷íûå HTML-äîêóìåíòû, ÷òî ìîæåò ïðèâåñòè ê óòå÷êå êîíôèäåíöèàëüíîé èíôîðìàöèè (íàïðèìåð, ïàðîëåé), ëèáî èíôîðìàöèè, ÿâëÿþùåéñÿ èíòåëëåêòóàëüíîé ñîáñòâåííîñòüþ. Èñõîäÿ èç òàêèõ ñîîáðàæåíèé, ìíîãèå ñèñòåìíûå àäìèíèñòðàòîðû ïðåäïî÷èòàþò èñïîëüçîâàòü äëÿ õðàíåíèÿ ñêðèïòîâ îòäåëüíóþ äèðåêòîðèþ, ðàáîòàÿ ñî âñåìè ðàçìåùåííûìè â íåé ôàéëàìè ïî CGI-èíòåðôåéñó. </simpara> <simpara>  ñëó÷àå, åñëè íåâîçìîæíî ãàðàíòèðîâàòü, ÷òî çàïðîñû íå ïåðåíàïðàâëÿþòñÿ, êàê áûëî ïîêàçàíî â ïðåäûäóùåì ðàçäåëå, íåîáõîäèìî óêàçûâàòü ïåðåìåííóþ doc_root, êîòîðàÿ îòëè÷àåòñÿ îò êîðíåâîé äèðåêòîðèè âåá-äîêóìåíòîâ. </simpara> <simpara> Âû ìîæåòå óñòàíîâèòü êîðíåâóþ äèðåêòîðèþ äëÿ PHP-ñêðèïòîâ, íàñòðîèâ ïàðàìåòð <link linkend="ini.doc-root">doc_root</link> â <link linkend="configuration.file">êîíôèãóðàöèîííîì ôàéëå</link>, ëèáî óñòàíîâèâ ïåðåìåííóþ îêðóæåíèÿ <envar>PHP_DOCUMENT_ROOT</envar>.  ñëó÷àå, åñëè PHP èñïîëüçóåòñÿ ïîñðåäñòâîì CGI, ïîëíûé ïóòü ê îòêðûâàåìîìó ôàéëó áóäåò ïîñòðîåí íà îñíîâàíèè çíà÷åíèÿ ïåðåìåííîé <parameter>doc_root</parameter> è óêàçàííîãî â çàïðîñå ïóòè. Òàêèì îáðàçîì, âû ìîæåòå áûòü óâåðåíû, ÷òî ñêðèïòû áóäóò âûïîëíÿòüñÿ òîëüêî âíóòðè óêàçàííîé âàìè äèðåêòîðèè (êðîìå äèðåêòîðèè <parameter>user_dir</parameter>, êîòîðàÿ îïèñàíà íèæå). </simpara> <simpara> Åùå îäíà èñïîëüçóåìàÿ ïðè íàñòðîéêå áåçîïàñíîñòè îïöèÿ - <link linkend="ini.user-dir">user_dir</link>.  ñëó÷àå, åñëè ïåðåìåííàÿ user_dir íå óñòàíîâëåíà, ïóòü ê îòêðûâàåìîìó ôàéëó ñòðîèòñÿ îòíîñèòåëüíî <parameter>doc_root</parameter>. Çàïðîñ âèäà <filename role="url">http://my.host/~user/doc.php</filename> ïðèâîäèò ê âûïîëíåíèþ ñêðèïòà, íàõîäÿùåãîñÿ íå â äîìàøíåì êàòàëîãå ñîîòâåòñòâóþùåãî ïîëüçîâàòåëÿ, à íàõîäÿùåãîñÿ â ïîäêàòàëîãå doc_root ñêðèïòà <filename role="uri">~user/doc.php</filename> (äà, èìÿ äèðåêòîðèè íà÷èíàåòñÿ ñ ñèìâîëà <literal>~</literal>). </simpara> <simpara> Íî åñëè ïåðåìåííîé <filename role="dir">public_php</filename> ïðèñâîåíî çíà÷åíèå, íàïðèìåð, <filename role="url">http://my.host/~user/doc.php</filename>, òîãäà â ïðèâåäåííîì âûøå ïðèìåðå áóäåò âûïîëíåí ñêðèïò <filename>doc.php</filename>, íàõîäÿùèéñÿ â äîìàøíåì êàòàëîãå ïîëüçîâàòåëÿ, â äèðåêòîðèè <filename role="dir">public_php</filename>. Íàïðèìåð, åñëè äîìàøíèé êàòàëîã ïîëüçîâàòåëÿ <filename role="dir">/home/user</filename>, áóäåò âûïîëíåí ôàéë <filename>/home/user/public_php/doc.php</filename>. </simpara> <simpara> Óñòàíîâêà îïöèè <parameter>user_dir</parameter> ïðîèñõîäèò íåçàâèñèìî îò óñòàíîâêè <parameter>doc_root</parameter>, òàêèì îáðàçîì âû ìîæåòå êîíòðîëèðîâàòü êîðíåâóþ äèðåêòîðèþ âåá-ñåðâåðà è ïîëüçîâàòåëüñêèå äèðåêòîðèè íåçàâèñèìî äðóã îò äðóãà. </simpara> </sect2> <sect2 id="security.cgi-bin.shell"> <title>Âàðèàíò 4: PHP âíå äåðåâà âåá-äîêóìåíòîâ</title> <para> Îäèí èç ñïîñîáîâ ñóùåñòâåííî ïîâûñèòü óðîâåíü áåçîïàñíîñòè - ïîìåñòèòü èñïîëíÿåìûé ìîäóëü PHP âíå äåðåâà âåá-äîêóìåíòîâ, íàïðèìåð â <filename role="dir">/usr/local/bin</filename>. Åäèíñòâåííûì íåäîñòàòêîì òàêîãî ïîäõîäà ÿâëÿåòñÿ òî, ÷òî ïåðâàÿ ñòðîêà êàæäîãî ñêðèïòà äîëæíà èìåòü âèä: <informalexample> <programlisting> <![CDATA[ #!/usr/local/bin/php ]]> </programlisting> </informalexample> Òàêæå íåîáõîäèìî ñäåëàòü âñå ôàéëû ñêðèïòîâ èñïîëíÿåìûìè. Òàêèì îáðàçîì, ñêðèïò áóäåò ðàññìàòðèâàòüñÿ òàê æå, êàê è ëþáîå äðóãîå CGI-ïðèëîæåíèå, íàïèñàííîå íà Perl, sh èëè ëþáîì äðóãîì ñêðèïòîâîì ÿçûêå, êîòîðûé èñïîëüçóåò äîïèñûâàíèå <literal>#!</literal> â íà÷àëî ôàéëà äëÿ çàïóñêà ñàìîãî ñåáÿ. </para> <para> ×òî áû âíóòðè ñêðèïòà âû ìîãëè ïîëó÷èòü êîððåêòíûå çíà÷åíèÿ ïåðåìåííûõ <envar>PATH_INFO</envar> è <envar>PATH_TRANSLATED</envar>, PHP äîëæåí áûòü ñêîíôèãóðèðîâàí ñ îïöèåé <link linkend="install.configure.enable-discard-path">--enable-discard-path</link>. </para> </sect2> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/current.xml?r=1.1&p=1 Index: phpdoc-ru/security/current.xml +++ phpdoc-ru/security/current.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.current"> <title>Íåîáõîäèìîñòü îáíîâëåíèé</title> <simpara> PHP, êàê è ëþáàÿ äðóãàÿ ñèñòåìà, âñå âðåìÿ òùàòåëüíî ïðîâåðÿåòñÿ è óëó÷øàåòñÿ. Êàæäàÿ íîâàÿ âåðñèÿ ñîäåðæèò ìíîæåñòâî êàê ñóùåñòâåííûõ, òàê è ìåëêèõ íîâøåñòâ è äîðàáîòîê, êîòîðûå, â òîì ÷èñëå, êàñàþòñÿ ïîâûøåíèÿ áåçîïàñíîñòè, ðàñøèðåíèÿ êîíôèãóðàöèîííûõ âîçìîæíîñòåé, à òàê æå ñòàáèëüíîñòè âàøåé ñèñòåìû. </simpara> <simpara> Êàê è â äðóãèõ ÿçûêàõ ïðîãðàììèðîâàíèÿ, ðåêîìåíäóåòñÿ ðåãóëÿðíî îáíîâëÿòü PHP è áûòü â êóðñå èçìåíåíèé, ñäåëàííûõ â ïîñëåäíèõ âåðñèÿõ. </simpara> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/database.xml?r=1.1&p=1 Index: phpdoc-ru/security/database.xml +++ phpdoc-ru/security/database.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.database"> <title>Áåçîïàñíîñòü áàç äàííûõ</title> <simpara> Íà ñåãîäíÿøíèé äåíü áàçû äàííûõ ÿâëÿþòñÿ êëþ÷åâûìè êîìïîíåíòàìè áîëüøèíñòâà âåá-ïðèëîæåíèé, ïîçâîëÿÿ ïðåäîñòàâëÿòü íà ñàéòàõ äèíàìè÷åñêèé êîíòåíò. Ïîñêîëüêó â òàêèõ ÁÄ ìîæåò õðàíèòüñÿ î÷åíü òî÷íàÿ èëè êîíôèäåíöèàëüíàÿ èíôîðìàöèÿ, âû äîëæíû îáåñïå÷èòü õîðîøóþ çàùèòó äàííûõ. </simpara> <simpara> Äëÿ èçâëå÷åíèÿ èëè ñîõðàíåíèÿ ëþáûõ äàííûõ âàì íåîáõîäèìî îòêðûòü ñîåäèíåíèå ñ áàçîé äàííûõ, îòïðàâèòü âåðíûé çàïðîñ, èçâëå÷ü ðåçóëüòàò è çàêðûòü ñîåäèíåíèå.  íàñòîÿùåå âðåìÿ íàèáîëåå ðàñïðîñòðàíåííûé ñòàíäàðò îáùåíèÿ - ñòðóêòóðèðîâàííûé ÿçûê çàïðîñîâ (SQL). Âñåãäà ñëåäóåò ïîìíèòü î âîçìîæíîñòè àòàêè <link linkend="security.database.sql-injection">ïîñðåäñòâîì SQL-çàïðîñà</link>. </simpara> <simpara> Î÷åâèäíî, ÷òî ñàì ïî ñåáå PHP íå ìîæåò çàùèòèòü âàøó áàçó äàííûõ. Ýòîò ðàçäåë äîêóìåíòàöèè ðàññêàçûâàåò îá îñíîâàõ áåçîïàñíîãî äîñòóïà è óïðàâëåíèÿ äàííûìè â PHP-ñêðèïòàõ. </simpara> <simpara> Çàïîìíèòå ïðîñòîå ïðàâèëî: ìàêñèìàëüíàÿ çàùèòà. ×åì áîëüøå ïîòåíöèàëüíî îïàñíûõ ó÷àñòêîâ ñèñòåìû âû ïðîðàáîòàåòå, òåì ñëîæíåå áóäåò ïîòåíöèàëüíîìó âçëîìùèêó ïîëó÷èòü äîñòóï ê áàçå äàííûõ èëè ïîâðåäèòü åå. Õîðîøèé äèçàéí áàçû äàííûõ è ïðîãðàììíûõ ïðèëîæåíèé ïîìîæåò âàì ñïðàâèòüñÿ ñ âàøèìè ñòðàõàìè. </simpara> <sect2 id="security.database.design"> <title>Ïðîåêòèðîâàíèå áàçû äàííûõ</title> <simpara> Ïåðâûé øàã - ýòî âñåãäà ñîçäàíèå ÁÄ, èñêëþ÷àÿ òîò ñëó÷àé, êîãäà âû õîòèòå èñïîëüçîâàòü ãîòîâóþ áàçó, ïðåäîñòàâëÿåìóþ òðåòüèì ëèöîì. Ïîñëå òîãî, êàê áàçà äàííûõ ñîçäàíà, îíà íàçíà÷àåòñÿ ïîëüçîâàòåëþ, êîòîðûé âûïîëíèë ñîçäàâøèé ÁÄ çàïðîñ. Êàê ïðàâèëî, òîëüêî âëàäåëåö (èëè ñóïåðïîëüçîâàòåëü) ìîæåò âûïîëíÿòü ðàçëè÷íûå äåéñòâèÿ ñ ðàçëè÷íûìè îáúåêòàìè, õðàíèìûìè â áàçå äàííûõ. Äëÿ òîãî, ÷òîáû è äðóãèå ïîëüçîâàòåëè èìåëè ê íåé äîñòóï, èõ íåîáõîäèìî íàäåëèòü ñîîòâåòñòâóþùèìè ïðèâåëåãèÿìè. </simpara> <simpara> Ïðèëîæåíèÿ íå äîëæíû ñîåäèíÿòüñÿ ñ áàçîé äàííûõ, èñïîëüçóÿ ó÷åòíóþ çàïèñü âëàäåëüöà èëè ñóïåðïîëüçîâàòåëÿ, èíà÷å îíè ñìîãóò ìîäèôèöèðîâàòü ñòðóêòóðó òàáëèö (íàïðèìåð, óäàëèòü íåêîòîðûå òàáëèöû) èëè äàæå óäàëèòü âñå ñîäåðæèìîå ÁÄ öåëèêîì. </simpara> <simpara> Âû ìîæåòå ñîçäàòü ðàçëè÷íûå ó÷åòíûå çàïèñè ïîëüçîâàòåëåé ÁÄ äëÿ êàæäîé èíäèâèäóàëüíîé ïîòðåáíîñòè ïðèëîæåíèÿ ñ ñîîòâåòñòâóþùèìè ôóíêöèîíàëüíûìè îãðàíè÷åíèÿìè. Ðåêîìåíäóåòñÿ íàçíà÷àòü òîëüêî ñàìûå íåîáõîäèìûå ïðèâèëåãèè, òàêæå âû äîëæíû èçáåãàòü ñèòóàöèé, êîãäà îäèí è òîò æå ïîëüçîâàòåëü ìîæåò âçàèìîäåéñòâîâàòü ñ áàçîé äàííûõ â íåñêîëüêèõ ðåæèìàõ. Âû äîëæíû ïîíèìàòü, ÷òî åñëè çëîóìûøëåííèê ñìîæåò âîñïîëüçîâàòüñÿ êàêîé-ëèáî ó÷åòíîé çàïèñüþ âàøåé ÁÄ, îí ñìîæåò âíîñèòü â áàçó âñå òå èçìåíåíèÿ, ÷òî è ïðîãðàììà, êîòîðàÿ èñïîëüçóåò òåêóùóþ ó÷åòíóþ çàïèñü. </simpara> <simpara> Âàì íå îáÿçàòåëüíî ðåàëèçîâûâàòü âñþ áèçíåñ-ëîãèêó â âåá-ïðèëîæåíèè (ò.å. â ñêðèïòàõ), äëÿ ýòîãî òàêæå ìîæíî èñïîëüçîâàòü âîçìîæíîñòè, ïðåäîñòàâëÿåìûå áàçîé äàííûõ: òðèããåðû, ïðåäñòàâëåíèÿ, ïðàâèëà.  ñëó÷àå ðîñòà ñèñòåìû âàì ïîíàäîáÿòñÿ íîâûå ñîåäèíåíèÿ ñ ÁÄ, è ëîãèêó ðàáîòû ïîíàäîáèòüñÿ äóáëèðîâàòü äëÿ êàæäîãî íîâîãî èíòåðôåéñà äîñòóïà. Èñõîäÿ èç âûøåñêàçàííîãî, òðèããåðû ìîãóò èñïîëüçîâàòüñÿ äëÿ ïðîçðà÷íîé è àâòîìàòè÷åñêîé îáðàáîòêè çàïèñåé, ÷òî ÷àñòî íåîáõîäèìî ïðè îòëàäêå ïðèëîæåíèé èëè ïðè òðàññèðîâêå îòêàòà òðàíçàêöèé. </simpara> </sect2> <sect2 id="security.database.connection"> <title>Ñîåäèíåíèå ñ áàçîé äàííûõ</title> <simpara> Âû ìîæåòå èñïîëüçîâàòü áåçîïàñíûå SSL èëè ssh ñîåäèíåíèÿ, äëÿ øèôðîâàíèÿ äàííûõ, êîòîðûìè îáìåíèâàþòñÿ êëèåíò è ñåðâåð. Åñëè âû ðåàëèçóåòå ÷òî-íèáóäü èç ýòîãî, òî ìîíèòîðèíã òðàôèêà è ñáîð äàííûõ î âàøåé áàçå äàííûõ äëÿ ïîòåíöèàëüíîãî âçëîìùèêà ñóùåñòâåííî óñëîæíèòñÿ. </simpara> <!--simpara> If your database server has native SSL support, consider using <link linkend="ref.openssl">OpenSSL functions</link> in communication between PHP and database via SSL. </simpara--> </sect2> <sect2 id="security.database.storage"> <title>Çàùèòà õðàíèëèùà áàçû äàííûõ</title> <simpara> SSL/SSH çàùèùàåò äàííûå, êîòîðûìè îáìåíèâàþòñÿ êëèåíò è ñåðâåð, íî íå çàùèùàþò ñàìè äàííûå, õðàíèìûå â áàçå äàííûõ. SSL - ïðîòîêîë øèôðîâàíèÿ íà óðîâíå ñåàíñà ïåðåäà÷è äàííûõ. </simpara> <simpara>  ñëó÷àå, åñëè âçëîìùèê ïîëó÷èë íåïîñðåäñòâåííûé äîñòóï ê ÁÄ (â îáõîä âåá-ñåðâåðà), îí ìîæåò èçâëå÷ü èíòåðåñóþùèå äàííûå èëè íàðóøèòü èõ öåëîñòíîñòü, ïîñêîëüêó èíôîðìàöèÿ íå çàùèùåíà íà óðîâíå ñàìîé ÁÄ. Øèôðîâàíèå äàííûõ - õîðîøèé ñïîñîá ïðåäîòâðàòèòü òàêóþ ñèòóàöèþ, íî ëèøü íåçíà÷èòåëüíîå êîëè÷åñòâî ÁÄ ïðåäîñòàâëÿþò òàêóþ âîçìîæíîñòü. </simpara> <simpara> Íàèáîëåå ïðîñòîå ðåøåíèå ýòîé ïðîáëåìû - óñòàíîâèòü âíà÷àëå îáûêíîâåííûé ïðîãðàììíûé ïàêåò äëÿ øèôðîâàíèÿ äàííûõ, à çàòåì èñïîëüçîâàòü åãî â âàøèõ ñêðèïòàõ. PHP, â òàêîì ñëó÷àå, ìîæåò ïîìî÷ü âàì â ðàáîòå ñ òàêèìè ðàñøèðåíèÿìè êàê <link linkend="ref.mcrypt">Mcrypt</link> è <link linkend="ref.mhash">Mhash</link>, ðåàëèçóþùèìè ðàçëè÷íûå àëãîðèòìû êðèïòîâàíèÿ. Ïðè òàêîì ïîäõîäå ñêðèïò âíà÷àëå øèôðóåò ñîõðàíÿåìûå äàííûå, à çàòåì äåøèôðóåò èõ ïðè çàïðîñå. Íèæå ïðèâåäåíû ïðèìåðû òîãî, êàê ðàáîòàåò øèôðîâàíèå äàííûõ â PHP-ñêðèïòàõ. </simpara> <simpara>  ñëó÷àå ðàáîòû ñî ñêðûòûìè ñëóæåáíûìè äàííûìè èõ íåøèôðîâàííîå ïðåäñòàâëåíèå íå òðåáóåòñÿ (ò.å. íå îòîáðàæàåòñÿ), è, êàê ñëåäñòâèå, ìîæíî èñïîëüçîâàòü õåøèðîâàíèå. Õîðîøî èçâåñòíûé ïðèìåð õýøèðîâàíèÿ - õðàíåíèå MD5-õåøà îò ïàðîëÿ â ÁÄ, âìåñòî õðàíåíèÿ îðèãèíàëüíîãî çíà÷åíèÿ. Áîëåå äåòàëüíàÿ èíôîðìàöèÿ äîñòóïíà â îïèñàíèè ôóíêöèé <function>crypt</function> and <function>md5</function>. </simpara> <example> <title>Èñïîëüçîâàíèå õåøèðîâàííûõ ïàðîëåé</title> <programlisting role="php"> <![CDATA[ // ñîõðàíåíèå õåøèðîâàííîãî ïàðîëÿ $query = sprintf("INSERT INTO users(name,pwd) VALUES('%s','%s');", addslashes($username), md5($password)); $result = pg_exec($connection, $query); // ïðîâåðêà ââåäåííîãî ïîëüçîâàòåëåì ëîãèíà è ïàðîëÿ íà êîððåêòíîñòü $query = sprintf("SELECT 1 FROM users WHERE name='%s' AND pwd='%s';", addslashes($username), md5($password)); $result = pg_exec($connection, $query); if (pg_numrows($result) > 0) { echo "Welcome, $username!"; } else { echo "Authentication failed for $username."; } ]]> </programlisting> </example> </sect2> <sect2 id="security.database.sql-injection"> <title>SQL-èíúåêöèè</title> <simpara> Ìíîãèå âåá-ðàçðàáîò÷èêè äàæå íå äîãàäûâàþòñÿ, ÷òî SQL-çàïðîñû ìîãóò áûòü ïîääåëàíû, è ñ÷èòàþò, ÷òî SQL-çàïðîñû âñåãäà äîñòîâåðíû. Íà ñàìîì äåëå ïîääåëüíûå çàïðîñû ìîãóò îáîéòè îãðàíè÷åíèÿ äîñòóïà, ñòàíäàðòíóþ ïðîâåðêó àâòîðèçàöèè, à íåêîòîðûå âèäû çàïðîñîâ ìîãóò äàòü âîçìîæíîñòü âûïîëíÿòü êîìàíäû îïåðàöèîííîé ñèñòåìû. </simpara> <simpara> Ïðèíóäèòåëüíîå âíåäðåíèå âðåäîíîñíûõ èíñòðóêöèé â SQL-çàïðîñû - ìåòîäèêà, â êîòîðîé âçëîìùèê ñîçäàåò èëè èçìåíÿåò òåêóùèå SQL-çàïðîñû äëÿ ðàáîòû ñî ñêðûòûìè äàííûìè, èõ èçìåíåíèÿ èëè äàæå âûïîëíåíèÿ îïàñíûõ êîììàíä îïåðàöèîííîé ñèñòåìû íà ñåðâåðå áàçû äàííûõ. Àòàêà âûïîëíÿåòñÿ íà áàçå ïðèëîæåíèÿ, ñòðîÿùåãî SQL-çàïðîñû èç ïîëüçîâàòåëüñêîãî ââîäà è ñòàòè÷åñêèõ ïåðåìåííûõ. Ñëåäóþùèå ïðèìåðû, ê ñîæàëåíèþ, ïîñòðîåíû íà ðåàëüíûõ ôàêòàõ. </simpara> <para> Áëàãîäàðÿ îòñóòñòâèþ ïðîâåðêè ïîëüçîâàòåëüñêîãî ââîäà è ñîåäèíåíèåì ñ áàçîé äàííûõ ïîä ó÷åòíîé çàïèñüþ ñóïåðïîëüçîâàòåëÿ (èëè ëþáîãî äðóãîãî ïîëüçîâàòåëÿ, íàäåëåííîãî ñîîòâåòñòâóþùèìè ïðèâåëåãèÿìè), âçëîìùèê ìîæåò ñîçäàòü åùå îäíîãî ïîëüçîâàòåëÿ ÁÄ ñ ïðàâàìè ñóïåðïîëüçîâàòåëÿ. <example> <title> Ïîñòðàíè÷íûé âûâîä ðåçóëüòàòà... è ñîçäàíèå ñóïåðïîëüçîâàòåëÿ â PostgreSQL è MySQL </title> <programlisting role="php"> <![CDATA[ $offset = argv[0]; // ïðîâåðêà ïîëüçîâàòåëüñêèõ äàííûõ îòñóòñòâóåò $query = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;"; // èñïîëüçóÿ PostgreSQL $result = pg_exec($conn, $query); // èñïîëüçóÿ MySQL $result = mysql_query($query); ]]> </programlisting> </example> Îáû÷íî ïîëüçîâàòåëè êëèêàþò ïî ññûëêàì 'âïåðåä' è 'íàçàä', âñëåäñòâèè ÷åãî çíà÷åíèå ïåðåìåííîé <varname>$offset</varname> çàíîñèòñÿ â àäðåñíóþ ñòðîêó. Ñêðèïò îæèäàåò, ÷òî <varname>$offset</varname> - äåñÿòèðè÷íîå ÷èñëî. Îäíàêî, âçëîìùèê ìîæåò ïîïûòàòüñÿ âçëîìàòü ñèñòåìó, ïðèñîåäèíèâ ê ñòðîêå çàïðîñà äîïîëíèòåëüíóþ ïîäñòðîêó, îáðàáîòàííóþ ôóíêöèåé <function>urlencode</function>: <informalexample> <programlisting role="sql"> <![CDATA[ // èñïîëüçóÿ PostgreSQL 0; insert into pg_shadow(usename,usesysid,usesuper,usecatupd,passwd) select 'crack', usesysid, 't','t','crack' from pg_shadow where usename='postgres'; -- // èñïîëüçóÿ MySQL 0; UPDATE user SET Password=PASSWORD('crack') WHERE user='root'; FLUSH PRIVILEGES; ]]> </programlisting> </informalexample> Åñëè ýòî ïðîèçîéäåò, ñêðèïò ïðåäîñòàâèò âçëîìùèêó äîñòóï ê áàçå ñ ïðàâàìè ñóïåðïîëüçîâàòåëÿ. Çàìåòèì, ÷òî <literal>0;</literal> èñïîëüçîâàí äëÿ òîãî, ÷òîáû çàäàòü ïðàâèëüíîå çíà÷åíèå ñìåùåíèÿ äëÿ ïåðâîãî çàïðîñà è êîððåêòíî åãî çàâåðøèòü. </para> <note> <para> Óæå ïðèâû÷íà òåõíîëîãèÿ, êîãäà ðàçðàáîò÷èêè óêàçûâàþò ïðèíóäèòåëüíîå èãíîðèðîâàíèå ïàðñåðîì SQL îñòàâøåéñÿ ÷àñòè çàïðîñà ïðè ïîìîùè íîòàöèè <literal>--</literal>, îçíà÷àþùåé êîììåíòàðèé. </para> </note> <para> Åùå îäèí âåðîÿòíûé ñïîñîá ïîëó÷èòü ïàðîëè ó÷åòíûõ çàïèñåé â ÁÄ - àòàêà ñòðàíèö, ïðåäîñòàâëÿþùèõ ïîèñê ïî áàçå. Âçëîìùèêó íóæíî ëèøü ïðîâåðèòü, èñïîëüçóåòñÿ ëè â çàïðîñå ïåðåäàâàåìàÿ íà ñåðâåð è íåîáðàáàòûâàåìàÿ íàäëåæàùèì îáðàçîì ïåðåìåííàÿ. Ýòî ìîæåò áûòü îäèí èç óñòàíàâëèâàåìûõ íà ïðåäûäóùåé ñòðàíèöå ôèëüòðîâ, òàêèõ êàê <literal>WHERE, ORDER BY, LIMIT</literal> è <literal>OFFSET</literal>, èñïîëüçóåìûõ ïðè ïîñòðîåíèè çàïðîñîâ <literal>SELECT</literal>.  ñëó÷àå, åñëè èñïîëüçóåìàÿ âàìè áàçà äàííûõ ïîääåðæèâàåò êîíñòðóêöèþ <literal>UNION</literal>, âçëîìùèê ìîæåò ïðèñîåäèíèòü ê îðèãèíàëüíîìó çàïðîñó åùå îäèí äîïîëíèòåëüíûé, äëÿ èçâëå÷åíèÿ ïîëüçîâàòåëüñêèõ ïàðîëåé. Íàñòîÿòåëüíî ðåêîìåíäóåì èñïîëüçîâàòü òîëüêî çàøèôðîâàííûå ïàðîëè. <example> <title> Ëèñòèíã ñòàòåé... è íåêîòîðûõ ïàðîëåé (äëÿ ëþáîé áàçû äàííûõ) </title> <programlisting role="php"> <![CDATA[ $query = "SELECT id, name, inserted, size FROM products WHERE size = '$size' ORDER BY $order LIMIT $limit, $offset;"; $result = odbc_exec($conn, $query); ]]> </programlisting> </example> Ñòàòè÷åñêàÿ ÷àñòü çàïðîñà ìîæåò êîìáèíèðîâàòüñÿ ñ äðóãèì SQL-çàïðîñîì, êîòîðûé îòêðîåò âñå ïàðîëè: <informalexample> <programlisting role="sql"> <![CDATA[ ' union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable; -- ]]> </programlisting> </informalexample> Åñëè ýòîò çàïðîñ (èñïîëüçóþùèé <literal>'</literal> è <literal>--</literal>) ïðèñîåäèíèòü ê çíà÷åíèþ îäíîé èç ïåðåìåííûõ, èñïîëüçóåìûõ äëÿ ôîðìèðîâàíèÿ <varname>$query</varname>, çàïðîñ çàìåòíî ïðåîáðàçèòñÿ. </para> <para> Êîìàíäû UPDATE òàêæå ìîãóò èñïîëüçîâàòüñÿ äëÿ àòàêè. Îïÿòü æå, åñòü óãðîçà ðàçäåëåíèÿ èíñòðóêöèè íà íåñêîëüêî çàïðîñîâ, ïðèñîåäèíåíèÿ äîïîëíèòåëüíîãî çàïðîñà. Òàêæå âçëîìùèê ìîæåò âèäîèçìåíèòü âûðàæåíèå <literal>SET</literal>.  ýòîì ñëó÷àå ïîòåíöèàëüíîìó âçëîìùèêó íåîáõîäèìî îáëàäàòü íåêîòîðîé äîïîëíèòåëüíîé èíôîðìàöèåé äëÿ óñïåøíîãî ìàíèïóëèðîâàíèÿ çàïðîñàìè. Ýòó èíôîðìàöèþ ìîæíî ïîëó÷èòü, ïðîàíàëèçèðîâàâ èñïîëüçóåìûå â ôîðìå èìåíà ïåðåìåííûõ ëèáî ïðîñòî ïåðåáèðàÿ âñå íàèáîëåå ðàñïðîñòðàíåííûå âàðèàíòû íàçâàíèÿ ñîîòâåòñòâóþùèõ ïîëåé (à èõ íå òàê óæ è ìíîãî). <example> <title> Îò âîññòàíîâëåíèÿ ïàðîëÿ... äî ïîëó÷åíèÿ äîïîëíèòåëüíûõ ïðèâèëåãèé (äëÿ ëþáîé áàçû äàííûõ) </title> <programlisting role="php"> <![CDATA[ $query = "UPDATE usertable SET pwd='$pwd' WHERE uid='$uid';"; ]]> </programlisting> </example> Íî çëîóìûøëåííèê ìîæåò ââåñòè çíà÷åíèå <literal>' or uid like'%admin%'; --</literal> äëÿ ïåðåìåííîé <varname>$uid</varname> äëÿ èçìåíåíèÿ ïàðîëÿ àäìèíèñòðàòîðà èëè ïðîñòî ïðèñâîèòü ïåðåìåííîé <varname>$pwd</varname> çíà÷åíèå <literal>"hehehe', admin='yes', trusted=100 "</literal> (ñ çàâåðøàþùèìè ïðîáåëàìè) äëÿ ïîëó÷åíèÿ äîïîëíèòåëüíûõ ïðèâåëåãèé. Ïðè âûïîëíåíèè çàïðîñû ïåðåïëåòàþòñÿ: <informalexample> <programlisting role="php"> <![CDATA[ // $uid == ' or uid like'%admin%'; -- $query = "UPDATE usertable SET pwd='...' WHERE uid='' or uid like '%admin%'; --"; // $pwd == "hehehe', admin='yes', trusted=100 " $query = "UPDATE usertable SET pwd='hehehe', admin='yes', trusted=100 WHERE ...;" ]]> </programlisting> </informalexample> </para> <para> Ïóãàþùèé ïðèìåð òîãî, êàê íà ñåðâåðå áàç äàííûõ ìîãóò âûïîëíÿòüñÿ êîìàíäû îïåðàöèîííîé ñèñòåìû. <example> <title>Âûïîëíåíèå êîìàíä îïåðàöèîííîé ñèñòåìû íà ñåðâåðå (äëÿ áàçû MSSQL)</title> <programlisting role="php"> <![CDATA[ $query = "SELECT * FROM products WHERE id LIKE '%$prod%'"; $result = mssql_query($query); ]]> </programlisting> </example> Åñëè âçëîìùèê ââåäåò çíà÷åíèìå <literal>a%' exec master..xp_cmdshell 'net user test testpass /ADD' --</literal> äëÿ ïåðåìåííîé <varname>$prod</varname>, òîãäà çàïðîñ <varname>$query</varname> áóäåò âûãëÿäåòü òàê: <informalexample> <programlisting role="php"> <![CDATA[ $query = "SELECT * FROM products WHERE id LIKE '%a%' exec master..xp_cmdshell 'net user test testpass /ADD'--"; $result = mssql_query($query); ]]> </programlisting> </informalexample> MSSQL ñåðâåð âûïîëíÿåò SQL-êîìàíäû â ïàêåòíîì ðåæèìå, â òîì ÷èñëå è îïåðàöèè ïî çàâåäåíèþ ëîêàëüíûõ ó÷åòíûõ çàïèñåé áàçû äàííûõ.  ñëó÷àå, åñëè ïðèëîæåíèå ðàáîòàåò ñ ïðèâèëåãèÿìè àäìèíèñòðàòîðà è ñåðâèñ MSSQL çàïóùåí ñ íåîáõîäèìûìè ïðèâèëåãèÿìè, âûïîëíèâ ïðèâåäåííûå âûøå äåéñòâèÿ, âçëîìùèê ïîëó÷èò àêêàóíò äëÿ äîñòóïà ê ñåðâåðó. </para> <note> <para> Íåêîòîðûå ïðèâåäåííûå â ýòîé ãëàâå ïðèìåðû êàñàþòñÿ êîíêðåòíîé áàçû äàííûõ. Ýòî íå îçíà÷àåò, ÷òî àíàëîãè÷íûå àòàêè íà äðóãèå ïðîãðàììíûå ïðîäóêòû íåâîçìîæíû. Ðàáîòîñïîñîáíîñòü âàøåé áàçû äàííûõ ìîæåò áûòü íàðóøåíà êàêèì-ëèáî äðóãèì ñïîñîáîì. </para> </note> <sect3 id="security.database.avoiding"> <title>Ñïîñîáû çàùèòû</title> <simpara> Âû ìîæåòå óòåøàòü ñåáÿ òåì, ÷òî â áîëüøèíñòâå ñëó÷àåâ, âçëîìùèê äîëæåí îáëàäàòü íåêîòîðîé èíôîðìàöèåé î ñòðóêòóðå áàçû äàííûõ. Âû ïðàâû, íî âû íå çíàåòå, êîãäà è êàê áóäåò ïðåäïðèíÿòà ïîïûòêà âçëîìà, â ñëó÷àå åñëè ýòî ïðîèçîéäåò âàøà ÁÄ îêàæåòñÿ íåçàùèùåííîé. Åñëè âû èñïîëüçóåòå ïðîãðàììíûé ïðîäóêò ñ îòêðûòûìè èñõîäíûìè êîäàìè èëè ïðîñòî îáùåäîñòóïíûé ïàêåò äëÿ ðàáîòû ñ áàçîé äàííûõ (íàïðèìåð êîíòåíò ìåíåäæåð èëè ôîðóì), âçëîìùèê ëåãêî ñìîæåò âîñïðîèçâåñòè èíòåðåñóþùèå åãî ó÷àñòêè êîäà.  ñëó÷àå åñëè îíè ïëîõî ñïðîåêòèðîâàíû, ýòî ìîæåò ÿâëÿòüñÿ îäíîé èç óãðîç âàøåé áåçîïàñíîñòè. </simpara> <simpara> Áîëüøèíñòâî óñïåøíûõ àòàê îñíîâûâàåòñÿ íà êîäå, íàïèñàííîì áåç ó÷åòà ñîîòâåòñòâóþùèõ òðåáîâàíèé áåçîïàñíîñòè. Íå äîâåðÿéòå íèêàêèì ââîäèì äàííûì, îñîáåííî åñëè îíè ïîñòóïàþò ñî ñòîðîíû êëèåíòà, äàæå åñëè ýòî ñïèñêè â ôîðìå, ñêðûòûå ïîëÿ èëè êóêè. Ïðèâåäåííûå ïðèìåðû ïîêàçûâàþò, ê êàêèì ïîñëåäñòâèÿì ìîãóò ïðèâåñòè ïîääåëàííûå çàïðîñû. </simpara> <itemizedlist> <listitem> <simpara> Ñòàðàéòåñü íå îòêðûâàòü ñîåäèíåíèå ñ áàçîé, èñïîëüçóÿ ó÷åòíóþ çàïèñü âëàäåëüöà èëè àäìèíèñòðàòîðà. Âñåãäà ñòàðàéòåñü èñïîëüçîâàòü ñïåöèàëüíî ñîçäàííûõ ïîëüçîâàòåëåé ñ ìàêñèìàëüíî îãðàíè÷åííûìè ïðàâàìè. </simpara> </listitem> <listitem> <simpara> Âñåãäà ïðîâåðÿéòå ââåäåííûå äàííûå íà ñîîòâåòñòâèå îæèäàåìîìó òèïó.  PHP åñòü ìíîæåñòâî ôóíêöèé äëÿ ïðîâåðêè äàííûõ: íà÷èíàÿ îò ïðîñòåéøèõ <link linkend="ref.variables">Ôóíêöèé äëÿ ðàáîòû ñ ïåðåìåííûìè</link> è <link linkend="ref.ctype">Ôóíêöèè îïðåäåëåíèÿ òèïà ñèìâîëîâ</link> (òàêèå êàê <function>is_numeric</function>, <function>ctype_digit</function>) è çàêàí÷èâàÿ <link linkend="ref.pcre">Perl-ñîâìåñòèìûìè ðåãóëÿðíûìè âûðàæåíèÿìè</link>. </simpara> </listitem> <listitem> <para>  ñëó÷àå, åñëè ïðèëîæåíèå îæèäàåò öèôðîâîé ââîä, ïðèìåíèòå ôóíêöèþ <function>is_numeric</function> äëÿ ïðîâåðêè ââåäåííûõ äàííûõ, èëè ïðèíóäèòåëüíî óêàæèòå èõ òèï ïðè ïîìîùè <function>settype</function>, èëè ïðîñòî èñïîëüçóéòå ÷èñëîâîå ïðåäñòàâëåíèå ïðè ïîìîùè ôóíêöèè <function>sprintf</function>. <example> <title>Áîëåå áåçîïàñíàÿ ðåàëèçàöèÿ ïîñòðàíè÷íîé íàâèãàöèè</title> <programlisting role="php"> <![CDATA[ settype($offset, 'integer'); $query = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;"; // îáðàòèòå âíèìàíèå íà ôîðìàò %d, èñïîëüçîâàíèå %s áûëî áû áåññìûñëåííî $query = sprintf("SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET %d;", $offset); ]]> </programlisting> </example> </para> </listitem> <listitem> <simpara> Ýêðàíèðóéòå ëþáîé íåöèôðîâîé ââîä, èñïîëüçóåìûé â çàïðîñàõ ê ÁÄ ïðè ïîìîùè ôóíêöèé <function>addslashes</function> èëè <function>addcslashes</function>. Îáðàòèòå âíèìàíèå íà <link linkend="security.database.storage">ïåðâûé ïðèìåð</link>. Ñëåäóåò ïîìíèòü, ÷òî îäíîãî èñïîëüçîâàíèÿ êàâû÷åê â çàïðîñå ìàëî, ýòî ëåãêî îáîéòè. </simpara> </listitem> <listitem> <simpara> Íå âûâîäèòå íèêàêîé èíôîðìàöèè î ÁÄ, îñîáåííî î åå ñòðóêòóðå. Òàêæå îçíàêîìüòåñü ñ ñîîòâåòñòâóþùèìè ðàçäåëàìè äîêóìåíòàöèè: <link linkend="security.errors">Ñîîáùåíèÿ îá îøèáêàõ</link> è <link linkend="ref.errorfunc">Ôóíêöèè îáðàáîòêè è ëîãèðîâàíèÿ îøèáîê</link>. </simpara> </listitem> <listitem> <simpara> Âû ìîæåòå èñïîëüçîâàòü õðàíèìûå ïðîöåäóðû è çàðàíåå îïðåäåëåííûå êóðñîðû äëÿ àáñòðàãèðîâàííîé ðàáîòû ñ äàííûìè, íå ïðåäîñòàâëÿÿ ïîëüçîâàòåëÿì ïðÿìîãî äîñòóïà ê äàííûì è ïðåäñòàâëåíèÿì, íî ýòî ðåøåíèå èìååò ñâîè îñîáåííîñòè. </simpara> </listitem> </itemizedlist> <simpara> Ïîìèìî âñåãî âûøåñêàçàííîãî, âû ìîæåòå ëîãèðîâàòü çàïðîñû â âàøåì ñêðèïòå ëèáî íà óðîâíå áàçû äàííûõ, åñëè îíà ýòî ïîääåðæèâàåò. Î÷åâèäíî, ÷òî ëîãèðîâàíèå íå ìîæåò ïðåäîòâðàòèòü íàíåñåíèå óùåðáà, íî ìîæåò ïîìî÷ü ïðè òðàññèðîâêå âçëîìàííîãî ïðèëîæåíèÿ. Ëîã-ôàéë ïîëåçåí íå ñàì ïî ñåáå, à èíôîðìàöèåé, êîòîðàÿ â íåì ñîäåðæèòñÿ. Ïðè÷åì, â áîëüøèíñòâå ñëó÷àåâ ïîëåçíî ëîãèðîâàòü âñå âîçìîæíûå äåòàëè. </simpara> </sect3> </sect2> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/errors.xml?r=1.1&p=1 Index: phpdoc-ru/security/errors.xml +++ phpdoc-ru/security/errors.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.errors"> <title>Ñîîáùåíèÿ îá îøèáêàõ</title> <para> Ñ òî÷êè çðåíèÿ áåçîïàñíîñòè âûâîä ñîîáùåíèé îá îøèáêàõ íåñåò â ñåáå êàê ïëþñû, òàê è ìèíóñû. </para> <para> Îäíà èç ñòàíäàðòíûõ ìåòîäèê, ïðèìåíÿåìûõ â àòàêàõ - ââîä íåêîððåêòíûõ äàííûõ ñ ïîñëåäóþùèì àíàëèçîì ñîäåðæàíèÿ è õàðàêòåðà ñîîáùåíèé îá îøèáêàõ. Ýòî äàåò âçëîìùèêó âîçìîæíîñòü ïðîâåðèòü ñêðèïòû è äàííûå ñåðâåðà íà íàëè÷èå ïîòåíöèàëüíûõ äûð. Íàïðèìåð, åñëè âçëîìùèê ïîëó÷èë íåêîòîðóþ èíôîðìàöèþ î ñòðàíèöå íà îñíîâàíèè îòïðàâêè ôîðìû, îí ïîïðîáóåò ïðåäîïðåäåëèòü íåêîòîðûå ïåðåäàâàåìûå çíà÷åíèÿ èëè ìîäèôèöèðîâàòü èõ: <example> <title>Àòàêà íà ïåðåìåííûå â HTML-ñòðàíèöå</title> <programlisting role="php"> <![CDATA[ <form method="post" action="attacktarget?username=badfoo&password=badfoo"> <input type="hidden" name="username" value="badfoo" /> <input type="hidden" name="password" value="badfoo" /> </form> ]]> </programlisting> </example> </para> <para> Âîçíèêàåìûå âî âðåìÿ ðàáîòû ñêðèïòîâ îøèáêè ÿâëÿþòñÿ äîñòàòî÷íî öåííîé èíôîðìàöèåé äëÿ ðàçðàáîò÷èêà, ñîäåðæàùåé òàêèå äàííûå, êàê ôóíêöèÿ èëè ôàéë, à òàêæå íîìåð ñòðîêè, â êîòîðîé âîçíèêëà îøèáêà. Âñÿ ýòà èíôîðìàöèÿ ìîæåò áûòü èñïîëüçîâàíà äëÿ âçëîìà. Äëÿ PHP-ðàçðàáîò÷èêà äîñòàòî÷íî ïðèâû÷íî ïîëüçîâàòüñÿ òàêèìè ôóíêöèÿìè, êàê <function>show_source</function>, <function>highlight_string</function> èëè <function>highlight_file</function> â öåëÿõ îòëàäêè, íî â æèâûõ ñàéòàõ ýòî ìîæåò îòêðûòü èíôîðìàöèþ î ñêðûòûõ ïåðåìåííûõ, íåïðîâåðÿåìîì ñèíòàêñèñå è äðóãèõ ïîòåíöèàëüíî îïàñíûõ ìîìåíòàõ. Îñîáåííî îïàñíî íàëè÷èå êîäà ñî âñòðîåííûì ìåõàíèçìîì îòëàäêè â ïóáëè÷íûõ ÷àñòÿõ ñàéòà. Âçëîìùèê ìîæåò ïîïûòàòüñÿ çàïóñòèòü îòëàäî÷íûé ìåõàíèçì, ïîäáèðàÿ îñíîâíûå ïðèçíàêè îòëàäêè: <example> <title>Èñïîëüçîâàíèå ñòàíäàðòíûõ îòëàäî÷íûõ ïåðåìåííûõ</title> <programlisting role="php"> <![CDATA[ <form method="post" action="attacktarget?errors=Y&showerrors=1&debug=1"> <input type="hidden" name="errors" value="Y" /> <input type="hidden" name="showerrors" value="1" /> <input type="hidden" name="debug" value="1" /> </form> ]]> </programlisting> </example> </para> <para> Íåçàâèñèìî îò ìåòîäà îáðàáîòêè îøèáîê âîçìîæíîñòü ïðîâåðêè ñèñòåìû íà íàëè÷èå îøèáîê ñíàáæàåò âçëîìùèêà äîïîëíèòåëüíîé èíôîðìàöèåé. </para> <para> Íàïðèìåð, ñòàíäàðòíûé âûâîä îá îøèáêå óêàçûâàåò îïåðàöèîííóþ ñèñòåìó, â êîòîðîé âûïîëíÿþòñÿ PHP ñêðèïòû. Åñëè âçëîìùèê àíàëèçèðóåò îáûêíîâåííóþ HTML-ñòðàíèöó, ïûòàÿñü íàéòè óÿçâèìûå ìåñòà, èñïîëüçóÿ ââîä íåâåðíûõ äàííûõ îí ìîæåò îáíàðóæèòü èñïîëüçîâàíèå PHP ñêðèïòîâ â äàííîé ñèñòåìå. </para> <para> Òàêæå óâåäîìëåíèå îá îøèáêå ìîæåò äàòü èíôîðìàöèþ î òîì, êàêàÿ áàçà äàííûõ èñïîëüçóåòñÿ, èëè, ê ïðèìåðó, êàê ïîñòðîåíà ëîãèêà ðàáîòû ñêðèïòîâ. Ýòî, â ñâîþ î÷åðåäü, ìîæåò ïîçâîëèòü âçëîìùèêó ïîäêëþ÷èòüñÿ ê îòêðûòîìó ïîðòó áàçû äàííûõ ëèáî íàéòè ñïåöèôè÷íûå îøèáêè â êîäå. Ïðîáóÿ ïîî÷åðåäíî ðàçëè÷íûå íåâåðíûå áëîêè äàííûõ, çëîóìûøëåííèê ìîæåò îïðåäåëèòü ïîðÿäîê àóòåíòèôèêàöèè â ñêðèïòå (íàïðèìåð, ïî íîìåðàì ñòðîê ñ îøèáêàìè) èëè ïðîâåðÿòü íà íàëè÷èå äûð ðàçëè÷íûå ó÷àñòêè êîäà. </para> <para> Âûâîä ñòàíäàðòíûõ îøèáîê, ñâÿçàííûõ ñ ôàéëîâîé ñèñòåìîé, ìîæåò óêàçàòü, ñ êàêèìè ïðèâåëåãèÿìè çàïóùåí âåá-ñåðâåð, è êàê îðãàíèçîâàíû êàòàëîãè ñàéòà. Îáðàáîòêà ïîäîáíûõ îøèáîê, íàïèñàííàÿ ðàçðàáîò÷èêàìè ïðèëîæåíèÿ, ìîæåò òîëüêî óñóãóáèòü ïðîáëåìó, åñëè âçëîìùèêîì áóäåò íàéäåí ñïîñîá îáíàðóæèòü "ñêðûòóþ" îòëàäî÷íóþ èíôîðìàöèþ. </para> <para> Ñóùåñòâóåò òðè îñíîâíû÷ ñïîñîáà ðåøåíèÿ ýòîé ïðîáëåìû. Ïåðâûé çàêëþ÷àåòñÿ â òîì, ÷òîáû ñòðóêòóðèðîâàòü âñå ôóíêöèè è ïîïûòàòüñÿ êîìïåíñèðîâàòü îáúåì âûäàâàåìûõ îøèáîê. Âòîðîé ñïîñîá - ïîëíîñòüþ îòêëþ÷èòü â ðàáîòàþùåì êîäå âûâîä ñîîáùåíèé îá îøèáêàõ. È, íàêîíåö, òðåòèé ñïîñîá - èñïîëüçîâàòü ñïåöèàëüíûå ñðåäñòâà PHP äëÿ ñîçäàíèÿ ñîáñòâåííîãî îáðàáîò÷èêà îøèáîê.  çàâèñèìîñòè îò èñïîëüçóåìîé âàìè ïîëèòèêè áåçîïàñíîñòè âû ìîæåòå ïðèìåíÿòü â âàøåé êîíêðåòíîé ñèòóàöèè âñå òðè ñïîñîáà. </para> <para> Îäèí èç âîçìîæíûõ ñïîñîáîâ îáåçîïàñèòü âàø êîä ïåðåä åãî ïóáëèêàöèåé äëÿ îáùåãî äîñòóïà - èíäèâèäóàëüíîå èñïîëüçîâàíèå <function>error_reporting</function>, ÷òîáû âûÿâèòü ïîòåíöèàëüíî îïàñíûå ïåðåìåííûå. Òåñòèðóÿ êîä ïåðåä âûïóñêîì ðåëèçà ïðè ïîìîùè çíà÷åíèÿ E_ALL, âû äîñòàòî÷íî ëåãêî ìîæåòå îáíàðóæèòü ó÷àñòêè êîäà, â êîòîðûõ ïåðåìåííûå ìîãóò áûòü ïîäìåíåíû ëèáî ìîäèôèöèðîâàíû. Ïîñëå îêîí÷àíèÿ òåñòèðîâàíèÿ, óñòàíîâèâ çíà÷åíèå E_NONE, âû ìîæåòå ïîëíîñòüþ îòêëþ÷èòü âûâîä ñîîáùåíèé îá îøèáêàõ. <example> <title>Ïîèñê ïîòåíöèàëüíî îïàñíûõ ïåðåìåííûõ ïðè ïîìîùè E_ALL</title> <programlisting role="php"> <![CDATA[ <?php if ($username) { // Ïåðåìåííàÿ íå èíèöèàëèçèðóåòñÿ ïåðåä èñïîëüçîâàíèåì $good_login = 1; } if ($good_login == 1) { // Åñëè ïðåäûäóùàÿ ïðîâåðêà ïîòåðïåëà íåóäà÷ó, ïåðåìåííàÿ îêàçûâàåòñÿ íåèíèöèàëèçèðîâàííîé readfile ("/highly/sensitive/data/index.html"); } ?> ]]> </programlisting> </example> </para> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/filesystem.xml?r=1.1&p=1 Index: phpdoc-ru/security/filesystem.xml +++ phpdoc-ru/security/filesystem.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.filesystem"> <title>Áåçîïàñíîñòü ôàéëîâîé ñèñòåìû</title> <simpara> PHP ÿâëÿåòñÿ îäíèì èç âàæíûõ ìîìåíòîâ â âîïðîñå áåçîïàñíîñòè ñåðâåðà, ïîñêîëüêó PHP-ñêðèïòû ìîãóò ìàíèïóëèðîâàòü ôàéëàìè è êàòàëîãàìè íà äèñêå.  ñâÿçè ñ ýòèì ñóùåñòâóþò êîíôèãóðàöèîííûå íàñòðîéêè, óêàçûâàþùèå, êàêèå ôàéëû ìîãóò áûòü äîñòóïíû è êàêèå îïåðàöèè ñ íèìè ìîæíî âûïîëíÿòü. Íåîáõîäèìî ïðîÿâëÿòü îñòîðîæíîñòü, ïîñêîëüêó ëþáîé èç ôàéëîâ ñ ñîîòâåòñòâóþùèìè ïðàâàìè äîñòóïà ìîæåò áûòü ïðî÷èòàí êàæäûì, êòî èìååò äîñòóï ê ôàéëîâîé ñèñòåìå. </simpara> <simpara> Ïîñêîëüêó â PHP èçíà÷àëüíî ïðåäïîëàãàëñÿ ïîëíîïðàâíûé ïîëüçîâàòåëüñêèé äîñòóï ê ôàéëîâîé ñèñòåìå, ìîæíî íàïèñàòü ñêðèïò, êîòîðûé ïîçâîëèò ÷èòàòü ñèñòåìíûå ôàéëû, òàêèå êàê /etc/passwd, óïðàâëÿòü ñåòåâûìè ñîåäèíåíèÿìè, îòïðàâëÿòü çàäàíèÿ ïðèíòåðó, è òàê äàëåå. Êàê ñëåäñòâèå âû âñåãäà äîëæíû áûòü óâåðåíû â òîì, ÷òî ôàéëû, êîòîðûå âû ÷èòàåòå èëè ìîäèôèöèðóåòå, ñîîòâåòñòâóþò âàøèì íàìåðåíèÿì. </simpara> <simpara> Ðàññìîòðèì ñëåäóþùèé ïðèìåð, â êîðîòîì ïîëüçîâàòåëü ñîçäàë ñêðèïò, óäàëÿþùèé ôàéë èç åãî äîìàøíåé äèðåêòîðèè. Ïðåäïîëàãàåòñÿ ñèòóàöèÿ, êîãäà âåá-èíòåðôåéñ, íàïèñàííûé íà PHP, ðåãóëÿðíî èñïîëüçóåòñÿ äëÿ ðàáîòû ñ ôàéëàìè, è íàñòðîéêè áåçîïàñíîñòè ïîçâîëÿþò óäàëÿòü ôàéëû â äîìàøíåì êàòàëîãå. </simpara> <para> <example> <title>Íåäîñòàòî÷íàÿ ïðîâåðêà âíåøíèõ äàííûõ.</title> <programlisting role="php"> <![CDATA[ <?php // Óäàëåíèå ôàéëà èç äîìàøíåé äèðåêòîðèè ïîëüçîâàòåëÿ $username = $_POST['user_submitted_name']; $homedir = "/home/$username"; $file_to_delete = "$userfile"; unlink ("$homedir/$userfile"); echo "$file_to_delete has been deleted!"; ?> ]]> </programlisting> </example> Ïîñêîëüêó ïåðåìåííûå ââîäÿòñÿ â ïîëüçîâàòåëüñêîé ôîðìå, ñóùåñòâóåò âîçìîæíîñòü óäàëèòü ôàéëû, ïðèíàäëåæàùèå êîìó-ëèáî äðóãîìó, ââåäÿ ñîîòâåòñòâóþùèå çíà÷åíèÿ.  ýòîì ñëó÷àå ìîæåò ïîíàäîáèòüñÿ àâòîðèçàöèÿ. Ïîñìîòðèì, ÷òî ïðîèçîéäåò, åñëè áóäóò îòïðàâëåíû çíà÷åíèÿ "../etc/" è "passwd". Ñêðèïò âûïîëíèò ñëåäóþùèå äåéñòâèÿ: <example> <title>Àòàêà íà ôàéëîâóþ ñèñòåìó</title> <programlisting role="php"> <![CDATA[ <?php // Óäàëåíèå ëþáîãî ôàéëà, äîñòóïíîãî èç PHP-ñêðèïòà. //  ñëó÷àå, åñëè PHP ðàáîòàåò ñ ïðàâàìè ïîëüçîâàòåëÿ root: $username = "../etc/"; $homedir = "/home/../etc/"; $file_to_delete = "passwd"; unlink ("/home/../etc/passwd"); echo "/home/../etc/passwd has been deleted!"; ?> ]]> </programlisting> </example> Cóùåñòâóþò äâà ðåøåíèÿ îïèñàííîé ïðîáëåìû. <itemizedlist> <listitem> <simpara> Îãðàíè÷èòü äîñòóï ïîëüçîâàòåëÿ, ñ ïðàâàìè êîòîðîãî ðàáîòàåò âåá-ñåðâåð. </simpara> </listitem> <listitem> <simpara> Ïðîâåðÿòü âñå äàííûå, ââîäèìûå ïîëüçîâàòåëåì. </simpara> </listitem> </itemizedlist> Âîò óëó÷øåíûé âàðèàíò êîäà: <example> <title>Áîëåå áåçîïàñíàÿ ïðîâåðêà èìåíè ôàéëà</title> <programlisting role="php"> <![CDATA[ <?php // Óäàëåíèå ëþáîãî ôàéëà, äîñòóïíîãî èç PHP-ñêðèïòà. $username = $_SERVER['REMOTE_USER']; // èñïîëüçîâàíèå àâòîðèçàöèè $homedir = "/home/$username"; $file_to_delete = basename("$userfile"); // óñå÷åíèå ïóòè unlink ($homedir/$file_to_delete); $fp = fopen("/home/logging/filedelete.log","+a"); //ëîãèðóåì óäàëåíèå $logstring = "$username $homedir $file_to_delete"; fputs ($fp, $logstring); fclose($fp); echo "$file_to_delete has been deleted!"; ?> ]]> </programlisting> </example> Îäíàêî è òàêàÿ ïðîâåðêà íå ó÷èòûâàåò âñå âîçìîæíûå ñèòóàöèè. Åñëè ñèñòåìà àâòîðèçàöèè ïîçâîëÿåò ïîëüçîâàòåëÿì âûáèðàòü ïðîèçâîëüíûå ëîãèíû, âëîìùèê ìîæåò ñîçäàòü ó÷åòíóþ çàïèñü âèäà "../etc/" è ñèñòåìà îïÿòü îêàæåòñÿ óÿçâèìîé. Èñõîäÿ èç ýòîãî, âàì ìîæåò ïîíàäîáèòüñÿ áîëåå ñòðîãàÿ ïðîâåðêà: <example> <title>Áîëåå ñòðîãàÿ ïðîâåðêà èìåíè ôàéëà</title> <programlisting role="php"> <![CDATA[ <?php $username = $_SERVER['REMOTE_USER']; // èñïîëüçîâàíèå àâòîðèçàöèè $homedir = "/home/$username"; if (!ereg('^[^./][^/]*$', $userfile)) die('bad filename'); //çàâåðøåíèå ðàáîòû if (!ereg('^[^./][^/]*$', $username)) die('bad username'); //çàâåðøåíèå ðàáîòû //etc... ?> ]]> </programlisting> </example> </para> <para>  çàâèñèìîñòè îò èñïîëüçóåìîé âàìè îïåðàöèîííîé ñèñòåìû íåîáõîäèìî ïðåäóñìàòðèâàòü âîçìîæíîñòü àòàêè íà ðàçíîîáðàçíûå ôàéëû, âêëþ÷àÿ ñèñòåìíûå ôàéëû óñòðîéñòâ (/dev/ èëè COM1), êîíôèãóðàöèîííûå ôàéëû (íàïðèìåð /etc/ èëè ôàéëû ñ ðàñøèðåíèåì .ini), õîðîøî èçâåñòíûå îáëàñòè õðàíåíèÿ äàííûõ (/home/, My Documents), è òàê äàëåå. Èñõîäÿ èç ýòîãî, êàê ïðàâèëî, ëåã÷å ðåàëèçîâàòü òàêóþ ïîëèòèêó áåçîïàñíîñòè, â êîòîðîé çàïðåùåíî âñå, èñêëþ÷àÿ òî, ÷òî ÿâíî ðàçðåøåíî. </para> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/general.xml?r=1.1&p=1 Index: phpdoc-ru/security/general.xml +++ phpdoc-ru/security/general.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.general"> <title>Îáùèå ðàññóæäåíèÿ</title> <simpara> Òàê êàê àáñîëþòíî áåçîïàñíûå ñèñòåìû ÿâëÿþòñÿ íå áîëåå, ÷åì ìèôîì, íà ïðàêòèêå ïðèõîäèòñÿ áàëàíñèðîâàòü ìåæäó êîìôîðòîì è áåçîïàñíîñòüþ. Åñëè êàæäàÿ ïåðåìåííàÿ, ââîäèìàÿ ïîëüçîâàòåëåì, áóäåò òðåáîâàòü äâå áèîìåòðè÷åñêèå ïðîâåðêè (íàïðèìåð, ñêàíèðîâàíèå ñåò÷àòêè ãëàçà è îòïå÷àòêè ïàëüöåâ), òî âû ïîëó÷èòå ïðåäåëüíî âûñîêóþ äîñòîâåðíîñòü äàííûõ. Íî ïîñêîëüêó çàïîëíåíèå ñëîæíîé ôîðìû áóäåò çàíèìàòü îêîëî ïîëó÷àñà, ó ïîëüçîâàòåëåé òàêîé ñèñòåìû íåïðåìåííî âîçíèêíåò æåëàíèå îáîéòè íàâÿç÷èâóþ çàùèòó. </simpara> <simpara> Ïðàâèëüíî ïîñòàâëåííàÿ çàùèòà äîëæíà ñîîòâåòñòâîâàòü îñíîâíûì òðåáîâàíèÿì áåçîïàñíîñòè, íå óõóäøàÿ ïðè ýòîì ðàáîòó ïîëüçîâàòåëÿ è íå óñëîæíÿÿ ñàìîìó ïðîãðàììèñòó ðàçðàáîòêó ïðîäóêòà. Âìåñòå ñ òåì, íåêîòîðûå àòàêè ìîãóò îñíîâûâàòüñÿ èìåííî íà òàêîì ïîäõîäå ê çàùèòå, ÷òî ïðèâîäèò ê åå ïîñòåïåííîìó îñëàáëåíèþ. </simpara> <simpara> Ñëåäóåò ïîìíèòü õîðîøóþ ïîãîâîðêó: íàäåæíîñòü ñèñòåìû îïðåäåëÿåòñÿ åå ñàìûì ñëàáûì çâåíîì. Íàïðèìåð, åñëè âñå òðàíçàêöèè ëîãèðóþòñÿ ïî âðåìåíè, ìåñòîðàñïîëîæåíèþ, òèïó òðàíçàêöèè è ðÿäó äðóãèõ ïàðàìåòðîâ, íî àâòîðèçàöèÿ ïîëüçîâàòåëÿ ïðîèñõîäèò âñåãî ëèøü ïî êóêå (cookie), òî ñâÿçü êîíêðåòíîé çàïèñè â ëîãå ñ ïîëüçîâàòåëåì ñèñòåìû âåñüìà ñîìíèòåëüíà. </simpara> <simpara> Ïðè òåñòèðîâàíèè ñëåäóåò ïîìíèòü, ÷òî âû íå ìîæåòå ïðîâåðèòü âñå âîçìîæíûå âàðèàíòû äàæå äëÿ ïðîñòåéøåé ñòðàíèöû. Äàííûå, êîòîðûå âû îæèäàåòå, ìîãóò ñîâåðøåííî íå ñîîòâåòñòâîâàòü òîìó, ÷òî ââåäåò ðàçúÿðåííûé ñëóæàùèé, õàêåð ñî ñòàæåì èëè äîìàøíèé êîò, ðàçãóëèâàþùèé ïî êëàâèàòóðå. Ïîýòîìó ëó÷øå ëîãè÷åñêè ïîäóìàòü íàä âîïðîñîì: â êàêîì ìåñòå ìîãóò áûòü ââåäåíû íåîæèäàííûå äàííûå, êàê èõ ìîæíî ìîäèôèöèðîâàòü, óñå÷ü ëèáî, íàîáîðîò, äîïîëíèòü. </simpara> <simpara> Èíòåðíåò íàïîëíåí ëþäüìè, êîòîðûå õîòÿò ñäåëàòü ñåáå èìÿ íà òîì, ÷òî âçëîìàþò âàø êîä, ðàçðóøàò ñàéò, îïóáëèêóþò íà íåì íåóìåñòíûé êîíòåíò èëè ïðîñòî ñäåëàþò âàøè äíè èíòåðåñíåå. È íå âàæíî, ìàëåíüêèé ó âàñ ñàéò èëè áîëüøîé, åñëè ó âàñ åñòü îíëàéí-ñåðâåð - âû óæå ïîòåíöèàëüíàÿ æåðòâà. Ìíîãèå ïðîãðàììû-âçëîìùèêè íåñîìòðÿò íà ðàçìåð, îíè ïðîñòî ïåðåáèðàþò ìàññèâû IP-àäðåñîâ, âûèñêèâàÿ î÷åðåäíóþ æåðòâó. Ïîñòàðàéòåñü íå ñòàòü îäíîé èç íèõ. </simpara> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/globals.xml?r=1.1&p=1 Index: phpdoc-ru/security/globals.xml +++ phpdoc-ru/security/globals.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.registerglobals"> <title>Èñïîëüçîâàíèå ãëîáàëüíûõ ïåðåìåííûõ (Register_Globals)</title> <para> Íàâåðíîå, íàèáîëåå ñïîðíûì ìîìåíòîì â ðàçðàáîòêå PHP ñòàëà çàìåíà çíà÷åíèÿ ïî óìîë÷àíèþ äëÿ îïöèè <link linkend="ini.register-globals"> register_globals</link> ñ ON íà OFF â âåðñèè <ulink url="&url.php.release4.2.0;">4.2.0</ulink>. Áîëüøèíñòâî ïîëüçîâàòåëåé äîâåðèëèñü ðàçðàáîò÷èêàì, äàæå íå çíàÿ, ÷òî ýòî çà îïöèÿ è êàê îíà âëèÿåò íà ðàáîòó PHP. Ýòà ñòðàíèöà äîêóìåíòàöèè ïðèçâàíà ïîêàçàòü, êàê ýòà íàñòðîéêà ñî÷åòàåòñÿ ñ âîïðîñàìè áåçîïàñíîñòè ïðè ðàçðàáîòêå ïðèëîæåíèé. Ñëåäóåò ïîíèìàòü, ÷òî ñàìà ïî ñåáå ýòà îïöèÿ íèêàê íå âëèÿåò íà áåçîïàñíîñòü, óðãîçó ïðåäñòàâëÿåò íåêîððåêòíîå èñïîëüçîâàíèå ïðåäîñòàâëÿåìûõ åþ âîçìîæíîñòåé. </para> <para>  ñëó÷àå, åñëè çíà÷åíèå ïàðàìåòðà register_globals ON, ïåðåä âûïîëíåíèåì âàøåãî êîäà áóäóò èíèöèàëèçèðîâàíû ðàçëè÷íûå ïåðåìåííûå, íàïðèìåð, ïåðåìåííûå, ïåðåäàííûå ïðè îòïðàâêå ôîðìû. Òàêæå, ó÷èòûâàÿ òîò ôàêò, ÷òî PHP íå òðåáóåò èíèöèàëèçàöèè ïåðåìåííûõ, íàïèñàòü ïîòåíöèàëüíî îïàñíûé êîä î÷åíü ëåãêî. Ýòî áûëî î÷åíü ñïîðíûì ðåøåíèåì, íî îáùåñòâî ðàçðàáîò÷èêîâ PHP ðåøèëî èçìåíèòü çíà÷åíèå ïî óìîë÷àíèþ ýòîé äèðåêòèâû íà OFF.  ïðîòèâíîì ñëó÷àå ïðè íàïèñàíèè êîäà ðàçðàáîò÷èêè íå ìîãëè áû ñ óâåðåííîñòüþ ñêàçàòü, îòêóäà ïðèøëà òà èëè èíàÿ ïåðåìåííàÿ è íàñêîëüêî îíà äîñòîâåðíà. Äî òàêîãî íîâîââåäåíèÿ ïåðåìåííûå, îïðåäåëÿåìûå ðàçðàáîò÷èêîì âíóòðè ñêðèïòà, è ïåðåäàâàåìûå ïîëüçîâàòåëåì âíåøíèå äàííûå ìîãëè ïåðåìåøèâàòüñÿ. Ïðèâåäåì ïðîñòîé ïðèìåð çëîóïîòðåáëåíèÿ êîíôèãóðàöèîííîé îïöèåé register_globals: </para> <para> <example> <title>Ïðèìåð îïàñíîãî êîäà ñ register_globals = on</title> <programlisting role="php"> <![CDATA[ <?php // óñòàíàâëèâàåì ïåðåìåííóþ $authorized = true òîëüêî äëÿ ïîëüçîâàòåëåé, ïðîøåäøèõ àâòîðèçàöèþ if (authenticated_user()) { $authorized = true; } // Ïîñêîëüêó â ñëó÷àå íåóäà÷è ïðè ïðîâåðêå àâòîðèçàöèè ïåðåìåííàÿ $authorized // íå óñòàíîâëåíà, îíà ìîæåò áûòü óñòàíîâëåíà àâòîìàòè÷åñêè, áëàãîäàðÿ register_globals, // íàïðèìåð, ïðè GET çàïðîñå GET auth.php?authorized=1. // Òàêèì îáðàçîì, ïðîéòè ýòó ïðîâåðêó ìîæíî áåç àâòîðèçàöèè if ($authorized) { include "/highly/sensitive/data.php"; } ?> ]]> </programlisting> </example> </para> <para>  ñëó÷àå register_globals = on ëîãèêà ðàáîòû ñêðèïòà ìîæåò áûòü íàðóøåíà.  ñëó÷àå, åñëè óñòàíîâëåííîå çíà÷åíèå off, ïåðåìåííàÿ <varname>$authorized</varname> íå ìîæåò áûòü óñòàíîâëåíà èç âíåøíèõ äàííûõ çàïðîñà, è ñêðèïò áóäåò ðàáîòàòü êîððåêòíî. Íî âñå æå èíèöèàëèçàöèÿ ïåðåìåííûõ - îäèí èç ïðèçíàêîâ õîðîøåãî òîíà â ïðîãðàììèðîâàíèè. Íàïðèìåð, â ïðèâåäåííîì âûøå ó÷àñòêå êîäà ìû ìîãëè ïîìåñòèòü <literal>$authorized = false</literal> â êà÷åñòâå ïåðâîé ñòðîêè. Òàêîé êîä ðàáîòàë áû êàê ñî çíà÷åíèåì on, òàê è off îïöèè register_globals, è ïîäðàçóìåâàÿ, ÷òî ïî óìîë÷àíèþ ïîëüçîâàòåëü íå ïðîõîäèë àâòîðèçàöèþ. </para> <para> Ïðèâåäåì åùå îäèí ïðèìåð, èñïîëüçóþùèé <link linkend="ref.session">ñåññèè</link>.  ñëó÷àå, åñëè register_globals = on, ìû ìîæåì èñïîëüçîâàòü ïåðåìåííóþ <varname>$username</varname> â ïðèâåäåííîì íèæå ïðèìåðå, íî òîãäà ó íàñ íå áóäåò óâåðåííîñòè â äîñòîâåðíîñòè åå çíà÷åíèÿ (ê ïðèìåðó, îíà ìîãëà áûòü ïåðåäàíà â GET-çàïðîñå). </para> <para> <example> <title>Ïðèìåð èñïîëüçîâàíèÿ ñåññèé ñî çíà÷åíèåì register_globals on èëè off</title> <programlisting role="php"> <![CDATA[ <?php // Ìû íå çíàåì, îòêóäà ïîëó÷åíà ïåðåìåííàÿ $username, íî òî÷íî çíàåì, ÷òî // ïåðåìåííàÿ $_SESSION õðàíèò â ñåáå äàííûå ñåññèè if (isset($_SESSION['username'])) { echo "Hello <b>{$_SESSION['username']}</b>"; } else { echo "Hello <b>Guest</b><br />"; echo "Would you like to login?"; } ?> ]]> </programlisting> </example> </para> <para> Òàêæå ñóùåñòâóåò âîçìîæíîñòü ðåàëèçàöèè îïåðàòèâíîãî ðåàãèðîâàíèÿ â ñëó÷àå ïîïûòêè ïîäìåíû ïåðåìåííûõ. Òàê êàê âî âðåìÿ ðàçðàáîòêè ïðèëîæåíèÿ ìû çíàåì îæèäàåìîå çíà÷åíèå ïåðåìåííîé, à òàêæå çíàåì åå äîñòîâåðíîå çíà÷åíèå, ìû ìîæåì èõ ñîïîñòàâèòü. Ýòî íå çàùèòèò êîä îò ïîäìåíû ïåðåìåííûõ, íî óñëîæíèò ïåðåáîð âîçìîæíûõ âàðèàíòîâ. Åñëè âû íå õîòèòå çíàòü, êàê èìåííî áûëè ïîëó÷åíû âíåøíèå äàííûå, èñïîëüçóéòå ïåðåìåííóþ <varname>$_REQUEST</varname>, êîòîðàÿ ñîñòîèò èç äàííûõ GET è POST çàïðîñîâ, à òàêæå äàííûõ COOKIE. Òàêæå, èíôîðìàöèþ îá ýòîì ìîæíî íàéòè â ðàçäåëå <link linkend="language.variables.external">âíåøíèå äàííûå â PHP</link>. </para> <para> <example> <title>Îáíàðóæåíèå ïîïûòêè ïîäìåíû ïåðåìåííûõ</title> <programlisting role="php"> <![CDATA[ <?php if (isset($_COOKIE['MAGIC_COOKIE'])) { // MAGIC_COOKIE ïîëó÷åíà èç äîñòîâåðíîãî èñòî÷íèêà. // Äëÿ ïîëíîé óâåðåííîñòè íåîáõîäèìî ïðîâåðèòü åå çíà÷åíèå. } elseif (isset($_GET['MAGIC_COOKIE']) || isset($_POST['MAGIC_COOKIE'])) { mail("admin@example.com", "Îáíàðóæåíà ïîïûòêà âçëîìà", $_SERVER['REMOTE_ADDR']); echo "Îáíàðóæåíî íàðóøåíèå áåçîïàñíîñòè, àäìèíèñòðàòîð óâåäîìëåí."; exit; } else { // MAGIC_COOKIE â äàííûõ çàïðîñà íå ïðèñóòñòâóåò } ?> ]]> </programlisting> </example> </para> <para> Ñëåäóåò ïîíèìàòü, ÷òî óñòàíîâêà register_globals â off íå ñäåëàåò âàø êîä áåçîïàñíûì. Êàæäóþ ïîëó÷åííóþ îò ïîëüçîâàòåëÿ ïåðåìåííóþ ñëåäóåò ïðîâåðÿòü íà ñîîòâåòñòâèå îæèäàåìîìó çíà÷åíèþ. Âñåãäà ïðîâåðÿéòå ââîä ïîëüçîâàòåëÿ è èíèöèàëèçèðóéòå âñå èñïîëüçóåìûå ïåðåìåííûå. Äëÿ ïðîâåðêè íà íàëè÷èå íåèíèöèàëèçèðîâàííûõ ïåðåìåííûõ ìîæíî âêëþ÷èòü â îïöèþ <function>error_reporting</function> îòîáðàæåíèå îøèáîê êàòåãîðèè <constant>E_NOTICE</constant>. </para> ¬e.superglobals; </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/hiding.xml?r=1.1&p=1 Index: phpdoc-ru/security/hiding.xml +++ phpdoc-ru/security/hiding.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.hiding"> <title>Ñîêðûòèå PHP</title> <para>  îáùåì ñëó÷àå âíåñåíèå íåÿñíîñòè íåíàìíîãî óëó÷øàåò çàùèùåííîñòü ñèñòåìû. Íî áûâàþò ñëó÷àè, êîãäà ñëåäóåò èñïîëüçîâàòü ìàëåéøóþ âîçìîæíîñòü. </para> <para> Íåñêîëüêî íåñëîæíûõ ìåòîäèê ìîãóò ïîìî÷ü âàì ñêðûòü PHP, ÷òî óñëîæíÿåò ðàáîòó ïîòåíöèàëüíîãî âçëîìùèêà, êîòîðûé ïûòàåòñÿ íàéòè áðåøü â âàøåé ñèñòåìå. Óñòàíîâèâ îïöèþ expose_php = off â êîíôèãóðàöèîííîì ôàéëå &php.ini;, âû óìåíüøèòå êîëè÷åñòâî äîñòóïíîé õàêåðó èíôîðìàöèè. </para> <para> Åùå îäíà ìåòîäèêà çàêëþ÷àåòñÿ â íàñòðîéêå âåá-ñåðâåðà òàêèì îáðàçîì, ÷òîáû îí îáðàáàòûâàë ôàéëû ñ ðàçëè÷íûìè ðàñøèðåíèÿìè êàê PHP-ñêðèïòû. Ýòî ìîæíî óêàçàòü êàê â &htaccess; ôàéëàõ, òàê è êîíôèãóðàöèîííîì ôàéëå Apache.  òàêîì ñëó÷àå âû ñìîæåòå èñïîëüçîâàòü ïðè íàïèñàíèè êîäà íåñòàíäàðòíûå ðàñøèðåíèÿ: <example> <title>Ìàñêèðîâêà PHP ïîä äðóãèå ÿçûêè ïðîãðàììèðîâàíèÿ</title> <programlisting role="apache-conf"> <![CDATA[ # Òåïåðü PHP-ñêðèïòû ìîãóò èìåòü òå æå ðàñøèðåíèÿ, ÷òî è äðóãèå ÿçûêè ïðîãðàììèðîâàíèÿ AddType application/x-httpd-php .asp .py .pl ]]> </programlisting> </example> Èëè ñêðûòü åãî ñîâñåì: <example> <title>Èñïîëüçîâàíèå íåèçâåñòíûõ ðàñøèðåíèé äëÿ PHP-ñêðèïòîâ</title> <programlisting role="apache-conf"> <![CDATA[ # Òåïåðü PHP-ñêðèïòû ìîãóò èìåòü íåèçâåñòíûå òèïû ôàéëîâ AddType application/x-httpd-php .bop .foo .133t ]]> </programlisting> </example> Òàêæå ìîæíî ñïðÿòàòü åãî ïîä âèäîì HTML-êîäà, ÷òî ïðèâåäåò ê ïîòåðå ïðîèçâîäèòåëüíîñòè, òàê êàê âñå HTML ôàéëû áóäóò îáðàáàòûâàòüñÿ êàê PHP-êîä: <example> <title>Ìàñêèðîâêà PHP-êîäà ïîä html-ôàéëû</title> <programlisting role="apache-conf"> <![CDATA[ # Òåïåðü PHP-ñêðòïû ìîãóò âûãëÿäåòü êàê îáûêíîâåííûé HTML AddType application/x-httpd-php .htm .html ]]> </programlisting> </example> ×òîáû äîñòè÷ü æåëàåìîãî ýôôåêòà, âû äîëæíû ïåðåèìåíîâàòü âñå âàøè ñêðèïòû â ñîîòâåòñòâèè ñ âûáðàííûì âàìè ðàñøèðåíèåì. Îïèñàííîå â ýòîì ðàçäåëå äîêóìåíòàöèè ïîâûøåíèå áåçîïàñíîñòè ÷åðåç ñîêðûòèå PHP èìååò ìàëî íåäîñòàòêîâ ïðè íåáîëüøèõ çàòðàòàõ. </para> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/index.xml?r=1.1&p=1 Index: phpdoc-ru/security/index.xml +++ phpdoc-ru/security/index.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- Last Revision before split: 1.66 --> <chapter id="security.index"> <title>Áåçîïàñíîñòü</title> &security.intro; &security.general; &security.cgi-bin; &security.apache; &security.filesystem; &security.database; &security.errors; &security.globals; &security.variables; &security.hiding; &security.current; </chapter> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/intro.xml?r=1.1&p=1 Index: phpdoc-ru/security/intro.xml +++ phpdoc-ru/security/intro.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.intro"> <title>Âñòóïëåíèå</title> <simpara> PHP ÿâëÿåòñÿ ìîùíûì ÿçûêîì ïðîãðàììèðîâàíèÿ è èíòåðïðåòàòîðîì, âçàèìîäåéñòâóþùèì ñ âåá-ñåðâåðîì êàê ìîäóëü ëèáî êàê íåçàâèñèìîå áèíàðíîå <acronym>CGI</acronym> ïðèëîæåíèå. PHP ñïîñîáåí îáðàùàòüñÿ ê ôàéëàì, âûïîëíÿòü ðàçëè÷íûå êîìàíäû íà ñåðâåðå è îòêðûâàòü ñåòåâûå ñîåäèíåíèÿ. Èìåííî ïîýòîìó âñå ñêðèïòû, èñïîëíÿåìûå íà ñåðâåðå ÿâëÿþòñÿ ïîòåíöèàëüíî îïàñíûìè. PHP èçíà÷àëüíî ðàçðàáàòûâàëñÿ êàê áîëåå çàùèùåííûé (îòíîñèòåëüíî Perl, C) ÿçûê äëÿ íàïèñàíèÿ CGI-ïðèëîæåíèé. Ïðè ïîìîùè ðÿäà íàñòðîåê âî âðåìÿ êîìïèëÿöèè, à òàêæå íàñòðîåê âî âðåìÿ ðàáîòû ïðèëîæåíèÿ, âû âñåãäà ñìîæåòå íàéòè ïîäõîäÿùåå ñî÷åòàíèå ñâîáîäû äåéñòâèé è áåçîïàñíîñòè. </simpara> <simpara> Ïîñêîëüêó ñóùåñòâóåò ìíîãî ðàçëè÷íûõ ñïîñîáîâ èñïîëüçîâàíèÿ PHP, èìååòñÿ è ìíîæåñòâî îïöèé, óïðàâëÿþùèõ åãî ïîâåäåíèåì. Øèðîêèé âûáîð îïöèé ãàðàíòèðóåò âàì âîçìîæíîñòü èñïîëüçîâàòü PHP â ðàçíûõ öåëÿõ, íî òàêæå îçíà÷àåò, ÷òî íåêîòîðûå êîìáèíàöèè îïöèé äåëàþò ñåðâåð íåçàùèùåííûì. </simpara> <simpara> Ãèáêîñòü êîíôèãóðèðîâàíèÿ PHP ìîæíî ñðàâíèòü ñ ãèáêîñòüþ ñàìîãî ÿçûêà. PHP ìîæíî èñïîëüçîâàòü äëÿ ñîçäàíèÿ ïîëíîöåííûõ ñåðâåðíûõ ïðèëîæåíèé, èñïîëüçóþùèõ äîñòóïíûå äëÿ óêàçàííîãî ïîëüçîâàòåëÿ âîçìîæíîñòè îïåðàöèîííîé ñèñòåìû, òàêæå âîçìîæíà ðåàëèçàöèÿ âêëþ÷åíèÿ ôàéëîâ, õðàíÿùèõñÿ íà ñåðâåðå ñ ìèíèìàëüíûì ðèñêîì â æåñòêî êîíòðîëèðóåìîé ñðåäå. Òî, íàñêîëüêî áåçîïàñåí âàø ñåðâåð è êàê íàñòðîåíî îêðóæåíèå, â áîëüøåé ÷àñòè çàâèñèò îò PHP-ðàçðàáîò÷èêà. </simpara> <simpara> Ýòà ãëàâà íà÷èíàåòñÿ ñ ðàññìîòðåíèÿ íåêîòîðûõ îáùèõ âîïðîñîâ áåçîïàñíîñòè, ðàçëè÷íûõ êîíôèãóðàöèîííûõ îïöèé è èõ êîìáèíàöèé, à òàêæå ñèòóàöèé, êîãäà èõ èñïîëüçîâàíèå ÿâëÿåòñÿ áåçîïàñíûì. Êðîìå òîãî, ïðèâîäÿòñÿ íåêîòîðûå ðàññóæäåíèÿ êàñàòåëüíî áåçîïàñíîãî êîäèðîâàíèÿ. </simpara> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/variables.xml?r=1.1&p=1 Index: phpdoc-ru/security/variables.xml +++ phpdoc-ru/security/variables.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.variables"> <title>Äàííûå, ââåäåííûå ïîëüçîâàòåëåì</title> <para> Íàèáîëåå îïàñíûå äûðû âî ìíîãèõ PHP-ñêðèïòàõ âîçíèêàþò íå ñòîëüêî èç-çà ñàìîãî ÿçûêà, ñêîëüêî èç-çà êîäà, íàïèñàííîãî áåç ó÷åòà ñîîòâåòñòâóþùèõ òðåáîâàíèé áåçîïàñíîñòè. Êàê ñëåäñòâèå, âû âñåãäà äîëæíû âûäåëÿòü âðåìÿ íà èññëåäîâàíèå ðàçðàáàòûâàåìîãî ó÷àñòêà êîäà, ÷òîáû îöåíèòü ïîòåíöèàëüíóþ óãðîçó îò ââîäà ïåðåìåííîé ñ íåñòàíäàðòíûì çíà÷åíèåì. <example> <title>Ïîòåíöèàëüíî îïàñíîå èñïîëüçîâàíèå ïåðåìåííûõ</title> <programlisting role="php"> <![CDATA[ <?php // óäàëèòü ôàéëû èç äîìàøíåé äèðåêòîðèè ïîëüçîâàòåëÿ... // à ìîæåò, åùå ÷òî íèáóäü? unlink ($evil_var); // çàïèñàòü â ëîã-ôàéë âûïîëíÿåìîå äåéñòâèå... // ìîæåò áûòü, äàæå /etc/passwd? fputs ($fp, $evil_var); // âûïîëíåíèå òðèâèàëüíûõ äåéñòâèé... èëè rm -rf *? system ($evil_var); exec ($evil_var); ?> ]]> </programlisting> </example> Âû äîëæíû òùàòåëüíî ïðîâåðÿòü âàø êîä è áûòü àáñîëþòíî óâåðåíû â òîì, ÷òî âñå äàííûå, ïåðåäàâàåìûå âåá-áðàóçåðîì, ïðîâåðÿþòñÿ íàäëåæàùèì îáðàçîì. Ïîïðîáóéòå îòâåòèòü äëÿ ñåáÿ íà ñëåäóþùèå âîïðîñû: <itemizedlist> <listitem> <simpara> Áóäåò ëè äàííûé ñêðèïò âîçäåéñòâîâàòü èñêëþ÷èòåëüíî íà ïðåäïîëàãàåìûå äàííûå? </simpara> </listitem> <listitem> <simpara> Ïðàâèëüíî ëè áóäóò îáðàáîòàíû íåêîððåêòíûå èëè íåñòàíäàðòíûå äàííûå? </simpara> </listitem> <listitem> <simpara> Âîçìîæíî ëè èñïîëüçîâàíèå ñêðèïòà íå ïðåäóñìîòðåííûì ñïîñîáîì? </simpara> </listitem> <listitem> <simpara> Âîçìîæíî ëè åãî èñïîëüçîâàíèå â ñî÷åòàíèè ñ äðóãèìè ñêðèïòàìè â íåãàòèâíûõ öåëÿõ? </simpara> </listitem> <listitem> <simpara> Áóäåò ëè êàæäàÿ òðàíçàêöèÿ êîððåêòíî ëîãèðîâàíà? </simpara> </listitem> </itemizedlist> Îòâåòèâ íà ýòè âîïðîñû âî âðåìÿ íàïèñàíèÿ ñêðèïòà, à íå ïîñëå, âû, âîçìîæíî, ïðåäîòâðàòèòå ïîñëåäóþùóþ äîðàáîòêó ñêðèïòà â öåëÿõ ïîâûøåíèÿ åãî áåçîïàñíîñòè. Íà÷èíàÿ ðàçðàáîòêó ñ ýòèõ âîïðîñîâ, âû íå ãàðàíòèðóåòå ïîëíóþ áåçîïàñíîñòü âàøåé ñèñòåìû, íî ñìîæåòå çíà÷èòåëüíî ïîâûñèòü å¸. </para> <para> Âû òàêæå ìîæåòå ïðåäóñìîòðåòü îòêëþ÷åíèå òàêèõ êîíôèãóðàöèîííûõ îïöèé, êàê register_globals, magic_quotes è íåêîòîðûõ äðóãèõ, êîòîðûå ìîãóò ïðèâîäèòü ê ñîìíåíèÿì îòíîñèòåëüíî ïðîèñõîæäåíèÿ èëè çíà÷åíèÿ ïîëó÷àåìûõ ïåðåìåííûõ. Èñïîëüçîâàíèå ïðè íàïèñàíèè êîäà ðåæèìà error_reporting(E_ALL) ìîæåò ïîìî÷ü, ïðåäóïðåæäàÿ âàñ îá èñïîëüçîâàíèè ïåðåìåííûõ äî èíèöèàëèçàöèè èëè ïðîâåðêè (÷òî ïðåäîòâðàòèò ðàáîòó ñ äàííûìè, îòëè÷íûè îò îæèäàåìûõ). </para> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 -->
http://cvs.php.net/co.php/phpdoc-ru/features/cookies.xml?r=1.1&p=1 Index: phpdoc-ru/features/cookies.xml +++ phpdoc-ru/features/cookies.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <chapter id="features.cookies"> <title>Cookies</title> <para> PHP ïðîçðà÷íî ïîääåðæèâàåò HTTP cookies. Cookies ýòî ìåõàíèçì õðàíåíèÿ äàííûõ áðîóçåðîì óäàëåííîé ìàøèíû äëÿ îòñëåæèâàíèÿ èëè èäåíòèôèêàöèè âîçâðàùàþùèõñÿ ïîñåòèòåëåé. Âû ìîæåòå óñòàíîâèòü cookies ïðè ïîìîùè ôóíêöèé <function>setcookie</function> èëè <function>setrawcookie</function>. Cookies ÿâëÿþòñÿ ÷àñòüþ HTTP-çàãîëîâêà, ïîýòîìó <function>setcookie</function> äîëæíà âûçûâàòüñÿ äî ëþáîãî âûâîäà äàííûõ â áðîóçåð. Ýòî òî æå ñàìîå îãðàíè÷åíèå, êîòîðîå èìååò ôóíêöèÿ <function>header</function>. Âû ìîæåòå èñïîëüçîâàòü <link linkend="ref.outcontrol">ôóíêöèè áóôåðèçàöèè âûâîäà</link>, ÷òîáû çàäåðæàòü âûâîä ðåçóëüòàòîâ ðàáîòû ñêðèïòà äî òîãî ìîìåíòà, êîãäà áóäåò èçâåñòíî, ïîíàäîáèòñÿ ëè óñòàíîâêà cookies èëè äðóãèõ HTTP-çàãîëîâêîâ. </para> <para> Ëþáûå cookies, îòïðàâëåííûå ñåðâåðó áðîóçåðîì êëèåíòà, áóäóò àâòîìàòè÷åñêè ïðåîáðàçîâàíû â ïåðåìåííûå PHP, ïîäîáíî äàííûì ìåòîäîâ GET è POST. Íà ýòîò ïðîöåññ âëèÿþò êîíôèãóðàöèîííûå äèðåêòèâû <literal>register_globals</literal> è <literal>variables_order</literal>. Äëÿ íàçíà÷åíèÿ íåñêîëüêèõ çíà÷åíèé îäíîé cookie, ïðîñòî äîáàâüòå <literal>[]</literal> ê å¸ èìåíè. </para> <para>  PHP 4.1.0 è âûøå, ãëîáàëüíûé ìàññèâ <varname>$_COOKIE</varname> âñåãäà àâòîìàòè÷åñêè çàïîëíÿåòñÿ çíà÷åíèÿìè ïîëó÷åííûõ cookies.  áîëåå ðàííèõ âåðñèÿõ îïðåäåëÿåòñÿ ìàññèâ <varname>$HTTP_COOKIE_VARS</varname> íî òîëüêî êîãäà âêëþ÷åíà äèðåêòèâà <literal>track_vars</literal>. (Ýòà äèðåêòèâà âñåãäà âêëþ÷åíà íà÷èíàÿ ñ PHP 4.0.3.) </para> <para> Äîïîëíèòåëüíàÿ èíôîðìàöèÿ, â òîì ÷èñëå è îá îñîáåííîñòÿõ ðåàëèçàöèè áðîóçåðîâ, ïðèâåäåíà â îïèñàíèè ôóíêöèé <function>setcookie</function> è <function>setrawcookie</function>. </para> </chapter> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/apache.xml?r=1.1&p=1 Index: phpdoc-ru/security/apache.xml +++ phpdoc-ru/security/apache.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.apache"> <title>Åñëè PHP óñòàíîâëåí êàê ìîäóëü Apache</title> <simpara> Êîãäà PHP èñïîëüçóåòñÿ êàê ìîäóëü Apache, îí íàñëåäóåò ïðàâà ïîëüçîâàòåëÿ, ñ êîòîðûìè áûë çàïóùåí âåá-ñåðâåð (îáû÷íî ýòî ïîëüçîâàòåëü 'nobody'). Ýòî âëèÿåò íà îáåñïå÷åíèå áåçîïàñíîñòè è ðåàëèçàöèþ àâòîðèçàöèè. Íàïðèìåð, åñëè âû èñïîëüçóåòå áàçó äàííûõ, êîòîðàÿ íå èìååò âñòðîåííîãî ìåõàíèçìà ðàçãðàíè÷åíèÿ äîñòóïà, âàì ïðèéäåòñÿ îáåñïå÷èòü äîñòóï ê ÁÄ äëÿ ïîëüçîâàòåëÿ 'nobody'.  òàêîì ñëó÷àå çëîâðåäíûé ñêðèïò ìîæåò ïîëó÷èòü äîñòóï ê áàçå äàííûõ è ìîäèôèöèðîâàòü åå, äàæå íå çíàÿ ëîãèíà è ïàðîëÿ. Âïîëíå âîçìîæíà ñèòóàöèÿ, êîãäà âåá-ïàóê íåâåðíûìè çàïðîñàìè ñòðàíèöû àäìèíèñòðàòîðà áàçû äàííûõ óíè÷òîæèò âñå äàííûå èëè äàæå ñòðóêòóðó ÁÄ. Âû ìîæåòå èçáåæàòü òàêîé ñèòóàöèè ïðè ïîìîùè àâòîðèçàöèè Apache èëè ðàçðàáîòàâ ñîáñòâåííóþ ìîäåëü äîñòóïà, èñïîëüçóÿ LDAP, ôàéëû &htaccess; èëè ëþáûå äðóãèå òåõíîëîãèè, âíåäðÿÿ ñîîòâåòñòâóþùèé êîä â âàøè ñêðèïòû. </simpara> <simpara> Äîñòàòî÷íî ÷àñòî èñïîëüçóþòñÿ òàêèå íàñòðîéêè áåçîïàñíîñòè, ïðè êîòîðûõ PHP (èìååòñÿ ââèäó ïîëüçîâàòåëü, ñ ïðàâàìè êîòîðîãî âûïîëíÿåòñÿ Apache) èìååò ìèíèìàëüíûå ïðèâåëåãèè, íàïðèìåð îòñóòñòâóåò âîçìîæíîñòü çàïèñè â ïîëüçîâàòåëüñêèå äèðåêòîðèè. Èëè, íàïðèìåð, îòñóòñòâóåò âîçìîæíîñòü ðàáîòàòü ñ áàçîé äàííûõ. Ïðè ýòîì ñèñòåìà áåçîïàñíîñòè íå ïîçâîëÿåò çàïèñûâàòü êàê "õîðîøèå", òàê è "ïëîõèå" ôàéëû, àíàëîãè÷íî ïîçâîëÿåò ïðîèçâîäèòü êàê "õîðîøèå", òàê è "ïëîõèå" òðàíçàêöèè. </simpara> <simpara> Ðàñïðîñòðàíåííîé îøèáêîé ÿâëÿåòñÿ çàïóñê Apache ñ ïðàâàìè ñóïåðïîëüçîâàòåëÿ èëè ëþáîå äðóãîå ðàñøèðåíèå ïîëíîìî÷èé âåá-ñåðâåðà. </simpara> <simpara> Ðàñøèðåíèå ïðèâèëåãèé âåá-ñåðâåðà äî ïîëíîìî÷èé óãðîæàåò ðàáîòîñïîñîáíîñòè âñåé ñèñòåìû, òàêèå êîìàíäû, êàê sudo, chroot äîëæíû âûïîëíÿòüñÿ èñêëþ÷èòåëüíî òåìè, êòî ñ÷èòàåò ñåáÿ ïðîôåññèîíàëàìè â âîïðîñàõ áåçîïàñíîñòè. </simpara> <simpara> Ñóùåñòâóåò íåñêîëüêî ïðîñòûõ ðåøåíèé. Èñïîëüçóÿ <link linkend="ini.open-basedir">open_basedir</link>, âû ìîæåòå îãðàíè÷èòü äåðåâî äîñòóïíûõ äèðåêòîðèé äëÿ PHP. Âû òàê æå ìîæåòå îïðåäåëèòü îáëàñòü äîñòóïà Apache, îãðàíè÷èâ âñå âåá-ñåðâèñû íå-ïîëüçîâàòåëüñêèìè èëè íå-ñèñòåìíûìè ôàéëàìè. </simpara> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/cgi-bin.xml?r=1.1&p=1 Index: phpdoc-ru/security/cgi-bin.xml +++ phpdoc-ru/security/cgi-bin.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.cgi-bin"> <title>Åñëè PHP óñòàíîâëåí êàê CGI</title> <sect2 id="security.cgi-bin.attacks"> <title>Âîçìîæíûå àòàêè</title> <simpara> Èñïîëüçîâàíèå PHP êàê áèíàðíîãî <acronym>CGI</acronym>-ïðèëîæåíèÿ ÿâëÿåòñÿ îäíèì èç âàðèàíòîâ, êîãäà ïî êàêèì-ëèáî ïðè÷èíàì íåæåëàòåëüíî èíòåãðèðîâàòü PHP â âåá-ñåðâåð (íàïðèìåð Apache) â êà÷åñòâå ìîäóëÿ, ëèáî ïðåäïîëàãàåòñÿ èñïîëüçîâàíèå òàêèõ óòèëèò, êàê chroot è setuid äëÿ îðãàíèçàöèè áåçîïàñíîãî îêðóæåíèÿ âî âðåìÿ ðàáîòû ñêðèïòîâ. Òàêàÿ óñòàíîâêà îáû÷íî ñîïðîâîæäàåòñÿ êîïèðîâàíèåì èñïîëíÿåìîãî ôàéëà PHP â äèðåêòîðèþ cgi-bin âåá-ñåðâåðà. CERT (îðãàíèçàöèÿ, ñëåäÿùàÿ çà óãðîçàìè áåçîïàñíîñòè) <ulink url="&url.cert;">CA-96.11</ulink> ðåêîìåíäóåò íå ïîìåùàòü êàêèå-ëèáî èíòåðïðåòàòîðû â êàòàëîã cgi-bin. Äàæå åñëè PHP èñïîëüçóåòñÿ êàê ñàìîñòîÿòåëüíûé èíòåðïðêòàòîð, îí ñïðîåêòèðîâàí òàê, ÷òîáû ïðåäîòâðàòèòü âîçìîæíîñòü ñëåäóþùèõ àòàê: </simpara> <itemizedlist> <listitem> <simpara> Äîñòóï ê ñèñòåìíûì ôàéëàì: <filename role="url">http://my.host/cgi-bin/php?/etc/passwd</filename> </simpara> <simpara> Äàííûå, ââåäåííûå â ñòðîêå çàïðîñà (URL) ïîñëå âîïðîñèòåëüíîãî çíàêà, ïåðåäàþòñÿ èíòåðïðåòàòîðó êàê àðãóìåíòû êîìàíäíîé ñòðîêè ñîãëàñíî CGI ïðîòîêîëó. Îáû÷íî èíòåðïðåòàòîðû îòêðûâàþò è èñïîëíÿþò ôàéë, óêàçàííûé â êà÷åñòâå ïåðâîãî àðãóìåíòà. </simpara> <simpara>  ñëó÷àå èñïîëüçîâàíèÿ PHP ïîñðåäñòâîì CGI-ïðîòîêîëà îí íå ñòàíåò èíòåðïðåòèðîâàòü àðãóìåíòû êîìàíäíîé ñòðîêè. </simpara> </listitem> <listitem> <simpara> Äîñòóï ê ïðîèçâîëüíîìó äîêóìåíòó íà ñåðâåðå: <filename role="url">http://my.host/cgi-bin/php/secret/doc.html</filename> </simpara> <simpara> Ñîãëàñíî îáùåïðèíÿòîìó ñîãëàøåíèþ ÷àñòü ïóòè â çàïðîøåííîé ñòðàíèöå, êîòîðàÿ ðàñïîëîæåíà ïîñëå èìåíè âûïîëíÿåìîãî ìîäóëÿ PHP, <filename role="uri">/secret/doc.html</filename>, èñïîëüçóåòñÿ äëÿ óêàçàíèÿ ôàéëà, êîòîðûé áóäåò èíòåðïðåòèðîâàí êàê <acronym>CGI</acronym>-ïðîãðàììà Îáû÷íî, íåêîòîðûå êîíôèãóðàöèîííûå îïöèè âåá-ñåðåâåðà (íàïðèìåð, Action äëÿ ñåðâåðà Apache) èñïîëüçóþòñÿ äëÿ ïåðåíàïðàâëåíèÿ äîêóìåíòà, ê ïðèìåðó, äëÿ ïåðåíàïðàâëåíèÿ çàïðîñîâ âèäà <filename role="url">http://my.host/secret/script.php</filename> èíòåðïðåòàòîðó PHP.  òàêîì ñëó÷àå âåá-ñåðâåð âíà÷àëå ïðîâåðÿåò ïðàâà äîñòóïà ê äèðåêòîðèè <filename role="uri">/secret</filename>, è ïîñëå ýòîãî ñîçäàåò ïåðåíàïðàâëåííûé çàïðîñ <filename role="url">http://my.host/cgi-bin/php/secret/script.php</filename>. Ê ñîæàëåíèþ, åñëè çàïðîñ èçíà÷àëüíî çàäàí â ïîëíîì âèäå, ïðîâåðêà íà íàëè÷èå ïðàâ äëÿ ôàéëà <filename role="uri">/secret/script.php</filename> íå âûïîëíÿåòñÿ, îíà ïðîèñõîäèò òîëüêî äëÿ ôàéëà <filename role="uri">/cgi-bin/php</filename>. Òàêèì îáðàçîì, ïîëüçîâàòåëü èìååò âîçìîæíîñòü îáðàòèòüñÿ ê <filename role="uri">/cgi-bin/php</filename>, è, êàê ñëåäñòâèå, ê ëþáîìó çàùèùåííîìó äîêóìåíòó íà ñåðâåðå. </simpara> <simpara>  PHP, óêàçûâàÿ âî âðåìÿ êîìïèëÿöèè îïöèþ <link linkend="install.configure.enable-force-cgi-redirect">--enable-force-cgi-redirect</link>, à òàêå îïöèè <link linkend="ini.doc-root">doc_root</link> è <link linkend="ini.user-dir">user_dir</link> âî âðåìÿ âûïîëíåíèÿ ñêðèïòà, ìîæíî ïðåäîòâðàòèòü ïîäîáíûå àòàêè äëÿ äèðåêòîðèé ñ îãðàíè÷åííûì äîñòóïîì. Áîëåå äåòàëüíî ïðèâåäåííûå îïöèè, à òàêæå èõ êîìáèíàöèè áóäóò ðàññìîòðåíû íèæå. </simpara> </listitem> </itemizedlist> </sect2> <sect2 id="security.cgi-bin.default"> <title>Âàðèàíò 1: îáñëóæèâàþòñÿ òîëüêî îáùåäîñòóïíûå ôàéëû</title> <simpara>  ñëó÷àå, åñëè íà âàøåì ñåðâåðå îòñóòñòâóþò ôàéëû, äîñòóï ê êîòîðûì îãðàíè÷åí ïàðîëåì ëèáî ôèëüòðîì ïî IP-àäðåñàì, íåò íèêàêîé íåîáõîäèìîñòè èñïîëüçîâàòü äàííûå îïöèè. Åñëè âàø âåá-ñåðâåð íå ðàçðåøàåò âûïîëíÿòü ïåðåíàïðàâëåíèÿ ëèáî íå èìååò âîçìîæíîñòè âçàèìîäåéñòâîâàòü ñ èñïîëíÿåìûì PHP-ìîäóëåì íà íåîáõîäèìîì óðîâíå áåçîïàñíîñòè, âû ìîæåòå èñïîëüçîâàòü îïöèþ <link linkend="install.configure.enable-force-cgi-redirect">--enable-force-cgi-redirect</link> âî âðåìÿ ñáîðêè PHP. Íî ïðè ýòîì âû äîëæíû óáåäèòüñÿ, ÷òî àëüòåðíàòèâíûå ñïîñîáû âûçîâà ñêðèïòà, òàêèå êàê íåïîñðåäñòâåííî âûçîâ <filename role="php">http://my.host/cgi-bin/php/dir/script.php</filename> ëèáî ñ ïåðåàäðåñàöèåé <filename role="php">http://my.host/dir/script.php</filename>, íåäîñòóïíû. </simpara> <simpara>  âåá-ñåðâåðå Apache ïåðåíàïðàâëåíèå ìîæåò áûòü ñêîíôèãóðèðîâàíî ïðè ïîìîùè äèðåêòèâ AddHandler è Action (îïèñàíî íèæå). </simpara> </sect2> <sect2 id="security.cgi-bin.force-redirect"> <title>Âàðèàíò 2: èñïîëüçîâàíèå --enable-force-cgi-redirect</title> <simpara> Ýòà îïöèÿ, óêàçûâàåìàÿ âî âðåìÿ ñáîðêè PHP, ïðåäîòâðàùàåò âûçîâ ñêðèïòîâ íåïîñðåäñòâåííî ïî àäðåñó âèäà <filename role="php">http://my.host/cgi-bin/php/secretdir/script.php</filename>. Âìåñòî ýòîãî, PHP áóäåò îáðàáàòûâàòü ïðèøåäøèé çàïðîñ òîëüêî â òîì ñëó÷àå, åñëè îí áûë ïåðåíàïðàâëåí âåá-ñåðâåðîì. </simpara> <simpara> Îáû÷íî ïåðåíàïðàâëåíèå â âåá-ñåðâåðå Apache íàñòðàèâàåòñÿ ïðè ïîìîùè ñëåäóþùèõ îïöèé: </simpara> <programlisting role="apache-conf"> <![CDATA[ Action php-script /cgi-bin/php AddHandler php-script .php ]]> </programlisting> <simpara> Ýòà îïöèÿ ïðîâåðåíà òîëüêî äëÿ âåá-ñåðâåðà Apache, åå ðàáîòà îñíîâûâàåòñÿ íà óñòàíîâêå â ñëó÷àå ïåðåíàïðàâëåíèÿ íåñòàíäàðòíîé ïåðåìåííîé <envar>REDIRECT_STATUS</envar>, íàõîäÿùåéñÿ â CGI-îêðóæåíèè.  ñëó÷àå, åñëè âàø âåá-ñåðâåð íå ïðåäîñòàâëÿåò âîçìîæíîñòè îäíîçíà÷íî èäåíòèôèöèðîâàòü, ÿâëÿåòñÿ ëè äàííûé çàïðîñ ïåðåíàïðàâëåííûì, âû íå ìîæåòå èñïîëüçîâàòü îïèñûâàåìóþ â äàííîì ðàçäåëå îïöèþ è äîëæíû âîñïîëüçîâàòüñÿ ëþáûì äðóãèì ìåòîäîì ðàáîòû ñ CGI-ïðèëîæåíèÿìè. </simpara> </sect2> <sect2 id="security.cgi-bin.doc-root"> <title>Âàðèàíò 3: èñïîëüçîâàíèå îïöèé doc_root è user_dir</title> <simpara> Ðàçìåùåíèå äèíàìè÷åñêîãî êîíòåíòà, òàêîãî êàê ñêðèïòû ëèáî ëþáûå äðóãèå èñïîëíÿåìûå ôàéëû, â äèðåêòîðèè âåá-ñåðâåðà äåëàåò åãî ïîòåíöèàëüíî îïàñíûì.  ñëó÷àå, åñëè â êîíôèãóðàöèè ñåðâåðà äîïóùåíà îøèáêà, âîçìîæíà ñèòóàöèÿ, êîãäà ñêðèïòû íå âûïîëíÿþòñÿ, à îòîáðàæàþòñÿ â áðàóçåðå, êàê îáû÷íûå HTML-äîêóìåíòû, ÷òî ìîæåò ïðèâåñòè ê óòå÷êå êîíôèäåíöèàëüíîé èíôîðìàöèè (íàïðèìåð, ïàðîëåé), ëèáî èíôîðìàöèè, ÿâëÿþùåéñÿ èíòåëëåêòóàëüíîé ñîáñòâåííîñòüþ. Èñõîäÿ èç òàêèõ ñîîáðàæåíèé, ìíîãèå ñèñòåìíûå àäìèíèñòðàòîðû ïðåäïî÷èòàþò èñïîëüçîâàòü äëÿ õðàíåíèÿ ñêðèïòîâ îòäåëüíóþ äèðåêòîðèþ, ðàáîòàÿ ñî âñåìè ðàçìåùåííûìè â íåé ôàéëàìè ïî CGI-èíòåðôåéñó. </simpara> <simpara>  ñëó÷àå, åñëè íåâîçìîæíî ãàðàíòèðîâàòü, ÷òî çàïðîñû íå ïåðåíàïðàâëÿþòñÿ, êàê áûëî ïîêàçàíî â ïðåäûäóùåì ðàçäåëå, íåîáõîäèìî óêàçûâàòü ïåðåìåííóþ doc_root, êîòîðàÿ îòëè÷àåòñÿ îò êîðíåâîé äèðåêòîðèè âåá-äîêóìåíòîâ. </simpara> <simpara> Âû ìîæåòå óñòàíîâèòü êîðíåâóþ äèðåêòîðèþ äëÿ PHP-ñêðèïòîâ, íàñòðîèâ ïàðàìåòð <link linkend="ini.doc-root">doc_root</link> â <link linkend="configuration.file">êîíôèãóðàöèîííîì ôàéëå</link>, ëèáî óñòàíîâèâ ïåðåìåííóþ îêðóæåíèÿ <envar>PHP_DOCUMENT_ROOT</envar>.  ñëó÷àå, åñëè PHP èñïîëüçóåòñÿ ïîñðåäñòâîì CGI, ïîëíûé ïóòü ê îòêðûâàåìîìó ôàéëó áóäåò ïîñòðîåí íà îñíîâàíèè çíà÷åíèÿ ïåðåìåííîé <parameter>doc_root</parameter> è óêàçàííîãî â çàïðîñå ïóòè. Òàêèì îáðàçîì, âû ìîæåòå áûòü óâåðåíû, ÷òî ñêðèïòû áóäóò âûïîëíÿòüñÿ òîëüêî âíóòðè óêàçàííîé âàìè äèðåêòîðèè (êðîìå äèðåêòîðèè <parameter>user_dir</parameter>, êîòîðàÿ îïèñàíà íèæå). </simpara> <simpara> Åùå îäíà èñïîëüçóåìàÿ ïðè íàñòðîéêå áåçîïàñíîñòè îïöèÿ - <link linkend="ini.user-dir">user_dir</link>.  ñëó÷àå, åñëè ïåðåìåííàÿ user_dir íå óñòàíîâëåíà, ïóòü ê îòêðûâàåìîìó ôàéëó ñòðîèòñÿ îòíîñèòåëüíî <parameter>doc_root</parameter>. Çàïðîñ âèäà <filename role="url">http://my.host/~user/doc.php</filename> ïðèâîäèò ê âûïîëíåíèþ ñêðèïòà, íàõîäÿùåãîñÿ íå â äîìàøíåì êàòàëîãå ñîîòâåòñòâóþùåãî ïîëüçîâàòåëÿ, à íàõîäÿùåãîñÿ â ïîäêàòàëîãå doc_root ñêðèïòà <filename role="uri">~user/doc.php</filename> (äà, èìÿ äèðåêòîðèè íà÷èíàåòñÿ ñ ñèìâîëà <literal>~</literal>). </simpara> <simpara> Íî åñëè ïåðåìåííîé <filename role="dir">public_php</filename> ïðèñâîåíî çíà÷åíèå, íàïðèìåð, <filename role="url">http://my.host/~user/doc.php</filename>, òîãäà â ïðèâåäåííîì âûøå ïðèìåðå áóäåò âûïîëíåí ñêðèïò <filename>doc.php</filename>, íàõîäÿùèéñÿ â äîìàøíåì êàòàëîãå ïîëüçîâàòåëÿ, â äèðåêòîðèè <filename role="dir">public_php</filename>. Íàïðèìåð, åñëè äîìàøíèé êàòàëîã ïîëüçîâàòåëÿ <filename role="dir">/home/user</filename>, áóäåò âûïîëíåí ôàéë <filename>/home/user/public_php/doc.php</filename>. </simpara> <simpara> Óñòàíîâêà îïöèè <parameter>user_dir</parameter> ïðîèñõîäèò íåçàâèñèìî îò óñòàíîâêè <parameter>doc_root</parameter>, òàêèì îáðàçîì âû ìîæåòå êîíòðîëèðîâàòü êîðíåâóþ äèðåêòîðèþ âåá-ñåðâåðà è ïîëüçîâàòåëüñêèå äèðåêòîðèè íåçàâèñèìî äðóã îò äðóãà. </simpara> </sect2> <sect2 id="security.cgi-bin.shell"> <title>Âàðèàíò 4: PHP âíå äåðåâà âåá-äîêóìåíòîâ</title> <para> Îäèí èç ñïîñîáîâ ñóùåñòâåííî ïîâûñèòü óðîâåíü áåçîïàñíîñòè - ïîìåñòèòü èñïîëíÿåìûé ìîäóëü PHP âíå äåðåâà âåá-äîêóìåíòîâ, íàïðèìåð â <filename role="dir">/usr/local/bin</filename>. Åäèíñòâåííûì íåäîñòàòêîì òàêîãî ïîäõîäà ÿâëÿåòñÿ òî, ÷òî ïåðâàÿ ñòðîêà êàæäîãî ñêðèïòà äîëæíà èìåòü âèä: <informalexample> <programlisting> <![CDATA[ #!/usr/local/bin/php ]]> </programlisting> </informalexample> Òàêæå íåîáõîäèìî ñäåëàòü âñå ôàéëû ñêðèïòîâ èñïîëíÿåìûìè. Òàêèì îáðàçîì, ñêðèïò áóäåò ðàññìàòðèâàòüñÿ òàê æå, êàê è ëþáîå äðóãîå CGI-ïðèëîæåíèå, íàïèñàííîå íà Perl, sh èëè ëþáîì äðóãîì ñêðèïòîâîì ÿçûêå, êîòîðûé èñïîëüçóåò äîïèñûâàíèå <literal>#!</literal> â íà÷àëî ôàéëà äëÿ çàïóñêà ñàìîãî ñåáÿ. </para> <para> ×òî áû âíóòðè ñêðèïòà âû ìîãëè ïîëó÷èòü êîððåêòíûå çíà÷åíèÿ ïåðåìåííûõ <envar>PATH_INFO</envar> è <envar>PATH_TRANSLATED</envar>, PHP äîëæåí áûòü ñêîíôèãóðèðîâàí ñ îïöèåé <link linkend="install.configure.enable-discard-path">--enable-discard-path</link>. </para> </sect2> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/current.xml?r=1.1&p=1 Index: phpdoc-ru/security/current.xml +++ phpdoc-ru/security/current.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.current"> <title>Íåîáõîäèìîñòü îáíîâëåíèé</title> <simpara> PHP, êàê è ëþáàÿ äðóãàÿ ñèñòåìà, âñå âðåìÿ òùàòåëüíî ïðîâåðÿåòñÿ è óëó÷øàåòñÿ. Êàæäàÿ íîâàÿ âåðñèÿ ñîäåðæèò ìíîæåñòâî êàê ñóùåñòâåííûõ, òàê è ìåëêèõ íîâøåñòâ è äîðàáîòîê, êîòîðûå, â òîì ÷èñëå, êàñàþòñÿ ïîâûøåíèÿ áåçîïàñíîñòè, ðàñøèðåíèÿ êîíôèãóðàöèîííûõ âîçìîæíîñòåé, à òàê æå ñòàáèëüíîñòè âàøåé ñèñòåìû. </simpara> <simpara> Êàê è â äðóãèõ ÿçûêàõ ïðîãðàììèðîâàíèÿ, ðåêîìåíäóåòñÿ ðåãóëÿðíî îáíîâëÿòü PHP è áûòü â êóðñå èçìåíåíèé, ñäåëàííûõ â ïîñëåäíèõ âåðñèÿõ. </simpara> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/database.xml?r=1.1&p=1 Index: phpdoc-ru/security/database.xml +++ phpdoc-ru/security/database.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.database"> <title>Áåçîïàñíîñòü áàç äàííûõ</title> <simpara> Íà ñåãîäíÿøíèé äåíü áàçû äàííûõ ÿâëÿþòñÿ êëþ÷åâûìè êîìïîíåíòàìè áîëüøèíñòâà âåá-ïðèëîæåíèé, ïîçâîëÿÿ ïðåäîñòàâëÿòü íà ñàéòàõ äèíàìè÷åñêèé êîíòåíò. Ïîñêîëüêó â òàêèõ ÁÄ ìîæåò õðàíèòüñÿ î÷åíü òî÷íàÿ èëè êîíôèäåíöèàëüíàÿ èíôîðìàöèÿ, âû äîëæíû îáåñïå÷èòü õîðîøóþ çàùèòó äàííûõ. </simpara> <simpara> Äëÿ èçâëå÷åíèÿ èëè ñîõðàíåíèÿ ëþáûõ äàííûõ âàì íåîáõîäèìî îòêðûòü ñîåäèíåíèå ñ áàçîé äàííûõ, îòïðàâèòü âåðíûé çàïðîñ, èçâëå÷ü ðåçóëüòàò è çàêðûòü ñîåäèíåíèå.  íàñòîÿùåå âðåìÿ íàèáîëåå ðàñïðîñòðàíåííûé ñòàíäàðò îáùåíèÿ - ñòðóêòóðèðîâàííûé ÿçûê çàïðîñîâ (SQL). Âñåãäà ñëåäóåò ïîìíèòü î âîçìîæíîñòè àòàêè <link linkend="security.database.sql-injection">ïîñðåäñòâîì SQL-çàïðîñà</link>. </simpara> <simpara> Î÷åâèäíî, ÷òî ñàì ïî ñåáå PHP íå ìîæåò çàùèòèòü âàøó áàçó äàííûõ. Ýòîò ðàçäåë äîêóìåíòàöèè ðàññêàçûâàåò îá îñíîâàõ áåçîïàñíîãî äîñòóïà è óïðàâëåíèÿ äàííûìè â PHP-ñêðèïòàõ. </simpara> <simpara> Çàïîìíèòå ïðîñòîå ïðàâèëî: ìàêñèìàëüíàÿ çàùèòà. ×åì áîëüøå ïîòåíöèàëüíî îïàñíûõ ó÷àñòêîâ ñèñòåìû âû ïðîðàáîòàåòå, òåì ñëîæíåå áóäåò ïîòåíöèàëüíîìó âçëîìùèêó ïîëó÷èòü äîñòóï ê áàçå äàííûõ èëè ïîâðåäèòü åå. Õîðîøèé äèçàéí áàçû äàííûõ è ïðîãðàììíûõ ïðèëîæåíèé ïîìîæåò âàì ñïðàâèòüñÿ ñ âàøèìè ñòðàõàìè. </simpara> <sect2 id="security.database.design"> <title>Ïðîåêòèðîâàíèå áàçû äàííûõ</title> <simpara> Ïåðâûé øàã - ýòî âñåãäà ñîçäàíèå ÁÄ, èñêëþ÷àÿ òîò ñëó÷àé, êîãäà âû õîòèòå èñïîëüçîâàòü ãîòîâóþ áàçó, ïðåäîñòàâëÿåìóþ òðåòüèì ëèöîì. Ïîñëå òîãî, êàê áàçà äàííûõ ñîçäàíà, îíà íàçíà÷àåòñÿ ïîëüçîâàòåëþ, êîòîðûé âûïîëíèë ñîçäàâøèé ÁÄ çàïðîñ. Êàê ïðàâèëî, òîëüêî âëàäåëåö (èëè ñóïåðïîëüçîâàòåëü) ìîæåò âûïîëíÿòü ðàçëè÷íûå äåéñòâèÿ ñ ðàçëè÷íûìè îáúåêòàìè, õðàíèìûìè â áàçå äàííûõ. Äëÿ òîãî, ÷òîáû è äðóãèå ïîëüçîâàòåëè èìåëè ê íåé äîñòóï, èõ íåîáõîäèìî íàäåëèòü ñîîòâåòñòâóþùèìè ïðèâåëåãèÿìè. </simpara> <simpara> Ïðèëîæåíèÿ íå äîëæíû ñîåäèíÿòüñÿ ñ áàçîé äàííûõ, èñïîëüçóÿ ó÷åòíóþ çàïèñü âëàäåëüöà èëè ñóïåðïîëüçîâàòåëÿ, èíà÷å îíè ñìîãóò ìîäèôèöèðîâàòü ñòðóêòóðó òàáëèö (íàïðèìåð, óäàëèòü íåêîòîðûå òàáëèöû) èëè äàæå óäàëèòü âñå ñîäåðæèìîå ÁÄ öåëèêîì. </simpara> <simpara> Âû ìîæåòå ñîçäàòü ðàçëè÷íûå ó÷åòíûå çàïèñè ïîëüçîâàòåëåé ÁÄ äëÿ êàæäîé èíäèâèäóàëüíîé ïîòðåáíîñòè ïðèëîæåíèÿ ñ ñîîòâåòñòâóþùèìè ôóíêöèîíàëüíûìè îãðàíè÷åíèÿìè. Ðåêîìåíäóåòñÿ íàçíà÷àòü òîëüêî ñàìûå íåîáõîäèìûå ïðèâèëåãèè, òàêæå âû äîëæíû èçáåãàòü ñèòóàöèé, êîãäà îäèí è òîò æå ïîëüçîâàòåëü ìîæåò âçàèìîäåéñòâîâàòü ñ áàçîé äàííûõ â íåñêîëüêèõ ðåæèìàõ. Âû äîëæíû ïîíèìàòü, ÷òî åñëè çëîóìûøëåííèê ñìîæåò âîñïîëüçîâàòüñÿ êàêîé-ëèáî ó÷åòíîé çàïèñüþ âàøåé ÁÄ, îí ñìîæåò âíîñèòü â áàçó âñå òå èçìåíåíèÿ, ÷òî è ïðîãðàììà, êîòîðàÿ èñïîëüçóåò òåêóùóþ ó÷åòíóþ çàïèñü. </simpara> <simpara> Âàì íå îáÿçàòåëüíî ðåàëèçîâûâàòü âñþ áèçíåñ-ëîãèêó â âåá-ïðèëîæåíèè (ò.å. â ñêðèïòàõ), äëÿ ýòîãî òàêæå ìîæíî èñïîëüçîâàòü âîçìîæíîñòè, ïðåäîñòàâëÿåìûå áàçîé äàííûõ: òðèããåðû, ïðåäñòàâëåíèÿ, ïðàâèëà.  ñëó÷àå ðîñòà ñèñòåìû âàì ïîíàäîáÿòñÿ íîâûå ñîåäèíåíèÿ ñ ÁÄ, è ëîãèêó ðàáîòû ïîíàäîáèòüñÿ äóáëèðîâàòü äëÿ êàæäîãî íîâîãî èíòåðôåéñà äîñòóïà. Èñõîäÿ èç âûøåñêàçàííîãî, òðèããåðû ìîãóò èñïîëüçîâàòüñÿ äëÿ ïðîçðà÷íîé è àâòîìàòè÷åñêîé îáðàáîòêè çàïèñåé, ÷òî ÷àñòî íåîáõîäèìî ïðè îòëàäêå ïðèëîæåíèé èëè ïðè òðàññèðîâêå îòêàòà òðàíçàêöèé. </simpara> </sect2> <sect2 id="security.database.connection"> <title>Ñîåäèíåíèå ñ áàçîé äàííûõ</title> <simpara> Âû ìîæåòå èñïîëüçîâàòü áåçîïàñíûå SSL èëè ssh ñîåäèíåíèÿ, äëÿ øèôðîâàíèÿ äàííûõ, êîòîðûìè îáìåíèâàþòñÿ êëèåíò è ñåðâåð. Åñëè âû ðåàëèçóåòå ÷òî-íèáóäü èç ýòîãî, òî ìîíèòîðèíã òðàôèêà è ñáîð äàííûõ î âàøåé áàçå äàííûõ äëÿ ïîòåíöèàëüíîãî âçëîìùèêà ñóùåñòâåííî óñëîæíèòñÿ. </simpara> <!--simpara> If your database server has native SSL support, consider using <link linkend="ref.openssl">OpenSSL functions</link> in communication between PHP and database via SSL. </simpara--> </sect2> <sect2 id="security.database.storage"> <title>Çàùèòà õðàíèëèùà áàçû äàííûõ</title> <simpara> SSL/SSH çàùèùàåò äàííûå, êîòîðûìè îáìåíèâàþòñÿ êëèåíò è ñåðâåð, íî íå çàùèùàþò ñàìè äàííûå, õðàíèìûå â áàçå äàííûõ. SSL - ïðîòîêîë øèôðîâàíèÿ íà óðîâíå ñåàíñà ïåðåäà÷è äàííûõ. </simpara> <simpara>  ñëó÷àå, åñëè âçëîìùèê ïîëó÷èë íåïîñðåäñòâåííûé äîñòóï ê ÁÄ (â îáõîä âåá-ñåðâåðà), îí ìîæåò èçâëå÷ü èíòåðåñóþùèå äàííûå èëè íàðóøèòü èõ öåëîñòíîñòü, ïîñêîëüêó èíôîðìàöèÿ íå çàùèùåíà íà óðîâíå ñàìîé ÁÄ. Øèôðîâàíèå äàííûõ - õîðîøèé ñïîñîá ïðåäîòâðàòèòü òàêóþ ñèòóàöèþ, íî ëèøü íåçíà÷èòåëüíîå êîëè÷åñòâî ÁÄ ïðåäîñòàâëÿþò òàêóþ âîçìîæíîñòü. </simpara> <simpara> Íàèáîëåå ïðîñòîå ðåøåíèå ýòîé ïðîáëåìû - óñòàíîâèòü âíà÷àëå îáûêíîâåííûé ïðîãðàììíûé ïàêåò äëÿ øèôðîâàíèÿ äàííûõ, à çàòåì èñïîëüçîâàòü åãî â âàøèõ ñêðèïòàõ. PHP, â òàêîì ñëó÷àå, ìîæåò ïîìî÷ü âàì â ðàáîòå ñ òàêèìè ðàñøèðåíèÿìè êàê <link linkend="ref.mcrypt">Mcrypt</link> è <link linkend="ref.mhash">Mhash</link>, ðåàëèçóþùèìè ðàçëè÷íûå àëãîðèòìû êðèïòîâàíèÿ. Ïðè òàêîì ïîäõîäå ñêðèïò âíà÷àëå øèôðóåò ñîõðàíÿåìûå äàííûå, à çàòåì äåøèôðóåò èõ ïðè çàïðîñå. Íèæå ïðèâåäåíû ïðèìåðû òîãî, êàê ðàáîòàåò øèôðîâàíèå äàííûõ â PHP-ñêðèïòàõ. </simpara> <simpara>  ñëó÷àå ðàáîòû ñî ñêðûòûìè ñëóæåáíûìè äàííûìè èõ íåøèôðîâàííîå ïðåäñòàâëåíèå íå òðåáóåòñÿ (ò.å. íå îòîáðàæàåòñÿ), è, êàê ñëåäñòâèå, ìîæíî èñïîëüçîâàòü õåøèðîâàíèå. Õîðîøî èçâåñòíûé ïðèìåð õýøèðîâàíèÿ - õðàíåíèå MD5-õåøà îò ïàðîëÿ â ÁÄ, âìåñòî õðàíåíèÿ îðèãèíàëüíîãî çíà÷åíèÿ. Áîëåå äåòàëüíàÿ èíôîðìàöèÿ äîñòóïíà â îïèñàíèè ôóíêöèé <function>crypt</function> and <function>md5</function>. </simpara> <example> <title>Èñïîëüçîâàíèå õåøèðîâàííûõ ïàðîëåé</title> <programlisting role="php"> <![CDATA[ // ñîõðàíåíèå õåøèðîâàííîãî ïàðîëÿ $query = sprintf("INSERT INTO users(name,pwd) VALUES('%s','%s');", addslashes($username), md5($password)); $result = pg_exec($connection, $query); // ïðîâåðêà ââåäåííîãî ïîëüçîâàòåëåì ëîãèíà è ïàðîëÿ íà êîððåêòíîñòü $query = sprintf("SELECT 1 FROM users WHERE name='%s' AND pwd='%s';", addslashes($username), md5($password)); $result = pg_exec($connection, $query); if (pg_numrows($result) > 0) { echo "Welcome, $username!"; } else { echo "Authentication failed for $username."; } ]]> </programlisting> </example> </sect2> <sect2 id="security.database.sql-injection"> <title>SQL-èíúåêöèè</title> <simpara> Ìíîãèå âåá-ðàçðàáîò÷èêè äàæå íå äîãàäûâàþòñÿ, ÷òî SQL-çàïðîñû ìîãóò áûòü ïîääåëàíû, è ñ÷èòàþò, ÷òî SQL-çàïðîñû âñåãäà äîñòîâåðíû. Íà ñàìîì äåëå ïîääåëüíûå çàïðîñû ìîãóò îáîéòè îãðàíè÷åíèÿ äîñòóïà, ñòàíäàðòíóþ ïðîâåðêó àâòîðèçàöèè, à íåêîòîðûå âèäû çàïðîñîâ ìîãóò äàòü âîçìîæíîñòü âûïîëíÿòü êîìàíäû îïåðàöèîííîé ñèñòåìû. </simpara> <simpara> Ïðèíóäèòåëüíîå âíåäðåíèå âðåäîíîñíûõ èíñòðóêöèé â SQL-çàïðîñû - ìåòîäèêà, â êîòîðîé âçëîìùèê ñîçäàåò èëè èçìåíÿåò òåêóùèå SQL-çàïðîñû äëÿ ðàáîòû ñî ñêðûòûìè äàííûìè, èõ èçìåíåíèÿ èëè äàæå âûïîëíåíèÿ îïàñíûõ êîììàíä îïåðàöèîííîé ñèñòåìû íà ñåðâåðå áàçû äàííûõ. Àòàêà âûïîëíÿåòñÿ íà áàçå ïðèëîæåíèÿ, ñòðîÿùåãî SQL-çàïðîñû èç ïîëüçîâàòåëüñêîãî ââîäà è ñòàòè÷åñêèõ ïåðåìåííûõ. Ñëåäóþùèå ïðèìåðû, ê ñîæàëåíèþ, ïîñòðîåíû íà ðåàëüíûõ ôàêòàõ. </simpara> <para> Áëàãîäàðÿ îòñóòñòâèþ ïðîâåðêè ïîëüçîâàòåëüñêîãî ââîäà è ñîåäèíåíèåì ñ áàçîé äàííûõ ïîä ó÷åòíîé çàïèñüþ ñóïåðïîëüçîâàòåëÿ (èëè ëþáîãî äðóãîãî ïîëüçîâàòåëÿ, íàäåëåííîãî ñîîòâåòñòâóþùèìè ïðèâåëåãèÿìè), âçëîìùèê ìîæåò ñîçäàòü åùå îäíîãî ïîëüçîâàòåëÿ ÁÄ ñ ïðàâàìè ñóïåðïîëüçîâàòåëÿ. <example> <title> Ïîñòðàíè÷íûé âûâîä ðåçóëüòàòà... è ñîçäàíèå ñóïåðïîëüçîâàòåëÿ â PostgreSQL è MySQL </title> <programlisting role="php"> <![CDATA[ $offset = argv[0]; // ïðîâåðêà ïîëüçîâàòåëüñêèõ äàííûõ îòñóòñòâóåò $query = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;"; // èñïîëüçóÿ PostgreSQL $result = pg_exec($conn, $query); // èñïîëüçóÿ MySQL $result = mysql_query($query); ]]> </programlisting> </example> Îáû÷íî ïîëüçîâàòåëè êëèêàþò ïî ññûëêàì 'âïåðåä' è 'íàçàä', âñëåäñòâèè ÷åãî çíà÷åíèå ïåðåìåííîé <varname>$offset</varname> çàíîñèòñÿ â àäðåñíóþ ñòðîêó. Ñêðèïò îæèäàåò, ÷òî <varname>$offset</varname> - äåñÿòèðè÷íîå ÷èñëî. Îäíàêî, âçëîìùèê ìîæåò ïîïûòàòüñÿ âçëîìàòü ñèñòåìó, ïðèñîåäèíèâ ê ñòðîêå çàïðîñà äîïîëíèòåëüíóþ ïîäñòðîêó, îáðàáîòàííóþ ôóíêöèåé <function>urlencode</function>: <informalexample> <programlisting role="sql"> <![CDATA[ // èñïîëüçóÿ PostgreSQL 0; insert into pg_shadow(usename,usesysid,usesuper,usecatupd,passwd) select 'crack', usesysid, 't','t','crack' from pg_shadow where usename='postgres'; -- // èñïîëüçóÿ MySQL 0; UPDATE user SET Password=PASSWORD('crack') WHERE user='root'; FLUSH PRIVILEGES; ]]> </programlisting> </informalexample> Åñëè ýòî ïðîèçîéäåò, ñêðèïò ïðåäîñòàâèò âçëîìùèêó äîñòóï ê áàçå ñ ïðàâàìè ñóïåðïîëüçîâàòåëÿ. Çàìåòèì, ÷òî <literal>0;</literal> èñïîëüçîâàí äëÿ òîãî, ÷òîáû çàäàòü ïðàâèëüíîå çíà÷åíèå ñìåùåíèÿ äëÿ ïåðâîãî çàïðîñà è êîððåêòíî åãî çàâåðøèòü. </para> <note> <para> Óæå ïðèâû÷íà òåõíîëîãèÿ, êîãäà ðàçðàáîò÷èêè óêàçûâàþò ïðèíóäèòåëüíîå èãíîðèðîâàíèå ïàðñåðîì SQL îñòàâøåéñÿ ÷àñòè çàïðîñà ïðè ïîìîùè íîòàöèè <literal>--</literal>, îçíà÷àþùåé êîììåíòàðèé. </para> </note> <para> Åùå îäèí âåðîÿòíûé ñïîñîá ïîëó÷èòü ïàðîëè ó÷åòíûõ çàïèñåé â ÁÄ - àòàêà ñòðàíèö, ïðåäîñòàâëÿþùèõ ïîèñê ïî áàçå. Âçëîìùèêó íóæíî ëèøü ïðîâåðèòü, èñïîëüçóåòñÿ ëè â çàïðîñå ïåðåäàâàåìàÿ íà ñåðâåð è íåîáðàáàòûâàåìàÿ íàäëåæàùèì îáðàçîì ïåðåìåííàÿ. Ýòî ìîæåò áûòü îäèí èç óñòàíàâëèâàåìûõ íà ïðåäûäóùåé ñòðàíèöå ôèëüòðîâ, òàêèõ êàê <literal>WHERE, ORDER BY, LIMIT</literal> è <literal>OFFSET</literal>, èñïîëüçóåìûõ ïðè ïîñòðîåíèè çàïðîñîâ <literal>SELECT</literal>.  ñëó÷àå, åñëè èñïîëüçóåìàÿ âàìè áàçà äàííûõ ïîääåðæèâàåò êîíñòðóêöèþ <literal>UNION</literal>, âçëîìùèê ìîæåò ïðèñîåäèíèòü ê îðèãèíàëüíîìó çàïðîñó åùå îäèí äîïîëíèòåëüíûé, äëÿ èçâëå÷åíèÿ ïîëüçîâàòåëüñêèõ ïàðîëåé. Íàñòîÿòåëüíî ðåêîìåíäóåì èñïîëüçîâàòü òîëüêî çàøèôðîâàííûå ïàðîëè. <example> <title> Ëèñòèíã ñòàòåé... è íåêîòîðûõ ïàðîëåé (äëÿ ëþáîé áàçû äàííûõ) </title> <programlisting role="php"> <![CDATA[ $query = "SELECT id, name, inserted, size FROM products WHERE size = '$size' ORDER BY $order LIMIT $limit, $offset;"; $result = odbc_exec($conn, $query); ]]> </programlisting> </example> Ñòàòè÷åñêàÿ ÷àñòü çàïðîñà ìîæåò êîìáèíèðîâàòüñÿ ñ äðóãèì SQL-çàïðîñîì, êîòîðûé îòêðîåò âñå ïàðîëè: <informalexample> <programlisting role="sql"> <![CDATA[ ' union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable; -- ]]> </programlisting> </informalexample> Åñëè ýòîò çàïðîñ (èñïîëüçóþùèé <literal>'</literal> è <literal>--</literal>) ïðèñîåäèíèòü ê çíà÷åíèþ îäíîé èç ïåðåìåííûõ, èñïîëüçóåìûõ äëÿ ôîðìèðîâàíèÿ <varname>$query</varname>, çàïðîñ çàìåòíî ïðåîáðàçèòñÿ. </para> <para> Êîìàíäû UPDATE òàêæå ìîãóò èñïîëüçîâàòüñÿ äëÿ àòàêè. Îïÿòü æå, åñòü óãðîçà ðàçäåëåíèÿ èíñòðóêöèè íà íåñêîëüêî çàïðîñîâ, ïðèñîåäèíåíèÿ äîïîëíèòåëüíîãî çàïðîñà. Òàêæå âçëîìùèê ìîæåò âèäîèçìåíèòü âûðàæåíèå <literal>SET</literal>.  ýòîì ñëó÷àå ïîòåíöèàëüíîìó âçëîìùèêó íåîáõîäèìî îáëàäàòü íåêîòîðîé äîïîëíèòåëüíîé èíôîðìàöèåé äëÿ óñïåøíîãî ìàíèïóëèðîâàíèÿ çàïðîñàìè. Ýòó èíôîðìàöèþ ìîæíî ïîëó÷èòü, ïðîàíàëèçèðîâàâ èñïîëüçóåìûå â ôîðìå èìåíà ïåðåìåííûõ ëèáî ïðîñòî ïåðåáèðàÿ âñå íàèáîëåå ðàñïðîñòðàíåííûå âàðèàíòû íàçâàíèÿ ñîîòâåòñòâóþùèõ ïîëåé (à èõ íå òàê óæ è ìíîãî). <example> <title> Îò âîññòàíîâëåíèÿ ïàðîëÿ... äî ïîëó÷åíèÿ äîïîëíèòåëüíûõ ïðèâèëåãèé (äëÿ ëþáîé áàçû äàííûõ) </title> <programlisting role="php"> <![CDATA[ $query = "UPDATE usertable SET pwd='$pwd' WHERE uid='$uid';"; ]]> </programlisting> </example> Íî çëîóìûøëåííèê ìîæåò ââåñòè çíà÷åíèå <literal>' or uid like'%admin%'; --</literal> äëÿ ïåðåìåííîé <varname>$uid</varname> äëÿ èçìåíåíèÿ ïàðîëÿ àäìèíèñòðàòîðà èëè ïðîñòî ïðèñâîèòü ïåðåìåííîé <varname>$pwd</varname> çíà÷åíèå <literal>"hehehe', admin='yes', trusted=100 "</literal> (ñ çàâåðøàþùèìè ïðîáåëàìè) äëÿ ïîëó÷åíèÿ äîïîëíèòåëüíûõ ïðèâåëåãèé. Ïðè âûïîëíåíèè çàïðîñû ïåðåïëåòàþòñÿ: <informalexample> <programlisting role="php"> <![CDATA[ // $uid == ' or uid like'%admin%'; -- $query = "UPDATE usertable SET pwd='...' WHERE uid='' or uid like '%admin%'; --"; // $pwd == "hehehe', admin='yes', trusted=100 " $query = "UPDATE usertable SET pwd='hehehe', admin='yes', trusted=100 WHERE ...;" ]]> </programlisting> </informalexample> </para> <para> Ïóãàþùèé ïðèìåð òîãî, êàê íà ñåðâåðå áàç äàííûõ ìîãóò âûïîëíÿòüñÿ êîìàíäû îïåðàöèîííîé ñèñòåìû. <example> <title>Âûïîëíåíèå êîìàíä îïåðàöèîííîé ñèñòåìû íà ñåðâåðå (äëÿ áàçû MSSQL)</title> <programlisting role="php"> <![CDATA[ $query = "SELECT * FROM products WHERE id LIKE '%$prod%'"; $result = mssql_query($query); ]]> </programlisting> </example> Åñëè âçëîìùèê ââåäåò çíà÷åíèìå <literal>a%' exec master..xp_cmdshell 'net user test testpass /ADD' --</literal> äëÿ ïåðåìåííîé <varname>$prod</varname>, òîãäà çàïðîñ <varname>$query</varname> áóäåò âûãëÿäåòü òàê: <informalexample> <programlisting role="php"> <![CDATA[ $query = "SELECT * FROM products WHERE id LIKE '%a%' exec master..xp_cmdshell 'net user test testpass /ADD'--"; $result = mssql_query($query); ]]> </programlisting> </informalexample> MSSQL ñåðâåð âûïîëíÿåò SQL-êîìàíäû â ïàêåòíîì ðåæèìå, â òîì ÷èñëå è îïåðàöèè ïî çàâåäåíèþ ëîêàëüíûõ ó÷åòíûõ çàïèñåé áàçû äàííûõ.  ñëó÷àå, åñëè ïðèëîæåíèå ðàáîòàåò ñ ïðèâèëåãèÿìè àäìèíèñòðàòîðà è ñåðâèñ MSSQL çàïóùåí ñ íåîáõîäèìûìè ïðèâèëåãèÿìè, âûïîëíèâ ïðèâåäåííûå âûøå äåéñòâèÿ, âçëîìùèê ïîëó÷èò àêêàóíò äëÿ äîñòóïà ê ñåðâåðó. </para> <note> <para> Íåêîòîðûå ïðèâåäåííûå â ýòîé ãëàâå ïðèìåðû êàñàþòñÿ êîíêðåòíîé áàçû äàííûõ. Ýòî íå îçíà÷àåò, ÷òî àíàëîãè÷íûå àòàêè íà äðóãèå ïðîãðàììíûå ïðîäóêòû íåâîçìîæíû. Ðàáîòîñïîñîáíîñòü âàøåé áàçû äàííûõ ìîæåò áûòü íàðóøåíà êàêèì-ëèáî äðóãèì ñïîñîáîì. </para> </note> <sect3 id="security.database.avoiding"> <title>Ñïîñîáû çàùèòû</title> <simpara> Âû ìîæåòå óòåøàòü ñåáÿ òåì, ÷òî â áîëüøèíñòâå ñëó÷àåâ, âçëîìùèê äîëæåí îáëàäàòü íåêîòîðîé èíôîðìàöèåé î ñòðóêòóðå áàçû äàííûõ. Âû ïðàâû, íî âû íå çíàåòå, êîãäà è êàê áóäåò ïðåäïðèíÿòà ïîïûòêà âçëîìà, â ñëó÷àå åñëè ýòî ïðîèçîéäåò âàøà ÁÄ îêàæåòñÿ íåçàùèùåííîé. Åñëè âû èñïîëüçóåòå ïðîãðàììíûé ïðîäóêò ñ îòêðûòûìè èñõîäíûìè êîäàìè èëè ïðîñòî îáùåäîñòóïíûé ïàêåò äëÿ ðàáîòû ñ áàçîé äàííûõ (íàïðèìåð êîíòåíò ìåíåäæåð èëè ôîðóì), âçëîìùèê ëåãêî ñìîæåò âîñïðîèçâåñòè èíòåðåñóþùèå åãî ó÷àñòêè êîäà.  ñëó÷àå åñëè îíè ïëîõî ñïðîåêòèðîâàíû, ýòî ìîæåò ÿâëÿòüñÿ îäíîé èç óãðîç âàøåé áåçîïàñíîñòè. </simpara> <simpara> Áîëüøèíñòâî óñïåøíûõ àòàê îñíîâûâàåòñÿ íà êîäå, íàïèñàííîì áåç ó÷åòà ñîîòâåòñòâóþùèõ òðåáîâàíèé áåçîïàñíîñòè. Íå äîâåðÿéòå íèêàêèì ââîäèì äàííûì, îñîáåííî åñëè îíè ïîñòóïàþò ñî ñòîðîíû êëèåíòà, äàæå åñëè ýòî ñïèñêè â ôîðìå, ñêðûòûå ïîëÿ èëè êóêè. Ïðèâåäåííûå ïðèìåðû ïîêàçûâàþò, ê êàêèì ïîñëåäñòâèÿì ìîãóò ïðèâåñòè ïîääåëàííûå çàïðîñû. </simpara> <itemizedlist> <listitem> <simpara> Ñòàðàéòåñü íå îòêðûâàòü ñîåäèíåíèå ñ áàçîé, èñïîëüçóÿ ó÷åòíóþ çàïèñü âëàäåëüöà èëè àäìèíèñòðàòîðà. Âñåãäà ñòàðàéòåñü èñïîëüçîâàòü ñïåöèàëüíî ñîçäàííûõ ïîëüçîâàòåëåé ñ ìàêñèìàëüíî îãðàíè÷åííûìè ïðàâàìè. </simpara> </listitem> <listitem> <simpara> Âñåãäà ïðîâåðÿéòå ââåäåííûå äàííûå íà ñîîòâåòñòâèå îæèäàåìîìó òèïó.  PHP åñòü ìíîæåñòâî ôóíêöèé äëÿ ïðîâåðêè äàííûõ: íà÷èíàÿ îò ïðîñòåéøèõ <link linkend="ref.variables">Ôóíêöèé äëÿ ðàáîòû ñ ïåðåìåííûìè</link> è <link linkend="ref.ctype">Ôóíêöèè îïðåäåëåíèÿ òèïà ñèìâîëîâ</link> (òàêèå êàê <function>is_numeric</function>, <function>ctype_digit</function>) è çàêàí÷èâàÿ <link linkend="ref.pcre">Perl-ñîâìåñòèìûìè ðåãóëÿðíûìè âûðàæåíèÿìè</link>. </simpara> </listitem> <listitem> <para>  ñëó÷àå, åñëè ïðèëîæåíèå îæèäàåò öèôðîâîé ââîä, ïðèìåíèòå ôóíêöèþ <function>is_numeric</function> äëÿ ïðîâåðêè ââåäåííûõ äàííûõ, èëè ïðèíóäèòåëüíî óêàæèòå èõ òèï ïðè ïîìîùè <function>settype</function>, èëè ïðîñòî èñïîëüçóéòå ÷èñëîâîå ïðåäñòàâëåíèå ïðè ïîìîùè ôóíêöèè <function>sprintf</function>. <example> <title>Áîëåå áåçîïàñíàÿ ðåàëèçàöèÿ ïîñòðàíè÷íîé íàâèãàöèè</title> <programlisting role="php"> <![CDATA[ settype($offset, 'integer'); $query = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;"; // îáðàòèòå âíèìàíèå íà ôîðìàò %d, èñïîëüçîâàíèå %s áûëî áû áåññìûñëåííî $query = sprintf("SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET %d;", $offset); ]]> </programlisting> </example> </para> </listitem> <listitem> <simpara> Ýêðàíèðóéòå ëþáîé íåöèôðîâîé ââîä, èñïîëüçóåìûé â çàïðîñàõ ê ÁÄ ïðè ïîìîùè ôóíêöèé <function>addslashes</function> èëè <function>addcslashes</function>. Îáðàòèòå âíèìàíèå íà <link linkend="security.database.storage">ïåðâûé ïðèìåð</link>. Ñëåäóåò ïîìíèòü, ÷òî îäíîãî èñïîëüçîâàíèÿ êàâû÷åê â çàïðîñå ìàëî, ýòî ëåãêî îáîéòè. </simpara> </listitem> <listitem> <simpara> Íå âûâîäèòå íèêàêîé èíôîðìàöèè î ÁÄ, îñîáåííî î åå ñòðóêòóðå. Òàêæå îçíàêîìüòåñü ñ ñîîòâåòñòâóþùèìè ðàçäåëàìè äîêóìåíòàöèè: <link linkend="security.errors">Ñîîáùåíèÿ îá îøèáêàõ</link> è <link linkend="ref.errorfunc">Ôóíêöèè îáðàáîòêè è ëîãèðîâàíèÿ îøèáîê</link>. </simpara> </listitem> <listitem> <simpara> Âû ìîæåòå èñïîëüçîâàòü õðàíèìûå ïðîöåäóðû è çàðàíåå îïðåäåëåííûå êóðñîðû äëÿ àáñòðàãèðîâàííîé ðàáîòû ñ äàííûìè, íå ïðåäîñòàâëÿÿ ïîëüçîâàòåëÿì ïðÿìîãî äîñòóïà ê äàííûì è ïðåäñòàâëåíèÿì, íî ýòî ðåøåíèå èìååò ñâîè îñîáåííîñòè. </simpara> </listitem> </itemizedlist> <simpara> Ïîìèìî âñåãî âûøåñêàçàííîãî, âû ìîæåòå ëîãèðîâàòü çàïðîñû â âàøåì ñêðèïòå ëèáî íà óðîâíå áàçû äàííûõ, åñëè îíà ýòî ïîääåðæèâàåò. Î÷åâèäíî, ÷òî ëîãèðîâàíèå íå ìîæåò ïðåäîòâðàòèòü íàíåñåíèå óùåðáà, íî ìîæåò ïîìî÷ü ïðè òðàññèðîâêå âçëîìàííîãî ïðèëîæåíèÿ. Ëîã-ôàéë ïîëåçåí íå ñàì ïî ñåáå, à èíôîðìàöèåé, êîòîðàÿ â íåì ñîäåðæèòñÿ. Ïðè÷åì, â áîëüøèíñòâå ñëó÷àåâ ïîëåçíî ëîãèðîâàòü âñå âîçìîæíûå äåòàëè. </simpara> </sect3> </sect2> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/errors.xml?r=1.1&p=1 Index: phpdoc-ru/security/errors.xml +++ phpdoc-ru/security/errors.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.errors"> <title>Ñîîáùåíèÿ îá îøèáêàõ</title> <para> Ñ òî÷êè çðåíèÿ áåçîïàñíîñòè âûâîä ñîîáùåíèé îá îøèáêàõ íåñåò â ñåáå êàê ïëþñû, òàê è ìèíóñû. </para> <para> Îäíà èç ñòàíäàðòíûõ ìåòîäèê, ïðèìåíÿåìûõ â àòàêàõ - ââîä íåêîððåêòíûõ äàííûõ ñ ïîñëåäóþùèì àíàëèçîì ñîäåðæàíèÿ è õàðàêòåðà ñîîáùåíèé îá îøèáêàõ. Ýòî äàåò âçëîìùèêó âîçìîæíîñòü ïðîâåðèòü ñêðèïòû è äàííûå ñåðâåðà íà íàëè÷èå ïîòåíöèàëüíûõ äûð. Íàïðèìåð, åñëè âçëîìùèê ïîëó÷èë íåêîòîðóþ èíôîðìàöèþ î ñòðàíèöå íà îñíîâàíèè îòïðàâêè ôîðìû, îí ïîïðîáóåò ïðåäîïðåäåëèòü íåêîòîðûå ïåðåäàâàåìûå çíà÷åíèÿ èëè ìîäèôèöèðîâàòü èõ: <example> <title>Àòàêà íà ïåðåìåííûå â HTML-ñòðàíèöå</title> <programlisting role="php"> <![CDATA[ <form method="post" action="attacktarget?username=badfoo&password=badfoo"> <input type="hidden" name="username" value="badfoo" /> <input type="hidden" name="password" value="badfoo" /> </form> ]]> </programlisting> </example> </para> <para> Âîçíèêàåìûå âî âðåìÿ ðàáîòû ñêðèïòîâ îøèáêè ÿâëÿþòñÿ äîñòàòî÷íî öåííîé èíôîðìàöèåé äëÿ ðàçðàáîò÷èêà, ñîäåðæàùåé òàêèå äàííûå, êàê ôóíêöèÿ èëè ôàéë, à òàêæå íîìåð ñòðîêè, â êîòîðîé âîçíèêëà îøèáêà. Âñÿ ýòà èíôîðìàöèÿ ìîæåò áûòü èñïîëüçîâàíà äëÿ âçëîìà. Äëÿ PHP-ðàçðàáîò÷èêà äîñòàòî÷íî ïðèâû÷íî ïîëüçîâàòüñÿ òàêèìè ôóíêöèÿìè, êàê <function>show_source</function>, <function>highlight_string</function> èëè <function>highlight_file</function> â öåëÿõ îòëàäêè, íî â æèâûõ ñàéòàõ ýòî ìîæåò îòêðûòü èíôîðìàöèþ î ñêðûòûõ ïåðåìåííûõ, íåïðîâåðÿåìîì ñèíòàêñèñå è äðóãèõ ïîòåíöèàëüíî îïàñíûõ ìîìåíòàõ. Îñîáåííî îïàñíî íàëè÷èå êîäà ñî âñòðîåííûì ìåõàíèçìîì îòëàäêè â ïóáëè÷íûõ ÷àñòÿõ ñàéòà. Âçëîìùèê ìîæåò ïîïûòàòüñÿ çàïóñòèòü îòëàäî÷íûé ìåõàíèçì, ïîäáèðàÿ îñíîâíûå ïðèçíàêè îòëàäêè: <example> <title>Èñïîëüçîâàíèå ñòàíäàðòíûõ îòëàäî÷íûõ ïåðåìåííûõ</title> <programlisting role="php"> <![CDATA[ <form method="post" action="attacktarget?errors=Y&showerrors=1&debug=1"> <input type="hidden" name="errors" value="Y" /> <input type="hidden" name="showerrors" value="1" /> <input type="hidden" name="debug" value="1" /> </form> ]]> </programlisting> </example> </para> <para> Íåçàâèñèìî îò ìåòîäà îáðàáîòêè îøèáîê âîçìîæíîñòü ïðîâåðêè ñèñòåìû íà íàëè÷èå îøèáîê ñíàáæàåò âçëîìùèêà äîïîëíèòåëüíîé èíôîðìàöèåé. </para> <para> Íàïðèìåð, ñòàíäàðòíûé âûâîä îá îøèáêå óêàçûâàåò îïåðàöèîííóþ ñèñòåìó, â êîòîðîé âûïîëíÿþòñÿ PHP ñêðèïòû. Åñëè âçëîìùèê àíàëèçèðóåò îáûêíîâåííóþ HTML-ñòðàíèöó, ïûòàÿñü íàéòè óÿçâèìûå ìåñòà, èñïîëüçóÿ ââîä íåâåðíûõ äàííûõ îí ìîæåò îáíàðóæèòü èñïîëüçîâàíèå PHP ñêðèïòîâ â äàííîé ñèñòåìå. </para> <para> Òàêæå óâåäîìëåíèå îá îøèáêå ìîæåò äàòü èíôîðìàöèþ î òîì, êàêàÿ áàçà äàííûõ èñïîëüçóåòñÿ, èëè, ê ïðèìåðó, êàê ïîñòðîåíà ëîãèêà ðàáîòû ñêðèïòîâ. Ýòî, â ñâîþ î÷åðåäü, ìîæåò ïîçâîëèòü âçëîìùèêó ïîäêëþ÷èòüñÿ ê îòêðûòîìó ïîðòó áàçû äàííûõ ëèáî íàéòè ñïåöèôè÷íûå îøèáêè â êîäå. Ïðîáóÿ ïîî÷åðåäíî ðàçëè÷íûå íåâåðíûå áëîêè äàííûõ, çëîóìûøëåííèê ìîæåò îïðåäåëèòü ïîðÿäîê àóòåíòèôèêàöèè â ñêðèïòå (íàïðèìåð, ïî íîìåðàì ñòðîê ñ îøèáêàìè) èëè ïðîâåðÿòü íà íàëè÷èå äûð ðàçëè÷íûå ó÷àñòêè êîäà. </para> <para> Âûâîä ñòàíäàðòíûõ îøèáîê, ñâÿçàííûõ ñ ôàéëîâîé ñèñòåìîé, ìîæåò óêàçàòü, ñ êàêèìè ïðèâåëåãèÿìè çàïóùåí âåá-ñåðâåð, è êàê îðãàíèçîâàíû êàòàëîãè ñàéòà. Îáðàáîòêà ïîäîáíûõ îøèáîê, íàïèñàííàÿ ðàçðàáîò÷èêàìè ïðèëîæåíèÿ, ìîæåò òîëüêî óñóãóáèòü ïðîáëåìó, åñëè âçëîìùèêîì áóäåò íàéäåí ñïîñîá îáíàðóæèòü "ñêðûòóþ" îòëàäî÷íóþ èíôîðìàöèþ. </para> <para> Ñóùåñòâóåò òðè îñíîâíû÷ ñïîñîáà ðåøåíèÿ ýòîé ïðîáëåìû. Ïåðâûé çàêëþ÷àåòñÿ â òîì, ÷òîáû ñòðóêòóðèðîâàòü âñå ôóíêöèè è ïîïûòàòüñÿ êîìïåíñèðîâàòü îáúåì âûäàâàåìûõ îøèáîê. Âòîðîé ñïîñîá - ïîëíîñòüþ îòêëþ÷èòü â ðàáîòàþùåì êîäå âûâîä ñîîáùåíèé îá îøèáêàõ. È, íàêîíåö, òðåòèé ñïîñîá - èñïîëüçîâàòü ñïåöèàëüíûå ñðåäñòâà PHP äëÿ ñîçäàíèÿ ñîáñòâåííîãî îáðàáîò÷èêà îøèáîê.  çàâèñèìîñòè îò èñïîëüçóåìîé âàìè ïîëèòèêè áåçîïàñíîñòè âû ìîæåòå ïðèìåíÿòü â âàøåé êîíêðåòíîé ñèòóàöèè âñå òðè ñïîñîáà. </para> <para> Îäèí èç âîçìîæíûõ ñïîñîáîâ îáåçîïàñèòü âàø êîä ïåðåä åãî ïóáëèêàöèåé äëÿ îáùåãî äîñòóïà - èíäèâèäóàëüíîå èñïîëüçîâàíèå <function>error_reporting</function>, ÷òîáû âûÿâèòü ïîòåíöèàëüíî îïàñíûå ïåðåìåííûå. Òåñòèðóÿ êîä ïåðåä âûïóñêîì ðåëèçà ïðè ïîìîùè çíà÷åíèÿ E_ALL, âû äîñòàòî÷íî ëåãêî ìîæåòå îáíàðóæèòü ó÷àñòêè êîäà, â êîòîðûõ ïåðåìåííûå ìîãóò áûòü ïîäìåíåíû ëèáî ìîäèôèöèðîâàíû. Ïîñëå îêîí÷àíèÿ òåñòèðîâàíèÿ, óñòàíîâèâ çíà÷åíèå E_NONE, âû ìîæåòå ïîëíîñòüþ îòêëþ÷èòü âûâîä ñîîáùåíèé îá îøèáêàõ. <example> <title>Ïîèñê ïîòåíöèàëüíî îïàñíûõ ïåðåìåííûõ ïðè ïîìîùè E_ALL</title> <programlisting role="php"> <![CDATA[ <?php if ($username) { // Ïåðåìåííàÿ íå èíèöèàëèçèðóåòñÿ ïåðåä èñïîëüçîâàíèåì $good_login = 1; } if ($good_login == 1) { // Åñëè ïðåäûäóùàÿ ïðîâåðêà ïîòåðïåëà íåóäà÷ó, ïåðåìåííàÿ îêàçûâàåòñÿ íåèíèöèàëèçèðîâàííîé readfile ("/highly/sensitive/data/index.html"); } ?> ]]> </programlisting> </example> </para> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/filesystem.xml?r=1.1&p=1 Index: phpdoc-ru/security/filesystem.xml +++ phpdoc-ru/security/filesystem.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.filesystem"> <title>Áåçîïàñíîñòü ôàéëîâîé ñèñòåìû</title> <simpara> PHP ÿâëÿåòñÿ îäíèì èç âàæíûõ ìîìåíòîâ â âîïðîñå áåçîïàñíîñòè ñåðâåðà, ïîñêîëüêó PHP-ñêðèïòû ìîãóò ìàíèïóëèðîâàòü ôàéëàìè è êàòàëîãàìè íà äèñêå.  ñâÿçè ñ ýòèì ñóùåñòâóþò êîíôèãóðàöèîííûå íàñòðîéêè, óêàçûâàþùèå, êàêèå ôàéëû ìîãóò áûòü äîñòóïíû è êàêèå îïåðàöèè ñ íèìè ìîæíî âûïîëíÿòü. Íåîáõîäèìî ïðîÿâëÿòü îñòîðîæíîñòü, ïîñêîëüêó ëþáîé èç ôàéëîâ ñ ñîîòâåòñòâóþùèìè ïðàâàìè äîñòóïà ìîæåò áûòü ïðî÷èòàí êàæäûì, êòî èìååò äîñòóï ê ôàéëîâîé ñèñòåìå. </simpara> <simpara> Ïîñêîëüêó â PHP èçíà÷àëüíî ïðåäïîëàãàëñÿ ïîëíîïðàâíûé ïîëüçîâàòåëüñêèé äîñòóï ê ôàéëîâîé ñèñòåìå, ìîæíî íàïèñàòü ñêðèïò, êîòîðûé ïîçâîëèò ÷èòàòü ñèñòåìíûå ôàéëû, òàêèå êàê /etc/passwd, óïðàâëÿòü ñåòåâûìè ñîåäèíåíèÿìè, îòïðàâëÿòü çàäàíèÿ ïðèíòåðó, è òàê äàëåå. Êàê ñëåäñòâèå âû âñåãäà äîëæíû áûòü óâåðåíû â òîì, ÷òî ôàéëû, êîòîðûå âû ÷èòàåòå èëè ìîäèôèöèðóåòå, ñîîòâåòñòâóþò âàøèì íàìåðåíèÿì. </simpara> <simpara> Ðàññìîòðèì ñëåäóþùèé ïðèìåð, â êîðîòîì ïîëüçîâàòåëü ñîçäàë ñêðèïò, óäàëÿþùèé ôàéë èç åãî äîìàøíåé äèðåêòîðèè. Ïðåäïîëàãàåòñÿ ñèòóàöèÿ, êîãäà âåá-èíòåðôåéñ, íàïèñàííûé íà PHP, ðåãóëÿðíî èñïîëüçóåòñÿ äëÿ ðàáîòû ñ ôàéëàìè, è íàñòðîéêè áåçîïàñíîñòè ïîçâîëÿþò óäàëÿòü ôàéëû â äîìàøíåì êàòàëîãå. </simpara> <para> <example> <title>Íåäîñòàòî÷íàÿ ïðîâåðêà âíåøíèõ äàííûõ.</title> <programlisting role="php"> <![CDATA[ <?php // Óäàëåíèå ôàéëà èç äîìàøíåé äèðåêòîðèè ïîëüçîâàòåëÿ $username = $_POST['user_submitted_name']; $homedir = "/home/$username"; $file_to_delete = "$userfile"; unlink ("$homedir/$userfile"); echo "$file_to_delete has been deleted!"; ?> ]]> </programlisting> </example> Ïîñêîëüêó ïåðåìåííûå ââîäÿòñÿ â ïîëüçîâàòåëüñêîé ôîðìå, ñóùåñòâóåò âîçìîæíîñòü óäàëèòü ôàéëû, ïðèíàäëåæàùèå êîìó-ëèáî äðóãîìó, ââåäÿ ñîîòâåòñòâóþùèå çíà÷åíèÿ.  ýòîì ñëó÷àå ìîæåò ïîíàäîáèòüñÿ àâòîðèçàöèÿ. Ïîñìîòðèì, ÷òî ïðîèçîéäåò, åñëè áóäóò îòïðàâëåíû çíà÷åíèÿ "../etc/" è "passwd". Ñêðèïò âûïîëíèò ñëåäóþùèå äåéñòâèÿ: <example> <title>Àòàêà íà ôàéëîâóþ ñèñòåìó</title> <programlisting role="php"> <![CDATA[ <?php // Óäàëåíèå ëþáîãî ôàéëà, äîñòóïíîãî èç PHP-ñêðèïòà. //  ñëó÷àå, åñëè PHP ðàáîòàåò ñ ïðàâàìè ïîëüçîâàòåëÿ root: $username = "../etc/"; $homedir = "/home/../etc/"; $file_to_delete = "passwd"; unlink ("/home/../etc/passwd"); echo "/home/../etc/passwd has been deleted!"; ?> ]]> </programlisting> </example> Cóùåñòâóþò äâà ðåøåíèÿ îïèñàííîé ïðîáëåìû. <itemizedlist> <listitem> <simpara> Îãðàíè÷èòü äîñòóï ïîëüçîâàòåëÿ, ñ ïðàâàìè êîòîðîãî ðàáîòàåò âåá-ñåðâåð. </simpara> </listitem> <listitem> <simpara> Ïðîâåðÿòü âñå äàííûå, ââîäèìûå ïîëüçîâàòåëåì. </simpara> </listitem> </itemizedlist> Âîò óëó÷øåíûé âàðèàíò êîäà: <example> <title>Áîëåå áåçîïàñíàÿ ïðîâåðêà èìåíè ôàéëà</title> <programlisting role="php"> <![CDATA[ <?php // Óäàëåíèå ëþáîãî ôàéëà, äîñòóïíîãî èç PHP-ñêðèïòà. $username = $_SERVER['REMOTE_USER']; // èñïîëüçîâàíèå àâòîðèçàöèè $homedir = "/home/$username"; $file_to_delete = basename("$userfile"); // óñå÷åíèå ïóòè unlink ($homedir/$file_to_delete); $fp = fopen("/home/logging/filedelete.log","+a"); //ëîãèðóåì óäàëåíèå $logstring = "$username $homedir $file_to_delete"; fputs ($fp, $logstring); fclose($fp); echo "$file_to_delete has been deleted!"; ?> ]]> </programlisting> </example> Îäíàêî è òàêàÿ ïðîâåðêà íå ó÷èòûâàåò âñå âîçìîæíûå ñèòóàöèè. Åñëè ñèñòåìà àâòîðèçàöèè ïîçâîëÿåò ïîëüçîâàòåëÿì âûáèðàòü ïðîèçâîëüíûå ëîãèíû, âëîìùèê ìîæåò ñîçäàòü ó÷åòíóþ çàïèñü âèäà "../etc/" è ñèñòåìà îïÿòü îêàæåòñÿ óÿçâèìîé. Èñõîäÿ èç ýòîãî, âàì ìîæåò ïîíàäîáèòüñÿ áîëåå ñòðîãàÿ ïðîâåðêà: <example> <title>Áîëåå ñòðîãàÿ ïðîâåðêà èìåíè ôàéëà</title> <programlisting role="php"> <![CDATA[ <?php $username = $_SERVER['REMOTE_USER']; // èñïîëüçîâàíèå àâòîðèçàöèè $homedir = "/home/$username"; if (!ereg('^[^./][^/]*$', $userfile)) die('bad filename'); //çàâåðøåíèå ðàáîòû if (!ereg('^[^./][^/]*$', $username)) die('bad username'); //çàâåðøåíèå ðàáîòû //etc... ?> ]]> </programlisting> </example> </para> <para>  çàâèñèìîñòè îò èñïîëüçóåìîé âàìè îïåðàöèîííîé ñèñòåìû íåîáõîäèìî ïðåäóñìàòðèâàòü âîçìîæíîñòü àòàêè íà ðàçíîîáðàçíûå ôàéëû, âêëþ÷àÿ ñèñòåìíûå ôàéëû óñòðîéñòâ (/dev/ èëè COM1), êîíôèãóðàöèîííûå ôàéëû (íàïðèìåð /etc/ èëè ôàéëû ñ ðàñøèðåíèåì .ini), õîðîøî èçâåñòíûå îáëàñòè õðàíåíèÿ äàííûõ (/home/, My Documents), è òàê äàëåå. Èñõîäÿ èç ýòîãî, êàê ïðàâèëî, ëåã÷å ðåàëèçîâàòü òàêóþ ïîëèòèêó áåçîïàñíîñòè, â êîòîðîé çàïðåùåíî âñå, èñêëþ÷àÿ òî, ÷òî ÿâíî ðàçðåøåíî. </para> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/general.xml?r=1.1&p=1 Index: phpdoc-ru/security/general.xml +++ phpdoc-ru/security/general.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.general"> <title>Îáùèå ðàññóæäåíèÿ</title> <simpara> Òàê êàê àáñîëþòíî áåçîïàñíûå ñèñòåìû ÿâëÿþòñÿ íå áîëåå, ÷åì ìèôîì, íà ïðàêòèêå ïðèõîäèòñÿ áàëàíñèðîâàòü ìåæäó êîìôîðòîì è áåçîïàñíîñòüþ. Åñëè êàæäàÿ ïåðåìåííàÿ, ââîäèìàÿ ïîëüçîâàòåëåì, áóäåò òðåáîâàòü äâå áèîìåòðè÷åñêèå ïðîâåðêè (íàïðèìåð, ñêàíèðîâàíèå ñåò÷àòêè ãëàçà è îòïå÷àòêè ïàëüöåâ), òî âû ïîëó÷èòå ïðåäåëüíî âûñîêóþ äîñòîâåðíîñòü äàííûõ. Íî ïîñêîëüêó çàïîëíåíèå ñëîæíîé ôîðìû áóäåò çàíèìàòü îêîëî ïîëó÷àñà, ó ïîëüçîâàòåëåé òàêîé ñèñòåìû íåïðåìåííî âîçíèêíåò æåëàíèå îáîéòè íàâÿç÷èâóþ çàùèòó. </simpara> <simpara> Ïðàâèëüíî ïîñòàâëåííàÿ çàùèòà äîëæíà ñîîòâåòñòâîâàòü îñíîâíûì òðåáîâàíèÿì áåçîïàñíîñòè, íå óõóäøàÿ ïðè ýòîì ðàáîòó ïîëüçîâàòåëÿ è íå óñëîæíÿÿ ñàìîìó ïðîãðàììèñòó ðàçðàáîòêó ïðîäóêòà. Âìåñòå ñ òåì, íåêîòîðûå àòàêè ìîãóò îñíîâûâàòüñÿ èìåííî íà òàêîì ïîäõîäå ê çàùèòå, ÷òî ïðèâîäèò ê åå ïîñòåïåííîìó îñëàáëåíèþ. </simpara> <simpara> Ñëåäóåò ïîìíèòü õîðîøóþ ïîãîâîðêó: íàäåæíîñòü ñèñòåìû îïðåäåëÿåòñÿ åå ñàìûì ñëàáûì çâåíîì. Íàïðèìåð, åñëè âñå òðàíçàêöèè ëîãèðóþòñÿ ïî âðåìåíè, ìåñòîðàñïîëîæåíèþ, òèïó òðàíçàêöèè è ðÿäó äðóãèõ ïàðàìåòðîâ, íî àâòîðèçàöèÿ ïîëüçîâàòåëÿ ïðîèñõîäèò âñåãî ëèøü ïî êóêå (cookie), òî ñâÿçü êîíêðåòíîé çàïèñè â ëîãå ñ ïîëüçîâàòåëåì ñèñòåìû âåñüìà ñîìíèòåëüíà. </simpara> <simpara> Ïðè òåñòèðîâàíèè ñëåäóåò ïîìíèòü, ÷òî âû íå ìîæåòå ïðîâåðèòü âñå âîçìîæíûå âàðèàíòû äàæå äëÿ ïðîñòåéøåé ñòðàíèöû. Äàííûå, êîòîðûå âû îæèäàåòå, ìîãóò ñîâåðøåííî íå ñîîòâåòñòâîâàòü òîìó, ÷òî ââåäåò ðàçúÿðåííûé ñëóæàùèé, õàêåð ñî ñòàæåì èëè äîìàøíèé êîò, ðàçãóëèâàþùèé ïî êëàâèàòóðå. Ïîýòîìó ëó÷øå ëîãè÷åñêè ïîäóìàòü íàä âîïðîñîì: â êàêîì ìåñòå ìîãóò áûòü ââåäåíû íåîæèäàííûå äàííûå, êàê èõ ìîæíî ìîäèôèöèðîâàòü, óñå÷ü ëèáî, íàîáîðîò, äîïîëíèòü. </simpara> <simpara> Èíòåðíåò íàïîëíåí ëþäüìè, êîòîðûå õîòÿò ñäåëàòü ñåáå èìÿ íà òîì, ÷òî âçëîìàþò âàø êîä, ðàçðóøàò ñàéò, îïóáëèêóþò íà íåì íåóìåñòíûé êîíòåíò èëè ïðîñòî ñäåëàþò âàøè äíè èíòåðåñíåå. È íå âàæíî, ìàëåíüêèé ó âàñ ñàéò èëè áîëüøîé, åñëè ó âàñ åñòü îíëàéí-ñåðâåð - âû óæå ïîòåíöèàëüíàÿ æåðòâà. Ìíîãèå ïðîãðàììû-âçëîìùèêè íåñîìòðÿò íà ðàçìåð, îíè ïðîñòî ïåðåáèðàþò ìàññèâû IP-àäðåñîâ, âûèñêèâàÿ î÷åðåäíóþ æåðòâó. Ïîñòàðàéòåñü íå ñòàòü îäíîé èç íèõ. </simpara> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/globals.xml?r=1.1&p=1 Index: phpdoc-ru/security/globals.xml +++ phpdoc-ru/security/globals.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.registerglobals"> <title>Èñïîëüçîâàíèå ãëîáàëüíûõ ïåðåìåííûõ (Register_Globals)</title> <para> Íàâåðíîå, íàèáîëåå ñïîðíûì ìîìåíòîì â ðàçðàáîòêå PHP ñòàëà çàìåíà çíà÷åíèÿ ïî óìîë÷àíèþ äëÿ îïöèè <link linkend="ini.register-globals"> register_globals</link> ñ ON íà OFF â âåðñèè <ulink url="&url.php.release4.2.0;">4.2.0</ulink>. Áîëüøèíñòâî ïîëüçîâàòåëåé äîâåðèëèñü ðàçðàáîò÷èêàì, äàæå íå çíàÿ, ÷òî ýòî çà îïöèÿ è êàê îíà âëèÿåò íà ðàáîòó PHP. Ýòà ñòðàíèöà äîêóìåíòàöèè ïðèçâàíà ïîêàçàòü, êàê ýòà íàñòðîéêà ñî÷åòàåòñÿ ñ âîïðîñàìè áåçîïàñíîñòè ïðè ðàçðàáîòêå ïðèëîæåíèé. Ñëåäóåò ïîíèìàòü, ÷òî ñàìà ïî ñåáå ýòà îïöèÿ íèêàê íå âëèÿåò íà áåçîïàñíîñòü, óðãîçó ïðåäñòàâëÿåò íåêîððåêòíîå èñïîëüçîâàíèå ïðåäîñòàâëÿåìûõ åþ âîçìîæíîñòåé. </para> <para>  ñëó÷àå, åñëè çíà÷åíèå ïàðàìåòðà register_globals ON, ïåðåä âûïîëíåíèåì âàøåãî êîäà áóäóò èíèöèàëèçèðîâàíû ðàçëè÷íûå ïåðåìåííûå, íàïðèìåð, ïåðåìåííûå, ïåðåäàííûå ïðè îòïðàâêå ôîðìû. Òàêæå, ó÷èòûâàÿ òîò ôàêò, ÷òî PHP íå òðåáóåò èíèöèàëèçàöèè ïåðåìåííûõ, íàïèñàòü ïîòåíöèàëüíî îïàñíûé êîä î÷åíü ëåãêî. Ýòî áûëî î÷åíü ñïîðíûì ðåøåíèåì, íî îáùåñòâî ðàçðàáîò÷èêîâ PHP ðåøèëî èçìåíèòü çíà÷åíèå ïî óìîë÷àíèþ ýòîé äèðåêòèâû íà OFF.  ïðîòèâíîì ñëó÷àå ïðè íàïèñàíèè êîäà ðàçðàáîò÷èêè íå ìîãëè áû ñ óâåðåííîñòüþ ñêàçàòü, îòêóäà ïðèøëà òà èëè èíàÿ ïåðåìåííàÿ è íàñêîëüêî îíà äîñòîâåðíà. Äî òàêîãî íîâîââåäåíèÿ ïåðåìåííûå, îïðåäåëÿåìûå ðàçðàáîò÷èêîì âíóòðè ñêðèïòà, è ïåðåäàâàåìûå ïîëüçîâàòåëåì âíåøíèå äàííûå ìîãëè ïåðåìåøèâàòüñÿ. Ïðèâåäåì ïðîñòîé ïðèìåð çëîóïîòðåáëåíèÿ êîíôèãóðàöèîííîé îïöèåé register_globals: </para> <para> <example> <title>Ïðèìåð îïàñíîãî êîäà ñ register_globals = on</title> <programlisting role="php"> <![CDATA[ <?php // óñòàíàâëèâàåì ïåðåìåííóþ $authorized = true òîëüêî äëÿ ïîëüçîâàòåëåé, ïðîøåäøèõ àâòîðèçàöèþ if (authenticated_user()) { $authorized = true; } // Ïîñêîëüêó â ñëó÷àå íåóäà÷è ïðè ïðîâåðêå àâòîðèçàöèè ïåðåìåííàÿ $authorized // íå óñòàíîâëåíà, îíà ìîæåò áûòü óñòàíîâëåíà àâòîìàòè÷åñêè, áëàãîäàðÿ register_globals, // íàïðèìåð, ïðè GET çàïðîñå GET auth.php?authorized=1. // Òàêèì îáðàçîì, ïðîéòè ýòó ïðîâåðêó ìîæíî áåç àâòîðèçàöèè if ($authorized) { include "/highly/sensitive/data.php"; } ?> ]]> </programlisting> </example> </para> <para>  ñëó÷àå register_globals = on ëîãèêà ðàáîòû ñêðèïòà ìîæåò áûòü íàðóøåíà.  ñëó÷àå, åñëè óñòàíîâëåííîå çíà÷åíèå off, ïåðåìåííàÿ <varname>$authorized</varname> íå ìîæåò áûòü óñòàíîâëåíà èç âíåøíèõ äàííûõ çàïðîñà, è ñêðèïò áóäåò ðàáîòàòü êîððåêòíî. Íî âñå æå èíèöèàëèçàöèÿ ïåðåìåííûõ - îäèí èç ïðèçíàêîâ õîðîøåãî òîíà â ïðîãðàììèðîâàíèè. Íàïðèìåð, â ïðèâåäåííîì âûøå ó÷àñòêå êîäà ìû ìîãëè ïîìåñòèòü <literal>$authorized = false</literal> â êà÷åñòâå ïåðâîé ñòðîêè. Òàêîé êîä ðàáîòàë áû êàê ñî çíà÷åíèåì on, òàê è off îïöèè register_globals, è ïîäðàçóìåâàÿ, ÷òî ïî óìîë÷àíèþ ïîëüçîâàòåëü íå ïðîõîäèë àâòîðèçàöèþ. </para> <para> Ïðèâåäåì åùå îäèí ïðèìåð, èñïîëüçóþùèé <link linkend="ref.session">ñåññèè</link>.  ñëó÷àå, åñëè register_globals = on, ìû ìîæåì èñïîëüçîâàòü ïåðåìåííóþ <varname>$username</varname> â ïðèâåäåííîì íèæå ïðèìåðå, íî òîãäà ó íàñ íå áóäåò óâåðåííîñòè â äîñòîâåðíîñòè åå çíà÷åíèÿ (ê ïðèìåðó, îíà ìîãëà áûòü ïåðåäàíà â GET-çàïðîñå). </para> <para> <example> <title>Ïðèìåð èñïîëüçîâàíèÿ ñåññèé ñî çíà÷åíèåì register_globals on èëè off</title> <programlisting role="php"> <![CDATA[ <?php // Ìû íå çíàåì, îòêóäà ïîëó÷åíà ïåðåìåííàÿ $username, íî òî÷íî çíàåì, ÷òî // ïåðåìåííàÿ $_SESSION õðàíèò â ñåáå äàííûå ñåññèè if (isset($_SESSION['username'])) { echo "Hello <b>{$_SESSION['username']}</b>"; } else { echo "Hello <b>Guest</b><br />"; echo "Would you like to login?"; } ?> ]]> </programlisting> </example> </para> <para> Òàêæå ñóùåñòâóåò âîçìîæíîñòü ðåàëèçàöèè îïåðàòèâíîãî ðåàãèðîâàíèÿ â ñëó÷àå ïîïûòêè ïîäìåíû ïåðåìåííûõ. Òàê êàê âî âðåìÿ ðàçðàáîòêè ïðèëîæåíèÿ ìû çíàåì îæèäàåìîå çíà÷åíèå ïåðåìåííîé, à òàêæå çíàåì åå äîñòîâåðíîå çíà÷åíèå, ìû ìîæåì èõ ñîïîñòàâèòü. Ýòî íå çàùèòèò êîä îò ïîäìåíû ïåðåìåííûõ, íî óñëîæíèò ïåðåáîð âîçìîæíûõ âàðèàíòîâ. Åñëè âû íå õîòèòå çíàòü, êàê èìåííî áûëè ïîëó÷åíû âíåøíèå äàííûå, èñïîëüçóéòå ïåðåìåííóþ <varname>$_REQUEST</varname>, êîòîðàÿ ñîñòîèò èç äàííûõ GET è POST çàïðîñîâ, à òàêæå äàííûõ COOKIE. Òàêæå, èíôîðìàöèþ îá ýòîì ìîæíî íàéòè â ðàçäåëå <link linkend="language.variables.external">âíåøíèå äàííûå â PHP</link>. </para> <para> <example> <title>Îáíàðóæåíèå ïîïûòêè ïîäìåíû ïåðåìåííûõ</title> <programlisting role="php"> <![CDATA[ <?php if (isset($_COOKIE['MAGIC_COOKIE'])) { // MAGIC_COOKIE ïîëó÷åíà èç äîñòîâåðíîãî èñòî÷íèêà. // Äëÿ ïîëíîé óâåðåííîñòè íåîáõîäèìî ïðîâåðèòü åå çíà÷åíèå. } elseif (isset($_GET['MAGIC_COOKIE']) || isset($_POST['MAGIC_COOKIE'])) { mail("admin@example.com", "Îáíàðóæåíà ïîïûòêà âçëîìà", $_SERVER['REMOTE_ADDR']); echo "Îáíàðóæåíî íàðóøåíèå áåçîïàñíîñòè, àäìèíèñòðàòîð óâåäîìëåí."; exit; } else { // MAGIC_COOKIE â äàííûõ çàïðîñà íå ïðèñóòñòâóåò } ?> ]]> </programlisting> </example> </para> <para> Ñëåäóåò ïîíèìàòü, ÷òî óñòàíîâêà register_globals â off íå ñäåëàåò âàø êîä áåçîïàñíûì. Êàæäóþ ïîëó÷åííóþ îò ïîëüçîâàòåëÿ ïåðåìåííóþ ñëåäóåò ïðîâåðÿòü íà ñîîòâåòñòâèå îæèäàåìîìó çíà÷åíèþ. Âñåãäà ïðîâåðÿéòå ââîä ïîëüçîâàòåëÿ è èíèöèàëèçèðóéòå âñå èñïîëüçóåìûå ïåðåìåííûå. Äëÿ ïðîâåðêè íà íàëè÷èå íåèíèöèàëèçèðîâàííûõ ïåðåìåííûõ ìîæíî âêëþ÷èòü â îïöèþ <function>error_reporting</function> îòîáðàæåíèå îøèáîê êàòåãîðèè <constant>E_NOTICE</constant>. </para> ¬e.superglobals; </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/hiding.xml?r=1.1&p=1 Index: phpdoc-ru/security/hiding.xml +++ phpdoc-ru/security/hiding.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.hiding"> <title>Ñîêðûòèå PHP</title> <para>  îáùåì ñëó÷àå âíåñåíèå íåÿñíîñòè íåíàìíîãî óëó÷øàåò çàùèùåííîñòü ñèñòåìû. Íî áûâàþò ñëó÷àè, êîãäà ñëåäóåò èñïîëüçîâàòü ìàëåéøóþ âîçìîæíîñòü. </para> <para> Íåñêîëüêî íåñëîæíûõ ìåòîäèê ìîãóò ïîìî÷ü âàì ñêðûòü PHP, ÷òî óñëîæíÿåò ðàáîòó ïîòåíöèàëüíîãî âçëîìùèêà, êîòîðûé ïûòàåòñÿ íàéòè áðåøü â âàøåé ñèñòåìå. Óñòàíîâèâ îïöèþ expose_php = off â êîíôèãóðàöèîííîì ôàéëå &php.ini;, âû óìåíüøèòå êîëè÷åñòâî äîñòóïíîé õàêåðó èíôîðìàöèè. </para> <para> Åùå îäíà ìåòîäèêà çàêëþ÷àåòñÿ â íàñòðîéêå âåá-ñåðâåðà òàêèì îáðàçîì, ÷òîáû îí îáðàáàòûâàë ôàéëû ñ ðàçëè÷íûìè ðàñøèðåíèÿìè êàê PHP-ñêðèïòû. Ýòî ìîæíî óêàçàòü êàê â &htaccess; ôàéëàõ, òàê è êîíôèãóðàöèîííîì ôàéëå Apache.  òàêîì ñëó÷àå âû ñìîæåòå èñïîëüçîâàòü ïðè íàïèñàíèè êîäà íåñòàíäàðòíûå ðàñøèðåíèÿ: <example> <title>Ìàñêèðîâêà PHP ïîä äðóãèå ÿçûêè ïðîãðàììèðîâàíèÿ</title> <programlisting role="apache-conf"> <![CDATA[ # Òåïåðü PHP-ñêðèïòû ìîãóò èìåòü òå æå ðàñøèðåíèÿ, ÷òî è äðóãèå ÿçûêè ïðîãðàììèðîâàíèÿ AddType application/x-httpd-php .asp .py .pl ]]> </programlisting> </example> Èëè ñêðûòü åãî ñîâñåì: <example> <title>Èñïîëüçîâàíèå íåèçâåñòíûõ ðàñøèðåíèé äëÿ PHP-ñêðèïòîâ</title> <programlisting role="apache-conf"> <![CDATA[ # Òåïåðü PHP-ñêðèïòû ìîãóò èìåòü íåèçâåñòíûå òèïû ôàéëîâ AddType application/x-httpd-php .bop .foo .133t ]]> </programlisting> </example> Òàêæå ìîæíî ñïðÿòàòü åãî ïîä âèäîì HTML-êîäà, ÷òî ïðèâåäåò ê ïîòåðå ïðîèçâîäèòåëüíîñòè, òàê êàê âñå HTML ôàéëû áóäóò îáðàáàòûâàòüñÿ êàê PHP-êîä: <example> <title>Ìàñêèðîâêà PHP-êîäà ïîä html-ôàéëû</title> <programlisting role="apache-conf"> <![CDATA[ # Òåïåðü PHP-ñêðòïû ìîãóò âûãëÿäåòü êàê îáûêíîâåííûé HTML AddType application/x-httpd-php .htm .html ]]> </programlisting> </example> ×òîáû äîñòè÷ü æåëàåìîãî ýôôåêòà, âû äîëæíû ïåðåèìåíîâàòü âñå âàøè ñêðèïòû â ñîîòâåòñòâèè ñ âûáðàííûì âàìè ðàñøèðåíèåì. Îïèñàííîå â ýòîì ðàçäåëå äîêóìåíòàöèè ïîâûøåíèå áåçîïàñíîñòè ÷åðåç ñîêðûòèå PHP èìååò ìàëî íåäîñòàòêîâ ïðè íåáîëüøèõ çàòðàòàõ. </para> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/index.xml?r=1.1&p=1 Index: phpdoc-ru/security/index.xml +++ phpdoc-ru/security/index.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- Last Revision before split: 1.66 --> <chapter id="security.index"> <title>Áåçîïàñíîñòü</title> &security.intro; &security.general; &security.cgi-bin; &security.apache; &security.filesystem; &security.database; &security.errors; &security.globals; &security.variables; &security.hiding; &security.current; </chapter> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/intro.xml?r=1.1&p=1 Index: phpdoc-ru/security/intro.xml +++ phpdoc-ru/security/intro.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.intro"> <title>Âñòóïëåíèå</title> <simpara> PHP ÿâëÿåòñÿ ìîùíûì ÿçûêîì ïðîãðàììèðîâàíèÿ è èíòåðïðåòàòîðîì, âçàèìîäåéñòâóþùèì ñ âåá-ñåðâåðîì êàê ìîäóëü ëèáî êàê íåçàâèñèìîå áèíàðíîå <acronym>CGI</acronym> ïðèëîæåíèå. PHP ñïîñîáåí îáðàùàòüñÿ ê ôàéëàì, âûïîëíÿòü ðàçëè÷íûå êîìàíäû íà ñåðâåðå è îòêðûâàòü ñåòåâûå ñîåäèíåíèÿ. Èìåííî ïîýòîìó âñå ñêðèïòû, èñïîëíÿåìûå íà ñåðâåðå ÿâëÿþòñÿ ïîòåíöèàëüíî îïàñíûìè. PHP èçíà÷àëüíî ðàçðàáàòûâàëñÿ êàê áîëåå çàùèùåííûé (îòíîñèòåëüíî Perl, C) ÿçûê äëÿ íàïèñàíèÿ CGI-ïðèëîæåíèé. Ïðè ïîìîùè ðÿäà íàñòðîåê âî âðåìÿ êîìïèëÿöèè, à òàêæå íàñòðîåê âî âðåìÿ ðàáîòû ïðèëîæåíèÿ, âû âñåãäà ñìîæåòå íàéòè ïîäõîäÿùåå ñî÷åòàíèå ñâîáîäû äåéñòâèé è áåçîïàñíîñòè. </simpara> <simpara> Ïîñêîëüêó ñóùåñòâóåò ìíîãî ðàçëè÷íûõ ñïîñîáîâ èñïîëüçîâàíèÿ PHP, èìååòñÿ è ìíîæåñòâî îïöèé, óïðàâëÿþùèõ åãî ïîâåäåíèåì. Øèðîêèé âûáîð îïöèé ãàðàíòèðóåò âàì âîçìîæíîñòü èñïîëüçîâàòü PHP â ðàçíûõ öåëÿõ, íî òàêæå îçíà÷àåò, ÷òî íåêîòîðûå êîìáèíàöèè îïöèé äåëàþò ñåðâåð íåçàùèùåííûì. </simpara> <simpara> Ãèáêîñòü êîíôèãóðèðîâàíèÿ PHP ìîæíî ñðàâíèòü ñ ãèáêîñòüþ ñàìîãî ÿçûêà. PHP ìîæíî èñïîëüçîâàòü äëÿ ñîçäàíèÿ ïîëíîöåííûõ ñåðâåðíûõ ïðèëîæåíèé, èñïîëüçóþùèõ äîñòóïíûå äëÿ óêàçàííîãî ïîëüçîâàòåëÿ âîçìîæíîñòè îïåðàöèîííîé ñèñòåìû, òàêæå âîçìîæíà ðåàëèçàöèÿ âêëþ÷åíèÿ ôàéëîâ, õðàíÿùèõñÿ íà ñåðâåðå ñ ìèíèìàëüíûì ðèñêîì â æåñòêî êîíòðîëèðóåìîé ñðåäå. Òî, íàñêîëüêî áåçîïàñåí âàø ñåðâåð è êàê íàñòðîåíî îêðóæåíèå, â áîëüøåé ÷àñòè çàâèñèò îò PHP-ðàçðàáîò÷èêà. </simpara> <simpara> Ýòà ãëàâà íà÷èíàåòñÿ ñ ðàññìîòðåíèÿ íåêîòîðûõ îáùèõ âîïðîñîâ áåçîïàñíîñòè, ðàçëè÷íûõ êîíôèãóðàöèîííûõ îïöèé è èõ êîìáèíàöèé, à òàêæå ñèòóàöèé, êîãäà èõ èñïîëüçîâàíèå ÿâëÿåòñÿ áåçîïàñíûì. Êðîìå òîãî, ïðèâîäÿòñÿ íåêîòîðûå ðàññóæäåíèÿ êàñàòåëüíî áåçîïàñíîãî êîäèðîâàíèÿ. </simpara> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 --> http://cvs.php.net/co.php/phpdoc-ru/security/variables.xml?r=1.1&p=1 Index: phpdoc-ru/security/variables.xml +++ phpdoc-ru/security/variables.xml <?xml version="1.0" encoding="windows-1251"?> <!-- $Revision: 1.1 $ --> <!-- splitted from ./index.xml, last change in rev 1.66 --> <sect1 id="security.variables"> <title>Äàííûå, ââåäåííûå ïîëüçîâàòåëåì</title> <para> Íàèáîëåå îïàñíûå äûðû âî ìíîãèõ PHP-ñêðèïòàõ âîçíèêàþò íå ñòîëüêî èç-çà ñàìîãî ÿçûêà, ñêîëüêî èç-çà êîäà, íàïèñàííîãî áåç ó÷åòà ñîîòâåòñòâóþùèõ òðåáîâàíèé áåçîïàñíîñòè. Êàê ñëåäñòâèå, âû âñåãäà äîëæíû âûäåëÿòü âðåìÿ íà èññëåäîâàíèå ðàçðàáàòûâàåìîãî ó÷àñòêà êîäà, ÷òîáû îöåíèòü ïîòåíöèàëüíóþ óãðîçó îò ââîäà ïåðåìåííîé ñ íåñòàíäàðòíûì çíà÷åíèåì. <example> <title>Ïîòåíöèàëüíî îïàñíîå èñïîëüçîâàíèå ïåðåìåííûõ</title> <programlisting role="php"> <![CDATA[ <?php // óäàëèòü ôàéëû èç äîìàøíåé äèðåêòîðèè ïîëüçîâàòåëÿ... // à ìîæåò, åùå ÷òî íèáóäü? unlink ($evil_var); // çàïèñàòü â ëîã-ôàéë âûïîëíÿåìîå äåéñòâèå... // ìîæåò áûòü, äàæå /etc/passwd? fputs ($fp, $evil_var); // âûïîëíåíèå òðèâèàëüíûõ äåéñòâèé... èëè rm -rf *? system ($evil_var); exec ($evil_var); ?> ]]> </programlisting> </example> Âû äîëæíû òùàòåëüíî ïðîâåðÿòü âàø êîä è áûòü àáñîëþòíî óâåðåíû â òîì, ÷òî âñå äàííûå, ïåðåäàâàåìûå âåá-áðàóçåðîì, ïðîâåðÿþòñÿ íàäëåæàùèì îáðàçîì. Ïîïðîáóéòå îòâåòèòü äëÿ ñåáÿ íà ñëåäóþùèå âîïðîñû: <itemizedlist> <listitem> <simpara> Áóäåò ëè äàííûé ñêðèïò âîçäåéñòâîâàòü èñêëþ÷èòåëüíî íà ïðåäïîëàãàåìûå äàííûå? </simpara> </listitem> <listitem> <simpara> Ïðàâèëüíî ëè áóäóò îáðàáîòàíû íåêîððåêòíûå èëè íåñòàíäàðòíûå äàííûå? </simpara> </listitem> <listitem> <simpara> Âîçìîæíî ëè èñïîëüçîâàíèå ñêðèïòà íå ïðåäóñìîòðåííûì ñïîñîáîì? </simpara> </listitem> <listitem> <simpara> Âîçìîæíî ëè åãî èñïîëüçîâàíèå â ñî÷åòàíèè ñ äðóãèìè ñêðèïòàìè â íåãàòèâíûõ öåëÿõ? </simpara> </listitem> <listitem> <simpara> Áóäåò ëè êàæäàÿ òðàíçàêöèÿ êîððåêòíî ëîãèðîâàíà? </simpara> </listitem> </itemizedlist> Îòâåòèâ íà ýòè âîïðîñû âî âðåìÿ íàïèñàíèÿ ñêðèïòà, à íå ïîñëå, âû, âîçìîæíî, ïðåäîòâðàòèòå ïîñëåäóþùóþ äîðàáîòêó ñêðèïòà â öåëÿõ ïîâûøåíèÿ åãî áåçîïàñíîñòè. Íà÷èíàÿ ðàçðàáîòêó ñ ýòèõ âîïðîñîâ, âû íå ãàðàíòèðóåòå ïîëíóþ áåçîïàñíîñòü âàøåé ñèñòåìû, íî ñìîæåòå çíà÷èòåëüíî ïîâûñèòü å¸. </para> <para> Âû òàêæå ìîæåòå ïðåäóñìîòðåòü îòêëþ÷åíèå òàêèõ êîíôèãóðàöèîííûõ îïöèé, êàê register_globals, magic_quotes è íåêîòîðûõ äðóãèõ, êîòîðûå ìîãóò ïðèâîäèòü ê ñîìíåíèÿì îòíîñèòåëüíî ïðîèñõîæäåíèÿ èëè çíà÷åíèÿ ïîëó÷àåìûõ ïåðåìåííûõ. Èñïîëüçîâàíèå ïðè íàïèñàíèè êîäà ðåæèìà error_reporting(E_ALL) ìîæåò ïîìî÷ü, ïðåäóïðåæäàÿ âàñ îá èñïîëüçîâàíèè ïåðåìåííûõ äî èíèöèàëèçàöèè èëè ïðîâåðêè (÷òî ïðåäîòâðàòèò ðàáîòó ñ äàííûìè, îòëè÷íûè îò îæèäàåìûõ). </para> </sect1> <!-- Keep this comment at the end of the file Local variables: mode: sgml sgml-omittag:t sgml-shorttag:t sgml-minimize-attributes:nil sgml-always-quote-attributes:t sgml-indent-step:1 sgml-indent-data:t indent-tabs-mode:nil sgml-parent-document:nil sgml-default-dtd-file:"../../manual.ced" sgml-exposed-tags:nil sgml-local-catalogs:nil sgml-local-ecat-files:nil End: vim600: syn=xml fen fdm=syntax fdl=2 si vim: et tw=78 syn=sgml vi: ts=1 sw=1 -->