]> git.lizzy.rs Git - rust.git/commitdiff
extract area to a crate
authorAleksey Kladov <aleksey.kladov@gmail.com>
Fri, 4 Jan 2019 13:01:06 +0000 (16:01 +0300)
committerAleksey Kladov <aleksey.kladov@gmail.com>
Fri, 4 Jan 2019 13:58:10 +0000 (16:58 +0300)
Cargo.lock
crates/ra_arena/Cargo.toml [new file with mode: 0644]
crates/ra_arena/src/lib.rs [new file with mode: 0644]
crates/ra_lsp_server/src/main_loop.rs
crates/ra_lsp_server/src/main_loop/handlers.rs
crates/ra_lsp_server/src/server_world.rs
crates/ra_vfs/Cargo.toml
crates/ra_vfs/src/arena.rs [deleted file]
crates/ra_vfs/src/lib.rs

index 5f35f2872dee09dee7a2b8628b92b33bc25bae8a..4666347f8eefbd958d9f2417d073d82fb5be7928 100644 (file)
@@ -683,6 +683,10 @@ dependencies = [
  "unicase 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)",
 ]
 
+[[package]]
+name = "ra_arena"
+version = "0.1.0"
+
 [[package]]
 name = "ra_cli"
 version = "0.1.0"
@@ -808,6 +812,7 @@ version = "0.1.0"
 dependencies = [
  "crossbeam-channel 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)",
  "log 0.4.6 (registry+https://github.com/rust-lang/crates.io-index)",
+ "ra_arena 0.1.0",
  "relative-path 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)",
  "rustc-hash 1.0.1 (registry+https://github.com/rust-lang/crates.io-index)",
  "tempfile 3.0.5 (registry+https://github.com/rust-lang/crates.io-index)",
diff --git a/crates/ra_arena/Cargo.toml b/crates/ra_arena/Cargo.toml
new file mode 100644 (file)
index 0000000..9594e2d
--- /dev/null
@@ -0,0 +1,5 @@
+[package]
+edition = "2018"
+name = "ra_arena"
+version = "0.1.0"
+authors = ["Aleksey Kladov <aleksey.kladov@gmail.com>"]
diff --git a/crates/ra_arena/src/lib.rs b/crates/ra_arena/src/lib.rs
new file mode 100644 (file)
index 0000000..44d9e82
--- /dev/null
@@ -0,0 +1,97 @@
+//! Yet another index-based arena.
+
+use std::{
+    fmt,
+    marker::PhantomData,
+    ops::{Index, IndexMut},
+};
+
+#[derive(Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
+pub struct RawId(u32);
+
+impl From<RawId> for u32 {
+    fn from(raw: RawId) -> u32 {
+        raw.0
+    }
+}
+
+impl From<u32> for RawId {
+    fn from(id: u32) -> RawId {
+        RawId(id)
+    }
+}
+
+impl fmt::Debug for RawId {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        self.0.fmt(f)
+    }
+}
+
+impl fmt::Display for RawId {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        self.0.fmt(f)
+    }
+}
+
+#[derive(Clone, Debug)]
+pub struct Arena<ID: ArenaId, T> {
+    data: Vec<T>,
+    _ty: PhantomData<ID>,
+}
+
+#[macro_export]
+macro_rules! impl_arena_id {
+    ($name:ident) => {
+        impl $crate::ArenaId for $name {
+            fn from_raw(raw: $crate::RawId) -> Self {
+                $name(raw)
+            }
+            fn into_raw(self) -> $crate::RawId {
+                self.0
+            }
+        }
+    };
+}
+
+pub trait ArenaId {
+    fn from_raw(raw: RawId) -> Self;
+    fn into_raw(self) -> RawId;
+}
+
+impl<ID: ArenaId, T> Arena<ID, T> {
+    pub fn alloc(&mut self, value: T) -> ID {
+        let id = RawId(self.data.len() as u32);
+        self.data.push(value);
+        ID::from_raw(id)
+    }
+    pub fn iter<'a>(&'a self) -> impl Iterator<Item = (ID, &'a T)> {
+        self.data
+            .iter()
+            .enumerate()
+            .map(|(idx, value)| (ID::from_raw(RawId(idx as u32)), value))
+    }
+}
+
+impl<ID: ArenaId, T> Default for Arena<ID, T> {
+    fn default() -> Arena<ID, T> {
+        Arena {
+            data: Vec::new(),
+            _ty: PhantomData,
+        }
+    }
+}
+
+impl<ID: ArenaId, T> Index<ID> for Arena<ID, T> {
+    type Output = T;
+    fn index(&self, idx: ID) -> &T {
+        let idx = idx.into_raw().0 as usize;
+        &self.data[idx]
+    }
+}
+
+impl<ID: ArenaId, T> IndexMut<ID> for Arena<ID, T> {
+    fn index_mut(&mut self, idx: ID) -> &mut T {
+        let idx = idx.into_raw().0 as usize;
+        &mut self.data[idx]
+    }
+}
index 06dd373c02fce5761a8a38d04141eecd2df6faa6..60d9671dee7b139049d7c67c5b5c554802a371ea 100644 (file)
@@ -350,7 +350,7 @@ fn on_notification(
                 .write()
                 .add_file_overlay(&path, params.text_document.text)
             {
-                subs.add_sub(FileId(file_id.0));
+                subs.add_sub(FileId(file_id.0.into()));
             }
             return Ok(());
         }
@@ -379,7 +379,7 @@ fn on_notification(
                 .to_file_path()
                 .map_err(|()| format_err!("invalid uri: {}", uri))?;
             if let Some(file_id) = state.vfs.write().remove_file_overlay(path.as_path()) {
-                subs.remove_sub(FileId(file_id.0));
+                subs.remove_sub(FileId(file_id.0.into()));
             }
             let params = req::PublishDiagnosticsParams {
                 uri,
index b5792f3b81f1eb63328a7e52b896634d43c4a40a..4e895a9a9ea0892ce021afedc9065305e5c64e8a 100644 (file)
@@ -337,7 +337,10 @@ fn for_file(world: &ServerWorld, file_id: FileId) -> Result<Option<CargoTargetSp
                 None => return Ok(None),
             };
             let file_id = world.analysis().crate_root(crate_id)?;
-            let path = world.vfs.read().file2path(ra_vfs::VfsFile(file_id.0));
+            let path = world
+                .vfs
+                .read()
+                .file2path(ra_vfs::VfsFile(file_id.0.into()));
             let res = world.workspaces.iter().find_map(|ws| {
                 let tgt = ws.target_by_root(&path)?;
                 let res = CargoTargetSpec {
index c183c25afdc2807baf083e9b89308baa526ebc12..ebf2b15ccd80d120f9c05d0e672d00647e2bc4ec 100644 (file)
@@ -49,7 +49,7 @@ pub fn new(root: PathBuf, workspaces: Vec<CargoWorkspace>) -> ServerWorldState {
         let (mut vfs, roots) = Vfs::new(roots);
         for r in roots {
             let is_local = vfs.root2path(r).starts_with(&root);
-            change.add_root(SourceRootId(r.0), is_local);
+            change.add_root(SourceRootId(r.0.into()), is_local);
         }
 
         let mut crate_graph = CrateGraph::default();
@@ -60,7 +60,7 @@ pub fn new(root: PathBuf, workspaces: Vec<CargoWorkspace>) -> ServerWorldState {
                 for tgt in pkg.targets(ws) {
                     let root = tgt.root(ws);
                     if let Some(file_id) = vfs.load(root) {
-                        let file_id = FileId(file_id.0);
+                        let file_id = FileId(file_id.0.into());
                         let crate_id = crate_graph.add_crate_root(file_id);
                         if tgt.kind(ws) == TargetKind::Lib {
                             pkg_to_lib_crate.insert(pkg, crate_id);
@@ -113,14 +113,19 @@ pub fn process_changes(
                     if root_path.starts_with(&self.root) {
                         self.roots_to_scan -= 1;
                         for (file, path, text) in files {
-                            change.add_file(SourceRootId(root.0), FileId(file.0), path, text);
+                            change.add_file(
+                                SourceRootId(root.0.into()),
+                                FileId(file.0.into()),
+                                path,
+                                text,
+                            );
                         }
                     } else {
                         let files = files
                             .into_iter()
-                            .map(|(vfsfile, path, text)| (FileId(vfsfile.0), path, text))
+                            .map(|(vfsfile, path, text)| (FileId(vfsfile.0.into()), path, text))
                             .collect();
-                        libs.push((SourceRootId(root.0), files));
+                        libs.push((SourceRootId(root.0.into()), files));
                     }
                 }
                 VfsChange::AddFile {
@@ -129,13 +134,18 @@ pub fn process_changes(
                     path,
                     text,
                 } => {
-                    change.add_file(SourceRootId(root.0), FileId(file.0), path, text);
+                    change.add_file(
+                        SourceRootId(root.0.into()),
+                        FileId(file.0.into()),
+                        path,
+                        text,
+                    );
                 }
                 VfsChange::RemoveFile { root, file, path } => {
-                    change.remove_file(SourceRootId(root.0), FileId(file.0), path)
+                    change.remove_file(SourceRootId(root.0.into()), FileId(file.0.into()), path)
                 }
                 VfsChange::ChangeFile { file, text } => {
-                    change.change_file(FileId(file.0), text);
+                    change.change_file(FileId(file.0.into()), text);
                 }
             }
         }
@@ -173,18 +183,18 @@ pub fn uri_to_file_id(&self, uri: &Url) -> Result<FileId> {
             .read()
             .path2file(&path)
             .ok_or_else(|| format_err!("unknown file: {}", path.display()))?;
-        Ok(FileId(file.0))
+        Ok(FileId(file.0.into()))
     }
 
     pub fn file_id_to_uri(&self, id: FileId) -> Result<Url> {
-        let path = self.vfs.read().file2path(VfsFile(id.0));
+        let path = self.vfs.read().file2path(VfsFile(id.0.into()));
         let url = Url::from_file_path(&path)
             .map_err(|_| format_err!("can't convert path to url: {}", path.display()))?;
         Ok(url)
     }
 
     pub fn path_to_uri(&self, root: SourceRootId, path: &RelativePathBuf) -> Result<Url> {
-        let base = self.vfs.read().root2path(VfsRoot(root.0));
+        let base = self.vfs.read().root2path(VfsRoot(root.0.into()));
         let path = path.to_path(base);
         let url = Url::from_file_path(&path)
             .map_err(|_| format_err!("can't convert path to url: {}", path.display()))?;
index 7c170cdfcdaaaae6384128d36dd3cd6ad67245ea..e637063c97b34d97149edbd5b98a852648f76fe6 100644 (file)
@@ -12,6 +12,7 @@ crossbeam-channel = "0.3.5"
 log = "0.4.6"
 
 thread_worker = { path = "../thread_worker" }
+ra_arena = { path = "../ra_arena" }
 
 [dev-dependencies]
 tempfile = "3"
diff --git a/crates/ra_vfs/src/arena.rs b/crates/ra_vfs/src/arena.rs
deleted file mode 100644 (file)
index 6b42ae2..0000000
+++ /dev/null
@@ -1,53 +0,0 @@
-use std::{
-    marker::PhantomData,
-    ops::{Index, IndexMut},
-};
-
-#[derive(Clone, Debug)]
-pub(crate) struct Arena<ID: ArenaId, T> {
-    data: Vec<T>,
-    _ty: PhantomData<ID>,
-}
-
-pub(crate) trait ArenaId {
-    fn from_u32(id: u32) -> Self;
-    fn to_u32(self) -> u32;
-}
-
-impl<ID: ArenaId, T> Arena<ID, T> {
-    pub fn alloc(&mut self, value: T) -> ID {
-        let id = self.data.len() as u32;
-        self.data.push(value);
-        ID::from_u32(id)
-    }
-    pub fn iter<'a>(&'a self) -> impl Iterator<Item = (ID, &'a T)> {
-        self.data
-            .iter()
-            .enumerate()
-            .map(|(idx, value)| (ID::from_u32(idx as u32), value))
-    }
-}
-
-impl<ID: ArenaId, T> Default for Arena<ID, T> {
-    fn default() -> Arena<ID, T> {
-        Arena {
-            data: Vec::new(),
-            _ty: PhantomData,
-        }
-    }
-}
-
-impl<ID: ArenaId, T> Index<ID> for Arena<ID, T> {
-    type Output = T;
-    fn index(&self, idx: ID) -> &T {
-        let idx = idx.to_u32() as usize;
-        &self.data[idx]
-    }
-}
-
-impl<ID: ArenaId, T> IndexMut<ID> for Arena<ID, T> {
-    fn index_mut(&mut self, idx: ID) -> &mut T {
-        let idx = idx.to_u32() as usize;
-        &mut self.data[idx]
-    }
-}
index 5bbc3e99353371e424270b551bdad958d6e73c9c..cdea18d734227494429c0a3715a3654c6c1ae2fe 100644 (file)
@@ -13,7 +13,6 @@
 //! VFS is based on a concept of roots: a set of directories on the file system
 //! which are watched for changes. Typically, there will be a root for each
 //! Cargo package.
-mod arena;
 mod io;
 
 use std::{
 use crossbeam_channel::Receiver;
 use walkdir::DirEntry;
 use thread_worker::WorkerHandle;
-
-use crate::{
-    arena::{ArenaId, Arena},
-};
+use ra_arena::{Arena, RawId, impl_arena_id};
 
 pub use crate::io::TaskResult as VfsTask;
 
@@ -68,29 +64,13 @@ fn has_rs_extension(p: &Path) -> bool {
     p.extension() == Some(OsStr::new("rs"))
 }
 
-#[derive(Clone, Copy, PartialEq, Eq, Debug, Hash)]
-pub struct VfsRoot(pub u32);
-
-impl ArenaId for VfsRoot {
-    fn from_u32(idx: u32) -> VfsRoot {
-        VfsRoot(idx)
-    }
-    fn to_u32(self) -> u32 {
-        self.0
-    }
-}
-
-#[derive(Clone, Copy, PartialEq, Eq, Debug, Hash)]
-pub struct VfsFile(pub u32);
+#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
+pub struct VfsRoot(pub RawId);
+impl_arena_id!(VfsRoot);
 
-impl ArenaId for VfsFile {
-    fn from_u32(idx: u32) -> VfsFile {
-        VfsFile(idx)
-    }
-    fn to_u32(self) -> u32 {
-        self.0
-    }
-}
+#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
+pub struct VfsFile(pub RawId);
+impl_arena_id!(VfsFile);
 
 struct VfsFileData {
     root: VfsRoot,