• Andrea Parri (Microsoft)'s avatar
    Drivers: hv: vmbus: Replace the per-CPU channel lists with a global array of channels · 8b6a877c
    Andrea Parri (Microsoft) authored
    When Hyper-V sends an interrupt to the guest, the guest has to figure
    out which channel the interrupt is associated with.  Hyper-V sets a bit
    in a memory page that is shared with the guest, indicating a particular
    "relid" that the interrupt is associated with.  The current Linux code
    then uses a set of per-CPU linked lists to map a given "relid" to a
    pointer to a channel structure.
    
    This design introduces a synchronization problem if the CPU that Hyper-V
    will interrupt for a certain channel is changed.  If the interrupt comes
    on the "old CPU" and the channel was already moved to the per-CPU list
    of the "new CPU", then the relid -> channel mapping will fail and the
    interrupt is dropped.  Similarly, if the interrupt comes on the new CPU
    but the channel was not moved to the per-CPU list of the new CPU, then
    the mapping will fail and the interrupt is dropped.
    
    Relids are integers ranging from 0 to 2047.  The mapping from relids to
    channel structures can be done by setting up an array with 2048 entries,
    each entry being a pointer to a channel structure (hence total size ~16K
    bytes, which is not a problem).  The array is global, so there are no
    per-CPU linked lists to update.  The array can be searched and updated
    by loading from/storing to the array at the specified index.  With no
    per-CPU data structures, the above mentioned synchronization problem is
    avoided and the relid2channel() function gets simpler.
    Suggested-by: default avatarMichael Kelley <mikelley@microsoft.com>
    Signed-off-by: default avatarAndrea Parri (Microsoft) <parri.andrea@gmail.com>
    Link: https://lore.kernel.org/r/20200406001514.19876-4-parri.andrea@gmail.comReviewed-by: default avatarMichael Kelley <mikelley@microsoft.com>
    Signed-off-by: default avatarWei Liu <wei.liu@kernel.org>
    8b6a877c
vmbus_drv.c 64.9 KB