laboratorio no.6 digi iii
TRANSCRIPT
DIGITALES III
INFORME DE LABORATORIO NO. 6
USO DEL PLL INTERNO COMO OSCILADOR PRINCIPAL
Ángela Paola Beltrán Riveros 20091005009, Nataly Fernanda López Eraso 20071005097
1. Objetivos:
El propósito principal de esta práctica es utilizar otro dispositivo generador de señal de reloj para el microcontrolador el PLL interno.
Como objetivo secundario el uso del microcontrolador como un dispositivo de control digital en "lazo abierto" para variar la posición de un motor paso-a-paso (stepper motor).
Introducir al estudiante en el uso de lenguajes de alto nivel específicamente el lenguaje C para el desarrollo de aplicaciones con microcontroladores.
2. Planteamiento del Problema:
Diseñe y construya un sistema de disparo de proyectiles (cañón). Para el disparo del
proyectil se deberán ajustar previamente los ángulos de elevación (0 a 90º) y de rotación
(0 a 360º), los cuales deberán ser ingresados por medio de un teclado y visualizados en
una LCD. Luego de ajustados los parámetros anteriores se tendrá una tecla definida por
cada grupo de trabajo para el disparo del proyectil (por seguridad el proyectil debe ser un
elemento que no pueda causar ningún tipo de daño, por ejemplo un ping pon).
Es obligatorio el uso del PLL en esta práctica para hacer funcionar el microcontrolador,
esto no implica que cuando se realicen aplicaciones con motor paso el PLL deba ser
utilizado. Deberá utilizarse por lo menos un motor paso a paso en la implementación.
El programa diseñado para solucionar el ejercicio deberá ser desarrollado en lenguaje C.
Sugerencias: Consiga un motor paso a paso y a través del manual o de pruebas determine
las conexiones internas del motor. También determine el número de polos y la capacidad
de desplazamiento entre polos. El número de pasos necesarios para lograr que el motor
gire 360° será un parámetro útil en el programa.
Utilice circuitos de acción sobre el motor que soporten suficientemente su potencia. No
utilice las salidas del microcontrolador directamente porque es muy factible que puedan
dañarse.
3. Análisis y Modelamiento de la Solución
Para construir el sistema de disparo de proyectiles, se utilizaron tres motores de la
siguiente manera:
1. Motor Paso a Paso para ajustar ángulo de giro 0º a 360º
2. Motor-reductor para ajustar el ángulo de elevación 0º a 90º
3. Motor-reductor para disparar el proyectil
Los ángulos son ingresados por medio de un teclado matricial y se visualizan en una
pantalla LCD. Luego de ajustados los parámetros de rotación y elevación se presiona la
tecla “B”, y luego para el disparo del proyectil se presiona la tecla “C”.
PLL: PhaseLockLoop (PLL) (Oscilador por enganche de fase): Usa un oscilador a cristal de baja frecuencia para producir frecuencias de clock más altas.
MÓDULO PLL: El PLL consiste de:
• Oscilador Controlado por Tensión de ancho de banda programable (VCO) • Módulo divisor de frecuencia del VCO programable • Detector de fase • Filtro de Lazo • Detector de Enclavamiento • Opera en Modo “Adquisición” o Modo “Tracking” CGMVCLK es la salida del “PLL module” • Es el exacto múltiplo entero de CGMXCLK • 4 X de la frecuencia interna del Bus (si es seleccionada)
SECUENCIA DE PROGRAMACIÓN DEL PLL 1. Seleccionar la frecuencia de Bus deseada, FBUSDES.
FBUSDES = 8 MHz 2. Calcular la frecuencia de VCO deseada (4 veces la FBusDes), FVCLKDES
FVCLKDES = 4 x FBUSDES
FVCLKDES = 4 x 8 MHz = 32 MHz 3. Elegir una frecuencia práctica de referencia del PLL, FRCLK.
FRCLK = 32,768Khz,típicamente usamos:
Frclk = 32,768Khz y R = 1 (reference clock divider) y P = 0 4. Seleccionar un multiplicador de la frecuencia del VCO, N
N = FVCLKDES / FRCLK (el entero positivo más cercano)
N = 32 MHz / 32,768kHz = 977 (3D1 Hexa) 5. Calcular y verificar la adecuación de las frecuencias del VCO y el Bus, FVCLCK y FBUS.
FVCLK = N x FRCLK
FVCLCK= 977 x 32,768 Khz = 32,014336 MHz
FBUS = (FVCLK) / 4
Fbus = 8,003584 Mhz 6. Seleccionar un multiplicador de rango (pot. De 2) del VCO, E.
De acuerdo a tabla (ver manual) para Fvclk = 32 MHz E = 2 7. Seleccionar un multiplicador de rango lineal del VCO, L.
L = Redondeo (Fvclk / 4 x FNOM)
L=32,014336Mhz / 4 x 38,4Khz = 208,4266
L= 208 (D0 hexa)
Donde FNOM = frecuencia nominal
VCO = 38,4 KHz @ 5.0 Volts 8. Calcular y verificar la frecuencia de centro del rango del VCO, FVRS.
FVRS = L x 2^E x FNOM
FVRS = L x 4 x FNOM= 208 x 4 x 38,4 KHz
FVRS = 31,9488 MHz
[Fvrs - Fvclk] < o = FNOM x 2^E /2 cumple. REGISTROS PLL
Al inicio de todo proyecto se realiza un diagrama de flujo que permite comprender de forma organizada y efectiva la aplicación que se realizará. Por lo tanto el diagrama de flujo realizado en ésta práctica fue el siguiente:
Posteriormente se revisa el hardware a utilizar, en este caso se utilizará:
1 Microcontrolador MC68HC908AP16
1 LCD
1 Teclado Alfanumérico
1 Motor paso-a-paso
5 Motores reductores
1 Batería de 12 v.
1 Cristal de 32 KHz
1 7805
Condensadores varios
Resistencias Varias
1 Pulsador (Reset)
Se decide en que puerto se ubicará cada uno de los dispositivos y se procede a trasncribir
el diagrama de flujo a código.
Finalmente el diagrama eléctrico implementado para el correcto funcionamiento de la
práctica fue el siguiente:
De esta forma se logró el correcto funcionamiento de la aplicación que permitió comprobar
la efectividad del PLL como oscilador principal, el control de un motor paso a paso y el
lenguaje C como lenguaje de programación para microcontroladores.
4. Conclusiones
Se implementó la práctica utilizando el PLL interno del microcontroador, esto permitió ver
que se puede utilizar diferentes cristales para lograr la frecuencia de oscilación que se
requiera para el desarrollo de la práctica en este caso 4 MHz.
Se utilizó el microcontrolador como un sistema de control digital en “Lazo Abierto” que
variaba la posición de un motor paso-a-paso visualizando en la LCD los análogos de
rotación y de elevación.
Se manejó un lenguaje de alto nivel para el desarrollo de la práctica, en éste caso C que
permitió la versatilidad del programa logrando todo lo solicitado en el diseño de forma más
transparente y sencilla que con el ensamblador.
5. Anexos
Código fuente
#include <hidef.h> /* for
EnableInterrupts macro */
#include "derivative.h" /* include
peripheral declarations */
#define Disable_COP() CONFIG1_COPD =
1 //Deshabilitar el COP
//Mensajes en la FLASH
const unsigned char M2[17]={"Ang de
elevacion"};
const unsigned char M1[17]={"Ang de
rotacion "};
const unsigned char
TABLAKBI[8]={0X70,0XF0,0XB0,0XF0,0XD
0,0XF0,0XE0,0XF0};
const unsigned char
TABLAMOTOR2[8]={0XF8,0XF4,0XF2,0XF
1,0XF8,0XF4,0XF2,0XF1};//TABLAMOTOR
const unsigned char
TABLAMOTOR1[8]={0XF1,0XF2,0XF4,0XF
8,0XF1,0XF2,0XF4,0XF8};//TABLAMOTOR
unsigned int POSKBI=0;
unsigned int POSMOTOR1=0;
unsigned int POSMOTOR2=7;
unsigned int ANGULO1=0;
unsigned int ANGULO2=0;
unsigned int KBIENTRA=0;
unsigned int KBISALE=0;
unsigned int POSLCD=0;
unsigned int NTEMP=0;
// PARA LA LCD
#define CLEAR_DIS 0b00000001
//Borrar display
#define MODE_SET 0b00000110
//Incrementar y mover
#define DIS_NOCUR_NOBLI
0b00001100 //Display ON, cursor Off,
cursor Estático
#define DL_N_F 0b00111000
//Interface de 8 bits, 2 lineas
#define E_On() PTC_PTC3 = 1
#define E_Off() PTC_PTC3 = 0
#define RS_On() PTC_PTC2 = 1
#define RS_Off() PTC_PTC2 = 0
// declaracion de rutina de retardo
void delay(unsigned long nroIteraciones){
unsigned long i;
for(i=0;i<nroIteraciones;i++);
}
//LCD
void control(void){
RS_Off();
}
void enviar(int num){
PTA=num;
E_On();
delay(1);
E_Off();
delay(1);
}
void dato(void){
RS_On();
}
void lcdstart(void) {
DDRA=0XFF;
DDRC_DDRC2=1;
DDRC_DDRC3=1;
E_Off();
delay(400);
control();
enviar(DL_N_F);
control();
enviar(MODE_SET);
control();
enviar(DIS_NOCUR_NOBLI);
}
/////////////////////////////
void mensaje1(void){
unsigned long i;
POSLCD=0;
control();
enviar(CLEAR_DIS);
delay(400);
control();
enviar(0x80);
for(i=0;i<17;i++){
dato();
enviar(M1[i]);
}
}
void mensaje2(void){
unsigned long i;
POSLCD=0;
control();
enviar(CLEAR_DIS);
delay(400);
control();
enviar(0x80);
for(i=0;i<17;i++){
dato();
enviar(M2[i]);
}
}
///////////////////////////////////
void motor1(void){
PTB=(TABLAMOTOR2[POSMOTOR1])|(PT
B&0XF0);
POSMOTOR1++;
if(POSMOTOR1==8){
POSMOTOR1=0;
}
}
void rotar1(unsigned long ang){
unsigned int i;
for(i=0;i<ang;i++){
motor1();
delay(1000);
}
}
void motor1a(void){
PTB=(TABLAMOTOR1[POSMOTOR2])|(PT
B&0XF0);
POSMOTOR2++;
if(POSMOTOR2==8){
POSMOTOR2=0;
}
}
void rotar1a(unsigned long ang){
unsigned int i;
for(i=0;i<ang;i++){
motor1a();
delay(1000);
}
}
void motor2(void){
PTC=(~TABLAMOTOR2[POSMOTOR2])|(P
TC&0X0F);
POSMOTOR2++;
if(POSMOTOR2==8){
POSMOTOR2=0;
}
}
void rotar2(unsigned long ang){
unsigned int i;
for(i=0;i<ang;i++){
PTC=(0x50)|(PTC&0X0F);
//motor2();
delay(1000);
PTC=(0xF0)|(PTC&0X1F);
delay(50);
}
PTC=(0xF0)|(PTC&0X0F);
}
void rotar3(unsigned long ang){
unsigned int i;
for(i=0;i<ang;i++){
PTC=(0xA0)|(PTC&0X0F);
//motor2();
delay(500);
PTC=(0xF0)|(PTC&0X1F);
delay(25);
}
PTC=(0xF0)|(PTC&0X0F);
}
///////////////////////////////////
interrupt 2 void int_irq(void){
}
interrupt 15 void int_kbi(void){
KBISALE=PTB&0XF0;
KBIENTRA=PTD&0X0F;
control();
enviar(0xC0+POSLCD);
POSLCD++;
if(KBIENTRA==0X07){
if(KBISALE==0X70){
ANGULO1=NTEMP/(15/2)-1;
rotar1(ANGULO1);
PTB=PTB&0XF0;
POSLCD=0;
NTEMP=0;
mensaje2();
}
if(KBISALE==0XB0){
ANGULO1=NTEMP/(15/2);
rotar1a(ANGULO1);
PTB=PTB&0XF0;
POSLCD=0;
NTEMP=0;
mensaje2();
}
if(KBISALE==0XD0){
ANGULO2=NTEMP;
rotar2(ANGULO2*2);
POSLCD=0;
NTEMP=0;
mensaje1();
}
if(KBISALE==0XE0){
ANGULO2=NTEMP;
rotar3(ANGULO2);
POSLCD=0;
NTEMP=0;
mensaje1();
}
}
if(KBIENTRA==0X0B){
if(KBISALE==0X70){
dato();
enviar('3');
NTEMP=3+NTEMP*10;
}
if(KBISALE==0XB0){
dato();
enviar('6');
NTEMP=6+NTEMP*10;
}
if(KBISALE==0XD0){
dato();
enviar('9');
NTEMP=9+NTEMP*10;
}
if(KBISALE==0XE0){
dato();
enviar('°');
}
}
if(KBIENTRA==0X0D){
if(KBISALE==0X70){
dato();
enviar('2');
NTEMP=2+NTEMP*10;
}
if(KBISALE==0XB0){
dato();
enviar('5');
NTEMP=5+NTEMP*10;
}
if(KBISALE==0XD0){
dato();
enviar('8');
NTEMP=8+NTEMP*10;
}
if(KBISALE==0XE0){
dato();
enviar('0');
NTEMP=0+NTEMP*10;
}
}
if(KBIENTRA==0X0E){
if(KBISALE==0X70){
dato();
enviar('1');
NTEMP=1+NTEMP*10;
}
if(KBISALE==0XB0){
dato();
enviar('4');
NTEMP=4+NTEMP*10;
}
if(KBISALE==0XD0){
dato();
enviar('7');
NTEMP=7+NTEMP*10;
}
if(KBISALE==0XE0){
PTB=(0XF0)|(PTB&0XF0);
delay(5000);
PTB=(0XF1)|(PTB&0XF0);
delay(2500);
PTB=(0XF0)|(PTB&0XF0);
delay(5000);
PTB=(0XF1)|(PTB&0XF0);
delay(2500);
PTB=(0XF0)|(PTB&0XF0);
delay(5000);
PTB=(0XF1)|(PTB&0XF0);
delay(2500);
PTB=(0XF0)|(PTB&0XF0);
delay(5000);
}
}
delay(2000);
KBSCR_ACK=1;
}
interrupt 7 void int_tim1(void){
T1SC_TOF=0;
PTB=TABLAKBI[POSKBI]|(PTB&0X0F);
POSKBI++;
if(POSKBI==8){
POSKBI=0;
}
}
void main(void) {
Disable_COP();
PCTL=0x00;
PBWC_AUTO=1;
PMSH=132;
PMRS=32 ;
PCTL_PLLON = 1;
while(PBWC_LOCK != 0);
PCTL_BCS = 1;
//PTC=0;
lcdstart();
mensaje1();
DDRD_DDRD7=1;
DDRB=0XFF;
DDRC=0XFF;
PTB=0;
PTD_PTD7=0;
KBSCR_IMASK=1;
KBIER=0XFF;
KBSCR_ACK=1;
KBSCR_IMASK=0;
T1SC=0b01110011;
T1MOD=2000;
EnableInterrupts;
T1SC_TSTOP=0;
for(;;) {
}
}