1// Copyright 2015 Google Inc. All rights reserved. 2// 3// Licensed under the Apache License, Version 2.0 (the "License"); 4// you may not use this file except in compliance with the License. 5// You may obtain a copy of the License at 6// 7// http://www.apache.org/licenses/LICENSE-2.0 8// 9// Unless required by applicable law or agreed to in writing, software 10// distributed under the License is distributed on an "AS IS" BASIS, 11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12// See the License for the specific language governing permissions and 13// limitations under the License. 14 15package config 16 17import ( 18 "fmt" 19 "strings" 20 21 "android/soong/android" 22) 23 24var ( 25 armToolchainCflags = []string{ 26 "-msoft-float", 27 } 28 29 armCflags = []string{ 30 "-fomit-frame-pointer", 31 } 32 33 armCppflags = []string{} 34 35 armLdflags = []string{ 36 "-Wl,--hash-style=gnu", 37 "-Wl,-m,armelf", 38 } 39 40 armLldflags = armLdflags 41 42 armFixCortexA8LdFlags = []string{"-Wl,--fix-cortex-a8"} 43 44 armNoFixCortexA8LdFlags = []string{"-Wl,--no-fix-cortex-a8"} 45 46 armArmCflags = []string{ 47 "-fstrict-aliasing", 48 } 49 50 armThumbCflags = []string{ 51 "-mthumb", 52 "-Os", 53 } 54 55 armArchVariantCflags = map[string][]string{ 56 "armv7-a": []string{ 57 "-march=armv7-a", 58 "-mfloat-abi=softfp", 59 "-mfpu=vfpv3-d16", 60 }, 61 "armv7-a-neon": []string{ 62 "-march=armv7-a", 63 "-mfloat-abi=softfp", 64 "-mfpu=neon", 65 }, 66 "armv8-a": []string{ 67 "-march=armv8-a", 68 "-mfloat-abi=softfp", 69 "-mfpu=neon-fp-armv8", 70 }, 71 "armv8-2a": []string{ 72 "-march=armv8.2-a", 73 "-mfloat-abi=softfp", 74 "-mfpu=neon-fp-armv8", 75 }, 76 } 77 78 armCpuVariantCflags = map[string][]string{ 79 "cortex-a7": []string{ 80 "-mcpu=cortex-a7", 81 "-mfpu=neon-vfpv4", 82 // Fake an ARM compiler flag as these processors support LPAE which clang 83 // don't advertise. 84 // TODO This is a hack and we need to add it for each processor that supports LPAE until some 85 // better solution comes around. See Bug 27340895 86 "-D__ARM_FEATURE_LPAE=1", 87 }, 88 "cortex-a8": []string{ 89 "-mcpu=cortex-a8", 90 }, 91 "cortex-a15": []string{ 92 "-mcpu=cortex-a15", 93 "-mfpu=neon-vfpv4", 94 // Fake an ARM compiler flag as these processors support LPAE which clang 95 // don't advertise. 96 // TODO This is a hack and we need to add it for each processor that supports LPAE until some 97 // better solution comes around. See Bug 27340895 98 "-D__ARM_FEATURE_LPAE=1", 99 }, 100 "cortex-a32": []string{ 101 "-mcpu=cortex-a32", 102 "-mfpu=neon-vfpv4", 103 // Fake an ARM compiler flag as these processors support LPAE which clang 104 // don't advertise. 105 // TODO This is a hack and we need to add it for each processor that supports LPAE until some 106 // better solution comes around. See Bug 27340895 107 "-D__ARM_FEATURE_LPAE=1", 108 }, 109 "cortex-a53": []string{ 110 "-mcpu=cortex-a53", 111 "-mfpu=neon-fp-armv8", 112 // Fake an ARM compiler flag as these processors support LPAE which clang 113 // don't advertise. 114 // TODO This is a hack and we need to add it for each processor that supports LPAE until some 115 // better solution comes around. See Bug 27340895 116 "-D__ARM_FEATURE_LPAE=1", 117 }, 118 "cortex-a55": []string{ 119 "-mcpu=cortex-a55", 120 "-mfpu=neon-fp-armv8", 121 // Fake an ARM compiler flag as these processors support LPAE which clang 122 // don't advertise. 123 // TODO This is a hack and we need to add it for each processor that supports LPAE until some 124 // better solution comes around. See Bug 27340895 125 "-D__ARM_FEATURE_LPAE=1", 126 }, 127 "cortex-a75": []string{ 128 "-mcpu=cortex-a55", 129 "-mfpu=neon-fp-armv8", 130 // Fake an ARM compiler flag as these processors support LPAE which clang 131 // don't advertise. 132 // TODO This is a hack and we need to add it for each processor that supports LPAE until some 133 // better solution comes around. See Bug 27340895 134 "-D__ARM_FEATURE_LPAE=1", 135 }, 136 "cortex-a76": []string{ 137 "-mcpu=cortex-a55", 138 "-mfpu=neon-fp-armv8", 139 // Fake an ARM compiler flag as these processors support LPAE which clang 140 // don't advertise. 141 // TODO This is a hack and we need to add it for each processor that supports LPAE until some 142 // better solution comes around. See Bug 27340895 143 "-D__ARM_FEATURE_LPAE=1", 144 }, 145 "krait": []string{ 146 "-mcpu=krait", 147 "-mfpu=neon-vfpv4", 148 // Fake an ARM compiler flag as these processors support LPAE which clang 149 // don't advertise. 150 // TODO This is a hack and we need to add it for each processor that supports LPAE until some 151 // better solution comes around. See Bug 27340895 152 "-D__ARM_FEATURE_LPAE=1", 153 }, 154 "kryo": []string{ 155 // Use cortex-a53 because the GNU assembler doesn't recognize -mcpu=kryo 156 // even though clang does. 157 "-mcpu=cortex-a53", 158 "-mfpu=neon-fp-armv8", 159 // Fake an ARM compiler flag as these processors support LPAE which clang 160 // don't advertise. 161 // TODO This is a hack and we need to add it for each processor that supports LPAE until some 162 // better solution comes around. See Bug 27340895 163 "-D__ARM_FEATURE_LPAE=1", 164 }, 165 "kryo385": []string{ 166 // Use cortex-a53 because kryo385 is not supported in clang. 167 "-mcpu=cortex-a53", 168 // Fake an ARM compiler flag as these processors support LPAE which clang 169 // don't advertise. 170 // TODO This is a hack and we need to add it for each processor that supports LPAE until some 171 // better solution comes around. See Bug 27340895 172 "-D__ARM_FEATURE_LPAE=1", 173 }, 174 } 175) 176 177const ( 178 name = "arm" 179 ndkTriple = "arm-linux-androideabi" 180 clangTriple = "armv7a-linux-androideabi" 181) 182 183func init() { 184 // Just exported. Not created as a Ninja static variable. 185 exportedVars.ExportString("ArmClangTriple", clangTriple) 186 187 exportedVars.ExportStringListStaticVariable("ArmLdflags", armLdflags) 188 exportedVars.ExportStringList("ArmLldflags", armLldflags) 189 pctx.VariableFunc("ArmLldflags", func(ctx android.PackageVarContext) string { 190 maxPageSizeFlag := "-Wl,-z,max-page-size=" + ctx.Config().MaxPageSizeSupported() 191 flags := append(armLldflags, maxPageSizeFlag) 192 return strings.Join(flags, " ") 193 }) 194 195 exportedVars.ExportStringListStaticVariable("ArmFixCortexA8LdFlags", armFixCortexA8LdFlags) 196 exportedVars.ExportStringListStaticVariable("ArmNoFixCortexA8LdFlags", armNoFixCortexA8LdFlags) 197 198 // Clang cflags 199 exportedVars.ExportStringListStaticVariable("ArmToolchainCflags", armToolchainCflags) 200 exportedVars.ExportStringListStaticVariable("ArmCflags", armCflags) 201 exportedVars.ExportStringListStaticVariable("ArmCppflags", armCppflags) 202 203 // Clang ARM vs. Thumb instruction set cflags 204 exportedVars.ExportStringListStaticVariable("ArmArmCflags", armArmCflags) 205 exportedVars.ExportStringListStaticVariable("ArmThumbCflags", armThumbCflags) 206 207 exportedVars.ExportVariableReferenceDict("ArmArchVariantCflags", armArchVariantCflagsVar) 208 exportedVars.ExportVariableReferenceDict("ArmCpuVariantCflags", armCpuVariantCflagsVar) 209 210 // Clang arch variant cflags 211 exportedVars.ExportStringListStaticVariable("ArmArmv7ACflags", armArchVariantCflags["armv7-a"]) 212 exportedVars.ExportStringListStaticVariable("ArmArmv7ANeonCflags", armArchVariantCflags["armv7-a-neon"]) 213 exportedVars.ExportStringListStaticVariable("ArmArmv8ACflags", armArchVariantCflags["armv8-a"]) 214 exportedVars.ExportStringListStaticVariable("ArmArmv82ACflags", armArchVariantCflags["armv8-2a"]) 215 216 // Clang cpu variant cflags 217 exportedVars.ExportStringListStaticVariable("ArmGenericCflags", armCpuVariantCflags[""]) 218 exportedVars.ExportStringListStaticVariable("ArmCortexA7Cflags", armCpuVariantCflags["cortex-a7"]) 219 exportedVars.ExportStringListStaticVariable("ArmCortexA8Cflags", armCpuVariantCflags["cortex-a8"]) 220 exportedVars.ExportStringListStaticVariable("ArmCortexA15Cflags", armCpuVariantCflags["cortex-a15"]) 221 exportedVars.ExportStringListStaticVariable("ArmCortexA32Cflags", armCpuVariantCflags["cortex-a32"]) 222 exportedVars.ExportStringListStaticVariable("ArmCortexA53Cflags", armCpuVariantCflags["cortex-a53"]) 223 exportedVars.ExportStringListStaticVariable("ArmCortexA55Cflags", armCpuVariantCflags["cortex-a55"]) 224 exportedVars.ExportStringListStaticVariable("ArmKraitCflags", armCpuVariantCflags["krait"]) 225 exportedVars.ExportStringListStaticVariable("ArmKryoCflags", armCpuVariantCflags["kryo"]) 226} 227 228var ( 229 armArchVariantCflagsVar = map[string]string{ 230 "armv7-a": "${config.ArmArmv7ACflags}", 231 "armv7-a-neon": "${config.ArmArmv7ANeonCflags}", 232 "armv8-a": "${config.ArmArmv8ACflags}", 233 "armv8-2a": "${config.ArmArmv82ACflags}", 234 } 235 236 armCpuVariantCflagsVar = map[string]string{ 237 "": "${config.ArmGenericCflags}", 238 "cortex-a7": "${config.ArmCortexA7Cflags}", 239 "cortex-a8": "${config.ArmCortexA8Cflags}", 240 "cortex-a9": "${config.ArmGenericCflags}", 241 "cortex-a15": "${config.ArmCortexA15Cflags}", 242 "cortex-a32": "${config.ArmCortexA32Cflags}", 243 "cortex-a53": "${config.ArmCortexA53Cflags}", 244 "cortex-a53.a57": "${config.ArmCortexA53Cflags}", 245 "cortex-a55": "${config.ArmCortexA55Cflags}", 246 "cortex-a72": "${config.ArmCortexA53Cflags}", 247 "cortex-a73": "${config.ArmCortexA53Cflags}", 248 "cortex-a75": "${config.ArmCortexA55Cflags}", 249 "cortex-a76": "${config.ArmCortexA55Cflags}", 250 "krait": "${config.ArmKraitCflags}", 251 "kryo": "${config.ArmKryoCflags}", 252 "kryo385": "${config.ArmCortexA53Cflags}", 253 "exynos-m1": "${config.ArmCortexA53Cflags}", 254 "exynos-m2": "${config.ArmCortexA53Cflags}", 255 } 256) 257 258type toolchainArm struct { 259 toolchainBionic 260 toolchain32Bit 261 ldflags string 262 lldflags string 263 toolchainCflags string 264} 265 266func (t *toolchainArm) Name() string { 267 return name 268} 269 270func (t *toolchainArm) IncludeFlags() string { 271 return "" 272} 273 274func (t *toolchainArm) ClangTriple() string { 275 // http://b/72619014 work around llvm LTO bug. 276 return clangTriple 277} 278 279func (t *toolchainArm) ndkTriple() string { 280 // Use current NDK include path, while ClangTriple is changed. 281 return ndkTriple 282} 283 284func (t *toolchainArm) ToolchainCflags() string { 285 return t.toolchainCflags 286} 287 288func (t *toolchainArm) Cflags() string { 289 return "${config.ArmCflags}" 290} 291 292func (t *toolchainArm) Cppflags() string { 293 return "${config.ArmCppflags}" 294} 295 296func (t *toolchainArm) Ldflags() string { 297 return t.ldflags 298} 299 300func (t *toolchainArm) Lldflags() string { 301 return t.lldflags // TODO: handle V8 cases 302} 303 304func (t *toolchainArm) InstructionSetFlags(isa string) (string, error) { 305 switch isa { 306 case "arm": 307 return "${config.ArmArmCflags}", nil 308 case "thumb", "": 309 return "${config.ArmThumbCflags}", nil 310 default: 311 return t.toolchainBase.InstructionSetFlags(isa) 312 } 313} 314 315func (toolchainArm) LibclangRuntimeLibraryArch() string { 316 return name 317} 318 319func armToolchainFactory(arch android.Arch) Toolchain { 320 var fixCortexA8 string 321 toolchainCflags := make([]string, 2, 3) 322 323 toolchainCflags[0] = "${config.ArmToolchainCflags}" 324 toolchainCflags[1] = armArchVariantCflagsVar[arch.ArchVariant] 325 326 toolchainCflags = append(toolchainCflags, 327 variantOrDefault(armCpuVariantCflagsVar, arch.CpuVariant)) 328 329 switch arch.ArchVariant { 330 case "armv7-a-neon": 331 switch arch.CpuVariant { 332 case "cortex-a8", "": 333 // Generic ARM might be a Cortex A8 -- better safe than sorry 334 fixCortexA8 = "${config.ArmFixCortexA8LdFlags}" 335 default: 336 fixCortexA8 = "${config.ArmNoFixCortexA8LdFlags}" 337 } 338 case "armv7-a": 339 fixCortexA8 = "${config.ArmFixCortexA8LdFlags}" 340 case "armv8-a", "armv8-2a": 341 // Nothing extra for armv8-a/armv8-2a 342 default: 343 panic(fmt.Sprintf("Unknown ARM architecture version: %q", arch.ArchVariant)) 344 } 345 346 return &toolchainArm{ 347 ldflags: strings.Join([]string{ 348 "${config.ArmLdflags}", 349 fixCortexA8, 350 }, " "), 351 lldflags: "${config.ArmLldflags}", 352 toolchainCflags: strings.Join(toolchainCflags, " "), 353 } 354} 355 356func init() { 357 registerToolchainFactory(android.Android, android.Arm, armToolchainFactory) 358} 359