@inco/lightning 0.8.0-devnet-4 → 0.8.0-devnet-5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (40) hide show
  1. package/README.md +59 -1
  2. package/manifest.yaml +22 -0
  3. package/package.json +1 -1
  4. package/src/DeployUtils.sol +71 -25
  5. package/src/IncoLightning.sol +27 -7
  6. package/src/IncoVerifier.sol +18 -1
  7. package/src/Lib.alphanet.sol +390 -3
  8. package/src/Lib.demonet.sol +390 -3
  9. package/src/Lib.devnet.sol +391 -4
  10. package/src/Lib.sol +391 -4
  11. package/src/Lib.template.sol +387 -0
  12. package/src/Lib.testnet.sol +390 -3
  13. package/src/libs/incoLightning_alphanet_v0_297966649.sol +390 -3
  14. package/src/libs/incoLightning_alphanet_v1_725458969.sol +390 -3
  15. package/src/libs/incoLightning_alphanet_v2_976644394.sol +390 -3
  16. package/src/libs/incoLightning_demonet_v0_863421733.sol +390 -3
  17. package/src/libs/incoLightning_demonet_v2_467437523.sol +390 -3
  18. package/src/libs/incoLightning_devnet_v0_340846814.sol +390 -3
  19. package/src/libs/incoLightning_devnet_v1_904635675.sol +390 -3
  20. package/src/libs/incoLightning_devnet_v2_295237520.sol +390 -3
  21. package/src/libs/incoLightning_devnet_v3_976859633.sol +390 -3
  22. package/src/libs/incoLightning_devnet_v4_409204766.sol +921 -0
  23. package/src/libs/incoLightning_testnet_v0_183408998.sol +390 -3
  24. package/src/libs/incoLightning_testnet_v2_889158349.sol +390 -3
  25. package/src/lightning-parts/AccessControl/AdvancedAccessControl.sol +65 -4
  26. package/src/lightning-parts/AccessControl/BaseAccessControlList.sol +71 -5
  27. package/src/lightning-parts/DecryptionAttester.sol +16 -3
  28. package/src/lightning-parts/EncryptedInput.sol +48 -2
  29. package/src/lightning-parts/EncryptedOperations.sol +134 -1
  30. package/src/lightning-parts/Fee.sol +29 -6
  31. package/src/lightning-parts/primitives/EventCounter.sol +36 -5
  32. package/src/lightning-parts/primitives/HandleGeneration.sol +38 -6
  33. package/src/lightning-parts/primitives/HandleMetadata.sol +28 -0
  34. package/src/lightning-parts/primitives/LightningAddressGetter.sol +10 -0
  35. package/src/lightning-parts/primitives/VerifierAddressGetter.sol +10 -0
  36. package/src/lightning-parts/primitives/test/SignatureVerifier.t.sol +0 -2
  37. package/src/periphery/IncoUtils.sol +1 -0
  38. package/src/periphery/SessionVerifier.sol +35 -7
  39. package/src/test/TestFakeInfra.t.sol +536 -1
  40. package/src/version/IncoLightningConfig.sol +2 -2
@@ -10,14 +10,24 @@ import {SignatureChecker} from "@openzeppelin/contracts/utils/cryptography/Signa
10
10
  import {IBaseAccessControlList} from "./interfaces/IBaseAccessControlList.sol";
11
11
  import {LightningAddressGetter} from "../primitives/LightningAddressGetter.sol";
12
12
 
13
+ /// @title AdvancedAccessControlStorage
14
+ /// @notice Diamond storage pattern for advanced ACL session nonce tracking
15
+ /// @dev Stores per-account session nonces that allow users to invalidate all previously signed vouchers
13
16
  abstract contract AdvancedAccessControlStorage {
14
17
 
18
+ /// @notice Storage struct for advanced access control state
15
19
  struct AacStorage {
16
- mapping(address => bytes32) activeVouchersSessionNonce; // initial session nonce is 0
20
+ /// @notice Maps account addresses to their active voucher session nonce
21
+ /// @dev Vouchers signed with a different nonce are invalid. Initial nonce is bytes32(0).
22
+ mapping(address => bytes32) activeVouchersSessionNonce;
17
23
  }
18
24
 
25
+ /// @notice Storage slot location using keccak256 of a unique namespace string
19
26
  bytes32 private constant AAC_STORAGE_LOCATION = keccak256("inco.storage.AdvancedAccessControl");
20
27
 
28
+ /// @notice Retrieves the storage struct from its dedicated slot
29
+ /// @dev Uses assembly to directly access the storage slot for gas efficiency
30
+ /// @return $ Reference to the AacStorage struct
21
31
  function getAacStorage() internal pure returns (AacStorage storage $) {
22
32
  bytes32 loc = AAC_STORAGE_LOCATION;
23
33
  assembly {
@@ -27,12 +37,24 @@ abstract contract AdvancedAccessControlStorage {
27
37
 
28
38
  }
29
39
 
40
+ /// @title VoucherEip712Checker
41
+ /// @notice EIP-712 typed data signing utilities for allowance vouchers
42
+ /// @dev Provides deterministic hashing of AllowanceVoucher structs for signature verification.
43
+ /// The voucher structure allows sharers to delegate access to their encrypted data
44
+ /// with flexible verification logic defined by an external contract.
30
45
  abstract contract VoucherEip712Checker is IVoucherEip712Checker, EIP712Upgradeable {
31
46
 
47
+ /// @notice EIP-712 type hash for the AllowanceVoucher struct
48
+ /// @dev Computed once at compile time for gas efficiency
32
49
  bytes32 constant ALLOWANCE_VOUCHER_STRUCT_HASH = keccak256(
33
50
  "AllowanceVoucher(bytes32 sessionNonce,address verifyingContract,bytes4 callFunction,bytes sharerArgData)"
34
51
  );
35
52
 
53
+ /// @notice Computes the EIP-712 digest for an allowance voucher
54
+ /// @dev The digest can be signed by the sharer to authorize access.
55
+ /// Uses EIP-712 structured data hashing with domain separator.
56
+ /// @param voucher The voucher to compute the digest for
57
+ /// @return The EIP-712 typed data hash ready for signing
36
58
  function allowanceVoucherDigest(AllowanceVoucher memory voucher) public view returns (bytes32) {
37
59
  return _hashTypedDataV4(
38
60
  keccak256(
@@ -49,6 +71,21 @@ abstract contract VoucherEip712Checker is IVoucherEip712Checker, EIP712Upgradeab
49
71
 
50
72
  }
51
73
 
74
+ /// @title AdvancedAccessControl
75
+ /// @notice Voucher-based access delegation for encrypted data sharing
76
+ /// @dev Enables flexible access control patterns where data owners can sign vouchers
77
+ /// authorizing others to access their encrypted data under specific conditions.
78
+ ///
79
+ /// Voucher flow:
80
+ /// 1. Sharer signs an AllowanceVoucher specifying conditions (via verifyingContract)
81
+ /// 2. Requester presents the voucher with proof when requesting access
82
+ /// 3. This contract verifies the signature and calls the verifyingContract
83
+ /// 4. Access is granted if the verifyingContract returns ALLOWANCE_GRANTED_MAGIC_VALUE
84
+ ///
85
+ /// Security features:
86
+ /// - Session nonces allow sharers to invalidate all previous vouchers
87
+ /// - EIP-712 typed data ensures vouchers are human-readable when signing
88
+ /// - Supports both EOA and smart contract signatures (ERC-1271)
52
89
  abstract contract AdvancedAccessControl is
53
90
  IAdvancedAccessControl,
54
91
  AdvancedAccessControlStorage,
@@ -58,11 +95,28 @@ abstract contract AdvancedAccessControl is
58
95
 
59
96
  using SignatureChecker for address;
60
97
 
98
+ /// @notice Thrown when a voucher signature is invalid for the claimed signer
99
+ /// @param signer The address that allegedly signed the voucher
100
+ /// @param digest The EIP-712 digest that should have been signed
101
+ /// @param signature The invalid signature provided
61
102
  error InvalidVoucherSignature(address signer, bytes32 digest, bytes signature);
103
+
104
+ /// @notice Thrown when a voucher's session nonce doesn't match the sharer's active nonce
105
+ /// @param providedSessionNonce The nonce in the voucher
106
+ /// @param activeSessionNonce The sharer's current active session nonce
62
107
  error InvalidVoucherSessionNonce(bytes32 providedSessionNonce, bytes32 activeSessionNonce);
63
108
 
64
- /// @dev meant to for simulation, can't be a view function as it calls other contracts
65
- /// @dev returns true if the account is allowed to access the handle, false or reverts otherwise
109
+ /// @notice Checks if an account is allowed to access a handle using a signed voucher proof
110
+ /// @dev Intended for simulation/off-chain calls. Not a view function as it calls external contracts.
111
+ /// Verification steps:
112
+ /// 1. Verify the sharer has access to the handle
113
+ /// 2. Verify the voucher signature is valid
114
+ /// 3. Verify the session nonce is current
115
+ /// 4. Call the verifyingContract to check access conditions
116
+ /// @param handle The encrypted value handle to check access for
117
+ /// @param account The account requesting access
118
+ /// @param proof The allowance proof containing voucher, signature, and requester data
119
+ /// @return True if access is allowed, false or reverts otherwise
66
120
  function isAllowedWithProof(bytes32 handle, address account, AllowanceProof memory proof) public returns (bool) {
67
121
  require(
68
122
  IBaseAccessControlList(incoLightningAddress).isAllowed(handle, proof.sharer),
@@ -87,11 +141,18 @@ abstract contract AdvancedAccessControl is
87
141
  return (success && result.length >= 32 && abi.decode(result, (bytes32)) == ALLOWANCE_GRANTED_MAGIC_VALUE);
88
142
  }
89
143
 
144
+ /// @notice Returns the current active voucher session nonce for an account
145
+ /// @dev Vouchers must include this nonce to be valid. Initial value is bytes32(0).
146
+ /// @param account The account to check the session nonce for
147
+ /// @return The current active session nonce
90
148
  function getActiveVouchersSessionNonce(address account) public view returns (bytes32) {
91
149
  return getAacStorage().activeVouchersSessionNonce[account];
92
150
  }
93
151
 
94
- /// @notice invalidates all previously signed vouchers
152
+ /// @notice Invalidates all previously signed vouchers by updating the session nonce
153
+ /// @dev Generates a new random nonce using the caller's address and block.prevrandao.
154
+ /// Any vouchers signed with the previous nonce become invalid immediately.
155
+ /// Call this if you suspect voucher compromise or want to revoke all delegations.
95
156
  function updateActiveVouchersSessionNonce() external {
96
157
  getAacStorage().activeVouchersSessionNonce[msg.sender] =
97
158
  keccak256(abi.encodePacked(msg.sender, block.prevrandao));
@@ -7,15 +7,22 @@ import {EventCounter} from "../primitives/EventCounter.sol";
7
7
  import {VerifierAddressGetter} from "../primitives/VerifierAddressGetter.sol";
8
8
  import {AllowanceProof} from "../AccessControl/AdvancedAccessControl.types.sol";
9
9
 
10
+ /// @title AccessControlListStorage
11
+ /// @notice Storage layout for the Access Control List (ACL).
12
+ /// @dev Uses ERC-7201 namespaced storage pattern to avoid storage collisions.
10
13
  contract AccessControlListStorage {
11
14
 
15
+ /// @dev Storage struct for ACL state.
12
16
  struct AclStorage {
17
+ /// @dev Maps (handle, account) pairs to persistent access permissions.
13
18
  mapping(bytes32 handle => mapping(address account => bool isAllowed)) persistedAllowedPairs;
19
+ /// @dev Maps handles to whether they are revealed (publicly accessible).
14
20
  mapping(bytes32 handle => bool isAllowed) persistedAllowedForDecryption;
15
21
  }
16
22
 
17
23
  bytes32 private constant ACL_STORAGE_LOCATION = keccak256("inco.storage.ACL");
18
24
 
25
+ /// @dev Returns a pointer to the ACL storage struct.
19
26
  function getAclStorage() internal pure returns (AclStorage storage $) {
20
27
  bytes32 loc = ACL_STORAGE_LOCATION;
21
28
  assembly {
@@ -25,6 +32,16 @@ contract AccessControlListStorage {
25
32
 
26
33
  }
27
34
 
35
+ /// @title BaseAccessControlList
36
+ /// @notice Manages access permissions for encrypted handles.
37
+ /// @dev Implements a two-tier permission system:
38
+ /// - **Persistent permissions**: Stored permanently, survive across transactions.
39
+ /// - **Transient permissions**: Stored in transient storage (EIP-1153), cleared at end of transaction.
40
+ ///
41
+ /// Access is granted if any of these conditions are true:
42
+ /// 1. Transient permission exists for (handle, account)
43
+ /// 2. Persistent permission exists for (handle, account)
44
+ /// 3. The handle has been revealed (public access)
28
45
  abstract contract BaseAccessControlList is
29
46
  IBaseAccessControlList,
30
47
  AccessControlListStorage,
@@ -32,19 +49,36 @@ abstract contract BaseAccessControlList is
32
49
  EventCounter
33
50
  {
34
51
 
52
+ /// @notice Thrown when proof verification fails during handle claiming.
53
+ /// @param verifyingContract The contract that was supposed to verify.
54
+ /// @param callFunction The function selector that was called.
55
+ /// @param argData The argument data that failed verification.
35
56
  error ProofVerificationFailed(address verifyingContract, bytes4 callFunction, bytes argData);
36
57
 
58
+ /// @notice Emitted when persistent access is granted to an account for a handle.
59
+ /// @param handle The encrypted handle.
60
+ /// @param account The account granted access.
61
+ /// @param eventId The unique event ID.
37
62
  event Allow(bytes32 handle, address account, uint256 eventId);
38
63
 
64
+ /// @notice Emitted when a handle is revealed for public access.
65
+ /// @param handle The encrypted handle that was revealed.
66
+ /// @param eventId The unique event ID.
39
67
  event Reveal(bytes32 handle, uint256 eventId);
40
68
 
41
- /// @dev persistent
69
+ /// @notice Grants persistent access to an account for an encrypted handle.
70
+ /// @dev Caller must already have access to the handle. This permission survives across transactions.
71
+ /// @param handle The encrypted handle to grant access to.
72
+ /// @param account The account to grant access to.
42
73
  function allow(bytes32 handle, address account) public {
43
74
  require(isAllowed(handle, msg.sender), SenderNotAllowedForHandle(handle, msg.sender));
44
75
  allowInternal(handle, account);
45
76
  }
46
77
 
47
- /// @dev Permanently allows public decryption/reencryption access to anyone for the given handle.
78
+ /// @notice Reveals a handle, granting permanent public access to anyone.
79
+ /// @dev Once revealed, the encrypted value can be decrypted by anyone. This is irreversible.
80
+ /// Caller must have access to the handle.
81
+ /// @param handle The encrypted handle to reveal.
48
82
  function reveal(bytes32 handle) public {
49
83
  require(isAllowed(handle, msg.sender), SenderNotAllowedForHandle(handle, msg.sender));
50
84
  AclStorage storage $ = getAclStorage();
@@ -54,7 +88,9 @@ abstract contract BaseAccessControlList is
54
88
  setDigest(abi.encodePacked(EOps.Reveal, handle, id));
55
89
  }
56
90
 
57
- /// @dev persistent
91
+ /// @dev Internal function to grant persistent access without ownership check.
92
+ /// @param handle The encrypted handle to grant access to.
93
+ /// @param account The account to grant access to.
58
94
  function allowInternal(bytes32 handle, address account) internal {
59
95
  AclStorage storage $ = getAclStorage();
60
96
  $.persistedAllowedPairs[handle][account] = true;
@@ -63,13 +99,20 @@ abstract contract BaseAccessControlList is
63
99
  setDigest(abi.encodePacked(EOps.Allow, handle, account, id));
64
100
  }
65
101
 
66
- // todo current transient allowance is unsafe, make storage account bound + how to clean between UserOps
102
+ /// @notice Grants transient access to an account for an encrypted handle.
103
+ /// @dev Transient permissions are cleared at the end of the transaction (EIP-1153).
104
+ /// Caller must have access to the handle.
105
+ /// @param handle The encrypted handle to grant access to.
106
+ /// @param account The account to grant access to.
67
107
  function allowTransient(bytes32 handle, address account) public {
68
108
  require(isAllowed(handle, msg.sender), SenderNotAllowedForHandle(handle, msg.sender));
69
109
  allowTransientInternal(handle, account);
70
110
  }
71
111
 
72
- /// @dev no ownership check is performed
112
+ /// @dev Internal function to grant transient access without ownership check.
113
+ /// Uses assembly to store in transient storage and track keys for cleanup.
114
+ /// @param handle The encrypted handle to grant access to.
115
+ /// @param account The account to grant access to.
73
116
  function allowTransientInternal(bytes32 handle, address account) internal {
74
117
  bytes32 key = keccak256(abi.encodePacked(handle, account));
75
118
  assembly {
@@ -81,6 +124,10 @@ abstract contract BaseAccessControlList is
81
124
  }
82
125
  }
83
126
 
127
+ /// @notice Checks if transient access exists for a handle-account pair.
128
+ /// @param handle The encrypted handle to check.
129
+ /// @param account The account to check access for.
130
+ /// @return True if transient access is granted.
84
131
  function allowedTransient(bytes32 handle, address account) public view returns (bool) {
85
132
  bool isAllowedTransient;
86
133
  bytes32 key = keccak256(abi.encodePacked(handle, account));
@@ -90,6 +137,9 @@ abstract contract BaseAccessControlList is
90
137
  return isAllowedTransient;
91
138
  }
92
139
 
140
+ /// @notice Clears all transient storage entries.
141
+ /// @dev Should be called at the end of a transaction to reset transient permissions.
142
+ /// Iterates through all stored keys and clears them.
93
143
  function cleanTransientStorage() external {
94
144
  assembly {
95
145
  let length := tload(0)
@@ -103,6 +153,10 @@ abstract contract BaseAccessControlList is
103
153
  }
104
154
  }
105
155
 
156
+ /// @notice Claims access to a handle using a signed allowance proof.
157
+ /// @dev Verifies the proof via IncoVerifier and grants persistent access if valid.
158
+ /// @param handle The encrypted handle to claim access to.
159
+ /// @param proof The signed allowance proof from an authorized sharer.
106
160
  function claimHandle(bytes32 handle, AllowanceProof memory proof) public {
107
161
  require(
108
162
  incoVerifier.isAllowedWithProof(handle, msg.sender, proof),
@@ -113,15 +167,27 @@ abstract contract BaseAccessControlList is
113
167
  allowInternal(handle, msg.sender);
114
168
  }
115
169
 
170
+ /// @notice Checks if persistent access exists for a handle-account pair.
171
+ /// @param handle The encrypted handle to check.
172
+ /// @param account The account to check access for.
173
+ /// @return True if persistent access is granted.
116
174
  function persistAllowed(bytes32 handle, address account) public view returns (bool) {
117
175
  AclStorage storage $ = getAclStorage();
118
176
  return $.persistedAllowedPairs[handle][account];
119
177
  }
120
178
 
179
+ /// @notice Checks if an account has access to an encrypted handle.
180
+ /// @dev Returns true if any of: transient access, persistent access, or handle is revealed.
181
+ /// @param handle The encrypted handle to check.
182
+ /// @param account The account to check access for.
183
+ /// @return True if the account has access to the handle.
121
184
  function isAllowed(bytes32 handle, address account) public view returns (bool) {
122
185
  return allowedTransient(handle, account) || persistAllowed(handle, account) || isRevealed(handle);
123
186
  }
124
187
 
188
+ /// @notice Checks if a handle has been revealed for public access.
189
+ /// @param handle The encrypted handle to check.
190
+ /// @return True if the handle has been revealed.
125
191
  function isRevealed(bytes32 handle) public view returns (bool) {
126
192
  AclStorage storage $ = getAclStorage();
127
193
  return $.persistedAllowedForDecryption[handle];
@@ -6,20 +6,33 @@ import {EIP712Upgradeable} from "@openzeppelin/contracts-upgradeable/utils/crypt
6
6
  import {SignatureVerifier} from "./primitives/SignatureVerifier.sol";
7
7
  import {IDecryptionAttester} from "./interfaces/IDecryptionAttester.sol";
8
8
 
9
- // todo pre charging transient decrypted values leads to a superior DevX
10
-
11
- // todo #1032 add DecryptionAttester to IncoVerifier, will include signature verifier as well and fix #874
9
+ /// @title DecryptionAttester
10
+ /// @notice Verifies decryption attestations signed by covalidators.
11
+ /// @dev When a user requests decryption of an encrypted handle, the covalidator decrypts
12
+ /// the value and signs an attestation. This contract verifies that attestation using EIP-712
13
+ /// typed data signatures. The attestation binds a handle to its decrypted value, allowing
14
+ /// on-chain verification that a decryption was performed correctly by authorized covalidators.
12
15
  abstract contract DecryptionAttester is IDecryptionAttester, SignatureVerifier, EIP712Upgradeable {
13
16
 
17
+ /// @dev EIP-712 type hash for DecryptionAttestation struct.
14
18
  bytes32 constant DECRYPTION_ATTESTATION_STRUCT_HASH =
15
19
  keccak256("DecryptionAttestation(bytes32 handle,bytes32 value)");
16
20
 
21
+ /// @notice Computes the EIP-712 digest for a decryption attestation.
22
+ /// @dev Used to verify signatures from covalidators attesting to a decryption result.
23
+ /// @param decryption The decryption attestation containing the handle and decrypted value.
24
+ /// @return The EIP-712 typed data hash that should be signed by covalidators.
17
25
  function decryptionAttestationDigest(DecryptionAttestation memory decryption) public view returns (bytes32) {
18
26
  return _hashTypedDataV4(
19
27
  keccak256(abi.encode(DECRYPTION_ATTESTATION_STRUCT_HASH, decryption.handle, decryption.value))
20
28
  );
21
29
  }
22
30
 
31
+ /// @notice Validates a decryption attestation against covalidator signatures.
32
+ /// @dev Verifies that the attestation was signed by the required threshold of covalidators.
33
+ /// @param decryption The decryption attestation to validate.
34
+ /// @param signatures Array of signatures from covalidators.
35
+ /// @return True if the attestation has valid signatures from the required covalidators.
23
36
  function isValidDecryptionAttestation(DecryptionAttestation memory decryption, bytes[] memory signatures)
24
37
  public
25
38
  view
@@ -8,8 +8,14 @@ import {IEncryptedInput} from "./interfaces/IEncryptedInput.sol";
8
8
  import {HandleAlreadyExists} from "../Errors.sol";
9
9
  import {Fee} from "./Fee.sol";
10
10
 
11
- // This error ordinarily indicates an unintentional mismatch between the client-side context and the ambient on-chain
12
- // context
11
+ /// @notice Thrown when the handle computed on-chain doesn't match the handle prepended to the input.
12
+ /// @dev This typically indicates a mismatch between client-side encryption context and on-chain context.
13
+ /// @param externalHandle The handle prepended to the input by the client.
14
+ /// @param computedHandle The handle computed on-chain from the ciphertext and context.
15
+ /// @param chainId The chain ID used in handle computation.
16
+ /// @param aclAddress The ACL contract address used in handle computation.
17
+ /// @param userAddress The user address used in handle computation.
18
+ /// @param contractAddress The contract address used in handle computation.
13
19
  error ExternalHandleDoesNotMatchComputedHandle(
14
20
  bytes32 externalHandle,
15
21
  bytes32 computedHandle,
@@ -21,8 +27,19 @@ error ExternalHandleDoesNotMatchComputedHandle(
21
27
  int32 version
22
28
  );
23
29
 
30
+ /// @title EncryptedInput
31
+ /// @notice Handles the submission of client-encrypted values to create on-chain encrypted handles.
32
+ /// @dev Users encrypt values client-side and submit them with a prepended handle as a checksum.
33
+ /// The contract verifies the handle matches the on-chain computation to ensure context consistency.
34
+ /// This is a paid operation - users must send ETH to cover processing costs.
24
35
  abstract contract EncryptedInput is IEncryptedInput, BaseAccessControlList, HandleGeneration, Fee {
25
36
 
37
+ /// @notice Emitted when a new encrypted input is submitted.
38
+ /// @param result The generated handle for the encrypted value.
39
+ /// @param contractAddress The contract that submitted the input.
40
+ /// @param user The user who encrypted the value.
41
+ /// @param ciphertext The encrypted data (without the prepended handle).
42
+ /// @param eventId The unique event ID for ordering.
26
43
  event NewInput(
27
44
  bytes32 indexed result,
28
45
  address indexed contractAddress,
@@ -32,18 +49,37 @@ abstract contract EncryptedInput is IEncryptedInput, BaseAccessControlList, Hand
32
49
  uint256 eventId
33
50
  );
34
51
 
52
+ /// @notice Submits a client-encrypted uint256 value to create an encrypted handle.
53
+ /// @dev This is a paid operation. The input must contain a prepended handle for verification.
54
+ /// @param input The encrypted input with prepended handle checksum.
55
+ /// @param user The user address that encrypted the value.
56
+ /// @return newValue The encrypted uint256 handle.
35
57
  function newEuint256(bytes calldata input, address user) external payable returns (euint256 newValue) {
36
58
  return euint256.wrap(newInput(input, user, ETypes.Uint256));
37
59
  }
38
60
 
61
+ /// @notice Submits a client-encrypted boolean value to create an encrypted handle.
62
+ /// @dev This is a paid operation. The input must contain a prepended handle for verification.
63
+ /// @param input The encrypted input with prepended handle checksum.
64
+ /// @param user The user address that encrypted the value.
65
+ /// @return newValue The encrypted boolean handle.
39
66
  function newEbool(bytes calldata input, address user) external payable returns (ebool newValue) {
40
67
  return ebool.wrap(newInput(input, user, ETypes.Bool));
41
68
  }
42
69
 
70
+ /// @notice Submits a client-encrypted address value to create an encrypted handle.
71
+ /// @dev This is a paid operation. The input must contain a prepended handle for verification.
72
+ /// @param input The encrypted input with prepended handle checksum.
73
+ /// @param user The user address that encrypted the value.
74
+ /// @return newValue The encrypted address handle.
43
75
  function newEaddress(bytes calldata input, address user) external payable returns (eaddress newValue) {
44
76
  return eaddress.wrap(newInput(input, user, ETypes.AddressOrUint160OrBytes20));
45
77
  }
46
78
 
79
+ /// @dev Internal function to process encrypted input with fee payment.
80
+ /// @param user The user address that encrypted the value.
81
+ /// @param inputType The type of encrypted value.
82
+ /// @return newHandle The generated handle.
47
83
  function newInput(bytes calldata input, address user, ETypes inputType)
48
84
  internal
49
85
  paying
@@ -52,6 +88,11 @@ abstract contract EncryptedInput is IEncryptedInput, BaseAccessControlList, Hand
52
88
  newHandle = _newInput(input, user, inputType);
53
89
  }
54
90
 
91
+ /// @dev Internal function to process encrypted input without fee payment.
92
+ /// Used for internal operations that don't require user payment.
93
+ /// @param user The user address that encrypted the value.
94
+ /// @param inputType The type of encrypted value.
95
+ /// @return newHandle The generated handle.
55
96
  function newInputNotPaying(bytes calldata input, address user, ETypes inputType)
56
97
  internal
57
98
  returns (bytes32 newHandle)
@@ -60,8 +101,13 @@ abstract contract EncryptedInput is IEncryptedInput, BaseAccessControlList, Hand
60
101
  }
61
102
 
62
103
  /// @notice Creates a new input with a prepended handle as a checksum.
104
+ /// @dev Verifies the external handle matches the computed handle, ensures the handle
105
+ /// doesn't already exist, emits the NewInput event, and grants access to the user
106
+ /// and calling contract.
63
107
  /// @param input The input that contains the handle prepended to the ciphertext.
64
108
  /// @param user The user address associated with the input.
109
+ /// @param inputType The type of encrypted value being created.
110
+ /// @return handle The generated handle for the encrypted value.
65
111
  function _newInput(bytes calldata input, address user, ETypes inputType) private returns (bytes32 handle) {
66
112
  // Since there is no sensible way to handle abi.decode errors (https://github.com/argotorg/solidity/issues/10381)
67
113
  // at least fail early on a conservative minimum length