On Mon, 2 Jul 2018 at 19:32, Paolo Bonzini <pbonzini@xxxxxxxxxx> wrote: > > On 02/07/2018 12:14, Wanpeng Li wrote: > > + unsigned long flags, ipi_bitmap_low = 0, ipi_bitmap_high = 0, icr = 0; > > + int cpu, apic_id, ret = 1; > > + > > + if (cpumask_empty(mask)) > > + return true; > > + > > + local_irq_save(flags); > > + > > + for_each_cpu(cpu, mask) { > > + apic_id = per_cpu(x86_cpu_to_apicid, cpu); > > + if (apic_id < BITS_PER_LONG) > > + __set_bit(apic_id, &ipi_bitmap_low); > > + else if (apic_id < 2 * BITS_PER_LONG) > > + __set_bit(apic_id - BITS_PER_LONG, &ipi_bitmap_high); > > + else > > + goto ipi_mask_done; > > + } > > CPU masks are themselves bitmaps made of longs, so you should be able to > avoid the loop here. As we discuss offline, loop is needed since I need to convert processor id which is allocated by OS to apic id. > > > +static void kvm_send_ipi_mask(const struct cpumask *mask, int vector) > > +{ > > + if (!__send_ipi_mask(mask, vector)) > > + orig_apic.send_IPI_mask(mask, vector); > > +} > > + > > +static void kvm_send_ipi_mask_allbutself(const struct cpumask *mask, int vector) > > +{ > > + unsigned int this_cpu = smp_processor_id(); > > + struct cpumask new_mask; > > + const struct cpumask *local_mask; > > + > > + cpumask_copy(&new_mask, mask); > > + cpumask_clear_cpu(this_cpu, &new_mask); > > + local_mask = &new_mask; > > + if (!__send_ipi_mask(local_mask, vector)) > > + orig_apic.send_IPI_mask_allbutself(mask, vector); > > +} > > Likewise, here it should be possible to check the highest bit in the > mask before copying it. __send_ipi_mask() has already handled sparse APIC ID and > 128 APID ID scenarios. Regards, Wanpeng Li