Sie sind auf Seite 1von 9

UNIVERSIDAD TECNOLGICA NACIONAL

Facultad Regional Crdoba


INFORMTICA II .
Unidad V: Puerta Serie
Control desde la Bios.
Existen distintas funciones, aunque similares, en compiladores como el Turbo C de Borland el
Microsoft C para el manejo de los puertos seriales de la PC desde la BIOS, para establecer una
comunicacin entre dos dispositivos.
Esta primera aproximacin se realiza utilizando la funcin de la BIOS int 14h (en C int 0x14),
programando directamente sobre los registros de la CPU, de la familia x86.
Esta interrupcin int 14h es una funcin cuyas variables de ingreso son los registros: AH, AL,
DX y de salida el registro AX.
En Microsoft:
unsigned _bios_serialcom (unsigned modo, unsigned port, unsigned puerto)
En Borland:
int bioscom (int modo, char config, int port),
Valores que puede tomar modo que se corresponde con lo ingresado en el registro AH
0
1
2
3

Inicializar el puerto
Enviar un carcter
Recibir un carcter
Devolver el estado del puerto

Valores que puede tomar config, como registro AL


Nmero de Bits

7, 6, 5
Velocidad
Baudios

4,3
en Paridad

2
Bits de parada

Tabla 1
Opciones posibles:
Baudios 9600 4800 2400 1200 600 300 150 110
Bits
111 110 101 100 011 010 001 000
Paridad
Sin
Impar
Par
Bits
Parada
Uno
Dos

de

00 10
01
11

Bits
Datos
siete
ocho

0
1

Valores Posibles para port


0
1
2
3

COM1
COM2
COM3
COM4

a) Problemas Resueltos
5-1) DUP que enve datos al puerto serie de la PC.

de
10
11

1,0
Bits de datos

#include <conio.h>
#include <stdio.h>
#include <bios.h>
int puerto, dato, envio, config, ultimo=0;
void main(void)
{
clrscr();
printf("Ingrese puerto COM a usar: ");
scanf("%d", &puerto);
while(puerto<1 || puerto>4)
{
clrscr();
printf("ERROR... Debe ingresar 1, 2, 3 o 4\n\n");
printf("Ingrese puerto COM a usar: ");
scanf("%d", &puerto);
}
puerto--;
config=0x83; //Equivale en Binario: 10000011. Ver relacin con tabla 1
bioscom(0,config,puerto); //con 0 en el primer argumento inicializamos.
do
{
clrscr();
printf("Dato a enviar (ULTIMO: %d) --> ",ultimo);
scanf("%d", &dato); /captura desde teclado
while(dato<0 || dato>255)
{
printf("ERROR... Ingrese dato de 8 bits \n\n);
printf("Dato a enviar (ULTIMO: %d) --> ",ultimo);
scanf("%d", &dato);
}
envio=bioscom(1,dato,puerto); // con 1 en el primer argumento envo un carcter.
ultimo=dato; //muestra el ltimo dato enviado
}while(1==1);
}
5-2) DUP que lea reciba la entrada de datos desde el puerto serie de la PC.
#include <conio.h>
#include <stdio.h>
#include <dos.h>
#include <math.h>
#include <bios.h>
int puerto, k, j, dato, config;
char lectura[1],dato1[2];
void main(void)
{
clrscr();
printf("Ingrese puerto COM a usar: ");
scanf("%d", &puerto);
while(puerto<1 || puerto>4)
{
clrscr();
printf("ERROR... Debe ingresar 1, 2, 3 o 4 !!!\n\n");
printf("Ingrese puerto COM a usar: ");
scanf("%d", &puerto);
}

puerto--;
config=0x83;
bioscom(0,config,puerto); // opcin 0 para configurar de acuerdo a 0x83 = . 10000011
clrscr();
gotoxy(15,5);
printf("RECEPCION DE DATOS VIA SERIE");
gotoxy(10,8);
printf("Config --> COM %d \\ 1200 bps \\ 8N1", puerto+1);
gotoxy(35,10);
printf("Escape --> Salir");
gotoxy(25,12);
printf("MONITOR DE RECEPCION: ");
do{
if(!kbhit()) dato1[0]=leer( );
if(!kbhit())
{
gotoxy(40,12);
printf("%1s ",dato1);
}
}while(!kbhit());
getch( );
}
// funcin para leer el puerto
char leer( )
{
do{
dato=bioscom(2,0,puerto); //la opcin 2 es para leer desde el puerto
} while (!kbhit());
return(dato);
}
5-3) Hacer un programa que utilizando la funcin de comunicaciones serie del BIOS indique en
primer lugar el estado de un puerto serie determinado y a continuacin que haga de espejo
devolviendo las maysculas de los caracteres que recibe. Debe terminar su operacin cuando
reciba la orden Ctrl + Z.
#include <bios.h>
#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include <conio.h>

/*int bioscom (int modo, char config, int port ) */


/*int system (const char * command), da 0 si ocurre o -1 si falla*/
/*int toupper(int ch)*/
/*getch()*/

#define INICI 0U
/*U unsigned*/
#define ENVIO 1U
#define RECIB 2U
#define ESTAD 3U
#define PUERTO 0U
void printstatus (int result);
void main(void)
{
char letra = 'A';
int result;
unsigned char tosend = (0xA0 | 0x0 | 0x3 | 0x0 ), counter;
/*formato con operador de bits*/
/*
2400 N 8 1
*/
system ("cls");
puts ("-----------------------------------------");
puts (" Resultado del setup");
puts ("_________________________________________");
result = bioscom ( INICI, tosend, PUERTO);

printf ("Valor numrico devuelto: %d \n", result);


printstatus (result);
puts (" ");
puts ("_________________________________________");
puts ("
Resultado de verificacin");
puts ("_________________________________________");
result = bioscom (ESTAD, 0U, PUERTO);
printf ("Valor numrico devuelto: %d \n", result);
printstatus (result);
puts (" ");
if ((letra=getch ()) ==26) {
puts ("Recib EOF");
return;
}
else
puts ("\n Entro en funcin espejo\n");
while (letra !=26){
while (!(letra = (char) bioscom (RECIB, 0, PUERTO)));
result = bioscom (ENVIO, toupper (letra), PUERTO);
printf("\n Resultado del envo: %d\n", (char) result);
printf("%c %3d", letra, letra);
}
}
void printstatus (int result) {
if (result&32768) printf("Error de temporizacin\n");/* & operador de comparacion*/
if (result&16384) printf("Reg de Desplaz de Transf Vaco\n");
if (result&8192) printf("Reg de Mant de transf vaco \n");
if (result&4096) printf("Error de Interrupcin\n");
if (result&2048) printf("Error de estructura\n");
if (result&1024) printf("Error de paridad\n");
if (result&512) printf("Error de sobreescritura\n");
if (result&256) printf("Datos preparados\n");
if (result&128) printf("Detecto DTR y/o RTS\n");
if (result&64) printf("Indicador de llamada\n");
if (result&32) printf("Datos listos\n");
if (result&16) printf("Listo para enviar\n");
if (result&8) printf("Cambio en DTR y/o RTS\n");
if (result&4) printf("Detecto llamada \n");
if (result&2) printf("Cambio en datos listos\n");
if (result&1) printf("Cambio en listos para enviar\n");
}
b) Problemas Propuestos
5-4) DUF que inicialice la puerta serie 0, a 9.600 baudios, con paridad impar, 1 bit de parada y 8
bits de datos.
___________________________________________________________________________________
5-5) DUF que enve un caracter a la puerta serie 0, a 2400 baudios, con paridad par, 1 bit de
parada y 8 bits de datos.
___________________________________________________________________________________
5-6) DUF que reciba un caracter en la puerta serie 1, a 4800 baudios, con paridad impar, 2 bits de
parada y 7 bits de datos.
___________________________________________________________________________________

Puerto Serie en Linux


5-7) DUP que inicializa un puerto serie abrindolo como archivo, imprima la velocidad y
caractersticas de transmisin actuales, configure la velocidad y caractersticas de transmisin e
imprime el estado en que queda el puerto.
#include <stdio.h>

#include
#include
#include
#include
#include

<stdlib.h>
<fcntl.h>
/* Definiciones de
<errno.h>
/* Definiciones de
<sys/ioctl.h>
/* Constantes para
<termios.h>
/* Estructura de control

control de archivos */
control de errores */
ioctl */
termios */

void estadolinea( char *puerto, struct termios opciones );


int main( void ) {
int fd;
char puerto[] = "/dev/ttyS0"; // COM1
struct termios opciones;
fd = open(puerto, O_RDWR | O_NOCTTY | O_NDELAY | O_NONBLOCK);
if (fd == -1) {
perror("open_port");
exit( 1 );
}
else
fcntl(fd, F_SETFL, 0); // funciona en forma sncrona
// con FNDELAY lo hace en forma asncrona
// Estado de linea por la estructura termios
tcgetattr( fd, &opciones );
printf( "Antes de configurar: \n" );
estadolinea( puerto, opciones );
// Fijando velocidad del puerto
cfsetispeed( &opciones, B2400 );
// Habilitacin del receptor y modo local
opciones.c_cflag |= (CLOCAL | CREAD);
// Tamao de palabra
opciones.c_cflag &= ~CSIZE; /* Enmascara bits de tamao de palabra */
opciones.c_cflag |= CS8;
/* Selecciona 8 bits */
// Esto es para fijar 1 stop bit
opciones.c_cflag &= ~CSTOPB;
// Esto es para fijar 2 stop bits.
//opciones.c_cflag |= CSTOPB;
// Esto es para fijar NO paridad (N)
opciones.c_cflag &= ~PARENB;
// Esto es para fijar paridad par (E)
//opciones.c_cflag |= PARENB;
//opciones.c_cflag &= ~PARODD;
// Esto es para fijar paridad impar (O)
//opciones.c_cflag |= PARENB;
//opciones.c_cflag |= PARODD;
// Escritura de la configuracin en el puerto: tc set(establece) attr
tcsetattr( fd, TCSANOW, &opciones );
// Lectura de la configuracin del puerto: tc get(obtener) attr(ibutes)
tcgetattr( fd, &opciones );
printf( "Despus de configurar:\n" );
estadolinea( puerto, opciones );
close( fd );
}
void estadolinea( char *puerto, struct termios opciones ) {
int speed;
printf( "%s: ", puerto );
// Bits de cada palabra
if( (opciones.c_cflag & CSIZE) == CS5) printf( "5" );

if( (opciones.c_cflag & CSIZE) == CS6) printf( "6" );


if( (opciones.c_cflag & CSIZE) == CS7) printf( "7" );
if( (opciones.c_cflag & CSIZE) == CS8) printf( "8" );
// Paridad
if( (opciones.c_cflag & PARENB) == 0) printf( "N" );
else {
if( (opciones.c_cflag & PARODD) == PARODD) printf( "O" );
else printf( "E" ); // paridad par
}
// Bits de parada
if( (opciones.c_cflag & CSTOPB) == CSTOPB) printf( "2" );
else printf( "1" );
// Velocidad de transmisin
printf( " " );
speed = cfgetispeed( &opciones ); //obtener la w del Puerto:cf get o speed
switch( speed ) {
case B50: printf( "50" ); break;
case B75: printf( "75" ); break;
case B110: printf( "110" ); break;
case B134: printf( "134" ); break;
case B150: printf( "150" ); break;
case B200: printf( "200" ); break;
case B300: printf( "300" ); break;
case B600: printf( "600" ); break;
case B1200: printf( "1200" ); break;
case B1800: printf( "1800" ); break;
case B2400: printf( "2400" ); break;
case B4800: printf( "4800" ); break;
case B9600: printf( "9600" ); break;
case B19200: printf( "19200" ); break;
case B38400: printf( "38400" ); break;
case B57600: printf( "57600" ); break;
case B115200: printf( "115200" ); break;
default: printf ( "Error" ); break;
}
printf( " bps\n" );
}

5-8) DUP que inicialice un puerto serie abrindolo como archivo, imprima la velocidad y
caractersticas de transmisin, configure la velocidad y caractersticas de transmisin de acuerdo
a lo ingresado en la lnea de comandos e imprima el estado en que queda el puerto.
#include
#include
#include
#include
#include
#include
#include

<stdio.h>
<stdlib.h>
<string.h>
<fcntl.h>
/* Definiciones de control de archivos */
<errno.h>
/* Definiciones de control de errores */
<sys/ioctl.h>
/* Constantes para ioctl */
<termios.h>
/* Estructura de control termios */

void estadolinea( char *puerto, struct termios opciones );


int velocidad( int speed );
int main( int argc, char *argv[] ) {
int fd;
/* descriptor archivo del puerto */
char puerto[12] = "/dev/ttyS";
int longpal;
/* longitud de palabra */
struct termios opciones;
/* CONTROL DE CONSISTENCIA DE LA LINEA DE COMANDOS */
if( argc < 4 ) {
printf( "\nUso: %s puerto[0..3] disciplina[ej. 8N1] velocidad[bps]\n\n",
argv[0] );
exit(1);
}
strcat( puerto, argv[1] );
printf( "Puerto: %s\n", puerto );

if( (atoi(argv[1]) < 0) || (atoi(argv[1]) > 3) ) {//atoi: convierte una


//cadena a su valor nmerico. Ej: valor = (123);
printf( "\nEl puerto debe ser entre 0 y 3\n\n" );
exit(1);
}
if( (atoi(&argv[2][0]) < 5) || (atoi(&argv[2][0]) > 8) ) {
printf( "Chars por palabra debe estar entre 5 y 8\n" );
exit( 1 );
}
if( (toupper(argv[2][1]) != 'N') && (toupper(argv[2][1]) != 'E') &&
(toupper(argv[2][1]) != 'O') ) {
printf( "Paridad debe ser N, E, O\n" );
exit( 1 );
}
if( (atoi(&argv[2][2]) < 1) || (atoi(&argv[2][2]) > 2) ) {
printf( "Bits de stop debe ser 1 2\n" );
exit( 1 );
}
/* FIN CONTROL DE CONSISTENCIA DE LA LINEA DE COMANDOS */
// Apertura del puerto
fd = open(puerto, O_RDWR | O_NOCTTY | O_NDELAY | O_NONBLOCK);
if (fd == -1) {
perror("open_port");
exit( 1 );
}
else
fcntl(fd, F_SETFL, 0); // funciona en forma sincrona
// Lectura de estado de linea por la estructura termios
tcgetattr( fd, &opciones );
printf( "Antes de configurar: \n" );
estadolinea( puerto, opciones );
// Fijando velocidad del puerto en baudios cfsetospeed
cfsetispeed( &opciones, velocidad( atoi(argv[3]) ) );
// Habilitacin del receptor y modo local
opciones.c_cflag |= (CLOCAL | CREAD);
// Tamao de palabra
opciones.c_cflag &= ~CSIZE; /* Mask the character size bits */
switch( atoi(&argv[2][0]) ) {
case 5: longpal = CS5; break;
case 6: longpal = CS6; break;
case 7: longpal = CS7; break;
case 8: longpal = CS8; break;
}
opciones.c_cflag |= longpal;
// Fijando la cantidad de stop bits
if( atoi(&argv[2][2]) == 1 )
opciones.c_cflag &= ~CSTOPB;
else
opciones.c_cflag |= CSTOPB;
// Fijando la paridad
if( toupper(argv[2][1]) == 'N' )
opciones.c_cflag &= ~PARENB;
if( toupper(argv[2][1]) == 'E' ) {
opciones.c_cflag |= PARENB;
opciones.c_cflag &= ~PARODD;
}
if( toupper(argv[2][1]) == 'O' ) {
opciones.c_cflag |= PARENB;
opciones.c_cflag |= PARODD;
}

// Fijacin de los parmetros el puerto


tcsetattr( fd, TCSANOW, &opciones );
// Obtencin de los parmetros el puerto
tcgetattr( fd, &opciones );
printf( "Despus de configurar: \n" );
estadolinea( puerto, opciones );
close( fd );
}
void estadolinea( char *puerto, struct termios opciones ) {
int speed;
printf( "%s: ", puerto );
// Bits de cada palabra
if( (opciones.c_cflag & CSIZE)
if( (opciones.c_cflag & CSIZE)
if( (opciones.c_cflag & CSIZE)
if( (opciones.c_cflag & CSIZE)

==
==
==
==

CS5)
CS6)
CS7)
CS8)

printf(
printf(
printf(
printf(

"5"
"6"
"7"
"8"

);
);
);
);

// Paridad
if( (opciones.c_cflag & PARENB) == 0) printf( "N" );
else {
if( (opciones.c_cflag & PARODD) == PARODD) printf( "O" );
else printf( "E" ); // paridad par
}
// Bits de parada
if( (opciones.c_cflag & CSTOPB) == CSTOPB) printf( "2" );
else printf( "1" );
// Velocidad de transmisin
printf( " " );
speed = cfgetispeed( &opciones );
switch( speed ) {
case B50: printf( "50" ); break;
case B75: printf( "75" ); break;
case B110: printf( "110" ); break;
case B134: printf( "134" ); break;
case B150: printf( "150" ); break;
case B200: printf( "200" ); break;
case B300: printf( "300" ); break;
case B600: printf( "600" ); break;
case B1200: printf( "1200" ); break;
case B1800: printf( "1800" ); break;
case B2400: printf( "2400" ); break;
case B4800: printf( "4800" ); break;
case B9600: printf( "9600" ); break;
case B19200: printf( "19200" ); break;
case B38400: printf( "38400" ); break;
case B57600: printf( "57600" ); break;
case B115200: printf( "115200" ); break;
default: printf ( "Error" ); break;
}
printf( " bps\n" );
}
int velocidad( int speed ) {
switch( speed ) {
case 50: return( B50 );
case 75: return( B75 );
case 110: return( B110 );
case 134: return( B134 );
case 150: return( B150 );
case 200: return( B200 );
case 300: return( B300 );
case 600:return( B600 );
case 1200: return( B1200 );
case 1800: return( B1800 );

case 2400: return( B2400 );


case 4800: return( B4800 );
case 9600: return( B9600 );
case 19200: return( B19200 );
case 38400: return( B38400 );
case 57600: return( B57600 );
case 115200: return( B115200 );
default: printf ( "Error velocidad no permitida\n" );
exit(1);
break;
}
}

Das könnte Ihnen auch gefallen