Security - CL2 Flashcards
Buffer Overflow
In information security and programming, a buffer overflow, or buffer overrun, is an anomaly where a program, while writing data to a buffer, overruns the buffer’s boundary and overwrites adjacent memory locations.
Buffers are areas of memory set aside to hold data, often while moving it from one section of a program to another, or between programs. Buffer overflows can often be triggered by malformed inputs; if one assumes all inputs will be smaller than a certain size and the buffer is created to be that size, then an anomalous transaction that produces more data could cause it to write past the end of the buffer. If this overwrites adjacent data or executable code, this may result in erratic program behavior, including memory access errors, incorrect results, and crashes.
Exploiting the behavior of a buffer overflow is a well-known security exploit. On many systems, the memory layout of a program, or the system as a whole, is well defined. By sending in data designed to cause a buffer overflow, it is possible to write into areas known to hold executable code and replace it with malicious code, or to selectively overwrite data pertaining to the program’s state, therefore causing behavior that was not intended by the original programmer. Buffers are widespread in operating system (OS) code, so it is possible to make attacks that perform privilege escalation and gain unlimited access to the computer’s resources. The famed Morris worm in 1988 used this as one of its attack techniques.
Programming languages commonly associated with buffer overflows include C and C++, which provide no built-in protection against accessing or overwriting data in any part of memory and do not automatically check that data written to an array (the built-in buffer type) is within the boundaries of that array. Bounds checking can prevent buffer overflows, but requires additional code and processing time. Modern operating systems use a variety of techniques to combat malicious buffer overflows, notably by randomizing the layout of memory, or deliberately leaving space between buffers and looking for actions that write into those areas (“canaries”).
Link:
https://en.wikipedia.org/wiki/Buffer_overflow
SQL/Code Injection
Code injection
Code injection is the exploitation of a computer bug that is caused by processing invalid data. Injection is used by an attacker to introduce (or “inject”) code into a vulnerable computer program and change the course of execution. The result of successful code injection can be disastrous, for example by allowing computer worms to propagate.
Code injection vulnerabilities occur when an application sends untrusted data to an interpreter. Injection flaws are most often found in SQL, LDAP, XPath, or NoSQL queries; OS commands; XML parsers, SMTP headers, program arguments, etc. Injection flaws tend to be easier to discover when examining source code than via testing. Scanners and fuzzers can help find injection fla
Injection can result in data loss or corruption, lack of accountability, or denial of access. Injection can sometimes lead to complete host takeover.
Certain types of code injection are errors in interpretation, giving special meaning to user input. Similar interpretation errors exist outside the world of computer science such as the comedy routine Who’s on First?. In the routine, there is a failure to distinguish proper names from regular words. Likewise, in some types of code injection, there is a failure to distinguish user input from system commands.
Code injection techniques are popular in system hacking or cracking to gain information, privilege escalation or unauthorized access to a system. Code injection can be used malevolently for many purposes, including:
- Arbitrarily modifying values in a database through SQL injection. The impact of this can range from website defacement to serious compromise of sensitive data.
- Installing malware or executing malevolent code on a server by injecting server scripting code (such as PHP or ASP).
- Privilege escalation to root permissions by exploiting Shell Injection vulnerabilities in a setuid root binary on UNIX, or Local System by exploiting a service on Microsoft Windows.
- Attacking web users with HTML/script injection (Cross-site scripting).
In 2008, 5.66% of all vulnerabilities reported that year were classified as Code Injection, the highest year on record. In 2015, this had decreased to 0.77%.
SQL injection
SQL injection is a code injection technique, used to attack data-driven applications, in which malicious SQL statements are inserted into an entry field for execution (e.g. to dump the database contents to the attacker). SQL injection must exploit a security vulnerability in an application’s software, for example, when user input is either incorrectly filtered for string literal escape characters embedded in SQL statements or user input is not strongly typed and unexpectedly executed. SQL injection is mostly known as an attack vector for websites but can be used to attack any type of SQL database.
SQL injection attacks allow attackers to spoof identity, tamper with existing data, cause repudiation issues such as voiding transactions or changing balances, allow the complete disclosure of all data on the system, destroy the data or make it otherwise unavailable, and become administrators of the database server.
In a 2012 study, it was observed that the average web application received 4 attack campaigns per month, and retailers received twice as many attacks as other industries.
Links:
https: //en.wikipedia.org/wiki/Code_injection
https: //en.wikipedia.org/wiki/SQL_injection
Authentication Attacks
Design Flaws in Authentication Mechanisms
Authentication functionality is subject to more design weaknesses than any other security mechanism commonly employed in web applications. Even in the apparently simple, standard model where an application authenticates users based on their username and password, shortcomings in the design of this model can leave the application highly vulnerable to unauthorized access.
Bad Passwords Many web applications employ no or minimal controls over the quality of users’ passwords. It is common to encounter applications that allow passwords that are: - Very short or blank - Common dictionary words or names - The same as the username - Still set to a default value
Brute-Forcible Login
Login functionality presents an open invitation for an attacker to try to guess usernames and passwords and therefore gain unauthorized access to the application. If the application allows an attacker to make repeated login attempts with different passwords until he guesses the correct one, it is highly vulnerable even to an amateur attacker who manually enters some common usernames and passwords into his browser.
Recent compromises of high-profile sites have provided access to hundreds of thousands of real-world passwords that were stored either in cleartext or
using brute-forcible hashes. Here are the most popular real-world passwords:
- password
- website name
- 12345678
- qwerty
- abc123
- 111111
- monkey
- 12345
- letmein
In this situation, any serious attacker will use automated techniques to attempt to guess passwords, based on lengthy lists of common values. Given today’s
bandwidth and processing capabilities, it is possible to make thousands of login attempts per minute from a standard PC and DSL connection. Even the most
robust passwords will eventually be broken in this scenario.
Verbose Failure Messages
A typical login form requires the user to enter two pieces of information — a username and password. Some applications require several more, such as date
of birth, a memorable place, or a PIN.
When a login attempt fails, you can of course infer that at least one piece of information was incorrect. However, if the application tells you which piece of information was invalid, you can exploit this behavior to considerably diminish the effectiveness of the login mechanism.
In the simplest case, where a login requires a username and password, an application might respond to a failed login attempt by indicating whether the reason for the failure was an unrecognized username or the wrong password, as illustrated in Figure 6-3.
Vulnerable Transmission of Credentials
If an application uses an unencrypted HTTP connection to transmit login credentials, an eavesdropper who is suitably positioned on the network can, of course, intercept them. Depending on the user’s location, potential eavesdroppers may reside:
- On the user’s local network
- Within the user’s IT department
- Within the user’s ISP
- On the Internet backbone
- Within the ISP hosting the application
- Within the IT department managing the application
Even if login occurs over HTTPS, credentials may still be disclosed to unauthorized parties if the application handles them in an unsafe manner:
- If credentials are transmitted as query string parameters, as opposed to in the body of a POST request, these are liable to be logged in various
places, such as within the user’s browser history, within the web server logs, and within the logs of any reverse proxies employed within the hosting infrastructure. If an attacker succeeds in compromising any of these resources, he may be able to escalate privileges by capturing the user credentials stored there.
- Although most web applications do use the body of a POST request to submit the HTML login form itself, it is surprisingly common to see the login request being handled via a redirect to a different URL with the same
credentials passed as query string parameters. Why application developers consider it necessary to perform these bounces is unclear, but having elected to do so, it is easier to implement them as 302 redirects to a URL
than as POST requests using a second HTML form submitted via JavaScript.
- Web applications sometimes store user credentials in cookies, usually to implement poorly designed mechanisms for login, password change, “remember me,” and so on. These credentials are vulnerable to capture via attacks that compromise user cookies and, in the case of persistent cookies, by anyone who gains access to the client’s local filesystem. Even if the credentials are encrypted, an attacker still can simply replay the cookie and therefore log in as a user without actually knowing her credentials.
Many applications use HTTP for unauthenticated areas of the application and switch to HTTPS at the point of login. If this is the case, then the correct place to switch to HTTPS is when the login page is loaded in the browser, enabling a user to verify that the page is authentic before entering credentials. However, it
is common to encounter applications that load the login page itself using HTTP and then switch to HTTPS at the point where credentials are submitted. This is unsafe, because a user cannot verify the authenticity of the login page itself and therefore has no assurance that the credentials will be submitted securely. A suitably positioned attacker can intercept and modify the login page, changing the target URL of the login form to use HTTP. By the time an astute user realizes that the credentials have been submitted using HTTP, they will have been compromised.
Password Change Functionality
Surprisingly, many web applications do not provide any way for users to change their password. However, this functionality is necessary for a well-designed
authentication mechanism for two reasons:
- Periodic enforced password change mitigates the threat of password compromise. It reduces the window in which a given password can be targeted in a guessing attack. It also reduces the window in which a compromised password can be used without detection by the attacker.
- Users who suspect that their passwords may have been compromised need to be able to quickly change their password to reduce the threat of unauthorized use.
Forgotten Password Functionality
Like password change functionality, mechanisms for recovering from a forgotten password situation often introduce problems that may have been avoided
in the main login function, such as username enumeration. In addition to this range of defects, design weaknesses in forgotten password functions frequently make this the weakest link at which to attack the
application’s overall authentication logic.
“Remember Me” Functionality
Applications often implement “remember me” functions as a convenience to users. This way, users don’t need to reenter their username and password each time they use the application from a specific computer. These functions are often insecure by design and leave the user exposed to attack both locally and by users on other computers:
- Some “remember me” functions are implemented using a simple persistent cookie, such as RememberUser=daf (see Figure 6-6). When this cookie is submitted to the initial application page, the application trusts the cookie to authenticate the user, and it creates an application session for that person, bypassing the login. An attacker can use a list of common or enumerated usernames to gain full access to the application without any authentication.
- Some “remember me” functions set a cookie that contains not the username but a kind of persistent session identifier, such as RememberUser=1328.
When the identifier is submitted to the login page, the application looks up the user associated with it and creates an application session for that user. As with ordinary session tokens, if the session identifiers of
other users can be predicted or extrapolated, an attacker can iterate through a large number of potential identifiers to find those associated with application users, and therefore gain access to their accounts
without authentication.
- Even if the information stored for reidentifying users is suitably protected (encrypted) to prevent other users from determining or guessing it, the information may still be vulnerable to capture through a bug such as
cross-site scripting (see Chapter 12), or by an attacker who has local access to the user’s computer.
User Impersonation Functionality
Some applications implement the facility for a privileged user of the application to impersonate other users in order to access data and carry out actions within
their user context. For example, some banking applications allow helpdesk operators to verbally authenticate a telephone user and then switch their application session into that user’s context to assist him or her. Various design flaws commonly exist within impersonation functionality:
- It may be implemented as a “hidden” function, which is not subject to proper access controls. For example, anyone who knows or guesses the URL /admin/ImpersonateUser.jsp may be able to make use of the function and impersonate any other user
- The application may trust user-controllable data when determining whether the user is performing impersonation. For example, in addition to a valid
session token, a user may submit a cookie specifying which account his session is currently using. An attacker may be able to modify this value and gain access to other user accounts without authentication
- If an application allows administrative users to be impersonated, any weakness in the impersonation logic may result in a vertical privilege escalation vulnerability. Rather than simply gaining access to other ordinary users’ data, an attacker may gain full control of the application.
- Some impersonation functionality is implemented as a simple “backdoor” password that can be submitted to the standard login page along with any username to authenticate as that user. This design is highly insecure for many reasons, but the biggest opportunity for attackers is that they are likely to discover this password when performing standard attacks such as brute-forcing of the login. If the backdoor password is matched before
the user’s actual password, the attacker is likely to discover the function of the backdoor password and therefore gain access to every user’s account.
Similarly, a brute-force attack might result in two different “hits,” thereby revealing the backdoor password.
Incomplete Validation of Credentials
Well-designed authentication mechanisms enforce various requirements on passwords, such as a minimum length or the presence of both uppercase and
lowercase characters. Correspondingly, some poorly designed authentication mechanisms not only do not enforce these good practices but also do not take
into account users’ own attempts to comply with them.
For example, some applications truncate passwords and therefore validate only the first n characters. Some applications perform a case-insensitive check of passwords. Some applications strip unusual characters (sometimes on the pretext of performing input validation) before checking passwords. In recent times, behavior of this kind has been identified in some surprisingly high-profile web applications, usually as a result of trial and error by curious users.
Each of these limitations on password validation reduces by an order of magnitude the number of variations available in the set of possible passwords. Through experimentation, you can determine whether a password is being fully validated or whether any limitations are in effect. You can then fine-tune your automated attacks against the login to remove unnecessary test cases,
thereby massively reducing the number of requests necessary to compromise user accounts.
Nonunique Usernames
Some applications that support self-registration allow users to specify their own username and do not enforce a requirement that usernames be unique.
Although this is rare, the authors have encountered more than one application with this behavior.
This represents a design flaw for two reasons:
- One user who shares a username with another user may also happen to select the same password as that user, either during registration or in a subsequent password change. In this eventuality, the application either rejects the second user’s chosen password or allows two accounts to have identical credentials. In the first instance, the application’s behavior effectively discloses to one user the credentials of the other user. In the second instance, subsequent logins by one of the users result in access to the other user’s account.
- An attacker may exploit this behavior to carry out a successful brute-force attack, even though this may not be possible elsewhere due to restrictions on failed login attempts. An attacker can register a specific username
multiple times with different passwords while monitoring for the differential response that indicates that an account with that username and password already exists. The attacker will have ascertained a target user’s password without making a single attempt to log in as that user.
Badly designed self-registration functionality can also provide a means for username enumeration. If an application disallows duplicate usernames, an attacker may attempt to register large numbers of common usernames to identify the existing usernames that are rejected.
Predictable Usernames
Some applications automatically generate account usernames according to a predictable sequence (cust5331, cust5332, and so on). When an application
behaves like this, an attacker who can discern the sequence can quickly arrive at a potentially exhaustive list of all valid usernames, which can be used as the basis for further attacks. Unlike enumeration methods that rely on making repeated requests driven by wordlists, this means of determining usernames can be carried out nonintrusively with minimal interaction with the application.
Predictable Initial Passwords
In some applications, users are created all at once or in sizeable batches and are automatically assigned initial passwords, which are then distributed to them through some means. The means of generating passwords may enable an attacker to predict the passwords of other application users. This kind of vulnerability is more common on intranet-based corporate applications — for example, where every employee has an account created on her behalf and receives a printed notification of her password. In the most vulnerable cases, all users receive the same password, or one closely derived from their username or job function. In other cases, generated
passwords may contain sequences that could be identified or guessed with access to a very small sample of initial passwords.
Insecure Distribution of Credentials
Many applications employ a process in which credentials for newly created accounts are distributed to users out-of-band of their normal interaction with the application (for example, via post, e-mail, or SMS text message). Sometimes, this is done for reasons motivated by security concerns, such as to provide assurance that the postal or e-mail address supplied by the user actually belongs to that person.
In some cases, this process can present a security risk. For example, suppose that the message distributed contains both username and password, there is
no time limit on their use, and there is no requirement for the user to change the password on first login. It is highly likely that a large number, even the majority, of application users will not modify their initial credentials and that the distribution messages will remain in existence for a lengthy period, during which they may be accessed by an unauthorized party.
Sometimes, what is distributed is not the credentials themselves, but rather an “account activation” URL, which enables users to set their own initial password. If the series of these URLs sent to successive users manifests any kind of sequence, an attacker can identify this by registering multiple users in close succession and then infer the activation URLs sent to recent and forthcoming users. A related behavior by some web applications is to allow new users to register accounts in a seemingly secure manner and then to send a welcome e-mail to each new user containing his full login credentials. In the worst case, a security conscious user who decides to immediately change his possibly compromised password then receives another e-mail containing the new password “for future reference.” This behavior is so bizarre and unnecessary that users would be well advised to stop using web applications that indulge in it.
Session Management Attacks
The session management mechanism is a fundamental security component in the majority of web applications. It is what enables the application to uniquely identify a given user across a number of different requests and to handle the data that it accumulates about the state of that user’s interaction with the application. Where an application implements login functionality, session management is of particular importance, because it is what enables the application to persist its assurance of any given user’s identity beyond the request in which
he supplies his credentials.
Because of the key role played by session management mechanisms, they are a prime target for malicious attacks against the application. If an attacker can break an application’s session management, she can effectively bypass its authentication controls and masquerade as other application users without
knowing their credentials. If an attacker compromises an administrative user in this way, the attacker can own the entire application.
As with authentication mechanisms, a wide variety of defects can commonly be found in session management functions. In the most vulnerable cases, an attacker simply needs to increment the value of a token issued to him by the application to switch his context to that of a different user. In this situation, the application is wide open for anyone to access all areas. At the other end
of the spectrum, an attacker may have to work extremely hard, deciphering several layers of obfuscation and devising a sophisticated automated attack, before finding a chink in the application’s armor.
The Need for State
The HTTP protocol is essentially stateless. It is based on a simple request-response model, in which each pair of messages represents an independent transaction.
The protocol itself contains no mechanism for linking the series of requests made by a particular user and distinguishing these from all the other requests
received by the web server. In the early days of the Web, there was no need for any such mechanism: websites were used to publish static HTML pages for anyone to view. Today, things are very different. The majority of web “sites” are in fact web applications. They allow you to register and log in. They let you buy and sell goods. They remember your preferences the next time you visit. They deliver rich multimedia experiences with content created dynamically based on what you click and type. To implement any of this functionality, web applications need to use the concept of a session. The most obvious use of sessions is in applications that support logging in.
After entering your username and password, you can use the application as the user whose credentials you have entered, until you log out or the session expires due to inactivity. Without a session, a user would have to reenter his password on every page of the application. Hence, after authenticating the user once, the application creates a session for him and treats all requests belonging to that session as coming from that user. Applications that do not have a login function also typically need to use sessions. Many sites selling merchandise do not require customers to create accounts. However, they allow users to browse the catalog, add items to a shopping basket, provide delivery details, and make a payment. In this scenario, there is no need to authenticate the user’s identity: for the majority of his visit, the application does not know or care who the user is. But to do business with him, it needs to know which series of requests it receives originated from the same user.
The simplest and still most common means of implementing sessions is to issue each user a unique session token or identifier. On each subsequent request to the application, the user resubmits this token, enabling the application to
determine which sequence of earlier requests the current request relates to.
In most cases, applications use HTTP cookies as the transmission mechanism for passing these session tokens between server and client. The server’s first response to a new client contains an HTTP header like the following:
Set-Cookie: ASP.NET_SessionId=mza2ji454s04cwbgwb2ttj55
and subsequent requests from the client contain this header:
Cookie: ASP.NET_SessionId=mza2ji454s04cwbgwb2ttj55
This standard session management mechanism is inherently vulnerable to various categories of attack. An attacker’s primary objective in targeting the mechanism is to somehow hijack the session of a legitimate user and thereby
masquerade as that person. If the user has been authenticated to the application, the attacker may be able to access private data belonging to the user or carry out unauthorized actions on that person’s behalf. If the user is unauthenticated, the attacker may still be able to view sensitive information submitted by the user during her session.
As in the previous example of a Microsoft IIS server running ASP.NET, most commercial web servers and web application platforms implement their own off-the-shelf session management solution based on HTTP cookies. They provide APIs that web application developers can use to integrate their own sessiondependent functionality with this solution.
Some off-the-shelf implementations of session management have been found to be vulnerable to various attacks, which results in users’ sessions being compromised (these are discussed later in this chapter). In addition, some developers find that they need more fine-grained control over session behavior than is provided for them by the built-in solutions, or they want to avoid some vulnerabilities inherent in cookie-based solutions. For these reasons, it is fairly common to see bespoke and/or non-cookie-based session management mechanisms used in security-critical applications such as online banking. The vulnerabilities that exist in session management mechanisms largely
fall into two categories:
1. Weaknesses in the generation of session tokens
2. Weaknesses in the handling of session tokens throughout their life cycle
Weaknesses in Token Generation
Session management mechanisms are often vulnerable to attack because tokens are generated in an unsafe manner that enables an attacker to identify the values of tokens that have been issued to other users.
Meaningful Tokens
Some session tokens are created using a transformation of the user’s username or e-mail address, or other information associated with that person. This information may be encoded or obfuscated in some way and may be combined with other data.
For example, the following token may initially appear to be a long random
string:
757365723d6461663b6170703d61646d696e3b646174653d30312f31322f3131
However, on closer inspection, you can see that it contains only hexadecimal characters. Guessing that the string may actually be a hex encoding of a string of ASCII characters, you can run it through a decoder to reveal the following:
user=daf;app=admin;date=10/09/11
Attackers can exploit the meaning within this session token to attempt to
guess the current sessions of other application users. Using a list of enumerated or common usernames, they can quickly generate large numbers of potentially valid tokens and test these to confirm which are valid.
Tokens that contain meaningful data often exhibit a structure. In other words, they contain several components, often separated by a delimiter, that can be extracted and analyzed separately to allow an attacker to understand their function and means of generation. Here are some components that may be encountered within structured tokens:
- The account username
- The numeric identifier that the application uses to distinguish between
accounts
- The user’s first and last names
- The user’s e-mail address
- The user’s group or role within the application
- A date/time stamp
- An incrementing or predictable number
- The client IP address
Each different component within a structured token, or indeed the entire
token, may be encoded in different ways. This can be a deliberate measure to obfuscate their content, or it can simply ensure safe transport of binary data via HTTP. Encoding schemes that are commonly encountered include XOR, Base64, and hexadecimal representation using ASCII characters (see Chapter 3). It may be necessary to test various decodings on each component of a structured token to unpack it to its original form.
Predictable Tokens
Some session tokens do not contain any meaningful data associating them
with a particular user. Nevertheless, they can be guessed because they contain sequences or patterns that allow an attacker to extrapolate from a sample of tokens to find other valid tokens recently issued by the application. Even if the extrapolation involves some trial and error (for example, one valid guess per 1,000 attempts), this would still enable an automated attack to identify large numbers of valid tokens in a relatively short period of time. Vulnerabilities relating to predictable token generation may be much easier to discover in commercial implementations of session management, such as web servers or web application platforms, than they are in bespoke applications.
When you are remotely targeting a bespoke session management mechanism, your sample of issued tokens may be restricted by the server’s capacity, the activity of other users, your bandwidth, network latency, and so on. In a laboratory environment, however, you can quickly create millions of sample tokens, all precisely sequenced and time-stamped, and you can eliminate interference caused by other users.
In the simplest and most brazenly vulnerable cases, an application may use
a simple sequential number as the session token. In this case, you only need to obtain a sample of two or three tokens before launching an attack that will quickly capture 100% of currently valid sessions.
Figure 7-1 shows Burp Intruder being used to cycle the last two digits of a
sequential session token to find values where the session is still active and can be hijacked. Here, the length of the server’s response is a reliable indicator that a valid session has been found. The extract grep feature has also been used to show the name of the logged-in user for each session.
In other cases, an application’s tokens may contain more elaborate sequences that take some effort to discover. The types of potential variations you might encounter here are open-ended, but the authors’ experience in the field indicates that predictable session tokens commonly arise from three different sources:
- Concealed sequences
- Time dependency
- Weak random number generation
Concealed Sequences It is common to encounter session tokens that cannot be easily predicted when analyzed in their raw form but that contain sequences that reveal themselves when the tokens are suitably decoded or unpacked. Consider the following series of values, which form one component of a structured session token: lwjVJA Ls3Ajg xpKr+A XleXYg 9hyCzA jeFuNg JaZZoA No immediate pattern is discernible; however, a cursory inspection indicates that the tokens may contain Base64-encoded data. In addition to the mixed-case alphabetic and numeric characters, there is a + character, which is also valid in a Base64-encoded string. Running the tokens through a Base64 decoder reveals the following: --Õ$ .ÍÀŽ Æ’«ø ^W-b ö‚Ì ?án6 %¦Y These strings appear to be gibberish and also contain nonprinting characters. This normally indicates that you are dealing with binary data rather than ASCII text. Rendering the decoded data as hexadecimal numbers gives you the following: 9708D524 2ECDC08E C692ABF8 5E579762 F61C82CC 8DE16E36 25A659A0 There is still no visible pattern. However, if you subtract each number from the previous one, you arrive at the following: FF97C4EB6A 97C4EB6A FF97C4EB6A 97C4EB6A FF97C4EB6A FF97C4EB6A which immediately reveals the concealed pattern. The algorithm used to generate tokens adds 0x97C4EB6A to the previous value, truncates the result to a 32-bit number, and Base64-encodes this binary data to allow it to be transported using the text-based protocol HTTP. Using this knowledge, you can easily write a script to produce the series of tokens that the server will next produce, and the series that it produced prior to the captured sample.
Time Dependency
Some web servers and applications employ algorithms to generate session tokens that use the time of generation as an input to the token’s value. If insuffi cient other entropy is incorporated into the algorithm, you may be able to predict other users’ tokens. Although any given sequence of tokens on its own may appear to be random, the same sequence coupled with information about the time at which each token was generated may contain a discernible pattern. In a busy application with a large number of sessions being created each second, a scripted attack may succeed in identifying large numbers of other users’ tokens.
When testing the web application of an online retailer, the authors encountered the following sequence of session tokens:
3124538-1172764258718
3124539-1172764259062
3124540-1172764259281
3124541-1172764259734
3124542-1172764260046
3124543-1172764260156
3124544-1172764260296
3124545-1172764260421
3124546-1172764260812
3124547-1172764260890
Each token is clearly composed of two separate numeric components. The
first number follows a simple incrementing sequence and is easy to predict.
The second number increases by a varying amount each time. Calculating the differences between its value in each successive token reveals the following:
344
219
453
312
110
140
125
391
78
The sequence does not appear to contain a reliably predictable pattern. However, it would clearly be possible to brute-force the relevant number range in an automated attack to discover valid values in the sequence. Before attempting this attack, however, we wait a few minutes and gather a further sequence of tokens:
3124553-1172764800468
3124554-1172764800609
3124555-1172764801109
3124556-1172764801406
3124557-1172764801703
3124558-1172764802125
3124559-1172764802500
3124560-1172764802656
3124561-1172764803125
3124562-1172764803562
Comparing this second sequence of tokens with the first, two points are immediately obvious:
- The first numeric sequence continues to progress incrementally; however,
five values have been skipped since the end of the first sequence. This is
presumably because the missing values have been issued to other users
who logged in to the application in the window between the two tests.
- The second numeric sequence continues to progress by similar intervals
as before; however, the first value we obtain is a massive 539,578 greater
than the previous value.
This second observation immediately alerts us to the role played by time
in generating session tokens. Apparently, only five tokens have been issued
between the two token-grabbing exercises. However, a period of approximately 10 minutes has elapsed. The most likely explanation is that the second number is time-dependent and is probably a simple count of milliseconds.
Indeed, our hunch is correct. In a subsequent phase of our testing we perform a code review, which reveals the following token-generation algorithm:
String sessId = Integer.toString(s_SessionIndex++) +
“-” +
System.currentTimeMillis();
Given our analysis of how tokens are created, it is straightforward to construct a scripted attack to harvest the session tokens that the application issues to other users:
- We continue polling the server to obtain new session tokens in quick
succession.
- We monitor the increments in the fi rst number. When this increases by
more than 1, we know that a token has been issued to another user.
- When a token has been issued to another user, we know the upper and
lower bounds of the second number that was issued to that person, because we possess the tokens that were issued immediately before and after his. Because we are obtaining new session tokens frequently, the range between these bounds will typically consist of only a few hundred values.
- Each time a token is issued to another user, we launch a brute-force attack
to iterate through each number in the range, appending this to the missing incremental number that we know was issued to the other user. We
attempt to access a protected page using each token we construct, until
the attempt succeeds and we have compromised the user’s session.
- Running this scripted attack continuously will enable us to capture the
session token of every other application user. When an administrative
user logs in, we will fully compromise the entire application.
Weak Random Number Generation
Very little that occurs inside a computer is random. Therefore, when randomness is required for some purpose, software uses various techniques to generate numbers in a pseudorandom manner. Some of the algorithms used produce sequences that appear to be stochastic and manifest an even spread across the range of possible values. Nevertheless, they can be extrapolated forwards or backwards with perfect accuracy by anyone who obtains a small sample of values. When a predictable pseudorandom number generator is used to produce session tokens, the resulting tokens are vulnerable to sequencing by an attacker.
Weaknesses in Session Token Handling
No matter how effective an application is at ensuring that the session tokens it generates do not contain any meaningful information and are not susceptible to analysis or prediction, its session mechanism will be wide open to attack if those tokens are not handled carefully after generation. For example, if tokens are disclosed to an attacker via some means, the attacker can hijack user sessions even if predicting the tokens is impossible. An application’s unsafe handling of tokens can make it vulnerable to attack in several ways.
Disclosure of Tokens on the Network
This area of vulnerability arises when the session token is transmitted across the network in unencrypted form, enabling a suitably positioned eavesdropper to obtain the token and therefore masquerade as the legitimate user. Suitable positions for eavesdropping include the user’s local network, within the user’s IT department, within the user’s ISP, on the Internet backbone, within the application’s ISP, and within the IT department of the organization hosting the application. In each case, this includes both authorized personnel of the relevant organization and any external attackers who have compromised the infrastructure concerned.
In the simplest case, where an application uses an unencrypted HTTP connection for communications, an attacker can capture all data transmitted between client and server, including login credentials, personal information, payment details, and so on. In this situation, an attack against the user’s session is often unnecessary because the attacker can already view privileged information and can log in using captured credentials to perform other malicious actions.
However, there may still be instances where the user’s session is the primary target. For example, if the captured credentials are insuffi cient to perform a second login (for example, in a banking application, they may include a number displayed on a changing physical token, or specifi c digits from the user’s PIN), the attacker may need to hijack the eavesdropped session to perform arbitrary actions. Or if logins are audited closely, and the user is notified of each successful login, an attacker may want to avoid performing his own login to be as stealthy as possible.
In other cases, an application may use HTTPS to protect key client-server
communications yet may still be vulnerable to interception of session tokens on the network. This weakness may occur in various ways, many of which can arise specifically when HTTP cookies are used as the transmission mechanism for session tokens:
- Some applications elect to use HTTPS to protect the user’s credentials
during login but then revert to HTTP for the remainder of the user’s session. Many web mail applications behave in this way. In this situation, an
eavesdropper cannot intercept the user’s credentials but may still capture
the session token. The Firesheep tool, released as a plug-in for Firefox,
makes this an easy process.
- Some applications use HTTP for preauthenticated areas of the site, such
as the site’s front page, but switch to HTTPS from the login page onward.
However, in many cases the user is issued a session token at the first page
visited, and this token is not modified when the user logs in. The user’s
session, which is originally unauthenticated, is upgraded to an authenticated session after login. In this situation an eavesdropper can intercept a user’s token before login, wait for the user’s communications to switch to HTTPS, indicating that the user is logging in, and then attempt to access a protected page (such as My Account) using that token.
- Even if the application issues a fresh token following successful login,
and uses HTTPS from the login page onward, the token for the user’s
authenticated session may still be disclosed. This can happen if the user
revisits a preauthentication page (such as Help or About), either by following links within the authenticated area, by using the back button, or
by typing the URL directly.
- In a variation on the preceding case, the application may attempt to switch
to HTTPS when the user clicks the Login link. However, it may still accept
a login over HTTP if the user modifi es the URL accordingly. In this situation, a suitably positioned attacker can modify the pages returned in the
preauthenticated areas of the site so that the Login link points to an HTTP
page. Even if the application issues a fresh session token after successful login, the attacker may still intercept this token if he has successfully
downgraded the user’s connection to HTTP.
- Some applications use HTTP for all static content within the application,
such as images, scripts, style sheets, and page templates. This behavior
is often indicated by a warning within the user’s browser, as shown in
Figure 7-9. When a browser shows this warning, it has already retrieved
the relevant item over HTTP, so the session token has already been transmitted. The purpose of the browser’s warning is to let the user decline
to process response data that has been received over HTTP and so may
be tainted. As described previously, an attacker can intercept the user’s
session token when the user’s browser accesses a resource over HTTP and
use this token to access protected, nonstatic areas of the site over HTTPS.
- Even if an application uses HTTPS for every page, including unauthenticated areas of the site and static content, there may still be circumstances in which users’ tokens are transmitted over HTTP. If an attacker can somehow induce a user to make a request over HTTP (either to the HTTP service on the same server if one is running or to http://server:443/ otherwise), his token may be submitted. Means by which the attacker may attempt this include sending the user a URL in an e-mail or instant message, placing autoloading links into a website the attacker controls, or using clickable banner ads.
Disclosure of Tokens in Logs
Aside from the clear-text transmission of session tokens in network communications, the most common place where tokens are simply disclosed to unauthorized view is in system logs of various kinds. Although it is a rarer occurrence, the consequences of this kind of disclosure are usually more serious. Those logs may be viewed by a far wider range of potential attackers, not just by someone who is suitably positioned to eavesdrop on the network.
Many applications provide functionality for administrators and other support personnel to monitor and control aspects of the application’s runtime state,
including user sessions. For example, a helpdesk worker assisting a user who is having problems may ask for her username, locate her current session through a list or search function, and view relevant details about the session. Or an administrator may consult a log of recent sessions in the course of investigating a security breach. Often, this kind of monitoring and control functionality discloses the actual session token associated with each session. And often, the functionality is poorly protected, allowing unauthorized users to access the list of current session tokens, and thereby hijack the sessions of all application users.
Vulnerable Mapping of Tokens to Sessions
Various common vulnerabilities in session management mechanisms arise
because of weaknesses in how the application maps the creation and processing of session tokens to individual users’ sessions themselves.
The simplest weakness is to allow multiple valid tokens to be concurrently
assigned to the same user account. In virtually every application, there is no
legitimate reason why any user should have more than one session active at one time. Of course, it is fairly common for a user to abandon an active session and start a new one — for example, because he closes a browser window or moves to a different computer. But if a user appears to be using two different sessions simultaneously, this usually indicates that a security compromise has occurred: either the user has disclosed his credentials to another party, or an attacker has obtained his credentials through some other means. In both cases, permitting concurrent sessions is undesirable, because it allows users to persist in undesirable practices without inconvenience and because it allows an attacker to use captured credentials without risk of detection.
A related but distinct weakness is for applications to use “static” tokens.
These look like session tokens and may initially appear to function like them, but in fact they are no such thing. In these applications, each user is assigned a token, and this same token is reissued to the user every time he logs in. The application always accepts the token as valid regardless of whether the user has recently logged in and been issued with it. Applications like this really involve a misunderstanding about the whole concept of what a session is, and the benefits it provides for managing and controlling access to the application.
Sometimes, applications operate like this as a means of implementing poorly designed “remember me” functionality, and the static token is accordingly stored in a persistent cookie (see Chapter 6). Sometimes the tokens themselves are vulnerable to prediction attacks, making the vulnerability far more serious. Rather than compromising the sessions of currently logged-in users, a successful attack compromises, for all time, the accounts of all registered users.
Vulnerable Session Termination
Proper termination of sessions is important for two reasons. First, keeping the life span of a session as short as is necessary reduces the window of opportunity within which an attacker may capture, guess, or misuse a valid session token.
Second, it provides users with a means of invalidating an existing session when they no longer require it. This enables them to reduce this window further and to take some responsibility for securing their session in a shared computing environment. The main weaknesses in session termination functions involve failures to meet these two key objectives.
Some applications do not enforce effective session expiration. Once created, a session may remain valid for many days after the last request is received, before the server eventually expires the session. If tokens are vulnerable to some kind of sequencing flaw that is particularly difficult to exploit (for example, 100,000 guesses for each valid token identified), an attacker may still be able to capture the tokens of every user who has accessed the application in the recent past.
Client Exposure to Token Hijacking
An attacker can target other users of the application in an attempt to capture or misuse the victim’s session token in various ways:
- An obvious payload for cross-site scripting attacks is to query the user’s
cookies to obtain her session token, which can then be transmitted to an
arbitrary server controlled by the attacker. All the various permutations
of this attack are described in detail in Chapter 12.
- Various other attacks against users can be used to hijack the user’s session in different ways. With session fixation vulnerabilities, an attacker feeds a known session token to a user, waits for her to log in, and then hijacks her session. With cross-site request forgery attacks, an attacker makes a crafted request to an application from a web site he controls, and he exploits the fact that the user’s browser automatically submits her current cookie with this request.
Access Control Attacks
Within the application’s core security mechanisms, access controls are logically built on authentication and session management. So far, you have seen how an
application can first verify a user’s identity and then confirm that a particular sequence of requests that it receives originated from the same user. The primary reason that the application needs to do these things — in terms of security, at least — is because it needs a way to decide whether it should permit a given request to perform its attempted action or access the resources it is requesting.
Access controls are a critical defense mechanism within the application because they are responsible for making these key decisions. When they are defective, an attacker can often compromise the entire application, taking control of administrative functionality and accessing sensitive data belonging to every other user.
Access control vulnerabilities are conceptually simple: The application lets you do something you shouldn’t be able to. The differences between separate flaws really come down to the different ways in which this core defect is manifested and the different techniques you need to employ to detect it. This chapter describes all
these techniques, showing how you can exploit different kinds of behavior within an application to perform unauthorized actions and access protected data.
Common Vulnerabilities
Access controls can be divided into three broad categories: vertical, horizontal, and context-dependent.
Vertical access controls allow different types of users to access different parts of the application’s functionality. In the simplest case, this typically involves a division between ordinary users and administrators. In more complex cases, vertical access controls may involve fi ne-grained user roles granting access to specific functions, with each user being allocated to a single role, or a combination of different roles.
Horizontal access controls allow users to access a certain subset of a wider range of resources of the same type. For example, a web mail application may allow you to read your e-mail but no one else’s, an online bank may let you transfer money out of your account only, and a workflow application may allow you to update tasks assigned to you but only read tasks assigned to other people.
Context-dependent access controls ensure that users’ access is restricted to what is permitted given the current application state. For example, if a user is following multiple stages within a process, context-dependent access controls may prevent the user from accessing stages out of the prescribed order.
In many cases, vertical and horizontal access controls are intertwined. For example, an enterprise resource planning application may allow each accounts payable clerk to pay invoices for a specific organizational unit and no other. The accounts payable manager, on the other hand, may be allowed to pay invoices for any unit. Similarly, clerks may be able to pay invoices for small amounts, but larger invoices must be paid by the manager. The finance director may be able to view invoice payments and receipts for every organizational unit in the company but may not be permitted to pay any invoices.
Access controls are broken if any user can access functionality or resources for which he or she is not authorized. There are three main types of attacks against
access controls, corresponding to the three categories of controls:
- Vertical privilege escalation occurs when a user can perform functions that his assigned role does not permit him to. For example, if an ordinary user can perform administrative functions, or a clerk can pay invoices of
any size, access controls are broken.
- Horizontal privilege escalation occurs when a user can view or modify resources to which he is not entitled. For example, if you can use a web mail application to read other people’s e-mail, or if a payment clerk can process invoices for an organizational unit other than his own, access controls are broken.
- Business logic exploitation occurs when a user can exploit a flaw in the application’s state machine to gain access to a key resource. For example, a user may be able to bypass the payment step in a shopping checkout
sequence.
It is common to find cases where vulnerability in the application’s horizontal separation of privileges can lead immediately to a vertical escalation attack. For example, if a user finds a way to set a different user’s password, the user can attack an administrative account and take control of the application.
In the cases described so far, broken access controls enable users who have authenticated themselves to the application in a particular user context to perform actions or access data for which that context does not authorize them.
However, in the most serious cases of broken access control, it may be possible for completely unauthorized users to gain access to functionality or data that
is intended to be accessed only by privileged authenticated users.
Cross-Site Request Forgery (XSRF)
What is CSRF
Cross site request forgery (CSRF), also known as XSRF, Sea Surf or Session Riding, is an attack vector that tricks a web browser into executing an unwanted action in an application to which a user is logged in.
A successful CSRF attack can be devastating for both the business and user. It can result in damaged client relationships, unauthorized fund transfers, changed passwords and data theft—including stolen session cookies.
CSRFs are typically conducted using malicious social engineering, such as an email or link that tricks the victim into sending a forged request to a server. As the unsuspecting user is authenticated by their application at the time of the attack, it’s impossible to distinguish a legitimate request from a forged one.
Link:
https://www.imperva.com/learn/application-security/csrf-cross-site-request-forgery/
Cross-Site Script Inclusion (XSSI)
Cross-Site Script Inclusion (XSSI)
As shown earlier, a page hosted on a third-party web site can include a tag that sources a JavaScript document from our web site.
Cross-Domain Inclusion of Static Script
In general, this is not a problem; the tag specifically allows the inclusion of script from other domains to enable the sharing of code. For instance, our web site might serve a JavaScript library that provides DHTML pull-down menus, navigation bars, and the like, and some other web site may choose to use our script as the basis for the site’s user-navigation features. Usually, this would only happen if the owners of that second site trust us, both from a security perspective and for stability reasons (we may choose to update our script in a way that’s not compatible with their use of it).
However, if the script is generated dynamically based on a user session, we could have a security problem, as we will demonstrate in the remainder of this section.
The converse situation (our application including a third-party script resource) is dangerous if we do not have full control over the contents of that script (i.e., we fully trust
hosting it). The script will run in our page’s context and will have full access to all client-side data related to our user’s session with our application.
Cross-Site Scripting (XSS)
Cross-site scripting (XSS) is a type of computer security vulnerability typically found in web applications. XSS enables attackers to inject client-side scripts into web pages viewed by other users. A cross-site scripting vulnerability may be used by attackers to bypass access controls such as the same-origin policy. Cross-site scripting carried out on websites accounted for roughly 84% of all security vulnerabilities documented by Symantec up until 2007. In 2017, XSS was still considered a major threat vector. XSS effects vary in range from petty nuisance to significant security risk, depending on the sensitivity of the data handled by the vulnerable site and the nature of any security mitigation implemented by the site’s owner network.
Link:
https://en.wikipedia.org/wiki/Cross-site_scripting
Symmetric Key Cryptography
Symmetric-key algorithms are algorithms for cryptography that use the same cryptographic keys for both encryption of plaintext and decryption of ciphertext. The keys may be identical or there may be a simple transformation to go between the two keys. The keys, in practice, represent a shared secret between two or more parties that can be used to maintain a private information link. This requirement that both parties have access to the secret key is one of the main drawbacks of symmetric key encryption, in comparison to public-key encryption (also known as asymmetric key encryption).
Link:
https://en.wikipedia.org/wiki/Symmetric-key_algorithm
Asymmetric Key Cryptography
Public-key cryptography, or asymmetric cryptography, is a cryptographic system that uses pairs of keys: public keys which may be disseminated widely, and private keys which are known only to the owner. The generation of such keys depends on cryptographic algorithms based on mathematical problems to produce one-way functions. Effective security only requires keeping the private key private; the public key can be openly distributed without compromising security.
In such a system, any person can encrypt a message using the receiver’s public key, but that encrypted message can only be decrypted with the receiver’s private key.
Robust authentication is also possible. A sender can combine a message with a private key to create a short digital signature on the message. Anyone with the corresponding public key can combine a message, a putative digital signature on it, and the known public key to verify whether the signature was valid, i.e. made by the owner of the corresponding private key.
Public key algorithms are fundamental security ingredients in modern cryptosystems, applications and protocols assuring the confidentiality, authenticity and non-repudiability of electronic communications and data storage. They underpin various Internet standards, such as Transport Layer Security (TLS), S/MIME, PGP, and GPG. Some public key algorithms provide key distribution and secrecy (e.g., Diffie–Hellman key exchange), some provide digital signatures (e.g., Digital Signature Algorithm), and some provide both (e.g., RSA).
Link:
https://en.wikipedia.org/wiki/Public-key_cryptography