Fixed /skel problem creating files/dirs as root

This commit is contained in:
Bruce Leidl 2018-03-19 15:29:57 -04:00
parent 70fff31f46
commit 0bb2496d92
2 changed files with 22 additions and 10 deletions

View File

@ -166,7 +166,8 @@ impl Realm {
fn create_home_directory(&self) -> Result<()> { fn create_home_directory(&self) -> Result<()> {
let home = self.base_path().join("home"); let home = self.base_path().join("home");
mkdir_chown(&home, 1000, 1000)?; fs::create_dir(&home)?;
chown(&home, 1000, 1000)?;
let skel = PathBuf::from(REALMS_BASE_PATH).join("skel"); let skel = PathBuf::from(REALMS_BASE_PATH).join("skel");
if skel.exists() { if skel.exists() {
info!("Populating realm home directory with files from {}", skel.display()); info!("Populating realm home directory with files from {}", skel.display());

View File

@ -48,10 +48,7 @@ pub fn is_valid_realm_name(name: &str) -> bool {
name.chars().all(is_alphanum_or_dash) name.chars().all(is_alphanum_or_dash)
} }
pub fn mkdir_chown(path: &Path, uid: u32, gid: u32) -> io::Result<()> { pub fn chown(path: &Path, uid: u32, gid: u32) -> io::Result<()> {
if !path.exists() {
fs::create_dir(path)?;
}
let cstr = CString::new(path.as_os_str().as_bytes())?; let cstr = CString::new(path.as_os_str().as_bytes())?;
unsafe { unsafe {
if libc::chown(cstr.as_ptr(), uid, gid) == -1 { if libc::chown(cstr.as_ptr(), uid, gid) == -1 {
@ -61,15 +58,29 @@ pub fn mkdir_chown(path: &Path, uid: u32, gid: u32) -> io::Result<()> {
Ok(()) Ok(())
} }
fn copy_path(from: &Path, to: &Path) -> Result<()> {
if to.exists() {
bail!("destination path {} already exists which is not expected", to.display());
}
let meta = from.metadata()?;
if from.is_dir() {
fs::create_dir(to)?;
} else {
fs::copy(&from, &to)?;
}
chown(to, meta.uid(), meta.gid())?;
Ok(())
}
pub fn copy_tree(from_base: &Path, to_base: &Path) -> Result<()> { pub fn copy_tree(from_base: &Path, to_base: &Path) -> Result<()> {
for entry in WalkDir::new(from_base) { for entry in WalkDir::new(from_base) {
let path = entry?.path().to_owned(); let path = entry?.path().to_owned();
let to = to_base.join(path.strip_prefix(from_base)?); let to = to_base.join(path.strip_prefix(from_base)?);
if path.is_dir() { if &to != to_base {
let meta = path.metadata()?; copy_path(&path, &to)
mkdir_chown(&to, meta.uid(), meta.gid())?;
} else {
fs::copy(&path, &to)
.map_err(|e| format_err!("failed to copy {} to {}: {}", path.display(), to.display(), e))?; .map_err(|e| format_err!("failed to copy {} to {}: {}", path.display(), to.display(), e))?;
} }
} }