La biblia que voy a pasar consta de:
- Quejas mias

- Ejemplos para ver las diferencias, prueba y error es lo mejor
- Y tratar de explicar finalmente el porque. Asi si sabes como funciona vas a saber que tenes que hacer.
Esto es en general sobre la programacion ASM y para nada algo que afecte a tu problema:Noto que los programas en ASM nunca se hacen como se deberian, en realidad no es un problema, es problema de como es que se enseña ASM buscandole lo mas simple para hacerlo funcionar. Y es por esto que usamos CBLOCK para lo que no es, usamos EQU para tambien cosas que no son, como en tu ejemplo te tomas mas trabajo poniendole ORG a cosas que no deberias proecuparte, nos olvidamos completamente del linker, y a esto me refiero a como se linkean los simbolos entre archivos, etc. Pero como ves esto se sigue haciendo porque simplemente funciona xD y nadie quiere meterse con mayores problemas.
Solo para recordar los pasos que sigue cualquier programador = Precompilar - > Compilar -> Linkear
Ahora si con tu problemaEl problema que tenes es que cuando incluis un archivo de la forma en que lo estas incluyendo ocurre que el compilador agarra copia todo lo del otro archivo y lo pega en tu archivo principal ANTES de compilarlo (directiva de PREprocesamiento).
Voy a seguir con mi ejemplo anterior, el cual funcionaba:
Si tomamos en cuenta lo que dije, sabemos que el archivo final va a ser algo asi:
LIST P=16F84A , r=DEC
;RADIX DEC
INCLUDE <p16f84a.inc>
#define TEST PORTA,0
__CONFIG _CP_OFF & _PWRTE_OFF & _WDT_ON & _XT_OSC
ORG 0
GOTO PRINCIPAL
ORG 4
RETURN
PRINCIPAL:
BSF TEST
GOTO PRINCIPAL
END
Es decir donde esta el include es donde va a parar todo lo del otro archivo.
Probemos otro caso.. Esta ves vamos a poner el include abajo, Usemos esto ( test.inc no cambio ):
LIST P=16F84A , r=DEC
;RADIX DEC
INCLUDE <p16f84a.inc>
__CONFIG _CP_OFF & _PWRTE_OFF & _WDT_ON & _XT_OSC
ORG 0
GOTO PRINCIPAL
ORG 4
RETURN
PRINCIPAL:
BSF TEST
GOTO PRINCIPAL
INCLUDE "test.inc"
END
Ocurre que si ahora intentamos compilar vamos a tener algo asi:
LIST P=16F84A , r=DEC
;RADIX DEC
INCLUDE <p16f84a.inc>
__CONFIG _CP_OFF & _PWRTE_OFF & _WDT_ON & _XT_OSC
ORG 0
GOTO PRINCIPAL
ORG 4
RETURN
PRINCIPAL:
BSF TEST ;Aca linea 16
GOTO PRINCIPAL
#define TEST PORTA,0
END
Y tambien un hermoso error diciendo:
Error[113] /home/fabian/workspace/MPLAB/PIC16asm.X/main.asm 16 : Symbol not previously defined (TEST)
Error[128] /home/fabian/workspace/MPLAB/PIC16asm.X/main.asm 16 : Missing argument(s)
Por supuesto, si lo que estamos intentando usar todavia no fue definido. La definicion se encuentra ABAJO, y el compilador (ojo el compilador es) se queja de que cuando llego a BSF TEST eso no existe!
-------------------------------------------------------------------------------------------------------------------------------------------
SubrutinasEsto para una subrutina no es problema, ¿ por que no ?
Cambiemos nuestros archivos para probarlo:
main.asm
LIST P=16F84A , r=DEC
;RADIX DEC
INCLUDE <p16f84a.inc>
__CONFIG _CP_OFF & _PWRTE_OFF & _WDT_ON & _XT_OSC
ORG 0
GOTO PRINCIPAL
ORG 4
RETURN
PRINCIPAL:
CALL TEST
GOTO PRINCIPAL
INCLUDE "test.inc"
END
test.inc
Rapidamente vemos que ya hay algo raro, como podemos usar PORTA en test.inc si nunca incluimos el .inc del microprocesador alli. Es decir no estaria definido, pero si pensamos que el include es copiar y pegar todo tiene sentido. Esto se realiza antes de la compilacion, entonces al momento de compilar se encuentra con este codigo
LIST P=16F84A , r=DEC
;RADIX DEC
INCLUDE <p16f84a.inc>
__CONFIG _CP_OFF & _PWRTE_OFF & _WDT_ON & _XT_OSC
ORG 0
GOTO PRINCIPAL
ORG 4
RETURN
PRINCIPAL:
CALL TEST
GOTO PRINCIPAL
TEST
BSF PORTA,0
RETURN
END
Lo cual es totalmente valido. Dejo el codigo como se ubica en la memoria:
Line Address Opcode Label DisAssy
1 000 2805 GOTO 0x5
2 001 3400 RETLW 0x0
3 002 3400 RETLW 0x0
4 003 3FFF ADDLW 0xFF
5 004 0008 RETURN
6 005 2007 CALL 0x7
7 006 2805 GOTO 0x5
8 007 1405 BSF PORTA, 0x0
9 008 0008 RETURN
¿ Que ocurre si lo pongo al principio ?Tengo varios lados donde ponerlo obviamente. Uno es aca:
LIST P=16F84A , r=DEC
;RADIX DEC
INCLUDE <p16f84a.inc>
INCLUDE "test.inc"
__CONFIG _CP_OFF & _PWRTE_OFF & _WDT_ON & _XT_OSC
ORG 0
GOTO PRINCIPAL
Tenemos los siguientes errores:
Error[150] /home/fabian/workspace/MPLAB/PIC16asm.X/test.inc 4 : Labels must be defined in a code or data section when making an object file
Error[152] /home/fabian/workspace/MPLAB/PIC16asm.X/test.inc 5 : Executable code and data must be defined in an appropriate section
Error[152] /home/fabian/workspace/MPLAB/PIC16asm.X/test.inc 6 : Executable code and data must be defined in an appropriate section
Y es justamente el problema que tenemos, resulta que ahora estamos intentando poner codigo en un lugar que no esta definido como codigo ni datos. Antes era una directiva de preprocesamiento por lo cual no ocupa espacio y no necesita estar en esos lugares. Una solucion seria ponerlo luego de los vectores de Reset e Interrupcion,
Es decir aca:
ORG 0
GOTO PRINCIPAL
ORG 4
RETURN
INCLUDE "test.inc"
PRINCIPAL:
CALL TEST
GOTO PRINCIPAL
GENIAL! ahora si compilo correctamente, y si vemos como quedo en nuestra memoria, veremos que el codigo se encuentra donde pusimos nuestro include:
Line Address Opcode Label DisAssy
1 000 2807 GOTO 0x7
2 001 3400 RETLW 0x0
3 002 3400 RETLW 0x0
4 003 3FFF ADDLW 0xFF
5 004 0008 RETURN
6 005 1405 BSF PORTA, 0x0
7 006 0008 RETURN
8 007 2005 CALL 0x5
9 008 2807 GOTO 0x7