habanalabs: fix completion queue handling when host is BE
This patch fix the CQ irq handler to work in hosts with BE architecture. It adds the correct endian-swapping macros around the relevant memory accesses. Signed-off-by: Ben Segal <bpsegal20@gmail.com> Reviewed-by: Oded Gabbay <oded.gabbay@gmail.com> Signed-off-by: Oded Gabbay <oded.gabbay@gmail.com>
This commit is contained in:
parent
213ad5ad01
commit
4e87334a0e
|
@ -80,8 +80,7 @@ irqreturn_t hl_irq_handler_cq(int irq, void *arg)
|
||||||
struct hl_cs_job *job;
|
struct hl_cs_job *job;
|
||||||
bool shadow_index_valid;
|
bool shadow_index_valid;
|
||||||
u16 shadow_index;
|
u16 shadow_index;
|
||||||
u32 *cq_entry;
|
struct hl_cq_entry *cq_entry, *cq_base;
|
||||||
u32 *cq_base;
|
|
||||||
|
|
||||||
if (hdev->disabled) {
|
if (hdev->disabled) {
|
||||||
dev_dbg(hdev->dev,
|
dev_dbg(hdev->dev,
|
||||||
|
@ -90,29 +89,29 @@ irqreturn_t hl_irq_handler_cq(int irq, void *arg)
|
||||||
return IRQ_HANDLED;
|
return IRQ_HANDLED;
|
||||||
}
|
}
|
||||||
|
|
||||||
cq_base = (u32 *) (uintptr_t) cq->kernel_address;
|
cq_base = (struct hl_cq_entry *) (uintptr_t) cq->kernel_address;
|
||||||
|
|
||||||
while (1) {
|
while (1) {
|
||||||
bool entry_ready = ((cq_base[cq->ci] & CQ_ENTRY_READY_MASK)
|
bool entry_ready = ((le32_to_cpu(cq_base[cq->ci].data) &
|
||||||
|
CQ_ENTRY_READY_MASK)
|
||||||
>> CQ_ENTRY_READY_SHIFT);
|
>> CQ_ENTRY_READY_SHIFT);
|
||||||
|
|
||||||
if (!entry_ready)
|
if (!entry_ready)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
cq_entry = (u32 *) &cq_base[cq->ci];
|
cq_entry = (struct hl_cq_entry *) &cq_base[cq->ci];
|
||||||
|
|
||||||
/*
|
/* Make sure we read CQ entry contents after we've
|
||||||
* Make sure we read CQ entry contents after we've
|
|
||||||
* checked the ownership bit.
|
* checked the ownership bit.
|
||||||
*/
|
*/
|
||||||
dma_rmb();
|
dma_rmb();
|
||||||
|
|
||||||
shadow_index_valid =
|
shadow_index_valid = ((le32_to_cpu(cq_entry->data) &
|
||||||
((*cq_entry & CQ_ENTRY_SHADOW_INDEX_VALID_MASK)
|
CQ_ENTRY_SHADOW_INDEX_VALID_MASK)
|
||||||
>> CQ_ENTRY_SHADOW_INDEX_VALID_SHIFT);
|
>> CQ_ENTRY_SHADOW_INDEX_VALID_SHIFT);
|
||||||
|
|
||||||
shadow_index = (u16)
|
shadow_index = (u16) ((le32_to_cpu(cq_entry->data) &
|
||||||
((*cq_entry & CQ_ENTRY_SHADOW_INDEX_MASK)
|
CQ_ENTRY_SHADOW_INDEX_MASK)
|
||||||
>> CQ_ENTRY_SHADOW_INDEX_SHIFT);
|
>> CQ_ENTRY_SHADOW_INDEX_SHIFT);
|
||||||
|
|
||||||
queue = &hdev->kernel_queues[cq->hw_queue_id];
|
queue = &hdev->kernel_queues[cq->hw_queue_id];
|
||||||
|
@ -122,8 +121,7 @@ irqreturn_t hl_irq_handler_cq(int irq, void *arg)
|
||||||
queue_work(hdev->cq_wq, &job->finish_work);
|
queue_work(hdev->cq_wq, &job->finish_work);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/* Update ci of the context's queue. There is no
|
||||||
* Update ci of the context's queue. There is no
|
|
||||||
* need to protect it with spinlock because this update is
|
* need to protect it with spinlock because this update is
|
||||||
* done only inside IRQ and there is a different IRQ per
|
* done only inside IRQ and there is a different IRQ per
|
||||||
* queue
|
* queue
|
||||||
|
@ -131,7 +129,8 @@ irqreturn_t hl_irq_handler_cq(int irq, void *arg)
|
||||||
queue->ci = hl_queue_inc_ptr(queue->ci);
|
queue->ci = hl_queue_inc_ptr(queue->ci);
|
||||||
|
|
||||||
/* Clear CQ entry ready bit */
|
/* Clear CQ entry ready bit */
|
||||||
cq_base[cq->ci] &= ~CQ_ENTRY_READY_MASK;
|
cq_entry->data = cpu_to_le32(le32_to_cpu(cq_entry->data) &
|
||||||
|
~CQ_ENTRY_READY_MASK);
|
||||||
|
|
||||||
cq->ci = hl_cq_inc_ptr(cq->ci);
|
cq->ci = hl_cq_inc_ptr(cq->ci);
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue