1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/xpcom/reflect/xptcall/src/md/unix/xptcinvoke_sparc_openbsd.cpp Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,128 @@ 1.4 +/* -*- Mode: C; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ 1.5 +/* This Source Code Form is subject to the terms of the Mozilla Public 1.6 + * License, v. 2.0. If a copy of the MPL was not distributed with this 1.7 + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 1.8 + 1.9 +/* Platform specific code to invoke XPCOM methods on native objects */ 1.10 + 1.11 +#include "xptcprivate.h" 1.12 + 1.13 +#if !defined(__sparc__) 1.14 +#error "This code is for Sparc only" 1.15 +#endif 1.16 + 1.17 +typedef unsigned nsXPCVariant; 1.18 + 1.19 +extern "C" uint32_t 1.20 +invoke_count_words(uint32_t paramCount, nsXPTCVariant* s) 1.21 +{ 1.22 + uint32_t result = 0; 1.23 + for(uint32_t i = 0; i < paramCount; i++, s++) 1.24 + { 1.25 + if(s->IsPtrData()) 1.26 + { 1.27 + result++; 1.28 + continue; 1.29 + } 1.30 + switch(s->type) 1.31 + { 1.32 + case nsXPTType::T_I8 : 1.33 + case nsXPTType::T_I16 : 1.34 + case nsXPTType::T_I32 : 1.35 + result++; 1.36 + break; 1.37 + case nsXPTType::T_I64 : 1.38 + result+=2; 1.39 + break; 1.40 + case nsXPTType::T_U8 : 1.41 + case nsXPTType::T_U16 : 1.42 + case nsXPTType::T_U32 : 1.43 + result++; 1.44 + break; 1.45 + case nsXPTType::T_U64 : 1.46 + result+=2; 1.47 + break; 1.48 + case nsXPTType::T_FLOAT : 1.49 + result++; 1.50 + break; 1.51 + case nsXPTType::T_DOUBLE : 1.52 + result+=2; 1.53 + break; 1.54 + case nsXPTType::T_BOOL : 1.55 + case nsXPTType::T_CHAR : 1.56 + case nsXPTType::T_WCHAR : 1.57 + result++; 1.58 + break; 1.59 + default: 1.60 + // all the others are plain pointer types 1.61 + result++; 1.62 + break; 1.63 + } 1.64 + } 1.65 + // nuts, I know there's a cooler way of doing this, but it's late 1.66 + // now and it'll probably come to me in the morning. 1.67 + if (result & 0x3) result += 4 - (result & 0x3); // ensure q-word alignment 1.68 + return result; 1.69 +} 1.70 + 1.71 +extern "C" uint32_t 1.72 +invoke_copy_to_stack(uint32_t* d, uint32_t paramCount, nsXPTCVariant* s) 1.73 +{ 1.74 +/* 1.75 + We need to copy the parameters for this function to locals and use them 1.76 + from there since the parameters occupy the same stack space as the stack 1.77 + we're trying to populate. 1.78 +*/ 1.79 + uint32_t *l_d = d; 1.80 + nsXPTCVariant *l_s = s; 1.81 + uint32_t l_paramCount = paramCount; 1.82 + uint32_t regCount = 0; // return the number of registers to load from the stack 1.83 + 1.84 + typedef struct { 1.85 + uint32_t hi; 1.86 + uint32_t lo; 1.87 + } DU; // have to move 64 bit entities as 32 bit halves since 1.88 + // stack slots are not guaranteed 16 byte aligned 1.89 + 1.90 + for(uint32_t i = 0; i < l_paramCount; i++, l_d++, l_s++) 1.91 + { 1.92 + if (regCount < 5) regCount++; 1.93 + if(l_s->IsPtrData()) 1.94 + { 1.95 + if(l_s->type == nsXPTType::T_JSVAL) 1.96 + { 1.97 + // On SPARC, we need to pass a pointer to HandleValue 1.98 + *((void**)l_d) = &l_s->ptr; 1.99 + } else 1.100 + { 1.101 + *((void**)l_d) = l_s->ptr; 1.102 + } 1.103 + continue; 1.104 + } 1.105 + switch(l_s->type) 1.106 + { 1.107 + case nsXPTType::T_I8 : *((int32_t*) l_d) = l_s->val.i8; break; 1.108 + case nsXPTType::T_I16 : *((int32_t*) l_d) = l_s->val.i16; break; 1.109 + case nsXPTType::T_I32 : *((int32_t*) l_d) = l_s->val.i32; break; 1.110 + case nsXPTType::T_I64 : 1.111 + case nsXPTType::T_U64 : 1.112 + case nsXPTType::T_DOUBLE : *((uint32_t*) l_d++) = ((DU *)l_s)->hi; 1.113 + if (regCount < 5) regCount++; 1.114 + *((uint32_t*) l_d) = ((DU *)l_s)->lo; 1.115 + break; 1.116 + case nsXPTType::T_U8 : *((uint32_t*) l_d) = l_s->val.u8; break; 1.117 + case nsXPTType::T_U16 : *((uint32_t*) l_d) = l_s->val.u16; break; 1.118 + case nsXPTType::T_U32 : *((uint32_t*) l_d) = l_s->val.u32; break; 1.119 + case nsXPTType::T_FLOAT : *((float*) l_d) = l_s->val.f; break; 1.120 + case nsXPTType::T_BOOL : *((uint32_t*) l_d) = l_s->val.b; break; 1.121 + case nsXPTType::T_CHAR : *((uint32_t*) l_d) = l_s->val.c; break; 1.122 + case nsXPTType::T_WCHAR : *((int32_t*) l_d) = l_s->val.wc; break; 1.123 + default: 1.124 + // all the others are plain pointer types 1.125 + *((void**)l_d) = l_s->val.p; 1.126 + break; 1.127 + } 1.128 + } 1.129 + return regCount; 1.130 +} 1.131 +