Академический Документы
Профессиональный Документы
Культура Документы
Cdigo de la pareja:
MT-10
NDICE GENERAL
1 INTRODUCCIN...................................................................................................................2 2 DIAGRAMA DE SUBSISTEMAS......................................................................................... 3 3 DESCRIPCIN DEL SUBSISTEMA HARDWARE............................................................ 4 4 DESCRIPCIN DEL SUBSISTEMA SOFTWARE............................................................10 5 PRINCIPALES PROBLEMAS ENCONTRADOS............................................................. 15 6 MANUAL DE USUARIO..................................................................................................... 16 7 BIBLIOGRAFA................................................................................................................... 17
El sistema es fcilmente extrapolable no slo a equipos de aire aconcionado, sino cualquier otro cuyo control remoto est basado en infrarrojos. En general podemos distinguir dos familias dentro de los mandos a distancia: con y sin memoria. Los primeros son a los que nos dedicaremos. En este tipo de mandos el emisor de la trama no se limita a enviar un cdigo asignado a cada botn, sino que reenva la configuracin completa al dispositivo, independientemente del botn pulsado. Esto entraa un grado de complejidad mayor respecto al mando sin memoria, como puede ser el de una televisin estndar. Sin embargo, aunque en este momento nos centramos en un equipo de aire acondicionado, el sistema pretende poder ser capaz en un futuro de 'aprender' y gestionar controles remotos de ambos tipos.
2 Diagrama de subsistemas
Las especificaciones del Tulio incluyen: Comunicacin radio en 868MHz Comunicacin con dispositivos externos: UART, SPI, I2C, SMBUS Conversores analgico digitales Salidas/entradas de propsito general Temporizadores internos
Esquema elctrico. El nodo de control consta de: Una Raspberry Pi en la cual, mediante una interfaz de usuario se podr seleccionar la trama a enviar, el tiempo de bit y la frecuencia de portadora. En l correr un servidor basado en JavaScript que proporcionar una interfaz sencilla desde la que configurar la informacin a enviar y un botn para enviarla. Un Tulio, que se comunicar con la Raspberry Pi mediante UART, recogiendo la informacin indicada por el usuario y envindola por radio al nodo del aire acondicionado. El cdigo implementado se describe en el apartado de software.
Un display LCD conectado al GPIO de Raspberry que nos ser til a la hora de saber la temperatura a la que hemos configurado el aire acondicionado y la direccin IP asignada a la Raspberry una vez conectada a la red. La descripcin del software que controla lo que se muestra en el display se detallar en el apartado de software.
Justificacin de la solucin adoptada. El nodo descrito se encarga nicamente de recoger y retransmitir al nodo del aire acondicionado la informacin necesaria para reconstruir y emitir la trama que cambia la temperatura en el dispositivo. Por tanto, hemos optado por relegar el trabajo de construccin de la trama al otro nodo, quedando este con una funcionalidad bastante sencilla pero efectiva. Problemas encontrados durante la implementacin. Dada la fcil implementacin de la transmisin radio proporcionada por el fabricante del Tulio, conseguir el correcto funcionamiento de esta parte fue bastante sencillo. La instalacin del LCD no fue complicada pero hubo algunas complicaciones al usar la librera software y encontrar los smbolos adecuados.
Esquema elctrico. En la sala del aire acondicionado habr un nodo compuesto por: Un Tulio, que recibe por radio la trama que deber enviar al aire acondicionado. Un circuito emisor, compuesto por un led infrarrojo y un circuito amplificador basado en un transistor (BC107).
Justificacin de la solucin adoptada. Las tramas enviadas por un mando a distancia estndar constan de pulsos modulados (usualmente a 38kHz). Por tanto, nuestro emisor debe ser capaz de modular los bits de la trama antes de ser enviados. A diferencia del primer hito y tal y como expusimos, hemos sustituido el oscilador hardware basado en NE555 por un temporizador del microcontrolador utilizado (C1110). De este modo el usuario puede configurar fcilmente desde el nodo de control la frecuencia de portadora y el tiempo de bit, permitiendo usar cualquier tipo de mando a distancia. 7
Por tanto, el circuito externo al microcontrolador es sencillamente un led infrarrojo con un circuito amplificador que se comunica con el aire acondicionado. Mediante el pin P0_0 del Tulio controlamos dicho led. Justificaciones tericas de los valores adoptados para cada uno de los componentes. Para el circuito amplificador hemos utilizado un transistor NPN y una resistencia de 47 tal y como se indica a continuacin. Este montaje amplifica la seal a la salida del pin para que el led emita con mayor intensidad.
Problemas encontrados durante la implementacin. Los principales problemas vinieron a raz de que, al estar trabajando con SDCC, no disponamos de la funcin sleep() de C, necesaria para generar el tiempo de bit. Esto nos llev a plantearnos maneras alternativas, y decidimos usar un timer del Tulio. En primera instancia se utiliz el temporizador n2, especializado para controlar slots de tiempo. Sin embargo, no fuimos capaces de hacerlo funcionar, y revisando los ficheros de la librera encontramos que el chip de nuestro modelo no soportaba dicho timer. Otro de los problemas fue decidir cmo controlar el pin de salida de la trama: mediante PWM o haciendo oscilar directamente el pin. Para evitar usar dos temporizadores (uno para generar el tiempo de bit y otro para la frecuencia de portadora), optamos por hacer oscilar directamente el pin. Aqu el problema fue implementar correctamente el cdigo para poder generar, a partir de un solo timer, la frecuencia de portadora y el tiempo de bit.
#import import RPi.GPIO as GPIO import time from datetime import datetime from Adafruit_CharLCD import Adafruit_CharLCD from subprocess import * from time import sleep, strftime # Define LCD_RS = LCD_E = LCD_D4 = LCD_D5 = LCD_D6 = LCD_D7 = GPIO to LCD mapping 7 8 25 24 23 18
LCD_LINE_1 = 0x80 # LCD RAM address for the 1st line LCD_LINE_2 = 0xC0 # LCD RAM address for the 2nd line # Timing constants E_PULSE = 0.00005 E_DELAY = 0.00005
def main(): # Main program block GPIO.cleanup() GPIO.setmode(GPIO.BCM) GPIO.setup(LCD_E, GPIO.OUT) GPIO.setup(LCD_RS, GPIO.OUT) GPIO.setup(LCD_D4, GPIO.OUT) GPIO.setup(LCD_D5, GPIO.OUT) GPIO.setup(LCD_D6, GPIO.OUT) GPIO.setup(LCD_D7, GPIO.OUT) # Initialise display lcd_init() # Send some test lcd_byte(LCD_LINE_1, LCD_CMD) lcd_string("P i m o t e") lcd_byte(LCD_LINE_2, LCD_CMD) lcd_string("Alfredo y Sara")
# # # # # # #
time.sleep(3) # 3 second delay # Send some text while 1: lcd_byte(LCD_LINE_1, LCD_CMD) # lcd_string(datetime.now().strftime('%b %d %H:%M:%S\n')) cmd2 = "cat /home/pi/pimoteserver/temp.txt" estado = run_cmd(cmd2) lcd_string(estado) lcd_byte(LCD_LINE_2, LCD_CMD) cmd = "ip addr show eth0 | grep inet | awk '{print $2}' | cut -d/ -f1 | tr -d '\n'" ipaddr = run_cmd(cmd) if ipaddr == "": lcd_string("Sin conexion") else: lcd_string('IP %s' % ( ipaddr )) def run_cmd(cmd): p = Popen(cmd, shell=True, stdout=PIPE) output = p.communicate()[0] return output def lcd_init(): # Initialise display lcd_byte(0x33,LCD_CMD) lcd_byte(0x32,LCD_CMD) lcd_byte(0x28,LCD_CMD) lcd_byte(0x0C,LCD_CMD) lcd_byte(0x06,LCD_CMD) lcd_byte(0x01,LCD_CMD)
10
GPIO.output(LCD_RS, mode) # RS # High bits GPIO.output(LCD_D4, False) GPIO.output(LCD_D5, False) GPIO.output(LCD_D6, False) GPIO.output(LCD_D7, False) if bits&0x10==0x10: GPIO.output(LCD_D4, True) if bits&0x20==0x20: GPIO.output(LCD_D5, True) if bits&0x40==0x40: GPIO.output(LCD_D6, True) if bits&0x80==0x80: GPIO.output(LCD_D7, True) # Toggle 'Enable' pin time.sleep(E_DELAY) GPIO.output(LCD_E, True) time.sleep(E_PULSE) GPIO.output(LCD_E, False) time.sleep(E_DELAY) # Low bits GPIO.output(LCD_D4, False) GPIO.output(LCD_D5, False) GPIO.output(LCD_D6, False) GPIO.output(LCD_D7, False) if bits&0x01==0x01: GPIO.output(LCD_D4, True) if bits&0x02==0x02: GPIO.output(LCD_D5, True) if bits&0x04==0x04: GPIO.output(LCD_D6, True) if bits&0x08==0x08: GPIO.output(LCD_D7, True) # Toggle 'Enable' pin time.sleep(E_DELAY) GPIO.output(LCD_E, True) time.sleep(E_PULSE) GPIO.output(LCD_E, False) time.sleep(E_DELAY) if __name__ == '__main__': main() GPIO.cleanup()
11
raspi_wd.sh Este shell script se encarga de monitorizar el fichero de texto que se actualiza cada vez que el usuario quiere realizar alguna accin sobre el aire acondicionado. Para no acaparar todos los recursos de la mquina con un bucle utiliza la herramienta inotifywait. Se encuentra en la carpeta usr/sbin, y es controlado por un daemon de la carpeta init.d. Adems est configurado para que arranque con el sistema, de modo que el sistema est operativo desde el arranque.
#! /bin/sh ### BEGIN INIT INFO # Provides: # Required-Start: # Required-Stop: # Default-Start: # Default-Stop: # Short-Description: # Description: ### END INIT INFO
watchdog del archivo arg.txt $all $all 2 3 4 5 0 1 6 Short script description Longer script description.
case "$1" in start) echo "Iniciando raspi_wd... " while inotifywait -e close_write /home/pi/pimoteserver/arg.txt; do cd /home/pi/enviatramas; PAR=`cat /home/pi/pimoteserver/arg.txt` ; ./raspibase $PAR; done ;; stop) echo "Deteniendo raspi_wd..." kill -9 `ps -ef|grep -v grep |grep raspi_wd.sh| awk '{print $2}'` ;; *) echo "Modo de empleo: /etc/init.d/raspi_wd.sh {start|stop}" exit 1 ;; esac exit 0
server.sh Este shell script tiene la funcin de arrancar la interfaz de usuario web automticamente. Se encuentra en la carpeta usr/sbin, y es controlado por un daemon de la carpeta init.d. Adems est configurado para que arranque con el sistema, de modo que el servidor est operativo cuando el dispositivo se enciende.
#! /bin/sh ### BEGIN INIT INFO # Provides: # Required-Start: # Required-Stop: # Default-Start: # Default-Stop: # Short-Description: # Description: ### END INIT INFO
pimote server $all $all 2 3 4 5 0 1 6 Short script description Longer script description.
case "$1" in start) echo "Iniciando server Pimote... " cd /home/pi/quiz_edit nodejs ./quiz.js &
12
pimote_server.js Este fichero es el ncleo de la aplicacin web programada en NodeJS. Con ella proporcionamos una interfaz de usuario sencilla para que el sistema completo sea cmodo de usar. No incluimos en esta memoria los cdigos HTML5 pero en su lugar mostramos la siguiente captura de la aplicacin, ms representativa de dicho cdigo.
= = = = =
HTTP.createServer(function(request, response) { var MODEL = { show: function (button, action) { FS.readFile('arg.txt','utf-8', function(err, arg) { if (!err) { arg = arg.replace(new RegExp(button + ':.*\n', 'g'), ''); } else { action(err); }; }); FS.readFile('buttons.txt', 'utf-8', function(err, buttons) { if (!err) {
13
14
15
show: function () { MODEL.show(button, function(err, resp) { if (!err) CONTROLLER.send(); // redireccin a 'GET quiz/index' else VIEW.error(500, "Server bbdd Error_b"); }); }, update: function () { MODEL.update(button, function(err) { if (!err) CONTROLLER.index(); // redireccin a 'GET quiz/index' else VIEW.error(500, "Server bbdd Error_c"); }); } } var url = URL.parse(request.url, true); var post_data = ""; request.on('data', function (chunk) { post_data += chunk; }); request.on('end', function() { post_data = QS.parse(post_data); // "question" variable global -> visible en controlador button = (post_data.preg || url.query.preg); //question = (post_data.preg + (post_data.resp == null ? "" : ": " + post_data.resp) || url.query.preg); if(post_data.resp != null){ button += ": " + post_data.resp; } var route = (post_data._method || request.method) + ' ' + url.pathname; switch (route) { case 'GET /index' : CONTROLLER.index() ; break; case 'GET /show' : CONTROLLER.show() ; break; case 'GET /new' : CONTROLLER.new() ; break; case 'GET /edit' : CONTROLLER.edit() ; break; case 'PUT /update' : CONTROLLER.update() ; break; case 'POST /create' : CONTROLLER.create() ; break; case 'GET /remove' : CONTROLLER.remove() ; break; case 'DELETE /delete' : CONTROLLER.delete() ; break; default: { if (request.method == 'GET') CONTROLLER.file() ; else VIEW.error(400, "Unsupported request"); } }
16
emisor.c Este fichero, ejecutado en el Tulio situado en la sala de control, se encarga de recibir la informacin por la UART y reenviarla va radio. Para recibir informacin por el puerto serie, chequea de manera peridica si hay datos en el pin mediante un buffer circular. Para emitir datos va radio utilizamos la funcionalidad aportada por el fabricante, con lo que basta ejecutar la funcin cc1110_tx(source, destination, data, data_length, type). Adems de todo esto, cabe destacar que el microcontrolador entra en reposo cuando no se estn recibiendo datos.
/ ************************************************************************* ********* Filename: emisor.c Description: Codigo para transmitir una trama recibida por UART del nodo base al nodo del a/c. Comments: El dispositivo enva los datos al nodo del a/c. Despus de enviarlo se pone en modo de ahorro de energa. ************************************************************************* **********/ #include "hal_main.h" #include "libcc1110.h" #define TX_ADD 10 #define RX_ADD 20 #define SLEEP_PERIOD 1 #define UART_TX_PERIOD 5 // Sleep Timer period #define UART_BUFFER_SIZE 150 //******** Variables for this app volatile UINT8 current_232_data = 0; // byte to store rs232 received data volatile UINT8 current_232_pos = 0; // current position of buffer to store data volatile UINT8 rs232_buf[UART_BUFFER_SIZE]; // buffer where data is stored volatile Buffer_cir rs232_buf_cir; //******** Flags and triggers volatile UINT8 flag_ST = 0; // Sleep Timer flag volatile UINT8 flag_UART = 0; // Uart RX flag //******** Configuracion RF ******************** //estas tres variables siempre deben estar definidas***** //********************************************* UINT8 rf_power = RF_POWER_P10; UINT8 rf_channel = 0x01; // Configuracion del canal RF network_address netAdd; // network address structure void main(void) { BYTE status = 0;
17
18
raspi_base.c Este fichero es ejecutado en la Raspberry Pi, y se encarga de leer la informacin de un fichero .txt con la informacin a enviar con el fin de transmitirla a continuacin por el puerto serie.
/ ***************************************************************************** ****** Filename: raspi_base.c Description: Enva los datos seleccionados por el usuario al Tulio para configurar el aire acondicionado via radio. Important: Advierta que los pines estn configurados a 3.3V y las especificaciones de RS232 son para 12V. Si conecta esto a un dispositivo RS232 podra daar su Raspberry Pi. ***************************************************************************** ******/ #include #include #include #include #include <stdio.h> <unistd.h> <fcntl.h> <termios.h> <errno.h>
int main(int argc, char *argv[]) { //------------------------//----- SETUP UART -------//------------------------int uart0_filestream = -1; unsigned char tx_buffer[700]; unsigned char *p_tx_buffer; int i; int palabras; struct termios options; unsigned int speed = B115200; uart0_filestream = open("/dev/ttyUSB0", O_RDWR | O_NOCTTY | O_NDELAY); //Open in non blocking write mode if (uart0_filestream == -1) { //ERROR - CAN'T OPEN SERIAL PORT perror("Error - Unable to open UART. Ensure it is not in use by another application\n"); } tcgetattr(uart0_filestream, &options); options.c_cflag = CS8 | CLOCAL | CREAD; options.c_iflag = IGNBRK; //IGNPAR | ICRNL; options.c_oflag = 0; options.c_lflag = 0; cfsetospeed(&options, speed); cfsetispeed(&options, speed); tcflush(uart0_filestream, TCIOFLUSH); tcsetattr(uart0_filestream, TCSANOW, &options); //----- TX BYTES ----//tx_buffer[] = {header, header, header, header, header, header, //<Set baud rate
19
20
Nodo de la sala de aire acondicionado receptor_ac.c Este cdigo, ejecutado por el Tulio de la sala de aire acondicionado, es el ms complejo de todos los expuestos, puesto que es el que genera la trama modulada en uno de sus pines. Para empezar, un buffer circular chequea si llega nueva informacin va radio.
buffer_cir_get (&buf_rx, radio_buf, BUFFER_SIZE)
Cuando esto ocurre, se recorre el array radio_buf y se guarda en diferentes variables la informacin correspondiente a tiempo de bit y de portadora. Con ellos se configura el timer 3 (ajustado a frecuencia de portadora) y se calcula el nmero de iteraciones del mismo que conforman un tiempo de bit (variable veces). A continuacin, un bucle for recorre slo los elementos de radio_buf que corresponden a la trama que se debe enviar al aire acondicionado. Dentro de dicho bucle se recorre cada bit de la trama con una mscara, encendiendo o apagando el pin P0_0 en funcin de su valor (0 o 1). Para asegurarnos de que el tiempo de bit es el adecuado, se comprueba mediante el bucle while(counter < veces) que se han producido el nmero de iteraciones del timer 3 necesarias para que haya transcurrido el tiempo de bit. Para contar las iteraciones se comprueba el valor del registro TIMIF, en el cual el bit 0 corresponde al flag de overflow del timer 3.
/ ***************************************************************************** ***** Filename: receptor_ac.c Description: Comments: Cdigo de prueba para transmitir una trama recibida por radio desde el nodo base al a/c.
El dispositivo recibe los datos del nodo base y los enva al a/c. Despus de enviarlo se pone en modo de ahorro de energa. ***************************************************************************** ******/ #include #include #include #include "hal_main.h" "libcc1110.h" "hal_timer.h" "hal_defines.h"
#define LED_TOGGLE() \ do { \ GLED = LED_ON; RLED = LED_ON; halWait(200); GLED = LED_OFF; RLED = LED_OFF; } while (0) #define PORT_0 #define PORT_1 #define PORT_2 0 1 2
\ \ \ \ \
21
//******** Configuracion RF ******************** //estas tres variables siempre deben estar definidas***** //********************************************* UINT8 rf_power = RF_POWER_P10; // TX Power Output UINT8 rf_channel = 0x01; // RF channel configuration network_address netAdd; // network address structure //********Buffer circular RF******************** //********************************************* extern Buffer_cir buf_rx; void main(void){ //Tiempo de bit en useg UINT32 tbit = 0; //Periodo de portadora en miliseg. UINT8 tcarrier = 0; //El periodo fijado en el timer debe ser la mitad que tcarrier UINT8 tadaptada = 0; UINT8 veces = 0; UINT8 counter = 0; UINT8 index = 0; UINT8 mask; /***Rx de datos***/ //Radio Buffer (ver includes para ms informacin) UINT8 radio_buf[BUFFER_SIZE]; //direccion UINT16 dst_add = 0; // Configura direccion de la fuente netAdd.my_address = RX_ADD; // Inicializacin de leds del Tulio INIT_RLED(); INIT_GLED(); RLED = LED_OFF; GLED = LED_OFF; /*********************************************************** * Estas dos instrucciones deben estar juntas al principio de cualquier aplicacin de Tulio. */ SET_MAIN_CLOCK_SOURCE(CRYSTAL); // Elige el cristal oscilador como reloj del sistema cc1110_init(); // AWD HW init // Radio como receptor set_rx(); // Bucle principal while (1) { // chequea nueva informacin por radio en buffer circular
22
Justificacin de la solucin adoptada Tal y como se explic anteriormente, generar la trama mediante un temporizador del microcontrolador fue la alternativa ante la imposibilidad de utilizar la funcin sleep(), necesaria para generar el tiempo de bit, adems de servir para eliminar el oscilador hardware anteriormente utilizado. Adems se ha procurado usar un solo temporizador en lugar de dos 23
para generar tanto la oscilacin de la trama modulada como el tiempo de bit, con el fin de no sobrecargar el micro. Plan de pruebas Para comprobar el correcto funcionamiento del cdigo implementado, fijamos una trama de prueba y su correspondiente tiempo de bit y frecuencia de portadora. Los datos son: Trama: 01010000 01100101 01101110 01100101 Tiempo de bit terico: 531 s Frecuencia de portadora: 1/26 s => 38 kHz
En la segunda captura vemos en detalle uno de los bits a la salida del pin. En el se puede comprobar que la frecuencia de portadora y el tiempo de bit se aproximan a los calculados tericamente.
24
25
26
# def capture_data(channel): # if GPIO.input(channel): # print('Input was HIGH') # data.append(1) # t_carrier_start = timeit.timeit() #check time at beginning # GPIO.add_event_detect(22, GPIO.RISING, callback=capture_tcarrier) # t_carrier_start = timeit.timeit() #reset start time for next cycle # # # # # # # # else: print('Input was LOW') data.append(0) t_bit_end = timeit.timeit() #check time at the end diff_tbit = t_bit_end - t_bit_start print('Bit time: '+diff_tbit) tbit.append(diff_tbit) t_bit_start = timeit.timeit() #reset start time for next cycle
#the function called by the interrupt on pin 18 def capture_tcarrier(channel): t_carrier_start = timeit.timeit() #check start time while GPIO.input(channel) == GPIO.HIGH: pass #wait t_carrier_end = timeit.timeit() #check time at the end diff_tcarrier = 2*(t_bit_end - t_bit_start) print('Carrier period: '+diff_tcarrier) tcarrier.append(diff_tcarrier) #initialize the interrupt print('Detecting signal') try: print('entro') GPIO.add_event_detect(11, GPIO.RISING, callback=capture_data) GPIO.add_event_detect(12, GPIO.RISING, callback=capture_tcarrier) print('por aqui ando') except KeyboardInterrupt:
27
Sin embargo al hacer pruebas nos topamos con que al ser un programa en espacio de usuario, no tena la suficiente rapidez para capturar todas las interrupciones al verse interrumpido por otros procesos del sistema. Por tanto nos dispusimos a la opcin ms fiable en cuanto a lo que tiempo y rapidez de atencin se refiere: hacer un driver. Para la realizacin de dicho driver utilizamos ampliamente el libro de referencia Linux Device Drivers de la editorial O'Reilly, puesto que era la primera vez que nos enfrentabamos a una tarea similar. El principal problema a la hora de implementar el driver estaba en que los fabricantes de Raspberry Pi no dan soporte para ciertas funcionalidades como por ejemplo el muestreo del GPIO a nivel hardware. Es decir, se puede implementar, pero no est documentado en detalle. El primer escollo a superar fue encontrar los valores de los registros para poder escribir y leer de ellos, as como la manera de hacerlo. Finalmente, el driver que hemos desarrollado es capaz de muestrear la seal entrante de por un pin, y almacenarlo en un buffer que ser posteriormente pasado al espacio de usuario para ser interpretado. El cdigo es el que se detalla a continuacin: 28
/* * PIMOTE driver */ #include #include #include #include #include #include #include #include #include <linux/module.h> <linux/kernel.h> <linux/fs.h> <linux/init.h> <linux/io.h> <linux/ioport.h> <linux/interrupt.h> <linux/timer.h> <linux/gpio.h>
#define MAJOR_NUMBER 70 //Function Select Registers //FSELn = 000 --> Pin n is an input //FSELn = 001 --> Pin n is an output #define GPFSEL0 0x20200000 #define GPFSEL1 0x20200004 #define GPFSEL2 0x20200008 #define GPFSEL3 0x2020000C #define GPFSEL4 0x20200010 #define GPFSEL5 0x20200014 //Pin Level Registers //LEVn = 0 --> Pin n is low //LEVn = 1 --> Pin n is high #define GPLEV0 0x20200034 #define GPLEV1 0x20200038 //Pin Output Set Registers //SETn = 0 --> No effect //SETn = 1 --> Set GPIO pin n #define GPSET0 0x2020001C #define GPSET1 0x20200020 //Pin Output Clear Registers //CLRn = 0 --> No effect //CLRn = 1 --> Clear GPIO pin n #define GPCLR0 0x20200028 #define GPCLR1 0x2020002C //Event Detect //EDSn = 0 --> //EDSn = 1 --> #define GPEDS0 #define GPEDS1 Status Registers Event not detected on pin n Event detected on pin n 0x20200040 0x20200044
//Rising Edge Detect Enable Registers //RENn = 0 --> Rising edge detect disabled on pin n //RENn = 1 --> Rising edge detect enabled on pin n (sets corresponding bit in EDSn) #define GPREN0 0x2020004C #define GPREN1 0x20200050 //Falling Edge //FENn = 0 --> //FENn = 1 --> #define GPFEN0 #define GPFEN1 Detect Enable Registers Falling edge detect disabled on pin n Falling edge detect enabled on pin n (sets corresponding bit in EDSn) 0x20200058 0x2020005C
29
30
31
32
33
34
6 Manual de usuario
Para controlar el sistema implementado hasta ahora deberemos seguir los siguientes pasos: En primer lugar encendemos la Raspberry Pi conectndola a la corriente a travs del puerto micro-USB y alimentamos los Tulios conectndolos a un equipo/Raspberry a travs del puerto USB. En el sistema receptor, adems del Tulio, debemos alimentar el circuito que contiene el led infrarrojo que le enva la trama al aire acondicionado. Para ello conectamos los pines de alimentacin y masa del Tulio a la placa de insercin y el pin0 a la entrada del circuito amplificador. (Comprobamos que el led verde esta encendido, si esto no ocurriese, comprobar las conexiones entre la placa y el Tulio) Una vez alimentados nos conectamos al servidor de la Raspberry para acceder a la interfaz de usuario del sistema. En un navegador introducimos la direccin IP asignada a la Raspberry seguido del puerto 3000 y /index que nos llevar a la pgina principal
host:3000/index
donde host es la direccin IP asignada al dispositivo (Esta direccin aparecer reflejada en el display)
35
Una vez en el servidor seleccionamos lo que queremos enviar en el spinner disponible en la pgina principal y pulsamos el botn enviar. La temperatura enviada aparecer en el display y se habr enviado
Adicionalmente, si quiere guardar una nueva trama, deber introducir el fichero de texto con la informacin de la trama en la carpeta enviatramas situada en el directorio home/pi/ de Raspberry y despus pulsar en guardar nueva trama en el servidor, donde nos aparecer una sencilla interfaz en la que introducir el nombre del botn (en maysculas) y el nombre del fichero .txt al que hace referencia dicho botn (Para ello es importante mantener la extensin del fichero cuando guardemos el botn). Por ejemplo:
OFF: tramaoff.txt
Tras esto pulsamos el botn para guardarlo y ya dispondremos del nuevo botn en el spinner de la pgina principal.
Anlogamente dispone de una interfaz para editar o borrar botones de la lista de botones disponibles. 36
7 Bibliografa
Informacin sobre drivers en Linux: Third Edition of Linux Device Drivers, by Jonathan Corbet, Alessandro Rubini, and Greg Kroah-Hartma. LIRC GPIO driver: http://aron.ws/projects/lirc_rpi/ Informacin sobre los pines del GPIO: http://elinux.org/RPi_Low-level_peripherals Agradecimientos a Guy Palmer. Datasheet del CC1110 por Texas Instruments Agradecimientos al equipo de Temp-LSI
37