# OffBlocksSmartWalletFactory.sol

### Contract Overview

#### Inherits:

* `OwnableUpgradeable` from OpenZeppelin
* Also imports `IERC20` interface from OpenZeppelin which is used in the contract, as well as `OffBlocksSmartWallet` contract which is a contract factory deploys in the `deploySmartWallet` method

**Author:** OffBlocks Team

**Description:** This contract serves as a factory for creating and managing OffBlocks smart wallets, which are deployed on EVM chains supporting ERC-4337. It features functionality for creating new smart wallets, handling withdrawals with a delay mechanism, and maintaining a registry of smart wallets to verify their authenticity.

## Initializer

```solidity
function initialize(address _owner, uint256 _withdrawalDelay) external initializer
```

* **Description**: Sets up the smart wallet factory with an owner and a predefined withdrawal delay.
* **Inputs**:
  * `_owner`: Address of the factory contract owner.
  * `_withdrawalDelay`: Time delay (in seconds) required between withdrawal operations from smart wallets.
* **Notes**: This function initializes the contract and can only be called once during the contract's lifetime.

### Functions

**deploySmartWallet**

```solidity
function deploySmartWallet(address _walletOwner, address _escrow, address _smartWalletFactory, uint256 _salt) external onlyOwner
```

* **Description**: Deploys a new OffBlocks smart wallet with a unique owner, linked to an escrow contract.
* **Inputs**:
  * `_walletOwner`: Address that will own the smart wallet.
  * `_escrow`: Escrow contract address associated with the smart wallet.
  * `_smartWalletFactory`: This factory contract address.
  * `_salt`: A nonce to ensure the uniqueness of the smart wallet deployment.
* **Modifiers**: `onlyOwner`
* **Emits**: `SmartWalletCreated` event upon successful creation.

**updateWithdrawalDelay**

```solidity
function updateWithdrawalDelay(uint256 _newDelay) external onlyOwner
```

* **Description**: Updates the withdrawal delay for all smart wallets.
* **Inputs**:
  * `_newDelay`: New withdrawal delay in seconds.
* **Modifiers**: `onlyOwner`
* **Emits**: `WithdrawalDelayChanged` event indicating the new delay.

**batchRegisterSmartWallets**

```solidity
function batchRegisterSmartWallets(address[] calldata _walletOwners, address[] calldata _smartWallets) external onlyOwner
```

* **Description**: Registers multiple third-party smart wallets to their respective owners.
* **Inputs**:
  * `_walletOwners`: An array of addresses owning the smart wallets.
  * `_smartWallets`: An array of third-party smart wallet addresses to be registered.
* **Modifiers**: `onlyOwner`
* **Emits**: `ThirdPartySmartWalletRegistered` event for each smart wallet registered.

**batchUnregisterSmartWallets**

```solidity
function batchUnregisterSmartWallets(address[] calldata _walletOwners, address[] calldata _smartWallets) external onlyOwner
```

* **Description**: Unregisters multiple third-party smart wallets from their respective owners.
* **Inputs**:
  * `_walletOwners`: An array of addresses owning the smart wallets.
  * `_smartWallets`: An array of third-party smart wallet addresses to be unregistered.
* **Modifiers**: `onlyOwner`
* **Emits**: `ThirdPartySmartWalletUnregistered` event for each smart wallet unregistered.

**rescueTokens**

```solidity
function rescueTokens(address _token) external onlyOwner
```

* **Description**: Allows the owner to rescue ERC20 tokens mistakenly sent to the contract.
* **Inputs**:
  * `_token`: The ERC20 token address to be rescued.
* **Modifiers**: `onlyOwner`
* **Emits**: `RescueTokens` event indicating the successful rescue operation.

**getWithdrawalDelay**

```solidity
function getWithdrawalDelay() external view returns (uint256)
```

* **Description**: Retrieves the current withdrawal delay setting.
* **Outputs**:
  * `uint256`: The withdrawal delay in seconds.

**getIsSmartWallet**

```solidity
function getIsSmartWallet(address _wallet) external view returns (bool)
```

* **Description**: Checks if a given address is registered as an OffBlocks smart wallet.
* **Inputs**:
  * `_wallet`: The address to check.
* **Outputs**:
  * `bool`: True if the address is a registered smart wallet, false otherwise.

**getSmartWalletsOfUser**

```solidity
function getSmartWalletsOfUser(address _walletOwner) external view returns (address[] memory)
```

* **Description**: Lists all smart wallets associated with a given owner.
* **Inputs**:
  * `_walletOwner`: Owner whose smart wallets are to be listed.
* **Outputs**:
  * `address[]`: An array of smart wallet addresses owned by the specified user.

**precomputeSmartWalletAddress**

```solidity
function precomputeSmartWalletAddress(address _walletOwner, address _escrow, address _smartWalletFactory, uint256 _salt) external view returns (address)
```

* **Description**: Precomputes the address of a smart wallet before its deployment using the provided parameters.
* **Inputs**:
  * `_walletOwner`: The intended owner of the smart wallet.
  * `_escrow`: The escrow contract address associated with the smart wallet.
  * `_smartWalletFactory`: The smart wallet factory contract address (typically this contract).
  * `_salt`: A unique nonce used to generate the smart wallet's address.
* **Outputs**:
  * `address`: The precomputed address of the smart wallet.

**registerSmartWallet**

```solidity
function registerSmartWallet(address _walletOwner, address _smartWallet) public onlyOwner
```

* **Description**: Registers a third-party smart wallet under a specific owner.
* **Inputs**:
  * `_walletOwner`: The owner of the smart wallet.
  * `_smartWallet`: The address of the third-party smart wallet to be registered.
* **Modifiers**: `onlyOwner`
* **Emits**: `ThirdPartySmartWalletRegistered` event upon successful registration.

**unregisterSmartWallet**

```solidity
function unregisterSmartWallet(address _walletOwner, address _smartWallet) public onlyOwner
```

* **Description**: Unregisters a previously registered third-party smart wallet.
* **Inputs**:
  * `_walletOwner`: The owner of the smart wallet.
  * `_smartWallet`: The address of the third-party smart wallet to be unregistered.
* **Modifiers**: `onlyOwner`
* **Emits**: `ThirdPartySmartWalletUnregistered` event upon successful unregistration.

#### Modifiers

* **onlyOwner**: Ensures that only the contract owner can invoke the function.

#### Events

Several events are defined to notify external observers of significant actions within the contract:

* `SmartWalletCreated`
* `ThirdPartySmartWalletRegistered`
* `ThirdPartySmartWalletUnregistered`
* `RescueTokens`
* `RescueETH`
* `WithdrawalDelayChanged`

#### Errors

* `DelayOutOfRange`: Triggered when the provided withdrawal delay is outside the allowed range.
* `ZeroAddress`: Indicates that an operation was attempted with the zero address, which is often invalid.
* `ZeroTokens`: Occurs when a token operation involves zero tokens, which is generally not allowed.
* `NotASmartWallet`: Asserts that an address is not recognized as a smart wallet by the factory.
* `ERC20TransferFailed`: Signals a failure in transferring ERC20 tokens.
* `ArrayLengthMismatch`: Indicates that provided arrays do not match in length, which is usually required for batch operations.

This comprehensive overview covers the essential aspects of the `OffBlocksSmartWalletFactory` contract, including its purpose, key functions, and the operational context within the Ethereum or compatible EVM blockchain ecosystem.
