Errores en Simulacion - Codewarrior 6.3

De Wikitronica
Saltar a: navegación, buscar

En el desarrollo de un programa, al momento de una depuración de un proyecto nos puede aparecer una serie de mensajes de error. En muchas ocasiones la causa de estos mensajes de error no es evidente. En este artículo se presenta una explicación de la causa de algunos de los mensajes de error mas comunes.

Error de Valor Fuera de Rango

Error de Valor Fuera de Rango


Este error es muy común a la hora de realizar programas y ocurre cuando la definición de una subrutina o una etiqueta se realiza muy lejos al llamado de la misma. Generalmente se utiliza la instrucción BSR (aunque el problema se presenta en general para cualquier branch que se utilice: BCC, BCS, BEQ, BHCC, BHCS, BHI, BHS, BIH, BIL, BLO, BLS, BMC, BMI, BMS, BNE, BPL, BRA, BRN , BSR).


El error se debe a que el branch posee un offset relativo que indica cuanto se le puede sumar a la dirección actual para obtener la nueva dirección (PC -> PC + $0002 + rel). El ensamblador calcula un offset relativo de 8 bits, como este offset puede ser tanto positivo como negativo tendrá un rango que va desde -128 (salto hacia arriba en el código) hasta 127 (salto hacia abajo en el código), por lo tanto si una subrutina se define a más de 127 lineas por debajo al llamado a la misma, se presentara este error.


Soluciones

Se pueden establecer tres tipos de soluciones para este caso:

A. Si el código principal es muy largo, se debe definir las subrutinas justo después de las llamadas con BSR, una vez realizada cada una de estas realizamos un BRA al código principal

;***************************************************************************************************
;                               Codigo de Ejemplo                                                  *
;***************************************************************************************************
 
; Include derivative-specific definitions
                INCLUDE 'derivative.inc'
;
; export symbols
                ABSENTRY Configurar_SP_COP
;
; definicion de variables

                ORG    Z_RAMStart

Contador:    DS.B 1
Num1:        DS.B 1
Num2:        DS.B 1

; code section

                ORG    ROMStart
 
Configurar_SP_COP:
 
                LDHX   #RAMEnd+1        
                TXS                ; SP / $17FF
 
                LDA   #$42        
                STA   SOPT1        ; Se guarda en SOPT1
                                   ; COPE = 0, COPT = 1, STOPE= 0
                                   ; 0, 0, RSTOPE= 0
                                   ; BKGDPE= 1 --- Habilita el backroung debug mode
                                   ; RSTPE = 0 --- Deshabilita el RESET

Configuracion_Previa:

                BSR Configurar_GPIO
                BSR Configurar_RTC
                BRA main

; -------------------------------------------------------------------
Configurar_GPIO:
           
;Se configura los 6 bits inferiores de PTC y los 2 bits superiores de PTE como salida
;Corresponden a los leds de la tarjeta

                LDA #$3F
                STA PTCDD
                LDA #$C0
                STA PTEDD

                LDA #$3F
                STA PTCD
                LDA #$C0
                STA PTED
           
                RTS

; ---------------------------------------------------------------------------
Configurar_RTC:

                LDA #$04
                STA SCGC2       ; Habilitamos el Clock Gate para el RTC
           
                LDA #00                
                STA RTCMOD    ; Definimos el valor del registro modulo del RTC
           
                LDA #%00011000    ; Configuramos el RTCSC / Reloj configurado a 1ms. Fuente reloj interna 1khz.
                                  ; Interrupciones habilitadas (bit 4)
                                  ; RTIF=0, RTCLKS6=0 RTCLKS5=0
                                  ; RTIE=1, RTCPS3=1, RTCPS2=0
                                  ; RTCPS1=0, RTCPS0=0
                STA RTCSC
          
                RTS

main:

                MOV #10, Contador
                MOV #1, Num1
                MOV #2, Num2
                ...
                ...
                ...

                CLI

                ...
                ...
                ...
                BRA *

;**************************************************************
;*                 RUTINAS DE INTERRUPCION                    *
;**************************************************************
 ;Limpiamos las banderas de interrupcion. Se escribe un 1 en la bandera RTIF  
          
                LDA RTCSC
                ORA #%10000000
                STA RTCSC
   
                ...
                ...   
                ...
   
                RTI

;**************************************************************
;*                 INTERRUPT VECTORS                          *
;**************************************************************
               ORG   $FFFE
               DC.W  Configurar_SP_COP     ; Reset

               ORG   $FFCE
               DC.W  Interrupcion_RTC

B. Por cuestiones de estética del código muchos programadores no podrían elegir la primera solución, como alternativa de ello se puede establecer la siguiente configuración, el cual consiste en sustituir los BSR por etiquetas


Configurar_SP_COP:
 
                LDHX   #RAMEnd+1        
                TXS                ; SP / $17FF
 
                LDA   #$42        
                STA   SOPT1        ; Se guarda en SOPT1
                                   ; COPE = 0, COPT = 1, STOPE= 0
                                   ; 0, 0, RSTOPE= 0
                                   ; BKGDPE= 1 --- Habilita el backroung debug mode
                                   ; RSTPE = 0 --- Deshabilita el RESET

; -------------------------------------------------------------------
Configurar_GPIO:
           
;Se configura los 6 bits inferiores de PTC y los 2 bits superiores de PTE como salida
;Corresponden a los leds de la tarjeta

                LDA #$3F
                STA PTCDD
                LDA #$C0
                STA PTEDD

                LDA #$3F
                STA PTCD
                LDA #$C0
                STA PTED

; ---------------------------------------------------------------------------
Configurar_RTC:

                LDA #$04
                STA SCGC2       ; Habilitamos el Clock Gate para el RTC
           
                LDA #00                
                STA RTCMOD    ; Definimos el valor del registro modulo del RTC
           
                LDA #%00011000    ; Configuramos el RTCSC / Reloj configurado a 1ms. Fuente reloj interna 1khz.
                                  ; Interrupciones habilitadas (bit 4)
                                  ; RTIF=0, RTCLKS6=0 RTCLKS5=0
                                  ; RTIE=1, RTCPS3=1, RTCPS2=0
                                  ; RTCPS1=0, RTCPS0=0
                STA RTCSC

main:

                MOV #10, Contador
                MOV #1, Num1
                MOV #2, Num2
                ...
                ...
                ...

                CLI
                ...
                ...
                ...

                BRA *

C. En vez de aplicar BRS, se puede manejar el comando JSR (Jump Subrutine)eliminado por completo este error, ya que esta última instrucción no presenta limitaciones en cuanto al salto:


Configurar_SP_COP:
 
                LDHX   #RAMEnd+1        
                TXS                ; SP / $17FF
 
                LDA   #$42        
                STA   SOPT1        ; Se guarda en SOPT1
                                   ; COPE = 0, COPT = 1, STOPE= 0
                                   ; 0, 0, RSTOPE= 0
                                   ; BKGDPE= 1 --- Habilita el backroung debug mode
                                   ; RSTPE = 0 --- Deshabilita el RESET

Configuracion_Previa:

                JSR Configurar_GPIO
                JSR Configurar_RTC
main:

                MOV #10, Contador
                MOV #1, Num1
                MOV #2, Num2
                ...
                ...
                ...

                CLI
                ...
                ...
                ...

                BRA *

; -------------------------------------------------------------------
Configurar_GPIO:
           
;Se configura los 6 bits inferiores de PTC y los 2 bits superiores de PTE como salida
;Corresponden a los leds de la tarjeta

                LDA #$3F
                STA PTCDD
                LDA #$C0
                STA PTEDD

                LDA #$3F
                STA PTCD
                LDA #$C0
                STA PTED
           
                RTS

; ---------------------------------------------------------------------------
Configurar_RTC:

                LDA #$04
                STA SCGC2       ; Habilitamos el Clock Gate para el RTC
           
                LDA #00                
                STA RTCMOD    ; Definimos el valor del registro modulo del RTC
           
                LDA #%00011000    ; Configuramos el RTCSC / Reloj configurado a 1ms. Fuente reloj interna 1khz.
                                  ; Interrupciones habilitadas (bit 4)
                                  ; RTIF=0, RTCLKS6=0 RTCLKS5=0
                                  ; RTIE=1, RTCPS3=1, RTCPS2=0
                                  ; RTCPS1=0, RTCPS0=0
                STA RTCSC
          
                RTS

Si el problema no es con el BSR, sino con algún otro branch, una forma de solucionar el error (aunque no es la más eficiente) es hacer que el branch salte a una etiqueta y en esta etiqueta se hace un JMP (jump) que salte a la dirección deseada.

Supongamos que se quieren encender los leds de PTCD si estos se encuentran apagados, sin embargo la rutina Encender_Leds se encuentra muy lejos, entonces:


            LDA #$FF

            CMP PTCD

            BEQ jump

jump:  JMP Encender_Leds

Pantalla en blanco en el True-Time Simulator & Real-Timer Debugger

Al momento de realizar cualquier programa debemos tomar en cuenta el manejo de los vectores de interrupción (Ver Interrupciones.). Cada vector de interrupción se encuentra en una dirección en específico, y cada vector de interrupción es un espacio de memoria de 2bytes. En este espacio de memoria se debe definir siempre la dirección de memoria (PC) en donde se encuentra el código (función) va a atender dicha interrupción (Recordar que existe un vector asociado a cada tipo de interrupción).


El valor por defecto que se encuentra en un vector de interrupción es la dirección 0xFFFF.

Si realizamos un programa en el que no configuramos apropiadamente el vector de interrupción del RESET y simulamos el programa con la opción Full Chip Simulation el mismo realizará la compilación, pero si se realiza un Reset Target Boton reset.png en el True-Time Simulator & Real-Timer Debugger el programa va a buscar en el vector de interrupción del RESET la dirección de la rutina de atención a esa interrupción, pero como no se ha asignado ninguna el valor que se obtiene es 0xFFFF. En este caso la próxima instrucción que se ejecuta es PC=0xFFFF y el programa deja de funcionar. Peor aún, si realizamos la depuración en la opción P&E Multilink/ Cyclone Pro aparecerá la pantalla en blanco sin ejecutar ningún código.


Solución

Para eliminar la pantalla en blanco solo hace falta definir correctamente los vectores de interrupción. Entre los vectores de interrupción mas usados tenemos

;**************************************************************
;*                 Interrupt Vectors                          *
;**************************************************************
            ORG   $FFCE
            DC.W  Vrtc        ; Interrupcion del RTC
          
            ORG   $FFFA
            DC.W  Virq        ; Interrupcion del IRQ

            ORG   $FFFE
            DC.W  Vreset      ; Reset del programa


Para mas información sobre la direccion de origen de los vectores de interrupcion revisar la pagina 54 del reference manual.

Error de Valor Truncado a 1 Byte

Error de Valor truncado a 1 byte


Este error generalmente aparece al compilar cuando en el código se está utilizando una instrucción cuyo modo de direccionamiento no se puede aplicar sobre el operando utilizado, por ejemplo se está trabajando con una instrucción cuyo modo de direccionamiento es directo y un operando fuera de PPAGE 0.

Se sabe que el modo de direccionamiento directo solo funciona para posiciones de memoria entre $0000 y $17FF, (revisar página 51 del reference manual). Un registro u operando en general que se utilice y esté definido fuera de esos rangos de memoria no podrá ser accedido mediante el modo de direccinamiento directo. Un error muy común es colocar:

BSET RTCSC_RTIE, RTCSC

Sin embargo el modo de direccionamiento de BSET es directo y el registro RTCSC se encuentra en la posición de memoria $1830 donde ya no funciona esta instrucción.

Existen otras razones por las cuales Codewarrior muestra este error:

  • Este error se presenta si se trata de cargar al acumulador o a algún registro un valor superior a 255 ($FF). Esto sucede ya que tanto el acumulador como los registros del MC9S08QE128 son de 8 bits, por lo que el máximo número que se puede cargar en ellos es $FF.
  • Hay ocasiones en las cuales este error se presenta cuando se define una variable (con DS.B) en el origen de la RAM, en lugar de hacerlo en Z_RAMStart. El problema se corrige cambiando:
ORG RAMStart

por:

ORG Z_RAMStart

en la sección de variables del código.


  • En ocasiones este error aparece si se esta utilizando una instrucción sobre una variable que no se ha declarado. Es importante verificar que todas las variables que se estén usando en el programa estén declaradas, (preferiblemente en ORG Z_RAMStart) para evitar este tipo de errores.


Error de Definición de Macro Esperada

Error de Valor truncado a 1 byte


Este error de directiva, se presenta cuando el compilador espera la definición de una macro, esto sucede cuando no se deja un espacio (o sangría) antes de escribir la instrucción. Las únicas veces que no se deja sangría antes de escribir una instrucción es cuando se definen variables o se realizan macros. Este error se puede corregir fácilmente colocando unos espacios (o tab) antes de escribir la instrucción.

Si se tiene:

LDA #$00
STA PTCD

El programa dara error. En cambio este funcionara si se coloca:

      LDA #$00
      STA PTCD

Referencia

  • Freescale CodeWarrior 6.3 (CodeWarrior Help System)

Contributors

CeMoron, Nsroger, Racuna