In this writing there will be only technical description of the vulnerability and reasons for its happening. Detailed PoC and attack vector will be released in 2 weeks after community update its systems.
Everyone who cares little about safety of the web already knows that WordPress leads failed to protect community from several public issues known for a quite long time. At very this moment there is lack of documentation (in this particular case documentation and WP security officials even mislead developers), lack of warnings towards hosting vendors, plugin and theme developers and in general no interest to inform the community in proper way, but that is not the case for THEIR (privileged keepers of the problemattic community knowledge no matter we talk about infosec or tits) own products and services.
Unserialize in WordPress
WordPress handles its serialization via
maybe_unserialize functions and those functions are advertised as “security” functions e.g. the ones responsible for making sure that serialized data went trough them and that is the proof for preventing unserialize of the user input (see documentation and code comments). That is notorious lie and in combination with silence only towards community, many valuable projects out there are leaved vulnerable of this types of attacks.
Advanced Custom Fields 5.7.10 issue
This is one of the most used plugins when we talk about WordPress development. There are tons of themes that are build on the top of this plugin, many plugins for it in the form of contacts forms, shopping carts, user dashboards, … and many many more custom WP implementations.
So, how ACF stores data?
When we dive deep ACF uses its function
acf_update_value which in fact is
acf_update_metadata and that is
update_metadata from the field value aspect. Yes, the data is stored into
postmeta table. If we count there is only one call towards
maybe_serialize function, before storage. We are clear until now?!
ACF reads fields values via
acf_get_value function and if we check its code (in 5.7.10) then we have the following:
// load value
$value = acf_get_metadata( $post_id, $field['name'] );// if value was duplicated, it may now be a serialized string!
$value = maybe_unserialize( $value );
get_metadata call from value perspective => we have one
maybe_unserialize of the input there, but right after it there is another one
maybe_unserialize call, which should be harmless for payloads not serialized by the system and it is used for prevention of double serialized values?! NOT! We have: one call on input and two calls on output => unserialize of user input, only because developer used “security” functions advertised by the api and security team…
It is worth to be mentioned that plugin itself isn’t vulnerable on this type of attacks (except towards underling PHP and WP — both have issues), but in combination with many popular plugins (100k+ active installs) there are quite interesting POI gadget chains. Those would be considered and explained in two weeks from now. UPDATE ASAP!
For smooth updating :)
If you are wp developer or wp host provider or wp security product provider with valuable list of clients, we offer subscription list and we are exceptional (B2B only).