$T_DOT_WORD = '\.(quad|long|value|byte|zero)';
$T_DOT_GLOBAL = '\.global';
+
+ $T_HDR_literal16 = "\.section\t\.rodata.cst16\n\t.align 16\n";
$T_HDR_literal = "\.section\t\.rodata\n";
+
$T_HDR_misc = "\.text\n\t\.align 8\n";
$T_HDR_data = "\.data\n\t\.align 8\n";
$T_HDR_rodata = "\.section\t\.rodata\n\t\.align 8\n";
+
+ # the assembler on x86_64/Linux refuses to generate code for
+ # .quad x - y
+ # where x is in the text section and y in the rodata section.
+ # It works if y is in the text section, though. This is probably
+ # going to cause difficulties for PIC, I imagine.
+ $T_HDR_relrodata= "\.text\n\t\.align 8\n";
+
$T_HDR_closure = "\.data\n\t\.align 8\n";
$T_HDR_info = "\.text\n\t\.align 8\n";
$T_HDR_entry = "\.text\n\t\.align 8\n";
$T_CONST_LBL = '^\.LLC(\d+):$'; # regexp for what such a lbl looks like
$T_POST_LBL = ':';
- $T_MOVE_DIRVS = '^((\s+\.align\s+\d+|\s+\.proc\s+\d+|\s+\.global\s+\S+|\.text|\.data|\.stab.*|\.section.*|\s+\.type.*|\s+\.size.*)\n)';
+ $T_MOVE_DIRVS = '^((\s+\.align\s+\d+|\s+\.proc\s+\d+|\s+\.global\s+\S+|\.text|\.data|\.stab.*|\s*\.section.*|\s+\.type.*|\s+\.size.*)\n)';
$T_COPY_DIRVS = '\.(global|proc|stab)';
$T_DOT_WORD = '\.(long|word|byte|half|skip|uahalf|uaword)';
$chk[++$i] = $_;
$chkcat[$i] = 'rodata';
$chksymb[$i] = '';
+ } elsif ( $TargetPlatform =~ /-darwin/
+ && (/^\s*\.subsections_via_symbols/
+ ||/^\s*\.no_dead_strip.*/)) {
+ # Don't allow Apple's linker to do any dead-stripping of symbols
+ # in this file, because it will mess up info-tables in mangled
+ # code.
+ # The .no_dead_strip directives are actually put there by
+ # the gcc3 "used" attribute on entry points.
+
+ } elsif ( $TargetPlatform =~ /^powerpc-apple-.*/ && (
+ /^\s*\.picsymbol_stub/
+ || /^\s*\.section __TEXT,__picsymbol_stub1,.*/
+ || /^\s*\.section __TEXT,__picsymbolstub1,.*/
+ || /^\s*\.symbol_stub/
+ || /^\s*\.section __TEXT,__symbol_stub1,.*/
+ || /^\s*\.section __TEXT,__symbolstub1,.*/
+ || /^\s*\.lazy_symbol_pointer/
+ || /^\s*\.non_lazy_symbol_pointer/ ))
+ {
+ $chk[++$i] = $_;
+ $chkcat[$i] = 'dyld';
+ $chksymb[$i] = '';
+
+ } elsif ( $TargetPlatform =~ /^powerpc-apple-.*/ && $chkcat[$i] eq 'dyld' && /^\s*\.data/)
+ { # non_lazy_symbol_ptrs that point to local symbols
+ $chk[++$i] = $_;
+ $chkcat[$i] = 'dyld';
+ $chksymb[$i] = '';
} elsif ( /^\s+/ ) { # most common case first -- a simple line!
# duplicated from the bottom
} elsif ( /\.\.ng:$/ && $TargetPlatform =~ /^alpha-/ ) {
# Alphas: Local labels not to be confused with new chunks
$chk[$i] .= $_;
- } elsif ( $TargetPlatform =~ /-darwin/
- && /^\t\.subsections_via_symbols/) {
- # Don't allow Apple's linker to do any dead-stripping of symbols
- # in this file, because it will mess up info-tables in mangled
- # code.
-
# NB: all the rest start with a non-space
} elsif ( $TargetPlatform =~ /^mips-/
$chkcat[$i] = 'unknown';
}
- } elsif ( $TargetPlatform =~ /^powerpc-apple-.*/ && (
- /^\.picsymbol_stub/
- || /^\.section __TEXT,__picsymbol_stub1,.*/
- || /^\.section __TEXT,__picsymbolstub1,.*/
- || /^\.symbol_stub/
- || /^\.section __TEXT,__symbol_stub1,.*/
- || /^\.section __TEXT,__symbolstub1,.*/
- || /^\.lazy_symbol_pointer/
- || /^\.non_lazy_symbol_pointer/ ))
- {
- $chk[++$i] = $_;
- $chkcat[$i] = 'dyld';
- $chksymb[$i] = '';
- } elsif ( $TargetPlatform =~ /^powerpc-apple-.*/ && /^\.data/ && $chkcat[$i] eq 'dyld')
- { # non_lazy_symbol_ptrs that point to local symbols
- $chk[++$i] = $_;
- $chkcat[$i] = 'dyld';
- $chksymb[$i] = '';
} elsif ( $TargetPlatform =~ /^powerpc-.*-linux/ && /^\.LCTOC1 = /o ) {
# PowerPC Linux's large-model PIC (-fPIC) generates a gobal offset
# table "by hand". Be sure to copy it over.
# print out all the literal strings next
for ($i = 0; $i < $numchks; $i++) {
if ( $chkcat[$i] eq 'literal' ) {
- print OUTASM $T_HDR_literal, $chk[$i];
+
+ # HACK: try to detect 16-byte constants and align them
+ # on a 16-byte boundary. x86_64 sometimes needs 128-bit
+ # aligned constants.
+ if ( $TargetPlatform =~ /^x86_64/ ) {
+ $z = $chk[$i];
+ if ($z =~ /(\.long.*\n.*\.long.*\n.*\.long.*\n.*\.long|\.quad.*\n.*\.quad)/) {
+ print OUTASM $T_HDR_literal16;
+ } else {
+ print OUTASM $T_HDR_literal;
+ }
+ } else {
+ print OUTASM $T_HDR_literal;
+ }
+
+ print OUTASM $chk[$i];
print OUTASM "; end literal\n" if $TargetPlatform =~ /^hppa/; # for the splitter
$chkcat[$i] = 'DONE ALREADY';
# If this is an entry point with an info table,
# eliminate the entry symbol and all directives involving it.
if (defined($infochk{$symb}) && $TargetPlatform !~ /^ia64-/) {
- $c =~ s/^.*$symb_(entry|ret)${T_POST_LBL}\n//;
- $c =~ s/^\s*\..*$symb.*\n//g;
+ @o = ();
+ foreach $l (split(/\n/,$c)) {
+ next if $l =~ /^.*$symb_(entry|ret)${T_POST_LBL}/;
+
+ # If we have .type/.size direrctives involving foo_entry,
+ # then make them refer to foo_info instead. The information
+ # in these directives is used by the cachegrind annotator,
+ # so it is worthwhile keeping.
+ if ($l =~ /^\s*\.(type|size).*$symb_(entry|ret)/) {
+ $l =~ s/$symb(_entry|_ret)/${symb}_info/g;
+ push(@o,$l);
+ next;
+ }
+ next if $l =~ /^\s*\..*$symb.*\n?/;
+ push(@o,$l);
+ }
+ $c = join("\n",@o) . "\n";
}
print OUTASM $T_HDR_entry;