PHP code example of guycalledseven / php-ext-oqs

1. Go to this page and download the library: Download guycalledseven/php-ext-oqs library. Choose the download type require.

2. Extract the ZIP file and open the index.php.

3. Add this code to the index.php.
    
        
<?php
require_once('vendor/autoload.php');

/* Start to develop here. Best regards https://php-download.com/ */

    

guycalledseven / php-ext-oqs example snippets


// Example of best practice
[$ct, $shared_secret] = $kem->encap($pk);

// Now, derive a 32-byte AES key and a 16-byte IV from the shared secret
$keying_material = hash_hkdf('sha256', $shared_secret, 48, 'my-app-encryption', 'some-salt');
$aes_key = substr($keying_material, 0, 32);
$iv = substr($keying_material, 32, 16);


use Oqs\Kem;
use Oqs\Sig;

// 1. Key Encapsulation (KEM) Example with ML-KEM
$kem = new Kem(Kem::ALG_ML_KEM_768);

// Generate a public/private key pair
[$publicKey, $secretKey] = $kem->keypair();

// A client encapsulates a secret against the public key,
// generating a ciphertext and a shared secret.
[$ciphertext, $sharedSecretA] = $kem->encap($publicKey);

// The server decapsulates the ciphertext with the secret key
// to derive the same shared secret.
$sharedSecretB = $kem->decap($ciphertext, $secretKey);

assert($sharedSecretA === $sharedSecretB);
echo "KEM shared secrets match!\n";


// IMPORTANT: The raw shared secret should be passed through a KDF
// like HKDF before being used as an encryption key.
$encryption_key = hash_hkdf('sha256', $sharedSecretA, 32, 'my-app-aes-key');


// 2. Digital Signature (SIG) Example with ML-DSA
$sig = new Sig(Sig::ALG_ML_DSA_65);

// Generate a signing key pair
[$signingPublicKey, $signingSecretKey] = $sig->keypair();

$message = "This is the message to sign.";

// Sign the message with the secret key
$signature = $sig->sign($message, $signingSecretKey);

// Verify the signature against the message and public key
$isValid = $sig->verify($message, $signature, $signingPublicKey);

assert($isValid === true);
echo "Signature is valid!\n";


$kem = new Oqs\Kem('Kyber512');
$details = $kem->details();
print_r($details);
/* Output:
Array
(
    [name] => Kyber512
    [version] => ...
    [claimed_nist_level] => 1
    [ind_cca] => 1
    [length_public_key] => 800
    [length_secret_key] => 1632
    [length_ciphertext] => 768
    [length_shared_secret] => 32
)
*/

use Oqs\Kem;
use Oqs\Sig;
use Oqs\Exception as OqsException;

$kem = new Kem('ML-KEM-768');
$s = $kem->sizes();                 // ['pk'=>..,'sk'=>..,'ct'=>..,'ss'=>..]
[$pk,$sk] = $kem->keypair();        // returns [pk, sk] as binary strings
[$ct,$ssA] = $kem->encap($pk);      // encaps → [ciphertext, shared_secret]
$ssB = $kem->decap($ct, $sk);       // decaps → shared_secret
assert($ssA === $ssB);

$sig = new Sig('ML-DSA-65');
[$spk,$ssk] = $sig->keypair();
$signature = $sig->sign("hello", $ssk);
$ok = $sig->verify("hello", $signature, $spk); // bool

Kem::algorithms(); // list enabled KEM names
Sig::algorithms(); // list enabled SIG names


try {
    // This will now throw an Oqs\Exception
    $kem = new Kem('Some-Invalid-Algorithm');

} catch (OqsException $e) {
    // This block will ONLY catch exceptions thrown from your extension.
    echo "Caught an OQS-specific error: " . $e->getMessage();

} catch (\Exception $e) {
    // Other general errors would be caught here.
    echo "Caught a generic error: " . $e->getMessage();
}
sh
pie install guycalledseven/php-ext-oqs
sh
VERSION=0.2.0
PHP_MM=$(php -r 'echo PHP_MAJOR_VERSION, ".", PHP_MINOR_VERSION;')
ASSET="php_oqs-${VERSION}_php${PHP_MM}-x86_64-linux-glibc.zip"     # pick the asset for your platform
curl -fsSLO "https://github.com/guycalledseven/php-ext-oqs/releases/download/$VERSION/$ASSET"
unzip -o "$ASSET" oqs.so -d "$(php -r 'echo ini_get("extension_dir");')"
sh
php --ri oqs
dockerfile
FROM php:8.4-cli
ARG OQS_VERSION=0.2.0
RUN set -eux; \
    arch="$(uname -m | sed 's/aarch64/arm64/')"; \
    curl -fsSL -o /tmp/oqs.zip "https://github.com/guycalledseven/php-ext-oqs/releases/download/${OQS_VERSION}/php_oqs-${OQS_VERSION}_php${PHP_VERSION%.*}-${arch}-linux-glibc.zip"; \
    php -r '$z = new PharData("/tmp/oqs.zip"); $z->extractTo(ini_get("extension_dir"), "oqs.so", true);'; \
    rm /tmp/oqs.zip; \
    docker-php-ext-enable oqs
sh
sudo apt install cmake libssl-dev php-dev
sh
php -d extension=$PWD/modules/oqs.so --ri oqs | grep liboqs
bash
rm -rf build/* run-tests.php
phpize

# macOS
./configure --with-php-config=/opt/homebrew/opt/php/bin/php-config

# Debian 
# ./configure --enable-oqs
phpize
OQS_COMMIT=$(git -C /path/to/liboqs rev-parse --short HEAD) \
./configure --with-oqs=/usr/local

make clean && make -j
sh
NO_INTERACTION=1 make test                                 # all tests
NO_INTERACTION=1 make test TESTS=tests/001-basic.phpt     # a single test
cp modules/oqs.so "$(php -r 'echo ini_get("extension_dir") . "\n";')"

# enable macOS
xattr -dr com.apple.quarantine /opt/homebrew/lib/php/pecl/20240924/oqs.so
install_name_tool -add_rpath /opt/homebrew/lib "$(php -i | awk -F'=> ' '/^extension_dir/ {print $2}')/oqs.so"

# enable on linux
php -i | grep extension_dir
echo "extension=oqs.so" | sudo tee /etc/php/$(php -r 'echo PHP_MAJOR_VERSION.".".PHP_MINOR_VERSION;')/mods-available/oqs.ini
sudo phpenmod oqs 2>/dev/null || true



# php -r '$f = php_ini_scanned_files(); echo $f ? dirname(explode(",", $f)[0]) . "\n" : "none\n";'
conf
/opt/homebrew/etc/php/8.4/conf.d/oqs.ini
extension=oqs
sh
php generate-docs.php --format=stub > oqs.stub.php
sh
php generate-docs.php --format=markdown > OQS_CONSTANTS.md
sh
php -m | grep oqs
php -r '[$k]=[new Oqs\Kem("ML-KEM-768")]; var_dump($k->sizes());'