From 6382c745325bdc4be37dcb16ea124d7f5e74e6d7 Mon Sep 17 00:00:00 2001 From: ctrlc03 <93448202+ctrlc03@users.noreply.github.com> Date: Fri, 3 Oct 2025 15:30:22 +0100 Subject: [PATCH] chore: allow mock input validator in CRISP --- examples/CRISP/client/.env.example | 2 +- .../contracts/CRISPInputValidatorFactory.sol | 2 +- .../Mocks/MockCRISPInputValidator.sol | 49 +++++++++++++++++++ examples/CRISP/deploy/Deploy.s.sol | 16 +++++- examples/CRISP/server/.env.example | 2 +- .../ICiphernodeRegistry.json | 2 +- .../interfaces/IEnclave.sol/IEnclave.json | 2 +- .../NaiveRegistryFilter.json | 4 +- .../scripts/deployEnclave.ts | 14 +++--- 9 files changed, 79 insertions(+), 14 deletions(-) create mode 100644 examples/CRISP/contracts/Mocks/MockCRISPInputValidator.sol diff --git a/examples/CRISP/client/.env.example b/examples/CRISP/client/.env.example index 6d6aac6760..9296e8aa99 100644 --- a/examples/CRISP/client/.env.example +++ b/examples/CRISP/client/.env.example @@ -1,5 +1,5 @@ VITE_ENCLAVE_API=http://127.0.0.1:4000 VITE_TWITTER_SERVERLESS_API= VITE_WALLETCONNECT_PROJECT_ID= -VITE_E3_PROGRAM_ADDRESS=0x4ed7c70F96B99c776995fB64377f0d4aB3B0e1C1 # Default E3 program address from anvil +VITE_E3_PROGRAM_ADDRESS=0x322813Fd9A801c5507c9de605d63CEA4f2CE6c44 # Default E3 program address from anvil VITE_SEMAPHORE_ADDRESS=0x9A9f2CCfdE556A7E9Ff0848998Aa4a0CFD8863AE diff --git a/examples/CRISP/contracts/CRISPInputValidatorFactory.sol b/examples/CRISP/contracts/CRISPInputValidatorFactory.sol index e578127eaf..7c5350fe51 100644 --- a/examples/CRISP/contracts/CRISPInputValidatorFactory.sol +++ b/examples/CRISP/contracts/CRISPInputValidatorFactory.sol @@ -12,7 +12,7 @@ import {CRISPInputValidator} from "./CRISPInputValidator.sol"; /// @notice Factory for deploying minimal proxy instances of CRISPInputValidator. contract CRISPInputValidatorFactory is Factory { /// @notice Initializes the factory with the CRISPInputValidator implementation. - constructor() Factory(address(new CRISPInputValidator())) {} + constructor(address inputValidator) Factory(inputValidator) {} /// @notice Deploys a new CRISPInputValidator clone. /// @param _policyAddr Address of the associated policy contract. diff --git a/examples/CRISP/contracts/Mocks/MockCRISPInputValidator.sol b/examples/CRISP/contracts/Mocks/MockCRISPInputValidator.sol new file mode 100644 index 0000000000..8f7bf67077 --- /dev/null +++ b/examples/CRISP/contracts/Mocks/MockCRISPInputValidator.sol @@ -0,0 +1,49 @@ +// SPDX-License-Identifier: LGPL-3.0-only +// +// This file is provided WITHOUT ANY WARRANTY; +// without even the implied warranty of MERCHANTABILITY +// or FITNESS FOR A PARTICULAR PURPOSE. +pragma solidity >=0.8.27; + +import {IInputValidator} from "@enclave-e3/contracts/contracts/interfaces/IInputValidator.sol"; +import {IBasePolicy} from "@excubiae/contracts/interfaces/IBasePolicy.sol"; +import {Clone} from "@excubiae/contracts/proxy/Clone.sol"; +import {IVerifier} from "../CRISPVerifier.sol"; + +/// @title MockCRISPInputValidator. +/// @notice Mock Enclave Input Validator +contract MockCRISPInputValidator is IInputValidator, Clone { + /// @notice The policy that will be used to validate the input. + IBasePolicy internal policy; + + /// @notice The verifier that will be used to validate the input. + IVerifier internal noirVerifier; + + /// @notice The error emitted when the input data is empty. + error EmptyInputData(); + /// @notice The error emitted when the input data is invalid. + error InvalidInputData(bytes reason); + /// @notice The error emitted when the Noir proof is invalid. + error InvalidNoirProof(); + + /// @notice Initializes the contract with appended bytes data for configuration. + function _initialize() internal virtual override(Clone) { + super._initialize(); + + (address policyAddr, address verifierAddr) = abi.decode(_getAppendedBytes(), (address, address)); + policy = IBasePolicy(policyAddr); + noirVerifier = IVerifier(verifierAddr); + } + + /// @notice Validates input + /// @param sender The account that is submitting the input. + /// @param data The input to be verified. + /// @return input The decoded, policy-approved application payload. + function validate(address sender, bytes memory data) external returns (bytes memory input) { + if (data.length == 0) revert EmptyInputData(); + + (,,, bytes memory vote) = abi.decode(data, (bytes, bytes, bytes32[], bytes)); + + input = vote; + } +} diff --git a/examples/CRISP/deploy/Deploy.s.sol b/examples/CRISP/deploy/Deploy.s.sol index 7dc1dff08f..e4991e44dd 100644 --- a/examples/CRISP/deploy/Deploy.s.sol +++ b/examples/CRISP/deploy/Deploy.s.sol @@ -32,6 +32,8 @@ import {IE3Program} from "@enclave-e3/contracts/contracts/interfaces/IE3Program. import {IEnclave} from "@enclave-e3/contracts/contracts/interfaces/IEnclave.sol"; import {CRISPCheckerFactory} from "../contracts/CRISPCheckerFactory.sol"; import {CRISPPolicyFactory} from "../contracts/CRISPPolicyFactory.sol"; +import {CRISPInputValidator} from "../contracts/CRISPInputValidator.sol"; +import {MockCRISPInputValidator} from "../contracts/Mocks/MockCRISPInputValidator.sol"; import {CRISPInputValidatorFactory} from "../contracts/CRISPInputValidatorFactory.sol"; import {HonkVerifier} from "../contracts/CRISPVerifier.sol"; import {MockRISC0Verifier} from "../contracts/Mocks/MockRISC0Verifier.sol"; @@ -179,7 +181,19 @@ contract CRISPProgramDeploy is Script { CRISPPolicyFactory policyFactory = new CRISPPolicyFactory(); console2.log("Deployed CRISPPolicyFactory to", address(policyFactory)); - CRISPInputValidatorFactory inputValidatorFactory = new CRISPInputValidatorFactory(); + bool useMockIV = vm.envOr("USE_MOCK_INPUT_VALIDATOR", false); + address inputValidatorAddress; + if (useMockIV) { + console2.log("Using MockCRISPInputValidator"); + inputValidatorAddress = address(new MockCRISPInputValidator()); + } else { + console2.log("Using CRISPInputValidator"); + inputValidatorAddress = address(new CRISPInputValidator()); + } + + console2.log("Deployed InputValidator to: ", inputValidatorAddress); + + CRISPInputValidatorFactory inputValidatorFactory = new CRISPInputValidatorFactory(inputValidatorAddress); console2.log( "Deployed CRISPInputValidatorFactory to", address(inputValidatorFactory) diff --git a/examples/CRISP/server/.env.example b/examples/CRISP/server/.env.example index e25bfab57f..5275eeb47d 100644 --- a/examples/CRISP/server/.env.example +++ b/examples/CRISP/server/.env.example @@ -13,7 +13,7 @@ CRON_API_KEY=1234567890 ENCLAVE_ADDRESS="0xe7f1725E7734CE288F8367e1Bb143E90bb3F0512" CIPHERNODE_REGISTRY_ADDRESS="0xCf7Ed3AccA5a467e9e704C703E8D87F634fB0Fc9" NAIVE_REGISTRY_FILTER_ADDRESS="0xDc64a140Aa3E981100a9becA4E685f962f0cF6C9" -E3_PROGRAM_ADDRESS="0x4ed7c70F96B99c776995fB64377f0d4aB3B0e1C1" # CRISPProgram Contract Address +E3_PROGRAM_ADDRESS="0x322813Fd9A801c5507c9de605d63CEA4f2CE6c44" # CRISPProgram Contract Address # E3 Config E3_WINDOW_SIZE=40 diff --git a/packages/enclave-contracts/artifacts/contracts/interfaces/ICiphernodeRegistry.sol/ICiphernodeRegistry.json b/packages/enclave-contracts/artifacts/contracts/interfaces/ICiphernodeRegistry.sol/ICiphernodeRegistry.json index 63ec1552b3..6fcabb0550 100644 --- a/packages/enclave-contracts/artifacts/contracts/interfaces/ICiphernodeRegistry.sol/ICiphernodeRegistry.json +++ b/packages/enclave-contracts/artifacts/contracts/interfaces/ICiphernodeRegistry.sol/ICiphernodeRegistry.json @@ -219,5 +219,5 @@ "deployedLinkReferences": {}, "immutableReferences": {}, "inputSourceName": "project/contracts/interfaces/ICiphernodeRegistry.sol", - "buildInfoId": "solc-0_8_27-8287ebf5be05227965814498ddef24fc9009e2f0" + "buildInfoId": "solc-0_8_27-9aea5e3f6e25811e781e96c22e8edaf1eb1a01c5" } \ No newline at end of file diff --git a/packages/enclave-contracts/artifacts/contracts/interfaces/IEnclave.sol/IEnclave.json b/packages/enclave-contracts/artifacts/contracts/interfaces/IEnclave.sol/IEnclave.json index 524089c238..08b2500f7c 100644 --- a/packages/enclave-contracts/artifacts/contracts/interfaces/IEnclave.sol/IEnclave.json +++ b/packages/enclave-contracts/artifacts/contracts/interfaces/IEnclave.sol/IEnclave.json @@ -704,5 +704,5 @@ "deployedLinkReferences": {}, "immutableReferences": {}, "inputSourceName": "project/contracts/interfaces/IEnclave.sol", - "buildInfoId": "solc-0_8_27-8287ebf5be05227965814498ddef24fc9009e2f0" + "buildInfoId": "solc-0_8_27-9aea5e3f6e25811e781e96c22e8edaf1eb1a01c5" } \ No newline at end of file diff --git a/packages/enclave-contracts/artifacts/contracts/registry/NaiveRegistryFilter.sol/NaiveRegistryFilter.json b/packages/enclave-contracts/artifacts/contracts/registry/NaiveRegistryFilter.sol/NaiveRegistryFilter.json index e41dbde5d7..88b78ae36f 100644 --- a/packages/enclave-contracts/artifacts/contracts/registry/NaiveRegistryFilter.sol/NaiveRegistryFilter.json +++ b/packages/enclave-contracts/artifacts/contracts/registry/NaiveRegistryFilter.sol/NaiveRegistryFilter.json @@ -305,5 +305,5 @@ "deployedLinkReferences": {}, "immutableReferences": {}, "inputSourceName": "project/contracts/registry/NaiveRegistryFilter.sol", - "buildInfoId": "solc-0_8_27-e09265851ba98e1f1077468e6dbf08ff116b5fb9" -} + "buildInfoId": "solc-0_8_27-9aea5e3f6e25811e781e96c22e8edaf1eb1a01c5" +} \ No newline at end of file diff --git a/packages/enclave-contracts/scripts/deployEnclave.ts b/packages/enclave-contracts/scripts/deployEnclave.ts index de9d52c166..ead1aea1b6 100644 --- a/packages/enclave-contracts/scripts/deployEnclave.ts +++ b/packages/enclave-contracts/scripts/deployEnclave.ts @@ -42,8 +42,6 @@ export const deployEnclave = async (withMocks?: boolean) => { const enclaveAddress = await enclave.getAddress(); - console.log("Enclave deployed to: ", enclaveAddress); - const { ciphernodeRegistry } = await deployAndSaveCiphernodeRegistryOwnable({ enclaveAddress: enclaveAddress, owner: ownerAddress, @@ -52,8 +50,6 @@ export const deployEnclave = async (withMocks?: boolean) => { const ciphernodeRegistryAddress = await ciphernodeRegistry.getAddress(); - console.log("CiphernodeRegistry deployed to: ", ciphernodeRegistryAddress); - const { naiveRegistryFilter } = await deployAndSaveNaiveRegistryFilter({ ciphernodeRegistryAddress: ciphernodeRegistryAddress, owner: ownerAddress, @@ -62,8 +58,6 @@ export const deployEnclave = async (withMocks?: boolean) => { const naiveRegistryFilterAddress = await naiveRegistryFilter.getAddress(); - console.log("NaiveRegistryFilter deployed to: ", naiveRegistryFilterAddress); - const registryAddress = await enclave.ciphernodeRegistry(); if (registryAddress === ciphernodeRegistryAddress) { @@ -75,6 +69,14 @@ export const deployEnclave = async (withMocks?: boolean) => { console.log(`Enclave contract updated with registry`); } + console.log(` + Deployments: + ---------------------------------------------------------------------- + Enclave: ${enclaveAddress} + CiphernodeRegistry: ${ciphernodeRegistryAddress} + NaiveRegistryFilter: ${naiveRegistryFilterAddress} + `); + // Deploy mocks only if specified const shouldDeployMocks = process.env.DEPLOY_MOCKS === "true" || withMocks;