diff --git a/Cargo.toml b/Cargo.toml index 6a11287..4c713c8 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -24,21 +24,23 @@ include = [ ] [features] +default = ["std"] +std = ["regex?/std", "unicode-normalization?/std"] # Includes the full canonical text of each license text = [] # Allows analysis of text to determine if it might be an SPDX license text -detection = ["regex", "unicode-normalization"] +detection = ["std", "regex", "unicode-normalization"] # Allows de/serialization of a spdx::detection::Store for quicker loading -detection-cache = ["detection", "zstd"] +detection-cache = ["std", "detection", "zstd"] # Inlines a cache into this crate, which contains all of the licenses from the # SPDX crate that the crate version was packaged with -detection-inline-cache = ["detection-cache"] +detection-inline-cache = ["std", "detection-cache"] # Performs license detection in parallel within the same text -detection-parallel = ["detection", "rayon"] +detection-parallel = ["std", "detection", "rayon"] [dependencies] rayon = { version = "1.11", optional = true } -regex = { version = "1.12", optional = true } +regex = { version = "1.12", optional = true, default-features = false, features = ["perf", "unicode"] } # In most cases expressions are quite small so we can avoid heap allocations smallvec = "1.15" unicode-normalization = { version = "0.1", optional = true } diff --git a/src/error.rs b/src/error.rs index acfb77c..2be80e8 100644 --- a/src/error.rs +++ b/src/error.rs @@ -1,4 +1,5 @@ -use std::{error::Error, fmt}; +use alloc::string::String; +use core::{error::Error, fmt}; /// An error related to parsing of an SPDX license expression /// or identifier @@ -8,7 +9,7 @@ pub struct ParseError { pub original: String, /// The range of characters in the original string that result /// in this error - pub span: std::ops::Range, + pub span: core::ops::Range, /// The specific reason for the error pub reason: Reason, } diff --git a/src/expression.rs b/src/expression.rs index 8dfd267..a9254a1 100644 --- a/src/expression.rs +++ b/src/expression.rs @@ -4,9 +4,11 @@ mod minimize; mod parser; use crate::{LicenseReq, error::ParseError}; +use alloc::string::String; +use alloc::vec::Vec; +use core::fmt; pub use minimize::MinimizeError; use smallvec::SmallVec; -use std::fmt; /// A license requirement inside an SPDX license expression /// @@ -16,7 +18,7 @@ pub struct ExpressionReq { /// The license requirement pub req: LicenseReq, /// The span in the original license expression string containing the requirement - pub span: std::ops::Range, + pub span: core::ops::Range, } impl PartialEq for ExpressionReq { @@ -238,7 +240,7 @@ impl fmt::Display for Expression { } } -impl std::str::FromStr for Expression { +impl core::str::FromStr for Expression { type Err = ParseError; fn from_str(s: &str) -> Result { Self::parse(s) diff --git a/src/expression/minimize.rs b/src/expression/minimize.rs index 8e53652..78e6a9d 100644 --- a/src/expression/minimize.rs +++ b/src/expression/minimize.rs @@ -1,6 +1,7 @@ use super::Expression; use crate::{LicenseReq, Licensee}; -use std::fmt; +use alloc::vec::Vec; +use core::fmt; /// Errors that can occur when trying to minimize the requirements for an [`Expression`] #[derive(Debug, PartialEq, Eq)] @@ -25,7 +26,7 @@ impl fmt::Display for MinimizeError { } } -impl std::error::Error for MinimizeError { +impl core::error::Error for MinimizeError { fn description(&self) -> &str { match self { Self::TooManyRequirements(_) => "too many requirements in license expression", diff --git a/src/expression/parser.rs b/src/expression/parser.rs index b4385f3..e29f63a 100644 --- a/src/expression/parser.rs +++ b/src/expression/parser.rs @@ -4,6 +4,9 @@ use crate::{ expression::{ExprNode, Expression, ExpressionReq, Operator}, lexer::{Lexer, Token}, }; +use alloc::borrow::ToOwned; +use alloc::boxed::Box; +use alloc::string::String; use smallvec::SmallVec; impl Expression { @@ -163,7 +166,7 @@ impl Expression { struct OpAndSpan { op: Op, - span: std::ops::Range, + span: core::ops::Range, } let lexer = Lexer::new_mode(original, mode); @@ -184,7 +187,7 @@ impl Expression { Ok(()) }; - let make_err_for_token = |last_token: Option>, span: std::ops::Range| { + let make_err_for_token = |last_token: Option>, span: core::ops::Range| { let expected: &[&str] = match last_token { None | Some(Token::And | Token::Or | Token::OpenParen) => &["", "("], Some(Token::CloseParen) => &["AND", "OR"], diff --git a/src/lexer.rs b/src/lexer.rs index fd45cde..025787b 100644 --- a/src/lexer.rs +++ b/src/lexer.rs @@ -2,6 +2,7 @@ use crate::{ ExceptionId, LicenseId, error::{ParseError, Reason}, }; +use alloc::borrow::ToOwned; /// Parsing configuration for SPDX expression #[derive(Default, Copy, Clone)] @@ -106,9 +107,9 @@ pub enum Token<'a> { Or, } -impl std::fmt::Display for Token<'_> { - fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - std::fmt::Debug::fmt(self, f) +impl core::fmt::Display for Token<'_> { + fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result { + core::fmt::Debug::fmt(self, f) } } @@ -244,7 +245,7 @@ pub struct LexerToken<'a> { /// The token that was lexed pub token: Token<'a>, /// The range of the token characters in the original license expression - pub span: std::ops::Range, + pub span: core::ops::Range, } impl<'a> Iterator for Lexer<'a> { diff --git a/src/lib.rs b/src/lib.rs index f0e56b4..1188be7 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -1,6 +1,9 @@ #![cfg_attr(docsrs, feature(doc_cfg))] #![deny(missing_docs)] #![doc = include_str!("../README.md")] +#![cfg_attr(not(feature = "std"), no_std)] + +extern crate alloc; /// Error types pub mod error; @@ -21,14 +24,16 @@ pub mod detection; #[allow(missing_docs)] pub mod text; +use alloc::boxed::Box; +use alloc::string::String; +use core::{ + cmp::{self, Ordering}, + fmt, +}; pub use error::ParseError; pub use expression::Expression; pub use lexer::ParseMode; pub use licensee::Licensee; -use std::{ - cmp::{self, Ordering}, - fmt, -}; /// Flags that can apply to licenses and/or license exceptions pub mod flags { @@ -87,7 +92,7 @@ impl Eq for LicenseId {} impl Ord for LicenseId { #[inline] - fn cmp(&self, o: &Self) -> Ordering { + fn cmp(&self, o: &Self) -> core::cmp::Ordering { self.l.index.cmp(&o.l.index) } } @@ -99,7 +104,7 @@ impl PartialOrd for LicenseId { } } -impl std::ops::Deref for LicenseId { +impl core::ops::Deref for LicenseId { type Target = License; #[inline] @@ -253,7 +258,7 @@ impl PartialOrd for ExceptionId { } } -impl std::ops::Deref for ExceptionId { +impl core::ops::Deref for ExceptionId { type Target = Exception; #[inline] @@ -585,7 +590,7 @@ pub fn gnu_license_id(base: &str, or_later: bool) -> Option { v[base.len()..].copy_from_slice(b"-only"); } - let Ok(s) = std::str::from_utf8(v.as_slice()) else { + let Ok(s) = core::str::from_utf8(v.as_slice()) else { // Unreachable, but whatever return None; }; @@ -645,8 +650,8 @@ pub fn license_version() -> &'static str { #[cfg(test)] mod test { use super::LicenseItem; - use crate::{Expression, license_id}; + use alloc::string::ToString; #[test] fn gnu_or_later_display() { diff --git a/src/licensee.rs b/src/licensee.rs index 6377d55..cd39ecb 100644 --- a/src/licensee.rs +++ b/src/licensee.rs @@ -3,7 +3,10 @@ use crate::{ error::{ParseError, Reason}, lexer::{Lexer, Token}, }; -use std::fmt; +use alloc::borrow::ToOwned; +use alloc::boxed::Box; +use alloc::string::String; +use core::fmt; /// A convenience wrapper for a license and optional additional text that can be /// checked against a license requirement to see if it satisfies the requirement @@ -26,7 +29,7 @@ impl fmt::Display for Licensee { } } -impl std::str::FromStr for Licensee { +impl core::str::FromStr for Licensee { type Err = ParseError; fn from_str(s: &str) -> Result { @@ -243,7 +246,7 @@ impl Licensee { impl PartialOrd for Licensee { #[inline] - fn partial_cmp(&self, o: &LicenseReq) -> Option { + fn partial_cmp(&self, o: &LicenseReq) -> Option { self.inner.partial_cmp(o) } } @@ -267,6 +270,9 @@ mod test { use crate::{ AdditionItem, LicenseItem, LicenseRef, LicenseReq, Licensee, exception_id, license_id, }; + use alloc::borrow::ToOwned; + use alloc::boxed::Box; + use alloc::vec::Vec; const LICENSEES: &[&str] = &[ "LicenseRef-Embark-Proprietary",