이 포스트는 이 블로그를 참고했습니다! -> click!
저 블로그는 ONOS 2.7.0 버전이 아닌 다른 버전을 사용하고 있어 명령어 사용이 달라지는 부분들이 있으니, 최근의 정보를 확인하고 싶다면 제 글을 쭉 따라해보시면 됩니다!
window 사용자 기준
Ubuntu를 실행하기 위한 가상머신이 필요합니다!
저는 vmware을 설치하여 사용했습니다.
그리고, Ununtu 22.04버전 이미지를 다운로드받아서, vmware에서 실행시켜주면 됩니다.
ONOS 설치 블로그
위 블로그를 참고하여 ONOS를 설치했습니다.
그대로 쭉 따라하시면 잘 설치 될겁니다!


저는 이렇게 설치가 잘 되었습니다.
ONOS CLI를 실행하는데, 먼저 컴퓨터의 IP주소를 알아야 해요!
ip route | grep default
위 명령어를 통해 공유기의 IP주소를 확인했습니다.
저는 192.168.224.2 인 것으로 확인했습니다.
그 다음으로는 pc의 주소인데,
ip addr show
위 명령어를 통해 192.168.224.128인 것을 확인했습니다.

그러면 이렇게 본인의 IP주소를 넣어 ONOS에 접속할 수 있습니다.
초기 비밀번호는 karaf입니다.
-p 옵션은 포트번호를 지정합니다. 로컬인 클라이언트가 ONOS 컨트롤러로 SSH 연결을 시도할 때 서버의 8101포트를 통해서 SSH 요청을 보내도록 지정하는 것입니다. 즉, 나가는 포트는 랜덤한 동적 포트로 설정되지만, ONOS컨트롤러는 고정된 포트(여기서는 8101) 포트로 SSH 연결을 수신합니다.
이제는 가상 네트워크를 구성해서 OpenFlow 프로토콜을 기반으로 ONOS와 연결해볼 것입니다.
여기에서 OpenFlow는 SDN에서 사용하는 프로토콜입니다!
OpenFlow를 사용하기 위해서는 ONOS CLI로 접속하여 OpenFlow프로토콜을 지원하는 ONOS 애플리케이션인 'org.onosproject.openflow'를 활성화 해주어야 합니다.
다음과 같이 진행합니다.

두 번째로 친 명령어는 현재 실행중인 앱을 조회하는 명령어입니다.
openflow 관련 애플리케이션들이 실행되는 것을 확인할 수 있습니다.
그리곤, 다른 터미널을 열어 apt-get을 이용해 mininet을 설치해주어야 합니다.
sudo apt-get install mininet
오픈소스 SW인 OpenFlow 기반의 가상 스위치를 제공해주는 Open vswitch(이하 OVS)도 패키지 관리도구인 apt-get으로 설치해줍니다.
sudo apt-get install openvswitch-switch
설치가 완료되면, mininet으로 1개의 OVS 스위치(s1)에 두 개의 가상 Host(h1,h2)와 ONOS 제어기(c0)가 연결되도록 가상네트워크를 구성하기 위해서

아까 확인했던 pc의 ip주소를 넣어 명령어를 실행시켜 주면 됩니다.


명령어의 옵션은 위와 같습니다.
명령어 실행 후, ONOS CLI에서 현재 ONOS와 연결된 스위치 정보를 조회해보면 OVS 스위치 1대가 ONOS와 연결이 되었음을 확인할 수 있습니다.

mininet cli에서 ping테스트를 해보면, 아직 flow rule을 설정하지 않아 서로 메시지를 주고받을 순 없다고 나옵니다.


nodes 명령어를 통해 확인해보면, c0,h1,h2,s1 이렇게 4개의 Node가 생긴 것을 확인할 수 있습니다.

이러한 상황입니다.
여기에서 각 Node들의 interface정보들을 확인해보면,


ONOS가 바라보는 가상 네트워크 구조는 앞서 Mininet으로 파악한 가상 네트워크 구조와 동일하지만, ONOS는 직접 Flow Rule을 설정해주어야 하기 때문에 각 장치별 요소를 구분하기 위한 값이 Mininet을 통해 파악한 것과는 조금 다릅니다.

먼저 ONOS CLI로 접속하여 현재 연결된 OVS 스위치 정보를 조회해보면, Mininet에서는 s1이라는 노드로 표현되었지만, 여기서는 of:0000000000000001라는 고유의 장치 ID 값을 가집니다.

이번에는 hosts명령어를 통해 확인한 것입니다.
locations=[of:0000000000000001/2]는 호스트 of:0000000000000001가 스위치의 2번포트에 연결되어있음을 의미합니다.

이 사진이 최종 연결구조입니다.
h1이 연결된 OVS 스위치(s1)의 s1-eth1 인터페이스는 1번 포트이고, h2가 연결된 s1-eth2는 2번 포트로 인식됨을 확인할 수 있습니다.
이제 이렇게 최종 확인된 가상 네트워크 구조를 가지고, ONOS의 Flow Rule 설정을 통해 두 Host 간 통신이 되도록 해볼 것입니다.
Openflow 프로토콜에서는 flow rule 설정 방식이 두 가지 있습니다. 하나는 flow rule이 정의되지 않은 미지의 패킷이 SDN 스위치로 유입되었을 때, SDN 제어기에 의해 flow rule이 결정되는 reactive 모드이고, 다른 하나는 네트워크 관리자에 의하여 SDN 스위치에 미리 flow rule을 등록하는 proactive 모드입니다.
reactive모드를 실행하기 위해서는 ONOS CLI에서 org.onosproject.fwd애플리케이션을 실행시켜야 합니다. 이 애플리케이션은 packet-in메시지를 SDN 제어기인 ONOS로 보내도록 flow rule을 설정하여 ONOS가 reactive모드로 동작하도록 합니다.

명령어가 잘 실행되었습니다.

mininet cli에서 다시 ping을 보내보면, 기존에는 안되던 h1과 h2의 ping이 성공적으로 잘 수행된 것을 확인할 수 있습니다.
ONOS를 통해 직접 flow rule이 OVS 스위치 s1에 설정된 것입니다.

ONOS CLI에서 flows 명령어를 통해 flow rule을 조회해보면 ADDED상태로 추가된 rule을 확인할 수 있습니다.
이제부터는 ONOS에서 제공하는 REST API를 활용해서 Proactive모드로써 직접 Flow Rule을 설정해볼 것입니다.
일단 ONOS CLI에 접속하여 Reactive 모드를 테스트하기 위해 앞서 실행했던 org.onosproject.fwd를 비활성화해줍니다.

그리고 flow_rule_post.sh라는 스크립트 파일을 만들 것입니다. 이 스크립트 파일은 ONOS REST API를 이용해서 JSON파일로 정의된 Flow Rule을 해당 OVS 스위치에 설정하는 역할을 수행합니다.
flow_rule_post.sh에는 아래 내용을 넣어주면 됩니다. 역시 IP주소는 바꾸어 넣어야 합니다.
ONOS_IP=192.168.224.128
ONOS_PORT=8181
curl -X POST --header "Content-Type: application/json" --header "Accept: application/json" -d @$1 "http://$ONOS_IP:$ONOS_PORT/onos/v1/flows/" --user karaf:karaf

이제 flow rule을 정의해볼 것입니다.
h1에서 h2로 데이터를 보낼 수 있도록 OVS스위치 s1의 1번포트로 패킷이 들어오면 2번포트로 내보내라는 flow rule을 정의해볼 것입니다.

이를 위해 OVS 스위치 s1의 입력포트(IN_PORT)는 1번, 출력포트(OUTPUT)는 2번으로 지정된 flow rule을 5000이라는 우선순위를 적용하여 flow_h1_to_h2.json라는 JSON포맷 파일로 생성합니다.
{
"flows": [
{
"priority": "50000",
"timeout": 0,
"isPermanent": true,
"deviceId": "of:0000000000000001",
"treatment": {
"instructions": [
{
"type": "OUTPUT",
"port": "2"
}
]
},
"selector": {
"criteria": [
{
"type": "IN_PORT",
"port": "1"
}
]
}
}
]
}
이번에는 반대로 h2에서 h1으로 데이터를 보낼 수 있도록 OVS스위치 s1의 2번 포트로 패킷이 들어오면 1번 포트로 내보내라는 Flow Rule을 정의해볼 것입니다.

이를 위해 OVS 스위치 s1 (of:0000000000000001) 의 입력포트 (IN_PORT) 는 2번, 출력포트 (OUTPUT) 는 1번으로 지정된 Flow Rule을 5000이라는 우선순위 (Priority) 를 적용해 'flow_h2_to_h1.json' 라는 JSON 포맷 파일로 생성합니다.
{
"flows": [
{
"priority": "50000",
"timeout": 0,
"isPermanent": true,
"deviceId": "of:0000000000000001",
"treatment": {
"instructions": [
{
"type": "OUTPUT",
"port": "1"
}
]
},
"selector": {
"criteria": [
{
"type": "IN_PORT",
"port": "2"
}
]
}
}
]
}

편의를 위해 생성한 파일의 권한까지 변경해준 모습입니다.
JSON 파일로 정의한 Flow Rule 파일 (flow_h2_to_h1.json, flow_h2_to_h1.json) 들을 먼저 앞에서 작성한 flow_rule_post.sh 스크립트 파일을 이용하여, ONOS를 통해 OVS 스위치 s1 (of:0000000000000001) 로 Flow Rule 정보를 등록해줍니다. Flow Rule이 정상적으로 내려갔다면 스위치 s1의 Device ID와 등록한 Flow Rule의 ID 값이 출력됩니다.
./flow_rule_post.sh flow_h1_to_h2.json flow_h2_to_h1.json
./flow_rule_post.sh flow_h2_to_h1.json

ONOS CLI로 접근하여 실제 등록된 FlowRule정보를 확인해보면, 성공적으로 등록된 것을 확인할 수 있습니다.

이제 네트워크 구조를 도식화해보면 다음과 같습니다.

이 사진 역시 블로그에서 가져온 것이라 세부적 flow Id, c0 address, MAC address는 다릅니다.
flow rule이 등록된 상태에서 mininet CLI를 통해 h1과 h2의 ping테스트를 해보면 성공적으로 수행되는 것을 확인할 수 있습니다.

먼저 h1에서 h2로 Ping 메시지를 보낼 경우, h1은 h2의 MAC 주소를 알아내기 위해 ARP 요청 메시지를 보내고, 해당 메시지는 OVS 스위치 s1의 1번포트로 전달됩니다. 이때 OVS 스위치 s1은 메시지의 처리를 위해 자신의 Flow Table에 등록된 Flow Rule을 찾아봅니다. Flow Table에서 입력포트 (IN_PORT) 가 1번인 Match Field가 일치하여, 해당 ARP 요청 메시지는 출력포트 (OUTPUT) 인 OVS 스위치 s1의 2번포트를 통해서 h2로 전달됩니다.

h1로부터 ARP 요청 메시지를 받은 h2는 자신의 MAC 주소를 포함한 ARP 응답 메시지를 보내고, 해당 메시지는 OVS 브릿지 s1의 2번포트로 전달됩니다. 이때 OVS 스위치 s1은 메시지의 처리를 위해 자신의 Flow Table에서 Flow Rule을 찾아봅니다. Flow Table에서 입력포트 (IN_PORT) 가 2번인 Match Field가 일치하여, 해당 ARP 응답 메시지는 출력포트 (OUTPUT) 인 OVS 스위치 s1의 1번포트를 통해서 h1로 전달됩니다.

h2로부터 ARP 응답 메시지를 전달받은 h1은 해당 메시지에 포함된 h2의 MAC 주소를 파악하고 해당 MAC 주소를 이용하여 ICMP 요청 메시지를 h2에 전달합니다. 이때 해당 메시지는 OVS 스위치 s1의 1번 포트로 제일 먼저 전달되며, OVS 스위치 s1은 메시지의 처리를 위해 자신의 Flow Table에 등록된 Flow Rule을 찾아봅니다. Flow Table에서 입력포트 (IN_PORT) 가 1번인 Match Field가 일치하여, 해당 ICMP 요청 메시지는 출력포트 (OUTPUT) 인 OVS 스위치 s1의 2번포트를 통해서 h2로 전달됩니다.

h1로부터 ICMP 요청 메시지(echo request)를 받은 h2는 이에 대한 응답으로 ICMP 응답 메시지(echo reply)를 생성해 h1으로 전달합니다. 이때 해당 메시지는 OVS 브릿지 s1의 2번포트로 먼저 전달됩니다. 그리고 OVS 스위치 s1은 메시지의 처리를 위해 자신의 Flow Table에서 Flow Rule을 찾아봅니다. Flow Table에서 입력포트 (IN_PORT) 가 2번인 Match Field가 일치하여, 해당 ARP 응답 메시지는 출력포트 (OUTPUT) 인 OVS 스위치 s1의 1번포트를 통해서 h1으로 전달됩니다.

여기까지 h1에서 h2로 Ping 메시지를 보내는 동안 OVS 스위치 s1에 등록된 Flow Rule이 어떻게 적용되어 데이터를 전달하는지 살펴보았습니다. h2에서 h1으로 Ping 메시지를 보내는 경우에도 마찬가지로 동일한 방식으로 Flow Rule이 적용되어 통신이 이루어집니다.

