{"id":709,"date":"2010-06-26T12:23:16","date_gmt":"2010-06-26T10:23:16","guid":{"rendered":"http:\/\/blog.benny-baumann.de\/?p=709"},"modified":"2010-06-26T13:26:36","modified_gmt":"2010-06-26T11:26:36","slug":"mediawiki-ohne-e","status":"publish","type":"post","link":"https:\/\/blog.benny-baumann.de\/?p=709","title":{"rendered":"MediaWiki-Fehlermeldung beim Registrieren durch preg_replace mit \/e"},"content":{"rendered":"<p>Nach dem es bei mir die Tage auf dem Server wieder mal einen Einzug gab bei dem auch ein MediaWiki 1.15.4 eingerichtet wurde, stellte sich heraus, dass dieses mit der auf diesem Server herrschenden Policy nicht ganz zurecht kommt. Aufgefallen ist dies bei der Nutzerregistrierung, die einen entsprechenden Fehler lieferte, dennoch aber den Account anlegte.<!--more--><\/p>\n<p>Basierend auf der Fehlermeldung<br \/>\n<code>Fatal error: SUHOSIN - Use of preg_replace() with \/e modifier is forbidden by configuration in \/var\/www\/virtual\/example.com\/htdocs\/includes\/GlobalFunctions.php(1127) : regexp code on line 1127<\/code><\/p>\n<p>wurde eine grobe Kot-Suche iniziiert und auch auf Anhieb der \u00dcbelt\u00e4ter gefunden:<\/p>\n<pre lang=\"php\">\/**\r\n * @todo document\r\n *\/\r\nfunction wfQuotedPrintable( $string, $charset = '' ) {\r\n        # Probably incomplete; see RFC 2045\r\n        if( empty( $charset ) ) {\r\n                global $wgInputEncoding;\r\n                $charset = $wgInputEncoding;\r\n        }\r\n        $charset = strtoupper( $charset );\r\n        $charset = str_replace( 'ISO-8859', 'ISO8859', $charset ); \/\/ ?\r\n\r\n        $illegal = '\\x00-\\x08\\x0b\\x0c\\x0e-\\x1f\\x7f-\\xff=';\r\n        $replace = $illegal . '\\t ?_';\r\n        if( !preg_match( \"\/[$illegal]\/\", $string ) ) return $string;\r\n        $out = \"=?$charset?Q?\";\r\n        $out .= preg_replace( \"\/([$replace])\/e\", 'sprintf(\"=%02X\",ord(\"$1\"))', $string );\r\n        $out .= '?=';\r\n        return $out;\r\n}<\/pre>\n<p>Der Fix an sich ist nicht weiter schwierig, da es wieder einmal allein darum geht, aus einem preg_replace mit \/e ein preg_replace_callback zu erzeugen. H\u00e4tten wir also:<\/p>\n<pre lang=\"php\">\/**\r\n * @todo document\r\n *\/\r\nfunction wfQuotedPrintable_cb($m) {\r\n        return sprintf(\"=%02X\",ord($m[1]));\r\n}\r\n\/**\r\n * @todo document\r\n *\/\r\nfunction wfQuotedPrintable( $string, $charset = '' ) {\r\n        # Probably incomplete; see RFC 2045\r\n        if( empty( $charset ) ) {\r\n                global $wgInputEncoding;\r\n                $charset = $wgInputEncoding;\r\n        }\r\n        $charset = strtoupper( $charset );\r\n        $charset = str_replace( 'ISO-8859', 'ISO8859', $charset ); \/\/ ?\r\n\r\n        $illegal = '\\x00-\\x08\\x0b\\x0c\\x0e-\\x1f\\x7f-\\xff=';\r\n        $replace = $illegal . '\\t ?_';\r\n        if( !preg_match( \"\/[$illegal]\/\", $string ) ) return $string;\r\n        $out = \"=?$charset?Q?\";\r\n        $out .= preg_replace_callback( \"\/([$replace])\/\", 'wfQuotedPrintable_cb', $string );\r\n        $out .= '?=';\r\n        return $out;\r\n}<\/pre>\n<p>Und da mich der Source an dieser Stelle so sch\u00f6n anl\u00e4chelt, will ich mal gar nicht so sein:<\/p>\n<pre lang=\"php\">\/**\r\n * Printed-Quotable-escapes a character given as part of a preg_replace_callback operation.\r\n *\r\n * @param array Contains the matches of the replace command that the result should be based on\r\n * @return string\r\n *\/\r\nfunction wfQuotedPrintable_cb($m) {\r\n        return sprintf(\"=%02X\",ord($m[1]));\r\n}\r\n\/**\r\n * Escapes a string in printed-quotable format.\r\n * @param string The string to escape\r\n * @param string The Charset to use\r\n * @return string\r\n *\/\r\nfunction wfQuotedPrintable( $string, $charset = '' ) {\r\n        # Probably incomplete; see RFC 2045\r\n        if( empty( $charset ) ) {\r\n                global $wgInputEncoding;\r\n                $charset = $wgInputEncoding;\r\n        }\r\n        $charset = strtoupper( $charset );\r\n        $charset = str_replace( 'ISO-8859', 'ISO8859', $charset ); \/\/ ?\r\n\r\n        $illegal = '\\x00-\\x08\\x0b\\x0c\\x0e-\\x1f\\x7f-\\xff=';\r\n        $replace = $illegal . '\\t ?_';\r\n        if( !preg_match( \"\/[$illegal]\/\", $string ) ) return $string;\r\n        $out = \"=?$charset?Q?\";\r\n        $out .= preg_replace_callback( \"\/([$replace])\/\", 'wfQuotedPrintable_cb', $string );\r\n        $out .= '?=';\r\n        return $out;\r\n}<\/pre>\n<p>Und sehe, dass die sich von MediaWiki in Bezug auf die Parameter-Dokumentation ja gar nicht so viel M\u00fche geben \ud83d\ude09 Mediawiki-konformen Code erh\u00e4lt man daher, wenn man die mit @ beginnenden Kommentarzeilen wegl\u00e4sst.<\/p>\n<p>Ein weiterer Blick in die Sources ergab aber noch eine Reihe weiterer Problemstellen, die sich aber mit der gleichen Technik leicht beheben lassen. Dazu aber bei Gelegenheit mehr.<\/p>\n<p class=\"wp-flattr-button\"><a href=\"https:\/\/blog.benny-baumann.de\/?flattrss_redirect&amp;id=709&amp;md5=02453a6343ee400fd3ead1fb4f9bfc4f\" title=\"Flattr\" target=\"_blank\"><img src=\"http:\/\/blog.benny-baumann.de\/wp-content\/plugins\/flattr\/img\/flattr-badge-large.png\" srcset=\"http:\/\/blog.benny-baumann.de\/wp-content\/plugins\/flattr\/img\/flattr-badge-large.png\" alt=\"Flattr this!\"\/><\/a><\/p>","protected":false},"excerpt":{"rendered":"<p>Nach dem es bei mir die Tage auf dem Server wieder mal einen Einzug gab bei dem auch ein MediaWiki 1.15.4 eingerichtet wurde, stellte sich heraus, dass dieses mit der auf diesem Server herrschenden Policy nicht ganz zurecht kommt. Aufgefallen ist dies bei der Nutzerregistrierung, die einen entsprechenden Fehler lieferte, dennoch aber den Account anlegte.<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"ngg_post_thumbnail":0,"footnotes":""},"categories":[29],"tags":[14,98,276,13,21],"class_list":["post-709","post","type-post","status-publish","format-standard","hentry","category-software","tag-bugs","tag-developement","tag-mediawiki","tag-patch","tag-php"],"_links":{"self":[{"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/posts\/709","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=709"}],"version-history":[{"count":6,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/posts\/709\/revisions"}],"predecessor-version":[{"id":714,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=\/wp\/v2\/posts\/709\/revisions\/714"}],"wp:attachment":[{"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=709"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=709"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/blog.benny-baumann.de\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=709"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}