Loops returning primtives are boxed even in return position

Description

Reported here: https://groups.google.com/d/topic/clojure/atoFzbyuyos/discussion

(defn first-bit? {:inline (fn [n] `(== 1 (clojure.lang.Numbers/and ~n, 1)) )} [^long n] (== 1 (clojure.lang.Numbers/and n, 1))) (defn exp-int ^double [^double x, ^long c] (loop [result 1.0, factor x, c c] (if (> c 0) (recur (if (first-bit? c) (* result factor) result), (* factor factor), (bit-shift-right c 1)) result)))

Last lines of the Java bytecode of `exp-int`:

59 dload 5; /* result */ 61 invokestatic 40; /* java.lang.Double java.lang.Double.valueOf(double c) */ 64 checkcast 85; /* java.lang.Number */ 67 invokevirtual 89; /* double doubleValue() */ 70 dreturn;

The compiler doesn't currently infer the primitive type as soon as there is a recur:

(use '[clojure.contrib.repl-utils :only [expression-info]]) (expression-info '(loop [a 1] a)) ;=> {:class long, :primitive? true} (expression-info '(loop [a 1] (if true a (recur a))) ;=> nil

Patch attached.

Environment

None

Attachments

1
  • 21 Nov 2012, 11:17 AM

Activity

Christophe Grand November 27, 2012 at 10:40 AM

FYI, gvec.clj has two loops which return primitives and thus was formerly boxed.

Timothy Baldridge November 26, 2012 at 4:59 PM

Tests also pass here. Looked through the code and played with a patched version of Clojure. I can't see a problem with it.

Stuart Halloway November 26, 2012 at 1:12 AM

Tests pass, code looks reasonable. Would appreciate additional review.

Completed

Details

Assignee

Reporter

Approval

Patch

Priority

Affects versions

Fix versions

Created November 21, 2012 at 11:17 AM
Updated December 22, 2012 at 3:53 PM
Resolved December 22, 2012 at 3:53 PM