blob: 369063431fefcabfc4f2ba39d9ac7494cbfae362 [file] [log] [blame]
Jan Sjödin30a52de2011-02-28 21:45:04 +00001//===- lib/MC/MCELF.cpp - MC ELF ------------------------------------------===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9//
10// This file implements ELF object file writer information.
11//
12//===----------------------------------------------------------------------===//
13
Tim Northover5cc3dc82012-12-07 16:50:23 +000014#include "llvm/MC/MCELF.h"
Jan Sjödin30a52de2011-02-28 21:45:04 +000015#include "llvm/MC/MCAssembler.h"
16#include "llvm/MC/MCELFSymbolFlags.h"
17#include "llvm/MC/MCFixupKindInfo.h"
18#include "llvm/Support/ELF.h"
Jan Sjödin30a52de2011-02-28 21:45:04 +000019
20namespace llvm {
21
22void MCELF::SetBinding(MCSymbolData &SD, unsigned Binding) {
23 assert(Binding == ELF::STB_LOCAL || Binding == ELF::STB_GLOBAL ||
Rafael Espindola5fa925e2015-01-23 04:44:35 +000024 Binding == ELF::STB_WEAK || Binding == ELF::STB_GNU_UNIQUE);
Jan Sjödin30a52de2011-02-28 21:45:04 +000025 uint32_t OtherFlags = SD.getFlags() & ~(0xf << ELF_STB_Shift);
26 SD.setFlags(OtherFlags | (Binding << ELF_STB_Shift));
27}
28
29unsigned MCELF::GetBinding(const MCSymbolData &SD) {
30 uint32_t Binding = (SD.getFlags() & (0xf << ELF_STB_Shift)) >> ELF_STB_Shift;
31 assert(Binding == ELF::STB_LOCAL || Binding == ELF::STB_GLOBAL ||
Rafael Espindola5fa925e2015-01-23 04:44:35 +000032 Binding == ELF::STB_WEAK || Binding == ELF::STB_GNU_UNIQUE);
Jan Sjödin30a52de2011-02-28 21:45:04 +000033 return Binding;
34}
35
36void MCELF::SetType(MCSymbolData &SD, unsigned Type) {
37 assert(Type == ELF::STT_NOTYPE || Type == ELF::STT_OBJECT ||
38 Type == ELF::STT_FUNC || Type == ELF::STT_SECTION ||
Joerg Sonnenbergerfc184732013-10-29 01:06:17 +000039 Type == ELF::STT_COMMON || Type == ELF::STT_TLS ||
40 Type == ELF::STT_GNU_IFUNC);
Jan Sjödin30a52de2011-02-28 21:45:04 +000041
42 uint32_t OtherFlags = SD.getFlags() & ~(0xf << ELF_STT_Shift);
43 SD.setFlags(OtherFlags | (Type << ELF_STT_Shift));
44}
45
46unsigned MCELF::GetType(const MCSymbolData &SD) {
47 uint32_t Type = (SD.getFlags() & (0xf << ELF_STT_Shift)) >> ELF_STT_Shift;
48 assert(Type == ELF::STT_NOTYPE || Type == ELF::STT_OBJECT ||
49 Type == ELF::STT_FUNC || Type == ELF::STT_SECTION ||
Joerg Sonnenbergerfc184732013-10-29 01:06:17 +000050 Type == ELF::STT_COMMON || Type == ELF::STT_TLS || Type == ELF::STT_GNU_IFUNC);
Jan Sjödin30a52de2011-02-28 21:45:04 +000051 return Type;
52}
53
Jack Carter2f8d9d92013-02-19 21:57:35 +000054// Visibility is stored in the first two bits of st_other
55// st_other values are stored in the second byte of get/setFlags
Jan Sjödin30a52de2011-02-28 21:45:04 +000056void MCELF::SetVisibility(MCSymbolData &SD, unsigned Visibility) {
57 assert(Visibility == ELF::STV_DEFAULT || Visibility == ELF::STV_INTERNAL ||
58 Visibility == ELF::STV_HIDDEN || Visibility == ELF::STV_PROTECTED);
59
Rafael Espindolae90c1cb2011-05-16 16:17:21 +000060 uint32_t OtherFlags = SD.getFlags() & ~(0x3 << ELF_STV_Shift);
Jan Sjödin30a52de2011-02-28 21:45:04 +000061 SD.setFlags(OtherFlags | (Visibility << ELF_STV_Shift));
62}
63
Ulrich Weigand0a51abc2014-07-11 17:34:44 +000064unsigned MCELF::GetVisibility(const MCSymbolData &SD) {
Jan Sjödin30a52de2011-02-28 21:45:04 +000065 unsigned Visibility =
Rafael Espindolae90c1cb2011-05-16 16:17:21 +000066 (SD.getFlags() & (0x3 << ELF_STV_Shift)) >> ELF_STV_Shift;
Jan Sjödin30a52de2011-02-28 21:45:04 +000067 assert(Visibility == ELF::STV_DEFAULT || Visibility == ELF::STV_INTERNAL ||
68 Visibility == ELF::STV_HIDDEN || Visibility == ELF::STV_PROTECTED);
69 return Visibility;
70}
71
Jack Carter2f8d9d92013-02-19 21:57:35 +000072// Other is stored in the last six bits of st_other
73// st_other values are stored in the second byte of get/setFlags
74void MCELF::setOther(MCSymbolData &SD, unsigned Other) {
Logan Chienee365952013-12-05 00:34:11 +000075 uint32_t OtherFlags = SD.getFlags() & ~(0x3f << ELF_STO_Shift);
76 SD.setFlags(OtherFlags | (Other << ELF_STO_Shift));
Jack Carter2f8d9d92013-02-19 21:57:35 +000077}
78
Ulrich Weigand0a51abc2014-07-11 17:34:44 +000079unsigned MCELF::getOther(const MCSymbolData &SD) {
Jack Carter2f8d9d92013-02-19 21:57:35 +000080 unsigned Other =
Logan Chienee365952013-12-05 00:34:11 +000081 (SD.getFlags() & (0x3f << ELF_STO_Shift)) >> ELF_STO_Shift;
Jack Carter2f8d9d92013-02-19 21:57:35 +000082 return Other;
83}
84
Jan Sjödin30a52de2011-02-28 21:45:04 +000085}