Ignore:
Timestamp:
Apr 22, 2010, 6:24:56 AM (15 years ago)
Author:
[email protected]
Message:

2010-04-22 Gabor Loki <[email protected]>

Reviewed by Gavin Barraclough.

Use BLX and BX to keep happy the return stack predictor above ARMv4
https://bugs.webkit.org/show_bug.cgi?id=37862

Inspired by Jacob Bramley's patch from JaegerMonkey

  • assembler/ARMAssembler.cpp: (JSC::ARMAssembler::executableCopy):
  • assembler/ARMAssembler.h: (JSC::ARMAssembler::): (JSC::ARMAssembler::bx): (JSC::ARMAssembler::blx): (JSC::ARMAssembler::loadBranchTarget): (JSC::ARMAssembler::jmp): (JSC::ARMAssembler::getLdrImmAddress):
  • assembler/MacroAssemblerARM.h: (JSC::MacroAssemblerARM::jump): (JSC::MacroAssemblerARM::nearCall): (JSC::MacroAssemblerARM::call): (JSC::MacroAssemblerARM::ret): (JSC::MacroAssemblerARM::prepareCall): (JSC::MacroAssemblerARM::call32):
File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/JavaScriptCore/assembler/MacroAssemblerARM.h

    r56348 r58091  
    11/*
    22 * Copyright (C) 2008 Apple Inc.
    3  * Copyright (C) 2009 University of Szeged
     3 * Copyright (C) 2009, 2010 University of Szeged
    44 * All rights reserved.
    55 *
     
    475475    void jump(RegisterID target)
    476476    {
    477         move(target, ARMRegisters::pc);
     477        m_assembler.bx(target);
    478478    }
    479479
     
    567567    Call nearCall()
    568568    {
     569#if WTF_ARM_ARCH_AT_LEAST(5)
     570        ensureSpace(2 * sizeof(ARMWord), sizeof(ARMWord));
     571        m_assembler.loadBranchTarget(ARMRegisters::S1, ARMAssembler::AL, true);
     572        return Call(m_assembler.blx(ARMRegisters::S1), Call::LinkableNear);
     573#else
    569574        prepareCall();
    570575        return Call(m_assembler.jmp(ARMAssembler::AL, true), Call::LinkableNear);
     576#endif
    571577    }
    572578
    573579    Call call(RegisterID target)
    574580    {
    575         prepareCall();
    576         move(ARMRegisters::pc, target);
     581        m_assembler.blx(target);
    577582        JmpSrc jmpSrc;
    578583        return Call(jmpSrc, Call::None);
     
    586591    void ret()
    587592    {
    588         m_assembler.mov_r(ARMRegisters::pc, linkRegister);
     593        m_assembler.bx(linkRegister);
    589594    }
    590595
     
    682687    Call call()
    683688    {
     689#if WTF_ARM_ARCH_AT_LEAST(5)
     690        ensureSpace(2 * sizeof(ARMWord), sizeof(ARMWord));
     691        m_assembler.loadBranchTarget(ARMRegisters::S1, ARMAssembler::AL, true);
     692        return Call(m_assembler.blx(ARMRegisters::S1), Call::Linkable);
     693#else
    684694        prepareCall();
    685695        return Call(m_assembler.jmp(ARMAssembler::AL, true), Call::Linkable);
     696#endif
    686697    }
    687698
     
    887898    void prepareCall()
    888899    {
     900#if WTF_ARM_ARCH_VERSION < 5
    889901        ensureSpace(2 * sizeof(ARMWord), sizeof(ARMWord));
    890902
    891903        m_assembler.mov_r(linkRegister, ARMRegisters::pc);
     904#endif
    892905    }
    893906
    894907    void call32(RegisterID base, int32_t offset)
    895908    {
     909#if WTF_ARM_ARCH_AT_LEAST(5)
     910        int targetReg = ARMRegisters::S1;
     911#else
     912        int targetReg = ARMRegisters::pc;
     913#endif
     914        int tmpReg = ARMRegisters::S1;
     915
    896916        if (base == ARMRegisters::sp)
    897917            offset += 4;
     
    900920            if (offset <= 0xfff) {
    901921                prepareCall();
    902                 m_assembler.dtr_u(true, ARMRegisters::pc, base, offset);
     922                m_assembler.dtr_u(true, targetReg, base, offset);
    903923            } else if (offset <= 0xfffff) {
    904                 m_assembler.add_r(ARMRegisters::S0, base, ARMAssembler::OP2_IMM | (offset >> 12) | (10 << 8));
     924                m_assembler.add_r(tmpReg, base, ARMAssembler::OP2_IMM | (offset >> 12) | (10 << 8));
    905925                prepareCall();
    906                 m_assembler.dtr_u(true, ARMRegisters::pc, ARMRegisters::S0, offset & 0xfff);
     926                m_assembler.dtr_u(true, targetReg, tmpReg, offset & 0xfff);
    907927            } else {
    908                 ARMWord reg = m_assembler.getImm(offset, ARMRegisters::S0);
     928                ARMWord reg = m_assembler.getImm(offset, tmpReg);
    909929                prepareCall();
    910                 m_assembler.dtr_ur(true, ARMRegisters::pc, base, reg);
     930                m_assembler.dtr_ur(true, targetReg, base, reg);
    911931            }
    912932        } else  {
     
    914934            if (offset <= 0xfff) {
    915935                prepareCall();
    916                 m_assembler.dtr_d(true, ARMRegisters::pc, base, offset);
     936                m_assembler.dtr_d(true, targetReg, base, offset);
    917937            } else if (offset <= 0xfffff) {
    918                 m_assembler.sub_r(ARMRegisters::S0, base, ARMAssembler::OP2_IMM | (offset >> 12) | (10 << 8));
     938                m_assembler.sub_r(tmpReg, base, ARMAssembler::OP2_IMM | (offset >> 12) | (10 << 8));
    919939                prepareCall();
    920                 m_assembler.dtr_d(true, ARMRegisters::pc, ARMRegisters::S0, offset & 0xfff);
     940                m_assembler.dtr_d(true, targetReg, tmpReg, offset & 0xfff);
    921941            } else {
    922                 ARMWord reg = m_assembler.getImm(offset, ARMRegisters::S0);
     942                ARMWord reg = m_assembler.getImm(offset, tmpReg);
    923943                prepareCall();
    924                 m_assembler.dtr_dr(true, ARMRegisters::pc, base, reg);
     944                m_assembler.dtr_dr(true, targetReg, base, reg);
    925945            }
    926946        }
     947#if WTF_ARM_ARCH_AT_LEAST(5)
     948        m_assembler.blx(targetReg);
     949#endif
    927950    }
    928951
Note: See TracChangeset for help on using the changeset viewer.