示例#1
0
bool XenDriver::mtrrType( unsigned long long guestAddress, uint8_t &type ) const throw()
{
	const uint8_t MTRR_TYPE_UNCACHABLE = 0;
	const uint8_t MTRR_TYPE_WRTHROUGH = 4;

	int32_t seg, index;
	uint8_t overlap_mtrr = 0, overlap_mtrr_pos = 0;

	static bool hwMtrrInit = false;
	static struct hvm_hw_mtrr hwMtrr;

	if ( !hwMtrrInit ) {
		StatsCollector::instance().incStat( "partialContext" );
		StatsCollector::instance().incStat( "partialMtrr" );
		if ( xc_domain_hvm_getcontext_partial( xci_, domain_, HVM_SAVE_CODE( MTRR ), 0, &hwMtrr,
		                                       sizeof( hwMtrr ) ) != 0 ) {

			if ( logHelper_ )
				logHelper_->error( std::string( "xc_domain_hvm_getcontext_partial() failed: " ) +
				                   strerror( errno ) );

			return false;
		} else
			hwMtrrInit = true;
	}

	uint8_t def_type = hwMtrr.msr_mtrr_def_type & 0xff;
	uint8_t enabled = hwMtrr.msr_mtrr_def_type >> 10;
	uint8_t *u8_fixed = ( uint8_t * )hwMtrr.msr_mtrr_fixed;

	if ( !( enabled & 0x2 ) ) {
		type = MTRR_TYPE_UNCACHABLE;
		return true;
	}

	if ( ( guestAddress < 0x100000 ) && ( enabled & 1 ) ) {

		/* Fixed range MTRR takes effective */
		int32_t addr = ( uint32_t )guestAddress;

		if ( addr < 0x80000 ) {
			seg = ( addr >> 16 );
			return u8_fixed[seg];
		} else if ( addr < 0xc0000 ) {
示例#2
0
unsigned long xc_translate_foreign_address(int xc_handle, uint32_t dom,
                                           int vcpu, unsigned long long virt)
{
    xc_dominfo_t dominfo;
    uint64_t paddr, mask, pte = 0;
    int size, level, pt_levels = 2;
    void *map;

    if (xc_domain_getinfo(xc_handle, dom, 1, &dominfo) != 1 
        || dominfo.domid != dom)
        return 0;

    /* What kind of paging are we dealing with? */
    if (dominfo.hvm) {
        struct hvm_hw_cpu ctx;
        if (xc_domain_hvm_getcontext_partial(xc_handle, dom,
                                             HVM_SAVE_CODE(CPU), vcpu,
                                             &ctx, sizeof ctx) != 0)
            return 0;
        if (!(ctx.cr0 & CR0_PG))
            return virt >> PAGE_SHIFT;
        pt_levels = (ctx.msr_efer&EFER_LMA) ? 4 : (ctx.cr4&CR4_PAE) ? 3 : 2;
        paddr = ctx.cr3 & ((pt_levels == 3) ? ~0x1full : ~0xfffull);
    } else {