brintos

brintos / llvm-project-archived public Read only

0
0
Text · 6.2 KiB · 3c8a703 Raw
250 lines · plain
1#!/usr/bin/env perl2# Wrapper around LLVM tools to generate a native .o from llvm-gxx using an3# LLVM back-end (CBE by default).4 5# set up defaults.6$Verbose = 0;7$SaveTemps = 1;8$PreprocessOnly = 0;9$CompileDontLink = 0;10$Backend = 'cbe';11chomp ($ProgramName = `basename $0`);12 13sub boldprint {14	print "", @_, "";15}16 17# process command-line options.18# most of these are passed on to llvm-gxx.19$GCCOptions = "";20for ($i = 0; $i <= $#ARGV; ++$i) {	21	if ($ARGV[$i] =~ /-mllvm-backend=([a-z0-9]*)/) {22		$Backend = $1;23		if ($ProgramName =~ /llvm-native-gxx/) {24			splice (@ARGV, $i, 1);25			--$i;26		}27	} elsif ($ARGV[$i] eq "-E") {28		$PreprocessOnly = 1;29	} elsif ($ARGV[$i] eq "-c") {30		$GCCOptions .= " " . $ARGV[$i];31		$CompileDontLink = 1;32	} elsif ($ARGV[$i] eq "-v") {33		$GCCOptions .= " " . $ARGV[$i];34		$Verbose = 1;35	} elsif ($ARGV[$i] eq "-o") {36		$OutputFile = $ARGV[$i + 1];37	} elsif ($ARGV[$i] eq "-save-temps") {38		$GCCOptions .= " " . $ARGV[$i];39		$SaveTemps = 1;40	} elsif ($ARGV[$i] =~ /\.bc$/) {41		push (@BytecodeFiles, $ARGV[$i]);42	} elsif ($ARGV[$i] =~ /^-L/) {43		$GCCOptions .= " " . $ARGV[$i];44		push (@LibDirs, $ARGV[$i]);45	} elsif ($ARGV[$i] =~ /^-l/) {46		$GCCOptions .= " " . $ARGV[$i];47		push (@Libs, $ARGV[$i]);48	} elsif ($ARGV[$i] =~ /\.(c|cpp|cc|i|ii|C)$/) {49		$LastCFile = $ARGV[$i];50	}51}52 53sub GetDefaultOutputFileName {54	my $DefaultOutputFileBase;55 56	if ($ProgramName =~ /llvm-native-gxx/) {57		$DefaultOutputFileBase = $LastCFile;58	} elsif ($ProgramName =~ /native-build/) {59		$DefaultOutputFileBase = $BytecodeFiles[0];60	}61 62	my $def = $DefaultOutputFileBase;63 64	die "Can't figure out name of output file.\n"65		unless $DefaultOutputFileBase66			   && (($ProgramName !~ /native-build/)67				   || $#BytecodeFiles == 0);68 69	print "Warning: defaulting output file name ",70		"based on '$DefaultOutputFileBase'\n" if $Verbose;71 72	if ($ProgramName =~ /llvm-native-gxx/) {73		$def =~ s/\.(c|cpp|cc|i|ii|C)$/.o/;74	} elsif ($ProgramName =~ /native-build/) {75		$def =~ s/\.bc$/.$Backend/;76		if ($CompileDontLink) {77			$def .= ".o";78		}79	}80 81	return $def;82}83 84# run a command, optionally echoing, and quitting if it fails:85sub run {86	my $command = join(" ", @_);87	print "$command\n" if $Verbose;88	$command =~ s/\"/\\\"/g;89	system $command and die "$0: $command failed";90}91 92sub LinkBytecodeFilesIntoTemporary {93	my $FinalOutputFileName = shift @_;94	my @BytecodeFiles = @_;95 96	my $BCFiles = join (" ", @BytecodeFiles);97	my $LinkedBCFile;98	if ($SaveTemps) {99		$LinkedBCFile = "${FinalOutputFileName}.llvm.bc";100	} else {101		$LinkedBCFile = "/tmp/nativebuild-$$.llvm.bc";102	}103	run "llvm-link -o $LinkedBCFile $BCFiles";104	return $LinkedBCFile;105}106 107sub CompileBytecodeToNative {108	my ($BCFile, $Backend, $OutputFile) = @_;109 110	my $GeneratedCode;111	if ($Backend eq 'cbe') {112		if ($SaveTemps) {113			$GeneratedCode = "${OutputFile}.c";114		} else {115			$GeneratedCode = "/tmp/nativebuild-$$.c";116		}117		run "llc -march=c -f -o $GeneratedCode $BCFile";118	} elsif ($Backend eq 'llc') {119		if ($SaveTemps) {120			$GeneratedCode = "${OutputFile}.s";121		} else {122			$GeneratedCode = "/tmp/nativebuild-$$.s";123		}124		run "llc -f -o $GeneratedCode $BCFile";125	}126	my $LibDirs = join (" ", @LibDirs);127	my $Libs = join (" ", @Libs);128	run "gcc $GCCOptions $GeneratedCode -o $OutputFile $LibDirs $Libs";129	run "rm $BCFile $GeneratedCode"130		unless $SaveTemps;131}132 133sub CompileCToNative {134	my ($LLVMGCCCommand, $Backend, $OutputFile) = @_;135	run $LLVMGCCCommand;136	if ($PreprocessOnly) {137		return;138	}139	my $BCFile = "${OutputFile}.llvm.bc";140	if ($CompileDontLink) {141		run "mv ${OutputFile} $BCFile";142	} else { # gccld messes with the output file name143		run "mv ${OutputFile}.bc $BCFile";144	}145	my $GeneratedCode;146	if ($Backend eq 'cbe') {147		$GeneratedCode = "${OutputFile}.cbe.c";148		run "llc -march=c -f -o $GeneratedCode $BCFile";149	} elsif ($Backend eq 'llc') {150		$GeneratedCode = "${OutputFile}.llc.s";151		run "llc -f -o $GeneratedCode $BCFile";152	}153	my $NativeGCCOptions = "";154	if ($CompileDontLink) {155		$NativeGCCOptions = "-c";156	}157	run "gcc $NativeGCCOptions $GeneratedCode -o $OutputFile";158	run "rm ${OutputFile}.llvm.bc $GeneratedCode"159		unless $SaveTemps;160}161 162# guess the name of the output file, if -o was not specified.163$OutputFile = GetDefaultOutputFileName () unless $OutputFile;164print "Output file is $OutputFile\n" if $Verbose;165# do all the dirty work:166if ($ProgramName eq /native-build/) {167	my $LinkedBCFile = LinkBytecodeFilesIntoTemporary (@BytecodeFiles);168	CompileBytecodeToNative ($LinkedBCFile, $Backend, $OutputFile);169} elsif ($ProgramName =~ /llvm-native-gxx/) {170	# build the llvm-gxx command line.171	$LLVMGCCCommand = join (" ", ("llvm-g++", @ARGV));172	CompileCToNative ($LLVMGCCCommand, $Backend, $OutputFile);173}174 175# we're done.176exit 0;177 178__END__179 180=pod181 182=head1 NAME183 184llvm-native-gxx185 186=head1 SYNOPSIS187 188llvm-native-g++ [OPTIONS...] FILE189 190native-build [OPTIONS...] FILE191 192=head1 DESCRIPTION193 194llvm-native-g++ is a wrapper around the LLVM command-line tools which generates195a native object (.o) file by compiling FILE with llvm-g++, and then running 196an LLVM back-end (CBE by default) over the resulting bitcode, and then197compiling the resulting code to a native object file.198 199If called as "native-build", it compiles bitcode to native code, and takes200different options.201 202=head1 OPTIONS203 204llvm-native-g++ takes the same options as llvm-gcc. All options205except -mllvm-backend=... are passed on to llvm-g++.206 207=over 4208 209=item -mllvm-backend=BACKEND210 211Use BACKEND for native code generation. 212 213=item -v214 215Print command lines that llvm-native-g++ runs.216 217=item -o FILE218 219llvm-native-g++ tries to guess the name of the llvm-g++ output file by looking220for this option in the command line. If it can't find it, it finds the last C221or C++ source file named on the command line, and turns its suffix into .o. See222BUGS.223 224=item -save-temps225 226Save temporary files used by llvm-native-g++ (and llvm-g++, and g++).227 228=back229 230=head1 BUGS231 232llvm-native-g++ only handles the case where llvm-g++ compiles a single233file per invocation.  llvm-native-g++ has weak command-line argument234parsing and is a poor substitute for making g++/g++.c do this stuff.235 236This manual page does not adequately document native-build mode.237 238llvm-native-g++ is pretty gross because it represents the blind merging of two239other scripts that predated it. It could use some code clean-up.240 241=head1 SEE ALSO242 243g++(1)244 245=head1 AUTHOR246 247Brian R. Gaeke248 249=cut250