Skip to main content
Yanked

This release has been yanked by its maintainers, and will be ignored by installers, except when explicitly specified.
Consider using release 0.6.1 instead.

Python Bindings for DCAP-QVL

Python bindings for parsing and verifying Intel SGX/TDX DCAP (Data Center Attestation Primitives) quotes. Built on a Rust implementation for use in TEE (Trusted Execution Environment) remote attestation workflows.

Quick Start

# Install from PyPI
pip install dcap-qvl

# Basic usage
python -c "
import dcap_qvl
print('DCAP-QVL Python bindings successfully installed!')
print(f'Available functions: {dcap_qvl.__all__}')
"

Features

  • Parse and inspect SGX/TDX quotes (headers, reports, embedded certificates)
  • Extract PCK certificate extension fields (FMSPC, PPID, CPU SVN, etc.) or look up arbitrary OIDs
  • Verify SGX and TDX quotes against collateral data
  • Handle quote collateral data (serialize/deserialize JSON)
  • Asynchronous collateral fetching from PCCS/PCS with async/await support
  • Pure Rust implementation with Python bindings
  • Cross-platform compatibility (Linux, macOS, Windows)
  • Compatible with Python 3.8+

Installation

From PyPI (recommended)

pip install dcap-qvl

Using uv

uv add dcap-qvl

Usage

Parsing Quotes

import dcap_qvl

raw = open("quote.bin", "rb").read()
quote = dcap_qvl.parse_quote(raw)

# Quote type
print(quote.quote_type())  # "SGX" or "TDX"
print(quote.fmspc())       # e.g. "B0C06F000000"

# Header fields
hdr = quote.header
print(hdr.version, hdr.tee_type, hdr.attestation_key_type)

# Report body (TdReport10, TdReport15, or SgxEnclaveReport)
report = quote.report
if quote.is_tdx():
    print(report.mr_td.hex())
    print(report.rt_mr0.hex())
else:
    print(report.mr_enclave.hex())
    print(report.mr_signer.hex())
print(report.report_data.hex())

# Embedded PEM certificate chain
pem = quote.cert_chain_pem_bytes()  # bytes or None

PCK Extension Parsing

# From a parsed quote
ext = quote.pck_extension()  # PckExtension or None
if ext:
    print(ext.fmspc.hex())   # 6-byte FMSPC
    print(ext.ppid.hex())    # PPID
    print(ext.cpu_svn.hex()) # CPU SVN
    print(ext.pce_svn)       # PCE SVN (int)
    print(ext.pce_id.hex())  # PCE ID
    print(ext.sgx_type)      # SGX type (int)

# From a PEM certificate chain directly
ext = dcap_qvl.parse_pck_extension_from_pem(pem_bytes)
print(ext.fmspc.hex())

# Look up any OID in the Intel SGX extension (recursive search)
value = ext.get_value("1.2.840.113741.1.13.1.2.17")  # PCESVN
if value is not None:
    print(value.hex())

Basic Quote Verification

import dcap_qvl
import json
import time

# Load quote data (binary)
with open("path/to/quote", "rb") as f:
    quote_data = f.read()

# Load collateral data (JSON)
with open("path/to/collateral.json", "r") as f:
    collateral_json = json.load(f)

# Create collateral object
collateral = dcap_qvl.QuoteCollateralV3.from_json(json.dumps(collateral_json))

# Verify the quote
now = int(time.time())
try:
    result = dcap_qvl.verify(quote_data, collateral, now)
    print(f"Verification successful! Status: {result.status}")
    print(f"Advisory IDs: {result.advisory_ids}")
except ValueError as e:
    print(f"Verification failed: {e}")

Working with Collateral Data

# Create collateral manually
collateral = dcap_qvl.QuoteCollateralV3(
    pck_crl_issuer_chain="...",
    root_ca_crl=b"...",  # bytes
    pck_crl=b"...",      # bytes
    tcb_info_issuer_chain="...",
    tcb_info="...",      # JSON string
    tcb_info_signature=b"...",  # bytes
    qe_identity_issuer_chain="...",
    qe_identity="...",   # JSON string
    qe_identity_signature=b"...",  # bytes
)

# Serialize to JSON
json_str = collateral.to_json()

# Deserialize from JSON
collateral = dcap_qvl.QuoteCollateralV3.from_json(json_str)

API Reference

Async Collateral Functions

All collateral functions are asynchronous and must be awaited. They use the Rust async runtime for optimal performance.

async get_collateral(pccs_url: str, raw_quote: bytes) -> QuoteCollateralV3

Fetch full collateral (PCK cert chain, TCB info, QE identity, CRLs) for a raw DCAP quote from the given PCCS / PCS URL. Handles every supported certification data type (including cert_type 2 / 3 where the PCK cert is retrieved from PCCS via encrypted PPID).

Parameters:

Returns:

  • QuoteCollateralV3: Quote collateral data (with PCK certificate chain attached)

Raises:

  • ValueError: If the quote is invalid, the HTTP client can't be built, or the PCCS / PCS fetch fails

Example:

import asyncio
import dcap_qvl

async def main():
    pccs_url = "https://api.trustedservices.intel.com"
    quote_data = open("quote.bin", "rb").read()
    collateral = await dcap_qvl.get_collateral(pccs_url, quote_data)
    print(f"Got collateral: {len(collateral.tcb_info)} chars")

asyncio.run(main())

async get_collateral_from_pcs(raw_quote: bytes) -> QuoteCollateralV3

Get collateral from Intel's PCS (default).

Parameters:

  • raw_quote: Raw quote data as bytes

Returns:

  • QuoteCollateralV3: Quote collateral data

Raises:

  • ValueError: If quote is invalid or FMSPC cannot be extracted
  • RuntimeError: If network request fails

Example:

import asyncio
import dcap_qvl

async def main():
    quote_data = open("quote.bin", "rb").read()
    collateral = await dcap_qvl.get_collateral_from_pcs(quote_data)
    print(f"Got collateral from Intel PCS")

asyncio.run(main())

async get_collateral_and_verify(raw_quote: bytes, pccs_url: Optional[str] = None) -> VerifiedReport

Get collateral and verify quote in one step.

Parameters:

  • raw_quote: Raw quote data as bytes
  • pccs_url: Optional PCCS URL (uses Intel PCS if None)

Returns:

  • VerifiedReport: Verification results

Raises:

  • ValueError: If quote is invalid or verification fails
  • RuntimeError: If network request fails

Example:

import asyncio
import dcap_qvl

async def main():
    quote_data = open("quote.bin", "rb").read()
    result = await dcap_qvl.get_collateral_and_verify(quote_data)
    print(f"Status: {result.status}")
    print(f"Advisory IDs: {result.advisory_ids}")

asyncio.run(main())

Classes

QuoteCollateralV3

Represents quote collateral data required for verification.

Constructor:

QuoteCollateralV3(
    pck_crl_issuer_chain: str,
    root_ca_crl: bytes,
    pck_crl: bytes,
    tcb_info_issuer_chain: str,
    tcb_info: str,
    tcb_info_signature: bytes,
    qe_identity_issuer_chain: str,
    qe_identity: str,
    qe_identity_signature: bytes,
)

Methods:

  • to_json() -> str: Serialize to JSON string
  • from_json(json_str: str) -> QuoteCollateralV3: Create from JSON string (static method)

Properties:

  • pck_crl_issuer_chain: str
  • root_ca_crl: bytes
  • pck_crl: bytes
  • tcb_info_issuer_chain: str
  • tcb_info: str
  • tcb_info_signature: bytes
  • qe_identity_issuer_chain: str
  • qe_identity: str
  • qe_identity_signature: bytes

VerifiedReport

Contains the results of quote verification.

Properties:

  • status: str: Verification status (e.g., "OK", "SW_HARDENING_NEEDED", "CONFIGURATION_NEEDED", "OUT_OF_DATE", "REVOKED")
  • advisory_ids: List[str]: List of Intel security advisory IDs (e.g., "INTEL-SA-00334")
  • ppid: bytes: Platform PPID parsed from the PCK certificate

Methods:

  • to_json() -> str: Serialize to JSON string

Quote

Represents a parsed SGX or TDX quote. Created via parse_quote() or Quote.parse().

Properties:

  • header: QuoteHeader: Parsed quote header
  • report: Union[TdReport10, TdReport15, SgxEnclaveReport]: Parsed report body

Methods:

  • parse(raw_quote: bytes) -> Quote: Parse from raw bytes (static method)
  • fmspc() -> str: FMSPC as uppercase hex string
  • ca() -> str: Certificate Authority identifier
  • is_sgx() -> bool / is_tdx() -> bool: Check quote type
  • quote_type() -> str: Returns "SGX" or "TDX"
  • cert_chain_pem_bytes() -> Optional[bytes]: Embedded PEM certificate chain
  • pck_extension() -> Optional[PckExtension]: Parse Intel SGX extension from leaf PCK cert

QuoteHeader

Properties:

  • version: int, attestation_key_type: int, tee_type: int
  • qe_svn: int, pce_svn: int
  • qe_vendor_id: bytes (16 bytes), user_data: bytes (20 bytes)

TdReport10 / TdReport15

TDX TDREPORT structures. TdReport15 extends TdReport10 with tee_tcb_svn2 and mr_service_td.

Properties (TdReport10):

  • tee_tcb_svn: bytes, mr_seam: bytes, mr_signer_seam: bytes, seam_attributes: bytes
  • td_attributes: bytes, xfam: bytes, mr_td: bytes, mr_config_id: bytes
  • mr_owner: bytes, mr_owner_config: bytes
  • rt_mr0: bytes, rt_mr1: bytes, rt_mr2: bytes, rt_mr3: bytes
  • report_data: bytes

SgxEnclaveReport

Properties:

  • cpu_svn: bytes, attributes: bytes
  • mr_enclave: bytes, mr_signer: bytes
  • report_data: bytes

PckExtension

Parsed values from the Intel SGX extension in the PCK leaf certificate.

Properties:

  • ppid: bytes, cpu_svn: bytes, pce_svn: int, pce_id: bytes
  • fmspc: bytes (6 bytes), sgx_type: int
  • platform_instance_id: Optional[bytes]

Methods:

  • get_value(oid: str) -> Optional[bytes]: Look up any OID in the Intel SGX extension by dotted-decimal string. Returns raw DER value bytes, or None if not found.

Functions

parse_quote(raw_quote: bytes) -> Quote

Parse a raw SGX or TDX quote from bytes.

parse_pck_extension_from_pem(pem_bytes: bytes) -> PckExtension

Parse the Intel SGX extension from a PEM-encoded certificate chain (uses the first/leaf certificate).

verify(raw_quote: bytes, collateral: QuoteCollateralV3, now_secs: int) -> VerifiedReport

Verify a quote with the provided collateral data.

Parameters:

  • raw_quote: Raw quote data as bytes
  • collateral: Quote collateral data
  • now_secs: Current timestamp in seconds since Unix epoch

Returns:

  • VerifiedReport: Verification results

Raises:

  • ValueError: If verification fails

verify_with_root_ca(raw_quote: bytes, collateral: QuoteCollateralV3, root_ca_der: bytes, now_secs: int) -> VerifiedReport

Verify a quote with a custom root CA certificate (DER format) instead of the built-in Intel root CA.

Development

Building from Source

If you want to build from source or contribute to development:

# Clone the repository
git clone https://github.com/Phala-Network/dcap-qvl.git
cd dcap-qvl/python-bindings

# Install development dependencies (including maturin)
uv sync

# Build and install the Python extension in development mode
uv run maturin develop --features python

# Run tests
uv run pytest tests/ -v

Note: maturin is only required for building from source. Regular users installing from PyPI don't need maturin.

Running Examples

After installing the package, you can run the examples:

# Download the examples from the repository
git clone https://github.com/Phala-Network/dcap-qvl.git
cd dcap-qvl/python-bindings

# Basic functionality test
python examples/basic_test.py

# Full example (requires sample data files)
python examples/python_example.py

Or if you're using uv for development:

# Basic functionality test
uv run python examples/basic_test.py

# Full example (requires sample data files)
uv run python examples/python_example.py

Testing Across Python Versions

The project includes comprehensive testing across all supported Python versions:

# Quick test across all Python versions
make test_python_versions

# Test current Python version only
make test_python

See PYTHON_TESTING.md for detailed information about Python version compatibility testing.

Requirements

For regular usage (installing from PyPI):

  • Python 3.8+

For development (building from source):

  • Python 3.8+
  • Rust toolchain (rustc, cargo) 1.83+
  • maturin (automatically installed with uv sync)

License

MIT License - see LICENSE for details.

Contributing

Contributions are welcome! Please feel free to submit a Pull Request.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

dcap_qvl-0.6.0.tar.gz (287.4 kB view details)

Uploaded Source

Built Distributions

If you're not sure about the file name format, learn more about wheel file names.

dcap_qvl-0.6.0-cp38-abi3-win_amd64.whl (2.1 MB view details)

Uploaded CPython 3.8+Windows x86-64

dcap_qvl-0.6.0-cp38-abi3-musllinux_1_1_x86_64.whl (2.7 MB view details)

Uploaded CPython 3.8+musllinux: musl 1.1+ x86-64

dcap_qvl-0.6.0-cp38-abi3-musllinux_1_1_aarch64.whl (2.6 MB view details)

Uploaded CPython 3.8+musllinux: musl 1.1+ ARM64

dcap_qvl-0.6.0-cp38-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl (2.7 MB view details)

Uploaded CPython 3.8+manylinux: glibc 2.17+ x86-64

dcap_qvl-0.6.0-cp38-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl (2.6 MB view details)

Uploaded CPython 3.8+manylinux: glibc 2.17+ ARM64

dcap_qvl-0.6.0-cp38-abi3-macosx_11_0_arm64.whl (2.3 MB view details)

Uploaded CPython 3.8+macOS 11.0+ ARM64

dcap_qvl-0.6.0-cp38-abi3-macosx_10_12_x86_64.whl (2.4 MB view details)

Uploaded CPython 3.8+macOS 10.12+ x86-64

File details

Details for the file dcap_qvl-0.6.0.tar.gz.

File metadata

  • Download URL: dcap_qvl-0.6.0.tar.gz
  • Upload date:
  • Size: 287.4 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.14

File hashes

Hashes for dcap_qvl-0.6.0.tar.gz
Algorithm Hash digest
SHA256 525023ea23471f84de060ba3edff31a36e7397e8daa1981cefc654dac28cac0d
MD5 47b7c9f34e36bbc9b06f8e3f31536664
BLAKE2b-256 b71ff911f4cf1ac8038cfefe8289fbf306d0bebf92371d1ccbfb73a190655bb4

See more details on using hashes here.

Provenance

The following attestation bundles were made for dcap_qvl-0.6.0.tar.gz:

Publisher: python-wheels.yml on Phala-Network/dcap-qvl

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file dcap_qvl-0.6.0-cp38-abi3-win_amd64.whl.

File metadata

  • Download URL: dcap_qvl-0.6.0-cp38-abi3-win_amd64.whl
  • Upload date:
  • Size: 2.1 MB
  • Tags: CPython 3.8+, Windows x86-64
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.13.14

File hashes

Hashes for dcap_qvl-0.6.0-cp38-abi3-win_amd64.whl
Algorithm Hash digest
SHA256 9d8fedfa5561dd5682c23880c18faea782d1e972b1249ceb4df27ce43e78da25
MD5 76f42d498e7e8791f15abfcdb1a670fd
BLAKE2b-256 7b51fe61f3850fa257a11df272fb9119a9552adcb33bd1b80f1a36dd572efac6

See more details on using hashes here.

Provenance

The following attestation bundles were made for dcap_qvl-0.6.0-cp38-abi3-win_amd64.whl:

Publisher: python-wheels.yml on Phala-Network/dcap-qvl

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file dcap_qvl-0.6.0-cp38-abi3-musllinux_1_1_x86_64.whl.

File metadata

File hashes

Hashes for dcap_qvl-0.6.0-cp38-abi3-musllinux_1_1_x86_64.whl
Algorithm Hash digest
SHA256 5f47f96944193ac5be1f38cfef7585a5b0572aafc07f792f743f423d3077d25d
MD5 12a3bd8f5d37f35b241627db2dd6761f
BLAKE2b-256 2617d27fb6ca24402a257bfbd64bda53efb86b1158d75e9809abc876e8de5b14

See more details on using hashes here.

Provenance

The following attestation bundles were made for dcap_qvl-0.6.0-cp38-abi3-musllinux_1_1_x86_64.whl:

Publisher: python-wheels.yml on Phala-Network/dcap-qvl

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file dcap_qvl-0.6.0-cp38-abi3-musllinux_1_1_aarch64.whl.

File metadata

File hashes

Hashes for dcap_qvl-0.6.0-cp38-abi3-musllinux_1_1_aarch64.whl
Algorithm Hash digest
SHA256 f39b21370e7f5d73f475101094ecdfcc1c264ee0b12945233dabcd7532382b4e
MD5 92e175e5cafcfb5c8686c3290aca61b1
BLAKE2b-256 7b0042c1649aac0255eaf70beadb1e5d37e7cbb3fe23c262a1a746982a9cb965

See more details on using hashes here.

Provenance

The following attestation bundles were made for dcap_qvl-0.6.0-cp38-abi3-musllinux_1_1_aarch64.whl:

Publisher: python-wheels.yml on Phala-Network/dcap-qvl

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file dcap_qvl-0.6.0-cp38-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl.

File metadata

File hashes

Hashes for dcap_qvl-0.6.0-cp38-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl
Algorithm Hash digest
SHA256 c22e42020bb24fab4ca45ac0033d456c9c47927f280ecd145a626786b50c62d3
MD5 562815a559a7ce1ee483b3886d73cb05
BLAKE2b-256 b120f3a2c9db9c759b7499d792eb3636984f15c13556fed696891636913201aa

See more details on using hashes here.

Provenance

The following attestation bundles were made for dcap_qvl-0.6.0-cp38-abi3-manylinux_2_17_x86_64.manylinux2014_x86_64.whl:

Publisher: python-wheels.yml on Phala-Network/dcap-qvl

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file dcap_qvl-0.6.0-cp38-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl.

File metadata

File hashes

Hashes for dcap_qvl-0.6.0-cp38-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl
Algorithm Hash digest
SHA256 028ee7412c3411bd8bb9470bee31bc73b15fef0d5c6497576f6177aa58ec6058
MD5 348691762a13c76b1c3740273d3743ef
BLAKE2b-256 a41d4df33eddbdefdb973b620736d17b082e2d5ec491a5e463805cf4aa17ad27

See more details on using hashes here.

Provenance

The following attestation bundles were made for dcap_qvl-0.6.0-cp38-abi3-manylinux_2_17_aarch64.manylinux2014_aarch64.whl:

Publisher: python-wheels.yml on Phala-Network/dcap-qvl

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file dcap_qvl-0.6.0-cp38-abi3-macosx_11_0_arm64.whl.

File metadata

File hashes

Hashes for dcap_qvl-0.6.0-cp38-abi3-macosx_11_0_arm64.whl
Algorithm Hash digest
SHA256 9971506dfe8fc14c16674fc8d0d35108dc3a093ab34bbd65a488cc965eb030e1
MD5 4e14cb70a1396ad9965623e0ab6ec797
BLAKE2b-256 4f18cec578ae4f94c5bcdcc49371d30e8471d9238af451b68cbed67718b5e314

See more details on using hashes here.

Provenance

The following attestation bundles were made for dcap_qvl-0.6.0-cp38-abi3-macosx_11_0_arm64.whl:

Publisher: python-wheels.yml on Phala-Network/dcap-qvl

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file dcap_qvl-0.6.0-cp38-abi3-macosx_10_12_x86_64.whl.

File metadata

File hashes

Hashes for dcap_qvl-0.6.0-cp38-abi3-macosx_10_12_x86_64.whl
Algorithm Hash digest
SHA256 22d57ae5b21a1bf3211f1d0ca1d3197144ace2c65790e8d4c290045a1ccd3f78
MD5 b9e3e14baf0bae356f48cdf1474f752d
BLAKE2b-256 f187e7ac5076ef7dc969fb59d27ead74e709f65b50e63c019d9628c8a8e82196

See more details on using hashes here.

Provenance

The following attestation bundles were made for dcap_qvl-0.6.0-cp38-abi3-macosx_10_12_x86_64.whl:

Publisher: python-wheels.yml on Phala-Network/dcap-qvl

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Release history Release notifications | RSS feed

0.6.1

8 files

This release

0.6.0 This release

8 files

0.5.3

8 files

0.5.2

8 files

0.4.0

8 files

0.3.13

8 files

0.3.12

8 files

0.3.11

8 files

0.3.10

8 files

0.3.9

8 files

0.3.8

8 files

0.3.7

8 files

0.3.6

8 files

0.3.5

8 files

0.3.4

8 files

0.3.2

8 files

0.3.0

8 files

0.2.2

2 files

0.1.3

2 files

0.1.2

1 file

0.1.1

1 file

0.1.0

3 files

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page