GNU Linux-libre 4.14.262-gnu1
[releases.git] / drivers / net / ethernet / huawei / hinic / hinic_hw_wq.h
1 /*
2  * Huawei HiNIC PCI Express Linux driver
3  * Copyright(c) 2017 Huawei Technologies Co., Ltd
4  *
5  * This program is free software; you can redistribute it and/or modify it
6  * under the terms and conditions of the GNU General Public License,
7  * version 2, as published by the Free Software Foundation.
8  *
9  * This program is distributed in the hope it will be useful, but WITHOUT
10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
12  * for more details.
13  *
14  */
15
16 #ifndef HINIC_HW_WQ_H
17 #define HINIC_HW_WQ_H
18
19 #include <linux/types.h>
20 #include <linux/semaphore.h>
21 #include <linux/atomic.h>
22
23 #include "hinic_hw_if.h"
24 #include "hinic_hw_wqe.h"
25
26 struct hinic_free_block {
27         int     page_idx;
28         int     block_idx;
29 };
30
31 struct hinic_wq {
32         struct hinic_hwif       *hwif;
33
34         int             page_idx;
35         int             block_idx;
36
37         u16             wqebb_size;
38         u16             wq_page_size;
39         u16             q_depth;
40         u16             max_wqe_size;
41         u16             num_wqebbs_per_page;
42
43         /* The addresses are 64 bit in the HW */
44         u64             block_paddr;
45         void            **shadow_block_vaddr;
46         u64             *block_vaddr;
47
48         int             num_q_pages;
49         u8              *shadow_wqe;
50         u16             *shadow_idx;
51
52         atomic_t        cons_idx;
53         atomic_t        prod_idx;
54         atomic_t        delta;
55         u16             mask;
56 };
57
58 struct hinic_wqs {
59         struct hinic_hwif       *hwif;
60         int                     num_pages;
61
62         /* The addresses are 64 bit in the HW */
63         u64                     *page_paddr;
64         u64                     **page_vaddr;
65         void                    ***shadow_page_vaddr;
66
67         struct hinic_free_block *free_blocks;
68         int                     alloc_blk_pos;
69         int                     return_blk_pos;
70         int                     num_free_blks;
71
72         /* Lock for getting a free block from the WQ set */
73         struct semaphore        alloc_blocks_lock;
74 };
75
76 struct hinic_cmdq_pages {
77         /* The addresses are 64 bit in the HW */
78         u64                     page_paddr;
79         u64                     *page_vaddr;
80         void                    **shadow_page_vaddr;
81
82         struct hinic_hwif       *hwif;
83 };
84
85 int hinic_wqs_cmdq_alloc(struct hinic_cmdq_pages *cmdq_pages,
86                          struct hinic_wq *wq, struct hinic_hwif *hwif,
87                          int cmdq_blocks, u16 wqebb_size, u16 wq_page_size,
88                          u16 q_depth, u16 max_wqe_size);
89
90 void hinic_wqs_cmdq_free(struct hinic_cmdq_pages *cmdq_pages,
91                          struct hinic_wq *wq, int cmdq_blocks);
92
93 int hinic_wqs_alloc(struct hinic_wqs *wqs, int num_wqs,
94                     struct hinic_hwif *hwif);
95
96 void hinic_wqs_free(struct hinic_wqs *wqs);
97
98 int hinic_wq_allocate(struct hinic_wqs *wqs, struct hinic_wq *wq,
99                       u16 wqebb_size, u16 wq_page_size, u16 q_depth,
100                       u16 max_wqe_size);
101
102 void hinic_wq_free(struct hinic_wqs *wqs, struct hinic_wq *wq);
103
104 struct hinic_hw_wqe *hinic_get_wqe(struct hinic_wq *wq, unsigned int wqe_size,
105                                    u16 *prod_idx);
106
107 void hinic_put_wqe(struct hinic_wq *wq, unsigned int wqe_size);
108
109 struct hinic_hw_wqe *hinic_read_wqe(struct hinic_wq *wq, unsigned int wqe_size,
110                                     u16 *cons_idx);
111
112 struct hinic_hw_wqe *hinic_read_wqe_direct(struct hinic_wq *wq, u16 cons_idx);
113
114 void hinic_write_wqe(struct hinic_wq *wq, struct hinic_hw_wqe *wqe,
115                      unsigned int wqe_size);
116
117 #endif