23 sept 2022

BRUCE SPRINGSTEEN

Bruce Frederick Joseph Springsteen nació el 23 de septiembre de 1949, hace 73 años, en Long Branch, Nueva Jersey, Estados Unidos. Tiene ascendencia irlandesa e italiana; hijo de Douglas Frederick Springsteen, un conductor de autobús que pasó mucho tiempo desempleado, y de Adele Ann Zerilli, secretaria. Su abuelo materno nació en Vico Equense, pueblo cercano a Nápoles. Y tiene dos hermanas menores, Virginia y Pamela.

Pasó su infancia en Freehold Borough, pueblo del estado de Nueva Jersey.

Su infancia y adolescencia se vieron marcadas por la severa educación recibida en los colegios católicos a los que asistió y por los apuros económicos de la familia, lo que provocó un cierto sentimiento de inferioridad y rebeldía.

En el año 1958, vio a Elvis Presley cuando actuaba en el show televisivo, de Ed Sullivan. Su primera guitarra le costó 18 dólares en una casa de empeños. En 1965 creó junto a Tex Vinyard y George Theiss, el grupo The Castilles, que fracasaría muy pronto. Tres años después dio vida a otro grupo, llamado Child, formado por Danny Federici, Vini Lopez y él.




John Hammond, el cazatalentos que descubrió a Bob Dylan, Billie Holiday, Aretha Franklin, entre otros, propone a Springsteen realizan una grabación de prueba para Columbia-CBS, la compañía discográfica para la que trabaja. Fueron dos horas de canciones acústicas en las que Bruce hace un recital privado para la discográfica. El 9 de junio de 1972 firma con en esa compañía.

A principios de 1973 sacó el álbum “Greetings from Ausbury Park”. Ese mismo año la CBS le amplía el contrato y sale otro álbum, “The Wild the Innocent & The E Street Shuffle”. En 1984 lanza su mayor éxito de ventas: “Born In The U.S.A.”, que permaneció durante siete semanas seguidas como número uno. Precisamente, el tema que da título al álbum, es una crítica a las miserias de su país, y no un “himno” a los E.E.U.U, como se cree popularmente .


Le siguió “Dancing In The Dark” y el famoso “Live 1975-1985”, un recopilatorio de 5 discos en directo con sus mejores canciones. En 1995, aparece “The Ghost Of Tom Joad” álbum que recuerda a “Nebraska”.

En 2002, publica “The Rising”, primer lanzamiento desde 1984 de un álbum completo de nuevas canciones grabadas con la E. Street Band, y el primer álbum de rock de estudio desde 1992. “The Rising”, con catorce temas nuevos y una versión de “My City of Ruins”, canción que interpretó durante los actos de homenaje a los damnificados por los atentados del 11 de septiembre, dio nombre a la gira y le hizo triunfar en los premios Grammy con tres de estos galardones.



En agosto de 2004 Springsteen, Pearl Jam y el trío de country Dixie Chicks fueron algunos de los 20 músicos que ofrecieron 34 conciertos por nueve estados de EE. UU. procurando que George W. Bush perdiera las elecciones presidenciales.

El 2 de noviembre de 2008 estrenó la canción “Working on a Dream” en un acto de la campaña electoral de Barack Obama. Esta canción formó parte de un trabajo de estudio, “Working on a Dream”, publicado el 27 de enero de 2009.

En su álbum de 2012, “Wrecking Ball”, aparecen estilos, como el folk, gospel y hip-hop. Su siguiente trabajo fue “High Hopes”, presentado el 14 de enero de 2014.

Su “The River Tour” se inició en enero de 2016 y el 14 de diciembre de 2018, se lanzó el álbum en vivo “Springsteen” en Broadway. Su decimonoveno álbum de estudio, “Western Stars”, fue lanzado el 14 de junio de 2019.

El 10 de septiembre de 2020, anunció un nuevo álbum con la E Street Band, ”Letter to You”, que es presentado el 23 de octubre de 2020.

Ha recibido 20 premios Grammy, dos Globos de Oro y un Premio de la Academia y vendido casi 190 millones de álbumes en todo el mundo.

Fue incluido en el “Songwriters Hall of Fame” y en el “Rock and Roll Hall of Fame” en 1999. En 2013 fue nombrado “MusiCares” del año, y en 2016, galardonado con la Medalla Presidencial de la Libertad.



Es apodado como “The Boss” (El jefe), y es conocido sobre todo, por su trabajo con el grupo E Street Band y considerado uno de los artistas más exitosos de la música rock, con ventas que superan los 64,5 millones de álbumes en los Estados Unidos y más de 120 millones a nivel mundial.

Durante la gira de promoción de Born in the U.S.A., conoce a Julianne Philips, con quien se casa en Lake Oswego, Oregón, el 13 de mayo de 1985. Se divorciaron en 1988. Su relación aparece en algunas canciones del álbum de 1987 Tunnel of Love.

En 1991, Después se casa con corista de la E Street Band, Patti Scialfa, con quien tuvo tres hijos: Evan James (1990), Jessica Rae (1991) y Sam Ryan (1994).

Ha sufrido depresión durante décadas y comenzó a enfrentarla con ejercicio corriendo hasta seis millas diarias y levantando pesas. También sigue una dieta principalmente vegetariana.

 




Esperamos que os haya gustado esta publicación. Si es así, no dudes en compartirla.

© Se permite reproducción total o parcial de este contenido, siempre y cuando se reconozca la fuente de información utilizada y se incluya el enlace a este artículo.

Equipo Xanur©2023.

14 sept 2022

MICROCONTROLADORES PROGRAMABLES (y V)

   

Quinta y última publicación sobre Microcontroladores Programables PIC, en la que veremos las interrupciones y el "Watchdog", con aplicaciones prácticas.



INTERRUPCIONES.

No hay una manera sencilla de explicar las interrupciones, pero como su nombre sugiere, una interrupción es un proceso o señal que hace “detener” el microcontrolador, y deje de hacer lo está haciendo, para que haga otra cosa.
Un símil cotidiano, podría ser este: Supongamos que estamos sentados en casa, charlando con alguien. De repente suena el teléfono. Entonces, detenemos la charla, y contestamos al teléfono y tenemos otra conversación, telefónica. Cuando terminamos, colgamos y retomamos la charlar con la persona en nuestra casa.
Esto es una idea de la función que realiza una interrupción de un procesador. El programa principal se está ejecutando según el código, pero cuando ocurre una interrupción, el programa principal se detiene para llevar a cabo otra rutina. Cuando esta finaliza, el procesador vuelve al código principal de nuevo.

En referencia al PIC, este tiene cuatro fuentes de interrupción, y se pueden dividir en dos grupos. Dos de ellas son fuentes de interrupciones que pueden ser aplicadas externamente al PIC, mientras que las otras dos son de procesos internos. Vamos a ver las dos externas aquí:




Si nos fijamos de nuevo en los pines del PIC, veremos que el pin 6 es RB0/INT. La función de RB0 ya la conocemos, es el bit 0 del Puerto B. 
Pero INT significa que este pin puede ser configurado como un una interrupción. Los bits del 4 al 7 del puerto B (pines 10 al 13), también se pueden utilizar para interrupciones. Pero antes de que usemos INT u otros pines del puerto B, necesitamos hacer dos cosas. Primero necesitamos decirle al PIC que vamos a usar las interrupciones. Y Segundo, necesitamos especificar que pin del puerto B usaremos.




Si recordamos el direccionamiento del PIC, hay un registro llamado INTCON, y su dirección es la 0Bh. Dentro de este registro hay 8 bits que pueden ser habilitados o deshabilitados.  Interrupciones Global"). Poniendo este bit a 1 le decimos al PIC que vamos a usar una interrupción.
El bit 4 de INTCON es llamado INTE ("INT Enable", o "Habilita INT"), o dicho de otro modo, que utilizaremos el pin 6 con su función INT, no como RB0. Poniendo este bit a 1 le estamos diciendo al PIC, que RB0 será un pin de interrupción.
Poniendo a 1 el bit 3 de INTCON, llamado RBIE, decimos al PIC que usaremos los bits del 4 al 7 del puerto B como interrupciones.
En este punto el PIC sabe que cuando uno de estos pines cambia a nivel alto o cambia nivel bajo, tiene que parar lo que esté haciendo e ir a una rutina de interrupción. 


Ahora, tenemos que decirle al PIC si la interrupción se va a producir en la transición ascendente de la señal, es decir cuando cambia de 0 Voltios a +5 Voltios, o en la descendente, o sea cuando cambia de +5V a 0V. 
Por defecto, esto está configurado para que sea en la transición ascendente, o flanco de subida de la señal. El flanco de "disparo" se configura en otro registro llamado OPTION, que está en la dirección 81h

El bit en el que estamos interesados es el bit 6, que se llama INTEDG ("INTerrupt EDGe", o "flanco para la interrupción"). Poniendo este a 1 hace que el PIC sea interrumpido en el flanco de subida o transición ascendente y poniéndolo a 0 hace que el PIC sea interrumpido en el flanco de bajada o transición descendente. 
Si necesitamos que el PIC haga la interrupción en el flanco de subida, no necesitamos configurar el bit. Pero, desafortunadamente el registro OPTION está en el Banco 1, lo que significa que hemos que cambiar del banco 0 al banco 1, cambiar el bit del registro OPTION, y después volver al banco 0. 

Lo mejor es hacer todas las operaciones con los registros del banco 1 de una sola vez, tales como configurar los pines de los puertos, etc... y después volver al banco 0 una vez terminado.



Internamente, y paso a paso, esto es lo que se debe hacer para usar interrupciones externas:

1º - Poner a 1 el bit 7 (GIE) del registro INTCON (OBh).
2º - En el mismo registro INTCON:
2.1 - Poner a 1 el bit 4 (INTE), para utilizar el pin 6 como entrada de Interrupción.
  2.2 - O poner a 1 el bit 3 (RBIE), para utilizar los pines del 10 al 13 (bits 4 a 7 del puerto B) como entrada de interrupción.

3º - En el registro OPTION (81h):
  3.1 - Poner a 1 el bit 6 (INTEDG) para activar la interrupción en el flanco de subida (de 0V a +5V).
  3.2 - Poner a 0 el bit 6 (INTEDG) para activar la interrupción en el flanco de bajada(de +5V a 0V).]

Cuando durante la ejecución del programa, sucede una interrupción, ocurren dos cosas. Primero, se activa un “flag”. Este le dice al procesador interno del PIC que ha ocurrido una interrupción. Y segundo, el Contador de Programa, apunta a una dirección particular dentro del PIC.

Flag de Interrupción.

En el registro INTCON, el bit 1 es el flag de interrupción llamado INTF, de "INTerrupt Flag". Entonces, cuando una interrupción ocurre, este flag se pondrá a 1. Si no hay interrupción, el flag seguirá a 0. 
Esto hace que el PIC no puede atender a cualquier otra interrupción de ninguna manera. Al ponerse el flag a 1, y el PIC irá a la rutina de interrupción para procesarla. Si el flag no se pone a 1, seguirá respondiendo a las interrupciones. 
Pero cuando se activa una interrupción, automáticamente pone el flag a 1, pero muy importante, no lo pone de nuevo a 0. Por lo que esta tarea tiene que hacerla el programador.


Posición de Memoria.

Al encender por primera vez el PIC, o si se hace un reset, el Contador de Programa apunta a la dirección 0000h, que está justo al principio de la memoria de programa. 
Sin embargo, cuando ocurre una interrupción, el Contador de Programa apunta a la dirección 0004h

Así que, cuando escribamos nuestro programa con interrupciones, lo primero que tenemos que decirle al PIC es que se salte la dirección 0004h, y mantenga, la rutina de interrupción que empieza en esa dirección 0004h, separada del resto del programa.

Esto es fácil de hacer. Primero, comenzamos nuestro programa con un comando o directiva del ensamblador, llamado ORG. Este comando significa Origen, o inicio. Y lo que le sigue es una dirección. Ya que el PIC comienza en la dirección 0000h, escribiremos "ORG 0000h". Lo siguiente que tenemos que hacer es saltarnos la dirección 0004h. Hacemos esto con una instrucción "GOTO", seguida de la etiqueta que apunte a nuestro programa principal. 

A continuación del "GOTO" ponemos otro comando ORG, pero esta vez seguido de la dirección 0004h. Es después de este comando donde introduciremos la rutina de interrupción. Ahora podemos, o bien escribir directamente nuestra rutina de interrupción seguida de un segundo comando ORG, o bien podemos poner una instrucción "GOTO" que apunte a la rutina de interrupción. 

Después, en la rutina de interrupción, para decirle al PIC que ha llegado al final de la misma tenemos que poner la instrucción "RETFIE" justo al final. Este comando significa "retorna de la rutina de interrupción". Cuando el PIC la ve, el Contador de Programa apuntará a la última posición en la que el PIC estaba antes de que ocurriese la interrupción.


1
2
3
4
5
6
7
8
9
            ORG      0000h      ; El PIC comienza aqui al oncender o reiniciar.
            GOTO     Inicio     ; Al al principio del programa principal.
            ORG      0004h      ; El PIC viene aquí cuando hay una interrupción.
            :                   ; Esta en nuerstra rutoina de interrupción.
            :                   ; con lo que eueramos que haga el PIC.
            :                   ; cuando reciba una interrupción.
            RETFIE              ; Fin de la rutina de interrupción.
Inicio
Principal



Hay dos cosas a tener en cuenta al utilizar interrupciones:

La primera es si los registros que usemos en el programa principal y en la rutina de interrupción son los mismos. Es decir, el contenido del registro, probablemente cambien cuando ocurra la interrupción. Por ejemplo, si usamos el registro W para enviar datos al puerto A en el programa principal, y también lo utilizamos en la rutina de interrupción para mover datos de una posición a otra. Si no vamos con cuidado, el registro W contendrá el último valor que tenía cuando estaba en la rutina de interrupción, y cuando vuelva de la interrupción, este dato se enviará al puerto A. Para evitar esto, dentro de la rutina de interrupción, se tienen que almacenar los contenidos del registro W, antes de usarlos. 

Lo segundo es que tiene que existir un retardo entre que ocurre una interrupción y que pueda ocurrir la siguiente. Como sabes, el PIC tiene un reloj externo que puede ser, o bien un Cristal, o bien una red RC (resistencia-condensador). Independientemente de la frecuencia de reloj, el PIC la divide entre 4 y la utiliza para su reloj interno. Por ejemplo, si usas un cristal de 4MHz, el PIC llevará a cabo las instrucciones a 1MHz. A este tiempo interno se le llama Ciclo de Instrucción. Pues según la hoja de características (datasheet), se debe dejar que pasen de 3 a 4 ciclos de instrucción entre interrupciones. 

Vamos a ver un ejemplo. Vamos a escribir un código que contará el número de veces que un interruptor o pulsador se activa, y después mostraremos ese número. El programa contará de 0 a 9, mostrando en 4 leds en formato binario, y la entrada o interrupción será por RB0. 
La primera cosa que tenemos que hacer es decirle al PIC que salte la dirección donde el Contador de Programa apuntará cuando ocurra una interrupción. 


1
2
3
4
5
6
            org      0x00       ; Aquí apunta el PIC al encender o reiniciar.
            goto     Principal  ; Va al principio del programa principal.
            org      0x04       ; comienzo de la rutina de interrupción.
            retfie              ; Esto indica al PIC el fin de la rutina de interrupción.
                                ; Y el PC volvera a apuntar al programa Principal.
Principal                       ; Cominenzo del Programa Principal.

NOTA: el formato hexadecimal se usa 0x00 o 0x04 en vez de 00h o 04h.


Ahora le vamos a decir que interrupciones vamos a utilizar, y que el pin de interrupción va a ser el pin 6 (RB0):

1
2
3
4
; 
bsf    INTCON,7    ; GIE - Global Interrupt Enable (1= Habiliatdo)
bsf    INTCON,4    ; INTE - RB0 Interrupt Enable (1= Habilitado).
;



Vamos a poner a 0 el flag de interrupción por si acaso, ya que no sabemos cómo está. 

1
2
3
; 
bcf    INTCON,1    ; INTF a 0, por si acaso.
;



Ahora vamos a configurar nuestros dos puertos. Hemos de tener en cuenta que, como estamos utilizando RB0 como pin de interrupción, este debe de ser configurado como entrada:

1
2
3
4
5
6
bsf      STATUS,5     ; Cambiamos al Banco 1.
movlw    0x01         ; 
movwf    TRISB        ; Establecemos RB0 como entrada.
movlw    0x10         ; 
movwf    TRISA        ; Los 4 primeros pines del Puerto A como Salida.
bcf      STATUS,5     ; Vuelve al Banco 0.



Vamos a utilizar una variable llamada CONTADOR para contar y almacenar el número de pulsaciones.

1
2
3
4
5
6
;
Bucle
movlw    CONTADOR,0   ; Movemos los contenidos de CONTADOR a W.
movwf    PORTA        ; Ahora lo movemos al Puerto A.
goto     Bucle        ; y continuamos haciendo esto.
end



Este sería el programa principal, y ahora tenemos que decirle al PIC que hacer cuando ocurra una interrupción.

La interrupción va a ser una conmutación. Lo que queremos que haga el PIC es añadir 1 a la variable CONTADOR cada vez que el interruptor esté cerrado. Sin embargo, solo queremos mostrar los número que el interruptor se cierra, de 0 a 9 veces. Pero, el puerto A tiene 5 bits, y si simplemente incrementamos el valor del puerto, tendremos una cuenta de hasta 31. Pero vamos a utilizar 4 diodos, con los cuales solo podemos mostrar de 0 a 15 (de 0 a F en hexadecimal, o 0000 a 1111 en binario). 

Con estas premisas vamos a escribir la rutina de interrupción. Lo primero que tenemos que hacer es almacenar de manera temporal los contenidos nuestro registro W, ya que lo estamos utilizando para transferir los contenidos de CONTADOR al PORTA. Si no lo almacenamos, entonces podríamos enviar un número completamente diferente como resultado de nuestras operaciones:

1
2
3
; 
movwf    TEMPORAL    ; Almacenamos W en una posición temporal.
;



Lo siguientes que necesitamos hacer es añadir 1 a nuestra variable CONTADOR:

1
2
3
; 
incf    CONTADOR    ; Incrementamos CONTADOR en 1 y ponemos
                    ; el resultado de vuelta en CONTADOR.



Lo siguientes es hacer una comprobación de CONTADOR para ha pasado el valor de 9. La forma en que lo podemos hacer es restándole 10.

1
2
3
; 
movlw    0x0A        ; Ponemos 10 en W
subwf    CONTADOR,0  ; Restamos W a CONTADOR y ponemos el resultado en W.



Como ya vimos en el capítulo Operadores Aritméticos y Lógicos, si restamos un número mayor a un número menor, el flag de Acarreo (CARRY) se pondrá a 1. Este flag también se pondrá a 1 si lo números son iguales y los restamos.

1
2
3
4
5
;
btfss    STATUS,0   ; Comprueba el flag de CARRY. Se activará si 
                    ; CONTADOR es igual o mayor que W.
                    ; Y se activará como resultado de
                    ; la instrucción subwf.




Ahora ya sabemos si el valor de CONTADOR es 9 o más. Así que, si CONTADOR es mayor que 9, lo ponemos de nuevo a 0, y de otro modo vuelve al programa principal para que podamos enviarlo al PORTA

La instrucción BFTSS, se saltará la siguiente instrucción si el flag de CARRY se pone a 1:


1
2
3
4
5
6
7
8
9
10
11
12
;
goto     continua     ; Si CONTADOR es < 10, continua... 
goto     limpiar      ; Si CONTADOR es > 9, lo ponemos a 0.
continua
bcf      INTCON,0x01  ; Ponemos a 0 este flas para permitir más interrupciones.
movfw   TEMPORAL      ; Restaura W el valor de antes de la interrupción.
retfie                ; Salir de la rutina de interrupción.
limpiar
clrf    CONTADOR      ; Ponemos el CONTADOR a 0.
bcf      INTCON,1     ; Ponemos a 0 este flag para permitir mas interrupciones.
retfie                ; Salir de la rutina de interrupción.




Con esto ya tenemos todo lo que necesitamos. Vamos a ponerlo todo junto y a definir los valores de nuestras constantes, justo al principio de nuestro programa. Seguidamente mostramos el listado completo y el esquema del circuito:


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
;**********************************************************;   
; PROGRAMA INTERRUPCION.asm      	FECHA: XX XXXXX 2022   ;
; Programa para contar de 0 a 9 y mostrar en LEDS binario. ;
; Usa el puerto RB0 (Pin 6) y RA (pines 17, 18, 1 y 2)     ;
; Revisión: 1.0       			Programa para PIC16F48A    ;
; Velocidad de Reloj: XTAL externo 4Mhz (1Mhz=1us)          ;
; WatchDog = OFF                     Tipo Reloj:  Cristal      ;
; Autor: XMG                      Por: XANUR2001/ ACME 2022    ;
; Compilado en : MPLAB X IDE v2.05 (MICROCHIP)              ;
; *********************************************************;
            org     0x00           ; Aquí apunta al encender o reset
;*****Establecimiento de constantes *******
INTCON      EQU       0x0B         ; Registro Control de Interrupciones.
PORTB       EQU       0x06         ; Dirección del puerto B.
PORTA       EQU       0x05         ; Dirección del Puerto A.
TRISB       EQU       0x86         ; Dirección del registro Puerto B.
.
TRISA       EQU       0x85         ; Dirección del registro Puerto A.
STATUS      EQU       0X03         ; Dirección del registro STATUS.
CONTADOR    EQU       0x0d         ; Variable para nuestro Contador.
TEMPORAL    EQU       0x0d         ; Almacén temporal para el registro W;
;
            goto      Principal    ; Va al programa principal 
                                    ; saltándose dirección interrupción.
;
;***************RUTINA DE INTERRUPCION*************************** después vuelve
            org       0x04    	   ; Aquí comienza rutina interrupción.
            movwf     TEMPORAL	   ; Almacenamos W en posición temporal.
            incf      CONTADOR,1   ; Incrementamos CONTADOR en 1 y 
                      			   ; ponemos resultado en CONTADOR. 
            movlw     0x0A   	   ; Ponemos 10 en W.
            subwf     CONTADOR,0   ; Restamos W a CONTADOR y ponemos
                                   ; el resultado en W. 
            btfss     STATUS,0	   ; Comprueba flag CARRY. Se activará si
                                   ; CONTADOR es igual o mayor que w, 
                                   ; y activará como resultado subwf.
            goto      continua	   ; Si CONTADOR es <10, continua. 
            goto      limpiar	   ; Si CONTADOR es >9, ponemos a 0
continua
            bcf       INTCON,0x01  ; Poner a 0 el flag para
                             	   ; permitir más interrupciones.
            movfw     TEMPORAL	   ; Restaura W al valor de antes.
                     			   ; de la interrupción. 
            retfie           	   ; Salir de la rutina de interrupción.
limpiar
            clrf      CONTADOR	   ; Pon CONTADOR otra vez a 0.
            bcf       INTCON,1	   ; Poner a 0 el flag para
                                   ; permitir más interrupciones.
            retfie           	   ; Salir de la rutina de interrupción.;
;
;***************FIN RUTINA DE INTERRUPCION*************************
;
;
;***************PROGRAMA PRINCIPAL***********************************
Principal                  	; Comienzo del programa principal.
;
;****************Configura los Registros de Interrupción*************  
            bsf       INTCON,7	   ; GIE enable (1=habilitado)
            bsf       INTCON,4	   ; INTE RB0 (1=habilitado)
            bcf       INTCON,1	   ; INTF - A 0 por si acaso.
;
;****************Configura los puertos*******************************
            bsf       STATUS,5	   ; Cambia al banco 1.
            movwf     TRISB  	   ; Establece RB0 como entrada
            movlw     0x10    	   ;           
            movwf     TRISA   	   ; Pone los 4 primeros pines del   
   				                   ; puerto A como salida
            bcf       STATUS,5	   ; Vuelve al banco 0.
;
;****************Ahora envía el valor de CONTADOR al PORTA***********
Bucle 
            movf      CONTADOR,0   ; Movemos contenidos de CONTADOR a W. 
            movwf     PORTA  	   ; Ahora lo movemos al puerto A. 
            goto      Bucle  	   ; Continuamos haciendo esto.
; 
;;**** Fin del Programa****            
            end
; Algunos compiladores necesitan esta instrucción,
; O por si nos olvidamos poner la instrucción 'goto'.





En el circuito, se puede observar un detalle. Se ha incluido un circuito llamado "anti-rebote" en el pulsador. Esto es para evitar que el PIC "crea" que ha existido más de una pulsación. Esto se consigue con el circuito anti-rebote. Cuando se pulsa y se pone a nivel alto, el condensador se carga. No importa cuántas veces se pulse y vaya a nivel alto (+5V), el condensador solo se cargará una vez. Cuando se suelta el pulsador, el condensador se descarga. De este modo el PIC solo “ve” una pulsación, en vez de un tren de impulsos.
Este "anti-rebote", también se puede realizar mediante código.


WTCHDOG

Ahora vamos a echar un vistazo a un temporizador interno, llamado "Watchdog Timer", que se puede traducir por "temporizador perro guardián".
Para saber su utilidad, veamos un supuesto. Imaginemos que hemos escrito un código, lo hemos compilado, y lo hemos simulado una y otra vez con éxito. Aparentemente todo funciona bien. Entonces, programamos el PIC y lo montamos en su circuito. Sin embargo, después de un largo periodo de funcionamiento, el programa se atasca en algún punto y el PIC se queda en un bucle.

Para solucionar esta posibilidad, se necesita alguna clase de reset, en el caso de que nuestro programa se quede atascado. Este es el propósito del watchdog timer

El funcionamiento del Watchdog es el siguiente. Cuando el watchdog timer (abreviado como WDT) está habilitado, un contador comienza en 00 y se incrementa en 1 hasta que alcanza FF. Cuando pasa de FF a 00 (lo cual es FF+1) el PIC se reiniciará, independientemente de lo que esté haciendo. La única manera de evitar que el WDT reinicie el PIC, es reiniciar el propio WDT poniéndolo de nuevo a 00 durante el programa. 

Para utilizar el WDT, tenemos que saber tres cosas:  
  1. Cuanto tiempo tenemos antes de tener que hacer un reinicio al WDT
  2. Como lo ponemos a cero. 
  3. Tenemos que habilitar el WDT dentro del PIC.


Tiempos de WDT

La hoja de datos del PIC, especifica que el WDT tiene un periodo desde su inicio hasta el final de 18 ms. Esto depende de varios factores, como el voltaje aplicado, la temperatura del PIC, etc... 
La razón de esta aproximación, se debe a que el reloj del WDT es mediante una red RC (Resistencia-Condensador) interna. Así pues, el tiempo de carga de la red RC, depende directamente del voltaje de alimentación. También depende de los valores de los componentes, los cuales cambian ligeramente dependiendo de su temperatura. Así que por comodidad, tomaremos los 18 ms como el tiempo de reinicio del WDT.
Sin embargo, podemos hacer este tiempo mayor. Dentro del PIC hay un elemento llamado Prescaler ("etapa previa de ajuste de escala"). Podemos programarlo, dividiendo el reloj interno de la red RC. Cuanto mayor sea el factor de división, más tiempo tardará el WDT en reiniciarse. El prescaler está localizado en el registro OPTION en la dirección 81h, los bit del 0 al 2 inclusive. Más abajo hay una tabla que muestra las asignaciones de los bits para cada ratio de división y el tiempo de reinicio del WDT:






Estos tiempos son independientes de la frecuencia del reloj externo. Para ayudar a clarificar esto, vamos a suponer que queremos que el WDT reinicie nuestro PIC después de cerca de medio segundo, como tiempo de seguridad ante fallo. El valor más próximo que tenemos es 576 ms o 0,576 segundos. Todo lo que hacemos es enviar b'101' a nuestro registro OPTION, de la siguiente manera:

1
2
movlw              b’101’    ; En hexadecimal sería 0x05.; 
movwf              81h       ; Y este es el registro OPTION.



Pero ahora hay una pequeña trampa. Por defecto el prescaler, está asignado a otro temporizador interno, denominado TMR0. Esto significa que tenemos que cambiar el prescaler al WDT. Para hacerlo hay que poner el bit 3 del WDT del registro OPTION a 1.
Es decir, para poder poner el prescaler a 576 ms, y asignarlo al WDT, Hay que enviar al registro OPTION el valor b'1101
  1. Tenemos que reiniciar el temporizador o contador (TMR0) y ponerlo a 0. 
  2. Luego cambiar al banco 1 para asignar el prescaler al WDT y configurar el tiempo. 
  3. Y después volver al banco 0. 
Este sería el código para hacer esta función:

1
2
3
4
5
6
7
8
Bcf	    STATUS,0	; Nos aseguramos de que estamos en el banco 0
clrf	01h     	; Dirección del temporizador TMR0. puesta a 0.
bsf	    STATUS,0  	; Cambiamos al banco 1.
clrwdt 		    	; reiniciamos el WDT y el prescaler
movlw	b’1101’   	; Seleccionamos el valor del nuevo preescaler a 576ms(bits 0 al 2)
                    ; ; y lo asignamos al WDT(ver bit 3 puesto a 1).
movwf	OPTION    	; y se lo asignamos al WDT
bcf  	STATUS,0  	; Vuelve al banco 0



Acabamos de ver la instrucción CLRWDT, que es la que se utiliza para reiniciar el WDT antes de que este reinicie al PIC. Así que todo lo que tenemos que hacer es calcular en qué punto del código ocurrirá la finalización del tiempo del WDT, y enviar el comando CLRWDT justo antes de este punto, para asegurarnos de que el PIC no se reinicia. 

Si tenemos un código largo, es posible que necesitemos más de un CLRWDT. Por ejemplo, si utilizas el tiempo por defecto 18 ms, entonces tenemos que asegurarnos de que el programa ve un CLRWDT cada 18 ms. 
Así que ahora llegamos al punto donde tenemos que trabajar y ver cuánto tiempo tarda nuestro código en ejecutarse, en tiempo real. 



Temporización de las instrucciones

Como hemos comentada anteriormente, el PIC toma el reloj externo y lo divide por 4. Y este tiempo interno es el llamado ciclo de instrucción. Hasta ahora hemos estado conectando un cristal de 4 MHz a nuestro PIC, por lo que internamente el PIC funcionará a 1Mhz. 
En términos de temporización, esto es:


También hemos visto que algunas instrucciones necesitan un solo ciclo de instrucción para ejecutarlas (1μs), mientras que otras emplearán dos ciclos en ser ejecutadas (2μs).

La hoja de características nos dice cuántos ciclos necesita cada instrucción. La forma más sencilla para recordarlo es muy simple. Asume que todas las instrucciones tardan 1 ciclo. Pero si una instrucción causa que el programa vaya a algún otro sitio, este necesitará 2 ciclos. 

A modo de ejemplo, la instrucción "movwf" requiere solo 1 ciclo, porque solo mueve un dato de un lugar a otro. 
En cambio, la instrucción "goto" tarda 2 ciclos, porque hace que el contador de programa (PC) vaya a otro sitio del programa. 
La instrucción RETURN tarda 2 ciclos, porque hace que el contador de programa vuelva al programa principal.

Pero hay cuatro instrucciones que pueden tardar 1 ó 2 ciclos, ya que dependen de un condicional. Estas son DECFSZ, INCFSZ, BTFSC y BTFSS. Estas instrucciones tienen una cosa en común y es que saltan la siguiente instrucción en caso de cumplirse cierta condición. Y si no se cumple la condición, entonces lleva a cabo la siguiente instrucción. 
Por ejemplo, la instrucción DECFSZ disminuye en 1 el valor almacenado en el registro F. Si el resultado es distinto a 0, entonces ejecuta la siguiente instrucción. Es este caso, la instrucción requiere solo 1 ciclo. Pero si el resultado es igual a 0, entonces la instrucción siguiente se la salta, y ejecuta la siguiente a la anterior. En este caso la instrucción necesita 2 ciclos. 

Para aclarar esto, vamos a mirar un código simple, y trabajaremos sobre los ciclos de instrucción que tarda:

1
2
3
4
5
            movlw         02
            movwf         CONTADOR
Bucle       decfsz        CONTADOR
            goto          Bucle
            end


En la primera instrucción simplemente mueve el valor 02 a W. Esto no causa ningún salto, por tanto es solo 1 ciclo.
La siguiente instrucción es similar, mueve los contenidos del registro W a CONTADOR. De nuevo, esto tardará 1 ciclo.
Ahora, la siguiente instrucción primero decrementa CONTADOR en 1. Esto es 1 ciclo. Después hará una comprobación para ver que CONTADOR es igual a 0. En este momento no lo es, por tanto vamos a la siguiente instrucción.
La siguiente instrucción es una de "goto", y por tanto tarda 2 ciclos.
Volvemos a nuestra instrucción DECFSZ, la que decrementa CONTADOR en 1 de nuevo. Esto tarda otro ciclo. Hace una comprobación para ver si CONTADOR es igual a 0. Esta vez lo es, y por tanto se salta la siguiente instrucción. Para saltarse la siguiente instrucción se requiere otro ciclo. Alcanzamos el final del programa.
Así que en total, con el valor de 02 para CONTADOR, este programa tarda 7 ciclos en total. Si estamos usando un cristal de 4MHz para nuestro reloj, entonces el programa tarda: 





SOFTWARE PROGRAMADOR.

En la estructura del PIC, hay unos elementos llamados "Fuses”,  que podríamos traducirlos como fusibles. No tienen nada que ver con los fusibles eléctricos que conocemos, sino que podríamos denominarlos como conmutadores electrónicos que se pueden "fundir" o establecer  por el programador. 

Uno de estos fusibles, es el que corresponde al  WDT para que pueda operar. 

Para hacerlo efectivo, tenemos dos formas posibles:

Una es escribiendo unas líneas al comienzo del programa, para configurar en el software programador del PIC la habilitación o deshabilitación de una serie de "fusibles". 

1
2
3
4
5
; **** INICIO PROGRAMA ****
    LIST p=16F84A         	; indicamos el PIC vamos a usar
    INCLUDE <p16f84a.inc>	; y la librería de instrucciones
    __CONFIG _XT_OSC & _WDT_OFF & _PWRTE_ON & _CP_OFF
; habilitación/deshabilitación de los fusibles del PIC



La otra forma hacerlo, es habilitar o deshabilitar manualmente en el software programador del PIC. En este último caso, varía dependiendo del software de programación. En cualquier caso, la documentación del programador suele explicar  cómo hacerlo. 

Los programadores gratuitos más usados, son IC-Prog y WinPic, que se puede descargar desde aquí: 

Con cualquiera de ambos, es muy sencillo configurar los fusibles. Basta con hacer clic en cada uno de las cajas de selección, como en las siguientes imágenes de IC-Prog y WinPic, respectivamente:





En el 16F84, tenemos varios “fusibles”. Uno ya lo hemos visto, el WDT y se puede configurar mediante _WDT_ON o _WDT_OFF. Y como hemos observado, tenemos también OSC, PWRT y CP.

Con OSC, configuramos el tipo de oscilador que vamos a usar, teniendo las siguientes opciones:
  • LP o “Low Power Crystal”, usa un cristal de baja potencia, de consumo optimizando.
  • XT o “Crystal/Resonator”, que usa un cristal resonante.
  • HS o “High Speed Crystal/Resonator”, usa un cristal resonante de alta velocidad.
  • RC o “Resistor/Capacitor”, el cual usa un oscilador Condensador-Resistencia.
En las tres primeras, usamos un cristal resonante, y la opción más popular es XT con una combinación de un cristal de cuarzo a 4MHz, con condensadores de 22pF, usando la siguiente configuración:




La opción RC, usa como oscilador formado por un Condensador y una resistencia. Esta configuración reduce los costes, pero por el contrario, los tiempos tienen menos fiabilidad. Esta sería la configuración:





Con PWRT, proporciona al PIC un retardo al encenderlo de 72ms (Nominales). Simplemente lo configuramos con  _PWRTE_ON o _PWRTE_OFF.

Con CP, proporciona una Protección de Código, para evitar copias no deseadas. Se configura con  _CP_ON o _CP_OFF.





Y con esta publicación, damos por terminada esta introducción a los PIC. En futuras entradas veremos ejemplos prácticos aplicados.

También, podéis consultar las publicaciones anteriores:

ENLACES.

Y a continuación, una serie de enlaces útiles sobre lo expuesto:

Hoja de características (Datasheet) del PIC 16F84A®:

Web del Fabricante Microchip®:

MPLAB de Microchip®:

Software PICKit2 Programmer (y otros recursos en Microchip):

NotePad++:

WinPic800:

IC-PROG:

Programador JDM, en Blog Xanur:

Programador PicKit, en Blog Xanur:

Electrónica Digital, en Blog Xanur:





Esperamos que os haya gustado esta publicación. Si es así, no dudes en compartirla.

© Se permite reproducción total o parcial de este contenido, siempre y cuando se reconozca la fuente de información utilizada y se incluya el enlace a este artículo.

Equipo Xanur©2022.