Changeset 11588


Ignore:
Timestamp:
01/25/09 10:13:49 (12 years ago)
Author:
ehuelsmann
Message:

Optimize MIN/MAX inline calculations: with the right stack use, we can avoid storing
and reloading of values with shorter execution paths and branches as a result.
Also enable the instructions pop2, dup2_x1 and dup2_x2.

Location:
trunk/abcl/src/org/armedbear/lisp
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • trunk/abcl/src/org/armedbear/lisp/compiler-pass2.lisp

    r11584 r11588  
    10261026                 83 ; aastore
    10271027                 87 ; pop
     1028                 88 ; pop2
    10281029                 89 ; dup
    10291030                 90 ; dup_x1
    10301031                 91 ; dup_x2
    10311032                 92 ; dup2
     1033                 93 ; dup2_x1
     1034                 94 ; dup2_x2
    10321035                 95 ; swap
    10331036                 96 ; iadd
     
    67256728                 (type2 (derive-compiler-type arg2)))
    67266729             (cond ((and (fixnum-type-p type1) (fixnum-type-p type2))
    6727                     (let* ((*register* *register*)
    6728                            (reg1 (allocate-register))
    6729                            (reg2 (allocate-register)))
    6730           (new-fixnum (null representation))
    6731                       (compile-form arg1 'stack :int)
    6732                       (emit 'dup)
    6733                       (emit 'istore reg1)
    6734                       (compile-form arg2 'stack :int)
    6735                       (emit 'dup)
    6736                       (emit 'istore reg2)
    6737                       (let ((LABEL1 (gensym))
    6738                             (LABEL2 (gensym)))
    6739                         (emit (if (eq op 'min) 'if_icmpge 'if_icmple) LABEL1)
    6740                         (emit 'iload reg1)
    6741                         (emit 'goto LABEL2)
    6742                         (label LABEL1)
    6743                         (emit 'iload reg2)
    6744                         (label LABEL2)))
     6730                    (new-fixnum (null representation))
     6731                    (compile-form arg1 'stack :int)
     6732                    (emit 'dup)
     6733                    (compile-form arg2 'stack :int)
     6734                    (emit 'dup_x1)
     6735                    (let ((LABEL1 (gensym)))
     6736                      (emit (if (eq op 'max) 'if_icmpge 'if_icmple) LABEL1)
     6737                      (emit 'swap)  ;; The lower stack value is greater-or-equal
     6738                      (label LABEL1)
     6739                      (emit 'pop))  ;; Throw away the lower stack value
    67456740        (emit-fixnum-init representation)
    67466741                    (emit-move-from-stack target representation))
    67476742                   ((and (java-long-type-p type1) (java-long-type-p type2))
    6748                     (let* ((*register* *register*)
    6749                            (reg1 (allocate-register-pair))
    6750                            (reg2 (allocate-register-pair)))
    6751                       (compile-form arg1 'stack :long)
    6752                       (emit 'dup2)
    6753                       (emit 'lstore reg1)
    6754                       (compile-form arg2 'stack :long)
    6755                       (emit 'dup2)
    6756                       (emit 'lstore reg2)
    6757                       (emit 'lcmp)
    6758                       (let ((LABEL1 (gensym))
    6759                             (LABEL2 (gensym)))
    6760                         (emit (if (eq op 'min) 'ifge 'ifle) LABEL1)
    6761                         (emit 'lload reg1)
    6762                         (emit 'goto LABEL2)
    6763                         (label LABEL1)
    6764                         (emit 'lload reg2)
    6765                         (label LABEL2)))
     6743                    (compile-form arg1 'stack :long)
     6744                    (emit 'dup2)
     6745                    (compile-form arg2 'stack :long)
     6746                    (emit 'dup2_x2)
     6747                    (emit 'lcmp)
     6748                    (let ((LABEL1 (gensym)))
     6749                      (emit (if (eq op 'max) 'ifge 'ifle) LABEL1)
     6750                      (emit 'dup2_x2) ;; pour-mans swap2
     6751                      (emit 'pop2)
     6752                      (label LABEL1)
     6753                      (emit 'pop2))
    67666754                    (convert-long representation)
    67676755                    (emit-move-from-stack target representation))
    67686756                   (t
    6769                     (let* ((*register* *register*)
    6770                            (reg1 (allocate-register))
    6771                            (reg2 (allocate-register)))
    6772                       (compile-form arg1 'stack nil)
    6773                       (emit 'dup)
    6774                       (astore reg1)
    6775                       (compile-form arg2 'stack nil)
    6776                       (emit 'dup)
    6777                       (astore reg2)
    6778                       (emit-invokevirtual +lisp-object-class+
    6779                                           (if (eq op 'min)
    6780                                               "isLessThanOrEqualTo"
    6781                                               "isGreaterThanOrEqualTo")
    6782                                           (lisp-object-arg-types 1) "Z")
    6783                       (let ((LABEL1 (gensym))
    6784                             (LABEL2 (gensym)))
     6757                    (compile-form arg1 'stack nil)
     6758                    (emit 'dup)
     6759                    (compile-form arg2 'stack nil)
     6760                    (emit 'dup_x1)
     6761                    (emit-invokevirtual +lisp-object-class+
     6762                                        (if (eq op 'max)
     6763                                            "isLessThanOrEqualTo"
     6764                                            "isGreaterThanOrEqualTo")
     6765                                        (lisp-object-arg-types 1) "Z")
     6766                      (let ((LABEL1 (gensym)))
    67856767                        (emit 'ifeq LABEL1)
    6786                         (aload reg1)
    6787                         (emit 'goto LABEL2)
     6768                        (emit 'swap)
    67886769                        (label LABEL1)
    6789                         (aload reg2)
    6790                         (label LABEL2)))
     6770                        (emit 'pop))
    67916771                    (fix-boxing representation nil)
    67926772                    (emit-move-from-stack target representation))))))
  • trunk/abcl/src/org/armedbear/lisp/opcodes.lisp

    r11582 r11588  
    141141(define-opcode sastore 86 1 nil)
    142142(define-opcode pop 87 1 -1)
    143 (define-opcode pop2 88 1 nil)
     143(define-opcode pop2 88 1 -2)
    144144(define-opcode dup 89 1 1)
    145145(define-opcode dup_x1 90 1 1)
    146146(define-opcode dup_x2 91 1 1)
    147147(define-opcode dup2 92 1 2)
    148 (define-opcode dup2_x1 93 1 nil)
    149 (define-opcode dup2_x2 94 1 nil)
     148(define-opcode dup2_x1 93 1 2)
     149(define-opcode dup2_x2 94 1 2)
    150150(define-opcode swap 95 1 0)
    151151(define-opcode iadd 96 1 -1)
Note: See TracChangeset for help on using the changeset viewer.