1 /*
2  * HvCallEvent.h
3  * Copyright (C) 2001  Mike Corrigan IBM Corporation
4  *
5  * This program is free software; you can redistribute it and/or modify
6  * it under the terms of the GNU General Public License as published by
7  * the Free Software Foundation; either version 2 of the License, or
8  * (at your option) any later version.
9  *
10  * This program is distributed in the hope that it will be useful,
11  * but WITHOUT ANY WARRANTY; without even the implied warranty of
12  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  * GNU General Public License for more details.
14  *
15  * You should have received a copy of the GNU General Public License
16  * along with this program; if not, write to the Free Software
17  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
18  */
19 
20 //==================================================================
21 //
22 //	This file contains the "hypervisor call" interface which is used to
23 //	drive the hypervisor from the OS.
24 //
25 //==================================================================
26 
27 //-------------------------------------------------------------------
28 // Standard Includes
29 //-------------------------------------------------------------------
30 #ifndef  _HVCALLSC_H
31 #include <asm/iSeries/HvCallSc.h>
32 #endif
33 
34 #ifndef  _HVTYPES_H
35 #include <asm/iSeries/HvTypes.h>
36 #endif
37 
38 #include <asm/abs_addr.h>
39 
40 //-------------------------------------------------------------------
41 // Other Includes
42 //-------------------------------------------------------------------
43 
44 //-------------------------------------------------------------------
45 // Constants
46 //-------------------------------------------------------------------
47 #ifndef _HVCALLEVENT_H
48 #define _HVCALLEVENT_H
49 
50 struct HvLpEvent;
51 
52 typedef u8 HvLpEvent_Type;
53 typedef u8 HvLpEvent_AckInd;
54 typedef u8 HvLpEvent_AckType;
55 
56 struct	HvCallEvent_PackedParms
57 {
58 	u8		xAckType:1;
59 	u8		xAckInd:1;
60 	u8		xRsvd:1;
61 	u8		xTargetLp:5;
62 	u8		xType;
63 	u16		xSubtype;
64 	HvLpInstanceId	xSourceInstId;
65 	HvLpInstanceId	xTargetInstId;
66 };
67 
68 typedef u8 HvLpDma_Direction;
69 typedef u8 HvLpDma_AddressType;
70 
71 struct	HvCallEvent_PackedDmaParms
72 {
73 	u8		xDirection:1;
74 	u8		xLocalAddrType:1;
75 	u8		xRemoteAddrType:1;
76 	u8		xRsvd1:5;
77 	HvLpIndex	xRemoteLp;
78 	u8		xType;
79 	u8		xRsvd2;
80 	HvLpInstanceId	xLocalInstId;
81 	HvLpInstanceId	xRemoteInstId;
82 };
83 
84 typedef u64 HvLpEvent_Rc;
85 typedef u64 HvLpDma_Rc;
86 
87 #define HvCallEventAckLpEvent				HvCallEvent +  0
88 #define HvCallEventCancelLpEvent			HvCallEvent +  1
89 #define HvCallEventCloseLpEventPath			HvCallEvent +  2
90 #define HvCallEventDmaBufList				HvCallEvent +  3
91 #define HvCallEventDmaSingle				HvCallEvent +  4
92 #define HvCallEventDmaToSp				HvCallEvent +  5
93 #define HvCallEventGetOverflowLpEvents			HvCallEvent +  6
94 #define HvCallEventGetSourceLpInstanceId		HvCallEvent +  7
95 #define HvCallEventGetTargetLpInstanceId		HvCallEvent +  8
96 #define HvCallEventOpenLpEventPath			HvCallEvent +  9
97 #define HvCallEventSetLpEventStack			HvCallEvent + 10
98 #define HvCallEventSignalLpEvent			HvCallEvent + 11
99 #define HvCallEventSignalLpEventParms			HvCallEvent + 12
100 #define HvCallEventSetInterLpQueueIndex			HvCallEvent + 13
101 #define HvCallEventSetLpEventQueueInterruptProc		HvCallEvent + 14
102 #define HvCallEventRouter15				HvCallEvent + 15
103 
104 //======================================================================
HvCallEvent_getOverflowLpEvents(u8 queueIndex)105 static inline void		HvCallEvent_getOverflowLpEvents(u8 queueIndex)
106 {
107 	HvCall1(HvCallEventGetOverflowLpEvents,queueIndex);
108 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
109 }
110 //======================================================================
HvCallEvent_setInterLpQueueIndex(u8 queueIndex)111 static inline void		HvCallEvent_setInterLpQueueIndex(u8 queueIndex)
112 {
113 	HvCall1(HvCallEventSetInterLpQueueIndex,queueIndex);
114 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
115 }
116 //======================================================================
HvCallEvent_setLpEventStack(u8 queueIndex,char * eventStackAddr,u32 eventStackSize)117 static inline void		HvCallEvent_setLpEventStack(u8 queueIndex,
118 					     char * eventStackAddr,
119 					     u32 eventStackSize)
120 {
121 	u64 abs_addr;
122 	abs_addr = virt_to_absolute( (unsigned long) eventStackAddr );
123 
124 	HvCall3(HvCallEventSetLpEventStack, queueIndex, abs_addr, eventStackSize);
125 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
126 }
127 //======================================================================
HvCallEvent_setLpEventQueueInterruptProc(u8 queueIndex,u16 lpLogicalProcIndex)128 static inline void		HvCallEvent_setLpEventQueueInterruptProc(u8 queueIndex,
129 							  u16 lpLogicalProcIndex)
130 {
131 	HvCall2(HvCallEventSetLpEventQueueInterruptProc,queueIndex,lpLogicalProcIndex);
132 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
133 }
134 //=====================================================================
HvCallEvent_signalLpEvent(struct HvLpEvent * event)135 static inline HvLpEvent_Rc HvCallEvent_signalLpEvent(struct HvLpEvent* event)
136 {
137 	u64 abs_addr;
138 	HvLpEvent_Rc retVal;
139 #ifdef DEBUG_SENDEVENT
140 	printk("HvCallEvent_signalLpEvent: *event = %016lx\n ", (unsigned long)event);
141 #endif
142 	abs_addr = virt_to_absolute( (unsigned long) event );
143 	retVal = (HvLpEvent_Rc)HvCall1(HvCallEventSignalLpEvent, abs_addr);
144 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
145 	return retVal;
146 }
147 //=====================================================================
HvCallEvent_signalLpEventFast(HvLpIndex targetLp,HvLpEvent_Type type,u16 subtype,HvLpEvent_AckInd ackInd,HvLpEvent_AckType ackType,HvLpInstanceId sourceInstanceId,HvLpInstanceId targetInstanceId,u64 correlationToken,u64 eventData1,u64 eventData2,u64 eventData3,u64 eventData4,u64 eventData5)148 static inline HvLpEvent_Rc  HvCallEvent_signalLpEventFast(HvLpIndex targetLp,
149 					   HvLpEvent_Type type,
150 					   u16 subtype,
151 					   HvLpEvent_AckInd ackInd,
152 					   HvLpEvent_AckType ackType,
153 					   HvLpInstanceId sourceInstanceId,
154 					   HvLpInstanceId targetInstanceId,
155 					   u64 correlationToken,
156 					   u64 eventData1,
157 					   u64 eventData2,
158 					   u64 eventData3,
159 					   u64 eventData4,
160 					   u64 eventData5)
161 {
162 	HvLpEvent_Rc retVal;
163 
164 	// Pack the misc bits into a single Dword to pass to PLIC
165 	union
166 	{
167 		struct HvCallEvent_PackedParms	parms;
168 		u64		dword;
169 	} packed;
170 	packed.parms.xAckType	= ackType;
171 	packed.parms.xAckInd	= ackInd;
172 	packed.parms.xRsvd	= 0;
173 	packed.parms.xTargetLp	= targetLp;
174 	packed.parms.xType	= type;
175 	packed.parms.xSubtype	= subtype;
176 	packed.parms.xSourceInstId	= sourceInstanceId;
177 	packed.parms.xTargetInstId	= targetInstanceId;
178 
179 	retVal = (HvLpEvent_Rc)HvCall7(HvCallEventSignalLpEventParms,
180 				       packed.dword,
181 				       correlationToken,
182 				       eventData1,eventData2,
183 				       eventData3,eventData4,
184 				       eventData5);
185 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
186 	return retVal;
187 }
188 //====================================================================
HvCallEvent_ackLpEvent(struct HvLpEvent * event)189 static inline HvLpEvent_Rc	HvCallEvent_ackLpEvent(struct HvLpEvent* event)
190 {
191 	u64 abs_addr;
192 	HvLpEvent_Rc retVal;
193 	abs_addr = virt_to_absolute( (unsigned long) event );
194 
195 	retVal = (HvLpEvent_Rc)HvCall1(HvCallEventAckLpEvent, abs_addr);
196 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
197 	return retVal;
198 }
199 //====================================================================
HvCallEvent_cancelLpEvent(struct HvLpEvent * event)200 static inline HvLpEvent_Rc   HvCallEvent_cancelLpEvent(struct HvLpEvent* event)
201 {
202 	u64 abs_addr;
203 	HvLpEvent_Rc retVal;
204 	abs_addr = virt_to_absolute( (unsigned long) event );
205 
206 	retVal = (HvLpEvent_Rc)HvCall1(HvCallEventCancelLpEvent, abs_addr);
207 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
208 	return retVal;
209 }
210 //===================================================================
HvCallEvent_getSourceLpInstanceId(HvLpIndex targetLp,HvLpEvent_Type type)211 static inline HvLpInstanceId	HvCallEvent_getSourceLpInstanceId(HvLpIndex targetLp, HvLpEvent_Type type)
212 {
213 	HvLpInstanceId retVal;
214 	retVal = HvCall2(HvCallEventGetSourceLpInstanceId,targetLp,type);
215 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
216 	return retVal;
217 }
218 //===================================================================
HvCallEvent_getTargetLpInstanceId(HvLpIndex targetLp,HvLpEvent_Type type)219 static inline HvLpInstanceId	HvCallEvent_getTargetLpInstanceId(HvLpIndex targetLp, HvLpEvent_Type type)
220 {
221 	HvLpInstanceId retVal;
222 	retVal = HvCall2(HvCallEventGetTargetLpInstanceId,targetLp,type);
223 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
224 	return retVal;
225 }
226 //===================================================================
HvCallEvent_openLpEventPath(HvLpIndex targetLp,HvLpEvent_Type type)227 static inline void		HvCallEvent_openLpEventPath(HvLpIndex targetLp,
228 					     HvLpEvent_Type type)
229 {
230 	HvCall2(HvCallEventOpenLpEventPath,targetLp,type);
231 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
232 }
233 //===================================================================
HvCallEvent_closeLpEventPath(HvLpIndex targetLp,HvLpEvent_Type type)234 static inline void		HvCallEvent_closeLpEventPath(HvLpIndex targetLp,
235 					      HvLpEvent_Type type)
236 {
237 	HvCall2(HvCallEventCloseLpEventPath,targetLp,type);
238 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
239 }
240 //===================================================================
HvCallEvent_dmaBufList(HvLpEvent_Type type,HvLpIndex remoteLp,HvLpDma_Direction direction,HvLpInstanceId localInstanceId,HvLpInstanceId remoteInstanceId,HvLpDma_AddressType localAddressType,HvLpDma_AddressType remoteAddressType,u64 localBufList,u64 remoteBufList,u32 transferLength)241 static inline HvLpDma_Rc	HvCallEvent_dmaBufList(HvLpEvent_Type type,
242 					HvLpIndex remoteLp,
243 					HvLpDma_Direction direction,
244 					HvLpInstanceId localInstanceId,
245 					HvLpInstanceId remoteInstanceId,
246 					HvLpDma_AddressType localAddressType,
247 					HvLpDma_AddressType remoteAddressType,
248 					// Do these need to be converted to
249 					// absolute addresses?
250 					u64 localBufList,
251 					u64 remoteBufList,
252 
253 					u32 transferLength)
254 {
255 	HvLpDma_Rc retVal;
256 	// Pack the misc bits into a single Dword to pass to PLIC
257 	union
258 	{
259 		struct HvCallEvent_PackedDmaParms	parms;
260 		u64		dword;
261 	} packed;
262 	packed.parms.xDirection		= direction;
263 	packed.parms.xLocalAddrType	= localAddressType;
264 	packed.parms.xRemoteAddrType	= remoteAddressType;
265 	packed.parms.xRsvd1		= 0;
266 	packed.parms.xRemoteLp		= remoteLp;
267 	packed.parms.xType		= type;
268 	packed.parms.xRsvd2		= 0;
269 	packed.parms.xLocalInstId	= localInstanceId;
270 	packed.parms.xRemoteInstId	= remoteInstanceId;
271 
272 	retVal = (HvLpDma_Rc)HvCall4(HvCallEventDmaBufList,
273 				     packed.dword,
274 				     localBufList,
275 				     remoteBufList,
276 				     transferLength);
277 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
278 	return retVal;
279 }
280 //=================================================================
HvCallEvent_dmaSingle(HvLpEvent_Type type,HvLpIndex remoteLp,HvLpDma_Direction direction,HvLpInstanceId localInstanceId,HvLpInstanceId remoteInstanceId,HvLpDma_AddressType localAddressType,HvLpDma_AddressType remoteAddressType,u64 localAddrOrTce,u64 remoteAddrOrTce,u32 transferLength)281 static inline HvLpDma_Rc	HvCallEvent_dmaSingle(HvLpEvent_Type type,
282 				       HvLpIndex remoteLp,
283 				       HvLpDma_Direction direction,
284 				       HvLpInstanceId localInstanceId,
285 				       HvLpInstanceId remoteInstanceId,
286 				       HvLpDma_AddressType localAddressType,
287 				       HvLpDma_AddressType remoteAddressType,
288 				       u64 localAddrOrTce,
289 				       u64 remoteAddrOrTce,
290 				       u32 transferLength)
291 {
292 	HvLpDma_Rc retVal;
293 	// Pack the misc bits into a single Dword to pass to PLIC
294 	union
295 	{
296 		struct HvCallEvent_PackedDmaParms	parms;
297 		u64		dword;
298 	} packed;
299 	packed.parms.xDirection		= direction;
300 	packed.parms.xLocalAddrType	= localAddressType;
301 	packed.parms.xRemoteAddrType	= remoteAddressType;
302 	packed.parms.xRsvd1		= 0;
303 	packed.parms.xRemoteLp		= remoteLp;
304 	packed.parms.xType		= type;
305 	packed.parms.xRsvd2		= 0;
306 	packed.parms.xLocalInstId	= localInstanceId;
307 	packed.parms.xRemoteInstId	= remoteInstanceId;
308 
309 	retVal = (HvLpDma_Rc)HvCall4(HvCallEventDmaSingle,
310 				     packed.dword,
311 				     localAddrOrTce,
312 				     remoteAddrOrTce,
313 				     transferLength);
314 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
315 	return retVal;
316 }
317 //=================================================================
HvCallEvent_dmaToSp(void * local,u32 remote,u32 length,HvLpDma_Direction dir)318 static inline HvLpDma_Rc	HvCallEvent_dmaToSp(void* local, u32 remote, u32 length, HvLpDma_Direction dir)
319 {
320 	u64 abs_addr;
321 	HvLpDma_Rc retVal;
322 	abs_addr = virt_to_absolute( (unsigned long) local );
323 
324 	retVal = (HvLpDma_Rc)HvCall4(HvCallEventDmaToSp,
325 				     abs_addr,
326 				     remote,
327 				     length,
328 				     dir);
329 	// getPaca()->adjustHmtForNoOfSpinLocksHeld();
330 	return retVal;
331 }
332 //================================================================
333 
334 #endif // _HVCALLEVENT_H
335 
336