pub struct Compiler<'a> { /* private fields */ }Expand description
Compiles YARA source code producing a set of compiled Rules.
The two most important methods in this type are Compiler::add_source
and Compiler::build. The former tells the compiler which YARA source
code must be compiled, and can be called multiple times with different
set of rules. The latter consumes the compiler and produces a set of
compiled Rules.
§Example
let mut compiler = yara_x::Compiler::new();
compiler
.add_source(r#"
rule always_true {
condition: true
}"#)?
.add_source(r#"
rule always_false {
condition: false
}"#)?;
let rules = compiler.build();
Implementations§
Source§impl<'a> Compiler<'a>
impl<'a> Compiler<'a>
Sourcepub fn add_include_dir<P: AsRef<Path>>(&mut self, dir: P) -> &mut Self
pub fn add_include_dir<P: AsRef<Path>>(&mut self, dir: P) -> &mut Self
Adds a directory to the list of directories where the compiler should look for included files.
When an include statement is found, the compiler looks for the included
file in the directories added with this function, in the order they were
added.
If this function is not called, the compiler will only look for included files in the current directory.
Use Compiler::enable_includes for controlling whether include statements are allowed or not.
§Example
let mut compiler = Compiler::new();
compiler.add_include_dir("/path/to/rules")
.add_include_dir("/another/path");Sourcepub fn add_source<'src, S>(&mut self, src: S) -> Result<&mut Self, CompileError>where
S: Into<SourceCode<'src>>,
pub fn add_source<'src, S>(&mut self, src: S) -> Result<&mut Self, CompileError>where
S: Into<SourceCode<'src>>,
Adds some YARA source code to be compiled.
The src parameter accepts any type that implements Into<SourceCode>,
such as &str, &[u8], or an instance of SourceCode itself. The source
code may include one or more YARA rules.
You can call this function multiple times to add different sets of rules.
If the provided source code contains syntax or semantic errors that prevent
compilation, the function returns the first encountered error. All errors
found during compilation are also recorded and can be retrieved using
Compiler::errors.
Even if previous calls to this function resulted in compilation errors, you may continue adding additional rules. Only successfully compiled rules will be included in the final rule set.
Sourcepub fn define_global<T: TryInto<Variable>>(
&mut self,
ident: &str,
value: T,
) -> Result<&mut Self, VariableError>
pub fn define_global<T: TryInto<Variable>>( &mut self, ident: &str, value: T, ) -> Result<&mut Self, VariableError>
Defines a global variable and sets its initial value.
Global variables must be defined before adding any YARA source code
that references them via Compiler::add_source. Once defined, the
variable’s initial value is preserved in the compiled Rules and
will be used unless overridden.
When scanning, each scanner instance can modify the initial value of
the variable using crate::Scanner::set_global.
T can be any type that implements TryInto<Variable>, including:
i64, i32, i16, i8, u32, u16, u8, f64, f32, bool,
&str, String and serde_json::Value.
When using a serde_json::Value there are certain limitations: keys
in maps must be valid YARA identifiers (the first character must be _
or a letter, the remaining ones must be _, a letter or a digit),
because these maps are translated into YARA structures. Also, all items
in an array must have the same type.
assert!(Compiler::new()
.define_global("some_int", 1)?
.add_source("rule some_int_not_zero {condition: some_int != 0}")
.is_ok());
Sourcepub fn new_namespace(&mut self, namespace: &str) -> &mut Self
pub fn new_namespace(&mut self, namespace: &str) -> &mut Self
Creates a new namespace.
Further calls to Compiler::add_source will put the rules under the
newly created namespace. If the new namespace is named as the current
one, no new namespace is created.
In the example below both rules foo and bar are put into the same
namespace (the default namespace), therefore bar can use foo as
part of its condition, and everything is ok.
assert!(Compiler::new()
.add_source("rule foo {condition: true}")?
.add_source("rule bar {condition: foo}")
.is_ok());
In this other example the rule foo is put in the default namespace,
but the rule bar is put under the bar namespace. This implies that
foo is not visible to bar, and the second call to add_source
fails.
assert!(Compiler::new()
.add_source("rule foo {condition: true}")?
.new_namespace("bar")
.add_source("rule bar {condition: foo}")
.is_err());
Sourcepub fn build(self) -> Rules
pub fn build(self) -> Rules
Builds the source code previously added to the compiler.
This function consumes the compiler and returns an instance of
Rules.
Sourcepub fn add_linter<L: Linter + 'a>(&mut self, linter: L) -> &mut Self
pub fn add_linter<L: Linter + 'a>(&mut self, linter: L) -> &mut Self
Adds a linter to the compiler.
Linters perform additional checks to each YARA rule, generating
warnings when a rule does not meet the linter’s requirements. See
crate::linters for a list of available linters.
Sourcepub fn ignore_module<M: Into<String>>(&mut self, module: M) -> &mut Self
pub fn ignore_module<M: Into<String>>(&mut self, module: M) -> &mut Self
Tell the compiler that a YARA module is not supported.
Import statements for ignored modules will be ignored without errors, but a warning will be issued. Any rule that makes use of an ignored module will be also ignored, while the rest of the rules that don’t rely on that module will be correctly compiled.
Sourcepub fn ban_module<M: Into<String>, T: Into<String>, E: Into<String>>(
&mut self,
module: M,
error_title: T,
error_message: E,
) -> &mut Self
pub fn ban_module<M: Into<String>, T: Into<String>, E: Into<String>>( &mut self, module: M, error_title: T, error_message: E, ) -> &mut Self
Tell the compiler that a YARA module can’t be used.
Import statements for the banned module will cause an error. The error message can be customized by using the given error title and message.
If this function is called multiple times with the same module name, the error title and message will be updated.
Sourcepub fn colorize_errors(&mut self, yes: bool) -> &mut Self
pub fn colorize_errors(&mut self, yes: bool) -> &mut Self
Specifies whether the compiler should produce colorful error messages.
Colorized error messages contain ANSI escape sequences that make them look nicer on compatible consoles.
The default setting is false.
Sourcepub fn errors_max_width(&mut self, width: usize) -> &mut Self
pub fn errors_max_width(&mut self, width: usize) -> &mut Self
Sets the maximum number of columns in error messages.
The default value is 140.
Sourcepub fn switch_warning(
&mut self,
code: &str,
enabled: bool,
) -> Result<&mut Self, InvalidWarningCode>
pub fn switch_warning( &mut self, code: &str, enabled: bool, ) -> Result<&mut Self, InvalidWarningCode>
Enables or disables a specific type of warning.
Each warning type has a description code (i.e: slow_pattern,
unsupported_module, etc.). This function allows to enable or disable
a specific type of warning identified by the given code.
Returns an error if the given warning code doesn’t exist.
Sourcepub fn switch_all_warnings(&mut self, enabled: bool) -> &mut Self
pub fn switch_all_warnings(&mut self, enabled: bool) -> &mut Self
Enables or disables all warnings.
Sourcepub fn relaxed_re_syntax(&mut self, yes: bool) -> &mut Self
pub fn relaxed_re_syntax(&mut self, yes: bool) -> &mut Self
Enables a more relaxed syntax check for regular expressions.
YARA-X enforces stricter regular expression syntax compared to YARA.
For instance, YARA accepts invalid escape sequences and treats them
as literal characters (e.g., \R is interpreted as a literal ‘R’). It
also allows some special characters to appear unescaped, inferring
their meaning from the context (e.g., { and } in /foo{}bar/ are
literal, but in /foo{0,1}bar/ they form the repetition operator
{0,1}).
This setting controls whether the compiler should mimic YARA’s behavior, allowing constructs that YARA-X doesn’t accept by default.
This should be called before any rule is added to the compiler.
§Panics
If called after adding rules to the compiler.
Sourcepub fn error_on_slow_pattern(&mut self, yes: bool) -> &mut Self
pub fn error_on_slow_pattern(&mut self, yes: bool) -> &mut Self
When enabled, slow patterns produce an error instead of a warning.
This is disabled by default.
Sourcepub fn error_on_slow_loop(&mut self, yes: bool) -> &mut Self
pub fn error_on_slow_loop(&mut self, yes: bool) -> &mut Self
When enabled, potentially slow loops produce an error instead of a warning.
This is disabled by default.
Sourcepub fn enable_includes(&mut self, yes: bool) -> &mut Self
pub fn enable_includes(&mut self, yes: bool) -> &mut Self
Controls whether include statements are allowed.
By default, the compiler allows the use of include statements, which
include the content of other files. When includes are disabled, any
attempt to use an include statement will result in a compile error.
let mut compiler = Compiler::new();
compiler.enable_includes(false); // Disable includesSourcepub fn errors(&self) -> &[CompileError]
pub fn errors(&self) -> &[CompileError]
Retrieves all errors generated by the compiler.
This method returns every error encountered during the compilation,
across all invocations of Compiler::add_source.
Sourcepub fn warnings(&self) -> &[Warning]
pub fn warnings(&self) -> &[Warning]
Returns the warnings emitted by the compiler.
This method returns every warning issued during the compilation,
across all invocations of Compiler::add_source.
Sourcepub fn emit_wasm_file<P>(self, path: P) -> Result<(), EmitWasmError>
pub fn emit_wasm_file<P>(self, path: P) -> Result<(), EmitWasmError>
Emits a .wasm file with the WASM module generated by the compiler.
This file can be inspected and converted to WASM text format by using third-party tooling. This is useful for debugging issues with incorrectly emitted WASM code.
Trait Implementations§
Auto Trait Implementations§
impl<'a> !Freeze for Compiler<'a>
impl<'a> !RefUnwindSafe for Compiler<'a>
impl<'a> !Send for Compiler<'a>
impl<'a> !Sync for Compiler<'a>
impl<'a> Unpin for Compiler<'a>
impl<'a> UnsafeUnpin for Compiler<'a>
impl<'a> !UnwindSafe for Compiler<'a>
Blanket Implementations§
Source§impl<'a, T, E> AsTaggedExplicit<'a, E> for Twhere
T: 'a,
impl<'a, T, E> AsTaggedExplicit<'a, E> for Twhere
T: 'a,
Source§impl<'a, T, E> AsTaggedImplicit<'a, E> for Twhere
T: 'a,
impl<'a, T, E> AsTaggedImplicit<'a, E> for Twhere
T: 'a,
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> FmtForward for T
impl<T> FmtForward for T
Source§fn fmt_binary(self) -> FmtBinary<Self>where
Self: Binary,
fn fmt_binary(self) -> FmtBinary<Self>where
Self: Binary,
self to use its Binary implementation when Debug-formatted.Source§fn fmt_display(self) -> FmtDisplay<Self>where
Self: Display,
fn fmt_display(self) -> FmtDisplay<Self>where
Self: Display,
self to use its Display implementation when
Debug-formatted.Source§fn fmt_lower_exp(self) -> FmtLowerExp<Self>where
Self: LowerExp,
fn fmt_lower_exp(self) -> FmtLowerExp<Self>where
Self: LowerExp,
self to use its LowerExp implementation when
Debug-formatted.Source§fn fmt_lower_hex(self) -> FmtLowerHex<Self>where
Self: LowerHex,
fn fmt_lower_hex(self) -> FmtLowerHex<Self>where
Self: LowerHex,
self to use its LowerHex implementation when
Debug-formatted.Source§fn fmt_octal(self) -> FmtOctal<Self>where
Self: Octal,
fn fmt_octal(self) -> FmtOctal<Self>where
Self: Octal,
self to use its Octal implementation when Debug-formatted.Source§fn fmt_pointer(self) -> FmtPointer<Self>where
Self: Pointer,
fn fmt_pointer(self) -> FmtPointer<Self>where
Self: Pointer,
self to use its Pointer implementation when
Debug-formatted.Source§fn fmt_upper_exp(self) -> FmtUpperExp<Self>where
Self: UpperExp,
fn fmt_upper_exp(self) -> FmtUpperExp<Self>where
Self: UpperExp,
self to use its UpperExp implementation when
Debug-formatted.Source§fn fmt_upper_hex(self) -> FmtUpperHex<Self>where
Self: UpperHex,
fn fmt_upper_hex(self) -> FmtUpperHex<Self>where
Self: UpperHex,
self to use its UpperHex implementation when
Debug-formatted.Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§impl<T> Pipe for Twhere
T: ?Sized,
impl<T> Pipe for Twhere
T: ?Sized,
Source§fn pipe<R>(self, func: impl FnOnce(Self) -> R) -> Rwhere
Self: Sized,
fn pipe<R>(self, func: impl FnOnce(Self) -> R) -> Rwhere
Self: Sized,
Source§fn pipe_ref<'a, R>(&'a self, func: impl FnOnce(&'a Self) -> R) -> Rwhere
R: 'a,
fn pipe_ref<'a, R>(&'a self, func: impl FnOnce(&'a Self) -> R) -> Rwhere
R: 'a,
self and passes that borrow into the pipe function. Read moreSource§fn pipe_ref_mut<'a, R>(&'a mut self, func: impl FnOnce(&'a mut Self) -> R) -> Rwhere
R: 'a,
fn pipe_ref_mut<'a, R>(&'a mut self, func: impl FnOnce(&'a mut Self) -> R) -> Rwhere
R: 'a,
self and passes that borrow into the pipe function. Read moreSource§fn pipe_borrow<'a, B, R>(&'a self, func: impl FnOnce(&'a B) -> R) -> R
fn pipe_borrow<'a, B, R>(&'a self, func: impl FnOnce(&'a B) -> R) -> R
Source§fn pipe_borrow_mut<'a, B, R>(
&'a mut self,
func: impl FnOnce(&'a mut B) -> R,
) -> R
fn pipe_borrow_mut<'a, B, R>( &'a mut self, func: impl FnOnce(&'a mut B) -> R, ) -> R
Source§fn pipe_as_ref<'a, U, R>(&'a self, func: impl FnOnce(&'a U) -> R) -> R
fn pipe_as_ref<'a, U, R>(&'a self, func: impl FnOnce(&'a U) -> R) -> R
self, then passes self.as_ref() into the pipe function.Source§fn pipe_as_mut<'a, U, R>(&'a mut self, func: impl FnOnce(&'a mut U) -> R) -> R
fn pipe_as_mut<'a, U, R>(&'a mut self, func: impl FnOnce(&'a mut U) -> R) -> R
self, then passes self.as_mut() into the pipe
function.Source§fn pipe_deref<'a, T, R>(&'a self, func: impl FnOnce(&'a T) -> R) -> R
fn pipe_deref<'a, T, R>(&'a self, func: impl FnOnce(&'a T) -> R) -> R
self, then passes self.deref() into the pipe function.Source§impl<T> Pointable for T
impl<T> Pointable for T
Source§impl<T> Tap for T
impl<T> Tap for T
Source§fn tap_borrow<B>(self, func: impl FnOnce(&B)) -> Self
fn tap_borrow<B>(self, func: impl FnOnce(&B)) -> Self
Borrow<B> of a value. Read moreSource§fn tap_borrow_mut<B>(self, func: impl FnOnce(&mut B)) -> Self
fn tap_borrow_mut<B>(self, func: impl FnOnce(&mut B)) -> Self
BorrowMut<B> of a value. Read moreSource§fn tap_ref<R>(self, func: impl FnOnce(&R)) -> Self
fn tap_ref<R>(self, func: impl FnOnce(&R)) -> Self
AsRef<R> view of a value. Read moreSource§fn tap_ref_mut<R>(self, func: impl FnOnce(&mut R)) -> Self
fn tap_ref_mut<R>(self, func: impl FnOnce(&mut R)) -> Self
AsMut<R> view of a value. Read moreSource§fn tap_deref<T>(self, func: impl FnOnce(&T)) -> Self
fn tap_deref<T>(self, func: impl FnOnce(&T)) -> Self
Deref::Target of a value. Read moreSource§fn tap_deref_mut<T>(self, func: impl FnOnce(&mut T)) -> Self
fn tap_deref_mut<T>(self, func: impl FnOnce(&mut T)) -> Self
Deref::Target of a value. Read moreSource§fn tap_dbg(self, func: impl FnOnce(&Self)) -> Self
fn tap_dbg(self, func: impl FnOnce(&Self)) -> Self
.tap() only in debug builds, and is erased in release builds.Source§fn tap_mut_dbg(self, func: impl FnOnce(&mut Self)) -> Self
fn tap_mut_dbg(self, func: impl FnOnce(&mut Self)) -> Self
.tap_mut() only in debug builds, and is erased in release
builds.Source§fn tap_borrow_dbg<B>(self, func: impl FnOnce(&B)) -> Self
fn tap_borrow_dbg<B>(self, func: impl FnOnce(&B)) -> Self
.tap_borrow() only in debug builds, and is erased in release
builds.Source§fn tap_borrow_mut_dbg<B>(self, func: impl FnOnce(&mut B)) -> Self
fn tap_borrow_mut_dbg<B>(self, func: impl FnOnce(&mut B)) -> Self
.tap_borrow_mut() only in debug builds, and is erased in release
builds.Source§fn tap_ref_dbg<R>(self, func: impl FnOnce(&R)) -> Self
fn tap_ref_dbg<R>(self, func: impl FnOnce(&R)) -> Self
.tap_ref() only in debug builds, and is erased in release
builds.Source§fn tap_ref_mut_dbg<R>(self, func: impl FnOnce(&mut R)) -> Self
fn tap_ref_mut_dbg<R>(self, func: impl FnOnce(&mut R)) -> Self
.tap_ref_mut() only in debug builds, and is erased in release
builds.Source§fn tap_deref_dbg<T>(self, func: impl FnOnce(&T)) -> Self
fn tap_deref_dbg<T>(self, func: impl FnOnce(&T)) -> Self
.tap_deref() only in debug builds, and is erased in release
builds.