Replace brittle gcc3_linux_aarch64 vtableSlotCall with pure assembler code

*  For one, as discussed in the comment at <https://gerrit.libreoffice.org/c/
core/+/91978/2#message-97da6c6ece7ae7bd49e9eb4843be333192fcc057> "Port to
FreeBSD aarch64":

"So it looks like Clang does not treat those register asm as we expect it would,
at least on aarch64.

"Witness a local Linux recent master --with-distro=LibreOfficeAndroidAarch64
[i.e., using Clang] build's

> $ llvm-objdump --disassemble instdir/program/libgcc3_uno.a
[...]
> 0000000000000000 <vtableSlotCall>:
>        0: ff 43 03 d1   sub     sp, sp, #208
>        4: f4 4f 0b a9   stp     x20, x19, [sp, #176]
>        8: fd 7b 0c a9   stp     x29, x30, [sp, #192]
>        c: fd 03 03 91   add     x29, sp, #192
>       10: a8 43 00 91   add     x8, x29, #16
>       14: bf 83 1d f8   stur    xzr, [x29, #-40]
>       18: e0 07 04 a9   stp     x0, x1, [sp, #64]
>       1c: e2 0f 05 a9   stp     x2, x3, [sp, #80]
>       20: e4 17 06 a9   stp     x4, x5, [sp, #96]
>       24: e6 1f 07 a9   stp     x6, x7, [sp, #112]
>       28: e0 07 00 6d   stp     d0, d1, [sp]
>       2c: e2 0f 01 6d   stp     d2, d3, [sp, #16]
>       30: e4 17 02 6d   stp     d4, d5, [sp, #32]
>       34: e6 1f 03 6d   stp     d6, d7, [sp, #48]
>       38: a8 03 1c f8   stur    x8, [x29, #-64]
>       3c: a0 43 5e b8   ldur    w0, [x29, #-28]
>       40: a1 03 5e b8   ldur    w1, [x29, #-32]
>       44: a5 83 5e f8   ldur    x5, [x29, #-24]
>       48: e4 03 08 aa   mov     x4, x8
>       4c: e2 03 01 91   add     x2, sp, #64
>       50: e3 03 00 91   mov     x3, sp
>       54: f3 03 01 91   add     x19, sp, #64
>       58: f4 03 00 91   mov     x20, sp
>       5c: 00 00 00 94   bl      0x5c <vtableSlotCall+0x5c>
>       60: 60 06 40 a9   ldp     x0, x1, [x19]
>       64: 80 06 40 6d   ldp     d0, d1, [x20]
>       68: 82 0e 41 6d   ldp     d2, d3, [x20, #16]
>       6c: fd 7b 4c a9   ldp     x29, x30, [sp, #192]
>       70: f4 4f 4b a9   ldp     x20, x19, [sp, #176]
>       74: ff 43 03 91   add     sp, sp, #208
>       78: c0 03 5f d6   ret
[...]

vs. [this commit's vtableslotcall.s; see below for details].

"And also latest Clang 12 trunk still does e.g.

> $ cat test.c
> void f(long);
> void g() {
>     register long volatile a asm ("x8");
>     f(a);
> }
> $ clang --target=unknown-linux-aarch64 -S -O2 test.c
> $ cat test.s
>         .text
>         .file   "test.c"
>         .globl  g                               // -- Begin function g
>         .p2align        2
>         .type   g,@function
> g:                                      // @g
> // %bb.0:                               // %entry
>         sub     sp, sp, #16                     // =16
>         ldr     x0, [sp, #8]
>         add     sp, sp, #16                     // =16
>         b       f
> .Lfunc_end0:
>         .size   g, .Lfunc_end0-g
>                                         // -- End function
>         .ident  "clang version 12.0.0 (git@github.com:llvm/llvm-project eb31ddd71eb44d53ebe12a09c9587198bb6f2a2e)"
>         .section        ".note.GNU-stack","",@progbits
>         .addrsig

"(This is probably also the underlying issue that
eb15ac837e 'android: Avoid throwing exceptions
through the bridges' tries to hack arond.)"

*  For another, this also gets rid of the
dddb527db1 "Again, no -fstack-protector-strong for
gcc3_linux_aarch64/cpp2uno.cxx" hack.

The contents of the new vtableslotcall.s is effectively the GCC 10 -S output of
the old vtableSlotCall C++ function from cpp2uno.cxx.  (And as cpp2uno.cxx only
takes the address of vtableSlotCall, never calls it directly, it does not matter
that it declares it with an imprecise

  extern "C" void vtableSlotCall();

signature.)

Change-Id: Icfbf0622a47825ff7cf21008de27d3da6a2f0ebd
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/99660
Tested-by: Jenkins
Reviewed-by: Stephan Bergmann <sbergman@redhat.com>
This commit is contained in:
Stephan Bergmann
2020-07-29 09:56:02 +02:00
parent b6222a90f1
commit 252aba41e5
3 changed files with 75 additions and 65 deletions
+2 -6
View File
@@ -30,17 +30,13 @@ else ifeq ($(CPUNAME),AARCH64)
ifneq ($(filter ANDROID DRAGONFLY FREEBSD LINUX NETBSD OPENBSD,$(OS)),)
bridges_SELECTED_BRIDGE := gcc3_linux_aarch64
bridge_exception_objects := abi uno2cpp
bridge_asm_objects := vtableslotcall
bridge_exception_objects := abi cpp2uno uno2cpp
$(eval $(call gb_Library_add_exception_objects,$(gb_CPPU_ENV)_uno, \
bridges/source/cpp_uno/$(bridges_SELECTED_BRIDGE)/callvirtualfunction, \
$(if $(HAVE_GCC_STACK_CLASH_PROTECTION),-fno-stack-clash-protection) \
))
$(eval $(call gb_Library_add_exception_objects,$(gb_CPPU_ENV)_uno, \
bridges/source/cpp_uno/$(bridges_SELECTED_BRIDGE)/cpp2uno, \
-fstack-protector \
))
endif
else ifeq ($(CPUNAME),AXP)
@@ -42,7 +42,7 @@
#include "abi.hxx"
extern "C" void vtableSlotCall_();
extern "C" void vtableSlotCall();
namespace {
@@ -304,64 +304,6 @@ extern "C" void vtableCall(
}
}
struct aarch64_va_list {
void * stack;
void * gr_top;
void * vr_top;
int gr_offs;
int vr_offs;
};
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wuninitialized"
#pragma GCC diagnostic ignored "-Wvolatile-register-var"
extern "C" void vtableSlotCall(
unsigned long gpr0, unsigned long gpr1, unsigned long gpr2,
unsigned long gpr3, unsigned long gpr4, unsigned long gpr5,
unsigned long gpr6, unsigned long gpr7, double fpr0, double fpr1,
double fpr2, double fpr3, double fpr4, double fpr5, double fpr6,
double fpr7, ...)
{
register void * volatile indirectRet asm ("x8");
register sal_Int32 volatile functionIndex asm ("x9");
register sal_Int32 volatile vtableOffset asm ("x10");
va_list ap;
va_start(ap, fpr7);
assert(sizeof (va_list) == sizeof (aarch64_va_list));
unsigned long gpr[8];
gpr[0] = gpr0;
gpr[1] = gpr1;
gpr[2] = gpr2;
gpr[3] = gpr3;
gpr[4] = gpr4;
gpr[5] = gpr5;
gpr[6] = gpr6;
gpr[7] = gpr7;
double fpr[8];
fpr[0] = fpr0;
fpr[1] = fpr1;
fpr[2] = fpr2;
fpr[3] = fpr3;
fpr[4] = fpr4;
fpr[5] = fpr5;
fpr[6] = fpr6;
fpr[7] = fpr7;
vtableCall(
functionIndex, vtableOffset, gpr,
reinterpret_cast<unsigned long *>(fpr),
static_cast<unsigned long *>(
reinterpret_cast<aarch64_va_list *>(&ap)->stack),
indirectRet);
asm volatile(
"ldp x0, x1, [%[gpr_]]\n\t"
"ldp d0, d1, [%[fpr_]]\n\t"
"ldp d2, d3, [%[fpr_], #16]\n\t"
:: [gpr_]"r" (gpr), [fpr_]"r" (fpr)
: "r0", "r1", "v0", "v1", "v2", "v3");
va_end(ap);
}
#pragma GCC diagnostic pop
std::size_t const codeSnippetSize = 8 * 4;
unsigned char * generateCodeSnippet(
@@ -0,0 +1,72 @@
/* -*- tab-width: 4; indent-tabs-mode: nil; fill-column: 100 -*- */
/*
* This file is part of the LibreOffice project.
*
* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/.
*
* This file incorporates work covered by the following license notice:
*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed
* with this work for additional information regarding copyright
* ownership. The ASF licenses this file to you under the Apache
* License, Version 2.0 (the "License"); you may not use this file
* except in compliance with the License. You may obtain a copy of
* the License at http://www.apache.org/licenses/LICENSE-2.0 .
*/
.arch armv8-a
.text
.align 2
.global vtableSlotCall
.hidden vtableSlotCall
.type vtableSlotCall, %function
vtableSlotCall:
.cfi_startproc
stp x29, x30, [sp, -192]!
.cfi_def_cfa_offset 192
.cfi_offset 29, -192
.cfi_offset 30, -184
add x11, sp, 192
mov x29, sp
stp x19, x20, [sp, 16]
.cfi_offset 19, -176
.cfi_offset 20, -168
add x20, sp, 128
add x19, sp, 64
stp x11, x11, [sp, 32]
str x11, [sp, 48]
stp wzr, wzr, [sp, 56]
stp x0, x1, [sp, 64]
mov w0, w9
mov w1, w10
stp x2, x3, [sp, 80]
mov x3, x20
mov x2, x19
stp x4, x5, [sp, 96]
mov x5, x8
mov x4, x11
stp x6, x7, [sp, 112]
stp d0, d1, [sp, 128]
stp d2, d3, [sp, 144]
stp d4, d5, [sp, 160]
stp d6, d7, [sp, 176]
bl vtableCall
ldp x0, x1, [x19]
ldp d0, d1, [x20]
ldp d2, d3, [x20, #16]
ldp x19, x20, [sp, 16]
ldp x29, x30, [sp], 192
.cfi_restore 30
.cfi_restore 29
.cfi_restore 19
.cfi_restore 20
.cfi_def_cfa_offset 0
ret
.cfi_endproc
.size vtableSlotCall, .-vtableSlotCall
.section .note.GNU-stack, "", @progbits
/* vim:set shiftwidth=4 softtabstop=4 expandtab */