CVE-2021-41264: Improper Initialization (CWE-665)
value: OpenZeppelin Contracts is a library for smart contract development. In affected versions upgradeable contracts using `UUPSUpgradeable` may be vulnerable to an attack affecting uninitialized implementation contracts. A fix is included in version 4.3.2 of `@openzeppelin/contracts` and `@openzeppelin/contracts-upgradeable`. For users unable to upgrade; initialize implementation contracts using `UUPSUpgradeable` by invoking the initializer function (usually called `initialize`). An example is provided [in the forum](https://forum.openzeppelin.com/t/security-advisory-initialize-uups-implementation-contracts/15301).
CWE description: The product does not initialize or incorrectly initializes a resource, which might leave the resource in an unexpected state when it is accessed or used.
CVSS v3 base score: 9.8
Published: 2021-11-12T18:15Z
Repository: https://github.com/OpenZeppelin/openzeppelin-contracts
Language: Other
Files changed: CHANGELOG.md, contracts/proxy/utils/UUPSUpgradeable.sol
Commit date: 2021-09-14 18:06:00 -0300
Commit message: Restrict upgrade to proxy context in UUPSUpgradeable

Co-authored-by: Francisco Giordano <frangio.1@gmail.com>
(cherry picked from commit 6241995ad323952e38f8d405103ed994a2dcde8e)

Diff: diff --git a/CHANGELOG.md b/CHANGELOG.md
index a6976a94..7fa6e4ad 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,7 +1,11 @@
 # Changelog
 
+## 4.3.2
+
+ * `UUPSUpgradeable`: Add modifiers to prevent `upgradeTo` and `upgradeToAndCall` being executed on any contract that is not the active ERC1967 proxy. This prevents these functions being called on implementation contracts or minimal ERC1167 clones, in particular.
+
 ## 4.3.1 (2021-08-26)
 
  * `TimelockController`: Add additional isOperationReady check.
 
 ## 4.3.0 (2021-08-17)
diff --git a/contracts/proxy/utils/UUPSUpgradeable.sol b/contracts/proxy/utils/UUPSUpgradeable.sol
index eeb52896..a88b2c23 100644
--- a/contracts/proxy/utils/UUPSUpgradeable.sol
+++ b/contracts/proxy/utils/UUPSUpgradeable.sol
@@ -15,31 +15,47 @@ import "../ERC1967/ERC1967Upgrade.sol";
  * The {_authorizeUpgrade} function must be overridden to include access restriction to the upgrade mechanism.
  *
  * _Available since v4.1._
  */
 abstract contract UUPSUpgradeable is ERC1967Upgrade {
+    /// @custom:oz-upgrades-unsafe-allow state-variable-immutable state-variable-assignment
+    address private immutable __self = address(this);
+
+    /**
+     * @dev Check that the execution is being performed through a delegatecall call and that the execution context is
+     * a proxy contract with an implementation (as defined in ERC1967) pointing to self. This should only be the case
+     * for UUPS and transparent proxies that are using the current contract as their implementation. Execution of a
+     * function through ERC1167 minimal proxies (clones) would not normally pass this test, but is not guaranteed to
+     * fail.
+     */
+    modifier onlyProxy() {
+        require(address(this) != __self, "Function must be called through delegatecall");
+        require(_getImplementation() == __self, "Function must be called through active proxy");
+        _;
+    }
+
     /**
      * @dev Upgrade the implementation of the proxy to `newImplementation`.
      *
      * Calls {_authorizeUpgrade}.
      *
      * Emits an {Upgraded} event.
      */
-    function upgradeTo(address newImplementation) external virtual {
+    function upgradeTo(address newImplementation) external virtual onlyProxy {
         _authorizeUpgrade(newImplementation);
-        _upgradeToAndCallSecure(newImplementation, bytes(""), false);
+        _upgradeToAndCallSecure(newImplementation, new bytes(0), false);
     }
 
     /**
      * @dev Upgrade the implementation of the proxy to `newImplementation`, and subsequently execute the function call
      * encoded in `data`.
      *
      * Calls {_authorizeUpgrade}.
      *
      * Emits an {Upgraded} event.
      */
-    function upgradeToAndCall(address newImplementation, bytes memory data) external payable virtual {
+    function upgradeToAndCall(address newImplementation, bytes memory data) external payable virtual onlyProxy {
         _authorizeUpgrade(newImplementation);
         _upgradeToAndCallSecure(newImplementation, data, true);
     }
 
     /**

Vulnerable code:     function upgradeTo(address newImplementation) external virtual {
        _upgradeToAndCallSecure(newImplementation, bytes(""), false);
    function upgradeToAndCall(address newImplementation, bytes memory data) external payable virtual {
Fixed code: ## 4.3.2

 * `UUPSUpgradeable`: Add modifiers to prevent `upgradeTo` and `upgradeToAndCall` being executed on any contract that is not the active ERC1967 proxy. This prevents these functions being called on implementation contracts or minimal ERC1167 clones, in particular.

    /// @custom:oz-upgrades-unsafe-allow state-variable-immutable state-variable-assignment
    address private immutable __self = address(this);

    /**
     * @dev Check that the execution is being performed through a delegatecall call and that the execution context is
     * a proxy contract with an implementation (as defined in ERC1967) pointing to self. This should only be the case
     * for UUPS and transparent proxies that are using the current contract as their implementation. Execution of a
     * function through ERC1167 minimal proxies (clones) would not normally pass this test, but is not guaranteed to
     * fail.
     */
    modifier onlyProxy() {
        require(address(this) != __self, "Function must be called through delegatecall");
        require(_getImplementation() == __self, "Function must be called through active proxy");
        _;
    }

    function upgradeTo(address newImplementation) external virtual onlyProxy {
        _upgradeToAndCallSecure(newImplementation, new bytes(0), false);
    function upgradeToAndCall(address newImplementation, bytes memory data) external payable virtual onlyProxy {