Skip to content

Commit

Permalink
Implement and test monomorphization
Browse files Browse the repository at this point in the history
  • Loading branch information
oli-obk committed Sep 6, 2023
1 parent 202fbed commit 0f4ff52
Show file tree
Hide file tree
Showing 3 changed files with 92 additions and 4 deletions.
27 changes: 25 additions & 2 deletions compiler/rustc_smir/src/stable_mir/fold.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,8 @@ use std::ops::ControlFlow;
use crate::rustc_internal::Opaque;

use super::ty::{
Allocation, Binder, Const, ConstDef, ExistentialPredicate, FnSig, GenericArgKind, GenericArgs,
Promoted, RigidTy, TermKind, Ty, UnevaluatedConst,
Allocation, Binder, Const, ConstDef, ConstantKind, ExistentialPredicate, FnSig, GenericArgKind,
GenericArgs, Promoted, RigidTy, TermKind, Ty, TyKind, UnevaluatedConst,
};

pub trait Folder: Sized {
Expand Down Expand Up @@ -205,3 +205,26 @@ impl Foldable for FnSig {
})
}
}

pub enum Never {}

/// In order to instantiate a `Foldable`'s generic parameters with specific arguments,
/// `GenericArgs` can be used as a `Folder` that replaces all mentions of generic params
/// with the entries in its list.
impl Folder for GenericArgs {
type Break = Never;

fn visit_ty(&mut self, ty: &Ty) -> ControlFlow<Self::Break, Ty> {
ControlFlow::Continue(match ty.kind() {
TyKind::Param(p) => self[p],
_ => *ty,
})
}

fn fold_const(&mut self, c: &Const) -> ControlFlow<Self::Break, Const> {
ControlFlow::Continue(match &c.literal {
ConstantKind::Param(p) => self[p.clone()].clone(),
_ => c.clone(),
})
}
}
38 changes: 38 additions & 0 deletions compiler/rustc_smir/src/stable_mir/ty.rs
Original file line number Diff line number Diff line change
Expand Up @@ -138,13 +138,51 @@ pub struct ImplDef(pub(crate) DefId);
#[derive(Clone, Debug)]
pub struct GenericArgs(pub Vec<GenericArgKind>);

impl std::ops::Index<ParamTy> for GenericArgs {
type Output = Ty;

fn index(&self, index: ParamTy) -> &Self::Output {
self.0[index.index as usize].expect_ty()
}
}

impl std::ops::Index<ParamConst> for GenericArgs {
type Output = Const;

fn index(&self, index: ParamConst) -> &Self::Output {
self.0[index.index as usize].expect_const()
}
}

#[derive(Clone, Debug)]
pub enum GenericArgKind {
Lifetime(Region),
Type(Ty),
Const(Const),
}

impl GenericArgKind {
/// Panic if this generic argument is not a type, otherwise
/// return the type.
#[track_caller]
pub fn expect_ty(&self) -> &Ty {
match self {
GenericArgKind::Type(ty) => ty,
_ => panic!("{self:?}"),
}
}

/// Panic if this generic argument is not a const, otherwise
/// return the const.
#[track_caller]
pub fn expect_const(&self) -> &Const {
match self {
GenericArgKind::Const(c) => c,
_ => panic!("{self:?}"),
}
}
}

#[derive(Clone, Debug)]
pub enum TermKind {
Type(Ty),
Expand Down
31 changes: 29 additions & 2 deletions tests/ui-fulldeps/stable-mir/crate-info.rs
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,18 @@

#![feature(rustc_private)]
#![feature(assert_matches)]
#![feature(control_flow_enum)]

extern crate rustc_hir;
extern crate rustc_middle;
extern crate rustc_smir;

use rustc_hir::def::DefKind;
use rustc_middle::ty::TyCtxt;
use rustc_smir::{rustc_internal, stable_mir};
use rustc_smir::{
rustc_internal,
stable_mir::{self, fold::Foldable},
};
use std::assert_matches::assert_matches;
use std::io::Write;
use std::ops::ControlFlow;
Expand Down Expand Up @@ -116,7 +120,30 @@ fn test_stable_mir(tcx: TyCtxt<'_>) -> ControlFlow<()> {
stable_mir::mir::Terminator::Call { func, .. } => match func {
stable_mir::mir::Operand::Constant(c) => match &c.literal.literal {
stable_mir::ty::ConstantKind::Allocated(alloc) => {
assert!(alloc.bytes.is_empty())
assert!(alloc.bytes.is_empty());
match c.literal.ty.kind() {
stable_mir::ty::TyKind::RigidTy(stable_mir::ty::RigidTy::FnDef(
def,
mut args,
)) => {
let func = def.body();
match func.locals[1]
.fold(&mut args)
.continue_value()
.unwrap()
.kind()
{
stable_mir::ty::TyKind::RigidTy(
stable_mir::ty::RigidTy::Uint(_),
) => {}
stable_mir::ty::TyKind::RigidTy(
stable_mir::ty::RigidTy::Tuple(_),
) => {}
other => panic!("{other:?}"),
}
}
other => panic!("{other:?}"),
}
}
other => panic!("{other:?}"),
},
Expand Down

0 comments on commit 0f4ff52

Please sign in to comment.