QuakeGod
2023-10-08 483170e190a0dd4666b2a63e5d31466052ba0c6a
提交 | 用户 | age
483170 1 /**
Q 2   ******************************************************************************
3   * @file           : KMachine.c
4   * @brief          : KMachine program body
5   ******************************************************************************
6     */
7
8 #include "KMachine.h"
9 #include "string.h"
10 #include "Globaldef.h"
11 #include "stm32f0xx_hal.h"
12
13 //#define OB_BASE               ((uint32_t)0x1FFFF800U)       /*!< FLASH Option Bytes base address */
14 //#define FLASHSIZE_BASE        ((uint32_t)0x1FFFF7CCU)       /*!< FLASH Size register base address */
15 //#define UID_BASE              ((uint32_t)0x1FFFF7ACU)       /*!< Unique device ID register base address */
16
17
18 stStoredKMSysCfg storedKMSysCfg ;
19 stKMem KMem;
20 stRunStat KMRunStat;
21
22 //uint8_t * pFlash1 = (uint8_t *)(STORECFGBASE);
23
24 //void * pConfigFlashBase = (uint8_t *)(STORECFGBASE);
25
26 //uint16_t FlashDatas[16];
27
28 //uint32_t * pUID = (uint32_t *)(UID_BASE);
29 const stKMInfoBlock KMInfoBlock =
30 {
31 //    sizeof(stKMInfoBlock),
32     (BOARD_TYPE<<8) + BOARD_VER,            //nDeviceType     BOARD_VER,            //nDevieVer
33     0x0104,            //ProgVer
34     0x0100,            //KLinkVer
35     0x0100,            //KBusVer
36 //    0x0100,            //KNetVer
37 //    0x0100,            //KWLVer
38     
39     4,                    //nCapacity1    ?K
40     1,                    //nCapacity2    ?k
41     
42     DINPUT,                    //nDInput;
43     DOUTPUT,                //nDOutput
44     
45     0,                    //nAInput
46     0,                    //nAOutput
47     0,                    //nHInput
48     0,                    //nHOutput
49     0,                    //nExt1;
50     0,                    //nExt2;
51     0,                    //nLogSize;
52     0,                    //nPorts;
53     0,                    //nManSize;
54     0,                    //nAbility;
55     6,                    //nSwitchBits;
56 };
57 const char VersionStr[] __attribute__((at(FLASH_BASE + 0X1000))) //__attribute__((at(0X8001000)))
58     = "3.00";
59
60 const stStoredKMSysCfg KMDefaultSysCfg /*__attribute__((at(STORECFGBASE)))*/ =
61 {
62     START_SIGN,
63     0x0000,
64     {
65         CFG_VER,
66         0x0000,                //workmode
67         0x0000,                //switchfunc
68         0x0000,                //pad1;
69         {                //comportparam[2]
70             {
71                 PortType_KLink,    //PorttType
72                 1,                            //Station
73                 2304,                        //Buadrate = * 100;
74                 0,                            //ByteSize
75                 0,                            //Parity
76                 0,                            //StopBits
77                 0,                            //endType
78                 0,                            //EofChar
79                 0,                            //SofChar
80                 0,                            //endtime
81                 0,                            //recvbuf
82                 0,                            //bufsize
83             },
84             {
85                 PortType_KBus,    //PorttType
86                 0,                            //Station
87                 2304,                        //Buadrate = * 100;
88                 0,                            //ByteSize
89                 0,                            //Parity
90                 0,                            //StopBits
91                 0,                            //endType
92                 0,                            //EofChar
93                 0,                            //SofChar
94                 0,                            //endtime
95                 0,                            //recvbuf
96                 0,                            //bufsize
97             }
98         },
99         {{0},{0},{0},{0},{0},{0},{0},{0},{0},{0},{0},{0},{0},{0},{0},{0}},    //inputfilterparam
100         {{0,1},{0,1},{0,1},{0,1},{0,1},{0,1},{0,1},{0,1},{0,1},{0,1},{0,1},{0,1},{0,1},{0,1},{0,1},{0,1}},    //outputholdparam
101         {        //default port mapping
102                 0x0010,
103                 0x0020,
104                 0x0030,
105                 0x0040,
106                 0x0050,
107                 0x0060
108         },
109         0x0003,            //padding s 
110         0x0004,
111         0x0005,
112         0x0006,
113         0x0007,
114         0x0008,
115         0x0009,
116         0x000a,
117         0x000b,
118         0x000c,
119     },
120     0x0011,                //CRC16
121     END_SIGN,
122 };
123
124 //const stKMSysCfg KMDefaultSysCfg2[7] /*__attribute__((at(STORECFGBASE+sizeof(stKMSysCfg))))*/;
125     
126 int ReadFlashMem(void * pBuf, void * pAddrFlash, int nByteSize)
127 {
128 //    memcpy(pBuf,pAddrFlash,nSize);
129     for (int i=0;i<nByteSize/4;i++)
130     {
131         ((uint32_t *)pBuf)[i] = ((uint32_t *)pAddrFlash)[i];
132     }
133     for (int i=nByteSize/4*2;i<nByteSize/2;i++)
134     {
135         ((uint16_t *)pBuf)[i] = ((uint16_t *)pAddrFlash)[i];
136     }
137     return nByteSize;
138 }
139 int EraseFlashMem(void * pAddrFlash, unsigned int Pages)
140 {
141     HAL_StatusTypeDef res;
142     res = HAL_FLASH_Unlock();
143     uint32_t ErrNo;    
144     FLASH_EraseInitTypeDef erase1;
145     erase1.NbPages=Pages;
146     erase1.PageAddress=(unsigned int)pAddrFlash;
147     erase1.TypeErase=FLASH_TYPEERASE_PAGES;
148     res = HAL_FLASHEx_Erase(&erase1,&ErrNo);
149     res = HAL_FLASH_Lock();
150     return res;
151 }
152 int WriteToFlashMemNoErase(void * pBuf, void * pAddrFlash, unsigned int nByteSize)
153 {
154         HAL_StatusTypeDef res;
155     res = HAL_FLASH_Unlock();
156 /*    
157     for (int i=0;i<nSize/2;i++)
158     {
159         res = HAL_FLASH_Program(FLASH_TYPEPROGRAM_HALFWORD, (uint32_t)pAddrFlash + i*2, ((uint16_t *)pBuf)[i]);
160     }
161 */    
162 ///*    
163     for (int i=0;i<nByteSize/4;i++)
164     {
165         res = HAL_FLASH_Program(FLASH_TYPEPROGRAM_WORD, (uint32_t)pAddrFlash + i*4, ((uint32_t *)pBuf)[i]);
166     }
167     
168     for (int i = nByteSize/4 * 2 ; i < nByteSize/2 ; i++)
169     {
170         res = HAL_FLASH_Program(FLASH_TYPEPROGRAM_HALFWORD, (uint32_t)pAddrFlash + i*2, ((uint16_t *)pBuf)[i]);
171     }
172 //*/    
173     res = HAL_FLASH_Lock();
174     
175     return res;
176 }
177 int EraseAndWriteToFlashMem(void * pBuf, void * pAddrFlash, unsigned int nByteSize)
178 {
179     
180     HAL_StatusTypeDef res;
181     res = HAL_FLASH_Unlock();
182     uint32_t ErrNo;    
183     FLASH_EraseInitTypeDef erase1;
184     erase1.NbPages=1;
185     erase1.PageAddress=(unsigned int)pAddrFlash;
186     erase1.TypeErase=FLASH_TYPEERASE_PAGES;
187     res = HAL_FLASHEx_Erase(&erase1,&ErrNo);
188     
189     for (int i=0;i<nByteSize/2;i++)
190     {
191         res = HAL_FLASH_Program(FLASH_TYPEPROGRAM_HALFWORD, (uint32_t)pAddrFlash + i*2, ((uint16_t *)pBuf)[i]);
192     }
193 /*    
194     for (int i=0;i<nSize/4;i++)
195     {
196         res = HAL_FLASH_Program(FLASH_TYPEPROGRAM_WORD, (uint32_t)pAddrFlash + i*4, ((uint32_t *)pBuf)[i]);
197     }
198     
199     for (int i = nSize/4 * 2 ; i < nSize/2 ; i++)
200     {
201         res = HAL_FLASH_Program(FLASH_TYPEPROGRAM_HALFWORD, (uint32_t)pAddrFlash + i*2, ((uint16_t *)pBuf)[i]);
202     }
203 */    
204     res = HAL_FLASH_Lock();
205     
206     return res;
207 }
208
209 int ReadFactoryData(void * pDatabuf, int nByteCount)
210 {
211     memcpy(pDatabuf,(stFactoryData *)FACTORY_DATA_BASE,nByteCount);
212     return 0;
213 }
214 int WriteFactoryData(void * pDataBuf, int nByteCount)
215 {
216     stFactoryData * p1 = (stFactoryData*) pDataBuf;
217     stFactoryData * p2 = (stFactoryData *)FACTORY_DATA_BASE;
218     p1->Seq1= p2->Seq1+1;
219     
220     EraseAndWriteToFlashMem(pDataBuf, (stFactoryData *)FACTORY_DATA_BASE,nByteCount);
221     return 0;
222 }
223
224 int ReadProgram(int nProgByteAddr, void *pBuf, int nByteSize, int nBank)
225 {
226     if (nBank==0)    {
227         ReadFlashMem(pBuf, (void *)(STORE_PRG_BASE+nProgByteAddr), nByteSize);
228     }else if (nBank ==1) {
229         ReadFlashMem(pBuf, (void *)(ALT_PRG_BASE+nProgByteAddr), nByteSize);
230     }else if (KMRunStat.nBinProgBank==0) {
231         ReadFlashMem(pBuf, (void *)(STORE_PRG_BASE+nProgByteAddr), nByteSize);
232     } else {
233         ReadFlashMem(pBuf, (void *)(ALT_PRG_BASE+nProgByteAddr), nByteSize);
234     }        
235     return 0;
236 }
237 int WriteProgram(int nProgAddress, void * pBuf, int nByteSize, int nBank)
238 {
239             // Program Save Address;//
240           // Program 2 Save Address; //
241     void * progByteAddr;
242     if (nBank == 0) {
243         progByteAddr=(void *)(STORE_PRG_BASE+nProgAddress);
244     }else if (nBank==1) {
245         progByteAddr=(void *)(ALT_PRG_BASE+nProgAddress);
246     } else if (KMRunStat.nBinProgBank==0) {
247         progByteAddr=(void *)(ALT_PRG_BASE+nProgAddress);
248     }else{
249         progByteAddr=(void *)(STORE_PRG_BASE+nProgAddress);
250     }
251     if ( (nProgAddress & (STORE_PRG_PAGESIZE - 1)) ==0)    {
252         EraseAndWriteToFlashMem(pBuf, progByteAddr, nByteSize);
253     }else{
254         WriteToFlashMemNoErase(pBuf, progByteAddr, nByteSize);
255     }
256     return 0;
257 }
258
259 int LoadDefaultSysCfg(pStoredKMSysCfg theStoredKMSysCfg)
260 {
261     memcpy(theStoredKMSysCfg,&KMDefaultSysCfg,sizeof(stStoredKMSysCfg));
262     return 0;
263 }
264 int ReadSysCfgFromFlash(pStoredKMSysCfg theStoredKMSysCfg)
265 {
266     pStoredKMSysCfg pSKMSysCfg = (pStoredKMSysCfg)(STORE_SYSREG_BASE);
267     // find latest Store Cfg
268     int s2=128;
269     int nIndex=-1;
270     int nMaxSeq=0;
271     for (int i=0;i<8;i++)
272     {
273             pSKMSysCfg = (pStoredKMSysCfg)(STORE_SYSREG_BASE + s2*i);
274         if (pSKMSysCfg->Sign1 == START_SIGN && pSKMSysCfg->EndSign1 == END_SIGN)
275         {
276             if (pSKMSysCfg->Seq1 > nMaxSeq) 
277             {
278                 nIndex=i;nMaxSeq=pSKMSysCfg->Seq1;
279             }
280         }
281     }
282     if (nIndex>=0 && nIndex <8)
283     {
284             ReadFlashMem(theStoredKMSysCfg,(void *)(STORE_SYSREG_BASE + nIndex * s2),sizeof(stStoredKMSysCfg));
285     //ReadFlashMem(theStoredKMSysCfg,(void *)(STORE_SYSREG_BASE ),sizeof(stStoredKMSysCfg));
286         //memcpy(theStoredKMSysCfg,(void *)(STORE_SYSREG_BASE ),sizeof(stStoredKMSysCfg));
287     }else {
288         LoadDefaultSysCfg(theStoredKMSysCfg);
289     }
290     //memcpy(theKMSysCfg,(void* )STORECFGBASE,sizeof(KMSysCfg));
291     return 0;
292 }
293
294 int WriteSysCfgToFlash(pStoredKMSysCfg theStoredKMSysCfg)
295 {
296     theStoredKMSysCfg->Seq1++;
297     theStoredKMSysCfg->Sign1 = START_SIGN;
298     theStoredKMSysCfg->EndSign1 = END_SIGN;
299 //        EraseAndWriteToFlashMem(theStoredKMSysCfg,(void *)STORE_SYSREG_BASE,sizeof(stStoredKMSysCfg));
300 //        return 0;
301 //    theKMSysCfg->cfgvar16++;
302     // find the next empty space to write
303     int nIndex=-1;
304     int s2=128;
305     for (int i=0;i<8;i++)
306     {
307         int skip=0;
308         unsigned char * nAddr2=(unsigned char *)(STORE_SYSREG_BASE + i * s2);
309         for (int j=0;j<s2;j++)
310         {
311             if ((nAddr2)[j] != 0xff)    {skip =1;break;}
312         }
313         if (skip==1) {continue;}
314         nIndex=i;
315         break;
316     }
317     if (nIndex >=0 && nIndex <8)    {    
318         WriteToFlashMemNoErase(theStoredKMSysCfg,(void *)(STORE_SYSREG_BASE + nIndex*s2),sizeof(stStoredKMSysCfg));
319     }
320     else     {
321         EraseAndWriteToFlashMem(theStoredKMSysCfg,(void *)STORE_SYSREG_BASE,sizeof(stStoredKMSysCfg));
322     }
323     return 0;
324 }
325
326 int is_pow_of_2(uint32_t x) {
327     return !(x & (x-1));
328 }
329
330 uint32_t next_pow_of_2(uint32_t x) 
331 {
332     if ( is_pow_of_2(x) )
333         return x;
334     x |= x>>1;
335     x |= x>>2;
336     x |= x>>4;
337     x |= x>>8;
338     x |= x>>16;
339     return x+1;
340 }
341
342 //uint8_t * pFlash1;
343 /*
344 stStoreCfg * GetCurStoreCfgAddr(void )
345 {
346     int s = sizeof(stStoreCfg);
347     int s2=next_pow_of_2(s);
348     stStoreCfg * p1;
349     int nMaxSN=0;
350     int nMaxId=0;
351     for (int i=0; s2*i < STORECFGPAGESIZE ; i++)
352     {
353         p1= (stStoreCfg *)(STORECFGBASE + s2 * i );
354         if (p1->Sign1 != START_SIGN) continue;
355         if (p1->EndSign1 != END_SIGN) continue;
356         
357         if (p1->Seq1 >= nMaxSN) {nMaxSN = p1->Seq1; nMaxId = i;}
358     }
359 //    nMaxId=nMaxId+1;
360     return     (stStoreCfg *)(STORECFGBASE + s2 * nMaxId);
361 }
362
363 stStoreCfg * GetNextStoreCfgAddr(stStoreCfg * CurCfg )
364 {
365     int s = sizeof(stStoreCfg);
366     int s2=next_pow_of_2(s);
367     uint32_t nAddr1 = (uint32_t) CurCfg;
368     uint32_t nAddr2 = nAddr1 + s2;
369     for (int i=1;i<33;i++)
370     {
371         int skip=0;
372         nAddr2 = nAddr1 + s2*i;
373         if ((nAddr2 + s) > STORECFGBASE + STORECFGPAGESIZE) 
374         {
375             nAddr2=STORECFGBASE; break;
376         }
377         for (int j=0;j<s2;j++)
378         {
379             if (((unsigned char *)nAddr2)[j] != 0xff)
380             {skip =1;}
381         }
382         if (skip==1) {continue;}
383         break;
384     }
385     stStoreCfg * p1 = (stStoreCfg *)nAddr2;    
386     return p1;
387 }
388
389
390 int SaveStoreCfg(stStoreCfg * CurCfg)
391 {
392     return 0;
393 }
394 */
395 // stStoreCfg Cfg2;
396
397 int LoadFlashDatas()
398 {
399         for (int i=0;i<16;i++)
400     {
401 //            FlashDatas[i]=((uint16_t *)pConfigFlashBase)[i];
402     }
403     return 0;
404 }
405 /*
406 int LoadAndUpdateStoreCfg()
407 {
408     stStoreCfg * pFCfg = (stStoreCfg *) GetCurStoreCfgAddr();
409
410     Cfg2.Sign1=START_SIGN;
411     Cfg2.Seq1=pFCfg[0].Seq1+1;
412     Cfg2.CRC1=0x7777;
413     Cfg2.PowerCount=pFCfg[0].PowerCount+1;
414     Cfg2.UpTime=pFCfg[0].UpTime+1;
415     Cfg2.UserData1=pFCfg[0].UserData1;
416     Cfg2.EndSign1=END_SIGN;
417     stStoreCfg * pFCfg2 = GetNextStoreCfgAddr(pFCfg);    
418     
419
420     HAL_StatusTypeDef res;        
421     if (pFCfg2 <= pFCfg)
422     {
423         res = (HAL_StatusTypeDef)EraseAndWriteToFlashMem(&Cfg2,pFCfg2,sizeof(stStoreCfg));
424         
425     }else
426     {
427         res = (HAL_StatusTypeDef)WriteToFlashMemNoErase(&Cfg2,pFCfg2,sizeof(stStoreCfg));
428     }    
429         return res;
430 }
431 */
432 int CheckSavedData(void * pStartAddr, int PageSize, int Pages, int DataSize)
433 {
434         return 0;
435 };
436
437
438 int nMaxRunStatIndex=-1;
439 unsigned int nMaxRunStatSeq=0;
440 int nNextRunStatSpace=0;
441 int LoadDefaultRunStat(pRunStat theRunStat)
442 {
443     theRunStat->PowerCount=1;
444 //    theRunStat->UpTime=0;
445 //    theRunStat->UserData1=0;
446 //    theRunStat->WorkMode=0;
447 //    theRunStat->WorkMode2=0;
448 //    theRunStat->nBinProgBank=0;
449 //    theRunStat->nBinProgSize=0;
450     return 0;
451 }
452 int LoadRunStat(pRunStat theRunStat)
453 {
454     uchar * pRunStatStore = (uchar *)STORE_RUNSTAT_BASE;
455     pRunStat pStoreRunStats = (pRunStat)pRunStatStore;
456 //    int s = sizeof(stRunStat);
457     
458     for (int i=0;i * sizeof(stRunStat) < (STORE_RUNSTAT_PAGESIZE * STORE_RUNSTAT_PAGES) ;i++)
459     {
460         if (pStoreRunStats[i].Sign1 == START_SIGN )
461         {
462             if (pStoreRunStats[i].Seq1 > nMaxRunStatSeq)
463             {
464                 nMaxRunStatSeq = pStoreRunStats[i].Seq1;
465                 nMaxRunStatIndex=i;
466                 nNextRunStatSpace=i+1;
467             }
468         }
469     }
470     if (nMaxRunStatIndex>=0) // && nMaxRunStatIndex <8)
471     {
472             ReadFlashMem(theRunStat,(void *)(pStoreRunStats+nMaxRunStatIndex),sizeof(stRunStat));
473     }else {
474         LoadDefaultRunStat(theRunStat);
475     }    
476     // find Next Space
477     // if Same Page with MaxSeq Index, then not erase, skip and skip.
478     // if next Page of MaxSeq Index, then earse if not empty;
479     if ((nNextRunStatSpace + 1) * sizeof(stRunStat) > STORE_RUNSTAT_PAGESIZE * STORE_RUNSTAT_PAGES)    {
480         nNextRunStatSpace=0;
481     }
482     return 0;
483 }
484
485 int SaveRunStat(pRunStat theRunStat)
486 {
487     nMaxRunStatSeq++;
488     theRunStat->Sign1=START_SIGN;
489     theRunStat->Seq1 = nMaxRunStatSeq;
490     theRunStat->PowerCount=KMem.PwrOnCount;
491     theRunStat->UpTime=KMem.TotalRunTime;
492     theRunStat->CRC1=0x11;
493     theRunStat->EndSign1=END_SIGN;
494     
495     //check empty
496     unsigned char *pFlash = (unsigned char *)(STORE_RUNSTAT_BASE + nNextRunStatSpace*sizeof(stRunStat));
497     int Skip=0;
498     for (int j=0;j<sizeof(stRunStat);j++)
499     {
500         if (pFlash[j]!=0xff) {Skip =1 ; break;}
501     }
502     if (Skip ==0 )
503     {
504         WriteToFlashMemNoErase(theRunStat,(void *)(STORE_RUNSTAT_BASE + nNextRunStatSpace*sizeof(stRunStat)),sizeof(stRunStat));
505     }else
506     {
507         EraseAndWriteToFlashMem(theRunStat,(void *)(STORE_RUNSTAT_BASE + nNextRunStatSpace*sizeof(stRunStat)),sizeof(stRunStat));
508     }
509     nMaxRunStatIndex=nNextRunStatSpace;
510     nNextRunStatSpace++;
511     if ((nNextRunStatSpace+1) * sizeof(stRunStat) > STORE_RUNSTAT_PAGESIZE * STORE_RUNSTAT_PAGES)
512     {
513         nNextRunStatSpace=0;
514     }
515     return 0;
516 }    
517
518
519 int nEventCount=0;
520 int nEventMinIndex;
521 int nEventMaxIndex;
522 unsigned int nEventMaxSeq=0;
523 int nEventNextSpace;
524 int nMaxCurTime=0;
525 volatile int PowerState = 0;
526
527 volatile int PowerDownEvent=0;
528 volatile int OldPowerDownEvent=0;
529 volatile int OldPowerDownEventTime=0;
530
531 int CheckEventLog()
532 {
533     unsigned int nMinEventSeq=999999999;
534     uchar * pEventStore = (uchar *)STORE_LOG_BASE;
535     pEventLog theEventLog = (pEventLog) pEventStore;
536 //    int s = sizeof(stEventLog);
537     nEventCount=0;
538     
539     for (int i=0;i * sizeof(stEventLog) < (STORE_LOG_PAGESIZE * STORE_LOG_PAGES) ;i++)
540     {
541         if (theEventLog[i].Sign1 == START_SIGN )
542         {
543             nEventCount++;
544             if (theEventLog[i].Seq1 > nEventMaxSeq)
545             {
546                 nEventMaxSeq = theEventLog[i].Seq1;
547                 nEventMaxIndex=i;
548                 nMaxCurTime=theEventLog[i].nTime;
549                 nEventNextSpace=i+1;
550             }
551             if (theEventLog[i].Seq1 < nMinEventSeq)
552             {
553                 nMinEventSeq = theEventLog[i].Seq1;
554                 nEventMinIndex = i;
555             }
556         }
557     }
558     // find Next Space
559     // if Same Page with MaxSeq Index, then not erase, skip and skip.
560     // if next Page of MaxSeq Index, then earse if not empty;
561     if ((nEventNextSpace + 1) * sizeof(stEventLog) > STORE_LOG_PAGESIZE * STORE_LOG_PAGES)    {
562         nEventNextSpace=0;
563     }
564     
565     return nEventCount;
566 }
567
568 int AddEventLog(uint32_t nTime, USHORT nEvent, USHORT nParam1, UINT nParam2)
569 {
570     nEventMaxSeq++;
571     stEventLog thisEventLog={START_SIGN, nEventMaxSeq, nTime,nEvent,nParam1,nParam2};
572     //check empty
573     unsigned char *pFlash = (unsigned char *)(STORE_LOG_BASE + nEventNextSpace*sizeof(stEventLog));
574     int Skip=0;
575     for (int j=0;j<sizeof(stEventLog);j++)
576     {
577         if (pFlash[j]!=0xff) {Skip =1 ; break;}
578     }
579     if (Skip ==0 )
580     {
581         WriteToFlashMemNoErase(&thisEventLog,(void *)(STORE_LOG_BASE + nEventNextSpace*sizeof(stEventLog)),sizeof(stEventLog));
582     }else
583     {
584         EraseAndWriteToFlashMem(&thisEventLog,(void *)(STORE_LOG_BASE + nEventNextSpace*sizeof(stEventLog)),sizeof(stEventLog));
585         
586     }
587     nEventMaxIndex=nEventNextSpace;
588     nEventNextSpace++;
589     if ((nEventNextSpace+1) * sizeof(stEventLog) > STORE_LOG_PAGESIZE * STORE_LOG_PAGES)
590     {
591         nEventNextSpace=0;
592     }
593     nEventCount++;
594     KMem.nEventCount=nEventCount;
595     return 0;
596 }    
597
598 pEventLog GetEventLogAddr(int nIndex)
599 {
600     int nEventIndex=nEventMinIndex + nIndex;
601     
602     if (nEventIndex * sizeof(stEventLog) >= (STORE_LOG_PAGESIZE * STORE_LOG_PAGES))
603     {
604         nEventIndex -= (STORE_LOG_PAGESIZE * STORE_LOG_PAGES)/sizeof(stEventLog);
605     }
606     unsigned char *pFlash = (unsigned char *)(STORE_LOG_BASE + nEventIndex*sizeof(stEventLog));
607     
608     return (pEventLog)pFlash;    
609 }
610     
611 int ClearEventLog(void)
612 {
613     EraseFlashMem((void *)STORE_LOG_BASE,STORE_LOG_PAGES);
614     nEventMinIndex=0;
615     nEventMaxIndex=0;
616     nEventMaxSeq=0;
617     nEventCount=0;
618     nEventNextSpace=0;
619     return 0;
620 }
621 int KMachineInit(void)
622 {
623 //    ClearEventLog();
624     CheckEventLog();
625     LoadRunStat(&KMRunStat);
626     KMem.CurTimeSec=nMaxCurTime;
627     KMem.TotalRunTime=KMRunStat.UpTime;
628     KMRunStat.PowerCount++;
629     KMem.PwrOnCount=KMRunStat.PowerCount;
630     SaveRunStat(&KMRunStat);
631     KMem.SDD[15]=nMaxRunStatIndex;
632     KMem.SDD[16]=nMaxRunStatSeq;
633     KMem.SDD[17]=nNextRunStatSpace;
634
635     
636     AddEventLog(KMem.CurTimeSec,EventTypePowerUp,1,12345);
637     KMem.SDD[19]=nEventCount;
638     KMem.SDD[20]=nEventMinIndex;
639     KMem.SDD[21]=nEventMaxIndex;
640     KMem.SDD[22]=nEventMaxSeq;
641     KMem.SDD[23]=nEventNextSpace;
642     
643     return 0;
644 }
645
646 inline void SetAddrBit(unsigned short * pW, unsigned char bitAddr)
647 {
648     (*pW)|=1<<(bitAddr&0xf);
649 }
650
651 inline void ResetBit(unsigned short * pW, unsigned char bitAddr)
652 {
653     (*pW)&=~(1<<(bitAddr&0xf));
654 }
655
656 static inline void SetBitValue(unsigned short * pW, unsigned char bitAddr, unsigned char Value)
657 {
658     if (Value)    {    SetAddrBit(pW, bitAddr);}
659     else {ResetBit(pW, bitAddr);}
660 }
661
662 static inline unsigned char GetBitValue(unsigned short W, unsigned char bitAddr)
663 {
664     if (W&(1<<(bitAddr&0xf))) return 1;
665     else return 0;
666 }
667
668
669 unsigned char GetCoilValue(unsigned char nCoilType, unsigned short nCoilAddr)
670 {
671         unsigned char thisValue=0;
672         unsigned short nWordAddr=(nCoilAddr&0xff0)>>4;
673         unsigned char nBitAddr=nCoilAddr&0xf;
674         switch(nCoilType)
675         {
676         case KLCoilTypeX:
677             if (nCoilAddr >= KLCoilXCount) return 0;
678             thisValue = GetBitValue(KMem.WX[nWordAddr], nBitAddr);
679             break;
680         case KLCoilTypeY:
681             if (nCoilAddr >= KLCoilYCount) return 0;
682             thisValue = GetBitValue(KMem.WY[nWordAddr], nBitAddr);
683             break;
684         case KLCoilTypeR:
685             if (nCoilAddr >= KLCoilRCount) return 0;
686             thisValue = GetBitValue(KMem.WR[nWordAddr], nBitAddr);
687             break;
688         case KLCoilTypeLX:
689             if (nCoilAddr >= KLCoilLXCount) return 0;
690              thisValue = GetBitValue(KMem.WLX[nWordAddr], nBitAddr);
691             break;
692         case KLCoilTypeLY:
693             if (nCoilAddr >= KLCoilLYCount) return 0;
694             thisValue = GetBitValue(KMem.WLY[nWordAddr], nBitAddr);
695             break;
696         case KLCoilTypeT:
697             if (nCoilAddr >= KLCoilTCount) return 0;
698             thisValue = GetBitValue(KMem.WT[nWordAddr], nBitAddr);
699             break;
700         case KLCoilTypeC:
701             if (nCoilAddr >= KLCoilCCount) return 0;
702             thisValue = GetBitValue(KMem.WC[nWordAddr], nBitAddr);
703             break;
704         case KLCoilTypeLR:
705             if (nCoilAddr >= KLCoilLRCount) return 0;
706             thisValue = GetBitValue(KMem.WLR[nWordAddr], nBitAddr); 
707             break;
708         case KLCoilTypeSR:
709             if (nCoilAddr >= KLCoilSRCount) return 0;
710             thisValue = GetBitValue(KMem.WSR[nWordAddr], nBitAddr);
711             break;
712             default:
713                 break;
714         }    
715         return thisValue;
716 }
717 int SetCoilValue(unsigned char nCoilType, unsigned short nCoilAddr, unsigned char nCoilValue)
718 {
719         unsigned short nWordAddr=(nCoilAddr&0xff0)>>4;
720         unsigned char nBitAddr=nCoilAddr&0xf;
721         switch(nCoilType)
722         {
723         case KLCoilTypeX:
724             if (nCoilAddr >= KLCoilXCount) return 0;
725             SetBitValue(&KMem.WX[nWordAddr], nBitAddr, nCoilValue);
726             break;
727         case KLCoilTypeY:
728             if (nCoilAddr >= KLCoilYCount) return 0;
729             SetBitValue(&KMem.WY[nWordAddr], nBitAddr, nCoilValue);
730             break;
731         case KLCoilTypeR:
732             if (nCoilAddr >= KLCoilRCount) return 0;
733             SetBitValue(&KMem.WR[nWordAddr], nBitAddr, nCoilValue);
734             break;
735         case KLCoilTypeLX:
736             if (nCoilAddr >= KLCoilLXCount) return 0;
737             SetBitValue(&KMem.WLX[nWordAddr], nBitAddr, nCoilValue);
738             break;
739         case KLCoilTypeLY:
740             if (nCoilAddr >= KLCoilLYCount) return 0;
741             SetBitValue(&KMem.WLY[nWordAddr], nBitAddr, nCoilValue);
742             break;
743         case KLCoilTypeT:
744             if (nCoilAddr >= KLCoilTCount) return 0;
745             SetBitValue(&KMem.WT[nWordAddr], nBitAddr, nCoilValue);
746             break;
747         case KLCoilTypeC:
748             if (nCoilAddr >= KLCoilCCount) return 0;
749             SetBitValue(&KMem.WC[nWordAddr], nBitAddr, nCoilValue);
750             break;
751         case KLCoilTypeLR:
752             if (nCoilAddr >= KLCoilLRCount) return 0;
753             SetBitValue(&KMem.WLR[nWordAddr], nBitAddr, nCoilValue);
754             break;
755         case KLCoilTypeSR:
756             if (nCoilAddr >= KLCoilSRCount) return 0;
757             SetBitValue(&KMem.WSR[nWordAddr], nBitAddr, nCoilValue);
758             break;
759             default:
760                 break;
761         }    
762         return 0;
763 }
764
765 int GetVarData(int nDataType, int nDataAddr)
766 {
767     // TODO: ?????????.
768     int thisValue = 0;
769     
770     switch (nDataType)
771     {
772     case KLDataTypeDEC:
773     case KLDataTypeHEX:
774         thisValue = nDataAddr;
775         break;
776     case KLDataTypeWX:
777         if (nDataAddr >= KLDataWXCount) return 0;
778         thisValue = KMem.WX[nDataAddr];
779         break;
780     case KLDataTypeWY:
781         if (nDataAddr >= KLDataWYCount) return 0;
782         thisValue = KMem.WY[nDataAddr];
783         break;
784     case KLDataTypeWR:
785         if (nDataAddr >= KLDataWRCount) return 0;
786         thisValue = KMem.WR[nDataAddr];
787         break;
788     case KLDataTypeWLX:
789         if (nDataAddr >= KLDataWLCount) return 0;
790         thisValue = KMem.WLX[nDataAddr];
791         break;
792     case KLDataTypeWLY:
793         if (nDataAddr >= KLDataWLCount) return 0;
794         thisValue = KMem.WLY[nDataAddr];
795         break;
796     case KLDataTypeDT:
797         if (nDataAddr >= KLDataDTCount) return 0;
798         thisValue = (signed short)KMem.DT[nDataAddr];
799         break;
800     case KLDataTypeSDT:
801         if (nDataAddr >= KLDataSDTCount) return 0;
802         thisValue = KMem.SDT[nDataAddr];
803         break;
804     case KLDataTypeWSR:
805         if (nDataAddr >= KLCoilLRCount) return 0;
806         thisValue = KMem.WSR[nDataAddr];
807         break;
808     case KLDataTypeSV:
809         if (nDataAddr >= KLDataSVCount) return 0;
810         thisValue = KMem.SV[nDataAddr];
811         break;
812     case KLDataTypeEV:
813         if (nDataAddr >= KLDataEVCount) return 0;
814         thisValue = KMem.EV[nDataAddr];
815         break;
816     case KLDataTypeLD:
817         if (nDataAddr >= KLDataLDCount) return 0;
818         thisValue = KMem.DT[nDataAddr];
819         break;
820     case KLDataSysCfg:
821         if (nDataAddr >= KLCoilSRCount) return 0;
822         thisValue = KMem.SDT[nDataAddr];
823         break;
824     case KLDataTypeFlash:
825         if (nDataAddr >= KLCoilSRCount) return 0;
826         thisValue = KMem.SDT[nDataAddr];
827         break;
828     case KLDataTypeTest:
829         if (nDataAddr >= KLCoilSRCount) return 0;
830         thisValue = KMem.SDT[nDataAddr];
831         break;
832     }
833     return thisValue;
834 }
835
836
837 int SetVarData(int nDataType, int nDataAddr, int nDataValue)
838 {
839     // TODO: ?????????.
840     switch (nDataType)
841     {
842 //    case KLDataTypeDEC:
843 //    case KLDataTypeHEX:
844 //        break;
845     case KLDataTypeWX:
846         if (nDataAddr >= KLDataWXCount) return 0;
847         KMem.WX[nDataAddr] = nDataValue;
848         break;
849     case KLDataTypeWY:
850         if (nDataAddr >= KLDataWYCount) return 0;
851         KMem.WY[nDataAddr] = nDataValue;
852         break;
853     case KLDataTypeWR:
854         if (nDataAddr >= KLDataWRCount) return 0;
855         KMem.WR[nDataAddr] = nDataValue;
856         break;
857     case KLDataTypeWLX:
858         if (nDataAddr >= KLDataWLCount) return 0;
859         KMem.WLX[nDataAddr] = nDataValue;
860         break;
861     case KLDataTypeWLY:
862         if (nDataAddr >= KLDataWLCount) return 0;
863         KMem.WLY[nDataAddr] = nDataValue;
864         break;
865     case KLDataTypeDT:
866         if (nDataAddr >= KLDataDTCount) return 0;
867         KMem.DT[nDataAddr] = nDataValue;
868         break;
869     case KLDataTypeSDT:
870         if (nDataAddr >= KLDataSDTCount) return 0;
871         KMem.SDT[nDataAddr] = nDataValue;
872         break;
873     case KLDataTypeWSR:
874         if (nDataAddr >= KLCoilLRCount) return 0;
875         KMem.WSR[nDataAddr] = nDataValue;
876         break;
877     case KLDataTypeSV:
878         if (nDataAddr >= KLDataSVCount) return 0;
879         KMem.SV[nDataAddr] = nDataValue;
880         break;
881     case KLDataTypeEV:
882         if (nDataAddr >= KLDataEVCount) return 0;
883         KMem.EV[nDataAddr] = nDataValue;
884         break;
885     case KLDataTypeLD:
886         if (nDataAddr >= KLDataLDCount) return 0;
887         KMem.DT[nDataAddr] = nDataValue;
888         break;
889     case KLDataSysCfg:
890         if (nDataAddr >= KLCoilSRCount) return 0;
891         KMem.SDT[nDataAddr] = nDataValue;
892         break;
893     case KLDataTypeFlash:
894         if (nDataAddr >= KLCoilSRCount) return 0;
895         KMem.SDT[nDataAddr] = nDataValue;
896         break;
897     case KLDataTypeTest:
898         if (nDataAddr >= KLCoilSRCount) return 0;
899         KMem.SDT[nDataAddr] = nDataValue;
900         break;
901     }
902
903     return 0;
904 }
905