@@ -937,22 +937,7 @@ func (sdb *IntraBlockState) AddBalance(addr accounts.Address, amount uint256.Int
937937 // EIP161: We must check emptiness for the objects such that the account
938938 // clearing (0,0,0 objects) can take effect.
939939 if amount .IsZero () {
940- stateObject , err := sdb .GetOrNewStateObject (addr )
941- if err != nil {
942- return err
943- }
944-
945- if stateObject .data .Empty () {
946- versionWritten (sdb , addr , BalancePath , accounts .NilKey , uint256.Int {})
947- if _ , ok := sdb .journal .dirties [addr ]; ! ok {
948- if dbg .TraceTransactionIO && (sdb .trace || dbg .TraceAccount (addr .Handle ())) {
949- fmt .Printf ("%d (%d.%d) Touch %x\n " , sdb .blockNum , sdb .txIndex , sdb .version , addr )
950- }
951- sdb .touchAccount (addr )
952- }
953- }
954-
955- return nil
940+ return sdb .TouchAccount (addr )
956941 }
957942
958943 prev , wasCommited , _ := sdb .getBalance (addr )
@@ -992,6 +977,27 @@ func (sdb *IntraBlockState) touchAccount(addr accounts.Address) {
992977 }
993978}
994979
980+ // TouchAccount materializes an empty account and records the zero-balance touch
981+ // needed for state clearing and trie consistency.
982+ func (sdb * IntraBlockState ) TouchAccount (addr accounts.Address ) error {
983+ stateObject , err := sdb .GetOrNewStateObject (addr )
984+ if err != nil {
985+ return err
986+ }
987+
988+ if stateObject .data .Empty () {
989+ versionWritten (sdb , addr , BalancePath , accounts .NilKey , uint256.Int {})
990+ if _ , ok := sdb .journal .dirties [addr ]; ! ok {
991+ if dbg .TraceTransactionIO && (sdb .trace || dbg .TraceAccount (addr .Handle ())) {
992+ fmt .Printf ("%d (%d.%d) Touch %x\n " , sdb .blockNum , sdb .txIndex , sdb .version , addr )
993+ }
994+ sdb .touchAccount (addr )
995+ }
996+ }
997+
998+ return nil
999+ }
1000+
9951001func (sdb * IntraBlockState ) getVersionedAccount (addr accounts.Address , readStorage bool ) (* accounts.Account , ReadSource , Version , error ) {
9961002 if sdb .versionMap == nil {
9971003 return nil , UnknownSource , UnknownVersion , nil
@@ -1122,10 +1128,11 @@ func (sdb *IntraBlockState) refreshVersionedAccount(addr accounts.Address, readA
11221128// SubBalance subtracts amount from the account associated with addr.
11231129// DESCRIBED: docs/programmers_guide/guide.md#address---identifier-of-an-account
11241130func (sdb * IntraBlockState ) SubBalance (addr accounts.Address , amount uint256.Int , reason tracing.BalanceChangeReason ) error {
1125- if amount .IsZero () && addr != params .SystemAddress {
1126- // We skip this early exit if the sender is the system address
1127- // because Gnosis has a special logic to create an empty system account
1128- // even after Spurious Dragon (see PR 5645 and Issue 18276).
1131+ if amount .IsZero () {
1132+ if addr == params .SystemAddress {
1133+ // Gnosis keeps an empty system account even after Spurious Dragon.
1134+ return sdb .TouchAccount (addr )
1135+ }
11291136 return nil
11301137 }
11311138
0 commit comments