Skip to content
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

Fix set of indexes for processed txs in pending mbs #4392

Merged

Conversation

SebastianMarian
Copy link
Contributor

Description of the reasoning behind the pull request (what feature was missing / how the problem was manifesting itself / what was the motive behind the refactoring)

  • Fixed set of indexes for processed txs in pending mini blocks, received in epoch start meta block, when a node starts in epoch before mini block partial execution feature is activated

Proposed Changes

Testing procedure

…ived in epoch start meta block, when a node starts in epoch before mini block partial execution feature is activated
@SebastianMarian SebastianMarian self-assigned this Aug 23, 2022
@SebastianMarian SebastianMarian changed the title * Fixed set of indexes for processed txs in pending mini blocks, rece… Fix set of indexes for processed txs in pending mbs Aug 23, 2022
@iulianpascalau iulianpascalau self-requested a review August 23, 2022 13:06
@@ -18,7 +18,7 @@ import (
"github.com/ElrondNetwork/elrond-go/sharding/nodesCoordinator"
)

type miniBlockInfo struct {
type miniBlocksInfo struct {
Copy link
Contributor

Choose a reason for hiding this comment

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

👍

mbsInfo.pendingMiniBlocksPerShardMap[receiverShardID] = append(mbsInfo.pendingMiniBlocksPerShardMap[receiverShardID], mbHeader.GetHash())
mbsInfo.pendingMiniBlocksMap[string(mbHeader.GetHash())] = struct{}{}

isPendingMiniBlockPartiallyExecuted := mbHeader.GetIndexOfLastTxProcessed() > -1 && mbHeader.GetIndexOfLastTxProcessed() < int32(mbHeader.GetTxCount())-1
Copy link
Contributor

Choose a reason for hiding this comment

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

so this composed condition will prevent the current edge case. Can we still have the scenario in which both fields are 0 (due to the unmarshaling of the empty slice) in which the if branch will still be executed?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

No, because if reserved field will be nil, no matter of reason, the first line in the method returns TxCount-1

// GetIndexOfLastTxProcessed returns index of the last transaction processed in the miniBlock
func (m *MiniBlockHeader) GetIndexOfLastTxProcessed() int32 {
	miniBlockHeaderReserved, err := m.getMiniBlockHeaderReserved()
	if err != nil || miniBlockHeaderReserved == nil {
		return int32(m.TxCount) - 1
	}

Copy link
Contributor Author

Choose a reason for hiding this comment

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

And here we check only with GetIndexOfLastTxProcessed twice and not with both fields. GetIndexOfFirstTxProcessed does not matter when we try to determine if a block is partially executed. Only the index of the last tx executed will say if a miniblock is not yet fully processed.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

A mini block referenced in a shard mini block header with indexOfFirstTxProcessed set to let's say: 0 or 5, could be partially executed or fully executed as well, in both cases, as all will depend by the value of the indexOfLastTxProcessed

Copy link
Contributor

Choose a reason for hiding this comment

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

there is a difference between reserved field nil or empty. Should we change the condition to:

if err != nil || len(miniBlockHeaderReserved) == 0 {

The marhaller will output an empty string for a struct with default values as can be seen in this test:

func Test2(t *testing.T){
    m := &marshal.GogoProtoMarshalizer{}

    b := &block.MiniBlockReserved{}

    buff, _ := m.Marshal(b)

    fmt.Println(buff)
    assert.NotNil(t, buff)
    assert.Equal(t, 0, len(buff))
}

Copy link
Contributor

Choose a reason for hiding this comment

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

could be changed to len() to accommodate both the nil and empty

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Actually miniBlockHeaderReserved could be only nil or NOT empty if you check the method m.getMiniBlockHeaderReserved() . There is no marshal but only unmarshal inside the method, so is not the case you underscored above. Anyways if we want this change, a new PR in elrond-go-core should be done. And also this change should be tested very well, as it will affect many parts of the code where the method is called.

// GetMiniBlockHeaderReserved returns the MiniBlockHeader Reserved field as a MiniBlockHeaderReserved
func (m *MiniBlockHeader) getMiniBlockHeaderReserved() (*MiniBlockHeaderReserved, error) {
	if len(m.Reserved) > 0 {
		mbhr := &MiniBlockHeaderReserved{}
		err := mbhr.Unmarshal(m.Reserved)
		if err != nil {
			return nil, err
		}

		return mbhr, nil
	}
	return nil, nil
}

Copy link
Contributor

Choose a reason for hiding this comment

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

return nil, nil. That is another red flag

Copy link
Contributor Author

Choose a reason for hiding this comment

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

This is for backwards compatibility as reserved was not used before scheduled miniblocks and here we can not pass the epoch notifier

Copy link
Contributor

Choose a reason for hiding this comment

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

still not agree. It can easily raise panics as we got used to use the code

epochStart/bootstrap/shardStorageHandler.go Show resolved Hide resolved
@codecov-commenter
Copy link

codecov-commenter commented Aug 23, 2022

Codecov Report

❗ No coverage uploaded for pull request base (rc/2022-july@df68515). Click here to learn what that means.
The diff coverage is n/a.

@@               Coverage Diff               @@
##             rc/2022-july    #4392   +/-   ##
===============================================
  Coverage                ?   73.83%           
===============================================
  Files                   ?      675           
  Lines                   ?    86847           
  Branches                ?        0           
===============================================
  Hits                    ?    64120           
  Misses                  ?    17933           
  Partials                ?     4794           

Help us with your feedback. Take ten seconds to tell us how you rate us. Have a feature suggestion? Share it here.

@raduchis raduchis self-requested a review August 23, 2022 18:34
mbsInfo.pendingMiniBlocksPerShardMap[receiverShardID] = append(mbsInfo.pendingMiniBlocksPerShardMap[receiverShardID], mbHeader.GetHash())
mbsInfo.pendingMiniBlocksMap[string(mbHeader.GetHash())] = struct{}{}

isPendingMiniBlockPartiallyExecuted := mbHeader.GetIndexOfLastTxProcessed() > -1 && mbHeader.GetIndexOfLastTxProcessed() < int32(mbHeader.GetTxCount())-1
Copy link
Contributor

Choose a reason for hiding this comment

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

could be changed to len() to accommodate both the nil and empty

Copy link
Collaborator

@gabi-vuls gabi-vuls left a comment

Choose a reason for hiding this comment

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

System test passed.

@gabi-vuls gabi-vuls merged commit 068a2f5 into rc/2022-july Aug 24, 2022
@gabi-vuls gabi-vuls deleted the fix-set-of-indexes-for-processed-txs-in-pending-mbs branch August 24, 2022 12:28
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.

None yet

5 participants