ARMAssembler.cpp revision 4dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3
14f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project/* libs/pixelflinger/codeflinger/ARMAssembler.cpp
24f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project**
34f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project** Copyright 2006, The Android Open Source Project
44f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project**
54f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project** Licensed under the Apache License, Version 2.0 (the "License");
64f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project** you may not use this file except in compliance with the License.
74f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project** You may obtain a copy of the License at
84f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project**
94f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project**     http://www.apache.org/licenses/LICENSE-2.0
104f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project**
114f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project** Unless required by applicable law or agreed to in writing, software
124f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project** distributed under the License is distributed on an "AS IS" BASIS,
134f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
144f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project** See the License for the specific language governing permissions and
154f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project** limitations under the License.
164f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project*/
174f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
184f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#define LOG_TAG "ARMAssembler"
194f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
204f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#include <stdio.h>
214f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#include <stdlib.h>
224f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#include <cutils/log.h>
234f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#include <cutils/properties.h>
244f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
254f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if defined(WITH_LIB_HARDWARE)
262eef60297a0ca1433d0824d6d662efd402709cfdThe Android Open Source Project#include <hardware_legacy/qemu_tracing.h>
274f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
284f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
294f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#include <private/pixelflinger/ggl_context.h>
304f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
314f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#include "codeflinger/ARMAssembler.h"
324f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#include "codeflinger/CodeCache.h"
334f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#include "codeflinger/disassem.h"
344f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
354f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project// ----------------------------------------------------------------------------
364f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
374f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectnamespace android {
384f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
394f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project// ----------------------------------------------------------------------------
404f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if 0
414f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark -
424f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark ARMAssembler...
434f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
444f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
454f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source ProjectARMAssembler::ARMAssembler(const sp<Assembly>& assembly)
464f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    :   ARMAssemblerInterface(),
474f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        mAssembly(assembly)
484f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
494f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mBase = mPC = (uint32_t *)assembly->base();
504f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mDuration = ggl_system_time();
514f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if defined(WITH_LIB_HARDWARE)
524f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mQemuTracing = true;
534f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
544f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
554f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
564f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source ProjectARMAssembler::~ARMAssembler()
574f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
584f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
594f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
604f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectuint32_t* ARMAssembler::pc() const
614f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
624f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    return mPC;
634f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
644f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
654f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectuint32_t* ARMAssembler::base() const
664f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
674f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    return mBase;
684f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
694f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
704f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::reset()
714f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
724f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mBase = mPC = (uint32_t *)mAssembly->base();
734f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mBranchTargets.clear();
744f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mLabels.clear();
754f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mLabelsInverseMapping.clear();
764f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mComments.clear();
774f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
784f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
794f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project// ----------------------------------------------------------------------------
804f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
814f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::disassemble(const char* name)
824f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
834f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    if (name) {
844f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        printf("%s:\n", name);
854f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    }
864f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    size_t count = pc()-base();
874f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    uint32_t* i = base();
884f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    while (count--) {
894f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        ssize_t label = mLabelsInverseMapping.indexOfKey(i);
904f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        if (label >= 0) {
914f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project            printf("%s:\n", mLabelsInverseMapping.valueAt(label));
924f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        }
934f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        ssize_t comment = mComments.indexOfKey(i);
944f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        if (comment >= 0) {
954f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project            printf("; %s\n", mComments.valueAt(comment));
964f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        }
974f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        printf("%08x:    %08x    ", int(i), int(i[0]));
984f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        ::disassemble((u_int)i);
994f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        i++;
1004f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    }
1014f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
1024f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1034f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::comment(const char* string)
1044f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
1054f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mComments.add(mPC, string);
1064f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
1074f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1084f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::label(const char* theLabel)
1094f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
1104f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mLabels.add(theLabel, mPC);
1114f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mLabelsInverseMapping.add(mPC, theLabel);
1124f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
1134f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1144f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::B(int cc, const char* label)
1154f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
1164f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mBranchTargets.add(branch_target_t(label, mPC));
1174f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (0xA<<24) | 0;
1184f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
1194f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1204f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::BL(int cc, const char* label)
1214f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
1224f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mBranchTargets.add(branch_target_t(label, mPC));
1234f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (0xB<<24) | 0;
1244f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
1254f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1264f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if 0
1274f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark -
1284f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark Prolog/Epilog & Generate...
1294f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
1304f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1314f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1324f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::prolog()
1334f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
1344f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    // write dummy prolog code
1354f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mPrologPC = mPC;
1364f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    STM(AL, FD, SP, 1, LSAVED);
1374f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
1384f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1394f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::epilog(uint32_t touched)
1404f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
1414f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    touched &= LSAVED;
1424f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    if (touched) {
1434f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        // write prolog code
1444f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        uint32_t* pc = mPC;
1454f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        mPC = mPrologPC;
1464f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        STM(AL, FD, SP, 1, touched | LLR);
1474f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        mPC = pc;
1484f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        // write epilog code
1494f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        LDM(AL, FD, SP, 1, touched | LLR);
1504f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        BX(AL, LR);
1514f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    } else {   // heh, no registers to save!
1524f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        // write prolog code
1534f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        uint32_t* pc = mPC;
1544f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        mPC = mPrologPC;
1554f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        MOV(AL, 0, R0, R0); // NOP
1564f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        mPC = pc;
1574f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        // write epilog code
1584f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        BX(AL, LR);
1594f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    }
1604f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
1614f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1624f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectint ARMAssembler::generate(const char* name)
1634f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
1644f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    // fixup all the branches
1654f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    size_t count = mBranchTargets.size();
1664f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    while (count--) {
1674f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        const branch_target_t& bt = mBranchTargets[count];
1684f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        uint32_t* target_pc = mLabels.valueFor(bt.label);
1694f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        LOG_ALWAYS_FATAL_IF(!target_pc,
1704f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                "error resolving branch targets, target_pc is null");
1714f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int32_t offset = int32_t(target_pc - (bt.pc+2));
1724f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        *bt.pc |= offset & 0xFFFFFF;
1734f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    }
1744f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1754f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    mAssembly->resize( int(pc()-base())*4 );
1764f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1774f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    // the instruction cache is flushed by CodeCache
1784f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    const int64_t duration = ggl_system_time() - mDuration;
1794f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    const char * const format = "generated %s (%d ins) at [%p:%p] in %lld ns\n";
1804f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    LOGI(format, name, int(pc()-base()), base(), pc(), duration);
1814f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1824f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if defined(WITH_LIB_HARDWARE)
1834f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    if (__builtin_expect(mQemuTracing, 0)) {
1844f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int err = qemu_add_mapping(int(base()), name);
1854f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        mQemuTracing = (err >= 0);
1864f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    }
1874f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
1884f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1894f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    char value[PROPERTY_VALUE_MAX];
1904f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    property_get("debug.pf.disasm", value, "0");
1914f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    if (atoi(value) != 0) {
1924f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        printf(format, name, int(pc()-base()), base(), pc(), duration);
1934f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        disassemble(name);
1944f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    }
1954f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1964f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    return NO_ERROR;
1974f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
1984f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
1994f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectuint32_t* ARMAssembler::pcForLabel(const char* label)
2004f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
2014f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    return mLabels.valueFor(label);
2024f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2034f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2044f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project// ----------------------------------------------------------------------------
2054f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2064f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if 0
2074f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark -
2084f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark Data Processing...
2094f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
2104f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2114f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::dataProcessing(int opcode, int cc,
2124f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int s, int Rd, int Rn, uint32_t Op2)
2134f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
2144f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (opcode<<21) | (s<<20) | (Rn<<16) | (Rd<<12) | Op2;
2154f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2164f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2174f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if 0
2184f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark -
2194f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark Multiply...
2204f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
2214f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2224f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project// multiply...
2234f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::MLA(int cc, int s,
2244f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int Rd, int Rm, int Rs, int Rn) {
2254f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    if (Rd == Rm) { int t = Rm; Rm=Rs; Rs=t; }
2264f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    LOG_FATAL_IF(Rd==Rm, "MLA(r%u,r%u,r%u,r%u)", Rd,Rm,Rs,Rn);
2274f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ =    (cc<<28) | (1<<21) | (s<<20) |
2284f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                (Rd<<16) | (Rn<<12) | (Rs<<8) | 0x90 | Rm;
2294f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2304f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::MUL(int cc, int s,
2314f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int Rd, int Rm, int Rs) {
2324f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    if (Rd == Rm) { int t = Rm; Rm=Rs; Rs=t; }
2334f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    LOG_FATAL_IF(Rd==Rm, "MUL(r%u,r%u,r%u)", Rd,Rm,Rs);
2344f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (s<<20) | (Rd<<16) | (Rs<<8) | 0x90 | Rm;
2354f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2364f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::UMULL(int cc, int s,
2374f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int RdLo, int RdHi, int Rm, int Rs) {
2384f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    LOG_FATAL_IF(RdLo==Rm || RdHi==Rm || RdLo==RdHi,
2394f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                        "UMULL(r%u,r%u,r%u,r%u)", RdLo,RdHi,Rm,Rs);
2404f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ =    (cc<<28) | (1<<23) | (s<<20) |
2414f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                (RdHi<<16) | (RdLo<<12) | (Rs<<8) | 0x90 | Rm;
2424f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2434f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::UMUAL(int cc, int s,
2444f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int RdLo, int RdHi, int Rm, int Rs) {
2454f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    LOG_FATAL_IF(RdLo==Rm || RdHi==Rm || RdLo==RdHi,
2464f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                        "UMUAL(r%u,r%u,r%u,r%u)", RdLo,RdHi,Rm,Rs);
2474f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ =    (cc<<28) | (1<<23) | (1<<21) | (s<<20) |
2484f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                (RdHi<<16) | (RdLo<<12) | (Rs<<8) | 0x90 | Rm;
2494f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2504f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::SMULL(int cc, int s,
2514f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int RdLo, int RdHi, int Rm, int Rs) {
2524f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    LOG_FATAL_IF(RdLo==Rm || RdHi==Rm || RdLo==RdHi,
2534f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                        "SMULL(r%u,r%u,r%u,r%u)", RdLo,RdHi,Rm,Rs);
2544f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ =    (cc<<28) | (1<<23) | (1<<22) | (s<<20) |
2554f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                (RdHi<<16) | (RdLo<<12) | (Rs<<8) | 0x90 | Rm;
2564f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2574f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::SMUAL(int cc, int s,
2584f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int RdLo, int RdHi, int Rm, int Rs) {
2594f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    LOG_FATAL_IF(RdLo==Rm || RdHi==Rm || RdLo==RdHi,
2604f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                        "SMUAL(r%u,r%u,r%u,r%u)", RdLo,RdHi,Rm,Rs);
2614f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ =    (cc<<28) | (1<<23) | (1<<22) | (1<<21) | (s<<20) |
2624f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                (RdHi<<16) | (RdLo<<12) | (Rs<<8) | 0x90 | Rm;
2634f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2644f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2654f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if 0
2664f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark -
2674f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark Branches...
2684f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
2694f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2704f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project// branches...
2714f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::B(int cc, uint32_t* pc)
2724f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
2734f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    int32_t offset = int32_t(pc - (mPC+2));
2744f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (0xA<<24) | (offset & 0xFFFFFF);
2754f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2764f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2774f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::BL(int cc, uint32_t* pc)
2784f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
2794f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    int32_t offset = int32_t(pc - (mPC+2));
2804f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (0xB<<24) | (offset & 0xFFFFFF);
2814f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2824f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2834f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::BX(int cc, int Rn)
2844f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
2854f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x12FFF10 | Rn;
2864f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2874f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2884f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if 0
2894f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark -
2904f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark Data Transfer...
2914f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
2924f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
2934f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project// data transfert...
2944f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::LDR(int cc, int Rd, int Rn, uint32_t offset) {
2954f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (1<<26) | (1<<20) | (Rn<<16) | (Rd<<12) | offset;
2964f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
2974f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::LDRB(int cc, int Rd, int Rn, uint32_t offset) {
2984f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (1<<26) | (1<<22) | (1<<20) | (Rn<<16) | (Rd<<12) | offset;
2994f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3004f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::STR(int cc, int Rd, int Rn, uint32_t offset) {
3014f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (1<<26) | (Rn<<16) | (Rd<<12) | offset;
3024f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3034f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::STRB(int cc, int Rd, int Rn, uint32_t offset) {
3044f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (1<<26) | (1<<22) | (Rn<<16) | (Rd<<12) | offset;
3054f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3064f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3074f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::LDRH(int cc, int Rd, int Rn, uint32_t offset) {
3084f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (1<<20) | (Rn<<16) | (Rd<<12) | 0xB0 | offset;
3094f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3104f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::LDRSB(int cc, int Rd, int Rn, uint32_t offset) {
3114f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (1<<20) | (Rn<<16) | (Rd<<12) | 0xD0 | offset;
3124f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3134f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::LDRSH(int cc, int Rd, int Rn, uint32_t offset) {
3144f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (1<<20) | (Rn<<16) | (Rd<<12) | 0xF0 | offset;
3154f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3164f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::STRH(int cc, int Rd, int Rn, uint32_t offset) {
3174f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (Rn<<16) | (Rd<<12) | 0xB0 | offset;
3184f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3194f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3204f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if 0
3214f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark -
3224f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark Block Data Transfer...
3234f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
3244f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3254f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project// block data transfer...
3264f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::LDM(int cc, int dir,
3274f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int Rn, int W, uint32_t reg_list)
3284f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{   //                    ED FD EA FA      IB IA DB DA
3294f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    const uint8_t P[8] = { 1, 0, 1, 0,      1, 0, 1, 0 };
3304f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    const uint8_t U[8] = { 1, 1, 0, 0,      1, 1, 0, 0 };
3314f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (4<<25) | (uint32_t(P[dir])<<24) |
3324f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project            (uint32_t(U[dir])<<23) | (1<<20) | (W<<21) | (Rn<<16) | reg_list;
3334f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3344f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3354f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::STM(int cc, int dir,
3364f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project        int Rn, int W, uint32_t reg_list)
3374f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{   //                    FA EA FD ED      IB IA DB DA
3384f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    const uint8_t P[8] = { 0, 1, 0, 1,      1, 0, 1, 0 };
3394f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    const uint8_t U[8] = { 0, 0, 1, 1,      1, 1, 0, 0 };
3404f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (4<<25) | (uint32_t(P[dir])<<24) |
3414f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project            (uint32_t(U[dir])<<23) | (0<<20) | (W<<21) | (Rn<<16) | reg_list;
3424f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3434f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3444f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if 0
3454f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark -
3464f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark Special...
3474f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
3484f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3494f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project// special...
3504f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::SWP(int cc, int Rn, int Rd, int Rm) {
3514f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (2<<23) | (Rn<<16) | (Rd << 12) | 0x90 | Rm;
3524f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3534f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::SWPB(int cc, int Rn, int Rd, int Rm) {
3544f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (2<<23) | (1<<22) | (Rn<<16) | (Rd << 12) | 0x90 | Rm;
3554f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3564f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::SWI(int cc, uint32_t comment) {
3574f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | (0xF<<24) | comment;
3584f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3594f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3604f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#if 0
3614f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark -
3624f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#pragma mark DSP instructions...
3634f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project#endif
3644f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3654f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project// DSP instructions...
3664f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::PLD(int Rn, uint32_t offset) {
3674f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    LOG_ALWAYS_FATAL_IF(!((offset&(1<<24)) && !(offset&(1<<21))),
3684f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                        "PLD only P=1, W=0");
3694f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = 0xF550F000 | (Rn<<16) | offset;
3704f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3714f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3724f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::CLZ(int cc, int Rd, int Rm)
3734f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
3744f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x16F0F10| (Rd<<12) | Rm;
3754f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3764f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3774f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::QADD(int cc,  int Rd, int Rm, int Rn)
3784f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
3794f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x1000050 | (Rn<<16) | (Rd<<12) | Rm;
3804f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3814f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3824f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::QDADD(int cc,  int Rd, int Rm, int Rn)
3834f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
3844f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x1400050 | (Rn<<16) | (Rd<<12) | Rm;
3854f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3864f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3874f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::QSUB(int cc,  int Rd, int Rm, int Rn)
3884f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
3894f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x1200050 | (Rn<<16) | (Rd<<12) | Rm;
3904f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3914f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3924f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::QDSUB(int cc,  int Rd, int Rm, int Rn)
3934f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
3944f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x1600050 | (Rn<<16) | (Rd<<12) | Rm;
3954f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
3964f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
3974f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::SMUL(int cc, int xy,
3984f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                int Rd, int Rm, int Rs)
3994f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
4004f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x1600080 | (Rd<<16) | (Rs<<8) | (xy<<4) | Rm;
4014f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
4024f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
4034f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::SMULW(int cc, int y,
4044f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                int Rd, int Rm, int Rs)
4054f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
4064f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x12000A0 | (Rd<<16) | (Rs<<8) | (y<<4) | Rm;
4074f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
4084f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
4094f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::SMLA(int cc, int xy,
4104f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                int Rd, int Rm, int Rs, int Rn)
4114f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
4124f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x1000080 | (Rd<<16) | (Rn<<12) | (Rs<<8) | (xy<<4) | Rm;
4134f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
4144f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
4154f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::SMLAL(int cc, int xy,
4164f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                int RdHi, int RdLo, int Rs, int Rm)
4174f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
4184f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x1400080 | (RdHi<<16) | (RdLo<<12) | (Rs<<8) | (xy<<4) | Rm;
4194f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
4204f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
4214f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Projectvoid ARMAssembler::SMLAW(int cc, int y,
4224f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project                int Rd, int Rm, int Rs, int Rn)
4234f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project{
4244f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project    *mPC++ = (cc<<28) | 0x1200080 | (Rd<<16) | (Rn<<12) | (Rs<<8) | (y<<4) | Rm;
4254f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}
4264f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
42796dbb4fc58fe2dcf4390e073dbb42cc77ef2f0b5Martyn Capewell#if 0
42896dbb4fc58fe2dcf4390e073dbb42cc77ef2f0b5Martyn Capewell#pragma mark -
42996dbb4fc58fe2dcf4390e073dbb42cc77ef2f0b5Martyn Capewell#pragma mark Byte/half word extract and extend (ARMv6+ only)...
43096dbb4fc58fe2dcf4390e073dbb42cc77ef2f0b5Martyn Capewell#endif
43196dbb4fc58fe2dcf4390e073dbb42cc77ef2f0b5Martyn Capewell
43296dbb4fc58fe2dcf4390e073dbb42cc77ef2f0b5Martyn Capewellvoid ARMAssembler::UXTB16(int cc, int Rd, int Rm, int rotate)
43396dbb4fc58fe2dcf4390e073dbb42cc77ef2f0b5Martyn Capewell{
43496dbb4fc58fe2dcf4390e073dbb42cc77ef2f0b5Martyn Capewell    *mPC++ = (cc<<28) | 0x6CF0070 | (Rd<<12) | ((rotate >> 3) << 10) | Rm;
43596dbb4fc58fe2dcf4390e073dbb42cc77ef2f0b5Martyn Capewell}
4364dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3Martyn Capewell#if 0
4374dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3Martyn Capewell#pragma mark -
4384dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3Martyn Capewell#pragma mark Bit manipulation (ARMv7+ only)...
4394dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3Martyn Capewell#endif
4404dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3Martyn Capewell
4414dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3Martyn Capewell// Bit manipulation (ARMv7+ only)...
4424dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3Martyn Capewellvoid ARMAssembler::UBFX(int cc, int Rd, int Rn, int lsb, int width)
4434dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3Martyn Capewell{
4444dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3Martyn Capewell    *mPC++ = (cc<<28) | 0x7E00000 | ((width-1)<<16) | (Rd<<12) | (lsb<<7) | 0x50 | Rn;
4454dc1fa8e8d1f14868ab8bba93a8cbb87f847c4e3Martyn Capewell}
44696dbb4fc58fe2dcf4390e073dbb42cc77ef2f0b5Martyn Capewell
4474f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project}; // namespace android
4484f6e8d7a00cbeda1e70cc15be9c4af1018bdad5The Android Open Source Project
449