Current situation: PHP2Shell. Two critical PHP vulnerabilities (CVSS 9.2) allow malicious code without login. Patches since 21 October 2026.What to do now →

CGI and FastCGI: The Basics

CGI starts a process for every request, FastCGI keeps processes alive. What that means for PHP, php-cgi and PHP-FPM and which settings affect security.

Last updated 4 min readPHP knowledge

In short: CGI (Common Gateway Interface) is an old interface in which the web server starts a new program for every request; for PHP, that program is php-cgi. FastCGI is the further development: PHP processes run permanently and accept many requests over a socket. PHP-FPM is the most important FastCGI implementation for PHP. What matters most for security are the cgi.* settings and the rule that a FastCGI endpoint must never be publicly reachable.

What is CGI?

CGI is one of the oldest methods by which web servers generate dynamic content. For the setting cgi.rfc2616_headers, the PHP manual refers to RFC 3875, the specification of the Common Gateway Interface. The beginnings of PHP were also CGI programs: in 1994 Rasmus Lerdorf wrote the first "Personal Home Page Tools" as CGI binaries in C.

The principle: for every request, the web server starts a new process, passes request data via environment variables and standard input, and reads the response from standard output. The process then ends. According to the PHP manual, with CGI and CLI PHP re-reads its php.ini on every call, with server modules only at startup.

This makes CGI robust, because every request begins with a fresh process. But it also makes CGI slow: starting the process, loading the configuration and initialising extensions cost time on every request.

What is FastCGI?

FastCGI solves the performance problem by keeping processes alive. The web server connects via a Unix socket or a TCP port to a running process and sends it the request in the FastCGI protocol. The process handles it and waits for the next one.

Feature CGI FastCGI with php-cgi FastCGI with PHP-FPM
Process per request yes no no
SAPI name cgi-fcgi cgi-fcgi fpm-fcgi
Pools with their own user no no yes
Process control web server web server module, e.g. mod_fcgid own master process
.user.ini is read yes yes yes

According to the manual, PHP-FPM is PHP's primary FastCGI implementation. It adds process management, pools, status pages and a slowlog to the protocol. The details are under PHP-FPM explained.

The cgi settings in php.ini

PHP has its own settings for CGI operation. The following values and descriptions come from the PHP manual:

  1. cgi.force_redirect (default 1, INI_SYSTEM): according to the manual, necessary to run PHP as CGI securely under most web servers. Turn off only "at your own risk"; under IIS it must be off.
  2. cgi.fix_pathinfo (default 1, INI_SYSTEM): ensures correct PATH_INFO and PATH_TRANSLATED values. Scripts should use SCRIPT_FILENAME instead of PATH_TRANSLATED.
  3. cgi.discard_path (default 0, INI_SYSTEM): allows the CGI binary to be placed safely outside the web directory without .htaccess protection being bypassed.
  4. fastcgi.impersonate (default 0, INI_SYSTEM): relevant only for IIS on Windows.
  5. user_ini.filename and user_ini.cache_ttl (default .user.ini and 300 seconds): control whether and how often PHP reads .user.ini files.

With Nginx, a clean handover of the script path is part of this. A readable basic pattern, with no guarantee for every environment:

location ~ \.php$ {
    try_files $uri =404;               # pass only existing files to PHP
    fastcgi_pass unix:/run/php/php8.3-fpm.sock;
    fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
    include fastcgi_params;
}

The line try_files $uri =404; prevents requests for non-existent .php paths from being passed on to PHP.

Why an open FastCGI endpoint is dangerous

The PHP manual warns explicitly: anyone who can open a FastCGI connection to PHP controls the configuration of the request, for example auto_prepend_file, and can thereby execute arbitrary code. The reason is that web servers may send PHP settings along via FastCGI parameters such as PHP_VALUE and PHP_ADMIN_VALUE.

Clear rules follow:

  • Connect PHP-FPM or php-cgi in FastCGI mode only via a Unix socket if the web server runs on the same host.
  • With TCP, set listen.allowed_clients and block the port in the firewall; notes on this are in the article Firewall for web servers.
  • Keep socket permissions tight with listen.owner, listen.group and listen.mode.
Important

Use ss -lntp | grep -i php to check whether a PHP process is listening on a TCP address. A binding to 0.0.0.0 or a public address is a case for urgent action.

CGI, FastCGI and PHP2Shell

Both php-cgi and PHP-FPM are affected by PHP2Shell. For both the same applies: update to 8.5.12, 8.4.27, 8.3.36 or 8.2.35, or a confirmed backport, then stop and restart all running PHP processes. In FastCGI setups with php-cgi, processes often keep running unnoticed because no dedicated service manages them. How to find and replace this legacy setup is described under php-cgi: a legacy setup with risk. In Plesk the variants are named differently; Plesk: understanding PHP handlers helps.

How does PHP SOS help?

  • Record handlers: We determine whether your websites run via CGI, FastCGI with php-cgi or PHP-FPM.
  • Close endpoints: We check sockets, ports and firewall rules so that no FastCGI endpoint is reachable from outside.
  • Patch and clean up: We update PHP and end all old processes, including orphaned php-cgi instances.
  • Replace: As part of server hardening we replace CGI legacy setups with PHP-FPM with separate pools.

Frequently asked questions

Is FastCGI the same as PHP-FPM?

No. FastCGI is a protocol through which a web server talks to an application process. PHP-FPM is a program that implements this protocol for PHP and manages the processes. php-cgi can also speak FastCGI but offers no pools.

Why is plain CGI considered outdated?

With CGI, the web server starts a new process for every request, and PHP reads its configuration each time. This costs time and resources. FastCGI and PHP-FPM keep processes permanently ready and are therefore significantly more efficient.

What is a .user.ini?

A .user.ini is a small configuration file in a web directory. According to the PHP manual, it is read only by the CGI and FastCGI SAPIs, which includes PHP-FPM. It may only contain settings with the modes INI_PERDIR, INI_USER or INI_ALL.

How do I tell whether php-cgi is running on my server?

Use read-only commands such as ps or pgrep to look for processes named php-cgi, and look in the web server configuration for entries such as mod_fcgid, Action or ScriptAlias with php-cgi. In hosting panels the operating mode is often called CGI or FastCGI application.

Sources

Immediate contact

Every hour counts. Write to us now.

Briefly describe your system, PHP version and observation. We will get back to you, clarify the situation and work remotely until the incident is closed and documented.

Immediate help