| b.liu | e958203 | 2025-04-17 19:18:16 +0800 | [diff] [blame] | 1 | #!/bin/sh |
| 2 | # |
| 3 | # Copyright (C) Voltaire Ltd. 2006. ALL RIGHTS RESERVED. |
| 4 | # |
| 5 | # This program is free software; you can redistribute it and/or |
| 6 | # modify it under the terms of the GNU General Public License |
| 7 | # as published by the Free Software Foundation; either version 2 |
| 8 | # of the License, or (at your option) any later version. |
| 9 | # |
| 10 | # This program is distributed in the hope that it will be useful, |
| 11 | # but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 12 | # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 13 | # GNU General Public License for more details. |
| 14 | # |
| 15 | # You should have received a copy of the GNU General Public License |
| 16 | # along with this program; if not, write to the Free Software |
| 17 | # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. |
| 18 | # |
| 19 | # Author: Dan Bar Dov <danb@voltaire.com> |
| 20 | |
| 21 | # iscsi_discovery: |
| 22 | # * does a send-targets discovery to the given IP |
| 23 | # * set the transport type to the preferred transport (or tcp is -t flag is not used) |
| 24 | # * tries to login |
| 25 | # * if succeeds, |
| 26 | # o logout, |
| 27 | # o mark record autmatic (unless -m flag is used) |
| 28 | # * else |
| 29 | # o reset transport type to TCP |
| 30 | # o try to login |
| 31 | # o if succeeded |
| 32 | # + logout |
| 33 | # + mark record automatic (unless -m flag is used) |
| 34 | # |
| 35 | |
| 36 | usage() |
| 37 | { |
| 38 | echo "Usage: $0 <IP> [-p <port>] [-d] [-t <tcp|iser> [-f]] [-m] [-l]" |
| 39 | echo "Options:" |
| 40 | echo "-p set the port number (default is 3260)." |
| 41 | echo "-d print debugging information" |
| 42 | echo "-t set transport (default is tcp)." |
| 43 | echo "-f force specific transport -disable the fallback to tcp (default is fallback enabled)." |
| 44 | echo " force the transport specified by the argument of the -t flag." |
| 45 | echo "-m manual startup - will set manual startup (default is automatic startup)." |
| 46 | echo "-l login to the new discovered nodes (default is false)." |
| 47 | } |
| 48 | |
| 49 | dbg() |
| 50 | { |
| 51 | $debug && echo $@ |
| 52 | } |
| 53 | |
| 54 | initialize() |
| 55 | { |
| 56 | trap "exit" 2 |
| 57 | debug=false |
| 58 | force="0" |
| 59 | log_out="1" |
| 60 | startup_manual="0" |
| 61 | #set default transport to tcp |
| 62 | transport=tcp |
| 63 | #set default port to 3260 |
| 64 | port=3260; |
| 65 | } |
| 66 | |
| 67 | parse_cmdline() |
| 68 | { |
| 69 | if [ $# -lt 1 ]; then |
| 70 | usage |
| 71 | exit 1 |
| 72 | fi |
| 73 | |
| 74 | # check if the IP address is valid |
| 75 | ip=`echo $1 | awk -F'.' '$1 != "" && $1 <=255 && $2 != "" && $2 <= 255 && $3 != "" && $3 <= 255 && $4 != "" && $4 <= 255 {print $0}'` |
| 76 | if [ -z "$ip" ]; then |
| 77 | echo "$1 is not a vaild IP address!" |
| 78 | exit 1 |
| 79 | fi |
| 80 | shift |
| 81 | while getopts "dfmlt:p:" options; do |
| 82 | case $options in |
| 83 | d ) debug=true;; |
| 84 | f ) force="1";; |
| 85 | t ) transport=$OPTARG;; |
| 86 | p ) port=$OPTARG;; |
| 87 | m ) startup_manual="1";; |
| 88 | l ) log_out=0;; |
| 89 | \? ) usage |
| 90 | exit 1;; |
| 91 | * ) usage |
| 92 | exit 1;; |
| 93 | esac |
| 94 | done |
| 95 | } |
| 96 | |
| 97 | discover() |
| 98 | { |
| 99 | # If open-iscsi is already logged in to the portal, exit |
| 100 | if [ $(iscsiadm -m session | grep -c ${ip}:${port}) -ne 0 ]; then |
| 101 | echo "Please logout from all targets on ${ip}:${port} before trying to run discovery on that portal" |
| 102 | exit 2 |
| 103 | fi |
| 104 | |
| 105 | connected=0 |
| 106 | discovered=0 |
| 107 | |
| 108 | dbg "starting discovery to $ip" |
| 109 | disc="$(iscsiadm -m discovery --type sendtargets --portal ${ip}:${port})" |
| 110 | echo "${disc}" | while read portal target |
| 111 | do |
| 112 | portal=${portal%,*} |
| 113 | select_transport |
| 114 | done |
| 115 | |
| 116 | discovered=$(echo "${disc}" | wc -l) |
| 117 | if [ ${discovered} = 0 ]; then |
| 118 | echo "failed to discover targets at ${ip}" |
| 119 | exit 2 |
| 120 | else |
| 121 | echo "discovered ${discovered} targets at ${ip}" |
| 122 | fi |
| 123 | } |
| 124 | |
| 125 | try_login() |
| 126 | { |
| 127 | if [ "$startup_manual" != "1" ]; then |
| 128 | iscsiadm -m node --targetname ${target} --portal ${portal} --op update -n node.conn[0].startup -v automatic |
| 129 | fi |
| 130 | iscsiadm -m node --targetname ${target} --portal ${portal} --login >/dev/null 2>&1 |
| 131 | ret=$? |
| 132 | if [ ${ret} = 0 ]; then |
| 133 | echo "Set target ${target} to automatic login over ${transport} to portal ${portal}" |
| 134 | ((connected++)) |
| 135 | if [ "$log_out" = "1" ]; then |
| 136 | iscsiadm -m node --targetname ${target} --portal ${portal} --logout |
| 137 | fi |
| 138 | else |
| 139 | echo "Cannot login over ${transport} to portal ${portal}" |
| 140 | iscsiadm -m node --targetname ${target} --portal ${portal} --op update -n node.conn[0].startup -v manual |
| 141 | fi |
| 142 | return ${ret} |
| 143 | } |
| 144 | |
| 145 | set_transport() |
| 146 | { |
| 147 | transport=$1 |
| 148 | case "$transport" in |
| 149 | iser) |
| 150 | # iSER does not use digest |
| 151 | iscsiadm -m node --targetname ${target} --portal ${portal} \ |
| 152 | --op update -n node.conn[0].iscsi.HeaderDigest -v None |
| 153 | iscsiadm -m node --targetname ${target} --portal ${portal} \ |
| 154 | --op update -n node.conn[0].iscsi.DataDigest -v None |
| 155 | ;; |
| 156 | cxgb3i) |
| 157 | # cxgb3i supports <= 16K packet (BHS + AHS + pdu payload + digests) |
| 158 | iscsiadm -m node --targetname ${target} --portal ${portal} \ |
| 159 | --op update -n node.conn[0].iscsi.MaxRecvDataSegmentLength \ |
| 160 | -v 8192 |
| 161 | ;; |
| 162 | esac |
| 163 | transport_name=`iscsiadm -m node -p ${portal} -T ${target} |awk '/transport_name/ {print $1}'` |
| 164 | iscsiadm -m node --targetname ${target} --portal ${portal} \ |
| 165 | --op update -n ${transport_name} -v ${transport} |
| 166 | } |
| 167 | |
| 168 | select_transport() |
| 169 | { |
| 170 | set_transport $transport |
| 171 | dbg "Testing $transport-login to target ${target} portal ${portal}" |
| 172 | try_login; |
| 173 | if [ $? != 0 -a "$force" = "0" ]; then |
| 174 | set_transport tcp |
| 175 | dbg "starting to test tcp-login to target ${target} portal ${portal}" |
| 176 | try_login; |
| 177 | fi |
| 178 | } |
| 179 | |
| 180 | check_iscsid() |
| 181 | { |
| 182 | #check if iscsid is running |
| 183 | pidof iscsid &>/dev/null |
| 184 | ret=$? |
| 185 | if [ $ret -ne 0 ]; then |
| 186 | echo "iscsid is not running" |
| 187 | echo "Exiting..." |
| 188 | exit 1 |
| 189 | fi |
| 190 | } |
| 191 | |
| 192 | check_iscsid |
| 193 | initialize |
| 194 | parse_cmdline "$@" |
| 195 | discover |