| /* |
| * Copyright 2013, The Android Open Source Project |
| * |
| * Licensed under the Apache License, Version 2.0 (the "License"); |
| * you may not use this file except in compliance with the License. |
| * You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| |
| #ifndef ABCC_ABCC_H |
| #define ABCC_ABCC_H |
| |
| #include <list> |
| #include <map> |
| #include <string> |
| #include <vector> |
| |
| namespace abcc { |
| |
| enum ReturnCode { |
| RET_OK, |
| RET_FAIL_RUN_CMD, |
| RET_FAIL_UNSUPPORT_ABI, |
| RET_FAIL_PREPARE_BITCODE, |
| RET_FAIL_PREPARE_TOOL, |
| RET_FAIL_CLEANUP, |
| RET_FAIL_TRANSLATE, |
| RET_FAIL_COMPILE, |
| RET_FAIL_LINK |
| }; |
| |
| enum Command { |
| CMD_TRANSLATE = 0, |
| CMD_COMPILE, |
| CMD_LINK, |
| CMD_LINK_RUNTIME |
| }; |
| |
| class TargetAbi { |
| public: |
| enum Abi { |
| ARMEABI = 0, |
| ARMEABI_V7A, |
| X86, |
| MIPS |
| }; |
| |
| private: |
| Abi mAbi; |
| |
| public: |
| TargetAbi(const std::string &abi); |
| operator int() const { return (int)mAbi; } |
| operator const char*() const { |
| if (mAbi == ARMEABI) return "armeabi"; |
| if (mAbi == ARMEABI_V7A) return "armeabi-v7a"; |
| if (mAbi == X86) return "x86"; |
| if (mAbi == MIPS) return "mips"; |
| return 0; |
| } |
| const char* getArch() const { |
| if (mAbi == ARMEABI || mAbi == ARMEABI_V7A) return "arm"; |
| if (mAbi == X86) return "x86"; |
| if (mAbi == MIPS) return "mips"; |
| return 0; |
| } |
| }; |
| |
| struct TargetAttributes { |
| const char *mArch; |
| const char *mTriple; |
| const char *mLinkEmulation; |
| const char *mBaseCFlags; |
| const char *mBaseLDFlags; |
| }; |
| |
| const TargetAttributes kGlobalTargetAttrs[] = { |
| {"arm", "armv5te-linux-androideabi", "armelf_linux_eabi", "", ""}, |
| #ifdef FORCE_ARM |
| {"arm", "armv7-linux-androideabi", "armelf_linux_eabi", "", ""}, |
| #else |
| {"arm", "thumbv7-linux-androideabi", "armelf_linux_eabi", "", ""}, |
| #endif |
| {"x86", "i686-linux-android", "elf_i386", "-disable-fp-elim -force-align-stack -mattr=-ssse3,-sse41,-sse42,-sse4a,-popcnt", ""}, |
| {"mips", "mipsel-linux-android", "elf32ltsmip", "", ""}, |
| }; |
| |
| // Used when computing mutual dependency |
| class BitcodeCompiler; |
| class BitcodeInfo; |
| typedef std::map<std::string/*soname*/, BitcodeInfo> SONameMap; |
| |
| class BitcodeInfo { |
| public: |
| BitcodeInfo() {} // Only for stl use |
| BitcodeInfo(const std::string &bc); |
| int readWrapper(BitcodeCompiler &); |
| static void dropExternalLDLibs(SONameMap &map); |
| |
| bool mShared; |
| int mOptimizationLevel; |
| std::string mBCPath; |
| std::string mTargetBCPath; |
| std::string mObjPath; |
| std::string mOutPath; |
| std::string mSOName; |
| std::string mLDFlags; // --no-undefined, ... |
| std::list<std::string> mLDLibs; // -lxxx, will be removed one-by-one until empty |
| std::string mLDLibsStr; // Immutable once read in |
| |
| public: |
| static int transferBytesToNumLe(const unsigned char *buffer, size_t n); |
| }; |
| |
| |
| class BitcodeCompiler { |
| protected: |
| TargetAbi mAbi; |
| std::string mSysroot; |
| std::string mWorkingDir; |
| |
| // Target-independent, but global |
| std::string mGlobalCFlags; |
| std::string mGlobalLDFlags; |
| std::string mGlobalLDLibs; |
| |
| ReturnCode mRet; |
| std::vector<BitcodeInfo> mBitcodeFiles; |
| SONameMap mSonameMap; |
| std::string mExecutableToolsPath[(unsigned)CMD_LINK_RUNTIME+1]; |
| |
| public: |
| BitcodeCompiler(const std::string &abi, const std::string &sysroot, const std::string &working_dir, const bool savetemps); |
| const ReturnCode returnCode() const { return mRet; } |
| virtual void cleanupPre() {} |
| virtual void cleanupPost() {} |
| void prepare() { |
| prepareBitcodes(); |
| if (returnCode() != RET_OK) |
| return; |
| |
| prepareToolchain(); |
| if (returnCode() != RET_OK) |
| return; |
| } |
| void execute() { |
| translate(); |
| if (returnCode() != RET_OK) |
| return; |
| |
| compile(); |
| if (returnCode() != RET_OK) |
| return; |
| |
| link(); |
| if (returnCode() != RET_OK) |
| return; |
| } |
| |
| private: |
| bool mSaveTemps; |
| |
| void prepareBitcodes(); |
| void createSONameMapping(); |
| virtual void getBitcodeFiles() = 0; |
| virtual void prepareToolchain() = 0; |
| virtual void copyRuntime(const BitcodeInfo &info) = 0; |
| virtual void removeIntermediateFile(const std::string &path) = 0; |
| void translate(); |
| void compile(); |
| void link(); |
| |
| public: |
| virtual int parseLDFlags(BitcodeInfo &info, const std::string &str) = 0; |
| |
| protected: |
| void runCmd(std::string cmd, bool dump = false); |
| }; |
| |
| } // namespace abcc |
| |
| // FIXME: We use LOGV, LOGE in Abcc.cpp, how to prevent this anti dependency? |
| #if ON_DEVICE |
| #include "Abcc_device.h" |
| #else |
| #include "Abcc_host.h" |
| #endif |
| |
| #endif |