home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
OS/2 Shareware BBS: 3 Comm
/
03-Comm.zip
/
STERM.ZIP
/
STERMK.C
< prev
next >
Wrap
Text File
|
1991-01-14
|
17KB
|
526 lines
/* STERMK.C
Process Key Definition File; filling in the
provided area with an array of pointers to
strings: (actually replace pointers with
new pointers.
*/
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#define INCL_SUB
#define INCL_DOSDEVICES
#include <os2kernl.h>
#include <process.h>
#define STERMK
#include "sterm.h"
#define VTBOT 0x3B /* bottom of keytrans tbl */
#define VTTOP 0x92 /* top of keytrans tbl */
typedef struct {
char *keyname; /* name of key */
char keysc; /* scan value for x00 or xe0 char */
} keydef;
/* PC keys available to re-map, try and keep the Alts
for us (xcept function keys */
static keydef keyn[ ] = {
{ "F1", '\x3b' },
{ "F2", '\x3c' },
{ "F3", '\x3d' },
{ "F4", '\x3e' },
{ "F5", '\x3f' },
{ "F6", '\x40' },
{ "F7", '\x41' },
{ "F8", '\x42' },
{ "F9", '\x43' },
{ "F10", '\x44' },
{ "F11", '\x85' },
{ "F12", '\x86' },
{ "HOME", '\x47' },
{ "CENTER", '\x4c' },
{ "UP->", '\x48' },
{ "PGUP", '\x49' },
{ "LEFT->", '\x4b' },
{ "RIGHT->", '\x4d' },
{ "END", '\x4f' },
{ "DOWN->", '\x50' },
{ "PGDN", '\x51' },
{ "INS", '\x52' },
{ "DEL", '\x53' },
{ "S-F1", '\x54' },
{ "S-F2", '\x55' },
{ "S-F3", '\x56' },
{ "S-F4", '\x57' },
{ "S-F5", '\x58' },
{ "S-F6", '\x59' },
{ "S-F7", '\x5a' },
{ "S-F8", '\x5b' },
{ "S-F9", '\x5c' },
{ "S-F10", '\x5d' },
{ "S-F11", '\x87' },
{ "S-F12", '\x88' },
{ "C-F1", '\x5e' },
{ "C-F2", '\x5f' },
{ "C-F3", '\x60' },
{ "C-F4", '\x61' },
{ "C-F5", '\x62' },
{ "C-F6", '\x63' },
{ "C-F7", '\x64' },
{ "C-F8", '\x65' },
{ "C-F9", '\x66' },
{ "C-F10", '\x67' },
{ "C-F11", '\x89' },
{ "C-F12", '\x8a' },
{ "C-HOME", '\x77' },
{ "C-UP->", '\x8d' },
{ "C-PGUP", '\x84' },
{ "C-KMIN", '\x8e' },
{ "C-LEFT->", '\x73' },
{ "C-CENTER", '\x8f' },
{ "C-RIGHT->",'\x74' },
{ "C-KPLUS", '\x90' },
{ "C-END", '\x75' },
{ "C-DOWN->", '\x91' },
{ "C-INS", '\x92' },
{ "C-PRTSC", '\x72' },
{ "A-F1", '\x68' },
{ "A-F2", '\x69' },
{ "A-F3", '\x6a' },
{ "A-F4", '\x6b' },
{ "A-F5", '\x6c' },
{ "A-F6", '\x6d' },
{ "A-F7", '\x6e' },
{ "A-F8", '\x6f' },
{ "A-F9", '\x70' },
{ "A-F10", '\x71' },
{ "A-F11", '\x8b' },
{ "A-F12", '\x8c' },
{ "", '\0' }
};
/* search for a PC key and return its scan code */
static UCHAR fpckey( PUCHAR pcn )
{
short ix = 0;
while ( ( keyn[ ix ].keysc != '\0' ) &&
( strcmp( keyn[ ix ].keyname, pcn ) != 0 ) )
ix++;
return( keyn[ ix ].keysc );
} /* end fpckey */
/* table of 3270 functions and their escape sequences */
typedef struct {
PCHAR f3270; /* 3270 key function */
PCHAR escseq; /* corresponding esc. seq. */
} ibmkeys;
static ibmkeys k3270[] = {
{ "PF1", "\x1bOP\r" }, /* PF1: ESC, O, P */
{ "PF2", "\x1bOQ\r" }, /* PF2: ESC, O, Q */
{ "PF3", "\x1bOR\r" }, /* PF3: ESC, O, R */
{ "PF4", "\x1bOw\r" }, /* PF4: ESC, O, w */
{ "PF5", "\x1bOx\r" }, /* PF5: ESC, O, x */
{ "PF6", "\x1bOy\r" }, /* PF6: ESC, O, y */
{ "PF7", "\x1bOt\r" }, /* PF7: ESC, O, t */
{ "PF8", "\x1bOu\r" }, /* PF8: ESC, O, u */
{ "PF9", "\x1bOv\r" }, /* PF9: ESC, O, v */
{ "PF10","\x1bOq\r" }, /* PF10:ESC, O, q */
/* home */
{ "HOME", "\x1b[H\r" },
{ "UP", "\x1b[A" }, /* up: ESC, [, A */
{ "LEFT", "\x1b[D" }, /* left: ESC [ D */
{ "RIGHT", "\x1b[C" }, /* right:ESC [ C */
{ "DOWN", "\x1b[B" }, /* down: ESC [ B */
{ "INS", "\x01" }, /* ins: CTLA */
{ "DEL", "\x02" }, /* del: CTLB */
{ "PF11", "\x1bOr\r" }, /* PF11: ESC,O,r */
{ "PF12", "\x1bOs\r" }, /* PF12: ESC, O, s */
{ "PA3", "\x1bOl\r" }, /* PA3: ESC,O,l */
{ "PA1", "\x1bOS\r" }, /* PA1: ESC, O, S */
{ "PA2", "\x1bOm\r" }, /* PA2: ESC, O, m */
{ "EEOF", "\x1b\x65\r" }, /* eeof: ESC e */
{ "CLEAR", "\x1bOM\r" }, /* clear: ESC, O, M*/
{ "", "" } /* end table */
};
/* search for an 3270 key and return ptr to esc seq. */
static PUCHAR f3270key( PUCHAR ibmk )
{
short ix = 0;
while ( ( k3270[ ix ].f3270 != '\0' ) &&
( strcmp( k3270[ ix ].f3270, ibmk ) != 0 ) )
ix++;
return( k3270[ ix ].escseq );
} /* end f3270key */
/* read file with form
PCKEY = 3270KEY
input: pathname of definition file
output: ptr to constructed trans tbl */
KREF PUCHAR prockey( PUCHAR kfn )
{
FILE *kf;
#define KLINE 80
char kstr[KLINE]; /* input statement */
char *ibmkey, /* 3270 function name */
*pckey; /* PC key name */
PUCHAR *outtbl; /* output tbl of ptrs */
PUCHAR escseq; /* esc seq ptr from f3270key */
char sccode; /* scan code of PC key */
kf = fopen( kfn, "r" );
if ( !kf )
errexit( "No Key Definition File");
/* acquire output table */
outtbl = calloc( (VTTOP-VTBOT+1), sizeof(outtbl) );
pckey = fgets( kstr, KLINE-1, kf );
while ( pckey )
{
if ( pckey[0] != '*' ) /* ignore comment */
{
pckey = strtok( kstr, " =" );
pckey = strupr( pckey );
sccode = fpckey( pckey );
if ( sccode == '\0' )
errexit( "Requires PC Keyname" );
ibmkey = strtok( NULL, " \n" );
if ( ibmkey )
{
strupr( ibmkey );
escseq = f3270key( ibmkey );
if ( escseq == NULL )
errexit( "Requires 3270 Key" );
}
else
errexit( "Requires 3270 Key" );
/* place the ptr to escape seq. at the key offset in outtbl */
outtbl[ sccode-VTBOT ] = escseq;
}
pckey = fgets( kstr, KLINE-1, kf );
}
return( (PUCHAR) outtbl );
} /* end prockey */
/* table of PC function keys with
extended scan out 00 or e0 between
0x3B and 0x92, default SimVT mapping */
KREF PUCHAR vtkey[VTTOP-VTBOT+1] =
{ "\x1bOP\r", /* 3b F1: ESC, O, P */
"\x1bOQ\r", /* 3c F2: ESC, O, Q */
"\x1bOR\r", /* 3d F3: ESC, O, R */
"\x1bOw\r", /* 3e F4: ESC, O, w */
"\x1bOx\r", /* 3f F5: ESC, O, x */
"\x1bOy\r", /* 40 F6: ESC, O, y */
"\x1bOt\r", /* 41 F7: ESC, O, t */
"\x1bOu\r", /* 42 F8: ESC, O, u */
"\x1bOv\r", /* 43 F9: ESC, O, v */
"\x1bOq\r", /* 44 F10:ESC, O, q */
"", /* 45 n/a */
"", /* 46 n/a */
/* home, */
"\x1b[H\r",
"\x1b[A", /* 48 up: ESC, [, A */
"\x1bOt\r", /* 49 pgup = F7 */
"", /* 4A n/a */
"\x1b[D", /* 4B left: ESC [ D */
"", /* 4C n/a */
"\x1b[C", /* 4D right:ESC [ C */
"", /* 4E n/a */
"\x1bOR\r", /* 4F end = PF3 */
"\x1b[B", /* 50 down: ESC [ B */
"\x1bOu\r", /* 51 pgdown = PF8 */
"\x01", /* 52 ins: CTLA */
"\x02", /* 53 del: CTLB */
"\x1bOr\r", /* 54 shift f1 PF11 */
"\x1bOs\r", /* 55 shift f2 PF12 */
"", /* 56 shift f3 */
"", /* 57 shift f4 */
"", /* 58 shift f5 */
"", /* 59 shift f6 */
"", /* 5A shift f7 */
"", /* 5B shift f8 */
"", /* 5C shift f9 */
"", /* 5D shift f10 */
"", /* 5E ctl f1 */
"", /* 5F ctl f2 */
"\x1bOl\r", /* 60 ctl f3 PA3 */
"", /* 61 ctl f4 */
"\x1bOS\r", /* 62 ctl f5 PA1 */
"\x1bOm\r", /* 63 ctl f6 PA2 */
"", /* 64 ctl f7 */
"", /* 65 ctl f8 */
"", /* 66 ctl f9 */
"", /* 67 ctl f10 */
"", /* 68 alt f1 */
"", /* 69 alt f2 */
"", /* 6A alt f3 */
"", /* 6B alt f4 */
"", /* 6C alt f5 */
"", /* 6D alt f6 */
"", /* 6E alt f7 */
"", /* 6F alt f8 */
"", /* 70 alt f9 */
"", /* 71 alt f10 */
"", /* 72 n/a */
"", /* 73 ctl left arr */
"", /* 74 ctl righ arr */
"\x1b\x65\r", /* 75 eeof: ESC e */
"", /* 76 ctl pgdn */
"\x1bOM\r", /* 77 clear: ctl home*/
"", /* 78 n/a */
"", /* 79 n/a */
"", /* 7a n/a */
"", /* 7b n/a */
"", /* 7c n/a */
"", /* 7d n/a */
"", /* 7e n/a */
"", /* 7f n/a */
"", /* 80 n/a */
"", /* 81 n/a */
"", /* 82 n/a */
"", /* 83 n/a */
"", /* 84 n/a */
"", /* 85 n/a */
"", /* 86 n/a */
"", /* 87 n/a */
"", /* 88 n/a */
"", /* 89 n/a */
"", /* 8a n/a */
"", /* 8b n/a */
"", /* 8c n/a */
"", /* 8d n/a */
"", /* 8e n/a */
"", /* 8f n/a */
"", /* 90 n/a */
"", /* 91 n/a */
"" /* 92 n/a */
};
/* translate PC key(s) to SIMVT sequence
returns length of output */
static int vtkeys( PUCHAR *ostr )
{
PUCHAR esp;
/* return -1 if key invalid, return 0
if no translation */
/* if tab, translate here */
if ( keyi.chChar == '\x09' )
{
*ostr = "\x1bOn\r"; return( 4 );
}
/* c-enter is linefeed aka newline,
SIM3278 screws this one up;
ship escseq to go to next line */
if ( keyi.chChar == '\n' )
{
return( 0 ); /* do nothing */
}
if ( ( keyi.chChar != 0 ) && ( keyi.chChar != 0xe0 ) )
return( 0 ); /* no translation */
/* may be back tab */
if ( keyi.chScan == '\x0f' )
{
*ostr = "\x1bOp\r"; return( 4 );
}
if ( ( keyi.chScan < VTBOT ) || ( keyi.chScan > VTTOP ) )
return ( -1 ); /* invalid character */
esp = Sim3270[keyi.chScan-VTBOT];
if ( ( (long) esp == 0 ) || ( *esp == '\0' ) )
return( -1 ); /* unsupported key */
*ostr = esp;
return( strlen( esp ) );
} /* end vtkeys */
/* Read with KeyBoard Functions
If Alt-X, signal EOJ */
void kbdin(void)
{
short wlen; /* actual written length */
MsgH kbmsg;
PUCHAR cmdp; /* ptr in above */
PUCHAR vtstr = ""; /* translated key string ptr */
USHORT nsave = 0;
USHORT cury = 0, curx = 0;
UCHAR cmdbuf[WSLEN];
#define INPLEN (72*2)
UCHAR saveline[INPLEN];
/* set binary keyboard mode */
keyb.cb = 10;
KbdGetStatus( (PKBDINFO) &keyb, 0 );
keyb.fsMask &= 0xffe0; /* insure shift report off */
keyb.fsMask |= 0x06; /* no echo, binary */
KbdSetStatus( (PKBDINFO) &keyb, 0 );
/* init cmdbuf, in case.. */
cmdp = cmdbuf;
while ( TRUE )
{
/* wait on a keypress */
KbdCharIn( (PKBDKEYINFO) &keyi, IO_WAIT, 0 );
/* filter out special 'alt' keys */
if ( ( keyi.chChar == 0 ) || ( keyi.chChar == 0xe0 ) )
switch ( keyi.chScan )
{
case EXITKEY:
{
/* if main in AWAIT, clear that */
if ( waitlen )
{ /* wait for ANY */
waitlen = 0; waitrc = AWAIT_EOJ;
DosSemClear( (HSEM) &waitsem );
}
DosSemClear( (HSEM) &exitsem ); /* signal main thread */
_dosendthread();
} /* alt-x */
case PLEX:
{ /* toggle local echo */
CurP->halfplex = ! CurP->halfplex;
continue;
} /* alt-e */
case CLEARKEY:
if ( keymode == tty )
{
clrscrn();
continue;
}
else
break;
case CMDKEY:
{ /* toggle command mode */
if ( keymode == command )
{
keymode = prevmode;
/* restore screen line */
VioWrtCellStr( saveline, INPLEN, 0, 0, 0 );
VioSetCurPos( cury, curx, 0 );
}
else
{
prevmode = keymode; keymode = command;
cmdp = cmdbuf;
/* save screen line */
nsave = INPLEN;
VioReadCellStr( saveline, (PUSHORT) &nsave,
0, 0, 0 );
VioGetCurPos( (PUSHORT) &cury, (PUSHORT) &curx, 0 );
VioSetCurPos( 0, 0, 0 );
VioWrtNChar( " ", INPLEN/2, 0, 0, 0 );
VioSetCurPos( 0, 0, 0 );
}
continue;
}
} /* end switch on scan char */
/* if key data not to be transmitted, just loop */
if ( keymode == ignore )
continue;
/* if command being read from keyboard */
if ( keymode == command )
{
if ( keyi.chChar == '\r' )
{ /* process command string */
*cmdp = '\0';
/* call cmd handler - STERMP */
verbex( cmdbuf );
cmdp = cmdbuf; /* reset ptr */
VioSetCurPos( 0, 0, 0 );
VioWrtNChar( " ", INPLEN/2, 0, 0, 0 );
VioSetCurPos( 0, 0, 0 );
}
else
{
/* should display char */
*cmdp = keyi.chChar;
VioWrtTTY( cmdp, 1, 0 );
cmdp++;
}
continue;
}
/* if we were AWAITing, stop processing script */
if ( waitlen )
{ /* wait for ANY */
waitlen = 0; waitrc = AWAIT_ENDP;
DosSemClear( (HSEM) &waitsem );
}
kbmsg.imdat = keyi.chChar; /* prime for normal case */
kbmsg.mtype = immed;
kbmsg.mlen = 1;
kbmsg.doecho = TRUE;
/* if terminal emulation, translate PC key to escape seq. */
if ( keymode == SIMVT )
{ /* translate PC key to string (if required) */
kbmsg.mlen = vtkeys( &vtstr );
if ( kbmsg.mlen < 0 )
{ /* send BEL */
VioWrtTTY( "\a", 1, 0 );
continue; /* invalid character */
}
/* set insert mode on/off for insert key */
if ( ( kbmsg.mlen == 1 ) && ( vtstr[0] == '\x01' ) )
{
kbmsg.doecho = FALSE; insmode ^= TRUE;
}
if ( kbmsg.mlen >= 1 )
{
/* put out hdr, then data */
if ( vtstr[ kbmsg.mlen-1 ] == '\r' )
kbmsg.doecho = FALSE; /* suppress echo for immediate actions */
kbmsg.mtype = dhead;
DosWrite( comoW, (PVOID) &kbmsg, sizeof(MsgH), (PUSHORT) &wlen );
DosWrite( comoW, (PVOID) vtstr, kbmsg.mlen, (PUSHORT) &wlen );
}
else
DosWrite( comoW, (PVOID) &kbmsg, sizeof(MsgH), (PUSHORT) &wlen );
}
else
/* send data key to the interested party */
DosWrite( comoW, (PVOID) &kbmsg, sizeof(MsgH), (PUSHORT) &wlen );
} /* end of while */
}