en_cq.c revision cd3109d23c32452c85d73cc1a01282846a23582c
1c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin/* 2c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * Copyright (c) 2007 Mellanox Technologies. All rights reserved. 3c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * 4c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * This software is available to you under a choice of one of two 5c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * licenses. You may choose to be licensed under the terms of the GNU 6c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * General Public License (GPL) Version 2, available from the file 7c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * COPYING in the main directory of this source tree, or the 8c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * OpenIB.org BSD license below: 9c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * 10c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * Redistribution and use in source and binary forms, with or 11c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * without modification, are permitted provided that the following 12c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * conditions are met: 13c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * 14c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * - Redistributions of source code must retain the above 15c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * copyright notice, this list of conditions and the following 16c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * disclaimer. 17c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * 18c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * - Redistributions in binary form must reproduce the above 19c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * copyright notice, this list of conditions and the following 20c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * disclaimer in the documentation and/or other materials 21c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * provided with the distribution. 22c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * 23c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, 24c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 25c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 26c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS 27c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN 28c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 29c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 30c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * SOFTWARE. 31c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin * 32c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin */ 33c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 34c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin#include <linux/mlx4/cq.h> 35c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin#include <linux/mlx4/qp.h> 36c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin#include <linux/mlx4/cmd.h> 37c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 38c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin#include "mlx4_en.h" 39c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 40c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilinstatic void mlx4_en_cq_event(struct mlx4_cq *cq, enum mlx4_event event) 41c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin{ 42c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin return; 43c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin} 44c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 45c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 46c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilinint mlx4_en_create_cq(struct mlx4_en_priv *priv, 47c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin struct mlx4_en_cq *cq, 48c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin int entries, int ring, enum cq_type mode) 49c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin{ 50c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin struct mlx4_en_dev *mdev = priv->mdev; 51c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin int err; 52c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 53c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->size = entries; 541fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin if (mode == RX) 55c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->buf_size = cq->size * sizeof(struct mlx4_cqe); 561fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin else 57c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->buf_size = sizeof(struct mlx4_cqe); 58c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 59c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->ring = ring; 60c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->is_tx = mode; 61c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin spin_lock_init(&cq->lock); 62c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 63c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin err = mlx4_alloc_hwq_res(mdev->dev, &cq->wqres, 64c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->buf_size, 2 * PAGE_SIZE); 65c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin if (err) 66c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin return err; 67c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 68c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin err = mlx4_en_map_buffer(&cq->wqres.buf); 69c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin if (err) 70c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin mlx4_free_hwq_res(mdev->dev, &cq->wqres, cq->buf_size); 71b51968d676db1c4e541b4c84de7ce7af812c9e9fYevgeny Petrilin else 72b51968d676db1c4e541b4c84de7ce7af812c9e9fYevgeny Petrilin cq->buf = (struct mlx4_cqe *) cq->wqres.buf.direct.buf; 73c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 74c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin return err; 75c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin} 76c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 7776532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Gullerint mlx4_en_activate_cq(struct mlx4_en_priv *priv, struct mlx4_en_cq *cq, 7876532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller int cq_idx) 79c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin{ 80c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin struct mlx4_en_dev *mdev = priv->mdev; 811fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin int err = 0; 821fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin char name[25]; 83c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 84c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->dev = mdev->pndev[priv->port]; 85c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->mcq.set_ci_db = cq->wqres.db.db; 86c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->mcq.arm_db = cq->wqres.db.db + 1; 87c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin *cq->mcq.set_ci_db = 0; 88c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin *cq->mcq.arm_db = 0; 89c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin memset(cq->buf, 0, cq->buf_size); 90c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 911fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin if (cq->is_tx == RX) { 921fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin if (mdev->dev->caps.comp_pool) { 931fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin if (!cq->vector) { 9476532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller sprintf(name, "%s-%d", priv->dev->name, 9576532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller cq->ring); 9676532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller /* Set IRQ for specific name (per ring) */ 971fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin if (mlx4_assign_eq(mdev->dev, name, &cq->vector)) { 9876532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller cq->vector = (cq->ring + 1 + priv->port) 9976532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller % mdev->dev->caps.num_comp_vectors; 1001fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin mlx4_warn(mdev, "Failed Assigning an EQ to " 10176532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller "%s ,Falling back to legacy EQ's\n", 10276532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller name); 1031fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin } 1041fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin } 1051fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin } else { 1061fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin cq->vector = (cq->ring + 1 + priv->port) % 1071fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin mdev->dev->caps.num_comp_vectors; 1081fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin } 1091fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin } else { 11076532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller /* For TX we use the same irq per 11176532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller ring we assigned for the RX */ 11276532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller struct mlx4_en_cq *rx_cq; 11376532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller 11476532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller cq_idx = cq_idx % priv->rx_ring_num; 11576532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller rx_cq = &priv->rx_cq[cq_idx]; 11676532d0c7e7424914ab6f24683c63e50f0a08f1cAlexander Guller cq->vector = rx_cq->vector; 1171fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin } 1181fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin 11938aab07c14adbf3c7257793d764a91923341e96aYevgeny Petrilin if (!cq->is_tx) 12038aab07c14adbf3c7257793d764a91923341e96aYevgeny Petrilin cq->size = priv->rx_ring[cq->ring].actual_size; 12138aab07c14adbf3c7257793d764a91923341e96aYevgeny Petrilin 122c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin err = mlx4_cq_alloc(mdev->dev, cq->size, &cq->wqres.mtt, &mdev->priv_uar, 123b8dd786f9417e5885929bfe33a235c76a9c1c569Yevgeny Petrilin cq->wqres.db.dma, &cq->mcq, cq->vector, cq->is_tx); 124c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin if (err) 125c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin return err; 126c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 127c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->mcq.comp = cq->is_tx ? mlx4_en_tx_irq : mlx4_en_rx_irq; 128c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->mcq.event = mlx4_en_cq_event; 129c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 130c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin if (cq->is_tx) { 131c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin init_timer(&cq->timer); 132c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->timer.function = mlx4_en_poll_tx_cq; 133c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->timer.data = (unsigned long) cq; 134c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin } else { 135c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin netif_napi_add(cq->dev, &cq->napi, mlx4_en_poll_rx_cq, 64); 136c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin napi_enable(&cq->napi); 137c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin } 138c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 139c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin return 0; 140c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin} 141c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 142fe0af03c69abc2178fc4667664726ec1f688539bAlexander Gullervoid mlx4_en_destroy_cq(struct mlx4_en_priv *priv, struct mlx4_en_cq *cq) 143c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin{ 144c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin struct mlx4_en_dev *mdev = priv->mdev; 145c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 146c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin mlx4_en_unmap_buffer(&cq->wqres.buf); 147c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin mlx4_free_hwq_res(mdev->dev, &cq->wqres, cq->buf_size); 148fe0af03c69abc2178fc4667664726ec1f688539bAlexander Guller if (priv->mdev->dev->caps.comp_pool && cq->vector) 1491fb9876e9bf895ea4127ff17180f1b2ab37771b6Yevgeny Petrilin mlx4_release_eq(priv->mdev->dev, cq->vector); 150cd3109d23c32452c85d73cc1a01282846a23582cYevgeny Petrilin cq->vector = 0; 151c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->buf_size = 0; 152c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->buf = NULL; 153c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin} 154c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 155c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilinvoid mlx4_en_deactivate_cq(struct mlx4_en_priv *priv, struct mlx4_en_cq *cq) 156c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin{ 157c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin struct mlx4_en_dev *mdev = priv->mdev; 158c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 159c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin if (cq->is_tx) 160c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin del_timer(&cq->timer); 16172876a603422d3767273ffb3918033fa1bfda0f3Yevgeny Petrilin else { 162c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin napi_disable(&cq->napi); 16372876a603422d3767273ffb3918033fa1bfda0f3Yevgeny Petrilin netif_napi_del(&cq->napi); 16472876a603422d3767273ffb3918033fa1bfda0f3Yevgeny Petrilin } 165c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 166c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin mlx4_cq_free(mdev->dev, &cq->mcq); 167c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin} 168c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 169c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin/* Set rx cq moderation parameters */ 170c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilinint mlx4_en_set_cq_moder(struct mlx4_en_priv *priv, struct mlx4_en_cq *cq) 171c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin{ 172c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin return mlx4_cq_modify(priv->mdev->dev, &cq->mcq, 173c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin cq->moder_cnt, cq->moder_time); 174c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin} 175c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 176c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilinint mlx4_en_arm_cq(struct mlx4_en_priv *priv, struct mlx4_en_cq *cq) 177c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin{ 178c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin mlx4_cq_arm(&cq->mcq, MLX4_CQ_DB_REQ_NOT, priv->mdev->uar_map, 179c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin &priv->mdev->uar_lock); 180c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 181c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin return 0; 182c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin} 183c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 184c27a02cd94d6695fbe5858ca364b1e415af02212Yevgeny Petrilin 185