1 // Copyright 2019 the V8 project authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "src/snapshot/embedded/platform-embedded-file-writer-base.h"
6
7 #include <string>
8
9 #include "src/common/globals.h"
10 #include "src/snapshot/embedded/platform-embedded-file-writer-aix.h"
11 #include "src/snapshot/embedded/platform-embedded-file-writer-generic.h"
12 #include "src/snapshot/embedded/platform-embedded-file-writer-mac.h"
13 #include "src/snapshot/embedded/platform-embedded-file-writer-win.h"
14
15 namespace v8 {
16 namespace internal {
17
PointerSizeDirective()18 DataDirective PointerSizeDirective() {
19 if (kSystemPointerSize == 8) {
20 return kQuad;
21 } else {
22 CHECK_EQ(4, kSystemPointerSize);
23 return kLong;
24 }
25 }
26
HexLiteral(uint64_t value)27 int PlatformEmbeddedFileWriterBase::HexLiteral(uint64_t value) {
28 return fprintf(fp_, "0x%" PRIx64, value);
29 }
30
DataDirectiveSize(DataDirective directive)31 int DataDirectiveSize(DataDirective directive) {
32 switch (directive) {
33 case kByte:
34 return 1;
35 case kLong:
36 return 4;
37 case kQuad:
38 return 8;
39 case kOcta:
40 return 16;
41 }
42 UNREACHABLE();
43 }
44
WriteByteChunk(const uint8_t * data)45 int PlatformEmbeddedFileWriterBase::WriteByteChunk(const uint8_t* data) {
46 size_t kSize = DataDirectiveSize(ByteChunkDataDirective());
47 size_t kHalfSize = kSize / 2;
48 uint64_t high = 0, low = 0;
49
50 switch (kSize) {
51 case 1:
52 low = *data;
53 break;
54 case 4:
55 low = *reinterpret_cast<const uint32_t*>(data);
56 break;
57 case 8:
58 low = *reinterpret_cast<const uint64_t*>(data);
59 break;
60 case 16:
61 #ifdef V8_TARGET_BIG_ENDIAN
62 memcpy(&high, data, kHalfSize);
63 memcpy(&low, data + kHalfSize, kHalfSize);
64 #else
65 memcpy(&high, data + kHalfSize, kHalfSize);
66 memcpy(&low, data, kHalfSize);
67 #endif // V8_TARGET_BIG_ENDIAN
68 break;
69 default:
70 UNREACHABLE();
71 }
72
73 if (high != 0) {
74 return fprintf(fp(), "0x%" PRIx64 "%016" PRIx64, high, low);
75 } else {
76 return fprintf(fp(), "0x%" PRIx64, low);
77 }
78 }
79
80 namespace {
81
DefaultEmbeddedTargetArch()82 EmbeddedTargetArch DefaultEmbeddedTargetArch() {
83 #if defined(V8_TARGET_ARCH_ARM)
84 return EmbeddedTargetArch::kArm;
85 #elif defined(V8_TARGET_ARCH_ARM64)
86 return EmbeddedTargetArch::kArm64;
87 #elif defined(V8_TARGET_ARCH_IA32)
88 return EmbeddedTargetArch::kIA32;
89 #elif defined(V8_TARGET_ARCH_X64)
90 return EmbeddedTargetArch::kX64;
91 #else
92 return EmbeddedTargetArch::kGeneric;
93 #endif
94 }
95
ToEmbeddedTargetArch(const char * s)96 EmbeddedTargetArch ToEmbeddedTargetArch(const char* s) {
97 if (s == nullptr) {
98 return DefaultEmbeddedTargetArch();
99 }
100
101 std::string string(s);
102 if (string == "arm") {
103 return EmbeddedTargetArch::kArm;
104 } else if (string == "arm64") {
105 return EmbeddedTargetArch::kArm64;
106 } else if (string == "ia32") {
107 return EmbeddedTargetArch::kIA32;
108 } else if (string == "x64") {
109 return EmbeddedTargetArch::kX64;
110 } else {
111 return EmbeddedTargetArch::kGeneric;
112 }
113 }
114
DefaultEmbeddedTargetOs()115 EmbeddedTargetOs DefaultEmbeddedTargetOs() {
116 #if defined(V8_OS_AIX)
117 return EmbeddedTargetOs::kAIX;
118 #elif defined(V8_OS_MACOSX)
119 return EmbeddedTargetOs::kMac;
120 #elif defined(V8_OS_WIN)
121 return EmbeddedTargetOs::kWin;
122 #else
123 return EmbeddedTargetOs::kGeneric;
124 #endif
125 }
126
ToEmbeddedTargetOs(const char * s)127 EmbeddedTargetOs ToEmbeddedTargetOs(const char* s) {
128 if (s == nullptr) {
129 return DefaultEmbeddedTargetOs();
130 }
131
132 std::string string(s);
133 if (string == "aix") {
134 return EmbeddedTargetOs::kAIX;
135 } else if (string == "chromeos") {
136 return EmbeddedTargetOs::kChromeOS;
137 } else if (string == "fuchsia") {
138 return EmbeddedTargetOs::kFuchsia;
139 } else if (string == "ios" || string == "mac") {
140 return EmbeddedTargetOs::kMac;
141 } else if (string == "win") {
142 return EmbeddedTargetOs::kWin;
143 } else {
144 return EmbeddedTargetOs::kGeneric;
145 }
146 }
147
148 } // namespace
149
NewPlatformEmbeddedFileWriter(const char * target_arch,const char * target_os)150 std::unique_ptr<PlatformEmbeddedFileWriterBase> NewPlatformEmbeddedFileWriter(
151 const char* target_arch, const char* target_os) {
152 auto embedded_target_arch = ToEmbeddedTargetArch(target_arch);
153 auto embedded_target_os = ToEmbeddedTargetOs(target_os);
154
155 if (embedded_target_os == EmbeddedTargetOs::kAIX) {
156 return std::make_unique<PlatformEmbeddedFileWriterAIX>(embedded_target_arch,
157 embedded_target_os);
158 } else if (embedded_target_os == EmbeddedTargetOs::kMac) {
159 return std::make_unique<PlatformEmbeddedFileWriterMac>(embedded_target_arch,
160 embedded_target_os);
161 } else if (embedded_target_os == EmbeddedTargetOs::kWin) {
162 return std::make_unique<PlatformEmbeddedFileWriterWin>(embedded_target_arch,
163 embedded_target_os);
164 } else {
165 return std::make_unique<PlatformEmbeddedFileWriterGeneric>(
166 embedded_target_arch, embedded_target_os);
167 }
168
169 UNREACHABLE();
170 }
171
172 } // namespace internal
173 } // namespace v8
174