/*
Copyright (C) Magna Carta Software, Inc. 1990,1991. All Rights Reserved.
CCT07.C: CCT06.C plus...
1) Raw data (ASCII) file transfer;
2) Interrupt-driven transmission;
3) Accepts XON-XOFF flow control signals from the remote system;
*/
#include <comm.h>
#include <modem.h>
#include <xfer.h>
#include <conio.h>
#include <dos.h>
#include <stdlib.h>
#include <string.h>
#if defined(__WATCOMC__)
#include <direct.h>
#elif !defined(MSC)
#include <ctype.h>
#endif
/* MANIFEST CONSTANTS AND MACROS */
#define DO_MENU ALT_M /* key for command summary */
/* FUNCTION PROTOTYPES */
void do_data_menu(COMM_PORT * p);
short do_modem_menu(COMM_PORT *p);
short do_txfile_menu(COMM_PORT *p);
long do_speed_menu(COMM_PORT * p);
short menu(COMM_PORT *p);
void term(COMM_PORT *p);
short xfer_progress(COMM_PORT *p, short status, unsigned long parm);
/* GLOBAL VARIABLES */
BYTE rxbuf[2048]; /* RECEIVE BUFFER */
BYTE txbuf[10*1024L]; /* large TRANSMIT buffer (for use with interrupts */
int vers = 7;
COMM_PORT port1;
MODEM m1;
XFER x; /* MUST be initialized to 0's */
#include "menus.c"
#include "xfermsg.c"
/* ------------------------ PROGRAM BEGINS HERE --------------------------- */
int main(void)
{
/* SET SPEED FOR DIRECT CONNECTION */
u8250_init(&port1, COM1, 19200L, DATABITS8, PARITY_NONE, STOPBITS1);
install_ipr(&port1, RECEIVE, NULL, rxbuf, sizeof(rxbuf));
/* THIS LINE INSTALLS A TRANSMITTER BUFFER EMPTY IPR */
install_ipr(&port1, TRANSMIT, NULL, txbuf, sizeof(txbuf));
install_isr(&port1, 4, NULL);
printf("CCT-COMM Version %d: Press Alt-M for a list of commands\n", vers);
term(&port1);
printf("\nEnd of CCT-COMM%d\n", vers);
return (0);
}
/*
TERM -- The terminal emulation routine. Simply polls the COM port and the
keyboard alternately for characters.
*/
void term(COMM_PORT *p)
{
short c; /* must be int to detect a -1 return */
set_rx_xlat(p, EOL, FALSE);
set_rx_xlat(p, LOCAL_ECHO, TRUE);
set_tx_xlat(p, FLOWCTL, XONXOFF); /* better assert flow control if > 2400 bps */
for (;;) {
/* CHECK SERIAL PORT FOR BYTE */
c_getc(p);
/* CHECK KEYBOARD FOR A KEY PRESS */
if ( (c = inkey()) != 0) {
if (c == DO_MENU) {
if (menu(p) == 1) break;
}
else c_putc(p, c);
}
}
}
#define DATA_FORMAT 'D' /* key to set speed */
#define SFILE_MENU 'F' /* key to send files */
#define DATA_SPEED 'S' /* key to set speed */
#define MODEM_MENU 'M' /* key to send modem commands */
#define EXIT 'Q' /* key to exit from main */
short menu(COMM_PORT *p)
{
short c, retval = 0, DONE = FALSE;
static char *menus[] = {
"\tD. Data Format",
"\tF. File Send Commands",
"\tM. Modem Commands.",
"\tS. Data Transfer Rate.",
"\tQ. EXIT from COMM.",
NULL /* null string terminates list */
};
char **p_menu;
c = !EXIT;
while (!DONE) {
puts("\n\n");
for (p_menu = menus; *p_menu != NULL; p_menu++) printf("%s\n", *p_menu);
printf("\n\t\t Enter selection (CR to quit menu) : ");
c = getchar();
c = toupper(c);
switch (c) {
case EXIT:
retval = 1;
DONE = TRUE;
break;
case SFILE_MENU:
DONE = do_txfile_menu(p);
break;
case DATA_FORMAT:
do_data_menu(p);
break;
case DATA_SPEED:
do_speed_menu(p);
break;
case MODEM_MENU:
DONE = do_modem_menu(p);
break;
default:
DONE = TRUE;
break;
}
}
puts("\nExiting menu");
return (retval); /* will be zero except if EXIT */
}
/*
DO_MODEM_MENU -- Send commands to the modem.
*/
short do_modem_menu(COMM_PORT *p)
{
short key;
short DONE=FALSE, ret = 0;
do {
puts("\nSEND COMMANDS TO THE MODEM");
puts("D. Dial");
puts("H. Hangup");
puts("I. Initialize");
puts("O. Go Offline");
puts("R. Reset\n");
puts("\nAny other key exits");
key = toupper(bios_key(_KEYBRD_READ) & 0XFF);
switch (key) {
case 'D':
modem_dial(p, "226-8088");
ret = 1;
DONE = TRUE;
break;
case 'H':
modem_hangup(p);
break;
case 'I':
modem_init(p, modem_type(p));
set_dtr(p, HIGH);
break;
case 'O':
modem_go_cmd(p, (short) atoi(&((MODEM *)p->modem)->escape[3]));
break;
case 'R':
modem_reset(p);
break;
default:
DONE = TRUE;
break;
}
} while (!DONE);
return (ret);
}
/*
DO_TXFILE_MENU -- Send a file to a remote system using ASCII.
*/
short do_txfile_menu(COMM_PORT *p)
{
short ret = 0;
char filename[80], sxlat[XLAT_SIZE];
struct ffblk fb;
/* SELECT THE FILE TO SEND */
filename[0] = '\0';
puts("\nSEND A FILE TO A REMOTE SYSTEM USING ASCII");
puts("\nEnter file name (ENTER to exit):");
scanf("%s", filename);
if (filename[0] == CR) return (0);
ret = findfirst(filename, &fb, FA_ARCH);
if (ret == EOF) return (EOF);
save_xlat(p, sxlat); /* save XLAT configuration */
/* USE XONXOFF FLOW CONTROL (this lets the receiver write to disk) */
set_rx_xlat(p, FLOWCTL, XONXOFF); /* better accept flow control if > 2400 bps */
set_tx_xlat(p, LOCAL_ECHO, OFF); /* optionally echo file to screen */
set_rx_xlat(p, LOCAL_ECHO, ON); /* optionally echo file to screen */
ret = fqueue(&x, fb.ff_name); /* queue the file to send */
x.len = 3072; /* you can constrain the xmit buffer size */
if (!ret) ret = fsend(p, &x, ASCII, 4*1024, xfer_progress); /* send the file */
rest_xlat(p, sxlat); /* restore XLAT configuration */
return (ret);
}