Documenti di Didattica
Documenti di Professioni
Documenti di Cultura
Introduccin.
Las rutinas en ensamblador nos dan informacin y control sobre el tiempo de ejecucin del
cdigo, y los recursos utilizados, como son la memoria tanto de programa como de datos
necesaria para realizar una tarea.
De lo anterior nos es claro que poder mezclar ambos tipos de programacin nos beneficiaria, ya que podramos
obtener las ventajas de cada uno de los lenguajes.
El PSoC Designer nos permite usar subrutinas desarrolladas en ensamblador desde lenguaje C, por medio de la
directiva #pragma fastcall16 que nos permite llamar a funciones en ensamblador desde C.
Conexiones.
Conecta tu LCD al Puerto 2 del PSoC, y tu teclado matricial al Puerto 1 como se hizo en la Practica 2. No se
necesitar ms hardware.
Desarrollo.
LCD (y el de LED en caso de que el LCD tenga Luz), no utilizaremos la barra y lo conectaremos al puerto 2 con los
mismos parmetros de la prctica anterior. El Teclado Matricial se conectar al puerto 1; este puerto deber configurarse
como Pull-Up.
Ahora ve al men File y selecciona New File, o Presiona el cono de Archivo Nuevo en la barra de mens. Te
aparecer una ventana pidindote el tipo y nombre del archivo que vas a crear. Selecciona .asm File y dale como
Nombre Subrutinas.
En este nuevo archivo vamos a crear nuestras subrutinas en ensamblador. Teclea el siguiente cdigo en este
nuevo archivo.
; __________________________________________________________________________
; | Archivo de Subrutinas |
; __________________________________________________________________________
export ReadKey
export _ReadKey
Este programa no es muy diferente a como hicimos nuestra subrutina en la prctica anterior. Sin embargo hay
algunas diferencias que hacen posible llamarlas desde C. La primera est en las lneas 21, 22, 58 y 59 del programa.
Las Primeras dos lineas sirven para que todos los archivos del proyecto tengan acceso a la
subrutina ReadKey que hicimos. Aqu puedes ver que la exportamos 2 veces. Una vez con el
nombre ReadKey y otra con el nombre _ReadKey la razon de exportarlo de esta manera, es
carcter _ al principio del combre cuando compila el programa. De esta manera, cuando
traducida como call _LED_ON. Exportamos nuestra subrutina con ambos nombres, para poder
llamarla tanto de C como de Ensamblador por medio del mismo nombre, ya que el ensamblador
no agrega el guin bajo al nombre. En las ultimas dos lineas podemos ver que nuestra subrutina
puede ser llamada con cualquiera de los dos nombres, ya que ambas etiquetas tienen el mismo
valor.
Es Recomendable que cada subrutina que creemos se encuentre dentro de las directivas
cdigo no se agregara a nuestro programa, por lo que usaremos menos memoria de codigo.
Vuelve al men File y selecciona New File, o Presiona el cono de Archivo Nuevo en la barra de mens. Te
aparecer una ventana pidindote el tipo y nombre del archivo que vas a crear. Selecciona .h File y dale como Nombre
Subrutinas. Esto creara un archivo de cabeceras de C. En este le diremos al compilador de C que subrutinas en
ensamblador existen, y como funcionan.
MC. Edgar Mauricio Romero Lpez
Dispositivos de Control. Gua de Practicas.
La primera lnea le dice al compilador que existe una funcin hecha en ensamblador que utiliza los mtodos
fastcall16 para pasado de argumentos desde y hacia C. La segunda lnea le indica que nuestra subrutina se encuentra
en un archivo diferente a nuestro programa principal (extern), regresa un dato tipo BYTE y no es necesario pasarle
ningn parmetro (void).
Los mtodos de pasado de argumentos mediante fastcall16, establecen la forma en que una subrutina en
ensamblador recibe y entrega parmetros cuando es llamada desde C. Veamos los siguientes ejemplos:
Parmetros de Entrada en
Declaracin en C Resultados en Ensamblador
Ensamblador
void MiFuncion(void) Ninguno Ninguno
void MiFuncion(char Param1) A = Param1 Ninguno
void MiFuncin(char Param1, char Param2) A = Param1 Ninguno
X = Param2
void MiFuncin(int Param1) A = < Param1 (LSB) Ninguno
X = > Param1 (MSB)
void MiFuncion(ptr* Param1) X = < Param1 (LSB) Ninguno
A = > Param1 (MSB)
char MiFuncion(void) Ninguno A = ResultChar
int MiFuncion(void) Ninguno A = < Param1 (LSB)
X = > Param1 (MSB)
ptr* MiFuncion(void) Ninguno X = < Param1 (LSB)
A = > Param1 (MSB)
void MiFuncion(char Param1, int Param2) [SP-3] = Param1 Ninguno
[SP-4] = < Param2 (LSB)
[SP-5] = >Param2 (MSB)
void MiFuncion(int Param1, int Param2) [SP-3] = < Param1 (LSB) Ninguno
[SP-4] = > Param1 (MSB)
[SP-5] = < Param2 (LSB)
[SP-6] = >Param2 (MSB)
void MiFuncion(ptr* Param1, ptr* Param2) [SP-3] = < Param1 (LSB) Ninguno
[SP-4] = > Param1 (MSB)
[SP-5] = < Param2 (LSB)
[SP-6] = >Param2 (MSB)
En la tabla se puede ver que cuando los parmetros de entrada de la funcin son 1 o 2 bytes, se pasan por
medio de los registros internos, cuando los datos son ms de 2 bytes, se pasan por medio del stack, guardando los
parmetros en el orden inverso al que se define en la cabecera de C, y si alguno de los datos es de ms de un byte, se
comienza a guardar primero los bytes mas significativos, y por ltimo los menos significativos. Cuando los valores de
retorno son de ms de 2 bytes, se deben regresar por medio de punteros o variables globales.
Si la rutina se utiliza en ensamblador, es necesario volver el stack al tamao adecuado despus de llamar a una
subrutina. Por ejemplo una subrutina que en C tiene la cabecera:
Compn el Cdigo del Programa, de tal manera que se adquieran los datos del teclado de forma correcta.
Ahora, crea 3 subrutinas en ensamblador, que puedan llamarse desde C. Las Cadenas de entrada de estas
subrutinas debern poder trabajar con las cadenas, sin importar en que pgina estn.
La primera deber comparar 2 cadenas (null - terminated) y regresar 1 si cadena1 inicia con la cadena2. Deber
estar declarada en C como: extern BYTE StrStartsWith(char *Cadena1, const char *Cadena2);
La segunda deber convertir una cadena (null - terminated) que contenga caracteres, nmeros y smbolos, a una
cadena que contenga solo nmeros smbolos y letras minsculas. Deber estar declarada en C como: extern *Ptr
LowerStr(char *CadenaFuente, char *CadenaDestino);
La ltima deber convertir un arreglo de 3 caracteres numricos ASCII a un nmero binario entre 0 y 999. El byte
2 del arreglo deber contener las unidades, el uno las decenas y el cero las centenas; en caso de que alguno de los
caracters no corresponda a un nmero ASCII, se deber regresar 0xFFFF. Deber estar declarada en C como: extern
WORD StrNum2Byte(char *Numeros);
Documenta debidamente las rutinas ponindole comentarios e indicando al inicio de cada una, que registros
modifica, y sus requerimientos de memoria en caso de tenerlos.
Haz un programa en C para demostrar el funcionamiento de tus funciones. Llama a este nuevo proyecto
Practica3b.