diff options
author | Keir Fraser <keir.fraser@citrix.com> | 2009-01-22 11:11:10 +0000 |
---|---|---|
committer | Keir Fraser <keir.fraser@citrix.com> | 2009-01-22 11:11:10 +0000 |
commit | 4a10e13111a0417d4c9f2d4ee2ce65955ef745d5 (patch) | |
tree | ab79bc92cfb65ab8c10bf7e29c388b52e421de4d /xen/arch/x86/microcode.c | |
parent | df29e279e265fbb2195124e31d0003064ecdc126 (diff) | |
download | xen-4a10e13111a0417d4c9f2d4ee2ce65955ef745d5.tar.gz xen-4a10e13111a0417d4c9f2d4ee2ce65955ef745d5.tar.bz2 xen-4a10e13111a0417d4c9f2d4ee2ce65955ef745d5.zip |
x86 ucode: microcode logic update
Update microcode logic:
1. separate microcode_fini_cpu() into 2 level to avoid deadlock (when
fail at microcode_update_cpu);
2. cancel redundant collect_cpu_info at microcode.c level, use
relative function at microcode driver level;
3. separate microcode_resume_cpu from microcode_update_cpu, because
it's redundant (should only be called when S3 wakeup) and will block newer
microcode update when user update newer microcode.dat from user level
Signed-off-by: Liu, Jinsong <jinsong.liu@intel.com>
Diffstat (limited to 'xen/arch/x86/microcode.c')
-rw-r--r-- | xen/arch/x86/microcode.c | 33 |
1 files changed, 12 insertions, 21 deletions
diff --git a/xen/arch/x86/microcode.c b/xen/arch/x86/microcode.c index b6eacda59b..80526a6103 100644 --- a/xen/arch/x86/microcode.c +++ b/xen/arch/x86/microcode.c @@ -49,25 +49,22 @@ struct microcode_info { char buffer[1]; }; -static void microcode_fini_cpu(int cpu) +static void __microcode_fini_cpu(int cpu) { struct ucode_cpu_info *uci = ucode_cpu_info + cpu; - spin_lock(µcode_mutex); xfree(uci->mc.mc_valid); - uci->mc.mc_valid = NULL; - spin_unlock(µcode_mutex); + memset(uci, 0, sizeof(*uci)); } -static int collect_cpu_info(int cpu) +static void microcode_fini_cpu(int cpu) { - struct ucode_cpu_info *uci = ucode_cpu_info + cpu; - - memset(uci, 0, sizeof(*uci)); - return microcode_ops->collect_cpu_info(cpu, &uci->cpu_sig); + spin_lock(µcode_mutex); + __microcode_fini_cpu(cpu); + spin_unlock(µcode_mutex); } -static int microcode_resume_cpu(int cpu) +int microcode_resume_cpu(int cpu) { int err = 0; struct ucode_cpu_info *uci = ucode_cpu_info + cpu; @@ -107,17 +104,11 @@ static int microcode_update_cpu(const void *buf, size_t size) spin_lock(µcode_mutex); - /* - * Check if the system resume is in progress (uci->mc.mc_valid != NULL), - * otherwise just request a firmware: - */ - if ( uci->mc.mc_valid ) { - err = microcode_resume_cpu(cpu); - } else { - err = collect_cpu_info(cpu); - if ( !err ) - err = microcode_ops->cpu_request_microcode(cpu, buf, size); - } + err = microcode_ops->collect_cpu_info(cpu, &uci->cpu_sig); + if ( likely(!err) ) + err = microcode_ops->cpu_request_microcode(cpu, buf, size); + else + __microcode_fini_cpu(cpu); spin_unlock(µcode_mutex); |