/[packages]/cauldron/libreoffice/current/SOURCES/0002-Linux-AArch64-port.patch
ViewVC logotype

Contents of /cauldron/libreoffice/current/SOURCES/0002-Linux-AArch64-port.patch

Parent Directory Parent Directory | Revision Log Revision Log


Revision 671886 - (show annotations) (download)
Thu Sep 4 10:22:11 2014 UTC (9 years, 7 months ago) by tv
File size: 55468 byte(s)
SILENT: new file ./SOURCES/0002-Linux-AArch64-port.patch
1 From 09f49fc55104ee7b0fe18dbb5068a4cad7d9fc25 Mon Sep 17 00:00:00 2001
2 From: Stephan Bergmann <sbergman@redhat.com>
3 Date: Fri, 29 Aug 2014 17:17:42 +0200
4 Subject: [PATCH 2/2] Linux AArch64 port
5
6 (cherry picked from commit 235fa0334e0b45c736b636ba1689e2f8c7458697)
7 Conflicts:
8 bridges/source/cpp_uno/gcc3_linux_aarch64/abi.cxx
9 bridges/source/cpp_uno/gcc3_linux_aarch64/cpp2uno.cxx
10 bridges/source/cpp_uno/gcc3_linux_aarch64/uno2cpp.cxx
11 configure.ac
12
13 Change-Id: I37044a37348b203944a8eb9d2204e619055f069d
14 ---
15 bridges/Library_cpp_uno.mk | 5 +
16 bridges/source/cpp_uno/gcc3_linux_aarch64/abi.cxx | 310 ++++++++++++++
17 bridges/source/cpp_uno/gcc3_linux_aarch64/abi.hxx | 87 ++++
18 .../gcc3_linux_aarch64/callvirtualfunction.cxx | 66 +++
19 .../gcc3_linux_aarch64/callvirtualfunction.hxx | 33 ++
20 .../source/cpp_uno/gcc3_linux_aarch64/cpp2uno.cxx | 464 +++++++++++++++++++++
21 .../source/cpp_uno/gcc3_linux_aarch64/uno2cpp.cxx | 376 +++++++++++++++++
22 configure.ac | 6 +
23 desktop/source/deployment/misc/dp_platform.cxx | 4 +-
24 jvmfwk/plugins/sunmajor/pluginlib/vendorbase.hxx | 2 +
25 solenv/gbuild/platform/LINUX_AARCH64_GCC.mk | 14 +
26 11 files changed, 1366 insertions(+), 1 deletion(-)
27 create mode 100644 bridges/source/cpp_uno/gcc3_linux_aarch64/abi.cxx
28 create mode 100644 bridges/source/cpp_uno/gcc3_linux_aarch64/abi.hxx
29 create mode 100644 bridges/source/cpp_uno/gcc3_linux_aarch64/callvirtualfunction.cxx
30 create mode 100644 bridges/source/cpp_uno/gcc3_linux_aarch64/callvirtualfunction.hxx
31 create mode 100644 bridges/source/cpp_uno/gcc3_linux_aarch64/cpp2uno.cxx
32 create mode 100644 bridges/source/cpp_uno/gcc3_linux_aarch64/uno2cpp.cxx
33 create mode 100644 solenv/gbuild/platform/LINUX_AARCH64_GCC.mk
34
35 diff --git a/bridges/Library_cpp_uno.mk b/bridges/Library_cpp_uno.mk
36 index c6ab9a0..0fcaf6b 100644
37 --- a/bridges/Library_cpp_uno.mk
38 +++ b/bridges/Library_cpp_uno.mk
39 @@ -35,6 +35,11 @@ $(call gb_LinkTarget_get_target,$(call gb_Library_get_linktarget,gcc3_uno)) : \
40 EXTRAOBJECTLISTS += $(call gb_CustomTarget_get_workdir,bridges/source/cpp_uno/gcc3_linux_arm)/armhelper.objectlist
41 endif
42
43 +else ifeq ($(OS)-$(CPUNAME),LINUX-AARCH64)
44 +
45 +bridges_SELECTED_BRIDGE := gcc3_linux_aarch64
46 +bridge_exception_objects := abi callvirtualfunction cpp2uno uno2cpp
47 +
48 else ifeq ($(OS)-$(CPUNAME),LINUX-AXP)
49
50 bridges_SELECTED_BRIDGE := gcc3_linux_alpha
51 diff --git a/bridges/source/cpp_uno/gcc3_linux_aarch64/abi.cxx b/bridges/source/cpp_uno/gcc3_linux_aarch64/abi.cxx
52 new file mode 100644
53 index 0000000..c177b22
54 --- /dev/null
55 +++ b/bridges/source/cpp_uno/gcc3_linux_aarch64/abi.cxx
56 @@ -0,0 +1,310 @@
57 +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
58 +/*
59 + * This file is part of the LibreOffice project.
60 + *
61 + * This Source Code Form is subject to the terms of the Mozilla Public
62 + * License, v. 2.0. If a copy of the MPL was not distributed with this
63 + * file, You can obtain one at http://mozilla.org/MPL/2.0/.
64 + *
65 + * This file incorporates work covered by the following license notice:
66 + *
67 + * Licensed to the Apache Software Foundation (ASF) under one or more
68 + * contributor license agreements. See the NOTICE file distributed
69 + * with this work for additional information regarding copyright
70 + * ownership. The ASF licenses this file to you under the Apache
71 + * License, Version 2.0 (the "License"); you may not use this file
72 + * except in compliance with the License. You may obtain a copy of
73 + * the License at http://www.apache.org/licenses/LICENSE-2.0 .
74 + */
75 +
76 +#include <sal/config.h>
77 +
78 +#include <cassert>
79 +#include <cstddef>
80 +#include <cstring>
81 +#include <typeinfo>
82 +
83 +#include <cxxabi.h>
84 +#include <dlfcn.h>
85 +
86 +#include <boost/unordered_map.hpp>
87 +#include <com/sun/star/uno/RuntimeException.hpp>
88 +#include <com/sun/star/uno/genfunc.h>
89 +#include <rtl/strbuf.hxx>
90 +#include <rtl/ustrbuf.hxx>
91 +#include <rtl/ustring.hxx>
92 +#include <sal/types.h>
93 +#include <typelib/typeclass.h>
94 +#include <typelib/typedescription.h>
95 +#include <uno/any2.h>
96 +#include <uno/mapping.h>
97 +
98 +#include <abi.hxx>
99 +
100 +namespace {
101 +
102 +OUString toUnoName(char const * name) {
103 + assert(name != 0);
104 + OUStringBuffer b;
105 + bool scoped = *name == 'N';
106 + if (scoped) {
107 + ++name;
108 + }
109 + for (;;) {
110 + assert(*name >= '0' && *name <= '9');
111 + std::size_t n = *name++ - '0';
112 + while (*name >= '0' && *name <= '9') {
113 + n = 10 * n + (*name++ - '0');
114 + }
115 + b.appendAscii(name, n);
116 + name += n;
117 + if (!scoped) {
118 + assert(*name == 0);
119 + break;
120 + }
121 + if (*name == 'E') {
122 + assert(name[1] == 0);
123 + break;
124 + }
125 + b.append('.');
126 + }
127 + return b.makeStringAndClear();
128 +}
129 +
130 +class Rtti {
131 +public:
132 + Rtti(): app_(dlopen(0, RTLD_LAZY)) {}
133 +
134 + ~Rtti() { dlclose(app_); }
135 +
136 + std::type_info * getRtti(typelib_TypeDescription const & type);
137 +
138 +private:
139 + typedef boost::unordered_map<OUString, std::type_info *, OUStringHash> Map;
140 +
141 + void * app_;
142 +
143 + osl::Mutex mutex_;
144 + Map map_;
145 +};
146 +
147 +std::type_info * Rtti::getRtti(typelib_TypeDescription const & type) {
148 + OUString unoName(type.pTypeName);
149 + osl::MutexGuard g(mutex_);
150 + Map::iterator i(map_.find(unoName));
151 + if (i == map_.end()) {
152 + OStringBuffer b;
153 + b.append("_ZTIN");
154 + for (sal_Int32 j = 0; j != -1;) {
155 + OString t(
156 + OUStringToOString(
157 + unoName.getToken(0, '.', j), RTL_TEXTENCODING_ASCII_US));
158 + b.append(t.getLength());
159 + b.append(t);
160 + }
161 + b.append('E');
162 + OString sym(b.makeStringAndClear());
163 + std::type_info * rtti = static_cast<std::type_info *>(
164 + dlsym(app_, sym.getStr()));
165 + if (rtti == 0) {
166 + char const * rttiName = sym.getStr() + std::strlen("_ZTI");
167 + assert(type.eTypeClass == typelib_TypeClass_EXCEPTION);
168 + typelib_CompoundTypeDescription const & ctd
169 + = reinterpret_cast<typelib_CompoundTypeDescription const &>(
170 + type);
171 + if (ctd.pBaseTypeDescription == 0) {
172 + rtti = new __cxxabiv1::__class_type_info(strdup(rttiName));
173 + } else {
174 + std::type_info * base = getRtti(
175 + ctd.pBaseTypeDescription->aBase);
176 + rtti = new __cxxabiv1::__si_class_type_info(
177 + strdup(rttiName),
178 + static_cast<__cxxabiv1::__class_type_info *>(base));
179 + }
180 + }
181 + i = map_.insert(Map::value_type(unoName, rtti)).first;
182 + }
183 + return i->second;
184 +}
185 +
186 +struct theRttiFactory: public rtl::Static<Rtti, theRttiFactory> {};
187 +
188 +std::type_info * getRtti(typelib_TypeDescription const & type) {
189 + return theRttiFactory::get().getRtti(type);
190 +}
191 +
192 +extern "C" void _GLIBCXX_CDTOR_CALLABI deleteException(void * exception) {
193 + abi_aarch64::__cxa_exception * header =
194 + static_cast<abi_aarch64::__cxa_exception *>(exception) - 1;
195 + OUString unoName(toUnoName(header->exceptionType->name()));
196 + typelib_TypeDescription * td = 0;
197 + typelib_typedescription_getByName(&td, unoName.pData);
198 + assert(td != 0);
199 + uno_destructData(exception, td, &css::uno::cpp_release);
200 + typelib_typedescription_release(td);
201 +}
202 +
203 +enum StructKind {
204 + STRUCT_KIND_EMPTY, STRUCT_KIND_FLOAT, STRUCT_KIND_DOUBLE, STRUCT_KIND_POD,
205 + STRUCT_KIND_DTOR
206 +};
207 +
208 +StructKind getStructKind(typelib_CompoundTypeDescription const * type) {
209 + StructKind k = type->pBaseTypeDescription == 0
210 + ? STRUCT_KIND_EMPTY : getStructKind(type->pBaseTypeDescription);
211 + for (sal_Int32 i = 0; i != type->nMembers; ++i) {
212 + StructKind k2 = StructKind();
213 + switch (type->ppTypeRefs[i]->eTypeClass) {
214 + case typelib_TypeClass_BOOLEAN:
215 + case typelib_TypeClass_BYTE:
216 + case typelib_TypeClass_SHORT:
217 + case typelib_TypeClass_UNSIGNED_SHORT:
218 + case typelib_TypeClass_LONG:
219 + case typelib_TypeClass_UNSIGNED_LONG:
220 + case typelib_TypeClass_HYPER:
221 + case typelib_TypeClass_UNSIGNED_HYPER:
222 + case typelib_TypeClass_CHAR:
223 + case typelib_TypeClass_ENUM:
224 + k2 = STRUCT_KIND_POD;
225 + break;
226 + case typelib_TypeClass_FLOAT:
227 + k2 = STRUCT_KIND_FLOAT;
228 + break;
229 + case typelib_TypeClass_DOUBLE:
230 + k2 = STRUCT_KIND_DOUBLE;
231 + break;
232 + case typelib_TypeClass_STRING:
233 + case typelib_TypeClass_TYPE:
234 + case typelib_TypeClass_ANY:
235 + case typelib_TypeClass_SEQUENCE:
236 + case typelib_TypeClass_INTERFACE:
237 + k2 = STRUCT_KIND_DTOR;
238 + break;
239 + case typelib_TypeClass_STRUCT:
240 + {
241 + typelib_TypeDescription * td = 0;
242 + TYPELIB_DANGER_GET(&td, type->ppTypeRefs[i]);
243 + k2 = getStructKind(
244 + reinterpret_cast<typelib_CompoundTypeDescription const *>(
245 + td));
246 + TYPELIB_DANGER_RELEASE(td);
247 + break;
248 + }
249 + default:
250 + assert(false);
251 + }
252 + switch (k2) {
253 + case STRUCT_KIND_EMPTY:
254 + // this means an empty sub-object, which nevertheless obtains a byte
255 + // of storage (TODO: does it?), so the full object cannot be a
256 + // homogenous collection of float or double
257 + case STRUCT_KIND_POD:
258 + assert(k != STRUCT_KIND_DTOR);
259 + k = STRUCT_KIND_POD;
260 + break;
261 + case STRUCT_KIND_FLOAT:
262 + case STRUCT_KIND_DOUBLE:
263 + if (k == STRUCT_KIND_EMPTY) {
264 + k = k2;
265 + } else if (k != k2) {
266 + assert(k != STRUCT_KIND_DTOR);
267 + k = STRUCT_KIND_POD;
268 + }
269 + break;
270 + case STRUCT_KIND_DTOR:
271 + return STRUCT_KIND_DTOR;
272 + }
273 + }
274 + return k;
275 +}
276 +
277 +}
278 +
279 +namespace abi_aarch64 {
280 +
281 +void mapException(
282 + __cxa_exception * exception, uno_Any * any, uno_Mapping * mapping)
283 +{
284 + assert(exception != 0);
285 + OUString unoName(toUnoName(exception->exceptionType->name()));
286 + typelib_TypeDescription * td = 0;
287 + typelib_typedescription_getByName(&td, unoName.pData);
288 + if (td == 0) {
289 + css::uno::RuntimeException e(
290 + "exception type not found: " + unoName,
291 + css::uno::Reference<css::uno::XInterface>());
292 + uno_type_any_constructAndConvert(
293 + any, &e,
294 + cppu::UnoType<css::uno::RuntimeException>::get().getTypeLibType(),
295 + mapping);
296 + } else {
297 + uno_any_constructAndConvert(any, exception->adjustedPtr, td, mapping);
298 + typelib_typedescription_release(td);
299 + }
300 +}
301 +
302 +void raiseException(uno_Any * any, uno_Mapping * mapping) {
303 + typelib_TypeDescription * td = 0;
304 + TYPELIB_DANGER_GET(&td, any->pType);
305 + if (td == 0) {
306 + throw css::uno::RuntimeException(
307 + "no typedescription for " + OUString(any->pType->pTypeName),
308 + css::uno::Reference<css::uno::XInterface>());
309 + }
310 + void * exc = __cxxabiv1::__cxa_allocate_exception(td->nSize);
311 + uno_copyAndConvertData(exc, any->pData, td, mapping);
312 + uno_any_destruct(any, 0);
313 + std::type_info * rtti = getRtti(*td);
314 + TYPELIB_DANGER_RELEASE(td);
315 + __cxxabiv1::__cxa_throw(exc, rtti, deleteException);
316 +}
317 +
318 +ReturnKind getReturnKind(typelib_TypeDescription const * type) {
319 + switch (type->eTypeClass) {
320 + default:
321 + assert(false);
322 + // fall through to avoid warnings
323 + case typelib_TypeClass_VOID:
324 + case typelib_TypeClass_BOOLEAN:
325 + case typelib_TypeClass_BYTE:
326 + case typelib_TypeClass_SHORT:
327 + case typelib_TypeClass_UNSIGNED_SHORT:
328 + case typelib_TypeClass_LONG:
329 + case typelib_TypeClass_UNSIGNED_LONG:
330 + case typelib_TypeClass_HYPER:
331 + case typelib_TypeClass_UNSIGNED_HYPER:
332 + case typelib_TypeClass_FLOAT:
333 + case typelib_TypeClass_DOUBLE:
334 + case typelib_TypeClass_CHAR:
335 + case typelib_TypeClass_ENUM:
336 + assert(type->nSize <= 16);
337 + return RETURN_KIND_REG;
338 + case typelib_TypeClass_STRING:
339 + case typelib_TypeClass_TYPE:
340 + case typelib_TypeClass_ANY:
341 + case typelib_TypeClass_SEQUENCE:
342 + case typelib_TypeClass_INTERFACE:
343 + return RETURN_KIND_INDIRECT;
344 + case typelib_TypeClass_STRUCT:
345 + if (type->nSize > 16) {
346 + return RETURN_KIND_INDIRECT;
347 + }
348 + switch (getStructKind(
349 + reinterpret_cast<typelib_CompoundTypeDescription const *>(
350 + type)))
351 + {
352 + case STRUCT_KIND_FLOAT:
353 + return RETURN_KIND_HFA_FLOAT;
354 + case STRUCT_KIND_DOUBLE:
355 + return RETURN_KIND_HFA_DOUBLE;
356 + case STRUCT_KIND_DTOR:
357 + return RETURN_KIND_INDIRECT;
358 + default:
359 + return RETURN_KIND_REG;
360 + }
361 + }
362 +}
363 +
364 +}
365 +
366 +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
367 diff --git a/bridges/source/cpp_uno/gcc3_linux_aarch64/abi.hxx b/bridges/source/cpp_uno/gcc3_linux_aarch64/abi.hxx
368 new file mode 100644
369 index 0000000..2e3ce61
370 --- /dev/null
371 +++ b/bridges/source/cpp_uno/gcc3_linux_aarch64/abi.hxx
372 @@ -0,0 +1,87 @@
373 +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
374 +/*
375 + * This file is part of the LibreOffice project.
376 + *
377 + * This Source Code Form is subject to the terms of the Mozilla Public
378 + * License, v. 2.0. If a copy of the MPL was not distributed with this
379 + * file, You can obtain one at http://mozilla.org/MPL/2.0/.
380 + *
381 + * This file incorporates work covered by the following license notice:
382 + *
383 + * Licensed to the Apache Software Foundation (ASF) under one or more
384 + * contributor license agreements. See the NOTICE file distributed
385 + * with this work for additional information regarding copyright
386 + * ownership. The ASF licenses this file to you under the Apache
387 + * License, Version 2.0 (the "License"); you may not use this file
388 + * except in compliance with the License. You may obtain a copy of
389 + * the License at http://www.apache.org/licenses/LICENSE-2.0 .
390 + */
391 +
392 +#ifndef INCLUDED_BRIDGES_SOURCE_CPP_UNO_GCC3_LINUX_AARCH64_ABI_HXX
393 +#define INCLUDED_BRIDGES_SOURCE_CPP_UNO_GCC3_LINUX_AARCH64_ABI_HXX
394 +
395 +#include <sal/config.h>
396 +
397 +#include <exception>
398 +#include <typeinfo>
399 +
400 +#include <typelib/typedescription.h>
401 +#include <uno/any2.h>
402 +#include <uno/mapping.h>
403 +
404 +namespace abi_aarch64 {
405 +
406 +// Following declarations from libstdc++-v3/libsupc++/unwind-cxx.h and
407 +// lib/gcc/*-*-*/*/include/unwind.h:
408 +
409 +struct _Unwind_Exception
410 +{
411 + unsigned exception_class __attribute__((__mode__(__DI__)));
412 + void * exception_cleanup;
413 + unsigned private_1 __attribute__((__mode__(__word__)));
414 + unsigned private_2 __attribute__((__mode__(__word__)));
415 +} __attribute__((__aligned__));
416 +
417 +struct __cxa_exception
418 +{
419 + std::type_info *exceptionType;
420 + void (*exceptionDestructor)(void *);
421 +
422 + std::unexpected_handler unexpectedHandler;
423 + std::terminate_handler terminateHandler;
424 +
425 + __cxa_exception *nextException;
426 +
427 + int handlerCount;
428 +
429 + int handlerSwitchValue;
430 + const unsigned char *actionRecord;
431 + const unsigned char *languageSpecificData;
432 + void *catchTemp;
433 + void *adjustedPtr;
434 +
435 + _Unwind_Exception unwindHeader;
436 +};
437 +
438 +struct __cxa_eh_globals
439 +{
440 + __cxa_exception *caughtExceptions;
441 + unsigned int uncaughtExceptions;
442 +};
443 +
444 +void mapException(
445 + __cxa_exception * exception, uno_Any * any, uno_Mapping * mapping);
446 +
447 +void raiseException(uno_Any * any, uno_Mapping * mapping);
448 +
449 +enum ReturnKind {
450 + RETURN_KIND_REG, RETURN_KIND_HFA_FLOAT, RETURN_KIND_HFA_DOUBLE,
451 + RETURN_KIND_INDIRECT };
452 +
453 +ReturnKind getReturnKind(typelib_TypeDescription const * type);
454 +
455 +}
456 +
457 +#endif
458 +
459 +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
460 diff --git a/bridges/source/cpp_uno/gcc3_linux_aarch64/callvirtualfunction.cxx b/bridges/source/cpp_uno/gcc3_linux_aarch64/callvirtualfunction.cxx
461 new file mode 100644
462 index 0000000..09f7696
463 --- /dev/null
464 +++ b/bridges/source/cpp_uno/gcc3_linux_aarch64/callvirtualfunction.cxx
465 @@ -0,0 +1,66 @@
466 +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
467 +/*
468 + * This file is part of the LibreOffice project.
469 + *
470 + * This Source Code Form is subject to the terms of the Mozilla Public
471 + * License, v. 2.0. If a copy of the MPL was not distributed with this
472 + * file, You can obtain one at http://mozilla.org/MPL/2.0/.
473 + *
474 + * This file incorporates work covered by the following license notice:
475 + *
476 + * Licensed to the Apache Software Foundation (ASF) under one or more
477 + * contributor license agreements. See the NOTICE file distributed
478 + * with this work for additional information regarding copyright
479 + * ownership. The ASF licenses this file to you under the Apache
480 + * License, Version 2.0 (the "License"); you may not use this file
481 + * except in compliance with the License. You may obtain a copy of
482 + * the License at http://www.apache.org/licenses/LICENSE-2.0 .
483 + */
484 +
485 +#include <sal/config.h>
486 +
487 +#include <cstring>
488 +
489 +#include <sal/types.h>
490 +#include <sal/alloca.h>
491 +
492 +#include <callvirtualfunction.hxx>
493 +
494 +void callVirtualFunction(
495 + unsigned long function, unsigned long * gpr, unsigned long * fpr,
496 + unsigned long * stack, sal_Int32 sp, void * ret)
497 +{
498 + void * stackargs;
499 + if (sp != 0) {
500 + stackargs = alloca(((sp + 1) >> 1) * 16);
501 + std::memcpy(stackargs, stack, sp * 8);
502 + }
503 + asm volatile(
504 + "ldp x0, x1, [%[gpr_]]\n\t"
505 + "ldp x2, x3, [%[gpr_], #16]\n\t"
506 + "ldp x4, x5, [%[gpr_], #32]\n\t"
507 + "ldp x6, x7, [%[gpr_], #48]\n\t"
508 + "ldr x8, %[ret_]\n\t"
509 + "ldr x9, %[function_]\n\t"
510 + "ldp d0, d1, [%[fpr_]]\n\t"
511 + "ldp d2, d3, [%[fpr_], #16]\n\t"
512 + "ldp d4, d5, [%[fpr_], #32]\n\t"
513 + "ldp d6, d7, [%[fpr_], #48]\n\t"
514 + "blr x9\n\t"
515 + "stp x0, x1, [%[gpr_]]\n\t"
516 + "stp d0, d1, [%[fpr_]]\n\t"
517 + "stp d2, d3, [%[fpr_], #16]\n\t"
518 + :: [gpr_]"r" (gpr), [fpr_]"r" (fpr), [function_]"m" (function),
519 + [ret_]"m" (ret),
520 + "m" (stackargs) // dummy input to prevent optimizing the alloca away
521 + : "r0", "r1", "r2", "r3", "r4", "r5", "r6", "r7", "r8", "r9", "r10",
522 + "r11", "r12", "r13", "r14", "r15", "r16", "r17", "r18"/*TODO?*/, "v0",
523 + "v1", "v2", "v3", "v4", "v5", "v6", "v7", "v8", "v9", "v10", "v11",
524 + "v12", "v13", "v14", "v15", "v16", "v17", "v18", "v19", "v20", "v21",
525 + "v22", "v23", "v24", "v25", "v26", "v27", "v28", "v29", "v30", "v31",
526 + "memory"
527 + // only the bottom 64 bits of v8--15 need to be preserved by callees
528 + );
529 +}
530 +
531 +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
532 diff --git a/bridges/source/cpp_uno/gcc3_linux_aarch64/callvirtualfunction.hxx b/bridges/source/cpp_uno/gcc3_linux_aarch64/callvirtualfunction.hxx
533 new file mode 100644
534 index 0000000..b1b003f
535 --- /dev/null
536 +++ b/bridges/source/cpp_uno/gcc3_linux_aarch64/callvirtualfunction.hxx
537 @@ -0,0 +1,33 @@
538 +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
539 +/*
540 + * This file is part of the LibreOffice project.
541 + *
542 + * This Source Code Form is subject to the terms of the Mozilla Public
543 + * License, v. 2.0. If a copy of the MPL was not distributed with this
544 + * file, You can obtain one at http://mozilla.org/MPL/2.0/.
545 + *
546 + * This file incorporates work covered by the following license notice:
547 + *
548 + * Licensed to the Apache Software Foundation (ASF) under one or more
549 + * contributor license agreements. See the NOTICE file distributed
550 + * with this work for additional information regarding copyright
551 + * ownership. The ASF licenses this file to you under the Apache
552 + * License, Version 2.0 (the "License"); you may not use this file
553 + * except in compliance with the License. You may obtain a copy of
554 + * the License at http://www.apache.org/licenses/LICENSE-2.0 .
555 + */
556 +
557 +#ifndef INCLUDED_BRIDGES_SOURCE_CPP_UNO_GCC3_LINUX_AARCH64_CALLVIRTUALFUNCTION_HXX
558 +#define INCLUDED_BRIDGES_SOURCE_CPP_UNO_GCC3_LINUX_AARCH64_CALLVIRTUALFUNCTION_HXX
559 +
560 +#include <sal/config.h>
561 +
562 +#include <sal/types.h>
563 +
564 +void callVirtualFunction(
565 + unsigned long function, unsigned long * gpr, unsigned long * fpr,
566 + unsigned long * stack, sal_Int32 sp, void * ret);
567 +
568 +#endif
569 +
570 +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
571 diff --git a/bridges/source/cpp_uno/gcc3_linux_aarch64/cpp2uno.cxx b/bridges/source/cpp_uno/gcc3_linux_aarch64/cpp2uno.cxx
572 new file mode 100644
573 index 0000000..a73d9be
574 --- /dev/null
575 +++ b/bridges/source/cpp_uno/gcc3_linux_aarch64/cpp2uno.cxx
576 @@ -0,0 +1,464 @@
577 +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
578 +/*
579 + * This file is part of the LibreOffice project.
580 + *
581 + * This Source Code Form is subject to the terms of the Mozilla Public
582 + * License, v. 2.0. If a copy of the MPL was not distributed with this
583 + * file, You can obtain one at http://mozilla.org/MPL/2.0/.
584 + *
585 + * This file incorporates work covered by the following license notice:
586 + *
587 + * Licensed to the Apache Software Foundation (ASF) under one or more
588 + * contributor license agreements. See the NOTICE file distributed
589 + * with this work for additional information regarding copyright
590 + * ownership. The ASF licenses this file to you under the Apache
591 + * License, Version 2.0 (the "License"); you may not use this file
592 + * except in compliance with the License. You may obtain a copy of
593 + * the License at http://www.apache.org/licenses/LICENSE-2.0 .
594 + */
595 +
596 +#include <sal/config.h>
597 +
598 +#include <cassert>
599 +#include <cstdarg>
600 +#include <cstddef>
601 +#include <cstdlib>
602 +#include <cstring>
603 +
604 +#include <dlfcn.h>
605 +
606 +#include <com/sun/star/uno/XInterface.hpp>
607 +#include <com/sun/star/uno/genfunc.hxx>
608 +#include <sal/alloca.h>
609 +#include <sal/types.h>
610 +#include <typelib/typeclass.h>
611 +#include <typelib/typedescription.h>
612 +#include <typelib/typedescription.hxx>
613 +
614 +#include <bridges/cpp_uno/shared/bridge.hxx>
615 +#include <bridges/cpp_uno/shared/cppinterfaceproxy.hxx>
616 +#include <bridges/cpp_uno/shared/types.hxx>
617 +#include <bridges/cpp_uno/shared/vtablefactory.hxx>
618 +
619 +#include <abi.hxx>
620 +
621 +extern "C" void vtableSlotCall_();
622 +
623 +namespace {
624 +
625 +void call(
626 + bridges::cpp_uno::shared::CppInterfaceProxy * proxy,
627 + css::uno::TypeDescription const & description,
628 + typelib_TypeDescriptionReference * returnType, sal_Int32 count,
629 + typelib_MethodParameter * parameters, unsigned long * gpr,
630 + unsigned long * fpr, unsigned long * stack, void * indirectRet)
631 +{
632 + typelib_TypeDescription * rtd = 0;
633 + if (returnType != 0) {
634 + TYPELIB_DANGER_GET(&rtd, returnType);
635 + }
636 + abi_aarch64::ReturnKind retKind = rtd == 0
637 + ? abi_aarch64::RETURN_KIND_REG : abi_aarch64::getReturnKind(rtd);
638 + bool retConv = rtd != 0
639 + && bridges::cpp_uno::shared::relatesToInterfaceType(rtd);
640 + void * retin = retKind == abi_aarch64::RETURN_KIND_INDIRECT && !retConv
641 + ? indirectRet : rtd == 0 ? 0 : alloca(rtd->nSize);
642 + void ** args = static_cast< void ** >(alloca(count * sizeof (void *)));
643 + void ** cppArgs = static_cast< void ** >(alloca(count * sizeof (void *)));
644 + typelib_TypeDescription ** argtds = static_cast<typelib_TypeDescription **>(
645 + alloca(count * sizeof (typelib_TypeDescription *)));
646 + sal_Int32 ngpr = 1;
647 + sal_Int32 nfpr = 0;
648 + sal_Int32 sp = 0;
649 + for (sal_Int32 i = 0; i != count; ++i) {
650 + if (!parameters[i].bOut
651 + && bridges::cpp_uno::shared::isSimpleType(parameters[i].pTypeRef))
652 + {
653 + switch (parameters[i].pTypeRef->eTypeClass) {
654 + case typelib_TypeClass_BOOLEAN:
655 + case typelib_TypeClass_BYTE:
656 + case typelib_TypeClass_SHORT:
657 + case typelib_TypeClass_UNSIGNED_SHORT:
658 + case typelib_TypeClass_LONG:
659 + case typelib_TypeClass_UNSIGNED_LONG:
660 + case typelib_TypeClass_HYPER:
661 + case typelib_TypeClass_UNSIGNED_HYPER:
662 + case typelib_TypeClass_CHAR:
663 + case typelib_TypeClass_ENUM:
664 + args[i] = ngpr == 8 ? stack + sp++ : gpr + ngpr++;
665 + break;
666 + case typelib_TypeClass_FLOAT:
667 + case typelib_TypeClass_DOUBLE:
668 + args[i] = nfpr == 8 ? stack + sp++ : fpr + nfpr++;
669 + break;
670 + default:
671 + assert(false);
672 + }
673 + argtds[i] = 0;
674 + } else {
675 + cppArgs[i] = reinterpret_cast<void *>(
676 + ngpr == 8 ? stack[sp++] : gpr[ngpr++]);
677 + typelib_TypeDescription * ptd = 0;
678 + TYPELIB_DANGER_GET(&ptd, parameters[i].pTypeRef);
679 + if (!parameters[i].bIn) {
680 + args[i] = alloca(ptd->nSize);
681 + argtds[i] = ptd;
682 + } else if (bridges::cpp_uno::shared::relatesToInterfaceType(ptd)) {
683 + args[i] = alloca(ptd->nSize);
684 + uno_copyAndConvertData(
685 + args[i], cppArgs[i], ptd, proxy->getBridge()->getCpp2Uno());
686 + argtds[i] = ptd;
687 + } else {
688 + args[i] = cppArgs[i];
689 + argtds[i] = 0;
690 + TYPELIB_DANGER_RELEASE(ptd);
691 + }
692 + }
693 + }
694 + uno_Any exc;
695 + uno_Any * pexc = &exc;
696 + proxy->getUnoI()->pDispatcher(
697 + proxy->getUnoI(), description.get(), retin, args, &pexc);
698 + if (pexc != 0) {
699 + for (sal_Int32 i = 0; i != count; ++i) {
700 + if (argtds[i] != 0) {
701 + if (parameters[i].bIn) {
702 + uno_destructData(args[i], argtds[i], 0);
703 + }
704 + TYPELIB_DANGER_RELEASE(argtds[i]);
705 + }
706 + }
707 + if (rtd != 0) {
708 + TYPELIB_DANGER_RELEASE(rtd);
709 + }
710 + abi_aarch64::raiseException(&exc, proxy->getBridge()->getUno2Cpp());
711 + }
712 + for (sal_Int32 i = 0; i != count; ++i) {
713 + if (argtds[i] != 0) {
714 + if (parameters[i].bOut) {
715 + uno_destructData(
716 + cppArgs[i], argtds[i],
717 + reinterpret_cast<uno_ReleaseFunc>(css::uno::cpp_release));
718 + uno_copyAndConvertData(
719 + cppArgs[i], args[i], argtds[i],
720 + proxy->getBridge()->getUno2Cpp());
721 + }
722 + uno_destructData(args[i], argtds[i], 0);
723 + TYPELIB_DANGER_RELEASE(argtds[i]);
724 + }
725 + }
726 + void * retout = 0; // avoid false -Werror=maybe-uninitialized
727 + switch (retKind) {
728 + case abi_aarch64::RETURN_KIND_REG:
729 + switch (rtd == 0 ? typelib_TypeClass_VOID : rtd->eTypeClass) {
730 + case typelib_TypeClass_VOID:
731 + break;
732 + case typelib_TypeClass_BOOLEAN:
733 + case typelib_TypeClass_BYTE:
734 + case typelib_TypeClass_SHORT:
735 + case typelib_TypeClass_UNSIGNED_SHORT:
736 + case typelib_TypeClass_LONG:
737 + case typelib_TypeClass_UNSIGNED_LONG:
738 + case typelib_TypeClass_HYPER:
739 + case typelib_TypeClass_UNSIGNED_HYPER:
740 + case typelib_TypeClass_CHAR:
741 + case typelib_TypeClass_ENUM:
742 + std::memcpy(gpr, retin, rtd->nSize);
743 + assert(!retConv);
744 + break;
745 + case typelib_TypeClass_FLOAT:
746 + case typelib_TypeClass_DOUBLE:
747 + std::memcpy(fpr, retin, rtd->nSize);
748 + assert(!retConv);
749 + break;
750 + case typelib_TypeClass_STRUCT:
751 + if (retConv) {
752 + retout = gpr;
753 + } else {
754 + std::memcpy(gpr, retin, rtd->nSize);
755 + }
756 + break;
757 + default:
758 + assert(false);
759 + }
760 + break;
761 + case abi_aarch64::RETURN_KIND_HFA_FLOAT:
762 + assert(rtd != 0);
763 + switch (rtd->nSize) {
764 + case 16:
765 + std::memcpy(fpr + 3, static_cast<char *>(retin) + 12, 4);
766 + // fall through
767 + case 12:
768 + std::memcpy(fpr + 2, static_cast<char *>(retin) + 8, 4);
769 + // fall through
770 + case 8:
771 + std::memcpy(fpr + 1, static_cast<char *>(retin) + 4, 4);
772 + // fall through
773 + case 4:
774 + std::memcpy(fpr, retin, 4);
775 + break;
776 + default:
777 + assert(false);
778 + }
779 + assert(!retConv);
780 + break;
781 + case abi_aarch64::RETURN_KIND_HFA_DOUBLE:
782 + assert(rtd != 0);
783 + std::memcpy(fpr, retin, rtd->nSize);
784 + assert(!retConv);
785 + break;
786 + case abi_aarch64::RETURN_KIND_INDIRECT:
787 + retout = indirectRet;
788 + break;
789 + }
790 + if (retConv) {
791 + uno_copyAndConvertData(
792 + retout, retin, rtd, proxy->getBridge()->getUno2Cpp());
793 + uno_destructData(retin, rtd, 0);
794 + }
795 + if (rtd != 0) {
796 + TYPELIB_DANGER_RELEASE(rtd);
797 + }
798 +}
799 +
800 +extern "C" void vtableCall(
801 + sal_Int32 functionIndex, sal_Int32 vtableOffset,
802 + unsigned long * gpr, unsigned long * fpr, unsigned long * stack,
803 + void * indirectRet)
804 +{
805 + bridges::cpp_uno::shared::CppInterfaceProxy * proxy
806 + = bridges::cpp_uno::shared::CppInterfaceProxy::castInterfaceToProxy(
807 + reinterpret_cast<char *>(gpr[0]) - vtableOffset);
808 + typelib_InterfaceTypeDescription * type = proxy->getTypeDescr();
809 + assert(functionIndex < type->nMapFunctionIndexToMemberIndex);
810 + sal_Int32 pos = type->pMapFunctionIndexToMemberIndex[functionIndex];
811 + css::uno::TypeDescription desc(type->ppAllMembers[pos]);
812 + switch (desc.get()->eTypeClass) {
813 + case typelib_TypeClass_INTERFACE_ATTRIBUTE:
814 + if (type->pMapMemberIndexToFunctionIndex[pos] == functionIndex) {
815 + // Getter:
816 + call(
817 + proxy, desc,
818 + reinterpret_cast<typelib_InterfaceAttributeTypeDescription *>(
819 + desc.get())->pAttributeTypeRef,
820 + 0, 0, gpr, fpr, stack, indirectRet);
821 + } else {
822 + // Setter:
823 + typelib_MethodParameter param = {
824 + 0,
825 + reinterpret_cast<typelib_InterfaceAttributeTypeDescription *>(
826 + desc.get())->pAttributeTypeRef,
827 + true, false };
828 + call(proxy, desc, 0, 1, &param, gpr, fpr, stack, indirectRet);
829 + }
830 + break;
831 + case typelib_TypeClass_INTERFACE_METHOD:
832 + switch (functionIndex) {
833 + case 1:
834 + proxy->acquireProxy();
835 + break;
836 + case 2:
837 + proxy->releaseProxy();
838 + break;
839 + case 0:
840 + {
841 + typelib_TypeDescription * td = 0;
842 + TYPELIB_DANGER_GET(
843 + &td,
844 + (reinterpret_cast<css::uno::Type *>(gpr[1])
845 + ->getTypeLibType()));
846 + if (td != 0 && td->eTypeClass == typelib_TypeClass_INTERFACE) {
847 + css::uno::XInterface * ifc = 0;
848 + proxy->getBridge()->getCppEnv()->getRegisteredInterface(
849 + proxy->getBridge()->getCppEnv(),
850 + reinterpret_cast<void **>(&ifc), proxy->getOid().pData,
851 + reinterpret_cast<typelib_InterfaceTypeDescription *>(
852 + td));
853 + if (ifc != 0) {
854 + uno_any_construct(
855 + reinterpret_cast<uno_Any *>(indirectRet), &ifc, td,
856 + reinterpret_cast<uno_AcquireFunc>(
857 + css::uno::cpp_acquire));
858 + ifc->release();
859 + TYPELIB_DANGER_RELEASE(td);
860 + break;
861 + }
862 + TYPELIB_DANGER_RELEASE(td);
863 + }
864 + }
865 + // fall through
866 + default:
867 + call(
868 + proxy, desc,
869 + reinterpret_cast<typelib_InterfaceMethodTypeDescription *>(
870 + desc.get())->pReturnTypeRef,
871 + reinterpret_cast<typelib_InterfaceMethodTypeDescription *>(
872 + desc.get())->nParams,
873 + reinterpret_cast<typelib_InterfaceMethodTypeDescription *>(
874 + desc.get())->pParams,
875 + gpr, fpr, stack, indirectRet);
876 + }
877 + break;
878 + default:
879 + assert(false);
880 + }
881 +}
882 +
883 +struct aarch64_va_list {
884 + void * stack;
885 + void * gr_top;
886 + void * vr_top;
887 + int gr_offs;
888 + int vr_offs;
889 +};
890 +
891 +#pragma GCC diagnostic push
892 +#pragma GCC diagnostic ignored "-Wvolatile-register-var"
893 +extern "C" void vtableSlotCall(
894 + unsigned long gpr0, unsigned long gpr1, unsigned long gpr2,
895 + unsigned long gpr3, unsigned long gpr4, unsigned long gpr5,
896 + unsigned long gpr6, unsigned long gpr7, double fpr0, double fpr1,
897 + double fpr2, double fpr3, double fpr4, double fpr5, double fpr6,
898 + double fpr7, ...)
899 +{
900 + register void * volatile indirectRet asm ("x8");
901 + register sal_Int32 volatile functionIndex asm ("x9");
902 + register sal_Int32 volatile vtableOffset asm ("x10");
903 + va_list ap;
904 + va_start(ap, fpr7);
905 + assert(sizeof (va_list) == sizeof (aarch64_va_list));
906 + unsigned long gpr[8];
907 + gpr[0] = gpr0;
908 + gpr[1] = gpr1;
909 + gpr[2] = gpr2;
910 + gpr[3] = gpr3;
911 + gpr[4] = gpr4;
912 + gpr[5] = gpr5;
913 + gpr[6] = gpr6;
914 + gpr[7] = gpr7;
915 + double fpr[8];
916 + fpr[0] = fpr0;
917 + fpr[1] = fpr1;
918 + fpr[2] = fpr2;
919 + fpr[3] = fpr3;
920 + fpr[4] = fpr4;
921 + fpr[5] = fpr5;
922 + fpr[6] = fpr6;
923 + fpr[7] = fpr7;
924 + vtableCall(
925 + functionIndex, vtableOffset, gpr,
926 + reinterpret_cast<unsigned long *>(fpr),
927 + static_cast<unsigned long *>(
928 + reinterpret_cast<aarch64_va_list *>(&ap)->stack),
929 + indirectRet);
930 + asm volatile(
931 + "ldp x0, x1, [%[gpr_]]\n\t"
932 + "ldp d0, d1, [%[fpr_]]\n\t"
933 + "ldp d2, d3, [%[fpr_], #16]\n\t"
934 + :: [gpr_]"r" (gpr), [fpr_]"r" (fpr)
935 + : "r0", "r1", "v0", "v1", "v2", "v3");
936 +}
937 +#pragma GCC diagnostic pop
938 +
939 +std::size_t const codeSnippetSize = 8 * 4;
940 +
941 +unsigned char * generateCodeSnippet(
942 + unsigned char * code, sal_Int32 functionIndex, sal_Int32 vtableOffset)
943 +{
944 + // movz x9, <low functionIndex>
945 + reinterpret_cast<unsigned int *>(code)[0] = 0xD2800009
946 + | ((functionIndex & 0xFFFF) << 5);
947 + // movk x9, <high functionIndex>, LSL #16
948 + reinterpret_cast<unsigned int *>(code)[1] = 0xF2A00009
949 + | ((functionIndex >> 16) << 5);
950 + // movz x10, <low vtableOffset>
951 + reinterpret_cast<unsigned int *>(code)[2] = 0xD280000A
952 + | ((vtableOffset & 0xFFFF) << 5);
953 + // movk x10, <high vtableOffset>, LSL #16
954 + reinterpret_cast<unsigned int *>(code)[3] = 0xF2A0000A
955 + | ((vtableOffset >> 16) << 5);
956 + // ldr x11, +2*4
957 + reinterpret_cast<unsigned int *>(code)[4] = 0x5800004B;
958 + // br x11
959 + reinterpret_cast<unsigned int *>(code)[5] = 0xD61F0160;
960 + reinterpret_cast<unsigned long *>(code)[3]
961 + = reinterpret_cast<unsigned long>(&vtableSlotCall);
962 + return code + codeSnippetSize;
963 +}
964 +
965 +}
966 +
967 +struct bridges::cpp_uno::shared::VtableFactory::Slot { void * fn; };
968 +
969 +bridges::cpp_uno::shared::VtableFactory::Slot *
970 +bridges::cpp_uno::shared::VtableFactory::mapBlockToVtable(void * block) {
971 + return static_cast<Slot *>(block) + 2;
972 +}
973 +
974 +sal_Size bridges::cpp_uno::shared::VtableFactory::getBlockSize(
975 + sal_Int32 slotCount)
976 +{
977 + return (slotCount + 2) * sizeof (Slot) + slotCount * codeSnippetSize;
978 +}
979 +
980 +bridges::cpp_uno::shared::VtableFactory::Slot *
981 +bridges::cpp_uno::shared::VtableFactory::initializeBlock(
982 + void * block, sal_Int32 slotCount)
983 +{
984 + Slot * slots = mapBlockToVtable(block);
985 + slots[-2].fn = 0;
986 + slots[-1].fn = 0;
987 + return slots + slotCount;
988 +}
989 +
990 +unsigned char * bridges::cpp_uno::shared::VtableFactory::addLocalFunctions(
991 + Slot ** slots, unsigned char * code, sal_PtrDiff writetoexecdiff,
992 + typelib_InterfaceTypeDescription const * type, sal_Int32 functionOffset,
993 + sal_Int32 functionCount, sal_Int32 vtableOffset)
994 +{
995 + (*slots) -= functionCount;
996 + Slot * s = *slots;
997 + for (sal_Int32 i = 0; i != type->nMembers; ++i) {
998 + typelib_TypeDescription * td = 0;
999 + TYPELIB_DANGER_GET(&td, type->ppMembers[i]);
1000 + assert(td != 0);
1001 + switch (td->eTypeClass) {
1002 + case typelib_TypeClass_INTERFACE_ATTRIBUTE:
1003 + {
1004 + typelib_InterfaceAttributeTypeDescription * atd
1005 + = reinterpret_cast<
1006 + typelib_InterfaceAttributeTypeDescription *>(td);
1007 + // Getter:
1008 + (s++)->fn = code + writetoexecdiff;
1009 + code = generateCodeSnippet(
1010 + code, functionOffset++, vtableOffset);
1011 + // Setter:
1012 + if (!atd->bReadOnly) {
1013 + (s++)->fn = code + writetoexecdiff;
1014 + code = generateCodeSnippet(
1015 + code, functionOffset++, vtableOffset);
1016 + }
1017 + break;
1018 + }
1019 + case typelib_TypeClass_INTERFACE_METHOD:
1020 + (s++)->fn = code + writetoexecdiff;
1021 + code = generateCodeSnippet(code, functionOffset++, vtableOffset);
1022 + break;
1023 + default:
1024 + assert(false);
1025 + }
1026 + TYPELIB_DANGER_RELEASE(td);
1027 + }
1028 + return code;
1029 +}
1030 +
1031 +void bridges::cpp_uno::shared::VtableFactory::flushCode(
1032 + unsigned char const * begin, unsigned char const * end)
1033 +{
1034 + static void (*clear_cache)(unsigned char const *, unsigned char const *)
1035 + = (void (*)(unsigned char const *, unsigned char const *)) dlsym(
1036 + RTLD_DEFAULT, "__clear_cache");
1037 + (*clear_cache)(begin, end);
1038 +}
1039 +
1040 +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
1041 diff --git a/bridges/source/cpp_uno/gcc3_linux_aarch64/uno2cpp.cxx b/bridges/source/cpp_uno/gcc3_linux_aarch64/uno2cpp.cxx
1042 new file mode 100644
1043 index 0000000..9c9a24a
1044 --- /dev/null
1045 +++ b/bridges/source/cpp_uno/gcc3_linux_aarch64/uno2cpp.cxx
1046 @@ -0,0 +1,376 @@
1047 +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
1048 +/*
1049 + * This file is part of the LibreOffice project.
1050 + *
1051 + * This Source Code Form is subject to the terms of the Mozilla Public
1052 + * License, v. 2.0. If a copy of the MPL was not distributed with this
1053 + * file, You can obtain one at http://mozilla.org/MPL/2.0/.
1054 + *
1055 + * This file incorporates work covered by the following license notice:
1056 + *
1057 + * Licensed to the Apache Software Foundation (ASF) under one or more
1058 + * contributor license agreements. See the NOTICE file distributed
1059 + * with this work for additional information regarding copyright
1060 + * ownership. The ASF licenses this file to you under the Apache
1061 + * License, Version 2.0 (the "License"); you may not use this file
1062 + * except in compliance with the License. You may obtain a copy of
1063 + * the License at http://www.apache.org/licenses/LICENSE-2.0 .
1064 + */
1065 +
1066 +#include <sal/config.h>
1067 +
1068 +#include <cassert>
1069 +#include <cstring>
1070 +#include <exception>
1071 +#include <typeinfo>
1072 +
1073 +#include <cxxabi.h>
1074 +
1075 +#include <bridges/cpp_uno/shared/bridge.hxx>
1076 +#include <bridges/cpp_uno/shared/types.hxx>
1077 +#include <bridges/cpp_uno/shared/unointerfaceproxy.hxx>
1078 +#include <bridges/cpp_uno/shared/vtables.hxx>
1079 +#include <com/sun/star/uno/Exception.hpp>
1080 +#include <com/sun/star/uno/RuntimeException.hpp>
1081 +#include <com/sun/star/uno/genfunc.hxx>
1082 +#include <rtl/textenc.h>
1083 +#include <rtl/ustring.hxx>
1084 +#include <sal/alloca.h>
1085 +#include <sal/types.h>
1086 +#include <typelib/typeclass.h>
1087 +#include <typelib/typedescription.h>
1088 +#include <uno/any2.h>
1089 +#include <uno/data.h>
1090 +
1091 +#include <abi.hxx>
1092 +#include <callvirtualfunction.hxx>
1093 +
1094 +namespace {
1095 +
1096 +void pushArgument(
1097 + unsigned long value, unsigned long * stack, sal_Int32 * sp,
1098 + unsigned long * regs, sal_Int32 * nregs)
1099 +{
1100 + (*nregs != 8 ? regs[(*nregs)++] : stack[(*sp)++]) = value;
1101 +}
1102 +
1103 +void call(
1104 + bridges::cpp_uno::shared::UnoInterfaceProxy * proxy,
1105 + bridges::cpp_uno::shared::VtableSlot slot,
1106 + typelib_TypeDescriptionReference * returnType, sal_Int32 count,
1107 + typelib_MethodParameter * parameters, void * returnValue, void ** arguments,
1108 + uno_Any ** exception)
1109 +{
1110 + typelib_TypeDescription * rtd = 0;
1111 + TYPELIB_DANGER_GET(&rtd, returnType);
1112 + abi_aarch64::ReturnKind retKind = abi_aarch64::getReturnKind(rtd);
1113 + bool retConv = bridges::cpp_uno::shared::relatesToInterfaceType(rtd);
1114 + void * ret = retConv ? alloca(rtd->nSize) : returnValue;
1115 + unsigned long ** thisPtr
1116 + = reinterpret_cast<unsigned long **>(proxy->getCppI()) + slot.offset;
1117 + unsigned long * stack = static_cast<unsigned long *>(
1118 + alloca(count * sizeof (unsigned long)));
1119 + sal_Int32 sp = 0;
1120 + unsigned long gpr[8];
1121 + sal_Int32 ngpr = 0;
1122 + unsigned long fpr[8];
1123 + sal_Int32 nfpr = 0;
1124 + gpr[ngpr++] = reinterpret_cast<unsigned long>(thisPtr);
1125 + void ** cppArgs = static_cast<void **>(alloca(count * sizeof (void *)));
1126 + typelib_TypeDescription ** ptds =
1127 + static_cast<typelib_TypeDescription **>(
1128 + alloca(count * sizeof (typelib_TypeDescription *)));
1129 + for (sal_Int32 i = 0; i != count; ++i) {
1130 + if (!parameters[i].bOut &&
1131 + bridges::cpp_uno::shared::isSimpleType(parameters[i].pTypeRef))
1132 + {
1133 + cppArgs[i] = 0;
1134 + switch (parameters[i].pTypeRef->eTypeClass) {
1135 + case typelib_TypeClass_BOOLEAN:
1136 + pushArgument(
1137 + *static_cast<sal_Bool *>(arguments[i]), stack, &sp, gpr,
1138 + &ngpr);
1139 + break;
1140 + case typelib_TypeClass_BYTE:
1141 + pushArgument(
1142 + *static_cast<sal_Int8 *>(arguments[i]), stack, &sp, gpr,
1143 + &ngpr);
1144 + break;
1145 + case typelib_TypeClass_SHORT:
1146 + pushArgument(
1147 + *static_cast<sal_Int16 *>(arguments[i]), stack, &sp, gpr,
1148 + &ngpr);
1149 + break;
1150 + case typelib_TypeClass_UNSIGNED_SHORT:
1151 + pushArgument(
1152 + *static_cast<sal_uInt16 *>(arguments[i]), stack, &sp, gpr,
1153 + &ngpr);
1154 + break;
1155 + case typelib_TypeClass_LONG:
1156 + case typelib_TypeClass_ENUM:
1157 + pushArgument(
1158 + *static_cast<sal_Int32 *>(arguments[i]), stack, &sp, gpr,
1159 + &ngpr);
1160 + break;
1161 + case typelib_TypeClass_UNSIGNED_LONG:
1162 + pushArgument(
1163 + *static_cast<sal_uInt32 *>(arguments[i]), stack, &sp, gpr,
1164 + &ngpr);
1165 + break;
1166 + case typelib_TypeClass_HYPER:
1167 + pushArgument(
1168 + *static_cast<sal_Int64 *>(arguments[i]), stack, &sp, gpr,
1169 + &ngpr);
1170 + break;
1171 + case typelib_TypeClass_UNSIGNED_HYPER:
1172 + pushArgument(
1173 + *static_cast<sal_uInt64 *>(arguments[i]), stack, &sp, gpr,
1174 + &ngpr);
1175 + break;
1176 + case typelib_TypeClass_FLOAT:
1177 + pushArgument(
1178 + *static_cast<unsigned int *>(arguments[i]), stack, &sp, fpr,
1179 + &nfpr);
1180 + break;
1181 + case typelib_TypeClass_DOUBLE:
1182 + pushArgument(
1183 + *static_cast<unsigned long *>(arguments[i]), stack, &sp,
1184 + fpr, &nfpr);
1185 + break;
1186 + case typelib_TypeClass_CHAR:
1187 + pushArgument(
1188 + *static_cast<sal_Unicode *>(arguments[i]), stack, &sp, gpr,
1189 + &ngpr);
1190 + break;
1191 + default:
1192 + assert(false);
1193 + }
1194 + } else {
1195 + typelib_TypeDescription * ptd = 0;
1196 + TYPELIB_DANGER_GET(&ptd, parameters[i].pTypeRef);
1197 + if (!parameters[i].bIn) {
1198 + cppArgs[i] = alloca(ptd->nSize);
1199 + uno_constructData(cppArgs[i], ptd);
1200 + ptds[i] = ptd;
1201 + pushArgument(
1202 + reinterpret_cast<unsigned long>(cppArgs[i]), stack, &sp,
1203 + gpr, &ngpr);
1204 + } else if (bridges::cpp_uno::shared::relatesToInterfaceType(ptd)) {
1205 + cppArgs[i] = alloca(ptd->nSize);
1206 + uno_copyAndConvertData(
1207 + cppArgs[i], arguments[i], ptd,
1208 + proxy->getBridge()->getUno2Cpp());
1209 + ptds[i] = ptd;
1210 + pushArgument(
1211 + reinterpret_cast<unsigned long>(cppArgs[i]), stack, &sp,
1212 + gpr, &ngpr);
1213 + } else {
1214 + cppArgs[i] = 0;
1215 + pushArgument(
1216 + reinterpret_cast<unsigned long>(arguments[i]), stack, &sp,
1217 + gpr, &ngpr);
1218 + TYPELIB_DANGER_RELEASE(ptd);
1219 + }
1220 + }
1221 + }
1222 + try {
1223 + try {
1224 + callVirtualFunction(
1225 + (*thisPtr)[slot.index], gpr, fpr, stack, sp, ret);
1226 + } catch (css::uno::Exception &) {
1227 + throw;
1228 + } catch (std::exception & e) {
1229 + throw css::uno::RuntimeException(
1230 + ("C++ code threw "
1231 + + OStringToOUString(typeid(e).name(), RTL_TEXTENCODING_UTF8)
1232 + + ": " + OStringToOUString(e.what(), RTL_TEXTENCODING_UTF8)),
1233 + css::uno::Reference<css::uno::XInterface>());
1234 + } catch (...) {
1235 + throw css::uno::RuntimeException(
1236 + "C++ code threw unknown exception",
1237 + css::uno::Reference<css::uno::XInterface>());
1238 + }
1239 + } catch (css::uno::Exception &) {
1240 + abi_aarch64::mapException(
1241 + reinterpret_cast<abi_aarch64::__cxa_eh_globals *>(
1242 + __cxxabiv1::__cxa_get_globals())->caughtExceptions,
1243 + *exception, proxy->getBridge()->getCpp2Uno());
1244 + for (sal_Int32 i = 0; i != count; ++i) {
1245 + if (cppArgs[i] != 0) {
1246 + uno_destructData(
1247 + cppArgs[i], ptds[i],
1248 + reinterpret_cast<uno_ReleaseFunc>(css::uno::cpp_release));
1249 + TYPELIB_DANGER_RELEASE(ptds[i]);
1250 + }
1251 + }
1252 + TYPELIB_DANGER_RELEASE(rtd);
1253 + return;
1254 + }
1255 + *exception = 0;
1256 + for (sal_Int32 i = 0; i != count; ++i) {
1257 + if (cppArgs[i] != 0) {
1258 + if (parameters[i].bOut) {
1259 + if (parameters[i].bIn) {
1260 + uno_destructData(arguments[i], ptds[i], 0);
1261 + }
1262 + uno_copyAndConvertData(
1263 + arguments[i], cppArgs[i], ptds[i],
1264 + proxy->getBridge()->getCpp2Uno());
1265 + }
1266 + uno_destructData(
1267 + cppArgs[i], ptds[i],
1268 + reinterpret_cast<uno_ReleaseFunc>(css::uno::cpp_release));
1269 + TYPELIB_DANGER_RELEASE(ptds[i]);
1270 + }
1271 + }
1272 + switch (retKind) {
1273 + case abi_aarch64::RETURN_KIND_REG:
1274 + switch (rtd->eTypeClass) {
1275 + case typelib_TypeClass_VOID:
1276 + break;
1277 + case typelib_TypeClass_BOOLEAN:
1278 + case typelib_TypeClass_BYTE:
1279 + case typelib_TypeClass_SHORT:
1280 + case typelib_TypeClass_UNSIGNED_SHORT:
1281 + case typelib_TypeClass_LONG:
1282 + case typelib_TypeClass_UNSIGNED_LONG:
1283 + case typelib_TypeClass_HYPER:
1284 + case typelib_TypeClass_UNSIGNED_HYPER:
1285 + case typelib_TypeClass_CHAR:
1286 + case typelib_TypeClass_ENUM:
1287 + case typelib_TypeClass_STRUCT:
1288 + std::memcpy(ret, gpr, rtd->nSize);
1289 + break;
1290 + case typelib_TypeClass_FLOAT:
1291 + case typelib_TypeClass_DOUBLE:
1292 + std::memcpy(ret, fpr, rtd->nSize);
1293 + break;
1294 + default:
1295 + assert(false);
1296 + }
1297 + break;
1298 + case abi_aarch64::RETURN_KIND_HFA_FLOAT:
1299 + switch (rtd->nSize) {
1300 + case 16:
1301 + std::memcpy(static_cast<char *>(ret) + 12, fpr + 3, 4);
1302 + // fall through
1303 + case 12:
1304 + std::memcpy(static_cast<char *>(ret) + 8, fpr + 2, 4);
1305 + // fall through
1306 + case 8:
1307 + std::memcpy(static_cast<char *>(ret) + 4, fpr + 1, 4);
1308 + // fall through
1309 + case 4:
1310 + std::memcpy(ret, fpr, 4);
1311 + break;
1312 + default:
1313 + assert(false);
1314 + }
1315 + break;
1316 + case abi_aarch64::RETURN_KIND_HFA_DOUBLE:
1317 + std::memcpy(ret, fpr, rtd->nSize);
1318 + break;
1319 + case abi_aarch64::RETURN_KIND_INDIRECT:
1320 + break;
1321 + }
1322 + if (retConv) {
1323 + uno_copyAndConvertData(
1324 + returnValue, ret, rtd, proxy->getBridge()->getCpp2Uno());
1325 + uno_destructData(
1326 + ret, rtd, reinterpret_cast<uno_ReleaseFunc>(css::uno::cpp_release));
1327 + }
1328 + TYPELIB_DANGER_RELEASE(rtd);
1329 +}
1330 +
1331 +}
1332 +
1333 +namespace bridges { namespace cpp_uno { namespace shared {
1334 +
1335 +void unoInterfaceProxyDispatch(
1336 + uno_Interface * pUnoI, typelib_TypeDescription const * pMemberDescr,
1337 + void * pReturn, void ** pArgs, uno_Any ** ppException)
1338 +{
1339 + UnoInterfaceProxy * proxy = static_cast<UnoInterfaceProxy *>(pUnoI);
1340 + switch (pMemberDescr->eTypeClass) {
1341 + case typelib_TypeClass_INTERFACE_ATTRIBUTE:
1342 + {
1343 + typelib_InterfaceAttributeTypeDescription const * atd
1344 + = reinterpret_cast<
1345 + typelib_InterfaceAttributeTypeDescription const *>(
1346 + pMemberDescr);
1347 + VtableSlot slot(getVtableSlot(atd));
1348 + if (pReturn != 0) { // getter
1349 + call(
1350 + proxy, slot, atd->pAttributeTypeRef, 0, 0, pReturn, pArgs,
1351 + ppException);
1352 + } else { // setter
1353 + typelib_MethodParameter param = {
1354 + 0, atd->pAttributeTypeRef, true, false };
1355 + typelib_TypeDescriptionReference * rtd = 0;
1356 + typelib_typedescriptionreference_new(
1357 + &rtd, typelib_TypeClass_VOID, OUString("void").pData);
1358 + slot.index += 1;
1359 + call(proxy, slot, rtd, 1, &param, pReturn, pArgs, ppException);
1360 + typelib_typedescriptionreference_release(rtd);
1361 + }
1362 + break;
1363 + }
1364 + case typelib_TypeClass_INTERFACE_METHOD:
1365 + {
1366 + typelib_InterfaceMethodTypeDescription const * mtd
1367 + = reinterpret_cast<
1368 + typelib_InterfaceMethodTypeDescription const *>(
1369 + pMemberDescr);
1370 + VtableSlot slot(getVtableSlot(mtd));
1371 + switch (slot.index) {
1372 + case 1:
1373 + pUnoI->acquire(pUnoI);
1374 + *ppException = 0;
1375 + break;
1376 + case 2:
1377 + pUnoI->release(pUnoI);
1378 + *ppException = 0;
1379 + break;
1380 + case 0:
1381 + {
1382 + typelib_TypeDescription * td = 0;
1383 + TYPELIB_DANGER_GET(
1384 + &td,
1385 + (reinterpret_cast<css::uno::Type *>(pArgs[0])
1386 + ->getTypeLibType()));
1387 + if (td != 0) {
1388 + uno_Interface * ifc = 0;
1389 + proxy->pBridge->getUnoEnv()->getRegisteredInterface(
1390 + proxy->pBridge->getUnoEnv(),
1391 + reinterpret_cast<void **>(&ifc), proxy->oid.pData,
1392 + reinterpret_cast<
1393 + typelib_InterfaceTypeDescription *>(td));
1394 + if (ifc != 0) {
1395 + uno_any_construct(
1396 + reinterpret_cast<uno_Any *>(pReturn), &ifc, td,
1397 + 0);
1398 + ifc->release(ifc);
1399 + TYPELIB_DANGER_RELEASE(td);
1400 + *ppException = 0;
1401 + break;
1402 + }
1403 + TYPELIB_DANGER_RELEASE(td);
1404 + }
1405 + }
1406 + // fall through
1407 + default:
1408 + call(
1409 + proxy, slot, mtd->pReturnTypeRef, mtd->nParams,
1410 + mtd->pParams, pReturn, pArgs, ppException);
1411 + break;
1412 + }
1413 + break;
1414 + }
1415 + default:
1416 + assert(false);
1417 + }
1418 +}
1419 +
1420 +} } }
1421 +
1422 +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
1423 diff --git a/configure.ac b/configure.ac
1424 index 5ead2a0..826797f8 100644
1425 --- a/configure.ac
1426 +++ b/configure.ac
1427 @@ -4292,6 +4292,12 @@ linux-gnu*)
1428
1429 case "$host_cpu" in
1430
1431 + aarch64)
1432 + CPUNAME=AARCH64
1433 + PLATFORMID=linux_aarch64
1434 + RTL_ARCH=AARCH64
1435 + OUTPATH=unxlngaarch64
1436 + ;;
1437 alpha)
1438 CPUNAME=AXP
1439 RTL_ARCH=ALPHA
1440 diff --git a/desktop/source/deployment/misc/dp_platform.cxx b/desktop/source/deployment/misc/dp_platform.cxx
1441 index 09b3fcd..6b04004 100644
1442 --- a/desktop/source/deployment/misc/dp_platform.cxx
1443 +++ b/desktop/source/deployment/misc/dp_platform.cxx
1444 @@ -45,7 +45,7 @@
1445 #define PLATFORM_LINUX_S390x "linux_s390x"
1446 #define PLATFORM_LINUX_HPPA "linux_hppa"
1447 #define PLATFORM_LINUX_ALPHA "linux_alpha"
1448 -
1449 +#define PLATFORM_LINUX_AARCH64 "linux_aarch64"
1450
1451
1452 #define PLATFORM_SOLARIS_SPARC "solaris_sparc"
1453 @@ -149,6 +149,8 @@ namespace
1454 ret = checkOSandCPU("Linux", "HPPA");
1455 else if (token == PLATFORM_LINUX_ALPHA)
1456 ret = checkOSandCPU("Linux", "ALPHA");
1457 + else if (token == PLATFORM_LINUX_AARCH64)
1458 + ret = checkOSandCPU("Linux", "AARCH64");
1459 else if (token == PLATFORM_SOLARIS_SPARC)
1460 ret = checkOSandCPU("Solaris", "SPARC");
1461 else if (token == PLATFORM_SOLARIS_SPARC64)
1462 diff --git a/jvmfwk/plugins/sunmajor/pluginlib/vendorbase.hxx b/jvmfwk/plugins/sunmajor/pluginlib/vendorbase.hxx
1463 index 25baaee5..29f2641 100644
1464 --- a/jvmfwk/plugins/sunmajor/pluginlib/vendorbase.hxx
1465 +++ b/jvmfwk/plugins/sunmajor/pluginlib/vendorbase.hxx
1466 @@ -65,6 +65,8 @@ OpenJDK at least, but probably not true for Lemotes JDK */
1467 #define JFW_PLUGIN_ARCH "parisc"
1468 #elif defined AXP
1469 #define JFW_PLUGIN_ARCH "alpha"
1470 +#elif defined AARCH64
1471 +#define JFW_PLUGIN_ARCH "aarch64"
1472 #else // SPARC, INTEL, POWERPC, MIPS, ARM, IA64, M68K, HPPA, ALPHA
1473 #error unknown platform
1474 #endif // SPARC, INTEL, POWERPC, MIPS, ARM, IA64, M68K, HPPA, ALPHA
1475 diff --git a/solenv/gbuild/platform/LINUX_AARCH64_GCC.mk b/solenv/gbuild/platform/LINUX_AARCH64_GCC.mk
1476 new file mode 100644
1477 index 0000000..682199e
1478 --- /dev/null
1479 +++ b/solenv/gbuild/platform/LINUX_AARCH64_GCC.mk
1480 @@ -0,0 +1,14 @@
1481 +# -*- Mode: makefile-gmake; tab-width: 4; indent-tabs-mode: t -*-
1482 +#
1483 +# This file is part of the LibreOffice project.
1484 +#
1485 +# This Source Code Form is subject to the terms of the Mozilla Public
1486 +# License, v. 2.0. If a copy of the MPL was not distributed with this
1487 +# file, You can obtain one at http://mozilla.org/MPL/2.0/.
1488 +#
1489 +
1490 +gb_COMPILERDEFAULTOPTFLAGS := -Os
1491 +
1492 +include $(GBUILDDIR)/platform/linux.mk
1493 +
1494 +# vim: set noet sw=4:
1495 --
1496 1.9.3
1497

  ViewVC Help
Powered by ViewVC 1.1.30