private function _processCertificate(ValidatorState $state, Certificate $cert): ValidatorState
    {
        // (a.1) verify signature
        $this->_verifySignature($state, $cert);
        // (a.2) check validity period
        $this->_checkValidity($cert);
        // (a.3) check that certificate is not revoked
        $this->_checkRevocation($cert);
        // (a.4) check issuer
        $this->_checkIssuer($state, $cert);
        // (b)(c) if certificate is self-issued and it is not
        // the final certificate in the path, skip this step
        if (!($cert->isSelfIssued() && !$state->isFinal())) {
            // (b) check permitted subtrees
            $this->_checkPermittedSubtrees($state, $cert);
            // (c) check excluded subtrees
            $this->_checkExcludedSubtrees($state, $cert);
        }
        $extensions = $cert->tbsCertificate()->extensions();
        if ($extensions->hasCertificatePolicies()) {
            // (d) process policy information
            if ($state->hasValidPolicyTree()) {
                $state = $state->validPolicyTree()->processPolicies($state,
                    $cert);
            }
        } else {
            // (e) certificate policies extension not present,
            // set the valid_policy_tree to NULL
            $state = $state->withoutValidPolicyTree();
        }
        // (f) check that explicit_policy > 0 or valid_policy_tree is set
        if (!($state->explicitPolicy() > 0 || $state->hasValidPolicyTree())) {
            throw new PathValidationException("No valid policies.");
        }
        return $state;
    }