Modifikator für vertragslose Anrufe [duplizieren]

Der Modifikator, der verwendet wird, um zu prüfen, ob ein Vertrag eine Funktion in Solidity aufruft, verwendet den Assembler-Code extsize. Ich frage mich, warum das gemacht wird. Die Verwendung von Assembly erscheint mir sehr "hackish" (warum hat Solidity keine "normale" Funktion, um dies zu überprüfen?). Der fragliche Code ist

modifier noContract(address _addr){
  uint32 size;
  assembly {
    size := extcodesize(_addr)
  }
  require (size == 0);
  _;
}

(bearbeitet von https://ethereum.stackexchange.com/a/15642/33191 )

Warum nicht msg.sender == tx.orginals Scheck verwenden? Gibt es hier eine Lücke?

Ist der Grund für die Verwendung extsize, dass dies (etwas) weniger Gas verbrauchen könnte?

Könnten Sie einige Links teilen, um welchen Code Sie sprechen?
Ich werde meine Frage bearbeiten. Aber hier ist eine Quelle. ethereum.stackexchange.com/questions/15641/…
FYI, das ist kein Modifikator. Es ist eine Funktion.
Sie haben Recht, ich habe den kopierten Code nicht überprüft.

Antworten (1)

tx.originsollte in EXTREM seltenen Fällen verwendet werden. Wenn Sie überprüfen , überprüfen tx.originSie, von wem der Anruf stammt. Bei unsachgemäßer Verwendung kann dies also extreme Schwachstellen öffnen oder möglicherweise die Funktionalität Ihres Vertrags beeinträchtigen.

person a -> contract-a -> contract-bWenn Sie es aktivieren, tx.originwird contract-bes in die Adresse von aufgelöst, person anicht in die Adresse von contract-a. Wenn Sie es überprüfen msg.sender, wird es sein contract-a.

Der Grund, warum Assembler verwendet wird, ist, wie Sie betonen, dass es derzeit keine integrierten soliden Funktionen gibt, um dies zu handhaben. Solidität ist noch eine recht junge Sprache, daher ist es nicht verwunderlich.

in Bezug darauf, keinen Vertrag zu haben, sich selbst anrufen zu können

Es gibt nur wenige Möglichkeiten, wie dies passieren kann:

1) Spezifische Programmierfunktionen oder -logik, die den Vertrag dazu zwingen, sich selbst aufzurufen

2) Aufruf unbekannter Verträge, die die Ausführung von Fallback-Code auslösen können

Option 1 ist kein wirkliches Problem, da dies sehr einfach zu kontrollieren ist, aber Option 2 kann Sie für Hacking-Versuche auf Ihren Vertrag öffnen, da der unbekannte Vertrag, den Sie anrufen, möglicherweise eine Fallback-Funktion implementieren könnte, die Aufrufe an Ihren Vertrag auslösen würde.

Ich denke, Ihr Problem sollte besser gelöst werden, indem festgestellt wird, welche Funktionen es dem Vertrag ermöglichen, sich selbst aufzurufen, und diese Funktionen geändert werden, während alle Aufrufe unbekannter Verträge entfernt werden, die die Codeausführung auslösen könnten, für die Sie das Ergebnis nicht kennen. Sie könnten einige Assembler-Zaubereien implementieren, um dies zu verhindern, aber für mich klingt das so, als würden Sie dadurch potenziellen Schwachstellen ausgesetzt.

Mal sehen, ob ich es richtig verstehe. Wenn Sie Ihren modifizierten Modifikator verwenden (kein Wortspiel beabsichtigt), können Sie verhindern, dass sich der Vertrag selbst aufruft (über einen CALL-Code). Aber dies wird bereits verhindert, indem entweder die tx.orgin-Methode oder die extcodesize-Methode verwendet wird? Warum beides verwenden? Ich glaube, ich verpasse hier etwas.
Sie möchten auch nicht, dass sich der laufende Vertrag selbst nennt? In diesem Fall würde ich Ihren ursprünglichen Beitrag aktualisieren, um dies klarzustellen, da nicht klar ist, wonach Sie suchen. Dies kann niemals verhindert werden, tx.originda ein Anruf niemals von einem Vertragskonto stammen kann, sondern immer von einem EOA stammen muss (zumindest vorerst bis zur Kontoentnahme). Sie sollten es niemals wirklich verwenden, tx.origines ist gefährlich und sollte unter extremen Umständen verwendet werden. Es hört sich so an, als ob das, wonach Sie suchen, durch Vertragsumgestaltung gelöst werden kann, anstatt zu versuchen, eine hackige Lösung zu implementieren.
Nein, das war nicht meine Frage. Ich verstehe nicht, was Sie mit "aber das würde nur prüfen, ob der Anruf von diesem Konto stammt." meinen. Warum würden Sie qrequire(msg.sender==tx.origin)` zum Modifikator hinzufügen? Ist das nicht immer wahr, wenn extcodesize 0 ist?
Ja, du hast Recht, ich entschuldige mich für die Verwirrung. Es wird immer wahr sein, ja. Wenn Sie sich fragen, warum Sie nicht das eine oder andere verwenden sollten, liegt das ganz bei Ihnen. Die Absicht dahinter ist jedoch unterschiedlich. tx.originden Absender des Anrufs extcodesizenachschlagen, während die Größe des gespeicherten Codes nachschlagen soll. Ich würde davon ausgehen, dass extcodesize mit Assemblierung wahrscheinlich etwas billiger wäre als mittx.origin
Okay, das klärt meine Frage. Ich habe mich tatsächlich gefragt, ob ihre Ergebnisse in irgendeiner Weise anders sein würden.
Toll, freut mich, dass ich helfen konnte! Die Ergebnisse unterscheiden sich wirklich nicht, aber ich finde, dass die Antworten, die Sie von der Community erhalten, unterschiedlich sein werden. tx.originhat etwas böses Blut mit seiner Verwendung verbunden, da es zu einer Reihe von Schwachstellen führt, die zu hochkarätigen Hacks führen. Abgesehen davon kommt es darauf an, wie Sie implementieren tx.origin. Viel Glück!