git.delta.rocks / jrsonnet / refs/heads / master

difftreelog

source

crates/jrsonnet-rowan-parser/src/token_set.rs2.0 KiBsourcehistory
1use std::fmt;23use crate::SyntaxKind;45#[derive(Clone, Copy, Default)]6pub struct SyntaxKindSet(u128);78impl SyntaxKindSet {9	#[allow(dead_code)]10	pub const EMPTY: Self = Self(0);11	pub const ALL: Self = Self(u128::MAX);1213	pub const fn new(kinds: &[SyntaxKind]) -> Self {14		let mut res = 0u128;15		let mut i = 0;16		while i < kinds.len() {17			res |= mask(kinds[i]);18			i += 1;19		}20		Self(res)21	}2223	#[must_use]24	pub const fn union(self, other: Self) -> Self {25		Self(self.0 | other.0)26	}27	#[must_use]28	pub const fn with(self, kind: SyntaxKind) -> Self {29		Self(self.0 | mask(kind))30	}3132	pub fn contains(&self, kind: SyntaxKind) -> bool {33		if !is_token(kind) {34			return false;35		}36		self.0 & mask(kind) != 037	}38}39impl fmt::Display for SyntaxKindSet {40	fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {41		let mut v = self.0;42		let mut variants = <Vec<SyntaxKind>>::new();43		for i in 0..128 {44			if v & 1 == 1 {45				variants.push(SyntaxKind::from_raw(i));46			}47			v >>= 1;48			if v == 0 {49				break;50			}51		}52		for (i, v) in variants.iter().enumerate() {53			if i == 0 {54			} else if i == variants.len() - 1 {55				write!(f, " or ")?;56			} else {57				write!(f, ", ")?;58			}59			write!(f, "{v:?}")?;60		}61		Ok(())62	}63}64impl fmt::Debug for SyntaxKindSet {65	fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {66		let mut v = self.0;67		let mut variants = <Vec<SyntaxKind>>::new();68		for i in 0..128 {69			if v & 1 == 1 {70				variants.push(SyntaxKind::from_raw(i));71			}72			v >>= 1;73			if v == 0 {74				break;75			}76		}77		f.debug_tuple("SyntaxKindSet").field(&variants).finish()78	}79}8081const fn mask(kind: SyntaxKind) -> u128 {82	assert!(kind as u32 <= 128, "mask for not a token kind");83	1u128 << (kind as u128)84}8586#[macro_export]87macro_rules! TS {88	($($tt:tt)*) => {89		$crate::SyntaxKindSet::new(&[90			$(91				$crate::T![$tt]92			),*93		])94	};95}9697#[test]98fn sanity() {99	assert!(100		(SyntaxKind::LEXING_ERROR as u32) < 127,101		"can't keep KindSet as bitset"102	);103}104fn is_token(kind: SyntaxKind) -> bool {105	(kind as u32) < 127106}