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 multiplication overflow for function 1 and 2 #87

Closed

Conversation

lancechentw
Copy link
Contributor

The original code calculated required buffer space for decoded values by
mutiplying byte_count by 8. Since byte_count was given the type
u8, the multiplication result would overflowed if byte_count is
greater than 31. In other words, if more than 248 coils/discrete inputs
were requested.

This PR cast byte_count to u16 before it is used to calculate the
required buffer space, thus prevents the overflow.

The original code calculated required buffer space for decoded values by
mutiplying `byte_count` by 8. Since `byte_count` was given the type
`u8`, the multiplication result would overflowed if `byte_count` is
greater than 31. In other words, if more than 248 coils/discrete inputs
were requested.

This PR cast `byte_count` to u16 before it is used to calculate the
required buffer space, thus prevents the overflow.
Copy link
Member

@uklotzde uklotzde left a comment

Choose a reason for hiding this comment

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

Thank your for finding and fixing this serious issue!

Would it be possible to detect the overflow with a unit test to prevent regressions?

src/codec/mod.rs Outdated
@@ -234,15 +234,15 @@ impl TryFrom<Bytes> for Response {
let x = &bytes[2..];
// Here we have not information about the exact requested quantity so we just
// unpack the whole byte.
let quantity = u16::from(byte_count * 8);
let quantity = byte_count as u16 * 8;
Copy link
Member

Choose a reason for hiding this comment

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

Using u16::from(byte_count) * 8 would be safer than casting the value with as.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Thanks for the feedback! I will fix this and try to add a test case later today.

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 fixed and test cases are added in the latest commits. Please let me know if the fixes are preferred to be squashed.

@uklotzde uklotzde added the bug label Aug 12, 2021
@uklotzde
Copy link
Member

You can ignore the clippy warnings. These will finally be fixed by #88.

@uklotzde uklotzde modified the milestones: v0.4.0, v0.4.1, v0.5.0 Aug 12, 2021
@uklotzde
Copy link
Member

@flosse Backport this fix and publish v0.4.1?

just in case of accidental lossy conversion
Both test cases assume the spec'd max quantity, which is 2000, of items are
requested, which is actually far more than the number that would cause
multiplication overflow, which was 249.
Copy link
Member

@uklotzde uklotzde left a comment

Choose a reason for hiding this comment

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

Thank you for walking the extra mile by adding regression tests!

@uklotzde
Copy link
Member

I'll stash the commits and fix the formatting issues while rebasing.

@uklotzde
Copy link
Member

Merged.

@uklotzde uklotzde closed this Aug 13, 2021
@uklotzde uklotzde modified the milestones: v0.5.0, v0.4.1 Aug 13, 2021
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

2 participants