```\nfunction unlock(\n    uint128 lockId,\n    address recipient, uint256 amount,\n    bytes4 lockSource, bytes4 tokenSource,\n    bytes32 tokenSourceAddress,\n    bytes calldata signature) external isActive {\n    // Create message hash and validate the signature\n    IValidator(validator).createUnlock(\n            lockId,\n            recipient,\n            amount,\n            lockSource,\n            tokenSource,\n            tokenSourceAddress,\n            signature);\n\n    // Mark lock as received\n    address tokenAddress = tokenSourceMap[tokenSource][tokenSourceAddress];\n    require(tokenAddress != address(0), "Bridge: unsupported token");\n    TokenInfo memory tokenInfo = tokenInfos[tokenAddress];\n\n    // Transform amount form system to token precision\n    uint256 amountWithTokenPrecision = fromSystemPrecision(amount, tokenInfo.precision);\n    uint256 fee = 0;\n    if (msg.sender == unlockSigner) {\n        fee = FeeOracle(feeOracle).minFee(tokenAddress);\n        require(amountWithTokenPrecision > fee, "Bridge: amount too small");\n        amountWithTokenPrecision = amountWithTokenPrecision - fee;\n    }\n\n    if (tokenInfo.tokenType == TokenType.Base) {\n        // If token is WETH - transfer ETH\n        payable(recipient).transfer(amountWithTokenPrecision);\n        if (fee > 0) {\n            payable(feeCollector).transfer(fee);\n        }\n    } else if (tokenInfo.tokenType == TokenType.Native) {\n        // If token is native - transfer the token\n        IERC20(tokenAddress).safeTransfer(recipient, amountWithTokenPrecision);\n        if (fee > 0) {\n            IERC20(tokenAddress).safeTransfer(feeCollector, fee);\n        }\n    } else if (tokenInfo.tokenType == TokenType.Wrapped) {\n        // Else token is wrapped - mint tokens to the user\n        WrappedToken(tokenAddress).mint(recipient, amountWithTokenPrecision);\n        if (fee > 0) {\n            WrappedToken(tokenAddress).mint(feeCollector, fee);\n        }\n    } else if (tokenInfo.tokenType == TokenType.WrappedV0) {\n        // Legacy wrapped token\n        IWrappedTokenV0(tokenAddress).mint(recipient, amountWithTokenPrecision);\n        if (fee > 0) {\n            IWrappedTokenV0(tokenAddress).mint(feeCollector, fee);\n        }\n    }\n\n    emit Received(recipient, tokenAddress, amountWithTokenPrecision, lockId, lockSource);\n}\n```\n