Команда Sucuri проанализировала ряд популярных плагинов в директории WordPress.org на использование функций add_query_arg()
и remove_query_arg()
. Многие из них оказались уязвимыми.
Уязвимые плагины
Среди уязвимых плагинов были названы следующие:
- Jetpack
- WordPress SEO
- Google Analytics by Yoast
- All In one SEO
- BuddyPress
- bbPress
- Gravity Forms
- Ряд плагинов от Easy Digital Downloads
- UpdraftPlus
- WP-E-Commerce
- WPTouch
- Download Monitor
- Related Posts for WordPress
- My Calendar
- P3 Profiler
- Give
- Множество продуктов iThemes, включая Builder and Exchange
- Broken-Link-Checker
- Ninja Forms
При использовании любого из этих плагинов, убедитесь в том, что у вас установлена самая свежая версия. Многие авторы уже выпустили обновления, а для самых популярных плагинов, включая Jetpack от Automattic, команда WordPress.org решила выпустить фоновое обновление.
Учтите, что если в данном списке нет ваших плагинов, это не значит, что они не уязвимы. Команда Sucuri проверила лишь 400 плагинов в порядке их популярности. В случае если вы не уверены, обязательно обратитесь на страницу плагина на сайте WordPress.org и посмотрите раздел Changelog, чтобы узнать в какой версии была устранена данная уязвимость.
Разработчикам тем и плагинов рекомендуется проанализировать использование функций add_query_arg()
и remove_query_arg()
в своих плагинах.
Технические детали
Многие разработчики, используя функции add_query_arg()
или remove_query_arg()
подразумевали, что они экранируют вывод результата, но к сожалению это не так.
При отсутствии аргумента $query
, эти функции используют текущий адрес сайта, который находится в глобальном массиве $_SERVER['REQUEST_URI']
. При этом, найденный адрес используется как есть, и может содержать любой пользовательский ввод:
$link = add_query_arg( 'foo', 'bar' ); printf( '<a href="%s">link</a>', $link );
На первый взгляд кажется, что данная безобидная функция добавляет аргумент foo=bar
к текущему URL и выводит в виде ссылки, но поскольку результат функции зависит от текущего адреса, злоумышленник может запросить что-нибудь подобное:
http://example.org/?"><script>alert()</script>
Здесь двойные кавычки закрывают тэг ссылки, и далее злоумышленник может исполнять любой JavaScript код, включая кражу куки авторизованных пользователей. Исправить это легко с помощью функций экранирования esc_url()
и esc_url_raw()
:
$link = add_query_arg( 'foo', 'bar' ); // Опасно! $link = esc_url( $link ); // Теперь безопасно. printf( '<a href="%s">link</a>', $link );
В случае работы с редиректами, или HTTP API в WordPress, вместо esc_url()
следует использовать функцию esc_url_raw()
, которая экранирует адрес, но не готовит его для вывода на экран.
Об основах безопасности WordPress и о том, почему следует всегда обновлять ядро, темы и плагины, читайте в нашей статье.