4 * Copyright(c) 2017 Cavium, Inc.. All rights reserved.
7 * Redistribution and use in source and binary forms, with or without
8 * modification, are permitted provided that the following conditions
11 * * Redistributions of source code must retain the above copyright
12 * notice, this list of conditions and the following disclaimer.
13 * * Redistributions in binary form must reproduce the above copyright
14 * notice, this list of conditions and the following disclaimer in
15 * the documentation and/or other materials provided with the
17 * * Neither the name of Cavium, Inc. nor the names of its
18 * contributors may be used to endorse or promote products derived
19 * from this software without specific prior written permission.
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
24 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
25 * OWNER(S) OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
26 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
27 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
28 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
29 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
30 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
31 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
34 #include <rte_ethdev.h>
35 #include <rte_cycles.h>
36 #include <rte_malloc.h>
39 #include "lio_struct.h"
40 #include "lio_ethdev.h"
44 lio_dma_zone_free(struct lio_device *lio_dev, const struct rte_memzone *mz)
46 const struct rte_memzone *mz_tmp;
50 lio_dev_err(lio_dev, "Memzone NULL\n");
54 mz_tmp = rte_memzone_lookup(mz->name);
56 lio_dev_err(lio_dev, "Memzone %s Not Found\n", mz->name);
60 ret = rte_memzone_free(mz);
62 lio_dev_err(lio_dev, "Memzone free Failed ret %d\n", ret);
66 * lio_init_instr_queue()
67 * @param lio_dev - pointer to the lio device structure.
68 * @param txpciq - queue to be initialized.
70 * Called at driver init time for each input queue. iq_conf has the
71 * configuration parameters for the queue.
73 * @return Success: 0 Failure: -1
76 lio_init_instr_queue(struct lio_device *lio_dev,
77 union octeon_txpciq txpciq,
78 uint32_t num_descs, unsigned int socket_id)
80 uint32_t iq_no = (uint32_t)txpciq.s.q_no;
81 struct lio_instr_queue *iq;
85 instr_type = LIO_IQ_INSTR_TYPE(lio_dev);
87 q_size = instr_type * num_descs;
88 iq = lio_dev->instr_queue[iq_no];
89 iq->iq_mz = rte_eth_dma_zone_reserve(lio_dev->eth_dev,
90 "instr_queue", iq_no, q_size,
93 if (iq->iq_mz == NULL) {
94 lio_dev_err(lio_dev, "Cannot allocate memory for instr queue %d\n",
99 iq->base_addr_dma = iq->iq_mz->phys_addr;
100 iq->base_addr = (uint8_t *)iq->iq_mz->addr;
102 iq->max_count = num_descs;
104 /* Initialize a list to holds requests that have been posted to Octeon
105 * but has yet to be fetched by octeon
107 iq->request_list = rte_zmalloc_socket("request_list",
108 sizeof(*iq->request_list) *
112 if (iq->request_list == NULL) {
113 lio_dev_err(lio_dev, "Alloc failed for IQ[%d] nr free list\n",
115 lio_dma_zone_free(lio_dev, iq->iq_mz);
119 lio_dev_dbg(lio_dev, "IQ[%d]: base: %p basedma: %lx count: %d\n",
120 iq_no, iq->base_addr, (unsigned long)iq->base_addr_dma,
123 iq->lio_dev = lio_dev;
124 iq->txpciq.txpciq64 = txpciq.txpciq64;
126 iq->host_write_index = 0;
127 iq->lio_read_index = 0;
130 rte_atomic64_set(&iq->instr_pending, 0);
132 /* Initialize the spinlock for this instruction queue */
133 rte_spinlock_init(&iq->lock);
134 rte_spinlock_init(&iq->post_lock);
136 rte_atomic64_clear(&iq->iq_flush_running);
138 lio_dev->io_qmask.iq |= (1ULL << iq_no);
140 /* Set the 32B/64B mode for each input queue */
141 lio_dev->io_qmask.iq64B |= ((instr_type == 64) << iq_no);
142 iq->iqcmd_64B = (instr_type == 64);
148 lio_setup_instr_queue0(struct lio_device *lio_dev)
150 union octeon_txpciq txpciq;
151 uint32_t num_descs = 0;
154 num_descs = LIO_NUM_DEF_TX_DESCS_CFG(lio_dev);
156 lio_dev->num_iqs = 0;
158 lio_dev->instr_queue[0] = rte_zmalloc(NULL,
159 sizeof(struct lio_instr_queue), 0);
160 if (lio_dev->instr_queue[0] == NULL)
163 lio_dev->instr_queue[0]->q_index = 0;
164 lio_dev->instr_queue[0]->app_ctx = (void *)(size_t)0;
166 txpciq.s.q_no = iq_no;
167 txpciq.s.pkind = lio_dev->pfvf_hsword.pkind;
168 txpciq.s.use_qpg = 0;
170 if (lio_init_instr_queue(lio_dev, txpciq, num_descs, SOCKET_ID_ANY)) {
171 rte_free(lio_dev->instr_queue[0]);
172 lio_dev->instr_queue[0] = NULL;
182 * lio_delete_instr_queue()
183 * @param lio_dev - pointer to the lio device structure.
184 * @param iq_no - queue to be deleted.
186 * Called at driver unload time for each input queue. Deletes all
187 * allocated resources for the input queue.
190 lio_delete_instr_queue(struct lio_device *lio_dev, uint32_t iq_no)
192 struct lio_instr_queue *iq = lio_dev->instr_queue[iq_no];
194 rte_free(iq->request_list);
195 iq->request_list = NULL;
196 lio_dma_zone_free(lio_dev, iq->iq_mz);
200 lio_free_instr_queue0(struct lio_device *lio_dev)
202 lio_delete_instr_queue(lio_dev, 0);
203 rte_free(lio_dev->instr_queue[0]);
204 lio_dev->instr_queue[0] = NULL;