Aktuellt läge: PHP2Shell. Två kritiska PHP-sårbarheter (CVSS 9,2) tillåter skadlig kod utan inloggning. Patchar sedan den 21 oktober 2026.Vad som bör göras nu →

php_admin_value: spärra inställningar mot överskrivning

En säkerhetsinställning hjälper föga om applikationen ändrar den igen med en kodrad. Med php_admin_value och php_admin_flag fastställer ni värden för PHP-FPM och Apache bindande.

Aktualitet 5 min läsningHärdning och konfiguration

Kort sagt: php_admin_value och php_admin_flag sätter PHP-inställningar i PHP-FPM-poolen eller i Apache-konfigurationen så att applikationer varken kan ändra dem via ini_set() eller via .htaccess. php.net kräver just detta för PHP2Shell-övergångsåtgärderna, till exempel för memory_limit=-1. Efter att ha satt dem måste tjänsten startas om, och värdet bör kontrolleras i webbkontexten.

Varför ”satt” inte betyder ”spärrat”

Under dagarna efter den 21 oktober 2026 skrev många administratörer in php.nets övergångsåtgärder i sin php.ini. En detalj i rekommendationen försvann då ofta: memory_limit=-1 ska sättas så att applikationer inte kan skriva över det. php.net nämner uttryckligen php_admin_value i FPM-poolen eller i Apache-konfigurationen för det.

Skälet är enkelt. Många CMS, butiker och ramverk sätter egna värden, till exempel en högre minnesgräns för importer. Står värdet bara i php.ini skriver applikationen över det vid nästa anrop. Skyddsåtgärden finns då på papperet men inte i den pågående processen.

Det berör inte bara PHP2Shell. Varje härdning, från avstängda felutskrifter till uppladdningsgränser, är bara så stark som sitt svagaste lager.

Vem som överhuvudtaget får ändra PHP-inställningar

PHP har fyra ändringslägen. Varje inställning har ett av dem, och det avgör på vilka ställen den kan sättas. Betydelserna kommer från PHP-manualen.

Läge Var värdet kan sättas Exempel
INI_USER i skriptet via ini_set() och i .user.ini få körtidsvärden
INI_PERDIR php.ini, .htaccess, httpd.conf, .user.ini post_max_size, session.upload_progress.enabled
INI_SYSTEM bara php.ini eller httpd.conf file_uploads, disable_functions
INI_ALL överallt, även via ini_set() memory_limit, display_errors, open_basedir

Farliga är framför allt INI_ALL-värden: de går att ändra från vilket skript som helst. INI_PERDIR-värden går visserligen inte att ändra via ini_set(), men väl via en .htaccess vid mod_php eller en .user.ini vid PHP-FPM. Den som har skrivrättigheter i webbroten, alltså även inplanterad kod, kan skapa sådana filer.

php_admin_value i FPM-poolen och i Apache

Vid PHP-FPM står värdena i poolfilen. PHP-manualen fastslår: värden som sätts med php_admin_value och php_admin_flag kan inte skrivas över med ini_set(). För av-på-värden tar ni php_admin_flag, för alla andra php_admin_value.

; /etc/php/8.3/fpm/pool.d/seite1.conf (utdrag)
[seite1]
user = seite1
group = seite1
listen = /run/php/seite1.sock

php_admin_value[memory_limit] = -1
php_admin_value[post_max_size] = 32M
php_admin_value[upload_max_filesize] = 24M
php_admin_flag[session.upload_progress.enabled] = off
php_admin_flag[display_errors] = off
php_admin_value[error_log] = /var/log/php/seite1-fehler.log
php_admin_value[open_basedir] = /var/www/seite1/:/tmp/seite1/

memory_limit=-1 hör enligt php.net bara hemma i konfigurationen tillsammans med en minnesgräns via container eller cgroup. Hur det lyckas med systemd står i inlägget Sätta minnesgränser med systemd och cgroups.

Med Apache och mod_php hör direktiven hemma i serverkonfigurationen eller i VirtualHost. Enligt PHP-manualen är de inte tillåtna i .htaccess, och när de väl är satta kan varken .htaccess eller ini_set() ändra dem.

<VirtualHost *:443>
    ServerName www.example.de
    DocumentRoot /var/www/seite1/public
    <IfModule php_module>
        php_admin_value memory_limit -1
        php_admin_value post_max_size 32M
        php_admin_value upload_max_filesize 24M
        php_admin_flag session.upload_progress.enabled off
        php_admin_flag display_errors off
    </IfModule>
</VirtualHost>

Två finesser ur manualen: för att radera ett tidigare satt värde använder ni none som värde. Och PHP-konstanter som E_ALL saknar betydelse i Apache-konfigurationen; för error_reporting måste ni där ange talvärdet.

Vilka värden ni bör spärra

Inte varje inställning behöver vara spärrad. Det är rimligt för allt som rör säkerhet eller fungerar som övergångsåtgärd:

  1. php.nets PHP2Shell-övergångsvärden: memory_limit, post_max_size, upload_max_filesize, session.upload_progress.enabled och på PHP 8.5 fatal_error_backtraces.
  2. Felutskrift och loggning: display_errors, display_startup_errors, log_errors, error_log.
  3. Filåtkomst och isolering: open_basedir, upload_tmp_dir, session.save_path.
  4. Nätverksåtkomst från PHP: allow_url_include och, om applikationen inte behöver det, allow_url_fopen.
  5. Spärrade funktioner via disable_functions, som i poolen enligt manualen kompletterar php.ini-listan och inte ersätter den. Detaljer i guiden Använd disable_functions rätt.

För session.upload_progress.enabled är spärren särskilt viktig, eftersom värdet annars kunde slås på igen via en .user.ini. Mer om det under Stäng av session.upload_progress: rätt och permanent.

Kontrollera att spärren verkar

Starta efter varje ändring om tjänsten och kontrollera värdet i webbkontexten. En kort kontrollfil som raderas direkt igen visar om poolen håller värdet, även när applikationen vill ändra det:

<?php
// Kontrollfil: lägg ut den kort, anropa den en gång via domänen, radera den direkt
header('Content-Type: text/plain');
$vorher = ini_get('memory_limit');
$versuch = @ini_set('memory_limit', '256M');
echo "memory_limit: $vorher\n";
echo 'Änderung per ini_set() ', ($versuch === false ? 'blockiert' : 'MÖGLICH'), "\n";

Förväntat är -1 och ”blockiert”. Lyder utskriften ”MÖGLICH” är värdet inte satt via php_admin_value eller tjänsten ännu inte omstartad. Upprepa kontrollen för varje pool och varje PHP-version.

Tips

Håll de spärrade värdena samlade centralt, till exempel i en poolmall eller i er konfigurationshantering. Webbhotellspaneler skriver ibland över handändrade poolfiler vid nästa sparande; där hör värdena hemma i de fält som panelen tillhandahåller.

Hur PHP ordnar sina konfigurationsnivåer sammantaget förklarar php.ini förklarad: uppbyggnad, nivåer och företräde. De fullständiga övergångsåtgärderna står under Akuta åtgärder när ni ännu inte kan patcha.

Slutsats: först spärrat är verkligen satt

php.nets övergångsåtgärder för PHP2Shell har lyft fram en skillnad som tidigare ofta förbisågs: ett värde i php.ini är för många inställningar bara ett förslag, ett värde i php_admin_value en föreskrift. För bekvämlighetsvärden som tidszonen saknar skillnaden betydelse. För säkerhetsinställningar och övergångsåtgärder avgör den om åtgärden överhuvudtaget verkar i den pågående driften.

Insatsen är överskådlig: en handfull rader per pool eller VirtualHost, en omstart, en kort kontroll. Håll listan över spärrade värden liten och motiverad, så att utvecklare kan förstå varför deras applikation inte får ändra ett värde. Och underhåll listan i era mallar, så att nya webbplatser ärver den automatiskt.

Hur hjälper PHP SOS konkret?

  • Läsa ut nivåerna: Vi tar reda på vilka värden från php.ini, pool, Apache, .htaccess eller .user.ini som faktiskt gäller för varje webbplats.
  • Sätta spärrar: Säkerhetsrelevanta värden och PHP2Shell-övergångsåtgärderna lägger vi in som php_admin_value respektive php_admin_flag och startar om tjänsterna.
  • Testa applikationen: Vi kontrollerar att applikationen körs felfritt med de spärrade värdena och analyserar felloggen.
  • Underhålla mallar: Inom ramen för serverhärdningen för vi över värdena till poolmallar och dokumentation.

Vanliga frågor

Vad är skillnaden mellan php_value och php_admin_value?

Båda sätter en PHP-inställning. Värden från php_value kan applikationen senare ändra igen, till exempel via ini_set() eller .htaccess. Värden från php_admin_value och php_admin_flag är enligt PHP-manualen spärrade för ini_set(), i Apache även för .htaccess.

Kan jag skriva php_admin_value i en .htaccess-fil?

Nej. Enligt PHP-manualen är php_admin_value inte tillåtet i .htaccess-filer. Det hör hemma i Apache-serverkonfigurationen eller i VirtualHost, i PHP-FPM i poolfilen.

Vad händer om en applikation försöker ändra ett spärrat värde?

Anropet av ini_set() misslyckas och returnerar false, det spärrade värdet består. Väl programmerade applikationer klarar det. Kontrollera ändå felloggen och de viktigaste funktionerna efter omställningen.

Måste jag starta om efter en ändring i poolen?

Ja. PHP-FPM läser poolfilerna vid start eller när tjänsten laddas om. Med Apache och mod_php gäller samma sak för serverkonfigurationen. Utan omstart fortsätter det gamla värdet att gälla.

Går disable_functions att utöka i poolen?

Ja, med en särdrag: enligt PHP-manualen skriver disable_functions i FPM-poolen inte över värdena från php.ini utan kompletterar dem. Poolen kan alltså spärra fler funktioner men inte häva några.

Källor

Direktkontakt

Varje timme räknas. Skriv till oss nu.

Beskriv kort system, PHP-version och observation. Vi hör av oss, klarlägger läget och arbetar på distans tills incidenten är avslutad och dokumenterad.

Direkthjälp