Skip to content

Fix: Allow appending to struct at the end of storage layout #1136 #1147

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 14 commits into
base: master
Choose a base branch
from

Conversation

ginzahatemi
Copy link

Issue

When appending fields to a struct that is at the end of a contract's storage layout, the upgrades validation incorrectly reports an incompatible layout error. This happens despite the fact that this operation is safe, as it only extends into previously unused storage space.

Fix

This PR modifies the storage layout validation logic to properly handle struct field appending when:

  1. The struct is at the end of the storage layout
  2. Only new fields are added (no modification to existing fields)
  3. The fields are appended at the end of the struct

The changes include:

  • Added detection for when fields are only being appended to a struct
  • Enhanced the operation filter in layoutLevenshtein to handle struct member changes
  • Added appropriate documentation explaining the safety of this operation

Works With

  • Regular storage variables
  • Namespaced storage (ERC-7201)

Fixes #1136

…tructs in storage layout. Added checks for struct member changes
Copy link
Member

@ericglau ericglau left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the PR.
Can you please add some tests? These should include when validations should pass, and when validations should report errors (for example, when appending at the end of a struct, but the struct is not at the end of storage).

…ludes cases for valid and invalid struct modifications, ensuring proper error handling and namespace support.
…ayoutComparator to improve code clarity and maintainability.
…ncy. Cleaned up whitespace in struct append tests for improved readability.
…mplement tests for valid and invalid struct appending scenarios in storage layout validation.
@ginzahatemi
Copy link
Author

Hi @ericglau ,

I have implemented the changes based on your suggestions. Could you please review them at your convenience? If everything looks good, would you mind proceeding with the merge?

Thank you!

Copy link
Member

@ericglau ericglau left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've adjusted the test cases for the second scenario to properly demonstrate insertion before the end of storage layout.

However, the first test case is still failing with the following operations even though it should have been filtered out by the new code in compare.ts:

 [
    {
      "kind": "typechange",
      "change": {
        "kind": "struct members",
        "ops": [
          {
            "kind": "append",
            "totalCost": 0,
            "predecessor": {
              "kind": "nop",
              "totalCost": 0,
              "predecessor": {
                "kind": "nop",
                "totalCost": 0,
                "predecessor": {
                  "kind": "nop",
                  "totalCost": 0
                }
              }
            },
            "updated": {
              "label": "z",
              "type": {
                "id": "t_uint256",
                "head": "t_uint256",
                "item": {
                  "label": "uint256",
                  "numberOfBytes": "32"
                }
              },
              "offset": 0,
              "slot": "2"
            }
          }
        ],
...

The logic for the comparison may need to be investigated or this may need further debugging.

@@ -0,0 +1,42 @@
// SPDX-License-Identifier: MIT
pragma solidity ^0.8.0;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is missing test cases for namespaced structs as described in #1136

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've added test cases for namespaced structs as requested in the latest commit. Let me know if there are any more suggestions

…tructs in storage layout. Added checks for struct member changes
…ludes cases for valid and invalid struct modifications, ensuring proper error handling and namespace support.
…ayoutComparator to improve code clarity and maintainability.
…ncy. Cleaned up whitespace in struct append tests for improved readability.
…mplement tests for valid and invalid struct appending scenarios in storage layout validation.
@ginzahatemi
Copy link
Author

Hey @ericglau I have made the suggested changes and pushed some commit, could you review them, if they are Ok or not?

@ginzahatemi ginzahatemi force-pushed the struct-append-1136 branch 2 times, most recently from 1c682de to a53fcf5 Compare April 29, 2025 08:51
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Cannot append to struct at the end of storage layout
2 participants