From 946c47c8ef8592eabb7eed054546c627dbaee37b Mon Sep 17 00:00:00 2001 From: Matthew Treinish Date: Fri, 4 Mar 2022 10:05:59 -0500 Subject: [PATCH 1/7] Upgrade PyO3 and numpy to 0.16.0 This commit updates pyo3 and numpy to the latest release 0.16.0. The details on these releases can be found here: https://pyo3.rs/v0.16.0/changelog.html and https://github.com/PyO3/rust-numpy/blob/main/CHANGELOG.md Unfortunately there are a number of breaking changes and deprecations we will have to update our usage to account for. This commit starts the process by fixing the compiler errors due to changes in behavior a subsequent commit will address the deprecation warnings. --- Cargo.lock | 103 ++++++------------ Cargo.toml | 4 +- src/cartesian_product.rs | 4 +- src/coloring.rs | 2 +- ...ected_components.rs => conn_components.rs} | 0 src/connectivity/mod.rs | 18 +-- src/dag_algo/mod.rs | 8 +- src/isomorphism/mod.rs | 12 +- src/iterators.rs | 2 +- src/lib.rs | 6 +- src/matching/mod.rs | 4 +- src/shortest_path/mod.rs | 8 +- src/tensor_product.rs | 4 +- src/transitivity.rs | 4 +- src/traversal/bfs_visit.rs | 4 +- src/traversal/dfs_visit.rs | 2 +- src/traversal/dijkstra_visit.rs | 4 +- src/traversal/mod.rs | 10 +- src/union.rs | 4 +- 19 files changed, 83 insertions(+), 120 deletions(-) rename src/connectivity/{connected_components.rs => conn_components.rs} (100%) diff --git a/Cargo.lock b/Cargo.lock index bb3f19931..a2eefb233 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -25,12 +25,6 @@ version = "1.3.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a" -[[package]] -name = "cfg-if" -version = "0.1.10" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822" - [[package]] name = "cfg-if" version = "1.0.0" @@ -43,7 +37,7 @@ version = "0.5.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "06ed27e177f16d65f0f0c22a213e17c696ace5dd64b14258b52f9417ccb52db4" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "crossbeam-utils", ] @@ -53,7 +47,7 @@ version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "6455c0ca19f0d2fbf751b908d5c55c1f5cbc65e03c4225427254b46890bdde1e" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "crossbeam-epoch", "crossbeam-utils", ] @@ -64,7 +58,7 @@ version = "0.9.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "4ec02e091aa634e2c3ada4a392989e7c3116673ef0ac5b72232439094d73b7fd" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "crossbeam-utils", "lazy_static", "memoffset", @@ -77,7 +71,7 @@ version = "0.8.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d82cfc11ce7f2c3faef78d8a684447b40d503d9681acebed6cb728d45940c4db" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "lazy_static", ] @@ -99,7 +93,7 @@ version = "0.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "7fcd999463524c52659517fe2cea98493cfe485d10565e7b0fb07dbba7ad2753" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "libc", "wasi", ] @@ -136,24 +130,10 @@ dependencies = [ [[package]] name = "indoc" -version = "0.3.6" +version = "1.0.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "47741a8bc60fb26eb8d6e0238bbb26d8575ff623fdc97b1a2c00c050b9684ed8" +checksum = "e7906a9fababaeacb774f72410e497a1d18de916322e33797bb2cd29baa23c9e" dependencies = [ - "indoc-impl", - "proc-macro-hack", -] - -[[package]] -name = "indoc-impl" -version = "0.3.6" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ce046d161f000fffde5f432a0d034d0341dc152643b2598ed5bfce44c4f3a8f0" -dependencies = [ - "proc-macro-hack", - "proc-macro2", - "quote", - "syn", "unindent", ] @@ -163,7 +143,7 @@ version = "0.1.10" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "bee0328b1209d157ef001c94dd85b4f8f64139adb0eac2659f4b08382b2f474d" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", ] [[package]] @@ -280,11 +260,10 @@ dependencies = [ [[package]] name = "numpy" -version = "0.15.1" +version = "0.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7f3a190dd1aa88ee0de91e59e970d5b85cfa079a9ff6531b69f811ccd0c2a6e1" +checksum = "9e051c9e722a66c2e619b2a30f731e80b75f172d98ae3518b61b08a1d3d850a3" dependencies = [ - "cfg-if 0.1.10", "libc", "ndarray", "num-complex 0.4.0", @@ -315,7 +294,7 @@ version = "0.8.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d76e8e1493bcac0d2766c42737f34458f1c8c50c0d23bcb24ea953affb273216" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "instant", "libc", "redox_syscall", @@ -323,25 +302,6 @@ dependencies = [ "winapi", ] -[[package]] -name = "paste" -version = "0.1.18" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "45ca20c77d80be666aef2b45486da86238fabe33e38306bd3118fe4af33fa880" -dependencies = [ - "paste-impl", - "proc-macro-hack", -] - -[[package]] -name = "paste-impl" -version = "0.1.18" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d95a7db200b97ef370c8e6de0088252f7e0dfff7d047a28528e47456c0fc98b6" -dependencies = [ - "proc-macro-hack", -] - [[package]] name = "petgraph" version = "0.6.0" @@ -358,12 +318,6 @@ version = "0.2.10" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "ac74c624d6b2d21f425f752262f42188365d7b8ff1aff74c82e45136510a4857" -[[package]] -name = "proc-macro-hack" -version = "0.5.19" -source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dbf0c48bc1d91375ae5c3cd81e3722dff1abcf81a30960240640d223f59fe0e5" - [[package]] name = "proc-macro2" version = "1.0.29" @@ -375,11 +329,11 @@ dependencies = [ [[package]] name = "pyo3" -version = "0.15.1" +version = "0.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7cf01dbf1c05af0a14c7779ed6f3aa9deac9c3419606ac9de537a2d649005720" +checksum = "9d1a3df45cb95bd954fac00bd9609062640fd7fb9e9946a660092c9e015421fb" dependencies = [ - "cfg-if 1.0.0", + "cfg-if", "hashbrown", "indexmap", "indoc", @@ -387,27 +341,38 @@ dependencies = [ "num-bigint", "num-complex 0.4.0", "parking_lot", - "paste", "pyo3-build-config", + "pyo3-ffi", "pyo3-macros", "unindent", ] [[package]] name = "pyo3-build-config" -version = "0.15.1" +version = "0.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dbf9e4d128bfbddc898ad3409900080d8d5095c379632fbbfbb9c8cfb1fb852b" +checksum = "386a68f0f5f2f9932815068bc8049a56989f2437d96dbb31d1fb11b63ce90364" dependencies = [ "once_cell", ] +[[package]] +name = "pyo3-ffi" +version = "0.16.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a9a4e2f74dc77eea5ce11d19f0afaeb632b6590f8cbb1d5ee2f1330b766803e8" +dependencies = [ + "libc", + "pyo3-build-config", +] + [[package]] name = "pyo3-macros" -version = "0.15.1" +version = "0.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "67701eb32b1f9a9722b4bc54b548ff9d7ebfded011c12daece7b9063be1fd755" +checksum = "dbff3a1579934968a53bcc78ac33663ed2577accda05d484097679cc8d28e52d" dependencies = [ + "proc-macro2", "pyo3-macros-backend", "quote", "syn", @@ -415,9 +380,9 @@ dependencies = [ [[package]] name = "pyo3-macros-backend" -version = "0.15.1" +version = "0.16.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f44f09e825ee49a105f2c7b23ebee50886a9aee0746f4dd5a704138a64b0218a" +checksum = "90644126c8c1ac7b47f794dd20a5729f8646b91c49edb31689c90f8cb3c33ea9" dependencies = [ "proc-macro2", "pyo3-build-config", @@ -576,9 +541,9 @@ checksum = "8ccb82d61f80a663efe1f787a51b16b5a51e3314d6ac365b08639f52387b33f3" [[package]] name = "unindent" -version = "0.1.7" +version = "0.1.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f14ee04d9415b52b3aeab06258a3f07093182b88ba0f9b8d203f211a7a7d41c7" +checksum = "514672a55d7380da379785a4d70ca8386c8883ff7eaae877be4d2081cebe73d8" [[package]] name = "version_check" diff --git a/Cargo.toml b/Cargo.toml index dca1eed8c..0eadadd3d 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -22,7 +22,7 @@ crate-type = ["cdylib"] ahash = { version = "0.7.6", default-features = false } petgraph = "0.6.0" fixedbitset = "0.4.1" -numpy = "0.15.1" +numpy = "0.16.0" rand = "0.8" rand_pcg = "0.3" rayon = "1.5" @@ -32,7 +32,7 @@ num-complex = "0.4" retworkx-core = { path = "./retworkx-core" } [dependencies.pyo3] -version = "0.15.1" +version = "0.16.0" features = ["extension-module", "hashbrown", "num-bigint", "num-complex", "indexmap"] [dependencies.hashbrown] diff --git a/src/cartesian_product.rs b/src/cartesian_product.rs index aa7c1490e..4e69e4e56 100644 --- a/src/cartesian_product.rs +++ b/src/cartesian_product.rs @@ -100,7 +100,7 @@ fn cartesian_product( /// mpl_draw(graph_product) #[pyfunction()] #[pyo3(text_signature = "(first, second, /)")] -fn graph_cartesian_product( +pub fn graph_cartesian_product( py: Python, first: &graph::PyGraph, second: &graph::PyGraph, @@ -149,7 +149,7 @@ fn graph_cartesian_product( /// mpl_draw(graph_product) #[pyfunction()] #[pyo3(text_signature = "(first, second, /)")] -fn digraph_cartesian_product( +pub fn digraph_cartesian_product( py: Python, first: &digraph::PyDiGraph, second: &digraph::PyDiGraph, diff --git a/src/coloring.rs b/src/coloring.rs index c2b708e75..c81c80835 100644 --- a/src/coloring.rs +++ b/src/coloring.rs @@ -35,7 +35,7 @@ use rayon::prelude::*; /// :rtype: dict #[pyfunction] #[pyo3(text_signature = "(graph, /)")] -fn graph_greedy_color(py: Python, graph: &graph::PyGraph) -> PyResult { +pub fn graph_greedy_color(py: Python, graph: &graph::PyGraph) -> PyResult { let mut colors: DictMap = DictMap::new(); let mut node_vec: Vec = graph.graph.node_indices().collect(); let mut sort_map: HashMap = HashMap::with_capacity(graph.node_count()); diff --git a/src/connectivity/connected_components.rs b/src/connectivity/conn_components.rs similarity index 100% rename from src/connectivity/connected_components.rs rename to src/connectivity/conn_components.rs diff --git a/src/connectivity/mod.rs b/src/connectivity/mod.rs index d6b260d80..a833264a3 100644 --- a/src/connectivity/mod.rs +++ b/src/connectivity/mod.rs @@ -12,7 +12,7 @@ #![allow(clippy::float_cmp)] -mod connected_components; +mod conn_components; mod core_number; use super::{digraph, get_edge_iter_with_weights, graph, weight_callable, InvalidNode, NullGraph}; @@ -228,8 +228,8 @@ pub fn digraph_find_cycle(graph: &digraph::PyDiGraph, source: Option) -> /// :rtype: int #[pyfunction] #[pyo3(text_signature = "(graph, /)")] -fn number_connected_components(graph: &graph::PyGraph) -> usize { - connected_components::number_connected_components(&graph.graph) +pub fn number_connected_components(graph: &graph::PyGraph) -> usize { + conn_components::number_connected_components(&graph.graph) } /// Find the connected components in an undirected graph @@ -242,7 +242,7 @@ fn number_connected_components(graph: &graph::PyGraph) -> usize { #[pyfunction] #[pyo3(text_signature = "(graph, /)")] pub fn connected_components(graph: &graph::PyGraph) -> Vec> { - connected_components::connected_components(&graph.graph) + conn_components::connected_components(&graph.graph) } /// Returns the set of nodes in the component of graph containing `node`. @@ -265,7 +265,7 @@ pub fn node_connected_component(graph: &graph::PyGraph, node: usize) -> PyResult )); } - Ok(connected_components::bfs_undirected( + Ok(conn_components::bfs_undirected( &graph.graph, node, &mut graph.graph.visit_map(), @@ -301,7 +301,7 @@ pub fn is_connected(graph: &graph::PyGraph) -> PyResult { /// :rtype: int #[pyfunction] #[pyo3(text_signature = "(graph, /)")] -fn number_weakly_connected_components(graph: &digraph::PyDiGraph) -> usize { +pub fn number_weakly_connected_components(graph: &digraph::PyDiGraph) -> usize { let mut weak_components = graph.node_count(); let mut vertex_sets = UnionFind::new(graph.graph.node_bound()); for edge in graph.graph.edge_references() { @@ -325,7 +325,7 @@ fn number_weakly_connected_components(graph: &digraph::PyDiGraph) -> usize { #[pyfunction] #[pyo3(text_signature = "(graph, /)")] pub fn weakly_connected_components(graph: &digraph::PyDiGraph) -> Vec> { - connected_components::connected_components(&graph.graph) + conn_components::connected_components(&graph.graph) } /// Check if the graph is weakly connected @@ -535,7 +535,7 @@ pub fn digraph_complement(py: Python, graph: &digraph::PyDiGraph) -> PyResult) -> /// :rtype: list #[pyfunction] #[pyo3(text_signature = "(dag, key, /)")] -fn lexicographical_topological_sort( +pub fn lexicographical_topological_sort( py: Python, dag: &digraph::PyDiGraph, key: PyObject, @@ -400,7 +400,7 @@ fn lexicographical_topological_sort( /// :raises DAGHasCycle: if a cycle is encountered while sorting the graph #[pyfunction] #[pyo3(text_signature = "(graph, /)")] -fn topological_sort(graph: &digraph::PyDiGraph) -> PyResult { +pub fn topological_sort(graph: &digraph::PyDiGraph) -> PyResult { let nodes = match algo::toposort(&graph.graph, None) { Ok(nodes) => nodes, Err(_err) => return Err(DAGHasCycle::new_err("Sort encountered a cycle")), @@ -427,7 +427,7 @@ fn topological_sort(graph: &digraph::PyDiGraph) -> PyResult { /// :rtype: list #[pyfunction] #[pyo3(text_signature = "(graph, filter)")] -fn collect_runs( +pub fn collect_runs( py: Python, graph: &digraph::PyDiGraph, filter_fn: PyObject, @@ -499,7 +499,7 @@ fn collect_runs( /// :rtype: list #[pyfunction] #[pyo3(text_signature = "(graph, filter_fn, color_fn)")] -fn collect_bicolor_runs( +pub fn collect_bicolor_runs( py: Python, graph: &digraph::PyDiGraph, filter_fn: PyObject, diff --git a/src/isomorphism/mod.rs b/src/isomorphism/mod.rs index 19e0e0249..aded52b18 100644 --- a/src/isomorphism/mod.rs +++ b/src/isomorphism/mod.rs @@ -62,7 +62,7 @@ use pyo3::Python; text_signature = "(first, second, /, node_matcher=None, edge_matcher=None, id_order=True, call_limit=None)" )] -fn digraph_is_isomorphic( +pub fn digraph_is_isomorphic( py: Python, first: &digraph::PyDiGraph, second: &digraph::PyDiGraph, @@ -125,7 +125,7 @@ fn digraph_is_isomorphic( text_signature = "(first, second, /, node_matcher=None, edge_matcher=None, id_order=True, call_limit=None)" )] -fn graph_is_isomorphic( +pub fn graph_is_isomorphic( py: Python, first: &graph::PyGraph, second: &graph::PyGraph, @@ -195,7 +195,7 @@ fn graph_is_isomorphic( text_signature = "(first, second, /, node_matcher=None, edge_matcher=None, id_order=False, induced=True, call_limit=None)" )] -fn digraph_is_subgraph_isomorphic( +pub fn digraph_is_subgraph_isomorphic( py: Python, first: &digraph::PyDiGraph, second: &digraph::PyDiGraph, @@ -266,7 +266,7 @@ fn digraph_is_subgraph_isomorphic( text_signature = "(first, second, /, node_matcher=None, edge_matcher=None, id_order=False, induced=True, call_limit=None)" )] -fn graph_is_subgraph_isomorphic( +pub fn graph_is_subgraph_isomorphic( py: Python, first: &graph::PyGraph, second: &graph::PyGraph, @@ -337,7 +337,7 @@ fn graph_is_subgraph_isomorphic( text_signature = "(first, second, /, node_matcher=None, edge_matcher=None, id_order=True, subgraph=False, induced=True, call_limit=None)" )] -fn digraph_vf2_mapping( +pub fn digraph_vf2_mapping( py: Python, first: &digraph::PyDiGraph, second: &digraph::PyDiGraph, @@ -414,7 +414,7 @@ fn digraph_vf2_mapping( text_signature = "(first, second, /, node_matcher=None, edge_matcher=None, id_order=True, subgraph=False, induced=True, call_limit=None)" )] -fn graph_vf2_mapping( +pub fn graph_vf2_mapping( py: Python, first: &graph::PyGraph, second: &graph::PyGraph, diff --git a/src/iterators.rs b/src/iterators.rs index 52398ba82..6a7fa567e 100644 --- a/src/iterators.rs +++ b/src/iterators.rs @@ -332,7 +332,7 @@ where return Ok(false); } } - Err(ref err) if err.is_instance::(py) => { + Err(ref err) if err.is_instance_of::(py) => { return Ok(false); } Err(err) => return Err(err), diff --git a/src/lib.rs b/src/lib.rs index 20cebd077..4a35418d1 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -75,8 +75,6 @@ use std::hash::Hash; use retworkx_core::dictmap::*; -use crate::generators::PyInit_generators; - trait IsNan { fn is_nan(&self) -> bool; } @@ -401,7 +399,7 @@ fn retworkx(py: Python<'_>, m: &PyModule) -> PyResult<()> { graph_unweighted_average_shortest_path_length ))?; m.add_wrapped(wrap_pyfunction!(metric_closure))?; - m.add_wrapped(wrap_pyfunction!(steiner_tree))?; + m.add_wrapped(wrap_pyfunction!(steiner_tree::steiner_tree))?; m.add_wrapped(wrap_pyfunction!(digraph_dfs_search))?; m.add_wrapped(wrap_pyfunction!(graph_dfs_search))?; m.add_wrapped(wrap_pyfunction!(articulation_points))?; @@ -427,6 +425,6 @@ fn retworkx(py: Python<'_>, m: &PyModule) -> PyResult<()> { m.add_class::()?; m.add_class::()?; m.add_class::()?; - m.add_wrapped(wrap_pymodule!(generators))?; + m.add_wrapped(wrap_pymodule!(generators::generators))?; Ok(()) } diff --git a/src/matching/mod.rs b/src/matching/mod.rs index 04bc2666f..af85be79d 100644 --- a/src/matching/mod.rs +++ b/src/matching/mod.rs @@ -11,7 +11,7 @@ // under the License. use crate::graph; -use retworkx_core::max_weight_matching; +use retworkx_core::max_weight_matching as mwm; use hashbrown::HashSet; @@ -80,7 +80,7 @@ pub fn max_weight_matching( default_weight: i128, verify_optimum: bool, ) -> PyResult> { - max_weight_matching::max_weight_matching( + mwm::max_weight_matching( &graph.graph, max_cardinality, |e| weight_callable(py, &weight_fn, e.weight(), default_weight), diff --git a/src/shortest_path/mod.rs b/src/shortest_path/mod.rs index a9d3ca5b8..866cacb24 100644 --- a/src/shortest_path/mod.rs +++ b/src/shortest_path/mod.rs @@ -484,7 +484,7 @@ pub fn graph_all_pairs_dijkstra_shortest_paths( /// is provided. #[pyfunction] #[pyo3(text_signature = "(graph, node, goal_fn, edge_cost_fn, estimate_cost_fn, /)")] -fn digraph_astar_shortest_path( +pub fn digraph_astar_shortest_path( py: Python, graph: &digraph::PyDiGraph, node: usize, @@ -542,7 +542,7 @@ fn digraph_astar_shortest_path( /// is provided. #[pyfunction] #[pyo3(text_signature = "(graph, node, goal_fn, edge_cost_fn, estimate_cost_fn /)")] -fn graph_astar_shortest_path( +pub fn graph_astar_shortest_path( py: Python, graph: &graph::PyGraph, node: usize, @@ -598,7 +598,7 @@ fn graph_astar_shortest_path( /// is provided. #[pyfunction] #[pyo3(text_signature = "(graph, start, k, edge_cost, /, goal=None)")] -fn digraph_k_shortest_path_lengths( +pub fn digraph_k_shortest_path_lengths( py: Python, graph: &digraph::PyDiGraph, start: usize, @@ -746,7 +746,7 @@ pub fn graph_k_shortest_path_lengths( #[pyo3( text_signature = "(graph, /, weight_fn=None, as_undirected=False, default_weight=1.0, parallel_threshold=300)" )] -fn digraph_floyd_warshall( +pub fn digraph_floyd_warshall( py: Python, graph: &digraph::PyDiGraph, weight_fn: Option, diff --git a/src/tensor_product.rs b/src/tensor_product.rs index 87a29d2a0..6f24c6b3d 100644 --- a/src/tensor_product.rs +++ b/src/tensor_product.rs @@ -121,7 +121,7 @@ fn tensor_product( /// mpl_draw(graph_product) #[pyfunction()] #[pyo3(text_signature = "(first, second, /)")] -fn graph_tensor_product( +pub fn graph_tensor_product( py: Python, first: &graph::PyGraph, second: &graph::PyGraph, @@ -169,7 +169,7 @@ fn graph_tensor_product( /// mpl_draw(graph_product) #[pyfunction()] #[pyo3(text_signature = "(first, second, /)")] -fn digraph_tensor_product( +pub fn digraph_tensor_product( py: Python, first: &digraph::PyDiGraph, second: &digraph::PyDiGraph, diff --git a/src/transitivity.rs b/src/transitivity.rs index c8b22d860..6bcb25f94 100644 --- a/src/transitivity.rs +++ b/src/transitivity.rs @@ -70,7 +70,7 @@ fn _graph_triangles(graph: &graph::PyGraph, node: usize) -> (usize, usize) { /// :rtype: float #[pyfunction] #[pyo3(text_signature = "(graph, /)")] -fn graph_transitivity(graph: &graph::PyGraph) -> f64 { +pub fn graph_transitivity(graph: &graph::PyGraph) -> f64 { let node_indices: Vec = graph.graph.node_indices().collect(); let (triangles, triples) = node_indices .par_iter() @@ -171,7 +171,7 @@ fn _digraph_triangles(graph: &digraph::PyDiGraph, node: usize) -> (usize, usize) /// Physical Review E, 76(2), 026107 (2007) #[pyfunction] #[pyo3(text_signature = "(graph, /)")] -fn digraph_transitivity(graph: &digraph::PyDiGraph) -> f64 { +pub fn digraph_transitivity(graph: &digraph::PyDiGraph) -> f64 { let node_indices: Vec = graph.graph.node_indices().collect(); let (triangles, triples) = node_indices .par_iter() diff --git a/src/traversal/bfs_visit.rs b/src/traversal/bfs_visit.rs index 446931cb4..75ea38e79 100644 --- a/src/traversal/bfs_visit.rs +++ b/src/traversal/bfs_visit.rs @@ -56,9 +56,9 @@ pub fn bfs_handler( match res { Err(e) => { - if e.is_instance::(py) { + if e.is_instance_of::(py) { Ok(Control::Prune) - } else if e.is_instance::(py) { + } else if e.is_instance_of::(py) { Ok(Control::Break(())) } else { Err(e) diff --git a/src/traversal/dfs_visit.rs b/src/traversal/dfs_visit.rs index c373ec532..0ec650584 100644 --- a/src/traversal/dfs_visit.rs +++ b/src/traversal/dfs_visit.rs @@ -51,7 +51,7 @@ pub fn dfs_handler( match res { Err(e) => { - if e.is_instance::(py) { + if e.is_instance_of::(py) { Ok(Control::Prune) } else { Err(e) diff --git a/src/traversal/dijkstra_visit.rs b/src/traversal/dijkstra_visit.rs index 6391508c6..a73c47988 100644 --- a/src/traversal/dijkstra_visit.rs +++ b/src/traversal/dijkstra_visit.rs @@ -51,9 +51,9 @@ pub fn dijkstra_handler( match res { Err(e) => { - if e.is_instance::(py) { + if e.is_instance_of::(py) { Ok(Control::Prune) - } else if e.is_instance::(py) { + } else if e.is_instance_of::(py) { Ok(Control::Break(())) } else { Err(e) diff --git a/src/traversal/mod.rs b/src/traversal/mod.rs index de53fe999..8e06dfe16 100644 --- a/src/traversal/mod.rs +++ b/src/traversal/mod.rs @@ -71,7 +71,7 @@ use crate::iterators::EdgeList; /// :rtype: EdgeList #[pyfunction] #[pyo3(text_signature = "(graph, /, source=None)")] -fn digraph_dfs_edges(graph: &digraph::PyDiGraph, source: Option) -> EdgeList { +pub fn digraph_dfs_edges(graph: &digraph::PyDiGraph, source: Option) -> EdgeList { EdgeList { edges: dfs_edges(&graph.graph, source.map(NodeIndex::new)), } @@ -116,7 +116,7 @@ fn digraph_dfs_edges(graph: &digraph::PyDiGraph, source: Option) -> EdgeL /// :rtype: EdgeList #[pyfunction] #[pyo3(text_signature = "(graph, /, source=None)")] -fn graph_dfs_edges(graph: &graph::PyGraph, source: Option) -> EdgeList { +pub fn graph_dfs_edges(graph: &graph::PyGraph, source: Option) -> EdgeList { EdgeList { edges: dfs_edges(&graph.graph, source.map(NodeIndex::new)), } @@ -137,7 +137,7 @@ fn graph_dfs_edges(graph: &graph::PyGraph, source: Option) -> EdgeList { /// :rtype: BFSSuccessors #[pyfunction] #[pyo3(text_signature = "(graph, node, /)")] -fn bfs_successors(py: Python, graph: &digraph::PyDiGraph, node: usize) -> iterators::BFSSuccessors { +pub fn bfs_successors(py: Python, graph: &digraph::PyDiGraph, node: usize) -> iterators::BFSSuccessors { let index = NodeIndex::new(node); let mut bfs = Bfs::new(&graph.graph, index); let mut out_list: Vec<(PyObject, Vec)> = Vec::with_capacity(graph.node_count()); @@ -175,7 +175,7 @@ fn bfs_successors(py: Python, graph: &digraph::PyDiGraph, node: usize) -> iterat /// :rtype: set #[pyfunction] #[pyo3(text_signature = "(graph, node, /)")] -fn ancestors(graph: &digraph::PyDiGraph, node: usize) -> HashSet { +pub fn ancestors(graph: &digraph::PyDiGraph, node: usize) -> HashSet { let index = NodeIndex::new(node); let mut out_set: HashSet = HashSet::new(); let reverse_graph = Reversed(&graph.graph); @@ -202,7 +202,7 @@ fn ancestors(graph: &digraph::PyDiGraph, node: usize) -> HashSet { /// :rtype: set #[pyfunction] #[pyo3(text_signature = "(graph, node, /)")] -fn descendants(graph: &digraph::PyDiGraph, node: usize) -> HashSet { +pub fn descendants(graph: &digraph::PyDiGraph, node: usize) -> HashSet { let index = NodeIndex::new(node); let mut out_set: HashSet = HashSet::new(); let res = algo::dijkstra(&graph.graph, index, None, |_| 1); diff --git a/src/union.rs b/src/union.rs index 12b8a6f5d..86d665b0c 100644 --- a/src/union.rs +++ b/src/union.rs @@ -126,7 +126,7 @@ fn union( /// :rtype: PyGraph #[pyfunction(merge_nodes = false, merge_edges = false)] #[pyo3(text_signature = "(first, second, /, merge_nodes=False, merge_edges=False)")] -fn graph_union( +pub fn graph_union( py: Python, first: &graph::PyGraph, second: &graph::PyGraph, @@ -174,7 +174,7 @@ fn graph_union( /// :rtype: PyDiGraph #[pyfunction(merge_nodes = false, merge_edges = false)] #[pyo3(text_signature = "(first, second, /, merge_nodes=False, merge_edges=False)")] -fn digraph_union( +pub fn digraph_union( py: Python, first: &digraph::PyDiGraph, second: &digraph::PyDiGraph, From 58ab94e57f967ba4a363719749dbfe72f60f09e8 Mon Sep 17 00:00:00 2001 From: georgios-ts Date: Sun, 6 Mar 2022 21:42:55 +0200 Subject: [PATCH 2/7] fix pyproto deprecation warnings --- src/digraph.rs | 67 +++++----- src/graph.rs | 21 ++-- src/isomorphism/vf2.rs | 13 +- src/iterators.rs | 272 +++++++++++++++++++---------------------- src/traversal/mod.rs | 6 +- 5 files changed, 175 insertions(+), 204 deletions(-) diff --git a/src/digraph.rs b/src/digraph.rs index 2e5024e5c..a5bcc4407 100644 --- a/src/digraph.rs +++ b/src/digraph.rs @@ -24,9 +24,8 @@ use indexmap::IndexSet; use retworkx_core::dictmap::*; -use pyo3::class::PyMappingProtocol; use pyo3::exceptions::PyIndexError; -use pyo3::gc::{PyGCProtocol, PyVisit}; +use pyo3::gc::PyVisit; use pyo3::prelude::*; use pyo3::types::{PyBool, PyDict, PyList, PyLong, PyString, PyTuple}; use pyo3::PyTraverseError; @@ -151,7 +150,7 @@ use super::dag_algo::is_directed_acyclic_graph; /// ``PyDiGraph`` object will not be a multigraph. When ``False`` if a /// method call is made that would add parallel edges the the weight/weight /// from that method call will be used to update the existing edge in place. -#[pyclass(module = "retworkx", subclass, gc)] +#[pyclass(module = "retworkx", subclass)] #[pyo3(text_signature = "(/, check_cycle=False, multigraph=True)")] #[derive(Clone)] pub struct PyDiGraph { @@ -2638,22 +2637,20 @@ impl PyDiGraph { pub fn copy(&self) -> PyDiGraph { self.clone() } -} -#[pyproto] -impl PyMappingProtocol for PyDiGraph { /// Return the number of nodes in the graph fn __len__(&self) -> PyResult { Ok(self.graph.node_count()) } - fn __getitem__(&'p self, idx: usize) -> PyResult<&'p PyObject> { + + fn __getitem__(&self, idx: usize) -> PyResult<&PyObject> { match self.graph.node_weight(NodeIndex::new(idx as usize)) { Some(data) => Ok(data), None => Err(PyIndexError::new_err("No node found for index")), } } - fn __setitem__(&'p mut self, idx: usize, value: PyObject) -> PyResult<()> { + fn __setitem__(&mut self, idx: usize, value: PyObject) -> PyResult<()> { let data = match self.graph.node_weight_mut(NodeIndex::new(idx as usize)) { Some(node_data) => node_data, None => return Err(PyIndexError::new_err("No node found for index")), @@ -2662,41 +2659,15 @@ impl PyMappingProtocol for PyDiGraph { Ok(()) } - fn __delitem__(&'p mut self, idx: usize) -> PyResult<()> { + fn __delitem__(&mut self, idx: usize) -> PyResult<()> { match self.graph.remove_node(NodeIndex::new(idx as usize)) { Some(_) => Ok(()), None => Err(PyIndexError::new_err("No node found for index")), } } -} - -fn is_cycle_check_required(dag: &PyDiGraph, a: NodeIndex, b: NodeIndex) -> bool { - let mut parents_a = dag - .graph - .neighbors_directed(a, petgraph::Direction::Incoming); - let mut children_b = dag - .graph - .neighbors_directed(b, petgraph::Direction::Outgoing); - parents_a.next().is_some() && children_b.next().is_some() && dag.graph.find_edge(a, b).is_none() -} -fn weight_transform_callable( - py: Python, - map_fn: &Option, - value: &PyObject, -) -> PyResult { - match map_fn { - Some(map_fn) => { - let res = map_fn.call1(py, (value,))?; - Ok(res.to_object(py)) - } - None => Ok(value.clone_ref(py)), - } -} + // Functions to enable Python Garbage Collection -// Functions to enable Python Garbage Collection -#[pyproto] -impl PyGCProtocol for PyDiGraph { // Function for PyTypeObject.tp_traverse [1][2] used to tell Python what // objects the PyDiGraph has strong references to. // @@ -2732,6 +2703,30 @@ impl PyGCProtocol for PyDiGraph { } } +fn is_cycle_check_required(dag: &PyDiGraph, a: NodeIndex, b: NodeIndex) -> bool { + let mut parents_a = dag + .graph + .neighbors_directed(a, petgraph::Direction::Incoming); + let mut children_b = dag + .graph + .neighbors_directed(b, petgraph::Direction::Outgoing); + parents_a.next().is_some() && children_b.next().is_some() && dag.graph.find_edge(a, b).is_none() +} + +fn weight_transform_callable( + py: Python, + map_fn: &Option, + value: &PyObject, +) -> PyResult { + match map_fn { + Some(map_fn) => { + let res = map_fn.call1(py, (value,))?; + Ok(res.to_object(py)) + } + None => Ok(value.clone_ref(py)), + } +} + fn _from_adjacency_matrix<'p, T>( py: Python<'p>, matrix: PyReadonlyArray2<'p, T>, diff --git a/src/graph.rs b/src/graph.rs index e6665b7ee..9cab988fa 100644 --- a/src/graph.rs +++ b/src/graph.rs @@ -21,9 +21,8 @@ use hashbrown::{HashMap, HashSet}; use indexmap::IndexSet; use retworkx_core::dictmap::*; -use pyo3::class::PyMappingProtocol; use pyo3::exceptions::PyIndexError; -use pyo3::gc::{PyGCProtocol, PyVisit}; +use pyo3::gc::PyVisit; use pyo3::prelude::*; use pyo3::types::{PyBool, PyDict, PyList, PyLong, PyString, PyTuple}; use pyo3::PyTraverseError; @@ -114,7 +113,7 @@ use petgraph::visit::{ /// object will not be a multigraph. When ``False`` if a method call is /// made that would add parallel edges the the weight/weight from that /// method call will be used to update the existing edge in place. -#[pyclass(module = "retworkx", subclass, gc)] +#[pyclass(module = "retworkx", subclass)] #[pyo3(text_signature = "(/, multigraph=True)")] #[derive(Clone)] pub struct PyGraph { @@ -1713,22 +1712,20 @@ impl PyGraph { pub fn copy(&self) -> PyGraph { self.clone() } -} -#[pyproto] -impl PyMappingProtocol for PyGraph { /// Return the nmber of nodes in the graph fn __len__(&self) -> PyResult { Ok(self.graph.node_count()) } - fn __getitem__(&'p self, idx: usize) -> PyResult<&'p PyObject> { + + fn __getitem__(&self, idx: usize) -> PyResult<&PyObject> { match self.graph.node_weight(NodeIndex::new(idx)) { Some(data) => Ok(data), None => Err(PyIndexError::new_err("No node found for index")), } } - fn __setitem__(&'p mut self, idx: usize, value: PyObject) -> PyResult<()> { + fn __setitem__(&mut self, idx: usize, value: PyObject) -> PyResult<()> { let data = match self.graph.node_weight_mut(NodeIndex::new(idx)) { Some(node_data) => node_data, None => return Err(PyIndexError::new_err("No node found for index")), @@ -1737,17 +1734,15 @@ impl PyMappingProtocol for PyGraph { Ok(()) } - fn __delitem__(&'p mut self, idx: usize) -> PyResult<()> { + fn __delitem__(&mut self, idx: usize) -> PyResult<()> { match self.graph.remove_node(NodeIndex::new(idx as usize)) { Some(_) => Ok(()), None => Err(PyIndexError::new_err("No node found for index")), } } -} -// Functions to enable Python Garbage Collection -#[pyproto] -impl PyGCProtocol for PyGraph { + // Functions to enable Python Garbage Collection + // Function for PyTypeObject.tp_traverse [1][2] used to tell Python what // objects the PyGraph has strong references to. // diff --git a/src/isomorphism/vf2.rs b/src/isomorphism/vf2.rs index 9590fb514..0b64bb6e8 100644 --- a/src/isomorphism/vf2.rs +++ b/src/isomorphism/vf2.rs @@ -22,8 +22,8 @@ use std::marker; use hashbrown::HashMap; use retworkx_core::dictmap::*; -use pyo3::class::iter::{IterNextOutput, PyIterProtocol}; -use pyo3::gc::{PyGCProtocol, PyVisit}; +use pyo3::class::iter::IterNextOutput; +use pyo3::gc::PyVisit; use pyo3::prelude::*; use pyo3::PyTraverseError; @@ -977,7 +977,7 @@ where macro_rules! vf2_mapping_impl { ($name:ident, $Ty:ty) => { - #[pyclass(module = "retworkx", gc)] + #[pyclass(module = "retworkx")] pub struct $name { vf2: Vf2Algorithm<$Ty, Option, Option>, } @@ -1001,8 +1001,8 @@ macro_rules! vf2_mapping_impl { } } - #[pyproto] - impl PyIterProtocol for $name { + #[pymethods] + impl $name { fn __iter__(slf: PyRef) -> Py<$name> { slf.into() } @@ -1015,10 +1015,7 @@ macro_rules! vf2_mapping_impl { None => Ok(IterNextOutput::Return("Ended")), }) } - } - #[pyproto] - impl PyGCProtocol for $name { fn __traverse__(&self, visit: PyVisit) -> Result<(), PyTraverseError> { for j in 0..2 { for node in self.vf2.st[j].graph.node_weights() { diff --git a/src/iterators.rs b/src/iterators.rs index 6a7fa567e..6c43fb7e5 100644 --- a/src/iterators.rs +++ b/src/iterators.rs @@ -30,9 +30,7 @@ // from `usize` to `f64`. // // You should always implement `PyGCProtocol` for the new custom return type. If you -// don't store any python object, just use the macro `default_pygc_protocol_impl`. -// -// e.g `default_pygc_protocol_impl!(MyReadOnlyType);` +// don't store any python object, just use `impl PyGCProtocol for MyReadOnlyType {}`. // // Types `T, K, V` above should implement `PyHash`, `PyEq`, `PyDisplay` traits. // These are arleady implemented for many primitive rust types and `PyObject`. @@ -46,12 +44,10 @@ use std::hash::Hasher; use num_bigint::BigUint; use retworkx_core::dictmap::*; -use pyo3::class::iter::{IterNextOutput, PyIterProtocol}; -use pyo3::class::{PyMappingProtocol, PyObjectProtocol, PySequenceProtocol}; +use pyo3::class::iter::IterNextOutput; use pyo3::exceptions::{PyIndexError, PyKeyError, PyNotImplementedError}; -use pyo3::gc::{PyGCProtocol, PyVisit}; +use pyo3::gc::PyVisit; use pyo3::prelude::*; -use pyo3::types::PySequence; use pyo3::PyTraverseError; macro_rules! last_type { @@ -294,39 +290,18 @@ where } } -impl PyEq for Vec -where - A: PyEq, -{ - #[inline] - fn eq(&self, other: &PySequence, py: Python) -> PyResult { - if other.len()? as usize != self.len() { - return Ok(false); - } - - for (i, item) in self.iter().enumerate() { - let other_raw = other.get_item(i)?; - if !PyEq::eq(item, other_raw, py)? { - return Ok(false); - } - } - Ok(true) - } -} - -impl PyEq for DictMap +impl PyEq for DictMap where for<'p> K: PyEq + Clone + pyo3::ToBorrowedObject, for<'p> V: PyEq, { #[inline] - fn eq(&self, other: &PyObject, py: Python) -> PyResult { - let other_ref = other.as_ref(py); - if other_ref.len()? != self.len() { + fn eq(&self, other: &PyAny, py: Python) -> PyResult { + if other.len()? != self.len() { return Ok(false); } for (key, value) in self { - match other_ref.get_item(key) { + match other.get_item(key) { Ok(other_raw) => { if !PyEq::eq(value, other_raw, py)? { return Ok(false); @@ -423,23 +398,18 @@ impl PyDisplay for DictMap { } } -macro_rules! default_pygc_protocol_impl { - ($name:ident) => { - #[pyproto] - impl PyGCProtocol for $name { - fn __traverse__(&self, _: PyVisit) -> Result<(), PyTraverseError> { - Ok(()) - } +trait PyGCProtocol { + fn __traverse__(&self, _: PyVisit) -> Result<(), PyTraverseError> { + Ok(()) + } - fn __clear__(&mut self) {} - } - }; + fn __clear__(&mut self) {} } macro_rules! custom_vec_iter_impl { ($name:ident, $data:ident, $T:ty, $doc:literal) => { #[doc = $doc] - #[pyclass(module = "retworkx", gc)] + #[pyclass(module = "retworkx")] #[derive(Clone)] pub struct $name { pub $data: Vec<$T>, @@ -459,17 +429,22 @@ macro_rules! custom_vec_iter_impl { fn __setstate__(&mut self, state: Vec<$T>) { self.$data = state; } - } - #[pyproto] - impl<'p> PyObjectProtocol<'p> for $name { - fn __richcmp__( - &self, - other: &'p PySequence, - op: pyo3::basic::CompareOp, - ) -> PyResult { - let compare = |other: &PySequence| -> PyResult { - Python::with_gil(|py| PyEq::eq(&self.$data, other, py)) + fn __richcmp__(&self, other: &PyAny, op: pyo3::basic::CompareOp) -> PyResult { + let compare = |other: &PyAny| -> PyResult { + Python::with_gil(|py| { + if other.len()? as usize != self.$data.len() { + return Ok(false); + } + + for (i, item) in self.$data.iter().enumerate() { + let other_raw = other.get_item(i)?; + if !PyEq::eq(item, other_raw, py)? { + return Ok(false); + } + } + Ok(true) + }) }; match op { pyo3::basic::CompareOp::Eq => compare(other), @@ -491,21 +466,29 @@ macro_rules! custom_vec_iter_impl { Ok(hasher.finish()) } - } - #[pyproto] - impl PySequenceProtocol for $name { fn __len__(&self) -> PyResult { Ok(self.$data.len()) } - fn __getitem__(&'p self, idx: isize) -> PyResult<$T> { - if idx >= self.$data.len().try_into().unwrap() { + fn __getitem__(&self, idx: isize) -> PyResult<$T> { + if idx.abs() >= self.$data.len().try_into().unwrap() { Err(PyIndexError::new_err(format!("Invalid index, {}", idx))) + } else if idx < 0 { + let len = self.$data.len(); + Ok(self.$data[len + idx as usize].clone()) } else { Ok(self.$data[idx as usize].clone()) } } + + fn __traverse__(&self, vis: PyVisit) -> Result<(), PyTraverseError> { + PyGCProtocol::__traverse__(self, vis) + } + + fn __clear__(&mut self) { + PyGCProtocol::__clear__(self) + } } }; } @@ -546,7 +529,6 @@ custom_vec_iter_impl!( " ); -#[pyproto] impl PyGCProtocol for BFSSuccessors { fn __traverse__(&self, visit: PyVisit) -> Result<(), PyTraverseError> { for node in &self.bfs_successors { @@ -593,7 +575,7 @@ custom_vec_iter_impl!( " ); -default_pygc_protocol_impl!(NodeIndices); +impl PyGCProtocol for NodeIndices {} custom_vec_iter_impl!( EdgeList, @@ -631,7 +613,7 @@ custom_vec_iter_impl!( " ); -default_pygc_protocol_impl!(EdgeList); +impl PyGCProtocol for EdgeList {} custom_vec_iter_impl!( WeightedEdgeList, @@ -670,7 +652,6 @@ custom_vec_iter_impl!( " ); -#[pyproto] impl PyGCProtocol for WeightedEdgeList { fn __traverse__(&self, visit: PyVisit) -> Result<(), PyTraverseError> { for edge in &self.edges { @@ -714,7 +695,7 @@ custom_vec_iter_impl!( " ); -default_pygc_protocol_impl!(EdgeIndices); +impl PyGCProtocol for EdgeIndices {} impl PyHash for EdgeList { fn hash(&self, py: Python, state: &mut H) -> PyResult<()> { @@ -726,7 +707,7 @@ impl PyHash for EdgeList { impl PyEq for EdgeList { #[inline] fn eq(&self, other: &PyAny, py: Python) -> PyResult { - PyEq::eq(&self.edges, other.downcast::()?, py) + PyEq::eq(&self.edges, other, py) } } @@ -766,39 +747,7 @@ custom_vec_iter_impl!( " ); -default_pygc_protocol_impl!(Chains); - -macro_rules! py_object_protocol_impl { - ($name:ident, $data:ident) => { - #[pyproto] - impl<'p> PyObjectProtocol<'p> for $name { - fn __richcmp__(&self, other: PyObject, op: pyo3::basic::CompareOp) -> PyResult { - let compare = |other: PyObject| -> PyResult { - Python::with_gil(|py| PyEq::eq(&self.$data, &other, py)) - }; - match op { - pyo3::basic::CompareOp::Eq => compare(other), - pyo3::basic::CompareOp::Ne => match compare(other) { - Ok(res) => Ok(!res), - Err(err) => Err(err), - }, - _ => Err(PyNotImplementedError::new_err("Comparison not implemented")), - } - } - - fn __str__(&self) -> PyResult { - Python::with_gil(|py| Ok(format!("{}{}", stringify!($name), self.$data.str(py)?))) - } - - fn __hash__(&self) -> PyResult { - let mut hasher = DefaultHasher::new(); - Python::with_gil(|py| PyHash::hash(&self.$data, py, &mut hasher))?; - - Ok(hasher.finish()) - } - } - }; -} +impl PyGCProtocol for Chains {} macro_rules! py_iter_protocol_impl { ($name:ident, $data:ident, $T:ty) => { @@ -808,8 +757,8 @@ macro_rules! py_iter_protocol_impl { iter_pos: usize, } - #[pyproto] - impl PyIterProtocol for $name { + #[pymethods] + impl $name { fn __iter__(slf: PyRef) -> Py<$name> { slf.into() } @@ -833,7 +782,7 @@ macro_rules! custom_hash_map_iter_impl { $K:ty, $V:ty, $doc:literal ) => { #[doc = $doc] - #[pyclass(module = "retworkx", gc)] + #[pyclass(module = "retworkx")] #[derive(Clone)] pub struct $name { pub $data: DictMap<$K, $V>, @@ -878,43 +827,61 @@ macro_rules! custom_hash_map_iter_impl { iter_pos: 0, } } - } - py_object_protocol_impl!($name, $data); + fn __richcmp__(&self, other: &PyAny, op: pyo3::basic::CompareOp) -> PyResult { + let compare = |other: &PyAny| -> PyResult { + Python::with_gil(|py| PyEq::eq(&self.$data, other, py)) + }; + match op { + pyo3::basic::CompareOp::Eq => compare(other), + pyo3::basic::CompareOp::Ne => match compare(other) { + Ok(res) => Ok(!res), + Err(err) => Err(err), + }, + _ => Err(PyNotImplementedError::new_err("Comparison not implemented")), + } + } - #[pyproto] - impl PySequenceProtocol for $name { - fn __len__(&self) -> PyResult { - Ok(self.$data.len()) + fn __str__(&self) -> PyResult { + Python::with_gil(|py| Ok(format!("{}{}", stringify!($name), self.$data.str(py)?))) } - fn __contains__(&self, key: $K) -> PyResult { - Ok(self.$data.contains_key(&key)) + fn __hash__(&self) -> PyResult { + let mut hasher = DefaultHasher::new(); + Python::with_gil(|py| PyHash::hash(&self.$data, py, &mut hasher))?; + + Ok(hasher.finish()) } - } - #[pyproto] - impl PyMappingProtocol for $name { fn __len__(&self) -> PyResult { Ok(self.$data.len()) } - fn __getitem__(&'p self, key: $K) -> PyResult<$V> { + fn __contains__(&self, key: $K) -> PyResult { + Ok(self.$data.contains_key(&key)) + } + + fn __getitem__(&self, key: $K) -> PyResult<$V> { match self.$data.get(&key) { Some(data) => Ok(data.clone()), None => Err(PyIndexError::new_err("No node found for index")), } } - } - #[pyproto] - impl PyIterProtocol for $name { fn __iter__(slf: PyRef) -> $nameKeys { $nameKeys { $keys: slf.$data.keys().copied().collect(), iter_pos: 0, } } + + fn __traverse__(&self, vis: PyVisit) -> Result<(), PyTraverseError> { + PyGCProtocol::__traverse__(self, vis) + } + + fn __clear__(&mut self) { + PyGCProtocol::__clear__(self) + } } py_iter_protocol_impl!($nameKeys, $keys, $K); @@ -944,7 +911,7 @@ custom_hash_map_iter_impl!( graph. It behaves as a drop in replacement for a readonly ``dict``. " ); -default_pygc_protocol_impl!(Pos2DMapping); +impl PyGCProtocol for Pos2DMapping {} custom_hash_map_iter_impl!( EdgeIndexMap, @@ -969,7 +936,6 @@ custom_hash_map_iter_impl!( " ); -#[pyproto] impl PyGCProtocol for EdgeIndexMap { fn __traverse__(&self, visit: PyVisit) -> Result<(), PyTraverseError> { for edge in &self.edge_map { @@ -1014,7 +980,7 @@ impl PyGCProtocol for EdgeIndexMap { /// second_target = next(edges_iter) /// second_path = edges[second_target] /// -#[pyclass(module = "retworkx", gc)] +#[pyclass(module = "retworkx")] #[derive(Clone)] pub struct PathMapping { pub paths: DictMap>, @@ -1066,17 +1032,37 @@ impl PathMapping { iter_pos: 0, } } -} -py_object_protocol_impl!(PathMapping, paths); + fn __richcmp__(&self, other: &PyAny, op: pyo3::basic::CompareOp) -> PyResult { + let compare = |other: &PyAny| -> PyResult { + Python::with_gil(|py| PyEq::eq(&self.paths, other, py)) + }; + match op { + pyo3::basic::CompareOp::Eq => compare(other), + pyo3::basic::CompareOp::Ne => match compare(other) { + Ok(res) => Ok(!res), + Err(err) => Err(err), + }, + _ => Err(PyNotImplementedError::new_err("Comparison not implemented")), + } + } + + fn __str__(&self) -> PyResult { + Python::with_gil(|py| Ok(format!("PathMapping{}", self.paths.str(py)?))) + } + + fn __hash__(&self) -> PyResult { + let mut hasher = DefaultHasher::new(); + Python::with_gil(|py| PyHash::hash(&self.paths, py, &mut hasher))?; + + Ok(hasher.finish()) + } -#[pyproto] -impl PyMappingProtocol for PathMapping { - /// Return the number of nodes in the graph fn __len__(&self) -> PyResult { Ok(self.paths.len()) } - fn __getitem__(&'p self, idx: usize) -> PyResult { + + fn __getitem__(&self, idx: usize) -> PyResult { match self.paths.get(&idx) { Some(data) => Ok(NodeIndices { nodes: data.clone(), @@ -1084,30 +1070,24 @@ impl PyMappingProtocol for PathMapping { None => Err(PyIndexError::new_err("No node found for index")), } } -} - -#[pyproto] -impl PySequenceProtocol for PathMapping { - fn __len__(&self) -> PyResult { - Ok(self.paths.len()) - } fn __contains__(&self, index: usize) -> PyResult { Ok(self.paths.contains_key(&index)) } -} -#[pyproto] -impl PyIterProtocol for PathMapping { fn __iter__(slf: PyRef) -> PathMappingKeys { PathMappingKeys { path_keys: slf.paths.keys().copied().collect(), iter_pos: 0, } } -} -default_pygc_protocol_impl!(PathMapping); + fn __traverse__(&self, _vis: PyVisit) -> Result<(), PyTraverseError> { + Ok(()) + } + + fn __clear__(&mut self) {} +} py_iter_protocol_impl!(PathMappingKeys, path_keys, usize); py_iter_protocol_impl!(PathMappingValues, path_values, NodeIndices); @@ -1123,7 +1103,7 @@ impl PyHash for PathMapping { impl PyEq for PathMapping { #[inline] fn eq(&self, other: &PyAny, py: Python) -> PyResult { - PyEq::eq(&self.paths, &other.to_object(py), py) + PyEq::eq(&self.paths, other, py) } } @@ -1175,7 +1155,7 @@ custom_hash_map_iter_impl!( " ); -default_pygc_protocol_impl!(PathLengthMapping); +impl PyGCProtocol for PathLengthMapping {} impl PyHash for PathLengthMapping { fn hash(&self, py: Python, state: &mut H) -> PyResult<()> { @@ -1187,7 +1167,7 @@ impl PyHash for PathLengthMapping { impl PyEq for PathLengthMapping { #[inline] fn eq(&self, other: &PyAny, py: Python) -> PyResult { - PyEq::eq(&self.path_lengths, &other.to_object(py), py) + PyEq::eq(&self.path_lengths, other, py) } } @@ -1216,7 +1196,7 @@ custom_hash_map_iter_impl!( return as a read-only mapping/dict. " ); -default_pygc_protocol_impl!(CentralityMapping); +impl PyGCProtocol for CentralityMapping {} custom_hash_map_iter_impl!( NodesCountMapping, @@ -1259,7 +1239,7 @@ custom_hash_map_iter_impl!( second_path = edges[second_target] " ); -default_pygc_protocol_impl!(NodesCountMapping); +impl PyGCProtocol for NodesCountMapping {} custom_hash_map_iter_impl!( AllPairsPathLengthMapping, @@ -1295,7 +1275,7 @@ custom_hash_map_iter_impl!( " ); -default_pygc_protocol_impl!(AllPairsPathLengthMapping); +impl PyGCProtocol for AllPairsPathLengthMapping {} custom_hash_map_iter_impl!( AllPairsPathMapping, @@ -1331,7 +1311,7 @@ custom_hash_map_iter_impl!( " ); -default_pygc_protocol_impl!(AllPairsPathMapping); +impl PyGCProtocol for AllPairsPathMapping {} custom_hash_map_iter_impl!( NodeMap, @@ -1356,7 +1336,7 @@ custom_hash_map_iter_impl!( the object. " ); -default_pygc_protocol_impl!(NodeMap); +impl PyGCProtocol for NodeMap {} custom_hash_map_iter_impl!( ProductNodeMap, @@ -1378,7 +1358,7 @@ custom_hash_map_iter_impl!( " ); -default_pygc_protocol_impl!(ProductNodeMap); +impl PyGCProtocol for ProductNodeMap {} custom_hash_map_iter_impl!( BiconnectedComponents, @@ -1401,4 +1381,4 @@ custom_hash_map_iter_impl!( " ); -default_pygc_protocol_impl!(BiconnectedComponents); +impl PyGCProtocol for BiconnectedComponents {} diff --git a/src/traversal/mod.rs b/src/traversal/mod.rs index 8e06dfe16..36e31d464 100644 --- a/src/traversal/mod.rs +++ b/src/traversal/mod.rs @@ -137,7 +137,11 @@ pub fn graph_dfs_edges(graph: &graph::PyGraph, source: Option) -> EdgeLis /// :rtype: BFSSuccessors #[pyfunction] #[pyo3(text_signature = "(graph, node, /)")] -pub fn bfs_successors(py: Python, graph: &digraph::PyDiGraph, node: usize) -> iterators::BFSSuccessors { +pub fn bfs_successors( + py: Python, + graph: &digraph::PyDiGraph, + node: usize, +) -> iterators::BFSSuccessors { let index = NodeIndex::new(node); let mut bfs = Bfs::new(&graph.graph, index); let mut out_list: Vec<(PyObject, Vec)> = Vec::with_capacity(graph.node_count()); From 7804887e2a5d45bba6b8a753d4d08e00514e0e44 Mon Sep 17 00:00:00 2001 From: Ivan Carvalho Date: Sun, 6 Mar 2022 20:27:39 -0800 Subject: [PATCH 3/7] Fix error making coverage fail --- src/iterators.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/iterators.rs b/src/iterators.rs index 6c43fb7e5..202f567b7 100644 --- a/src/iterators.rs +++ b/src/iterators.rs @@ -476,7 +476,7 @@ macro_rules! custom_vec_iter_impl { Err(PyIndexError::new_err(format!("Invalid index, {}", idx))) } else if idx < 0 { let len = self.$data.len(); - Ok(self.$data[len + idx as usize].clone()) + Ok(self.$data[len - idx.abs() as usize].clone()) } else { Ok(self.$data[idx as usize].clone()) } From 491ebdbf734a85927529bcda3ce28c02994c86ff Mon Sep 17 00:00:00 2001 From: Ivan Carvalho Date: Sun, 6 Mar 2022 20:27:55 -0800 Subject: [PATCH 4/7] Bump PyO3 to 0.16.1 --- Cargo.lock | 20 ++++++++++---------- Cargo.toml | 2 +- 2 files changed, 11 insertions(+), 11 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index a2eefb233..cb300f111 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -329,9 +329,9 @@ dependencies = [ [[package]] name = "pyo3" -version = "0.16.0" +version = "0.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9d1a3df45cb95bd954fac00bd9609062640fd7fb9e9946a660092c9e015421fb" +checksum = "c00e5e97bb258ac0fcea67da5e845aae5f7e6fb4f723ec94a503a6d0a541ccb7" dependencies = [ "cfg-if", "hashbrown", @@ -349,18 +349,18 @@ dependencies = [ [[package]] name = "pyo3-build-config" -version = "0.16.0" +version = "0.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "386a68f0f5f2f9932815068bc8049a56989f2437d96dbb31d1fb11b63ce90364" +checksum = "f61cb87bf5c9503fa0e7f38bcd311b31993328a5e29f3507dfbf763c8ccd37f4" dependencies = [ "once_cell", ] [[package]] name = "pyo3-ffi" -version = "0.16.0" +version = "0.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a9a4e2f74dc77eea5ce11d19f0afaeb632b6590f8cbb1d5ee2f1330b766803e8" +checksum = "5dd4b0b76ae07ca5a7b0527a75afc9f47744d14f4f3576bdf66a9a2420b5c54d" dependencies = [ "libc", "pyo3-build-config", @@ -368,9 +368,9 @@ dependencies = [ [[package]] name = "pyo3-macros" -version = "0.16.0" +version = "0.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "dbff3a1579934968a53bcc78ac33663ed2577accda05d484097679cc8d28e52d" +checksum = "a845f73eda2aa27d35b3840e2c6f0c9447347cdb49954552f09ae7b1f432a3d9" dependencies = [ "proc-macro2", "pyo3-macros-backend", @@ -380,9 +380,9 @@ dependencies = [ [[package]] name = "pyo3-macros-backend" -version = "0.16.0" +version = "0.16.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "90644126c8c1ac7b47f794dd20a5729f8646b91c49edb31689c90f8cb3c33ea9" +checksum = "4e72ef79ca96c2dcb66d9b22f149400ac6c6b32ab468398ebbcb145d72f80c00" dependencies = [ "proc-macro2", "pyo3-build-config", diff --git a/Cargo.toml b/Cargo.toml index 0eadadd3d..7f5beff46 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -32,7 +32,7 @@ num-complex = "0.4" retworkx-core = { path = "./retworkx-core" } [dependencies.pyo3] -version = "0.16.0" +version = "0.16.1" features = ["extension-module", "hashbrown", "num-bigint", "num-complex", "indexmap"] [dependencies.hashbrown] From 1cf163c056b2e587f8f9303f3897991722cfa707 Mon Sep 17 00:00:00 2001 From: Matthew Treinish Date: Fri, 25 Mar 2022 06:56:27 -0400 Subject: [PATCH 5/7] Bump to latest pyo3 and numpy release --- Cargo.lock | 24 ++++++++++++------------ Cargo.toml | 4 ++-- 2 files changed, 14 insertions(+), 14 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index cb300f111..ef6a513b2 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -260,9 +260,9 @@ dependencies = [ [[package]] name = "numpy" -version = "0.16.0" +version = "0.16.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "9e051c9e722a66c2e619b2a30f731e80b75f172d98ae3518b61b08a1d3d850a3" +checksum = "383ae168529a39fc97cbc1d9d4fa865377731a519bc27553ed96f50594de7c45" dependencies = [ "libc", "ndarray", @@ -329,9 +329,9 @@ dependencies = [ [[package]] name = "pyo3" -version = "0.16.1" +version = "0.16.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c00e5e97bb258ac0fcea67da5e845aae5f7e6fb4f723ec94a503a6d0a541ccb7" +checksum = "a378727d5fdcaafd15b5afe9842cff1c25fdc43f62a162ffda2263c57ad98703" dependencies = [ "cfg-if", "hashbrown", @@ -349,18 +349,18 @@ dependencies = [ [[package]] name = "pyo3-build-config" -version = "0.16.1" +version = "0.16.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f61cb87bf5c9503fa0e7f38bcd311b31993328a5e29f3507dfbf763c8ccd37f4" +checksum = "4fbb27a3e96edd34c13d97d0feefccc90a79270c577c66e19d95af8323823dfc" dependencies = [ "once_cell", ] [[package]] name = "pyo3-ffi" -version = "0.16.1" +version = "0.16.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5dd4b0b76ae07ca5a7b0527a75afc9f47744d14f4f3576bdf66a9a2420b5c54d" +checksum = "7b719fff844bcf3f911132112ec06527eb195f6a98e0c42cf97e1118929fd4ea" dependencies = [ "libc", "pyo3-build-config", @@ -368,9 +368,9 @@ dependencies = [ [[package]] name = "pyo3-macros" -version = "0.16.1" +version = "0.16.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a845f73eda2aa27d35b3840e2c6f0c9447347cdb49954552f09ae7b1f432a3d9" +checksum = "f795e52d3320abb349ca28b501a7112154a87f353fae1c811deecd58e99cfa9b" dependencies = [ "proc-macro2", "pyo3-macros-backend", @@ -380,9 +380,9 @@ dependencies = [ [[package]] name = "pyo3-macros-backend" -version = "0.16.1" +version = "0.16.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4e72ef79ca96c2dcb66d9b22f149400ac6c6b32ab468398ebbcb145d72f80c00" +checksum = "39e03aa57a3bb7b96982958088df38302a139df4eef54671bc595f26556cb75b" dependencies = [ "proc-macro2", "pyo3-build-config", diff --git a/Cargo.toml b/Cargo.toml index 7f5beff46..829e575fc 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -22,7 +22,7 @@ crate-type = ["cdylib"] ahash = { version = "0.7.6", default-features = false } petgraph = "0.6.0" fixedbitset = "0.4.1" -numpy = "0.16.0" +numpy = "0.16.2" rand = "0.8" rand_pcg = "0.3" rayon = "1.5" @@ -32,7 +32,7 @@ num-complex = "0.4" retworkx-core = { path = "./retworkx-core" } [dependencies.pyo3] -version = "0.16.1" +version = "0.16.2" features = ["extension-module", "hashbrown", "num-bigint", "num-complex", "indexmap"] [dependencies.hashbrown] From 02a95f3dd0559652e3d34e34d25abb1ff011c58a Mon Sep 17 00:00:00 2001 From: Matthew Treinish Date: Fri, 25 Mar 2022 08:01:46 -0400 Subject: [PATCH 6/7] Update additional dependencies in Cargo.lock --- Cargo.lock | 73 +++++++++++++++++++++++++++--------------------------- 1 file changed, 37 insertions(+), 36 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index ef6a513b2..54e6acd29 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -15,9 +15,9 @@ dependencies = [ [[package]] name = "autocfg" -version = "1.0.1" +version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cdb031dd78e28731d87d56cc8ffef4a8f36ca26c38fe2de700543e627f8a464a" +checksum = "d468802bab17cbc0cc575e9b053f41e72aa36bfa6b7f55e3529ffa43161b97fa" [[package]] name = "bitflags" @@ -33,9 +33,9 @@ checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" [[package]] name = "crossbeam-channel" -version = "0.5.1" +version = "0.5.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "06ed27e177f16d65f0f0c22a213e17c696ace5dd64b14258b52f9417ccb52db4" +checksum = "5aaa7bd5fb665c6864b5f963dd9097905c54125909c7aa94c9e18507cdbe6c53" dependencies = [ "cfg-if", "crossbeam-utils", @@ -54,10 +54,11 @@ dependencies = [ [[package]] name = "crossbeam-epoch" -version = "0.9.5" +version = "0.9.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4ec02e091aa634e2c3ada4a392989e7c3116673ef0ac5b72232439094d73b7fd" +checksum = "1145cf131a2c6ba0615079ab6a638f7e1973ac9c2634fcbeaaad6114246efe8c" dependencies = [ + "autocfg", "cfg-if", "crossbeam-utils", "lazy_static", @@ -67,9 +68,9 @@ dependencies = [ [[package]] name = "crossbeam-utils" -version = "0.8.5" +version = "0.8.8" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d82cfc11ce7f2c3faef78d8a684447b40d503d9681acebed6cb728d45940c4db" +checksum = "0bf124c720b7686e3c2663cf54062ab0f68a88af2fb6a030e87e30bf721fcb38" dependencies = [ "cfg-if", "lazy_static", @@ -89,9 +90,9 @@ checksum = "279fb028e20b3c4c320317955b77c5e0c9701f05a1d309905d6fc702cdc5053e" [[package]] name = "getrandom" -version = "0.2.3" +version = "0.2.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "7fcd999463524c52659517fe2cea98493cfe485d10565e7b0fb07dbba7ad2753" +checksum = "d39cd93900197114fa1fcb7ae84ca742095eed9442088988ae74fa744e930e77" dependencies = [ "cfg-if", "libc", @@ -139,9 +140,9 @@ dependencies = [ [[package]] name = "instant" -version = "0.1.10" +version = "0.1.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "bee0328b1209d157ef001c94dd85b4f8f64139adb0eac2659f4b08382b2f474d" +checksum = "7a5bbe824c507c5da5956355e86a746d82e0e1464f65d862cc5e71da70e94b2c" dependencies = [ "cfg-if", ] @@ -154,15 +155,15 @@ checksum = "e2abad23fbc42b3700f2f279844dc832adb2b2eb069b2df918f455c4e18cc646" [[package]] name = "libc" -version = "0.2.101" +version = "0.2.121" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3cb00336871be5ed2c8ed44b60ae9959dc5b9f08539422ed43f09e34ecaeba21" +checksum = "efaa7b300f3b5fe8eb6bf21ce3895e1751d9665086af2d64b42f19701015ff4f" [[package]] name = "lock_api" -version = "0.4.5" +version = "0.4.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "712a4d093c9976e24e7dbca41db895dabcbac38eb5f4045393d17a95bdfb1109" +checksum = "88943dd7ef4a2e5a4bfa2753aaab3013e34ce2533d1996fb18ef591e315e2b3b" dependencies = [ "scopeguard", ] @@ -178,9 +179,9 @@ dependencies = [ [[package]] name = "memoffset" -version = "0.6.4" +version = "0.6.5" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "59accc507f1338036a0477ef61afdae33cde60840f4dfe481319ce3ad116ddf9" +checksum = "5aa361d4faea93603064a027415f07bd8e1d5c88c9fbf68bf56a285428fd79ce" dependencies = [ "autocfg", ] @@ -250,9 +251,9 @@ dependencies = [ [[package]] name = "num_cpus" -version = "1.13.0" +version = "1.13.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "05499f3756671c15885fee9034446956fff3f243d6077b91e5767df161f766b3" +checksum = "19e64526ebdee182341572e50e9ad03965aa510cd94427a4549448f285e957a1" dependencies = [ "hermit-abi", "libc", @@ -273,9 +274,9 @@ dependencies = [ [[package]] name = "once_cell" -version = "1.8.0" +version = "1.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "692fcb63b64b1758029e0a96ee63e049ce8c5948587f2f7208df04625e5f6b56" +checksum = "87f3e037eac156d1775da914196f0f37741a274155e34a0b7e427c35d2a2ecb9" [[package]] name = "parking_lot" @@ -314,15 +315,15 @@ dependencies = [ [[package]] name = "ppv-lite86" -version = "0.2.10" +version = "0.2.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ac74c624d6b2d21f425f752262f42188365d7b8ff1aff74c82e45136510a4857" +checksum = "eb9f9e6e233e5c4a35559a617bf40a4ec447db2e84c20b55a6f83167b7e57872" [[package]] name = "proc-macro2" -version = "1.0.29" +version = "1.0.36" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b9f5105d4fdaab20335ca9565e106a5d9b82b6219b5ba735731124ac6711d23d" +checksum = "c7342d5883fbccae1cc37a2353b09c87c9b0f3afd73f5fb9bba687a1f733b029" dependencies = [ "unicode-xid", ] @@ -392,9 +393,9 @@ dependencies = [ [[package]] name = "quote" -version = "1.0.9" +version = "1.0.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c3d0b9745dc2debf507c8422de05d7226cc1f0644216dfdfead988f9b1ab32a7" +checksum = "b4af2ec4714533fcdf07e886f17025ace8b997b9ce51204ee69b6da831c3da57" dependencies = [ "proc-macro2", ] @@ -471,9 +472,9 @@ dependencies = [ [[package]] name = "redox_syscall" -version = "0.2.10" +version = "0.2.12" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "8383f39639269cde97d255a32bdb68c047337295414940c68bdd30c2e13203ff" +checksum = "8ae183fc1b06c149f0c1793e1eb447c8b04bfe46d48e9e48bfb8d2d7ed64ecf0" dependencies = [ "bitflags", ] @@ -518,15 +519,15 @@ checksum = "d29ab0c6d3fc0ee92fe66e2d99f700eab17a8d57d1c1d3b748380fb20baa78cd" [[package]] name = "smallvec" -version = "1.6.1" +version = "1.8.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "fe0f37c9e8f3c5a4a66ad655a93c74daac4ad00c441533bf5c6e7990bb42604e" +checksum = "f2dd574626839106c320a323308629dcb1acfc96e32a8cba364ddc61ac23ee83" [[package]] name = "syn" -version = "1.0.76" +version = "1.0.89" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "c6f107db402c2c2055242dbf4d2af0e69197202e9faacbef9571bbe47f5a1b84" +checksum = "ea297be220d52398dcc07ce15a209fce436d361735ac1db700cab3b6cdfb9f54" dependencies = [ "proc-macro2", "quote", @@ -547,9 +548,9 @@ checksum = "514672a55d7380da379785a4d70ca8386c8883ff7eaae877be4d2081cebe73d8" [[package]] name = "version_check" -version = "0.9.3" +version = "0.9.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5fecdca9a5291cc2b8dcf7dc02453fee791a280f3743cb0905f8822ae463b3fe" +checksum = "49874b5167b65d7193b8aba1567f5c7d93d001cafc34600cee003eda787e483f" [[package]] name = "wasi" From 4ec52f4c7067f32fe3db81de94aad0f9fc8875c1 Mon Sep 17 00:00:00 2001 From: Matthew Treinish Date: Fri, 25 Mar 2022 13:28:00 -0400 Subject: [PATCH 7/7] Empty commit to retrigger CI