/* * Copyright (c) 2011-2015, Emulex * All rights reserved. * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions are met: * * 1. Redistributions of source code must retain the above copyright notice, * this list of conditions and the following disclaimer. * * 2. Redistributions in binary form must reproduce the above copyright notice, * this list of conditions and the following disclaimer in the documentation * and/or other materials provided with the distribution. * * 3. Neither the name of the copyright holder nor the names of its contributors * may be used to endorse or promote products derived from this software * without specific prior written permission. * * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE * POSSIBILITY OF SUCH DAMAGE. * */ #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include "elxu_common.h" /* * This file contains functions specific to BSD. * Any non-static functions here should: * - be declared in elxu_common.h * - have an equivalent in elxu_linux.c, even if it's a stub */ #define OCS_DEV_TEMPLATE "/dev/ocs" typedef struct elxu_bsd_command_s { uint32_t magic; uint32_t size; // size of this structure uint8_t payload[256]; uint64_t in_addr; // user space address of input buffer uint64_t in_bytes; uint64_t out_addr; // user space address of output buffer uint64_t out_bytes; } elxu_bsd_command_t; #define ELXU_BSD_COMMAND _IOWR('Q', 0, struct elxu_bsd_command_s) elxu_device_t *os_build_device_list(char *path) { struct pci_conf_io pc; struct pci_conf conf[1024]; int fd; int i; int index; elxu_device_t *new_device; elxu_device_t *list; fd = open("/dev/pci", O_RDONLY); if (fd < 0) { return NULL; } bzero(&pc, sizeof(struct pci_conf_io)); pc.match_buf_len = sizeof(conf); pc.matches = conf; list = NULL; index = 0; ioctl(fd, PCIOCGETCONF, &pc); for (i=0; inext = list; list = new_device; new_device->vendor = conf[i].pc_vendor; new_device->device = conf[i].pc_device; new_device->driver = DEVICE_DRIVER_OCS; new_device->deviceIndex = index++; } close(fd); return list; } elxu_device_t *os_build_device_list_uspace(char *hostname) { /* User space driver not supported on BSD */ return NULL; } /** * @brief Open a device file. * * @par Description * This function opens a device file on BSD. * The input is an elxu_device_name_t which contains a device * index and a hostname. If the hostname is non-NULL then the * request is for a userspace driver, and the hostname is the * host one which the driver is running. This is not supported * on BSD. If the hostname is NULL then the index field * specifies which device file to open. * * * @param devname An elxu_device_name_t structure that specifies * the device to be opened. * * @return Returns a pointer to an elxu_device_t on success; * NULL on failure. */ elxu_device_t *os_open_device(elxu_device_name_t *devname) { elxu_device_t *device = NULL; char path[FILENAME_MAX]; if (devname->hostname) { printf("%s: user space driver not supported for FreeBSD\n", __func__); return NULL; } snprintf(path, sizeof(path), "%s%d", OCS_DEV_TEMPLATE, devname->devidx); device = elxu_device_by_index(devname->devidx); if (device == NULL) { return NULL; } device->fd = open(path, O_RDWR); if (device->fd < 0) { return NULL; } strcpy(device->device_file_name, path); return device; } /** * @brief Close a device file. * * @par Description * This function closes an open device file. * * * @param device A pointer to an elxu_device_t to be closed. * * @return Returns nothing. */ void os_close_device(elxu_device_t *device) { close(device->fd); } int os_remove_device(elxu_device_t *device) { //Driver owns the device in FreeBSD. return 0; } /** * @brief Send an ioctl to an open device. * * @par Description * This function sends an ioctl to an open device. * * @param device A pointer to the device. * @param req The request to be sent to the device. * @param arg The argument to be sent to the device. * * @return Returns 0 on success; non-zero on failure. */ int os_ioctl_device(elxu_device_t *device, int req, void *arg) { unsigned long ul_req = (unsigned long)req & 0xffffffff; return ioctl(device->fd, ul_req, arg); } /** * @brief Print iSCSI connection info for the given device. * * @par Description * This function prints iSCSI connection information for the * given device. BSD does not support iSCSI connection info, so * this function prints an error message and returns. * * @param device The device for which to print connection info. * * @return Returns nothing. */ void elxu_get_connection_info(elxu_device_t *device) { printf("iSCSI connection info is not supported on BSD\n"); } /* vim: set expandtab tabstop=4 shiftwidth=4: */