-
-
Notifications
You must be signed in to change notification settings - Fork 5.6k
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
Add proper error for attempted use of undef slot #50556
Conversation
Fixes the segfault in #50518 and turns it into a proper error at both the syntax level (to catch lowering generating bad slot references) as well as at the codegen level (to catch e.g. bad generated functions and opaque closures). However, note that the latter case is technically undefined behavior, because we do not model the possibility that an otherwise-defined argument could throw at access time. Of course, throwing an error is allowable as undefined behavior and preferable to a segfault.
Fixes the case from #50518, but we actually have two test cases in the tests that also hit this (e.g. this one: ``` f40964(xs::Int...=1; k = 2) = (xs, k) ```), but just happened not to hit the bad codegen path. #50556, once merged would have complained on those definitions as well, without this fix.
#50559 needs to be merged first for this not to error, since we actually had a test that triggered the bad lowering. |
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.
LGTM. Though I would much rather it not be UB to access any arguments (since we might like to look at their types and type parameters to improve optimization / inlining, and it seems really awkward if that is illegal as a special case)
@@ -296,7 +296,7 @@ | |||
(if (eq? n '|#self#|) (gensy) n)) | |||
arg-names)))) | |||
(let ((body (insert-after-meta body ;; don't specialize on generator arguments | |||
`((meta nospecialize ,@arg-names))))) | |||
`((meta nospecialize ,@(map (lambda (idx) `(slot ,(+ idx 1))) (iota (length arg-names)))))))) |
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.
IIRC, there was previously a bug (and open issue) that vararg arguments didn't get nospecialize'd for macros. Any idea if this fixed 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.
I don't think so. This is for generated functions.
Fixes the case from #50518, but we actually have two test cases in the tests that also hit this (e.g. this one: ``` f40964(xs::Int...=1; k = 2) = (xs, k) ``` ), but just happened not to hit the bad codegen path. #50556, once merged would have complained on those definitions as well, without this fix.
I agree with this, but that's a pre-existing issue. I wouldn't really have a problem with ripping out the whole special |
I had an off-by-one in #50556, since the argument slots actually start at 2 and `iota` starts at `0`. This was breaking StaticArrays precompiles, which attempts to precompile a generator with its abstract signature and without the nospecialize, those signatures are not compileable.
Fixes the case from #50518, but we actually have two test cases in the tests that also hit this (e.g. this one: ``` f40964(xs::Int...=1; k = 2) = (xs, k) ```), but just happened not to hit the bad codegen path. #50556, once merged would have complained on those definitions as well, without this fix. (cherry picked from commit c272236)
I had an off-by-one in #50556, since the argument slots actually start at 2 and `iota` starts at `0`. This was breaking StaticArrays precompiles, which attempts to precompile a generator with its abstract signature and without the nospecialize, those signatures are not compileable. Co-authored-by: Oscar Smith <[email protected]>
Fixes the case from #50518, but we actually have two test cases in the tests that also hit this (e.g. this one: ``` f40964(xs::Int...=1; k = 2) = (xs, k) ```), but just happened not to hit the bad codegen path. #50556, once merged would have complained on those definitions as well, without this fix. (cherry picked from commit c272236)
Fixes the segfault in #50518 and turns it into a proper error at both the syntax level (to catch lowering generating bad slot references) as well as at the codegen level (to catch e.g. bad generated functions and opaque closures). However, note that the latter case is technically undefined behavior, because we do not model the possibility that an otherwise-defined argument could throw at access time. Of course, throwing an error is allowable as undefined behavior and preferable to a segfault.