aboutsummaryrefslogtreecommitdiffstats
path: root/arch/x86
diff options
context:
space:
mode:
authorTakuya Yoshikawa <yoshikawa.takuya@oss.ntt.co.jp>2012-09-05 06:30:01 -0400
committerMarcelo Tosatti <mtosatti@redhat.com>2012-09-12 12:38:23 -0400
commitecba9a52acdf20530d561b7634b80c35c308943a (patch)
tree8a8ef1bd20dd24b4181acab240906da6978c117f /arch/x86
parent7de5bdc96c372ab875408c86e0099958dba89f56 (diff)
KVM: x86: lapic: Clean up find_highest_vector() and count_vectors()
find_highest_vector() and count_vectors(): - Instead of using magic values, define and use proper macros. find_highest_vector(): - Remove likely() which is there only for historical reasons and not doing correct branch predictions anymore. Using such heuristics to optimize this function is not worth it now. Let CPUs predict things instead. - Stop checking word[0] separately. This was only needed for doing likely() optimization. - Use for loop, not while, to iterate over the register array to make the code clearer. Note that we actually confirmed that the likely() did wrong predictions by inserting debug code. Acked-by: Michael S. Tsirkin <mst@redhat.com> Signed-off-by: Takuya Yoshikawa <yoshikawa.takuya@oss.ntt.co.jp> Signed-off-by: Marcelo Tosatti <mtosatti@redhat.com>
Diffstat (limited to 'arch/x86')
-rw-r--r--arch/x86/kvm/lapic.c30
1 files changed, 18 insertions, 12 deletions
diff --git a/arch/x86/kvm/lapic.c b/arch/x86/kvm/lapic.c
index 07ad628dadb..6f9fd633c88 100644
--- a/arch/x86/kvm/lapic.c
+++ b/arch/x86/kvm/lapic.c
@@ -66,6 +66,7 @@
66#define APIC_DEST_NOSHORT 0x0 66#define APIC_DEST_NOSHORT 0x0
67#define APIC_DEST_MASK 0x800 67#define APIC_DEST_MASK 0x800
68#define MAX_APIC_VECTOR 256 68#define MAX_APIC_VECTOR 256
69#define APIC_VECTORS_PER_REG 32
69 70
70#define VEC_POS(v) ((v) & (32 - 1)) 71#define VEC_POS(v) ((v) & (32 - 1))
71#define REG_POS(v) (((v) >> 5) << 4) 72#define REG_POS(v) (((v) >> 5) << 4)
@@ -208,25 +209,30 @@ static const unsigned int apic_lvt_mask[APIC_LVT_NUM] = {
208 209
209static int find_highest_vector(void *bitmap) 210static int find_highest_vector(void *bitmap)
210{ 211{
211 u32 *word = bitmap; 212 int vec;
212 int word_offset = MAX_APIC_VECTOR >> 5; 213 u32 *reg;
213 214
214 while ((word_offset != 0) && (word[(--word_offset) << 2] == 0)) 215 for (vec = MAX_APIC_VECTOR - APIC_VECTORS_PER_REG;
215 continue; 216 vec >= 0; vec -= APIC_VECTORS_PER_REG) {
217 reg = bitmap + REG_POS(vec);
218 if (*reg)
219 return fls(*reg) - 1 + vec;
220 }
216 221
217 if (likely(!word_offset && !word[0])) 222 return -1;
218 return -1;
219 else
220 return fls(word[word_offset << 2]) - 1 + (word_offset << 5);
221} 223}
222 224
223static u8 count_vectors(void *bitmap) 225static u8 count_vectors(void *bitmap)
224{ 226{
225 u32 *word = bitmap; 227 int vec;
226 int word_offset; 228 u32 *reg;
227 u8 count = 0; 229 u8 count = 0;
228 for (word_offset = 0; word_offset < MAX_APIC_VECTOR >> 5; ++word_offset) 230
229 count += hweight32(word[word_offset << 2]); 231 for (vec = 0; vec < MAX_APIC_VECTOR; vec += APIC_VECTORS_PER_REG) {
232 reg = bitmap + REG_POS(vec);
233 count += hweight32(*reg);
234 }
235
230 return count; 236 return count;
231} 237}
232 238