#!/bin/sh /etc/rc.common
|
|
START=91
|
|
STOP=10
|
|
|
|
extra_command "show" "Show current configuration of tgtd"
|
|
|
|
NAME=tgt
|
|
PROG=/usr/sbin/tgtd
|
|
USE_PROCD=1
|
|
|
|
tgtadm="/usr/sbin/tgtadm --lld iscsi"
|
|
logger="logger -p daemon.err -s -t $NAME"
|
|
|
|
validate_lun_section() {
|
|
uci_load_validate tgt lun "$1" "$2" \
|
|
'device:or(file, device)' \
|
|
'type:or("disk", "cd", "pt"):disk' \
|
|
'bstype:or("rdwr", "aio", "sg"):rdwr' \
|
|
'sync:bool:0' \
|
|
'direct:bool:0' \
|
|
'blocksize:uinteger' \
|
|
'mode_page:string' \
|
|
'product_id:string' \
|
|
'product_rev:string' \
|
|
'readonly:bool:0' \
|
|
'removable:bool' \
|
|
'scsi_id:string' \
|
|
'scsi_sn:string' \
|
|
'sense_format:range(0, 1)' \
|
|
'vendor_id:string' \
|
|
'rotation_rate:uinteger'
|
|
}
|
|
|
|
handle_lun() {
|
|
local tgt_lun=$1
|
|
local my_tgtid=${tgt_lun%_*}
|
|
local lun=${tgt_lun#*_}
|
|
|
|
[ "$my_tgtid" -eq "$tgtid" ] || return 0
|
|
|
|
[ "$2" = 0 ] || {
|
|
$logger "Validation failed for LUN $tgt_lun"
|
|
return 1
|
|
}
|
|
[ "$device" ] || {
|
|
$logger "Device is required for target $tgt_lun"
|
|
return 1
|
|
}
|
|
|
|
if [ "$sync" -ne 0 ] || [ "$direct" -ne 0 ]; then
|
|
local bsoflags
|
|
[ "$sync" -ne 0 ] && bsoflags="sync"
|
|
[ "$direct" -ne 0 ] && bsoflags="direct"
|
|
[ "$sync" -ne 0 ] && [ "$direct" -ne 0 ] && bsoflags="sync:direct"
|
|
bsoflags="--bsoflags $bsoflags"
|
|
fi
|
|
|
|
blocksize=${blocksize+--blocksize=$blocksize}
|
|
local params='' i
|
|
for i in mode_page product_id product_rev readonly removable scsi_id scsi_sn sense_format vendor_id rotation_rate; do
|
|
eval params=\${$i+$i=\$$i,}\$params
|
|
done
|
|
|
|
local _tgtadm="$tgtadm --mode logicalunit --tid $tgtid --lun $lun"
|
|
$_tgtadm --op new --backing-store "$device" --device-type "$type" --bstype "$bstype" $bsoflags $blocksize || {
|
|
$logger "Failed to create lun $tgt_lun"
|
|
return 1
|
|
}
|
|
$_tgtadm --op update --param $params || {
|
|
$logger "Failed to update lun $tgt_lun"
|
|
return 1
|
|
}
|
|
}
|
|
|
|
validate_account_section () {
|
|
uci_load_validate tgt account "$1" "$2" \
|
|
'target:list(uinteger)' \
|
|
'user:string' \
|
|
'password:string' \
|
|
'outgoing:bool:0'
|
|
}
|
|
|
|
handle_account() {
|
|
local _tgtadm="$tgtadm --mode account"
|
|
|
|
[ "$2" = 0 ] || {
|
|
$logger "Validation failed for account ${user:-$1}"
|
|
return 1
|
|
}
|
|
[ "$user" ] || {
|
|
$logger "User is required for account $1. Run 'uci show tgt.$1' and check options"
|
|
return 1
|
|
}
|
|
[ "$target" ] || {
|
|
$logger "Target is required for account $user"
|
|
return 1
|
|
}
|
|
[ "$password" ] || {
|
|
$logger "Password is required for account $user"
|
|
return 1
|
|
}
|
|
$_tgtadm --op new --user "$user" --password "$password" || {
|
|
$logger "Failed to create user $username"
|
|
return 1
|
|
}
|
|
}
|
|
|
|
bind_account_to_target() {
|
|
local _tgtadm="$tgtadm --mode account"
|
|
|
|
[ "$2" = 0 ] || {
|
|
$logger "Validation failed for account ${user:-$1}"
|
|
return 1
|
|
}
|
|
|
|
[ "$outgoing" -ne 0 ] && outgoing=--outgoing || outgoing=""
|
|
local t
|
|
for t in $target; do
|
|
[ "$t" -eq "$tgtid" ] && {
|
|
$_tgtadm --op bind --tid "$tgtid" --user "$user" $outgoing || {
|
|
$logger "Failed to bind user $username to target $tgtid"
|
|
return 1
|
|
}
|
|
}
|
|
done
|
|
return 0
|
|
}
|
|
|
|
validate_target_section() {
|
|
uci_load_validate tgt target "$1" "$2" \
|
|
'name:string:iqn.2012-06.org.openwrt' \
|
|
'allow_address:list(string):ALL' \
|
|
'allow_name:list(string)'
|
|
}
|
|
|
|
handle_target() {
|
|
local tgtid=$1
|
|
local _tgtadm="$tgtadm --mode target"
|
|
|
|
[ "$tgtid" -ge 0 ] || return 1
|
|
[ "$2" = 0 ] || {
|
|
$logger "Validation failed for target $tgtid"
|
|
return 1
|
|
}
|
|
$_tgtadm --op new --tid "$tgtid" --targetname "$name" || {
|
|
$logger "Failed to create target $tgtid"
|
|
return 1
|
|
}
|
|
local i
|
|
for i in $allow_address; do
|
|
$_tgtadm --op bind --tid "$tgtid" --initiator-address "$i" || {
|
|
$logger "Failed to set allow $i to connect to target $tgtid"
|
|
return 1
|
|
}
|
|
done
|
|
for i in $allow_name; do
|
|
$_tgtadm --op bind --tid "$tgtid" --initiator-name "$i" || {
|
|
$logger "Failed to set allow $i to connect to target $tgtid"
|
|
return 1
|
|
}
|
|
done
|
|
config_foreach validate_lun_section lun handle_lun || return 1
|
|
config_foreach validate_account_section account bind_account_to_target || return 1
|
|
}
|
|
|
|
configure() {
|
|
config_load $NAME
|
|
$tgtadm --mode sys --op update --name State -v offline || {
|
|
$logger "Failed to set system state to Offline"
|
|
return 1
|
|
}
|
|
config_foreach validate_account_section account handle_account || return 1
|
|
config_foreach validate_target_section target handle_target || return 1
|
|
$tgtadm --mode sys --op update --name State -v ready || {
|
|
$logger "Failed to set system state to Ready"
|
|
return 1
|
|
}
|
|
return 0
|
|
}
|
|
|
|
validate_tgt_section() {
|
|
uci_load_validate tgt options "$1" "$2" \
|
|
'iothreads:uinteger' \
|
|
'portal:list(string)' \
|
|
'nop_interval:uinteger' \
|
|
'nop_count:uinteger' \
|
|
'logging:bool:0'
|
|
}
|
|
|
|
start_tgt_instance() {
|
|
local fg_flag=-f
|
|
[ "$2" = 0 ] || {
|
|
$logger "Validation failed for tgt options"
|
|
return 1
|
|
}
|
|
procd_open_instance
|
|
procd_set_param command $PROG
|
|
[ "$logging" -eq 1 ] && fg_flag=-D
|
|
procd_append_param command "$fg_flag"
|
|
[ "$iothreads" ] && procd_append_param command -t "$iothreads"
|
|
[ "$portal$nop_interval$nop_count" ] && {
|
|
local iscsi="" i
|
|
for i in nop_interval nop_count; do
|
|
eval iscsi=\${$i+$i=\$$i,}\$iscsi
|
|
done
|
|
for i in $portal; do
|
|
iscsi="portal=$i,$iscsi"
|
|
done
|
|
procd_append_param command --iscsi "$iscsi"
|
|
}
|
|
procd_set_param respawn
|
|
procd_close_instance
|
|
logger -p daemon.info -t "$NAME" -s "Configuration will be loaded in seconds"
|
|
( sleep 5; configure || { stop_service; exit 1; } ) &
|
|
}
|
|
|
|
start_service() {
|
|
validate_tgt_section tgt start_tgt_instance
|
|
}
|
|
|
|
stop_service() {
|
|
$tgtadm --mode sys --op update --name State -v offline || {
|
|
$logger "Failed to set system state to Offline"
|
|
return 1
|
|
}
|
|
$tgtadm --mode target --op show \
|
|
| awk '$1 == "Target" {sub(/:/,"",$2); print $2}' \
|
|
| xargs -r -n1 $tgtadm --mode target --op delete --force --tid
|
|
$tgtadm --mode sys --op delete
|
|
procd_kill tgt
|
|
}
|
|
|
|
reload_service() {
|
|
stop_service
|
|
start_service
|
|
}
|
|
|
|
service_triggers() {
|
|
procd_add_reload_trigger "tgt"
|
|
|
|
procd_open_validate
|
|
validate_tgt_section
|
|
validate_account_section
|
|
validate_target_section
|
|
validate_lun_section
|
|
procd_close_validate
|
|
}
|
|
|
|
show() {
|
|
$tgtadm --mode target --op show
|
|
}
|