CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to CCS Technical Support

Flash write and read functions - 16F15323 or 324

 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
Dimi Island



Joined: 05 Mar 2021
Posts: 2
Location: Brazil

View user's profile Send private message Visit poster's website

Flash write and read functions - 16F15323 or 324
PostPosted: Fri Mar 05, 2021 11:49 am     Reply with quote

Hello,
I'm using PIC16F15323 with the CCS PCM compiler version 5.075 and I would like to write and read a value from your flash saved at any address, similar to the use of an EEPROM.
I found this topic similar to my need:
https://www.ccsinfo.com/forum/viewtopic.php?t=54707
It was answered in 2006 by Ttelmah.
I made some small adaptations to the code to see if it ran on my device, but without success.
Follow my sheets:

Main.c
Code:

#include "main.h"
#include "16F15323_flash.h"
/*
#include <16f526.h>
#device ADC=8
#device *=8
#fuses INTRC,NOWDT,NOMCLR
#use delay(clock=8000000)
*/
#use rs232 (XMIT=PIN_B0, baud=9600) //simple output for debugging

/*
Ttelmah say:
Simple test program to demonstrate the internal data flash
#include "526flash.h" //code to access this memory
Now key to understand with this memory, is that when erased all the bits
are'1'. A write can change a bit from '1' to '0', but cannot change a bit from
'0' to '1'. To change a bit to '1', the row has to be erased. So if when
writing a value, a bit needs to change to '1', the page containing the byte
has to be erased first. This means all the other bytes in this page, need to
be read, and then the whole page written back.
I've 'encapsulated' this in a routine that checks which way the bits have
to change and automatically performs the read and erase if needed.
This is 'write_as_eeprom'. Notes in the include file.
*/

void main()
{
   int8 temp;

   SETUP_ADC(ADC_OFF);
   SETUP_ADC_PORTS(NO_ANALOGS);
   setup_comparator(NC_NC_NC_NC);

   //Minimum test program
   //This will store a byte, then read it, but then write a second byte to the
   //same page, then write to this location a second time, requiring bits to
   //be set, and then read the both locations and verify the erase/'auto save'
   //has worked.
   write_as_eeprom(0,0xAA); //write a byte
   temp=read_byte_flash(0); //read it
   printf("Byte at zero %2x\n\r",temp); //diagnostic
   write_as_eeprom(1,0x50); //now write to address 1
   //second write forcing an erase..
   write_as_eeprom(1,0x55); //Needs two bits in the low nibble set to '1'
   //so the page has to erase if it is to work...
   temp=read_byte_flash(0); //now check if byte 0 is still OK
   printf("Byte at zero %2x\n\r",temp); //diagnostic byte 0
   temp=read_byte_flash(1); //and do the same for byte 1
   printf("Byte at one %2x\n\r",temp); //diagnostic byte 1
 
   while (TRUE)
   {
      //stop and do nothing else
   }
}


Main.h
Code:

#include <16F15323.h>
#device ADC=10

#FUSES RSTOSC_EXT               //On Power-up clock running from External Oscillator
#FUSES NOCLKOUT                 //I/O function on OSC2
#FUSES CKS                      //Clock Switching Enabled
#FUSES FCMEN                    //Fail-safe clock monitor enabled
#FUSES MCLR                     //Master Clear pin enabled
#FUSES NOPUT                    //No Power Up Timer
#FUSES NOLPBOR                  //Low-Power Brownout reset is disabled
#FUSES NOBROWNOUT               //No brownout reset
#FUSES BORV24                   //Brownout reset at 2.4V
#FUSES ZCDDIS                   //Zero-cross detect circuit is disabled at POR
#FUSES PPS1WAY                  //Allows only one reconfiguration of peripheral pins
#FUSES STVREN                   //Stack full/underflow will cause reset
#FUSES WDTSW                    //Watch Dog Timer Postscale settable in software
#FUSES WDTWIN_SW                //Watchdog Window is settable in software
#FUSES WDTCLK_SW                //WDT clock source settable in software
#FUSES BBSIZ512                 //Boot block size 512 bytes
#FUSES NOBOOTBLOCK           
#FUSES SAF                   
#FUSES NOWRT                    //Program memory not write protected
#FUSES NOWRTB                   //Boot block not write protected
#FUSES NOWRTC                   //Configuration registers not write protected
#FUSES NOWRTSAF             
#FUSES NOLVP                    //No low voltage prgming, B3(PIC16) or B5(PIC18) used for I/O
#FUSES NOPROTECT                //Code not protected from reading

#device ICD=TRUE
#use delay(internal=1MHz)


16F15323_flash.h
Code:

#byte EEADR=getenv("SFR:EEADR")
#byte EECON=getenv("SFR:EECON")
#byte EEDATA=getenv("SFR:EEDATA") //EE registers
#bit RD=getenv("BIT:RD")
#bit WR=getenv("BIT:WR")
#bit FREE=getenv("BIT:FREE")
#bit WREN=getenv("BIT:WREN") //EE control bits
//The 'flash data memory' on this chip behaves like a sort of hybrid between
//flash program memory, and EEPROM. The erase size if just 8bytes (so not
//a terribly large 'page', and the control only has a simple 'unlock' sequence

//Implements four routines:
// write_byte_flash(address, value) - writes 'value' to 'address'
// read_byte_flash(address) - returns the byte at 'address'
// erase_row_flash(address) - erases the eight byte row containing 'address'
// write_as_eeprom(address, value) - this is the complex one
//it reads the byte at 'address' and if bits only have to turn 'off' (1->0)
//simply writes the byte. If however any bit has to turn 'on', this cannot
//be done without erasing the page. In this case it reads the whole page
//into a RAM buffer, erases the page, changes the one byte needed, and
//writes the page back. Allows the data flash to be 'written' as if it was
//EEPROM (hence the name), and will not erase if it is not required to do so.

void write_byte_flash(unsigned int8 address, unsigned int8 value)
{
   //write a single byte to an address. This does not erase, so a bit cannot
   //be set to '1' by this routine.
   EEADR=address; //select address
   EEDATA=value; //data to write
   WREN=TRUE; //trigger a write
   WR=TRUE;
}

unsigned int8 read_byte_flash(unsigned int8 address)
{
   //read a single byte from the flash
   unsigned int8 temp;
   EEADR=address; //select address
   RD=TRUE; //trigger a read
   temp=EEDATA;
   return temp;
}

void erase_row_flash(unsigned int8 address)
{
   //The erase uses the top three bits of the specified address as the page to erase
   EEADR=address; //select address
   FREE=TRUE;
   WREN=TRUE;
   WR=TRUE; //trigger the erase
}

//
void write_as_eeprom(unsigned int8 address, unsigned int8 value)
{
   //this allows a single byte to be written to any address and automatically
   //erases if necessary.
   unsigned int8 low3; //low 3 bits of address
   unsigned int8 buffer[8];
   unsigned int8 temp;
   low3=address&7; //index into the buffer
   //Now I need to determine if the row has to be erased.
   
   buffer[0]=read_byte_flash(address);
   //Now if writing the byte would only set bits to zero, an erase is not needed
   if ((value & buffer[0]) == value)
   {
      //Just write
      write_byte_flash(address,value);
      return;
   }
   //otherwise we need to erase the row.
   //First read the row.
   for (temp=0;temp<8;temp++)
   {
      buffer[temp]=read_byte_flash((address&0x38)+temp);
   }
   //Now update the byte to change
   buffer[low3]=value;
   //erase the row
   erase_row_flash(address);
   //and write back all eight bytes
   for (temp=0;temp<8;temp++)
   {
      write_byte_flash((address&0x38)+temp, buffer[temp]);
   }
}


Follows errors generated when compiling:
Code:

Compiling E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\main on 05-mar-21 at 14:23
*** Error 28 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 2(31,32): Expecting an identifier  Bad SFR name
*** Error 12 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 3(2,6): Undefined identifier
*** Error 48 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 3(7,12): Expecting a (
*** Error 28 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 3(31,32): Expecting an identifier  Bad SFR name
*** Error 48 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 4(2,6): Expecting a (
*** Error 48 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 4(7,13): Expecting a (
*** Error 28 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 4(33,34): Expecting an identifier  Bad SFR name
*** Error 48 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 5(2,5): Expecting a (
*** Error 48 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 5(6,8): Expecting a (
*** Error 43 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 5(24,25): Expecting a declaration
*** Error 43 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 5(0,1): Expecting a declaration
*** Error 12 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 29(4,9): Undefined identifier   EEADR
*** Error 12 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 30(4,10): Undefined identifier   EEDATA
*** Error 12 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 39(4,9): Undefined identifier   EEADR
*** Error 12 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 40(4,6): Undefined identifier   RD
*** Error 12 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 41(9,15): Undefined identifier   EEDATA
*** Error 12 "E:\Trabalho\Cursos\12 - Pic e Flash memory\CCS_simula_flash_16F15323\16F15323_flash.h" Line 48(4,9): Undefined identifier   EEADR
*** Error 100 "main.c" Line 9(5,66): USE parameter value is out of range   Not a number: PIN_B0
*** Error 132 "main.c" Line 40(34,38): STDOUT not defined (may be missing #USE RS232)  ::
*** Error 132 "main.c" Line 46(34,38): STDOUT not defined (may be missing #USE RS232)  ::
*** Error 132 "main.c" Line 48(33,37): STDOUT not defined (may be missing #USE RS232)  ::
      21 Errors,  0 Warnings.
Build Failed.


I understand that the datasheet says that access to flash memory from this pic is indirect using FSR. But how do I do that?
Could you please help me Ttelmah? Very Happy
Thank you very much for your valuable help.
_________________
Dimi Island
Brazil
Ttelmah



Joined: 11 Mar 2010
Posts: 19561

View user's profile Send private message

PostPosted: Fri Mar 05, 2021 12:18 pm     Reply with quote

Unfortunately your chip is not at all similar to the one I wrote that for.
The flash page on your chip is 64 bytes long, not 8 bytes, and the read
and write access uses different registers.
On your chip the CCS functions should work. The code you found was
specific for the rather unusual flash access on the 526.
The same potential 'trick could be used of not erasing if bits only have to
be set to zero.
You'd need to read a whole 64 byte page, change just the byte you want,
and write the whole page back.
The supplied read_program_memory and write_program_memory
functions will do the whole thing. The write needs to be done to a page
boundary, then the write will perform an erase. You need to look at
13.3.5 in the data sheet which outlines the procedure needed.
Dimi Island



Joined: 05 Mar 2021
Posts: 2
Location: Brazil

View user's profile Send private message Visit poster's website

PostPosted: Fri Mar 12, 2021 12:35 pm     Reply with quote

Thank you very much by your response.
It's work now.
I don't see the 13.3.5 only 4.0 Memory Organization.
I'm hep Very Happy
_________________
Dimi Island
Brazil
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Page 1 of 1

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group