eCOG1k Writing Data to Flash Memory

22
AN018 – eCOG1k Writing Data to Flash Memory Version 1.2 This document describes an application designed to write data to the internal flash memory of the eCOG1k microcontroller. 28 January 2008 Cyan Technology Ltd.

Transcript of eCOG1k Writing Data to Flash Memory

Page 1: eCOG1k Writing Data to Flash Memory

AN018 – eCOG1k Writing Data to Flash Memory Version 1.2

This document describes an application designed to write data to the internal flash memory of the eCOG1k microcontroller.

28 January 2008 Cyan Technology Ltd.

Page 2: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

This product is not designed or intended to be used for on-line control of aircraft, aircraft navigation or communications systems or in air traffic control applications or in the design, construction, operation or maintenance of any nuclear facility, or for any medical use related to either life support equipment or any other life-critical application. Cyan Technology Ltd specifically disclaims any express or implied warranty of fitness for any or all of such uses. Ask your sales representative for details.

This document is intended only to assist the reader in the use of the product. Cyan Technology Ltd shall not be liable for any loss or damage arising from the use of any information in this guide, any error or omission in such information, or any incorrect use of the product.

Cyan TechnologyTM, the Cyan Technology logo and Max-eICETM are trademarks of Cyan Holdings Ltd. CyanIDE® and eCOG® are registered trademarks of Cyan Holdings Ltd. Cyan Technology Ltd recognises other brand and product names as trademarks or registered trademarks of their respective holders.

Any product described in this document is subject to continuous developments and improvements. All particulars of the product and its use contained in this document are given by Cyan Technology Ltd in good faith. However, all warranties implied or expressed, including but not limited to implied warranties of merchantability, or fitness for purpose, are excluded.

This document contains confidential and proprietary information of Cyan Technology Ltd and is protected by copyright laws. Its receipt or possession does not convey any rights to reproduce, manufacture, use or sell anything based on information contained within this document.

©Cyan Technology Ltd, 2008

Confidential and Proprietary Information

28 January 2008 Cyan Technology Ltd. Page 2 of 22

Page 3: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

28 January 2008 Cyan Technology Ltd. Page 3 of 22

Revision History Version Date Notes

V1.0 09/11/2004 First Release

V1.1 11/03/2005 Updated for CyanIDE V1.1

V1.2 20/03/2007 Corrected memory addresses in description.

Page 4: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

28 January 2008 Cyan Technology Ltd. Page 4 of 22

Contents 1 Introduction.......................................................................................... 5

2 Glossary .............................................................................................. 5

3 Operation............................................................................................. 6

4 Flash Memory Access ......................................................................... 7 4.1 The Memory Management Unit ................................................................. 7 4.2 Memory Management for the Flash Memory............................................. 7

5 Software Operation.............................................................................. 8

6 Requirements .................................................................................... 10

7 Example Application .......................................................................... 11 7.1 Installing and Compiling the Example ..................................................... 11 7.2 Testing..................................................................................................... 11

8 Limitations ......................................................................................... 12

Appendix A General Flash Erase/Write Procedures.............................. 13 A.1 Erase Process ......................................................................................... 13 A.2 Page Erase.............................................................................................. 13 A.3 Block Mass Erase Procedure .................................................................. 13 A.4 Programming Procedure ......................................................................... 14 A.5 Page Programming Procedure ................................................................ 14 A.6 Word Programming Procedure................................................................ 14

Appendix B Software Listings................................................................ 15 B.1 main.c ...................................................................................................... 15 B.2 flash_routine.c ......................................................................................... 16 B.3 cstartup.asm............................................................................................ 19

Page 5: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

1 Introduction

This document describes an application designed to write data to the internal flash memory of the eCOG1k microcontroller.

A full description of the flash memory can be found in the eCOG1k User Manual. In addition, application note AN001 – eCOG1k Internal Flash Memory, shows how the memory is organised and used.

2 Glossary

eCOG1 Cyan Technology microcontroller CyanIDE Integrated Development Environment for eCOG1 microcontroller MMU Memory Management Unit.

The on-chip I/O registers may be accessed as complete registers, or as named bit fields within the registers. The include file ecog1.h contains structure definitions for all on-chip registers and bit fields. To access any register, use the structure prefix rg. To access a bit field within a register, use the structure prefix fd. For example:

// Write to flash program data register rg.flash_prg_data = 0xA55A; // Write to period bit field in configuration register fd.flash_prg_cfg.period = 0x01F3;

28 January 2008 Cyan Technology Ltd. Page 5 of 22

Page 6: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

3 Operation

Due to the way in which flash memory works, it is not possible to read from any address in flash while any part of it is being programmed or erased. This means that it is necessary for any code that writes to the flash memory to execute from another memory, otherwise the program fails because the processor cannot read the correct code from the flash memory while it is being programmed.

This application note demonstrates how to use the internal RAM of the eCOG1k as the location of the code that performs the writing of the flash memory. This code is defined as a separate function and is compiled to a pre-defined address within the flash memory. The software copies this code from flash memory to the internal RAM of the eCOG1k, and executes it from there to program or erase the flash. This technique allows the entire flash memory to be written.

This example software simply writes a value to a pre-defined page of flash for demonstration purposes.

Figure 1 demonstrates this process chronologically, and a full description is given in section 5.

1) erase/write routine in

flash memory

0x05FF

0x0400

2) Mapped to data space

0x09FF

0x0800

0xE93F 0xE810

4) erase/write routine in

RAM memory

0x01FF

0x0000

3) Copy 0x130 words of code

5) Mapped to code space

0x83FF

0x8000

0x03FF

Logical Code

Memory

Logical Data

Memory Internal

RAM

Internal Flash

6) Executed at 0x8010 in code space

Figure 1. Chronological map of program operation

28 January 2008 Cyan Technology Ltd. Page 6 of 22

Page 7: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

4 Flash Memory Access

4.1 The Memory Management Unit The eCOG1k’s memory (both internal and external) is mapped through the memory management unit (MMU) to the eCOG1k processor, allowing a variety of memories to be arranged as code and/or data memory. This allows multiple memories to be mapped to either code or data, or a single device to be mapped to both code and data. The translators are available for both internal and external memories, including the internal flash memory and the internal RAM.

4.2 Memory Management for the Flash Memory The MMU is responsible for translating the physical address of the various memories to CPU specific logical addresses. The unit allows the mapping of different memory devices to the same logical memory space by means of address translators. Memory access to the correct memory is then automatic and carried out by simply addressing the logical memory location. The MMU contains 13 individual address translators, 4 of which are used for code memory translation and 9 for data memory translation.

The MMU translators for the flash memory are available through the MMU register block. The following registers control the logical address, physical address and sizes of the memory segments and the side in which the memory is allocated (code or data). Note that the address values specified in these registers are the most significant 16 bits of a 24-bit address field, and the remaining bits are 0. The actual size of the memory segment is the value in the size register + 1, shifted left by 8 bits. The size register contents must be a value of 2n – 1, where n is an integer, so that the segment size is a power of 2. mmu.flash_code_log mmu.flash_data_log mmu.flash_code_phy mmu.flash_data_phy mmu.flash_code_size mmu.flash_data_size

The flash memory code space translator is always enabled. The flash memory data space translator is enabled and disabled by setting or clearing bit 4 in the mmu.translate_en register.

A full description of the MMU is given in theUser Manual. Further examples of using the MMU may be found in application notes AN001 (eCOG1k Internal Flash memory), AN002 (eCOG1k External Flash Memory) and AN003 (eCOG1k SDRAM Interface).

Appendix A contains general instructions for erasing and writing flash memory completely, by page or by word, including timings and control signals.

28 January 2008 Cyan Technology Ltd. Page 7 of 22

Page 8: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

5 Software Operation

The file flash_routine.c contains the code that is eventually run from RAM, and the function code is preceded by the following line.

#pragma code_segment ERASE_PROGRAM

This code line is specific to the eCOG1k compiler. The code_segment command indicates that the following code should be compiled and located at the address given by the constant value ERASE_PROGRAM. This constant is defined as a code segment and assigned to a logical address in code space by the following statements at the end of the cstartup.asm file.

.CSEG ERASE_PROGRAM ORG H'0400

Together, the #pragma statement in flash_routine.c and the .CSEG statement in cstartup.asm indicate that the function is to be located at address 0x0400 hexadecimal in the code segment. The location is selected to be high enough so that it does not interfere with the code memory used by the main function main.c; it is possible to change this address if required by altering the ORG value in cstartup.asm described above. Fixing the location of this function allows the main function to copy the routine to the desired location in RAM where it can be executed, allowing the flash writing to proceed.

The function in flash_routine.c shares two variables with the main function in main.c; page which represents the flash memory page to be programmed, and buffer which contains 256 words of data to be written to flash memory. The software has a single function; it performs an erase on the selected memory block and then writes the 256 words of data from buffer to the flash memory at the desired page. By default page is set arbitrarily to 60 (=0x3c) and buffer is filled with 0x9988 so that it is easily identifiable when debugging. In a real application, the page value would be modified by the application to select different areas of the flash memory.

The variable initialisation section generates the flash physical address to be programmed from passed parameters, and also initialises timing specific variables. The values of the timing specific variables are covered in the eCOG1k User Manual and in application note AN001 – eCOG1k Internal Flash Memory.

Before programming flash memory, it is essential to erase the contents of the flash memory area to be programmed. This is necessary because flash programming of logical data bits cannot be reversed individually. The example program first performs a page erase on the required page, then writes the data stored in buffer to the flash memory as 8 rows of 32 words. The exact sequence used is given in appendix A and follows that used in application note AN001 – eCOG1k Internal Flash Memory.

The main function in main.c is responsible for loading this code into RAM and executing it such that flash memory writes can proceed without accessing the internal flash until they have completed. All interrupts must be disabled until the flash write procedure has completed. If they are not disabled, then any interrupt causes the CPU to attempt to fetch the interrupt vector from flash memory. This read from flash fails, and the processor then branches to an undefined address. The requirement to run the flash code without interruption also prevents tasks such as maintaining a Real-Time Clock.

It is possible to copy the interrupt vector table and interrupt service routines to RAM as well as the flash programming code, but care must be taken to maintain the correct timing of the flash erase and write routines if interrupts are not disabled.

28 January 2008 Cyan Technology Ltd. Page 8 of 22

Page 9: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

Initially, the memory map is defined as shown below by the code in cstartup.asm.

Logical Memory Physical memory Function Start

Address End Address

Location Start Address

End Address

Size (words)

Code 0x0000 0x77FF Internal flash 0x0000 0x77FF 30K Data 0x0000 0x07FF Internal flash 0x7800 0x7FFF 2K Data 0xE800 0xEFFF Internal RAM 0x0000 0x07FF 2K

Table 1. Initial memory map

Table 1 shows the memory map used in this application, as implemented by the main section of the code. The default MMU configuration after reset is that 30K words of the internal flash are mapped to code space at logical addresses 0x0000 to 0x77FF. The remaining 2K words (4K bytes) are hidden by the mapping of registers at locations 0x7800 to 0x7FFF. In addition to the mapping at reset, 512 words of internal flash from 0x0400 to 0x05FF are mapped into data space at logical addresses 0x0800 to 0x09FF.

512 words of internal RAM are mapped into data space at logical addresses 0xE800 to 0xE8FF. The same 512 words are also mapped into code space inside a larger block. The internal RAM at physical addresses 0x0000 to 0x03FF is mapped to logical addresses 0x8000 to 0x83FF in data space.

The main function of the memory management part of the application is to map both the internal flash and the internal RAM into both the data and code space address translators. This allows code to be executed from either of the physical memories. It also allows the processor to treat the code as data and perform reads and writes on memory from which code can also be executed. The operation of the code is as follows.

1. After initialisation, 512 words of flash memory at physical address 0x0400 are mapped into data space at logical address 0x0800. This effectively maps the eCOG’s data memory to the erase/write routine stored in the flash memory, and subsequent data reads at this address access the flash memory code.

2. The flash memory data space translator is enabled, allowing the software to access the internal flash as data memory.

3. The 0x130 words of code at logical data address 0x0800 (mapped to the routine code in flash) are copied to logical data address 0xE810 (which is mapped to 0x0010 in RAM as shown in figure 2). The code segment is now in RAM memory.

4. The code maps 1K words of RAM at the beginning of the physical RAM to the logical code address 0x8000. The routine (residing in RAM) is now mapped into the eCOG’s code space.

5. The RAM code address translators are then enabled and the routine is executed from 0x8010 in RAM. The logical code space defined by the RAM translator is also shared with the default flash mapping. Any accesses to this address range are now performed on the RAM due to the precedence of the two translators (see the eCOG1k User Manual for a full description).

28 January 2008 Cyan Technology Ltd. Page 9 of 22

Page 10: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

6 Requirements

The software that accompanies this application note (AN018SW.zip) is written to run under CyanIDE version 1.1. Both are freely available for download from www.cyantechnology.com. The main code listing is also given in Appendix B.

An eCOG1k development kit. The software described in this application note is based on the development kit, although the code could easily be adapted for use on any eCOG1k microcontroller application.

A full description of the internal flash memory is available in the eCOG1k User Manual, and some examples are given in application note AN001.

The application uses pre-defined programming cycles and timings; the exact programming sequence is given in Appendix A.

28 January 2008 Cyan Technology Ltd. Page 10 of 22

Page 11: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

7 Example Application

7.1 Installing and Compiling the Example Extract the software archive AN018SW.zip to the CyanIDE projects folder. Usually this is <C:\Documents and Settings\username\My Documents\CyanIDE Projects>). The project can then be loaded into CyanIDE by selecting Project->Open, navigating to this directory and selecting the project file flash_prg.cyp. To compile the application and run it immediately, either select Debug->Run or press the F5 key. Alternatively, the application can be compiled by selecting Build->Rebuild All without executing it immediately. The Build window in the CyanIDE environment should display the following results. Building flash_prg [Release] ecog1cfg evalboard.cfg -o temp/evalboard.asm -quiet ecogncc -quiet -DNDEBUG -I..\driver_lib -otemp/main.asm main.c main.c(72) : Warning 1 : <cast>: cast between function pointer and non-function object main.c: 1 warning, 0 errors. ecogncc -quiet -DNDEBUG -I..\driver_lib -otemp/flash_routine.asm flash_routine.c ecogcl -pack cstartup -map internal -DNDEBUG -I..\driver_lib -lib ..\driver_lib -o out/flash_prg -cmdfile temp/files.tmp out/flash_prg.xpv - 0 error(s), 0 warning(s) eCOG Compiler/Linker V1.1 (17 November 2004) (c) Cyan Technology Limited 2002, 2003, 2004 Processing command line files ... Processing library files ... Packing segments ... Final assembly ... NO ERRORS FOUND Generating ROMs ... Build finished.

7.2 Testing Wait a short while after running the code and then stop the software by selecting Debug->Stop from the menu or pressing Shift+F5. The entire flash memory should still be mapped into code space at address 0x0000, as this is the normal configuration of the MMU when running the application. To inspect the contents of the flash memory, open the memory window by selecting Debug->Windows->Memory from the menu or press Ctrl+5. This displays the memory window on the CyanIDE desktop as shown below. Change the memory view indicated by Region to CODE using the drop down menu as shown. Either manually scroll to address 0x003C00 (page 60 x 256 words) or enter the value 0x003C00 into the address box. The memory window should display the contents of this location. If the code has executed correctly then the value 0x9988 should be displayed in all of the locations between 0x003C00 to 0x003CFF of code space, as illustrated in Figure 2.

Figure 2. eCOG memory dump shown in CyanIDE

28 January 2008 Cyan Technology Ltd. Page 11 of 22

Page 12: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

8 Limitations

The flash erase/write routine used in the application software is based on the CPU running at 25MHz. As the flash erase/write timings and wait state calculations are hard coded in this routine, and have to be ensured by the user, different operating frequencies require these values to be recalculated. Failure to do this may result in erroneous operation and/or slow programming times. The following register values need to be set to ensure correct operation.

The write strobe pulse width for the flash memory is set via the fd.flash.prg_cfg.period field. The flash memory has a required programming time TW of 20µs. The flash prg_cfg period value, TPERIOD, is calculated from

1−⎟⎟⎠

⎞⎜⎜⎝

⎛=

CPU

WPERIOD T

TT

where TW is the flash program time (write strobe pulse width) and TCPU is the CPU clock period. Thus for a guaranteed write strobe pulse width of 20µs at a CPU clock frequency of 25MHz (TCPU = 40ns), TPERIOD should be set to a value of (20µs / 40ns) – 1 = 499 (=0x1F3).

Wait states for flash read accesses are programmed in the MMU flash control register, using the mmu.flash_ctrl.wait_states and mmu.flash_ctrl.early_req_en fields.

CPU clock frequency early_req_en wait_states FCPU < 5 MHz 1 0

5 MHz ≤ FCPU ≤ 10 MHz 0 0 10 MHz < FCPU 0 1

Table 2. Flash memory wait states

28 January 2008 Cyan Technology Ltd. Page 12 of 22

Page 13: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

Appendix A General Flash Erase/Write Procedures

A.1 Erase Process The user can either erase a single page of flash memory (Page Erase), or an entire block (Mass Erase), the two available blocks being the main flash memory block and the information block.

A.2 Page Erase The following procedure describes how to erase a single page of flash memory:

1. Write a non-zero value into the period field of the flash.prg_cfg register.

2. Set flash.prg_ctrl register to 0x2900. This value must be written to flash.prg_ctrl first to enable any flash erase operations.

3. Set the base address of the page to be erased in the flash.prg_adr register. Note - in the case of a page erase in the main Flash memory block the least significant 8 bits of this register are ignored when determining the page. When erasing a page in the information block the least significant 6 bits are ignored.

4. Set flash.prg_ctrl register to 0x2954 for the main memory block or 0x2974 for the information block.

5. Wait 5 us minimum.

6. Set flash.prg_ctrl register to 0x2955 for the main memory block or 0x2975 for the information block.

7. Wait 10 ms.

8. Set flash.prg_ctrl register to 0x2951 for the main memory block or 0x2971 for the information block.

9. Wait 5 us minimum

10. Set flash.prg_ctrl register to 0x2900 to complete the erase process.

11. Set flash.prg_ctrl register to 0x0000 to exit program mode.

A.3 Block Mass Erase Procedure The following procedure describes how to erase the entire contents of either the main block or both the main block and information block of the flash memory.

1. Write a non-zero value into the period field of the flash.prg_cfg register.

2. Set flash.prg_ctrl register to 0x2900. This value must be written to flash.prg_ctrl first to enable any flash erase operations.

3. Set flash.prg_ctrl register to 0x295C for the main memory block or 0x297C for both blocks.

4. Wait 5 us minimum.

5. Set flash.prg_ctrl register to 0x295D for the main memory block or 0x297D for both blocks.

6. Wait 210 ms.

7. Set flash.prg_ctrl register to 0x2959 for the main memory block or 0x2979 for both blocks.

8. Wait 5 us minimum

9. Set flash.prg_ctrl register to 0x2900 to complete the erase process.

10. Set flash.prg_ctrl register to 0x0000 to exit program mode.

28 January 2008 Cyan Technology Ltd. Page 13 of 22

Page 14: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

A.4 Programming Procedure Any location must be in the erased state prior to programming. The erased state for all bits within any word is '1'. The programming procedure can change a '1' to a '0', but cannot change a '0' to a '1'. This can only be done by an erase process.

A.5 Page Programming Procedure This is an example sequence for programming the Flash Memory:

1. First follow the Page Erase Procedure or Mass Erase Procedure for the page or block in question. Next perform the following sequence of writes to the flash.prg_ctrl register:

2. Set the word program time in the period field of the flash.prg_cfg register.

3. Set flash.prg_ctrl register to 0x2900 (enable program mode).

4. Set the start word address in the flash.prg_adr register.

5. Set flash.prg_ctrl register to 0x2992 for the main memory block or 0x29B2 for the information block.

6. Wait 5 us.

7. Set flash.prg_ctrl register to 0x2993 for the main memory block or 0x29B3 for the information block.

8. Wait 10 us.

9. Wait for the busy bit in register flash.prg_adr to go low ('0') indicating there is no write in progress.

10. Write the (next) data word to the flash.prg_data register.

11. Increment the word address and write it into the flash.prg_adr register.

12. If the least significant 5 bits of the flash.prg_adr are not 0x1F, repeat from step 9.

13. Set the last write bit in register flash.prg_cfg and write the last program data.

14. Wait for the busy bit to go low ('0') indicating the last write has completed.

15. Set flash.prg_ctrl register to 0x2991 for the main memory block or 0x29B1 for the information block.

16. Set flash.prg_ctrl register to 0x2900.

17. If there are more words to write, repeat from step 5.

18. Set flash.prg_ctrl register to 0x0000.

19. Exit program mode.

Care should be taken not to exceed a maximum duration of 4 ms for each page of 32 addresses for the main flash block, or each page of 16 addresses for the information block, before repeating the outer loop (points 5 to 17).

A.6 Word Programming Procedure It is not necessary to program a whole page at once, a number of words or a single word can be programmed on its own. To do this, repeat the Page Programming Procedure for the word(s) in question, but is not necessary to perform the loops for a whole page.

When programming a word in either the main flash block or the information block, the outer loop must be executed when the programming address crosses a 5 bit boundary, e.g. from 0x001F to 0x0020, or 0x345F to 0x3460.

28 January 2008 Cyan Technology Ltd. Page 14 of 22

Page 15: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

Appendix B Software Listings

B.1 main.c /*============================================================================= Cyan Technology Limited FILE - main.c DESCRIPTION Minimal main function Copies code segment from flash address to RAM and executes it CHANGE LOG 01/10/04 - Version 1.0 - Tony Ward Initial version modified from original generated by internal apps dept =============================================================================*/ #include <ecog.h> #include <ecog1.h> #include "driver_lib.h" extern void erase_program(void); int page; int buffer[256]; //Original Memory Map //code 0 77ff irom 0000 77ff erase_program routine physical address H'400 of flash //data 0 7ff irom 7800 7fff //data e800 efff iram 0 7ff typedef void(*func_ptr)(void); func_ptr ptr_fon; int main(int argc, char* argv[]) { int aux; /* Source address in logical RAM from where the routine will be copied */ int* src_add_ptr = (int *)(0x0800) ; int* dest_add_ptr; /* Destination address variable */ /* Set up the system clocks */ ssm_cpu_clk(SSM_HIGH_PLL, 6, 7); ssm_tmr_clk(SSM_HIGH_REF, 0); /* Set up the flash write variables */ page = 60; /* Page within flash */ for (aux=0; aux<256; aux++) { buffer[aux]=0x9988 ; /* Fill flash write buffer */ } /* Set up the MMU to map physical flash 0x0400 to logical data 0x0800 */ rg.mmu.flash_data_log = 0x0008; /* Logical data address 0x0800 */ rg.mmu.flash_data_phy = 0x0004; /* Physical flash address (of routine) 0x0400 */ rg.mmu.flash_data_size = 0x01; /* 512 words of flash */ rg.mmu.translate_en = 0x0010; /* Only flash data translation enabled */ /* Copy routine mapped to logical RAM to destination address (in RAM) */ dest_add_ptr = (int *)(0xe810); /* Destination address in logical RAM */ for (aux=0; aux<0x0130; aux++) { /* Routine size H'0130 */ *dest_add_ptr++ = *src_add_ptr++; } /* Remap the routines destination address to code space, and execute from RAM */ rg.mmu.translate_en = 0x0000; /* Disable RAM mapping for code area */ rg.mmu.ram_code_log = 0x0080; /* Logical code address 0x8000 */ rg.mmu.ram_code_phy = 0x0000; /* Physical RAM address 0 */ rg.mmu.ram_code_size = 0x03; /* 1K words of RAM */ rg.mmu.translate_en = 0x0002; /* Enable RAM mapping for code area */ ptr_fon = (func_ptr)0x8010; ptr_fon(); /* Execute the routine */ return 0; /* Break here after execution, then examine 0x3c00 in code space */ }

28 January 2008 Cyan Technology Ltd. Page 15 of 22

Page 16: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

B.2 flash_routine.c /*============================================================================= Cyan Technology Limited FILE - flash_routine.c DESCRIPTION Performs flash memory erase and write with user specified data CHANGE LOG 01/10/04 - Version 1.0 - Tony Ward Initial version modified from original generated by internal apps dept. =============================================================================*/ #include <ecog.h> #include <ecog1.h> #include "driver_lib.h" extern int page; /* Variables shared with main.c */ extern int buffer[256]; /* Defines the location of the following code in memory */ #pragma code_segment ERASE_PROGRAM void erase_program(void) { int* data = &buffer[0]; int usec_count ; /* variables required for timing delays */ int usec_ripple ; int msec_count ; int msec_ripple ; int count; int row_address = page << 3 ; /* Flash access parameters */ int adr = page << 8; int word_count ; int row_count ; msec_count = 1100; msec_ripple = 0; usec_count = 2 ; usec_ripple = 0 ; /************************************************************************* * Begin Erase procedure */ /* Need a non-zero value in here, defines the access time in ticks */ fd.flash.prg_cfg.period = 0x1f3 ; /* Enable erase/write, no command */ rg.flash.prg_ctrl = 0x2900 ; /* Set the address for the flash erase/write */ rg.flash.prg_adr = row_address << 5 ; /* Set the page erase command */ /* Enable erase_op, xe and erase signals */ rg.flash.prg_ctrl = 0x2954 ; /* This loop generates a 5us delay */ fd.ssm.tap_sel3.tmr = usec_ripple; for ( count = 0 ; count < 5 ; count++ ) { rg.tim.tmr_ld = usec_count ; rg.tim.cmd = TIM_CMD_TMR_LD_MASK; rg.tim.ctrl_en = TIM_CTRL_EN_TMR_CNT_MASK; while ( rg.tim.tmr_cnt ) ; rg.tim.ctrl_dis = TIM_CTRL_DIS_TMR_CNT_MASK; } /* Enable the nvstr signal */ rg.flash.prg_ctrl = 0x2955 ; /* This loop generates a 10ms delay */

28 January 2008 Cyan Technology Ltd. Page 16 of 22

Page 17: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

fd.ssm.tap_sel3.tmr = msec_ripple ; for ( count = 0 ; count < 10 ; count++ ) { rg.tim.tmr_ld = msec_count ; rg.tim.cmd = TIM_CMD_TMR_LD_MASK; rg.tim.ctrl_en = TIM_CTRL_EN_TMR_CNT_MASK; while ( rg.tim.tmr_cnt ) ; rg.tim.ctrl_dis = TIM_CTRL_DIS_TMR_CNT_MASK; } /* Remove the erase signal */ rg.flash.prg_ctrl = 0x2951 ; /* This loop generates a 5us delay */ fd.ssm.tap_sel3.tmr = usec_ripple; for ( count = 0 ; count < 5 ; count++ ) { rg.tim.tmr_ld = usec_count ; rg.tim.cmd = TIM_CMD_TMR_LD_MASK; rg.tim.ctrl_en = TIM_CTRL_EN_TMR_CNT_MASK; while ( rg.tim.tmr_cnt ) ; rg.tim.ctrl_dis = TIM_CTRL_DIS_TMR_CNT_MASK; } /* Remove all control signals */ rg.flash.prg_ctrl = 0x2900 ; /* Disable the flash memory */ rg.flash.prg_ctrl = 0x0000 ; /************************************************************************* * End Erase procedure */ /************************************************************************* * Begin Write procedure */ /* This register is used to control the write period for the Flash memory. * The write period is (register+1) multiplied by the CPU period. The * write period must be between 20 and 40 micro seconds. The closer we get * to 20 micro seconds the faster the programming will be. * * Register CPU Freq Write Period * ------------------------------------ * 0x1F3 25 MHz 20 us * 0x1F3 12.5 MHz 40 us */ fd.flash.prg_cfg.period = 0x1f3 ; /* Enable the flash memory */ rg.flash.prg_ctrl = 0x2900 ; /* The following code is responsible for programming data * Programming is carried out in rows of 32 words, for a page this is 8 rows */ for ( row_count = 0 ; row_count < 8 ; row_count++ ) { /* Set the programming address */ rg.flash.prg_adr = adr; /* Set the flash control to write mode */ /* enable program_op, xe and prog */ rg.flash.prg_ctrl = 0x2992 ; /* Wait 5us */ fd.ssm.tap_sel3.tmr = usec_ripple; for ( count = 0 ; count < 5 ; count++ ) { rg.tim.tmr_ld = usec_count ; rg.tim.cmd = TIM_CMD_TMR_LD_MASK; rg.tim.ctrl_en = TIM_CTRL_EN_TMR_CNT_MASK; while ( rg.tim.tmr_cnt ) ; rg.tim.ctrl_dis = TIM_CTRL_DIS_TMR_CNT_MASK; } /* Enable nvstr */

28 January 2008 Cyan Technology Ltd. Page 17 of 22

Page 18: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

rg.flash.prg_ctrl = 0x2993 ; /* Wait 10us */ fd.ssm.tap_sel3.tmr = usec_ripple; for ( count = 0 ; count < 10 ; count++ ) { rg.tim.tmr_ld = usec_count ; rg.tim.cmd = TIM_CMD_TMR_LD_MASK; rg.tim.ctrl_en = TIM_CTRL_EN_TMR_CNT_MASK; while ( rg.tim.tmr_cnt ) ; rg.tim.ctrl_dis = TIM_CTRL_DIS_TMR_CNT_MASK; } /* Allows controller to indicate data has been captured */ fd.flash.prg_cfg.last_wr = 0 ; /* Loop to program data, 32 words */ for ( word_count = 0 ; word_count < 32 ; word_count++ ) { /* Set last write flag if necessary */ if ( 31 == word_count ) fd.flash.prg_cfg.last_wr = 1 ; /* Set address and data */ rg.flash.prg_adr = adr; rg.flash.prg_data = *data++ ; /* Wait for programming to complete */ while ( fd.flash.prg_adr.bsy ) ; /* Increment programming address */ adr++; } /* Remove prog signal */ rg.flash.prg_ctrl = 0x2991 ; /* Remove all control signals */ rg.flash.prg_ctrl = 0x2900 ; } /* Disable the flash memory */ rg.flash.prg_ctrl = 0x0000 ; /************************************************************************* * End Write procedure */ }

28 January 2008 Cyan Technology Ltd. Page 18 of 22

Page 19: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

B.3 cstartup.asm ;============================================================================== ; Cyan Technology Ltd ; ; FILE ; cstartup.asm - Assembler startup for C programs. ; ; DESCRIPTION ; Defines C segments. Contains initial code called before C is started ;============================================================================== MODULE cstartup .ALL ; ; C reserves DATA address 0 for the NULL pointer. The value H'DEAD is put in ; here so that it is easier to spot the effect of a NULL pointer during ; debugging. User memory for constants grows upwards from H'0001. The first ; address is given the equate symbol $??LO_ADDR. ; .SEG C_RESERVED1 ORG 0 dc H'DEAD $??LO_ADDR EQU $ ; ; DATA addresses H'EFE0-H'EFFF are used for scratchpad RAM in interrupt mode. ; DATA addresses H'EFC0-H'EFDF are used for scratchpad RAM in user mode. ; DATA addresses H'EFB8-H'EFBF are used for register storage in interrupt mode. ; Then follows the interrupt stack, user stack and user heap. ; User memory for variables grows downwards from the end of the user stack. ; This version of cstartup only contains one area of scratchpad RAM ; which constrains users not to write re-entrant re-interruptable ; code. ; The interrupt stack must start at IY-38 to be compatible with the C compiler. ; .SEG C_RESERVED2 ORG H'EFB8 $??HI_ADDR DEQU $ ds 8 ; Interrupt register storage ds 32 ; User Scratchpad IY_SCRATCH DEQU $ $?irq_scratchpad? DEQU $ ds 32 ; Interrupt Scratchpad ; ; The registers that control the functional blocks of the eCOG1 are located ; at addresses H'FEA0 to H'FFCF. The C header file <ecog1.h> declares an ; external structure that descibes the registers. This variable is defined ; below. ; .SEG REGISTERS ORG H'FEA0 $fd: $rg ds 304 ; ; C requires the following segments: ; CONST - Constants in ROM. For example: ; const char c = 'c' ; ; printf( "Hello World!" ) ; ; VAR - Variables in RAM. These are set to zero by the cstartup code. ; For example: ; int i ; (in file scope) ; static int i ; (in function scope) ; INIT - Initialisd variables in RAM. For example: ; int i = 9 ; (in file scope) ; static int i = 9 ; (in function scope) ; INITC - Initialisation data for the INIT segment ; HEAP - The heap. Required if malloc() etc. are used. ; STACK - The stack. Always required. ; ; The memory allocated to each segment is defined by the value of

28 January 2008 Cyan Technology Ltd. Page 19 of 22

Page 20: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

; $??<segment_name>_SIZE as set below. These sizes can be set manually or, if ; the appropriate line is tagged with !PACK and the -pack option is specified ; to ECOGCL, ECOGCL will write in the size actually required for the segment. ; The sizes of the STACK and HEAP segments must be set by the user. ; $??ISTACK_SIZE = H'0040 $??STACK_SIZE = H'0100 $??HEAP_SIZE = H'0080 ; ROM segments $??INITC_SIZE = h'0000 ; !PACK $??CONST_SIZE = h'0002 ; !PACK ; RAM segments $??INIT_SIZE = h'0000 ; !PACK $??VAR_SIZE = h'0104 ; !PACK ; -- Locate DATA segments in memory -- ; ; Segments are allocated sequentially by the ??ALLOCATE macro. They may be ; set at fixed addresses by setting ADDR prior to calling ??ALLOCATE. ; ??ALLOCATE MACRO seg .SEG &seg ORG ADDR $??&seg!_LO = ADDR ADDR = ADDR + $??&seg!_SIZE $??&seg!_HI = ADDR-1 ENDMAC ; Allocate DATA ROM ADDR = $??LO_ADDR ??ALLOCATE INITC ??ALLOCATE CONST ; Allocate DATA RAM ADDR = $??HI_ADDR - $??VAR_SIZE - $??INIT_SIZE ADDR = ADDR - $??ISTACK_SIZE - $??STACK_SIZE - $??HEAP_SIZE ??ALLOCATE INIT ??ALLOCATE VAR ??ALLOCATE HEAP ??ALLOCATE STACK ??ALLOCATE ISTACK ; -- Memory initialisation macros -- ; ; Segments may be initialised by filling with a constant value using the ; ??SEGFILL macro. Two symbols are passed, the segment name and the value to ; fill with. A third symbol (the size) is assumed. ; ??SEGFILL MACRO seg, value LOCAL fill_loop IF $??&seg!_SIZE ld x, #$??&seg ld al, #$??&seg!_SIZE ld ah, &value &fill_loop: st ah, @(0,x) add x, #1 sub al, #1 bne &fill_loop ENDIF ENDMAC ; ; Segments may be initialised by copying an initialisation segment with ; the ??SEGCOPY macro. Two symbols are passed, the source and destination ; segment names. ; ??SEGCOPY MACRO src, dest IF $??&src!_SIZE NE $??&dest!_SIZE .ERR "Copy segments different sizes" ENDIF IF $??&src!_SIZE ld x, #$??&src ld y, #$??&dest ld al, #$??&src!_SIZE bc

28 January 2008 Cyan Technology Ltd. Page 20 of 22

Page 21: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

ENDIF ENDMAC ; ; Fills a block of memory with a value. Three values are passed, the start ; address for the block, the number of addresses to write to and the value ; to be written. ; ??MEMFILL MACRO start, length, value LOCAL fill_loop ld x, &start ld al, &length ld ah, &value &fill_loop: st ah, @(0,x) add x, #1 sub al, #1 bne &fill_loop ENDMAC ; ; Input argument for main(). ; .SEG CONST argv dc 0,0 ; NULL as two-word byte address ; ; Start of Code. ; .CODE ORG H'40 $?cstart_code: bra $ecog1ConfigMMU ; configure MMU and Cache Banks $ecog1ConfigContinue: ; ; Initialise segments. The HEAP and STACK are filled with H'9999 and H'aaaa ; respectively so that their maximum runtime extents can be checked. The ; INIT segment is set from the ROM initialisers in the INITC segment. The non ; initialised RAM segment VAR is set to zero (compiler puts 0 initialised ; variables in these segments as well as uninitialised ones,x). ; ??SEGFILL HEAP, #h'9999 ??SEGFILL STACK, #h'AAAA ??SEGFILL ISTACK, #h'BBBB ??SEGCOPY INITC, INIT ??SEGFILL VAR, #h'0 ; Set interrupt stack pointer. ld y, #IY_SCRATCH ; Set user mode flag to allow interupts. st flags, @(-1,y) ld al, @(-1,y) or al, #h'10 st al, @(-1,y) ld flags, @(-1,y) ; Set usermode stack pointer ld y, #$??STACK_HI ; Call ecog1Config to setup eCOG1 peripherals ; Defined in module produced by configuration compiler bsr $ecog1Config ; Call main, setting argc and argv[0] to 0. ld ah, #argv ld al, #0 bsr $main ; ; Main may exit by returning or by explicitly calling $exit. In either case ; exit code will be in AL. ; $exit:

28 January 2008 Cyan Technology Ltd. Page 21 of 22

Page 22: eCOG1k Writing Data to Flash Memory

AN018 eCOG1k Writing Data to Flash Memory Version 1.2

28 January 2008 Cyan Technology Ltd. Page 22 of 22

brk ; Alert the user if in debug mode bra 0 ; Restart ; ; This is the minimal interrupt routine. The contents of FLAGS is restored ; as the program counter is restored using rti. ; $minimal_handler: st flags,@(-33,y) ; Store Flags st al, @(-34,y) ; Store AL ld al, @(-33,y) ; Put Flags into AL or al, #h'0010 ; Set usermode st al, @(-33,y) ; Store the value to be restored to Flags brk ; Alert the user if in debug mode ld al, @(-34,y) ; Restore AL rti @(-33,y) ; Restore PC and Flags ; ; The address exception can happen often during development. A handler ; is put here to catch the exception. ; $address_error: st flags,@(-33,y) ; Store Flags st al, @(-34,y) ; Store AL ld al, @(-33,y) ; Put Flags into AL or al, #h'0010 ; Set usermode st al, @(-33,y) ; Store the value to be restored to Flags brk ; Alert the user if in debug mode ld al, #h'a st al, @h'ff69 ; Clear status in mmu.address_exception ld al, #h'200 st al, @h'ff7a ; Clear status in emi.ctrl_sts ld al, @(-34,y) ; Restore AL rti @(-33,y) ; Restore PC and Flags ; End of startup code $??CSTARTUP_END EQU $ ; Define address of flash write routine .CSEG ERASE_PROGRAM ORG H'0400 ENDMOD