This does some rudimentary conversions of instructions that aren't
available in thumb mode.
This allows building OpenH264 for Windows Phone 8 (and Windows RT),
which only supports thumb mode, and the OpenH264 arm assembly is
hardcoded for arm mode.
This is similar to how libvpx supports assembling in thumb mode - the
source itself is arm mode only, but a perl script can replace
instruction combinations that aren't supported in thumb mode. This
is a small subset of those conversions.
---
gas-preprocessor.pl | 31 +++++++++++++++++++++++++++++++
1 file changed, 31 insertions(+)
diff --git a/gas-preprocessor.pl b/gas-preprocessor.pl
index 3d1049b..bbc5ff4 100755
--- a/gas-preprocessor.pl
+++ b/gas-preprocessor.pl
@@ -27,6 +27,7 @@ my $arch;
my $as_type = "apple-gas";
my $fix_unreq = $^O eq "darwin";
+my $force_thumb = 0;
my $usage_str = "
$0\n
@@ -43,6 +44,7 @@ command. Following options are currently supported:
-as-type - one value out of {{,apple-}{gas,clang},armasm}
-fix-unreq
-no-fix-unreq
+ -force-thumb - assemble as thumb regardless of the input source
";
sub usage() {
@@ -74,6 +76,8 @@ while (@options) {
my $opt = shift @options;
if ($opt =~ /^-(no-)?fix-unreq$/) {
$fix_unreq = $1 ne "no-";
+ } elsif ($opt eq "-force-thumb") {
+ $force_thumb = 1;
} elsif ($opt eq "-arch") {
$arch = shift @options;
die "unknown arch: '$arch'\n" if not exists $comments{$arch};
@@ -213,6 +217,15 @@ my @ifstack;
my %symbols;
+if ($force_thumb) {
+ # This doesn't go through the initial parsing loop below
+ if ($as_type eq "armasm") {
+ parse_line("THUMB\n");
+ } else {
+ parse_line(".thumb\n");
+ }
+}
+
# pass 1: parse .macro
# note that the handling of arguments is probably overly permissive vs. gas
# but it should be the same for valid cases
@@ -883,6 +896,24 @@ sub handle_serialized_line {
$line =~ s/&0x/& 0x/g;
}
+ if ($force_thumb) {
+ # Convert register post indexing to a separate add instruction.
+ # This converts "ldrneb r9, [r0], r2" into "ldrneb r9, [r0]",
+ # "add r0, r2".
+ $line =~
s/^(\s*)((ldr|str)(ne)?[bhd]?)(\s+)(\w+),(\s*\w+,)?\s*\[(\w+)\],\s*(\w+)/$1$2$5$6,$7
[$8]\n$1add$4$5$8, $8, $9/g;
+
+ # Convert "mov pc, lr" into "bx lr", since the former only works
+ # for switching from arm to thumb (and only in armv7), but not
+ # from thumb to arm.
+ s/mov(\s*)pc\s*,\s*lr/bx$1lr/g;
+
+ # Convert stmdb/ldmia with only one register into a plain str/ldr with
post-increment/decrement
+ $line =~ s/^(\s*)stmdb(\s+)sp!\s*,\s*\{([^,-]+)\}/$1str$2$3, [sp,
#-4]!/g;
+ $line =~ s/^(\s*)ldmia(\s+)sp!\s*,\s*\{([^,-]+)\}/$1ldr$2$3, [sp],
#4/g;
+
+ $line =~ s/\.arm/.thumb/x;
+ }
+
# comment out unsupported directives
$line =~ s/\.type/$comm$&/x if $as_type =~ /^(apple-|armasm)/;
$line =~ s/\.func/$comm$&/x if $as_type =~ /^(apple-|clang)/;
--
1.8.1.2
_______________________________________________
libav-devel mailing list
[email protected]
https://lists.libav.org/mailman/listinfo/libav-devel