Autor Tema: Estructura no identificada  (Leído 2969 veces)

0 Usuarios y 1 Visitante están viendo este tema.

Desconectado JuanjoPic

  • PIC12
  • **
  • Mensajes: 97
Estructura no identificada
« en: 13 de Septiembre de 2017, 22:15:56 »
Hola amigos
Estoy iniciando con el compilador xc8 y tengo problemas al utilizar las estructuras de los registros.


El programa es simple, solo prendo un led con el pic 16f716.

Este es el programa:

#include "fuses_pic16f716.h"         

void configuracion_pines(){
    ADCON1 = 0xff;
    PORTA = 0b00000000;
    TRISA = 0x00;
}
void main(void) {
    configuracion_pines();
    while(1){
    PORTAbits_t.RA0 = 1;                             // ESTA ESTRUCTURA NO ES RECONOCIDA 
    }       
}

Este mensaje me entrega MPLAB X:

main.c:22: error: (285) no identifier in declaration
main.c:22: error: (314) ";" expected



Hice otro programa  que realiza lo mismo (encender un led) pero ataque directo al registro como se muestra en el siguiente programa:

#include "fuses_pic16f716.h"


void configuracion_pines(){
    ADCON1 = 0xff;
    PORTA = 0b00000000;
    TRISA = 0x00;
}
void main(void) {
    configuracion_pines();
    while(1){
    PORTA |= 0b00000001;                         // CAMBIE LA ESTRUCTURA POR ESTA LINEA (SETEO EL SOLO EL BIT0 DEL REGISTRO PORTA)
    }   
}

y este si me funciona bien (compila, he incluso lo he simulado en el ISIS )


Mi pregunta es:

¿Por que no me funciona cuando utilizo la estructura, si me funciona cuando ataco al registro directamente?

Cualquier ayuda me sera de utilidad
Gracias




Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re:Estructura no identificada
« Respuesta #1 en: 14 de Septiembre de 2017, 00:04:38 »
es que el TIPO de estructura es PORTAbits_t pero esto es el tipo ( como esta conformada la estructura ) La que luego se define como estructura de ese tipo es:

PORTAbits

en resumen, la nomeclatura que usa XC8 es "nombre de registro" + "bits" ejemplo:

Código: C
  1. PORTAbits.RA0 = 1;
  2. INTCONbits.GIE = 0;

Desconectado JuanjoPic

  • PIC12
  • **
  • Mensajes: 97
Re:Estructura no identificada
« Respuesta #2 en: 14 de Septiembre de 2017, 00:45:58 »
Excelente, me funciono.

Ingrese al .h y encontré esto:

typedef union {
    struct {
        unsigned RA0                    :1;
        unsigned RA1                    :1;
        unsigned RA2                    :1;
        unsigned RA3                    :1;
        unsigned RA4                    :1;
    };
} PORTAbits_t;

extern volatile PORTAbits_t PORTAbits @ 0x005;


Viendo la sintaxis en negrita note lo que me haz comentado

Gracias por tu ayuda  ((:-)).











Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re:Estructura no identificada
« Respuesta #3 en: 14 de Septiembre de 2017, 08:39:12 »
Esa sintaxis tiene 2 cosas. La primera quees la parte del extern y definirlo como la estructura que antes se definio.

La otra parte que es exclusiva del compilador XC8 y algunos otros compiladores es ese arroba con la direccion de memoria, para indicar donde debe estar ubicada esa varaible.
Si te vas a GCC es distinto, y tenes que jugar con el linker + atributos de la variable
O definen el acceso asi:

Código: C
  1. #define IOPIN0         (*((volatile unsigned long *) 0xE0028000))
  2.  
  3. IOPIN0 = 10;
La diferencia de este ultimo con el de microchip, es que no enes estructuras, y termina todo siendo OR/ANDs sobre el "registro".
« Última modificación: 14 de Septiembre de 2017, 08:43:26 por KILLERJC »

Desconectado JuanjoPic

  • PIC12
  • **
  • Mensajes: 97
Re:Estructura no identificada
« Respuesta #4 en: 14 de Septiembre de 2017, 17:19:08 »
Gracias por comentar KILLERJC.

Leyendo tu comentario, varias cosas que no entendí ojala me pudieras ayudar a entenderlas.

El compilador XC8 con el @ "enmascara" utilizar (*((volatile unsigned long *) 0xE0028000)) ?........ (se que la sintaxis que esta en negrita lo que hace es utilizar un puntero del tipo volatile unsigned long*..... con el apunta a la dirección 0xE0028000...y con el * realiza indireccion  sobre la dirección de memoria y así almacena un dato con el puntero).

Lo otro que no se es sobre GCC...¿Es un compilador?

Mi ultima consulta es acerca del linker. Tengo entendido que el linker "une" los bloques que el compilador crea cuando se utilizan funciones para que después se generen el archivo .hex.
El compilador XC8 si no utiliza un linker, ¿Como une esos bloques ? (o estoy complemente errado y el linker no funciona así?).

Gracias por comentar.

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re:Estructura no identificada
« Respuesta #5 en: 14 de Septiembre de 2017, 20:32:55 »
Respuesta corta a todas tus preguntas

Citar
El compilador XC8 con el @ "enmascara" utilizar (*((volatile unsigned long *) 0xE0028000)) ?

En realida el @ le dice al compilador que la estructura PORTAbits se encuentra en una direccion fija y absoluta de la memoria RAM, para el caso del PORTA es 0x05. Y si estos 2 son """equivalentes"""" :

Código: C
  1. #define PORTA         (*((volatile unsigned int *) 0x05))
  2. extern volatile unsigned int PORTAbits @ 0x005;

Citar
Lo otro que no se es sobre GCC...¿Es un compilador?

Si es un compilador gratuito, de aca esta derivado el XC16, y los micros con ARM pueden usar este compilador tambien. Incluso podes usarlo para tu PC.

Citar
Mi ultima consulta es acerca del linker. Tengo entendido que el linker "une" los bloques que el compilador crea cuando se utilizan funciones para que después se generen el archivo .hex.

Empecemos por el compilador, el compilador va revisar la sintaxis y errores del programa, tambien va a generar en que secciones poner las variables, el codigo, etc (secciones no es lo mimso que lugar de la memoria), tambien realiza cualquier directiva de preprocesamiento. Y lo hace archivo a archivo. Por ejemplo vos podes tener una funcion definida en otro archivo, pero el compilador no le importa eso, el simplemente va a crear una bandera de llamada a ese otro archivo ( sea cual fuese ).

Luego llega el linker, y revisa archivo por archivo e intenta unir estos, esa llamada a la funcion antes no tenia direccion de memoria. El linker entonces va a asignar un lugar de memoria para cada pedazo de codigo, usualmente en secciones. Una ves que encuentra el lugar procede a reemplazar esas banderas que dije antes por las direcciones de memoria que les asigno.

En resumen si, une archivos  tambien organiza la memoria.

Citar
El compilador XC8 si no utiliza un linker, ¿Como une esos bloques ? (o estoy complemente errado y el linker no funciona así?).

Si lo usa, lee el la salida de la compilacion.

Desconectado JuanjoPic

  • PIC12
  • **
  • Mensajes: 97
Re:Estructura no identificada
« Respuesta #6 en: 14 de Septiembre de 2017, 21:44:45 »
Gracias por tus respuestas KILLERJC

Descargare el compilador GCC para aprender bien como funciona el linker, ya que me es interesante saber como el linker funciona

Ademas creo que aprenderé bien los tipos de archivos que se crean, como el .xml, y entender como funcionan para sacar provecho de ellos.

PD: cualquier recomendación me sera util de como iniciar en aprender y entender el compilador y los archivos que se crean.

Gracias por tu ayuda.

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re:Estructura no identificada
« Respuesta #7 en: 15 de Septiembre de 2017, 00:07:46 »
No es necesario que bajes GCC para aprender que es el linker, lo podes ver todo utilizando XC8.

Yo escribi un poco pero mas que nada para Assembler.

A pesar que empece con dsPIC ( utilizando XC16, parecido a GCC ) doy una introduccion, asi que seria util que leas al menos la primer "respuesta" ( lo primero que pongo en ese tema ) sobre los compiladores:

http://www.todopic.com.ar/foros/index.php?topic=45240.msg376311#msg376311

Luego como ya ese thread pasa a ser exclusivo de dsPIC e implementar ASM dentro de este, te diria que pases a este link

http://www.todopic.com.ar/foros/index.php?topic=45254.msg376570#msg376570

Ese ultimo link trata sobre PIC18 y su forma de direccionamiento, pero en la segunda hoja ( que es donde te doy el link ) empieza a hablar sobre los archivos linker.
Mas abajo doy un oco mas de ejemplos y ver los errores que dan:

http://www.todopic.com.ar/foros/index.php?topic=45254.msg376641#msg376641

Se que esta todo desordenado, pero es el unico lugar que me acuerdo que lo explique ( masomenos ) pero que espero te arroje alguna luz. Y luego solo queda jugar con el compilador.

Observaras que hasta el momento hable de XC16, de ASM, GCC, y a pesar que sean distintos compiladores, todos comparten el mismo proceso, que esta explicado en el primer link.


Desconectado JuanjoPic

  • PIC12
  • **
  • Mensajes: 97
Re:Estructura no identificada
« Respuesta #8 en: 16 de Septiembre de 2017, 02:22:25 »
Gracias por la info KILLERJC

Bueno de todos modos descargue el GCC  que viene incluido dentro de MinGW

me gustaría saber si es factible lo que expondré a continuación.

Quiero crear un archivo .c  para después aplicar al compilador y poder obtener el .hex,  y asi poder cargar el archivo a un pic o simularlo.
mi idea es la siguiente.

En el archivo .c creare un ejemplo básico de encender un led en pic16716, para eso necesito:
- Configurar los fuses 
- Setear solo tres registros que son ADCON1, TRISA y PORTA.

El codigo, llamado LED.c, seria algo asi:

Código: [Seleccionar]
// Fuses
Fuses();   // Aqui debiera ir la direccion de los fuses

// Direcciones de los registros a usar
#define ADCON1         (*((volatile unsigned int *) 0x9f))   // direccion de memoria ADCON1 pic16f716
#define TRISA          (*((volatile unsigned int *) 0x85))    // direccion de memoria TRISA pic16f716
#define PORTA          (*((volatile unsigned int *) 0x05))   // direccion de memoria PORTA pic16f716

void main(){
int* PUERTO = PORTA;
int* DIRECCION = TRISA;
int* ADC_CONFIG = ADCON1;

// AHORA SETEO REGISTROS
*PUERTO = 0X00;        // Limpio puerto
*DIRECCION = 0X00;   // Todos pines como salida
*ADC_CONFIG = 0XFF;  //Todos digitales

//ENCIENDO UN LED
while(1){
*PUERTO |= 0x01;  //Enciendo PIN0 puerto A
}
}


Encontré los comando que el compilador utiliza para crear archivos -> https://iie.fing.edu.uy/~vagonbar/gcc-make/gcc.htm


Según el link nº1 el proceso del compilador es: pre-procesor-->compilador (crea un .s)-->ensamblador (crea un .o) y luego entra el LINKER.
Según la web debiera hacer lo siguiente (por la venta de comandos en windows):
- preprocesador: llamo a mi archivo LED.c y utilizando -E +  nombre del archivo (que sera  LED)  obtengo el archivo LED.cpp (esto no es de mucha utilidad, según yo xD)
- compilador: con el LED.c  y utilizando -S + nombre de archivo (que sera LED) obtengo un archivo en ensamblador que con nombre LED.s
- ensamblador: llamo a mi archivo LED.s creado y utilizando -o + nombre del archvio a obtener (que tambien ser llamara led) creara mi archivo objeto llamado LED.o. (según la web se puede saltar todo eso, usando LED.c -o y me genera el LED.o...¿que beneficio tiene saltar la creación del .s?)
Ahora viene el trabajo del LINKER!!
El link 2 y 3 que me enviaste entendí que debo "configurar" las direcciones de memoria donde el linker pondrá el código objeto, que en mi caso sera el LED.o. Según eso debiera dar los rangos de memoria de FLASH, que son:
-page (esto no se que es)??
-config (aqui van los fuses, segun datasheet del pic16f716 esta dentro de este rango de dirección de memoria de programa (2000h-3FFFh))
-idlocs (esto no se que es)??
-EEPROM (hay una memoria EEPROM en la memoria de programa??)

Luego los rangos de la memoria RAM. El pic que utilizo tiene 2 bankos, entonces debería escribir algo así (los rangos los saque de su datasheet):
DATABANK   NAME=BANK0       START=0x00            END=0x7F
DATABANK   NAME=BANK1       START=0x80            END=0x17F

Entonces por lo que entiendo, el linker como sabe los rangos de memoria tomara las direcciones de los registros y las "unirá" al respectivo banko (esto para la RAM) y para la memoria de programa tomara lo que esta dentro del main y lo "unirá" desde el 0x0000 de la memoria en adelante y así al final se tendrá el .hex (esta correcto esto???).

El LINKER debiera crearlo aparte, osea en un documento de texto (como el block de notas o notepad++) escribo el código (rango de direcciones de la RAM y FLASH) y al momento de guardar le cambio la extensión .lnk (¿?¿?)

Con el linker creado debiera enlazarlo con mi código objeto, pero el comando que debo utilizar no se bien como utilizarlo aun (la web habla de enlazado dinámico y estático).

KILLERJC  me gustaría que pudieras ayudarme con lo que he escrito, verificando los pasos que he puesto si están bien o mal o le falta, etc.

PD: en el código de ejemplo los FUSES no se como se direccionan, ya que su dirección esta en la memoria de programa. Tengo entendido que los punteros  "apuntan" a la RAM  y no se si se puede hacer algo asi:
#define CONFIG        (*((volatile unsigned long *) 0x2000))

Disculpa si es muy largo el texto pero quise ser lo mas explicito y claro posible. Me sera de mucha utilidad que me pudieras corregir y ayudar a construir un .hex 

Gracias por la ayuda.


Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re:Estructura no identificada
« Respuesta #9 en: 16 de Septiembre de 2017, 10:16:23 »
Tal ves no nos comprendimos.
GCC usualmente es un compilador para la arquitectura x86 o x86_x64. Por lo tanto las instrucciones en Assembler que va a generar van a ser para una PC.

GCC el mas comun acepta algunos ARM ( microprocesadores ) y luego todo x86 y x64, pero existen tambien compiladores especificos para algunos microcontroladores como son los Cortex-M, los cuales su ejecutable no simplemente se llama "gcc" sino pasa a tener una denominacion "gcc-arm-none-eabi"

Lo habia puesto antes, pero se ve que lo borre, Microchip tomo GCC y lo modifico para hacer su XC16, asi que lo mas cercano a GCC es usar XC16 para algun dsPIC/PIC24.

Asi que el programa va a salir con instrucciones ASM para un microprocesador Pentium por ejemplo y no un PIC, como las computadoras tienen el OS, apenas intentes ejecutar ese programa en tu PC vas a tener un error de memoria.

Otra cosa distinta es que Microchip en ASM utiliza 2 ejecutables distintos. El primero es el compilador, y el segundo un linker. Mientras que para XC8 utiliza todo el mismo, igual que para GCC

Citar
- preprocesador: llamo a mi archivo LED.c y utilizando -E +  nombre del archivo (que sera  LED)  obtengo el archivo LED.cpp (esto no es de mucha utilidad, según yo xD)
- compilador: con el LED.c  y utilizando -S + nombre de archivo (que sera LED) obtengo un archivo en ensamblador que con nombre LED.s
- ensamblador: llamo a mi archivo LED.s creado y utilizando -o + nombre del archvio a obtener (que tambien ser llamara led) creara mi archivo objeto llamado LED.o. (según la web se puede saltar todo eso, usando LED.c -o y me genera el LED.o...¿que beneficio tiene saltar la creación del .s?)
Ahora viene el trabajo del LINKER!!

Cuando compilas realizas esos 3 pasos de forma directa. Podes realizarlo paso a paso si queres. Pero no tiene sentido, simplemente

Código: [Seleccionar]
gcc -c -o hola.o hola.c
Citar
El link 2 y 3 que me enviaste entendí que debo "configurar" las direcciones de memoria donde el linker pondrá el código objeto, que en mi caso sera el LED.o. Según eso debiera dar los rangos de memoria de FLASH, que son:

Este archivo ya te lo provee Microchip ( .lkr ), pero para SU propio linker.
Ya debemos saber que con GCC no podemos compilar para los PICs, por lo que no tiene mucho sentido avanzar sobre el linker, pero si te interesa para ver las diferencias aca pongo uno de los archivos linker para un ST ( ARM ) utilizando AC6 ( IDE Eclipse modificado ) con GCC:

Código: [Seleccionar]
/* Entry Point */
ENTRY(Reset_Handler)

/* Highest address of the user mode stack */
_estack = 0x20001000;    /* end of RAM */

_Min_Heap_Size = 0;      /* required amount of heap  */
_Min_Stack_Size = 0x400; /* required amount of stack */

/* Memories definition */
MEMORY
{
  RAM (xrw) : ORIGIN = 0x20000000, LENGTH = 4K
  ROM (rx) : ORIGIN = 0x8000000, LENGTH = 16K
}

/* Sections */
SECTIONS
{
  /* The startup code into ROM memory */
  .isr_vector :
  {
    . = ALIGN(4);
    KEEP(*(.isr_vector)) /* Startup code */
    . = ALIGN(4);
  } >ROM

  /* The program code and other data into ROM memory */
  .text :
  {
    . = ALIGN(4);
    *(.text)           /* .text sections (code) */
    *(.text*)          /* .text* sections (code) */
    *(.glue_7)         /* glue arm to thumb code */
    *(.glue_7t)        /* glue thumb to arm code */
    *(.eh_frame)

    KEEP (*(.init))
    KEEP (*(.fini))

    . = ALIGN(4);
    _etext = .;        /* define a global symbols at end of code */
  } >ROM

  /* Constant data into ROM memory*/
  .rodata :
  {
    . = ALIGN(4);
    *(.rodata)         /* .rodata sections (constants, strings, etc.) */
    *(.rodata*)        /* .rodata* sections (constants, strings, etc.) */
    . = ALIGN(4);
  } >ROM

  .ARM.extab   : {
  . = ALIGN(4);
  *(.ARM.extab* .gnu.linkonce.armextab.*)
  . = ALIGN(4);
  } >ROM
 
  .ARM : {
    . = ALIGN(4);
    __exidx_start = .;
    *(.ARM.exidx*)
    __exidx_end = .;
    . = ALIGN(4);
  } >ROM

  .preinit_array     :
  {
    . = ALIGN(4);
    PROVIDE_HIDDEN (__preinit_array_start = .);
    KEEP (*(.preinit_array*))
    PROVIDE_HIDDEN (__preinit_array_end = .);
    . = ALIGN(4);
  } >ROM
 
  .init_array :
  {
    . = ALIGN(4);
    PROVIDE_HIDDEN (__init_array_start = .);
    KEEP (*(SORT(.init_array.*)))
    KEEP (*(.init_array*))
    PROVIDE_HIDDEN (__init_array_end = .);
    . = ALIGN(4);
  } >ROM
 
  .fini_array :
  {
    . = ALIGN(4);
    PROVIDE_HIDDEN (__fini_array_start = .);
    KEEP (*(SORT(.fini_array.*)))
    KEEP (*(.fini_array*))
    PROVIDE_HIDDEN (__fini_array_end = .);
    . = ALIGN(4);
  } >ROM

  /* Used by the startup to initialize data */
  _sidata = LOADADDR(.data);

  /* Initialized data sections into RAM memory */
  .data :
  {
    . = ALIGN(4);
    _sdata = .;        /* create a global symbol at data start */
    *(.data)           /* .data sections */
    *(.data*)          /* .data* sections */

    . = ALIGN(4);
    _edata = .;        /* define a global symbol at data end */
  } >RAM AT> ROM

 
  /* Uninitialized data section into RAM memory */
  . = ALIGN(4);
  .bss :
  {
    /* This is used by the startup in order to initialize the .bss secion */
    _sbss = .;         /* define a global symbol at bss start */
    __bss_start__ = _sbss;
    *(.bss)
    *(.bss*)
    *(COMMON)

    . = ALIGN(4);
    _ebss = .;         /* define a global symbol at bss end */
    __bss_end__ = _ebss;
  } >RAM

  /* User_heap_stack section, used to check that there is enough RAM left */
  ._user_heap_stack :
  {
    . = ALIGN(8);
    PROVIDE ( end = . );
    PROVIDE ( _end = . );
    . = . + _Min_Heap_Size;
    . = . + _Min_Stack_Size;
    . = ALIGN(8);
  } >RAM

 

  /* Remove information from the compiler libraries */
  /DISCARD/ :
  {
    libc.a ( * )
    libm.a ( * )
    libgcc.a ( * )
  }

  .ARM.attributes 0 : { *(.ARM.attributes) }

Observaras que la notacion es totalmente distinta a lo que era con el compilador MPASM.

Citar
Entonces por lo que entiendo, el linker como sabe los rangos de memoria tomara las direcciones de los registros y las "unirá" al respectivo banko (esto para la RAM) y para la memoria de programa tomara lo que esta dentro del main y lo "unirá" desde el 0x0000 de la memoria en adelante y así al final se tendrá el .hex (esta correcto esto???).
El linker esta consciente del tamaño de las seccion y del microcontrolador, por lo cual intenta ubicarlas por el mismo en donde sea.

Luego del proceso de linkeo tenes varias opciones de salida. Podes tener un COF ( que es lo mejor para verlo en el Proteus ) y tambien podes tener un .HEX (que respeta el formato de Intel  https://es.wikipedia.org/wiki/Intel_HEX ) , pero otros ejecutables pueden tambien sacar otros tipos de archivos como .ELF y .BIN

Citar
Con el linker creado debiera enlazarlo con mi código objeto, pero el comando que debo utilizar no se bien como utilizarlo aun (la web habla de enlazado dinámico y estático).
En los microcontroladores no usamos enlazado dinamico creo que nunca, al menos nunca lo realice.
En enlazado dinamico es compilar las "librerias" de forma aparte del programa principal. De esa forma si en algun momento tenes que cambiar la libreria, no debes compilar todo el programa de vuelta, solo cambias esa libreria. Tiene sus ventajas y desventajas.
En el enlazado estatico, compilas todo junto, lo bueno de esto es que si una funciona no se usa, el optimizador simplemente puede quitarlo.


Citar
KILLERJC  me gustaría que pudieras ayudarme con lo que he escrito, verificando los pasos que he puesto si están bien o mal o le falta, etc.

PD: en el código de ejemplo los FUSES no se como se direccionan, ya que su dirección esta en la memoria de programa. Tengo entendido que los punteros  "apuntan" a la RAM  y no se si se puede hacer algo asi:
#define CONFIG        (*((volatile unsigned long *) 0x2000))

Disculpa si es muy largo el texto pero quise ser lo mas explicito y claro posible. Me sera de mucha utilidad que me pudieras corregir y ayudar a construir un .hex 

Y esta parte sabes que ya no tiene importancia ya que no es posible con GCC.

Proba con XC8, lee la salida de compilacion y trata de entender los pasos que hacen, las opciones ,etc.

Desconectado tsk

  • PIC18
  • ****
  • Mensajes: 257
Re:Estructura no identificada
« Respuesta #10 en: 16 de Septiembre de 2017, 12:22:43 »
Asi que el programa va a salir con instrucciones ASM para un microprocesador Pentium por ejemplo y no un PIC, como las computadoras tienen el OS, apenas intentes ejecutar ese programa en tu PC vas a tener un error de memoria.

De hecho produce instrucciones ASM para el micro destino

Un ejemplo sencillo

Código: C
  1. #include <stdio.h>              /* Required for printf */
  2.  
  3. int main (int argc, char * argv[])
  4. {
  5.    printf ("Hello, world!");
  6.  
  7.    return 0;
  8. }

xc16-gcc -S hello.c -o helloXC16.s
Código: ASM
  1. .file "<path>/hello.c"
  2.         .section .const,psv,page
  3. .LC0:
  4.         .asciz  "Hello, world!"
  5.         .section        .text,code
  6.         .align  2
  7.         .global _main   ; export
  8.         .type   _main,@function
  9. _main:
  10.         .set ___PA___,1
  11.         lnk     #4
  12.         mov     w0,[w14]
  13.         mov     w1,[w14+2]
  14.         mov     #.LC0,w4
  15.         mov     w4,[w15++]
  16.         rcall   __printf_0
  17.         dec2    w15,w15
  18.         clr     w4
  19.         mov     w4,w0
  20.         ulnk   
  21.         return 
  22.         .set ___PA___,0
  23.         .size   _main, .-_main
  24.  
  25.         .section __c30_signature, info, data
  26.         .word 0x0001
  27.         .word 0x0000
  28.         .word 0x0000
  29.  
  30. ; MCHP configuration words
  31.  
  32.         .set ___PA___,0
  33.         .end

arm-none-eabi-gcc -S hello.c -o helloARM.c
Código: ASM
  1. .cpu arm7tdmi
  2.         .eabi_attribute 20, 1
  3.         .eabi_attribute 21, 1
  4.         .eabi_attribute 23, 3
  5.         .eabi_attribute 24, 1
  6.         .eabi_attribute 25, 1
  7.         .eabi_attribute 26, 1
  8.         .eabi_attribute 30, 6
  9.         .eabi_attribute 34, 0
  10.         .eabi_attribute 18, 4
  11.         .file   "hello.c"
  12.         .section        .rodata
  13.         .align  2
  14. .LC0:
  15.         .ascii  "Hello, world!\000"
  16.         .text
  17.         .align  2
  18.         .global main
  19.         .syntax unified
  20.         .arm
  21.         .fpu softvfp
  22.         .type   main, %function
  23. main:
  24.         @ Function supports interworking.
  25.         @ args = 0, pretend = 0, frame = 8
  26.         @ frame_needed = 1, uses_anonymous_args = 0
  27.         push    {fp, lr}
  28.         add     fp, sp, #4
  29.         sub     sp, sp, #8
  30.         str     r0, [fp, #-8]
  31.         str     r1, [fp, #-12]
  32.         ldr     r0, .L3
  33.         bl      printf
  34.         mov     r3, #0
  35.         mov     r0, r3
  36.         sub     sp, fp, #4
  37.         @ sp needed
  38.         pop     {fp, lr}
  39.         bx      lr
  40. .L4:
  41.         .align  2
  42. .L3:
  43.         .word   .LC0
  44.         .size   main, .-main
  45.         .ident  "GCC: (GNU Tools for ARM Embedded Processors 6-2017-q2-update) 6.3.1 20170620 (release) [ARM/embedded-6-branch revision 249437]"

avr-gcc -S hello.c -o helloAVR.s
Código: ASM
  1. .file   "hello.c"
  2. __SP_H__ = 0x3e
  3. __SP_L__ = 0x3d
  4. __SREG__ = 0x3f
  5. __tmp_reg__ = 0
  6. __zero_reg__ = 1
  7.         .section        .rodata
  8. .LC0:
  9.         .string "Hello, world!"
  10.         .text
  11. .global main
  12.         .type   main, @function
  13. main:
  14.         push r28
  15.         push r29
  16.         rcall .
  17.         rcall .
  18.         in r28,__SP_L__
  19.         in r29,__SP_H__
  20. /* prologue: function */
  21. /* frame size = 4 */
  22. /* stack size = 6 */
  23. .L__stack_usage = 6
  24.         std Y+2,r25
  25.         std Y+1,r24
  26.         std Y+4,r23
  27.         std Y+3,r22
  28.         ldi r24,lo8(.LC0)
  29.         ldi r25,hi8(.LC0)
  30.         mov r24,r25
  31.         push r24
  32.         ldi r24,lo8(.LC0)
  33.         ldi r25,hi8(.LC0)
  34.         push r24
  35.         rcall printf
  36.         pop __tmp_reg__
  37.         pop __tmp_reg__
  38.         ldi r24,0
  39.         ldi r25,0
  40. /* epilogue start */
  41.         pop __tmp_reg__
  42.         pop __tmp_reg__
  43.         pop __tmp_reg__
  44.         pop __tmp_reg__
  45.         pop r29
  46.         pop r28
  47.         ret
  48.         .size   main, .-main
  49.         .ident  "GCC: (GNU) 4.8.2"
  50. .global __do_copy_data

xc32-gcc -S hello.c -o helloXC32.s
Código: ASM
  1. .file   1 "hello.c"
  2.         .section .mdebug.abi32
  3.         .previous
  4.         .gnu_attribute 4, 3
  5.         .section        .rodata,code
  6.         .align  2
  7. .LC0:
  8.         .ascii  "Hello, world!\000"
  9.         .section        .text,code
  10.         .align  2
  11.         .globl  main
  12.         .set    nomips16
  13.         .set    nomicromips
  14.         .ent    main
  15.         .type   main, @function
  16. main:
  17.         .frame  $fp,24,$31              # vars= 0, regs= 2/0, args= 16, gp= 0
  18.         .mask   0xc0000000,-4
  19.         .fmask  0x00000000,0
  20.         .set    noreorder
  21.         .set    nomacro
  22. # End mchp_output_function_prologue
  23.         addiu   $sp,$sp,-24
  24.         sw      $31,20($sp)
  25.         sw      $fp,16($sp)
  26.         move    $fp,$sp
  27.         sw      $4,24($fp)
  28.         sw      $5,28($fp)
  29.         lui     $2,%hi(.LC0)
  30.         addiu   $4,$2,%lo(.LC0)
  31.         jal     _printf_0
  32.         nop
  33.  
  34.         move    $2,$0
  35.         move    $sp,$fp
  36.         lw      $31,20($sp)
  37.         lw      $fp,16($sp)
  38.         addiu   $sp,$sp,24
  39.         j       $31
  40.         nop
  41.  
  42.         .set    macro
  43.         .set    reorder
  44. # Begin mchp_output_function_epilogue
  45. # End mchp_output_function_epilogue
  46.         .end    main
  47.         .size   main, .-main
  48.         .ident  "GCC: (Microchip Technology) 4.5.2 MPLAB XC32 Compiler v1.34"
  49. # Begin MCHP vector dispatch table
  50. # End MCHP vector dispatch table
  51. # Microchip Technology PIC32 MCU configuration words

xtensa-lx106-elf-gcc -S hello.c -o helloXTENSA.s
Código: ASM
  1. .file   "hello.c"
  2.         .section        .rodata
  3.         .align  4
  4. .LC0:
  5.         .string "Hello, world!"
  6.         .text
  7.         .literal_position
  8.         .literal .LC1, .LC0
  9.         .align  4
  10.         .global main
  11.         .type   main, @function
  12. main:
  13.         addi    sp, sp, -32
  14.         s32i.n  a0, sp, 28
  15.         s32i.n  a15, sp, 24
  16.         mov.n   a15, sp
  17.         s32i.n  a2, a15, 0
  18.         s32i.n  a3, a15, 4
  19.         l32r    a2, .LC1
  20.         call0   printf
  21.         movi.n  a2, 0
  22.         mov.n   sp, a15
  23.         l32i.n  a0, sp, 28
  24.         l32i.n  a15, sp, 24
  25.         addi    sp, sp, 32
  26.         ret.n
  27.         .size   main, .-main
  28.         .ident  "GCC: (crosstool-NG 1.20.0) 4.8.2"

msp430-gcc -S hello.c -o helloMSP430.s
Código: ASM
  1. .file   "hello.c"
  2.         .cpu 430
  3.         .mpy none
  4.  
  5.         .section        .rodata
  6. .LC0:
  7.         .string "Hello, world!"
  8.         .section        .init9,"ax",@progbits
  9.         .p2align 1,0
  10. .global main
  11.         .type   main,@function
  12. /***********************
  13.  * Function `main'
  14. ***********************/
  15. main:
  16.         mov     r1, r4
  17.         add     #2, r4
  18.         sub     #4, r1
  19.         mov     r15, -6(r4)
  20.         mov     r14, -4(r4)
  21.         push    #.LC0
  22.         call    #printf
  23.         add     #2, r1
  24.         mov     #0, r15
  25.         add     #4, r1
  26. .LIRD0:
  27. .Lfe1:
  28.         .size   main,.Lfe1-main
  29. ;; End of function

gcc -S hello.c -o helloX86_64.s
Código: ASM
  1. .file   "hello.c"
  2.         .section        .rodata
  3. .LC0:
  4.         .string "Hello, world!"
  5.         .text
  6.         .globl  main
  7.         .type   main, @function
  8. main:
  9. .LFB0:
  10.         .cfi_startproc
  11.         pushq   %rbp
  12.         .cfi_def_cfa_offset 16
  13.         .cfi_offset 6, -16
  14.         movq    %rsp, %rbp
  15.         .cfi_def_cfa_register 6
  16.         subq    $16, %rsp
  17.         movl    %edi, -4(%rbp)
  18.         movq    %rsi, -16(%rbp)
  19.         movl    $.LC0, %edi
  20.         movl    $0, %eax
  21.         call    printf
  22.         movl    $0, %eax
  23.         leave
  24.         .cfi_def_cfa 7, 8
  25.         ret
  26.         .cfi_endproc
  27. .LFE0:
  28.         .size   main, .-main
  29.         .ident  "GCC: (Ubuntu 4.8.4-2ubuntu1~14.04.3) 4.8.4"
  30.         .section        .note.GNU-stack,"",@progbits

De hecho GCC soporta cerca de las 50 arquitecturas distintas
Saludos

Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re:Estructura no identificada
« Respuesta #11 en: 16 de Septiembre de 2017, 12:47:58 »
Fui muy general al hablar, te agradesco la correccion, y te super agradesco el aporte.

Los ejemplos que pase tratan de MPASM, pense que hubiera sido mas simple de ver para alguien que maneja la arquitectura del PIC16 ya que sus archivos linker son "sencillos", ya que son un poco mas literales al expresar como esta formado.

El quiere implementarlo en un PIC16, donde yo vi unicamente existen para XC16 en adelante como vos mostraste el uso de GCC. No conozco si se bajo alguna toolchain para eso, pero parece que no, asi que seguramente estemos hablando de estrictamente el compilador "gcc".

No tengo conocimiento de que exista para las familias que utilizan el equivalente de XC8. Si es asi es un error mio. Y deben ser estos para que pueda simularlos con Proteus como el quiere.

¿Por que decidi que vaya por el uso de XC8/MPASM y revise su linker ?

Porque al crear el proyecto ya esta todo armado. Por lo cual puede ver la salida sin tener que usar la linea de comandos (aunque XC8 si o si hay que usarlo ). Sin tener que crear el archivo Linker, solamente verlo y poder compararlo con el de otros micros PIC16/18, y observar solo la respuesta de la consola.
Es un inicio, y relativamente sencillo segun mi apreciacion.

Luego si que vaya mas a fondo teniendo una idea basica de que es o que hace. Al menos creo que es la forma mas facil de que el aprenda.
Si existe otra forma, no la conozco, y cualquier aporte es por supuesto bienvenido.

Desconectado JuanjoPic

  • PIC12
  • **
  • Mensajes: 97
Re:Estructura no identificada
« Respuesta #12 en: 16 de Septiembre de 2017, 18:18:39 »
Entonces, me quedo con que GCC no puede realzar una compilación para un pic16f pero si podría para uno de 16 bit  .

Si quisiera hacer una compilación paso a paso (como he expuesto en el paso anterior) debiera hacer los mismo pasos que este tutorial dice
Este tutorial  enseña a utilizar GCC desde la ventana de comandos de windows, yo lo haría lo mismo pero con XC8 y con sus respectivos comando (me imagino que debieran ser los mismos que utiliza GCC, como -o -s etc y algunos otros más que pudieran ser únicos del compilador XC8).

Si lo anterior funciona debiera agregarr el linker. Como dijo KILLERJC

Citar
Este archivo ya te lo provee Microchip ( .lkr ), pero para SU propio linker.

Ingrese a la carpeta donde se instalo XC8 (que en mi caso es C:\Program Files\Microchip\xc8\v1.43) dentro de ella busque los linkers que debieran estar creados ya que los provee Microchip.
Utilizando la barra de búsqueda (ingrese que buscara .lkr) encontré  que los linkers están en la carpeta data, pero en su interior hay solo archivos .lkr para pics 18fxxxx.

Pero como dijo KILLERJC
Citar
Otra cosa distinta es que Microchip en ASM utiliza 2 ejecutables distintos. El primero es el compilador, y el segundo un linker. Mientras que para XC8 utiliza todo el mismo, igual que para GCC
Al parecer es cierto (no es que dude de ti KILLERJC, solo comprobar xD), ya que no encontré un linker para los 16f, entonces XC8 de "alguna" forma compila y enlaza sin un linker.
Si lo hace así, ¿Como sabe el compilador que pic utilizo, ya que el linker expresa los rangos de memoria  y no todos los pics 16f tienen los mis tamaños de RAM y FLASH?.
(creo que me auto respondere...sino por favor me corrijan)
Esa "de alguna forma" que el XC8 realiza la compilación y linkeo  debe ser por algún comando o una serie de ellos que lo logran. Siguiendo el consejo de KILLERJC, compile un proyecto y esto obtengo en la salida de la consola:

Citar
make -f nbproject/Makefile-default.mk SUBPROJECTS= .build-conf
make[1]: Entering directory 'C:/Users/JUANJO/MPLABXProjects/PWM_16f716.X'
make  -f nbproject/Makefile-default.mk dist/default/production/PWM_16f716.X.production.hex
make[2]: Entering directory 'C:/Users/JUANJO/MPLABXProjects/PWM_16f716.X'
"C:\Program Files\Microchip\xc8\v1.43\bin\xc8.exe" --pass1  --chip=16F716 -Q -G  --double=24 --float=24 --opt=default,+asm,+asmfile,-speed,+space,-debug --addrqual=ignore --mode=free -P -N255 --warn=0 --asmlist --summary=default,-psect,-class,+mem,-hex,-file --output=default,-inhx032 --runtime=default,+clear,+init,-keep,-no_startup,-osccal,-resetbits,-download,-stackcall,+clib --output=-mcof,+elf:multilocs --stack=compiled:auto:auto "--errformat=%f:%l: error: (%n) %s" "--warnformat=%f:%l: warning: (%n) %s" "--msgformat=%f:%l: advisory: (%n) %s"    -obuild/default/production/main.p1  main.c
"C:\Program Files\Microchip\xc8\v1.43\bin\xc8.exe"  --chip=16F716 -G -mdist/default/production/PWM_16f716.X.production.map  --double=24 --float=24 --opt=default,+asm,+asmfile,-speed,+space,-debug --addrqual=ignore --mode=free -P -N255 --warn=0 --asmlist --summary=default,-psect,-class,+mem,-hex,-file --output=default,-inhx032 --runtime=default,+clear,+init,-keep,-no_startup,-osccal,-resetbits,-download,-stackcall,+clib --output=-mcof,+elf:multilocs --stack=compiled:auto:auto "--errformat=%f:%l: error: (%n) %s" "--warnformat=%f:%l: warning: (%n) %s" "--msgformat=%f:%l: advisory: (%n) %s"    --memorysummary dist/default/production/memoryfile.xml -odist/default/production/PWM_16f716.X.production.elf  build/default/production/main.p1     
Microchip MPLAB XC8 C Compiler (Free Mode) V1.43
Build date: Jul 24 2017
Part Support Version: 1.43
Copyright (C) 2017 Microchip Technology Inc.
License type: Node Configuration

:: warning: (1273) Omniscient Code Generation not available in Free mode

Memory Summary:
    Program space        used    44h (    68) of   800h words   (  3.3%)
    Data space           used     8h (     8 ) of    80h bytes   (  6.2%)
    EEPROM space         None available
    Data stack space     used     0h (     0) of    50h bytes   (  0.0%)
    Configuration bits   used     1h (     1) of     1h word    (100.0%)
    ID Location space    used     0h (     0) of     4h bytes   (  0.0%)

Al parecer, aqui es donde el XC8 sabe que pic utilizo y asi saber los rangos de memoria
Citar
"C:\Program Files\Microchip\xc8\v1.43\bin\xc8.exe"  --chip=16F716 -G -mdist/default/production/PWM_16f716.X.production.map

Creo que con el comando --chip le digo que pic utilizo para que este sepa los rangos de memorias (ono??)

Ademas comprobe lo que KILLERJC dijo acerca del compilador en ASM. El compilador de ASM, el mpasm, entre a su carpeta raiz y si tiene los linkers de todos los pics 10f, 12f, 16f, 18f, etc. Entonces este compilador si necesita los linkers de los pics.

En resumen, creo que esto deberia hacer para lograr mi "auto-compilacion" y asi mi .hex:
1.- hacer lo que dice el tutorial para poder utilizar el XC8 desde la ventana de comandos y asi poder aplicar los comandos del compilador.
2.- tener creado mi archivo .c (que este caso era LED.c)
3.- encontrar los comandos "minimos" para llevar acabo la compilación hasta llegar a mi .hex

Gracias por tu tiempo y ayuda KILLERJC, estaré atento a tus consejos y ayudas a las interrogantes que he expuesto y pasos que he descrito. (Puede que para algunos sea inútil saber esto y no le tomen mucha importancia, pero créeme que para mi es si es de importancia, ya que es este programa quien al final de cuentas nos crea los archivos que se cargan a los pics)



Desconectado KILLERJC

  • Colaborador
  • DsPIC33
  • *****
  • Mensajes: 8242
Re:Estructura no identificada
« Respuesta #13 en: 16 de Septiembre de 2017, 22:35:06 »
tsk tiene mucha mas experiencia que yo con compiladores. Asi que si alguien tiene la verdad es el.

Respecto del linker en XC8.
En realidad no muestra cuando lo linkea, pense que si lo hacia al mostrar 2 lineas. Mirando un poco el .map generado en el proyecto simple de XC8 me encuentro con esta parte:

Citar
Microchip MPLAB XC8 Compiler V1.36 ()

Linker command line:

--edf=/opt/microchip/xc8/v1.36/dat/en_msgs.txt -cs \
  -h+dist/default/production/XC8C.X.production.sym \
  --cmf=dist/default/production/XC8C.X.production.cmf -z -Q16F84A \
  -o/tmp/xcX5ug00z -Mdist/default/production/XC8C.X.production.map -E1 \
  -ver=XC8 -ASTACK=0Ch-04dh -pstack=STACK -ACODE=00h-03FFh \
  -ASTRCODE=00h-03FFh -ASTRING=00h-0FFhx4 -ACONST=00h-0FFhx4 \
  -AENTRY=00h-0FFhx4 -ABANK0=0Ch-04Dh -ARAM=0Ch-04Dh -AABS1=0Ch-04Fh \
  -ACOMMON=04Eh-04Fh -ASFR0=00h-0Bh -ASFR1=080h-0CDh \
  -preset_vec=00h,intentry,init,end_init -ppowerup=CODE -pcinit=CODE \
  -pfunctab=CODE -ACONFIG=02007h-02007h -pconfig=CONFIG -DCONFIG=2 \
  -AIDLOC=02000h-02003h -pidloc=IDLOC -DIDLOC=2 -AEEDATA=00h-03Fh/02100h \
  -peeprom_data=EEDATA -DEEDATA=2 -DCODE=2 -DSTRCODE=2 -DSTRING=2 -DCONST=2 \
  -DENTRY=2 -k /tmp/xcXJ9c1UP.obj \
  dist/default/production/XC8C.X.production.obj

Parece ser que el compilador XC8 toma como argumento el tipo de PIC que esta usando ( el --chip ), y genera todos los argumentos para llamar al linker, el cual el ejecutable del linker se llama "HLINK" Pero lo hace todo internamente.
Y como se ve, no existe archivo, todos los valores son pasados por parametros al linker.

Citar
Ingrese a la carpeta donde se instalo XC8 (que en mi caso es C:\Program Files\Microchip\xc8\v1.43) dentro de ella busque los linkers que debieran estar creados ya que los provee Microchip.
Utilizando la barra de búsqueda (ingrese que buscara .lkr) encontré  que los linkers están en la carpeta data, pero en su interior hay solo archivos .lkr para pics 18fxxxx.

Igual, tampoco tienen nada esos archivos, en resumen lo hace todo internamente el XC8.
Asi que retiro lo dicho, pienso que XC8 no es el mejor ejemplo para ver esto jeje.

PD: Si queres tenes un PDF que se llama: "MPLAB ® XC8 C Compiler User’s Guide" que habla sobre el linker/compilador, todas las opciones y su comportamiento.

Desconectado JuanjoPic

  • PIC12
  • **
  • Mensajes: 97
Re:Estructura no identificada
« Respuesta #14 en: 17 de Septiembre de 2017, 20:46:07 »
Gracias por la recomendacion KILLERJC.

Ojala que TSK nos entregue de su experiencia en compiladores para que nosotros los novatos podamos aprender  :P