Skip to content

Commit

Permalink
Fix to one-variant enums.
Browse files Browse the repository at this point in the history
  • Loading branch information
FractalFir committed Jan 20, 2024
1 parent 637b04f commit be4731c
Show file tree
Hide file tree
Showing 11 changed files with 349 additions and 261 deletions.
9 changes: 7 additions & 2 deletions src/aggregate.rs
Original file line number Diff line number Diff line change
Expand Up @@ -306,8 +306,13 @@ fn aggregate_adt<'tyctx>(
ops.extend(adt_adress_ops);
ops.push(CILOp::LdcI32(variant_idx as i32));
let field_name = "_tag".into();
let layout = tyctx.layout_of(rustc_middle::ty::ParamEnvAnd{param_env:ParamEnv::reveal_all(),value:adt_type}).expect("Could not get type layout!");
let (disrc_type,_) = crate::utilis::adt::enum_tag_info(&layout.layout,tyctx);
let layout = tyctx
.layout_of(rustc_middle::ty::ParamEnvAnd {
param_env: ParamEnv::reveal_all(),
value: adt_type,
})
.expect("Could not get type layout!");
let (disrc_type, _) = crate::utilis::adt::enum_tag_info(&layout.layout, tyctx);
ops.push(CILOp::STField(Box::new(FieldDescriptor::new(
adt_type_ref,
disrc_type,
Expand Down
10 changes: 5 additions & 5 deletions src/binop.rs
Original file line number Diff line number Diff line change
Expand Up @@ -222,7 +222,7 @@ fn sub_unchecked<'tyctx>(
}
}
fn ne_unchecked<'tyctx>(ty_a: Ty<'tyctx>, ty_b: Ty<'tyctx>) -> Vec<CILOp> {
vec![eq_unchecked(ty_a,ty_b), CILOp::LdcI32(0), CILOp::Eq]
vec![eq_unchecked(ty_a, ty_b), CILOp::LdcI32(0), CILOp::Eq]
}
fn eq_unchecked<'tyctx>(ty_a: Ty<'tyctx>, _ty_b: Ty<'tyctx>) -> CILOp {
//vec![CILOp::Eq]
Expand All @@ -237,8 +237,8 @@ fn eq_unchecked<'tyctx>(ty_a: Ty<'tyctx>, _ty_b: Ty<'tyctx>) -> CILOp {
)
.into(),
),
_=>CILOp::Eq,
}
_ => CILOp::Eq,
},
TyKind::Int(int) => match int {
IntTy::I128 => CILOp::Call(
CallSite::new(
Expand All @@ -249,8 +249,8 @@ fn eq_unchecked<'tyctx>(ty_a: Ty<'tyctx>, _ty_b: Ty<'tyctx>) -> CILOp {
)
.into(),
),
_=>CILOp::Eq,
}
_ => CILOp::Eq,
},
TyKind::Bool => CILOp::Eq,
TyKind::Float(_) => CILOp::Eq,
TyKind::RawPtr(_) => CILOp::Eq,
Expand Down
271 changes: 142 additions & 129 deletions src/compile_test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -109,150 +109,163 @@ fn test_lib(args: &[&str], test_name: &str) {
}
macro_rules! test_lib {
($test_name:ident,$is_stable:ident) => {
mod $test_name {mod $is_stable{
#[cfg(test)]
static COMPILE_LOCK: std::sync::Mutex<()> = std::sync::Mutex::new(());
#[test]
fn release() {
// Ensures no two compilations run at the same time.
let lock = COMPILE_LOCK.lock();
super::super::test_lib(
&[
"-O",
"--crate-type=lib",
"-Z",
super::super::backend_path(),
"-C",
&format!("linker={}", super::super::RUSTC_CODEGEN_CLR_LINKER.display()),
concat!("../", stringify!($test_name), ".rs"),
"-o",
concat!("./", stringify!($test_name), ".rlib"),
//"--target",
// "clr64-unknown-clr"
],
stringify!($test_name),
);
drop(lock);
}
#[test]
fn debug() {
let lock = COMPILE_LOCK.lock();
super::super::test_lib(
&[
"--crate-type=lib",
"-Z",
super::super::backend_path(),
"-C",
&format!("linker={}", super::super::RUSTC_CODEGEN_CLR_LINKER.display()),
concat!("../", stringify!($test_name), ".rs"),
"-o",
concat!("./", stringify!($test_name), ".rlib"),
//"--target",
// "clr64-unknown-clr"
],
stringify!($test_name),
);
drop(lock);
mod $test_name {
mod $is_stable {
#[cfg(test)]
static COMPILE_LOCK: std::sync::Mutex<()> = std::sync::Mutex::new(());
#[test]
fn release() {
// Ensures no two compilations run at the same time.
let lock = COMPILE_LOCK.lock();
super::super::test_lib(
&[
"-O",
"--crate-type=lib",
"-Z",
super::super::backend_path(),
"-C",
&format!(
"linker={}",
super::super::RUSTC_CODEGEN_CLR_LINKER.display()
),
concat!("../", stringify!($test_name), ".rs"),
"-o",
concat!("./", stringify!($test_name), ".rlib"),
//"--target",
// "clr64-unknown-clr"
],
stringify!($test_name),
);
drop(lock);
}
#[test]
fn debug() {
let lock = COMPILE_LOCK.lock();
super::super::test_lib(
&[
"--crate-type=lib",
"-Z",
super::super::backend_path(),
"-C",
&format!(
"linker={}",
super::super::RUSTC_CODEGEN_CLR_LINKER.display()
),
concat!("../", stringify!($test_name), ".rs"),
"-o",
concat!("./", stringify!($test_name), ".rlib"),
//"--target",
// "clr64-unknown-clr"
],
stringify!($test_name),
);
drop(lock);
}
}
}}
}
};
}
macro_rules! run_test {
($prefix:ident,$test_name:ident,$is_stable:ident) => {
mod $test_name { mod $is_stable{
#[cfg(test)]
use ntest::timeout;
#[cfg(test)]
static COMPILE_LOCK: std::sync::Mutex<()> = std::sync::Mutex::new(());
#[test]
#[timeout(30_000)]
fn release() {
let lock = COMPILE_LOCK.lock();
let test_dir = concat!("./test/", stringify!($prefix), "/");
// Ensures the test directory is present
std::fs::create_dir_all(test_dir).expect("Could not setup the test env");
// Builds the backend if neceasry
super::super::RUSTC_BUILD_STATUS
.as_ref()
.expect("Could not build rustc!");
// Compiles the test project
let mut cmd = std::process::Command::new("rustc");
//.env("RUST_TARGET_PATH","../../")
cmd.current_dir(test_dir)
.args([
"-O",
"-Z",
super::super::backend_path(),
"-C",
&format!("linker={}", super::super::RUSTC_CODEGEN_CLR_LINKER.display()),
concat!("./", stringify!($test_name), ".rs"),
"-o",
concat!("./", stringify!($test_name), ".exe"),
//"--target",
//"clr64-unknown-clr"
]);
eprintln!("Command: {cmd:?}");
let out =
cmd.output()
.expect("failed to execute process");
// If stderr is not empty, then something went wrong, so print the stdout and stderr for debuging.
if !out.stderr.is_empty() {
let stdout = String::from_utf8(out.stdout)
.expect("rustc error contained non-UTF8 characters.");
let stderr = String::from_utf8(out.stderr)
.expect("rustc error contained non-UTF8 characters.");
panic!("stdout:\n{stdout}\nstderr:\n{stderr}");
}
let exec_path = concat!("../", stringify!($test_name));
drop(lock);
//super::peverify(exec_path, test_dir);

super::super::test_dotnet_executable(exec_path, test_dir);
}
#[test]
#[timeout(30_000)]
fn debug() {
let lock = COMPILE_LOCK.lock();
let test_dir = concat!("./test/", stringify!($prefix), "/");
// Ensures the test directory is present
std::fs::create_dir_all(test_dir).expect("Could not setup the test env");
// Builds the backend if neceasry
super::super::RUSTC_BUILD_STATUS
.as_ref()
.expect("Could not build rustc!");
let test_name = concat!("debug_", stringify!($test_name));
let output_path = format!("./{test_name}.exe");
// Compiles the test project
let out = std::process::Command::new("rustc")
mod $test_name {
mod $is_stable {
#[cfg(test)]
use ntest::timeout;
#[cfg(test)]
static COMPILE_LOCK: std::sync::Mutex<()> = std::sync::Mutex::new(());
#[test]
#[timeout(30_000)]
fn release() {
let lock = COMPILE_LOCK.lock();
let test_dir = concat!("./test/", stringify!($prefix), "/");
// Ensures the test directory is present
std::fs::create_dir_all(test_dir).expect("Could not setup the test env");
// Builds the backend if neceasry
super::super::RUSTC_BUILD_STATUS
.as_ref()
.expect("Could not build rustc!");
// Compiles the test project
let mut cmd = std::process::Command::new("rustc");
//.env("RUST_TARGET_PATH","../../")
.current_dir(test_dir)
.args([
cmd.current_dir(test_dir).args([
"-O",
"-Z",
super::super::backend_path(),
"-C",
&format!("linker={}", super::super::RUSTC_CODEGEN_CLR_LINKER.display()),
&format!(
"linker={}",
super::super::RUSTC_CODEGEN_CLR_LINKER.display()
),
concat!("./", stringify!($test_name), ".rs"),
"-o",
&output_path,
concat!("./", stringify!($test_name), ".exe"),
//"--target",
//"clr64-unknown-clr"
])
.output()
.expect("failed to execute process");
// If stderr is not empty, then something went wrong, so print the stdout and stderr for debuging.
if !out.stderr.is_empty() {
let stdout = String::from_utf8(out.stdout)
.expect("rustc error contained non-UTF8 characters.");
let stderr = String::from_utf8(out.stderr)
.expect("rustc error contained non-UTF8 characters.");
panic!("stdout:\n{stdout}\nstderr:\n{stderr}");
]);
eprintln!("Command: {cmd:?}");
let out = cmd.output().expect("failed to execute process");
// If stderr is not empty, then something went wrong, so print the stdout and stderr for debuging.
if !out.stderr.is_empty() {
let stdout = String::from_utf8(out.stdout)
.expect("rustc error contained non-UTF8 characters.");
let stderr = String::from_utf8(out.stderr)
.expect("rustc error contained non-UTF8 characters.");
panic!("stdout:\n{stdout}\nstderr:\n{stderr}");
}
let exec_path = concat!("../", stringify!($test_name));
drop(lock);
//super::peverify(exec_path, test_dir);

super::super::test_dotnet_executable(exec_path, test_dir);
}
#[test]
#[timeout(30_000)]
fn debug() {
let lock = COMPILE_LOCK.lock();
let test_dir = concat!("./test/", stringify!($prefix), "/");
// Ensures the test directory is present
std::fs::create_dir_all(test_dir).expect("Could not setup the test env");
// Builds the backend if neceasry
super::super::RUSTC_BUILD_STATUS
.as_ref()
.expect("Could not build rustc!");
let test_name = concat!("debug_", stringify!($test_name));
let output_path = format!("./{test_name}.exe");
// Compiles the test project
let out = std::process::Command::new("rustc")
//.env("RUST_TARGET_PATH","../../")
.current_dir(test_dir)
.args([
"-Z",
super::super::backend_path(),
"-C",
&format!(
"linker={}",
super::super::RUSTC_CODEGEN_CLR_LINKER.display()
),
concat!("./", stringify!($test_name), ".rs"),
"-o",
&output_path,
//"--target",
//"clr64-unknown-clr"
])
.output()
.expect("failed to execute process");
// If stderr is not empty, then something went wrong, so print the stdout and stderr for debuging.
if !out.stderr.is_empty() {
let stdout = String::from_utf8(out.stdout)
.expect("rustc error contained non-UTF8 characters.");
let stderr = String::from_utf8(out.stderr)
.expect("rustc error contained non-UTF8 characters.");
panic!("stdout:\n{stdout}\nstderr:\n{stderr}");
}
let exec_path = format!("../{test_name}");
drop(lock);
//super::peverify(&exec_path, test_dir);
super::super::test_dotnet_executable(&exec_path, test_dir);
}
let exec_path = format!("../{test_name}");
drop(lock);
//super::peverify(&exec_path, test_dir);
super::super::test_dotnet_executable(&exec_path, test_dir);
}
}}
}
};
}
macro_rules! cargo_test {
Expand Down
18 changes: 14 additions & 4 deletions src/constant.rs
Original file line number Diff line number Diff line change
Expand Up @@ -120,8 +120,13 @@ fn create_const_adt_from_bytes<'ctx>(
} else {
panic!("Invalid enum type {enum_type:?}");
};
let layout = tyctx.layout_of(rustc_middle::ty::ParamEnvAnd{param_env:ParamEnv::reveal_all(),value:enum_ty}).expect("Could not get type layout!");
let (disrc_type,discr_size) = crate::utilis::adt::enum_tag_info(&layout.layout,tyctx);
let layout = tyctx
.layout_of(rustc_middle::ty::ParamEnvAnd {
param_env: ParamEnv::reveal_all(),
value: enum_ty,
})
.expect("Could not get type layout!");
let (disrc_type, discr_size) = crate::utilis::adt::enum_tag_info(&layout.layout, tyctx);
let mut ops = vec![CILOp::NewTMPLocal(enum_type.into())];
let curr_variant = match discr_size {
0 => todo!("Can't yet handle constant enums with 0-sized tags."),
Expand Down Expand Up @@ -710,8 +715,13 @@ fn load_const_scalar<'ctx>(
}
TyKind::Adt(adt_def, _subst) => match adt_def.adt_kind() {
AdtKind::Enum => {
let layout = tyctx.layout_of(rustc_middle::ty::ParamEnvAnd{param_env:ParamEnv::reveal_all(),value:scalar_type}).expect("Could not get type layout!");
let (disrc_type,_) = crate::utilis::adt::enum_tag_info(&layout.layout,tyctx);
let layout = tyctx
.layout_of(rustc_middle::ty::ParamEnvAnd {
param_env: ParamEnv::reveal_all(),
value: scalar_type,
})
.expect("Could not get type layout!");
let (disrc_type, _) = crate::utilis::adt::enum_tag_info(&layout.layout, tyctx);
let enum_dotnet = tpe.as_dotnet().expect("Enum scalar not an ADT!");
vec![
CILOp::NewTMPLocal(tpe.into()),
Expand Down
9 changes: 7 additions & 2 deletions src/rvalue.rs
Original file line number Diff line number Diff line change
Expand Up @@ -410,8 +410,13 @@ pub fn handle_rvalue<'tcx>(
//TODO: chose proper tag type based on variant count of `owner`
//let discr_ty = owner_ty.discriminant_ty(tyctx);
//let discr_type = tycache.type_from_cache(discr_ty, tyctx, Some(method_instance));
let layout = tyctx.layout_of(rustc_middle::ty::ParamEnvAnd{param_env:ParamEnv::reveal_all(),value:owner_ty}).expect("Could not get type layout!");
let (disrc_type,_) = crate::utilis::adt::enum_tag_info(&layout.layout,tyctx);
let layout = tyctx
.layout_of(rustc_middle::ty::ParamEnvAnd {
param_env: ParamEnv::reveal_all(),
value: owner_ty,
})
.expect("Could not get type layout!");
let (disrc_type, _) = crate::utilis::adt::enum_tag_info(&layout.layout, tyctx);
let owner = if let crate::r#type::Type::DotnetType(dotnet_type) = owner {
dotnet_type.as_ref().clone()
} else {
Expand Down
Loading

0 comments on commit be4731c

Please sign in to comment.