Ich habe eine Flusenprüfungswarnung in Remix für meinen Smart Contract in Solidity:addFeature(int128,uint256,bool,uint256,uint256,uint16,uint16,address) high: infinite. If the gas requirement of a function is higher than the block gas limit, it cannot be executed. Please avoid loops in your functions or actions that modify large areas of storage (this includes clearing or copying arrays in storage)
Feature
ist eine Struktur mit vielen Feldern:
struct Feature {
int128 key;
uint256 goal;
bool finishOnGoal;
uint campaignStart; // timestamp
uint campaignFinish; // timestamp
PledgeType pledgeType; // enum
FixedPledge fixedPledge; // description for enum value #1
VariablePledge variablePledge; // description for enum value #2
PrepaymentType prepaymentType; // enum
FixedPrepayment fixedPrepayment; // description for enum value #1
PercentPrepayment percentPrepayment; // description for enum value #2
uint16 maxDevelopmentDelay; // days
uint16 developmentDuration; // days
ConfirmationType confirmationType; // enum
UserConfirmation userConfirmation; // description for enum value #1
address developer;
}
...
// featureKey => feature
mapping (int128 => Feature) features;
// featureKey => feature
mapping (int128 => FeatureData) data;
...
// common feature data
function addFeature(
int128 key,
uint256 goal,
bool finishOnGoal,
uint campaignStart, // timestamp
uint campaignFinish, // timestamp
uint16 maxDevelopmentDelay,
uint16 developmentDuration,
address developer) public
ownerOnly
withState(key, State.NotSet)
{
Feature memory feature;
feature.key = key;
feature.goal = goal;
feature.finishOnGoal = finishOnGoal;
feature.campaignStart = campaignStart;
feature.campaignFinish = campaignFinish;
feature.maxDevelopmentDelay = maxDevelopmentDelay;
feature.developmentDuration = developmentDuration;
feature.developer = developer;
FeatureData memory featureData;
featureData.state = State.Deployment;
featureData.backers = new address[](0);
featureData.raised = 0;
featureData.prepaid = 0;
features[key] = feature;
data[key] = featureData;
}
Warum habe ich diese Warnung? Was kann / sollte geändert werden, um das Problem zu beheben (ohne die Funktionalität zu verlieren)? AFAIK gibt es hier weder Schleifen- noch Array- Modifikationen ( nur Karten ).
Hier ist ein Minimalvertrag, der das Problem zeigt:
pragma solidity ^0.4.24;
contract Test {
mapping (uint128 => address[]) data;
function addFeature() public {
data[0] = new address[](0);
}
}
address[]
Sie können überprüfen, ob dies das Problem ist, das Sie haben, indem Sie das Feld aus entfernen FeatureData
und prüfen, ob Sie immer noch eine unendliche Gasschätzung erhalten.
Ich glaube , das Problem ist, dass die statische Analyse nicht ausgefeilt genug ist, um zu wissen, dass das Array, das Sie kopieren, immer die Länge 0 hat. Es sieht nur, dass ein Array vom Speicher in den Speicher kopiert werden muss, und kann keine gute Gasschätzung vornehmen .
Der obige einfache Code hat jedoch ungefähr feste Benzinkosten, sodass die Warnung sicher ignoriert werden kann. Wenn Sie überprüfen, dass das gleiche Problem die Warnung in Ihrem Code verursacht, können Sie sie meiner Meinung nach auch ignorieren.
Wenn Sie die Warnung loswerden möchten, können Sie stattdessen diesen Code schreiben. Ich vermute, dass dies sowieso gaseffizienter ist:
FeatureData storage featureData = data[key];
featureData.state = State.Deployment;
featureData.backers.length = 0;
featureData.raised = 0;
featureData.prepaid = 0;
Benutzer19510
FeatureData
In-Memory aufgrund desbackers
Arrays mit dynamischer Größe in den Speicher kopiert werden soll . Könnten Sie genug Code teilen, damit es möglich ist, dies zu kompilieren?4ntoine
Benutzer19510