Taller de Microcontroladores MSP430
Taller de Microcontroladores MSP430
Taller de Microcontroladores MSP430
1 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
Contenido
1 Introduccin a los microcontroladores
2 MSP430 y CCS
2.1 Por qu MSP430?
2.2 Qu necesitamos para empezar a programar?
2.3 Elementos bsicos
2.4 Archivos Importantes
3 Manipulando los registros del microcontrolador
3.1 Lgica Binaria
3.1.1 NOT (~)
3.1.2 AND (&)
3.1.3 OR (|)
3.1.4 OR exclusivo (^)
3.1.5 Suma (+)
3.2 Qu es un registro?
3.3 Enmascaramiento de Registros
3.3.1 Elevacin de bits
3.3.2 Hundimiento de bits
3.4 Ejemplo: Manipulando el registro Watchdog Timer
4 GPIO (General-purpose input/output)
4.1 Registros importantes
4.1.1 PxSEL, PxSEL2
4.1.2 PxDIR
4.1.3 PxOUT
4.1.4 PxIN
4.1.5 PxREN
4.2 Ejemplo 1: Encendido de LEDs
4.2.1 Ejemplo 1.1
4.2.2 Ejemplo 1.2
4.2.3 Ejemplo 1.3
06/07/2015 03:27 p. m.
2 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
Microcontrolador se puede describir en trminos muy simplificados como un computador pequeo. Es un chip
que se puede programar para una aplicacin especfica, es capaz de ejecutar un programa de manera secuencial
y de responder a estmulos externos. En general, todos los microcontroladores son capaces de:
Operar a una frecuencia mayor a unos cuntos MHz.
Guardar datos en sus registros y realizar operaciones matemticas y lgicas.
Configurar entradas o salidas digitales.
Generar interrupciones relacionadas a algn evento para responder adecuadamente ejecutando un trozo
de cdigo especfico.
Cada tipo de microcontrolador se caracteriza de los dems segn su frecuencia de operacin y los recursos o
mdulos que tiene disponibles. En este taller revisaremos los siguientes mdulos:
GPIO (General-purpose input/output).
Timers (Contadores de ciclos de reloj).
Conversor Anlogo Digital (ADC).
06/07/2015 03:27 p. m.
3 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
MSP430 y CCS
Por qu MSP430?
Si bien es cierto en la actualidad existe una gran cantidad de microcontroladores en el mercado, como los AVR
de ATMEL (Arduino los ocupa), los PIC de microchip o el 8051 de Intel, en ICARO hemos decidido optar por
la tecnologa de Texas Intrument (MSP430) ya que cuentan con un alto desempeo, lo que los pone a la altura
de un PIC, son sencillos de programar (se basa en el lenguaje C), no necesitan un perifrico programador
externo y adems es muy barato: 9.9 dolares incluyendo costos de envio! . Ms informacin.
(http://www.ti.com/ww/en/launchpad/launchpads-msp430.html#tabs)
Elementos bsicos
Para la realizacin de este taller se necesita:
Launchpad MSP430 con el chip M430G2553
Cable USB
Software Code Composer Studio (CCS). Descargar (> 1Gb,
requiere registro) (http://processors.wiki.ti.com/index.php
/Download_CCS)
Placa de testeo (Entregada por ICARO).
Archivos Importantes
Launchpad
Descargar Userguide. Gua de usuario muy detallada que incluye todo lo que se puede hacer con el
MSP430 y qu registros modificar para lograr lo que se quiere.
Descargar msp430g2553.h. Archivo de definiciones en lenguaje C para el chip msp430g2553. Incluye
nombres para todos los registros y tipos de comportamiento, para hacer ms llevadera la programacin.
06/07/2015 03:27 p. m.
4 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
microcontroladores es totalmente digital, donde las cantidades y direcciones de memoria son representadas con
nmeros binarios.
Lgica Binaria
En la lgica binaria existen solo dos valores, 1 y 0. Estos valores son representados por un voltaje, generalmente
Vcc para el 1 y tierra para el 0. A un nmero binario de una cifra se le llama bit, mientras que a un nmero
binario de 8 bits (8 cifras) se le llama byte.
Decimal
Binario
~A
AND (&)
A B A&B
0 0
0 1
1 0
1 1
OR (|)
A B A|B
0 0
0 1
1 0
1 1
OR exclusivo (^)
06/07/2015 03:27 p. m.
5 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
A B A^B
0 0
0 1
1 0
1 1
Suma (+)
A
A+B
Carry
Notar que en la suma, el resultado es equivalente a hacer (A | B), y el carry es equivalente a hacer (A & B).
Todas estas operaciones se pueden hacer sobre nmeros de ms bits, aplicando la operacin para cada bit por
separado.
A
A&B
Qu es un registro?
Podemos pensar, y sin entrar en detalles de la electrnica de por medio, en un registro como la una unidad mas
bsica de memoria del microcontrolador. Por lo general un registro es nmero de 8 bits (1 byte) que guarda
informacin de dos tipos:
1. Registros que guardan informacin variable con la que podemos operar durante la ejecucin de nuestro
programa.
2. Registros que guardan informacin sobre la configuracin del microcontrolador y que definen cmo se
comporta y qu debe hacer en determinadas circunstancias.
Revisemos el siguiente cdigo C:
int8 A;
A = 0b10110010;
A = 0xB2;
A = 178;
//
//
//
//
Definicin
Asignacin
Asignacin
Asignacin
06/07/2015 03:27 p. m.
6 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
C
C
C
C
C
C
C
//
//
//
//
//
//
//
= ~A;
= A &
= A |
= A +
= A ^
&= B;
|= A;
B;
B;
B;
B;
C = NOT A
C = A AND B
C = A OR B
C = A SUM B
C = A XOR B
Equivalente a C = C & B;
Equivalente a C = C | A;
Es importante destacar que si la suma de dos nmeros de 8 bits resulta en un nmero mayor a 8 bits, y el registro
de destino tiene 8 bits, el resultado ser truncado, dejando como resultado los 8 bits menos significativos.
Enmascaramiento de Registros
Siguiendo con la misma idea, las dos ltimas lneas del cdigo anterior representan un "enmascaramiento" del
registro C. sto porque se le est aplicando una operacin sobre s mismo. Se pueden distinguir dos tipos de
enmascaramiento:
Elevacin de bits.
Hundimiento de bits.
Elevacin de bits
Si se tiene dos registros A y B y se desea elevar los bits de B en A, basta con realizar la operacin OR entre
ellos. A = A | B.
Esto significa tomar los bits que son igual a 1 en el registro B y hacerlos igual a 1 en el registro A.
A
1 0
1 1
0 0
1 0
1 1
0 1
1 0
1 1
A=A|B
1 1
1 1
1 0
1 1
Hundimiento de bits
Si se tiene dos registros A y B y se desea hundir los bits de B en A, es necesario negar el registro B y luego
aplicar un AND con el registro A, es decir, A = A & ~B.
Esto significa tomar los bits que son igual a 1 en el registro B y hacerlos igual a 0 en el registro A.
A
1 0 1 1 0 0 1 0
~B
0 0 1 0 0 1 0 0
A = A & ~B
0 0 1 0 0 0 0 0
06/07/2015 03:27 p. m.
7 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
int8 A = 0b00010010;
int8 B = 0b00010001;
// Definicin de registros
A |= B;
A &= ~B;
El cdigo muestra la estructura bsica de los programas que escribiremos. La primera lnea incluye el archivo de
definiciones que nos ayudar en la programacin. Luego se define el mtodo main(), que representa la puerta de
entrada a nuestro programa. El mtodo main() se ejecuta secuencialmente lnea por lnea hasta que termina. En
este tipo de programas es tpico ver la aparicin de un while infinito, que se ejecuta cclicamente mientras el
microcontrolador est encendido.
Antes del while infinito suelen encontrarse definiciones para los distintos registros del microcontrolador, y que
definen su comportamiento.
En el cdigo slo se ve una lnea que deshabilita el whatchdog timer modificando el registro WDTCTL. Notar que
para definir el registro se utilizan otros dos registros que no hemos definido anteriormente (WDTPW y WDTHOLD).
Esto es posible ya que todos estos nombres estn previamente definidos en el archivo msp430.h.
Finalmente, es importante mencionar que los nombres de los registros no son al azar y coinciden con los
nombres que se manejan en el userguide. Para ver las posibilidades de configuracin del registro WDTCTL, revisar
la pgina 355 del userguide.
Registros importantes
06/07/2015 03:27 p. m.
8 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
Para manipular cada pin GPIO se deben configurar los siguientes registros.
PxSEL, PxSEL2
La combinacin entre PxSEL y PxSEL2 determinar la funcin de cada pin, permitiendo optar entre I/O,
funcin del perifrico primario, etc. Prcticamente en todas las aplicaciones utilizaremos I/O.
Los registros PxSEL y PxSEL2 son del tipo escritura y por defecto el valor de ambos es 0.
PxDIR
Corresponde a un registro de escritura en el cual se determina si cada pin seleccionado anteriormente como I/O
es de entrada (I) o salida (O). Su valor por defecto es 0.
Bit = 0: Pin de entrada.
Bit = 1: Pin de salida.
PxOUT
Corresponde al valor que escribiremos en los pines seleccionados como Output.
Bit = 0: Output low.
Bit = 1: Output high.
PxIN
Corresponde a un registro solo de lectura el cual almacena el valor de los pines de entrada.
Bit = 0: Input low.
Bit = 1: Input high.
PxREN
Registro solo de escritura que permite habilitar las resistencias de Pullup/Pulldown en los pines que fueron
puestos como entrada.
Bit = 0: Resistencias de Pullup/Pulldown desabilitadas.
Bit = 1: Resistencias de Pullup/Pulldown habilitadas.
Para determinar si la resistencia puesta en la entrada corresponde a Pullup o Pulldown debemos utilizar el
registro PxOUT.
Bit = 0: Resistencia de Pulldown.
Bit = 1: Resistencia de Pullup.
06/07/2015 03:27 p. m.
9 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
Ejemplo 1.1
En este ejemplo buscamos implementar un cdigo que haga parpadear un LED. Esto se logra cambiando el valor
de una salida de 1 a 0 y viceversa, a una frecuencia que sea apreciable. (Recuerda que si el cambio es muy
rpido no podrs verlo).
/*
Cdigo que prende un LED espera un tiempo, luego apaga
el LED.
En este caso usaremos el LED de la tarjeta que se
encuentra en el pin 0 del puerto 1 (P1.0)
*/
#include <msp430.h>
#include <inttypes.h>
//inclusiones.
void main(){
WDTCTL= WDTPW+WDTHOLD;
//funcion principal
//Apagamos el watchdog
P1SEL= 0x00;
P1DIR|= BIT0;
P1OUT|=BIT0;
while(1){
//Loop infinito
P1OUT|=BIT0;
//prende el LED
__delay_cycles(100000); //espera
P1OUT&=~BIT0;
//apaga el LED
__delay_cycles(100000); //espera
}
}
//Inlcusiones
void main(){
//Funcin principal
WDTCTL= WDTPW+WDTHOLD;
P1SEL= 0x00;
P1DIR|= (BIT0+BIT6);
P1OUT|=BIT0;
P1OUT&=~BIT6;
while(1){
__delay_cycles(100000);
P1OUT^=BIT6;
P1OUT^=BIT0;
}
06/07/2015 03:27 p. m.
10 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
En esta oportunidad hemos utilizado la funcin XOR la cual se encarga de levantar los bit que estaba en 0 y
bajar los que estaban en 1. De este modo el parpadeo solo necesita una sola linea.
Ejemplo 1.3
Ahora agregaremos la posibilidad de cambiar la frecuencia de parpadeo de los LED por medio de un botn
como entrada. La idea es que cada vez que se presione el botn el LED parpadee ms rpido, luego vuelve a la
frecuencia original.
/*
Los LED se encuentran en los pines 0 y 6 del puerto 1
El botn se encuentra en el pin 3 del puerto 1
*/
#include <msp430.h>
#include <inttypes.h>
int i=0;
int T=30000;
//Inculsiones
//Declaracin de variables.
void main(){
WDTCTL= WDTPW+WDTHOLD;
P1SEL= 0x00;
P1DIR|= (BIT0+BIT6);
//Salidas
P1DIR&=~BIT3;
P1REN|=BIT3;
//Entradas
//Pull-down para la entrada
P1OUT|=BIT0;
P1OUT&=~BIT6;
while(1){
for(i=0;i<T;i++);
//primer for
if((P1IN&BIT3)==0){
T=T-1500;}
// primer if
P1OUT^=BIT6;
P1OUT^=BIT0;
if(T<=1500){T=30000;}
//segundo if
}
}
Al principio se realizan las mismas declaraciones de siempre. Al momento de definir las salidas hemos agregado
las lineas correspondiente a las entradas. Dentro del while, usamos el primer for para esperar T ciclos vacos.
Luego entramos al primer if, en ste preguntamos si la entrada es igual a 0. De ser as, entonces el tiempo de
espera T se disminuye. Luego hacemos parpadear los LEDs. El segundo if se preocupa de revisar las
condiciones de borde para que T siempre sea un nmero valido.
Ejemplo 1.4
Ahora implementaremos el mismo cdigo anterior con la diferencia principal de que utilizaremos interrupciones.
En general stas son tiles ya que nos permiten ahorrarnos lineas de cdigo y implementar soluciones ms
eficientes. El programa se efectuara de forma normal hasta que ocurra un evento especifico (por ejemplo que se
06/07/2015 03:27 p. m.
11 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
presione un botn). En ese caso el programa interrumpe su ejecucin y se salta hasta la rutina de interrupcin.
Una vez terminada esta vuelve a ejecutarse de forma normal.
#include <msp430.h>
#include <inttypes.h>
int i=0;
int T=30000;
void main(){
WDTCTL= WDTPW+WDTHOLD;
P1SEL= 0x00;
P1DIR|= (BIT0+BIT6);
P1DIR&=~BIT3;
P1REN|=BIT3;
P1IE|=BIT3;
P1IES|=BIT3;
P1IFG&=~BIT3;
P1OUT|=BIT0;
P1OUT&=~BIT6;
_BIS_SR(GIE);
while(1){
for(i=0;i<T;i++);
P1OUT^=BIT6;
P1OUT^=BIT0;
if(T<=1500){T=30000;}
}
}
//Rutina de interrupcin.
#pragma vector= PORT1_VECTOR
__interrupt void Led_ISR (void){
P1IFG&=~BIT3;
T=T-2000;
}
Como podemos ver cuando se presione el botn el programa se interrumpir y se salta hasta la rutina de
interrupcin. En ella se acorta el periodo de espera y luego se regresa al cdigo original. Como podemos ver con
esta solucin no es necesario revisar en cada iteracin si es que esta apretado o no el botn, el periodo T se
acortara solo cuando sea necesario.
Ejemplo 1.5
Finalmente en el siguiente cdigo se muestra como realizar definiciones a conveniencia tanto de variables como
de funciones. El programa es igual al ejemplo 1.4 en cuanto a funcionalidad se refiere.
#include <msp430.h>
#include <inttypes.h>
#define led1 BIT0
#define led2 BIT6
void led_toggle(uint8_t led);
void led_init();
06/07/2015 03:27 p. m.
12 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
int i=0;
int T=30000;
void main(){
WDTCTL= WDTPW+WDTHOLD;
led_init();
_BIS_SR(GIE);
while(1){
for(i=0; i<T;i++);
led_toggle(led1+led2);
if(T<=1500){T=30000;}
}
}
ADC
Ejemplo 1: Uso bsico del ADC
#include <msp430.h>
void main(void) {
WDTCTL = WDTPW + WDTHOLD;
// Se detiene el watchdog
// ADC
ADC10CTL0 = SREF_0 + ADC10SHT_2 + ADC10ON;
ADC10CTL1 = INCH_5 + SHS_0 + ADC10DIV_0 + ADC10SSEL_0 + CONSEQ_0;
ADC10AE0 = BIT5;
ADC10CTL0 |= ENC;
// LEDs
P1SEL = 0;
P1DIR |= BIT0 + BIT6;
//
//
//
//
06/07/2015 03:27 p. m.
13 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
while(1){
__delay_cycles(100000);
ADC10CTL0 |= ADC10SC;
while( ADC10CTL1 & ADC10BUSY );
// Esperamos un poco
// Empieza conversin del ADC
// Espero a que la conversin est lista
/*
* ADC10MEM guarda el valor de la conversin digital.
* Es un registro de 10 bits, por lo que su valor mximo es 2^10 = 1024
* */
if( ADC10MEM > 512 ){
P1OUT |= BIT0;
P1OUT |= BIT6;
} else {
P1OUT &=~ BIT0;
P1OUT &=~ BIT6;
}
}
}
Comunicacin UART
Ejemplo 1: Enviando un caracter
#include <msp430.h>
void main(void) {
WDTCTL = WDTPW + WDTHOLD;
// Se detiene el watchdog
//
//
//
//
/*
* Los siguientes registros configuran la velocidad de transmisin: 9600 baud con 16.000.000 HZ
* Las configuraciones posibles estn listadas en el userguide, pgina 435.
*
* */
UCA0BR0 = 1666;
UCA0BR1 = 1666>>8;
UCA0MCTL = 6<<1;
UCA0CTL1 &= ~UCSWRST;
// **Initialize USCI state machine**
while (1){
__delay_cycles(100000);
while (!(IFG2&UCA0TXIFG));
UCA0TXBUF = 'N';
}
06/07/2015 03:27 p. m.
14 de 15
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
// EL caracter "\n" indica un salto de lnea en Windows, til para mejorar la lectur
void UART_TXchar2();
void main(void) {
WDTCTL = WDTPW + WDTHOLD;
// Se detiene el watchdog
//
//
//
//
while (1){
__delay_cycles(100000);
UART_TXchar2(palabra);
}
}
// Para enviar strings (arreglo de char), es necesario enviar cada char individualmente
void UART_TXchar2( unsigned char *c )
{
int i = 0;
for(i;i<20; i++){
if(c[i] == 0){
break;
}else{
while (!(IFG2&UCA0TXIFG));
// USCI_A0 TX buffer ready?
UCA0TXBUF = c[i];
// Envo el caracter "i" del arreglo de chars
}
}
}
06/07/2015 03:27 p. m.
15 de 15
Pin Funcionalidad
http://web.ing.puc.cl/~ieee/wiki/index.php?title=Taller_de_Microcontrol...
Comentario
P1.3 UP
Entrada digital
P1.4 DOWN
Entrada digital
P1.5 Velocidad
P1.6 LEFT
Entrada digital. Es necesario desconectar el jumper del led para poder ocuparlo como
entrada digital.
P1.7 RIGHT
Entrada digital
06/07/2015 03:27 p. m.