Nuvoton ICP Spec

  1 /*************************************************************************
  2  *
  3  *    File name   : FlashPrg.c
  4  *    Description :
  5  *
  6  *    History :
  7  *    1. Date        : 9, 2018
  8  *       Author      : 
  9  *       Description : 
 10  *
 11  *    $Revision: 0 $
 12  **************************************************************************/
 13 
 14 /*
 15  * ICP WRITER MODE COMMAND
 16  * 1'b0, 1'b0,FOEN,FCEN,FCTRL[3:0]
 17  */
 18 #define ICPCMD_EntryMode                   0x55AA03 
 19 #define ICPCMD_Standby                   0x30
 20 #define ICPCMD_ReadCompanyID             0x0B
 21 #define ICPCMD_ReadDeviceID              0x0C
 22 #define ICPCMD_FlashProgram              0x21
 23 #define ICPCMD_FlashEraseVerify          0x09
 24 #define ICPCMD_FlashProgramVerify        0x0A
 25 #define ICPCMD_WholechipErase            0x26
 26 #define ICPCMD_FlashRead                   0x00
 27 
 28 typedef struct{
 29   INT32U Sectorsz;            // Sector Size in Bytes
 30   INT32U SectorAddr;          // Address of Sector
 31 } SPC_SECTORS_Type;
 32 
 33 typedef struct{
 34     INT16U RstLevel;
 35     INT16U dlyEntryMode;
 36     INT8U dlyTz;
 37     INT8U dlyTrd;        
 38     INT8U dlyTprog;    
 39     INT8U dlyTme;
 40     INT8U dlyTeph;    
 41 }DLY_Type;
 42 
 43 // special sectors
 44 static SPC_SECTORS_Type tSpcSectors[] = {
 45     [Bidx_NUC126_128K_4K_2K_8B] = { .Sectorsz = 0x8, .SectorAddr = 0x300000,},
 46     [Bidx_NUC126_256K_4K_2K_8B] = { .Sectorsz = 0x8, .SectorAddr = 0x300000,},
 47     [Bidx_NUC400_256k_16K_16B] = { .Sectorsz = 0x10, .SectorAddr = 0x300000,},
 48     [Bidx_NUC400_512k_16K_16B] = { .Sectorsz = 0x10, .SectorAddr = 0x300000,},
 49 
 50     [Bidx_M451_040k_4K_8B] = { .Sectorsz = 0x8, .SectorAddr = 0x300000,},
 51     [Bidx_M451_072k_4K_8B] = { .Sectorsz = 0x8, .SectorAddr = 0x300000,},
 52     [Bidx_M451_128k_4K_8B] = { .Sectorsz = 0x8, .SectorAddr = 0x300000,},
 53     [Bidx_M451_256k_4K_8B] = { .Sectorsz = 0x8, .SectorAddr = 0x300000,},
 54 };
 55 
 56 #define    SpcSectorAddr     tSpcSectors[M_BlkIndex].SectorAddr
 57 #define    SpcSectorSize     tSpcSectors[M_BlkIndex].Sectorsz
 58 
 59 // ICP Timing Parameters Table
 60 static DLY_Type tDlys[] = {
 61     [Bidx_NUC126_128K_4K_2K_8B] = {.RstLevel = 0xffff, .dlyEntryMode = 500, .dlyTz = 1, .dlyTrd = 1, .dlyTprog = 100, .dlyTme = 80, .dlyTeph = 5,},
 62     [Bidx_NUC126_256K_4K_2K_8B] = {.RstLevel = 0xffff, .dlyEntryMode = 500, .dlyTz = 1, .dlyTrd = 1, .dlyTprog = 100, .dlyTme = 80, .dlyTeph = 5,},
 63 
 64     [Bidx_NUC400_256k_16K_16B] = {.RstLevel = 0x0000, .dlyEntryMode = 100, .dlyTz = 1, .dlyTrd = 1, .dlyTprog = 40, .dlyTme = 60, .dlyTeph = 5,},
 65     [Bidx_NUC400_512k_16K_16B] = { .RstLevel = 0x0000, .dlyEntryMode = 100,.dlyTz = 1, .dlyTrd = 1, .dlyTprog = 40, .dlyTme = 60, .dlyTeph = 5,},
 66 
 67     [Bidx_M451_040k_4K_8B] = {.RstLevel = 0xffff, .dlyEntryMode = 500, .dlyTz = 1, .dlyTrd = 1, .dlyTprog = 60, .dlyTme = 90, .dlyTeph = 5,},
 68     [Bidx_M451_072k_4K_8B] = {.RstLevel = 0xffff, .dlyEntryMode = 500, .dlyTz = 1, .dlyTrd = 1, .dlyTprog = 60, .dlyTme = 90, .dlyTeph = 5,},
 69     [Bidx_M451_128k_4K_8B] = {.RstLevel = 0xffff, .dlyEntryMode = 500, .dlyTz = 1, .dlyTrd = 1, .dlyTprog = 60, .dlyTme = 90, .dlyTeph = 5,},
 70     [Bidx_M451_256k_4K_8B] = {.RstLevel = 0xffff, .dlyEntryMode = 500, .dlyTz = 1, .dlyTrd = 1, .dlyTprog = 60, .dlyTme = 90, .dlyTeph = 5,},            
 71 };
 72 
 73 #define    RL         tDlys[M_BlkIndex].RstLevel
 74 #define    EM         tDlys[M_BlkIndex].dlyEntryMode
 75 #define    Tz         tDlys[M_BlkIndex].dlyTz
 76 #define    Trd     tDlys[M_BlkIndex].dlyTrd
 77 #define    Tprog     tDlys[M_BlkIndex].dlyTprog
 78 #define    Tme     tDlys[M_BlkIndex].dlyTme
 79 #define    Teph     tDlys[M_BlkIndex].dlyTeph
 80 
 81 
 82 void EntryMode(void)
 83 {
 84     INT32U code = ICPCMD_EntryMode;
 85     INT8U i;
 86 
 87     make_lock();
 88 
 89     ICETDA_DPORT(IODecVaddr) = 0xFFFF;
 90     
 91     RESET_DPORT(IODecVaddr) = RL;
 92     delay_x1us(EM);
 93 
 94     /* 50 clocks */
 95     for(i=0; i<50; i++)
 96     {
 97         ICETCK_DPORT(IODecVaddr) = 0xFFFF;
 98         delay_x1us(1); 
 99 
100         ICETCK_DPORT(IODecVaddr) = 0x0000;
101         delay_x1us(1); 
102     }
103 
104     /* ICP Mode Entry Code */
105     for(i=0; i<24; i++)
106     {    
107         ICETDA_DPORT(IODecVaddr)=(code&0x800000)? 0xFFFF:0x0000;
108         delay_x1us(1); 
109 
110         ICETCK_DPORT(IODecVaddr) = 0xFFFF;
111         delay_x1us(1); 
112 
113         ICETCK_DPORT(IODecVaddr) = 0x0000;
114         delay_x1us(1); 
115 
116         code=code<<1;
117     }
118 
119     /* ICP Mode clean reset,icpda,icpck statues */
120     ICETDA_DPORT(IODecVaddr) = 0x0000;
121     ICETCK_DPORT(IODecVaddr) = 0x0000;
122     delay_x1us(50);
123 
124     make_unlock();
125 }
126 
127 void SendHead(INT32U dev_addr, INT8U cmd)
128 {
129     INT32U i, head = 0;
130 
131     head|=((dev_addr<<8)|cmd);
132 
133     for(i=0; i<32; i++)
134     {        
135         ICETDA_DPORT(IODecVaddr)=(head&0x80000000)? 0xFFFF:0x0000;
136 
137         ICETCK_DPORT(IODecVaddr) = 0xFFFF;
138         ICETCK_DPORT(IODecVaddr) = 0x0000;
139 
140         head=head<<1;
141     }
142     ICETDA_DPORT(IODecVaddr) = 0x0000;   
143 }
144 
145 void ICPRead(INT32U dev_addr,INT32U dev_size, INT8U cmd, INT32U *buf)
146 {
147     INT32U i,j;
148     INT8U tmp;
149     
150     SendHead(dev_addr,cmd);
151 
152     for(i=0; i<dev_size; i++)
153     {
154         ICETDA_ZPORT(IODecVaddr) = 0xFFFF;
155 
156         ICETCK_DPORT(IODecVaddr) = 0xFFFF;//Tri-State
157         ICETCK_DPORT(IODecVaddr) = 0x0000;    
158         delay_x1us(Tz);                 
159 
160         for(j=0; j<32; j++)             //(Read 32 bits from ICE_DAT pin)
161         {
162             ICETCK_DPORT(IODecVaddr) = 0xFFFF;
163             
164             tmp = ICETDA_ZPORT(IODecVaddr);
165             
166             ICETCK_DPORT(IODecVaddr) = 0x0000;
167             
168             buf[i] = (tmp&0x01)|(buf[i]<<1);
169         }
170 
171         ICETCK_DPORT(IODecVaddr) = 0xFFFF;//Tri-State        
172         ICETCK_DPORT(IODecVaddr) = 0x0000;
173         delay_x1us(Tz);     
174     
175         ICETDA_DPORT(IODecVaddr) = (i == dev_size-1)?0xFFFF:0x0000;    //NCONT        
176         delay_x1us(Trd);
177 
178         ICETCK_DPORT(IODecVaddr) = 0xFFFF;
179         ICETCK_DPORT(IODecVaddr) = 0x0000;
180         delay_x1us(1);         
181 
182     }
183     ICETDA_DPORT(IODecVaddr) = 0x0000;    
184 }
185 
186 void ICPWrite(INT32U dev_addr,INT32U dev_size, INT8U cmd, INT32U *buf)
187 {
188     INT32U i,j;
189 
190     SendHead(dev_addr,cmd);
191 
192     for(i=0; i<dev_size; i++)
193     {
194         ICETCK_DPORT(IODecVaddr) = 0xFFFF;//Tri-State
195         ICETCK_DPORT(IODecVaddr) = 0x0000;    
196         delay_x1us(Tz);                 
197         
198         for(j=0; j<32; j++)             //(Write 32 bits to ICE_DAT pin)
199         {
200             ICETDA_DPORT(IODecVaddr) = (buf[i] & (0x80000000>>j))?0xFFFF:0x0000;    
201 
202             ICETCK_DPORT(IODecVaddr) = 0xFFFF;    
203             ICETCK_DPORT(IODecVaddr) = 0x0000;
204         }
205         ICETCK_DPORT(IODecVaddr) = 0xFFFF;//Tri-State
206         ICETCK_DPORT(IODecVaddr) = 0x0000;
207         delay_x1us(Tz);                 
208 
209         ICETDA_DPORT(IODecVaddr) = (i == dev_size-1)?0xFFFF:0x0000;    //NCONT
210         delay_x1us(Tprog);
211         
212         ICETCK_DPORT(IODecVaddr) = 0xFFFF;
213         ICETCK_DPORT(IODecVaddr) = 0x0000;
214         delay_x1us(Teph);
215         
216     }
217     ICETDA_DPORT(IODecVaddr) = 0x0000;
218 }
219 
220 void ICPErase(INT32U dev_addr,INT32U dev_size, INT8U cmd, INT32U *buf)
221 {
222     INT32U i,j;
223 
224     SendHead(dev_addr,cmd);
225 
226     for(i=0; i<dev_size; i++)
227     {
228         ICETCK_DPORT(IODecVaddr) = 0xFFFF;//Tri-State
229         ICETCK_DPORT(IODecVaddr) = 0x0000;    
230         delay_x1us(Tz);                 
231         
232         for(j=0; j<32; j++)             //(Write 32 bits to ICE_DAT pin)
233         {
234             ICETDA_DPORT(IODecVaddr) = (buf[i] & (0x80000000>>j))?0xFFFF:0x0000;    
235 
236             ICETCK_DPORT(IODecVaddr) = 0xFFFF;    
237             ICETCK_DPORT(IODecVaddr) = 0x0000;
238         }
239         ICETCK_DPORT(IODecVaddr) = 0xFFFF;//Tri-State
240         ICETCK_DPORT(IODecVaddr) = 0x0000;
241         delay_x1us(Tz);                 
242 
243         ICETDA_DPORT(IODecVaddr) = (i == dev_size-1)?0xFFFF:0x0000;    //NCONT
244         delay_x1ms(Tme);
245         
246         ICETCK_DPORT(IODecVaddr) = 0xFFFF;
247         ICETCK_DPORT(IODecVaddr) = 0x0000;
248         delay_x1us(Teph);
249         
250     }
251 
252     ICETDA_DPORT(IODecVaddr) = 0x0000;    
253 }

 

posted @ 2018-09-06 18:07  大白菜菜pp  阅读(286)  评论(0编辑  收藏  举报