Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Dynamic support of QPU topologies for the mapping pass #1589

Open
1 task done
bmhowe23 opened this issue Apr 30, 2024 · 5 comments
Open
1 task done

Dynamic support of QPU topologies for the mapping pass #1589

bmhowe23 opened this issue Apr 30, 2024 · 5 comments
Labels
enhancement New feature or request UnitaryHack Good issue for UnitaryHack

Comments

@bmhowe23
Copy link
Collaborator

Required prerequisites

  • Search the issue tracker to check if your feature has already been mentioned or rejected in other issues.

Describe the feature

CUDA-Q currently supports specification of QPU mapping topologies via static configuration files in

  • runtime/cudaq/platform/default/rest/helpers/iqm
  • runtime/cudaq/platform/default/rest/helpers/oqc

It would be nicer if these topologies could be dynamically fetched from their corresponding host services, either via a standalone command-line tool and/or a library call that could be integrated into the runtime. (The most ideal solution is a common implementation that supports both options.)

@bmhowe23 bmhowe23 added enhancement New feature or request UnitaryHack Good issue for UnitaryHack labels Apr 30, 2024
@owen-oqc
Copy link
Contributor

owen-oqc commented May 2, 2024

To illustrate this. The OQC SDK or the

from client.qcaas_client.client import OQCClient, QPUTask

# email = 
# password = 

def get_two_qubit_coupling(email: str, password: str) -> list:
    client = OQCClient(url='https://int.cloud.oqc.app/qpu',
                       email=email,
                       password=password)

    qpu_id = "qpu:uk:3:9829a5504g"

    calibration = client.get_calibration(qpu_id)
    # fetched from https://int.uk.cloud.oqc.app/9829a5504g/monitoring/calibrations
    return list(calibration['two_qubit'].keys())

get_two_qubit_coupling(email, password)

Return

['1-2', '10-1', '10-11', '12-13', '14-13', '14-15', '15-8', '16-17', '18-14', '19-11', '2-3', '20-19', '24-23', '24-27', '26-35', '27-34', '29-20', '29-30', '30-31', '31-30', '32-31', '33-32', '34-33', '34-35', '4-3', '4-5', '6-5', '7-16', '7-6', '8-5', '9-12', '9-2']

Shows unique couplings between different coupling similar to the static definitions here note the 1-based indexing in the above as opposed to the better zero based indexing in the cudaq routing file.

Since this is authentication protected here's a portion of the returned JSON to work against which could be included from this fake server utility as a new response

{'1-2': {'coupling': {'control_qubit': 1, 'target_qubit': 2}, 'fCX': 0.0}, '10-1': {'coupling': {'control_qubit': 10, 'target_qubit': 1}, 'fCX': 0.9999977226364618}, '10-11': {'coupling': {'control_qubit': 10, 'target_qubit': 11}, 'fCX': 0.999999}, '12-13': {'coupling': {'control_qubit': 12, 'target_qubit': 13}, 'fCX': 0.999999}, '14-13': {'coupling': {'control_qubit': 14, 'target_qubit': 13}, 'fCX': 0.999999}, '14-15': {'coupling': {'control_qubit': 14, 'target_qubit': 15}, 'fCX': 0.999999}, '15-8': {'coupling': {'control_qubit': 15, 'target_qubit': 8}, 'fCX': 0.999999}, '16-17': {'coupling': {'control_qubit': 16, 'target_qubit': 17}, 'fCX': 0.999999}, '18-14': {'coupling': {'control_qubit': 18, 'target_qubit': 14}, 'fCX': 0.999999}, '19-11': {'coupling': {'control_qubit': 19, 'target_qubit': 11}, 'fCX': 0.999999}, '2-3': {'coupling': {'control_qubit': 2, 'target_qubit': 3}, 'fCX': 0.999999}, '20-19': {'coupling': {'control_qubit': 20, 'target_qubit': 19}, 'fCX': 0.999999}, '24-23': {'coupling': {'control_qubit': 24, 'target_qubit': 23}, 'fCX': 0.999999}, '24-27': {'coupling': {'control_qubit': 24, 'target_qubit': 27}, 'fCX': 0.999999}, '26-35': {'coupling': {'control_qubit': 26, 'target_qubit': 35}, 'fCX': 0.999999}, '27-34': {'coupling': {'control_qubit': 27, 'target_qubit': 34}, 'fCX': 0}, '29-20': {'coupling': {'control_qubit': 29, 'target_qubit': 20}, 'fCX': 0.999999}, '29-30': {'coupling': {'control_qubit': 29, 'target_qubit': 30}, 'fCX': 0.0}, '30-31': {'coupling': {'control_qubit': 30, 'target_qubit': 31}, 'fCX': None}, '31-30': {'coupling': {'control_qubit': 31, 'target_qubit': 30}, 'fCX': 0.999999}, '32-31': {'coupling': {'control_qubit': 32, 'target_qubit': 31}, 'fCX': 0.999999}, '33-32': {'coupling': {'control_qubit': 33, 'target_qubit': 32}, 'fCX': None}, '34-33': {'coupling': {'control_qubit': 34, 'target_qubit': 33}, 'fCX': None}, '34-35': {'coupling': {'control_qubit': 34, 'target_qubit': 35}, 'fCX': 0.999999}, '4-3': {'coupling': {'control_qubit': 4, 'target_qubit': 3}, 'fCX': 0.6733723548983703}, '4-5': {'coupling': {'control_qubit': 4, 'target_qubit': 5}, 'fCX': 0.250}, '6-5': {'coupling': {'control_qubit': 6, 'target_qubit': 5}, 'fCX': None}, '7-16': {'coupling': {'control_qubit': 7, 'target_qubit': 16}, 'fCX': 0.999999}, '7-6': {'coupling': {'control_qubit': 7, 'target_qubit': 6}, 'fCX': 0.999999}, '8-5': {'coupling': {'control_qubit': 8, 'target_qubit': 5}, 'fCX': 0.999999}, '9-12': {'coupling': {'control_qubit': 9, 'target_qubit': 12}, 'fCX': None}, '9-2': {'coupling': {'control_qubit': 9, 'target_qubit': 2}, 'fCX': 0.0}}

@owen-oqc
Copy link
Contributor

owen-oqc commented May 2, 2024

What about using fCX to disconnect where we may have sporadic low fidelities (None, 0 or < some threshold)?

@kukushechkin
Copy link
Contributor

From the IQM side — we've recently added the possibility to specify gates per pair/qubit and in the near future we plan to make the would architecture endpoint /quantum-architecture calibration-aware.

@freetonik
Copy link

Another comment from IQM side — in addition to what @kukushechkin said above, we also plan, in near future, to incorporate fidelity data into quantum architecture, explicitly list gate implementations, and separate QPU topology data from "gates". So, overall, it should be possible to fetch:

  • QPU topology
  • list of gates, per qubit/pair, which is available with the latest (or any given, if specified) calibration
  • list of implementation per gate-locus, with priority
  • fidelities per gate-locus (when data available)

It may look something like this: /calibration/<UUID>/gates would return:

"gates": {
    "prx": {
        "implementations": {
            "drag_gaussian": {
                "priority": 0,
                "loci": [["QB1"], ["QB2"], ["QB3"], ["QB4"], ["QB5"], ["QB6"]]
            },
            "tgss_crf": {
                "priority": 1,
                "loci": [["QB1"], ["QB2"], ["QB3"], ["QB4"], ["QB5"], ["QB6"]]
            },
            ...
        }
    }, 
    ...
}

and /calibration/<UUID>/metrics would return:

"metrics": {
    ...
    "QB9-QB10.cz_gate_fidelity": {
        "value": "0.9784502054220903",
        "uncertainty": "0.0024997208080908347",
        "timestamp": "2024-04-29T14:50:28.381109"
    },
    ...
}

@bmhowe23
Copy link
Collaborator Author

bmhowe23 commented Jun 3, 2024

Just for clarification, this item is still available for anybody to grab and implement for UnityHack.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request UnitaryHack Good issue for UnitaryHack
Projects
None yet
Development

No branches or pull requests

4 participants