1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145
/*! Is there an executable file at the given path? [![](https://docs.rs/is_executable/badge.svg)](https://docs.rs/is_executable/) [![](http://meritbadge.herokuapp.com/is_executable) ![](https://img.shields.io/crates/d/is_executable.png)](https://crates.io/crates/is_executable) [![Unix Build Status](https://travis-ci.org/fitzgen/is_executable.png?branch=master)](https://travis-ci.org/fitzgen/is_executable) [![Windows Build Status](https://ci.appveyor.com/api/projects/status/github/fitzgen/is_executable?branch=master&svg=true)](https://ci.appveyor.com/project/fitzgen/is-executable) A small helper function which determines whether or not the given path points to an executable file. If there is no file at the given path, or the file is not executable, then `false` is returned. When there is a file and the file is executable, then `true` is returned. This crate works on both unix-based operating systems (mac, linux, freebsd, etc.) and Windows. The API comes in two flavors: 1. An extension trait to add an `is_executable` method on `std::path::Path`: ```rust use std::path::Path; use is_executable::IsExecutable; fn main() { let path = Path::new("some/path/to/a/file"); // Determine if `path` is executable. if path.is_executable() { println!("The path is executable!"); } else { println!("The path is _not_ executable!"); } } ``` 2. For convenience, a standalone `is_executable` function, which takes any `AsRef<Path>`: ```rust use std::path::Path; use is_executable::is_executable; fn main() { let path = Path::new("some/path/to/a/file"); // Determine if `path` is executable. if is_executable(&path) { println!("The path is executable!"); } else { println!("The path is _not_ executable!"); } } ``` */ #[cfg(target_os = "windows")] extern crate winapi; use std::path::Path; /// Returns `true` if there is a file at the given path and it is /// executable. Returns `false` otherwise. /// /// See the module documentation for details. pub fn is_executable<P>(path: P) -> bool where P: AsRef<Path>, { path.as_ref().is_executable() } /// An extension trait for `std::fs::Path` providing an `is_executable` method. /// /// See the module documentation for examples. pub trait IsExecutable { /// Returns `true` if there is a file at the given path and it is /// executable. Returns `false` otherwise. /// /// See the module documentation for details. fn is_executable(&self) -> bool; } #[cfg(unix)] mod unix { use std::os::unix::fs::PermissionsExt; use std::path::Path; use super::IsExecutable; impl IsExecutable for Path { fn is_executable(&self) -> bool { let metadata = match self.metadata() { Ok(metadata) => metadata, Err(_) => return false, }; let permissions = metadata.permissions(); metadata.is_file() && permissions.mode() & 0o111 != 0 } } } #[cfg(target_os = "windows")] mod windows { use std::os::windows::ffi::OsStrExt; use std::path::Path; use winapi::ctypes::{c_ulong, wchar_t}; use winapi::um::winbase::GetBinaryTypeW; use super::IsExecutable; impl IsExecutable for Path { fn is_executable(&self) -> bool { let windows_string = self .as_os_str() .encode_wide() .chain(Some(0)) .collect::<Vec<wchar_t>>(); let windows_string_ptr = windows_string.as_ptr(); let mut binary_type: c_ulong = 42; let binary_type_ptr = &mut binary_type as *mut c_ulong; let ret = unsafe { GetBinaryTypeW(windows_string_ptr, binary_type_ptr) }; if binary_type_ptr.is_null() { return false; } if ret != 0 { let binary_type = unsafe { *binary_type_ptr }; match binary_type { 0 // A 32-bit Windows-based application | 1 // An MS-DOS-based application | 2 // A 16-bit Windows-based application | 3 // A PIF file that executes an MS-DOS-based application | 4 // A POSIX – based application | 5 // A 16-bit OS/2-based application | 6 // A 64-bit Windows-based application => return true, _ => (), } } false } } }