SW/블록체인

블록체인 : 이더리움의 P2P 네트워크, 데이터베이스, 인코딩 방법 및 노드 디스커버리 과정

얇은생각 2022. 2. 5. 07:30
반응형

이더리움 네트워크, 노드

이더리움의 공동 계층 (Common Layer)은 전체 아키텍처에서 공통으로 사용하는 기능을 포함하고 있습니다. Common Layer에 대해서는 RLPx P2P 네트워크 프로토콜 등을 설명하고, 블록체인의 데이터를 효율적으로 저장하기 위한 스토리지 기능 그리고 Recursive Length Prefix (RLP) 데이터 인코딩 방법도 소개합니다. Application Layer에서는 이더리움이 단순 암호화폐가 아닌 블록체인 기술을 적용하여 다양한 문제를 해결하기 위한 서비스들을 개발/운영할 수 있는 플랫폼이라는 것을 설명합니다.

이더리움은 P2P 네트워크에 연결된 모든 노드들이 같은 역할과 기능을 수행하는 완전 분산형 P2P 토폴로지로 구성됩니다. 또한, 개별 peer들이 스스로 이웃 노드를 찾아내어 동작하는 Pure P2P 방식을 사용합니다. 이더리움 wallet, Mist, Geth client 등은 모두 하나의 노드로서 이더리움의 P2P 네트워크에 연결되어 있는 것입니다. 기본적으로 이더리움의 노드들이 EVM를 실행하며 다른 노드들과 동일한 블록체인 상태를 유지하는 것은 맞지만, 조금 더 세부적으로 구분해볼 수 있습니다.

노드의 역할로 구분해보면 마이닝 작업을 수행하는 마이너 노드와 일반 사용자 노드로 나눌 수 있고, 블록체인 동기화 방식으로 구분하면 전체 블록체인 데이터를 동기화하는 전체 노드(Full node)와 블록 헤더 정보 등 일부 데이터만 동기화하는 라이트 노드(light node)로 구분할 수 있습니다. 추가적으로, 아래의 그림은 이더리움 노드의 전 세계 분포도입니다. 8,197개의 클라이언트가 실행 중이고, 그 중에 26.80%인 2,197개가 미국에서 실행 중인 것을 보여줍니다. 한국은 323개로 약 3.94%의 클라이언트를 실행하고 있습니다.

 

블록체인 : 이더리움의 P2P 네트워크, 데이터베이스, 인코딩 방법 및 노드 디스커버리 과정 1

 

이더리움 네트워크 메커니즘을 간략하게 설명하겠습니다. 우선 네트워크에 참여하는 노드들이 있습니다. 이것은 go-ethereum, parity, cpp-ethereum, 등의 Ethereum Client에 의해서 동작합니다. 이러한 노드(클라이언트)들은 다음과 같이 서로 p2p 네트워크를 형성합니다. 네트워크를 형성하기 위해서는 RLPx라는 프로토콜을 사용합니다.

그리고 서비스들 간의 통신을 위해서는 eth라는 프로토콜을 사용합니다. 그리고 클라이언트를 구동시키면, node가 JSON-RPC server를 실행하고 노출시킵니다. 이더리움 네트워크 밖에 있는 web app 혹은 native app 등은 이러한 JSON-RPC 서버에 요청해서 이더리움 네트워크 안의 데이터를 얻을 수 있습니다. 이것은 web3를 통해서 이루어질 것이고, transaction의 값을 읽거나 balance 등을 조회할 수 있습니다.

 

 

 

이더리움 P2P 프로토콜 : RLPx

이더리움은 P2P 네트워크상에서 일반 전송과 애플리케이션 간의 통신을 위해서 RLPx라는 암호화된 네트워크 프로토콜을 사용합니다. RLPx에는 peer간의 노드를 탐색하기 위한 기능과 ECDSA로 서명된 UDP 프로토콜과 암호화된 TCP 프로토콜 등 이더리움 전반에 걸쳐 사용되는 P2P 네트워크 기능이 포함되어 있습니다.

RLPx는 이더리움의 노드 간의 P2P 연결과 노드 디스커버리뿐만 아니라 블록체인 동기화를 수행하는 eth프로토콜, P2P 메시징을 수행하는 Whisper의 shh 프로토콜, P2P 파일 시스템인 Swarm의 bzz 프로토콜 등 상위 응용 프로토콜에서 공통으로 사용하는 기반 프로토콜입니다.

 

 

 

노드 디스커버리 프로토콜

먼저 노드 디스커버리 프로토콜을 통해 노드를 찾은 후에 eth, shh, bzz 등 어떤 응용 프로토콜을 사용할 것인지 결정합니다. 이더리움 네트워크에서 한 노드가 네트워크에 참여하기 위해서는 네트워크상의 다른 노드들과 서로 연결되어야 합니다. 모든 노드와 연결될 필요는 없지만, 그중 일부 노드와는 반드시 연결되어야 합니다.

중앙 서버가 없는 분산 네트워크에서 어떻게 노드들이 다른 노드들을 찾고 연결할까요? 이더리움은 분산 해시 테이블인 카데리마 프로토콜을 기반으로 네트워크상에 노드를 탐지하는 노드 디스커버리 프로토콜을 개발했습니다. 이더리움의 노드 디스커버리 프로토콜은 네트워크에 연결된 RLPx 노드들을 탐지하는데 사용되는 UDP기반의 RPC 프로토콜입니다.

이더리움은 RLPx 프로토콜을 통해서 P2P 오버레이 네트워크를 구축하고 노드 탐지를 수행합니다. 일반 노드가 이더리움 네트워크에 연결될 때 다른 노드를 탐색하는데, 최초 탐색은 부트스트랩 노드에 접속하는 것부터 시작됩니다. 부트스트랩 노드는 네트워크상의 peer 노드들을 찾는 데 사용되며, 대신 블록체인 정보는 저장하지 않습니다.

그리고 일정 시간 동안 연결되어 있는 노드들의 목록을 유지합니다. 노드 디스커버리의 절차에 대해서 간략히 소개하겠습니다. 노드 디스커버리의 절차에 대해서 간략히 소개하겠습니다. 우선 일반 노드들은 부트스트랩 노드를 통해서 초기 연결할 노드의 목록을 전달받습니다. 그 다음 노드 디스커버리 프로토콜을 사용하여 노드들과의 연결을 시작합니다.

마지막으로, 노드들과 연결이 되면 부트스트랩 노드와의 접속을 중단합니다. 노드 디스커버리 프로토콜은 ping, pong, findnode, neighbors라는 네 가지 패킷 타입으로 다른 노드들을 탐색합니다. 각각의 패킷 타입에 대해서 설명하겠습니다.

 

블록체인 : 이더리움의 P2P 네트워크, 데이터베이스, 인코딩 방법 및 노드 디스커버리 과정 2

 

Ping은 노드가 온라인 상태인지를 확인하기 위한 패킷입니다. 연결되어 있는 피어 노드 중 첫 번째 노드에게 자신의 ping을 보내고, ping을 받은 노드는 pong 패킷을 보내서 응답합니다. Pong은 ping에 대한 응답 패킷입니다.

findnode는 목표 노드의 주변에 위치한 peer 노드들에게 전달됩니다. findnode 패킷의 수신자는 해당 목표 노드 주변에 위치한 노드들을 알고 있다면 해당 노드들의 목록을 neighbors 패킷에 포함하여 반환합니다. Neighbors는 findnode에 대한 응답 패킷이고, 요청된 목표 노드의 인접한 노드들이 포함되어 있습니다.

 

 

 

enode : 노드의 주소

이더리움의 각 노드는 enode라는 URL로 표현되며, 노드 주소의 역할을 합니다.

 

블록체인 : 이더리움의 P2P 네트워크, 데이터베이스, 인코딩 방법 및 노드 디스커버리 과정 3

 

아래를 보면 enode에 대한 예시를 확인할 수 있습니다.

 

블록체인 : 이더리움의 P2P 네트워크, 데이터베이스, 인코딩 방법 및 노드 디스커버리 과정 4

 

각각을 분해해서 요소를 살펴보겠습니다. “Enode://9157…”에서 시작해서 @전까지가 enode URL을 나타냅니다. “9157…. e9e”는 타원 곡선 방식 (ECDSA)을 사용하여 개인 키로 서명한 512bit의 공개키입니다. @는 구분자입니다. 그 다음은 호스트의 IP 주소가 나오며, 여기서는 10.5.57.7이 되겠습니다. 30303은 TCP port 번호, disport=30301은 UDP port 번호입니다.

 

 

 

부트스트랩 노드에 연결하는 방법

이더리움을 처음 시작할 때 부트스트랩 노드와 연결해야 하는데, 이더리움 네트워크상에서 부트스트랩 노드에 연결하는 방법이 몇 가지 있습니다. 첫째는 default로서 geth 클라이언트를 구동하면 go-ethereum 프로그램에 하드 코딩된 부트스트랩 노드 목록을 참조하여 연결을 시도합니다.

둘째, geth 클라이언트를 구동할 때 --bootstrap 옵션을 사용하여 부트스트랩 노드를 직접 지정하는 것입니다. 예시는 아래와 같습니다. 셋째, geth 클라이언트 콘솔 상에서 admin.addPeer()를 사용하여 연결하고자 하는 노드를 지정해서 연결할 수 있습니다.

넷째, geth가 구동할 때, 항상 특정 노드와 연결하게 해주는 정적 노드 기능을 활용하는 것입니다. geth 데이터 디렉터리 아래에 static-nodes.json 파일을 생성하고, 파일 안에 “enode://공개키@IP주소:포트” 형태로 항상 연결할 노드를 명시하면 geth 실행과 동시에 해당 enode에 연결됩니다.

 

 

 

이더리움 데이터베이스

이더리움은 기본 저장소로 내부에 ethdb 패키지를 통해 key value 저장소인 레벨 DB를 사용하고 있습니다. 이때 ethdb라는 패키지로 레벨 DB를 래핑하여 사용하고 있는데, 이렇게 함으로써 나중에 코드의 변경 없이 다른 DBMS로 손쉽게 교체할 수 있습니다.

이더리움에서는 머클 트리의 트랜잭션과 리시트 정보, 머클 패트리샤 트리 내의 모든 상태 정보, EVM의 비휘발성 저장소 등 이더리움에서 스토리지에 저장될 필요가 있는 모든 정보를 레벨 DB에 저장합니다. 레벨 DB는 사용하기 쉽다는 장점이 있지만, 데이터의 조회 기능이 너무 단순하고 인덱스를 지원하지 않습니다.

그래서 데이터 용량이 커지면 탐색 시간이 많이 소요되고 복잡한 질의는 불가능합니다. 이러한 문제를 해결하기 위해서 이더리움은 블록체인 데이터를 mongo DB 등으로 변환하는 프로젝트를 활발히 진행하고 있습니다.

 

 

 

RLP (Recursive Length Prefix) Encoding

이더리움은 내부에서 임의로 중첩된 바이너리 배열을 인코딩하기 위해서 직접 RLP (Recursive Length Prefix)라는 인코딩방법을 구현했습니다. RLP 인코딩은 이더리움에 있는 객체들을 직렬화하는데 사용되는 메인 인코딩 방법입니다. 그래서 RLP 인코딩은 블록 헤더의 상태 및 트랜잭션, 리시트, 머클 트리 상의 데이터와 통신 프로토콜 상의 메시지 등 이더리움에서 전체적으로 사용됩니다.

RLP말고 이미 고안된 많은 인코딩 방법들이 있지만, 이더리움에서 RLP 인코딩을 직접 구현한 이유는 구현한 인코딩 과정이 단순해서 인코딩 크기를 줄이고 바이트 단위의 일관성을 확보하기 위해서입니다. RLP 인코딩 함수는 하나의 item을 취하며, item은 String과 item들의 list로 정의됩니다.

 

 

 

DApp (Decentralized App)

이더리움은 비트코인처럼 암호화폐 구현 만을 위한 블록체인 플랫폼을 지향하는 것이 아니라, 암호화폐 이더와 블록체인 기술을 사용하여 다양한 문제를 해결하는 서비스들을 개발하고 운영할 수 있는 플랫폼을 목표로 합니다. 여기서 언급한 다양한 문제를 해결하는 서비스들을 Decentralized App이라 하며, 스마트 컨트랙트에 기반한 서비스를 제공하는 탈중앙 애플리케이션입니다.

 

블록체인 : 이더리움의 P2P 네트워크, 데이터베이스, 인코딩 방법 및 노드 디스커버리 과정 5

 

이더리움은 이 DApp을 구동시킬 수 있는 플랫폼입니다. 현재 천여 개 이상의 DApp 프로젝트가 추진 중이며, 주식, 보험, 복권과 같은 금융 분야뿐만 아니라 쿠폰, 투표 등 다양한 분야에서 개발 중입니다. 특히, 급여, 회계, 지분 등 조직 운영에 필요한 데이터를 블록체인에 올려서 운영하는 탈중앙화 자율조직(DAO)은 많은 관심을 받고 있습니다.

이러한 Dapp의 특징으로 어떠한 특정 주체를 신뢰할 필요가 없다는 것, 투명한 운영 원칙, 향상된 보안, 개인정보 보호, 글로벌 서비스의 용이함 등이 있습니다. 개발자는 Javascript, html 등을 이용해서 smart contract를 기반으로 하는 Web service인 Dapp을 구현할 수 있습니다.

이를 위해서 이더리움은 web3.js라는 Javascript 라이브러리를 제공합니다. web3.js는 JSON-RPC를 사용하여 블록체인의 데이터와 스마트 콘트랙트의 바이트 코드를 Javascript로 다룰 수 있게 하는 라이브러리입니다. 개발자가 스마트 컨트랙트를 개발한 후 블록체인에 배포하면 스마트 컨트랙트의 어카운트 주소와 ABI(Application Binary Interface)가 생성되는데 이것들을 알면 web3.js를 통해서 스마트 컨트랙트의 특정 함수를 실행시킬 수 있습니다.

 

 

 

Swarm: P2P File System

스웜(Swarm)은 인센티브 방식으로 운영되는 p2p 파일 시스템이며 CDN(Content Delivery Network)과 유사한 콘텐츠 전달 채널입니다. 스웜은 블록체인의 데이터뿐만 아니라 Dapp의 코드와 데이터 등을 탈중앙화된 분산 형태로 저장하고 해당 콘텐츠를 전달하기 위해 사용됩니다.

사실, 기존에도 토렌트와 같은 p2p 파일 시스템이 있지만, 이것은 서비스를 지속적으로 운영해야 할 인센티브가 없어 안정적으로 운영되기 어렵습니다. 그래서 성능과 품질을 보장할 수 없습니다. 하지만 스웜은 SWAP이라는 인센티브 시스템을 적용합니다.

SWAP (Swarm Accounting Protocol)은 콘텐츠를 다운받으면 이를 제공한 노드에게 대가를 지급하고, 인기 있는 콘텐츠를 제공하면 해당 콘텐츠를 다운받아 사용한 피어들로부터 대가를 받을 수 있는 인센티브 시스템입니다. 따라서 SWAP를 통해 스웜 네트워크 참여자들은 모두 각자 역할에 따라 보상을 받기 때문에 자체적으로 유지되고 성장할 수 있습니다.

현재 SWAP은 PoC(Proof of Concept)으로 구현 중에 있고, 이것의 최종 목표는 디도스 공격을 무력화하고, 무정지 운영되며, 인센티브 기반 하에 자생적으로 운영되는 것입니다. 위스퍼는 Dapp들이 서로 통신하기 위한 통신 프로토콜이며, 쉽고 효율적인 통신수단을 제공합니다. 이더리움은 geth와 C++ 클라이언트에 포함되어 배포되고 있으며, 실험적으로 운영되고 있습니다.

위스퍼는 추적 불가능한 P2P 메세징 프로토콜이고 Multi-casting, broadcasting, M-to-M과 같은 다양한 노드 간 메세징을 지원합니다 또한, 암호화 알고리즘을 사용하는데, 비대칭 암호화 알고리즘으로 SECP256k1의 공개키 방식을 사용하고, 대칭 키 방법으로는 AES-GCM 알고리즘을 사용합니다. 참고로, 위스퍼를 구동하려면, geth 구동 시 ?shh 옵션을 사용하면 됩니다.

 

 

 

참조

http://www.kmooc.kr/courses/course-v1:POSTECHk+CSED490U1+2021_T1/about

 

블록체인 입문

블록체인과 암호화폐 기술을 깊이 배우기에 앞서, 비 전공자들도 이해를 할 수 있는 수준으로 블록체인과 암화화폐에 대한 high-level 설명 및 응용 예시를 제공하고 실제 상황에 적용할 수 있다.

www.kmooc.kr

 

반응형