Unchecked 문법 [TIL / Solidity]

알락·2022년 12월 8일
0

이더리움

목록 보기
14/16

openZeppelin이 제공하는 ERC721 라이브러리를 살펴보다가 익숙지 않은 문법이 발견했다. 간단한 연산을 uncheck로 선언된 중괄호 scope 안에서 하는 것이다.

해당 문법을 사용하는 함수 예시는 다음과 같다.

[_transfer 문법]

function _transfer(
        address from,
        address to,
        uint256 tokenId
    ) internal virtual {
        require(ERC721.ownerOf(tokenId) == from, "ERC721: transfer from incorrect owner");
        require(to != address(0), "ERC721: transfer to the zero address");

        _beforeTokenTransfer(from, to, tokenId, 1);

        require(ERC721.ownerOf(tokenId) == from, "ERC721: transfer from incorrect owner");

        delete _tokenApprovals[tokenId];
		// ============================
        //			unchecked 문법
        // ============================
        unchecked {
            _balances[from] -= 1;
            _balances[to] += 1;
        }
        // =============================
        _owners[tokenId] = to;

        emit Transfer(from, to, tokenId);

        _afterTokenTransfer(from, to, tokenId, 1);
    }

그냥 지나쳐 버리기보다는 한 번 더 살펴보기 위해 관련 내용을 찾아봤다.


uncheked

위 함수의 같은 경우는 NFT 보유 개수를 증감하는 데에 사용하였다. 당장 확인해도 큰 문제가 없을 것 같은 연산이다.

unchecked 문법은 솔리디티 버전 0.8.0 이상부터 사용할 수 있다.

내용인 즉슨, 0.8.0 버전 이상부터는 대부분의 연산에 대하여 기본적으로 오버플로우와 언더플로우를 런타임 때 체크하게 되었다는 것이다. 만약 연산 결과가 위 두 문제 중에 하나를 발생시키면 트랜잭션 과정 중에 발생한 모든 것들을 되돌려버리고 이전 상태로 돌아가게 만든다.

기본 설정으로 대부분의 연산에 이런 검증 과정을 거치다보니, 당연히 혹은 거의 오버-언더플로우가 일어나지 않을 연산을 할 때도 불필요하게 사용된다. 이는 곧 가스비로 연결되게 된다. 그래서 충분히 보장되어있거나 굳이 필요하지 않을 경우에 검증과정을 생략하고 연산을 하기 위해 unchecked를 사용한다.


영향

오버-언더플로우를 검사하기 위해 사용되는 라이브러리를 이제 따로 임포트하여 사용할 필요가 없어진다. safeMath 가 그 대표적인 예이다. 하지만 솔리디티 0.8.0 이상에서만 가능한 얘기니 그 이전 버전으로 작성할 때는 솔리디티 버전을 이해하여 라이브러리를 사용할지 말아야할지 판단해야 한다.

또한 safeMath 에서 제공하는 나누기 연산의 zero divide는 0.8.0 이상의 솔리디티 컨트랙트가 따로 검사를 안 하기 때문에 참고하기 바란다. 0.8.0 이상의 솔리디티 버전에서 zero divide 연산에 대한 에러를 기본적으로 내준다. 하지만 unchecked가 zero divide 에 대해서 에러메시지를 안 내게 하진 않기 때문에 해당 에러는 따로 처리해주어야 한다.

참고

profile
블록체인 개발 공부 중입니다, 프로그래밍 공부합시다!

0개의 댓글