Beispiel #1
0
static void ppro_setup_ctrs(struct op_x86_model_spec const *model,
                            struct op_msrs const * const msrs)
{
    u64 val;
    int i;

    if (!reset_value) {
        reset_value = kzalloc(sizeof(reset_value[0]) * num_counters,
                              GFP_ATOMIC);
        if (!reset_value)
            return;
    }

    if (cpu_has_arch_perfmon) {
        union cpuid10_eax eax;
        eax.full = cpuid_eax(0xa);

        /*
         * For Core2 (family 6, model 15), don't reset the
         * counter width:
         */
        if (!(eax.split.version_id == 0 &&
                current_cpu_data.x86 == 6 &&
                current_cpu_data.x86_model == 15)) {

            if (counter_width < eax.split.bit_width)
                counter_width = eax.split.bit_width;
        }
    }

    /* clear all counters */
    for (i = 0; i < num_counters; ++i) {
        if (!msrs->controls[i].addr)
            continue;
        rdmsrl(msrs->controls[i].addr, val);
        if (val & ARCH_PERFMON_EVENTSEL_ENABLE)
            op_x86_warn_in_use(i);
        val &= model->reserved;
        wrmsrl(msrs->controls[i].addr, val);
        /*
         * avoid a false detection of ctr overflows in NMI *
         * handler
         */
        wrmsrl(msrs->counters[i].addr, -1LL);
    }

    /* enable active counters */
    for (i = 0; i < num_counters; ++i) {
        if (counter_config[i].enabled && msrs->counters[i].addr) {
            reset_value[i] = counter_config[i].count;
            wrmsrl(msrs->counters[i].addr, -reset_value[i]);
            rdmsrl(msrs->controls[i].addr, val);
            val &= model->reserved;
            val |= op_x86_get_ctrl(model, &counter_config[i]);
            wrmsrl(msrs->controls[i].addr, val);
        } else {
            reset_value[i] = 0;
        }
    }
}
static void ppro_setup_ctrs(struct op_x86_model_spec const *model,
			    struct op_msrs const * const msrs)
{
	u64 val;
	int i;

	if (cpu_has_arch_perfmon) {
		union cpuid10_eax eax;
		eax.full = cpuid_eax(0xa);

		if (!(eax.split.version_id == 0 &&
			__this_cpu_read(cpu_info.x86) == 6 &&
				__this_cpu_read(cpu_info.x86_model) == 15)) {

			if (counter_width < eax.split.bit_width)
				counter_width = eax.split.bit_width;
		}
	}

	
	for (i = 0; i < num_counters; ++i) {
		if (!msrs->controls[i].addr)
			continue;
		rdmsrl(msrs->controls[i].addr, val);
		if (val & ARCH_PERFMON_EVENTSEL_ENABLE)
			op_x86_warn_in_use(i);
		val &= model->reserved;
		wrmsrl(msrs->controls[i].addr, val);
		wrmsrl(msrs->counters[i].addr, -1LL);
	}

	
	for (i = 0; i < num_counters; ++i) {
		if (counter_config[i].enabled && msrs->counters[i].addr) {
			reset_value[i] = counter_config[i].count;
			wrmsrl(msrs->counters[i].addr, -reset_value[i]);
			rdmsrl(msrs->controls[i].addr, val);
			val &= model->reserved;
			val |= op_x86_get_ctrl(model, &counter_config[i]);
			wrmsrl(msrs->controls[i].addr, val);
		} else {
			reset_value[i] = 0;
		}
	}
}