ERC-165는 계약이 특정 interface를 구현한다고 선언하는 supportsInterface(bytes4) 조회 규약입니다. Interface ID는 해당 interface 함수 selectors를 XOR한 bytes4이며 supportsInterface 호출은 30,000 gas 이내에 응답해야 합니다. 탐지자는 먼저 ERC-165 ID 0x01ffc9a7에 true, invalid ID 0xffffffff에 false인지 확인한 뒤 목표 ID를 질의합니다. 그러나 true는 계약의 자기 선언일 뿐 각 함수가 올바른 의미·권한·반환값으로 동작하거나 악성 callback이 없다는 암호학적 증명이 아닙니다.
Interface ID는 selector 집합의 XOR입니다
Function selector는 canonical signature keccak256의 앞 4바이트입니다. ERC-165 interface ID는 interface에 속한 함수 selectors를 XOR합니다. Return type은 selector에 포함되지 않고 overloaded functions는 인수 types가 달라 별도 selector를 가집니다. Event와 error selector는 interface ID에 넣지 않습니다.
Solidity type(IMyInterface).interfaceId로 계산할 수 있지만 상속된 interface의 함수 포함 방식과 compiler 표현을 test vector로 확인합니다. 소스의 함수 이름을 정렬해 문자열 hash 하나를 만드는 방식이 아닙니다.
supportsInterface의 true는 계약이 그 표찰을 붙였다는 뜻이며, 표찰에 적힌 행동을 정직하게 수행한다는 보증서는 아닙니다.
JOBCOIN 해설

그림은 이 주제의 공통 개념을 단순화한 설명입니다. 아래 항목에서 이 글의 구체적인 조건과 예외를 함께 읽어보세요.
- Interface ID는 selector 집합의 XOR입니다
Function selector는 canonical signature keccak256의 앞 4바이트입니다.
- 두 단계 사전 검사로 ERC-165 지원을 확인합니다
EIP-165 탐지 절차는 STATICCALL 성격의 조회로 0x01ffc9a7 지원이 true인지 확인하고 0xffffffff에는 false인지 확인합니다.
- NFT 수신자 사례에서 실제 callback을 분리합니다
ERC-721 계약이 receiver의 ERC165 응답만 보고 safeTransfer를 끝내는 것이 아니라 onERC721Received를 실제 호출하고 magic return value를 검사 하는 이유가 경계입니다.
AI로 제작한 개념도 · 실제 가격·거래 내역·통계가 아닙니다.
두 단계 사전 검사로 ERC-165 지원을 확인합니다
EIP-165 탐지 절차는 STATICCALL 성격의 조회로 0x01ffc9a7 지원이 true인지 확인하고 0xffffffff에는 false인지 확인합니다. 둘을 통과한 계약에 목표 interface ID를 질의합니다. 호출 실패, 짧거나 malformed returndata도 false 또는 unknown으로 처리합니다.
30,000 gas 제한은 조회가 과도한 작업으로 caller를 소진시키지 않도록 합니다. Proxy fallback, revert와 empty return이 있을 수 있으므로 ABI bool decoding 전에 success와 정확한 반환 길이를 검사합니다.
| 관찰 | 판정 | 후속 |
|---|---|---|
| 165 true·ffff false | ERC-165 후보 | 목표 ID 조회 |
| 165 false | 미지원 | 다른 탐지 정책 |
| ffff true | 규약 불일치 | 결과 불신 |
| 목표 ID true | 지원 선언 | 실제 동작 시험 |
| Revert·malformed | unknown·미지원 | 안전 fallback |
NFT 수신자 사례에서 실제 callback을 분리합니다
ERC-721 계약이 receiver의 ERC165 응답만 보고 safeTransfer를 끝내는 것이 아니라 onERC721Received를 실제 호출하고 magic return value를 검사하는 이유가 경계입니다. Receiver가 interface를 true로 선언해도 callback에서 revert하거나 다른 값을 반환할 수 있습니다.
반대로 일부 오래된 contract는 동작은 구현했지만 ERC-165를 선언하지 않을 수 있습니다. Application이 미지원 contract를 허용할지, unsafe transfer를 제공할지는 자산 복구 위험과 함께 정책으로 정합니다. Interface 탐지를 존재하지 않는 함수의 안전한 호출로 바꾸지 않습니다.
- 목표 canonical 함수 signatures를 확정합니다.
- 각 selector와 XOR interface ID를 독립 계산합니다.
- ERC-165 ID와 invalid ID 응답을 먼저 검사합니다.
- Success·returndata length·bool 값을 검증합니다.
- 목표 함수의 실제 return·state effect도 시험합니다.
Proxy와 upgrade는 응답을 바꿀 수 있습니다
Proxy는 fallback delegatecall로 implementation의 supportsInterface를 실행하므로 upgrade 뒤 같은 주소 응답이 달라질 수 있습니다. 캐시에 영구 저장하면 새 기능을 놓치거나 제거된 interface를 계속 지원한다고 표시할 수 있습니다. Block hash와 implementation code hash를 함께 기록합니다.
Diamond나 모듈형 계약은 selector routing table과 supportsInterface registry가 어긋날 수 있습니다. Registry update와 facet 변경을 원자적으로 유지하고 실제 selector가 어느 target으로 가는지 확인합니다.
보안·경제 의미는 별도 검증입니다
ERC-165는 function semantics, access control, token solvency나 standard 전체 준수를 검사하지 않습니다. 악성 contract는 어떤 ID에도 true를 반환하면서 호출 시 자산을 훔치거나 gas를 소진할 수 있습니다.
Indexer는 interface true를 분류 hint로 사용하고 verified code, 호출 결과와 events를 교차 확인합니다. Frontend는 ‘ERC-721 지원’ 같은 라벨을 감사·공식 인증처럼 표시하지 않고 관찰 block과 확인 범위를 남깁니다.
자주 묻는 질문
supportsInterface가 true면 함수 호출도 성공하나요?
아닙니다. 함수가 revert하거나 잘못된 값을 반환할 수 있어 실제 호출 조건을 검증해야 합니다.
Interface ID에 event도 포함하나요?
아닙니다. 해당 interface의 function selectors를 XOR합니다.
EOA에 supportsInterface를 호출하면 되나요?
Code가 없으므로 정상 ERC-165 응답을 기대할 수 없습니다. 먼저 code 존재와 호출 결과를 확인합니다.
더 깊이 읽기
본문에서 다룬 개념과 확인 절차를 다음 글에서 이어서 살펴보세요.



