블록체인 기술을 이해해보기 (feat. baesh coin)

평소 블록체인에 관심이 많아 이런저런 기술 블로그를 찾아보면서, 언젠가 블록체인을 제대로 이해해보고 내 이름으로 된 코인도 직접 만들어 보고 싶다는 생각을 했습니다. 몇 년간 마음속으로만 품고 있다가 시간적 여유가 생겨 본격적으로 만들어 보았고, 그 과정에서 공부한 것들을 정리해보고자 합니다. 해당 기술을 적용하여 직접 만든 코인을 Baesh Coin에 간단하게 구현해 놓았습니다.
블록체인
블록체인의 정의
블록체인이란 뭘까요? 일단 위키백과에는 다음과 같이 정의합니다.
블록체인은 관리 대상 데이터를
블록이라고 하는 소규모 데이터들이 P2P 방식을 기반으로 생성된 체인 형태의 연결고리 기반 분산 데이터 저장 환경에 저장하여 누구라도 임의로 수정할 수 없고 누구나 변경의 결과를 열람할 수 있는 분산 컴퓨팅 기술 기반의 원장 관리 기술이다.
블록체인을 전공하지 않는 저로써는 크게 와닿지는 않았습니다. 데이터 블록들이 연결되어 있고 이 데이터들은 분산되어 있으며, 임의로 수정할 수 없다. 정도로만 단순하게 이해했습니다.
블록체인의 활용
우리가 블록체인하면 가장 먼저 떠오르는게 뭘까요? 바로 비트코인이죠. 왜 비트코인이 가장 먼저 떠오를까요? 블록체인은 비트코인이랑 동의어일까요? 그렇지 않습니다.
블록체인은 하나의 데이터를 관리하는 방식 기술일 뿐이며 이를 기반으로 다양한 상품들을 만들어 낼 수 있지만, 그 중 비트코인이 금전적으로 가장 엮여있어 대중들에게 친숙하기 때문입니다.
블록체인 기술을 쓰는 이유는 수정이 불가능한 분산된 데이터 입니다. 코인을 제외하고 모바일 운전면허증이나 국가보훈등록증 등에도 활용하고 있습니다.
하지만 이번 글에서는 가장 친숙한 비트코인 예시를 위주로 어떻게 블록체인이 구성되어 있으며 코인을 어떻게 만들 수 있는지에 대해 작성하고자 합니다.
블록체인의 구조
블록체인은 마치 자료구조시간에 배운 Linked List와 비슷하다고 느껴집니다. 헤더와 바디로 구성되어 있고 각 노드(블록)끼리 연결되어 있는 점도 비슷하죠.
다만 중요한 차이가 있는데, Linked List는 각 노드의 값을 자유롭게 수정할 수 있지만 블록체인은 그렇지 않습니다. 블록체인에서는 각 블록이 이전 블록의 해시값을 가지고 있기 때문에, 만약 중간에 있는 블록 하나를 수정하면 해시값이 달라지고 그 뒤에 연결된 모든 블록의 해시값이 전부 무효화됩니다. 이게 바로 블록체인이 "수정이 불가능하다"고 말하는 이유입니다.
아래 그림을 보면 각 블록이 이전 블록의 해시값을 참조하며 체인처럼 연결되어 있는 모습을 확인할 수 있습니다.
사실 블록체인을 어떻게 활용하는지에 따라 헤더에 들어갈 값과 바디에 들어갈 값은 달라질 수 있습니다. 하지만 가장 기본적으로 들어가는 것들을 기반으로 어떤 것으로 구성되어있는지 확인해 봅시다.
헤더
헤더에는 일반적으로 아래와 같은 해당 블록의 메타정보들이 들어가게 됩니다.
- 이전 블록의 해시값
- 머클루트 (바디에 담긴 트랜잭션들을 요약한 해시값)
- 논스
- 채굴 당시의 timestamp
- 난이도 타겟
여기서 생소할만한 단어가 두 개 있는데요. 먼저 머클루트는 바디에 들어있는 트랜잭션들을 머클 트리(Merkle Tree) 라는 구조로 정리한 뒤 나오는 최종 해시값입니다. 머클 트리는 트랜잭션들을 둘씩 짝지어 해싱하고, 그 결과를 또 짝지어 해싱하 고... 이걸 반복해서 하나의 루트 해시로 만드는 구조입니다. 이렇게 하면 바디에 수많은 트랜잭션이 있어도 머클루트 하나만으로 내용이 변조되었는지 빠르게 검증할 수 있습니다.
머클 트리를 그림으로 표현하면 아래와 같습니다.
그리고 논스의 경우 블록을 채굴할 때 논스 값을 계속해서 변경하여 타겟에 맞는 값을 찾기위한 난수라고 생각하시면 됩니다. 자세한 것은 이후 채굴 과정에서 자세하게 설명을 하겠습니다.
바디
바디에는 해당 블록이 어떤 것에 쓰이느냐에 따라 천차만별입니다. 비트코인의 경우 해당 블록의 바디 값에는 누가 누구에게 몇 비트코인을 전송 했는지에 대한 장부가 모두 기록 되어 있습니다. 이를 기반으로 전 세계 사람들은 마음만 먹으면 이체 과정을 전부 열람할 수 있는거죠.
여기서 블록체인의 핵심 특성 중 하나인 탈중앙화 개념이 등장합니다. 기존 은행 시스템에서는 중앙 서버 하나가 모든 거래 기록을 관리하지만, 블록체인에서는 네트워크에 참여한 모든 노드가 동일한 데이터를 가지고 있습니다. 특정 기관 하나가 데이터를 독점하지 않기 때문에 누구도 함부로 조작할 수 없고, 설령 일부 노드가 망가지더라도 전체 네트워크는 정상적으로 유지됩니다.
채굴
블록을 하나하나 쌓아가는 것을 채굴이라고 하는데요. 어떤 기준에서 채굴을 하게 될까요? 이것도 정하기 나름이지만 기본적으로 생성한 해시값이 특정 조건에 일치하게 되면 블록을 쌓을 권한이 주어집니다. 이런 방식을 작업 증명(Proof of Work, PoW) 이라고 합니다. 쉽게 말해서 "이만큼 컴퓨팅 자원을 써서 열심히 일했다"는 것을 증명하는 방식이죠. 아래 그림은 이 채굴 과정을 간단하게 나타낸 것입니다.
예를 들면 sha-256 암호화 방식 으로 앞 자리가 0으로 7개 시작하는 해시값을 찾으면 블록을 쌓을 자격을 준다고 정합시다. 그럼 사용자는 계속해서 해시값을 찾도록 컴퓨터를 돌릴것이고
0000000a8e9444549320e82f8d85f8184d092d6e3c54d1d8039e1451f2d65961 이런 값을 우연히 찾게 되면 사용자는 채굴에 성공한 것입니다. 여기서 7이라는 값은 난이도라고하며 숫자를 키울수록 해당하는 해시값을 찾기가 더욱 오래걸리겠죠. 0000000 이 prefix는 타겟이라고 하며 우리가 찾고자 하는 해시값의 일부가 됩니다.
그럼 해당하는 해시값은 어떻게 생성할 수 있을까요? 우리는 이때 위에서 언급한 블록의 헤더에 들어있는 고유 값을 활용하여 생성합니다.
위에서 설명한 헤더 정보들, 즉 이전 블록 해시값 + 머클루트 + 타임스탬프 + 난이도 타겟 + 논스를 합해서 해싱 과정을 통해 하나의 해시로 만듭니다. 바디에 있는 트랜잭션들은 머클 트리를 통해 이미 머클루트 하나로 요약되어 있기 때문에, 실제로 해싱하는 건 헤더 부분만입니다. 만약 이 값이 위에서 정한 타겟에 부합하면 블록을 하나 쌓게 됩니다. 만약 이 값이 틀리다? 그러면 논스 값을 계속해서 수정하여(예를들면 값을 1씩 증가한다거나...) 정답인 것을 계속해서 찾도록 합니다.
이렇게 자원을 사용하여 정답인 해시값을 찾아 블록을 쌓게되면 유저에게 보상을 해주어야합니다. 그래야 유저들이 계속해서 채굴을 하며 해당 체인이 유지가 가능하니까요. 채굴한 유저의 지갑에 정해진 값의 코인을 넣어줍니다.
참고로 비트코인이 사용하는 이 PoW 방식 외에도 지분 증명(Proof of Stake, PoS) 등 다양한 합의 알고리즘이 존재합니다. 이더리움의 경 우 원래 PoW를 사용하다가 PoS로 전환한 것으로 유명하죠. 이 부분은 나중에 기회가 되면 따로 정리해보겠습니다.