Share your thoughts in the 2024 State of Clojure Survey!

Welcome! Please see the About page for a little more info on how this works.

+1 vote
in Compiler by

Primitive function and recur variables can't pass through a (try) cleanly; they're boxed to Object instead. This causes reflection warnings for fns or loops that use primitive types.

`
user=> (set! warn-on-reflection true)
true

user=> (fn [] (loop [t 0] (recur t)))

<user$eval676$fn677 user$eval676$fn677@3d80023a>

user=> (fn [] (loop [t 0] (recur (try t))))
NO_SOURCE_FILE:1 recur arg for primitive local: t is not matching primitive, had: Object, needed: long
Auto-boxing loop arg: t

<user$eval680$fn681 user$eval680$fn681@5419323a>

user=> (fn [^long x] (recur (try x)))
NO_SOURCE_FILE:1 recur arg for primitive local: x is not matching primitive, had: Object, needed: long

CompilerException java.lang.IllegalArgumentException: recur arg for primitive local: x is not matching primitive, had: Object, needed: long, compiling:(NO_SOURCE_PATH:1:1)
`

7 Answers

0 votes
by

Comment made by: davidj

Without commenting on the most desirable behavior, the following code does not cause reflection warnings:

`
user=> (set! warn-on-reflection true)
true
user=> (fn [] (loop [t 0] (recur (long (try t)))))

<user$eval673$fn674 user$eval673$fn674@4e56c411>

`

0 votes
by

Comment made by: bronsa

Similar ticket http://dev.clojure.org/jira/browse/CLJ-701

0 votes
by

Comment made by: hiredman

try/catch in the compiler only implements Expr, not MaybePrimitiveExpr, looking at extending TryExpr with MaybePrimitiveExpr it seems simple enough, but it turns out recur analyzes it's arguments in the statement context, which causes (try ...) to essentially wrap itself in a function like ((fn (link: ) (try ...))), at which point it is an invokeexpr which is much harder to add maybeprimitiveexpr too and it reduces to the same case as CLJ-701

0 votes
by

Comment made by: hiredman

http://dev.clojure.org/jira/browse/CLJ-701 has a patch that I think solves this

0 votes
by

Comment made by: alexmiller

Should I dupe this to CLJ-701?

0 votes
by

Comment made by: hiredman

if you want the fixes for try out of the return context to be part of CLJ-701 then yes it is a dupe, if you are unsure or would prefer 701 to stay more focused (my patch may not be acceptable, or may be too large and doing too much) then no it wouldn't be a dupe. I sort of took it on myself to solve both in the patch on CLJ-701 because I came to CLJ-701 via Nicola's comment here, and the same compiler machinery can be used for both.

I think the status is pending on the status of CLJ-701.

0 votes
by
Reference: https://clojure.atlassian.net/browse/CLJ-1422 (reported by aphyr)
...