Forum Discussion

Altera_Forum's avatar
Altera_Forum
Icon for Honored Contributor rankHonored Contributor
16 years ago

Programming the ID number for Cyclone II

Hi there! I wonder if we could program our special ID number into the FPGA without changing this number in the project? Can I do it, for example, with the help of USB-Blaster or QII or Nios? We don't want to put this number in the project & compile for many times for the different FPGA. So I'm trying to find the easiest way for resolving...

Does anybody try to do it in many ways, ah?

8 Replies

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Usually ID and serial numbers are programmed in a special sector in the flash memory, and can be read by the FPGA when needed.

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    No ... I meant that I do want program the number (my device's address) but not changing this number in VHDL-code, but somehow else! And the matter is how can I do it in the right and easy way! TIA!

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    You don't need to change the VHDL code to change the data in the flash. Depending on how the flash memory is connected to your board, you can write your number just after you've programmed the flash with the FPGA configuration.

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Oh, sorry, the second time I didn't explain correctly ... I don't want yo install to my board an extra flash/eeprom device, I mean the other way of giving ID number for FPGA Cyclone II maybe by Quartus Software or Nios or somehow else ...

    The purpose is to give for our board a special number, the same number as FPGA and this number will be the address of the network. Now is it clear?

    Tusen takk, Daixiwen.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Don't you have any configuration device on your board? How do you configure the FPGA on power up?

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Sure I use EPCS4!!! So, you advise to load this number to EPCS4? But which sector? And how will the FPGA know from where take this number?

  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    I usually use the last page of the configuration flash, as it is done in some of Altera's design examples.

    If you have a Nios cpu with an epcs controller core, you can use the API provided with the driver to find the number of pages and read/write the last one.
  • Altera_Forum's avatar
    Altera_Forum
    Icon for Honored Contributor rankHonored Contributor

    Here is the code I use to store configuration information in the flash.

    Just define a C structure called FlashConfigStruct that holds all your configuration parameters. It must contain an unsigned int called Magic, and you should define a constant called FLASH_MAGIC containing any value you want.

    The routine will use this to report if it read a valid configuration or not.

    
    # include "sys/alt_flash.h"
    # include "system.h"
    FlashConfigStruct FlashConfig;
    int DoReadFlash()
    {
        alt_flash_fd* Fd;
        flash_region* Regions;
        unsigned int NumberOfRegions;
        unsigned char *Buffer;
        
        Fd = alt_flash_open_dev(EPCS_FLASH_CONTROLLER_NAME);
        if (!Fd)
        {
            printf("Flash not found\n");
            return 0;
        }
        if (alt_get_flash_info(Fd, &Regions, (int*) &NumberOfRegions) != 0)
        {
            // error while retreiving the flash information
            printf("Couldn't retreive flash information\n");
            alt_flash_close_dev(Fd);
            return 0;
        }            
        // allocate a bloc
        Buffer = malloc(Regions->block_size);
        if (!Buffer)
        {
            printf("Not enough memory\n");
            alt_flash_close_dev(Fd);
            return 0;
        }        
        
        // read flash last block
        if (alt_read_flash(Fd,
            Regions->offset+(Regions->number_of_blocks-1)*Regions->block_size,
            Buffer, Regions->block_size))
        {
            printf("Error while reading flash block\n");
            free(Buffer);
            alt_flash_close_dev(Fd);
            return 0;        
        }
        
        // copy into the structure
        memcpy(&FlashConfig,Buffer,sizeof(FlashConfigStruct));
        free(Buffer);
        alt_flash_close_dev(Fd);
        
        // check block contents
        if (FlashConfig.Magic != FLASH_MAGIC)
        {
            printf("Flash contents invalid\n");
            return 0;
        }
        
        return -1;          
    }
    void ReadFlash()
    {
        if (!DoReadFlash())
        {
            printf("Taking default configuration.\n");
            
            FlashConfig.Magic=FLASH_MAGIC;
    // fill here the other members of FlashConfig with defaults values
        }
    }
    int WriteFlash()
    {
        alt_flash_fd* Fd;
        flash_region* Regions;
        unsigned int NumberOfRegions;
        unsigned char *Buffer;
        
        Fd = alt_flash_open_dev(EPCS_FLASH_CONTROLLER_NAME);
        if (!Fd)
        {
            printf("Flash not found\n");
            return 0;
        }
        if (alt_get_flash_info(Fd, &Regions, (int*) &NumberOfRegions) != 0)
        {
            // error while retreiving the flash information
            printf("Couldn't retreive flash information\n");
            alt_flash_close_dev(Fd);
            return 0;
        }            
        // allocate a bloc
        Buffer = calloc(Regions->block_size,1);
        if (!Buffer)
        {
            printf("Not enough memory\n");
            alt_flash_close_dev(Fd);
            return 0;
        }        
        // copy into the buffer
        memcpy(Buffer,&FlashConfig,sizeof(FlashConfigStruct));
        
        // write flash last block
        if (alt_write_flash(Fd,
            Regions->offset+(Regions->number_of_blocks-1)*Regions->block_size,
            Buffer, Regions->block_size))
        {
            printf("Error while writing flash block\n");
            free(Buffer);
            alt_flash_close_dev(Fd);
            return 0;        
        }
        
        free(Buffer);
        alt_flash_close_dev(Fd);
        
        return -1;          
    }
    

    Call ReadFlash() from your application init, and WriteFlash when you updated the FlashConfig structure and want to store it to flash.

    The code will use the last block of the first region. Every EPCS I encountered until now has only one region, so the block used is the last one in the flash.