├── .gitignore ├── src ├── symbols.rs ├── _clap.rs ├── clipboard.rs ├── generator │ └── tests.rs ├── main.rs └── generator.rs ├── README.md ├── Cargo.toml └── Cargo.lock /.gitignore: -------------------------------------------------------------------------------- 1 | /target 2 | **/*.rs.bk 3 | -------------------------------------------------------------------------------- /src/symbols.rs: -------------------------------------------------------------------------------- 1 | pub const SYMBOLS_SIZE: usize = 9; 2 | 3 | pub const SYMBOLS: [&str; SYMBOLS_SIZE] = ["$", "-", "_", "!", "@", "#", "*", ".", "/"]; 4 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | Password generator 2 | ================== 3 | 4 | (I'm learning Rust, and this is my first module!) 5 | 6 | Generates passwords that are secure and easy-to-type on mobile. 7 | 8 | ``` 9 | $ ./passgen 10 | correct horse battery 20$ Staple 11 | ``` 12 | 13 | Thanks 14 | ------ 15 | 16 | MIT license 17 | -------------------------------------------------------------------------------- /Cargo.toml: -------------------------------------------------------------------------------- 1 | [package] 2 | name = "passgen" 3 | version = "0.1.0" 4 | authors = ["Rico Sta. Cruz "] 5 | edition = "2018" 6 | 7 | # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html 8 | 9 | [dependencies] 10 | clap = "2.33.0" 11 | rand = "*" 12 | regex = "1" 13 | clipboard = "*" 14 | -------------------------------------------------------------------------------- /src/_clap.rs: -------------------------------------------------------------------------------- 1 | // extern crate clap; 2 | // use clap::{App, Arg}; 3 | // let app = App::new("Passgen").version("0.0.1").arg( 4 | // Arg::with_name("words") 5 | // .short("w") 6 | // .long("words") 7 | // .help("Number of words") 8 | // .value_name("N") 9 | // .takes_value(true), 10 | // ); 11 | 12 | // let matches = app.get_matches(); 13 | // println!("{:?}", matches); 14 | -------------------------------------------------------------------------------- /src/clipboard.rs: -------------------------------------------------------------------------------- 1 | extern crate clipboard; 2 | 3 | use clipboard::{ClipboardContext, ClipboardProvider}; 4 | use std::boxed::Box; 5 | use std::io::Write; 6 | use std::process::{Command, Stdio}; 7 | 8 | /// Copies a string to a clipboard. 9 | pub fn copy_to_clipboard(value: &str) { 10 | match copy_via_xsel(value) { 11 | Err(_) => match copy_via_clipboard_rs(value) { 12 | Err(_) => (), 13 | Ok(_) => (), 14 | }, 15 | Ok(_) => (), 16 | }; 17 | } 18 | 19 | /// Copy via the 'xsel' utility, if present. 20 | /// This is preferrable to `clipboard` or `x11-clipboard` because it won't clear the clipboard 21 | /// after the program exits. 22 | pub fn copy_via_xsel(value: &str) -> Result<(), std::io::Error> { 23 | let proc = Command::new("xsel") 24 | .stdin(Stdio::piped()) 25 | .arg("-b") 26 | .spawn()?; 27 | 28 | proc.stdin.unwrap().write_all(value.as_bytes()) 29 | } 30 | 31 | /// Copy via the 'xsel' utility, if present. 32 | pub fn copy_via_clipboard_rs(value: &str) -> Result<(), Box<(dyn std::error::Error + 'static)>> { 33 | let mut ctx: ClipboardContext = ClipboardProvider::new()?; 34 | ctx.set_contents(value.to_owned()) 35 | } 36 | -------------------------------------------------------------------------------- /src/generator/tests.rs: -------------------------------------------------------------------------------- 1 | extern crate regex; 2 | use super::*; 3 | use regex::Regex; 4 | 5 | #[test] 6 | fn it_has_defaults() { 7 | let gen = Generator::new(); 8 | assert_eq!(gen.word_count, 4); 9 | assert_eq!(gen.use_spaces, true); 10 | } 11 | 12 | #[test] 13 | fn it_can_set_things() { 14 | let gen = Generator::new().word_count(8).use_spaces(false); 15 | assert_eq!(gen.word_count, 8); 16 | assert_eq!(gen.use_spaces, false); 17 | } 18 | 19 | #[test] 20 | fn it_can_generate_passwords() { 21 | let has_spaces = Regex::new(r" ").unwrap(); 22 | let has_letters = Regex::new(r"[a-zA-Z]").unwrap(); 23 | let has_numbers = Regex::new(r"[0-9]").unwrap(); 24 | 25 | for _x in 0..100 { 26 | let result = Generator::new().generate(); 27 | assert!(result.len() > 0); 28 | assert!(has_spaces.is_match(&result)); 29 | assert!(has_letters.is_match(&result)); 30 | assert!(has_numbers.is_match(&result)); 31 | } 32 | } 33 | 34 | #[test] 35 | // Use `cargo test[ify] -- --nocapture` to show these 36 | fn it_print_generated_passwords() { 37 | println!("Examples:"); 38 | for _x in 0..8 { 39 | let result = Generator::new().generate(); 40 | println!(" {}", result); 41 | } 42 | } 43 | -------------------------------------------------------------------------------- /src/main.rs: -------------------------------------------------------------------------------- 1 | //! Utilities for generating random passwords 2 | //! 3 | //! We generate random passwords with this. 4 | //! 5 | //! ``` 6 | //! let password = Generator::new().generate(); 7 | //! println!("{}", password) 8 | //! // => "correct horse Battery staple $20" 9 | //! ``` 10 | //! 11 | //! You can pass some options: 12 | //! 13 | //! ``` 14 | //! let password = Generator::new() 15 | //! .use_spaces(false) 16 | //! .word_count(3) 17 | //! .generate(); 18 | //! println!("{}", password) 19 | //! // => "Correct-horse-staple-$20" 20 | //! ``` 21 | 22 | extern crate clap; 23 | 24 | mod clipboard; 25 | mod generator; 26 | mod symbols; 27 | mod words; 28 | 29 | use crate::clipboard::copy_to_clipboard; 30 | use clap::{App, Arg}; 31 | pub use generator::Generator; 32 | 33 | /// The CLI runner 34 | fn main() { 35 | let app = App::new("Passgen") 36 | .about("Generates passwords") 37 | .version("0.0.1") 38 | .arg( 39 | Arg::with_name("no-spaces") 40 | .short("s") 41 | .long("no-spaces") 42 | .help("Remove spaces"), 43 | ) 44 | .arg( 45 | Arg::with_name("newline") 46 | .short("n") 47 | .long("newline") 48 | .help("Print ending newline"), 49 | ) 50 | .arg( 51 | Arg::with_name("clipboard") 52 | .short("c") 53 | .long("clipboard") 54 | .help("Copy to clipboard"), 55 | // ) 56 | // .arg( 57 | // Arg::with_name("no-symbols") 58 | // .short("y") 59 | // .long("no-symbols") 60 | // .help("Remove symbols"), 61 | // ) 62 | // .arg( 63 | // Arg::with_name("words") 64 | // .short("w") 65 | // .long("words") 66 | // .help("Number of words") 67 | // .value_name("N") 68 | // .takes_value(true), 69 | // ) 70 | ); 71 | 72 | let matches = app.get_matches(); 73 | // println!("{:?}", matches); 74 | 75 | let gen = Generator::new().word_count(4); 76 | 77 | let gen = gen.use_spaces(!matches.is_present("no-spaces")); 78 | let passwd = gen.generate(); 79 | 80 | if matches.is_present("newline") { 81 | println!("{}", passwd) 82 | } else if matches.is_present("clipboard") { 83 | copy_to_clipboard(&passwd); 84 | eprintln!("Copied to clipboard."); 85 | } else { 86 | print!("{}", passwd) 87 | }; 88 | } 89 | -------------------------------------------------------------------------------- /src/generator.rs: -------------------------------------------------------------------------------- 1 | extern crate rand; 2 | use crate::symbols::{SYMBOLS, SYMBOLS_SIZE}; 3 | use crate::words::{WORDS, WORDS_SIZE}; 4 | use rand::prelude::ThreadRng; 5 | use rand::Rng; 6 | #[cfg(test)] 7 | mod tests; 8 | 9 | pub struct Generator { 10 | /// Random number generator 11 | rng: ThreadRng, 12 | 13 | /// Number of words to generate 14 | word_count: u64, 15 | 16 | /// If spaces are to be used 17 | use_spaces: bool, 18 | } 19 | 20 | /// Methods used for public consumption. 21 | impl Generator { 22 | /// Create a new password generator 23 | /// 24 | /// ``` 25 | /// let gen = Generator::new(); 26 | /// gen.generate() 27 | /// // => "correct horse battery staple" 28 | /// ``` 29 | pub fn new() -> Self { 30 | Self { 31 | rng: rand::thread_rng(), 32 | word_count: 4, 33 | use_spaces: true, 34 | } 35 | } 36 | 37 | pub fn word_count(self, value: u64) -> Self { 38 | Self { 39 | word_count: value, 40 | ..self 41 | } 42 | } 43 | 44 | pub fn use_spaces(self, value: bool) -> Self { 45 | Self { 46 | use_spaces: value, 47 | ..self 48 | } 49 | } 50 | 51 | /// Generate a password 52 | pub fn generate(&self) -> String { 53 | let count = self.word_count; 54 | let parts = self.gen_words(count); 55 | let parts = self.capitalize_one_word(&parts); 56 | let parts = self.add_junk(&parts); 57 | let use_spaces = self.use_spaces; 58 | 59 | if use_spaces { 60 | parts.join(" ") 61 | } else { 62 | parts.join("-") 63 | } 64 | } 65 | } 66 | 67 | /// These are internal delegate methods. 68 | impl Generator { 69 | /// Returns `count` random words 70 | /// 71 | /// ``` 72 | /// gen_words() 73 | /// // => ["hey", "yeah", "oh", "what"] 74 | /// ``` 75 | pub fn gen_words(&self, count: u64) -> Vec { 76 | let mut words: Vec = vec![]; 77 | let mut index = 0; 78 | 79 | while index < count { 80 | words.push(self.gen_random_word()); 81 | index += 1; 82 | } 83 | 84 | words 85 | } 86 | 87 | /// Capitalizes one word in a list of words 88 | /// ``` 89 | /// let source = vec!["hello", "world"] 90 | /// let result = capitalize_one_word(&source) 91 | /// // => ["hello", "World"] 92 | /// ``` 93 | pub fn capitalize_one_word(&self, source: &[String]) -> Vec { 94 | let mut rng = self.rng; 95 | 96 | // Find the spot to place the junk in 97 | let len = source.len(); 98 | let n = rng.gen_range(0, len); 99 | 100 | let mut result: Vec = vec![]; 101 | 102 | // Reconstruct result 103 | result.extend_from_slice(&source[0..n]); 104 | result.push(capitalize_word(&source[n])); 105 | result.extend_from_slice(&source[(n + 1)..]); 106 | result 107 | } 108 | 109 | /// Adds "junk" into a vector of strings. 110 | /// ``` 111 | /// self.add_junk(["hello", "world"]) 112 | /// // => ["hello", "world", "20$"] 113 | /// ``` 114 | pub fn add_junk(&self, source: &[String]) -> Vec { 115 | let mut result: Vec = vec![]; 116 | let mut rng = self.rng; 117 | let junk = self.gen_junk(); 118 | 119 | // Find the spot to place the junk in 120 | let len = source.len(); 121 | let n = rng.gen_range(1, len + 1); 122 | 123 | // Reconstruct result 124 | result.extend_from_slice(&source[0..n]); 125 | result.push(junk); 126 | result.extend_from_slice(&source[n..]); 127 | result 128 | } 129 | 130 | /// Gets "junk", or a string of random numbers and symbols 131 | /// ``` 132 | /// self.gen_junk() 133 | /// // => "20.1$" 134 | /// ``` 135 | fn gen_junk(&self) -> String { 136 | let mut rng = self.rng; 137 | 138 | let parts = match rng.gen_range(0, 3) { 139 | 0 => vec![self.gen_digits(), self.gen_symbols()], 140 | 1 => vec![self.gen_digits(), self.gen_symbols(), self.gen_digits()], 141 | _ => vec![self.gen_symbols(), self.gen_digits()], 142 | }; 143 | 144 | parts.join("") 145 | } 146 | 147 | /// Returns some symbols 148 | /// ``` 149 | /// self.gen_symbols() 150 | /// // => "!$" 151 | /// ``` 152 | pub fn gen_symbols(&self) -> String { 153 | let mut rng = self.rng; 154 | 155 | match rng.gen_range(0, 2) { 156 | 0 => format!("{}{}", self.gen_random_symbol(), self.gen_random_symbol()), 157 | _ => self.gen_random_symbol(), 158 | } 159 | } 160 | 161 | /// Returns one random number as a string. 162 | /// 163 | /// ``` 164 | /// self.gen_digits() 165 | /// // => "832" 166 | /// ``` 167 | pub fn gen_digits(&self) -> String { 168 | let mut rng = self.rng; 169 | rng.gen_range(1, 99).to_string() 170 | } 171 | 172 | /// Returns one random word. 173 | /// 174 | /// ``` 175 | /// self.gen_random_word() 176 | /// // => "potato" 177 | /// ``` 178 | pub fn gen_random_word(&self) -> String { 179 | let mut rng = self.rng; 180 | let n: usize = rng.gen_range(0, WORDS_SIZE); 181 | String::from(WORDS[n]) 182 | } 183 | 184 | /// Returns one random symbol. 185 | /// 186 | /// ``` 187 | /// self.gen_random_symbol() 188 | /// // => "$" 189 | /// ``` 190 | pub fn gen_random_symbol(&self) -> String { 191 | let mut rng = self.rng; 192 | let n: usize = rng.gen_range(0, SYMBOLS_SIZE); 193 | String::from(SYMBOLS[n]) 194 | } 195 | } 196 | 197 | pub fn capitalize_word(source: &str) -> String { 198 | let first = &source[0..1]; 199 | let letter = first.to_ascii_uppercase(); 200 | let rest = &source[1..]; 201 | format!("{}{}", letter, rest) 202 | } 203 | -------------------------------------------------------------------------------- /Cargo.lock: -------------------------------------------------------------------------------- 1 | # This file is automatically @generated by Cargo. 2 | # It is not intended for manual editing. 3 | [[package]] 4 | name = "aho-corasick" 5 | version = "0.7.6" 6 | source = "registry+https://github.com/rust-lang/crates.io-index" 7 | dependencies = [ 8 | "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 9 | ] 10 | 11 | [[package]] 12 | name = "ansi_term" 13 | version = "0.11.0" 14 | source = "registry+https://github.com/rust-lang/crates.io-index" 15 | dependencies = [ 16 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 17 | ] 18 | 19 | [[package]] 20 | name = "atty" 21 | version = "0.2.13" 22 | source = "registry+https://github.com/rust-lang/crates.io-index" 23 | dependencies = [ 24 | "libc 0.2.60 (registry+https://github.com/rust-lang/crates.io-index)", 25 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 26 | ] 27 | 28 | [[package]] 29 | name = "bitflags" 30 | version = "1.1.0" 31 | source = "registry+https://github.com/rust-lang/crates.io-index" 32 | 33 | [[package]] 34 | name = "block" 35 | version = "0.1.6" 36 | source = "registry+https://github.com/rust-lang/crates.io-index" 37 | 38 | [[package]] 39 | name = "c2-chacha" 40 | version = "0.2.2" 41 | source = "registry+https://github.com/rust-lang/crates.io-index" 42 | dependencies = [ 43 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 44 | "ppv-lite86 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)", 45 | ] 46 | 47 | [[package]] 48 | name = "cfg-if" 49 | version = "0.1.9" 50 | source = "registry+https://github.com/rust-lang/crates.io-index" 51 | 52 | [[package]] 53 | name = "clap" 54 | version = "2.33.0" 55 | source = "registry+https://github.com/rust-lang/crates.io-index" 56 | dependencies = [ 57 | "ansi_term 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)", 58 | "atty 0.2.13 (registry+https://github.com/rust-lang/crates.io-index)", 59 | "bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)", 60 | "strsim 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)", 61 | "textwrap 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)", 62 | "unicode-width 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 63 | "vec_map 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)", 64 | ] 65 | 66 | [[package]] 67 | name = "clipboard" 68 | version = "0.5.0" 69 | source = "registry+https://github.com/rust-lang/crates.io-index" 70 | dependencies = [ 71 | "clipboard-win 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 72 | "objc 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)", 73 | "objc-foundation 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 74 | "objc_id 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 75 | "x11-clipboard 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)", 76 | ] 77 | 78 | [[package]] 79 | name = "clipboard-win" 80 | version = "2.2.0" 81 | source = "registry+https://github.com/rust-lang/crates.io-index" 82 | dependencies = [ 83 | "winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)", 84 | ] 85 | 86 | [[package]] 87 | name = "getrandom" 88 | version = "0.1.8" 89 | source = "registry+https://github.com/rust-lang/crates.io-index" 90 | dependencies = [ 91 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 92 | "libc 0.2.60 (registry+https://github.com/rust-lang/crates.io-index)", 93 | ] 94 | 95 | [[package]] 96 | name = "lazy_static" 97 | version = "1.3.0" 98 | source = "registry+https://github.com/rust-lang/crates.io-index" 99 | 100 | [[package]] 101 | name = "libc" 102 | version = "0.2.60" 103 | source = "registry+https://github.com/rust-lang/crates.io-index" 104 | 105 | [[package]] 106 | name = "log" 107 | version = "0.4.8" 108 | source = "registry+https://github.com/rust-lang/crates.io-index" 109 | dependencies = [ 110 | "cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)", 111 | ] 112 | 113 | [[package]] 114 | name = "malloc_buf" 115 | version = "0.0.6" 116 | source = "registry+https://github.com/rust-lang/crates.io-index" 117 | dependencies = [ 118 | "libc 0.2.60 (registry+https://github.com/rust-lang/crates.io-index)", 119 | ] 120 | 121 | [[package]] 122 | name = "memchr" 123 | version = "2.2.1" 124 | source = "registry+https://github.com/rust-lang/crates.io-index" 125 | 126 | [[package]] 127 | name = "objc" 128 | version = "0.2.6" 129 | source = "registry+https://github.com/rust-lang/crates.io-index" 130 | dependencies = [ 131 | "malloc_buf 0.0.6 (registry+https://github.com/rust-lang/crates.io-index)", 132 | ] 133 | 134 | [[package]] 135 | name = "objc-foundation" 136 | version = "0.1.1" 137 | source = "registry+https://github.com/rust-lang/crates.io-index" 138 | dependencies = [ 139 | "block 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)", 140 | "objc 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)", 141 | "objc_id 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)", 142 | ] 143 | 144 | [[package]] 145 | name = "objc_id" 146 | version = "0.1.1" 147 | source = "registry+https://github.com/rust-lang/crates.io-index" 148 | dependencies = [ 149 | "objc 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)", 150 | ] 151 | 152 | [[package]] 153 | name = "passgen" 154 | version = "0.1.0" 155 | dependencies = [ 156 | "clap 2.33.0 (registry+https://github.com/rust-lang/crates.io-index)", 157 | "clipboard 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 158 | "rand 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)", 159 | "regex 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 160 | ] 161 | 162 | [[package]] 163 | name = "ppv-lite86" 164 | version = "0.2.5" 165 | source = "registry+https://github.com/rust-lang/crates.io-index" 166 | 167 | [[package]] 168 | name = "rand" 169 | version = "0.7.0" 170 | source = "registry+https://github.com/rust-lang/crates.io-index" 171 | dependencies = [ 172 | "getrandom 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 173 | "libc 0.2.60 (registry+https://github.com/rust-lang/crates.io-index)", 174 | "rand_chacha 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 175 | "rand_core 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 176 | "rand_hc 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)", 177 | ] 178 | 179 | [[package]] 180 | name = "rand_chacha" 181 | version = "0.2.1" 182 | source = "registry+https://github.com/rust-lang/crates.io-index" 183 | dependencies = [ 184 | "c2-chacha 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", 185 | "rand_core 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 186 | ] 187 | 188 | [[package]] 189 | name = "rand_core" 190 | version = "0.5.0" 191 | source = "registry+https://github.com/rust-lang/crates.io-index" 192 | dependencies = [ 193 | "getrandom 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)", 194 | ] 195 | 196 | [[package]] 197 | name = "rand_hc" 198 | version = "0.2.0" 199 | source = "registry+https://github.com/rust-lang/crates.io-index" 200 | dependencies = [ 201 | "rand_core 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)", 202 | ] 203 | 204 | [[package]] 205 | name = "regex" 206 | version = "1.2.1" 207 | source = "registry+https://github.com/rust-lang/crates.io-index" 208 | dependencies = [ 209 | "aho-corasick 0.7.6 (registry+https://github.com/rust-lang/crates.io-index)", 210 | "memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)", 211 | "regex-syntax 0.6.11 (registry+https://github.com/rust-lang/crates.io-index)", 212 | "thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)", 213 | ] 214 | 215 | [[package]] 216 | name = "regex-syntax" 217 | version = "0.6.11" 218 | source = "registry+https://github.com/rust-lang/crates.io-index" 219 | 220 | [[package]] 221 | name = "strsim" 222 | version = "0.8.0" 223 | source = "registry+https://github.com/rust-lang/crates.io-index" 224 | 225 | [[package]] 226 | name = "textwrap" 227 | version = "0.11.0" 228 | source = "registry+https://github.com/rust-lang/crates.io-index" 229 | dependencies = [ 230 | "unicode-width 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", 231 | ] 232 | 233 | [[package]] 234 | name = "thread_local" 235 | version = "0.3.6" 236 | source = "registry+https://github.com/rust-lang/crates.io-index" 237 | dependencies = [ 238 | "lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)", 239 | ] 240 | 241 | [[package]] 242 | name = "unicode-width" 243 | version = "0.1.5" 244 | source = "registry+https://github.com/rust-lang/crates.io-index" 245 | 246 | [[package]] 247 | name = "vec_map" 248 | version = "0.8.1" 249 | source = "registry+https://github.com/rust-lang/crates.io-index" 250 | 251 | [[package]] 252 | name = "winapi" 253 | version = "0.3.7" 254 | source = "registry+https://github.com/rust-lang/crates.io-index" 255 | dependencies = [ 256 | "winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 257 | "winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)", 258 | ] 259 | 260 | [[package]] 261 | name = "winapi-i686-pc-windows-gnu" 262 | version = "0.4.0" 263 | source = "registry+https://github.com/rust-lang/crates.io-index" 264 | 265 | [[package]] 266 | name = "winapi-x86_64-pc-windows-gnu" 267 | version = "0.4.0" 268 | source = "registry+https://github.com/rust-lang/crates.io-index" 269 | 270 | [[package]] 271 | name = "x11-clipboard" 272 | version = "0.3.3" 273 | source = "registry+https://github.com/rust-lang/crates.io-index" 274 | dependencies = [ 275 | "xcb 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)", 276 | ] 277 | 278 | [[package]] 279 | name = "xcb" 280 | version = "0.8.2" 281 | source = "registry+https://github.com/rust-lang/crates.io-index" 282 | dependencies = [ 283 | "libc 0.2.60 (registry+https://github.com/rust-lang/crates.io-index)", 284 | "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", 285 | ] 286 | 287 | [metadata] 288 | "checksum aho-corasick 0.7.6 (registry+https://github.com/rust-lang/crates.io-index)" = "58fb5e95d83b38284460a5fda7d6470aa0b8844d283a0b614b8535e880800d2d" 289 | "checksum ansi_term 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ee49baf6cb617b853aa8d93bf420db2383fab46d314482ca2803b40d5fde979b" 290 | "checksum atty 0.2.13 (registry+https://github.com/rust-lang/crates.io-index)" = "1803c647a3ec87095e7ae7acfca019e98de5ec9a7d01343f611cf3152ed71a90" 291 | "checksum bitflags 1.1.0 (registry+https://github.com/rust-lang/crates.io-index)" = "3d155346769a6855b86399e9bc3814ab343cd3d62c7e985113d46a0ec3c281fd" 292 | "checksum block 0.1.6 (registry+https://github.com/rust-lang/crates.io-index)" = "0d8c1fef690941d3e7788d328517591fecc684c084084702d6ff1641e993699a" 293 | "checksum c2-chacha 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "7d64d04786e0f528460fc884753cf8dddcc466be308f6026f8e355c41a0e4101" 294 | "checksum cfg-if 0.1.9 (registry+https://github.com/rust-lang/crates.io-index)" = "b486ce3ccf7ffd79fdeb678eac06a9e6c09fc88d33836340becb8fffe87c5e33" 295 | "checksum clap 2.33.0 (registry+https://github.com/rust-lang/crates.io-index)" = "5067f5bb2d80ef5d68b4c87db81601f0b75bca627bc2ef76b141d7b846a3c6d9" 296 | "checksum clipboard 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "25a904646c0340239dcf7c51677b33928bf24fdf424b79a57909c0109075b2e7" 297 | "checksum clipboard-win 2.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "e3a093d6fed558e5fe24c3dfc85a68bb68f1c824f440d3ba5aca189e2998786b" 298 | "checksum getrandom 0.1.8 (registry+https://github.com/rust-lang/crates.io-index)" = "34f33de6f0ae7c9cb5e574502a562e2b512799e32abb801cd1e79ad952b62b49" 299 | "checksum lazy_static 1.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "bc5729f27f159ddd61f4df6228e827e86643d4d3e7c32183cb30a1c08f604a14" 300 | "checksum libc 0.2.60 (registry+https://github.com/rust-lang/crates.io-index)" = "d44e80633f007889c7eff624b709ab43c92d708caad982295768a7b13ca3b5eb" 301 | "checksum log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)" = "14b6052be84e6b71ab17edffc2eeabf5c2c3ae1fdb464aae35ac50c67a44e1f7" 302 | "checksum malloc_buf 0.0.6 (registry+https://github.com/rust-lang/crates.io-index)" = "62bb907fe88d54d8d9ce32a3cceab4218ed2f6b7d35617cafe9adf84e43919cb" 303 | "checksum memchr 2.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "88579771288728879b57485cc7d6b07d648c9f0141eb955f8ab7f9d45394468e" 304 | "checksum objc 0.2.6 (registry+https://github.com/rust-lang/crates.io-index)" = "31d20fd2b37e07cf5125be68357b588672e8cefe9a96f8c17a9d46053b3e590d" 305 | "checksum objc-foundation 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "1add1b659e36c9607c7aab864a76c7a4c2760cd0cd2e120f3fb8b952c7e22bf9" 306 | "checksum objc_id 0.1.1 (registry+https://github.com/rust-lang/crates.io-index)" = "c92d4ddb4bd7b50d730c215ff871754d0da6b2178849f8a2a2ab69712d0c073b" 307 | "checksum ppv-lite86 0.2.5 (registry+https://github.com/rust-lang/crates.io-index)" = "e3cbf9f658cdb5000fcf6f362b8ea2ba154b9f146a61c7a20d647034c6b6561b" 308 | "checksum rand 0.7.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d47eab0e83d9693d40f825f86948aa16eff6750ead4bdffc4ab95b8b3a7f052c" 309 | "checksum rand_chacha 0.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "03a2a90da8c7523f554344f921aa97283eadf6ac484a6d2a7d0212fa7f8d6853" 310 | "checksum rand_core 0.5.0 (registry+https://github.com/rust-lang/crates.io-index)" = "615e683324e75af5d43d8f7a39ffe3ee4a9dc42c5c701167a71dc59c3a493aca" 311 | "checksum rand_hc 0.2.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ca3129af7b92a17112d59ad498c6f81eaf463253766b90396d39ea7a39d6613c" 312 | "checksum regex 1.2.1 (registry+https://github.com/rust-lang/crates.io-index)" = "88c3d9193984285d544df4a30c23a4e62ead42edf70a4452ceb76dac1ce05c26" 313 | "checksum regex-syntax 0.6.11 (registry+https://github.com/rust-lang/crates.io-index)" = "b143cceb2ca5e56d5671988ef8b15615733e7ee16cd348e064333b251b89343f" 314 | "checksum strsim 0.8.0 (registry+https://github.com/rust-lang/crates.io-index)" = "8ea5119cdb4c55b55d432abb513a0429384878c15dde60cc77b1c99de1a95a6a" 315 | "checksum textwrap 0.11.0 (registry+https://github.com/rust-lang/crates.io-index)" = "d326610f408c7a4eb6f51c37c330e496b08506c9457c9d34287ecc38809fb060" 316 | "checksum thread_local 0.3.6 (registry+https://github.com/rust-lang/crates.io-index)" = "c6b53e329000edc2b34dbe8545fd20e55a333362d0a321909685a19bd28c3f1b" 317 | "checksum unicode-width 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "882386231c45df4700b275c7ff55b6f3698780a650026380e72dabe76fa46526" 318 | "checksum vec_map 0.8.1 (registry+https://github.com/rust-lang/crates.io-index)" = "05c78687fb1a80548ae3250346c3db86a80a7cdd77bda190189f2d0a0987c81a" 319 | "checksum winapi 0.3.7 (registry+https://github.com/rust-lang/crates.io-index)" = "f10e386af2b13e47c89e7236a7a14a086791a2b88ebad6df9bf42040195cf770" 320 | "checksum winapi-i686-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ac3b87c63620426dd9b991e5ce0329eff545bccbbb34f3be09ff6fb6ab51b7b6" 321 | "checksum winapi-x86_64-pc-windows-gnu 0.4.0 (registry+https://github.com/rust-lang/crates.io-index)" = "712e227841d057c1ee1cd2fb22fa7e5a5461ae8e48fa2ca79ec42cfc1931183f" 322 | "checksum x11-clipboard 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "89bd49c06c9eb5d98e6ba6536cf64ac9f7ee3a009b2f53996d405b3944f6bcea" 323 | "checksum xcb 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)" = "5e917a3f24142e9ff8be2414e36c649d47d6cc2ba81f16201cdef96e533e02de" 324 | --------------------------------------------------------------------------------