# HG changeset patch # User Raphaël Gomès # Date 2019-07-02 15:15:03 # Node ID 326fdce22fb222492dc0ba114f4244aa2b8b3aff # Parent 717686c5e461b03cd34d010f9143f04bc5262cc6 rust: switch hg-core and hg-cpython to rust 2018 edition Many interesting changes have happened in Rust since the Oxidation Plan was introduced, like the 2018 edition and procedural macros: - Opting in to the 2018 edition is a clear benefit in terms of future proofing, new (nice to have) syntactical sugar notwithstanding. It also has a new non-lexical, non-AST based borrow checker that has fewer bugs(!) and allows us to write correct code that in some cases would have been rejected by the old one. - Procedural macros allow us to use the PyO3 crate which maintainers have expressed the clear goal of compiling on stable, which would help in code maintainability compared to rust-cpython. In this patch are the following changes: - Removing most `extern crate` uses - Updating `use` clauses (`crate` keyword, nested `use`) - Removing `mod.rs` in favor of an aptly named module file Like discussed in the mailing list ( https://www.mercurial-scm.org/pipermail/mercurial-devel/2019-July/132316.html ), until Rust integration in Mercurial is considered to be out of the experimental phase, the maximum version of Rust allowed is whatever the latest version Debian packages. Differential Revision: https://phab.mercurial-scm.org/D6597 diff --git a/rust/hg-core/Cargo.toml b/rust/hg-core/Cargo.toml --- a/rust/hg-core/Cargo.toml +++ b/rust/hg-core/Cargo.toml @@ -3,6 +3,7 @@ name = "hg-core" version = "0.1.0" authors = ["Georges Racinet "] description = "Mercurial pure Rust core library, with no assumption on Python bindings (FFI)" +edition = "2018" [lib] name = "hg" diff --git a/rust/hg-core/src/dirstate/mod.rs b/rust/hg-core/src/dirstate.rs rename from rust/hg-core/src/dirstate/mod.rs rename to rust/hg-core/src/dirstate.rs diff --git a/rust/hg-core/src/dirstate/dirs_multiset.rs b/rust/hg-core/src/dirstate/dirs_multiset.rs --- a/rust/hg-core/src/dirstate/dirs_multiset.rs +++ b/rust/hg-core/src/dirstate/dirs_multiset.rs @@ -8,10 +8,9 @@ //! A multiset of directory names. //! //! Used to counts the references to directories in a manifest or dirstate. +use crate::{utils::files, DirsIterable, DirstateEntry, DirstateMapError}; use std::collections::hash_map::{Entry, Iter}; use std::collections::HashMap; -use {DirsIterable, DirstateEntry, DirstateMapError}; -use utils::files; #[derive(PartialEq, Debug)] pub struct DirsMultiset { diff --git a/rust/hg-core/src/dirstate/parsers.rs b/rust/hg-core/src/dirstate/parsers.rs --- a/rust/hg-core/src/dirstate/parsers.rs +++ b/rust/hg-core/src/dirstate/parsers.rs @@ -3,13 +3,13 @@ // This software may be used and distributed according to the terms of the // GNU General Public License version 2 or any later version. +use crate::{ + CopyVec, CopyVecEntry, DirstateEntry, DirstatePackError, DirstateParents, + DirstateParseError, DirstateVec, +}; use byteorder::{BigEndian, ReadBytesExt, WriteBytesExt}; use std::collections::HashMap; use std::io::Cursor; -use { - CopyVec, CopyVecEntry, DirstateEntry, DirstatePackError, DirstateParents, - DirstateParseError, DirstateVec, -}; /// Parents are stored in the dirstate as byte hashes. const PARENT_SIZE: usize = 20; diff --git a/rust/hg-core/src/filepatterns.rs b/rust/hg-core/src/filepatterns.rs --- a/rust/hg-core/src/filepatterns.rs +++ b/rust/hg-core/src/filepatterns.rs @@ -1,11 +1,13 @@ -use crate::{LineNumber, PatternError, PatternFileError}; +use crate::{ + utils::{files::get_path_from_bytes, replace_slice, SliceExt}, + LineNumber, PatternError, PatternFileError, +}; +use lazy_static::lazy_static; use regex::bytes::Regex; use std::collections::HashMap; use std::fs::File; use std::io::Read; use std::vec::Vec; -use utils::files::get_path_from_bytes; -use utils::{replace_slice, SliceExt}; lazy_static! { static ref RE_ESCAPE: Vec> = { diff --git a/rust/hg-core/src/lib.rs b/rust/hg-core/src/lib.rs --- a/rust/hg-core/src/lib.rs +++ b/rust/hg-core/src/lib.rs @@ -2,12 +2,6 @@ // // This software may be used and distributed according to the terms of the // GNU General Public License version 2 or any later version. -extern crate byteorder; -extern crate memchr; -#[macro_use] -extern crate lazy_static; -extern crate regex; - mod ancestors; pub mod dagops; pub use ancestors::{AncestorsIterator, LazyAncestors, MissingAncestors}; @@ -50,7 +44,7 @@ pub trait Graph { /// Return the two parents of the given `Revision`. /// /// Each of the parents can be independently `NULL_REVISION` - fn parents(&self, Revision) -> Result<[Revision; 2], GraphError>; + fn parents(&self, rev: Revision) -> Result<[Revision; 2], GraphError>; } pub type LineNumber = usize; diff --git a/rust/hg-core/src/utils/mod.rs b/rust/hg-core/src/utils.rs rename from rust/hg-core/src/utils/mod.rs rename to rust/hg-core/src/utils.rs diff --git a/rust/hg-core/tests/test_missing_ancestors.rs b/rust/hg-core/tests/test_missing_ancestors.rs --- a/rust/hg-core/tests/test_missing_ancestors.rs +++ b/rust/hg-core/tests/test_missing_ancestors.rs @@ -1,7 +1,3 @@ -extern crate hg; -extern crate rand; -extern crate rand_pcg; - use hg::testing::VecGraph; use hg::Revision; use hg::*; diff --git a/rust/hg-cpython/Cargo.toml b/rust/hg-cpython/Cargo.toml --- a/rust/hg-cpython/Cargo.toml +++ b/rust/hg-cpython/Cargo.toml @@ -2,6 +2,7 @@ name = "hg-cpython" version = "0.1.0" authors = ["Georges Racinet "] +edition = "2018" [lib] name='rusthg' diff --git a/rust/hg-cpython/src/ancestors.rs b/rust/hg-cpython/src/ancestors.rs --- a/rust/hg-cpython/src/ancestors.rs +++ b/rust/hg-cpython/src/ancestors.rs @@ -34,13 +34,15 @@ //! [`LazyAncestors`]: struct.LazyAncestors.html //! [`MissingAncestors`]: struct.MissingAncestors.html //! [`AncestorsIterator`]: struct.AncestorsIterator.html -use crate::conversion::{py_set, rev_pyiter_collect}; -use cindex::Index; +use crate::{ + cindex::Index, + conversion::{py_set, rev_pyiter_collect}, + exceptions::GraphError, +}; use cpython::{ ObjectProtocol, PyClone, PyDict, PyList, PyModule, PyObject, PyResult, Python, PythonObject, ToPyObject, }; -use exceptions::GraphError; use hg::Revision; use hg::{ AncestorsIterator as CoreIterator, LazyAncestors as CoreLazy, diff --git a/rust/hg-cpython/src/cindex.rs b/rust/hg-cpython/src/cindex.rs --- a/rust/hg-cpython/src/cindex.rs +++ b/rust/hg-cpython/src/cindex.rs @@ -10,14 +10,14 @@ //! Ideally, we should use an Index entirely implemented in Rust, //! but this will take some time to get there. #[cfg(feature = "python27")] -extern crate python27_sys as python_sys; +use python27_sys as python_sys; #[cfg(feature = "python3")] -extern crate python3_sys as python_sys; +use python3_sys as python_sys; -use self::python_sys::PyCapsule_Import; use cpython::{PyClone, PyErr, PyObject, PyResult, Python}; use hg::{Graph, GraphError, Revision, WORKING_DIRECTORY_REVISION}; use libc::c_int; +use python_sys::PyCapsule_Import; use std::ffi::CStr; use std::mem::transmute; diff --git a/rust/hg-cpython/src/dagops.rs b/rust/hg-cpython/src/dagops.rs --- a/rust/hg-cpython/src/dagops.rs +++ b/rust/hg-cpython/src/dagops.rs @@ -9,10 +9,12 @@ //! `hg-core` package. //! //! From Python, this will be seen as `mercurial.rustext.dagop` -use crate::conversion::{py_set, rev_pyiter_collect}; -use cindex::Index; +use crate::{ + cindex::Index, + conversion::{py_set, rev_pyiter_collect}, + exceptions::GraphError, +}; use cpython::{PyDict, PyModule, PyObject, PyResult, Python}; -use exceptions::GraphError; use hg::dagops; use hg::Revision; use std::collections::HashSet; diff --git a/rust/hg-cpython/src/dirstate.rs b/rust/hg-cpython/src/dirstate.rs --- a/rust/hg-cpython/src/dirstate.rs +++ b/rust/hg-cpython/src/dirstate.rs @@ -19,17 +19,14 @@ use hg::{ DirstateEntry, DirstateMapError, DirstatePackError, DirstateParents, DirstateParseError, DirstateVec, }; +use libc::{c_char, c_int}; +#[cfg(feature = "python27")] +use python27_sys::PyCapsule_Import; +#[cfg(feature = "python3")] +use python3_sys::PyCapsule_Import; +use std::cell::RefCell; use std::collections::HashMap; use std::ffi::CStr; - -#[cfg(feature = "python27")] -extern crate python27_sys as python_sys; -#[cfg(feature = "python3")] -extern crate python3_sys as python_sys; - -use self::python_sys::PyCapsule_Import; -use libc::{c_char, c_int}; -use std::cell::RefCell; use std::mem::transmute; /// C code uses a custom `dirstate_tuple` type, checks in multiple instances diff --git a/rust/hg-cpython/src/discovery.rs b/rust/hg-cpython/src/discovery.rs --- a/rust/hg-cpython/src/discovery.rs +++ b/rust/hg-cpython/src/discovery.rs @@ -12,13 +12,15 @@ //! - [`PartialDiscover`] is the Rust implementation of //! `mercurial.setdiscovery.partialdiscovery`. -use crate::conversion::{py_set, rev_pyiter_collect}; -use cindex::Index; +use crate::{ + cindex::Index, + conversion::{py_set, rev_pyiter_collect}, + exceptions::GraphError, +}; use cpython::{ ObjectProtocol, PyDict, PyModule, PyObject, PyResult, Python, PythonObject, ToPyObject, }; -use exceptions::GraphError; use hg::discovery::PartialDiscovery as CorePartialDiscovery; use hg::Revision; diff --git a/rust/hg-cpython/src/exceptions.rs b/rust/hg-cpython/src/exceptions.rs --- a/rust/hg-cpython/src/exceptions.rs +++ b/rust/hg-cpython/src/exceptions.rs @@ -12,8 +12,10 @@ //! existing Python exceptions if appropriate. //! //! [`GraphError`]: struct.GraphError.html -use cpython::exc::{RuntimeError, ValueError}; -use cpython::{exc, PyErr, Python}; +use cpython::{ + exc::{IOError, RuntimeError, ValueError}, + py_exception, PyErr, Python, +}; use hg; py_exception!(rustext, GraphError, ValueError); @@ -55,7 +57,7 @@ impl PatternFileError { match inner { hg::PatternFileError::IO(e) => { let value = (e.raw_os_error().unwrap_or(2), e.to_string()); - PyErr::new::(py, value) + PyErr::new::(py, value) } hg::PatternFileError::Pattern(e, l) => match e { hg::PatternError::UnsupportedSyntax(m) => { diff --git a/rust/hg-cpython/src/filepatterns.rs b/rust/hg-cpython/src/filepatterns.rs --- a/rust/hg-cpython/src/filepatterns.rs +++ b/rust/hg-cpython/src/filepatterns.rs @@ -10,10 +10,10 @@ //! `hg-core` crate. From Python, this will be seen as `rustext.filepatterns` //! and can be used as replacement for the the pure `filepatterns` Python module. //! +use crate::exceptions::{PatternError, PatternFileError}; use cpython::{ PyBytes, PyDict, PyModule, PyObject, PyResult, PyTuple, Python, ToPyObject, }; -use exceptions::{PatternError, PatternFileError}; use hg::{build_single_regex, read_pattern_file, LineNumber, PatternTuple}; /// Rust does not like functions with different return signatures. diff --git a/rust/hg-cpython/src/lib.rs b/rust/hg-cpython/src/lib.rs --- a/rust/hg-cpython/src/lib.rs +++ b/rust/hg-cpython/src/lib.rs @@ -19,10 +19,10 @@ //! 'Generic DAG ancestor algorithms - Rust implementation' //! ``` +/// This crate uses nested private macros, `extern crate` is still needed in +/// 2018 edition. #[macro_use] extern crate cpython; -extern crate hg; -extern crate libc; pub mod ancestors; mod cindex;