mirror of
https://github.com/facebook/sapling.git
synced 2024-12-24 13:34:37 +03:00
backingstore: add Tree
and TreeEntry
Rust structs to pass manifest
Summary: This diff adds Rust structs to represent the data EdenFS wants from a manifest so we can pass these to EdenFS. Reviewed By: wez Differential Revision: D18365440 fbshipit-source-id: b474ceb698d9230e1b02c2cce1bec2a32bd3f94f
This commit is contained in:
parent
1713cfca79
commit
9328adfaf9
@ -7,7 +7,7 @@
|
||||
* This file is generated with cbindgen. Please run `./tools/cbindgen.sh` to
|
||||
* update this file.
|
||||
*
|
||||
* @generated SignedSource<<9e8a2dc050438223b658363f7614992e>>
|
||||
* @generated SignedSource<<d354b7cf7fd596344df4dabeebf5e77e>>
|
||||
*
|
||||
*/
|
||||
|
||||
@ -76,6 +76,13 @@ public:
|
||||
#include <cstdlib>
|
||||
#include <new>
|
||||
|
||||
enum class RustTreeEntryType : uint8_t {
|
||||
Tree,
|
||||
RegularFile,
|
||||
ExecutableFile,
|
||||
Symlink,
|
||||
};
|
||||
|
||||
struct RustBackingStore;
|
||||
|
||||
template<typename T>
|
||||
@ -94,6 +101,22 @@ operator folly::ByteRange() const {
|
||||
}
|
||||
};
|
||||
|
||||
struct RustTreeEntry {
|
||||
RustCBytes hash;
|
||||
RustCBytes name;
|
||||
RustTreeEntryType ttype;
|
||||
uint64_t *size;
|
||||
RustCBytes *content_sha1;
|
||||
};
|
||||
|
||||
struct RustTree {
|
||||
const RustTreeEntry *entries;
|
||||
/// This makes sure `entries` above is pointing to a valid memory.
|
||||
RustVec<RustTreeEntry> *_entries;
|
||||
uintptr_t length;
|
||||
RustCBytes hash;
|
||||
};
|
||||
|
||||
extern "C" {
|
||||
|
||||
void rust_backingstore_free(RustBackingStore *store);
|
||||
|
@ -78,6 +78,7 @@ public:
|
||||
[export]
|
||||
prefix= "Rust"
|
||||
exclude = ["CFallible"]
|
||||
include = ["Tree", "TreeEntry", "TreeEntryType"]
|
||||
|
||||
[export.rename]
|
||||
"CFallible" = "CFallibleBase"
|
||||
|
@ -14,6 +14,8 @@ mod backingstore;
|
||||
mod cbytes;
|
||||
mod cfallible;
|
||||
mod tests;
|
||||
mod tree;
|
||||
|
||||
pub use cbytes::CBytes;
|
||||
pub use cfallible::CFallible;
|
||||
pub use tree::Tree;
|
||||
|
105
eden/scm/lib/backingstore/src/raw/tree.rs
Normal file
105
eden/scm/lib/backingstore/src/raw/tree.rs
Normal file
@ -0,0 +1,105 @@
|
||||
/*
|
||||
* Copyright (c) Facebook, Inc. and its affiliates.
|
||||
*
|
||||
* This software may be used and distributed according to the terms of the
|
||||
* GNU General Public License version 2.
|
||||
*/
|
||||
|
||||
//! Representation of tree in EdenFS.
|
||||
//!
|
||||
//! Structs in this file should be keep in sync with `eden/fs/model/{Tree, TreeEntry}.h`.
|
||||
|
||||
use crate::raw::CBytes;
|
||||
use failure::{format_err, Fallible};
|
||||
use manifest::{tree::List, FileType, FsNode};
|
||||
use std::convert::TryFrom;
|
||||
use types::PathComponentBuf;
|
||||
|
||||
#[repr(u8)]
|
||||
pub enum TreeEntryType {
|
||||
Tree,
|
||||
RegularFile,
|
||||
ExecutableFile,
|
||||
Symlink,
|
||||
}
|
||||
|
||||
impl From<FileType> for TreeEntryType {
|
||||
fn from(file_type: FileType) -> Self {
|
||||
match file_type {
|
||||
FileType::Regular => TreeEntryType::RegularFile,
|
||||
FileType::Executable => TreeEntryType::ExecutableFile,
|
||||
FileType::Symlink => TreeEntryType::Symlink,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[repr(C)]
|
||||
pub struct TreeEntry {
|
||||
hash: CBytes,
|
||||
name: CBytes,
|
||||
ttype: TreeEntryType,
|
||||
// Using pointer as `Option<T>`
|
||||
size: *mut u64,
|
||||
content_sha1: *mut CBytes,
|
||||
}
|
||||
|
||||
impl TreeEntry {
|
||||
fn try_from_path_node(path: PathComponentBuf, node: FsNode) -> Fallible<Self> {
|
||||
let (ttype, hash) = match node {
|
||||
FsNode::Directory(Some(hgid)) => (TreeEntryType::Tree, hgid.as_ref().to_vec()),
|
||||
FsNode::File(metadata) => (metadata.file_type.into(), metadata.hgid.as_ref().to_vec()),
|
||||
_ => return Err(format_err!("received an ephemeral directory")),
|
||||
};
|
||||
|
||||
Ok(TreeEntry {
|
||||
hash: hash.into(),
|
||||
name: path.as_ref().as_byte_slice().to_vec().into(),
|
||||
ttype,
|
||||
// TODO: we currently do not have these information stored in Mercurial.
|
||||
size: std::ptr::null_mut(),
|
||||
content_sha1: std::ptr::null_mut(),
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
#[repr(C)]
|
||||
pub struct Tree {
|
||||
entries: *const TreeEntry,
|
||||
/// This makes sure `entries` above is pointing to a valid memory.
|
||||
entries_ptr: *mut Vec<TreeEntry>,
|
||||
length: usize,
|
||||
hash: CBytes,
|
||||
}
|
||||
|
||||
impl TryFrom<List> for Tree {
|
||||
type Error = failure::Error;
|
||||
|
||||
fn try_from(list: List) -> Result<Self, Self::Error> {
|
||||
match list {
|
||||
List::NotFound | List::File => Err(format_err!("not found")),
|
||||
List::Directory(list) => {
|
||||
let entries = list
|
||||
.into_iter()
|
||||
.map(|(path, node)| TreeEntry::try_from_path_node(path, node))
|
||||
.collect::<Fallible<Vec<_>>>()?;
|
||||
|
||||
let entries = Box::new(entries);
|
||||
let length = entries.len();
|
||||
|
||||
Ok(Tree {
|
||||
entries: entries.as_ptr(),
|
||||
entries_ptr: Box::into_raw(entries),
|
||||
length,
|
||||
hash: Vec::new().into(),
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Drop for Tree {
|
||||
fn drop(&mut self) {
|
||||
let entry = unsafe { Box::from_raw(self.entries_ptr) };
|
||||
drop(entry);
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user