Truffle로 처음 시작하는 Solidity 개발 환경 구축
일반적으로 DApp을 개발하기 위해서 사용하는 대표적인 언어는 Solidity입니다. 더불어 Truffle을 이용하면 개발 환경을 매우 쉽게 구축할 수 있습니다. 더불어 메타마스크(MetaMask)는 이더리움 관련 앱을 개발하거나 사용하는 전반적인 과정에 있어서 필요하기 때문에 미리 설치해두시면 좋습니다. 말 나온 김에 MetaMask부터 설치를 진행하겠습니다.
▶ MetaMask 공식 홈페이지: https://metamask.io/
Metamask는 Chrome 확장 프로그램의 형태로 이용할 수 있습니다. 다운로드를 받아주세요.
Metamask를 처음 시작하면, 곧바로 지갑을 생성하여 관리할 수 있습니다.
약관에도 동의를 해주겠습니다.
이후에 비밀번호 설정창이 나오고 비밀번호를 입력하여 생성하면 다음과 같이 접속할 수 있습니다.
기본적으로 우리의 지갑은 [이더리움 메인넷]으로 설정되어 있습니다. 우리는 개발 목적으로 진행하고자 하므로, 일단 테스트넷으로 설정을 바꿀 필요가 있습니다.
[Ropsten 테스트넷]으로 변경합니다. 테스트넷은 말 그대로 개발자가 테스트를 쉽게 하기 위한 목적이므로 무료로 가상 이더를 입금 받을 수 있습니다. 따라서 가상의 이더를 입금 받기 위하여 [입금]를 누릅니다.
이후에 [이더 얻기] 버튼을 누릅니다.
그러면 Faucet에서 이더를 무료로 송금 받을 수 있습니다.
이 때 MetaMask가 동작하여 지갑을 연동하고 Faucet으로부터 이더를 얻게 됩니다.
약간의 시간이 흐른 뒤에 성공적으로 이더를 송금 받은 것을 확인할 수 있습니다.
이제 MetaMask에 대한 기본적인 사용 방법에 대해서 알아보았으므로, DApp 개발을 위한 개발환경을 구축합시다.
※ 사전 요구사항 구축 ※
가장 먼저 파이썬이 필요합니다. 파이썬 설치가 되어 있지 않다면, 공식 홈페이지에 접속하여 파이썬을 설치합니다.
https://www.python.org/downloads/
[Download] 버튼을 눌러 파이썬을 다운로드 받습니다.
[Add Python 3.7 to PATH]에 체크하여 기본 설정 그대로 설치를 진행합니다.
이후에 NPM을 설치하기 위해 node.js을 설치합니다. 공식 홈페이지에 접속하여 그대로 다운로드 하시면 됩니다.
마찬가지로 기본 설정 그대로 설치하면 됩니다.
또한 테스트넷 이외에도 Private 블록체인 환경을 구축해 놓는 것이 좋습니다. Ganache를 이용하면 손쉽게 우리 컴퓨터에 가상의 이더리움 네트워크가 생성됩니다.
https://www.trufflesuite.com/ganache
기본 설정 그대로 설치하시면 됩니다.
Ganache는 Microsoft 응용 프로그램 형태로 설치가 가능하군요.
다만 앱 설치 과정에서 개발자 모드가 체크되어 있지 않다면 설치가 안 될 수 있습니다. 그럴 때는 개발자 모드 설정을 위하여 [설정]으로 이동할 수 있도록 합니다.
[개발자 모드]에 체크한 뒤에 다시 설치를 진행하면 됩니다.
Ganache가 설치 완료되면, 곧 바로 [QUICKSTART] 모드로 로컬 이더리움 네트워크 서버를 구동시킬 수 있습니다.
다음과 같이 10개의 기본적인 이더리움 지갑이 주어지고, 개발 테스트에 충분한 만큼의 이더리움이 미리 들어가 있는 것을 알 수 있습니다. 이제 이를 이용해 테스트 할 수 있습니다.
※ Truffle 개발환경 구축 ※
이제 본격적으로 Truffle을 이용해 개발환경을 구축합니다. 따라서 가장 먼저 Truffle을 설치합니다.
npm install -g truffle@5.0.2
이 때 python과 npm 모두 기본적으로 설치 되어 있어야 합니다.
저는 다음과 같이 truffle이 설치되었습니다.
이제 하나의 폴더를 만든 뒤에, 명령 프롬프트에서 해당 폴더로 이동하여 truffle 프로젝트를 초기화합니다.
truffle init
이후에 실제로 개발 환경은 JS를 함께 사용하여 진행하게 됩니다. npm init으로 종속성 설정을 하시면 됩니다.
이제 package.json 파일을 작성합니다. 일반적으로 DApp을 개발할 때 자주 사용되는 라이브러리가 종속성으로 작성되어 있습니다.
{
"name": "hello-world",
"version": "1.0.0",
"description": "",
"main": "truffle-config.js",
"directories": {
"test": "test"
},
"scripts": {
"dev": "lite-server",
"test": "echo \"Error: no test specified\" && exit 1"
},
"author": "",
"license": "ISC",
"devDependencies": {
"truffle": "5.0.2",
"truffle-contract": "3.0.6",
"nodemon": "^1.17.3",
"bootstrap": "4.1.3",
"chai": "^4.1.2",
"chai-bignumber": "^2.0.2",
"chai-as-promised": "^7.1.1",
"lite-server": "^2.3.0"
}
}
Visual Studio Code와 같은 에디터(Editor) 프로그램을 실행하여, 우리의 프로젝트 폴더에 접속합니다. 그리고 npm install을 입력해 필요한 라이브러리를 설치합니다.
이제 contracts 폴더에 HelloWorld.sol 파일을 생성합니다. 다음과 같이 작성합니다.
pragma solidity ^0.5.0;
contract HelloWorld {
uint public hello = 0;
}
hello라는 public 변수에 0이라는 값을 넣어 주었으므로, 누구든지 이 앱에 접근하여 hello라는 변수의 값을 확인할 수 있을 것입니다. 이제 Solidity 소스코드를 컴파일하여 Byte Code 형태로 변환합니다.
truffle compile
컴파일 결과 다음과 같이 build/contracts 폴더에 HelloWorld.json 파일이 생성됩니다.
truffle-config.js 소스코드를 수정하여 개발 전용 서버를 입력하여 연동합니다. 아까 설치한 Ganache 서버를 입력하면 됩니다. IP로는 로컬 호스트(Local Host)를 의미하는 127.0.0.1과 포트 번호로는 7545를 입력하면 됩니다.
module.exports = {
networks: {
development: {
host: "127.0.0.1",
port: 7545,
network_id: "*"
}
},
compilers: {
solc: {
optimizer: {
enabled: true,
runs: 200
}
}
}
}
Ganache 프로그램에서도 기본적인 포트는 7545 포트로 설정된 것을 확인할 수 있으므로, 이를 그대로 넣습니다.
이후에 /migrations 폴더에 2_deploy_contracts.js 파일을 생성합니다.
const HelloWorld = artifacts.require("HelloWorld");
module.exports = function(deployer) {
deployer.deploy(HelloWorld);
};
이후에 truffle migrate를 입력하여 Deploy를 진행해보세요.
스마트 컨트랙트 배포 결과 그 비용으로 약간의 이더리움이 차감된 것을 확인할 수 있습니다.
이제 truffle console 명령을 입력하여 콘솔 환경에서 스마트 컨트랙트 정보를 확인합니다.
'블록체인' 카테고리의 다른 글
이더리움(Ethereum) DAO 재귀 함수 해킹 사례 (1) | 2018.04.09 |
---|---|
이더리움(Ethereum) 도스(DoS) 공격 사례 (0) | 2018.04.09 |
이더리움(Ethereum)의 개요 (0) | 2018.04.09 |
이더리움(Ethereum) DAO 재귀 함수 해킹 사례
나동빈
이더리움 DAO 재귀적 이더리움 전송 공격
2016년 6월에 이더리움 DAO 계약 플랫폼에 존재하는 취약점을 이용해 360만 개의 이더리움(ETH)이 해킹당하는 사고가 발생했습니다. 이 사건 때문에 이더리움의 가격은 폭락하였고, 궁극적으로 전체 이더리움의 10%에 달하는 이더리움이 해킹당하는 결과를 낳았습니다.
이더리움 DAO 플랫폼은 당연히 코드를 기반으로 작동하며 내부적으로 나누기(Split) 기능이 사용됩니다. splitDAO() 함수는 특정 계정의 잔액과 합계 금액을 갱신하는 함수입니다. 따라서 splitDAO가 다시 호출되기 이전에 어떠한 함수의 호출이라도 발생시킬 수 있다면 무한 재귀 호출(Infinite Recursion)을 발생시켜 원하는 만큼 자금을 이동시킬 수 있습니다.
다시 말해 이러한 해킹 기법의 기본적인 원리는 나누기(Split) 함수를 실행한 뒤에 DAO가 보상(Reward)를 인출하려고 할 때, 인출이 끝나기 전에 나누기 함수를 다시 실행하는 것입니다. 따라서 잔액을 업데이트하지 않고 다시 실행하여 계속해서 이더리움을 가져올 수 있게 됩니다. 쉽게 말해 DAO 토큰을 환불 받고도 DAO 토큰이 계속 남아있어 무한정 인출할 수 있는 것입니다. 취약한 소스코드는 구체적으로 다음과 같습니다.
function splitDAO(
uint _proposalID,
address _newCurator
) noEther onlyTokenholders returns (bool _success) {
...
// 이더리움을 이동시키고 새로운 토큰을 지정 받습니다.
uint fundsToBeMoved =
(balances[msg.sender] * p.splitData[0].splitBalance) / p.splitData[0].totalSupply;
if (p.splitData[0].newDAO.createTokenProxy.value(fundsToBeMoved)(msg.sender) == false)
throw;
// 공격자가 위 IF문을 재귀적으로 무한정 수행하도록 만들어 부당이익을 취합니다.
...
// DAO 토큰을 삭제합니다.
Transfer(msg.sender, 0, balances[msg.sender]);
withdrawRewardFor(msg.sender); // 결과적으로 이더리움을 받게 됩니다.
...
return true;
}
따라서 원래는 무한정 수행되지 않도록 설계된 소스코드를 무한정 수행하여 막대한 양의 이더리움을 해킹할 수 있었던 것입니다. 구체적인 공격 순서는 다음과 같습니다.
① 나누기(Split)를 요청하고 투표 기간이 만료될 때까지 기다립니다.
② splitDAO() 함수를 이용해 나누기를 수행합니다.
③ DAO 플랫폼은 createTokenProxy()함수를 실행해 적절한 토큰을 보내줍니다.
④ 3번 과정 이후에 withdrawRewardFor() 함수를 실행해 잔고가 업데이트 완료되기 전에 보상(Reward)을 받을 수 있도록 합니다.
⑤ DAO 플랫폼이 4번 과정을 수행하고 있는 동안에 동일한 파라미터로 2번 과정의 splitDAO() 함수를 다시 실행합니다.
⑥ 결과적으로 DAO 플랫폼이 더 많은 자식 토큰(Child Token)을 지급해주며, 잔고가 업데이트되기 전에 보상을 받습니다.
⑦ 5번 과정으로 돌아갑니다.
⑧ DAO가 잔고를 업데이트하도록 둡니다. 7번 과정에서 5번 과정으로 돌아간다는 점에서 이러한 재귀적 과정은 끝나지 않습니다.
기본적으로 많은 양의 수수료(Fee)를 발생시키지 않기 때으므로 사실상 무한정 공격을 수행할 수 있었습니다. 즉 앞서 언급했던 이더리움의 수수료 방어 기법은 이러한 공격 기법에 대한 해결책을 제시해줄 수 없는 것입니다. 결과적으로 악의적인 의도를 가진 공격자는 위 해킹 기법으로 자식 DAO 지갑으로 엄청난 양의 이더리움을 수금(Receive)할 수 있었습니다.
▶ 실제 공격자의 자식 DAO 지갑: https://www.etherchain.org/account/0x304a554a310c7e546dfe434669c62820b7d83490#history
실제 공격자의 지갑을 살펴보면 2016년 6월에 무려 360만 개의 이더리움을 소유한 것을 알 수 있습니다. 실로 어마어마한 금액으로 이더리움 개발팀의 빠른 대책이 필요한 상황이었습니다.
물론 취약점은 DAO 플랫폼 자체가 가지는 취약점이며 이더리움 개발팀은 이를 개선하기 위해서 다양한 해결법을 제시했습니다. 다만 블록체인 시스템은 중앙 기관이 없다는 점에서 무분별하게 이더리움 개발팀이 개입하는 경우 그 사회적 파장이 커질 수 있다는 점도 감안해야 했습니다. 또한 공격자의 개인키를 알아낼 수 없다는 점에서 거래를 무효 처리할 수도 없는 상황이었습니다.
그래서 DAO 프로젝트의 책임 개발자는 소프트 포크(Soft Fork)와 하드 포크(Hard Fork)로 크게 두 가지 해결책을 제시했습니다. 소프트 포크를 이용한 방법은 DAO와 해당 공격자의 자식 DAO 지갑의 사용을 정지하는 형태의 소프트 포크입니다. 또한 하드 포크는 DAO 토큰 보유자들이 이더리움을 돌려받도록 하는 형태의 하드 포크입니다.
결과적으로 이더리움 재단이 다양한 관계자들과 협의하여 소프트 포크 기술을 적용하도록 의사결정이 이루어졌습니다. 하지만 네트워크 불안정 문제가 발생하여 재협의를 진행하게 되었고, 하드 포크를 수행하는 방향으로 다시 의사결정이 이루어졌습니다. 따라서 1,920,000번째 블록을 기준으로 하드 포크가 성공적으로 진행되었습니다.
다만 하드 포크가 진행됨에 되어 기존의 기술을 따르는 이더리움 클래식(Ethereum Classic)과 새롭게 탄생한 이더리움(Ethereum)으로 이더리움 블록체인 플랫폼이 나뉘게 되었습니다. 이더리움 클래식은 하드 포크를 수행하기 전의 블록체인을 기반으로 상장된 가상화폐입니다. 다시 말해 기술적인 개선이 사실상 이루어지지 않았다는 점에서 가치가 평가절하 되고 있습니다.
이더리움 클래식도 이더리움과 동일하게 PoW 방식을 채택하고 있으며 추가적인 하드포크도 주기적으로 진행하고 있는 상황이라는 점에서 이목이 집중되고 있습니다. 현재 공식 이더리움 블록체인은 이더리움(ETH)이며 이더리움 클래식은 잔류 기술로 남아있는 상황입니다.
이러한 블록체인 보안 침해사고 발생의 가장 근본적인 이유는 기술 인증 제도가 명확히 잡혀있지 ISMS, PIMS 등과 같이 기술 인증 제도가 블록체인 플랫폼에도 적절히 적용될 수 있도록 해야 합니다. 더불어 보안 검증을 받은 블록체인 기술만 살아남을 수 있도록 하는, 시장 전체에 걸친 분위기가 형성되어야 한다고 생각합니다.
또한 일정 수준 이상의 시장 규모가 있는 블록체인 개발팀의 경우, 자체적으로 자문 능력이 뛰어난 컨설팅 팀과 보안 전문가 팀을 구성하도록 하여 미연에 침해사고를 방지할 필요가 있습니다. 2018년 이후 앞으로도 계속해서 블록체인 기술과 산업은 호황기를 이룰 것입니다. 빠른 사업화와 개발 능력 또한 물론 중요한 요소이지만 안정적인 시스템을 구축하기 위한 지속적인 노력이 필요한 시점이라고 생각합니다.
'블록체인' 카테고리의 다른 글
Truffle로 처음 시작하는 Solidity 개발 환경 구축 (0) | 2019.07.10 |
---|---|
이더리움(Ethereum) 도스(DoS) 공격 사례 (0) | 2018.04.09 |
이더리움(Ethereum)의 개요 (0) | 2018.04.09 |
이더리움(Ethereum) 도스(DoS) 공격 사례
나동빈
이더리움 도스(DoS) 공격
앞서 이더리움은 튜링 완전한 특징을 가진다고 했습니다. 당연히 튜링 완전하다는 점에서 무한 루프가 발생할 수 있을 것입니다. 하지만 이더리움에서는 수수료(Fee)가 존재하기 때문에 공격을 수행할 때마다 일정한 수수료를 공격자가 지불해야 합니다. 이는 결과적으로 채굴자들에게 더 많은 수수료를 지급하여 채굴자들을 유입시키는 역할을 수행합니다. 그래서 공격 덕분에 오히려 보안이 증가하는 것입니다. 이는 이더리움 블록체인의 선순환 구조를 형성합니다.
하지만 만약 이더리움의 수수료가 굉장히 저렴하다면 악의적인 목적을 가진 공격자는 도스(DoS) 공격을 수행할 수 있습니다. 실제로 2016년 말에는 이더리움 네트워크에 지속적인 도스 공격이 감행이 되었습니다. 그 결과 네트워크가 불안정해져 트랜잭션 속도가 느려지고, 채굴에 제약이 생기게 되었습니다. 대표적인 도스 공격 방식으로는 다음의 두 가지가 존재합니다.
· 무작위 계정(Account) 생성 공격
· 무작위 거래(Transaction) 수행 공격
이더리움은 기본적으로 가스(Gas)라고 불리는 수수료가 매우 저렴하다는 장점이 있는데 이를 역이용하여 의미가 없는 거래를 매우 많이 발생시켜 과부하를 주는 방식이 주로 사용되었습니다. 사실 이 문제의 궁극적인 원인은 수수료가 적절한 수준으로 설정이 되지 않았기 때문이며 이를 해결하기 위해서는 하드 포크(Hard Fork)가 필요했습니다.
따라서 현재까지는 이더리움에 대한 도스 공격의 대응책으로 하드포크를 많이 수행하였습니다. 하드포크의 과정에서는 수수료 비용을 조정하고, 빈 거래 및 계정에 대한 정보를 일괄 삭제하는 작업이 수행됩니다. 실제로 2,463,000번째 블록에서 하드포크를 수행하여 이더리움 블록체인을 개선한 이력이 있습니다. 이어서 2,675,000번째 블록에서도 하드포크를 수행했습니다.
이더리움은 작업 증명(Proof-of-Work) 방식에 근간하고 있으며 하나의 블록에 고작 200개 가량의 거래(Transaction) 정보를 담는다는 점에서 속도 측면에서 한계를 가지고 있습니다. 따라서 도스 공격에 매우 취약한 상태이며 실제로 거래량 폭증으로 인해 거래가 정상적으로 처리되지 않았던 사례가 많았습니다. 이러한 거래 속도 문제를 이더리움이 넘어야 할 산입니다.
컨설팅적 관점에서 이러한 문제의 해결 방안을 제시하자면 기존의 PoW 방식을 고수하지 않고 다른 합의 알고리즘을 부분적으로 채택하는 것이 효율적이라고 생각합니다. 따라서 PoS, DPoS 등의 방식을 적용하도록 하드포크를 수행하여 불필요한 컴퓨터 자원 낭비를 줄이고, 거래 속도를 향상시켜야 합니다. 실질적으로 채굴을 수행하는 노드가 적은 이오스(EOS) 블록체인 플랫폼 등을 벤치마킹할 필요가 있습니다. 물론 보안성을 유지할 수 있는 선에서 높은 거래 속도를 유지할 수 있는 선에서의 의사결정이 필요할 것이라고 생각합니다.
'블록체인' 카테고리의 다른 글
Truffle로 처음 시작하는 Solidity 개발 환경 구축 (0) | 2019.07.10 |
---|---|
이더리움(Ethereum) DAO 재귀 함수 해킹 사례 (1) | 2018.04.09 |
이더리움(Ethereum)의 개요 (0) | 2018.04.09 |
이더리움(Ethereum)의 개요
나동빈
이더리움 개요
이더리움(Ethereum)은 ‘블록체인 기술을 활용한 어플리케이션을 손쉽게 개발할 수 있도록 해주는 플랫폼’으로 비탈릭 부테린(Vitalik Buterin)이 개발했습니다. 현재 존재하는 이더리움 클래식(Ethereum Classic)이 이더리움 가상화폐의 초기 모델입니다. 이러한 이더리움이 매우 사랑받고 성장하게 된 계기는 개발자 친화적인 환경이 구성되어있다는 특징 때문입니다.
이더리움은 튜링 완전(Turing-Complete)한 시스템을 갖추고 있어 개발 언어에 구애받지 않고 누구나 이더리움 기반의 어플리케이션을 개발할 수 있습니다. 대표적으로 스마트 컨트랙트나 분산 어플리케이션(Decentralized Application)을 작성할 수 있습니다. 특히 트랜잭션 형식, 상태변환 함수 등을 정의할 수 있다는 점에서 매우 활용도가 높은 가상화폐 플랫폼입니다.
이더리움은 익명성(Anonymity), 무국경성(Borderlessness), 탈중앙성(Decentralization), 분산 네트워크(Distributed Network), DDoS 차단(DDoS Attack-Proof), 분할성(Divisibility into Pieces), 투명성(Transparency) 등의 특징을 가진다는 점에서 다른 블록체인과 흡사한 구조를 가지고 있습니다. 다만 여기에서 추가적으로 ‘플랫폼을 통한 응용성’과 ‘스마트 컨트랙트’라는 특별한 기술이 적용되어 시장에서 굉장히 큰 영향력을 행사하고 있습니다.
이더리움의 목적
이더리움의 목적은 누구나 손쉽게 분산 어플리케이션을 제작할 수 있도록 공통적인 프로토콜을 제시하는 것입니다. 실제로 이더리움을 기반으로 하는 매우 많은 어플리케이션과 블록체인 플랫폼이 존재합니다. 다양한 분산 어플리케이션에 적용될 수 있는 개발 방법론을 제공하고, 누구나 빠르고 보안성이 높은 어플리케이션을 개발할 수 있도록 해줍니다. 특히 다른 어플리케이션과의 효율적인 상호작용이 필요한 상황에서 적용할 수 있는 플랫폼입니다.
이러한 목적을 달성할 수 있는 기술적 근간은 튜링 완전 언어를 지원한다는 점입니다. 튜링 완전 언어란 ‘수학 문제를 풀 수 있는 일반적인 알고리즘을 만들어낼 수 있는 프로그래밍 언어’를 의미하는 것으로 조건문, 반복문 등을 포함한 문법 체계를 갖추고 있어야 합니다. 그 대표적인 것이 바로 솔리디티(Solidity)이며 사실상 상상 가능한 대부분의 거래를 프로그래밍 할 수 있습니다.
DAO(Decentralized Autonomous Organization)
DAO(Decentralized Autonomous Organization)란 단어 그대로 탈중앙화 자율조직을 의미합니다. 다시 말해 중앙 관리 조직이 없는 상태에서 참여자들이 자율적으로 제안과 투표 등의 의 사표현을 하여 조직을 관리할 수 있습니다. DAO 시스템에는 자체적인 인공지능이 적용되어 전체 의사표현 과정이 효과적으로 처리되며 궁극적으로 투자자들은 이더리움을 이용해 DAO 토큰을 구매하고, 특정한 서비스에 투자할 수 있게 됩니다.
'블록체인' 카테고리의 다른 글
Truffle로 처음 시작하는 Solidity 개발 환경 구축 (0) | 2019.07.10 |
---|---|
이더리움(Ethereum) DAO 재귀 함수 해킹 사례 (1) | 2018.04.09 |
이더리움(Ethereum) 도스(DoS) 공격 사례 (0) | 2018.04.09 |