Implement global merge optimization for global variables.

This commit implements two command line switches -global-merge-on-external
and -global-merge-aligned, and both of them are false by default, so this
optimization is disabled by default for all targets.

For ARM64, some back-end behaviors need to be tuned to get this optimization
further enabled.



git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@208934 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Jiangning Liu
2014-05-15 23:45:42 +00:00
parent 01a02d91dc
commit d5db8765d6
20 changed files with 448 additions and 68 deletions

View File

@@ -0,0 +1,22 @@
; RUN: opt %s -mtriple=aarch64-none-linux-gnu -global-merge -S -o - | FileCheck %s
; RUN: opt %s -mtriple=aarch64-none-linux-gnu -global-merge -global-merge-on-external -global-merge-aligned -S -o - | FileCheck %s
; RUN: opt %s -mtriple=arm64-linux-gnuabi -global-merge -S -o - | FileCheck %s
; RUN: opt %s -mtriple=arm64-linux-gnuabi -global-merge -global-merge-on-external -global-merge-aligned -S -o - | FileCheck %s
; RUN: opt %s -mtriple=arm64-apple-ios -global-merge -S -o - | FileCheck %s
; RUN: opt %s -mtriple=arm64-apple-ios -global-merge -global-merge-on-external -global-merge-aligned -S -o - | FileCheck %s
@m = internal global i32 0, align 4
@n = internal global i32 0, align 4
; CHECK: @_MergedGlobals = internal global { i32, i32 } zeroinitializer
define void @f1(i32 %a1, i32 %a2) {
; CHECK-LABEL: @f1
; CHECK: getelementptr inbounds ({ i32, i32 }* @_MergedGlobals, i32 0, i32 0)
; CHECK: getelementptr inbounds ({ i32, i32 }* @_MergedGlobals, i32 0, i32 1)
store i32 %a1, i32* @m, align 4
store i32 %a2, i32* @n, align 4
ret void
}

View File

@@ -0,0 +1,30 @@
; RUN: opt %s -mtriple=aarch64-none-linux-gnu -global-merge -global-merge-on-external -global-merge-aligned -S -o - | FileCheck %s
; RUN: opt %s -mtriple=arm64-linux-gnuabi -global-merge -global-merge-on-external -global-merge-aligned -S -o - | FileCheck %s
; RUN: opt %s -mtriple=arm64-apple-ios -global-merge -global-merge-on-external -global-merge-aligned -S -o - | FileCheck %s
@x = global i32 0, align 4
@y = global i32 0, align 4
@z = global i32 0, align 4
; CHECK: @_MergedGlobals_x = global { i32, i32, i32 } zeroinitializer, align 16
; CHECK: @x = alias getelementptr inbounds ({ i32, i32, i32 }* @_MergedGlobals_x, i32 0, i32 0)
; CHECK: @y = alias getelementptr inbounds ({ i32, i32, i32 }* @_MergedGlobals_x, i32 0, i32 1)
; CHECK: @z = alias getelementptr inbounds ({ i32, i32, i32 }* @_MergedGlobals_x, i32 0, i32 2)
define void @f1(i32 %a1, i32 %a2) {
; CHECK-LABEL: @f1
; CHECK: getelementptr inbounds ({ i32, i32, i32 }* @_MergedGlobals_x, i32 0, i32 0)
; CHECK: getelementptr inbounds ({ i32, i32, i32 }* @_MergedGlobals_x, i32 0, i32 1)
store i32 %a1, i32* @x, align 4
store i32 %a2, i32* @y, align 4
ret void
}
define void @g1(i32 %a1, i32 %a2) {
; CHECK-LABEL: @g1
; CHECK: getelementptr inbounds ({ i32, i32, i32 }* @_MergedGlobals_x, i32 0, i32 1)
; CHECK: getelementptr inbounds ({ i32, i32, i32 }* @_MergedGlobals_x, i32 0, i32 2)
store i32 %a1, i32* @y, align 4
store i32 %a2, i32* @z, align 4
ret void
}

View File

@@ -0,0 +1,27 @@
; RUN: opt %s -mtriple=aarch64-none-linux-gnu -global-merge -global-merge-on-external -global-merge-aligned -S -o - | FileCheck %s
; RUN: opt %s -mtriple=arm64-linux-gnuabi -global-merge -global-merge-on-external -global-merge-aligned -S -o - | FileCheck %s
; RUN: opt %s -mtriple=arm64-apple-ios -global-merge -global-merge-on-external -global-merge-aligned -S -o - | FileCheck %s
@x = global [1000 x i32] zeroinitializer, align 1
@y = global [1000 x i32] zeroinitializer, align 1
@z = internal global i32 1, align 4
; CHECK: @_MergedGlobals_x = global { i32, [1000 x i32] } { i32 1, [1000 x i32] zeroinitializer }, align 4096
; CHECK: @_MergedGlobals_y = global { [1000 x i32] } zeroinitializer, align 4096
; CHECK: @x = alias getelementptr inbounds ({ i32, [1000 x i32] }* @_MergedGlobals_x, i32 0, i32 1)
; CHECK: @y = alias getelementptr inbounds ({ [1000 x i32] }* @_MergedGlobals_y, i32 0, i32 0)
define void @f1(i32 %a1, i32 %a2, i32 %a3) {
; CHECK-LABEL: @f1
; CHECK: %x3 = getelementptr inbounds [1000 x i32]* getelementptr inbounds ({ i32, [1000 x i32] }* @_MergedGlobals_x, i32 0, i32 1), i32 0, i64 3
; CHECK: %y3 = getelementptr inbounds [1000 x i32]* getelementptr inbounds ({ [1000 x i32] }* @_MergedGlobals_y, i32 0, i32 0), i32 0, i64 3
; CHECK: store i32 %a3, i32* getelementptr inbounds ({ i32, [1000 x i32] }* @_MergedGlobals_x, i32 0, i32 0), align 4
%x3 = getelementptr inbounds [1000 x i32]* @x, i32 0, i64 3
%y3 = getelementptr inbounds [1000 x i32]* @y, i32 0, i64 3
store i32 %a1, i32* %x3, align 4
store i32 %a2, i32* %y3, align 4
store i32 %a3, i32* @z, align 4
ret void
}

View File

@@ -0,0 +1,4 @@
targets = set(config.root.targets_to_build.split())
if not 'AArch64' in targets:
config.unsupported = True

View File

@@ -1,23 +1,4 @@
; RUN: llc %s -O0 -o - | FileCheck -check-prefix=NO-MERGE %s
; RUN: llc %s -O0 -o - -global-merge=false | FileCheck -check-prefix=NO-MERGE %s
; RUN: llc %s -O0 -o - -global-merge=true | FileCheck -check-prefix=NO-MERGE %s
; RUN: llc %s -O1 -o - | FileCheck -check-prefix=MERGE %s
; RUN: llc %s -O1 -o - -global-merge=false | FileCheck -check-prefix=NO-MERGE %s
; RUN: llc %s -O1 -o - -global-merge=true | FileCheck -check-prefix=MERGE %s
; MERGE-NOT: .zerofill __DATA,__bss,_bar,20,2
; MERGE-NOT: .zerofill __DATA,__bss,_baz,20,2
; MERGE-NOT: .zerofill __DATA,__bss,_foo,20,2
; MERGE: .zerofill __DATA,__bss,__MergedGlobals,60,4
; MERGE-NOT: .zerofill __DATA,__bss,_bar,20,2
; MERGE-NOT: .zerofill __DATA,__bss,_baz,20,2
; MERGE-NOT: .zerofill __DATA,__bss,_foo,20,2
; NO-MERGE-NOT: .zerofill __DATA,__bss,__MergedGlobals,60,4
; NO-MERGE: .zerofill __DATA,__bss,_bar,20,2
; NO-MERGE: .zerofill __DATA,__bss,_baz,20,2
; NO-MERGE: .zerofill __DATA,__bss,_foo,20,2
; NO-MERGE-NOT: .zerofill __DATA,__bss,__MergedGlobals,60,4
; RUN: opt %s -mtriple=arm-linux-gnuabi -global-merge -S -o - | FileCheck %s
target datalayout = "e-p:32:32:32-i1:8:32-i8:8:32-i16:16:32-i32:32:32-i64:32:64-f32:32:32-f64:32:64-v64:32:64-v128:32:128-a0:0:32-n32-S32"
target triple = "thumbv7-apple-ios3.0.0"
@@ -26,6 +7,8 @@ target triple = "thumbv7-apple-ios3.0.0"
@baz = internal global [5 x i32] zeroinitializer, align 4
@foo = internal global [5 x i32] zeroinitializer, align 4
; CHECK: @_MergedGlobals = internal global { [5 x i32], [5 x i32], [5 x i32] } zeroinitializer
; Function Attrs: nounwind ssp
define internal void @initialize() #0 {
%1 = tail call i32 bitcast (i32 (...)* @calc to i32 ()*)() #3

View File

@@ -1,23 +1,6 @@
; RUN: llc %s -O0 -o - | FileCheck -check-prefix=NO-MERGE %s
; RUN: llc %s -O0 -o - -global-merge=false | FileCheck -check-prefix=NO-MERGE %s
; RUN: llc %s -O0 -o - -global-merge=true | FileCheck -check-prefix=NO-MERGE %s
; RUN: llc %s -O1 -o - | FileCheck -check-prefix=MERGE %s
; RUN: llc %s -O1 -o - -global-merge=false | FileCheck -check-prefix=NO-MERGE %s
; RUN: llc %s -O1 -o - -global-merge=true | FileCheck -check-prefix=MERGE %s
; RUN: opt %s -mtriple=arm64-linux-gnuabi -global-merge -S -o - | FileCheck %s
; MERGE-NOT: .zerofill __DATA,__bss,_bar,20,2
; MERGE-NOT: .zerofill __DATA,__bss,_baz,20,2
; MERGE-NOT: .zerofill __DATA,__bss,_foo,20,2
; MERGE: .zerofill __DATA,__bss,__MergedGlobals,60,4
; MERGE-NOT: .zerofill __DATA,__bss,_bar,20,2
; MERGE-NOT: .zerofill __DATA,__bss,_baz,20,2
; MERGE-NOT: .zerofill __DATA,__bss,_foo,20,2
; NO-MERGE-NOT: .zerofill __DATA,__bss,__MergedGlobals,60,4
; NO-MERGE: .zerofill __DATA,__bss,_bar,20,2
; NO-MERGE: .zerofill __DATA,__bss,_baz,20,2
; NO-MERGE: .zerofill __DATA,__bss,_foo,20,2
; NO-MERGE-NOT: .zerofill __DATA,__bss,__MergedGlobals,60,4
; CHECK: @_MergedGlobals = internal global { [5 x i32], [5 x i32], [5 x i32] } zeroinitializer
target datalayout = "e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64-n32:64-S128"
target triple = "arm64-apple-ios7.0.0"