SCSI란
SCSI(Small Computer System Interface)는 컴퓨터와 주변 장치를 연결하는 프로토콜입니다. 주로 하드디스크, CD-ROM, 테이프 드라이브 같은 외부 저장 장치들은 SCSI 드라이버를 통하여 액세스 됩니다. SCSI는 iSCSI, FCoE(Fiber Channel over Ethernet), 가상 시스템 드라이버(virtio), SAS, NVMe 등도 지원합니다. 즉 시스템에서 디스크를 사용하기 위해 디스크를 연결해 주는 역할을 SCSI가 담당한다고 볼 수 있습니다.
ISCSI란
ISCSI(Internet Small Computer System Interface)는 SCSI를 TCP/IP 네트워크를 통해 전송하기 위한 표준 프로토콜입니다. ISCSI를 이용하면 블록 장치 또는 파일 등을 네트워크를 통해 전달할 수 있으며 이용자들은 디스크가 마치 물리적으로 연결된 로컬 스토리지처럼 연결해 사용할 수 있게 됩니다. 네트워크를 통해 전송되므로 성능은 네트워크 속도에 의해 좌우됩니다.
즉 SCSI는 대부분의 물리적 연결을 지원해 주는 프로토콜이며, ISCSI는 네트워크를 통한 스토리지 연결을 지원 해주는 프로토콜입니다. ISCSI를 이용하게 되면 지역의 구분 없이 네트워크 통신만 되면 스토리지를 사용할 수 있는 장점이 있습니다.
ISCSI 구성 요소
Initiator | ISCSI 클라이언트를 나타내는 고유한 이름(IQN)으로 인증에 사용된다. |
Target | ICSI 서버에 설정하는 고유 이름(IQN)으로 클라이언트로 내보낼 LUN들을 포함하고 있는 리소스 |
IQN(iSCSI Qualified Name) | mm.naming-authority:unique 이름과 같은 형식으로 정해지며 ISCSI 노드를 식별하기 위한 고유 이름입니다.
예: iqn.2024-01.com.test.server • iqn: iSCSI Qualified Name을 나타내는 키워드 • yyyy-mm: 대상 식별자의 생성 년도와 월을 나타낸다. • naming-authority: 네임스페이스를 나타내며 일반 적으로 조직 이나 업체의 이름. • unique name: 조직에서 할당한 대상의 고유 이름 |
LUN | Target에서 제공하는 개별 블록 장치를 나타내는 논리적 장치 번호 |
ACL(Access Control List) | LUN에 대한 접근을 Initiator의 IQN을 기반으로 제한하는 접근 제어 목록 |
Portal | Target의 IP 주소와 포트 정보로, 연결 설정에 사용 |
TPG(Target Portal Group) | Target의 전체 설정을 포함하는 그룹으로, 포털, LUN, ACL 등의 정보를 통합 관리합니다. |
테스트 환경
RHEL 8
RHEL 9
목표
연습은 크게 2가지 부분 서버 타겟 설정 부분과 클라이언트 설정 부분으로 진행합니다. 먼저 서버에서 2G 파일을 ISCSI를 통해 제공한 뒤, 클라이언트에는 서버에서 내보낸 디스크를 연결하는 작업을 합니다.
ISCSI 서버 구성
필요 패키지 설치
# yum install iscsi-initiator-utils targetcli
ISCSI 서비스 시작 및 활성화
재부팅 후에도 서비스를 유지하기 위해 ISCSI 데몬을 enable 합니다.
아래 enable 명령에 –now를 이용하면 데몬을 시작해 주는 기능이 추가됩니다.
# systemctl enable iscsid --now
Created symlink /etc/systemd/system/multi-user.target.wants/iscsid.service → /usr/lib/systemd/system/iscsid.service.
ISCSI 설정
iscsi 데몬을 설정하는 CLI 도구인 targetcli를 사용하면 쉽게 스토리지를 설정할 수 있다. 이 cli 도구를 실행하여 진입한 화면에서 iscsi를 구성한다.
# targetcli
targetcli shell version 2.1.53
Copyright 2011-2013 by Datera, Inc and others.
For help on commands, type 'help'.
/> ls
o- / ....................................................................................................... [...]
o- backstores ............................................................................................ [...]
| o- block ................................................................................ [Storage Objects: 0]
| o- fileio ............................................................................... [Storage Objects: 0]
| o- pscsi ................................................................................ [Storage Objects: 0]
| o- ramdisk .............................................................................. [Storage Objects: 0]
o- iscsi .......................................................................................... [Targets: 0]
o- loopback ....................................................................................... [Targets: 0]
위와 같이 targetcli 모드에 접근해서 ls 명령어를 입력하면 크게 backstores 영역과 iscsi 그리고 loopback 영역으로 구분되는 걸 볼 수 있다. backstores 영역은 iscsi에서 사용할 디스크를 정의하는 부분이고, iscsi 영역은 클라이언트가 접속할 네트워크 주소와 권한 lun 등을 정의하는 공간이다. iscsi에서 설정하는 lun의 경우에는 backstores 영역에서 정의한 디스크만 가져다 사용할 수 있다.
그러므로 iscsi 영역을 설정하기 전에 먼저 backstores쪽에 ISCSI서버를 통하여 제공할 디스크를 설정한다.
- 스토리지 생성 (fileio 사용)
iscsi를 통해 전달할 스토리지를 생성한다. 스토리지는 block 방식과 file방식을 많이 사용하는데 file방식은 일반 파일을 디스크처럼 내보내는 방식을 말하고 block 방식은 실제 디스크를 내보내는 방식을 말한다.
아래 명령에서는 fileio방식을 이용하여 /root/disk1 이라는 2G짜리 파일을 생성해서 디스크를 내보낸다. /root/disk1 이라는 파일은 targetcli 명령에 의해 자동으로 생성된다.
/> backstores/fileio create disk1 /root/disk1 size=2G
/root/disk1 exists, using its size (2147483648 bytes) instead
Created fileio disk1 with size 2147483648
/> ls
o- / ....................................................................................................... [...]
o- backstores ............................................................................................ [...]
| o- block ................................................................................ [Storage Objects: 0]
| o- fileio ............................................................................... [Storage Objects: 1]
| | o- disk1 ..................................................... [/root/disk1 (2.0GiB) write-back deactivated]
| | o- alua ................................................................................. [ALUA Groups: 1]
| | o- default_tg_pt_gp ..................................................... [ALUA state: Active/optimized]
| o- pscsi ................................................................................ [Storage Objects: 0]
| o- ramdisk .............................................................................. [Storage Objects: 0]
o- iscsi .......................................................................................... [Targets: 0]
o- loopback ....................................................................................... [Targets: 0]
/>
- IQN(iSCSI Qualified Name) 생성IQN(iSCSI Qualified Name)은 iqn.yyyy-mm.naming-authority:unique 이름과 같은 형식으로 정해지며 ISCSI 노드를 식별하기 위한 고유 이름입니다.
- iqn: iSCSI Qualified Name을 나타내는 키워드
- yyyy-mm: 대상 식별자의 생성 년도와 월을 나타낸다.
- naming-authority: 네임스페이스를 나타내며 일반 적으로 조직 이나 업체의 이름.
- unique name: 조직에서 할당한 대상의 고유 이름
iscsi/ create iqn.2024-01.com.test.server
명령어 전체 실행 결과:
/> iscsi/ create iqn.2024-01.com.test.server
...
/> ls
o- / ....................................................................................................... [...]
o- backstores ............................................................................................ [...]
| o- block ................................................................................ [Storage Objects: 0]
| o- fileio ............................................................................... [Storage Objects: 1]
| | o- disk1 ..................................................... [/root/disk1 (2.0GiB) write-back deactivated]
| | o- alua ................................................................................. [ALUA Groups: 1]
| | o- default_tg_pt_gp ..................................................... [ALUA state: Active/optimized]
| o- pscsi ................................................................................ [Storage Objects: 0]
| o- ramdisk .............................................................................. [Storage Objects: 0]
o- iscsi .......................................................................................... [Targets: 1]
| o- iqn.2024-01.com.test.server ..................................................................... [TPGs: 1]
| o- tpg1 ............................................................................. [no-gen-acls, no-auth]
| o- acls ........................................................................................ [ACLs: 0]
| o- luns ........................................................................................ [LUNs: 0]
| o- portals .................................................................................. [Portals: 1]
| o- 0.0.0.0:3260 ................................................................................... [OK]
o- loopback ....................................................................................... [Targets: 0]
/>
하나의 iscsi 데몬은 서버에 올라와 있는 여러 네트워크 인터페이스를 통해 접근할 수 있습니다. 어느 네트워크로 접속했을 때 어떤 디스크를 보이게 할지에 대해서 TPG(Target Portal Group) 단위로 관리를 합니다. TPG를 이용하면 클라이언트가 접속했을 때 사용할 디스크와 접근 권한 등을 설정할 수 있습니다. IQN을 생성하면 기본적으로 하나의 TPG가 생성됩니다.
생성된 기본 TPG(Target Portal Group)를 보면 acls, luns, portals가 보입니다.
acl: 접근 권한 정보
lun: 내보낼 스토리지 정보
portals: 클라이언트가 접속하기 위한 네트워크 정보
해당 내용들을 차례로 설정해 보도록 하겠습니다.
- acl 설정
접근 권한 부분입니다. 다양한 접근 권한 설정이 있지만 ISCSI initiator 식별자인 IQN을 이용하는 방식을 사용해 보도록 하겠습니다. 이 방법을 사용하면 지정된 IQN을 가지는 클라이언트만 접근할 수 있습니다.
/> iscsi/iqn.2024-01.com.test.server/tpg1/acls create iqn.2024-01.com.test.client1
Created Node ACL for iqn.2024-01.com.test.client1
/> iscsi/iqn.2024-01.com.test.server/tpg1/acls create iqn.2024-01.com.test.client2
Created Node ACL for iqn.2024-01.com.test.client2
IQN을 두 개를 넣어준 이유는 두 클라이언트에서 접속해서 사용해 보기 위함입니다. 참고로 두 클라이언트에서 접근한다고 해서 동시에 읽고 쓰기가 가능하지는 않습니다.
- luns 설정
위에서 생성한 스토리지인 disk1을 지정합니다.
/> iscsi/iqn.2024-01.com.test.server/tpg1/luns create /backstores/fileio/disk1
Created LUN 0.
Created LUN 0->0 mapping in node ACL iqn.2024-01.com.test.client2
Created LUN 0->0 mapping in node ACL iqn.2024-01.com.test.client1
- portal 설정
먼저 아래 기본 설정되어 있는 portal 주소를 보면 0.0.0.0으로 되어있습니다. 서버의 모든 IP로 접근 가능하게 되어있습니다.
/> cd iscsi/iqn.2024-01.com.test.server/tpg1/portals/
/iscsi/iqn.20.../tpg1/portals> ls
o- portals .......................................................................................... [Portals: 1]
o- 0.0.0.0:3260 ........................................................................................... [OK]
특정 인터페이스로만 접근이 가능하게 지우고 새로 설정합니다.
/iscsi/iqn.20.../tpg1/portals> delete 0.0.0.0 3260
Deleted network portal 0.0.0.0:3260
/iscsi/iqn.20.../tpg1/portals> create 192.168.155.88 3260
Using default IP port 3260
Created network portal 192.168.155.88:3260.
/iscsi/iqn.20.../tpg1/portals> ls
o- portals .......................................................................................... [Portals: 1]
o- 192.168.155.88:3260 .................................................................................... [OK]
서버의 모든 구성이 끝났습니다. 전체 설정을 살펴보도록 하겠습니다.
/iscsi/iqn.20.../tpg1/portals> cd /
/> ls
o- / ....................................................................................................... [...]
o- backstores ............................................................................................ [...]
| o- block ................................................................................ [Storage Objects: 0]
| o- fileio ............................................................................... [Storage Objects: 1]
| | o- disk1 ....................................................... [/root/disk1 (2.0GiB) write-back activated]
| | o- alua ................................................................................. [ALUA Groups: 1]
| | o- default_tg_pt_gp ..................................................... [ALUA state: Active/optimized]
| o- pscsi ................................................................................ [Storage Objects: 0]
| o- ramdisk .............................................................................. [Storage Objects: 0]
o- iscsi .......................................................................................... [Targets: 1]
| o- iqn.2024-01.com.test.server ..................................................................... [TPGs: 1]
| o- tpg1 ............................................................................. [no-gen-acls, no-auth]
| o- acls ........................................................................................ [ACLs: 2]
| | o- iqn.2024-01.com.test.client1 ....................................................... [Mapped LUNs: 1]
| | | o- mapped_lun0 .............................................................. [lun0 fileio/disk1 (rw)]
| | o- iqn.2024-01.com.test.client2 ....................................................... [Mapped LUNs: 1]
| | o- mapped_lun0 .............................................................. [lun0 fileio/disk1 (rw)]
| o- luns ........................................................................................ [LUNs: 1]
| | o- lun0 ................................................ [fileio/disk1 (/root/disk1) (default_tg_pt_gp)]
| o- portals .................................................................................. [Portals: 1]
| o- 192.168.155.88:3260 ............................................................................ [OK]
o- loopback ....................................................................................... [Targets: 0]
/>
- 저장하고 종료
saveconfig 명령을 이용하면 현재 설정이 저장됩니다.
/> saveconfig
Last 10 configs saved in /etc/target/backup/.
Configuration saved to /etc/target/saveconfig.json
exit 명령을 사용하면 종료되는데 사실 종료될 때도 자동으로 저장됩니다.
/> exit
Global pref auto_save_on_exit=true
Configuration saved to /etc/target/saveconfig.json
설정 변경 전 기록들은 /etc/target/backup 디렉터리에서 확인하실 수 있습니다.
[root@rhel88 ~]# ls /etc/target/backup/
saveconfig-20240131-14:27:05-json.gz saveconfig-20240131-14:36:53-json.gz saveconfig-20240131-15:31:26-json.gz
saveconfig-20240131-14:35:09-json.gz saveconfig-20240131-15:29:17-json.gz
- 방화벽 설정 (리눅스의 방화벽을 사용할 경우 오픈)
[root@rhel88 ~]# firewall-cmd --add-service=iscsi-target
success
[root@rhel88 ~]# firewall-cmd --add-service=iscsi-target --permanent
클라이언트 설정
필요 패키지 설치
yum install iscsi-initiator-utils
IQN 설정
서버의 ACL에 설정되어 있는 IQN으로 클라이언트 initiatorname을 설정합니다.
[root@rhel92 ~]# cat /etc/iscsi/initiatorname.iscsi
InitiatorName=iqn.2024-01.com.test.client1
IP주소를 이용한 타겟 검색
# iscsiadm --mode discoverydb --type sendtargets --portal 192.168.155.88 --discover
192.168.155.88:3260,1 iqn.2024-01.com.test.server
타겟을 찾으면 명령어 출력 결과에 타겟 IQN이 출력됩니다. 해당 정보를 이용해서 로그인하면 타겟에서 내보낸 디스크를 사용할 수 있습니다.
로그인
ISCSI는 사용하기 위해서 로그인 절차를 거칩니다. 한번 로그인 되면 재부팅 후에도 유지됩니다.
[root@rhel92 ~]# iscsiadm -m node -T iqn.2024-01.com.test.server --login
Logging in to [iface: default, target: iqn.2024-01.com.test.server, portal: 192.168.155.88,3260]
Login to [iface: default, target: iqn.2024-01.com.test.server, portal: 192.168.155.88,3260] successful
만약 ACL이 일치하지 않을 경우 아래와 같이 authorization failure 오류가 발생합니다.
[root@rhel92 /]# iscsiadm -m node -T iqn.2024-01.com.test.server --login
Logging in to [iface: default, target: iqn.2024-01.com.test.server, portal: 192.168.155.88,3260]
iscsiadm: Could not login to [iface: default, target: iqn.2024-01.com.test.server, portal: 192.168.155.88,3260].
iscsiadm: initiator reported error (24 - iSCSI login failed due to authorization failure)
iscsiadm: Could not log into all portals
디스크 확인
lsscsi 명령을 이용해서 디스크를 확인할 수 있습니다. 해당 명령어 -s 옵션을 이용하면 디스크 사이즈도 확인이 가능합니다.
[root@rhel92 ~]# lsscsi -s
[1:0:0:0] cd/dvd QEMU QEMU DVD-ROM 2.5+ /dev/sr0 9.59GB
[7:0:0:0] disk LIO-ORG disk1 4.0 /dev/sda 2.14GB
vendor 이름 부분이 LIO-ORG로 표기되는 2GB 짜리 디스크가 보입니다. LIO는 리눅스 커널에서 제공하는 ISCSI를 이용하여 제공한 Linux-IO를 뜻합니다.
여기까지 완료가 되었으면 이제 일반 디스크처럼 사용이 가능합니다.
마무리
ISCSI를 이용해 디스크를 인터넷을 통해 제공해 주는 방법을 봤습니다. ISCSI는 NFS와 다르게 여러 노드에서 동일 볼륨을 쓰는 작업이 안되는 부분이 있습니다. 정확히 말하면 동시에 쓰기는 가능하겠지만 그렇게 사용하면 디스크가 깨지므로 한 번에 한 곳에서만 잘 마운트 해서 사용해야 합니다.