diff options
| author | Stanislav Sedov <stas@FreeBSD.org> | 2009-08-15 16:15:50 +0000 |
|---|---|---|
| committer | Stanislav Sedov <stas@FreeBSD.org> | 2009-08-15 16:15:50 +0000 |
| commit | b966e2259cbae4b6cafcfeee614a95fd01442757 (patch) | |
| tree | 4b7d79c509c0a3d1928add825322245c92d28449 /sys/dev | |
| parent | 0c733d2a0b235d7e5bbb9bb0fa51587f490385c5 (diff) | |
Notes
Diffstat (limited to 'sys/dev')
| -rw-r--r-- | sys/dev/cpuctl/cpuctl.c | 20 |
1 files changed, 18 insertions, 2 deletions
diff --git a/sys/dev/cpuctl/cpuctl.c b/sys/dev/cpuctl/cpuctl.c index b0b24b4bea8c..418a3d449e6d 100644 --- a/sys/dev/cpuctl/cpuctl.c +++ b/sys/dev/cpuctl/cpuctl.c @@ -159,6 +159,8 @@ cpuctl_ioctl(struct cdev *dev, u_long cmd, caddr_t data, case CPUCTL_RDMSR: ret = cpuctl_do_msr(cpu, (cpuctl_msr_args_t *)data, cmd, td); break; + case CPUCTL_MSRSBIT: + case CPUCTL_MSRCBIT: case CPUCTL_WRMSR: ret = priv_check(td, PRIV_CPUCTL_WRMSR); if (ret != 0) @@ -212,6 +214,7 @@ cpuctl_do_cpuid(int cpu, cpuctl_cpuid_args_t *data, struct thread *td) static int cpuctl_do_msr(int cpu, cpuctl_msr_args_t *data, u_long cmd, struct thread *td) { + uint64_t reg; int is_bound = 0; int oldcpu; int ret; @@ -231,9 +234,22 @@ cpuctl_do_msr(int cpu, cpuctl_msr_args_t *data, u_long cmd, struct thread *td) if (cmd == CPUCTL_RDMSR) { data->data = 0; ret = rdmsr_safe(data->msr, &data->data); - } else { + } else if (cmd == CPUCTL_WRMSR) { ret = wrmsr_safe(data->msr, data->data); - } + } else if (cmd == CPUCTL_MSRSBIT) { + critical_enter(); + ret = rdmsr_safe(data->msr, ®); + if (ret == 0) + ret = wrmsr_safe(data->msr, reg | data->data); + critical_exit(); + } else if (cmd == CPUCTL_MSRCBIT) { + critical_enter(); + ret = rdmsr_safe(data->msr, ®); + if (ret == 0) + ret = wrmsr_safe(data->msr, reg & ~data->data); + critical_exit(); + } else + panic("[cpuctl,%d]: unknown operation requested: %lu", __LINE__, cmd); restore_cpu(oldcpu, is_bound, td); return (ret); } |
