ket/c_api/objects.rs
1// SPDX-FileCopyrightText: 2020 Evandro Chagas Ribeiro da Rosa <evandro@quantuloop.com>
2// SPDX-FileCopyrightText: 2020 Rafael de Santiago <r.santiago@ufsc.br>
3//
4// SPDX-License-Identifier: Apache-2.0
5
6//! C API for the objects module.
7
8use crate::{execution::LogicalQubit, prelude::*};
9
10/// Retrieves the status of a qubit in the `Process` instance.
11///
12/// # Arguments
13///
14/// * `process` - \[in\] A reference to the `Process` instance.
15/// * `qubit` - \[in\] The index of the qubit to query.
16/// * `allocated` - \[out\] A mutable pointer to a `bool` indicating if the qubit is allocated.
17/// * `measured` - \[out\] A mutable pointer to a `bool` indicating if the qubit is measured.
18///
19/// # Returns
20///
21/// An integer representing the error code. `0` indicates success.
22#[no_mangle]
23pub extern "C" fn ket_process_get_qubit_status(
24 process: &mut Process,
25 qubit: usize,
26 allocated: &mut bool,
27 measured: &mut bool,
28) -> i32 {
29 let qubit = LogicalQubit::main(qubit);
30 *allocated = *process.qubit_valid.get(&qubit).unwrap_or(&true);
31 *measured = *process.qubit_measured.get(&qubit).unwrap_or(&true);
32
33 KetError::Success.error_code()
34}
35
36/// Retrieves the measurement result from the `Process` instance.
37///
38/// # Arguments
39///
40/// * `process` - \[in\] A reference to the `Process` instance.
41/// * `index` - \[in\] The index of the measurement to query.
42/// * `available` - \[out\] A mutable pointer to a `bool` indicating if the result is available.
43/// * `result` - \[out\] A mutable pointer to a `u64` storing the measurement result.
44///
45/// # Returns
46///
47/// An integer representing the error code. `0` indicates success.
48#[no_mangle]
49pub extern "C" fn ket_process_get_measurement(
50 process: &Process,
51 index: usize,
52 available: &mut bool,
53 result: &mut u64,
54) -> i32 {
55 let measurement = process.get_measure(index);
56 if let Some(measurement) = measurement {
57 *result = measurement;
58 *available = true;
59 } else {
60 *available = false;
61 }
62
63 KetError::Success.error_code()
64}
65
66/// Retrieves the expected value from the `Process` instance.
67///
68/// # Arguments
69///
70/// * `process` - \[in\] A reference to the `Process` instance.
71/// * `index` - \[in\] The index of the expected value to query.
72/// * `available` - \[out\] A mutable pointer to a `bool` indicating if the result is available.
73/// * `result` - \[out\] A mutable pointer to a `f64` storing the expected value.
74///
75/// # Returns
76///
77/// An integer representing the error code. `0` indicates success.
78#[no_mangle]
79pub extern "C" fn ket_process_get_exp_value(
80 process: &Process,
81 index: usize,
82 available: &mut bool,
83 result: &mut f64,
84) -> i32 {
85 let exp_value = process.get_exp_value(index);
86 if let Some(exp_value) = exp_value {
87 *result = exp_value;
88 *available = true;
89 } else {
90 *available = false;
91 }
92
93 KetError::Success.error_code()
94}
95
96/// Retrieves the sample data from the `Process` instance.
97///
98/// # Arguments
99///
100/// * `process` - \[in\] A reference to the `Process` instance.
101/// * `index` - \[in\] The index of the sample to query.
102/// * `available` - \[out\] A mutable pointer to a `bool` indicating if the result is available.
103/// * `result` - \[out\] A mutable pointer to the array of `u64` storing the sample data.
104/// * `count` - \[out\] A mutable pointer to the array of `u64` storing the sample counts.
105/// * `size` - \[out\] A mutable pointer to the size of the sample data arrays.
106///
107/// # Returns
108///
109/// An integer representing the error code. `0` indicates success.
110#[no_mangle]
111pub extern "C" fn ket_process_get_sample(
112 process: &Process,
113 index: usize,
114 available: &mut bool,
115 result: &mut *const u64,
116 count: &mut *const u64,
117 size: &mut usize,
118) -> i32 {
119 let sample = process.get_sample(index);
120 if let Some(sample) = sample.as_ref() {
121 *result = sample.0.as_ptr();
122 *count = sample.1.as_ptr();
123 *size = sample.0.len();
124 *available = true;
125 } else {
126 *available = false;
127 }
128
129 KetError::Success.error_code()
130}
131
132/// Retrieves the size of the dump data from the `Process` instance.
133///
134/// # Arguments
135///
136/// * `process` - \[in\] A reference to the `Process` instance.
137/// * `index` - \[in\] The index of the dump to query.
138/// * `available` - \[out\] A mutable pointer to a `bool` indicating if the result is available.
139/// * `size` - \[out\] A mutable pointer to the size of the basis states in the dump.
140///
141/// # Returns
142///
143/// An integer representing the error code. `0` indicates success.
144#[no_mangle]
145pub extern "C" fn ket_process_get_dump_size(
146 process: &Process,
147 index: usize,
148 available: &mut bool,
149 size: &mut usize,
150) -> i32 {
151 let dump = process.get_dump(index);
152 if let Some(dump) = dump.as_ref() {
153 *size = dump.basis_states.len();
154 *available = true;
155 } else {
156 *available = false;
157 }
158
159 KetError::Success.error_code()
160}
161
162/// Retrieves the dump data from the `Process` instance.
163///
164/// # Arguments
165///
166/// * `process` - \[in\] A reference to the `Process` instance.
167/// * `index` - \[in\] The index of the dump to query.
168/// * `iterator` - \[in\] The iterator for accessing individual basis states in the dump.
169/// * `basis_state` - \[out\] A mutable pointer to the array of `u64` storing the basis state.
170/// * `basis_state_size` - \[out\] A mutable pointer to the size of the basis state array.
171/// * `amplitude_real` - \[out\] A mutable pointer to the real part of the amplitude.
172/// * `amplitude_imag` - \[out\] A mutable pointer to the imaginary part of the amplitude.
173///
174/// # Returns
175///
176/// An integer representing the error code. `0` indicates success.
177///
178/// # Safety
179///
180/// This function is marked as unsafe due to the use of raw pointers.
181#[no_mangle]
182pub unsafe extern "C" fn ket_process_get_dump(
183 process: &Process,
184 index: usize,
185 iterator: usize,
186 basis_state: &mut *const u64,
187 basis_state_size: &mut usize,
188 amplitude_real: &mut f64,
189 amplitude_imag: &mut f64,
190) -> i32 {
191 let dump = process.get_dump(index).unwrap();
192 let state = dump.basis_states[iterator].as_ptr();
193 let size = dump.basis_states[iterator].len();
194 *basis_state = state;
195 *basis_state_size = size;
196 *amplitude_real = dump.amplitudes_real[iterator];
197 *amplitude_imag = dump.amplitudes_imag[iterator];
198
199 KetError::Success.error_code()
200}