{"id":141,"date":"2026-01-19T00:00:00","date_gmt":"2026-01-18T23:00:00","guid":{"rendered":"https:\/\/helloblog.io\/pl\/krytyczna-eskalacja-uprawnien-acf-extended-formularz-rejestracji-admin\/"},"modified":"2026-01-19T00:00:00","modified_gmt":"2026-01-18T23:00:00","slug":"krytyczna-eskalacja-uprawnien-acf-extended-formularz-rejestracji-admin","status":"publish","type":"post","link":"https:\/\/helloblog.io\/pl\/krytyczna-eskalacja-uprawnien-acf-extended-formularz-rejestracji-admin\/","title":{"rendered":"Krytyczna eskalacja uprawnie\u0144 w ACF Extended: kiedy formularz rejestracji mo\u017ce da\u0107 atakuj\u0105cemu admina"},"content":{"rendered":"\n<p>W ekosystemie WordPressa najgro\u017aniejsze s\u0105 te b\u0142\u0119dy, kt\u00f3re nie wymagaj\u0105 logowania, a jednocze\u015bnie ko\u0144cz\u0105 si\u0119 przej\u0119ciem konta z wysokimi uprawnieniami. Dok\u0142adnie z tak\u0105 sytuacj\u0105 mieli\u015bmy do czynienia w dodatku <strong>Advanced Custom Fields: Extended<\/strong> (ACF Extended) \u2013 popularnym rozszerzeniu do ACF (Advanced Custom Fields), u\u017cywanym m.in. do budowania formularzy i mapowania p\u00f3l na akcje typu \u201eCreate user\u201d.<\/p>\n\n\n\n<p>Wed\u0142ug analizy Wordfence podatno\u015b\u0107 pozwala\u0142a <strong>niezautoryzowanemu atakuj\u0105cemu<\/strong> uzyska\u0107 <strong>eskalacj\u0119 uprawnie\u0144<\/strong> poprzez wymuszenie roli (np. <code>administrator<\/code>) podczas tworzenia u\u017cytkownika w formularzu. Problem zosta\u0142 za\u0142atany \u2013 kluczowe jest jednak to, \u017ce luka by\u0142a wykorzystywalna tylko w okre\u015blonej konfiguracji formularza.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Kogo dotyczy problem (i dlaczego nie ka\u017cda strona jest \u201eod razu\u201d zagro\u017cona)<\/h2>\n\n\n\n<p>Podatno\u015b\u0107 obejmuje <strong>Advanced Custom Fields: Extended w wersjach \u2264 0.9.2.1<\/strong> i dotyczy scenariusza, w kt\u00f3rym w\u0142a\u015bciciel strony u\u017cywa modu\u0142u formularzy ACF Extended do tworzenia lub aktualizacji u\u017cytkownik\u00f3w. Z technicznego punktu widzenia krytyczne jest to, czy w formularzu istnieje pole mapowane na <strong>rol\u0119 u\u017cytkownika<\/strong>.<\/p>\n\n\n\n<div class=\"wp-block-group callout callout-warning is-style-warning is-layout-flow wp-block-group-is-layout-flow\" style=\"border-width:1px;border-radius:8px;padding-top:1rem;padding-right:1.5rem;padding-bottom:1rem;padding-left:1.5rem\">\n\n<h4 class=\"wp-block-heading callout-title\">Warunek wykorzystania luki<\/h4>\n\n\n<p>Luka by\u0142a mo\u017cliwa do wykorzystania tylko wtedy, gdy w formularzu skonfigurowano mapowanie pola <code>role<\/code> (rola) na dane u\u017cytkownika. Bez takiego mapowania atakuj\u0105cy nie ma \u201euchwytu\u201d, \u017ceby wstrzykn\u0105\u0107 w\u0142asn\u0105 rol\u0119.<\/p>\n\n<\/div>\n\n\n\n<h2 class=\"wp-block-heading\">Na czym polega\u0142a eskalacja uprawnie\u0144<\/h2>\n\n\n\n<p>Sedno problemu: mechanizm obs\u0142ugi akcji \u201einsert user\u201d (tworzenie u\u017cytkownika) w ACF Extended pozwala\u0142 przekaza\u0107 argumenty do <code>wp_insert_user()<\/code> w spos\u00f3b, kt\u00f3ry nie blokowa\u0142 warto\u015bci roli dostarczanej z formularza. Je\u015bli formularz przyjmowa\u0142 (jawnie lub \u201epo\u015brednio\u201d przez mapowanie) parametr roli, to niezalogowany atakuj\u0105cy m\u00f3g\u0142 spr\u00f3bowa\u0107 wys\u0142a\u0107 <code>administrator<\/code> i utworzy\u0107 konto z pe\u0142nymi uprawnieniami.<\/p>\n\n\n\n<p>Wordfence opisuje, \u017ce logicznie mo\u017cna by oczekiwa\u0107, i\u017c ograniczenia ustawiane przy polu roli (np. \u201eAllow User Role\u201d) b\u0119d\u0105 respektowane r\u00f3wnie\u017c na etapie formularza. W podatnej wersji takie ograniczenia w kontek\u015bcie formularza nie by\u0142y skutecznie egzekwowane \u2013 w efekcie rola mog\u0142a zosta\u0107 ustawiona arbitralnie, o ile pole roli zosta\u0142o dodane do formularza.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Dlaczego to jest krytyczne (CVSS 9.8) w praktyce<\/h2>\n\n\n\n<p>Eskalacja do administratora oznacza w WordPressie praktycznie pe\u0142ne przej\u0119cie aplikacji. Po uzyskaniu dost\u0119pu admina atakuj\u0105cy mo\u017ce m.in.:<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n\n<li>instalowa\u0107\/aktualizowa\u0107 wtyczki i motywy (w tym wgra\u0107 z\u0142o\u015bliwe paczki z backdoorem),<\/li>\n\n\n<li>modyfikowa\u0107 tre\u015bci (np. wstrzykiwa\u0107 spam, linki SEO, przekierowania),<\/li>\n\n\n<li>zak\u0142ada\u0107 kolejne konta, zmienia\u0107 role innym u\u017cytkownikom,<\/li>\n\n\n<li>zmienia\u0107 ustawienia witryny, a w skrajnych przypadkach utrwali\u0107 dost\u0119p.<\/li>\n\n<\/ul>\n\n\n\n<h2 class=\"wp-block-heading\">Wersje podatne i poprawka (CVE-2025-14533)<\/h2>\n\n\n\n<p>Wordfence sklasyfikowa\u0142 podatno\u015b\u0107 jako <strong>Critical<\/strong> (CVSS 9.8) i przypisa\u0142 jej identyfikator <strong>CVE-2025-14533<\/strong>. Podatne s\u0105 wersje <strong>Advanced Custom Fields: Extended \u2264 0.9.2.1<\/strong>, a poprawka zosta\u0142a wydana w <strong>0.9.2.2<\/strong>.<\/p>\n\n\n\n<div class=\"wp-block-group callout callout-success is-style-success is-layout-flow wp-block-group-is-layout-flow\" style=\"border-width:1px;border-radius:8px;padding-top:1rem;padding-right:1.5rem;padding-bottom:1rem;padding-left:1.5rem\">\n\n<h4 class=\"wp-block-heading callout-title\">Co robi\u0107<\/h4>\n\n\n<p>Zaktualizuj Advanced Custom Fields: Extended do wersji 0.9.2.2 (lub nowszej, je\u015bli jest dost\u0119pna). To podstawowy krok, niezale\u017cnie od tego, czy masz skonfigurowane formularze u\u017cytkownik\u00f3w.<\/p>\n\n<\/div>\n\n\n\n<h2 class=\"wp-block-heading\">Szybki checklist dla os\u00f3b, kt\u00f3re buduj\u0105 formularze w ACF Extended<\/h2>\n\n\n\n<p>Je\u015bli korzystasz z ACF Extended jako \u201eform managera\u201d, warto przejrze\u0107 konfiguracj\u0119 pod k\u0105tem miejsc, w kt\u00f3rych rola mog\u0142a by\u0107 ustawiana przez formularz. To szczeg\u00f3lnie istotne przy formularzach typu rejestracja, onboarding, \u201ecreate account\u201d, a tak\u017ce przy akcjach aktualizuj\u0105cych u\u017cytkownika.<\/p>\n\n\n\n<ol class=\"wp-block-list\">\n\n<li>Sprawd\u017a, czy masz formularze z akcj\u0105 \u201eCreate user\u201d (<code>insert_user<\/code>) lub \u201eUpdate user`. <\/li>\n\n\n<li>Zweryfikuj, czy jakikolwiek field w tych formularzach mapuje si\u0119 na <code>role<\/code> (lub czy rola wynika z mapowania w grupie p\u00f3l).<\/li>\n\n\n<li>Je\u015bli rola musi by\u0107 ustawiana, ogranicz j\u0105 do minimalnie potrzebnych r\u00f3l i nie wystawiaj pola roli publicznie (z perspektywy UX i bezpiecze\u0144stwa to zwykle antywzorzec).<\/li>\n\n\n<li>Zadbaj o warstw\u0119 ochronn\u0105: firewall aplikacyjny (WAF) i monitorowanie pr\u00f3b rejestracji\/logowania, bo tego typu luki cz\u0119sto id\u0105 w parze z automatyzacj\u0105 atak\u00f3w.<\/li>\n\n<\/ol>\n\n\n\n<h2 class=\"wp-block-heading\">Warstwa ochrony od Wordfence: kiedy pojawi\u0142y si\u0119 regu\u0142y<\/h2>\n\n\n\n<p>Wordfence poinformowa\u0142, \u017ce u\u017cytkownicy <strong>Wordfence Premium<\/strong>, <strong>Wordfence Care<\/strong> oraz <strong>Wordfence Response<\/strong> otrzymali regu\u0142\u0119 firewalla chroni\u0105c\u0105 przed pr\u00f3bami wykorzystania tej podatno\u015bci <strong>11 grudnia 2025<\/strong>. U\u017cytkownicy darmowej wersji Wordfence dostali analogiczn\u0105 ochron\u0119 <strong>10 stycznia 2026<\/strong> (po 30 dniach).<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Chronologia ujawnienia i reakcja producenta<\/h2>\n\n\n\n<p>Z perspektywy procesu disclosure wida\u0107 tu do\u015b\u0107 sprawny przep\u0142yw: zg\u0142oszenie trafi\u0142o do Wordfence 10 grudnia 2025, weryfikacja i przekazanie szczeg\u00f3\u0142\u00f3w do zespo\u0142u ACF Extended nast\u0105pi\u0142y 11 grudnia, a poprawiona wersja wtyczki zosta\u0142a wydana 14 grudnia 2025.<\/p>\n\n\n\n<p>Podatno\u015b\u0107 odkry\u0142 i odpowiedzialnie zg\u0142osi\u0142 badacz <strong>andrea bocchetti<\/strong> w ramach programu bug bounty Wordfence.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Najwa\u017cniejsze wnioski dla praktyki WordPress dev<\/h2>\n\n\n\n<ul class=\"wp-block-list\">\n\n<li>Je\u015bli wystawiasz publiczny formularz, kt\u00f3ry dotyka obiekt\u00f3w u\u017cytkownika (rejestracja\/edycja), traktuj rol\u0119 jako dane wra\u017cliwe \u2013 najlepiej w og\u00f3le nie przyjmuj jej z inputu.<\/li>\n\n\n<li>Ograniczenia ustawione \u201ew UI wtyczki\u201d nie zawsze oznaczaj\u0105, \u017ce back-end konsekwentnie je egzekwuje. Warto czyta\u0107 changelogi i \u015bledzi\u0107 advisory dla popularnych dodatk\u00f3w.<\/li>\n\n\n<li>Wtyczki typu \u201eform builder\u201d + \u201euser management\u201d to cz\u0119sty wektor ataku, bo \u0142\u0105cz\u0105 zewn\u0119trzny input z krytycznymi operacjami (tworzenie kont, role, capabilities).<\/li>\n\n<\/ul>\n\n\n\n<h2 class=\"wp-block-heading\">Podsumowanie<\/h2>\n\n\n\n<p>W ACF Extended wykryto krytyczn\u0105 podatno\u015b\u0107 eskalacji uprawnie\u0144 (CVE-2025-14533), kt\u00f3ra w okre\u015blonej konfiguracji formularza pozwala\u0142a niezalogowanemu atakuj\u0105cemu utworzy\u0107 konto z rol\u0105 administratora. Poprawka jest dost\u0119pna w wersji <strong>0.9.2.2<\/strong>, wi\u0119c najrozs\u0105dniejszym krokiem jest szybka aktualizacja oraz przegl\u0105d formularzy u\u017cytkownik\u00f3w pod k\u0105tem mapowania <code>role<\/code>.<\/p>\n\n\n\n<figure class=\"wp-block-image size-large\"><img loading=\"lazy\" decoding=\"async\" width=\"2560\" height=\"1600\" src=\"https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-1-scaled-1.png\" alt=\"Ustawienia pola roli u\u017cytkownika w ACF Extended (Allow User Role)\" class=\"wp-image-139\" srcset=\"https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-1-scaled-1.png 2560w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-1-scaled-1-300x188.png 300w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-1-scaled-1-1024x640.png 1024w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-1-scaled-1-768x480.png 768w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-1-scaled-1-1536x960.png 1536w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-1-scaled-1-2048x1280.png 2048w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-1-scaled-1-400x250.png 400w\" sizes=\"auto, (max-width: 2560px) 100vw, 2560px\" \/><figcaption class=\"wp-element-caption\">Ograniczenia roli ustawiane na poziomie pola mog\u0105 nie wystarczy\u0107, je\u015bli formularz nie egzekwuje ich po stronie serwera. \u2014 <em>Forr\u00e1s: Wordfence.com<\/em><\/figcaption><\/figure>\n\n\n\n<figure class=\"wp-block-image size-large\"><img loading=\"lazy\" decoding=\"async\" width=\"2560\" height=\"1599\" src=\"https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-2-scaled-1.png\" alt=\"Konfiguracja formularza w ACF Extended z akcj\u0105 Create user i mapowaniem p\u00f3l\" class=\"wp-image-140\" srcset=\"https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-2-scaled-1.png 2560w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-2-scaled-1-300x187.png 300w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-2-scaled-1-1024x640.png 1024w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-2-scaled-1-768x480.png 768w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-2-scaled-1-1536x959.png 1536w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-2-scaled-1-2048x1279.png 2048w, https:\/\/helloblog.io\/app\/uploads\/sites\/8\/2026\/01\/acfe-2-scaled-1-400x250.png 400w\" sizes=\"auto, (max-width: 2560px) 100vw, 2560px\" \/><figcaption class=\"wp-element-caption\">Kluczowy scenariusz: formularz \u201eCreate user\u201d z mapowaniem p\u00f3l u\u017cytkownika, w tym roli. \u2014 <em>Forr\u00e1s: Wordfence.com<\/em><\/figcaption><\/figure>\n\n\n<div class=\"references-section\">\n                <h2>Odniesienia \/ \u0179r\u00f3d\u0142a<\/h2>\n                <ul class=\"references-list\"><li><a href=\"https:\/\/www.wordfence.com\/blog\/2026\/01\/100000-wordpress-sites-affected-by-privilege-escalation-vulnerability-in-advanced-custom-fields-extended-wordpress-plugin\/\" target=\"_blank\" rel=\"noopener noreferrer\">100,000 WordPress Sites Affected by Privilege Escalation Vulnerability in Advanced Custom Fields: Extended WordPress Plugin<\/a><\/li><li><a href=\"https:\/\/www.wordfence.com\/threat-intel\/vulnerabilities\/wordpress-plugins\/acf-extended\/advanced-custom-fields-extended-0921-unauthenticated-privilege-escalation-via-insert-user-form-action\" target=\"_blank\" rel=\"noopener noreferrer\">Advanced Custom Fields: Extended &lt;= 0.9.2.1 &#8212; Unauthenticated Privilege Escalation via Insert User Form Action<\/a><\/li><li><a href=\"https:\/\/www.cve.org\/CVERecord?id=CVE-2025-14533\" target=\"_blank\" rel=\"noopener noreferrer\">CVE-2025-14533<\/a><\/li><li><a href=\"https:\/\/wordpress.org\/plugins\/acf-extended\/\" target=\"_blank\" rel=\"noopener noreferrer\">Advanced Custom Fields: Extended<\/a><\/li><\/ul>\n            <\/div>","protected":false},"excerpt":{"rendered":"<p>Wtyczka Advanced Custom Fields: Extended (ACF Extended) mia\u0142a luk\u0119, kt\u00f3ra w okre\u015blonej konfiguracji pozwala\u0142a niezalogowanemu u\u017cytkownikowi nada\u0107 sobie rol\u0119 administratora. Sprawd\u017a, czy dotyczy to Twoich formularzy i co trzeba zaktualizowa\u0107.<\/p>\n","protected":false},"author":26,"featured_media":138,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[9],"tags":[80,35,81,15,10],"class_list":["post-141","post","type-post","status-publish","format-standard","has-post-thumbnail","hentry","category-bezpieczenstwo","tag-acf-extended","tag-bezpieczenstwo","tag-cve","tag-wordfence","tag-wordpress"],"_links":{"self":[{"href":"https:\/\/helloblog.io\/pl\/wp-json\/wp\/v2\/posts\/141","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/helloblog.io\/pl\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/helloblog.io\/pl\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/helloblog.io\/pl\/wp-json\/wp\/v2\/users\/26"}],"replies":[{"embeddable":true,"href":"https:\/\/helloblog.io\/pl\/wp-json\/wp\/v2\/comments?post=141"}],"version-history":[{"count":0,"href":"https:\/\/helloblog.io\/pl\/wp-json\/wp\/v2\/posts\/141\/revisions"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/helloblog.io\/pl\/wp-json\/wp\/v2\/media\/138"}],"wp:attachment":[{"href":"https:\/\/helloblog.io\/pl\/wp-json\/wp\/v2\/media?parent=141"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/helloblog.io\/pl\/wp-json\/wp\/v2\/categories?post=141"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/helloblog.io\/pl\/wp-json\/wp\/v2\/tags?post=141"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}