You switch a site to a newer PHP version, or move it to a new host, and a page dies with one line: Call to undefined function. The function isn't misspelled and the plugin worked yesterday. Almost every time, the code is fine and PHP is missing the extension that provides that function - every PHP version keeps its own list of enabled extensions, and the one you just switched to doesn't have it ticked. Here's how to tell which extension it is and switch it on in cPanel, usually in a couple of minutes.
What the error is telling you
The full message names the function and the file that called it:
PHP Fatal error: Uncaught Error: Call to undefined function mb_strlen() in /home/user/public_html/wp-content/plugins/some-plugin/includes/helpers.php:42PHP looked for mb_strlen() in everything it has loaded and found nothing. There are only three ways that happens:
- The extension that provides it is not enabled for the PHP version your site runs. This is the common case, and the fix is a checkbox.
- PHP itself removed the function in the version you moved to -
mysql_connect(),each(),create_function()and friends. No extension brings these back; the code has to change. - The function belongs to your code, not to PHP - a plugin calling a helper from another plugin that is disabled, a half-uploaded file, or a typo.
The same problem with a class looks slightly different on PHP 8: Class "ZipArchive" not found or Class "DOMDocument" not found. Treat it exactly the same way.
Step 1: Get the exact function name from the error log
If the page only shows a white screen or "There has been a critical error", the real line is in the log. In cPanel open Metrics → Errors, or open the error_log file in the site's folder with File Manager (see how to find and read error logs in cPanel). Note two things: the function or class name, and the file path - the path tells you which plugin, theme or script made the call.
Step 2: Match the function to its extension
These cover the large majority of what we see on cPanel accounts:
| Function or class in the error | Extension to enable |
|---|---|
mb_strlen(), mb_substr(), mb_strtolower() | mbstring |
curl_init(), curl_exec() | curl |
imagecreatefromjpeg(), imagecreatetruecolor(), imagewebp() | gd |
mysqli_connect(), new mysqli | mysqli (or nd_mysqli) |
new PDO('mysql:...') failing with "could not find driver" | pdo_mysql (or nd_pdo_mysql) |
simplexml_load_string(), simplexml_load_file() | simplexml |
DOMDocument | dom |
ZipArchive | zip |
idn_to_ascii(), NumberFormatter, grapheme_strlen() | intl |
bcadd(), bcmul(), bcdiv() | bcmath |
iconv(), iconv_strlen() | iconv |
finfo_open(), mime_content_type() | fileinfo |
exif_read_data() | exif |
sodium_crypto_box() and other sodium_* | sodium |
Imagick | imagick |
SoapClient | soap |
apcu_fetch(), apcu_store() | apcu |
For anything not in the table, look the function up on php.net: its manual page sits under the extension that provides it. If php.net has no page for it at all, it's not a PHP function - skip to "still undefined" below. Encoded plugins that fail with a message about the ionCube Loader are a separate fix: ionCube Loader errors in cPanel.
Step 3: Check what is loaded for the version your site actually runs
This is where most people lose half an hour. Running php -m over SSH lists the extensions of the command-line PHP, and on cPanel that is often a different version from the one MultiPHP Manager assigns to your domain. It can show mbstring while the website still fails.
The reliable check is from the web side. Create a file with a random name in the site's folder:
<?php phpinfo();Open it in the browser. The version at the top is the one your site really uses; search the page for the extension name. Delete the file as soon as you're done - it shows server details you don't want public.
If you prefer SSH, call the PHP binary for that exact version instead of plain php:
# CloudLinux servers (alt-php)
/opt/alt/php83/usr/bin/php -m | grep -i mbstring
# Other cPanel servers (EasyApache 4)
/opt/cpanel/ea-php83/root/usr/bin/php -m | grep -i mbstringStep 4: Enable the extension in cPanel
If your cPanel has "Select PHP Version"
That icon, under Software, means the server runs CloudLinux and you can switch extensions on yourself:
- Open Software → Select PHP Version.
- Make sure the current version shown is the one your site runs (the phpinfo page from step 3 tells you).
- Open the Extensions tab and tick the extension. Newer versions of this screen save as you tick; older ones have a Save button at the bottom.
- Reload the page that failed.
Two things trip people up here. First, mysqli and nd_mysqli (and pdo_mysql and nd_pdo_mysql) are two builds of the same functions against different drivers - tick one of each pair, not both, or they conflict. Second, Select PHP Version governs domains that MultiPHP Manager leaves on the server default. If MultiPHP Manager pins your domain to a specific version, the extensions for that domain come from the server's EasyApache 4 build instead, and ticking boxes here changes nothing for it.
If there is no "Select PHP Version"
Then PHP extensions are installed server-wide, as EasyApache 4 packages named like ea-php83-php-mbstring or ea-php83-php-intl. On shared hosting only the host can add them: open a ticket naming the extension and the PHP version, and it's normally a quick job. On your own VPS with WHM you can do it yourself under WHM → EasyApache 4 → Customize → PHP Extensions - see rebuilding PHP with EasyApache 4 without breaking sites.
Functions no extension can bring back
If the function is on this list, PHP removed it. Switching an extension on won't help, because there is no extension:
| Function | Removed in | Use instead |
|---|---|---|
mysql_connect(), mysql_query() and all mysql_* | PHP 7.0 | mysqli or PDO |
ereg(), eregi(), split() | PHP 7.0 | preg_match(), preg_split() |
mcrypt_encrypt() and all mcrypt_* | PHP 7.2 | openssl_encrypt() or sodium |
each() | PHP 8.0 | foreach |
create_function() | PHP 8.0 | an anonymous function |
money_format() | PHP 8.0 | NumberFormatter (intl) |
The real fix is updating the plugin, theme or script that still calls it - its developer has almost certainly shipped a version without it. If you need the site back right now, switching the domain to its previous PHP version in MultiPHP Manager buys time; just don't stay on an end-of-life PHP. The full approach is in changing your PHP version in cPanel without breaking your site.
WordPress: "missing the MySQL extension"
WordPress has its own wording for one of these. If you see
Your PHP installation appears to be missing the MySQL extension which is required by WordPress.then the PHP version your site runs has neither mysqli nor nd_mysqli enabled. Tick one of them as in step 4. It usually appears right after a PHP version switch, because each version keeps its own extension list and the new one started without it.
Still undefined after enabling it?
- You changed a different version. Recheck with phpinfo: the site may run 8.3 while you ticked the box under 8.2.
- The failing code runs from cron or the command line. A cron job calls a PHP binary directly, often
/usr/bin/phpor/usr/local/bin/php, which can be a different version with its own extensions. Point the cron line at the binary for your site's version, using the paths from step 3. - The function is disabled, not missing. Since PHP 8.0, a function listed in
disable_functionsis removed outright, soexec(),shell_exec()orproc_open()fail with "Call to undefined function" instead of PHP 7's "has been disabled for security reasons". Shared hosts commonly disable these. Search the phpinfo page fordisable_functions; if yours is listed, ask your host, or run that job somewhere you control the php.ini. - It isn't a PHP function at all. Functions like
wc_get_product()orget_field()come from plugins (WooCommerce, ACF). The error means that plugin is inactive, half-updated or loaded too late. Reinstall it and check that the plugin calling it is compatible with its current version.