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
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
//! # zlob
//!
//! High-performance glob pattern matching with SIMD optimizations.
//!
//! zlob is a Rust binding to the zlob library, which provides:
//! - POSIX-compatible glob pattern matching
//! - SIMD-optimized pattern matching for high performance
//! - Support for brace expansion (`{a,b,c}`)
//! - Tilde expansion (`~`, `~user`)
//! - `.gitignore` filtering
//! - Zero-copy path matching API
//!
//! For most use cases, use [`ZlobFlags::RECOMMENDED`]:
//!
//! ```no_run
//! use zlob::{zlob, ZlobFlags};
//!
//! // RECOMMENDED enables: brace expansion, recursive **, tilde expansion, no sorting
//! if let Some(result) = zlob("**/*.rs", ZlobFlags::RECOMMENDED)? {
//! for path in &result {
//! println!("{}", path);
//! }
//! }
//! # Ok::<(), zlob::ZlobError>(())
//! ```
//!
//! ## Basic Usage
//!
//! ```no_run
//! use zlob::{zlob, ZlobFlags};
//!
//! if let Some(result) = zlob("**/*.rs", ZlobFlags::RECOMMENDED)? {
//! for path in &result {
//! println!("{}", path);
//! }
//! }
//!
//! // Use brace expansion
//! if let Some(result) = zlob("src/{lib,main}.rs", ZlobFlags::BRACE)? {
//! // Index access
//! if !result.is_empty() {
//! println!("First match: {}", &result[0]);
//! }
//!
//! // Convert to Vec<String>
//! let paths: Vec<String> = result.to_strings();
//! }
//! # Ok::<(), zlob::ZlobError>(())
//! ```
//!
//! ## Path Matching (No Filesystem Access)
//!
//! For filtering a list of paths without filesystem access, use `zlob_match_paths`:
//!
//! ```
//! use zlob::{zlob_match_paths, ZlobFlags};
//!
//! let paths = ["src/lib.rs", "src/main.rs", "README.md"];
//! if let Some(matches) = zlob_match_paths("*.rs", &paths, ZlobFlags::empty())? {
//! assert_eq!(matches.len(), 2);
//! for path in &matches {
//! println!("{}", path);
//! }
//! }
//! # Ok::<(), zlob::ZlobError>(())
//! ```
//!
//! This is a zero-copy operation - the results reference the original input strings.
//!
//! ## Flags
//!
//! For most use cases, use [`ZlobFlags::RECOMMENDED`]:
//!
//! ```no_run
//! use zlob::{zlob, ZlobFlags};
//!
//! let result = zlob("**/*.rs", ZlobFlags::RECOMMENDED)?;
//!
//! // Add more flags as needed
//! let result = zlob("**/*.rs", ZlobFlags::RECOMMENDED | ZlobFlags::GITIGNORE)?;
//! # Ok::<(), zlob::ZlobError>(())
//! ```
//!
//! Control matching behavior with individual `ZlobFlags`:
//!
//! ```
//! use zlob::ZlobFlags;
//!
//! // Combine flags with bitwise OR
//! let flags = ZlobFlags::BRACE | ZlobFlags::DOUBLESTAR_RECURSIVE | ZlobFlags::PERIOD;
//!
//! // Common flags:
//! // - RECOMMENDED: Best defaults for typical usage (see above)
//! // - BRACE: Enable {a,b,c} expansion
//! // - DOUBLESTAR_RECURSIVE: Enable ** recursive directory matching
//! // - TILDE: Enable ~ home directory expansion
//! // - NOSORT: Don't sort results (faster)
//! // - PERIOD: Allow wildcards to match leading dots
//! // - GITIGNORE: Filter results with .gitignore rules
//! // - ONLYDIR: Match only directories
//! ```
//!
//! ## Supported Patterns
//!
//! We support all the varieties of glob pattern supported by rust's `glob` crate, posix `glob(3)`,
//! glibc `glob()` implementation and many more.
//!
//! Here are some of the most common patterns:
//!
//! | Pattern | Description |
//! |---------|-------------|
//! | `*` | Matches any string (including empty) |
//! | `?` | Matches any single character |
//! | `[abc]` | Matches one character from the set |
//! | `[!abc]` | Matches one character NOT in the set |
//! | `[a-z]` | Matches one character in the range |
//! | `**` | Matches zero or more path components (requires `DOUBLESTAR_RECURSIVE` or `RECOMMENDED`) |
//! | `{a,b}` | Matches alternatives (requires `BRACE` or `RECOMMENDED`) |
//! | `~` | Home directory (requires `TILDE` or `RECOMMENDED`) |
//! | `~user` | User's home directory (requires `TILDE` or `RECOMMENDED`) |
//!
//! **Note:** By default (for glibc compatibility), `**` is treated as `*`, and braces are not
//! supported
//! Use `ZlobFlags::DOUBLESTAR_RECURSIVE` or `ZlobFlags::RECOMMENDED` for recursive matching.
//!
//! ## Error Handling
//!
//! Operations return `Result<Option<_>, ZlobError>`:
//! - `Ok(Some(result))` - matches found
//! - `Ok(None)` - no matches (not an error)
//! - `Err(ZlobError)` - actual error (out of memory, aborted, etc.)
//!
//! ```no_run
//! use zlob::{zlob, ZlobFlags, ZlobError};
//!
//! match zlob("**/*.rs", ZlobFlags::RECOMMENDED) {
//! Ok(Some(result)) => println!("Found {} files", result.len()),
//! Ok(None) => println!("No files matched"),
//! Err(ZlobError::Aborted) => println!("Operation aborted"),
//! Err(ZlobError::NoSpace) => println!("Out of memory"),
//! }
//! ```
// Raw FFI bindings - use stub for docs.rs, generated bindings otherwise
// Safety: zlob_t is safe to send across threads
unsafe
pub use *;
pub use *;
pub use *;
pub use *;
/// Check if a pattern string contains any glob special characters.
///
/// Detects glob syntax using SIMD-accelerated scanning:
/// - Basic wildcards: `*`, `?`, `[`
/// - Brace expansion: `{` (only if `BRACE` flag is set)
/// - Extended glob patterns: `?(`, `*(`, `+(`, `@(`, `!(` (only if `EXTGLOB` flag is set)
///
/// This is useful for determining whether a string should be treated as a glob
/// pattern or as a literal file path.
///
/// # Example
///
/// ```
/// use zlob::{has_wildcards, ZlobFlags};
///
/// // Basic wildcards are always detected
/// assert!(has_wildcards("*.txt", ZlobFlags::empty()));
/// assert!(has_wildcards("file?.rs", ZlobFlags::empty()));
///
/// // Brace patterns only detected with BRACE flag
/// assert!(!has_wildcards("{a,b}.rs", ZlobFlags::empty()));
/// assert!(has_wildcards("{a,b}.rs", ZlobFlags::BRACE));
///
/// // Extglob patterns only detected with EXTGLOB flag
/// assert!(!has_wildcards("@(foo|bar)", ZlobFlags::empty()));
/// assert!(has_wildcards("@(foo|bar)", ZlobFlags::EXTGLOB));
///
/// // Literal paths
/// assert!(!has_wildcards("literal_path.txt", ZlobFlags::empty()));
/// ```