TODOPIC

Otros Microcontroladores / Dispositivos programables => Microcontroladores ARM => Mensaje iniciado por: juaperser1 en 02 de Septiembre de 2018, 11:32:46

Título: error de flash en atmel sam
Publicado por: juaperser1 en 02 de Septiembre de 2018, 11:32:46
Buenas a ver si alguien puede arrojarme luz sobre lo que esta pasando.

Tengo una aplicación que funciona perfectamente en un atmel sam s70, el problema viene al insertarle la funcionalidad de la memoria flash.
utilizo el ejemplo de flash que viene sin cambiar nada (ya lo he probado todo):

Código: [Seleccionar]
static uint8_t src_data[IFLASH_PAGE_SIZE];
static uint8_t chk_data[IFLASH_PAGE_SIZE];

/**
 * Example of using FLASH_0 to read and write buffer.
 */
void FLASH_0_example(void)
{
uint32_t page_size;
uint16_t i;

/* Init source data */
page_size = flash_get_page_size(&FLASH_0);

for (i = 0; i < page_size; i++) {
src_data[i] = i;
}

/* Write data to flash */
flash_write(&FLASH_0, 0x3200, src_data, page_size);

/* Read data from flash */
flash_read(&FLASH_0, 0x3200, chk_data, page_size);
}


La memoria flash funciona correctamente, es decir, graba y lee sin problemas, pero al ejecutar la funcion flash_write, el resto de la aplicacion deja de funcionar, creo que son las interrupciones, que dejan de funcionar, el programa poco despues de ejecutar la instrucción flash_write me lleva a :

Citar
/**
 * \brief Default interrupt handler for unused IRQs.
 */
void Dummy_Handler(void)
{
        while (1) { }
}

y el callstack no me sirve de nada ya que esta "dummy_handler" salta a modo de interrupción desde otra parte del programa que no tiene nada que ver.

alguien sabe que puede estar pasando?

he probado ha habilitar de nuevo las interrupciones pero parece que no funciona, la lectura no produce ningun error
Título: Re:error de flash en atmel sam
Publicado por: KILLERJC en 02 de Septiembre de 2018, 12:08:49
Siempre y cuando no este definida la interrupcion, tiene un weak alias a Dummy_Handler.

Es decir si vos definis la funcion de interrupcion utiliza la tuya, sino utiliza la Dummy_Handler.
El tema es que TODAS las demas interrupciones no definidas van al Dummy_Handler.

Debo imaginar entonces que pueden ocurrir 2 cosas.

- Alguna interrupcion que no debe ser activada, se activo
- Algun problema en la grabacion ocurrio, ya sea por mala alineacion, etc.

Mi primer paso seria tratar de determinar CUAL interrupcion ocurrio. Y para eso tenes la funcion _get_IPRS

https://www.keil.com/pack/doc/cmsis/Core/html/group__Core__Register__gr.html#ga2c32fc5c7f8f07fb3d436c6f6fe4e8c8

Citar
uint32_t __get_IPSR   (   void       )   

The function reads the Interrupt Program Status Register (IPSR) using the instruction MRS.

The ISPR contains the exception type number of the current Interrupt Service Routine (ISR). Each exception has an assocciated unique IRQn number. The following bits are used:

ISR_NUMBER (IPSR[8:0])
=0 Thread mode
=1 Reserved
=2 NMI
=3 HardFault
=4 MemManage
=5 BusFault
=6 UsageFault
=7-10 Reserved
=11 SVCall
=12 Reserved for Debug
=13 Reserved
=14 PendSV
=15 SysTick
=16 IRQ0
...
=n+15 IRQ(n-1)

Returns
ISPR register value

Remarks
This register is read-only.

Asi que como primer paso haria un codigo asi:

Código: C
  1. uint32_t phantomISR = 9999;
  2.  
  3. void Dummy_Handler(void)
  4. {
  5.     while(1) {
  6.         phantomISR = __get_IPSR();
  7.     }
  8. }

En tu startup .c, asi determinar desde donde ocurre la interrupcion. ( Para no definir 1 funcion para cada vector de ISR)

Luego de determinar desde donde viene esa interrupcion:
- Si es una interrupcion que no deberia haberse activado, entonces buscar la causa de porque se activo, o donde.
- Si es una interrupcion que se debio haber activado, pero vos no la tuviste en cuenta, con esto te vas a dar cuenta.
- Si es un error de alineacion, te vas a dar cuenta tambien, ya que las interrupciones que lo causan son MemFault/HardFault por ahi andan.
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 02 de Septiembre de 2018, 13:10:57
Ok buena idea, la causa del error ha sido la numero 3, es decir hardfault tiene que ser algo relacionado con la flash.
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 02 de Septiembre de 2018, 13:25:59
Bien parece ser que esta relacionado con la dirección donde lo estaba guardando, revisando el mapa de memoria veo que la SRAM esta a partir de la dirección 0x00400000

al cambiar a esa dirección, ya funciona el programa, pero al leer la región me da 0, cuando me deberia dar 0,1,2,3,4....

Código: [Seleccionar]
uint32_t page_size;
uint16_t i;

/* Init source data */
page_size = flash_get_page_size(&FLASH_0);

for (i = 0; i < page_size; i++) {
src_data[i] = i;
}

/* Write data to flash */
flash_write(&FLASH_0, 0x00400000, src_data, page_size);

/* Read data from flash */
flash_read(&FLASH_0, 0x00400000, chk_data, page_size);

el programa se ejecuta sin problemas, pero no lee lo que deberia o no graba en la region marcada.
Título: Re:error de flash en atmel sam
Publicado por: planeta9999 en 02 de Septiembre de 2018, 13:49:41
 
¿ Has ejecutado el flash_erase antes de escribir en la flash ?.

Si no borras previamente la página completa, no puedes escribir en la dirección correspondiente a esa página. Y hay que cuidarse de que en esa página no esté parte o la totalidad del programa que se está ejecutando.


Código: C++
  1. /**
  2.  * \brief Execute erase in the internal flash
  3.  */
  4. int32_t flash_erase(struct flash_descriptor *flash, const uint32_t dst_addr, const uint32_t page_nums)
  5. {
  6.         ASSERT(flash && page_nums);
  7.         uint32_t page_size   = _flash_get_page_size(&flash->dev);
  8.         uint32_t total_pages = _flash_get_total_pages(&flash->dev);
  9.         int32_t  rc;
  10.  
  11.         rc = flash_is_address_aligned(flash, dst_addr);
  12.         if (rc) {
  13.                 return rc;
  14.         }
  15.  
  16.         if ((page_nums > total_pages) || (dst_addr / page_size + page_nums > total_pages)) {
  17.                 return ERR_INVALID_ARG;
  18.         }
  19.  
  20.         _flash_erase(&flash->dev, dst_addr, page_nums);
  21.  
  22.         return ERR_NONE;
  23. }

Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 02 de Septiembre de 2018, 14:03:41
Hola planeta, pues acabo de probar lo que comentas, pero el comportamiento es el mismo, cuando leo solo leo 0, cuando deberia leer un buffer ascendente (1,2,3,4...)

tambien he probado a desbloquear la pagina:

Código: [Seleccionar]
void LeerFlash(void)
{
uint32_t page_size;
uint16_t i;

/* Init source data */
page_size = flash_get_page_size(&FLASH_0);

for (i = 0; i < page_size; i++) {
src_data[i] = i;
}

flash_unlock(&FLASH_0, 0x0047F800, page_size);

flash_erase(&FLASH_0, 0x0047F800,page_size);

/* Write data to flash */
flash_write(&FLASH_0, 0x0047F800, src_data, page_size);

/* Read data from flash */
flash_read(&FLASH_0, 0x0047F800, chk_data, page_size);

i=1;
}

el "i=1" es para parar el debug y ver los arrays src_data y chk_data, la dirección he usado esa que seria la direccion base 0x04000000 + 0x80000 (512B) -512*4

asi tendria 2048 bytes para guardar. pero nada cuando para en i=1; tengo el src_data[0]=0,src_data[1]=1, etc. pero el chk_data todo a 0.

no se que puede ser.
Título: Re:error de flash en atmel sam
Publicado por: planeta9999 en 02 de Septiembre de 2018, 14:06:13

Puede que necesites también bloquear y desbloquear la página con flash_lock y flash_unlock.

Lo que si es seguro, es que para escribir en la flash, siempre hay que borrar previamente la página completa en la que esté la dirección a escribir, si no el resultado puede ser imprevisible o no escribe nada.

PD: vaya, no había leído que ya has probado el unlock de la página. Tal vez necesites hacer un lock, escribir y luego el unlock. Por algún documento anda un organigrama del proceso completo de escritura en la flash, me parece que tanto el lock como el unlock estaban involucrados tras borrar la página.
Título: Re:error de flash en atmel sam
Publicado por: planeta9999 en 02 de Septiembre de 2018, 14:19:07

Este es un ejemplo completo de escritura.


Código: C++
  1. /**
  2.  * \brief Test flash writing.
  3.  *
  4.  * This test tests the flash writing function in the test page of the flash.
  5.  *
  6.  * \param test Current test case.
  7.  */
  8. static void run_flash_write_test(const struct test_case *test)
  9. {
  10.         uint32_t ul_page_buffer[IFLASH_PAGE_SIZE / sizeof(uint32_t)];
  11.         uint32_t ul_rc=0;
  12.         uint32_t ul_idx;
  13.         uint32_t ul_test_page_addr = TEST_PAGE_ADDRESS;
  14.         uint32_t *pul_test_page = (uint32_t *) ul_test_page_addr;
  15.  
  16.         /* Unlock the whole flash */
  17.         flash_unlock(IFLASH_ADDR,  ul_test_page_addr + IFLASH_PAGE_SIZE - 1, 0, 0);
  18.  
  19.         /* Write the test page with walking bit pattern */
  20.         for (ul_idx = 0; ul_idx < (IFLASH_PAGE_SIZE / 4); ul_idx++) {
  21.                 ul_page_buffer[ul_idx] = 1 << (ul_idx % 32);
  22.         }
  23.  
  24. #if (SAM4S || SAM4E || SAM4N || SAM4C || SAM4CP || SAM4CM || \
  25.          SAMV71 || SAMV70 || SAMS70 || SAME70)
  26.         /* Write the test page */
  27.         flash_erase_sector(ul_test_page_addr);
  28.  
  29.         flash_write(ul_test_page_addr,
  30.                         (void *)ul_page_buffer,
  31.                         IFLASH_PAGE_SIZE, 0);
  32. #else
  33.         flash_write(ul_test_page_addr,
  34.                         (void *)ul_page_buffer,
  35.                         IFLASH_PAGE_SIZE, 1);
  36. #endif
  37.  
  38.         /* Validate page contents */
  39.         for (ul_idx = 0; ul_idx < (IFLASH_PAGE_SIZE / 4); ul_idx++) {
  40.                 if (pul_test_page[ul_idx] != ul_page_buffer[ul_idx]) {
  41.                         ul_rc =1;
  42.                 }
  43.         }
  44.  
  45.         /* Validate the flash write function */
  46.         test_assert_true(test, ul_rc == 0, "Test flash write: flash write error!");
  47. }
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 02 de Septiembre de 2018, 14:23:09

Puede que necesites también bloquear y desbloquear la página con flash_lock y flash_unlock.

Lo que si es seguro, es que para escribir en la flash, siempre hay que borrar previamente la página completa en la que esté la dirección a escribir, si no el resultado puede ser imprevisible o no escribe nada.

PD: vaya, no había leído que ya has probado el unlock de la página. Tal vez necesites hacer un lock, escribir y luego el unlock. Por algún documento anda un organigrama del proceso completo de escritura en la flash, me parece que tanto el lock como el unlock estaban involucrados tras borrar la página.


Pues revisando la funcion unlock veo lo siguiente:

Código: [Seleccionar]
int32_t flash_unlock(struct flash_descriptor *flash, const uint32_t dst_addr, const uint32_t page_nums)
{
ASSERT(flash && page_nums);
uint32_t page_size   = _flash_get_page_size(&flash->dev);
uint32_t total_pages = _flash_get_total_pages(&flash->dev);
int32_t  rc;

rc = flash_is_address_aligned(flash, dst_addr);
if (rc) {
return rc;
}

if ((page_nums > total_pages) || (dst_addr / page_size + page_nums > total_pages)) {
return ERR_INVALID_ARG;
}

return _flash_unlock(&flash->dev, dst_addr, page_nums);
}

para devolver error, el segundo if tiene una condicion que es:

dst_addr / page_size + page_nums > total_pages 

si cogemos dst_addr como 0x400000 (4194304) el tamaño de pagina que es de 512 y el numero de paginas que como maximo son 1024 me parece que siempre es error ¿no? o estoy haciendo algo mas o esto no cuadra:

4194304/512 solo eso ya es 8192 >1024 siempre va  ha ser error :? :?
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 02 de Septiembre de 2018, 14:26:36

Este es un ejemplo completo de escritura.


Código: C++
  1. /**
  2.  * \brief Test flash writing.
  3.  *
  4.  * This test tests the flash writing function in the test page of the flash.
  5.  *
  6.  * \param test Current test case.
  7.  */
  8. static void run_flash_write_test(const struct test_case *test)
  9. {
  10.         uint32_t ul_page_buffer[IFLASH_PAGE_SIZE / sizeof(uint32_t)];
  11.         uint32_t ul_rc=0;
  12.         uint32_t ul_idx;
  13.         uint32_t ul_test_page_addr = TEST_PAGE_ADDRESS;
  14.         uint32_t *pul_test_page = (uint32_t *) ul_test_page_addr;
  15.  
  16.         /* Unlock the whole flash */
  17.         flash_unlock(IFLASH_ADDR,  ul_test_page_addr + IFLASH_PAGE_SIZE - 1, 0, 0);
  18.  
  19.         /* Write the test page with walking bit pattern */
  20.         for (ul_idx = 0; ul_idx < (IFLASH_PAGE_SIZE / 4); ul_idx++) {
  21.                 ul_page_buffer[ul_idx] = 1 << (ul_idx % 32);
  22.         }
  23.  
  24. #if (SAM4S || SAM4E || SAM4N || SAM4C || SAM4CP || SAM4CM || \
  25.          SAMV71 || SAMV70 || SAMS70 || SAME70)
  26.         /* Write the test page */
  27.         flash_erase_sector(ul_test_page_addr);
  28.  
  29.         flash_write(ul_test_page_addr,
  30.                         (void *)ul_page_buffer,
  31.                         IFLASH_PAGE_SIZE, 0);
  32. #else
  33.         flash_write(ul_test_page_addr,
  34.                         (void *)ul_page_buffer,
  35.                         IFLASH_PAGE_SIZE, 1);
  36. #endif
  37.  
  38.         /* Validate page contents */
  39.         for (ul_idx = 0; ul_idx < (IFLASH_PAGE_SIZE / 4); ul_idx++) {
  40.                 if (pul_test_page[ul_idx] != ul_page_buffer[ul_idx]) {
  41.                         ul_rc =1;
  42.                 }
  43.         }
  44.  
  45.         /* Validate the flash write function */
  46.         test_assert_true(test, ul_rc == 0, "Test flash write: flash write error!");
  47. }

ese ejemplo que has puesto es de las librerias antiguas, yo estoy usando las nuevas, aunque estoy haciendo mas o menos lo mismo lo que pasa es que la funcion unlock difiere, solo se le pasan 3 argumentos y como he puesto en mi post anterior creo que siempre da error???
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 02 de Septiembre de 2018, 15:09:44
a ver, recapitulando, como hemos visto para grabar en la flash tenemos uqe desbloquer la región borrar y luego escribir vale, hasta aqui todo claro pero en este micro es:


Código: [Seleccionar]
#define IFLASH_SIZE              _U_(0x00080000)       /*  512kB Memory segment type: flash */
#define IFLASH_PAGE_SIZE         _U_(       512)
#define IFLASH_NB_OF_PAGES       _U_(      1024)
#define IFLASH_ADDR              _U_(0x00400000)       /**< IFLASH base address (type: flash)*/

Que coincide con lo que dice la hoja de datos: http://ds.arm.com/media/resources/db/chip/atmel/sams70/Atmel-11242-32-bit-Cortex-M7-Microcontroller-SAM-S70Q-SAM-S70N-SAM-S70J_Datasheet.pdf

tenemos que la region de memoria de la flash empieza en 0x00400000 que el tamaño de la pagina son 512 y que tenemos 1024 paginas, vale hasta aqui todo perfecto, pero ahora vemso en la funcion unlock:

Código: [Seleccionar]
int32_t flash_unlock(struct flash_descriptor *flash, const uint32_t dst_addr, const uint32_t page_nums)
{
ASSERT(flash && page_nums);
uint32_t page_size   = _flash_get_page_size(&flash->dev);
uint32_t total_pages = _flash_get_total_pages(&flash->dev);
int32_t  rc;

rc = flash_is_address_aligned(flash, dst_addr);
if (rc) {
return rc;
}

if ((page_nums > total_pages) || (dst_addr / page_size + page_nums > total_pages)) {
return ERR_INVALID_ARG;
}

return _flash_unlock(&flash->dev, dst_addr, page_nums);
}

 que si vemos la segunda condición tomando el mejor de los casos como dst_addr como la base 0x00400000 y una sola pagina, tenemos que siempre va a soltar error:

ya que dst_addr/512+nº de paginas siempreeeeee es mayor que 1024

si vamos a la función erase:

Código: [Seleccionar]
int32_t flash_erase(struct flash_descriptor *flash, const uint32_t dst_addr, const uint32_t page_nums)
{
ASSERT(flash && page_nums);
uint32_t page_size   = _flash_get_page_size(&flash->dev);
uint32_t total_pages = _flash_get_total_pages(&flash->dev);
int32_t  rc;

rc = flash_is_address_aligned(flash, dst_addr);
if (rc) {
return rc;
}

if ((page_nums > total_pages) || (dst_addr / page_size + page_nums > total_pages)) {
return ERR_INVALID_ARG;
}

_flash_erase(&flash->dev, dst_addr, page_nums);

return ERR_NONE;
}

exactamente lo mismo

y si vamos a write:

Código: [Seleccionar]
int32_t flash_write(struct flash_descriptor *flash, uint32_t dst_addr, uint8_t *buffer, uint32_t length)
{
ASSERT(flash && buffer && length);

uint32_t page_size   = _flash_get_page_size(&flash->dev);
uint32_t total_pages = _flash_get_total_pages(&flash->dev);

/* Check if the address is valid */
if ((dst_addr > page_size * total_pages) || (dst_addr + length > page_size * total_pages)) {
return ERR_BAD_ADDRESS;
}

if (_flash_is_locked(&flash->dev, dst_addr)) {
return ERR_DENIED;
}

_flash_write(&flash->dev, dst_addr, buffer, length);

return ERR_NONE;
}

tambien va a saltar siempre error ERR_BAD_ADDRESS por que la direccion de la base 0x00400000 solo eso ya es mayor que 512*1024

asi que, o esto esta mal, o yo lo estoy entendiendo mal o ya no se que hacer...  :? :? quiere decir que debo grabarlo en la region de memoria ITCM, lo he probado y el programa se queda colgado asi que no puede ser asi que a ver si alguien me puede ayudar, estoy perdiendo mucho tiempo con esta tontería.

(https://i2.wp.com/directorioseogratis.com/wp-content/uploads/2017/11/tumblr_inline_oz5lni3Bvh1qhy6fn_500.jpg?fit=500%2C670)



PD: otra cosa curiosa, si coloco la direccion 0x0 si graba y lee, pero claro, me pisa el programa y me lo fastidia.
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 03 de Septiembre de 2018, 02:40:26
Bueno como nadie ha vuelto a constestar, supongo que mi premisa de que esto es absurdo es correcta, asi que solo se me ocurre una idea, reservar memoria de programa para que no me lo pise, alguien sabe como hacerlo? con 512 bytes tendría suficiente, en este micro no se exactamente como se hace, o hacer que el programa se guarde a partir de tal dirección, en PIC lo hacia de la siguiente manera:

Código: [Seleccionar]
#if defined (__PIC32C__)
#define KEEP
#else
#define KEEP    __attribute__ ((keep)) __attribute__((address(DRV_NVM_MEDIA_START_ADDRESS)))
#endif

#define APP_NVM_MEMORY_AREA_SIZE (DRV_NVM_MEDIA_SIZE * 1024) //32KB

//Reservamos 32KB de Flash
const uint8_t gAppFlashReserveArea[APP_NVM_MEMORY_AREA_SIZE] KEEP = {0};
Título: Re:error de flash en atmel sam
Publicado por: planeta9999 en 03 de Septiembre de 2018, 07:44:41
Utiliza la última página de la flash para tus datos y arreglado. Reubicar el programa solo tiene razón de ser para un sistema de bootloader y se suele hacer en el linker script.

Si no puedes usar una página cualquiera, no ocupada por el programa, habrá algún motivo, como el bloqueo desbloqueo de memoria, previo o posterior al borrado de pagina. Si lo intentas forzar, en direcciones de páginas usadas por el programa, tendras que salvar y restaurar la pagina tras la grabación, no tiene sentido salvo que vayas justo de flash, y aun así te podría colgar el micro.

Reubicar el programa para que salte a otra direccion en el arranque, sin un bootloader, no lo he hecho nunca, y no tiene sentido. Es intentar calzar el programa a la fuerza, por desconocer porque no te graba en una determinada página , es una solución chapucera, si es que se puede hacer.
Título: Re:error de flash en atmel sam
Publicado por: KILLERJC en 03 de Septiembre de 2018, 08:14:39
Citar
Bueno como nadie ha vuelto a constestar

Yo no poseo demasiado tiempo, estoy un rato, contesto y tengo que salir.

Si fuera ese el problema que vos comentas, de que nunca se cumpliria esa condicion. Nunca comenzaria a escribir realmente. Y te devolveria el valor ERR_INVALID_ARG o ERR_BAD_ADDRESS. Y no continuaria con la escritura, haciendo que no se produzca un Hard Fault. Si podes debugearlo paso a paso, considero que deberias ver cuando es que ocurre, si entra o no a las funciones, si sale con algun error o no. Es lo mas simple de ver sin renegar con el codigo fuente.

Sino la otra es buscar el codigo para Hard Fault, el cual te arrojaria la direccion del PC antes de que ocurra, y asi saber que instruccion es la que lo produjo. Pero esos micros ya deben tener modulos extras para eso ( que no me acuerdo el nombre, trace y algo )

https://mcuoneclipse.com/2012/11/24/debugging-hard-faults-on-arm-cortex-m/
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 03 de Septiembre de 2018, 08:41:35
Citar
Si no puedes usar una página cualquiera, no ocupada por el programa, habrá algún motivo, como el bloqueo desbloqueo de memoria, previo o posterior al borrado de pagina. Si lo intentas forzar, en direcciones
de páginas usadas por el programa, tendras que salvar y restaurar la pagina tras la grabación, no tiene sentido salvo que vayas justo de flash, y aun así te podría colgar el micro.

No se puede usar ninguna otra por que nunca se cumple la condicion, no puedes desbloquear la flash, ya que con la condicion dentro de la funcion unlock nunca se cumple con la dirección de memoria de la flash.

si reservo la memoria como he comentado no es una chapuza, el programa no se cambia de sitio, solo que ocupara mas por que tendrá una "variable muy grande vacia", y cuando graves en esa zona no se pisará el programa, solo se guardara en esa "variable grande". es como se hace en pic32 que comparte la flash para la memoria de programa.

Simplemente si se selecciona otra direccion que no sea la 0 o una muy baja no se graba.

Citar
habrá algún motivo


El motivo puede ser simplemente que este mal hecho, en este mismo proyecto he tenido que crear librerias para manerjar el RTT por que en las librerias no aparece, y modificar los fuentes del driver RTC para poder leer el dia de la semana por que no esta implementado en las librerías, tambien he tenido que modificar los fuentes de la uart asyncrona, las librerías son una basura asi que no te extrañe que para el caso de la flash también esten mal hechas, y no encontraras, mas ejemplo que el que puse yo al principio.


Citar
Si podes debugearlo paso a paso, considero que deberias ver cuando es que ocurre, si entra o no a las funciones, si sale con algun error o no. Es lo mas simple de ver sin renegar con el codigo fuente

precisamente vi lo de las condiciones a raiz de ir depurando, siempre saltaban las condiciones que comento y viendo los valores tenemos

Código: [Seleccionar]
if ((page_nums > total_pages) || (dst_addr / page_size + page_nums > total_pages)) {
return ERR_INVALID_ARG;
}

total_pages=1024

page_size =512

poniendo un page_num de 1, para tener el mejor de los casos y la direccion base de la flash 0x00400000 (‭4194304‬)

dentro de la condición tenemos que salta error si
Código: [Seleccionar]
dst_addr / page_size + page_nums > total_pages pero solo el dst_addr / page_size ya es mayor que 1024  :? :?

PD:
Citar
Bueno como nadie ha vuelto a constestar

Yo no poseo demasiado tiempo, estoy un rato, contesto y tengo que salir.

No se si ha sonado mal, no era por meter prisa ni por nada por el estilo simplemente que suponía que nadie sabia el porque pasa esto.

un saludo

 - Tienes que ingresar para ver archivos adjuntos -



Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 04 de Septiembre de 2018, 06:18:39
NEcesito ayuda con esto, no consigo hacer que funcione, la escritura de la flash solo parece funcionar bien a partir de la direccion 0x0 o valores muy bajos, pero me borra el programa principal, por lo tanto el programa de estar en esa zona.

Ademas no me deja guardar en la sección flash 0x00400000, esa zona de memoria no se puede ni desbloquear ni borrar ni guardar, por culpa de las condiciones dentro de las funciones, que por cierto si se borran no funciona igualmente.

he probado a reservar memoria con la instruccion keep pero el compilador me ignora los atributos:

 - Tienes que ingresar para ver archivos adjuntos -

lo raro es que en el Linker script "nunca he profuncidado nunca aquí"  tenemos lo siguiente:

/* Memory Spaces Definitions */
MEMORY
{
    rom (rx)    : ORIGIN = 0x00400000, LENGTH = 0x00080000 /* rom, 524288K */
    ram (rwx)   : ORIGIN = 0x20400000, LENGTH = 0x00040000 /* ram, 262144K */
}

/* The stack size used by the application. NOTE: you need to adjust according to your application. */
STACK_SIZE = DEFINED(STACK_SIZE) ? STACK_SIZE : DEFINED(__stack_size__) ? __stack_size__ : 0x0400;

/* The heapsize used by the application. NOTE: you need to adjust according to your application. */
HEAP_SIZE = DEFINED(HEAP_SIZE) ? HEAP_SIZE : DEFINED(__heap_size__) ? __heap_size__ : 0x0200;

dice que la rom esta en la direccion 0x00400000 cuando se supone que esta en 00800000:

alguien se le ocurre la solución o que esta pasando, yo me estoy quedando sin ideas.

(http://www.todopic.com.ar/foros/index.php?action=dlattach;topic=48975.0;attach=29665;image)
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 04 de Septiembre de 2018, 07:14:23
Haciendo ingenieria inversa a las librerias y condiciones que me iba encontrando a en la depuración he sacado que la maxima memoria accesibe es la direccion 0x80000=512MB de la flash que dice que tiene (como maxima), por lo tanto he restado, y las regiones de borrado y escritura son de 512X16=8192 (también ingeniería inversa). Así que desde la dirección 7C000 puedo escribir mis 512 de la pagina.

Parece que así funciona, ahora la explicación de por que la direccion de la flash es distinta en la hoja de datos, ni idea, si alguien sabe por que que lo comente.

un saludo
Título: Re:error de flash en atmel sam
Publicado por: KILLERJC en 04 de Septiembre de 2018, 08:55:21
El linker toma la Flash y la ROM ambas como "ROM" en el linker, de todas formas el linker no es el problema. Ya que sino tendrias un problema al compilar/linkear tu programa.


Citar
Haciendo ingenieria inversa a las librerias y condiciones que me iba encontrando a en la depuración he sacado que la maxima memoria accesibe es la direccion 0x80000=512MB de la flash

Y esa es la maxima direccion que podes escribir. Ya que la ROM es otra cosa. No es programable

Citar
Internal ROM
The SAM S70 embeds an Internal ROM for the SAM Boot Assistant (SAM-BA®), In Application Programming functions (IAP) and Fast Flash Programming Interface (FFPI).
At any time, the ROM is mapped at address 0x0080 0000
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 04 de Septiembre de 2018, 09:22:06
Citar
Y esa es la maxima direccion que podes escribir. Ya que la ROM es otra cosa. No es programable

Esa es la cosa, que la rom empieza en el 0x800000 no en la 0x80000 (fijate en los ceros).

Citar
Internal ROM
The SAM S70 embeds an Internal ROM for the SAM Boot Assistant (SAM-BA®), In Application Programming functions (IAP) and Fast Flash Programming Interface (FFPI).
At any time, the ROM is mapped at address 0x0080 0000

Ademas, en el linker script te dice que la rom empieza en la 0x00400000:

rom (rx)    : ORIGIN = 0x00400000, LENGTH = 0x00080000 /* rom, 524288K */

Cuando no es así, la rom empieza en la 0x00800000, en la 0x00400000 empieza la flash, la cual es inaccesible, ya que solo puedes acceder hasta la direccion 0x80000(con 4 ceros) te quedas dentro de la zona de ITCM, osea que algo esta mal, muy mal, no se para que ponen esa parte de flash si la toman como rom en el linker para que no puedas grabar nada ahi

(http://www.todopic.com.ar/foros/index.php?action=dlattach;topic=48975.0;attach=29665;image)

Título: Re:error de flash en atmel sam
Publicado por: planeta9999 en 05 de Septiembre de 2018, 09:13:52
Ufff, yo los SAM los descarté pronto, hace ya bastante tiempo. No me gustó nada el entorno de desarrollo, ni tampoco los asistentes para crear el programa, ni lo pobre que es el conjunto de fuentes de ejemplo que dan con el ASF. Parece todo como dejado caer de cualquier manera, y sin ningún tipo de actualización para mejorar el producto, desde hace tiempo.

El micro es muy barato, pero el resto es una castaña. Muy diferente es con los RT1020 de NXP, una maravilla en todos los aspectos, además son mucho más potentes (Cortex M7 a 500Mhz), muy baratos y puedes conectar Flash y SDRAM externa con mucha más capacidad que los micros que la integran dentro. Tengo ahora un diseño que instalará una SDRAM de 512 Megabit y una QSPI de 32 ó 64 Mbit para el arranque, luego se copia el programa él solo a la SDRAM y se ejecuta todo desde allí a la velocidad del rayo.

El SDK de los RT es fantástico, tienes fuentes de ejemplo para todo, y muy bien documentados. MCUXpresso es también genial, con asistentes para configurar Puertos, Reloj y Periféricos, que no tiene nada que envidiarle al Cubemx de ST. Es mucho mejor porque integra la importación de fuentes de ejemplo desde el SDK, cosa que no ofrece ST, en eso ST patina dejando al usuario a su suerte para que cree los programas por su cuenta, sin un miserable programa de ejemplo en el que inspirarte para crear el tuyo. Para mi, una buena librería de programas modelo de ejemplo es fundamental, como tiene Arduino, pero con NXP está mejor organizado.
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 05 de Septiembre de 2018, 13:46:55
Yo lo he usado en este proyecto, pero no los volveré a utilizar a no se que no tenga opción, es increible la cantidad de cosas que están mal o inacabadas, el driver del RTC no te permite leer los registros del día de la semana, ni configurar el formato de 12h o 24h he tenido que modificar los fuentes para añadirle las funciones , el buffer circular de la recepción de la uart se pisa con el de envio por que tiene la interrupciones cruzadas, el periférico del RTT no tiene driver, he tendido que crearlo yo, las interrupciones externas del puerto D no funcionan, ahora la memoria flash estas cosas...fatal todo, raro es lo que funciona bien, o la primera. En un seminario de microchip nos dijeron que iban a quitarse de enmedio todas las herramientas de atmel, que en dos años no iba a estar ni el atmel studio ni las herramientas de programación, pero de ahí a que ocurran estas cosas.... pff no recomiendo a nadie que utilice estos micros, al menos hasta que microchip los integre en su sistema y empiecen a darle soporte, y aun así, yo ya no los volveré a usar, al igual que los PIC.

Como están los RT en cuanto a disponibles? ¿les pasa lo mismo que a los kinetis? todo el entorno y librerías como comentas es mas o menos como el de kinetis no? con que herramienta los programas.

Yo estoy testeando para nuevos proyectos médicos los renesas (synergy) y los texas instrumens (C2000 y hercules), la calidad y fiabilidad de estos micros no tienen comparación, para pasar las normativas son los mejores ya que muchas librerías ya tienen varias certificaciones, pero la calidad se paga, son bastante caros.

Título: Re:error de flash en atmel sam
Publicado por: planeta9999 en 05 de Septiembre de 2018, 18:39:35

Los RT1020, ahora mismo están disponibles en LQFP100 en Mouser y otros distribuidores, el LQFP144 estará para finales de año. Tengo ya en fase de montaje dos prototipos con LQFP100, pero para poder usar la SDRAM externa necesito un LQFP144, y como no están aún, lo voy a sacar de una de las placas de evaluación que compré, que estas si que montan uno de 144 pines.

De momento no hay problemas de stock, incluso creo que NXP ya da samples gratuitos. El entorno de trabajo gratuito es el mismo en los Kinetis,  LPC e i.MX, se usa MCUXpresso con SDK bajados de la web de NXP, salvo los LPC que están integrados en MCUXpresso (no necesitan SDK).

Por ahora, voy a confiar en los i.MX, son muy baratos, muy potentes, y todo lo que he visto y probado me ha gustado mucho, mi idea es migrar todo lo que tengo con Kinetis a i.MX RT1020. Lo que en principio parecía un problema, que es necesitar flash externa, es justo lo contrario, es una gran ventaja, porque puedes montar Hyperflash o QSPI con mucha más memoria de la que te puede ofrecer cualquier otro micro que la lleve integrada. En la compilación, puedes configurar para que compile una imagen encriptada del programa, de esa manera aunque esté en memoria externa no te lo pueden fusilar, porque se carga y desencripta internamente en tiempo de ejecución.

Tengo aquí compradas varias QSPI de 32 y 64 Mbit, y SDRAM de 256Mbit y 512Mbit para ir probando. Se puede configurar para que arranque desde SD, Flash paralelo, QSPI o SPI Octal, que me han contado que vuela. Tienes la posibilidad de poder conectar una SDRAM externa con un montón de megas, y puedes configurar para que compile con arranque de RAM, que hace que al iniciar desde SD, QSPI o Hyperflash se copie automaticamente el programa a la SDRAM y se ejecute desde allí, una maravilla.

Por ahora no le encuentro ningún defecto, ya veremos cuando empiece los desarrollos en serio, ahora estoy leyendo mucha documentación, principalmente el Manual de Referencia y mirando los fuentes de ejemplo que trae el SDK. Ya hice acopio de material y tengo los PCB para montar los prototipos.
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 06 de Septiembre de 2018, 03:41:02
Entonces de momento no me sirven, donde trabajo necesitamos un buen stock de lo contrario podemos tener problemas, precisamente los kinetis los tuve que descartar por eso mismo (aunque no se que es peor con el atmel este)

Así que para testear los RT esperare hasta que hasta que se comercialicen normalmente, por que aunque me sirvieran ahora, no podría usarlos.

un saludo

Título: Re:error de flash en atmel sam
Publicado por: planeta9999 en 06 de Septiembre de 2018, 03:48:25

No hay ningún problema de stock. LQFP100 está disponible, y LQFP144 aún no se comercializa, lo liberan a final de año.
Título: Re:error de flash en atmel sam
Publicado por: juaperser1 en 06 de Septiembre de 2018, 09:36:45
a pensaba que ninguno se estaba comercializando mas alla de las muestras o poco mas.

que herramienta usas para depurar?
Título: Re:error de flash en atmel sam
Publicado por: planeta9999 en 06 de Septiembre de 2018, 16:54:44
a pensaba que ninguno se estaba comercializando mas alla de las muestras o poco mas.

que herramienta usas para depurar?

De LQFP100 puedes pedir muestras gratuitas a NXP, yo hace un rato he pedido de MK66 que son los que sigo usando en lo que monto para clientes,  y los RT1020 también estaban disponibles para samples. De RT1020 tengo de sobra los que compré a Digikey y algunos más que compré más tarde a Mouser.

Lo trabajo todo con MCUXpresso, puedes usar Jlink o Multilink, con ambos funciona igual para Programar y Depurar.

Lo interesante es usar una salida por COM virtual para sacar variables y textos en tiempo de ejecución a una ventana tipo hiperterminal usado el printf, como lo hace Arduino, es más interesante que los breakpoints y el paso a paso. Yo desde que usé Arduino, me acostumbré a depurar de esa manera, y es mucho mejor, ya no lo cambio por el viejo sistema de puntos de ruptura.

Jlink te crea un COM virtual, Multilink no lo se, el que más estoy usando es Jlink V9.

Otra cosa interesante es usar estos conectores de programación para JTAG o SWD, no necesitas conector en la placa, solo poner la huella en el PCB, el conector se lastra con unas pestañas de plástico y unos pines con amortiguador tocan sobre los pads del PCB. Los tengo puestos en un par de prototipos y van de fábula.


(https://i.imgur.com/DgQynaE.jpg)

(https://i.imgur.com/bABmbT7.jpg)

(https://i.imgur.com/Ypucn6a.jpg)

(https://i.imgur.com/c2uPztH.jpg)

(https://i.imgur.com/bDOiPjQ.jpg)