Skip to content

Commit

Permalink
Merge commit '9809f5d21990d9e24b3e9876ea7da756fd4e9def' into libgccji…
Browse files Browse the repository at this point in the history
…t-codegen
  • Loading branch information
antoyo committed Sep 28, 2021
2 parents df48731 + 9809f5d commit 7f32dd5
Show file tree
Hide file tree
Showing 19 changed files with 559 additions and 559 deletions.
38 changes: 19 additions & 19 deletions compiler/rustc_codegen_gcc/Cargo.lock
Original file line number Diff line number Diff line change
Expand Up @@ -25,9 +25,9 @@ checksum = "cdb031dd78e28731d87d56cc8ffef4a8f36ca26c38fe2de700543e627f8a464a"

[[package]]
name = "bitflags"
version = "1.2.1"
version = "1.3.2"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "cf1de2fe8c75bc145a2f577add951f8134889b4795d47466a54a5c846d691693"
checksum = "bef38d45163c2f1dde094a7dfd33ccf595c92905c8f8f4fdc18d06fb1037718a"

[[package]]
name = "cfg-if"
Expand Down Expand Up @@ -56,15 +56,15 @@ dependencies = [
[[package]]
name = "gccjit"
version = "1.0.0"
source = "git+https://github.com/antoyo/gccjit.rs#54be27e41fff7b6ab532e2e21a82df50a12b9ad3"
source = "git+https://github.com/antoyo/gccjit.rs#2d4fea7319f80531b2e5d264fca9f1c498a3a62e"
dependencies = [
"gccjit_sys",
]

[[package]]
name = "gccjit_sys"
version = "0.0.1"
source = "git+https://github.com/antoyo/gccjit.rs#54be27e41fff7b6ab532e2e21a82df50a12b9ad3"
source = "git+https://github.com/antoyo/gccjit.rs#2d4fea7319f80531b2e5d264fca9f1c498a3a62e"
dependencies = [
"libc 0.1.12",
]
Expand All @@ -85,7 +85,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "7fcd999463524c52659517fe2cea98493cfe485d10565e7b0fb07dbba7ad2753"
dependencies = [
"cfg-if",
"libc 0.2.98",
"libc 0.2.102",
"wasi",
]

Expand All @@ -101,7 +101,7 @@ version = "0.1.19"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "62b467343b94ba476dcb2500d242dadbb39557df889310ac77c5d99100aaac33"
dependencies = [
"libc 0.2.98",
"libc 0.2.102",
]

[[package]]
Expand All @@ -122,7 +122,7 @@ checksum = "96bd995a092cac79868250589869b5a5d656b02a02bd74c8ebdc566dc7203090"
dependencies = [
"fm",
"getopts",
"libc 0.2.98",
"libc 0.2.102",
"num_cpus",
"termcolor",
"threadpool",
Expand All @@ -138,15 +138,15 @@ checksum = "e32a70cf75e5846d53a673923498228bbec6a8624708a9ea5645f075d6276122"

[[package]]
name = "libc"
version = "0.2.98"
version = "0.2.102"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "320cfe77175da3a483efed4bc0adc1968ca050b098ce4f2f1c13a56626128790"
checksum = "a2a5ac8f984bfcf3a823267e5fde638acc3325f6496633a5da6bb6eb2171e103"

[[package]]
name = "memchr"
version = "2.4.0"
version = "2.4.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "b16bd47d9e329435e309c58469fe0791c2d0d1ba96ec0954152a5ae2b04387dc"
checksum = "308cc39be01b73d0d18f82a0e7b2a3df85245f84af96fdddc5d202d27e47b86a"

[[package]]
name = "num_cpus"
Expand All @@ -155,7 +155,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "05499f3756671c15885fee9034446956fff3f243d6077b91e5767df161f766b3"
dependencies = [
"hermit-abi",
"libc 0.2.98",
"libc 0.2.102",
]

[[package]]
Expand All @@ -181,7 +181,7 @@ version = "0.8.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "2e7573632e6454cf6b99d7aac4ccca54be06da05aca2ef7423d22d27d4d4bcd8"
dependencies = [
"libc 0.2.98",
"libc 0.2.102",
"rand_chacha",
"rand_core",
"rand_hc",
Expand Down Expand Up @@ -217,9 +217,9 @@ dependencies = [

[[package]]
name = "redox_syscall"
version = "0.2.9"
version = "0.2.10"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "5ab49abadf3f9e1c4bc499e8845e152ad87d2ad2d30371841171169e9d75feee"
checksum = "8383f39639269cde97d255a32bdb68c047337295414940c68bdd30c2e13203ff"
dependencies = [
"bitflags",
]
Expand Down Expand Up @@ -284,7 +284,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "dac1c663cfc93810f88aed9b8941d48cabf856a1b111c29a40439018d870eb22"
dependencies = [
"cfg-if",
"libc 0.2.98",
"libc 0.2.102",
"rand",
"redox_syscall",
"remove_dir_all",
Expand All @@ -311,17 +311,17 @@ dependencies = [

[[package]]
name = "unicode-width"
version = "0.1.8"
version = "0.1.9"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9337591893a19b88d8d87f2cec1e73fad5cdfd10e5a6f349f498ad6ea2ffb1e3"
checksum = "3ed742d4ea2bd1176e236172c8429aaf54486e7ac098db29ffe6529e0ce50973"

[[package]]
name = "wait-timeout"
version = "0.2.0"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "9f200f5b12eb75f8c1ed65abd4b2db8a6e1b138a20de009dacee265a2498f3f6"
dependencies = [
"libc 0.2.98",
"libc 0.2.102",
]

[[package]]
Expand Down
18 changes: 18 additions & 0 deletions compiler/rustc_codegen_gcc/Readme.md
Original file line number Diff line number Diff line change
Expand Up @@ -115,3 +115,21 @@ p loc->m_line
* Build the stage2 compiler (`rustup toolchain link debug-current build/x86_64-unknown-linux-gnu/stage2`).
* Clean and rebuild the codegen with `debug-current` in the file `rust-toolchain`.
### How to build a cross-compiling libgccjit
#### Building libgccjit
* Follow these instructions: https://preshing.com/20141119/how-to-build-a-gcc-cross-compiler/ with the following changes:
* Configure gcc with `../gcc/configure --enable-host-shared --disable-multilib --enable-languages=c,jit,c++ --disable-bootstrap --enable-checking=release --prefix=/opt/m68k-gcc/ --target=m68k-linux --without-headers`.
* Some shells, like fish, don't define the environment variable `$MACHTYPE`.
* Add `CFLAGS="-Wno-error=attributes -g -O2"` at the end of the configure command for building glibc (`CFLAGS="-Wno-error=attributes -Wno-error=array-parameter -Wno-error=stringop-overflow -Wno-error=array-bounds -g -O2"` for glibc 2.31, which is useful for Debian).
#### Configuring rustc_codegen_gcc
* Set `TARGET_TRIPLE="m68k-unknown-linux-gnu"` in config.sh.
* Since rustc doesn't support this architecture yet, set it back to `TARGET_TRIPLE="mips-unknown-linux-gnu"` (or another target having the same attributes). Alternatively, create a [target specification file](https://book.avr-rust.com/005.1-the-target-specification-json-file.html) (note that the `arch` specified in this file must be supported by the rust compiler).
* Set `linker='-Clinker=m68k-linux-gcc'`.
* Set the path to the cross-compiling libgccjit in `gcc_path`.
* Disable the 128-bit integer types if the target doesn't support them by using `let i128_type = context.new_type::<i64>();` in `context.rs` (same for u128_type).
* (might not be necessary) Disable the compilation of libstd.so (and possibly libcore.so?).
9 changes: 6 additions & 3 deletions compiler/rustc_codegen_gcc/config.sh
Original file line number Diff line number Diff line change
Expand Up @@ -21,12 +21,15 @@ fi

HOST_TRIPLE=$(rustc -vV | grep host | cut -d: -f2 | tr -d " ")
TARGET_TRIPLE=$HOST_TRIPLE
#TARGET_TRIPLE="aarch64-unknown-linux-gnu"
#TARGET_TRIPLE="m68k-unknown-linux-gnu"

linker=''
RUN_WRAPPER=''
if [[ "$HOST_TRIPLE" != "$TARGET_TRIPLE" ]]; then
if [[ "$TARGET_TRIPLE" == "aarch64-unknown-linux-gnu" ]]; then
if [[ "$TARGET_TRIPLE" == "m68k-unknown-linux-gnu" ]]; then
TARGET_TRIPLE="mips-unknown-linux-gnu"
linker='-Clinker=m68k-linux-gcc'
elif [[ "$TARGET_TRIPLE" == "aarch64-unknown-linux-gnu" ]]; then
# We are cross-compiling for aarch64. Use the correct linker and run tests in qemu.
linker='-Clinker=aarch64-linux-gnu-gcc'
RUN_WRAPPER='qemu-aarch64 -L /usr/aarch64-linux-gnu'
Expand All @@ -35,7 +38,7 @@ if [[ "$HOST_TRIPLE" != "$TARGET_TRIPLE" ]]; then
fi
fi

export RUSTFLAGS="$linker -Cpanic=abort -Cdebuginfo=2 -Clto=off -Zpanic-abort-tests -Zcodegen-backend=$(pwd)/target/${CHANNEL:-debug}/librustc_codegen_gcc.$dylib_ext --sysroot $(pwd)/build_sysroot/sysroot"
export RUSTFLAGS="$linker -Cpanic=abort -Zsymbol-mangling-version=v0 -Cdebuginfo=2 -Clto=off -Zpanic-abort-tests -Zcodegen-backend=$(pwd)/target/${CHANNEL:-debug}/librustc_codegen_gcc.$dylib_ext --sysroot $(pwd)/build_sysroot/sysroot"

# FIXME(antoyo): remove once the atomic shim is gone
if [[ `uname` == 'Darwin' ]]; then
Expand Down
2 changes: 1 addition & 1 deletion compiler/rustc_codegen_gcc/rust-toolchain
Original file line number Diff line number Diff line change
@@ -1 +1 @@
nightly-2021-09-17
nightly-2021-09-28
41 changes: 29 additions & 12 deletions compiler/rustc_codegen_gcc/src/asm.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ use rustc_codegen_ssa::traits::{AsmBuilderMethods, AsmMethods, BaseTypeMethods,

use rustc_hir::LlvmInlineAsmInner;
use rustc_middle::{bug, ty::Instance};
use rustc_span::Span;
use rustc_span::{Span, Symbol};
use rustc_target::asm::*;

use std::borrow::Cow;
Expand Down Expand Up @@ -173,7 +173,20 @@ impl<'a, 'gcc, 'tcx> AsmBuilderMethods<'tcx> for Builder<'a, 'gcc, 'tcx> {
continue
},
(Register(reg_name), None) => {
clobbers.push(reg_name);
// `clobber_abi` can add lots of clobbers that are not supported by the target,
// such as AVX-512 registers, so we just ignore unsupported registers
let is_target_supported = reg.reg_class().supported_types(asm_arch).iter()
.any(|&(_, feature)| {
if let Some(feature) = feature {
self.tcx.sess.target_features.contains(&Symbol::intern(feature))
} else {
true // Register class is unconditionally supported
}
});

if is_target_supported && !clobbers.contains(&reg_name) {
clobbers.push(reg_name);
}
continue
}
};
Expand Down Expand Up @@ -526,16 +539,20 @@ fn reg_to_gcc(reg: InlineAsmRegOrRegClass) -> ConstraintOrRegister {
let constraint = match reg {
// For vector registers LLVM wants the register name to match the type size.
InlineAsmRegOrRegClass::Reg(reg) => {
// TODO(antoyo): add support for vector register.
match reg.name() {
"ax" => "a",
"bx" => "b",
"cx" => "c",
"dx" => "d",
"si" => "S",
"di" => "D",
// For registers like r11, we have to create a register variable: https://stackoverflow.com/a/31774784/389119
name => return ConstraintOrRegister::Register(name),
match reg {
InlineAsmReg::X86(_) => {
// TODO(antoyo): add support for vector register.
//
// // For explicit registers, we have to create a register variable: https://stackoverflow.com/a/31774784/389119
return ConstraintOrRegister::Register(match reg.name() {
// Some of registers' names does not map 1-1 from rust to gcc
"st(0)" => "st",

name => name,
});
}

_ => unimplemented!(),
}
},
InlineAsmRegOrRegClass::RegClass(reg) => match reg {
Expand Down
15 changes: 1 addition & 14 deletions compiler/rustc_codegen_gcc/src/base.rs
Original file line number Diff line number Diff line change
@@ -1,13 +1,11 @@
use std::env;
use std::sync::Once;
use std::time::Instant;

use gccjit::{
Context,
FunctionType,
GlobalKind,
};
use rustc_hir::def_id::LOCAL_CRATE;
use rustc_middle::dep_graph;
use rustc_middle::middle::cstore::EncodedMetadata;
use rustc_middle::middle::exported_symbols;
Expand All @@ -20,7 +18,7 @@ use rustc_codegen_ssa::traits::DebugInfoMethods;
use rustc_session::config::DebugInfo;
use rustc_span::Symbol;

use crate::{GccContext, create_function_calling_initializers};
use crate::GccContext;
use crate::builder::Builder;
use crate::context::CodegenCx;

Expand Down Expand Up @@ -97,15 +95,6 @@ pub fn compile_codegen_unit<'tcx>(tcx: TyCtxt<'tcx>, cgu_name: Symbol) -> (Modul
{
let cx = CodegenCx::new(&context, cgu, tcx);

static START: Once = Once::new();
START.call_once(|| {
let initializer_name = format!("__gccGlobalCrateInit{}", tcx.crate_name(LOCAL_CRATE));
let func = context.new_function(None, FunctionType::Exported, context.new_type::<()>(), &[], initializer_name, false);
let block = func.new_block("initial");
create_function_calling_initializers(tcx, &context, block);
block.end_with_void_return(None);
});

let mono_items = cgu.items_in_deterministic_order(tcx);
for &(mono_item, (linkage, visibility)) in &mono_items {
mono_item.predefine::<Builder<'_, '_, '_>>(&cx, linkage, visibility);
Expand All @@ -124,8 +113,6 @@ pub fn compile_codegen_unit<'tcx>(tcx: TyCtxt<'tcx>, cgu_name: Symbol) -> (Modul
if cx.sess().opts.debuginfo != DebugInfo::None {
cx.debuginfo_finalize();
}

cx.global_init_block.end_with_void_return(None);
}

ModuleCodegen {
Expand Down
46 changes: 39 additions & 7 deletions compiler/rustc_codegen_gcc/src/builder.rs
Original file line number Diff line number Diff line change
Expand Up @@ -31,11 +31,12 @@ use rustc_codegen_ssa::traits::{
StaticBuilderMethods,
};
use rustc_middle::ty::{ParamEnv, Ty, TyCtxt};
use rustc_middle::ty::layout::{HasParamEnv, HasTyCtxt, LayoutError, LayoutOfHelpers, TyAndLayout};
use rustc_middle::ty::layout::{FnAbiError, FnAbiOfHelpers, FnAbiRequest, HasParamEnv, HasTyCtxt, LayoutError, LayoutOfHelpers, TyAndLayout};
use rustc_span::Span;
use rustc_span::def_id::DefId;
use rustc_target::abi::{
self,
call::FnAbi,
Align,
HasDataLayout,
Size,
Expand Down Expand Up @@ -347,6 +348,20 @@ impl<'tcx> LayoutOfHelpers<'tcx> for Builder<'_, '_, 'tcx> {
}
}

impl<'tcx> FnAbiOfHelpers<'tcx> for Builder<'_, '_, 'tcx> {
type FnAbiOfResult = &'tcx FnAbi<'tcx, Ty<'tcx>>;

#[inline]
fn handle_fn_abi_err(
&self,
err: FnAbiError<'tcx>,
span: Span,
fn_abi_request: FnAbiRequest<'tcx>,
) -> ! {
self.cx.handle_fn_abi_err(err, span, fn_abi_request)
}
}

impl<'gcc, 'tcx> Deref for Builder<'_, 'gcc, 'tcx> {
type Target = CodegenCx<'gcc, 'tcx>;

Expand Down Expand Up @@ -505,7 +520,6 @@ impl<'a, 'gcc, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'gcc, 'tcx> {
// FIXME(antoyo): rustc_codegen_ssa::mir::intrinsic uses different types for a and b but they
// should be the same.
let typ = a.get_type().to_signed(self);
let a = self.context.new_cast(None, a, typ);
let b = self.context.new_cast(None, b, typ);
a / b
}
Expand Down Expand Up @@ -1052,11 +1066,18 @@ impl<'a, 'gcc, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'gcc, 'tcx> {
}

/* Comparisons */
fn icmp(&mut self, op: IntPredicate, lhs: RValue<'gcc>, mut rhs: RValue<'gcc>) -> RValue<'gcc> {
if lhs.get_type() != rhs.get_type() {
fn icmp(&mut self, op: IntPredicate, mut lhs: RValue<'gcc>, mut rhs: RValue<'gcc>) -> RValue<'gcc> {
let left_type = lhs.get_type();
let right_type = rhs.get_type();
if left_type != right_type {
// NOTE: because libgccjit cannot compare function pointers.
if left_type.is_function_ptr_type().is_some() && right_type.is_function_ptr_type().is_some() {
lhs = self.context.new_cast(None, lhs, self.usize_type.make_pointer());
rhs = self.context.new_cast(None, rhs, self.usize_type.make_pointer());
}
// NOTE: hack because we try to cast a vector type to the same vector type.
if format!("{:?}", lhs.get_type()) != format!("{:?}", rhs.get_type()) {
rhs = self.context.new_cast(None, rhs, lhs.get_type());
else if format!("{:?}", left_type) != format!("{:?}", right_type) {
rhs = self.context.new_cast(None, rhs, left_type);
}
}
self.context.new_comparison(None, op.to_gcc_comparison(), lhs, rhs)
Expand Down Expand Up @@ -1210,6 +1231,17 @@ impl<'a, 'gcc, 'tcx> BuilderMethods<'a, 'tcx> for Builder<'a, 'gcc, 'tcx> {
else {
panic!("Unexpected type {:?}", value_type);
};

let lvalue_type = lvalue.to_rvalue().get_type();
let value =
// NOTE: sometimes, rustc will create a value with the wrong type.
if lvalue_type != value.get_type() {
self.context.new_cast(None, value, lvalue_type)
}
else {
value
};

self.llbb().add_assignment(None, lvalue, value);

aggregate_value
Expand Down Expand Up @@ -1413,7 +1445,7 @@ impl<'a, 'gcc, 'tcx> Builder<'a, 'gcc, 'tcx> {
impl<'a, 'gcc, 'tcx> StaticBuilderMethods for Builder<'a, 'gcc, 'tcx> {
fn get_static(&mut self, def_id: DefId) -> RValue<'gcc> {
// Forward to the `get_static` method of `CodegenCx`
self.cx().get_static(def_id)
self.cx().get_static(def_id).get_address(None)
}
}

Expand Down
Loading

0 comments on commit 7f32dd5

Please sign in to comment.