1 /* -*- Mode: C; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* This Source Code Form is subject to the terms of the Mozilla Public
3  * License, v. 2.0. If a copy of the MPL was not distributed with this
4  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5 
6 /* Implement shared vtbl methods. */
7 
8 #include "xptcprivate.h"
9 
10 #if defined(AIX)
11 
12 /*
13         For PPC (AIX & MAC), the first 8 integral and the first 13 f.p. parameters
14         arrive in a separate chunk of data that has been loaded from the registers.
15         The args pointer has been set to the start of the parameters BEYOND the ones
16         arriving in registers
17 */
18 extern "C" nsresult ATTRIBUTE_USED
PrepareAndDispatch(nsXPTCStubBase * self,uint32_t methodIndex,uint32_t * args,uint32_t * gprData,double * fprData)19 PrepareAndDispatch(nsXPTCStubBase* self, uint32_t methodIndex, uint32_t* args, uint32_t *gprData, double *fprData)
20 {
21     typedef struct {
22         uint32_t hi;
23         uint32_t lo;      // have to move 64 bit entities as 32 bit halves since
24     } DU;               // stack slots are not guaranteed 16 byte aligned
25 
26 #define PARAM_GPR_COUNT         7
27 
28     nsXPTCMiniVariant paramBuffer[PARAM_BUFFER_COUNT];
29     const nsXPTMethodInfo* info = nullptr;
30     uint8_t paramCount;
31     uint8_t i;
32 
33     NS_ASSERTION(self,"no self");
34 
35     self->mEntry->GetMethodInfo(uint16_t(methodIndex), &info);
36     NS_ASSERTION(info,"no method info");
37 
38     paramCount = info->GetParamCount();
39 
40     const uint8_t indexOfJSContext = info->IndexOfJSContext();
41 
42     uint32_t* ap = args;
43     uint32_t iCount = 0;
44     uint32_t fpCount = 0;
45     for(i = 0; i < paramCount; i++)
46     {
47         const nsXPTParamInfo& param = info->GetParam(i);
48         const nsXPTType& type = param.GetType();
49         nsXPTCMiniVariant* dp = &paramBuffer[i];
50 
51         if (i == indexOfJSContext) {
52             if (iCount < PARAM_GPR_COUNT)
53                 iCount++;
54             else
55                 ap++;
56         }
57 
58         if(param.IsOut() || !type.IsArithmetic())
59         {
60             if (iCount < PARAM_GPR_COUNT)
61                 dp->val.p = (void*) gprData[iCount++];
62             else
63                 dp->val.p = (void*) *ap++;
64             continue;
65         }
66         // else
67         switch(type)
68         {
69         case nsXPTType::T_I8      :  if (iCount < PARAM_GPR_COUNT)
70                                          dp->val.i8  = (int8_t) gprData[iCount++];
71                                      else
72                                          dp->val.i8  = (int8_t)  *ap++;
73                                      break;
74         case nsXPTType::T_I16     :  if (iCount < PARAM_GPR_COUNT)
75                                          dp->val.i16  = (int16_t) gprData[iCount++];
76                                      else
77                                          dp->val.i16  = (int16_t)  *ap++;
78                                      break;
79         case nsXPTType::T_I32     :  if (iCount < PARAM_GPR_COUNT)
80                                          dp->val.i32  = (int32_t) gprData[iCount++];
81                                      else
82                                          dp->val.i32  = (int32_t)  *ap++;
83                                      break;
84         case nsXPTType::T_I64     :  if (iCount < PARAM_GPR_COUNT)
85                                          ((DU *)dp)->hi  = (int32_t) gprData[iCount++];
86                                      else
87                                          ((DU *)dp)->hi  = (int32_t)  *ap++;
88                                      if (iCount < PARAM_GPR_COUNT)
89                                          ((DU *)dp)->lo  = (uint32_t) gprData[iCount++];
90                                      else
91                                          ((DU *)dp)->lo  = (uint32_t)  *ap++;
92                                      break;
93         case nsXPTType::T_U8      :  if (iCount < PARAM_GPR_COUNT)
94                                          dp->val.u8  = (uint8_t) gprData[iCount++];
95                                      else
96                                          dp->val.u8  = (uint8_t)  *ap++;
97                                      break;
98         case nsXPTType::T_U16     :  if (iCount < PARAM_GPR_COUNT)
99                                          dp->val.u16  = (uint16_t) gprData[iCount++];
100                                      else
101                                          dp->val.u16  = (uint16_t)  *ap++;
102                                      break;
103         case nsXPTType::T_U32     :  if (iCount < PARAM_GPR_COUNT)
104                                          dp->val.u32  = (uint32_t) gprData[iCount++];
105                                      else
106                                          dp->val.u32  = (uint32_t)  *ap++;
107                                      break;
108         case nsXPTType::T_U64     :  if (iCount < PARAM_GPR_COUNT)
109                                          ((DU *)dp)->hi  = (uint32_t) gprData[iCount++];
110                                      else
111                                          ((DU *)dp)->hi  = (uint32_t)  *ap++;
112                                      if (iCount < PARAM_GPR_COUNT)
113                                          ((DU *)dp)->lo  = (uint32_t) gprData[iCount++];
114                                      else
115                                          ((DU *)dp)->lo  = (uint32_t)  *ap++;
116                                      break;
117         case nsXPTType::T_FLOAT   :  if (fpCount < 13) {
118                                          dp->val.f  = (float) fprData[fpCount++];
119                                          if (iCount < PARAM_GPR_COUNT)
120                                              ++iCount;
121                                          else
122                                              ++ap;
123                                      }
124                                      else
125                                          dp->val.f   = *((float*)   ap++);
126                                      break;
127         case nsXPTType::T_DOUBLE  :  if (fpCount < 13) {
128                                          dp->val.d  = (double) fprData[fpCount++];
129                                          if (iCount < PARAM_GPR_COUNT)
130                                              ++iCount;
131                                          else
132                                              ++ap;
133                                          if (iCount < PARAM_GPR_COUNT)
134                                              ++iCount;
135                                          else
136                                              ++ap;
137                                      }
138                                      else {
139                                          dp->val.f   = *((double*)   ap);
140                                          ap += 2;
141                                      }
142                                      break;
143         case nsXPTType::T_BOOL    :  if (iCount < PARAM_GPR_COUNT)
144                                          dp->val.b  = (bool) gprData[iCount++];
145                                      else
146                                          dp->val.b  = (bool)  *ap++;
147                                      break;
148         case nsXPTType::T_CHAR    :  if (iCount < PARAM_GPR_COUNT)
149                                          dp->val.c  = (char) gprData[iCount++];
150                                      else
151                                          dp->val.c  = (char)  *ap++;
152                                      break;
153         case nsXPTType::T_WCHAR   :  if (iCount < PARAM_GPR_COUNT)
154                                          dp->val.wc  = (wchar_t) gprData[iCount++];
155                                      else
156                                          dp->val.wc  = (wchar_t)  *ap++;
157                                      break;
158         default:
159             NS_ERROR("bad type");
160             break;
161         }
162     }
163 
164     nsresult result = self->mOuter->CallMethod((uint16_t)methodIndex, info,
165                                                paramBuffer);
166 
167     return result;
168 }
169 
170 #define STUB_ENTRY(n)
171 
172 #define SENTINEL_ENTRY(n) \
173 nsresult nsXPTCStubBase::Sentinel##n() \
174 { \
175     NS_ERROR("nsXPTCStubBase::Sentinel called"); \
176     return NS_ERROR_NOT_IMPLEMENTED; \
177 }
178 
179 #include "xptcstubsdef.inc"
180 
181 #endif /* AIX */
182