1{$IFDEF OGC_INTERFACE}
2//#define __stringify(rn)								#rn // ??
3//#define ATTRIBUTE_ALIGN(v)							__attribute__((aligned(v)))
4//#define STACK_ALIGN(type, name, cnt, alignment)		u8 _al__##name[((sizeof(type)*(cnt)) + (alignment) + (((sizeof(type)*(cnt))%(alignment)) > 0 ? ((alignment) - ((sizeof(type)*(cnt))%(alignment))) : 0))]; \
5//													type *name = (type*)(((u32)(_al__##name)) + ((alignment) - (((u32)(_al__##name))&((alignment)-1))))
6
7procedure _sync(); inline; assembler;
8procedure _nop(); inline; assembler;
9procedure ppcsync(); inline; assembler;
10procedure ppchalt(); inline;
11//procedure mfpvr(); inline;
12function mfpvr(): cint32; inline;
13
14function mfdcr(_rn: cuint): cuint32; inline;
15procedure mtdcr(rn, val: cuint); inline;
16function mfmsr(): cuint32; inline;
17procedure mtmsr(val: cuint); inline;
18function mfdec(): cuint32; inline;
19procedure mtdec(_val: cuint); inline;
20function mfspr(_rn: cuint): cuint32; inline;
21procedure mtspr(_rn, _val: cuint); inline;
22
23{$define mfwpar()	:= mfspr(WPAR)}
24{$define mtwpar(_val)	:= mtspr(WPAR,_val)}
25
26{$define mfmmcr0()	:= mfspr(MMCR0)}
27{$define mtmmcr0(_val):= mtspr(MMCR0,_val)}
28{$define mfmmcr1()	:= mfspr(MMCR1)}
29{$define mtmmcr1(_val):= mtspr(MMCR1,_val)}
30
31{$define mfpmc1()	:= mfspr(PMC1)}
32{$define mtpmc1(_val) := mtspr(PMC1,_val)}
33{$define mfpmc2() := mfspr(PMC2)}
34{$define mtpmc2(_val) := mtspr(PMC2,_val)}
35{$define mfpmc3() := mfspr(PMC3)}
36{$define mtpmc3(_val) := mtspr(PMC3,_val)}
37{$define mfpmc4() := mfspr(PMC4)}
38{$define mtpmc4(_val) := mtspr(PMC4,_val)}
39
40{$define mfhid0() := mfspr(HID0)}
41{$define mthid0(_val) := mtspr(HID0,_val)}
42{$define mfhid1() := mfspr(HID1)}
43{$define mthid1(_val) := mtspr(HID1,_val)}
44{$define mfhid2() := mfspr(HID2)}
45{$define mthid2(_val) := mtspr(HID2,_val)}
46{$define mfhid4() := mfspr(HID4)}
47{$define mthid4(_val) := mtspr(HID4,_val)}
48
49function __lhbrx(base, index: cuint32): cuint16; inline;
50//procedure __lwbrx(base,index: cuint32); inline;
51function __lwbrx(base,index: cuint32): cuint32; inline;
52procedure __sthbrx(base,index,value: cuint32); inline;
53procedure __stwbrx(base,index,value: cuint32); inline;
54function cntlzw(_val: cuint32): cuint32; inline;
55procedure _CPU_MSR_GET( _msr_value: cuint32 ); inline;
56procedure _CPU_MSR_SET( _msr_value: cuint32 ); inline;
57procedure _CPU_ISR_Enable(); inline;
58procedure _CPU_ISR_Disable( _isr_cookie: cuint32 ); inline;
59procedure _CPU_ISR_Restore( _isr_cookie: cuint32 ); inline;
60procedure _CPU_ISR_Flash( _isr_cookie: cuint32 ); inline;
61procedure _CPU_FPR_Enable(); inline;
62procedure _CPU_FPR_Disable(); inline;
63function bswap16(val: cuint16): cuint16; inline;
64function bswap32(val: cuint32): cuint32; inline;
65function bswap64(val: cuint64): cuint64; inline;
66
67// Basic I/O
68function read32(addr: cuint32): cuint32; inline;
69procedure write32(addr, x: cuint32); inline;
70procedure mask32(addr, clear, _set: cuint32); inline;
71function read16(addr: cuint32): cuint16; inline;
72procedure write16(addr: cuint32; x: cuint16); inline;
73function read8(addr: cuint32): cuint8; inline;
74procedure write8(addr: cuint32; x: cuint8); inline;
75procedure writef32(addr: cuint32; x: f32); inline;
76{$ENDIF}
77
78
79
80
81{$IFDEF OGC_IMPLEMENTATION}
82procedure _sync(); inline; assembler;
83asm
84  sync
85end;
86
87procedure _nop(); inline; assembler;
88asm
89  nop
90end;
91
92procedure ppcsync(); inline; assembler;
93asm
94  sc
95end;
96
97procedure ppchalt(); inline;
98begin
99	asm
100    sync
101  end;
102	while true do
103  asm
104	  nop
105    li 3,0
106    nop
107  end;
108end;
109
110function mfpvr(): cint32; inline;
111var
112  _rval: cuint32;
113begin
114  asm
115//    mfpvr r3     // unrecognized opcode?
116    mfspr r3,287     // unrecognized opcode?
117  end;
118  result := _rval;
119end;
120
121function mfdcr(_rn: cuint): cuint32; inline;
122var
123  _rval: cuint32;
124begin
125  asm
126  //    mfdcr r3,_rn  // unrecognized opcode?
127  end;
128  result := _rval;
129end;
130
131procedure mtdcr(rn, val: cuint); inline;
132begin
133  asm
134//    mtdcr rn,r3   // unrecognized opcode?
135  end;
136end;
137
138function mfmsr(): cuint32; inline;
139var
140  _rval: cuint32;
141begin
142  asm
143    mfmsr r3
144  end;
145  result := _rval;
146end;
147
148procedure mtmsr(val: cuint); inline;
149begin
150  asm
151    mtmsr r3
152  end;
153end;
154
155function mfdec(): cuint32; inline;
156var
157  _rval: cuint32;
158begin
159  asm
160//    mfdec r3    // unrecognized opcode?
161    mfspr r3,22    // unrecognized opcode?
162  end;
163  result := _rval;
164end;
165
166procedure mtdec(_val: cuint); inline;
167begin
168  asm
169//    mtdec r3   // unrecognized opcode?
170    mtspr 22,r3   // unrecognized opcode?
171  end;
172end;
173
174function mfspr(_rn: cuint): cuint32; inline;
175var
176  _rval: cuint32 = 0;
177begin
178	asm
179    mfspr r3,r4
180  end;
181  result := _rval;
182end;
183
184procedure mtspr(_rn, _val: cuint); inline;
185begin
186  asm
187    mtspr r3,r4
188  end;
189end;
190
191function __lhbrx(base, index: cuint32): cuint16; inline;
192var
193  res: cuint16;
194begin
195	asm
196    lhbrx	r3,r4,r5
197  end;
198  result := res;
199end;
200
201//procedure __lwbrx(base,index: cuint32); inline;
202function __lwbrx(base,index: cuint32): cuint32; inline;
203var
204  res: cuint32;
205begin
206	asm
207    lwbrx	r3,r4,r5
208  end;
209  result := res;
210end;
211
212procedure __sthbrx(base,index,value: cuint32); inline;
213begin
214	asm
215    sthbrx	r3,r4,f5
216  end;
217end;
218
219procedure __stwbrx(base,index,value: cuint32); inline;
220begin
221	asm
222    stwbrx	r3,r4,r5
223  end;
224end;
225
226function cntlzw(_val: cuint32): cuint32; inline;
227var
228  _rval: cuint32;
229begin
230  asm
231    cntlzw r3, r4
232  end;
233  result := _rval;
234end;
235
236procedure _CPU_MSR_GET( _msr_value: cuint32 ); inline;
237begin
238  repeat
239    _msr_value := 0;
240    asm
241      mfmsr r3
242    end;
243  until false;
244end;
245
246procedure _CPU_MSR_SET( _msr_value: cuint32 ); inline;
247begin
248  asm
249    mtmsr r3
250  end;
251end;
252
253procedure _CPU_ISR_Enable(); inline;
254var
255  _val: cuint32 = 0;
256begin
257  asm
258		mfmsr r3
259		ori r3,r3,0x8000
260		mtmsr r3
261  end;
262end;
263
264procedure _CPU_ISR_Disable( _isr_cookie: cuint32 ); inline;
265var
266  _disable_mask: cuint32 = 0;
267begin
268	_isr_cookie := 0;
269  asm
270	  mfmsr r3
271	  rlwinm r4,r3,0,17,15
272	  mtmsr r4
273	  extrwi r3,r3,1,16
274  end;
275end;
276
277procedure _CPU_ISR_Restore( _isr_cookie: cuint32 ); inline;
278var
279  _enable_mask: cuint32 = 0;
280begin
281	asm
282    cmpwi r3,0
283    beq .L1
284    mfmsr r4
285    ori r4,r4,0x8000
286    mtmsr r4
287	.L1:
288  end;
289end;
290
291
292
293procedure _CPU_ISR_Flash( _isr_cookie: cuint32 ); inline;
294var
295  _flash_mask: cuint32 = 0;
296begin
297  asm
298    cmpwi r3,0
299    beq .L1
300    mfmsr r4
301    ori r4,r4,0x8000
302    mtmsr r4
303    rlwinm r4,r4,0,17,15
304    mtmsr r4
305    .L1:
306  end;
307end;
308
309procedure _CPU_FPR_Enable(); inline;
310var
311  _val: cuint32 = 0;
312begin
313  asm
314    mfmsr r3;
315    ori r3,r3,0x2000;
316    mtmsr r3
317  end;
318end;
319
320procedure _CPU_FPR_Disable(); inline;
321var
322  _val: cuint32 = 0;
323begin
324  asm
325    mfmsr r3;
326    rlwinm r3,r3,0,19,17;
327    mtmsr r3
328  end;
329end;
330
331function bswap16(val: cuint16): cuint16; inline;
332var
333  tmp: cuint16;
334begin
335	tmp := val;
336  result := __lhbrx(tmp,0); //??
337end;
338
339function bswap32(val: cuint32): cuint32; inline;
340var
341  tmp: cuint32;
342begin
343  tmp := val;
344	result := __lwbrx(tmp,0);
345end;
346
347function bswap64(val: cuint64): cuint64; inline;
348type
349	ullc = record
350    case integer of
351		  0: (ull: cuint64);
352		  1: (ul: array [0..1] of cuint32)
353	end;
354var
355  outv: ullc;
356  tmp: cuint64;
357begin
358	tmp := val;
359	outv.ul[0] := __lwbrx(tmp,4);
360	outv.ul[1] := __lwbrx(tmp,0);
361
362	result := outv.ull;
363end;
364
365
366// Basic I/O
367function read32(addr: cuint32): cuint32; inline;
368var
369	x: cuint32;
370begin
371  asm
372    lwz r3,0(r4) ;
373    sync
374  end;
375	result := x;
376end;
377
378procedure write32(addr, x: cuint32); inline;
379begin
380  asm
381    stw r3,0(r4) ;
382    eieio
383  end;
384end;
385
386
387procedure mask32(addr, clear, _set: cuint32); inline;
388begin
389	write32(addr, (read32(addr) and (not clear)) or _set);
390end;
391
392function read16(addr: cuint32): cuint16; inline;
393var
394	x: cuint16;
395begin
396	asm
397    lhz r3,0(r4) ;
398    sync
399  end;
400	result := x;
401end;
402
403procedure write16(addr: cuint32; x: cuint16); inline;
404begin
405	asm
406    sth r3,0(r4) ;
407    eieio
408  end;
409end;
410
411function read8(addr: cuint32): cuint8; inline;
412var
413	x: cuint8;
414begin
415  asm
416    lbz r3,0(r4) ;
417    sync
418  end;
419	result := x;
420end;
421
422procedure write8(addr: cuint32; x: cuint8); inline;
423begin
424	asm
425    stb r3,0(r4) ;
426    eieio
427  end;
428end;
429
430procedure writef32(addr: cuint32; x: f32); inline;
431begin
432	asm
433    stfs r3,0(r4) ;
434    eieio
435  end;
436end;
437
438{$ENDIF}
439
440
441
442
443
444
445
446
447
448
449
450