<commit_before>use std::iter;

use rustc::mir;
use rustc::mir::interpret::{InterpResult, PointerArithmetic};
use rustc::ty;
use rustc::ty::layout::{self, Align, LayoutOf, Size};
use rustc_apfloat::Float;
use rustc_span::source_map::Span;

use crate::*;

impl<'mir, 'tcx> EvalContextExt<'mir, 'tcx> for crate::MiriEvalContext<'mir, 'tcx> {}
pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriEvalContextExt<'mir, 'tcx> {
    fn call_intrinsic(
        &mut self,
        span: Span,
        instance: ty::Instance<'tcx>,
        args: &[OpTy<'tcx, Tag>],
        ret: Option<(PlaceTy<'tcx, Tag>, mir::BasicBlock)>,
        unwind: Option<mir::BasicBlock>,
    ) -> InterpResult<'tcx> {
        let this = self.eval_context_mut();
        if this.emulate_intrinsic(span, instance, args, ret)? {
            return Ok(());
        }
        let tcx = &{ this.tcx.tcx };
        let substs = instance.substs;

        // All these intrinsics take raw pointers, so if we access memory directly
        // (as opposed to through a place), we have to remember to erase any tag
        // that might still hang around!
        let intrinsic_name = &*tcx.item_name(instance.def_id()).as_str();

        // First handle intrinsics without return place.
        let (dest, ret) = match ret {
            None => match intrinsic_name {
                "miri_start_panic" => return this.handle_miri_start_panic(args, unwind),
                "abort" => {
                    // FIXME: remove, once the intrinsic on the rustc side is fixed.
                    throw_machine_stop!(TerminationInfo::Abort);
                }
                _ => throw_unsup_format!("unimplemented (diverging) intrinsic: {}", intrinsic_name),
            },
            Some(p) => p,
        };

        match intrinsic_name {
            "try" => return this.handle_try(args, dest, ret),

            "arith_offset" => {
                let offset = this.read_scalar(args[1])?.to_machine_isize(this)?;
                let ptr = this.read_scalar(args[0])?.not_undef()?;

                let pointee_ty = substs.type_at(0);
                let pointee_size = this.layout_of(pointee_ty)?.size.bytes() as i64;
                let offset = offset.overflowing_mul(pointee_size).0;
                let result_ptr = ptr.ptr_wrapping_signed_offset(offset, this);
                this.write_scalar(result_ptr, dest)?;
            }

            "assume" => {
                let cond = this.read_scalar(args[0])?.to_bool()?;
                if !cond {<commit_msg>abort intrinsic is handled by librustc_mir now<commit_after>use std::iter;

use rustc::mir;
use rustc::mir::interpret::{InterpResult, PointerArithmetic};
use rustc::ty;
use rustc::ty::layout::{self, Align, LayoutOf, Size};
use rustc_apfloat::Float;
use rustc_span::source_map::Span;

use crate::*;

impl<'mir, 'tcx> EvalContextExt<'mir, 'tcx> for crate::MiriEvalContext<'mir, 'tcx> {}
pub trait EvalContextExt<'mir, 'tcx: 'mir>: crate::MiriEvalContextExt<'mir, 'tcx> {
    fn call_intrinsic(
        &mut self,
        span: Span,
        instance: ty::Instance<'tcx>,
        args: &[OpTy<'tcx, Tag>],
        ret: Option<(PlaceTy<'tcx, Tag>, mir::BasicBlock)>,
        unwind: Option<mir::BasicBlock>,
    ) -> InterpResult<'tcx> {
        let this = self.eval_context_mut();
        if this.emulate_intrinsic(span, instance, args, ret)? {
            return Ok(());
        }
        let tcx = &{ this.tcx.tcx };
        let substs = instance.substs;

        // All these intrinsics take raw pointers, so if we access memory directly
        // (as opposed to through a place), we have to remember to erase any tag
        // that might still hang around!
        let intrinsic_name = &*tcx.item_name(instance.def_id()).as_str();

        // First handle intrinsics without return place.
        let (dest, ret) = match ret {
            None => match intrinsic_name {
                "miri_start_panic" => return this.handle_miri_start_panic(args, unwind),
                _ => throw_unsup_format!("unimplemented (diverging) intrinsic: {}", intrinsic_name),
            },
            Some(p) => p,
        };

        match intrinsic_name {
            "try" => return this.handle_try(args, dest, ret),

            "arith_offset" => {
                let offset = this.read_scalar(args[1])?.to_machine_isize(this)?;
                let ptr = this.read_scalar(args[0])?.not_undef()?;

                let pointee_ty = substs.type_at(0);
                let pointee_size = this.layout_of(pointee_ty)?.size.bytes() as i64;
                let offset = offset.overflowing_mul(pointee_size).0;
                let result_ptr = ptr.ptr_wrapping_signed_offset(offset, this);
                this.write_scalar(result_ptr, dest)?;
            }

            "assume" => {
                let cond = this.read_scalar(args[0])?.to_bool()?;
                if !cond {
{'fraction_non_alphanumeric': 0.1331833060556465, 'fraction_numerical': 0.0028641571194762683, 'mean_word_length': 2.350925291295408, 'pattern_counts': {'":': 0, '<': 25, '<?xml version=': 0, '>': 42, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '4192129', 'n_tokens_mistral': 1521, 'n_tokens_neox': 1524, 'n_words': 345}