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
Hare msg validation #572
Hare msg validation #572
Conversation
gavraz
commented
Feb 19, 2019
- Extracted validation
- Instance id is now uint32
- Broker validates instance id
- Fixed & added unit tests
85e0376
to
c4cf030
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please refrain from using explicit uint32 types, only cast to primitive type when serializing
hare/broker.go
Outdated
} | ||
broker.pending[instanceId.Id()] = append(broker.pending[instanceId.Id()], mOut) | ||
broker.pending[instanceId.Id()] = append(broker.pending[instanceId.Id()], hareMsg) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
are there any concurrent writes to pending[] map? should it be locked if so? I'd recommend running your unit tests with --race before you push
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am protecting it with the lock. Let me know if you see a scenario in which I do not. Didn't see issues with -race regarding this test.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
As I wrote in the comment above, if you'll move Register
into this select you could lose the mutex. @antonlerner what do you think? It is a different scenario than what you'd benchmarked, Register
is called less often than this loop
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I am not sure it is a good idea because I will eventually want to remove the inboxer interface and return the inbox. That will complicate the register call. We can probably solve it by passing a function on the channel but it sounds too complicated.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
you can still make this change and return the channel. Just create the channel and pass it to the dispatcher via the register channel. You can make this change as well as removing the inboxer as part of this PR.
continue | ||
} | ||
|
||
instanceId := NewBytes32(hareMsg.Message.InstanceId) | ||
// message validation |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Consider extracting the code below to a method (until // validation passed
), it will improve the readability
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I considered it before and decided that using continue is preferred on using the return value.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Your comment has nothing to do with what I wrote... the dispatcher
method is very long for no reason. Please break into smaller methods
hare/broker.go
Outdated
outbox map[uint32]chan *pb.HareMessage | ||
pending map[uint32][]*pb.HareMessage | ||
mutex sync.RWMutex | ||
maxReg uint32 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
consider renaming to lastReg
, "max" is a bit confusing
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
But it is the max and not the last. using the last will add the assumption that we never start a proc id' before id if id'>id. While this is correct for now I prefer not to add this assumption, nor see a reason to do that.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Of course you'll never start proc id' before id, if id'>id. The assumptions should be as strict as possible and should be loosened only when needed. In which case would you allow executing process out of order? Do you have tests for such cases?
hare/broker.go
Outdated
continue | ||
} | ||
|
||
if hareMsg.Message.InstanceId > broker.maxReg+1 { // intended for future unregistered instance |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
you can't read from maxReg
without locking broker.mutex
. I would suggest that you'll move Register
and Unregister
into this select loop and lose the mutex
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Also, you should also check that the InstanceId belongs to a "live" execution (i.e. that if someone tries to send you a message on a Hare instance that was already completed that message will be considered invalid)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
btw, currently it seems that no one calls Unregister
- open a bug (if it's a small fix then add it as part of this PR)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fixed 1 & 2.
Opened a bug for 3.
hare/broker.go
Outdated
} | ||
broker.pending[instanceId.Id()] = append(broker.pending[instanceId.Id()], mOut) | ||
broker.pending[instanceId.Id()] = append(broker.pending[instanceId.Id()], hareMsg) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
As I wrote in the comment above, if you'll move Register
into this select you could lose the mutex. @antonlerner what do you think? It is a different scenario than what you'd benchmarked, Register
is called less often than this loop
5de3d44
to
757b188
Compare
2a3e211
to
9df43b9
Compare
* Extracted validation * Instance id is now uint32 like layer id * Broker validates instance id * Replaced uint32 with InstanceId and id types * Event loop broker (no mutex)