Browse Source

ISLE: Build in maximum limit for multi constructor returns (#7526)

Allows users to avoid runaway rules that match too much stuff.

No statistically significant speed up to compilation on sightglass, but good to
have as a safeguard anyways.

Fixes #7500
pull/7538/head
Nick Fitzgerald 12 months ago
committed by GitHub
parent
commit
ebfe1ccd03
No known key found for this signature in database GPG Key ID: 4AEE18F83AFDEB23
  1. 11
      cranelift/codegen/src/opts.rs
  2. 2
      cranelift/isle/isle/isle_examples/link/multi_constructor_main.rs
  3. 2
      cranelift/isle/isle/isle_examples/link/multi_extractor_main.rs
  4. 26
      cranelift/isle/isle/src/codegen.rs

11
cranelift/codegen/src/opts.rs

@ -23,7 +23,16 @@ pub type Range = (usize, usize);
pub type ValueArray2 = [Value; 2]; pub type ValueArray2 = [Value; 2];
pub type ValueArray3 = [Value; 3]; pub type ValueArray3 = [Value; 3];
pub type ConstructorVec<T> = SmallVec<[T; 8]>; const MAX_ISLE_RETURNS: usize = 8;
pub type ConstructorVec<T> = SmallVec<[T; MAX_ISLE_RETURNS]>;
impl<T: smallvec::Array> generated_code::Length for SmallVec<T> {
#[inline]
fn len(&self) -> usize {
SmallVec::len(self)
}
}
pub(crate) mod generated_code; pub(crate) mod generated_code;
use generated_code::{ContextIter, IntoContextIter}; use generated_code::{ContextIter, IntoContextIter};

2
cranelift/isle/isle/isle_examples/link/multi_constructor_main.rs

@ -3,6 +3,8 @@ use multi_constructor::{ContextIter, IntoContextIter};
struct Context; struct Context;
const MAX_ISLE_RETURNS: usize = 100;
#[derive(Default)] #[derive(Default)]
struct It { struct It {
i: u32, i: u32,

2
cranelift/isle/isle/isle_examples/link/multi_extractor_main.rs

@ -2,6 +2,8 @@ mod multi_extractor;
use multi_extractor::{ContextIter, IntoContextIter}; use multi_extractor::{ContextIter, IntoContextIter};
const MAX_ISLE_RETURNS: usize = 100;
#[derive(Clone)] #[derive(Clone)]
pub enum A { pub enum A {
B, B,

26
cranelift/isle/isle/src/codegen.rs

@ -236,6 +236,16 @@ pub trait IntoContextIter {{
fn into_context_iter(self) -> Self::IntoIter; fn into_context_iter(self) -> Self::IntoIter;
}} }}
pub trait Length {{
fn len(&self) -> usize;
}}
impl<T> Length for std::vec::Vec<T> {{
fn len(&self) -> usize {{
std::vec::Vec::len(self)
}}
}}
pub struct ContextIterWrapper<I, C> {{ pub struct ContextIterWrapper<I, C> {{
iter: I, iter: I,
_ctx: std::marker::PhantomData<C>, _ctx: std::marker::PhantomData<C>,
@ -289,6 +299,11 @@ impl<T, E: Extend<T>, C> Extend<T> for ContextIterWrapper<E, C> {{
fn extend<I: IntoIterator<Item = T>>(&mut self, iter: I) {{ fn extend<I: IntoIterator<Item = T>>(&mut self, iter: I) {{
self.iter.extend(iter); self.iter.extend(iter);
}} }}
}}
impl<L: Length, C> Length for ContextIterWrapper<L, C> {{
fn len(&self) -> usize {{
self.iter.len()
}}
}} }}
"#, "#,
) )
@ -406,7 +421,7 @@ impl<T, E: Extend<T>, C> Extend<T> for ContextIterWrapper<E, C> {{
if let ReturnKind::Iterator = sig.ret_kind { if let ReturnKind::Iterator = sig.ret_kind {
writeln!( writeln!(
ctx.out, ctx.out,
"{} returns: &mut impl Extend<{}>,", "{} returns: &mut (impl Extend<{}> + Length),",
&ctx.indent, ret &ctx.indent, ret
)?; )?;
} }
@ -635,7 +650,14 @@ impl<T, E: Extend<T>, C> Extend<T> for ContextIterWrapper<E, C> {{
match ret_kind { match ret_kind {
ReturnKind::Plain => writeln!(ctx.out, ";")?, ReturnKind::Plain => writeln!(ctx.out, ";")?,
ReturnKind::Option => writeln!(ctx.out, ");")?, ReturnKind::Option => writeln!(ctx.out, ");")?,
ReturnKind::Iterator => writeln!(ctx.out, "));")?, ReturnKind::Iterator => {
writeln!(ctx.out, "));")?;
writeln!(
ctx.out,
"{}if returns.len() >= MAX_ISLE_RETURNS {{ return; }}",
ctx.indent
)?;
}
} }
} }
} }

Loading…
Cancel
Save