My Pentesting Space
LinkedIn
  • Welcome to Hackjiji
  • ๐Ÿ•ธ๏ธweb pentesting
    • Basics
    • Web pentest cheatsheet
    • Burpsuite and browser tricks
    • cUrl cheatsheet
    • CVE exploitation
    • JavaScript Obfuscation/Deobfuscation
  • Network pentesting
    • Basics
    • Nmap favorites
    • Host discovery
    • Port scanning
    • Network Services
      • RPC-NFC
      • WINRM - 5895-5896
      • FTP - 21
      • SMB - 445
      • RDP - 3389
      • SSH - 22
      • SMTP - 25
    • Firewall evasion
    • Pivoting and double pivoting
  • Physical pentesting
    • Bad USB - Rubber Duckies
  • Linux pentesting
    • Usefull command's
    • Privilege escalation
  • windows pentesting
    • Windows useful commands
    • Windows Reverse shell codes
    • Privilege escalation
  • Active Directory pentesting
    • Basics
    • AD
    • AAD
  • General
    • Hash cracking
    • Wordlist
    • Encoding/decoding
    • Environment setup
      • Install a new OS on seperated boot sector
      • Hyper-V
      • Virtualbox
    • Reverse-shell-cheatsheet
    • Metasploit cheatsheet
    • Vulnerability research
    • My scanning methodology
  • Events
    • HackTheBox Meetup - LFI2RCE
    • Radio Equans - QR Code Awareness campaign
    • Cybersecurity job campaign
Powered by GitBook
On this page
  • OWASP
  • OWASP cheatsheets
  • Guide for Penetration Testing OWASP Top 10 Vulnerabilities
  • Web development frameworks testing
  • HTML
  • Javascript
  • CVSS
  • HTTP headers and codes
  • Security Headers
  • General Headers
  • Entity Headers
  • Request Headers
  • Response Headers
  • Request Methods
  • Response Codes
  • Web pentest process
  • Information gathering
  • Cross Site Scripting (XSS)
  • SQL Injection (SQLi)
  • Write File Privileges
  • Mitigating SQL Injection
  • Sources
  1. web pentesting

Basics

PreviousWelcome to HackjijiNextWeb pentest cheatsheet

Last updated 4 months ago

OWASP

Open Web Application Testing Project Guide is available in this Github

At the start of each web pentest, I follow the OWASP guide to go through all possible security tests.

OWASP cheatsheets

Guide for Penetration Testing OWASP Top 10 Vulnerabilities

A01:2021 - Broken Access Control

  • Test Tool: Burp Suite

  • Command: Use Burp's Repeater to alter user roles or permissions in requests.

A02:2021 - Cryptographic Failures

  • Test Tool: OpenSSL

  • Command: openssl s_client -connect <hostname>:<port> to check SSL/TLS configuration.

A03:2021 - Injection

  • Test Tool: SQLmap

  • Command: sqlmap -u "http://example.com/page?id=1" --dbs

A04:2021 - Insecure Design

  • Test Tool: Manual code review

  • Command: N/A, engage in reviewing architecture and design patterns.

A05:2021 - Security Misconfiguration

  • Test Tool: Nmap

  • Command: nmap --script vuln <target> to detect misconfigurations.

A06:2021 - Vulnerable and Outdated Components

  • Test Tool: OWASP Dependency-Check

  • Command: dependency-check --project <proj_name> -s <source_path>

A07:2021 - Identification and Authentication Failures

  • Test Tool: Hydra

  • Command: hydra -l <username> -P <password_list> <target> http-post-form "/path:username=^USER^&password=^PASS^"

A08:2021 - Software and Data Integrity Failures

  • Test Tool: Manual review of CI/CD pipelines

  • Command: N/A, inspect integrity checks and configuration.

A09:2021 - Security Logging and Monitoring Failures

  • Test Tool: Splunk

  • Command: Analyze existing logs with specific search queries for anomalies.

A10:2021 - Server-Side Request Forgery (SSRF)

  • Test Tool: Burp Suite

  • Command: Use Burp's Intruder to manipulate URLs in requests for probable SSRF.

For more details, always refer to updated tools and methods per the latest security practices

Web development frameworks testing

To test HTML, SQL or any other web development framework, I use the W3schools resource which is great for testing and learning all different web developement frameworks:

HTML

Javascript

CVSS

A full description of all available parameters of each HTTP header is available at this site: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Strict-Transport-Security

HTTP headers and codes

Security Headers

Header

Description

Consequences If Not Implemented

Content-Security-Policy

CSP is a powerful security feature that allows you to specify domains from which resources such as scripts, styles, and images can be loaded. By strictly controlling where content can be loaded from, you can mitigate the risk of XSS (Cross-Site Scripting) attacks.

Without CSP, your application is more vulnerable to XSS attacks. An attacker could inject malicious scripts into your pages, allowing them to steal cookies, session tokens, or redirect users to malicious sites.

X-Content-Type-Options

This header prevents MIME-type sniffing by browsers. When set to nosniff, it instructs the browser to respect the content type declared in the Content-Type header.

If this header is omitted, browsers may guess the MIME type and could execute scripts that are intended to be treated as simple text. This might lead to execution of malicious code, exposing your application to attacks.

X-Frame-Options

This header protects your application from clickjacking attacks by controlling whether your site can be displayed in a frame or iframe. Setting it to DENY prevents any domain from framing your page, while SAMEORIGIN allows framing only from the same origin.

Absence of this header may allow attackers to embed your site within a malicious page, tricking users into clicking on elements they did not intend to click, potentially leading to unauthorized actions.

Strict-Transport-Security

This header ensures that browsers only connect to your website using HTTPS, thereby preventing man-in-the-middle attacks and ensuring data integrity and confidentiality. The max-age parameter specifies the duration in seconds that the browser should remember this setting.

Not using HSTS allows downgrade attacks, where a user is redirected from HTTPS to HTTP, exposing their data to eavesdropping or tampering by attackers. Sensitive information such as passwords could be intercepted.

X-XSS-Protection

This header allows you to enable (or disable) the built-in cross-site scripting filter available in most modern browsers. Setting it to 1; mode=block will block the response if an XSS attack is detected.

In the absence of this protection, browsers might not guard against XSS attacks effectively, leaving users vulnerable to attackers who can execute scripts that take control of their session or steal data.

Referrer-Policy

This header controls how much referrer information is passed to other sites when navigating away from your page. Different options allow you to limit referrer information based on conditions (e.g., origin, none).

Without this header, sensitive information (like session tokens or user identifiers) may be included in HTTP referrer headers when users navigate away, potentially exposing data to untrusted sites.

Feature-Policy (or Permissions-Policy)

This header controls which APIs and features can be used in the browser. You can enable or disable features such as geolocation, camera, and microphone for your site and for any embedded content.

Lack of control over these features could lead to unauthorized access to user devices and data. For instance, allowing access to the camera or microphone without user consent could be exploited for malicious purposes.

Access-Control-Allow-Origin

This header is part of the CORS (Cross-Origin Resource Sharing) mechanism that defines which origins can access resources on your server. Setting it to * allows all domains, while specific domains restrict access.

Omitting this header can lead to unauthorized access from other domains, exposing sensitive resources or allowing malicious websites to make requests to your server, potentially leading to data leakages.

General Headers

General headers are used in both HTTP requests and responses. They are contextual and are used to describe the message rather than its contents.

Header

Example

Description

Date

Date: Wed, 16 Feb 2022 10:38:44 GMT

Connection

Connection: close

Dictates if the current network connection should stay alive after the request finishes. Two commonly used values for this header are close and keep-alive. The close value from either the client or server means that they would like to terminate the connection, while the keep-alive header indicates that the connection should remain open to receive more data and input.


Entity Headers

Similar to general headers, Entity Headers can be common to both the request and response. These headers are used to describe the content (entity) transferred by a message. They are usually found in responses and POST or PUT requests.

Header

Example

Description

Content-Type

Content-Type: text/html

Media-Type

Media-Type: application/pdf

The media-type is similar to Content-Type, and describes the data being transferred. This header can play a crucial role in making the server interpret our input. The charset field may also be used with this header.

Boundary

boundary="b4e4fbd93540"

Acts as a marker to separate content when there is more than one in the same message. For example, within a form data, this boundary gets used as --b4e4fbd93540 to separate different parts of the form.

Content-Length

Content-Length: 385

Holds the size of the entity being passed. This header is necessary as the server uses it to read data from the message body, and is automatically generated by the browser and tools like cURL.

Content-Encoding

Content-Encoding: gzip

Data can undergo multiple transformations before being passed. For example, large amounts of data can be compressed to reduce the message size. The type of encoding being used should be specified using the Content-Encoding header.


Request Headers

The client sends Request Headers in an HTTP transaction. These headers are used in an HTTP request and do not relate to the content of the message. The following headers are commonly seen in HTTP requests.

Header

Example

Description

Host

Host: www.inlanefreight.com

Used to specify the host being queried for the resource. This can be a domain name or an IP address. HTTP servers can be configured to host different websites, which are revealed based on the hostname. This makes the host header an important enumeration target, as it can indicate the existence of other hosts on the target server.

User-Agent

User-Agent: curl/7.77.0

The User-Agent header is used to describe the client requesting resources. This header can reveal a lot about the client, such as the browser, its version, and the operating system.

Referer

Referer: http://www.inlanefreight.com/

Denotes where the current request is coming from. For example, clicking a link from Google search results would make https://google.com the referer. Trusting this header can be dangerous as it can be easily manipulated, leading to unintended consequences.

Accept

Accept: */*

The Accept header describes which media types the client can understand. It can contain multiple media types separated by commas. The */* value signifies that all media types are accepted.

Cookie

Cookie: PHPSESSID=b4e4fbd93540

Authorization

Authorization: BASIC cGFzc3dvcmQK

Another method for the server to identify clients. After successful authentication, the server returns a token unique to the client. Unlike cookies, tokens are stored only on the client-side and retrieved by the server per request. There are multiple types of authentication types based on the webserver and application type used.

A complete list of request headers and their usage can be found here.


Response Headers

Response Headers can be used in an HTTP response and do not relate to the content. Certain response headers such as Age, Location, and Server are used to provide more context about the response. The following headers are commonly seen in HTTP responses.

Header

Example

Description

Server

Server: Apache/2.2.14 (Win32)

Contains information about the HTTP server, which processed the request. It can be used to gain information about the server, such as its version, and enumerate it further.

Set-Cookie

Set-Cookie: PHPSESSID=b4e4fbd93540

Contains the cookies needed for client identification. Browsers parse the cookies and store them for future requests. This header follows the same format as the Cookie request header.

WWW-Authenticate

WWW-Authenticate: BASIC realm="localhost"

Notifies the client about the type of authentication required to access the requested resource.

Request Methods

The following are some of the commonly used methods:

Method

Description

GET

Requests a specific resource. Additional data can be passed to the server via query strings in the URL (e.g. ?param=value).

POST

Sends data to the server. It can handle multiple types of input, such as text, PDFs, and other forms of binary data. This data is appended in the request body present after the headers. The POST method is commonly used when sending information (e.g. forms/logins) or uploading data to a website, such as images or documents.

HEAD

Requests the headers that would be returned if a GET request was made to the server. It doesn't return the request body and is usually made to check the response length before downloading resources.

PUT

Creates new resources on the server. Allowing this method without proper controls can lead to uploading malicious resources.

DELETE

Deletes an existing resource on the webserver. If not properly secured, can lead to Denial of Service (DoS) by deleting critical files on the web server.

OPTIONS

Returns information about the server, such as the methods accepted by it.

PATCH

Applies partial modifications to the resource at the specified location.

The list only highlights a few of the most commonly used HTTP methods. The availability of a particular method depends on the server as well as the application configuration. For a full list of HTTP methods, you can visit this link.

Response Codes

HTTP status codes are used to tell the client the status of their request. An HTTP server can return five types of response codes:

Type

Description

1xx

Provides information and does not affect the processing of the request.

2xx

Returned when a request succeeds.

3xx

Returned when the server redirects the client.

4xx

Signifies improper requests from the client. For example, requesting a resource that doesn't exist or requesting a bad format.

5xx

Returned when there is some problem with the HTTP server itself.

The following are some of the commonly seen examples from each of the above HTTP method types:

Code

Description

200 OK

Returned on a successful request, and the response body usually contains the requested resource.

302 Found

Redirects the client to another URL. For example, redirecting the user to their dashboard after a successful login.

400 Bad Request

Returned on encountering malformed requests such as requests with missing line terminators.

403 Forbidden

Signifies that the client doesn't have appropriate access to the resource. It can also be returned when the server detects malicious input from the user.

404 Not Found

Returned when the client requests a resource that doesn't exist on the server.

500 Internal Server Error

Returned when the server cannot process the request.

For a full list of standard HTTP response codes, you can visit this link. Apart from the standard HTTP codes, various servers and providers such as Cloudflare or AWS implement their own codes.

Web pentest process

Information gathering

The primary goals of web reconnaissance include:

  • Identifying Assets: Uncovering all publicly accessible components of the target, such as web pages, subdomains, IP addresses, and technologies used. This step provides a comprehensive overview of the target's online presence.

  • Discovering Hidden Information: Locating sensitive information that might be inadvertently exposed, including backup files, configuration files, or internal documentation. These findings can reveal valuable insights and potential entry points for attacks.

  • Analysing the Attack Surface: Examining the target's attack surface to identify potential vulnerabilities and weaknesses. This involves assessing the technologies used, configurations, and possible entry points for exploitation.

  • Gathering Intelligence: Collecting information that can be leveraged for further exploitation or social engineering attacks. This includes identifying key personnel, email addresses, or patterns of behaviour that could be exploited.

Active Reconnaissance

In active reconnaissance, the attacker directly interacts with the target system to gather information. This interaction can take various forms:

Technique
Description
Example
Tools
Risk of Detection

Port Scanning

Identifying open ports and services running on the target.

Using Nmap to scan a web server for open ports like 80 (HTTP) and 443 (HTTPS).

Nmap, Masscan, Unicornscan

High: Direct interaction with the target can trigger intrusion detection systems (IDS) and firewalls.

Vulnerability Scanning

Probing the target for known vulnerabilities, such as outdated software or misconfigurations.

Running Nessus against a web application to check for SQL injection flaws or cross-site scripting (XSS) vulnerabilities.

Nessus, OpenVAS, Nikto

High: Vulnerability scanners send exploit payloads that security solutions can detect.

Network Mapping

Mapping the target's network topology, including connected devices and their relationships.

Using traceroute to determine the path packets take to reach the target server, revealing potential network hops and infrastructure.

Traceroute, Nmap

Medium to High: Excessive or unusual network traffic can raise suspicion.

Banner Grabbing

Retrieving information from banners displayed by services running on the target.

Connecting to a web server on port 80 and examining the HTTP banner to identify the web server software and version.

Netcat, curl

Low: Banner grabbing typically involves minimal interaction but can still be logged.

OS Fingerprinting

Identifying the operating system running on the target.

Using Nmap's OS detection capabilities (-O) to determine if the target is running Windows, Linux, or another OS.

Nmap, Xprobe2

Low: OS fingerprinting is usually passive, but some advanced techniques can be detected.

Service Enumeration

Determining the specific versions of services running on open ports.

Using Nmap's service version detection (-sV) to determine if a web server is running Apache 2.4.50 or Nginx 1.18.0.

Nmap

Low: Similar to banner grabbing, service enumeration can be logged but is less likely to trigger alerts.

Web Spidering

Crawling the target website to identify web pages, directories, and files.

Running a web crawler like Burp Suite Spider or OWASP ZAP Spider to map out the structure of a website and discover hidden resources.

Burp Suite Spider, OWASP ZAP Spider, Scrapy (customisable)

Low to Medium: Can be detected if the crawler's behaviour is not carefully configured to mimic legitimate traffic.

Passive Reconnaissance

In contrast, passive reconnaissance involves gathering information about the target without directly interacting with it. This relies on analysing publicly available information and resources, such as:

Technique
Description
Example
Tools
Risk of Detection

Search Engine Queries

Utilising search engines to uncover information about the target, including websites, social media profiles, and news articles.

Searching Google for "[Target Name] employees" to find employee information or social media profiles.

Google, DuckDuckGo, Bing, and specialised search engines (e.g., Shodan)

Very Low: Search engine queries are normal internet activity and unlikely to trigger alerts.

WHOIS Lookups

Querying WHOIS databases to retrieve domain registration details.

Performing a WHOIS lookup on a target domain to find the registrant's name, contact information, and name servers.

whois command-line tool, online WHOIS lookup services

Very Low: WHOIS queries are legitimate and do not raise suspicion.

DNS

Analysing DNS records to identify subdomains, mail servers, and other infrastructure.

Using dig to enumerate subdomains of a target domain.

dig, nslookup, host, dnsenum, fierce, dnsrecon

Very Low: DNS queries are essential for internet browsing and are not typically flagged as suspicious.

Web Archive Analysis

Examining historical snapshots of the target's website to identify changes, vulnerabilities, or hidden information.

Using the Wayback Machine to view past versions of a target website to see how it has changed over time.

Wayback Machine

Very Low: Accessing archived versions of websites is a normal activity.

Social Media Analysis

Gathering information from social media platforms like LinkedIn, Twitter, or Facebook.

Searching LinkedIn for employees of a target organisation to learn about their roles, responsibilities, and potential social engineering targets.

LinkedIn, Twitter, Facebook, specialised OSINT tools

Very Low: Accessing public social media profiles is not considered intrusive.

Code Repositories

Analysing publicly accessible code repositories like GitHub for exposed credentials or vulnerabilities.

Searching GitHub for code snippets or repositories related to the target that might contain sensitive information or code vulnerabilities.

GitHub, GitLab

Very Low: Code repositories are meant for public access, and searching them is not suspicious.

DNS

It's Like a Relay Race

Think of the DNS process as a relay race. Your computer starts with the domain name and passes it along to the resolver. The resolver then passes the request to the root server, the TLD server, and finally, the authoritative server, each one getting closer to the destination. Once the IP address is found, it's relayed back down the chain to your computer, allowing you to access the website.

DNS records

Record Type
Full Name
Description
Zone File Example

A

Address Record

Maps a hostname to its IPv4 address.

www.example.com. IN A 192.0.2.1

AAAA

IPv6 Address Record

Maps a hostname to its IPv6 address.

www.example.com. IN AAAA 2001:db8:85a3::8a2e:370:7334

CNAME

Canonical Name Record

Creates an alias for a hostname, pointing it to another hostname.

blog.example.com. IN CNAME webserver.example.net.

MX

Mail Exchange Record

Specifies the mail server(s) responsible for handling email for the domain.

example.com. IN MX 10 mail.example.com.

NS

Name Server Record

Delegates a DNS zone to a specific authoritative name server.

example.com. IN NS ns1.example.com.

TXT

Text Record

Stores arbitrary text information, often used for domain verification or security policies.

example.com. IN TXT "v=spf1 mx -all" (SPF record)

SOA

Start of Authority Record

Specifies administrative information about a DNS zone, including the primary name server, responsible person's email, and other parameters.

example.com. IN SOA ns1.example.com. admin.example.com. 2024060301 10800 3600 604800 86400

SRV

Service Record

Defines the hostname and port number for specific services.

_sip._udp.example.com. IN SRV 10 5 5060 sipserver.example.com.

PTR

Pointer Record

Used for reverse DNS lookups, mapping an IP address to a hostname.

1.2.0.192.in-addr.arpa. IN PTR www.example.com.

WHOIS

WHOIS is a widely used query and response protocol designed to access databases that store information about registered internet resources. Primarily associated with domain names, WHOIS can also provide details about IP address blocks and autonomous systems. Think of it as a giant phonebook for the internet, letting you look up who owns or is responsible for various online assets.

https://whoisfreaks.com/ can reveal changes in ownership, contact information, or technical details over time. This can be useful for tracking the evolution of the target's digital presence.

Each WHOIS record typically contains the following information:

  • Domain Name: The domain name itself (e.g., example.com)

  • Registrar: The company where the domain was registered (e.g., GoDaddy, Namecheap)

  • Registrant Contact: The person or organization that registered the domain.

  • Administrative Contact: The person responsible for managing the domain.

  • Technical Contact: The person handling technical issues related to the domain.

  • Creation and Expiration Dates: When the domain was registered and when it's set to expire.

  • Name Servers: Servers that translate the domain name into an IP address.

Let's consider three scenarios to help illustrate the value of WHOIS data.

  1. Scenario 1: Phishing Investigation

An email security gateway flags a suspicious email sent to multiple employees within a company. The email claims to be from the company's bank and urges recipients to click on a link to update their account information. A security analyst investigates the email and begins by performing a WHOIS lookup on the domain linked in the email.

The WHOIS record reveals the following:

  • Registration Date: The domain was registered just a few days ago.

  • Registrant: The registrant's information is hidden behind a privacy service.

  • Name Servers: The name servers are associated with a known bulletproof hosting provider often used for malicious activities.

This combination of factors raises significant red flags for the analyst. The recent registration date, hidden registrant information, and suspicious hosting strongly suggest a phishing campaign. The analyst promptly alerts the company's IT department to block the domain and warns employees about the scam.

Further investigation into the hosting provider and associated IP addresses may uncover additional phishing domains or infrastructure the threat actor uses.

  1. Scenario 2: Malware Analysis

A security researcher is analysing a new strain of malware that has infected several systems within a network. The malware communicates with a remote server to receive commands and exfiltrate stolen data. To gain insights into the threat actor's infrastructure, the researcher performs a WHOIS lookup on the domain associated with the command-and-control (C2) server.

The WHOIS record reveals:

  • Registrant: The domain is registered to an individual using a free email service known for anonymity.

  • Location: The registrant's address is in a country with a high prevalence of cybercrime.

  • Registrar: The domain was registered through a registrar with a history of lax abuse policies.

Based on this information, the researcher concludes that the C2 server is likely hosted on a compromised or "bulletproof" server. The researcher then uses the WHOIS data to identify the hosting provider and notify them of the malicious activity.

  1. Scenario 3: Threat Intelligence Report

A cybersecurity firm tracks the activities of a sophisticated threat actor group known for targeting financial institutions. Analysts gather WHOIS data on multiple domains associated with the group's past campaigns to compile a comprehensive threat intelligence report.

By analysing the WHOIS records, analysts uncover the following patterns:

  • Registration Dates: The domains were registered in clusters, often shortly before major attacks.

  • Registrants: The registrants use various aliases and fake identities.

  • Name Servers: The domains often share the same name servers, suggesting a common infrastructure.

  • Takedown History: Many domains have been taken down after attacks, indicating previous law enforcement or security interventions.

These insights allow analysts to create a detailed profile of the threat actor's tactics, techniques, and procedures (TTPs). The report includes indicators of compromise (IOCs) based on the WHOIS data, which other organisations can use to detect and block future attacks.

Web Archives

Web archives are digital repositories that store snapshots of websites across time, providing a historical record of their evolution. Among these archives, the Wayback Machine is the most comprehensive and accessible resource for web reconnaissance.

The Wayback Machine, a project by the Internet Archive, has been archiving the web for over two decades, capturing billions of web pages from across the globe. This massive historical data collection can be an invaluable resource for security researchers and investigators.

Feature
Description
Use Case in Reconnaissance

Historical Snapshots

View past versions of websites, including pages, content, and design changes.

Identify past website content or functionality that is no longer available.

Hidden Directories

Explore directories and files that may have been removed or hidden from the current version of the website.

Discover sensitive information or backups that were inadvertently left accessible in previous versions.

Content Changes

Track changes in website content, including text, images, and links.

Identify patterns in content updates and assess the evolution of a website's security posture.

By leveraging the Wayback Machine, you can gain a historical perspective on your target's online presence, potentially revealing vulnerabilities that may have been overlooked in the current version of the website.

Cross Site Scripting (XSS)

Cross Site Scripting (XSS) is a web application vulnerability that allows attackers to inject malicious scripts into content that is served to users. This typically occurs in the context of a web page, enabling scripts to be executed in the user's web browser.

Key Points:

  • Injection of JavaScript: As you mentioned, the vulnerability allows malicious JavaScript to be executed on the client-side, compromising user data and session integrity.

  • Lack of Sanitization: XSS vulnerabilities arise when there is insufficient sanitization or validation of user inputs at both the frontend and backend levels.

Types of Cross Site Scripting

  1. DOM-based XSS:

    • This type occurs when the client-side JavaScript modifies the Document Object Model (DOM) of a web page. The malicious script is typically executed as a result of changes made to the DOM based on user input. It does not involve sending data to the server; rather, it relies on the manipulation of the client-side page.

  2. Reflected XSS:

    • Reflected XSS happens when the malicious script is included in a URL (via query parameters) or in the headers and is reflected back from the server. To exploit this, the attacker must craft a link that contains the malicious script and trick the user into clicking it. The script is not stored; it is executed immediately when the user accesses the crafted URL.

  3. Stored XSS:

    • Stored XSS (or Persistent XSS) is indeed considered the most dangerous form of XSS. In this case, the malicious script is stored on the server (such as in a database) and is delivered to users in the context of a web page they are accessing. Since the script is saved on the server, multiple users can be affected simply by visiting the compromised page.

Prevention Measures

  • Front-end Prevention:

    • Input Validation: Ensure valid data is submitted, such as validating email formats with JavaScript.

      function validateEmail(email) {
          const re = /^(([^<>()[\]\\.,;:\s@\"]+(\.[^<>()[\]\\.,;:\s@\"]+)*)|(\".+\"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/;
          return re.test($("#login input[name=email]").val());
      }
  • input Sanitization: Use libraries like DOMPurify to sanitize user input, escaping special characters.

let clean = DOMPurify.sanitize(dirty);
  • Avoid Direct Input Usage: Never use user input directly in HTML tags or certain JavaScript and jQuery functions that can execute scripts.

  • Back-end Prevention:

    • Similar input validation is required on the back-end to prevent Stored and Reflected XSS.

    • Input Validation Example (PHP):

      if (filter_var($_GET['email'], FILTER_VALIDATE_EMAIL)) {
          // do task
      } else {
          // reject input - do not display it
      }

Input Sanitization Example (PHP):

addslashes($_GET['email']);

Back-end libraries like DOMPurify can also be utilized for sanitization:

import DOMPurify from 'dompurify';
var clean = DOMPurify.sanitize(dirty);

Output HTML Encoding:

  • Convert special characters to HTML codes when displaying user input to prevent injections.

  • Encoding Example (PHP):

    htmlentities($_GET['email']);

Encoding Example (NodeJS):

import encode from 'html-entities';
encode('<'); // -> '<'
  • Server Configuration:

    • Configure web servers to use HTTPS, set XSS prevention headers, and implement Content Security Policy (CSP) to restrict script sources.

    • Consider using a Web Application Firewall (WAF) for enhanced security.

  • Direct input

We should always ensure that we never use user input directly within certain HTML tags, like:

  1. JavaScript code <script></script>

  2. CSS Style Code <style></style>

  3. Tag/Attribute Fields <div name='INPUT'></div>

  4. HTML Comments <!-- -->

If user input goes into any of the above examples, it can inject malicious JavaScript code, which may lead to an XSS vulnerability. In addition to this, we should avoid using JavaScript functions that allow changing raw text of HTML fields, like:

  • DOM.innerHTML

  • DOM.outerHTML

  • document.write()

  • document.writeln()

  • document.domain

And the following jQuery functions:

  • html()

  • parseHTML()

  • add()

  • append()

  • prepend()

  • after()

  • insertAfter()

  • before()

  • insertBefore()

  • replaceAll()

  • replaceWith()

SQL Injection (SQLi)

A SQL injection occurs when a malicious user attempts to pass input that changes the final SQL query sent by the web application to the database, enabling the user to perform other unintended SQL queries directly against the database.

First, the attacker has to inject code outside the expected user input limits, so it does not get executed as simple user input. In the most basic case, this is done by injecting a single quote (') or a double quote (") to escape the limits of user input and inject data directly into the SQL query.

Once an attacker can inject, they have to look for a way to execute a different SQL query. This can be done using SQL code to make up a working query that executes both the intended and the new SQL queries. There are many ways to achieve this, like using stacked queries or using Union queriesCode:

Vulnerable PHP example code

$searchInput =  $_POST['findUser'];
$query = "select * from logins where username like '%$searchInput'";
$result = $conn->query($query);

In typical cases, the searchInput would be inputted to complete the query, returning the expected outcome. Any input we type goes into the following SQL query:

Code: sql

select * from logins where username like '%$searchInput'

So, if we input admin, it becomes '%admin'. In this case, if we write any SQL code, it would just be considered as a search term. For example, if we input SHOW DATABASES;, it would be executed as '%SHOW DATABASES;' The web application will search for usernames similar to SHOW DATABASES;. However, as there is no sanitization, in this case, we can add a single quote ('), which will end the user-input field, and after it, we can write actual SQL code. For example, if we search for 1'; DROP TABLE users;, the search input would be:

Code: php

'%1'; DROP TABLE users;'

Notice how we added a single quote (') after "1", in order to escape the bounds of the user-input in ('%$searchInput').

So, the final SQL query executed would be as follows:

Code: sql

select * from logins where username like '%1'; DROP TABLE users;'

As we can see from the syntax highlighting, we can escape the original query's bounds and have our newly injected query execute as well. Once the query is run, the users table will get deleted.

Note: In the above example, for the sake of simplicity, we added another SQL query after a semi-colon (;). Though this is actually not possible with MySQL, it is possible with MSSQL and PostgreSQL. In the coming sections, we'll discuss the real methods of injecting SQL queries in MySQL.

the MySQL documentation for operation precedence states that the AND operator would be evaluated before the OR operator. This means that if there is at least one TRUE condition in the entire query along with an OR operator, the entire query will evaluate to TRUE since the OR operator returns TRUE if one of its operands is TRUE.

An example of a condition that will always return true is '1'='1'. However, to keep the SQL query working and keep an even number of quotes, instead of using ('1'='1'), we will remove the last quote and use ('1'='1), so the remaining single quote from the original query would be in its place.

So, if we inject the below condition and have an OR operator between it and the original condition, it should always return true:

Code: sql

admin' or '1'='1

The final query should be as follow:

Code: sql

SELECT * FROM logins WHERE username='admin' or '1'='1' AND password = 'something';

This means the following:

  • If username is admin OR

  • If 1=1 return true 'which always returns true' AND

  • If password is something

The AND operator will be evaluated first, and it will return false. Then, the OR operator would be evalutated, and if either of the statements is true, it would return true. Since 1=1 always returns true, this query will return true, and it will grant us access.

Write File Privileges

To be able to write files to the back-end server using a MySQL database, we require three things:

  1. User with FILE privilege enabled

  2. MySQL global secure_file_priv variable not enabled

  3. Write access to the location we want to write to on the back-end server

Secure_file_priv

The secure_file_priv variable is used to determine where to read/write files from. An empty value lets us read files from the entire file system. Otherwise, if a certain directory is set, we can only read from the folder specified by the variable. On the other hand, NULL means we cannot read/write from any directory. MariaDB has this variable set to empty by default, which lets us read/write to any file if the user has the FILE privilege. However, MySQL uses /var/lib/mysql-files as the default folder. This means that reading files through a MySQL injection isn't possible with default settings. Even worse, some modern configurations default to NULL, meaning that we cannot read/write files anywhere within the system.

Within MySQL, we can use the following query to obtain the value of this variable:

SHOW VARIABLES LIKE 'secure_file_priv';

Mitigating SQL Injection


We have learned about SQL injections, why they occur, and how we can exploit them. We should also learn how to avoid these types of vulnerabilities in our code and patch them when found. Let's look at some examples of how SQL Injection can be mitigated.


Input Sanitization

Here's the snippet of the code from the authentication bypass section we discussed earlier:

Code: php

<SNIP>
  $username = $_POST['username'];
  $password = $_POST['password'];

  $query = "SELECT * FROM logins WHERE username='". $username. "' AND password = '" . $password . "';" ;
  echo "Executing query: " . $query . "<br /><br />";

  if (!mysqli_query($conn ,$query))
  {
          die('Error: ' . mysqli_error($conn));
  }

  $result = mysqli_query($conn, $query);
  $row = mysqli_fetch_array($result);
<SNIP>

As we can see, the script takes in the username and password from the POST request and passes it to the query directly. This will let an attacker inject anything they wish and exploit the application. Injection can be avoided by sanitizing any user input, rendering injected queries useless. Libraries provide multiple functions to achieve this, one such example is the mysqli_real_escape_string() function. This function escapes characters such as ' and ", so they don't hold any special meaning.

Code: php

<SNIP>
$username = mysqli_real_escape_string($conn, $_POST['username']);
$password = mysqli_real_escape_string($conn, $_POST['password']);

$query = "SELECT * FROM logins WHERE username='". $username. "' AND password = '" . $password . "';" ;
echo "Executing query: " . $query . "<br /><br />";
<SNIP>

The snippet above shows how the function can be used.

As expected, the injection no longer works due to escaping the single quotes. A similar example is the pg_escape_string() which used to escape PostgreSQL queries.


Input Validation

User input can also be validated based on the data used to query to ensure that it matches the expected input. For example, when taking an email as input, we can validate that the input is in the form of ...@email.com, and so on.

Consider the following code snippet from the ports page, which we used UNION injections on:

Code: php

<?php
if (isset($_GET["port_code"])) {
	$q = "Select * from ports where port_code ilike '%" . $_GET["port_code"] . "%'";
	$result = pg_query($conn,$q);
    
	if (!$result)
	{
   		die("</table></div><p style='font-size: 15px;'>" . pg_last_error($conn). "</p>");
	}
<SNIP>
?>

We see the GET parameter port_code being used in the query directly. It's already known that a port code consists only of letters or spaces. We can restrict the user input to only these characters, which will prevent the injection of queries. A regular expression can be used for validating the input:

Code: php

<SNIP>
$pattern = "/^[A-Za-z\s]+$/";
$code = $_GET["port_code"];

if(!preg_match($pattern, $code)) {
  die("</table></div><p style='font-size: 15px;'>Invalid input! Please try again.</p>");
}

$q = "Select * from ports where port_code ilike '%" . $code . "%'";
<SNIP>

The code is modified to use the preg_match() function, which checks if the input matches the given pattern or not. The pattern used is [A-Za-z\s]+, which will only match strings containing letters and spaces. Any other character will result in the termination of the script.

We can test the following injection:

Code: sql

'; SELECT 1,2,3,4-- -

As seen in the images above, input with injected queries was rejected by the server.


User Privileges

As discussed initially, DBMS software allows the creation of users with fine-grained permissions. We should ensure that the user querying the database only has minimum permissions.

Superusers and users with administrative privileges should never be used with web applications. These accounts have access to functions and features, which could lead to server compromise.

Mitigating SQL Injection

MariaDB [(none)]> CREATE USER 'reader'@'localhost';

Query OK, 0 rows affected (0.002 sec)


MariaDB [(none)]> GRANT SELECT ON ilfreight.ports TO 'reader'@'localhost' IDENTIFIED BY 'p@ssw0Rd!!';

Query OK, 0 rows affected (0.000 sec)

The commands above add a new MariaDB user named reader who is granted only SELECT privileges on the ports table. We can verify the permissions for this user by logging in:

Mitigating SQL Injection

HackJiji@htb[/htb]$ mysql -u reader -p

MariaDB [(none)]> use ilfreight;
MariaDB [ilfreight]> SHOW TABLES;

+---------------------+
| Tables_in_ilfreight |
+---------------------+
| ports               |
+---------------------+
1 row in set (0.000 sec)


MariaDB [ilfreight]> SELECT SCHEMA_NAME FROM INFORMATION_SCHEMA.SCHEMATA;

+--------------------+
| SCHEMA_NAME        |
+--------------------+
| information_schema |
| ilfreight          |
+--------------------+
2 rows in set (0.000 sec)


MariaDB [ilfreight]> SELECT * FROM ilfreight.credentials;
ERROR 1142 (42000): SELECT command denied to user 'reader'@'localhost' for table 'credentials'

The snippet above confirms that the reader user cannot query other tables in the ilfreight database. The user only has access to the ports table that is needed by the application.


Web Application Firewall

Web Application Firewalls (WAF) are used to detect malicious input and reject any HTTP requests containing them. This helps in preventing SQL Injection even when the application logic is flawed. WAFs can be open-source (ModSecurity) or premium (Cloudflare). Most of them have default rules configured based on common web attacks. For example, any request containing the string INFORMATION_SCHEMA would be rejected, as it's commonly used while exploiting SQL injection.


Parameterized Queries

Another way to ensure that the input is safely sanitized is by using parameterized queries. Parameterized queries contain placeholders for the input data, which is then escaped and passed on by the drivers. Instead of directly passing the data into the SQL query, we use placeholders and then fill them with PHP functions.

Consider the following modified code:

Code: php

<SNIP>
  $username = $_POST['username'];
  $password = $_POST['password'];

  $query = "SELECT * FROM logins WHERE username=? AND password = ?" ;
  $stmt = mysqli_prepare($conn, $query);
  mysqli_stmt_bind_param($stmt, 'ss', $username, $password);
  mysqli_stmt_execute($stmt);
  $result = mysqli_stmt_get_result($stmt);

  $row = mysqli_fetch_array($result);
  mysqli_stmt_close($stmt);
<SNIP>

The query is modified to contain two placeholders, marked with ? where the username and password will be placed. We then bind the username and password to the query using the mysqli_stmt_bind_param() function. This will safely escape any quotes and place the values in the query.

Sources

HackTheBox Academy

Holds the date and time at which the message originated. It's preferred to convert the time to the standard time zone.

Used to describe the type of resource being transferred. The value is automatically added by the browsers on the client-side and returned in the server response. The charset field denotes the encoding standard, such as .

Contains cookie-value pairs in the format name=value. A is a piece of data stored on the client-side and on the server, which acts as an identifier. These are passed to the server per request, thus maintaining the client's access. Cookies can also serve other purposes, such as saving user preferences or session tracking. There can be multiple cookies in a single header separated by a semi-colon.

For practical use cases regarding Information Gathering process refer to

For practical uses cases regarding Cross Site Scripting, refer to the page

Query result is true leading to auth bypass
mysqli_escape

๐Ÿ•ธ๏ธ
UTC
UTF-8
cookie
๐Ÿ‘
wstg/document/4-Web_Application_Security_Testing at master ยท OWASP/wstgGitHub
DOM Clobbering Prevention - OWASP Cheat Sheet Series
CSS Text Alignment and Text Direction
Logo
CSS Animations
JavaScript Tutorial
SQL Tryit Editor v1.6
W3Schools online HTML editor
JSFiddle - Code Playground
Logo
Logo
Logo
Information Gathering
Cross Site Scripting (XSS)
Logo
Logo
Logo
Logo
SQLi types
Failed because the query result is FALSE as tehe username "NotAdmin" does not exist