Advertisement
Guest User

IPC FIFO 1.3 Driver (Nintendo DS) by Coto

a guest
Aug 21st, 2017
167
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 23.60 KB | None | 0 0
  1. /*
  2. Copyright (C) 2015-2017  Coto
  3. This program is free software: you can redistribute it and/or modify
  4. it under the terms of the GNU General Public License as published by
  5. the Free Software Foundation, either version 3 of the License, or
  6. (at your option) any later version.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  10. GNU General Public License for more details.
  11. You should have received a copy of the GNU General Public License
  12. along with this program.  If not, see <http://www.gnu.org/licenses/>
  13. */
  14.  
  15. @this is Coto's IPC 1.3 Driver that allows from unidirectional FIFOs to acknowledge messages between processors, relying on physical FIFO interrupts. So the async interrupts prevent overhead between timing critical commands.
  16. @------------------------------------------------------------------------------------------------------
  17.  
  18. /*
  19. Copyright (C) 2015-2017  Coto
  20.  
  21. This program is free software: you can redistribute it and/or modify
  22. it under the terms of the GNU General Public License as published by
  23. the Free Software Foundation, either version 3 of the License, or
  24. (at your option) any later version.
  25.  
  26. This program is distributed in the hope that it will be useful,
  27. but WITHOUT ANY WARRANTY; without even the implied warranty of
  28. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  29. GNU General Public License for more details.
  30.  
  31. You should have received a copy of the GNU General Public License
  32. along with this program.  If not, see <http://www.gnu.org/licenses/>
  33. */
  34.  
  35. //<common_shared.h>
  36. /*
  37. Copyright (C) 2015-2017  Coto
  38.  
  39. This program is free software: you can redistribute it and/or modify
  40. it under the terms of the GNU General Public License as published by
  41. the Free Software Foundation, either version 3 of the License, or
  42. (at your option) any later version.
  43.  
  44. This program is distributed in the hope that it will be useful,
  45. but WITHOUT ANY WARRANTY; without even the implied warranty of
  46. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  47. GNU General Public License for more details.
  48.  
  49. You should have received a copy of the GNU General Public License
  50. along with this program.  If not, see <http://www.gnu.org/licenses/>
  51. */
  52.  
  53. //fifo ipc driver: revision 1.1
  54.  
  55. #ifndef nesds13d_commonipc
  56. #define nesds13d_commonipc
  57.  
  58. #include <nds.h>
  59. #include "wifi_shared.h"
  60.  
  61. #define fifo_requires_ack   (uint32)(0xffff1010)
  62. #define fifo_requires_ack_execok    (uint32)(0xe1e2e3e4)
  63.  
  64. #define fifo_writeuint32_ack    (uint32)(0xffff1011)
  65. //write value (not address) is ret value
  66.  
  67. #define fifo_writeuint16_ack    (uint32)(0xffff1012)
  68. //write value (not address) is ret value
  69.  
  70. #define fifo_writeuint8_ack (uint32)(0xffff1013)
  71. //write value (not address) is ret value
  72.  
  73. #define fifo_readuint32_ack (uint32)(0xffff1014)
  74.  
  75. #define fifo_readuint16_ack (uint32)(0xffff1015)
  76.  
  77. #define fifo_readuint8_ack  (uint32)(0xffff1016)
  78.  
  79. //project specific
  80. #define fifo_apunes_write   (uint32)(0xffff1017)
  81.  
  82.  
  83. #define fifoStub    ((u32)  0xf3f3a0a0)
  84. #define fifotagNotAssigned  ((int)-1)
  85. #define fifoCallbackNotAssigned ((int)-1)
  86. #define fifoAcknowledgedNotAssigned ((bool)false)
  87. #define fifoSentStatusNotAssigned   ((bool)false)
  88. #define fifoDefaultArg0ret  ((u32)0xffffffff)
  89.  
  90. #define fifoSize    ((int)0xf)
  91.  
  92. //ipc 1.3 commands (format: fifotag / message cmd / args 0 / args 1)
  93. #define fifoValidCommand    ((u32)  0xfafa0100)
  94. #define fifoSetCallbackCommand  ((u32)  0xfafa0101)
  95.  
  96. //callback format
  97. //typedef int * cback(int );
  98.  
  99. //ipc 1.3 sender status codes
  100. #define fifoSenderFailed    ((u32)  0xfafa1100)
  101. #define fifoSenderInProgress    ((u32)  0xfafa1101)
  102. #define fifoSenderAcknowledged  ((u32)  0xfafa1102)
  103.  
  104.  
  105. //---------------------------------------------------------------------------------
  106. typedef struct sIPCHandler {
  107. //---------------------------------------------------------------------------------
  108.     int fifotag;                //fifotagNotAssigned or assigned fifotag
  109.     u32 callbackHandler;        //callbackhandler to execute on the other core
  110.     bool sent;          //issued by sendCommand, if false, set true, if true just wait for acknowledge.
  111.     bool acknowledged;  //true yes,sendCommand success! / false no,sendCommand either pending or error
  112.     u32 Arg0ret;        //misc variable, useful for fetching meaningful data
  113. }tIPCHandler;
  114.  
  115.  
  116. //---------------------------------------------------------------------------------
  117. typedef struct sMyIPC {
  118. //---------------------------------------------------------------------------------
  119.    //uint32 heartbeat;          // counts frames
  120.    int16 touchX,   touchY;   // raw x/y
  121.    int16 touchXpx, touchYpx; // TFT x/y pixel
  122.  
  123.    int16 touchZ1,  touchZ2;  // TSC x-panel measurements
  124.    uint16 tdiode1,  tdiode2;  // TSC temperature diodes
  125.    uint32 temperature;        // TSC computed temperature
  126.  
  127.    uint16 buttons;            // keypad buttons
  128.    uint16 buttons_xy_folding;  // X, Y, /PENIRQ buttons
  129.    
  130.    union {
  131.        uint8 curtime[8];        // current time response from RTC
  132.  
  133.        struct {
  134.                u8 rtc_command;
  135.                u8 rtc_year;           //add 2000 to get 4 digit year
  136.                u8 rtc_month;          //1 to 12
  137.                u8 rtc_day;            //1 to (days in month)
  138.  
  139.                u8 rtc_incr;
  140.                u8 rtc_hours;          //0 to 11 for AM, 52 to 63 for PM
  141.                u8 rtc_minutes;        //0 to 59
  142.                u8 rtc_seconds;        //0 to 59
  143.        };
  144.    };
  145.     u8 touched;                 //TSC touched?
  146.    u8 touch_pendown;           //TSC already held before?
  147.    uint16 battery;            
  148.    uint16 aux;                
  149.  
  150.    vuint8 mailBusy;
  151.    
  152.     //IPC Clock
  153.    //[0]; //yy
  154.    //[1]; //mth
  155.    //[2]; //dd
  156.    //[3]; //wat - day of week?
  157.    //[4]; //hh
  158.    //[5]; //mm
  159.    //[6]; //ss
  160.    u8 clockdata[0x20];
  161.    
  162.     //APU Sync
  163.     u8 apu_busy;
  164.    
  165.     //APU setup
  166.     bool apu_ready; //true yes / false no
  167.    
  168.    //WIFI
  169.    bool wifi_enabled;
  170.    bool wifi_working;    //true = yes / false = no
  171.  
  172.    //transfer queue
  173.    u8 status; //see processor ipc read/writes flags
  174.    u32 buf_queue[0x10];
  175.  
  176.     u32 * IPC_ADDR;
  177.    char * ROM;   //pointer to ROM page
  178.    int rom_size;   //rom total size
  179.    
  180.     //dswifi specific
  181.     TdsnwifisrvStr dswifiSrv;
  182.    
  183.     tIPCHandler IPCHandle[fifoSize+1];
  184. } tMyIPC;
  185.  
  186. //Shared Work     027FF000h 4KB    -     -    -    R/W
  187.  
  188. //IPC Struct
  189. #define MyIPC ((tMyIPC volatile *)(0x027FF000))
  190.  
  191. //irqs
  192. #define VCOUNT_LINE_INTERRUPT 0
  193.  
  194. //arm7 specific
  195. #define KEY_XARM7 (1<<0)
  196. #define KEY_YARM7 (1<<1)
  197. #define KEY_HINGE (1<<7)
  198.  
  199. #ifdef ARM7
  200. #define     BIOS_IRQFLAGS   *(__irq_flags)
  201. #endif
  202.  
  203. #define     irq_vector_addr (__irq_vector)
  204.  
  205. //processor ipc read/writes flags
  206. /*
  207. #define ARM7_BUSYFLAGRD (u8)(0x08)
  208. #define ARM7_BUSYFLAGWR (u8)(0x0f)
  209. #define ARM9_BUSYFLAGRD (u8)(0x80)
  210. #define ARM9_BUSYFLAGWR (u8)(0xf0)
  211. */
  212.  
  213. //NESDS special
  214. #define FIFO_APU_PAUSE 0x1201
  215. #define FIFO_UNPAUSE 0x1202
  216. #define FIFO_APU_RESET 0x1204
  217. #define FIFO_SOUND_RESET 0x1206
  218.  
  219. #define FIFO_APU_BUSY 1
  220.  
  221. //FIFO SPECIAL
  222. #define FIFO_NDS_HW_SIZE (16*4)
  223. #define FIFO_SEND_BUFFER    //stream 64 bytes of data to other ARM Core, can be received through GetSoftFIFO 4 bytes a time, until it returns false (empty)
  224. #endif
  225.  
  226. #ifdef __cplusplus
  227. extern "C" {
  228. #endif
  229.  
  230. #ifdef ARM9
  231.  
  232. #endif
  233.  
  234. #ifdef ARM7
  235. #endif
  236.  
  237. //data0 = address
  238. extern uint32 Readuint32WordACK(uint32 data0);
  239. extern uint16 Readuint16WordACK(uint32 data0);
  240. extern uint8 Readuint8WordACK(uint32 data0);
  241.  
  242. //data0 = address / data1 = value
  243. extern bool Writeuint8WordACK(uint32 data0, uint8 data1);
  244. extern bool Writeuint16WordACK(uint32 data0, uint16 data1);
  245. extern bool Writeuint32WordACK(uint32 data0, uint32 data1);
  246.  
  247. extern bool SendMultipleWordACK(uint32 data0, uint32 data1, uint32 data2, uint32 data3);
  248. extern void SendMultipleWordByFifo(uint32 fifotag, uint32 data1, uint32 data2, uint32 data3, uint32 data4);
  249.  
  250. //project specific
  251. #ifdef ARM9
  252. extern bool WriteAPUNESACK(uint32 data0, uint32 data1);
  253. #endif
  254.  
  255. /*
  256. extern void sendbyte_ipc(uint8 word);
  257. extern u8 recvbyte_ipc();
  258. extern u32 read_ext_cpu(u32 address,u8 read_mode);
  259. extern void write_ext_cpu(u32 address,u32 value,u8 write_mode);
  260. */
  261.  
  262. //gbaemu4ds clock opcodes
  263. extern u8 gba_get_yearbytertc();
  264. extern u8 gba_get_monthrtc();
  265. extern u8 gba_get_dayrtc();
  266. extern u8 gba_get_dayofweekrtc();
  267. extern u8 gba_get_hourrtc();
  268. extern u8 gba_get_minrtc();
  269. extern u8 gba_get_secrtc();
  270.  
  271. //FIFO
  272. extern void FIFO_DRAINWRITE();
  273.  
  274.  
  275. extern void HandleFifoNotEmpty();
  276. extern void HandleFifoEmpty();
  277.  
  278.  
  279. //
  280. extern void apusetup();
  281.  
  282. //ipc 1.3
  283. extern bool getAcknowledgedFifoStatus(int fifotag);
  284. extern void ExecuteAndAckFifoCallback(int fifotag); //handle must
  285. extern int AllocNewFifo();
  286. extern int FreeFifo(int fifotag);
  287. extern bool SetFifoCallback(uint32 fifotag, uint32 handle);
  288. extern u32 SendCommand(uint32 fifotag, uint32 fifocmd, uint32 arg0, uint32 arg1, uint32 arg2);
  289. extern bool ReleaseAcknowledgedFifoCallback(int fifotag);   //only useful when SendCommand was successfully executed on external core
  290.  
  291. #ifdef __cplusplus
  292. }
  293. #endif
  294.  
  295.  
  296. //<common_shared.c>
  297.  
  298. //fifo ipc driver: revision 1.3
  299.  
  300. #include <nds.h>
  301. #include "common_shared.h"
  302.  
  303. #ifdef ARM7
  304.  
  305. #include <string.h>
  306.  
  307. #include "wifi_arm7.h"
  308. #include "arm7.h"
  309. #include "audiosys.h"
  310. #include "handler.h"
  311. #include "c_defs.h"
  312. #include "ds_misc.h"
  313.  
  314. #endif
  315.  
  316. #ifdef ARM9
  317.  
  318. #include "c_defs.h"
  319. #include "ds_misc.h"
  320.  
  321. #endif
  322.  
  323. // Ensures a SendArm[7/9]Command (FIFO message) command to be forcefully executed at target ARM Core, while the host ARM Core awaits.
  324. #ifdef ARM9
  325. __attribute__((section(".itcm")))
  326. #endif
  327. inline void FIFO_DRAINWRITE(){
  328.     while (!(REG_IPC_FIFO_CR & IPC_FIFO_SEND_EMPTY)){}
  329. }
  330.  
  331. #ifdef ARM9
  332. __attribute__((section(".itcm")))
  333. #endif
  334. inline bool SendMultipleWordACK(uint32 data0, uint32 data1, uint32 data2, uint32 data3){
  335.    
  336.     //uint32 reply = SendMultipleWordByFifo(fifo_requires_ack, data0, data1, data2, data3);
  337.     //if(reply == fifo_requires_ack_execok){
  338.     //  return true;
  339.     //}
  340.     return false;
  341. }
  342.  
  343. #ifdef ARM9
  344. __attribute__((section(".itcm")))
  345. #endif
  346. inline uint8 Readuint8WordACK(uint32 data0){            //data0 address -> return code: uint8 value from address
  347.    
  348.     //invalidate cache here (arm9)
  349.     #ifdef ARM9
  350.     //Prevent Cache problems.
  351.     DC_FlushRange((u32*)data0, (int)4);
  352.     #endif
  353.    
  354.     //return (uint8)SendMultipleWordByFifo((uint32)fifo_readuint8_ack, (uint32)data0, (uint32)0, (uint32)0, (uint32)0);
  355.     return 0;
  356. }
  357.  
  358. #ifdef ARM9
  359. __attribute__((section(".itcm")))
  360. #endif
  361. inline uint16 Readuint16WordACK(uint32 data0){          //data0 address -> return code: uint8 value from address
  362.    
  363.     //invalidate cache here (arm9)
  364.     #ifdef ARM9
  365.     //Prevent Cache problems.
  366.     DC_FlushRange((u32*)data0, (int)4);
  367.     #endif
  368.    
  369.     //return (uint16)SendMultipleWordByFifo((uint32)fifo_readuint16_ack, (uint32)data0, (uint32)0, (uint32)0, (uint32)0);
  370.     return 0;
  371. }
  372.  
  373. #ifdef ARM9
  374. __attribute__((section(".itcm")))
  375. #endif
  376. inline uint32 Readuint32WordACK(uint32 data0){          //data0 address -> return code: uint8 value from address
  377.    
  378.     //invalidate cache here (arm9)
  379.     #ifdef ARM9
  380.     //Prevent Cache problems.
  381.     DC_FlushRange((u32*)data0, (int)4);
  382.     #endif
  383.    
  384.     //return (uint32)SendMultipleWordByFifo((uint32)fifo_readuint32_ack, (uint32)data0, (uint32)0, (uint32)0, (uint32)0);
  385.     return 0;
  386. }
  387.  
  388. #ifdef ARM9
  389. __attribute__((section(".itcm")))
  390. #endif
  391. inline bool Writeuint8WordACK(uint32 data0, uint8 data1){           //data0 address / data1 value *uint32)
  392.    
  393.     //invalidate cache here (arm9)
  394.     #ifdef ARM9
  395.     //Prevent Cache problems.
  396.     DC_FlushRange((u32*)data0, (int)4);
  397.     #endif
  398.    
  399.     //uint32 reply = SendMultipleWordByFifo((uint32)fifo_writeuint8_ack, (uint32)data0, (uint32)data1, (uint32)0, (uint32)0);
  400.     //if(reply == data1){
  401.     //  return true;
  402.     //}
  403.     return false;
  404. }
  405.  
  406. #ifdef ARM9
  407. __attribute__((section(".itcm")))
  408. #endif
  409. inline bool Writeuint16WordACK(uint32 data0, uint16 data1){         //data0 address / data1 value *uint32)
  410.    
  411.     //invalidate cache here (arm9)
  412.     #ifdef ARM9
  413.     //Prevent Cache problems.
  414.     //DC_FlushRange((u32*)data0, (int)4);
  415.     #endif
  416.    
  417.     //uint32 reply = SendMultipleWordByFifo((uint32)fifo_writeuint16_ack, (uint32)data0, (uint32)data1, (uint32)0, (uint32)0);
  418.     //if(reply == data1){
  419.     //  return true;
  420.     //}
  421.     return false;
  422. }
  423.  
  424. #ifdef ARM9
  425. __attribute__((section(".itcm")))
  426. #endif
  427. inline bool Writeuint32WordACK(uint32 data0, uint32 data1){         //data0 address / data1 value *uint32)
  428.    
  429.     //invalidate cache here (arm9)
  430.     #ifdef ARM9
  431.     //Prevent Cache problems.
  432.     //DC_FlushRange((uint32*)data0, (int)4);
  433.     #endif
  434.    
  435.     //uint32 reply = SendMultipleWordByFifo((uint32)fifo_writeuint32_ack, (uint32)data0, (uint32)data1, (uint32)0, (uint32)0);
  436.     //if(reply == data1){
  437.     //  return true;
  438.     //}
  439.     return false;
  440. }
  441.  
  442.  
  443.  
  444. //Internal, not for usercode
  445.  
  446. #ifdef ARM9
  447. __attribute__((section(".itcm")))
  448. #endif
  449. inline bool getAcknowledgedFifoStatus(int fifotag)
  450. {
  451.     bool retstatus = false;
  452.     if( fifotag >= ((int)fifoSize+1)){
  453.         return retstatus;
  454.     }
  455.    
  456.     //ok fount it
  457.     if(MyIPC->IPCHandle[fifotag].fifotag == fifotag){
  458.         retstatus = MyIPC->IPCHandle[fifotag].acknowledged;
  459.     }
  460.    
  461.     return retstatus;
  462. }
  463.  
  464. //up to this point callback is not required anymore lol
  465. #ifdef ARM9
  466. __attribute__((section(".itcm")))
  467. #endif
  468. inline void ExecuteAndAckFifoCallback(int fifotag)  //channel
  469. {
  470.     if( fifotag >= ((int)fifoSize+1)){
  471.         return;
  472.     }
  473.    
  474.     //ok fount it
  475.     if(MyIPC->IPCHandle[fifotag].fifotag == fifotag){
  476.         MyIPC->IPCHandle[fifotag].acknowledged = true;
  477.     }
  478.     //else something went wrong
  479.     return;
  480. }
  481.  
  482. //for glue logic -> sendCommand, check if success ack, do external logic, then use this for release an already acknowledged sent message.
  483. #ifdef ARM9
  484. __attribute__((section(".itcm")))
  485. #endif
  486. inline bool ReleaseAcknowledgedFifoCallback(int fifotag){
  487.    
  488.     bool retstatus = false;
  489.     if( fifotag >= ((int)fifoSize+1)){
  490.         return retstatus;
  491.     }
  492.    
  493.     if(MyIPC->IPCHandle[fifotag].fifotag == fifotag){
  494.         if(MyIPC->IPCHandle[fifotag].acknowledged == true){
  495.             //acknowledge should reset acknowledge and sent to false, if send command is going to be forever called
  496.             MyIPC->IPCHandle[fifotag].sent = (bool)fifoSentStatusNotAssigned;
  497.             MyIPC->IPCHandle[fifotag].acknowledged = (bool)fifoAcknowledgedNotAssigned;
  498.             MyIPC->IPCHandle[fifotag].Arg0ret = (u32)fifoDefaultArg0ret;
  499.             retstatus = true;
  500.         }
  501.     }
  502.     return retstatus;
  503. }
  504.  
  505. //returns new fifotag or fifotagNotAssigned if failed (full)
  506. #ifdef ARM9
  507. __attribute__((section(".itcm")))
  508. #endif
  509. inline int AllocNewFifo()
  510. {
  511.     int i = 0;
  512.     for(i = 0; i < ((int)fifoSize+1); i++){
  513.         if(MyIPC->IPCHandle[i].fifotag == fifotagNotAssigned){
  514.             MyIPC->IPCHandle[i].fifotag = i;
  515.             break;
  516.         }
  517.     }
  518.    
  519.     if(i == ((int)fifoSize+1)){
  520.         i = fifotagNotAssigned;
  521.     }
  522.    
  523.     return i;
  524. }
  525.  
  526.  
  527. #ifdef ARM9
  528. __attribute__((section(".itcm")))
  529. #endif
  530. inline int FreeFifo(int fifotag)    //if freed returns old fifotag
  531. {
  532.     int i = 0;
  533.     for(i = 0; i < ((int)fifoSize+1); i++){
  534.         if(MyIPC->IPCHandle[i].fifotag == fifotag){
  535.             MyIPC->IPCHandle[i].fifotag = fifotagNotAssigned;
  536.             MyIPC->IPCHandle[i].callbackHandler = fifoCallbackNotAssigned;
  537.             MyIPC->IPCHandle[i].acknowledged = fifoAcknowledgedNotAssigned;
  538.             break;
  539.         }
  540.     }
  541.    
  542.     if(i == ((int)fifoSize+1)){
  543.         i = -1;
  544.     }
  545.    
  546.     return i;
  547. }
  548.  
  549.  
  550. //SetFifoCallback(uint32 fifotag, (u32)&AckFifoCallback); (from sender core)
  551. //returns true if callback was set, or false if something went wrong
  552. #ifdef ARM9
  553. __attribute__((section(".itcm")))
  554. #endif
  555. inline bool SetFifoCallback(uint32 fifotag, uint32 handle)  //channel / handler //rets fifotag if alloced or -1 if full
  556. {
  557.     bool retstatus = false;
  558.     if(fifotag >= ((int)fifoSize+1)){
  559.         return retstatus;
  560.     }
  561.    
  562.     //invalidate cache here (arm9)
  563.     #ifdef ARM9
  564.     //Prevent Cache problems.
  565.     DC_FlushRange((uint32*)&MyIPC->IPCHandle[fifotag], sizeof(MyIPC->IPCHandle[fifotag]));
  566.     #endif
  567.        
  568.     //MyIPC->IPCHandle[i].callbackHandler = (u32)handle;    //set handle in the other core
  569.     //send fifocallback message here
  570.     SendMultipleWordByFifo((uint32)fifotag, (uint32)fifoSetCallbackCommand,(u32)handle,(u32)0,(u32)0);  //stuck here
  571.    
  572.     while(MyIPC->IPCHandle[fifotag].fifotag != fifotag){}   //wait for assignment
  573.     retstatus = true;  
  574.    
  575.     return retstatus;
  576. }
  577.  
  578. //read ipc 1.3 sender status codes for feedback
  579. #ifdef ARM9
  580. __attribute__((section(".itcm")))
  581. #endif
  582. inline u32 SendCommand(uint32 fifotag, uint32 fifocmd, uint32 arg0, uint32 arg1, uint32 arg2)   //channel / message cmd
  583. {
  584.     u32 retstatus = 0;
  585.     if((int)fifotag > (int)fifoSize){
  586.         retstatus = (u32)(fifoSenderFailed);
  587.     }
  588.    
  589.     else if(MyIPC->IPCHandle[fifotag].fifotag == fifotagNotAssigned){
  590.         if(SetFifoCallback(fifotag, 0) == true){
  591.             SendCommand(fifotag, fifocmd, arg0, arg1, arg2);    //retry SendCommand since we got the fifotag
  592.         }
  593.         else{
  594.             retstatus = (u32)fifotagNotAssigned;    //oh no we couldnt get the fifotag
  595.         }
  596.     }
  597.     else{
  598.         if(MyIPC->IPCHandle[fifotag].sent == false){
  599.             SendMultipleWordByFifo(fifotag, fifocmd, arg0, arg1, arg2);
  600.             MyIPC->IPCHandle[fifotag].sent = true;
  601.             retstatus = (u32)fifoSenderInProgress;  //Sender In Progress
  602.         }
  603.         else{
  604.             if(getAcknowledgedFifoStatus(fifotag) == true){ //acknowledge from ext core should toggle to true
  605.                 retstatus = (u32)fifoSenderAcknowledged;    //OK
  606.             }
  607.             else{
  608.                 retstatus = (u32)fifoSenderInProgress;
  609.             }
  610.         }
  611.     }
  612.     return retstatus;
  613. }
  614.  
  615. #ifdef ARM9
  616. __attribute__((section(".itcm")))
  617. #endif
  618. inline void SendMultipleWordByFifo(uint32 fifotag, uint32 data1, uint32 data2, uint32 data3, uint32 data4)  //channel / message cmd
  619. {
  620.     FIFO_DRAINWRITE();  //should be cleared here from the other core
  621.    
  622.    
  623.     REG_IPC_FIFO_TX =   (u32)fifotag;   //raise irq here (fifo channel index)
  624.     REG_IPC_FIFO_TX =   (u32)data1;
  625.     REG_IPC_FIFO_TX =   (u32)data2;
  626.     REG_IPC_FIFO_TX =   (u32)data3;
  627.     REG_IPC_FIFO_TX =   (u32)data4;
  628.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  629.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  630.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  631.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  632.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  633.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  634.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  635.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  636.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  637.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  638.     REG_IPC_FIFO_TX =   (u32)fifoStub;
  639.    
  640.     REG_IPC_FIFO_CR |= IPC_FIFO_ERROR;
  641.    
  642.     while (REG_IPC_FIFO_CR & IPC_FIFO_ERROR){} //ack will be set (unset here) from the other core
  643.    
  644.    
  645. }
  646.  
  647. //project specific
  648.  
  649. //extern void APUSoundWrite(Uint address, Uint value);
  650. #ifdef ARM9 //arm9 only
  651. __attribute__((section(".itcm")))
  652. inline bool WriteAPUNESACK(uint32 data0, uint32 data1){        
  653.    
  654.     //invalidate cache here (arm9)
  655.     //Prevent Cache problems.
  656.     //DC_FlushRange((uint32*)data0, (int)4);
  657.    
  658.     //uint32 reply = SendMultipleWordByFifo((uint32)fifo_apunes_write, (uint32)data0, (uint32)data1, (uint32)0, (uint32)0);
  659.     //if(reply == data1){
  660.     //  return true;
  661.     //}
  662.     return false;
  663. }
  664. #endif
  665.  
  666.  
  667.  
  668. //FIFO HANDLER INIT
  669. #ifdef ARM9
  670. __attribute__((section(".itcm")))
  671. #endif
  672. inline void HandleFifoEmpty(){
  673.    
  674. }
  675.  
  676. //FIFO HANDLER INIT
  677. #ifdef ARM9
  678. __attribute__((section(".itcm")))
  679. #endif
  680. inline void HandleFifoNotEmpty(){
  681.     volatile uint32 fifotag = 0,cmd2 = 0,cmd3 = 0,cmd4 = 0;
  682.    
  683.     if(!(REG_IPC_FIFO_CR & IPC_FIFO_RECV_EMPTY)){
  684.         fifotag = REG_IPC_FIFO_RX;
  685.     }
  686.    
  687.     if(!(REG_IPC_FIFO_CR & IPC_FIFO_RECV_EMPTY)){
  688.         cmd2 = REG_IPC_FIFO_RX;
  689.     }
  690.    
  691.     if(!(REG_IPC_FIFO_CR & IPC_FIFO_RECV_EMPTY)){
  692.         cmd3 = REG_IPC_FIFO_RX;
  693.     }
  694.    
  695.     if(!(REG_IPC_FIFO_CR & IPC_FIFO_RECV_EMPTY)){
  696.         cmd4 = REG_IPC_FIFO_RX;
  697.     }
  698.  
  699.     //MyIPC->IPCHandle[i].callbackHandler = (u32)handle;    //set handle in the other core
  700.     //SendMultipleWordByFifo((uint32)i, (uint32)fifoSetCallbackCommand,(u32)handle,(u32)0);
  701.    
  702.    
  703.    
  704.     if(cmd2 == fifoSetCallbackCommand){
  705.         MyIPC->IPCHandle[fifotag].callbackHandler = (u32)cmd3;  //assign callback handler
  706.         MyIPC->IPCHandle[fifotag].fifotag = fifotag;    //assign fifo tag
  707.     }
  708.    
  709.  
  710.     /* //todo: rewrite
  711.     if(cmd1 == fifo_requires_ack){
  712.         switch (cmd2) {
  713.             //ARM7 command handler
  714.             #ifdef ARM7
  715.             case FIFO_APU_PAUSE:
  716.                 APU_paused=1;
  717.                 memset((u32*)buffer,0,sizeof(buffer));
  718.             break;
  719.             case FIFO_UNPAUSE:
  720.                 APU_paused=0;
  721.                 break;
  722.             case FIFO_APU_RESET:
  723.                 memset((u32*)buffer,0,sizeof(buffer));
  724.                 APU_paused=0;
  725.                 resetAPU();
  726.             break;
  727.             case FIFO_SOUND_RESET:
  728.                 lidinterrupt();
  729.             break;
  730.        
  731.             //arm9 wants to WifiSync
  732.             case(WIFI_SYNC):{
  733.                 Wifi_Sync();
  734.             }
  735.             break;
  736.            
  737.            
  738.            
  739.             //arm9 wants to send a WIFI context block address / userdata is always zero here
  740.             case(0xc1710101):{
  741.                 //  wifiAddressHandler( void * address, void * userdata )
  742.                 wifiAddressHandler((Wifi_MainStruct *)(u32)cmd3, 0);
  743.             }
  744.             break;
  745.             #endif
  746.            
  747.             //ARM9 command handler
  748.             #ifdef ARM9
  749.             //arm7 wants to WifiSync
  750.             case(WIFI_SYNC):{
  751.                 Wifi_Sync();
  752.             }
  753.             break;
  754.             #endif
  755.         }
  756.         //execute callback here by index
  757.     }
  758.    
  759.     else if(cmd1 == fifo_writeuint8_ack){
  760.        
  761.         //invalidate cache here (arm9)
  762.         #ifdef ARM9
  763.         //Prevent Cache problems.
  764.         DC_FlushRange((u32*)cmd2, (int)4);
  765.         #endif
  766.        
  767.         //data0 address / data1 value *uint32)
  768.         *(uint8*)cmd2 = (uint8)cmd3;
  769.        
  770.         //MyIPC->fiforeply = (uint32)*(uint8*)cmd2; //works with cmd2 passed directly
  771.         //execute callback here by index
  772.     }
  773.    
  774.     else if(cmd1 == fifo_writeuint16_ack){
  775.        
  776.         //invalidate cache here (arm9)
  777.         #ifdef ARM9
  778.         //Prevent Cache problems.
  779.         DC_FlushRange((u32*)cmd2, (int)4);
  780.         #endif
  781.        
  782.         //data0 address / data1 value *uint32)
  783.         *(uint16*)cmd2 = (uint16)cmd3;
  784.        
  785.         //MyIPC->fiforeply = (uint32)*(uint16*)cmd2;    //works with cmd2 passed directly
  786.         //execute callback here by index
  787.     }
  788.    
  789.     else if(cmd1 == fifo_writeuint32_ack){
  790.        
  791.         //invalidate cache here (arm9)
  792.         #ifdef ARM9
  793.         //Prevent Cache problems.
  794.         DC_FlushRange((u32*)cmd2, (int)4);
  795.         #endif
  796.        
  797.         //data0 address / data1 value *uint32)
  798.         *(uint32*)cmd2 = (uint32)cmd3;
  799.        
  800.         //MyIPC->fiforeply = *(uint32*)cmd2;    //works with cmd2 passed directly
  801.         //execute callback here by index
  802.     }
  803.    
  804.     else if(cmd1 == fifo_readuint8_ack){
  805.         //invalidate cache here (arm9)
  806.         #ifdef ARM9
  807.         //Prevent Cache problems.
  808.         DC_FlushRange((u32*)cmd2, (int)4);
  809.         #endif
  810.        
  811.         //MyIPC->fiforeply = *(uint8*)cmd2; //works with cmd2 passed directly
  812.         //execute callback here by index
  813.     }
  814.    
  815.     else if(cmd1 == fifo_readuint16_ack){
  816.         //invalidate cache here (arm9)
  817.         #ifdef ARM9
  818.         //Prevent Cache problems.
  819.         DC_FlushRange((u32*)cmd2, (int)4);
  820.         #endif
  821.        
  822.         //MyIPC->fiforeply = *(uint16*)cmd2;    //works with cmd2 passed directly
  823.         //execute callback here by index
  824.     }
  825.    
  826.     else if(cmd1 == fifo_readuint32_ack){
  827.         //invalidate cache here (arm9)
  828.         #ifdef ARM9
  829.         //Prevent Cache problems.
  830.         DC_FlushRange((u32*)cmd2, (int)4);
  831.         #endif
  832.        
  833.         //MyIPC->fiforeply = *(uint32*)cmd2;    //works with cmd2 passed directly
  834.         //execute callback here by index
  835.     }
  836.    
  837.     //project specific
  838.     #ifdef ARM7
  839.     //APUSoundWrite(Uint address, Uint value);
  840.     else if(cmd1 == fifo_apunes_write){
  841.         APUSoundWrite(cmd2, cmd3);
  842.         //execute callback here by index
  843.     }
  844.     #endif
  845.     */
  846.    
  847.     //execute commands (above)
  848.    
  849.     //and execute callback/acknowledge
  850.     ExecuteAndAckFifoCallback((int)fifotag);
  851.    
  852.     //ok, flush fifo & ack
  853.     REG_IPC_FIFO_CR |= (IPC_FIFO_ERROR | IPC_FIFO_SEND_CLEAR);
  854. }
  855.  
  856.  
  857. //FIFO HANDLER END
  858.  
  859.  
  860.  
  861.  
  862.  
  863. #ifdef ARM9
  864. void apusetup(){
  865.     MyIPC->IPC_ADDR = (u32*)ipc_region;
  866.     MyIPC->apu_ready = true;
  867. }
  868. #endif
  869.  
  870.  
  871.  
  872. //coto: humble ipc clock opcodes
  873. u8 gba_get_yearbytertc(){
  874.     return (u8)(u32)MyIPC->clockdata[0];
  875. }
  876.  
  877. u8 gba_get_monthrtc(){
  878.     return (u8)(u32)MyIPC->clockdata[1];
  879. }
  880.  
  881. u8 gba_get_dayrtc(){
  882.     return (u8)(u32)MyIPC->clockdata[2];
  883. }
  884.  
  885. u8 gba_get_dayofweekrtc(){
  886.     return (u8)(u32)MyIPC->clockdata[3];
  887. }
  888.  
  889.  
  890. u8 gba_get_hourrtc(){
  891.     return (u8)(u32)MyIPC->clockdata[4];
  892. }
  893.  
  894. u8 gba_get_minrtc(){
  895.     return (u8)(u32)MyIPC->clockdata[5];
  896. }
  897.  
  898. u8 gba_get_secrtc(){
  899.     return (u8)(u32)MyIPC->clockdata[6];
  900. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement