# OVM Deep Dive [KOR]

By [stalim17](https://paragraph.com/@-star) · 2023-05-23

---

핵심요약 – Layer 2 시스템용으로 설계된 모든 기능을 갖춘 EVM 호환 실행 환경인 OVM을 구축했습니다. 이 게시물은 OVM이 이더리움 메인 체인과 동일한 롤업을 가능하게 하는 방법을 설명합니다.

**OVM을 구축하는 이유는 무엇입니까?**

우리 팀의 많은 사람들은 이전에 계약을 지원하는 최초의 일반화된 플라즈마 구성인 [plapps를](https://medium.com/plasma-group/towards-a-general-purpose-plasma-f1cc4d49c1f4) 설계하기 위해 일했습니다 ! 그러나 plapps에는 제한된 "단어" 계약과 관련된 완전히 새로운 개발자 도구가 필요했습니다. 이더리움 L2는 단순히 이더리움을 _사용하여 확장하는 것을 의미하는 것이 아니라 이더리움 자체를 확장하는 것을_ 의미합니다 .

이것은 결국 이더리움 스마트 계약의 전체 기능 세트를 확장성 환경으로 가져오겠다고 약속한 최초의 L2 구성인 [Optimistic Rollup을](https://medium.com/plasma-group/ethereum-smart-contracts-in-l2-optimistic-rollup-2c1cef2ec537) 개발하게 했습니다 . [Unipig.exchange는](http://unipig.exchange/) 처음으로 이 전례 없는 기능을 시연했습니다. 처음으로 Uniswap은 L2에 있었습니다. 그러나 Unipig는 여전히 롤업의 힘을 활용하기 위해 L2 체인용으로 설계된 맞춤형 스마트 계약을 작성해야 했습니다. 개발자 경험을 보존하려면 더 나은 것이 필요했습니다.

**OVM이란 무엇입니까?**

OVM은 레이어 2 시스템에서 사용하도록 구축된 완전한 기능을 갖춘 EVM 호환 실행 환경입니다. 이를 통해 이더리움 메인 체인처럼 보이고 느끼고 작동하는 롤업 체인을 구현할 수 있습니다. Solidity에서 계약을 작성하고 Web3 API를 통해 체인과 상호 작용합니다!

OVM을 사용하면 dApp을 L2로 이동하기로 한 결정은 더 이상 아키텍처가 아닙니다. 단순히 배포의 문제입니다. 긴밀한 결합 및 구성 가능성을 포함하여 dApp 변경 사항을 구축하는 데 다른 것은 없습니다. 새로운 스마트 계약을 OVM 체인에 마음대로 배포할 수 있습니다. 즉, 머니 레고는 여전히 매력처럼 맞습니다.

그렇다면 이 마법은 어떻게 작용할까요? 그리고 OVM을 달성하기 어려웠던 이유는 무엇입니까? 다이빙하자!

**문제 설명: EVM-in-EVM**

모든 낙관적 L2 계획의 기초는 분쟁입니다. 플라즈마에서 롤업에 이르기까지 핵심 속성은 "낙관적 실행"입니다. 기본적으로 한 사람(또는 사람들)은 "이봐 L1, 이러한 트랜잭션을 실행할 필요가 없습니다. 결과는 X입니다!"라고 주장할 수 있습니다. 결과가 X가 아닌 경우 다른 당사자는 메인 체인에서 트랜잭션을 실행하여 잘못되었음을 증명하기 위해 비용을 지불할 수 있습니다.

![](https://storage.googleapis.com/papyrus_images/8d3acf2f2930e562f7f137a42c7a63b864ca06d752de698bd9af206e5ab19abd.png)

행복한 경우에는 트랜잭션을 체인에서 실행할 이유가 없습니다. 이것이 낙관적 실행이 전체 처리량을 확장하는 이유입니다. 그러나 안타까운 경우(예: 위의 경우) 트랜잭션을 재생할 **_수 있어야 합니다_**`tx2` . 그렇지 않으면 안전하지 않습니다!

Unipig용으로 작성된 [사용자 지정 코드는](https://github.com/plasma-group/pigi/blob/master/packages/unipig/src/contracts/UnipigTransitionEvaluator.sol) 기본적 으로 `execute_L2_tx()`. Unipig의 경우 호출할 수도 있습니다 `execute_uniswap_tx()`!

물론 우리가 정말로 원하는 것은 L1 사기 방지 트랜잭션 **내에서**`execute_EVM_tx()` 일반적인 L2 이더리움 트랜잭션을 실행할 수 있는 기능 입니다 ! 결과적으로 이더리움 트랜잭션을 서로 중첩시키는 것은 매우 까다롭습니다. 특히 L2 트랜잭션이 처음부터 L1 체인을 위한 것이 아니었을 때 더욱 그렇습니다!

![](https://storage.googleapis.com/papyrus_images/a7e8f4a6f9c6547aebbb1144942e48da9473d4ce6befbed77300601f40deaac0.png)

**EVM-in-EVM이 어려운 이유**

그러나 우리가 구축한 고유한 솔루션인 OVM에 대해 알아보기 전에 _이것이 왜 문제가 됩니까?_ EVM은 EVM 트랜잭션을 실행하기에 완벽한 장소가 아닙니까? 결국 EVM **입니다** !

**순진한 솔루션: L2 계약을 L1에 재배포**

본질적으로 EVM은 일련의 컴퓨터 [명령](https://ethervm.io/) 과 이러한 각 명령이 트랜잭션 중에 수행해야 하는 작업을 정의합니다. 이러한 지침을 함께 모아놓은 추악한 집합체를 스마트 계약이라고 합니다. `SafeMath.sol`예를 들어 다음은 Solidity 라이브러리가 배포되기 전에 컴파일되는 명령의 작은 샘플입니다 .

![](https://storage.googleapis.com/papyrus_images/b304eb61994fae1149611aaebe2a50d6219cd3a4c6c86ae702823cc36f3ecd85.png)

L1에서 L2 트랜잭션을 실행하려면 L2 트랜잭션에서 사용하는 코드(일명 스마트 계약)를 L1에 가져와야 합니다. 이를 수행하는 가장 간단한 방법은 계약을 L1에 재배포하는 것입니다!

![](https://storage.googleapis.com/papyrus_images/c467e4c37f62351b7c30b9a807e80a45f05c1b12fa6c07b2f4900978df9ed64f.png)

**작동하지 않는 이유: 다른 체인, 다른 결과**

경우에 따라 이 접근 방식이 실제로 작동 _합니다_ . 예를 들어 라이브러리는 기본적으로 , 등의 `SafeMath`수학 연산만 수행하는 간단한 계약입니다 . L2 계약을 L1에 재배포하면 L2와 동일하게 작동합니다! 결국 어떤 체인에서 발생하든 추가는 추가입니다.`add()subtract()SafeMath`

그러나 다른 계약의 경우 상황이 빠르게 무너집니다. 예를 들어, 현재 이더리움 타임스탬프에 42를 더한 값을 반환하는 이 간단한 계약을 생각해 보십시오.

    계약 TimeShifter { 
       function getShiftedTime() returns(uint) { 
          return block.timestamp + 42; 
       } 
    }
    

이 계약은 사기 증거를 위해 L1에 재배포할 때 동일한 결과를 반환합니까?

![](https://storage.googleapis.com/papyrus_images/8276d97b0c18c7c794e15aca8c874948c80aaf8236c8433427761b6c13119509.png)

분명히 아닙니다! 실제로 두 개의 서로 다른 L1 블록 간에 동일한 결과를 반환하지도 않습니다! 이는 재배치된 계약이 **L1** 타임스탬프를 가져오기 때문입니다. 그러나 올바르게 하려면 **L2** 타임스탬프를 반환해야 합니다 `execute_l2_tx`!

더 많은 예를 통해 생각해 보면 이것이 거의 모든 스마트 계약의 문제라는 것을 금방 깨닫게 될 것입니다. 예를 들어, ERC20을 상상해 보십시오. 계약을 L1에 재배포할 때 모든 잔고를 L2에 있던 것으로 어떻게 설정합니까? 목록은 계속됩니다.

**솔루션: OVM**

EVM-in-EVM 문제에 대해 역사적으로 제안된 솔루션은 두 가지 접근 방식을 취했습니다. 즉, [VM 자체를 분기](https://github.com/ethereum/EIPs/issues/726) 하거나 총알을 깨물고 [Solidity에서 전체 EVM 구현을 다시 작성하는 것입니다](https://github.com/leapdao/solEVM-enforcer/blob/307c3bc0e77526a6f217c442d609450e9a6729ff/contracts/EVMRuntime.sol#L57) . OVM은 문제에 대한 새로운 접근 방식으로 더 성능이 뛰어나고 유연하며 현재 Eth 1에서 작동하며 포크가 필요하지 않습니다!

### 컨테이너화: 실행 관리자

![](https://storage.googleapis.com/papyrus_images/226381199f8981bd244537eb1ca4979af1e254dba25e79afaaff531e1caf77f9.png)

핵심적으로 OVM은 OVM 계약의 [가상 컨테이너 역할을 하는 "실행 관리자"라고 하는 새로운 스마트 계약을 생성하여 이 문제를 해결합니다.](https://cloudacademy.com/blog/container-virtualization/) Execution Manager는 다음을 포함하여 L1과 L2 간의 실행 차이로 이어질 수 있는 모든 것을 가상화합니다.

*   계약 보관
    
*   `tx.origin`블록 번호, 타임스탬프 등과 같은 트랜잭션 "컨텍스트"
    
*   교차 계약 메시지 라우팅
    

기본적으로 L1과 L2 간에 약간의 차이를 보일 수 있는 EVM의 모든 기능에 대해 Execution Manager는 L1과 L2 간에 일관성을 유지하는 기능을 제공합니다.

작동 방식을 보여주는 장난감 예제로 다음과 같이 위의 타임스탬프 문제를 해결하는 컨테이너를 구성할 수 있습니다.

    계약 TimestampManager { 
        uint storage ovmTimestamp; 
        
        function setOvmTimestamp(숫자: uint) { 
            ovmTimestamp = 숫자; 
        } 
        
        function getOvmTimestamp() public returns(uint) { 
            return ovmTimestamp; 
        } 
    }
    

이제 위의 스마트 계약을 다시 만들 수 있지만 이번에는 컨테이너를 사용합니다.

    계약 OvmTimeShifter { 
       function getShiftedTime() returns(uint) { 
          return timestampManager.getOvmTimestamp() + 42; 
       } 
    }
    

이제 사기 증명 중에 L1에 컨테이너의 "가상 블록 번호"를 설정하여 올바른 값이 반환되도록 보장할 수 있습니다!

![](https://storage.googleapis.com/papyrus_images/af09cee8fc0799ff13a034a98def7ad7015bf451a2c1bf0c8da9d2637b46e0ab.png)

이것이 OVM이 EVM-in-EVM 실행을 가능하게 하는 방법의 핵심입니다: 체인 간에 다를 수 있는 EVM의 모든 구성 요소를 가상화합니다! 실제로 가상화해야 하는 약 15개의 이더리움 명령이 있습니다. 모든 기능을 갖춘 실제 Execution Manager를 [여기에서](https://github.com/ethereum-optimism/optimism-monorepo/blob/master/packages/ovm/src/contracts/ExecutionManager.sol) 볼 수 있습니다 !

**안전: 순도 검사기**

대신 컨테이너를 호출하기 위해 위의 계약을 약간 수정해야 했습니다 `block.timestamp`. 이로 인해 불일치가 수정되었지만 해당 특정 계약에만 해당됩니다! L2가 안전하려면 _모든_ L2 계약이 `block.timestamp`.

![](https://storage.googleapis.com/papyrus_images/dd60a6e7db60bd6f0081760be32f6ed8dd0cf1453f92914c9d2ccc7e3e7bb18b.png)

이를 시행하기 위해 OVM에는 ["순도 검사기"가 포함되어 있습니다. 이것은 주어진 스마트 계약이 Execution Manager를](https://github.com/ethereum-optimism/optimism-monorepo/blob/master/packages/ovm/src/contracts/PurityChecker.sol) **통해서만** 가상화된 명령에 액세스하는지 확인할 수 있는 기능입니다 . `block.timestamp`허용되지 않습니다! 이 요구 사항을 충족하지 않는 계약은 OVM에 배포되지 않도록 차단되어 임의의 계약이 위에 배포된 경우에도 L2 체인이 안전하게 유지되도록 합니다!

**개발자 경험: Transpiler**

계약에서 Execution Manager만 호출하도록 요구하는 또 다른 문제는 개발자 경험 `block.timestamp`입니다 `getOvmTimestamp()`. 이를 해결하기 위해 우리는 일반 EVM 바이트코드를 받아들이고 위에서 설명한 대로 컨테이너를 사용하는 OVM 바이트코드를 다시 내보내는 트랜스파일러를 구축했습니다. **이것은 개발자에게 OVM이 완전히 보이지 않는다는** 것을 의미합니다. 패키지를 Waffle 또는 Truffle과 같은 선호하는 테스트 스위트에 연결하기만 `solc-transpiler`하면 경주가 시작됩니다!

**앞으로**

우리는 OVM이 이더리움 L2를 위한 중요한 진전을 나타낸다고 생각합니다. 왜냐하면 이더리움을 _사용할_ 뿐만 아니라 이더리움을 사용할 수 있기 때문 _입니다_ **.** 단 몇 줄의 코드만으로 Solidity 계약을 더 저렴하고 빠른 솔루션으로 옮길 수 있다는 사실은 한동안 확장에 대해 가장 흥분하게 만들었습니다. 직접 해보고 싶다면 The Graph 및 Burner Wallet과 같은 표준 이더리움 도구에서 실시간으로 실행되는 Synthetix의 복잡한 교환 계약의 포트인 최신 OVM 전투 테스트를 여기에서 확인할 수 [있습니다](http://l2.synthetix.exchange/) .

더 자세히 알아보고 싶다면 [설명서](http://docs.optimism.io/) , [코드 를 확인하고](https://github.com/ethereum-optimism/optimism-monorepo) [discord](https://discord.optimism.io/) 에 문의하세요 !

[https://medium.com/ethereum-optimism/ovm-deep-dive-a300d1085f52](https://medium.com/ethereum-optimism/ovm-deep-dive-a300d1085f52)

---

*Originally published on [stalim17](https://paragraph.com/@-star/ovm-deep-dive-kor)*
