-
Notifications
You must be signed in to change notification settings - Fork 34
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
Validate i32/i64.load/store alignment #310
Conversation
expected_passed: 4482 | ||
expected_failed: 8 | ||
expected_passed: 4481 | ||
expected_failed: 9 |
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.
Hmm.
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.
This is due to another shortcoming in the spectest, will submit an issue.
Codecov Report
@@ Coverage Diff @@
## master #310 +/- ##
==========================================
- Coverage 99.32% 99.30% -0.03%
==========================================
Files 42 43 +1
Lines 12834 12933 +99
==========================================
+ Hits 12748 12843 +95
- Misses 86 90 +4 |
1c9f923
to
9da335e
Compare
f30fa0c
to
3e2d684
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.
This needs a unit test
369e0f5
to
68494f7
Compare
6b5c048
to
4a0edcb
Compare
8afdf74
to
ef93833
Compare
lib/fizzy/instructions.hpp
Outdated
@@ -16,6 +16,18 @@ struct InstructionMetrics | |||
/// The stack height change caused by the instruction execution, | |||
/// i.e. stack height _after_ execution - stack height _before_ execution. | |||
int8_t stack_height_change; | |||
|
|||
/// The memory width in bytes the instruction operates on or 0 in case not using the memory. | |||
uint8_t memory_width; |
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 can see now that it would be simpler to keep this as max_align
of {1,2,3,4}
, as in your tests.
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.
Maybe, but memory_width
is also fitting and describes what it does.
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 mean {0,1,2,3}
so you don't need to pre-process it during validation:
if (align > metrics.max_align)
throw validation_error{"alignment cannot exceed operand size"};
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 see. Even if we change that I still wouldn't use instruction_metrics
in the tests, otherwise the tests aren't that prone to mistakes :)
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.
Agreed.
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.
/// The largest acceptable alignment value satisfying `2 ** max_align < memory_width` where memory_width
/// is the number of bytes the instruction operates on. max_align is 0 if it does not operate on memory.
uint8_t max_align;
This is actually a bit weird because max_align = 0
is a valid value and with the current way memory_width = 0
would be invalid which is the default on non-memory instructions. It is only a nitpick. The difference in the parser is a single shift less.
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.
Not an issue to me.
36d58e1
to
7d10cc9
Compare
lib/fizzy/parser_expr.cpp
Outdated
std::tie(align, pos) = leb128u_decode<uint32_t>(pos, end); | ||
// NOTE: [0, 3] is the correct range (the hard limit is log2(64 / 8)) and checking it to | ||
// avoid overflows | ||
if ((align > 3) || (align > metrics.max_align)) |
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.
if ((align > 3) || (align > metrics.max_align)) | |
if (align > metrics.max_align) |
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 would still prefer the memory_width
version of the code.
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.
Why? To have nice looking table? It is mistake to keep in table data which you later need to modify by a constant expression.
809617d
to
b9623c6
Compare
/// The largest acceptable alignment value satisfying `2 ** max_align < memory_width` where | ||
/// memory_width is the number of bytes the instruction operates on. | ||
/// | ||
/// This field may contain invalid value for instructions not needing it. |
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.
It's default-initialized to 0, I wouldn't call it 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.
0 is invalid on non-memory ops, because the change preferred by @chfast makes 0 a valid value (1<<0 = 1).
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.
0 is valid value for memory instructions, and nonrelevant for non-memory instructions. To me it never contains "invalid value" like garbage.
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.
It does contain invalid value for non-memory ops.
Co-authored-by: Paweł Bylica <chfast@gmail.com>
Based on section 3.3.4: https://webassembly.github.io/spec/core/_download/WebAssembly.pdf