#include   <stdio.h>
#include   <stdlib.h>
#include   <string.h>
#include   <intuition/intuition.h>
#include   <proto/exec.h>
#include   <proto/intuition.h>
#include   <proto/dos.h>
#include   <comm.h>


#define   CR    ((char) 13)

#define   CSICHAR   '\x9B'
#define   CSI       "\x9B"
#define   HELP      CSI "?~"
#define   F1        CSI "0~"
#define   F2        CSI "1~"
#define   F3        CSI "2~"
#define   F4        CSI "3~"
#define   F5        CSI "4~"
#define   F6        CSI "5~"
#define   F7        CSI "6~"
#define   F8        CSI "7~"
#define   F9        CSI "8~"
#define   F10       CSI "9~"
#define   LOCAL     CSI "0;33;40m"
#define   NORMAL    CSI "0;31;40m"
#define   INPUT     CSI "0;33;42m"

#define   ASCII     0
#define   XMODEM    1
#define   YMODEM    2
#define   KERMIT    3

extern struct IntuitionBase *IntuitionBase;

void main(void);
void GetSerial(COMPORT);
void GetString(COMPORT, char *, int);
extern int _GetKey(COMPORT, UBYTE *);


char *proto[] = { "ASCII", "XMODEM", "YMODEM", "KERMIT" };



void  main()
{
    COMPORT   ser;
    char      buff[256];
    int       len, ret;
    int       oldflags;
    int       done = 0;
    int       protocol = XMODEM;
    int       pause;


    if ((IntuitionBase = (struct IntuitionBase *)
                 OpenLibrary("intuition.library", 33)) == NULL) {
	printf("Couldn't open intuition.library.\n");
	exit(1);
    }
    
    
    ser = ComOpen("serial.device", 0, 2400, 8, NO_PARITY, 1, 4096, 0, NULL);

    if (ser == NULL) {
	printf("term:  Error opening the serial port.\n");
	exit(1);
    }


    oldflags = ser->ComWindow->IDCMPFlags;
    ModifyIDCMP(ser->ComWindow, RAWKEY);
    ser->ComFlushTime = 0;


    printf(LOCAL "Console Terminal Emulator" NORMAL);
    printf("  Version 0.1  -  Copyright 1989, Lattice Inc.\n");
    printf("Hit the HELP key for help.\n\n");


    while(! done) {
        pause = 1;

        if (ComStatus(ser) != 0) {
            GetSerial(ser);
            pause--;
        }

	len = _GetKey(ser, buff);
	
	if (len <= 0) {
            if (pause)
	        Delay(2L);
	    continue;
	}

	if (buff[0] == CSICHAR) {
	    if (strcmp(buff, HELP) == 0) {
		printf(LOCAL "\n\nF1=Dial     F2=Hangup   F3=Status   "
                       "F4=Send     F5=Receive\nF6=ASCII    F7=XMODEM   "
                       "F8=YMODEM   F9=KERMIT   F10=Quit\n\n" NORMAL);
		fflush(stdout);
	    } else if (strcmp(buff, F1) == 0) {
		printf("\n\n" LOCAL "Enter number to dial: ");
		fflush(stdout);
		GetString(ser, buff, sizeof(buff));
		if (strlen(buff) == 0) {
		    printf(LOCAL "\nDialing aborted.\n\n" NORMAL);
		    continue;
		}
		printf(LOCAL "\n\nDialing...");
		fflush(stdout);
		ComDisc(ser);
		ret = ComDial(ser, buff);
		Delay(10L);
		ComFlush(ser);
		if (ret == 1)
		    printf("Connected.\n\n" NORMAL);
		else if (ret == 0)
		    printf("Aborted.\n\n" NORMAL);
		else
		    printf("Connect failed.\n\n" NORMAL);
		fflush(stdout);
	    } else if (strcmp(buff, F2) == 0) {
                if (ComCarrier(ser)) {
		    ComDisc(ser);
		    ComFlush(ser);
                }
		printf(LOCAL "\n\nDisconnected.\n\n" NORMAL);
		fflush(stdout);
            } else if (strcmp(buff, F3) == 0) {
                printf("\n\n" LOCAL);
                if (ComCarrier(ser))
                    printf("Connected\n");
                else
                    printf("Not Connected\n");
                printf("Transfer Protocol = %s\n\n" NORMAL, proto[protocol]);
                fflush(stdout);
            } else if (strcmp(buff, F4) == 0) {
                printf("\n\n" LOCAL "Name of file(s) to send: ");
                fflush(stdout);
		fflush(stdout);
		GetString(ser, buff, sizeof(buff));
		if (strlen(buff) == 0) {
		    printf(LOCAL "\n%s Send aborted.\n\n" NORMAL,
                                                          proto[protocol]);
		    continue;
		}
		printf(LOCAL "\nSending...\n");
		fflush(stdout);
                switch(protocol) {
                    case 0:  ComSendA(ser, buff);  break;
                    case 1:  ComSendX(ser, buff);  break;
                    case 2:  ComSendY(ser, buff);  break;
                    case 3:  ComSendK(ser, buff);  break;
                }
                printf("\n\n" NORMAL);
                fflush(stdout);
            } else if (strcmp(buff, F5) == 0) {
                if (protocol == KERMIT) {
                    printf(LOCAL "\n\nStarting Kermit Receive.  "
                                 "Hit <ESC> to abort...\n");
                    ret = ComRecvK(ser);
                    if (ret < 0)
                        printf("\nKermit Receive failed.\n\n" NORMAL);
                    else if (ret > 0)
                        printf("\nKermit Receive completed.\n\n" NORMAL);
                    else
                        printf("\nKermit Receive aborted.\n\n" NORMAL);
                } else if (protocol == ASCII) {
                    printf(LOCAL "\n\nEnter name of capture file: ");
                    GetString(ser, buff, sizeof(buff));
                    if (strlen(buff) == 0) {
                        printf(LOCAL "\nASCII capture aborted.\n\n" NORMAL);
                        continue;
                    }
                    printf(LOCAL "\nHit HELP or any function key to end"
                                   " the capture.\n\n" NORMAL);
                    ret = ComRecvA(ser, buff, CSICHAR, 0, 0);
                    if (ret != 1)
                        printf(LOCAL "\n\nASCII Capture failed.\n\n" NORMAL);
                    else
                        printf(LOCAL "\n\nASCII Capture ended.\n\n" NORMAL);
                } else {
                    printf(LOCAL "\n\nEnter name of receive file: ");
                    GetString(ser, buff, sizeof(buff));
                    if (strlen(buff) == 0) {
                        printf(LOCAL "\n%s Receive aborted.\n\n" NORMAL,
                                              proto[protocol]);
                        continue;
                    }
                    printf(LOCAL "\n\n%s Receive started.  Hit <ESC> to "
                                       "abort...\n", proto[protocol]);
                    if (protocol == XMODEM)
                        ret = ComRecvX(ser, buff);
                    else
                        ret = ComRecvY(ser, buff);
                    if (ret < 0)
                        printf("\n%s Receive failed.\n\n" NORMAL,
                                              proto[protocol]);
                    else if (ret == 0)
                        printf("\n%s Receive aborted.\n\n" NORMAL,
                                              proto[protocol]);
                    else
                        printf("\n%s Receive completed.\n\n" NORMAL,
                                              proto[protocol]);
                }
            } else if (strcmp(buff, F6) == 0) {
                protocol = ASCII;
                printf(LOCAL "\n\nProtocol set to ASCII.\n\n" NORMAL);
                fflush(stdout);
            } else if (strcmp(buff, F7) == 0) {
                protocol = XMODEM;
                printf(LOCAL "\n\nProtocol set to XMODEM.\n\n" NORMAL);
                fflush(stdout);
            } else if (strcmp(buff, F8) == 0) {
                protocol = YMODEM;
                printf(LOCAL "\n\nProtocol set to YMODEM.\n\n" NORMAL);
                fflush(stdout);
            } else if (strcmp(buff, F9) == 0) {
                protocol = KERMIT;
                printf(LOCAL "\n\nProtocol set to KERMIT.\n\n" NORMAL);
                fflush(stdout);
	    } else if (strcmp(buff, F10) == 0) {
		done++;
		continue;
	    } else {
		ComWrite(ser, buff, len);
	    }
	} else {
	    ComWrite(ser, buff, len);
	}
    }


    ModifyIDCMP(ser->ComWindow, oldflags);

    ComClose(ser);
	
    CloseLibrary((struct Library *) IntuitionBase);


    exit(0);
}




void GetSerial(comport)
    COMPORT     comport;
{
    char   buffer[128];
    int    len;
    int    i;


    if ((len = ComRead(comport, buffer, sizeof(buffer))) != 0) {
	for (i=0; i<len; i++)
	    putchar(buffer[i] & 0x7F);

	fflush(stdout);
    }


    return;
}



void GetString(comport, buffer, blen)
    COMPORT   comport;
    char      *buffer;
    int       blen;
{
    char    buff[16];
    int     len;
    int     slen = 0;

    printf(INPUT);
    fflush(stdout);

    for (len=_GetKey(comport, buff); buff[0] != '\r' && buff[0] != '\n';
                                         len=_GetKey(comport, buff)) {
	if (len != 1)
	    continue;

	switch(buff[0]) {
	    case '\b':  if (slen > 0) {
			    printf("\b \b");
			    fflush(stdout);
			    slen--;
			} else {
			    DisplayBeep(comport->ComWindow->WScreen);
			}
			break;
	    case 27:    buffer[0] = 0;
	    		return;
	    default:    if (slen < blen - 1) {
			    putchar(buff[0]);
			    fflush(stdout);
			    buffer[slen++] = buff[0];
			} else {
			    DisplayBeep(comport->ComWindow->WScreen);
			}
		        break;
	}
    }

    buffer[slen] = 0;


    return;
}
