def _strat_has_stabilizer_effect_from_unitary(val: Any) -> bool | None:
    """Attempts to infer whether val has stabilizer effect from its unitary.

    Returns whether unitary of `val` normalizes the Pauli group. Works only for
    2x2 unitaries.
    """
    # Do not try this strategy if there is no unitary or if the number of
    # qubits is greater than 3 since that would be expensive.
    qid_shape = qid_shape_protocol.qid_shape(val, default=None)
    if (
        qid_shape is None
        or len(qid_shape) > 3
        or qid_shape != (2,) * len(qid_shape)
        or not has_unitary_protocol.has_unitary(val)
    ):
        return None
    unitary = unitary_protocol.unitary(val)
    if len(qid_shape) == 1:
        return SingleQubitCliffordGate.from_unitary(unitary) is not None

    # Check if the action of the unitary on each single qubit pauli string leads to a pauli product.
    # Source: https://quantumcomputing.stackexchange.com/a/13158
    for q_idx in range(len(qid_shape)):
        for g in 'XZ':
            pauli_string = ['I'] * len(qid_shape)
            pauli_string[q_idx] = g
            ps = DensePauliString(pauli_string)
            p = ps._unitary_()
            if not pauli_string_decomposition.unitary_to_pauli_string(
                (unitary @ p @ unitary.T.conj())
            ):
                return False
    return True
Attempts to infer whether val has stabilizer effect from its unitary.

    Returns whether unitary of `val` normalizes the Pauli group. Works only for
    2x2 unitaries.
    
cirq-core/cirq/protocols/has_stabilizer_effect_protocol.py