david/ipxe
david
/
ipxe
Archived
1
0
Fork 0

[golan] Add Connect-IB, ConnectX-4 and ConnectX-4 Lx (Infiniband) support

Signed-off-by: Wissam Shoukair <wissams@mellanox.com>
Signed-off-by: Michael Brown <mcb30@ipxe.org>
This commit is contained in:
Wissam Shoukair 2016-03-21 15:09:13 +02:00 committed by Michael Brown
parent 3df598849b
commit 0a20373a2f
57 changed files with 13097 additions and 0 deletions

View File

@ -84,6 +84,14 @@ SRCDIRS += drivers/block
SRCDIRS += drivers/nvs
SRCDIRS += drivers/bitbash
SRCDIRS += drivers/infiniband
SRCDIRS += drivers/infiniband/mlx_utils_flexboot/src
SRCDIRS += drivers/infiniband/mlx_utils/src/public
SRCDIRS += drivers/infiniband/mlx_utils/mlx_lib/mlx_reg_access
SRCDIRS += drivers/infiniband/mlx_utils/mlx_lib/mlx_nvconfig
SRCDIRS += drivers/infiniband/mlx_utils/mlx_lib/mlx_vmac
SRCDIRS += drivers/infiniband/mlx_utils/mlx_lib/mlx_blink_leds
SRCDIRS += drivers/infiniband/mlx_utils/mlx_lib/mlx_link_speed
SRCDIRS += drivers/infiniband/mlx_nodnic/src
SRCDIRS += drivers/usb
SRCDIRS += interface/pxe interface/efi interface/smbios
SRCDIRS += interface/bofm

1168
src/drivers/infiniband/CIB_PRM.h Executable file

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,163 @@
#ifndef SRC_DRIVERS_INFINIBAND_FLEXBOOT_NODNIC_FLEXBOOT_NODNIC_H_
#define SRC_DRIVERS_INFINIBAND_FLEXBOOT_NODNIC_FLEXBOOT_NODNIC_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_nodnic/include/mlx_nodnic_data_structures.h"
#include "nodnic_prm.h"
#include <ipxe/io.h>
#include <ipxe/infiniband.h>
#include <ipxe/netdevice.h>
/*
* If defined, use interrupts in NODNIC driver
*/
#define NODNIC_IRQ_ENABLED
#define FLEXBOOT_NODNIC_MAX_PORTS 2
#define FLEXBOOT_NODNIC_PORT_BASE 1
#define FLEXBOOT_NODNIC_OPCODE_SEND 0xa
/* Port protocol */
enum flexboot_nodnic_protocol {
FLEXBOOT_NODNIC_PROT_IB_IPV6 = 0,
FLEXBOOT_NODNIC_PROT_ETH,
FLEXBOOT_NODNIC_PROT_IB_IPV4,
FLEXBOOT_NODNIC_PROT_FCOE
};
/** A flexboot nodnic port */
struct flexboot_nodnic_port {
/** Infiniband device */
struct ib_device *ibdev;
/** Network device */
struct net_device *netdev;
/** nodic port */
nodnic_port_priv port_priv;
/** Port type */
struct flexboot_nodnic_port_type *type;
/** Ethernet completion queue */
struct ib_completion_queue *eth_cq;
/** Ethernet queue pair */
struct ib_queue_pair *eth_qp;
};
/** A flexboot nodnic queue pair */
struct flexboot_nodnic_queue_pair {
nodnic_qp *nodnic_queue_pair;
};
/** A flexboot nodnic cq */
struct flexboot_nodnic_completion_queue {
nodnic_cq *nodnic_completion_queue;
};
/** A flexboot_nodnic device */
struct flexboot_nodnic {
/** PCI device */
struct pci_device *pci;
/** nic specific data*/
struct flexboot_nodnic_callbacks *callbacks;
/**nodnic device*/
nodnic_device_priv device_priv;
/**flexboot_nodnic ports*/
struct flexboot_nodnic_port port[FLEXBOOT_NODNIC_MAX_PORTS];
/** Device open request counter */
unsigned int open_count;
/** Port masking */
u16 port_mask;
/** device private data */
void *priv_data;
};
/** A flexboot_nodnic port type */
struct flexboot_nodnic_port_type {
/** Register port
*
* @v flexboot_nodnic flexboot_nodnic device
* @v port flexboot_nodnic port
* @ret mlx_status Return status code
*/
mlx_status ( * register_dev ) (
struct flexboot_nodnic *flexboot_nodnic,
struct flexboot_nodnic_port *port
);
/** Port state changed
*
* @v flexboot_nodnic flexboot_nodnic device
* @v port flexboot_nodnic port
* @v link_up Link is up
*/
void ( * state_change ) (
struct flexboot_nodnic *flexboot_nodnic,
struct flexboot_nodnic_port *port,
int link_up
);
/** Unregister port
*
* @v flexboot_nodnic flexboot_nodnic device
* @v port flexboot_nodnic port
*/
void ( * unregister_dev ) (
struct flexboot_nodnic *flexboot_nodnic,
struct flexboot_nodnic_port *port
);
};
struct cqe_data{
mlx_boolean owner;
mlx_uint32 qpn;
mlx_uint32 is_send;
mlx_uint32 is_error;
mlx_uint32 syndrome;
mlx_uint32 vendor_err_syndrome;
mlx_uint32 wqe_counter;
mlx_uint32 byte_cnt;
};
struct flexboot_nodnic_callbacks {
mlx_status ( * fill_completion ) ( void *cqe, struct cqe_data *cqe_data );
mlx_status ( * cqe_set_owner ) ( void *cq, unsigned int num_cqes );
mlx_size ( * get_cqe_size ) ();
mlx_status ( * fill_send_wqe[5] ) (
struct ib_device *ibdev,
struct ib_queue_pair *qp,
struct ib_address_vector *av,
struct io_buffer *iobuf,
struct nodnic_send_wqbb *wqbb,
unsigned long wqe_idx
);
void ( * irq ) ( struct net_device *netdev, int enable );
};
int flexboot_nodnic_probe ( struct pci_device *pci,
struct flexboot_nodnic_callbacks *callbacks,
void *drv_priv );
void flexboot_nodnic_remove ( struct pci_device *pci );
void flexboot_nodnic_eth_irq ( struct net_device *netdev, int enable );
int flexboot_nodnic_is_supported ( struct pci_device *pci );
void flexboot_nodnic_copy_mac ( uint8_t mac_addr[], uint32_t low_byte,
uint16_t high_byte );
#endif /* SRC_DRIVERS_INFINIBAND_FLEXBOOT_NODNIC_FLEXBOOT_NODNIC_H_ */

2663
src/drivers/infiniband/golan.c Executable file

File diff suppressed because it is too large Load Diff

319
src/drivers/infiniband/golan.h Executable file
View File

@ -0,0 +1,319 @@
#ifndef _GOLAN_H_
#define _GOLAN_H_
/*
* Copyright (C) 2013-2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include <byteswap.h>
#include <errno.h>
#include <stdio.h>
#include <unistd.h>
#include <ipxe/io.h>
#include <ipxe/pci.h>
#include <ipxe/pcibackup.h>
#include "CIB_PRM.h"
#define GOLAN_PCI_CONFIG_BAR_SIZE 0x100000//HERMON_PCI_CONFIG_BAR_SIZE //TODO: What is the BAR size?
#define GOLAN_PAS_SIZE sizeof(uint64_t)
#define GOLAN_INVALID_LKEY 0x00000100UL
#define GOLAN_MAX_PORTS 2
#define GOLAN_PORT_BASE 1
#define MELLANOX_VID 0x15b3
#define GOLAN_HCA_BAR PCI_BASE_ADDRESS_0 //BAR 0
#define GOLAN_HCR_MAX_WAIT_MS 10000
#define min(a,b) ((a)<(b)?(a):(b))
#define GOLAN_PAGE_SHIFT 12
#define GOLAN_PAGE_SIZE (1 << GOLAN_PAGE_SHIFT)
#define GOLAN_PAGE_MASK (GOLAN_PAGE_SIZE - 1)
#define MAX_MBOX ( GOLAN_PAGE_SIZE / MAILBOX_STRIDE )
#define DEF_CMD_IDX 1
#define MEM_CMD_IDX 0
#define NO_MBOX 0xffff
#define MEM_MBOX MEM_CMD_IDX
#define GEN_MBOX DEF_CMD_IDX
#define CMD_IF_REV 4
#define MAX_PASE_MBOX ((GOLAN_CMD_PAS_CNT) - 2)
#define CMD_STATUS( golan , idx ) ((struct golan_outbox_hdr *)(get_cmd( (golan) , (idx) )->out))->status
#define CMD_SYND( golan , idx ) ((struct golan_outbox_hdr *)(get_cmd( (golan) , (idx) )->out))->syndrome
#define QRY_PAGES_OUT( golan, idx ) ((struct golan_query_pages_outbox *)(get_cmd( (golan) , (idx) )->out))
#define VIRT_2_BE64_BUS( addr ) cpu_to_be64(((unsigned long long )virt_to_bus(addr)))
#define BE64_BUS_2_VIRT( addr ) bus_to_virt(be64_to_cpu(addr))
#define USR_2_BE64_BUS( addr ) cpu_to_be64(((unsigned long long )user_to_phys(addr, 0)))
#define BE64_BUS_2_USR( addr ) be64_to_cpu(phys_to_user(addr))
#define GET_INBOX(golan, idx) (&(((struct mbox *)(golan->mboxes.inbox))[idx]))
#define GET_OUTBOX(golan, idx) (&(((struct mbox *)(golan->mboxes.outbox))[idx]))
#define DIV_ROUND_UP(n,d) (((n) + (d) - 1) / (d))
/* Fw status fields */
typedef enum {
NO_ERRORS = 0x0,
SIGNATURE_ERROR = 0x1,
TOKEN_ERROR = 0x2,
BAD_BLOCK_NUMBER = 0x3,
BAD_OUTPUT_POINTER = 0x4, // pointer not align to mailbox size
BAD_INPUT_POINTER = 0x5, // pointer not align to mailbox size
INTERNAL_ERROR = 0x6,
INPUT_LEN_ERROR = 0x7, // input length less than 0x8.
OUTPUT_LEN_ERROR = 0x8, // output length less than 0x8.
RESERVE_NOT_ZERO = 0x9,
BAD_CMD_TYPE = 0x10,
} return_hdr_t;
struct golan_cmdq_md {
void *addr;
u16 log_stride;
u16 size;
};
struct golan_uar {
uint32_t index;
void *virt;
unsigned long phys;
};
/* Queue Pair */
#define GOLAN_SEND_WQE_BB_SIZE 64
#define GOLAN_SEND_UD_WQE_SIZE sizeof(struct golan_send_wqe_ud)
#define GOLAN_RECV_WQE_SIZE sizeof(struct golan_recv_wqe_ud)
#define GOLAN_WQEBBS_PER_SEND_UD_WQE DIV_ROUND_UP(GOLAN_SEND_UD_WQE_SIZE, GOLAN_SEND_WQE_BB_SIZE)
#define GOLAN_SEND_OPCODE 0x0a
#define GOLAN_WQE_CTRL_WQE_IDX_BIT 8
enum golan_ib_qp_state {
GOLAN_IB_QPS_RESET,
GOLAN_IB_QPS_INIT,
GOLAN_IB_QPS_RTR,
GOLAN_IB_QPS_RTS,
GOLAN_IB_QPS_SQD,
GOLAN_IB_QPS_SQE,
GOLAN_IB_QPS_ERR
};
struct golan_send_wqe_ud {
struct golan_wqe_ctrl_seg ctrl;
struct golan_av datagram;
struct golan_wqe_data_seg data;
};
union golan_send_wqe {
struct golan_send_wqe_ud ud;
uint8_t pad[GOLAN_WQEBBS_PER_SEND_UD_WQE * GOLAN_SEND_WQE_BB_SIZE];
};
struct golan_recv_wqe_ud {
struct golan_wqe_data_seg data[2];
};
struct golan_recv_wq {
struct golan_recv_wqe_ud *wqes;
/* WQ size in bytes */
int size;
/* In SQ, it will be increased in wqe_size (number of WQEBBs per WQE) */
u16 next_idx;
/** GRH buffers (if applicable) */
struct ib_global_route_header *grh;
/** Size of GRH buffers */
size_t grh_size;
};
struct golan_send_wq {
union golan_send_wqe *wqes;
/* WQ size in bytes */
int size;
/* In SQ, it will be increased in wqe_size (number of WQEBBs per WQE) */
u16 next_idx;
};
struct golan_queue_pair {
void *wqes;
int size;
struct golan_recv_wq rq;
struct golan_send_wq sq;
struct golan_qp_db *doorbell_record;
u32 doorbell_qpn;
enum golan_ib_qp_state state;
};
/* Completion Queue */
#define GOLAN_CQE_OPCODE_NOT_VALID 0x0f
#define GOLAN_CQE_OPCODE_BIT 4
#define GOLAN_CQ_DB_RECORD_SIZE sizeof(uint64_t)
#define GOLAN_CQE_OWNER_MASK 1
#define MANAGE_PAGES_PSA_OFFSET 0
#define PXE_CMDIF_REF 5
enum {
GOLAN_CQE_SW_OWNERSHIP = 0x0,
GOLAN_CQE_HW_OWNERSHIP = 0x1
};
enum {
GOLAN_CQE_SIZE_64 = 0,
GOLAN_CQE_SIZE_128 = 1
};
struct golan_completion_queue {
struct golan_cqe64 *cqes;
int size;
__be64 *doorbell_record;
};
/* Event Queue */
#define GOLAN_EQE_SIZE sizeof(struct golan_eqe)
#define GOLAN_NUM_EQES 8
#define GOLAN_EQ_DOORBELL_OFFSET 0x40
#define GOLAN_EQ_MAP_ALL_EVENTS \
((1 << GOLAN_EVENT_TYPE_PATH_MIG )| \
(1 << GOLAN_EVENT_TYPE_COMM_EST )| \
(1 << GOLAN_EVENT_TYPE_SQ_DRAINED )| \
(1 << GOLAN_EVENT_TYPE_SRQ_LAST_WQE )| \
(1 << GOLAN_EVENT_TYPE_SRQ_RQ_LIMIT )| \
(1 << GOLAN_EVENT_TYPE_CQ_ERROR )| \
(1 << GOLAN_EVENT_TYPE_WQ_CATAS_ERROR )| \
(1 << GOLAN_EVENT_TYPE_PATH_MIG_FAILED )| \
(1 << GOLAN_EVENT_TYPE_WQ_INVAL_REQ_ERROR )| \
(1 << GOLAN_EVENT_TYPE_WQ_ACCESS_ERROR )| \
(1 << GOLAN_EVENT_TYPE_SRQ_CATAS_ERROR )| \
(1 << GOLAN_EVENT_TYPE_INTERNAL_ERROR )| \
(1 << GOLAN_EVENT_TYPE_PORT_CHANGE )| \
(1 << GOLAN_EVENT_TYPE_GPIO_EVENT )| \
(1 << GOLAN_EVENT_TYPE_CLIENT_RE_REGISTER )| \
(1 << GOLAN_EVENT_TYPE_REMOTE_CONFIG )| \
(1 << GOLAN_EVENT_TYPE_DB_BF_CONGESTION )| \
(1 << GOLAN_EVENT_TYPE_STALL_EVENT )| \
(1 << GOLAN_EVENT_TYPE_PACKET_DROPPED )| \
(1 << GOLAN_EVENT_TYPE_CMD )| \
(1 << GOLAN_EVENT_TYPE_PAGE_REQUEST ))
enum golan_event {
GOLAN_EVENT_TYPE_COMP = 0x0,
GOLAN_EVENT_TYPE_PATH_MIG = 0x01,
GOLAN_EVENT_TYPE_COMM_EST = 0x02,
GOLAN_EVENT_TYPE_SQ_DRAINED = 0x03,
GOLAN_EVENT_TYPE_SRQ_LAST_WQE = 0x13,
GOLAN_EVENT_TYPE_SRQ_RQ_LIMIT = 0x14,
GOLAN_EVENT_TYPE_CQ_ERROR = 0x04,
GOLAN_EVENT_TYPE_WQ_CATAS_ERROR = 0x05,
GOLAN_EVENT_TYPE_PATH_MIG_FAILED = 0x07,
GOLAN_EVENT_TYPE_WQ_INVAL_REQ_ERROR = 0x10,
GOLAN_EVENT_TYPE_WQ_ACCESS_ERROR = 0x11,
GOLAN_EVENT_TYPE_SRQ_CATAS_ERROR = 0x12,
GOLAN_EVENT_TYPE_INTERNAL_ERROR = 0x08,
GOLAN_EVENT_TYPE_PORT_CHANGE = 0x09,
GOLAN_EVENT_TYPE_GPIO_EVENT = 0x15,
// GOLAN_EVENT_TYPE_CLIENT_RE_REGISTER = 0x16,
GOLAN_EVENT_TYPE_REMOTE_CONFIG = 0x19,
GOLAN_EVENT_TYPE_DB_BF_CONGESTION = 0x1a,
GOLAN_EVENT_TYPE_STALL_EVENT = 0x1b,
GOLAN_EVENT_TYPE_PACKET_DROPPED = 0x1f,
GOLAN_EVENT_TYPE_CMD = 0x0a,
GOLAN_EVENT_TYPE_PAGE_REQUEST = 0x0b,
GOLAN_EVENT_TYPE_PAGE_FAULT = 0x0C,
};
enum golan_port_sub_event {
GOLAN_PORT_CHANGE_SUBTYPE_DOWN = 1,
GOLAN_PORT_CHANGE_SUBTYPE_ACTIVE = 4,
GOLAN_PORT_CHANGE_SUBTYPE_INITIALIZED = 5,
GOLAN_PORT_CHANGE_SUBTYPE_LID = 6,
GOLAN_PORT_CHANGE_SUBTYPE_PKEY = 7,
GOLAN_PORT_CHANGE_SUBTYPE_GUID = 8,
GOLAN_PORT_CHANGE_SUBTYPE_CLIENT_REREG = 9
};
enum {
GOLAN_EQE_SW_OWNERSHIP = 0x0,
GOLAN_EQE_HW_OWNERSHIP = 0x1
};
enum {
GOLAN_EQ_UNARMED = 0,
GOLAN_EQ_ARMED = 1,
};
struct golan_event_queue {
uint8_t eqn;
uint64_t mask;
struct golan_eqe *eqes;
int size;
__be32 *doorbell;
uint32_t cons_index;
};
struct golan_port {
/** Infiniband device */
struct ib_device *ibdev;
/** Network device */
struct net_device *netdev;
/** VEP number */
u8 vep_number;
};
struct golan_mboxes {
void *inbox;
void *outbox;
};
#define GOLAN_OPEN 0x1
struct golan {
struct pci_device *pci;
struct golan_hca_init_seg *iseg;
struct golan_cmdq_md cmd;
struct golan_hca_cap caps; /* stored as big indian*/
struct golan_mboxes mboxes;
struct list_head pages;
uint32_t cmd_bm;
uint32_t total_dma_pages;
struct golan_uar uar;
struct golan_event_queue eq;
uint32_t pdn;
u32 mkey;
u32 flags;
struct golan_port ports[GOLAN_MAX_PORTS];
};
#endif /* _GOLAN_H_*/

View File

@ -0,0 +1,43 @@
#ifndef NODNIC_CMD_H_
#define NODNIC_CMD_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_nodnic_data_structures.h"
#include "../../mlx_utils/include/public/mlx_utils.h"
#include "../../mlx_utils/include/public/mlx_pci_gw.h"
mlx_status
nodnic_cmd_read(
IN nodnic_device_priv *device_priv,
IN mlx_uint32 address,
OUT mlx_pci_gw_buffer *buffer
);
mlx_status
nodnic_cmd_write(
IN nodnic_device_priv *device_priv,
IN mlx_uint32 address,
IN mlx_pci_gw_buffer buffer
);
#endif /* STUB_NODNIC_CMD_H_ */

View File

@ -0,0 +1,80 @@
#ifndef NODNIC_DEVICE_H_
#define NODNIC_DEVICE_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_nodnic_data_structures.h"
#define NODIC_SUPPORTED_REVISION 1
//Initialization segment
#define NODNIC_CMDQ_PHY_ADDR_HIGH_OFFSET 0x10
#define NODNIC_CMDQ_PHY_ADDR_LOW_OFFSET 0x14
#define NODNIC_NIC_INTERFACE_OFFSET 0x14
#define NODNIC_INITIALIZING_OFFSET 0x1fc
#define NODNIC_NIC_INTERFACE_SUPPORTED_OFFSET 0x1fc
#define NODNIC_LOCATION_OFFSET 0x240
#define NODNIC_CMDQ_PHY_ADDR_LOW_MASK 0xFFFFE000
#define NODNIC_NIC_INTERFACE_SUPPORTED_MASK 0x4000000
#define NODNIC_NIC_INTERFACE_BIT 9
#define NODNIC_DISABLE_INTERFACE_BIT 8
#define NODNIC_NIC_INTERFACE_SUPPORTED_BIT 26
#define NODNIC_INITIALIZING_BIT 31
#define NODNIC_NIC_DISABLE_INT_OFFSET 0x100c
//nodnic segment
#define NODNIC_REVISION_OFFSET 0x0
#define NODNIC_HARDWARE_FORMAT_OFFSET 0x0
mlx_status
nodnic_device_init(
IN nodnic_device_priv *device_priv
);
mlx_status
nodnic_device_teardown(
IN nodnic_device_priv *device_priv
);
mlx_status
nodnic_device_get_cap(
IN nodnic_device_priv *device_priv
);
mlx_status
nodnic_device_clear_int (
IN nodnic_device_priv *device_priv
);
mlx_status
nodnic_device_get_fw_version(
IN nodnic_device_priv *device_priv,
OUT mlx_uint16 *fw_ver_minor,
OUT mlx_uint16 *fw_ver_sub_minor,
OUT mlx_uint16 *fw_ver_major
);
#endif /* STUB_NODNIC_DEVICE_H_ */

View File

@ -0,0 +1,201 @@
#ifndef NODNIC_NODNICDATASTRUCTURES_H_
#define NODNIC_NODNICDATASTRUCTURES_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../mlx_utils/include/public/mlx_utils.h"
/* todo: fix coding convention */
#define NODNIC_MEMORY_ALIGN 0x1000
#define NODNIC_MAX_MAC_FILTERS 5
#define NODNIC_MAX_MGID_FILTERS 4
typedef struct _nodnic_device_priv nodnic_device_priv;
typedef struct _nodnic_port_priv nodnic_port_priv;
typedef struct _nodnic_device_capabilites nodnic_device_capabilites;
typedef struct _nodnic_qp nodnic_qp;
typedef struct _nodnic_cq nodnic_cq;
typedef struct _nodnic_eq nodnic_eq;
/* NODNIC Port states
* Bit 0 - port open/close
* Bit 1 - port is [not] in disabling DMA
* 0 - closed and not disabling DMA
* 1 - opened and not disabling DMA
* 3 - opened and disabling DMA
*/
#define NODNIC_PORT_OPENED 0b00000001
#define NODNIC_PORT_DISABLING_DMA 0b00000010
typedef enum {
ConnectX3 = 0,
Connectx4
}nodnic_hardware_format;
typedef enum {
NODNIC_QPT_SMI,
NODNIC_QPT_GSI,
NODNIC_QPT_UD,
NODNIC_QPT_RC,
NODNIC_QPT_ETH,
}nodnic_queue_pair_type;
typedef enum {
NODNIC_PORT_TYPE_IB = 0,
NODNIC_PORT_TYPE_ETH,
NODNIC_PORT_TYPE_UNKNOWN,
}nodnic_port_type;
#define RECV_WQE_SIZE 16
#define NODNIC_WQBB_SIZE 64
/** A nodnic send wqbb */
struct nodnic_send_wqbb {
mlx_uint8 force_align[NODNIC_WQBB_SIZE];
};
struct nodnic_ring {
mlx_uint32 offset;
/** Work queue entries */
/* TODO: add to memory entity */
mlx_physical_address wqe_physical;
mlx_void *map;
/** Size of work queue */
mlx_size wq_size;
/** Next work queue entry index
*
* This is the index of the next entry to be filled (i.e. the
* first empty entry). This value is not bounded by num_wqes;
* users must logical-AND with (num_wqes-1) to generate an
* array index.
*/
mlx_uint32 num_wqes;
mlx_uint32 qpn;
mlx_uint32 next_idx;
mlx_uint32 ring_pi;
};
struct nodnic_send_ring{
struct nodnic_ring nodnic_ring;
struct nodnic_send_wqbb *wqe_virt;
};
struct nodnic_recv_ring{
struct nodnic_ring nodnic_ring;
void *wqe_virt;
};
struct _nodnic_qp{
nodnic_queue_pair_type type;
struct nodnic_send_ring send;
struct nodnic_recv_ring receive;
};
struct _nodnic_cq{
/** cq entries */
mlx_void *cq_virt;
mlx_physical_address cq_physical;
mlx_void *map;
/** cq */
mlx_size cq_size;
};
struct _nodnic_eq{
mlx_void *eq_virt;
mlx_physical_address eq_physical;
mlx_void *map;
mlx_size eq_size;
};
struct _nodnic_device_capabilites{
mlx_boolean support_mac_filters;
mlx_boolean support_promisc_filter;
mlx_boolean support_promisc_multicast_filter;
mlx_uint8 log_working_buffer_size;
mlx_uint8 log_pkey_table_size;
mlx_boolean num_ports; // 0 - single port, 1 - dual port
mlx_uint8 log_max_ring_size;
#ifdef DEVICE_CX3
mlx_uint8 crspace_doorbells;
#endif
};
#ifdef DEVICE_CX3
/* This is the structure of the data in the scratchpad
* Read/Write data from/to its field using PCI accesses only */
typedef struct _nodnic_port_data_flow_gw nodnic_port_data_flow_gw;
struct _nodnic_port_data_flow_gw {
mlx_uint32 send_doorbell;
mlx_uint32 recv_doorbell;
mlx_uint32 reserved2[2];
mlx_uint32 armcq_cq_ci_dword;
mlx_uint32 dma_en;
} __attribute__ ((packed));
#endif
struct _nodnic_device_priv{
mlx_boolean is_initiailzied;
mlx_utils *utils;
//nodnic structure offset in init segment
mlx_uint32 device_offset;
nodnic_device_capabilites device_cap;
mlx_uint8 nodnic_revision;
nodnic_hardware_format hardware_format;
mlx_uint32 pd;
mlx_uint32 lkey;
mlx_uint64 device_guid;
nodnic_port_priv *ports;
#ifdef DEVICE_CX3
mlx_void *crspace_clear_int;
#endif
};
struct _nodnic_port_priv{
nodnic_device_priv *device;
mlx_uint32 port_offset;
mlx_uint8 port_state;
mlx_boolean network_state;
mlx_boolean dma_state;
nodnic_port_type port_type;
mlx_uint8 port_num;
nodnic_eq eq;
mlx_mac_address mac_filters[5];
mlx_status (*send_doorbell)(
IN nodnic_port_priv *port_priv,
IN struct nodnic_ring *ring,
IN mlx_uint16 index);
mlx_status (*recv_doorbell)(
IN nodnic_port_priv *port_priv,
IN struct nodnic_ring *ring,
IN mlx_uint16 index);
mlx_status (*set_dma)(
IN nodnic_port_priv *port_priv,
IN mlx_boolean value);
#ifdef DEVICE_CX3
nodnic_port_data_flow_gw *data_flow_gw;
#endif
};
#endif /* STUB_NODNIC_NODNICDATASTRUCTURES_H_ */

View File

@ -0,0 +1,229 @@
#ifndef NODNIC_PORT_H_
#define NODNIC_PORT_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_nodnic_data_structures.h"
#define NODNIC_PORT_MAC_FILTERS_OFFSET 0x10
typedef enum {
nodnic_port_option_link_type = 0,
nodnic_port_option_mac_low,
nodnic_port_option_mac_high,
nodnic_port_option_log_cq_size,
nodnic_port_option_reset_needed,
nodnic_port_option_mac_filters_en,
nodnic_port_option_port_state,
nodnic_port_option_network_en,
nodnic_port_option_dma_en,
nodnic_port_option_eq_addr_low,
nodnic_port_option_eq_addr_high,
nodnic_port_option_cq_addr_low,
nodnic_port_option_cq_addr_high,
nodnic_port_option_port_management_change_event,
nodnic_port_option_port_promisc_en,
nodnic_port_option_arm_cq,
nodnic_port_option_port_promisc_multicast_en,
#ifdef DEVICE_CX3
nodnic_port_option_crspace_en,
#endif
}nodnic_port_option;
struct nodnic_port_data_entry{
nodnic_port_option option;
mlx_uint32 offset;
mlx_uint8 align;
mlx_uint32 mask;
};
struct nodnic_qp_data_entry{
nodnic_queue_pair_type type;
mlx_uint32 send_offset;
mlx_uint32 recv_offset;
};
typedef enum {
nodnic_port_state_down = 0,
nodnic_port_state_initialize,
nodnic_port_state_armed,
nodnic_port_state_active,
}nodnic_port_state;
mlx_status
nodnic_port_get_state(
IN nodnic_port_priv *port_priv,
OUT nodnic_port_state *state
);
mlx_status
nodnic_port_get_type(
IN nodnic_port_priv *port_priv,
OUT nodnic_port_type *type
);
mlx_status
nodnic_port_query(
IN nodnic_port_priv *port_priv,
IN nodnic_port_option option,
OUT mlx_uint32 *out
);
mlx_status
nodnic_port_set(
IN nodnic_port_priv *port_priv,
IN nodnic_port_option option,
IN mlx_uint32 in
);
mlx_status
nodnic_port_create_cq(
IN nodnic_port_priv *port_priv,
IN mlx_size cq_size,
OUT nodnic_cq **cq
);
mlx_status
nodnic_port_destroy_cq(
IN nodnic_port_priv *port_priv,
IN nodnic_cq *cq
);
mlx_status
nodnic_port_create_qp(
IN nodnic_port_priv *port_priv,
IN nodnic_queue_pair_type type,
IN mlx_size send_wq_size,
IN mlx_uint32 send_wqe_num,
IN mlx_size receive_wq_size,
IN mlx_uint32 recv_wqe_num,
OUT nodnic_qp **qp
);
mlx_status
nodnic_port_destroy_qp(
IN nodnic_port_priv *port_priv,
IN nodnic_queue_pair_type type,
IN nodnic_qp *qp
);
mlx_status
nodnic_port_get_qpn(
IN nodnic_port_priv *port_priv,
IN struct nodnic_ring *ring,
OUT mlx_uint32 *qpn
);
mlx_status
nodnic_port_update_ring_doorbell(
IN nodnic_port_priv *port_priv,
IN struct nodnic_ring *ring,
IN mlx_uint16 index
);
mlx_status
nodnic_port_get_cq_size(
IN nodnic_port_priv *port_priv,
OUT mlx_uint64 *cq_size
);
mlx_status
nodnic_port_allocate_eq(
IN nodnic_port_priv *port_priv,
IN mlx_uint8 log_eq_size
);
mlx_status
nodnic_port_free_eq(
IN nodnic_port_priv *port_priv
);
mlx_status
nodnic_port_add_mac_filter(
IN nodnic_port_priv *port_priv,
IN mlx_mac_address mac
);
mlx_status
nodnic_port_remove_mac_filter(
IN nodnic_port_priv *port_priv,
IN mlx_mac_address mac
);
mlx_status
nodnic_port_add_mgid_filter(
IN nodnic_port_priv *port_priv,
IN mlx_mac_address mac
);
mlx_status
nodnic_port_remove_mgid_filter(
IN nodnic_port_priv *port_priv,
IN mlx_mac_address mac
);
mlx_status
nodnic_port_thin_init(
IN nodnic_device_priv *device_priv,
IN nodnic_port_priv *port_priv,
IN mlx_uint8 port_index
);
mlx_status
nodnic_port_set_promisc(
IN nodnic_port_priv *port_priv,
IN mlx_boolean value
);
mlx_status
nodnic_port_set_promisc_multicast(
IN nodnic_port_priv *port_priv,
IN mlx_boolean value
);
mlx_status
nodnic_port_init(
IN nodnic_port_priv *port_priv
);
mlx_status
nodnic_port_close(
IN nodnic_port_priv *port_priv
);
mlx_status
nodnic_port_enable_dma(
IN nodnic_port_priv *port_priv
);
mlx_status
nodnic_port_disable_dma(
IN nodnic_port_priv *port_priv
);
mlx_status
nodnic_port_read_reset_needed(
IN nodnic_port_priv *port_priv,
OUT mlx_boolean *reset_needed
);
mlx_status
nodnic_port_read_port_management_change_event(
IN nodnic_port_priv *port_priv,
OUT mlx_boolean *change_event
);
#endif /* STUB_NODNIC_PORT_H_ */

View File

@ -0,0 +1,77 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../include/mlx_cmd.h"
#include "../../mlx_utils/include/public/mlx_pci_gw.h"
#include "../../mlx_utils/include/public/mlx_bail.h"
#include "../../mlx_utils/include/public/mlx_pci.h"
#include "../../mlx_utils/include/public/mlx_logging.h"
mlx_status
nodnic_cmd_read(
IN nodnic_device_priv *device_priv,
IN mlx_uint32 address,
OUT mlx_pci_gw_buffer *buffer
)
{
mlx_status status = MLX_SUCCESS;
mlx_utils *utils = NULL;
if ( device_priv == NULL || buffer == NULL ) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
utils = device_priv->utils;
status = mlx_pci_gw_read(utils, PCI_GW_SPACE_NODNIC, address, buffer);
MLX_CHECK_STATUS(device_priv, status, read_error,"mlx_pci_gw_read failed");
read_error:
bad_param:
return status;
}
mlx_status
nodnic_cmd_write(
IN nodnic_device_priv *device_priv,
IN mlx_uint32 address,
IN mlx_pci_gw_buffer buffer
)
{
mlx_status status = MLX_SUCCESS;
mlx_utils *utils = NULL;
if ( device_priv == NULL ) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
utils = device_priv->utils;
status = mlx_pci_gw_write(utils, PCI_GW_SPACE_NODNIC, address, buffer);
MLX_CHECK_STATUS(device_priv, status, write_error,"mlx_pci_gw_write failed");
write_error:
bad_param:
return status;
}

View File

@ -0,0 +1,339 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../include/mlx_device.h"
#include "../include/mlx_cmd.h"
#include "../../mlx_utils/include/public/mlx_bail.h"
#include "../../mlx_utils/include/public/mlx_pci.h"
#include "../../mlx_utils/include/public/mlx_memory.h"
#include "../../mlx_utils/include/public/mlx_logging.h"
#define CHECK_BIT(field, offset) (((field) & ((mlx_uint32)1 << (offset))) != 0)
static
mlx_status
check_nodnic_interface_supported(
IN nodnic_device_priv* device_priv,
OUT mlx_boolean *out
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 output = 0;
status = nodnic_cmd_read(device_priv, NODNIC_NIC_INTERFACE_SUPPORTED_OFFSET,
&output);
MLX_FATAL_CHECK_STATUS(status, read_error, "failed to read nic_interface_supported");
*out = CHECK_BIT(output, NODNIC_NIC_INTERFACE_SUPPORTED_BIT);
read_error:
return status;
}
static
mlx_status
wait_for_device_initialization(
IN nodnic_device_priv* device_priv
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint8 try = 0;
mlx_uint32 buffer = 0;
#define CHECK_DEVICE_INIT_TRIES 10
for( ; try < CHECK_DEVICE_INIT_TRIES ; try++){
status = nodnic_cmd_read(device_priv, NODNIC_INITIALIZING_OFFSET, &buffer);
MLX_CHECK_STATUS(device_priv, status, read_error, "failed to read initializing");
if( !CHECK_BIT(buffer, NODNIC_INITIALIZING_BIT)){
goto init_done;
}
mlx_utils_delay_in_ms(100);
}
status = MLX_FAILED;
read_error:
init_done:
return status;
}
static
mlx_status
disable_nodnic_inteface(
IN nodnic_device_priv *device_priv
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 buffer = 0;
buffer = (1 << NODNIC_DISABLE_INTERFACE_BIT);
status = nodnic_cmd_write(device_priv, NODNIC_CMDQ_PHY_ADDR_LOW_OFFSET, buffer);
MLX_FATAL_CHECK_STATUS(status, write_err, "failed to write cmdq_phy_addr + nic_interface");
status = wait_for_device_initialization(device_priv);
MLX_FATAL_CHECK_STATUS(status, init_err, "failed to initialize device");
init_err:
write_err:
return status;
}
static
mlx_status
nodnic_device_start_nodnic(
IN nodnic_device_priv *device_priv
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 buffer = 0;
mlx_boolean nodnic_supported = 0;
status = wait_for_device_initialization(device_priv);
MLX_FATAL_CHECK_STATUS(status, wait_for_fw_err, "failed to initialize device");
status = check_nodnic_interface_supported(device_priv, &nodnic_supported);
MLX_FATAL_CHECK_STATUS(status, read_err,"failed to check nic_interface_supported");
if( nodnic_supported == 0 ){
status = MLX_UNSUPPORTED;
goto nodnic_unsupported;
}
buffer = (1 << NODNIC_NIC_INTERFACE_BIT);
status = nodnic_cmd_write(device_priv, NODNIC_NIC_INTERFACE_OFFSET, buffer);
MLX_FATAL_CHECK_STATUS(status, write_err, "failed to write cmdq_phy_addr + nic_interface");
status = wait_for_device_initialization(device_priv);
MLX_FATAL_CHECK_STATUS(status, init_err, "failed to initialize device");
init_err:
read_err:
write_err:
nodnic_unsupported:
wait_for_fw_err:
return status;
}
static
mlx_status
nodnic_device_get_nodnic_data(
IN nodnic_device_priv *device_priv
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 buffer = 0;
status = nodnic_cmd_read(device_priv, NODNIC_LOCATION_OFFSET, &device_priv->device_offset);
MLX_FATAL_CHECK_STATUS(status, nodnic_offset_read_err, "failed to read nodnic offset");
status = nodnic_cmd_read(device_priv,
device_priv->device_offset + NODNIC_REVISION_OFFSET, &buffer);
MLX_FATAL_CHECK_STATUS(status, nodnic_revision_read_err, "failed to read nodnic revision");
device_priv->nodnic_revision = (buffer >> 24) & 0xFF;
if( device_priv->nodnic_revision != NODIC_SUPPORTED_REVISION ){
MLX_DEBUG_ERROR(device_priv, "nodnic revision not supported\n");
status = MLX_UNSUPPORTED;
goto unsupported_revision;
}
status = nodnic_cmd_read(device_priv,
device_priv->device_offset + NODNIC_HARDWARE_FORMAT_OFFSET, &buffer);
MLX_FATAL_CHECK_STATUS(status, nodnic_hardware_format_read_err, "failed to read nodnic revision");
device_priv->hardware_format = (buffer >> 16) & 0xFF;
return status;
unsupported_revision:
nodnic_hardware_format_read_err:
nodnic_offset_read_err:
nodnic_revision_read_err:
disable_nodnic_inteface(device_priv);
return status;
}
mlx_status
nodnic_device_clear_int (
IN nodnic_device_priv *device_priv
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 disable = 1;
#ifndef DEVICE_CX3
status = nodnic_cmd_write(device_priv, NODNIC_NIC_DISABLE_INT_OFFSET, disable);
MLX_CHECK_STATUS(device_priv, status, clear_int_done, "failed writing to disable_bit");
#else
mlx_utils *utils = device_priv->utils;
mlx_uint64 clear_int = (mlx_uint64)(device_priv->crspace_clear_int);
mlx_uint32 swapped = 0;
if (device_priv->device_cap.crspace_doorbells == 0) {
status = nodnic_cmd_write(device_priv, NODNIC_NIC_DISABLE_INT_OFFSET, disable);
MLX_CHECK_STATUS(device_priv, status, clear_int_done, "failed writing to disable_bit");
} else {
/* Write the new index and update FW that new data was submitted */
disable = 0x80000000;
mlx_memory_cpu_to_be32(utils, disable, &swapped);
mlx_pci_mem_write (utils, MlxPciWidthUint32, 0, clear_int, 1, &swapped);
mlx_pci_mem_read (utils, MlxPciWidthUint32, 0, clear_int, 1, &swapped);
}
#endif
clear_int_done:
return status;
}
mlx_status
nodnic_device_init(
IN nodnic_device_priv *device_priv
)
{
mlx_status status = MLX_SUCCESS;
if( device_priv == NULL ){
status = MLX_INVALID_PARAMETER;
goto parm_err;
}
status = nodnic_device_start_nodnic(device_priv);
MLX_FATAL_CHECK_STATUS(status, start_nodnic_err, "nodnic_device_start_nodnic failed");
status = nodnic_device_get_nodnic_data(device_priv);
MLX_FATAL_CHECK_STATUS(status, data_err, "nodnic_device_get_nodnic_data failed");
return status;
data_err:
start_nodnic_err:
parm_err:
return status;
}
mlx_status
nodnic_device_teardown(
IN nodnic_device_priv *device_priv
)
{
mlx_status status = MLX_SUCCESS;
status = disable_nodnic_inteface(device_priv);
MLX_FATAL_CHECK_STATUS(status, disable_failed, "failed to disable nodnic interface");
disable_failed:
return status;
}
mlx_status
nodnic_device_get_cap(
IN nodnic_device_priv *device_priv
)
{
mlx_status status = MLX_SUCCESS;
nodnic_device_capabilites *device_cap = NULL;
mlx_uint32 buffer = 0;
mlx_uint64 guid_l = 0;
mlx_uint64 guid_h = 0;
if( device_priv == NULL ){
status = MLX_INVALID_PARAMETER;
goto parm_err;
}
device_cap = &device_priv->device_cap;
//get device capabilities
status = nodnic_cmd_read(device_priv, device_priv->device_offset + 0x0, &buffer);
MLX_FATAL_CHECK_STATUS(status, read_err, "failed to read nodnic first dword");
#define NODNIC_DEVICE_SUPPORT_MAC_FILTERS_OFFSET 15
#define NODNIC_DEVICE_SUPPORT_PROMISC_FILTER_OFFSET 14
#define NODNIC_DEVICE_SUPPORT_PROMISC_MULT_FILTER_OFFSET 13
#define NODNIC_DEVICE_LOG_WORKING_BUFFER_SIZE_OFFSET 8
#define NODNIC_DEVICE_LOG_WORKING_BUFFER_SIZE_MASK 0x7
#define NODNIC_DEVICE_LOG_PKEY_TABLE_SIZE_OFFSET 4
#define NODNIC_DEVICE_LOG_PKEY_TABLE_SIZE_MASK 0xF
#define NODNIC_DEVICE_NUM_PORTS_OFFSET 0
device_cap->support_mac_filters = CHECK_BIT(buffer, NODNIC_DEVICE_SUPPORT_MAC_FILTERS_OFFSET);
device_cap->support_promisc_filter = CHECK_BIT(buffer, NODNIC_DEVICE_SUPPORT_PROMISC_FILTER_OFFSET);
device_cap->support_promisc_multicast_filter = CHECK_BIT(buffer, NODNIC_DEVICE_SUPPORT_PROMISC_MULT_FILTER_OFFSET);
device_cap->log_working_buffer_size =
(buffer >> NODNIC_DEVICE_LOG_WORKING_BUFFER_SIZE_OFFSET) & NODNIC_DEVICE_LOG_WORKING_BUFFER_SIZE_MASK;
device_cap->log_pkey_table_size =
(buffer >> NODNIC_DEVICE_LOG_PKEY_TABLE_SIZE_OFFSET) & NODNIC_DEVICE_LOG_PKEY_TABLE_SIZE_MASK;
device_cap->num_ports = CHECK_BIT(buffer, NODNIC_DEVICE_NUM_PORTS_OFFSET) + 1;
#ifdef DEVICE_CX3
#define NODNIC_DEVICE_CRSPACE_DB_OFFSET 12
device_cap->crspace_doorbells = CHECK_BIT(buffer, NODNIC_DEVICE_CRSPACE_DB_OFFSET);
#endif
status = nodnic_cmd_read(device_priv, device_priv->device_offset + 0x4, &buffer);
MLX_FATAL_CHECK_STATUS(status, read_err, "failed to read nodnic second dword");
#define NODNIC_DEVICE_LOG_MAX_RING_SIZE_OFFSET 24
#define NODNIC_DEVICE_LOG_MAX_RING_SIZE_MASK 0x3F
#define NODNIC_DEVICE_PD_MASK 0xFFFFFF
device_cap->log_max_ring_size =
(buffer >> NODNIC_DEVICE_LOG_MAX_RING_SIZE_OFFSET) & NODNIC_DEVICE_LOG_MAX_RING_SIZE_MASK;
//get device magic numbers
device_priv->pd = buffer & NODNIC_DEVICE_PD_MASK;
status = nodnic_cmd_read(device_priv, device_priv->device_offset + 0x8, &buffer);
MLX_FATAL_CHECK_STATUS(status, read_err, "failed to read nodnic third dword");
device_priv->lkey = buffer;
#ifdef DEVICE_CX3
if ( device_cap->crspace_doorbells ) {
status = nodnic_cmd_read(device_priv, device_priv->device_offset + 0x18, &buffer);
MLX_FATAL_CHECK_STATUS(status, read_err, "failed to read nodnic_crspace_clear_int address");
device_priv->crspace_clear_int = device_priv->utils->config + buffer;
}
#endif
status = nodnic_cmd_read(device_priv, device_priv->device_offset + 0x10, (mlx_uint32*)&guid_h);
MLX_FATAL_CHECK_STATUS(status, read_err, "failed to read nodnic guid_h");
status = nodnic_cmd_read(device_priv, device_priv->device_offset + 0x14, (mlx_uint32*)&guid_l);
MLX_FATAL_CHECK_STATUS(status, read_err, "failed to read nodnic guid_l");
device_priv->device_guid = guid_l | (guid_h << 32);
read_err:
parm_err:
return status;
}
mlx_status
nodnic_device_get_fw_version(
IN nodnic_device_priv *device_priv,
OUT mlx_uint16 *fw_ver_minor,
OUT mlx_uint16 *fw_ver_sub_minor,
OUT mlx_uint16 *fw_ver_major
){
mlx_status status = MLX_SUCCESS;
mlx_uint32 buffer = 0;
if( device_priv == NULL ){
status = MLX_INVALID_PARAMETER;
goto parm_err;
}
status = nodnic_cmd_read(device_priv, 0x0, &buffer);
MLX_CHECK_STATUS(device_priv, status, read_err, "failed to read fw revision major and minor");
*fw_ver_minor = (mlx_uint16)(buffer >> 16);
*fw_ver_major = (mlx_uint16)buffer;
status = nodnic_cmd_read(device_priv, 0x4, &buffer);
MLX_CHECK_STATUS(device_priv, status, read_err, "failed to read fw revision sub minor");
*fw_ver_sub_minor = (mlx_uint16)buffer;
read_err:
parm_err:
return status;
}

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,113 @@
#ifndef MLXUTILS_INCLUDE_PRIVATE_MEMORYPRIV_H_
#define MLXUTILS_INCLUDE_PRIVATE_MEMORYPRIV_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../../mlx_utils/include/public/mlx_utils.h"
mlx_status
mlx_memory_alloc_priv(
IN mlx_utils *utils,
IN mlx_size size,
OUT mlx_void **ptr
);
mlx_status
mlx_memory_zalloc_priv(
IN mlx_utils *utils,
IN mlx_size size,
OUT mlx_void **ptr
);
mlx_status
mlx_memory_free_priv(
IN mlx_utils *utils,
IN mlx_void *ptr
);
mlx_status
mlx_memory_alloc_dma_priv(
IN mlx_utils *utils,
IN mlx_size size ,
IN mlx_size align,
OUT mlx_void **ptr
);
mlx_status
mlx_memory_free_dma_priv(
IN mlx_utils *utils,
IN mlx_size size ,
IN mlx_void *ptr
);
mlx_status
mlx_memory_map_dma_priv(
IN mlx_utils *utils,
IN mlx_void *addr ,
IN mlx_size number_of_bytes,
OUT mlx_physical_address *phys_addr,
OUT mlx_void **mapping
);
mlx_status
mlx_memory_ummap_dma_priv(
IN mlx_utils *utils,
IN mlx_void *mapping
);
mlx_status
mlx_memory_cmp_priv(
IN mlx_utils *utils,
IN mlx_void *first_block,
IN mlx_void *second_block,
IN mlx_size size,
OUT mlx_uint32 *out
);
mlx_status
mlx_memory_set_priv(
IN mlx_utils *utils,
IN mlx_void *block,
IN mlx_int32 value,
IN mlx_size size
);
mlx_status
mlx_memory_cpy_priv(
IN mlx_utils *utils,
OUT mlx_void *destination_buffer,
IN mlx_void *source_buffer,
IN mlx_size length
);
mlx_status
mlx_memory_cpu_to_be32_priv(
IN mlx_utils *utils,
IN mlx_uint32 source,
IN mlx_uint32 *destination
);
mlx_status
mlx_memory_be32_to_cpu_priv(
IN mlx_utils *utils,
IN mlx_uint32 source,
IN mlx_uint32 *destination
);
#endif /* STUB_MLXUTILS_INCLUDE_PRIVATE_MEMORYPRIV_H_ */

View File

@ -0,0 +1,72 @@
#ifndef STUB_MLXUTILS_INCLUDE_PRIVATE_PCIPRIV_H_
#define STUB_MLXUTILS_INCLUDE_PRIVATE_PCIPRIV_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../include/public/mlx_pci.h"
#include "../../include/public/mlx_utils.h"
mlx_status
mlx_pci_init_priv(
IN mlx_utils *utils
);
mlx_status
mlx_pci_read_priv(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint32 offset,
IN mlx_uintn count,
OUT mlx_void *buffer
);
mlx_status
mlx_pci_write_priv(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint32 offset,
IN mlx_uintn count,
IN mlx_void *buffer
);
mlx_status
mlx_pci_mem_read_priv(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint8 bar_index,
IN mlx_uint64 offset,
IN mlx_uintn count,
OUT mlx_void *buffer
);
mlx_status
mlx_pci_mem_write_priv(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint8 bar_index,
IN mlx_uint64 offset,
IN mlx_uintn count,
IN mlx_void *buffer
);
#endif /* STUB_MLXUTILS_INCLUDE_PRIVATE_PCIPRIV_H_ */

View File

@ -0,0 +1,68 @@
#ifndef SRC_DRIVERS_INFINIBAND_MLX_UTILS_INCLUDE_PRIVATE_MLX_UTILS_PRIV_H_
#define SRC_DRIVERS_INFINIBAND_MLX_UTILS_INCLUDE_PRIVATE_MLX_UTILS_PRIV_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../include/public/mlx_utils.h"
mlx_status
mlx_utils_delay_in_ms_priv(
IN mlx_uint32 msecs
);
mlx_status
mlx_utils_delay_in_us_priv(
IN mlx_uint32 usecs
);
mlx_status
mlx_utils_ilog2_priv(
IN mlx_uint32 i,
OUT mlx_uint32 *log
);
mlx_status
mlx_utils_init_lock_priv(
OUT void **lock
);
mlx_status
mlx_utils_free_lock_priv(
IN void *lock
);
mlx_status
mlx_utils_acquire_lock_priv (
IN void *lock
);
mlx_status
mlx_utils_release_lock_priv (
IN void *lock
);
mlx_status
mlx_utils_rand_priv (
IN mlx_utils *utils,
OUT mlx_uint32 *rand_num
);
#endif /* SRC_DRIVERS_INFINIBAND_MLX_UTILS_INCLUDE_PRIVATE_MLX_UTILS_PRIV_H_ */

View File

@ -0,0 +1,47 @@
#ifndef INCLUDE_PUBLIC_MLXBAIL_H_
#define INCLUDE_PUBLIC_MLXBAIL_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_types.h"
#define MLX_BAIL_ERROR(id, status,message) MLX_CHECK_STATUS(id, status, bail, message)
#define MLX_FATAL_CHECK_STATUS(status, label, message) \
do { \
if (status != MLX_SUCCESS) { \
MLX_DEBUG_FATAL_ERROR(message " (Status = %d)\n", status); \
goto label; \
} \
} while (0)
#define MLX_CHECK_STATUS(id, status, label, message) \
do { \
if (status != MLX_SUCCESS) { \
MLX_DEBUG_ERROR(id, message " (Status = %d)\n", status);\
goto label; \
} \
} while (0)
#endif /* INCLUDE_PUBLIC_MLXBAIL_H_ */

View File

@ -0,0 +1,63 @@
#ifndef MLXUTILS_INCLUDE_PUBLIC_MLX_ICMD_H_
#define MLXUTILS_INCLUDE_PUBLIC_MLX_ICMD_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_utils.h"
#define MLX_ICMD_MB_ADDR 0x100000
#define MLX_ICMD_MB_SIZE_ADDR 0x1000
#define MLX_ICMD_CTRL_ADDR 0x0
#define MLX_ICMD_SEMAPHORE_ADDR 0x0
#define MLX_ICMD_SEMAPHORE_ID 1234
enum {
FLASH_REG_ACCESS = 0x9001,
GET_FW_INFO = 0x8007,
QUERY_VIRTUAL_MAC = 0x9003,
SET_VIRTUAL_MAC = 0x9004,
QUERY_WOL_ROL = 0x9005,
SET_WOL_ROL = 0x9006,
OCBB_INIT = 0x9007,
OCBB_QUERY_HEADER_STATUS = 0x9008,
OCBB_QUERY_ETOC_STATUS = 0x9009,
OCBB_QUERY_SET_EVENT = 0x900A,
OCSD_INIT = 0xf004,
};
struct mlx_icmd_ocsd {
mlx_uint32 reserved;
mlx_uint64 address;
};
mlx_status
mlx_icmd_send_command(
IN mlx_utils *utils,
IN mlx_uint16 opcode,
IN OUT mlx_void* data,
IN mlx_uint32 write_data_size,
IN mlx_uint32 read_data_size
);
#endif /* MLXUTILS_INCLUDE_PUBLIC_MLX_ICMD_H_ */

View File

@ -0,0 +1,46 @@
#ifndef PUBLIC_INCLUDE_MLX_LOGGER_H_
#define PUBLIC_INCLUDE_MLX_LOGGER_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../../mlx_utils_flexboot/include/mlx_logging_priv.h"
#define MLX_DEBUG_FATAL_ERROR(...) MLX_DEBUG_FATAL_ERROR_PRIVATE(__VA_ARGS__)
#define MLX_DEBUG_ERROR(...) MLX_DEBUG_ERROR_PRIVATE(__VA_ARGS__)
#define MLX_DEBUG_WARN(...) MLX_DEBUG_WARN_PRIVATE(__VA_ARGS__)
#define MLX_DEBUG_INFO1(...) MLX_DEBUG_INFO1_PRIVATE(__VA_ARGS__)
#define MLX_DEBUG_INFO2(...) MLX_DEBUG_INFO2_PRIVATE(__VA_ARGS__)
#define MLX_DBG_ERROR(...) MLX_DBG_ERROR_PRIVATE(__VA_ARGS__)
#define MLX_DBG_WARN(...) MLX_DBG_WARN_PRIVATE(__VA_ARGS__)
#define MLX_DBG_INFO1(...) MLX_DBG_INFO1_PRIVATE(__VA_ARGS__)
#define MLX_DBG_INFO2(...) MLX_DBG_INFO2_PRIVATE(__VA_ARGS__)
#define MLX_TRACE_1_START() MLX_DBG_INFO1_PRIVATE("Start\n")
#define MLX_TRACE_1_END() MLX_DBG_INFO1_PRIVATE("End\n")
#define MLX_TRACE_1_END_STATUS(status) MLX_DBG_INFO1_PRIVATE("End (%s=%d)\n", #status,status)
#define MLX_TRACE_2_START() MLX_DBG_INFO2_PRIVATE("Start\n")
#define MLX_TRACE_2_END() MLX_DBG_INFO2_PRIVATE("End\n")
#define MLX_TRACE_2_END_STATUS(status) MLX_DBG_INFO2_PRIVATE("End (%s=%d)\n", #status,status)
#endif /* PUBLIC_INCLUDE_MLX_LOGGER_H_ */

View File

@ -0,0 +1,115 @@
#ifndef MLXUTILS_INCLUDE_PUBLIC_MEMORY_H_
#define MLXUTILS_INCLUDE_PUBLIC_MEMORY_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_utils.h"
mlx_status
mlx_memory_alloc(
IN mlx_utils *utils,
IN mlx_size size,
OUT mlx_void **ptr
);
mlx_status
mlx_memory_zalloc(
IN mlx_utils *utils,
IN mlx_size size,
OUT mlx_void **ptr
);
mlx_status
mlx_memory_free(
IN mlx_utils *utils,
IN mlx_void **ptr
);
mlx_status
mlx_memory_alloc_dma(
IN mlx_utils *utils,
IN mlx_size size ,
IN mlx_size align,
OUT mlx_void **ptr
);
mlx_status
mlx_memory_free_dma(
IN mlx_utils *utils,
IN mlx_size size ,
IN mlx_void **ptr
);
mlx_status
mlx_memory_map_dma(
IN mlx_utils *utils,
IN mlx_void *Addr ,
IN mlx_size NumberOfBytes,
OUT mlx_physical_address *PhysAddr,
OUT mlx_void **Mapping
);
mlx_status
mlx_memory_ummap_dma(
IN mlx_utils *utils,
IN mlx_void *Mapping
);
mlx_status
mlx_memory_cmp(
IN mlx_utils *utils,
IN mlx_void *first_block,
IN mlx_void *second_block,
IN mlx_size size,
OUT mlx_uint32 *out
);
mlx_status
mlx_memory_set(
IN mlx_utils *utils,
IN mlx_void *block,
IN mlx_int32 value,
IN mlx_size size
);
mlx_status
mlx_memory_cpy(
IN mlx_utils *utils,
OUT mlx_void *destination_buffer,
IN mlx_void *source_buffer,
IN mlx_size length
);
mlx_status
mlx_memory_cpu_to_be32(
IN mlx_utils *utils,
IN mlx_uint32 source,
IN mlx_uint32 *destination
);
mlx_status
mlx_memory_be32_to_cpu(
IN mlx_utils *utils,
IN mlx_uint32 source,
IN mlx_uint32 *destination
);
#endif /* STUB_MLXUTILS_INCLUDE_PUBLIC_MEMORY_H_ */

View File

@ -0,0 +1,78 @@
#ifndef STUB_MLXUTILS_INCLUDE_PUBLIC_PCI_H_
#define STUB_MLXUTILS_INCLUDE_PUBLIC_PCI_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_utils.h"
typedef enum {
MlxPciWidthUint8 = 0,
MlxPciWidthUint16,
MlxPciWidthUint32,
MlxPciWidthUint64,
} mlx_pci_width;
mlx_status
mlx_pci_init(
IN mlx_utils *utils
);
mlx_status
mlx_pci_read(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint32 offset,
IN mlx_uintn count,
OUT mlx_void *buffer
);
mlx_status
mlx_pci_write(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint32 offset,
IN mlx_uintn count,
IN mlx_void *buffer
);
mlx_status
mlx_pci_mem_read(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint8 bar_index,
IN mlx_uint64 offset,
IN mlx_uintn count,
OUT mlx_void *buffer
);
mlx_status
mlx_pci_mem_write(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint8 bar_index,
IN mlx_uint64 offset,
IN mlx_uintn count,
IN mlx_void *buffer
);
#endif /* STUB_MLXUTILS_INCLUDE_PUBLIC_PCI_H_ */

View File

@ -0,0 +1,81 @@
#ifndef INCLUDE_PUBLIC_MLX_PCI_GW_H_
#define INCLUDE_PUBLIC_MLX_PCI_GW_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_utils.h"
#define PCI_GW_FIRST_CAPABILITY_POINTER_OFFSET 0x34
#define PCI_GW_CAPABILITY_ID 0x9
#define PCI_GW_CAPABILITY_ID_OFFSET 0x0
#define PCI_GW_CAPABILITY_NEXT_POINTER_OFFSET 0x1
#define PCI_GW_CAPABILITY_SPACE_OFFSET 0x4
#define PCI_GW_CAPABILITY_STATUS_OFFSET 0x7
#define PCI_GW_CAPABILITY_COUNTER_OFFSET 0x8
#define PCI_GW_CAPABILITY_SEMAPHORE_OFFSET 0xC
#define PCI_GW_CAPABILITY_ADDRESS_OFFSET 0x10
#define PCI_GW_CAPABILITY_FLAG_OFFSET 0x10
#define PCI_GW_CAPABILITY_DATA_OFFSET 0x14
#define PCI_GW_SEMPHORE_TRIES 3000000
#define PCI_GW_GET_OWNERSHIP_TRIES 5000
#define PCI_GW_READ_FLAG_TRIES 3000000
#define PCI_GW_WRITE_FLAG 0x80000000
#define PCI_GW_SPACE_NODNIC 0x4
#define PCI_GW_SPACE_ALL_ICMD 0x3
#define PCI_GW_SPACE_SEMAPHORE 0xa
#define PCI_GW_SPACE_CR0 0x2
typedef mlx_uint32 mlx_pci_gw_buffer;
mlx_status
mlx_pci_gw_init(
IN mlx_utils *utils
);
mlx_status
mlx_pci_gw_teardown(
IN mlx_utils *utils
);
mlx_status
mlx_pci_gw_read(
IN mlx_utils *utils,
IN mlx_pci_gw_space space,
IN mlx_uint32 address,
OUT mlx_pci_gw_buffer *buffer
);
mlx_status
mlx_pci_gw_write(
IN mlx_utils *utils,
IN mlx_pci_gw_space space,
IN mlx_uint32 address,
IN mlx_pci_gw_buffer buffer
);
#endif /* INCLUDE_PUBLIC_MLX_PCI_GW_H_ */

View File

@ -0,0 +1,27 @@
#ifndef INCLUDE_PUBLIC_MLXTYPES_H_
#define INCLUDE_PUBLIC_MLXTYPES_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../../mlx_utils_flexboot/include/mlx_types_priv.h"
#endif /* INCLUDE_PUBLIC_MLXBAIL_H_ */

View File

@ -0,0 +1,106 @@
#ifndef MLXUTILS_INCLUDE_PUBLIC_MLXUTILS_H_
#define MLXUTILS_INCLUDE_PUBLIC_MLXUTILS_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_logging.h"
#include "mlx_types.h"
#define IN
#define OUT
typedef mlx_uint16 mlx_pci_gw_space;
typedef struct{
mlx_uint32 pci_cmd_offset;
mlx_pci_gw_space space;
} __attribute__ (( packed )) mlx_pci_gw;
typedef struct {
mlx_boolean icmd_opened;
mlx_boolean took_semaphore;
mlx_uint32 max_cmd_size;
} __attribute__ (( packed )) mlx_icmd ;
typedef struct{
mlx_pci *pci;
mlx_pci_gw pci_gw;
mlx_icmd icmd;
void *lock;
#ifdef DEVICE_CX3
/* ACCESS to BAR0 */
void *config;
#endif
} __attribute__ (( packed )) mlx_utils;
mlx_status
mlx_utils_init(
IN mlx_utils *utils,
IN mlx_pci *pci
);
mlx_status
mlx_utils_teardown(
IN mlx_utils *utils
);
mlx_status
mlx_utils_delay_in_ms(
IN mlx_uint32 msecs
);
mlx_status
mlx_utils_delay_in_us(
IN mlx_uint32 usecs
);
mlx_status
mlx_utils_ilog2(
IN mlx_uint32 i,
OUT mlx_uint32 *log
);
mlx_status
mlx_utils_init_lock(
IN OUT mlx_utils *utils
);
mlx_status
mlx_utils_free_lock(
IN OUT mlx_utils *utils
);
mlx_status
mlx_utils_acquire_lock (
IN OUT mlx_utils *utils
);
mlx_status
mlx_utils_release_lock (
IN OUT mlx_utils *utils
);
mlx_status
mlx_utils_rand (
IN mlx_utils *utils,
OUT mlx_uint32 *rand_num
);
#endif /* STUB_MLXUTILS_INCLUDE_PUBLIC_MLXUTILS_H_ */

View File

@ -0,0 +1,54 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../mlx_lib/mlx_blink_leds/mlx_blink_leds.h"
#include "../../include/public/mlx_memory.h"
#include "../../include/public/mlx_bail.h"
mlx_status
mlx_blink_leds(
IN mlx_utils *utils,
IN mlx_uint16 secs
)
{
mlx_status status = MLX_SUCCESS;
struct mlx_led_control led_control;
mlx_uint32 reg_status;
if (utils == NULL ) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
mlx_memory_set(utils, &led_control, 0, sizeof(led_control));
led_control.beacon_duration = secs;
status = mlx_reg_access(utils, REG_ID_MLCR, REG_ACCESS_WRITE, &led_control, sizeof(led_control),
&reg_status);
MLX_CHECK_STATUS(utils, status, reg_err, "mlx_reg_access failed ");
if (reg_status != 0) {
MLX_DEBUG_ERROR(utils,"mlx_reg_access failed with status = %d\n", reg_status);
status = MLX_FAILED;
goto reg_err;
}
reg_err:
bad_param:
return status;
}

View File

@ -0,0 +1,46 @@
#ifndef MLX_BLINK_LEDS_H_
#define MLX_BLINK_LEDS_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../mlx_lib/mlx_reg_access/mlx_reg_access.h"
#include "../../include/public/mlx_utils.h"
struct mlx_led_control {
mlx_uint32 reserved1 :16;
mlx_uint32 port :8;
mlx_uint32 bla :8;
/* -------------- */
mlx_uint32 beacon_duration :16;
mlx_uint32 reserved2 :16;
/* -------------- */
mlx_uint32 beacon_remain :16;
mlx_uint32 reserved3 :16;
};
mlx_status
mlx_blink_leds(
IN mlx_utils *utils,
IN mlx_uint16 secs
);
#endif /* MLX_NVCONFIG_H_ */

View File

@ -0,0 +1,180 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../mlx_lib/mlx_link_speed/mlx_link_speed.h"
#include "../../include/public/mlx_memory.h"
#include "../../include/public/mlx_bail.h"
mlx_status
mlx_set_link_speed(
IN mlx_utils *utils,
IN mlx_uint8 port_num,
IN LINK_SPEED_TYPE type,
IN LINK_SPEED speed
)
{
mlx_status status = MLX_SUCCESS;
struct mlx_link_speed link_speed;
mlx_uint32 reg_status;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
mlx_memory_set(utils, &link_speed, 0, sizeof(link_speed));
link_speed.loacl_port = port_num;
link_speed.proto_mask = 1 << type;
status = mlx_reg_access(utils, REG_ID_PTYS, REG_ACCESS_READ, &link_speed,
sizeof(link_speed), &reg_status);
MLX_CHECK_STATUS(utils, status, reg_err, "mlx_reg_access failed ");
if (reg_status != 0) {
MLX_DEBUG_ERROR(utils,"mlx_reg_access failed with status = %d\n", reg_status);
status = MLX_FAILED;
goto reg_err;
}
switch (speed) {
case LINK_SPEED_1GB:
link_speed.eth_proto_admin = link_speed.eth_proto_capability & LINK_SPEED_1GB_MASK;
break;
case LINK_SPEED_10GB:
link_speed.eth_proto_admin = link_speed.eth_proto_capability & LINK_SPEED_10GB_MASK;
break;
case LINK_SPEED_40GB:
link_speed.eth_proto_admin = link_speed.eth_proto_capability & LINK_SPEED_40GB_MASK;
break;
case LINK_SPEED_100GB:
link_speed.eth_proto_admin = link_speed.eth_proto_capability & LINK_SPEED_100GB_MASK;
break;
case LINK_SPEED_SDR:
link_speed.ib_proto_admin = link_speed.ib_proto_capability & LINK_SPEED_SDR_MASK;
break;
case LINK_SPEED_DEFAULT:
if (type == LINK_SPEED_ETH) {
link_speed.eth_proto_admin = link_speed.eth_proto_capability;
} else {
link_speed.ib_proto_admin = link_speed.ib_proto_capability;
}
break;
}
status = mlx_reg_access(utils, REG_ID_PTYS, REG_ACCESS_WRITE, &link_speed,
sizeof(link_speed), &reg_status);
MLX_CHECK_STATUS(utils, status, reg_err, "mlx_reg_access failed ");
if (reg_status != 0) {
MLX_DEBUG_ERROR(utils,"mlx_reg_access failed with status = %d\n", reg_status);
status = MLX_FAILED;
goto reg_err;
}
reg_err:
bad_param:
return status;
}
mlx_status
mlx_get_max_speed(
IN mlx_utils *utils,
IN mlx_uint8 port_num,
IN LINK_SPEED_TYPE type,
OUT mlx_uint64 *speed
)
{
mlx_status status = MLX_SUCCESS;
struct mlx_link_speed link_speed;
mlx_uint32 reg_status;
mlx_uint64 speed_giga = 0;
mlx_uint8 lanes_number = 1;
*speed = 0;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
mlx_memory_set(utils, &link_speed, 0, sizeof(link_speed));
link_speed.loacl_port = port_num;
link_speed.proto_mask = 1 << type;
status = mlx_reg_access(utils, REG_ID_PTYS, REG_ACCESS_READ, &link_speed,
sizeof(link_speed), &reg_status);
MLX_CHECK_STATUS(utils, status, reg_err, "mlx_reg_access failed ");
if (reg_status != 0) {
MLX_DEBUG_ERROR(utils,"mlx_reg_access failed with status = %d\n", reg_status);
status = MLX_FAILED;
goto reg_err;
}
if ( type == LINK_SPEED_ETH ) {
if ( link_speed.eth_proto_capability & LINK_SPEED_100GB_MASK ) {
speed_giga = 100;
} else if ( link_speed.eth_proto_capability & LINK_SPEED_56GB_MASK ) {
speed_giga = 56;
} else if ( link_speed.eth_proto_capability & LINK_SPEED_50GB_MASK ) {
speed_giga = 50;
} else if ( link_speed.eth_proto_capability & LINK_SPEED_40GB_MASK ) {
speed_giga = 40;
} else if (link_speed.eth_proto_capability & LINK_SPEED_25GB_MASK) {
speed_giga = 25;
} else if ( link_speed.eth_proto_capability & LINK_SPEED_20GB_MASK ) {
speed_giga = 20;
} else if ( link_speed.eth_proto_capability & LINK_SPEED_10GB_MASK) {
speed_giga = 10;
} else if ( link_speed.eth_proto_capability & LINK_SPEED_1GB_MASK ) {
speed_giga = 1;
}
} else {
if ( link_speed.ib_proto_capability & LINK_SPEED_EDR_MASK ) {
speed_giga = 25;
} else if ( link_speed.ib_proto_capability & LINK_SPEED_EDR20_MASK ) {
speed_giga = 20;
} else if ( link_speed.ib_proto_capability & LINK_SPEED_FDR_MASK ) {
speed_giga = 14;
} else if ( link_speed.ib_proto_capability & LINK_SPEED_QDR_MASK ) {
speed_giga = 10;
} else if ( link_speed.ib_proto_capability & LINK_SPEED_DDR_MASK ) {
speed_giga = 5;
} else if ( link_speed.ib_proto_capability & LINK_SPEED_SDR_MASK ) {
speed_giga = 2.5;
}
if ( link_speed.ib_link_width_capability & LINK_SPEED_WITDH_12_MASK ) {
lanes_number = 12;
} else if ( link_speed.ib_link_width_capability & LINK_SPEED_WITDH_8_MASK ) {
lanes_number = 8;
} else if (link_speed.ib_link_width_capability & LINK_SPEED_WITDH_4_MASK ) {
lanes_number = 4;
} else if (link_speed.ib_link_width_capability & LINK_SPEED_WITDH_2_MASK ) {
lanes_number = 2;
} else if (link_speed.ib_link_width_capability & LINK_SPEED_WITDH_1_MASK ) {
lanes_number = 1;
}
speed_giga = speed_giga * lanes_number;
}
// Return data in bits
*speed = speed_giga * GIGA_TO_BIT;
reg_err:
bad_param:
return status;
}

View File

@ -0,0 +1,145 @@
#ifndef MLX_LINK_SPEED_H_
#define MLX_LINK_SPEED_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../mlx_lib/mlx_reg_access/mlx_reg_access.h"
#include "../../include/public/mlx_utils.h"
#define LINK_SPEED_100GB_MASK (ETH_SPEED_ENABLE_MASK_100GBASECR4 | ETH_SPEED_ENABLE_MASK_100GBASESR4 | ETH_SPEED_ENABLE_MASK_100GBASEKR4 | ETH_SPEED_ENABLE_MASK_100GBASELR4)
#define LINK_SPEED_56GB_MASK (ETH_SPEED_ENABLE_MASK_56GBASER4)
#define LINK_SPEED_50GB_MASK (ETH_SPEED_ENABLE_MASK_50GBASECR2 | ETH_SPEED_ENABLE_MASK_50GBASEKR2)
#define LINK_SPEED_40GB_MASK (ETH_SPEED_ENABLE_MASK_40GBASECR4 | ETH_SPEED_ENABLE_MASK_40GBASEKR4 | ETH_SPEED_ENABLE_MASK_40GBASESR4 | ETH_SPEED_ENABLE_MASK_40GBASELR4)
#define LINK_SPEED_25GB_MASK (ETH_SPEED_ENABLE_MASK_25GBASECR | ETH_SPEED_ENABLE_MASK_25GBASEKR | ETH_SPEED_ENABLE_MASK_25GBASESR)
#define LINK_SPEED_20GB_MASK (ETH_SPEED_ENABLE_MASK_20GBASER2)
#define LINK_SPEED_10GB_MASK (ETH_SPEED_ENABLE_MASK_10GBASECR | ETH_SPEED_ENABLE_MASK_10GBASESR | ETH_SPEED_ENABLE_MASK_10GBASELR | ETH_SPEED_ENABLE_MASK_10GBASEKR)
#define LINK_SPEED_1GB_MASK (ETH_SPEED_ENABLE_MASK_1000BASECX | ETH_SPEED_ENABLE_MASK_1000BASEKX | ETH_SPEED_ENABLE_MASK_100BaseTX | ETH_SPEED_ENABLE_MASK_1000BASET)
#define LINK_SPEED_SDR_MASK 0x1
#define LINK_SPEED_DDR_MASK 0x2
#define LINK_SPEED_QDR_MASK 0xC
#define LINK_SPEED_FDR_MASK 0x10
#define LINK_SPEED_EDR20_MASK 0x200
#define LINK_SPEED_EDR_MASK 0x20
#define LINK_SPEED_WITDH_1_MASK 0x1
#define LINK_SPEED_WITDH_2_MASK 0x2
#define LINK_SPEED_WITDH_4_MASK 0x4
#define LINK_SPEED_WITDH_8_MASK 0x8
#define LINK_SPEED_WITDH_12_MASK 0x10
#define GIGA_TO_BIT 0x40000000
enum {
ETH_SPEED_ENABLE_MASK_1000BASECX = 0x0001,
ETH_SPEED_ENABLE_MASK_1000BASEKX = 0x0002,
ETH_SPEED_ENABLE_MASK_10GBASECX4 = 0x0004,
ETH_SPEED_ENABLE_MASK_10GBASEKX4 = 0x0008,
ETH_SPEED_ENABLE_MASK_10GBASEKR = 0x0010,
ETH_SPEED_ENABLE_MASK_20GBASER2 = 0x0020,
ETH_SPEED_ENABLE_MASK_40GBASECR4 = 0x0040,
ETH_SPEED_ENABLE_MASK_40GBASEKR4 = 0x0080,
ETH_SPEED_ENABLE_MASK_56GBASER4 = 0x0100,
ETH_SPEED_ENABLE_MASK_10GBASECR = 0x1000,
ETH_SPEED_ENABLE_MASK_10GBASESR = 0x2000,
ETH_SPEED_ENABLE_MASK_10GBASELR = 0x4000,
ETH_SPEED_ENABLE_MASK_40GBASESR4 = 0x8000,
ETH_SPEED_ENABLE_MASK_40GBASELR4 = 0x10000,
ETH_SPEED_ENABLE_MASK_50GBASEKR4 = 0x80000,
ETH_SPEED_ENABLE_MASK_100GBASECR4 = 0x100000,
ETH_SPEED_ENABLE_MASK_100GBASESR4 = 0x200000,
ETH_SPEED_ENABLE_MASK_100GBASEKR4 = 0x400000,
ETH_SPEED_ENABLE_MASK_100GBASELR4 = 0x800000,
ETH_SPEED_ENABLE_MASK_100BaseTX = 0x1000000,
ETH_SPEED_ENABLE_MASK_1000BASET = 0x2000000,
ETH_SPEED_ENABLE_MASK_10GBASET = 0x4000000,
ETH_SPEED_ENABLE_MASK_25GBASECR = 0x8000000,
ETH_SPEED_ENABLE_MASK_25GBASEKR = 0x10000000,
ETH_SPEED_ENABLE_MASK_25GBASESR = 0x20000000,
ETH_SPEED_ENABLE_MASK_50GBASECR2 = 0x40000000,
ETH_SPEED_ENABLE_MASK_50GBASEKR2 = 0x80000000,
ETH_SPEED_ENABLE_MASK_BAD = 0xffff,
};
typedef enum {
LINK_SPEED_IB = 0,
LINK_SPEED_FC,
LINK_SPEED_ETH,
} LINK_SPEED_TYPE;
typedef enum {
LINK_SPEED_1GB = 0,
LINK_SPEED_10GB,
LINK_SPEED_40GB,
LINK_SPEED_100GB,
LINK_SPEED_SDR,
LINK_SPEED_DEFAULT,
} LINK_SPEED;
struct mlx_link_speed {
mlx_uint32 proto_mask :3;
mlx_uint32 reserved1 :13;
mlx_uint32 loacl_port :8;
mlx_uint32 reserved2 :8;
/* -------------- */
mlx_uint32 reserved3 :32;
/* -------------- */
mlx_uint32 reserved4 :32;
/* -------------- */
mlx_uint32 eth_proto_capability :32;
/* -------------- */
mlx_uint32 ib_proto_capability :16;
mlx_uint32 ib_link_width_capability :16;
/* -------------- */
mlx_uint32 reserved5 :32;
/* -------------- */
mlx_uint32 eth_proto_admin :32;
/* -------------- */
mlx_uint32 ib_proto_admin :16;
mlx_uint32 ib_link_width_admin :16;
/* -------------- */
mlx_uint32 reserved6 :32;
/* -------------- */
mlx_uint32 eth_proto_oper :32;
/* -------------- */
mlx_uint32 ib_proto_oper :16;
mlx_uint32 ib_link_width_oper :16;
};
mlx_status
mlx_set_link_speed(
IN mlx_utils *utils,
IN mlx_uint8 port_num,
IN LINK_SPEED_TYPE type,
IN LINK_SPEED speed
);
mlx_status
mlx_get_max_speed(
IN mlx_utils *utils,
IN mlx_uint8 port_num,
IN LINK_SPEED_TYPE type,
OUT mlx_uint64 *speed
);
#endif /* MLX_LINK_SPEED_H_ */

View File

@ -0,0 +1,60 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_mtu.h"
#include "mlx_memory.h"
#include "mlx_bail.h"
mlx_status
mlx_get_max_mtu(
IN mlx_utils *utils,
IN mlx_uint8 port_num,
OUT mlx_uint32 *max_mtu
)
{
mlx_status status = MLX_SUCCESS;
struct mlx_mtu mtu;
mlx_uint32 reg_status;
*max_mtu = 0;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
mlx_memory_set(utils, &mtu, 0, sizeof(mtu));
mtu.local_port = port_num;
status = mlx_reg_access(utils, REG_ID_PMTU, REG_ACCESS_READ, &mtu,
sizeof(mtu), &reg_status);
MLX_CHECK_STATUS(utils, status, reg_err, "mlx_reg_access failed ");
if (reg_status != 0) {
MLX_DEBUG_ERROR(utils,"mlx_reg_access failed with status = %d\n", reg_status);
status = MLX_FAILED;
goto reg_err;
}
// Return data in bits
*max_mtu = mtu.max_mtu * BYTE_TO_BIT;
reg_err:
bad_param:
return status;
}

View File

@ -0,0 +1,52 @@
#ifndef MLX_MTU_H_
#define MLX_MTU_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_reg_access.h"
#include "mlx_utils.h"
#define BYTE_TO_BIT 0x8
struct mlx_mtu {
mlx_uint32 reserved1 :16;
mlx_uint32 local_port :8;
mlx_uint32 reserved2 :8;
/* -------------- */
mlx_uint32 reserved3 :16;
mlx_uint32 max_mtu :16;
/* -------------- */
mlx_uint32 reserved4 :16;
mlx_uint32 admin_mtu :16;
/* -------------- */
mlx_uint32 reserved5 :16;
mlx_uint32 oper_mtu :16;
};
mlx_status
mlx_get_max_mtu(
IN mlx_utils *utils,
IN mlx_uint8 port_num,
OUT mlx_uint32 *max_mtu
);
#endif /* MLX_MTU_H_ */

View File

@ -0,0 +1,295 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../mlx_lib/mlx_nvconfig/mlx_nvconfig.h"
#include "../../include/public/mlx_memory.h"
#include "../../include/public/mlx_bail.h"
#define TlvMappingEntry( _tlv_type, _real_tlv_type, _class_code, _fw_reset_needed) { \
.tlv_type = _tlv_type, \
.real_tlv_type = _real_tlv_type, \
.class_code = _class_code, \
.fw_reset_needed = _fw_reset_needed, \
}
struct nvconfig_tlv_mapping nvconfig_tlv_mapping[] = {
TlvMappingEntry(0x10, 0x10, NVRAM_TLV_CLASS_HOST, TRUE),
TlvMappingEntry(0x12, 0x12, NVRAM_TLV_CLASS_PHYSICAL_PORT, TRUE),
TlvMappingEntry(0x80, 0x80, NVRAM_TLV_CLASS_GLOBAL, TRUE),
TlvMappingEntry(0x81, 0x81, NVRAM_TLV_CLASS_GLOBAL, TRUE),
TlvMappingEntry(0x100, 0x100, NVRAM_TLV_CLASS_GLOBAL, TRUE),
TlvMappingEntry(0x2001, 0x195, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2010, 0x210, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2011, 0x211, NVRAM_TLV_CLASS_GLOBAL, FALSE),
TlvMappingEntry(0x2020, 0x2020, NVRAM_TLV_CLASS_PHYSICAL_PORT, FALSE),
TlvMappingEntry(0x2021, 0x221, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2023, 0x223, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2100, 0x230, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2101, 0x231, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2102, 0x232, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2103, 0x233, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2104, 0x234, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2105, 0x235, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2106, 0x236, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2107, 0x237, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2108, 0x238, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2109, 0x239, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x210A, 0x23A, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2200, 0x240, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2201, 0x241, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2202, 0x242, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2203, 0x243, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2204, 0x244, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2205, 0x245, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0x2207, 0x247, NVRAM_TLV_CLASS_HOST, FALSE),
TlvMappingEntry(0, 0, 0, 0),
};
static
mlx_status
nvconfig_set_fw_reset_level(
IN mlx_utils *utils,
IN mlx_uint16 tlv_type
)
{
#define WARM_REBOOT_RESET ((mlx_uint64)0x1 << 38)
mlx_status status = MLX_SUCCESS;
mlx_uint32 reg_status;
mlx_uint64 mfrl = WARM_REBOOT_RESET ;
mlx_uint8 index = 0;
mlx_boolean reset_needed = FALSE;
for (index = 0 ; nvconfig_tlv_mapping[index].tlv_type != 0 ; index++) {
if (nvconfig_tlv_mapping[index].tlv_type == tlv_type) {
reset_needed = nvconfig_tlv_mapping[index].fw_reset_needed;
}
}
if (reset_needed == FALSE) {
goto no_fw_reset_needed;
}
status = mlx_reg_access(utils, REG_ID_MFRL, REG_ACCESS_WRITE, &mfrl, sizeof(mfrl),
&reg_status);
MLX_CHECK_STATUS(utils, status, reg_err, "mlx_reg_access failed ");
if (reg_status != 0) {
MLX_DEBUG_ERROR(utils,"nvconfig_set_fw_reset_level failed with status = %d\n", reg_status);
status = MLX_FAILED;
goto reg_err;
}
reg_err:
no_fw_reset_needed:
return status;
}
static
mlx_status
nvconfig_get_tlv_type_and_class(
IN mlx_uint16 tlv_type,
OUT mlx_uint16 *real_tlv_type,
OUT NVRAM_CLASS_CODE *class_code
)
{
mlx_uint8 index = 0;
for ( ; nvconfig_tlv_mapping[index].tlv_type != 0 ; index ++) {
if ( nvconfig_tlv_mapping[index].tlv_type == tlv_type) {
*real_tlv_type = nvconfig_tlv_mapping[index].real_tlv_type;
*class_code = nvconfig_tlv_mapping[index].class_code;
return MLX_SUCCESS;
}
}
return MLX_NOT_FOUND;
}
static
void
nvconfig_fill_tlv_type(
IN mlx_uint8 port,
IN NVRAM_CLASS_CODE class_code,
IN mlx_uint16 tlv_type,
OUT union nvconfig_tlv_type *nvconfig_tlv_type
)
{
switch (class_code) {
case NVRAM_TLV_CLASS_GLOBAL:
nvconfig_tlv_type->global.param_class = NVRAM_TLV_CLASS_GLOBAL;
nvconfig_tlv_type->global.param_idx = tlv_type;
break;
case NVRAM_TLV_CLASS_HOST:
nvconfig_tlv_type->per_host.param_class = NVRAM_TLV_CLASS_HOST;
nvconfig_tlv_type->per_host.param_idx = tlv_type;
break;
case NVRAM_TLV_CLASS_PHYSICAL_PORT:
nvconfig_tlv_type->per_port.param_class = NVRAM_TLV_CLASS_PHYSICAL_PORT;
nvconfig_tlv_type->per_port.param_idx = tlv_type;
nvconfig_tlv_type->per_port.port = port;
break;
}
}
mlx_status
nvconfig_query_capability(
IN mlx_utils *utils,
IN mlx_uint8 port,
IN mlx_uint16 tlv_type,
OUT mlx_boolean *read_supported,
OUT mlx_boolean *write_supported
)
{
mlx_status status = MLX_SUCCESS;
struct nvconfig_nvqc nvqc;
mlx_uint32 reg_status;
NVRAM_CLASS_CODE class_code;
mlx_uint16 real_tlv_type;
if (utils == NULL || read_supported == NULL || write_supported == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = nvconfig_get_tlv_type_and_class(tlv_type, &real_tlv_type, &class_code);
MLX_CHECK_STATUS(utils, status, tlv_not_supported, "tlv not supported");
mlx_memory_set(utils, &nvqc, 0, sizeof(nvqc));
nvconfig_fill_tlv_type(port, class_code, real_tlv_type, &nvqc.tlv_type);
status = mlx_reg_access(utils, REG_ID_NVQC, REG_ACCESS_READ, &nvqc, sizeof(nvqc),
&reg_status);
MLX_CHECK_STATUS(utils, status, reg_err, "mlx_reg_access failed ");
if (reg_status != 0) {
MLX_DEBUG_ERROR(utils,"mlx_reg_access failed with status = %d\n", reg_status);
status = MLX_FAILED;
goto reg_err;
}
*read_supported = nvqc.support_rd;
*write_supported = nvqc.support_wr;
reg_err:
tlv_not_supported:
bad_param:
return status;
}
mlx_status
nvconfig_nvdata_invalidate(
IN mlx_utils *utils,
IN mlx_uint8 port,
IN mlx_uint16 tlv_type
)
{
mlx_status status = MLX_SUCCESS;
struct nvconfig_header nv_header;
mlx_uint32 reg_status;
NVRAM_CLASS_CODE class_code;
mlx_uint16 real_tlv_type;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = nvconfig_get_tlv_type_and_class(tlv_type, &real_tlv_type, &class_code);
MLX_CHECK_STATUS(utils, status, tlv_not_supported, "tlv not supported");
mlx_memory_set(utils, &nv_header, 0, sizeof(nv_header));
nvconfig_fill_tlv_type(port, class_code, real_tlv_type, &nv_header.tlv_type);
status = mlx_reg_access(utils, REG_ID_NVDI, REG_ACCESS_WRITE, &nv_header, sizeof(nv_header),
&reg_status);
MLX_CHECK_STATUS(utils, status, reg_err, "mlx_reg_access failed ");
if (reg_status != 0) {
MLX_DEBUG_ERROR(utils,"mlx_reg_access failed with status = %d\n", reg_status);
status = MLX_FAILED;
goto reg_err;
}
reg_err:
tlv_not_supported:
bad_param:
return status;
}
mlx_status
nvconfig_nvdata_access(
IN mlx_utils *utils,
IN mlx_uint8 port,
IN mlx_uint16 tlv_type,
IN REG_ACCESS_OPT opt,
IN mlx_size data_size,
IN NV_DEFAULT_OPT def_en,
IN OUT mlx_uint8 *version,
IN OUT mlx_void *data
)
{
mlx_status status = MLX_SUCCESS;
struct nvconfig_nvda nvda;
mlx_uint32 reg_status;
mlx_uint32 real_size_to_read;
mlx_uint32 index;
NVRAM_CLASS_CODE class_code;
mlx_uint16 real_tlv_type;
mlx_size data_size_align_to_dword;
if (utils == NULL || data == NULL || data_size > NVCONFIG_MAX_TLV_SIZE) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = nvconfig_get_tlv_type_and_class(tlv_type, &real_tlv_type, &class_code);
MLX_CHECK_STATUS(utils, status, tlv_not_supported, "tlv not supported");
data_size_align_to_dword = ((data_size + 3) / sizeof(mlx_uint32)) * sizeof(mlx_uint32);
mlx_memory_set(utils, &nvda, 0, sizeof(nvda));
nvda.nv_header.length = data_size_align_to_dword;
nvda.nv_header.rd_en = 0;
nvda.nv_header.def_en = def_en;
nvda.nv_header.over_en = 1;
nvda.nv_header.version = *version;
nvconfig_fill_tlv_type(port, class_code, real_tlv_type, &nvda.nv_header.tlv_type);
mlx_memory_cpy(utils, nvda.data, data, data_size);
for (index = 0 ; index * 4 < NVCONFIG_MAX_TLV_SIZE ; index++) {
mlx_memory_be32_to_cpu(utils,(((mlx_uint32 *)nvda.data)[index]), ((mlx_uint32 *)nvda.data) + index);
}
status = mlx_reg_access(utils, REG_ID_NVDA, opt, &nvda,
data_size_align_to_dword + sizeof(nvda.nv_header), &reg_status);
MLX_CHECK_STATUS(utils, status, reg_err, "mlx_reg_access failed ");
if (reg_status != 0) {
MLX_DEBUG_ERROR(utils,"mlx_reg_access failed with status = %d\n", reg_status);
status = MLX_FAILED;
goto reg_err;
}
for (index = 0 ; index * 4 < NVCONFIG_MAX_TLV_SIZE ; index++) {
mlx_memory_cpu_to_be32(utils,(((mlx_uint32 *)nvda.data)[index]), ((mlx_uint32 *)nvda.data) + index);
}
if (opt == REG_ACCESS_READ) {
real_size_to_read = (nvda.nv_header.length > data_size) ? data_size :
nvda.nv_header.length;
mlx_memory_cpy(utils, data, nvda.data, real_size_to_read);
*version = nvda.nv_header.version;
} else {
nvconfig_set_fw_reset_level(utils, tlv_type);
}
reg_err:
tlv_not_supported:
bad_param:
return status;
}

View File

@ -0,0 +1,140 @@
#ifndef MLX_NVCONFIG_H_
#define MLX_NVCONFIG_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../mlx_reg_access/mlx_reg_access.h"
#include "../../include/public/mlx_utils.h"
typedef enum {
NVRAM_TLV_CLASS_GLOBAL = 0,
NVRAM_TLV_CLASS_PHYSICAL_PORT = 1,
NVRAM_TLV_CLASS_HOST = 3,
} NVRAM_CLASS_CODE;
struct nvconfig_tlv_type_per_port {
mlx_uint32 param_idx :16;
mlx_uint32 port :8;
mlx_uint32 param_class :8;
};
struct nvconfig_tlv_type_per_host {
mlx_uint32 param_idx :10;
mlx_uint32 function :8;
mlx_uint32 host :6;
mlx_uint32 param_class :8;
};
struct nvconfig_tlv_type_global {
mlx_uint32 param_idx :24;
mlx_uint32 param_class :8;
};
struct nvconfig_tlv_mapping{
mlx_uint16 tlv_type;
mlx_uint16 real_tlv_type;
NVRAM_CLASS_CODE class_code;
mlx_boolean fw_reset_needed;
};
union nvconfig_tlv_type {
struct nvconfig_tlv_type_per_port per_port;
struct nvconfig_tlv_type_per_host per_host;
struct nvconfig_tlv_type_global global;
};
struct nvconfig_nvqc {
union nvconfig_tlv_type tlv_type;
/* -------------- */
mlx_uint32 support_rd :1; /*the configuration item is supported and can be read */
mlx_uint32 support_wr :1; /*the configuration item is supported and can be updated */
mlx_uint32 reserved1 :2;
mlx_uint32 version :4; /*The maximum version of the configuration item currently supported by the firmware. */
mlx_uint32 reserved2 :24;
};
struct nvconfig_header {
mlx_uint32 length :9; /*Size of configuration item data in bytes between 0..256 */
mlx_uint32 reserved0 :3;
mlx_uint32 version :4; /* Configuration item version */
mlx_uint32 reserved1 :7;
mlx_uint32 def_en :1; /*Choose whether to access the default value or the user-defined value.
0x0 Read or write the user-defined value.
0x1 Read the default value (only valid for reads).*/
mlx_uint32 rd_en :1; /*enables reading the TLV by lower priorities
0 - TLV can be read by the subsequent lifecycle priorities.
1 - TLV cannot be read by the subsequent lifecycle priorities. */
mlx_uint32 over_en :1; /*enables overwriting the TLV by lower priorities
0 - Can only be overwritten by the current lifecycle priority
1 - Allowed to be overwritten by subsequent lifecycle priorities */
mlx_uint32 header_type :2;
mlx_uint32 priority :2;
mlx_uint32 valid :2;
/* -------------- */
union nvconfig_tlv_type tlv_type;;
/* -------------- */
mlx_uint32 crc :16;
mlx_uint32 reserved :16;
};
#define NVCONFIG_MAX_TLV_SIZE 256
struct nvconfig_nvda {
struct nvconfig_header nv_header;
mlx_uint8 data[NVCONFIG_MAX_TLV_SIZE];
};
mlx_status
nvconfig_query_capability(
IN mlx_utils *utils,
IN mlx_uint8 port,
IN mlx_uint16 tlv_type,
OUT mlx_boolean *read_supported,
OUT mlx_boolean *write_supported
);
mlx_status
nvconfig_nvdata_invalidate(
IN mlx_utils *utils,
IN mlx_uint8 port,
IN mlx_uint16 tlv_type
);
mlx_status
nvconfig_nvdata_access(
IN mlx_utils *utils,
IN mlx_uint8 port,
IN mlx_uint16 tlv_type,
IN REG_ACCESS_OPT opt,
IN mlx_size data_size,
IN NV_DEFAULT_OPT def_en,
IN OUT mlx_uint8 *version,
IN OUT mlx_void *data
);
#endif /* MLX_NVCONFIG_H_ */

View File

@ -0,0 +1,482 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE( GPL2_OR_LATER);
#include "../../mlx_lib/mlx_nvconfig/mlx_nvconfig.h"
#include "../../include/public/mlx_memory.h"
#include "../../include/public/mlx_bail.h"
#include "../../mlx_lib/mlx_nvconfig/mlx_nvconfig_defaults.h"
struct tlv_default {
mlx_uint16 tlv_type;
mlx_size data_size;
mlx_status (*set_defaults)( IN void *data, IN int status,
OUT void *def_struct);
};
#define TlvDefaultEntry( _tlv_type, _data_size, _set_defaults) { \
.tlv_type = _tlv_type, \
.data_size = sizeof ( _data_size ), \
.set_defaults = _set_defaults, \
}
static
mlx_status
nvconfig_get_boot_default_conf(
IN void *data,
IN int status,
OUT void *def_struct
)
{
union mlx_nvconfig_nic_boot_conf *nic_boot_conf =
(union mlx_nvconfig_nic_boot_conf *) data;
struct mlx_nvconfig_port_conf_defaults *port_conf_def =
(struct mlx_nvconfig_port_conf_defaults *) def_struct;
/* boot_option_rom_en is deprecated - enabled always */
port_conf_def->boot_option_rom_en = DEFAULT_OPTION_ROM_EN;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"TLV not found. Using hard-coded defaults ");
port_conf_def->boot_vlan = nic_boot_conf->vlan_id;
port_conf_def->boot_protocol = nic_boot_conf->legacy_boot_prot;
port_conf_def->boot_retry_count = nic_boot_conf->boot_retry_count;
port_conf_def->boot_vlan_en = nic_boot_conf->en_vlan;
return MLX_SUCCESS;
nvdata_access_err:
port_conf_def->boot_vlan = DEFAULT_BOOT_VLAN;
port_conf_def->boot_protocol = DEFAULT_BOOT_PROTOCOL;
return status;
}
static
mlx_status
nvconfig_get_boot_ext_default_conf(
IN void *data,
IN int status,
OUT void *def_struct
)
{
union mlx_nvconfig_nic_boot_ext_conf *nic_boot_ext_conf =
(union mlx_nvconfig_nic_boot_ext_conf *) data;
struct mlx_nvconfig_port_conf_defaults *port_conf_def =
(struct mlx_nvconfig_port_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"TLV not found. Using hard-coded defaults ");
port_conf_def->linkup_timeout = nic_boot_ext_conf->linkup_timeout;
port_conf_def->ip_ver = nic_boot_ext_conf->ip_ver;
return MLX_SUCCESS;
nvdata_access_err:
port_conf_def->linkup_timeout = DEFAULT_BOOT_LINK_UP_TO;
port_conf_def->ip_ver = DEFAULT_BOOT_IP_VER;
return status;
}
static
mlx_status
nvconfig_get_iscsi_init_dhcp_default_conf(
IN void *data,
IN int status,
OUT void *def_struct
)
{
union mlx_nvconfig_iscsi_init_dhcp_conf *iscsi_init_dhcp_conf =
(union mlx_nvconfig_iscsi_init_dhcp_conf *) data;
struct mlx_nvconfig_port_conf_defaults *port_conf_def =
(struct mlx_nvconfig_port_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"TLV not found. Using hard-coded defaults ");
port_conf_def->iscsi_dhcp_params_en = iscsi_init_dhcp_conf->dhcp_iscsi_en;
port_conf_def->iscsi_ipv4_dhcp_en = iscsi_init_dhcp_conf->ipv4_dhcp_en;
return MLX_SUCCESS;
nvdata_access_err:
port_conf_def->iscsi_dhcp_params_en = DEFAULT_ISCSI_DHCP_PARAM_EN;
port_conf_def->iscsi_ipv4_dhcp_en = DEFAULT_ISCSI_IPV4_DHCP_EN;
return status;
}
static
mlx_status
nvconfig_get_ib_boot_default_conf(
IN void *data,
IN int status,
OUT void *def_struct
)
{
union mlx_nvconfig_nic_ib_boot_conf *ib_boot_conf =
(union mlx_nvconfig_nic_ib_boot_conf *) data;
struct mlx_nvconfig_port_conf_defaults *port_conf_def =
(struct mlx_nvconfig_port_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"nvconfig_nvdata_default_access failed ");
port_conf_def->boot_pkey = ib_boot_conf->boot_pkey;
nvdata_access_err:
return status;
}
static
mlx_status
nvconfig_get_wol_default_conf(
IN void *data,
IN int status,
OUT void *def_struct
)
{
union mlx_nvconfig_wol_conf *wol_conf = (union mlx_nvconfig_wol_conf *) data;
struct mlx_nvconfig_port_conf_defaults *port_conf_def =
(struct mlx_nvconfig_port_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"nvconfig_nvdata_default_access failed ");
port_conf_def->en_wol_magic = wol_conf->en_wol_magic;
nvdata_access_err:
return status;
}
static
mlx_status
nvconfig_get_iscsi_gen_default_conf(
IN void *data,
IN int status,
OUT void *def_struct)
{
union mlx_nvconfig_iscsi_general *iscsi_gen =
(union mlx_nvconfig_iscsi_general *) data;
struct mlx_nvconfig_port_conf_defaults *port_conf_def =
(struct mlx_nvconfig_port_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"nvconfig_nvdata_default_access failed ");
port_conf_def->iscsi_boot_to_target = iscsi_gen->boot_to_target;
port_conf_def->iscsi_vlan_en = iscsi_gen->vlan_en;
port_conf_def->iscsi_tcp_timestamps_en = iscsi_gen->tcp_timestamps_en;
port_conf_def->iscsi_chap_mutual_auth_en = iscsi_gen->chap_mutual_auth_en;
port_conf_def->iscsi_chap_auth_en = iscsi_gen->chap_auth_en;
port_conf_def->iscsi_lun_busy_retry_count = iscsi_gen->lun_busy_retry_count;
port_conf_def->iscsi_link_up_delay_time = iscsi_gen->link_up_delay_time;
nvdata_access_err:
return status;
}
static
mlx_status
nvconfig_get_ib_dhcp_default_conf(
IN void *data,
IN int status,
OUT void *def_struct
)
{
union mlx_nvconfig_ib_dhcp_conf *ib_dhcp =
(union mlx_nvconfig_ib_dhcp_conf *) data;
struct mlx_nvconfig_port_conf_defaults *port_conf_def =
(struct mlx_nvconfig_port_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"nvconfig_nvdata_default_access failed ");
port_conf_def->client_identifier = ib_dhcp->client_identifier;
port_conf_def->mac_admin_bit = ib_dhcp->mac_admin_bit;
nvdata_access_err:
return status;
}
static
mlx_status
nvconfig_get_ocsd_ocbb_default_conf( IN void *data,
IN int status, OUT void *def_struct) {
union mlx_nvconfig_ocsd_ocbb_conf *ocsd_ocbb =
(union mlx_nvconfig_ocsd_ocbb_conf *) data;
struct mlx_nvconfig_conf_defaults *conf_def =
(struct mlx_nvconfig_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"TLV not found. Using hard-coded defaults ");
conf_def->ocsd_ocbb_en = ocsd_ocbb->ocsd_ocbb_en;
return MLX_SUCCESS;
nvdata_access_err:
conf_def->ocsd_ocbb_en = DEFAULT_OCSD_OCBB_EN;
return status;
}
static
mlx_status
nvconfig_get_vpi_link_default_conf(
IN void *data,
IN int status,
OUT void *def_struct
)
{
union mlx_nvconfig_vpi_link_conf *vpi_link =
(union mlx_nvconfig_vpi_link_conf *) data;
struct mlx_nvconfig_port_conf_defaults *port_conf_def =
(struct mlx_nvconfig_port_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"nvconfig_nvdata_default_access failed ");
port_conf_def->network_link_type = vpi_link->network_link_type;
port_conf_def->default_link_type = vpi_link->default_link_type;
nvdata_access_err:
return status;
}
static
mlx_status
nvconfig_get_rom_banner_to_default_conf(
IN void *data,
IN int status,
OUT void *def_struct
)
{
union mlx_nvconfig_rom_banner_timeout_conf *rom_banner_timeout_conf =
(union mlx_nvconfig_rom_banner_timeout_conf *) data;
struct mlx_nvconfig_conf_defaults *conf_def =
(struct mlx_nvconfig_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"TLV not found. Using hard-coded defaults ");
conf_def->flexboot_menu_to = rom_banner_timeout_conf->rom_banner_to;
return MLX_SUCCESS;
nvdata_access_err:
conf_def->flexboot_menu_to = DEFAULT_FLEXBOOT_MENU_TO;
return status;
}
static
mlx_status
nvconfig_get_nv_virt_caps_default_conf(
IN void *data,
IN int status,
OUT void *def_struct
)
{
union mlx_nvconfig_virt_caps *nv_virt_caps =
(union mlx_nvconfig_virt_caps *) data;
struct mlx_nvconfig_conf_defaults *conf_def =
(struct mlx_nvconfig_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"TLV not found. Using hard-coded defaults ");
conf_def->max_vfs = nv_virt_caps->max_vfs_per_pf;
return MLX_SUCCESS;
nvdata_access_err:
conf_def->max_vfs = DEFAULT_MAX_VFS;
return status;
}
static
mlx_status
nvconfig_get_nv_virt_default_conf(
IN void *data,
IN int status,
OUT void *def_struct
)
{
union mlx_nvconfig_virt_conf *nv_virt_conf =
(union mlx_nvconfig_virt_conf *) data;
struct mlx_nvconfig_conf_defaults *conf_def =
(struct mlx_nvconfig_conf_defaults *) def_struct;
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"nvconfig_nvdata_default_access failed ");
conf_def->total_vfs = nv_virt_conf->num_of_vfs;
conf_def->sriov_en = nv_virt_conf->virt_mode;
nvdata_access_err:
return status;
}
static struct tlv_default tlv_port_defaults[] = {
TlvDefaultEntry(BOOT_SETTINGS_TYPE, union mlx_nvconfig_nic_boot_conf, &nvconfig_get_boot_default_conf),
TlvDefaultEntry(BOOT_SETTINGS_EXT_TYPE, union mlx_nvconfig_nic_boot_ext_conf, &nvconfig_get_boot_ext_default_conf),
TlvDefaultEntry(ISCSI_INITIATOR_DHCP_CONF_TYPE, union mlx_nvconfig_iscsi_init_dhcp_conf, &nvconfig_get_iscsi_init_dhcp_default_conf),
TlvDefaultEntry(IB_BOOT_SETTING_TYPE, union mlx_nvconfig_nic_ib_boot_conf, &nvconfig_get_ib_boot_default_conf),
TlvDefaultEntry(WAKE_ON_LAN_TYPE, union mlx_nvconfig_wol_conf, &nvconfig_get_wol_default_conf),
TlvDefaultEntry(ISCSI_GENERAL_SETTINGS_TYPE, union mlx_nvconfig_iscsi_general, &nvconfig_get_iscsi_gen_default_conf),
TlvDefaultEntry(IB_DHCP_SETTINGS_TYPE, union mlx_nvconfig_ib_dhcp_conf, &nvconfig_get_ib_dhcp_default_conf),
TlvDefaultEntry(VPI_LINK_TYPE, union mlx_nvconfig_vpi_link_conf, &nvconfig_get_vpi_link_default_conf),
};
static struct tlv_default tlv_general_defaults[] = {
TlvDefaultEntry(BANNER_TO_TYPE, union mlx_nvconfig_rom_banner_timeout_conf, &nvconfig_get_rom_banner_to_default_conf),
TlvDefaultEntry(GLOPAL_PCI_CAPS_TYPE, union mlx_nvconfig_virt_caps, &nvconfig_get_nv_virt_caps_default_conf),
TlvDefaultEntry(GLOPAL_PCI_SETTINGS_TYPE, union mlx_nvconfig_virt_conf, &nvconfig_get_nv_virt_default_conf),
TlvDefaultEntry(OCSD_OCBB_TYPE, union mlx_nvconfig_ocsd_ocbb_conf, &nvconfig_get_ocsd_ocbb_default_conf),
};
static
mlx_status
nvconfig_nvdata_default_access(
IN mlx_utils *utils,
IN mlx_uint8 port,
IN mlx_uint16 tlv_type,
IN mlx_size data_size,
OUT mlx_void *data
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 index;
mlx_uint8 version = 0;
status = nvconfig_nvdata_access(utils, port, tlv_type, REG_ACCESS_READ,
data_size, TLV_ACCESS_DEFAULT_EN, &version, data);
MLX_CHECK_STATUS(NULL, status, nvdata_access_err,
"nvconfig_nvdata_access failed ");
for (index = 0; index * 4 < data_size; index++) {
mlx_memory_be32_to_cpu(utils, (((mlx_uint32 *) data)[index]),
((mlx_uint32 *) data) + index);
}
nvdata_access_err:
return status;
}
static
mlx_status
nvconfig_nvdata_read_default_value(
IN mlx_utils *utils,
IN mlx_uint8 modifier,
IN struct tlv_default *def,
OUT void *def_struct
)
{
mlx_status status = MLX_SUCCESS;
void *data = NULL;
status = mlx_memory_zalloc(utils, def->data_size,&data);
MLX_CHECK_STATUS(utils, status, memory_err,
"mlx_memory_zalloc failed ");
status = nvconfig_nvdata_default_access(utils, modifier, def->tlv_type,
def->data_size, data);
def->set_defaults(data, status, def_struct);
mlx_memory_free(utils, &data);
memory_err:
return status;
}
static
void
nvconfig_nvdata_read_default_values(
IN mlx_utils *utils,
IN mlx_uint8 modifier,
IN struct tlv_default defaults_table[],
IN mlx_uint8 defaults_table_size,
OUT void *def_strct
)
{
struct tlv_default *defs;
unsigned int i;
for (i = 0; i < defaults_table_size; i++) {
defs = &defaults_table[i];
nvconfig_nvdata_read_default_value(utils, modifier, defs, def_strct);
}
}
mlx_status
nvconfig_read_port_default_values(
IN mlx_utils *utils,
IN mlx_uint8 port,
OUT struct mlx_nvconfig_port_conf_defaults *port_conf_def
)
{
mlx_status status = MLX_SUCCESS;
if (utils == NULL || port_conf_def == NULL) {
status = MLX_INVALID_PARAMETER;
MLX_DEBUG_ERROR(utils,"bad params.");
goto bad_param;
}
mlx_memory_set(utils, port_conf_def, 0, sizeof(*port_conf_def));
nvconfig_nvdata_read_default_values(utils, port, tlv_port_defaults,
(sizeof(tlv_port_defaults)/sizeof(tlv_port_defaults[0])),
port_conf_def);
bad_param:
return status;
}
mlx_status
nvconfig_read_general_default_values(
IN mlx_utils *utils,
OUT struct mlx_nvconfig_conf_defaults *conf_def
)
{
mlx_status status = MLX_SUCCESS;
if (utils == NULL || conf_def == NULL) {
status = MLX_INVALID_PARAMETER;
MLX_DEBUG_ERROR(utils,"bad params.");
goto bad_param;
}
mlx_memory_set(utils, conf_def, 0, sizeof(*conf_def));
nvconfig_nvdata_read_default_values(utils, 0, tlv_general_defaults,
(sizeof(tlv_general_defaults)/sizeof(tlv_general_defaults[0])),
conf_def);
bad_param:
return status;
}
mlx_status
nvconfig_read_rom_ini_values(
IN mlx_utils *utils,
OUT struct mlx_nvcofnig_romini *rom_ini
)
{
mlx_status status = MLX_SUCCESS;
if (utils == NULL || rom_ini == NULL) {
status = MLX_INVALID_PARAMETER;
MLX_DEBUG_ERROR(utils,"bad params.");
goto bad_param;
}
mlx_memory_set(utils, rom_ini, 0, sizeof(*rom_ini));
status = nvconfig_nvdata_default_access(utils, 0, GLOBAL_ROM_INI_TYPE,
sizeof(*rom_ini), rom_ini);
bad_param:
return status;
}

View File

@ -0,0 +1,94 @@
#ifndef MLX_NVCONFIG_DEFAULTS_H_
#define MLX_NVCONFIG_DEFAULTS_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_nvconfig_prm.h"
/*
* Default values
*/
#define DEFAULT_FLEXBOOT_MENU_TO 4
#define DEFAULT_MAX_VFS 8
#define DEFAULT_BOOT_PROTOCOL 1
#define DEFAULT_OPTION_ROM_EN 1
#define DEFAULT_BOOT_VLAN 1
#define DEFAULT_ISCSI_DHCP_PARAM_EN 1
#define DEFAULT_ISCSI_IPV4_DHCP_EN 1
#define DEFAULT_OCSD_OCBB_EN 1
#define DEFAULT_BOOT_IP_VER 0
#define DEFAULT_BOOT_LINK_UP_TO 0
struct mlx_nvconfig_port_conf_defaults {
mlx_uint8 pptx;
mlx_uint8 pprx;
mlx_boolean boot_option_rom_en;
mlx_boolean boot_vlan_en;
mlx_uint8 boot_retry_count;
mlx_uint8 boot_protocol;
mlx_uint8 boot_vlan;
mlx_uint8 boot_pkey;
mlx_boolean en_wol_magic;
mlx_uint8 network_link_type;
mlx_uint8 iscsi_boot_to_target;
mlx_boolean iscsi_vlan_en;
mlx_boolean iscsi_tcp_timestamps_en;
mlx_boolean iscsi_chap_mutual_auth_en;
mlx_boolean iscsi_chap_auth_en;
mlx_boolean iscsi_dhcp_params_en;
mlx_boolean iscsi_ipv4_dhcp_en;
mlx_uint8 iscsi_lun_busy_retry_count;
mlx_uint8 iscsi_link_up_delay_time;
mlx_uint8 client_identifier;
mlx_uint8 mac_admin_bit;
mlx_uint8 default_link_type;
mlx_uint8 linkup_timeout;
mlx_uint8 ip_ver;
};
struct mlx_nvconfig_conf_defaults {
mlx_uint8 max_vfs;
mlx_uint8 total_vfs;
mlx_uint8 sriov_en;
mlx_uint8 maximum_uar_bar_size;
mlx_uint8 uar_bar_size;
mlx_uint8 flexboot_menu_to;
mlx_boolean ocsd_ocbb_en;
};
mlx_status
nvconfig_read_port_default_values(
IN mlx_utils *utils,
IN mlx_uint8 port,
OUT struct mlx_nvconfig_port_conf_defaults *port_conf_def
);
mlx_status
nvconfig_read_general_default_values(
IN mlx_utils *utils,
OUT struct mlx_nvconfig_conf_defaults *conf_def
);
mlx_status
nvconfig_read_rom_ini_values(
IN mlx_utils *utils,
OUT struct mlx_nvcofnig_romini *rom_ini
);
#endif /* MLX_NVCONFIG_DEFAULTS_H_ */

View File

@ -0,0 +1,259 @@
#ifndef MLX_NVCONFIG_PRM_H_
#define MLX_NVCONFIG_PRM_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../include/public/mlx_types.h"
enum {
WAKE_ON_LAN_TYPE = 0x10,
VIRTUALIZATION_TYPE = 0x11,
VPI_LINK_TYPE = 0x12,
BOOT_SETTINGS_EXT_TYPE = 0x2001,
BANNER_TO_TYPE = 0x2010,
OCSD_OCBB_TYPE = 0x2011,
FLOW_CONTROL_TYPE = 0x2020,
BOOT_SETTINGS_TYPE = 0x2021,
ISCSI_GENERAL_SETTINGS_TYPE = 0x2100,
IB_BOOT_SETTING_TYPE = 0x2022,
IB_DHCP_SETTINGS_TYPE = 0x2023,
GLOPAL_PCI_SETTINGS_TYPE = 0x80,
GLOPAL_PCI_CAPS_TYPE = 0x81,
GLOBAL_ROM_INI_TYPE = 0x100,
// Types for iSCSI strings
DHCP_VEND_ID = 0x2101,
ISCSI_INITIATOR_IPV4_ADDR = 0x2102,
ISCSI_INITIATOR_SUBNET = 0x2103,
ISCSI_INITIATOR_IPV4_GATEWAY = 0x2104,
ISCSI_INITIATOR_IPV4_PRIM_DNS = 0x2105,
ISCSI_INITIATOR_IPV4_SECDNS = 0x2106,
ISCSI_INITIATOR_NAME = 0x2107,
ISCSI_INITIATOR_CHAP_ID = 0x2108,
ISCSI_INITIATOR_CHAP_PWD = 0x2109,
ISCSI_INITIATOR_DHCP_CONF_TYPE = 0x210a,
CONNECT_FIRST_TGT = 0x2200,
FIRST_TGT_IP_ADDRESS = 0x2201,
FIRST_TGT_TCP_PORT = 0x2202,
FIRST_TGT_BOOT_LUN = 0x2203,
FIRST_TGT_ISCSI_NAME = 0x2204,
FIRST_TGT_CHAP_ID = 0x2205,
FIRST_TGT_CHAP_PWD = 0x2207,
};
union mlx_nvconfig_nic_boot_conf {
struct {
mlx_uint32 vlan_id : 12;
mlx_uint32 link_speed : 4;
mlx_uint32 legacy_boot_prot : 8;
mlx_uint32 boot_retry_count : 3;
mlx_uint32 boot_strap_type : 3;
mlx_uint32 en_vlan : 1;
mlx_uint32 en_option_rom : 1;
};
mlx_uint32 dword;
};
union mlx_nvconfig_nic_boot_ext_conf {
struct {
mlx_uint32 linkup_timeout : 8;
mlx_uint32 ip_ver : 2;
mlx_uint32 reserved0 : 22;
};
mlx_uint32 dword;
};
union mlx_nvconfig_rom_banner_timeout_conf {
struct {
mlx_uint32 rom_banner_to : 4;
mlx_uint32 reserved : 28;
};
mlx_uint32 dword;
};
union mlx_nvconfig_virt_conf {
struct {
mlx_uint32 reserved0 :24;
mlx_uint32 pf_bar_size_valid :1;
mlx_uint32 vf_bar_size_valid :1;
mlx_uint32 num_pf_msix_valid :1;
mlx_uint32 num_vf_msix_valid :1;
mlx_uint32 num_pfs_valid :1;
mlx_uint32 fpp_valid :1;
mlx_uint32 full_vf_qos_valid :1;
mlx_uint32 sriov_valid :1;
/*-------------------*/
mlx_uint32 num_of_vfs :16;
mlx_uint32 num_of_pfs :4;
mlx_uint32 reserved1 :9;
mlx_uint32 fpp_en :1;
mlx_uint32 full_vf_qos :1;
mlx_uint32 virt_mode :1; //sriov_en
/*-------------------*/
mlx_uint32 log_pf_uar_bar_size :6;
mlx_uint32 log_vf_uar_bar_size :6;
mlx_uint32 num_pf_msix :10;
mlx_uint32 num_vf_msix :10;
};
mlx_uint32 dword[3];
};
union mlx_nvconfig_virt_caps {
struct {
mlx_uint32 reserved0 :24;
mlx_uint32 max_vfs_per_pf_valid :1;
mlx_uint32 max_total_msix_valid :1;
mlx_uint32 max_total_bar_valid :1;
mlx_uint32 num_pfs_supported :1;
mlx_uint32 num_vf_msix_supported :1;
mlx_uint32 num_pf_msix_supported :1;
mlx_uint32 vf_bar_size_supported :1;
mlx_uint32 pf_bar_size_supported :1;
/*-------------------*/
mlx_uint32 max_vfs_per_pf :16;
mlx_uint32 max_num_pfs :4;
mlx_uint32 reserved1 :9;
mlx_uint32 fpp_support :1;
mlx_uint32 vf_qos_control_support :1;
mlx_uint32 sriov_support :1;
/*-------------------*/
mlx_uint32 max_log_pf_uar_bar_size :6;
mlx_uint32 max_log_vf_uar_bar_size :6;
mlx_uint32 max_num_pf_msix :10;
mlx_uint32 max_num_vf_msix :10;
/*-------------------*/
mlx_uint32 max_total_msix;
/*-------------------*/
mlx_uint32 max_total_bar;
};
mlx_uint32 dword[5];
};
union mlx_nvconfig_iscsi_init_dhcp_conf {
struct {
mlx_uint32 reserved0 :30;
mlx_uint32 dhcp_iscsi_en :1;
mlx_uint32 ipv4_dhcp_en :1;
};
mlx_uint32 dword;
};
union mlx_nvconfig_nic_ib_boot_conf {
struct {
mlx_uint32 boot_pkey : 16;
mlx_uint32 reserved0 : 16;
};
mlx_uint32 dword;
};
union mlx_nvconfig_wol_conf {
struct {
mlx_uint32 reserved0 :9;
mlx_uint32 en_wol_passwd :1;
mlx_uint32 en_wol_magic :1;
mlx_uint32 reserved1 :21;
mlx_uint32 reserved2 :32;
};
mlx_uint32 dword[2];
};
union mlx_nvconfig_iscsi_general {
struct {
mlx_uint32 reserved0 :22;
mlx_uint32 boot_to_target :2;
mlx_uint32 reserved1 :2;
mlx_uint32 vlan_en :1;
mlx_uint32 tcp_timestamps_en :1;
mlx_uint32 chap_mutual_auth_en :1;
mlx_uint32 chap_auth_en :1;
mlx_uint32 reserved2 :2;
/*-------------------*/
mlx_uint32 vlan :12;
mlx_uint32 reserved3 :20;
/*-------------------*/
mlx_uint32 lun_busy_retry_count:8;
mlx_uint32 link_up_delay_time :8;
mlx_uint32 reserved4 :16;
};
mlx_uint32 dword[3];
};
union mlx_nvconfig_ib_dhcp_conf {
struct {
mlx_uint32 reserved :24;
mlx_uint32 client_identifier :4;
mlx_uint32 mac_admin_bit :4;
};
mlx_uint32 dword;
};
union mlx_nvconfig_ocsd_ocbb_conf {
struct {
mlx_uint32 reserved :31;
mlx_uint32 ocsd_ocbb_en :1;
};
mlx_uint32 dword;
};
union mlx_nvconfig_vpi_link_conf {
struct {
mlx_uint32 network_link_type :2;
mlx_uint32 default_link_type :2;
mlx_uint32 reserved :28;
};
mlx_uint32 dword;
};
struct mlx_nvcofnig_romini {
mlx_uint32 reserved0 :1;
mlx_uint32 shared_memory_en :1;
mlx_uint32 hii_vpi_en :1;
mlx_uint32 tech_enum :1;
mlx_uint32 reserved1 :4;
mlx_uint32 static_component_name_string :1;
mlx_uint32 hii_iscsi_configuration :1;
mlx_uint32 hii_ibm_aim :1;
mlx_uint32 hii_platform_setup :1;
mlx_uint32 hii_bdf_decimal :1;
mlx_uint32 hii_read_only :1;
mlx_uint32 reserved2 :10;
mlx_uint32 mac_enum :1;
mlx_uint32 port_enum :1;
mlx_uint32 flash_en :1;
mlx_uint32 fmp_en :1;
mlx_uint32 bofm_en :1;
mlx_uint32 platform_to_driver_en :1;
mlx_uint32 hii_en :1;
mlx_uint32 undi_en :1;
/* -------------- */
mlx_uint64 dhcp_user_class;
/* -------------- */
mlx_uint32 reserved3 :22;
mlx_uint32 uri_boot_retry_delay :4;
mlx_uint32 uri_boot_retry :4;
mlx_uint32 option_rom_debug :1;
mlx_uint32 promiscuous_vlan :1;
};
#endif /* MLX_NVCONFIG_PRM_H_ */

View File

@ -0,0 +1,145 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_ocbb.h"
#include "mlx_icmd.h"
#include "mlx_bail.h"
mlx_status
mlx_ocbb_init (
IN mlx_utils *utils,
IN mlx_uint64 address
)
{
mlx_status status = MLX_SUCCESS;
struct mlx_ocbb_init ocbb_init;
ocbb_init.address_hi = (mlx_uint32)(address >> 32);
ocbb_init.address_lo = (mlx_uint32)address;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_icmd_send_command(
utils,
OCBB_INIT,
&ocbb_init,
sizeof(ocbb_init),
0
);
MLX_CHECK_STATUS(utils, status, icmd_err, "mlx_icmd_send_command failed");
icmd_err:
bad_param:
return status;
}
mlx_status
mlx_ocbb_query_header_status (
IN mlx_utils *utils,
OUT mlx_uint8 *ocbb_status
)
{
mlx_status status = MLX_SUCCESS;
struct mlx_ocbb_query_status ocbb_query_status;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_icmd_send_command(
utils,
OCBB_QUERY_HEADER_STATUS,
&ocbb_query_status,
0,
sizeof(ocbb_query_status)
);
MLX_CHECK_STATUS(utils, status, icmd_err, "mlx_icmd_send_command failed");
*ocbb_status = ocbb_query_status.status;
icmd_err:
bad_param:
return status;
}
mlx_status
mlx_ocbb_query_etoc_status (
IN mlx_utils *utils,
OUT mlx_uint8 *ocbb_status
)
{
mlx_status status = MLX_SUCCESS;
struct mlx_ocbb_query_status ocbb_query_status;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_icmd_send_command(
utils,
OCBB_QUERY_ETOC_STATUS,
&ocbb_query_status,
0,
sizeof(ocbb_query_status)
);
MLX_CHECK_STATUS(utils, status, icmd_err, "mlx_icmd_send_command failed");
*ocbb_status = ocbb_query_status.status;
icmd_err:
bad_param:
return status;
}
mlx_status
mlx_ocbb_set_event (
IN mlx_utils *utils,
IN mlx_uint64 event_data,
IN mlx_uint8 event_number,
IN mlx_uint8 event_length,
IN mlx_uint8 data_length,
IN mlx_uint8 data_start_offset
)
{
mlx_status status = MLX_SUCCESS;
struct mlx_ocbb_set_event ocbb_event;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
ocbb_event.data_length = data_length;
ocbb_event.data_start_offset = data_start_offset;
ocbb_event.event_number = event_number;
ocbb_event.event_data = event_data;
ocbb_event.event_length = event_length;
status = mlx_icmd_send_command(
utils,
OCBB_QUERY_SET_EVENT,
&ocbb_event,
sizeof(ocbb_event),
0
);
MLX_CHECK_STATUS(utils, status, icmd_err, "mlx_icmd_send_command failed");
icmd_err:
bad_param:
return status;
}

View File

@ -0,0 +1,73 @@
#ifndef MLX_OCBB_H_
#define MLX_OCBB_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_utils.h"
#define MLX_OCBB_EVENT_DATA_SIZE 2
struct mlx_ocbb_init {
mlx_uint32 address_hi;
mlx_uint32 address_lo;
};
struct mlx_ocbb_query_status {
mlx_uint32 reserved :24;
mlx_uint32 status :8;
};
struct mlx_ocbb_set_event {
mlx_uint64 event_data;
mlx_uint32 event_number :8;
mlx_uint32 event_length :8;
mlx_uint32 data_length :8;
mlx_uint32 data_start_offset :8;
};
mlx_status
mlx_ocbb_init (
IN mlx_utils *utils,
IN mlx_uint64 address
);
mlx_status
mlx_ocbb_query_header_status (
IN mlx_utils *utils,
OUT mlx_uint8 *ocbb_status
);
mlx_status
mlx_ocbb_query_etoc_status (
IN mlx_utils *utils,
OUT mlx_uint8 *ocbb_status
);
mlx_status
mlx_ocbb_set_event (
IN mlx_utils *utils,
IN mlx_uint64 EventData,
IN mlx_uint8 EventNumber,
IN mlx_uint8 EventLength,
IN mlx_uint8 DataLength,
IN mlx_uint8 DataStartOffset
);
#endif /* MLX_OCBB_H_ */

View File

@ -0,0 +1,90 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../mlx_lib/mlx_reg_access/mlx_reg_access.h"
#include "../../include/public/mlx_icmd.h"
#include "../../include/public/mlx_bail.h"
#include "../../include/public/mlx_memory.h"
static
mlx_status
init_operation_tlv(
IN struct mail_box_tlv *mail_box_tlv,
IN mlx_uint16 reg_id,
IN REG_ACCESS_OPT reg_opt
)
{
#define TLV_OPERATION 1
mail_box_tlv->operation_tlv.Type = TLV_OPERATION;
#define MAD_CLASS_REG_ACCESS 1
mail_box_tlv->operation_tlv.cls = MAD_CLASS_REG_ACCESS;
#define TLV_OPERATION_SIZE 4
mail_box_tlv->operation_tlv.len = TLV_OPERATION_SIZE;
mail_box_tlv->operation_tlv.method = reg_opt;
mail_box_tlv->operation_tlv.register_id = reg_id;
return MLX_SUCCESS;
}
mlx_status
mlx_reg_access(
IN mlx_utils *utils,
IN mlx_uint16 reg_id,
IN REG_ACCESS_OPT reg_opt,
IN OUT mlx_void *reg_data,
IN mlx_size reg_size,
OUT mlx_uint32 *reg_status
)
{
mlx_status status = MLX_SUCCESS;
struct mail_box_tlv mail_box_tlv;
if (utils == NULL || reg_data == NULL || reg_status == NULL
|| reg_size > REG_ACCESS_MAX_REG_SIZE) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
mlx_memory_set(utils, &mail_box_tlv, 0, sizeof(mail_box_tlv));
init_operation_tlv(&mail_box_tlv, reg_id, reg_opt);
#define REG_ACCESS_TLV_REG 3
#define REG_TLV_HEADER_LEN 4
#define OP_TLV_SIZE 16
mail_box_tlv.reg_tlv.Type = REG_ACCESS_TLV_REG;
mail_box_tlv.reg_tlv.len = ((reg_size + REG_TLV_HEADER_LEN + 3) >> 2); // length is in dwords round up
mlx_memory_cpy(utils, &mail_box_tlv.reg_tlv.data, reg_data, reg_size);
reg_size += OP_TLV_SIZE + REG_TLV_HEADER_LEN;
status = mlx_icmd_send_command(utils, FLASH_REG_ACCESS, &mail_box_tlv, reg_size, reg_size);
MLX_CHECK_STATUS(utils, status, icmd_err, "failed to send icmd");
mlx_memory_cpy(utils, reg_data, &mail_box_tlv.reg_tlv.data,
reg_size - (OP_TLV_SIZE + REG_TLV_HEADER_LEN));
*reg_status = mail_box_tlv.operation_tlv.status;
icmd_err:
bad_param:
return status;
}

View File

@ -0,0 +1,82 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#ifndef MLX_REG_ACCESS_H_
#define MLX_REG_ACCESS_H_
#include "../../include/public/mlx_icmd.h"
#define REG_ACCESS_MAX_REG_SIZE 236
typedef enum {
REG_ACCESS_READ = 1,
REG_ACCESS_WRITE = 2,
} REG_ACCESS_OPT;
typedef enum {
TLV_ACCESS_DEFAULT_DIS = 0,
TLV_ACCESS_DEFAULT_EN = 1,
} NV_DEFAULT_OPT;
#define REG_ID_NVDA 0x9024
#define REG_ID_NVDI 0x9025
#define REG_ID_NVIA 0x9029
#define REG_ID_MLCR 0x902b
#define REG_ID_NVQC 0x9030
#define REG_ID_MFRL 0x9028
#define REG_ID_PTYS 0x5004
#define REG_ID_PMTU 0x5003
struct operation_tlv {
mlx_uint32 reserved0 :8; /* bit_offset:0 */ /* element_size: 8 */
mlx_uint32 status :7; /* bit_offset:8 */ /* element_size: 7 */
mlx_uint32 dr :1; /* bit_offset:15 */ /* element_size: 1 */
mlx_uint32 len :11; /* bit_offset:16 */ /* element_size: 11 */
mlx_uint32 Type :5; /* bit_offset:27 */ /* element_size: 5 */
mlx_uint32 cls :8; /* bit_offset:32 */ /* element_size: 8 */
mlx_uint32 method :7; /* bit_offset:40 */ /* element_size: 7 */
mlx_uint32 r :1; /* bit_offset:47 */ /* element_size: 1 */
mlx_uint32 register_id :16; /* bit_offset:48 */ /* element_size: 16 */
mlx_uint64 tid ; /* bit_offset:64 */ /* element_size: 64 */
};
struct reg_tlv {
mlx_uint32 reserved0 :16; /* bit_offset:0 */ /* element_size: 16 */
mlx_uint32 len :11; /* bit_offset:16 */ /* element_size: 11 */
mlx_uint32 Type :5; /* bit_offset:27 */ /* element_size: 5 */
mlx_uint8 data[REG_ACCESS_MAX_REG_SIZE];
};
struct mail_box_tlv {
struct operation_tlv operation_tlv;
struct reg_tlv reg_tlv;
};
mlx_status
mlx_reg_access(
IN mlx_utils *utils,
IN mlx_uint16 reg_id,
IN REG_ACCESS_OPT reg_opt,
IN OUT mlx_void *reg_data,
IN mlx_size reg_size,
OUT mlx_uint32 *reg_status
);
#endif /* MLX_REG_ACCESS_H_ */

View File

@ -0,0 +1,74 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../mlx_lib/mlx_vmac/mlx_vmac.h"
#include "../../include/public/mlx_icmd.h"
#include "../../include/public/mlx_bail.h"
mlx_status
mlx_vmac_query_virt_mac (
IN mlx_utils *utils,
OUT struct mlx_vmac_query_virt_mac *virt_mac
)
{
mlx_status status = MLX_SUCCESS;
if (utils == NULL || virt_mac == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_icmd_send_command(
utils,
QUERY_VIRTUAL_MAC,
virt_mac,
0,
sizeof(*virt_mac)
);
MLX_CHECK_STATUS(utils, status, icmd_err, "mlx_icmd_send_command failed");
icmd_err:
bad_param:
return status;
}
mlx_status
mlx_vmac_set_virt_mac (
IN mlx_utils *utils,
OUT struct mlx_vmac_set_virt_mac *virt_mac
)
{
mlx_status status = MLX_SUCCESS;
if (utils == NULL || virt_mac == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_icmd_send_command(
utils,
SET_VIRTUAL_MAC,
virt_mac,
sizeof(*virt_mac),
0
);
MLX_CHECK_STATUS(utils, status, icmd_err, "mlx_icmd_send_command failed");
icmd_err:
bad_param:
return status;
}

View File

@ -0,0 +1,60 @@
#ifndef MLX_VMAC_H_
#define MLX_VMAC_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../include/public/mlx_utils.h"
struct mlx_vmac_query_virt_mac {
mlx_uint32 reserved0 :30;
mlx_uint32 mac_aux_v :1;
mlx_uint32 virtual_mac_en :1;
mlx_uint32 parmanent_mac_high :16;
mlx_uint32 reserved1 :16;
mlx_uint32 parmanent_mac_low :32;
mlx_uint32 virtual_mac_high :16;
mlx_uint32 Reserved2 :16;
mlx_uint32 virtual_mac_low :32;
};
struct mlx_vmac_set_virt_mac {
mlx_uint32 Reserved0 :30;
mlx_uint32 mac_aux_v :1;
mlx_uint32 virtual_mac_en :1;
mlx_uint32 reserved1 :32;
mlx_uint32 reserved2 :32;
mlx_uint32 virtual_mac_high;
mlx_uint32 virtual_mac_low;
};
mlx_status
mlx_vmac_query_virt_mac (
IN mlx_utils *utils,
OUT struct mlx_vmac_query_virt_mac *virt_mac
);
mlx_status
mlx_vmac_set_virt_mac (
IN mlx_utils *utils,
OUT struct mlx_vmac_set_virt_mac *virt_mac
);
#endif /* MLX_VMAC_H_ */

View File

@ -0,0 +1,84 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_wol_rol.h"
#include "mlx_icmd.h"
#include "mlx_memory.h"
#include "mlx_bail.h"
mlx_status
mlx_set_wol (
IN mlx_utils *utils,
IN mlx_uint8 wol_mask
)
{
mlx_status status = MLX_SUCCESS;
struct mlx_wol_rol wol_rol;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
mlx_memory_set(utils, &wol_rol, 0, sizeof(wol_rol));
wol_rol.wol_mode_valid = TRUE;
wol_rol.wol_mode = wol_mask;
status = mlx_icmd_send_command(
utils,
SET_WOL_ROL,
&wol_rol,
sizeof(wol_rol),
0
);
MLX_CHECK_STATUS(utils, status, icmd_err, "mlx_icmd_send_command failed");
icmd_err:
bad_param:
return status;
}
mlx_status
mlx_query_wol (
IN mlx_utils *utils,
OUT mlx_uint8 *wol_mask
)
{
mlx_status status = MLX_SUCCESS;
struct mlx_wol_rol wol_rol;
if (utils == NULL || wol_mask == NULL) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
mlx_memory_set(utils, &wol_rol, 0, sizeof(wol_rol));
status = mlx_icmd_send_command(
utils,
QUERY_WOL_ROL,
&wol_rol,
0,
sizeof(wol_rol)
);
MLX_CHECK_STATUS(utils, status, icmd_err, "mlx_icmd_send_command failed");
*wol_mask = wol_rol.wol_mode;
icmd_err:
bad_param:
return status;
}

View File

@ -0,0 +1,61 @@
#ifndef MLX_WOL_ROL_H_
#define MLX_WOL_ROL_H_
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "mlx_utils.h"
typedef enum {
WOL_MODE_DISABLE = 0x0,
WOL_MODE_SECURE = 0x2,
WOL_MODE_MAGIC = 0x4,
WOL_MODE_ARP = 0x8,
WOL_MODE_BC = 0x10,
WOL_MODE_MC = 0x20,
WOL_MODE_UC = 0x40,
WOL_MODE_PHY = 0x80,
} WOL_MODE;
struct mlx_wol_rol {
mlx_uint32 reserved0 :32;
mlx_uint32 reserved1 :32;
mlx_uint32 wol_mode :8;
mlx_uint32 rol_mode :8;
mlx_uint32 reserved3 :14;
mlx_uint32 wol_mode_valid :1;
mlx_uint32 rol_mode_valid :1;
};
mlx_status
mlx_set_wol (
IN mlx_utils *utils,
IN mlx_uint8 wol_mask
);
mlx_status
mlx_query_wol (
IN mlx_utils *utils,
OUT mlx_uint8 *wol_mask
);
#endif /* MLX_WOL_ROL_H_ */

View File

@ -0,0 +1,9 @@
MlxDebugLogImpl()
{
DBGC((DEBUG),"");
}
MlxInfoLogImpl()
{
DBGC((INFO),"");
}
}

View File

@ -0,0 +1,371 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../include/public/mlx_bail.h"
#include "../../include/public/mlx_icmd.h"
#include "../../include/public/mlx_pci_gw.h"
#include "../../include/public/mlx_utils.h"
static
mlx_status
mlx_icmd_get_semaphore(
IN mlx_utils *utils
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 retries = 0;
mlx_uint32 semaphore_id;
mlx_uint32 buffer;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto invalid_param;
}
status = mlx_utils_rand(utils, &semaphore_id);
MLX_CHECK_STATUS(utils, status, rand_err, "failed to get random number");
#define ICMD_GET_SEMAPHORE_TRIES 2560
for (retries = 0 ; retries < ICMD_GET_SEMAPHORE_TRIES ; retries++) {
status = mlx_pci_gw_read( utils, PCI_GW_SPACE_SEMAPHORE,
MLX_ICMD_SEMAPHORE_ADDR, &buffer);
MLX_CHECK_STATUS(utils, status, read_err, "failed to read icmd semaphore");
if (buffer != 0) {
mlx_utils_delay_in_ms(10);
continue;
}
mlx_pci_gw_write( utils, PCI_GW_SPACE_SEMAPHORE,
MLX_ICMD_SEMAPHORE_ADDR, semaphore_id);
MLX_CHECK_STATUS(utils, status, set_err, "failed to set icmd semaphore");
status = mlx_pci_gw_read( utils, PCI_GW_SPACE_SEMAPHORE,
MLX_ICMD_SEMAPHORE_ADDR, &buffer);
MLX_CHECK_STATUS(utils, status, read_err, "failed to read icmd semaphore");
if (semaphore_id == buffer) {
status = MLX_SUCCESS;
utils->icmd.took_semaphore = TRUE;
break;
}
mlx_utils_delay_in_ms(10);
}
if (semaphore_id != buffer) {
status = MLX_FAILED;
}
read_err:
set_err:
rand_err:
invalid_param:
return status;
}
static
mlx_status
mlx_icmd_clear_semaphore(
IN mlx_utils *utils
)
{
mlx_status status = MLX_SUCCESS;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto invalid_param;
}
if (utils->icmd.took_semaphore == FALSE) {
goto semaphore_not_taken;
}
status = mlx_pci_gw_write( utils, PCI_GW_SPACE_SEMAPHORE,
MLX_ICMD_SEMAPHORE_ADDR, 0);
MLX_CHECK_STATUS(utils, status, read_err, "failed to clear icmd semaphore");
utils->icmd.took_semaphore = FALSE;
read_err:
semaphore_not_taken:
invalid_param:
return status;
}
static
mlx_status
mlx_icmd_init(
IN mlx_utils *utils
)
{
mlx_status status = MLX_SUCCESS;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto invalid_param;
}
if (utils->icmd.icmd_opened == TRUE) {
goto already_opened;
}
utils->icmd.took_semaphore = FALSE;
status = mlx_pci_gw_read( utils, PCI_GW_SPACE_ALL_ICMD,
MLX_ICMD_MB_SIZE_ADDR, &utils->icmd.max_cmd_size);
MLX_CHECK_STATUS(utils, status, read_err, "failed to read icmd mail box size");
utils->icmd.icmd_opened = TRUE;
read_err:
already_opened:
invalid_param:
return status;
}
static
mlx_status
mlx_icmd_set_opcode(
IN mlx_utils *utils,
IN mlx_uint16 opcode
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 buffer;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto invalid_param;
}
status = mlx_pci_gw_read( utils, PCI_GW_SPACE_ALL_ICMD,
MLX_ICMD_CTRL_ADDR, &buffer);
MLX_CHECK_STATUS(utils, status, read_err, "failed to read icmd ctrl");
#define MLX_ICMD_OPCODE_ALIGN 16
#define MLX_ICMD_OPCODE_MASK 0xffff
buffer = buffer & ~(MLX_ICMD_OPCODE_MASK << MLX_ICMD_OPCODE_ALIGN);
buffer = buffer | (opcode << MLX_ICMD_OPCODE_ALIGN);
status = mlx_pci_gw_write( utils, PCI_GW_SPACE_ALL_ICMD,
MLX_ICMD_CTRL_ADDR, buffer);
MLX_CHECK_STATUS(utils, status, write_err, "failed to write icmd ctrl");
write_err:
read_err:
invalid_param:
return status;
}
static
mlx_status
mlx_icmd_go(
IN mlx_utils *utils
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 buffer;
mlx_uint32 busy;
mlx_uint32 wait_iteration = 0;
if (utils == NULL) {
status = MLX_INVALID_PARAMETER;
goto invalid_param;
}
status = mlx_pci_gw_read( utils, PCI_GW_SPACE_ALL_ICMD,
MLX_ICMD_CTRL_ADDR, &buffer);
MLX_CHECK_STATUS(utils, status, read_err, "failed to read icmd ctrl");
#define MLX_ICMD_BUSY_ALIGN 0
#define MLX_ICMD_BUSY_MASK 0x1
busy = (buffer >> MLX_ICMD_BUSY_ALIGN) & MLX_ICMD_BUSY_MASK;
if (busy != 0) {
status = MLX_FAILED;
goto already_busy;
}
buffer = buffer | (1 << MLX_ICMD_BUSY_ALIGN);
status = mlx_pci_gw_write( utils, PCI_GW_SPACE_ALL_ICMD,
MLX_ICMD_CTRL_ADDR, buffer);
MLX_CHECK_STATUS(utils, status, write_err, "failed to write icmd ctrl");
#define MLX_ICMD_BUSY_MAX_ITERATIONS 1024
do {
if (++wait_iteration > MLX_ICMD_BUSY_MAX_ITERATIONS) {
status = MLX_FAILED;
MLX_DEBUG_ERROR(utils, "ICMD time out");
goto busy_timeout;
}
mlx_utils_delay_in_ms(10);
status = mlx_pci_gw_read( utils, PCI_GW_SPACE_ALL_ICMD,
MLX_ICMD_CTRL_ADDR, &buffer);
MLX_CHECK_STATUS(utils, status, read_err, "failed to read icmd ctrl");
busy = (buffer >> MLX_ICMD_BUSY_ALIGN) & MLX_ICMD_BUSY_MASK;
} while (busy != 0);
busy_timeout:
write_err:
already_busy:
read_err:
invalid_param:
return status;
}
static
mlx_status
mlx_icmd_get_status(
IN mlx_utils *utils,
OUT mlx_uint32 *out_status
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 buffer;
if (utils == NULL || out_status == NULL) {
status = MLX_INVALID_PARAMETER;
goto invalid_param;
}
status = mlx_pci_gw_read( utils, PCI_GW_SPACE_ALL_ICMD,
MLX_ICMD_CTRL_ADDR, &buffer);
MLX_CHECK_STATUS(utils, status, read_err, "failed to read icmd ctrl");
#define MLX_ICMD_STATUS_ALIGN 8
#define MLX_ICMD_STATUS_MASK 0xff
*out_status = (buffer >> MLX_ICMD_STATUS_ALIGN) & MLX_ICMD_STATUS_MASK;
read_err:
invalid_param:
return status;
}
static
mlx_status
mlx_icmd_write_buffer(
IN mlx_utils *utils,
IN mlx_void* data,
IN mlx_uint32 data_size
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 data_offset = 0;
mlx_size dword_size = sizeof(mlx_uint32);
if (utils == NULL || data == NULL) {
status = MLX_INVALID_PARAMETER;
goto invalid_param;
}
for (data_offset = 0 ; data_offset*dword_size < data_size ; data_offset++) {
status = mlx_pci_gw_write( utils, PCI_GW_SPACE_ALL_ICMD,
MLX_ICMD_MB_ADDR + data_offset*dword_size,
((mlx_uint32*)data)[data_offset]);
MLX_CHECK_STATUS(utils, status, write_err, "failed to write icmd MB");
}
write_err:
invalid_param:
return status;
}
static
mlx_status
mlx_icmd_read_buffer(
IN mlx_utils *utils,
OUT mlx_void* data,
IN mlx_uint32 data_size
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 data_offset = 0;
mlx_size dword_size = sizeof(mlx_uint32);
if (utils == NULL || data == NULL) {
status = MLX_INVALID_PARAMETER;
goto invalid_param;
}
for (data_offset = 0 ; data_offset*dword_size < data_size ; data_offset++) {
status = mlx_pci_gw_read( utils, PCI_GW_SPACE_ALL_ICMD,
MLX_ICMD_MB_ADDR + data_offset*dword_size,
(mlx_uint32*)data + data_offset);
MLX_CHECK_STATUS(utils, status, read_err, "failed to read icmd MB");
}
read_err:
invalid_param:
return status;
}
mlx_status
mlx_icmd_send_command(
IN mlx_utils *utils,
IN mlx_uint16 opcode,
IN OUT mlx_void* data,
IN mlx_uint32 write_data_size,
IN mlx_uint32 read_data_size
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 icmd_status;
if (utils == NULL || data == NULL) {
status = MLX_INVALID_PARAMETER;
goto invalid_param;
}
status = mlx_icmd_init(utils);
MLX_CHECK_STATUS(utils, status, open_err, "failed to open icmd");
if (write_data_size > utils->icmd.max_cmd_size ||
read_data_size > utils->icmd.max_cmd_size) {
status = MLX_INVALID_PARAMETER;
goto size_err;
}
status = mlx_icmd_get_semaphore(utils);
MLX_CHECK_STATUS(utils, status, semaphore_err, "failed to get icmd semaphore");
status = mlx_icmd_set_opcode(utils, opcode);
MLX_CHECK_STATUS(utils, status, opcode_err, "failed to set icmd opcode");
if (write_data_size != 0) {
status = mlx_icmd_write_buffer(utils, data, write_data_size);
MLX_CHECK_STATUS(utils, status, opcode_err, "failed to write icmd MB");
}
status = mlx_icmd_go(utils);
MLX_CHECK_STATUS(utils, status, go_err, "failed to activate icmd");
status = mlx_icmd_get_status(utils, &icmd_status);
MLX_CHECK_STATUS(utils, status, get_status_err, "failed to set icmd opcode");
if (icmd_status != 0) {
MLX_DEBUG_ERROR(utils, "icmd failed with status = %d\n", icmd_status);
status = MLX_FAILED;
goto icmd_failed;
}
if (read_data_size != 0) {
status = mlx_icmd_read_buffer(utils, data, read_data_size);
MLX_CHECK_STATUS(utils, status, read_err, "failed to read icmd MB");
}
read_err:
icmd_failed:
get_status_err:
go_err:
opcode_err:
mlx_icmd_clear_semaphore(utils);
semaphore_err:
size_err:
open_err:
invalid_param:
return status;
}

View File

@ -0,0 +1,238 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include <stddef.h>
#include "../../include/private/mlx_memory_priv.h"
#include "../../include/public/mlx_memory.h"
mlx_status
mlx_memory_alloc(
IN mlx_utils *utils,
IN mlx_size size,
OUT mlx_void **ptr
)
{
mlx_status status = MLX_SUCCESS;
*ptr = NULL;
if ( utils == NULL || size == 0 || *ptr != NULL ){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_alloc_priv(utils, size, ptr);
bad_param:
return status;
}
mlx_status
mlx_memory_zalloc(
IN mlx_utils *utils,
IN mlx_size size,
OUT mlx_void **ptr
)
{
mlx_status status = MLX_SUCCESS;
*ptr = NULL;
if ( utils == NULL || size == 0 || *ptr != NULL ){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_zalloc_priv(utils, size, ptr);
bad_param:
return status;
}
mlx_status
mlx_memory_free(
IN mlx_utils *utils,
IN mlx_void **ptr
)
{
mlx_status status = MLX_SUCCESS;
if ( utils == NULL || ptr == NULL || *ptr == NULL ){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_free_priv(utils, *ptr);
*ptr = NULL;
bad_param:
return status;
}
mlx_status
mlx_memory_alloc_dma(
IN mlx_utils *utils,
IN mlx_size size ,
IN mlx_size align,
OUT mlx_void **ptr
)
{
mlx_status status = MLX_SUCCESS;
*ptr = NULL;
if ( utils == NULL || size == 0 || *ptr != NULL ){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_alloc_dma_priv(utils, size, align, ptr);
bad_param:
return status;
}
mlx_status
mlx_memory_free_dma(
IN mlx_utils *utils,
IN mlx_size size ,
IN mlx_void **ptr
)
{
mlx_status status = MLX_SUCCESS;
if ( utils == NULL || size == 0 || ptr == NULL || *ptr == NULL ){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_free_dma_priv(utils, size, *ptr);
*ptr = NULL;
bad_param:
return status;
}
mlx_status
mlx_memory_map_dma(
IN mlx_utils *utils,
IN mlx_void *addr ,
IN mlx_size number_of_bytes,
OUT mlx_physical_address *phys_addr,
OUT mlx_void **mapping
)
{
mlx_status status = MLX_SUCCESS;
if ( utils == NULL || phys_addr == NULL ){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_map_dma_priv(utils, addr, number_of_bytes, phys_addr, mapping);
bad_param:
return status;
}
mlx_status
mlx_memory_ummap_dma(
IN mlx_utils *utils,
IN mlx_void *mapping
)
{
mlx_status status = MLX_SUCCESS;
if ( utils == NULL){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_ummap_dma_priv(utils, mapping);
bad_param:
return status;
}
mlx_status
mlx_memory_cmp(
IN mlx_utils *utils,
IN mlx_void *first_block,
IN mlx_void *second_block,
IN mlx_size size,
OUT mlx_uint32 *out
)
{
mlx_status status = MLX_SUCCESS;
if ( utils == NULL || first_block == NULL || second_block == NULL ||
out == NULL){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_cmp_priv(utils, first_block, second_block, size, out);
bad_param:
return status;
}
mlx_status
mlx_memory_set(
IN mlx_utils *utils,
IN mlx_void *block,
IN mlx_int32 value,
IN mlx_size size
)
{
mlx_status status = MLX_SUCCESS;
if ( utils == NULL || block == NULL){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_set_priv(utils, block, value, size);
bad_param:
return status;
}
mlx_status
mlx_memory_cpy(
IN mlx_utils *utils,
OUT mlx_void *destination_buffer,
IN mlx_void *source_buffer,
IN mlx_size length
)
{
mlx_status status = MLX_SUCCESS;
if ( utils == NULL || destination_buffer == NULL || source_buffer == NULL){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_cpy_priv(utils, destination_buffer, source_buffer, length);
bad_param:
return status;
}
mlx_status
mlx_memory_cpu_to_be32(
IN mlx_utils *utils,
IN mlx_uint32 source,
IN mlx_uint32 *destination
)
{
mlx_status status = MLX_SUCCESS;
if ( utils == NULL || destination == NULL ){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_cpu_to_be32_priv(utils, source, destination);
bad_param:
return status;
}
mlx_status
mlx_memory_be32_to_cpu(
IN mlx_utils *utils,
IN mlx_uint32 source,
IN mlx_uint32 *destination
)
{
mlx_status status = MLX_SUCCESS;
if ( utils == NULL || destination == NULL ){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
status = mlx_memory_be32_to_cpu_priv(utils, source, destination);
bad_param:
return status;
}

View File

@ -0,0 +1,117 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include <stddef.h>
#include "../../include/private/mlx_pci_priv.h"
#include "../../include/public/mlx_pci.h"
mlx_status
mlx_pci_init(
IN mlx_utils *utils
)
{
mlx_status status = MLX_SUCCESS;
if( utils == NULL){
status = MLX_INVALID_PARAMETER;
goto bail;
}
status = mlx_pci_init_priv(utils);
bail:
return status;
}
mlx_status
mlx_pci_read(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint32 offset,
IN mlx_uintn count,
OUT mlx_void *buffer
)
{
mlx_status status = MLX_SUCCESS;
if( utils == NULL || count == 0){
status = MLX_INVALID_PARAMETER;
goto bail;
}
status = mlx_pci_read_priv(utils, width, offset, count, buffer);
bail:
return status;
}
mlx_status
mlx_pci_write(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint32 offset,
IN mlx_uintn count,
IN mlx_void *buffer
)
{
mlx_status status = MLX_SUCCESS;
if( utils == NULL || count == 0){
status = MLX_INVALID_PARAMETER;
goto bail;
}
status = mlx_pci_write_priv(utils, width, offset, count, buffer);
bail:
return status;
}
mlx_status
mlx_pci_mem_read(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint8 bar_index,
IN mlx_uint64 offset,
IN mlx_uintn count,
OUT mlx_void *buffer
)
{
mlx_status status = MLX_SUCCESS;
if( utils == NULL || count == 0){
status = MLX_INVALID_PARAMETER;
goto bail;
}
status = mlx_pci_mem_read_priv(utils, bar_index, width, offset, count, buffer);
bail:
return status;
}
mlx_status
mlx_pci_mem_write(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint8 bar_index,
IN mlx_uint64 offset,
IN mlx_uintn count,
IN mlx_void *buffer
)
{
mlx_status status = MLX_SUCCESS;
if( utils == NULL || count == 0){
status = MLX_INVALID_PARAMETER;
goto bail;
}
status = mlx_pci_mem_write_priv(utils, width, bar_index, offset, count, buffer);
bail:
return status;
}

View File

@ -0,0 +1,392 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include "../../include/public/mlx_pci_gw.h"
#include "../../include/public/mlx_bail.h"
#include "../../include/public/mlx_pci.h"
#include "../../include/public/mlx_logging.h"
/* Lock/unlock GW on each VSEC access */
#undef VSEC_DEBUG
static
mlx_status
mlx_pci_gw_check_capability_id(
IN mlx_utils *utils,
IN mlx_uint8 cap_pointer,
OUT mlx_boolean *bool
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint8 offset = cap_pointer + PCI_GW_CAPABILITY_ID_OFFSET;
mlx_uint8 id = 0;
status = mlx_pci_read(utils, MlxPciWidthUint8, offset,
1, &id);
MLX_CHECK_STATUS(utils, status, read_err,"failed to read capability id");
*bool = ( id == PCI_GW_CAPABILITY_ID );
read_err:
return status;
}
static
mlx_status
mlx_pci_gw_get_ownership(
IN mlx_utils *utils
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 cap_offset = utils->pci_gw.pci_cmd_offset;
mlx_uint32 semaphore = 0;
mlx_uint32 counter = 0;
mlx_uint32 get_semaphore_try = 0;
mlx_uint32 get_ownership_try = 0;
for( ; get_ownership_try < PCI_GW_GET_OWNERSHIP_TRIES; get_ownership_try ++){
for( ; get_semaphore_try <= PCI_GW_SEMPHORE_TRIES ; get_semaphore_try++){
status = mlx_pci_read(utils, MlxPciWidthUint32, cap_offset + PCI_GW_CAPABILITY_SEMAPHORE_OFFSET,
1, &semaphore);
MLX_CHECK_STATUS(utils, status, read_err,"failed to read semaphore");
if( semaphore == 0 ){
break;
}
mlx_utils_delay_in_us(10);
}
if( semaphore != 0 ){
status = MLX_FAILED;
goto semaphore_err;
}
status = mlx_pci_read(utils, MlxPciWidthUint32, cap_offset + PCI_GW_CAPABILITY_COUNTER_OFFSET,
1, &counter);
MLX_CHECK_STATUS(utils, status, read_err, "failed to read counter");
status = mlx_pci_write(utils, MlxPciWidthUint32, cap_offset + PCI_GW_CAPABILITY_SEMAPHORE_OFFSET,
1, &counter);
MLX_CHECK_STATUS(utils, status, write_err,"failed to write semaphore");
status = mlx_pci_read(utils, MlxPciWidthUint32, cap_offset + PCI_GW_CAPABILITY_SEMAPHORE_OFFSET,
1, &semaphore);
MLX_CHECK_STATUS(utils, status, read_err,"failed to read semaphore");
if( counter == semaphore ){
break;
}
}
if( counter != semaphore ){
status = MLX_FAILED;
}
write_err:
read_err:
semaphore_err:
return status;
}
static
mlx_status
mlx_pci_gw_free_ownership(
IN mlx_utils *utils
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 cap_offset = utils->pci_gw.pci_cmd_offset;
mlx_uint32 value = 0;
status = mlx_pci_write(utils, MlxPciWidthUint32, cap_offset + PCI_GW_CAPABILITY_SEMAPHORE_OFFSET,
1, &value);
MLX_CHECK_STATUS(utils, status, write_err,"failed to write semaphore");
write_err:
return status;
}
static
mlx_status
mlx_pci_gw_set_space(
IN mlx_utils *utils,
IN mlx_pci_gw_space space
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 cap_offset = utils->pci_gw.pci_cmd_offset;;
mlx_uint8 space_status = 0;
/* set nodnic*/
status = mlx_pci_write(utils, MlxPciWidthUint16, cap_offset + PCI_GW_CAPABILITY_SPACE_OFFSET, 1, &space);
MLX_CHECK_STATUS(utils, status, read_error,"failed to write capability space");
status = mlx_pci_read(utils, MlxPciWidthUint8, cap_offset + PCI_GW_CAPABILITY_STATUS_OFFSET, 1, &space_status);
MLX_CHECK_STATUS(utils, status, read_error,"failed to read capability status");
if( (space_status & 0x20) == 0){
status = MLX_FAILED;
goto space_unsupported;
}
read_error:
space_unsupported:
return status;
}
static
mlx_status
mlx_pci_gw_wait_for_flag_value(
IN mlx_utils *utils,
IN mlx_boolean value
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint32 try = 0;
mlx_uint32 cap_offset = utils->pci_gw.pci_cmd_offset;
mlx_uint32 flag = 0;
for(; try < PCI_GW_READ_FLAG_TRIES ; try ++ ) {
status = mlx_pci_read(utils, MlxPciWidthUint32, cap_offset + PCI_GW_CAPABILITY_FLAG_OFFSET, 1, &flag);
MLX_CHECK_STATUS(utils, status, read_error, "failed to read capability flag");
if( ((flag & 0x80000000) != 0) == value ){
goto flag_valid;
}
mlx_utils_delay_in_us(10);
}
status = MLX_FAILED;
flag_valid:
read_error:
return status;
}
static
mlx_status
mlx_pci_gw_search_capability(
IN mlx_utils *utils,
OUT mlx_uint32 *cap_offset
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint8 cap_pointer = 0;
mlx_boolean is_capability = FALSE;
if( cap_offset == NULL || utils == NULL){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
//get first capability pointer
status = mlx_pci_read(utils, MlxPciWidthUint8, PCI_GW_FIRST_CAPABILITY_POINTER_OFFSET,
1, &cap_pointer);
MLX_CHECK_STATUS(utils, status, read_err,
"failed to read capability pointer");
//search the right capability
while( cap_pointer != 0 ){
status = mlx_pci_gw_check_capability_id(utils, cap_pointer, &is_capability);
MLX_CHECK_STATUS(utils, status, check_err
,"failed to check capability id");
if( is_capability == TRUE ){
*cap_offset = cap_pointer;
break;
}
status = mlx_pci_read(utils, MlxPciWidthUint8, cap_pointer +
PCI_GW_CAPABILITY_NEXT_POINTER_OFFSET ,
1, &cap_pointer);
MLX_CHECK_STATUS(utils, status, read_err,
"failed to read capability pointer");
}
if( is_capability != TRUE ){
status = MLX_NOT_FOUND;
}
check_err:
read_err:
bad_param:
return status;
}
mlx_status
mlx_pci_gw_init(
IN mlx_utils *utils
)
{
mlx_status status = MLX_SUCCESS;
mlx_pci_gw *pci_gw = NULL;
if( utils == NULL){
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
pci_gw = &utils->pci_gw;
status = mlx_pci_gw_search_capability(utils, &pci_gw->pci_cmd_offset);
MLX_CHECK_STATUS(utils, status, cap_err,
"mlx_pci_gw_search_capability failed");
#if ! defined ( VSEC_DEBUG )
status = mlx_pci_gw_get_ownership(utils);
MLX_CHECK_STATUS(utils, status, ownership_err,"failed to get ownership");
ownership_err:
#endif
cap_err:
bad_param:
return status;
}
mlx_status
mlx_pci_gw_teardown(
IN mlx_utils *utils __attribute__ ((unused))
)
{
#if ! defined ( VSEC_DEBUG )
mlx_pci_gw_free_ownership(utils);
#endif
return MLX_SUCCESS;
}
mlx_status
mlx_pci_gw_read(
IN mlx_utils *utils,
IN mlx_pci_gw_space space,
IN mlx_uint32 address,
OUT mlx_pci_gw_buffer *buffer
)
{
mlx_status status = MLX_SUCCESS;
mlx_pci_gw *pci_gw = NULL;
mlx_uint32 cap_offset = 0;
if (utils == NULL || buffer == NULL || utils->pci_gw.pci_cmd_offset == 0) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
mlx_utils_acquire_lock(utils);
pci_gw = &utils->pci_gw;
cap_offset = pci_gw->pci_cmd_offset;
#if ! defined ( VSEC_DEBUG )
if (pci_gw->space != space) {
status = mlx_pci_gw_set_space(utils, space);
MLX_CHECK_STATUS(utils, status, space_error,"failed to set space");
pci_gw->space = space;
}
#else
status = mlx_pci_gw_get_ownership(utils);
MLX_CHECK_STATUS(utils, status, ownership_err,"failed to get ownership");
status = mlx_pci_gw_set_space(utils, space);
MLX_CHECK_STATUS(utils, status, space_error,"failed to set space");
pci_gw->space = space;
#endif
status = mlx_pci_write(utils, MlxPciWidthUint32, cap_offset + PCI_GW_CAPABILITY_ADDRESS_OFFSET, 1, &address);
MLX_CHECK_STATUS(utils, status, read_error,"failed to write capability address");
#if defined ( DEVICE_CX3 )
/* WA for PCI issue (race) */
mlx_utils_delay_in_us ( 10 );
#endif
status = mlx_pci_gw_wait_for_flag_value(utils, TRUE);
MLX_CHECK_STATUS(utils, status, read_error, "flag failed to change");
status = mlx_pci_read(utils, MlxPciWidthUint32, cap_offset + PCI_GW_CAPABILITY_DATA_OFFSET, 1, buffer);
MLX_CHECK_STATUS(utils, status, read_error,"failed to read capability data");
#if defined ( VSEC_DEBUG )
status = mlx_pci_gw_free_ownership(utils);
MLX_CHECK_STATUS(utils, status, free_err,
"mlx_pci_gw_free_ownership failed");
free_err:
mlx_utils_release_lock(utils);
return status;
#endif
read_error:
space_error:
#if defined ( VSEC_DEBUG )
mlx_pci_gw_free_ownership(utils);
ownership_err:
#endif
mlx_utils_release_lock(utils);
bad_param:
return status;
}
mlx_status
mlx_pci_gw_write(
IN mlx_utils *utils,
IN mlx_pci_gw_space space,
IN mlx_uint32 address,
IN mlx_pci_gw_buffer buffer
)
{
mlx_status status = MLX_SUCCESS;
mlx_pci_gw *pci_gw = NULL;
mlx_uint32 cap_offset = 0;
mlx_uint32 fixed_address = address | PCI_GW_WRITE_FLAG;
if (utils == NULL || utils->pci_gw.pci_cmd_offset == 0) {
status = MLX_INVALID_PARAMETER;
goto bad_param;
}
mlx_utils_acquire_lock(utils);
pci_gw = &utils->pci_gw;
cap_offset = pci_gw->pci_cmd_offset;
#if ! defined ( VSEC_DEBUG )
if (pci_gw->space != space) {
status = mlx_pci_gw_set_space(utils, space);
MLX_CHECK_STATUS(utils, status, space_error,"failed to set space");
pci_gw->space = space;
}
#else
status = mlx_pci_gw_get_ownership(utils);
MLX_CHECK_STATUS(utils, status, ownership_err,"failed to get ownership");
status = mlx_pci_gw_set_space(utils, space);
MLX_CHECK_STATUS(utils, status, space_error,"failed to set space");
pci_gw->space = space;
#endif
status = mlx_pci_write(utils, MlxPciWidthUint32, cap_offset + PCI_GW_CAPABILITY_DATA_OFFSET, 1, &buffer);
MLX_CHECK_STATUS(utils, status, read_error,"failed to write capability data");
status = mlx_pci_write(utils, MlxPciWidthUint32, cap_offset + PCI_GW_CAPABILITY_ADDRESS_OFFSET, 1, &fixed_address);
MLX_CHECK_STATUS(utils, status, read_error,"failed to write capability address");
status = mlx_pci_gw_wait_for_flag_value(utils, FALSE);
MLX_CHECK_STATUS(utils, status, read_error, "flag failed to change");
#if defined ( VSEC_DEBUG )
status = mlx_pci_gw_free_ownership(utils);
MLX_CHECK_STATUS(utils, status, free_err,
"mlx_pci_gw_free_ownership failed");
free_err:
mlx_utils_release_lock(utils);
return status;
#endif
read_error:
space_error:
#if defined ( VSEC_DEBUG )
mlx_pci_gw_free_ownership(utils);
ownership_err:
#endif
mlx_utils_release_lock(utils);
bad_param:
return status;
}

View File

@ -0,0 +1,121 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#include <stddef.h>
#include "../../include/private/mlx_utils_priv.h"
#include "../../include/public/mlx_pci.h"
#include "../../include/public/mlx_utils.h"
mlx_status
mlx_utils_init(
IN mlx_utils *utils,
IN mlx_pci *pci
)
{
mlx_status status = MLX_SUCCESS;
if( pci == NULL || utils == NULL ){
status = MLX_INVALID_PARAMETER;
goto bail;
}
utils->pci = pci;
status = mlx_pci_init(utils);
status = mlx_utils_init_lock(utils);
bail:
return status;
}
mlx_status
mlx_utils_teardown(
IN mlx_utils *utils __attribute__ ((unused))
)
{
mlx_status status = MLX_SUCCESS;
mlx_utils_free_lock(utils);
return status;
}
mlx_status
mlx_utils_delay_in_ms(
IN mlx_uint32 msecs
)
{
mlx_utils_delay_in_ms_priv(msecs);
return MLX_SUCCESS;
}
mlx_status
mlx_utils_delay_in_us(
IN mlx_uint32 usecs
)
{
mlx_utils_delay_in_us_priv(usecs);
return MLX_SUCCESS;
}
mlx_status
mlx_utils_ilog2(
IN mlx_uint32 i,
OUT mlx_uint32 *log
)
{
mlx_utils_ilog2_priv(i, log);
return MLX_SUCCESS;
}
mlx_status
mlx_utils_init_lock(
IN OUT mlx_utils *utils
)
{
return mlx_utils_init_lock_priv(&(utils->lock));
}
mlx_status
mlx_utils_free_lock(
IN OUT mlx_utils *utils
)
{
return mlx_utils_free_lock_priv(utils->lock);
}
mlx_status
mlx_utils_acquire_lock (
IN OUT mlx_utils *utils
)
{
return mlx_utils_acquire_lock_priv(utils->lock);
}
mlx_status
mlx_utils_release_lock (
IN OUT mlx_utils *utils
)
{
return mlx_utils_release_lock_priv(utils->lock);
}
mlx_status
mlx_utils_rand (
IN mlx_utils *utils,
OUT mlx_uint32 *rand_num
)
{
return mlx_utils_rand_priv(utils, rand_num);
}

View File

@ -0,0 +1,61 @@
/*
* DebugPriv.h
*
* Created on: Jan 19, 2015
* Author: maord
*/
#ifndef STUB_MLXUTILS_INCLUDE_PRIVATE_FLEXBOOT_DEBUG_H_
#define STUB_MLXUTILS_INCLUDE_PRIVATE_FLEXBOOT_DEBUG_H_
#include <stdio.h>
#include <compiler.h>
#define MLX_DEBUG_FATAL_ERROR_PRIVATE(...) do { \
DBG("%s: ",__func__); \
DBG(__VA_ARGS__); \
} while ( 0 )
#define MLX_DEBUG_ERROR_PRIVATE(id, ...) do { \
DBGC(id, "%s: ",__func__); \
DBGC(id, __VA_ARGS__); \
} while ( 0 )
#define MLX_DEBUG_WARN_PRIVATE(id, ...) do { \
DBGC(id, "%s: ",__func__); \
DBGC(id, __VA_ARGS__); \
} while ( 0 )
#define MLX_DEBUG_INFO1_PRIVATE(id, ...) do { \
DBGC(id, "%s: ",__func__); \
DBGC(id, __VA_ARGS__); \
} while ( 0 )
#define MLX_DEBUG_INFO2_PRIVATE(id, ...) do { \
DBGC2(id, "%s: ",__func__); \
DBGC2(id, __VA_ARGS__); \
} while ( 0 )
#define MLX_DBG_ERROR_PRIVATE(...) do { \
DBG("%s: ",__func__); \
DBG(__VA_ARGS__); \
} while ( 0 )
#define MLX_DBG_WARN_PRIVATE(...) do { \
DBG("%s: ",__func__); \
DBG(__VA_ARGS__); \
} while ( 0 )
#define MLX_DBG_INFO1_PRIVATE(...) do { \
DBG("%s: ",__func__); \
DBG(__VA_ARGS__); \
} while ( 0 )
#define MLX_DBG_INFO2_PRIVATE(...) do { \
DBG2("%s: ",__func__); \
DBG2(__VA_ARGS__); \
} while ( 0 )
#endif /* STUB_MLXUTILS_INCLUDE_PRIVATE_FLEXBOOT_DEBUG_H_ */

View File

@ -0,0 +1,60 @@
/*
* types.h
*
* Created on: Jan 18, 2015
* Author: maord
*/
#ifndef A_MLXUTILS_INCLUDE_PUBLIC_TYPES_H_
#define A_MLXUTILS_INCLUDE_PUBLIC_TYPES_H_
#include <stdint.h>
//#include <errno.h>
#include <ipxe/pci.h>
#define MLX_SUCCESS 0
#define MLX_OUT_OF_RESOURCES (-1)
//(-ENOMEM)
#define MLX_INVALID_PARAMETER (-2)
//(-EINVAL)
#define MLX_UNSUPPORTED (-3)
//(-ENOSYS)
#define MLX_NOT_FOUND (-4)
#define MLX_FAILED (-5)
#undef TRUE
#define TRUE 1
#undef FALSE
#define FALSE !TRUE
typedef int mlx_status;
typedef uint8_t mlx_uint8;
typedef uint16_t mlx_uint16;
typedef uint32_t mlx_uint32;
typedef uint64_t mlx_uint64;
typedef uint32_t mlx_uintn;
typedef int8_t mlx_int8;
typedef int16_t mlx_int16;;
typedef int32_t mlx_int32;
typedef int64_t mlx_int64;
typedef uint8_t mlx_boolean;
typedef struct pci_device mlx_pci;
typedef size_t mlx_size;
typedef void mlx_void;
#define MAC_ADDR_LEN 6
typedef unsigned long mlx_physical_address;
typedef union {
struct {
uint32_t low;
uint32_t high;
} __attribute__ (( packed ));
uint8_t addr[MAC_ADDR_LEN];
} mlx_mac_address;
#endif /* A_MLXUTILS_INCLUDE_PUBLIC_TYPES_H_ */

View File

@ -0,0 +1,172 @@
/*
* MemoryPriv.c
*
* Created on: Jan 21, 2015
* Author: maord
*/
#include <ipxe/malloc.h>
#include <stddef.h>
#include <byteswap.h>
#include <ipxe/io.h>
#include "../../mlx_utils/include/private/mlx_memory_priv.h"
mlx_status
mlx_memory_alloc_priv(
IN mlx_utils *utils __attribute__ ((unused)),
IN mlx_size size,
OUT mlx_void **ptr
)
{
mlx_status status = MLX_SUCCESS;
*ptr = malloc(size);
if(*ptr == NULL){
status = MLX_OUT_OF_RESOURCES;
}
return status;
}
mlx_status
mlx_memory_zalloc_priv(
IN mlx_utils *utils __attribute__ ((unused)),
IN mlx_size size,
OUT mlx_void **ptr
)
{
mlx_status status = MLX_SUCCESS;
*ptr = zalloc(size);
if(*ptr == NULL){
status = MLX_OUT_OF_RESOURCES;
}
return status;
}
mlx_status
mlx_memory_free_priv(
IN mlx_utils *utils __attribute__ ((unused)),
IN mlx_void *ptr
)
{
mlx_status status = MLX_SUCCESS;
free(ptr);
return status;
}
mlx_status
mlx_memory_alloc_dma_priv(
IN mlx_utils *utils __attribute__ ((unused)),
IN mlx_size size ,
IN mlx_size align,
OUT mlx_void **ptr
)
{
mlx_status status = MLX_SUCCESS;
*ptr = malloc_dma(size, align);
if (*ptr == NULL) {
status = MLX_OUT_OF_RESOURCES;
} else {
memset(*ptr, 0, size);
}
return status;
}
mlx_status
mlx_memory_free_dma_priv(
IN mlx_utils *utils __attribute__ ((unused)),
IN mlx_size size ,
IN mlx_void *ptr
)
{
mlx_status status = MLX_SUCCESS;
free_dma(ptr, size);
return status;
}
mlx_status
mlx_memory_map_dma_priv(
IN mlx_utils *utils __attribute__ ((unused)),
IN mlx_void *addr ,
IN mlx_size number_of_bytes __attribute__ ((unused)),
OUT mlx_physical_address *phys_addr,
OUT mlx_void **mapping __attribute__ ((unused))
)
{
mlx_status status = MLX_SUCCESS;
*phys_addr = virt_to_bus(addr);
return status;
}
mlx_status
mlx_memory_ummap_dma_priv(
IN mlx_utils *utils __attribute__ ((unused)),
IN mlx_void *mapping __attribute__ ((unused))
)
{
mlx_status status = MLX_SUCCESS;
return status;
}
mlx_status
mlx_memory_cmp_priv(
IN mlx_utils *utils __unused,
IN mlx_void *first_block,
IN mlx_void *second_block,
IN mlx_size size,
OUT mlx_uint32 *out
)
{
mlx_status status = MLX_SUCCESS;
*out = memcmp(first_block, second_block, size);
return status;
}
mlx_status
mlx_memory_set_priv(
IN mlx_utils *utils __unused,
IN mlx_void *block,
IN mlx_int32 value,
IN mlx_size size
)
{
mlx_status status = MLX_SUCCESS;
memset(block, value, size);
return status;
}
mlx_status
mlx_memory_cpy_priv(
IN mlx_utils *utils __unused,
OUT mlx_void *destination_buffer,
IN mlx_void *source_buffer,
IN mlx_size length
)
{
mlx_status status = MLX_SUCCESS;
memcpy(destination_buffer, source_buffer, length);
return status;
}
mlx_status
mlx_memory_cpu_to_be32_priv(
IN mlx_utils *utils __unused,
IN mlx_uint32 source,
IN mlx_uint32 *destination
)
{
mlx_status status = MLX_SUCCESS;
*destination = cpu_to_be32(source);
return status;
}
mlx_status
mlx_memory_be32_to_cpu_priv(
IN mlx_utils *utils __unused,
IN mlx_uint32 source,
IN mlx_uint32 *destination
)
{
mlx_status status = MLX_SUCCESS;
*destination = be32_to_cpu(source);
return status;
}

View File

@ -0,0 +1,182 @@
/*
* MlxPciPriv.c
*
* Created on: Jan 21, 2015
* Author: maord
*/
#include <ipxe/pci.h>
#include "../../mlx_utils/include/private/mlx_pci_priv.h"
static
mlx_status
mlx_pci_config_byte(
IN mlx_utils *utils,
IN mlx_boolean read,
IN mlx_uint32 offset,
IN OUT mlx_uint8 *buffer
)
{
mlx_status status = MLX_SUCCESS;
if (read) {
status = pci_read_config_byte(utils->pci, offset, buffer);
}else {
status = pci_write_config_byte(utils->pci, offset, *buffer);
}
return status;
}
static
mlx_status
mlx_pci_config_word(
IN mlx_utils *utils,
IN mlx_boolean read,
IN mlx_uint32 offset,
IN OUT mlx_uint16 *buffer
)
{
mlx_status status = MLX_SUCCESS;
if (read) {
status = pci_read_config_word(utils->pci, offset, buffer);
}else {
status = pci_write_config_word(utils->pci, offset, *buffer);
}
return status;
}
static
mlx_status
mlx_pci_config_dword(
IN mlx_utils *utils,
IN mlx_boolean read,
IN mlx_uint32 offset,
IN OUT mlx_uint32 *buffer
)
{
mlx_status status = MLX_SUCCESS;
if (read) {
status = pci_read_config_dword(utils->pci, offset, buffer);
}else {
status = pci_write_config_dword(utils->pci, offset, *buffer);
}
return status;
}
static
mlx_status
mlx_pci_config(
IN mlx_utils *utils,
IN mlx_boolean read,
IN mlx_pci_width width,
IN mlx_uint32 offset,
IN mlx_uintn count,
IN OUT mlx_void *buffer
)
{
mlx_status status = MLX_SUCCESS;
mlx_uint8 *tmp = (mlx_uint8*)buffer;
mlx_uintn iteration = 0;
if( width == MlxPciWidthUint64) {
width = MlxPciWidthUint32;
count = count * 2;
}
for(;iteration < count ; iteration++) {
switch (width){
case MlxPciWidthUint8:
status = mlx_pci_config_byte(utils, read , offset++, tmp++);
break;
case MlxPciWidthUint16:
status = mlx_pci_config_word(utils, read , offset, (mlx_uint16*)tmp);
tmp += 2;
offset += 2;
break;
case MlxPciWidthUint32:
status = mlx_pci_config_dword(utils, read , offset, (mlx_uint32*)tmp);
tmp += 4;
offset += 4;
break;
default:
status = MLX_INVALID_PARAMETER;
}
if(status != MLX_SUCCESS) {
goto config_error;
}
}
config_error:
return status;
}
mlx_status
mlx_pci_init_priv(
IN mlx_utils *utils
)
{
mlx_status status = MLX_SUCCESS;
adjust_pci_device ( utils->pci );
#ifdef DEVICE_CX3
utils->config = ioremap ( pci_bar_start ( utils->pci, PCI_BASE_ADDRESS_0),
0x100000 );
#endif
return status;
}
mlx_status
mlx_pci_read_priv(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint32 offset,
IN mlx_uintn count,
OUT mlx_void *buffer
)
{
mlx_status status = MLX_SUCCESS;
status = mlx_pci_config(utils, TRUE, width, offset, count, buffer);
return status;
}
mlx_status
mlx_pci_write_priv(
IN mlx_utils *utils,
IN mlx_pci_width width,
IN mlx_uint32 offset,
IN mlx_uintn count,
IN mlx_void *buffer
)
{
mlx_status status = MLX_SUCCESS;
status = mlx_pci_config(utils, FALSE, width, offset, count, buffer);
return status;
}
mlx_status
mlx_pci_mem_read_priv(
IN mlx_utils *utils __attribute__ ((unused)),
IN mlx_pci_width width __attribute__ ((unused)),
IN mlx_uint8 bar_index __attribute__ ((unused)),
IN mlx_uint64 offset,
IN mlx_uintn count __attribute__ ((unused)),
OUT mlx_void *buffer
)
{
if (buffer == NULL || width != MlxPciWidthUint32)
return MLX_INVALID_PARAMETER;
*((mlx_uint32 *)buffer) = readl(offset);
return MLX_SUCCESS;
}
mlx_status
mlx_pci_mem_write_priv(
IN mlx_utils *utils __attribute__ ((unused)),
IN mlx_pci_width width __attribute__ ((unused)),
IN mlx_uint8 bar_index __attribute__ ((unused)),
IN mlx_uint64 offset,
IN mlx_uintn count __attribute__ ((unused)),
IN mlx_void *buffer
)
{
if (buffer == NULL || width != MlxPciWidthUint32)
return MLX_INVALID_PARAMETER;
barrier();
writel(*((mlx_uint32 *)buffer), offset);
return MLX_SUCCESS;
}

View File

@ -0,0 +1,83 @@
/*
* MlxUtilsPriv.c
*
* Created on: Jan 25, 2015
* Author: maord
*/
#include <unistd.h>
#include <stdlib.h>
#include <strings.h>
#include "../../mlx_utils/include/private/mlx_utils_priv.h"
mlx_status
mlx_utils_delay_in_ms_priv(
IN mlx_uint32 msecs
)
{
mdelay(msecs);
return MLX_SUCCESS;
}
mlx_status
mlx_utils_delay_in_us_priv(
IN mlx_uint32 usecs
)
{
udelay(usecs);
return MLX_SUCCESS;
}
mlx_status
mlx_utils_ilog2_priv(
IN mlx_uint32 i,
OUT mlx_uint32 *log
)
{
*log = ( fls ( i ) - 1 );
return MLX_SUCCESS;
}
mlx_status
mlx_utils_init_lock_priv(
OUT void **lock __unused
)
{
return MLX_SUCCESS;
}
mlx_status
mlx_utils_free_lock_priv(
IN void *lock __unused
)
{
return MLX_SUCCESS;
}
mlx_status
mlx_utils_acquire_lock_priv (
IN void *lock __unused
)
{
return MLX_SUCCESS;
}
mlx_status
mlx_utils_release_lock_priv (
IN void *lock __unused
)
{
return MLX_SUCCESS;
}
mlx_status
mlx_utils_rand_priv (
IN mlx_utils *utils __unused,
OUT mlx_uint32 *rand_num
)
{
do {
*rand_num = rand();
} while ( *rand_num == 0 );
return MLX_SUCCESS;
}

View File

@ -0,0 +1,47 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#ifndef SRC_DRIVERS_INFINIBAND_MLX_NODNIC_INCLUDE_PRM_NODNIC_PRM_H_
#define SRC_DRIVERS_INFINIBAND_MLX_NODNIC_INCLUDE_PRM_NODNIC_PRM_H_
#include "mlx_bitops.h"
struct nodnic_wqe_segment_data_ptr_st { /* Little Endian */
pseudo_bit_t byte_count[0x0001f];
pseudo_bit_t always0[0x00001];
/* -------------- */
pseudo_bit_t l_key[0x00020];
/* -------------- */
pseudo_bit_t local_address_h[0x00020];
/* -------------- */
pseudo_bit_t local_address_l[0x00020];
/* -------------- */
};
struct MLX_DECLARE_STRUCT ( nodnic_wqe_segment_data_ptr );
#define HERMON_MAX_SCATTER 1
struct nodnic_recv_wqe {
struct nodnic_wqe_segment_data_ptr data[HERMON_MAX_SCATTER];
} __attribute__ (( packed ));
#endif /* SRC_DRIVERS_INFINIBAND_MLX_NODNIC_INCLUDE_PRM_NODNIC_PRM_H_ */

View File

@ -0,0 +1,143 @@
/*
* Copyright (C) 2015 Mellanox Technologies Ltd.
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; either version 2 of the
* License, or any later version.
*
* This program is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
* 02110-1301, USA.
*/
FILE_LICENCE ( GPL2_OR_LATER );
#ifndef SRC_DRIVERS_INFINIBAND_MLX_NODNIC_INCLUDE_PRM_NODNIC_SHOMRON_PRM_H_
#define SRC_DRIVERS_INFINIBAND_MLX_NODNIC_INCLUDE_PRM_NODNIC_SHOMRON_PRM_H_
#include "nodnic_prm.h"
#define SHOMRON_MAX_GATHER 1
/* Send wqe segment ctrl */
struct shomronprm_wqe_segment_ctrl_send_st { /* Little Endian */
pseudo_bit_t opcode[0x00008];
pseudo_bit_t wqe_index[0x00010];
pseudo_bit_t reserved1[0x00008];
/* -------------- */
pseudo_bit_t ds[0x00006]; /* descriptor (wqe) size in 16bytes chunk */
pseudo_bit_t reserved2[0x00002];
pseudo_bit_t qpn[0x00018];
/* -------------- */
pseudo_bit_t reserved3[0x00002];
pseudo_bit_t ce[0x00002];
pseudo_bit_t reserved4[0x0001c];
/* -------------- */
pseudo_bit_t reserved5[0x00040];
/* -------------- */
pseudo_bit_t mss[0x0000e];
pseudo_bit_t reserved6[0x0000e];
pseudo_bit_t cs13_inner[0x00001];
pseudo_bit_t cs14_inner[0x00001];
pseudo_bit_t cs13[0x00001];
pseudo_bit_t cs14[0x00001];
/* -------------- */
pseudo_bit_t reserved7[0x00020];
/* -------------- */
pseudo_bit_t inline_headers1[0x00010];
pseudo_bit_t inline_headers_size[0x0000a]; //sum size of inline_hdr1+inline_hdrs (0x10)
pseudo_bit_t reserved8[0x00006];
/* -------------- */
pseudo_bit_t inline_headers2[0x00020];
/* -------------- */
pseudo_bit_t inline_headers3[0x00020];
/* -------------- */
pseudo_bit_t inline_headers4[0x00020];
/* -------------- */
pseudo_bit_t inline_headers5[0x00020];
};
/* Completion Queue Entry Format #### michal - fixed by gdror */
struct shomronprm_completion_queue_entry_st { /* Little Endian */
pseudo_bit_t reserved1[0x00080];
/* -------------- */
pseudo_bit_t reserved2[0x00010];
pseudo_bit_t ml_path[0x00007];
pseudo_bit_t reserved3[0x00009];
/* -------------- */
pseudo_bit_t slid[0x00010];
pseudo_bit_t reserved4[0x00010];
/* -------------- */
pseudo_bit_t rqpn[0x00018];
pseudo_bit_t sl[0x00004];
pseudo_bit_t l3_hdr[0x00002];
pseudo_bit_t reserved5[0x00002];
/* -------------- */
pseudo_bit_t reserved10[0x00020];
/* -------------- */
pseudo_bit_t srqn[0x00018];
pseudo_bit_t reserved11[0x0008];
/* -------------- */
pseudo_bit_t pkey_index[0x00020];
/* -------------- */
pseudo_bit_t reserved6[0x00020];
/* -------------- */
pseudo_bit_t byte_cnt[0x00020];
/* -------------- */
pseudo_bit_t reserved7[0x00040];
/* -------------- */
pseudo_bit_t qpn[0x00018];
pseudo_bit_t rx_drop_counter[0x00008];
/* -------------- */
pseudo_bit_t owner[0x00001];
pseudo_bit_t reserved8[0x00003];
pseudo_bit_t opcode[0x00004];
pseudo_bit_t reserved9[0x00008];
pseudo_bit_t wqe_counter[0x00010];
};
/* Completion with Error CQE #### michal - gdror fixed */
struct shomronprm_completion_with_error_st { /* Little Endian */
pseudo_bit_t reserved1[0x001a0];
/* -------------- */
pseudo_bit_t syndrome[0x00008];
pseudo_bit_t vendor_error_syndrome[0x00008];
pseudo_bit_t reserved2[0x00010];
/* -------------- */
pseudo_bit_t reserved3[0x00040];
};
struct MLX_DECLARE_STRUCT ( shomronprm_wqe_segment_ctrl_send );
struct MLX_DECLARE_STRUCT ( shomronprm_completion_queue_entry );
struct MLX_DECLARE_STRUCT ( shomronprm_completion_with_error );
struct shomron_nodnic_eth_send_wqe {
struct shomronprm_wqe_segment_ctrl_send ctrl;
struct nodnic_wqe_segment_data_ptr data[SHOMRON_MAX_GATHER];
} __attribute__ (( packed ));
union shomronprm_completion_entry {
struct shomronprm_completion_queue_entry normal;
struct shomronprm_completion_with_error error;
} __attribute__ (( packed ));
#endif /* SRC_DRIVERS_INFINIBAND_MLX_NODNIC_INCLUDE_PRM_NODNIC_SHOMRON_PRM_H_ */

View File

@ -186,6 +186,8 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
#define ERRFILE_smsc95xx ( ERRFILE_DRIVER | 0x007a0000 )
#define ERRFILE_acm ( ERRFILE_DRIVER | 0x007b0000 )
#define ERRFILE_eoib ( ERRFILE_DRIVER | 0x007c0000 )
#define ERRFILE_golan ( ERRFILE_DRIVER | 0x007d0000 )
#define ERRFILE_flexboot_nodnic ( ERRFILE_DRIVER | 0x007e0000 )
#define ERRFILE_aoe ( ERRFILE_NET | 0x00000000 )
#define ERRFILE_arp ( ERRFILE_NET | 0x00010000 )