거래 구조
거래는 입력값이라고 불리는 자금원에서부터 출력값으로 불리는 목적지까지의 가치의 전송을 인코딩하는 데이터 구조다.
4바이트: 버전
1~9바이트: 입력값 개수
가변적: 입력값
1~9바이트: 출력값 개수
가변적: 출력값
4바이트: 잠금시간
거래 출력값과 입력값
비트코인 거래로 구성되어 있는 블록을 구성하는 기본 요소는 '소비되지 않은 거래 출력값(UTXO)'이다. UTXO는 특정 소유주에 의해 암호로 잠겨있고, 블록체인 상에 기록되어 있다. 비트코인 네트워크는 수백만 개에 달하는 UTXO중에서 이용 가능한 UTXO를 전부 추적한다. 따라서 수백 개의 거래와 수백 개의 블록들 중에서 사용자의 비트코인은 UTXO의 형태로 산재해 있을 수 있다.
비트코인 주소 혹은 계좌에 보관된 잔액은 있을 수 없다. 특정 소유주에 대해서 잠겨있는 UTXO가 여기저기 산재되어 있을 뿐이다. 지갑이 사용자의 잔액을 계산하는 방법은 블록체인을 조사하여 해당 소유주가 보유한 UTXO 전부를 더하는 것이다. UTXO는 현금과 비슷하게 동작하는데 돈을 지불하는 방식에는 여러 가지가 있을 수 있다. (1000원짜리 물건을 1000원 지폐로 지불, 100원 10개로 지불... 등등)
거래가 소비하는 UTXO를 거래 입력값이라고 하고 거래가 생성하는 UTXO를 거래 출력값이라고 한다. 이런 식으로 UTXO를 소비하고 생성하면서 비트코인이 다른 소유주로 이동한다. 거래 내에서 현 소유주의 서명으로 UTXO의 암호를 풀어 소비하고, 새로운 소유주의 비트코인 주소로 UTXO를 잠가서 새로운 UTXO를 생성한다.
거래출력값
모든 비트코인 거래는 출력값을 생성하며 출력값은 비트코인 장부에 기록된다. 누군가에게 비트코인을 전송하는 것은 소유주의 주소에 등록된 소비가능한 UTXO를 생성한다는 것을 의미한다.
거래출력값의 구조
8바이트: 비트코인 총액(사토시 단위)
1~9바이트: 잠금 스크립트 길이
가변적: 잠금 스크립트
잠금 스크립트
잠금 스크립트는 특정 금액을 소비하기 위해 충족되어야 하는 조건을 규정하고 있다. 대부분의 경우 잠금 스크립트는 해당 출력값을 특정 비트 코인 주소에 잠가 놓게 되고, 이를 통해 그에 해당하는 금액의 소유권이 새로운 소유주에게로 이전된다. 소유주는 개인키로부터 생성된 서명을 담고 있는 해제 스크립트를 사용하여 금액을 소비한다.
거래 입력값
거래 입력값은 UTXO가 블록체인 내에 기록되는 경우 해당 거래의 해시와 일련번호를 참조하여 특정한 UTXO를 지정한다. UTXO를 소비하기 위해서 거래의 입력값에는 UTXO에 설정된 소비 조건을 만족시키는 해제 스크립트도 포함되어야 한다. 해제 스크립트는 대개 잠금 스크립트 내에 있는 비트코인 주소의 소유권을 입증하는 서명이다.
UTXO가 선택되면 지갑은 UTXO 각각을 위한 서명을 담고 있는 해제 스크립트를 생성함으로써 UTXO가 잠금 스크립트 조건을 만족시켜서 소비될 수 있도록 해 준다. 지갑은 이러한 UTXO 참조값과 해제 스크립트를 해당 거래에 입력값으로 추가한다.
거래 입력값의 구조
32바이트: 거래해시(소비될 UTXO를 담고 있는 거래에 대한 해시값)
4바이트: 출력값 인덱스(소비될 UTXO의 색인번호, vout)
1~9바이트: 해제 스크립트 길이
가변적: 해제 스크립트
4바이트: 일련번호(장애가 있는 tx 대체 기능)
거래 수수료
대부분의 거래는 수수료를 포함한다. 거래 수수료는 비트코인 네트워크 상에서 비트코인 채굴자에게 제공하는 일종의 보상금이다. 대부분의 지갑에서는 거래 수수료를 자동으로 계산하고 그 값을 거래에 포함시킨다.
거래 수수료는 모든 거래에 소액의 비용을 부과함으로써 다음 블록에 거래를 포함시키는 데에 대한 동기부여의 역할을 한다. 거래 수수료는 비트코인 단위로 표현되는 거래 가치가 아닌, 킬로 바이트 단위 거래 단위의 거래 크기를 근거로 계산된다. 채굴자는 거래 수수료 등 여러 가지 기준에 따라 거래의 우선순위를 정한다.
거래에 수수료 추가하기
거래의 데이터 구조에는 수수료 필드가 없다. 대신 입력값의 총합과 출력값의 총합의 차이로 수수료를 알 수 있다. 입력값의 총합에서 출력값의 총합을 제하고 남은 값이 수수료가 된다.
Fees = sum(Inputs) - sum(Outputs)
예를 들어 500원 짜리 물건을 사는데 1000원을 지불하는 상황이다. 그러면 500원은 가게 주인한테 가고 500원은 잔돈으로 받게 된다. 이 상황에서 1000원을 지불하는 것은 '입력'으로 들어가고 '500원(가게주인)과 잔돈(500원)'은 '출력'으로 들어간다.
그러나 비트코인 네트워크 상에서는 수수료라는 개념이 존재하기 때문에 잔돈의 일부인 50원(예시)이 수수료로 빠진다. 즉, 입력(1000원)이고 출력은 500원(가게 주인)과 잔돈(450원)이다. 입력 - 출력값인 50원은 수수료가 된다.
거래 사슬과 고아거래
거래는 사슬을 형성하고 있으며, 이전 거래의 출력값을 소비하여 다음 거래를 위한 출력값을 생성한다. 거래를 생성하는 과정에서 자식거래가 부모 거래보다 일찍 도착하는 경우가 존재한다. 이런 경우 자식 거래를 먼저 전송받은 노드는 부모 거래가 있다는 것을 파악할 수 있다. 왜나하면 자식 거래는 부모거래를 참조하여 만들어지기 때문이다. 따라서 노드는 자식 거래를 거부하기보다 부모 거래가 도착하기를 기다렸다가 자식 거래를 다른 노드로 전파한다.
부모거래가 없는 거래들로 이루어진 풀을 '고아거래 풀'이라고 한다. 부모 거래가 노드에 도착하면 해당 부모가 생성한 UTXO를 참조하는 고아거래는 고아거래 풀에서 벗어나서 유효화된다. 거래로 구성된 사슬 전체는 거래풀에 포함되어 블록에서 채굴될 준비를 마친다.
출처: 마스터링 비트코인 챕터 5
'프로그래밍 > Block Chain' 카테고리의 다른 글
| [Bitcoin] 거래 스크립트 2 (0) | 2025.04.28 |
|---|---|
| [Bitcoin] 거래 스크립트 1 (0) | 2025.04.27 |
| [Bitcoin] Descriptor (0) | 2025.04.22 |
| [Bitcoin] 지갑 2 (1) | 2025.04.21 |
| [Bitcoin] 지갑 1 (0) | 2025.04.20 |
댓글