diff --git a/docs/SDK/Explanation/WalletSigs/authSig.md b/docs/SDK/Explanation/WalletSigs/authSig.md index 8184fe95..21a5a6e0 100644 --- a/docs/SDK/Explanation/WalletSigs/authSig.md +++ b/docs/SDK/Explanation/WalletSigs/authSig.md @@ -97,3 +97,62 @@ Below is the complete [**React** project](https://replit.com/@lit/Smart-Contract ## Clearing the stored AuthSig If you want to clear the authSig stored in the browser local storage, you can call the [`disconnectWeb3` method](https://js-sdk.litprotocol.com/functions/auth_browser_src.ethConnect.disconnectWeb3.html). + +## What happens to the Authsig submitted to the Lit nodes? + +When you submit the `authSig` for retrieving the `symmetricKey` using the function `getEncryptionKey` the nodes verify the `authSig` based on the `accessControlConditions` passed along with it: + +### accessControlConditions + +1. We extract the Ethereum authSig from the passed `authSig` argument since it may contain multiple authSigs. +2. If its a non EIP-1271 authSig: + 1. We verify whether the signature for the `authSig.signedMessage` was produced by `authSig.address`. + 2. If the `authSig.signedMessage` starts with "I am creating an account to use" then check that it contains a timestamp. + 3. Otherwise, we parse it as a SIWE message. We convert the `authSig.sig` into a fixed length of bytes & validate its time constraints. This returns a compressed pubkey. Finally, the authSig is valid if the `authSig.address` equals the keccak256 hash of the pubkey. +3. If its an EIP-1271 authSig: + 1. We get the corresponding web3 provider RPC for the passed chain argument. + 2. Make an EIP-1559 transaction to the `authSig.address` along with the encoded `authSig.signedMessage` & `authSig.sig` as the data. + 3. And return the result of `isValidSignature` function as explained in the above section. +4. Finally, we check whether the result of 2/3 satisfies the given `accessControlConditions` argument. We do this by recursively making RPC chain calls for each condition and comparing their return value against the `returnValueTest.value`. + 1. Eg: Querying the `accessControlConditions.chain` for the ERC721 owner & comparing the result against the `returnValueTest.value` which may `:userAddress` or a specific wallet address. +5. We then return the combined results of all these comparision as per the accessControlConditions' boolean logic. + +### evmContractConditions + +1. We extract & validate the Ethereum authSig from the passed `authSig` argument just as above (1 - 3). +2. Match the number of parameters of the function's abi with the input parameters. +3. Substitute specials parameters with their actual values. Eg: `:userAddress` with the actual user's address. +4. Tokenize the input parameters & query the given `address` on the provided `chain`. +5. Parse the returned value against the `returnValueTest` object & return if its matched. + +### solRpcConditions + +1. We extract the Solana authSig from the passed `authSig` argument since it may contain multiple authSigs. +2. Get the ED-25519 public key from the `authSig.address` & use it to verify `authSig.sig` on `authSig.message`. +3. For each condition, first substitute the special params with their actual values & check if PDA is needed. +4. If so, we extract the program address from the `pdaParams` & use it to find a valid PDA and the corresponding bump seed. +5. We then make a Solana RPC call to `getAccountInfo` & parse its response using the `offset` & `fields` values provided in `pdaInterface`. We also ensure that the `pdaInterface.fields` contain the provided `pdaKey`. +6. Finally, we make another Solana RPC call for the given `method` & compare its result with the `returnValueTest.value`. + +### unifiedAccessControlCondition + +1. We start by extracting all the authSig items from the provided `authSig`. At least one of the following should be present: + 1. Ethereum + 2. Solana + 3. Cosmos + 4. Juno + 5. Kyve + 6. Cheqd +2. If algo is specified then it should only be be ED-25518. +3. Based on the provided `chain` we verify the above authSig items. + 1. Solana: As described in points [1 - 2](#solRpcConditions) + 2. Ethereum: As described in points [1 - 3](#accessControlConditions) + 3. Else for the chains- "cosmos", "kyve", "cheqd" & "juno" we validate the Cosmos authSig as follows: + 1. We start by extracting the `sig` & `signedMessage` from the given `authSig`. + 2. And check for all 4 recovery ids for Cosmos since it chops off the last byte of the V param in `sig`. + 3. Recover the `pubKey` from the above extracted `sig`, `signedMessage` & `recoveryId` (one from the above). + 4. We derive the Cosmos address by first taking the SHA256 hash of the `pubKey` & then taking the ripemd160 hash of it. Prefixing "cosmos" & followed by its bech32 encoding. + 5. Finally, return true if the `authSig.address` matches the above derived address. +4. Then for each control conditions we check whether the `authSig` satisfies the provided condition. + 1. For example, if the `authSig` corresponds to Ethereum then we validate the condition as explained in the [evmContractConditions](#evmContractConditions) section. Similarly for Solana as well. + 2. For Cosmos, we start by substituting the special params by their actual values, eg: `:userAddress`. Then call the Cosmos RPC endpoint & compare it result with the `returnValueTest.value`. diff --git a/docs/resources/supportedChains.md b/docs/resources/supportedChains.md index 8d48e8c6..4685e123 100644 --- a/docs/resources/supportedChains.md +++ b/docs/resources/supportedChains.md @@ -38,6 +38,7 @@ Don't see a blockchain you want? Fill out this form for EVM chains and we'll ad - hyperspace - scrollAlphaTestnet - zksync +- litprotocol - solana - solanaDevnet - solanaTestnet @@ -45,7 +46,8 @@ Don't see a blockchain you want? Fill out this form for EVM chains and we'll ad - kyve - evmosCosmos - evmosCosmosTestnet -- cheqd +- cheqdMainnet +- cheqdTestnet - juno diff --git a/package.json b/package.json index 365cfb26..e4994938 100644 --- a/package.json +++ b/package.json @@ -21,7 +21,7 @@ "@docusaurus/core": "2.1.0", "@docusaurus/plugin-google-analytics": "^2.1.0", "@docusaurus/preset-classic": "2.1.0", - "@lit-protocol/constants": "^2.1.135", + "@lit-protocol/constants": "^2.1.161", "@mdx-js/react": "^1.6.21", "@svgr/webpack": "^5.5.0", "clsx": "^1.1.1", diff --git a/yarn.lock b/yarn.lock index 32a7fdef..05bd0417 100644 --- a/yarn.lock +++ b/yarn.lock @@ -1681,18 +1681,18 @@ resolved "https://registry.npmjs.org/@leichtgewicht/ip-codec/-/ip-codec-2.0.4.tgz" integrity sha512-Hcv+nVC0kZnQ3tD9GVu5xSMR4VVYOteQIr/hwFPVEvPdlXqgGEuRjiheChHgdM+JyqdgNcmzZOX/tnl0JOiI7A== -"@lit-protocol/constants@^2.1.135": - version "2.1.135" - resolved "https://registry.yarnpkg.com/@lit-protocol/constants/-/constants-2.1.135.tgz#01b11c803500fd94a785dcf3ab12a9e8bb3bd6a8" - integrity sha512-6kHBR+e4l46gHIG2actqDpItOybKF+sNdqsZoXfghF1YdSbO/s/V2ZdCZkpfaRS0gwLShlNNt3rBuit3551bEA== +"@lit-protocol/constants@^2.1.161": + version "2.1.161" + resolved "https://registry.yarnpkg.com/@lit-protocol/constants/-/constants-2.1.161.tgz#d25b55199e7f624f7e762cd78e59a207c8510335" + integrity sha512-91Rs01/BmRdi7YYmwqkaqI7TYOxhldpLIf5nLBaAQNZloijdF073KbXa9dFZtVbTo3c8fG5O6ts6DOQLK7mSKA== dependencies: - "@lit-protocol/types" "2.1.135" + "@lit-protocol/types" "2.1.161" tslib "^2.3.0" -"@lit-protocol/types@2.1.135": - version "2.1.135" - resolved "https://registry.yarnpkg.com/@lit-protocol/types/-/types-2.1.135.tgz#5506ec024a0388c30904a57ea0805e9b030fcea7" - integrity sha512-n1XMVU+N4PuLuDamKmC147dzSfxq56yydzwqr59siApd81AcVbgzIFX4LjShNpm/+uslz3MqT1MHZ7a8ECNFJQ== +"@lit-protocol/types@2.1.161": + version "2.1.161" + resolved "https://registry.yarnpkg.com/@lit-protocol/types/-/types-2.1.161.tgz#ef700a74950f62f7b5077cdd0017d096470e6d31" + integrity sha512-d/PGjmuREERHghcxGOnq4SA0ivX8e3tta7eXEKKV7FfsUXW6fNsSfwaDRKUK3FtlhaRvKtdlatrrZP4emG1WSA== "@mdx-js/mdx@^1.6.22": version "1.6.22"