2016-05-05 1 views
0

Во многих языках программирования можно найти, если файл является исполняемым или нет, делая bitwise and между mode bits и 0111, что-то вроде:Как проверить, выполняется ли файл с помощью побитовых операций в Rust?

is_exec = (mode & 0111) != 0 

Где mode представляет биты режима с восьмеричным значением что-то вроде 100755, или 755.

Пример командной строки:

perl -e 'printf "%o\n", (stat "file")[2] & 0111' 

Я пытаюсь следовать этому подходу, используя ржавчину, но не может заставить его работать, это код, я использую:

fn print_dir(path: &PathBuf) {                                    
    let files = match fs::read_dir(&path) {                                
     Err(f) => {                                      
      println!("{}", f);                                    
      return;                                      
     }                                         
     Ok(f) => f                                       
    };                                          

    for f in files {                                      
     let file = f.unwrap();                                    
     let mode = file.metadata().unwrap().permissions().mode();                           
     println!("path: {} {:o} - {} {:0}", file.path().display(), mode, mode, mode & 0111);                    
    }                                          
} 

mode & 0111 не ведет себя так, как ожидалось, так как всегда возвращает положительные результаты. Я попробовал подобный код в Go, и это было очень прямо вперед:

var is_exec bool 
if m := f.Mode(); !m.IsDir() && m&0111 != 0 { 
    is_exec = true 
} 

Любая идея о том, как сделать это с Rust?

ответ

4

В ржавчине ведущий 0 не означает, что число находится в восьмеричном. Вы хотите использовать префикс 0o вместо:

fn main() { 
    println!("{}", 0111); // 111 
    println!("{}", 0o111); // 73 
} 

Other prefixes вы можете быть заинтересованы в:

0xBEEF // Hex (Base 16) => 48879 
0o1234 // Octal (Base 8) => 668 
0b0101 // Binary (Base 2) =>  5 
1

Вы близки, вы хотите использовать это (я использую unwrap() в примере для краткости):

let mode = fs::metadata(&f).unwrap().mode(); 
if mode & 0o111 != 0 { 
    println!("binary..."); 
} 

кредит из-за some code я работал с некоторое время назад.