⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 iscsi-probe.c

📁 这个linux源代码是很全面的~基本完整了~使用c编译的~由于时间问题我没有亲自测试~但就算用来做参考资料也是非常好的
💻 C
📖 第 1 页 / 共 4 页
字号:
        set_current_state(TASK_UNINTERRUPTIBLE);        schedule_timeout(MSECS_TO_JIFFIES(20));        return 1;    }     return rc;}/* caller must hold the iscsi_lun_probe_mutex */static int iscsi_probe_lun(iscsi_session_t *session, int lun){    char str[80];    int rc;    if (lun >= ISCSI_MAX_LUN)        return 0;    sprintf(str, "scsi add-single-device %d %d %d %d\n",             session->host_no, session->channel, session->target_id, lun);    str[sizeof(str) - 1] = '\0';    rc = write_proc_scsi_scsi(session, str);    if (rc < 0) {        /* clear the newline */        str[strlen(str) - 1] = '\0';        printk("iSCSI: session %p error %d writing '%s' to /proc/scsi/scsi\n",               session, rc, str);        return 0;    }        return rc;}static int iscsi_remove_lun(iscsi_session_t *session, int lun){    char str[88];    int rc = 0;    sprintf(str, "scsi remove-single-device %d %d %d %d\n",             session->host_no, session->channel, session->target_id, lun);    str[sizeof(str) - 1] = '\0';        rc = write_proc_scsi_scsi(session, str);    if (rc < 0) {        /* clear the newline */        str[strlen(str) - 1] = '\0';        printk("iSCSI: session %p error %d writing '%s' to /proc/scsi/scsi\n",               session, rc, str);        return 0;    }    else {        /* removed it */        clear_bit(lun, session->luns_activated);        return 1;    }        return rc;}static void empty_directory(char *dir, char *data, int size){    int fd;    struct dirent dent;    int rc, processed;    char *name = dir + strlen(dir);        /* there should only be directories in the target dir */    if ((fd = open(dir, O_DIRECTORY|O_RDONLY, 0)) >= 0) {        /* loop doing getdents, and unlinking files */        do {            rc = getdents(fd, (struct dirent *)data, size);            DEBUG_FLOW3("iSCSI: getdents %s, size %d, returned %d\n",                         dir, size, rc);            processed = 0;            while (processed < rc) {                memcpy(&dent, &data[processed], sizeof(dent));                strcpy(name, &data[processed] + offsetof(struct dirent, d_name));                if (strcmp(name, ".") && strcmp(name, "..")) {                    DEBUG_FLOW1("iSCSI: unlink %s\n", dir);                    unlink(dir);                }                processed += dent.d_reclen;             }        } while (rc > 0);                name[0] = '\0';        close(fd);    }}void iscsi_remove_luns(iscsi_session_t *session){    int l;    mm_segment_t oldfs;    char *data = session->RxBuf;    int size = sizeof(session->RxBuf) - 1;    char *lun_dir = session->target_link_dir + strlen(session->target_link_dir);    char *bus_dir = lun_dir - 2; /* before the slash */    char c;    /* try to release the kernel's SCSI device structures for every LUN */    down(&iscsi_lun_probe_mutex);    oldfs = get_fs();    set_fs( get_ds() );        for (l = 0; l < ISCSI_MAX_LUN; l++) {        if (session->target_link_dir[0] == '/') {            sprintf(lun_dir, "lun%d/", l);                        /* this assumes the session isn't using the RxBuf right now */            empty_directory(session->target_link_dir, data, size);                        rmdir(session->target_link_dir);        }        if (test_bit(l, session->luns_activated)) {            /* tell Linux to release the Scsi_Devices */            iscsi_remove_lun(session, l);        }    }    if (session->target_link_dir[0] == '/') {        /* and get rid of the target dir itself */        *lun_dir = '\0';        DEBUG_FLOW1("iSCSI: rmdir %s\n", session->target_link_dir);        rmdir(session->target_link_dir);        /* if the bus dir is empty now, get rid of it too, but don't corrupt the session's target dir */        while (*bus_dir != '/')            bus_dir--;        bus_dir++; /* leave the slash */        c = *bus_dir;        *bus_dir = '\0';                DEBUG_FLOW1("iSCSI: rmdir %s\n", session->target_link_dir);        rmdir(session->target_link_dir);        *bus_dir = c;    }    set_fs( oldfs );    up(&iscsi_lun_probe_mutex);}/* find all dir prefixes of pathname, and make them all if they don't exist */static void ensure_directories_exist(char *pathname, mode_t dir_mode){    char *end = pathname;    /* skip leading slashes */    while (end && *end && (*end == '/'))        end++;    while (end && (*end != '\0')) {        /* if there is another slash, make the dir.         * FIXME: we ought to ignore errors when the directory exists,         * but report errors where the directory doesn't exist and         * we failed to create it.         */        while ((*end != '/') && (*end != '\0'))            end++;                if (*end == '/') {            *end = '\0';            mkdir(pathname, dir_mode);            *end = '/';            end++;        }    }}static int get_device_scsi_quad(char *device_name, int *host, int *channel, int *target, int *lun){    int ret = 0;    u_long info[2];    struct file *filp = NULL;    struct inode *inode = NULL;    filp = filp_open(device_name, O_RDONLY|O_NONBLOCK, 0);    if (IS_ERR(filp)) {        return 0;    }        memset(info, 0, sizeof(info));    inode = filp->f_dentry->d_inode;    if (filp->f_op->ioctl(inode, filp, SCSI_IOCTL_GET_IDLUN, (unsigned long)info) == 0) {        if (target)            *target = info[0] & 0xff;        if (lun)            *lun = (info[0] >> 8) & 0xff;        if (channel)            *channel = (info[0] >> 16) & 0xff;#if ( LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,0) )        /* 2.4 kernels give us all the info we need with that ioctl. */        if (host)            *host = ((info[0] >> 24) & 0xff);                                       ret = 1;#else        /* 2.2 kernels have another ioctl to get the host number, and set the host         * above to something useless to us.         */        memset(info, 0, sizeof(info));        if (filp->f_op->ioctl(inode, filp, SCSI_IOCTL_GET_BUS_NUMBER, (unsigned long)info) == 0) {            if (host)                *host = info[0];            ret = 1;        }#endif    }    filp_close(filp, 0);    return ret;}static void iscsi_update_disk_links(iscsi_session_t *session, int max_sd_devices, int max_sd_partitions, mode_t dir_mode){    int i;    char devname[20];    /* we've reserved enough space in session->target_link_dir so that we can use it to build pathnames */    char *lun_dir = session->target_link_dir + strlen(session->target_link_dir);    /* FIXME: can we get the number of devices supported from the running kernel? */    for (i=0; i < max_sd_devices; i++) {        int host = -1, channel = -1, id = -1, lun = -1;        if (i < 26) {            sprintf(devname, "/dev/sd%c", 'a' + i);        }        else {            /* double char names for disknum 26+ */            sprintf(devname, "/dev/sd%c%c", 'a' + (i / 26) - 1, 'a' + (i % 26));        }        if (get_device_scsi_quad(devname, &host, &channel, &id, &lun)) {            if ((host == session->host_no) && (channel == session->channel) && (id == session->target_id)) {                char *partition = devname + strlen(devname);                char *link;                int p;                DEBUG_INIT4("iSCSI: disk device node %s = bus %d target %d LUN %d\n", devname, session->iscsi_bus, id, lun);                                /* ensure the LUN dir exists */                sprintf(lun_dir, "lun%d/", lun);                ensure_directories_exist(session->target_link_dir, dir_mode);                link = lun_dir + strlen(lun_dir);                /* symlink the whole-disk device */                strcpy(link, "disk");                unlink(session->target_link_dir); /* remove any existing symlink */                symlink(devname, session->target_link_dir); /* make a new symlink */                                /* and make links for each possible disk partition as well,                 * since we don't want to have to track what partitions get added or removed.                 * This works just like the normal partition device nodes, which                 * are always present, but may or may not be openable.                 */                for (p = 1; p <= max_sd_partitions; p++) {                    sprintf(partition, "%d", p);                    sprintf(link, "part%d", p);                    unlink(session->target_link_dir);                    symlink(devname, session->target_link_dir);                }            }        }    }    /* restore the session's target dir */    *lun_dir = '\0';}static void iscsi_update_tape_links(iscsi_session_t *session, int max_st_devices, mode_t dir_mode){    int i;    char devname[20];    /* we've reserved enough space in session->target_link_dir so that we can use it to build pathnames */    char *lun_dir = session->target_link_dir + strlen(session->target_link_dir);    /* FIXME: can we get the number of devices supported from the running kernel? */    for (i=0; i < max_st_devices; i++) {        int host = -1, channel = -1, id = -1, lun = -1;        /* we check the no-rewind device to avoid having side-effects */        sprintf(devname, "/dev/nst%d", i);        if (get_device_scsi_quad(devname, &host, &channel, &id, &lun)) {            if ((host == session->host_no) && (channel == session->channel) && (id == session->target_id)) {                char *link;                DEBUG_INIT4("iSCSI: tape device node %s = bus %d target %d LUN %d\n", devname, session->iscsi_bus, id, lun);                                /* ensure the LUN dir exists */                sprintf(lun_dir, "lun%d/", lun);                ensure_directories_exist(session->target_link_dir, dir_mode);                link = lun_dir + strlen(lun_dir);                /* auto-rewind nodes */                strcpy(link, "mt");                unlink(session->target_link_dir); /* remove any existing symlink */                sprintf(devname, "/dev/st%d", i);                symlink(devname, session->target_link_dir); /* make a new symlink */                strcpy(link, "mtl");                unlink(session->target_link_dir); /* remove any existing symlink */                sprintf(devname, "/dev/st%dl", i);                symlink(devname, session->target_link_dir); /* make a new symlink */                strcpy(link, "mtm");                unlink(session->target_link_dir); /* remove any existing symlink */                sprintf(devname, "/dev/st%dm", i);                symlink(devname, session->target_link_dir); /* make a new symlink */                strcpy(link, "mta");                unlink(session->target_link_dir); /* remove any existing symlink */                sprintf(devname, "/dev/st%da", i);                symlink(devname, session->target_link_dir); /* make a new symlink */                                    /* no rewind nodes */                strcpy(link, "mtn");                unlink(session->target_link_dir); /* remove any existing symlink */                sprintf(devname, "/dev/nst%d", i);                symlink(devname, session->target_link_dir); /* make a new symlink */                strcpy(link, "mtln");                unlink(session->target_link_dir); /* remove any existing symlink */                sprintf(devname, "/dev/nst%dl", i);                symlink(devname, session->target_link_dir); /* make a new symlink */                strcpy(link, "mtmn");                unlink(session->target_link_dir); /* remove any existing symlink */                sprintf(devname, "/dev/nst%dm", i);                symlink(devname, session->target_link_dir); /* make a new symlink */                strcpy(link, "mtan");                unlink(session->target_link_dir); /* remove any existing symlink */                sprintf(devname, "/dev/nst%da", i);                symlink(devname, session->target_link_dir); /* make a new symlink */            }        }    }    /* restore the session's target dir */    *lun_dir = '\0';}static void iscsi_update_generic_links(iscsi_session_t *session, int max_sg_devices, mode_t dir_mode){    int i;    char devname[20];    /* we've reserved enough space in session->target_link_dir so that we can use it to build pathnames */    char *lun_dir = session->target_link_dir + strlen(session->target_link_dir);    char *link;    /* FIXME: can we get the number of devices supported from the running kernel? */    for (i=0; i < max_sg_devices; i++) {

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -