paragonie/random_compat · critical · Error

COM does not exist

Error message

COM does not exist

What it means

This codepath uses Windows CAPICOM's Utilities.GetRandom() through the COM extension as a CSPRNG source. If the COM class is not available (class_exists('COM') fails) the library cannot use this backend and throws immediately rather than silently producing weak randomness. On the com_dotnet build this is a hard environment requirement.

Solutions

  1. Install/enable the COM dotnet extension: add extension=com_dotnet (or extension=php_com_dotnet.dll) to php.ini and restart PHP.
  2. Verify with php -m or class_exists('COM') that COM is available in the same SAPI that runs the code.
  3. Prefer upgrading PHP to >= 7.0 where native random_bytes() exists and random_compat is unnecessary.
  4. Use a random_compat build/backing appropriate for the actual platform (e.g. mcrypt, openssl, /dev/urandom backends).

Example fix

// before (assumes COM exists)
$bytes = random_bytes(32);
// after
if (!class_exists('COM')) {
    throw new RuntimeException('random_bytes(): COM extension required; enable com_dotnet in php.ini');
}
$bytes = random_bytes(32);
Defensive patterns

Strategy: fallback

Validate before calling

if (!class_exists('COM')) {
    throw new RuntimeException('COM extension missing; cannot use CAPICOM CSPRNG backend');
}

Try / catch

try {
    $bytes = random_bytes(32);
} catch (Error $e) {
    if ($e->getMessage() === 'COM does not exist') {
        // fall back to another CSPRNG source or fail securely
        throw new RuntimeException('No CSPRNG available: enable com_dotnet or upgrade to PHP 7+', 0, $e);
    }
    throw $e;
}

Prevention

When it happens

Trigger: Calling random_bytes() on a random_compat build where the COM backend was selected at load time, but the running PHP does not expose the COM class — i.e. PHP built without --enable-com-dotnet, the com_dotnet extension disabled in php.ini, or running on a non-Windows platform with this backend chosen.

Common situations: Deploying a Windows-targeted PHP build to Linux; php.ini missing 'extension=com_dotnet'; CLI vs web SAPI using different php.ini files where one lacks the extension; Docker images of PHP for Windows without the extension compiled in.

Understand the failure class

Background: "not installed", "pip install", "required for": how missing-dependency errors surface across open-source libraries — this error's family across 34 libraries.

Related errors


AI-assisted analysis of paragonie/random_compat@b5d188cc9d (2026-09-13). Data as JSON: /api/errors/07c258b95b6fad5e. Report an issue: GitHub.

Appendix: source

Thrown at lib/random_bytes_com_dotnet.php:61

        try {
            /** @var int $bytes */
            $bytes = RandomCompat_intval($bytes);
        } catch (TypeError $ex) {
            throw new TypeError(
                'random_bytes(): $bytes must be an integer'
            );
        }

        if ($bytes < 1) {
            throw new Error(
                'Length must be greater than 0'
            );
        }

        /** @var string $buf */
        $buf = '';
        if (!class_exists('COM')) {
            throw new Error(
                'COM does not exist'
            );
        }
        /** @var COM $util */
        $util = new COM('CAPICOM.Utilities.1');
        $execCount = 0;

        /**
         * Let's not let it loop forever. If we run N times and fail to
         * get N bytes of random data, then CAPICOM has failed us.
         */
        do {
            $buf .= base64_decode((string) $util->GetRandom($bytes, 0));
            if (RandomCompat_strlen($buf) >= $bytes) {
                /**
                 * Return our random entropy buffer here:
                 */
                return (string) RandomCompat_substr($buf, 0, $bytes);

View on GitHub (pinned to b5d188cc9d)