home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Club Amiga de Montreal - CAM
/
CAM_CD_1.iso
/
files
/
339.lha
/
DispMod
/
source
/
dispmod.c
< prev
next >
Wrap
C/C++ Source or Header
|
1990-02-07
|
13KB
|
485 lines
/****************************
* dispmod.c
* Display module for ROBBS.
*****************************/
#include <libraries/dos.h>
#include <fcntl.h>
#include <functions.h>
#include <exec/types.h>
#include <stdio.h>
#include <intuition/intuition.h>
#include <exec/memory.h>
#include <rexx/storage.h>
#include <rexx/rxslib.h>
#include "ConsoleIO.h"
#include "Rexx.h"
#include "defs.h"
char portname[17] = "ROBBS_ctrl";
char macroport[17] = "ROBBS_ctrl";
char command[10] = "SEND";
char keystring[255];
char status[100];
char normaltext[] = "\x9Bm";
char redtext[] = "\x9B33m";
UBYTE titlestring[77] = VERSION;
STRPTR Token;
int connected;
int outstanding_rexx_commands = 0;
int CRPending = 0;
struct RexxLib *RexxSysBase;
struct MsgPort RexxPort;
struct RexxMsg *rmptr, *OutMsg, *CreateRexxMsg();
BOOL KeepGoing = TRUE;
void FreePort();
char nexttoken();
STRPTR CreateArgstring();
struct IntuitionBase *IntuitionBase = NULL;
static struct IOStdReq *Console = NULL; /* see "ConsoleIO.h" */
static struct Window *mywindow = NULL; /* ptr to applications window */
static struct IntuiMessage *NewMessage; /* msg structure for GetMsg() */
static struct IOStdReq *rd = NULL, *wr = NULL;
static char *validargs[] =
{
"TEXT", /* 0 */
"LTEXT", /* 1 */
"HTEXT", /* 2 highlighted text, one colour only for now */
"LHTEXT", /* 3 same, with linefeed appended */
"CRSR", /* 4 cursor row, column */
"GETLINE", /* 5 getline [prompt] */
"STATUS", /* 6 */
"CONNECT", /* 7 */
"CTRL", /* 8 */
"TITLE", /* 9 */
"DIE", /* 10 */
NULL
};
static int numcmds = 11;
/* my window structure */
static struct NewWindow NewWindow = {
0,0,640,200, /* left, top, width, height */
0,1, /* detail, block pens */
CLOSEWINDOW | GADGETUP,
WINDOWCLOSE
| SMART_REFRESH
| ACTIVATE
| WINDOWDEPTH
| BORDERLESS
,
NULL, /* firstgadget */
NULL, /* checkmark */
titlestring, /* title */
0, /* screen */
NULL, /* bitmap */
0,0, /* min x,y */
640, 200, /* max x,y */
WBENCHSCREEN /* type */
};
/*--------------------------------------------------------------*/
/* cleanup: all done so close up and prepare to exit */
/*--------------------------------------------------------------*/
static void cleanup()
{
if (RexxSysBase != NULL)
{
RemPort(&RexxPort); /* unlink it */
FreePort(&RexxPort); /* release the port resources */
CloseLibrary(RexxSysBase);
}
if ( mywindow != NULL )
CloseWindow( mywindow );
if ( Console != NULL )
CloseConsoleIO();
if ( IntuitionBase != NULL )
CloseLibrary(IntuitionBase);
}
/*-------------------------------------------------------*/
/* init: initialize dispmod - set defaults */
/*-------------------------------------------------------*/
static void init()
{
IntuitionBase = (struct IntuitionBase *)
OpenLibrary("intuition.library", INTUITION_REV);
if( IntuitionBase == NULL )
{
puts("can't open intuition\n");
goto badopen;
}
if(( mywindow = OpenWindow(&NewWindow) ) == NULL)
{
puts("Can't open a window.\n");
goto badopen;
}
if(( Console = InitConsoleIO( mywindow, &rd, &wr ) ) == NULL)
{
puts("Can't open the console.\n");
goto badopen;
}
RexxSysBase = (struct RexxLib *)OpenLibrary("rexxsyslib.library",0L);
if (RexxSysBase == NULL)
{
printf("Can't open rexxsyslib.library.\n");
goto badopen;
}
InitPort(&RexxPort,"ROBBS_disp"); /* Initialize our message port */
AddPort(&RexxPort); /* Make the port public */
return;
badopen:
cleanup();
exit( 4 );
}
/*--------------------------------------------------------------*/
/* buildstatus: build status string from variables */
/*--------------------------------------------------------------*/
void buildstatus()
{
int j;
sprintf(status, "%s %s %lx %lx",portname, macroport, mywindow, wr);
}
/*-----------------------------------------------------------------*/
/* send_rexx_msg: send a message to a port */
/*-----------------------------------------------------------------*/
send_rexx_msg(port, cmd, s)
char *port;
char *cmd;
char *s;
{
struct MsgPort *localport;
/* RexxPort is reply port. look for reply there */
OutMsg = CreateRexxMsg(&RexxPort, "dccs", "DCCS" );
if (OutMsg != NULL)
{
OutMsg->rm_Args[0] = CreateArgstring( cmd, (long) strlen( cmd ));
OutMsg->rm_Args[1] = CreateArgstring( s, (long) strlen( s ));
OutMsg->rm_Action = RXFUNC | 1;
/* FillRexxMsg(OutMsg, 1L, 0L); */
Forbid();
localport = FindPort(port);
if (localport != 0) PutMsg(localport, OutMsg);
Permit();
};
outstanding_rexx_commands++;
return(0); /* ya, I know, I need error checking. */
}
/*-----------------------------------------------------------------*/
/* free_rexx_command: free the message we sent and decrement count */
/*-----------------------------------------------------------------*/
free_rexx_command(rexxmsg)
register struct RexxMsg *rexxmsg;
{
/* delete the argument that we originally sent */
DeleteArgstring(rexxmsg->rm_Args[0]);
DeleteArgstring(rexxmsg->rm_Args[1]);
/* delete the extended message */
DeleteRexxMsg(rexxmsg);
/* decrement the count of outstanding messages */
outstanding_rexx_commands--;
}
/*-----------------------------------------------------------------*/
/* sendfkey(number): inform of function key usage */
/*-----------------------------------------------------------------*/
sendfkey( num )
short num;
{
char message[8];
sprintf( message, "%c", num );
send_rexx_msg(macroport, "FKEY", message);
}
/*-----------------------------------------------------------------*/
/* sendhelp(number): inform of HELP key usage */
/*-----------------------------------------------------------------*/
sendhelp()
{
send_rexx_msg(macroport, "HELP", NULL);
}
/*-----------------------------------------------------------------*/
/* nexttoken(): search for next space or NULL in token string */
/*-----------------------------------------------------------------*/
char
nexttoken()
{
for ( ;(*Token != ' ' && *Token != '\0'); Token++ );
if (*Token == ' ') {
Token++;
return(' ');
}
else
return('\0');
}
/*-----------------------------------------------------------------*/
/* cr2lf(s): convert all instances of CR in string s to linefeeds */
/* : leave cr/lf combination alone */
/*-----------------------------------------------------------------*/
cr2lf ( s )
char *s;
{
if ( CRPending )
if ( *s != '\n' )
PutString("\n");
CRPending = 0;
for (; *s; s++) {
if ( (*s == '\r') && (*(s+1) != '\n') )
if ( *(s+1) = '\0' )
CRPending = 1;
else
*s = '\n';
}
}
/******************************************************/
/* Main Program */
/* */
/* This is the main body of the program. */
/******************************************************/
main()
{
ULONG class, waitmask;
int c, i, j, x, y, code, keycount ;
UBYTE character;
init();
waitmask = (1L << mywindow->UserPort->mp_SigBit)
| (1L << Console->io_Message.mn_ReplyPort->mp_SigBit)
| (1L << RexxPort.mp_SigBit);
KeepGoing = TRUE;
while( KeepGoing )
{
if (( rmptr = (struct RexxMsg *) GetMsg(&RexxPort)) == NULL )
{
Wait( waitmask );
rmptr = (struct RexxMsg *) GetMsg(&RexxPort);
}
if (rmptr)
{
if (rmptr->rm_Node.mn_Node.ln_Type == NT_REPLYMSG )
free_rexx_command(rmptr);
else
{
Token = rmptr->rm_Args[0];
for (i=0; i < numcmds; i++)
if ( StrcmpN(rmptr->rm_Args[0], validargs[i], 3L) == NULL)
break;
if (rmptr->rm_Action & 15L) {
Token = rmptr->rm_Args[1];
}
else {
nexttoken();
}
/* Set 'normal result codes'. these are set here, */
/* and only changed in case of error or when */
/* returning a result string (as in STATUS). */
rmptr->rm_Result1 = 0; /* return code */
rmptr->rm_Result2 = 0; /* secondary result */
switch (i)
{
case 0: /* TEXT */
case 1: /* LTEXT */
/* cr2lf(Token); */
PutString(normaltext);
PutString(Token);
if (i == 1) PutString("\n");
break;
case 2: /* HTEXT */
case 3: /* LHTEXT */
/* cr2lf(Token); */
PutString(redtext);
PutString(Token);
PutString(normaltext);
if (i == 3) PutString("\n");
break;
case 4: /* CURSOR */
for (j=0; Token[j] != ' '; j++);
Token[j] = '\0';
j++;
y = atoi(Token);
x = atoi(&Token[j]);
CursorXY(x,y);
break;
case 5: /* GETLINE */
if (*Token)
GetLine(Token, keystring);
else
GetLine(NULL, keystring);
if (rmptr->rm_Action & (RXFF_RESULT))
rmptr->rm_Result2 = (long)CreateArgstring(keystring,
(long)strlen(keystring));
break;
case 6: /* STATUS */
buildstatus();
if (rmptr->rm_Action & (RXFF_RESULT))
rmptr->rm_Result2 = (long)CreateArgstring(status,
(long)strlen(status));
break;
case 7: /* CONNECT */
if (*Token) {
for (j=0; Token[j] != ' '; j++) {
portname[j] = Token[j];
}
portname[j] = '\0';
nexttoken();
for (j=0; Token[j] != ' ' && Token[j]; j++) {
command[j] = Token[j];
}
command[j] = '\0';
connected = 1;
}
else
connected = 0;
break;
case 8: /* CTRL */
if (*Token)
strcpy(macroport, Token);
break;
case 9: /* TITLE */
strcpy(titlestring, Token);
SetWindowTitles(mywindow, titlestring, 0L);
break;
case 10: /* DIE */
KeepGoing = FALSE;
break;
default:
rmptr->rm_Result1 = 5; /* return code */
break;
}
ReplyMsg(rmptr); /* send it back */
}
}
/*----- Drain the keyboard buffer--------------*/
keystring[0] = '\0';
keycount = 0;
while ( c = CheckKey() )
{
if (c != CSI)
{
keystring[keycount++] = c;
keystring[keycount] = '\0';
}
else /* here if c == CSI */
{
character = GetKey();
if ( ('A' <= character) && (character <= 'D') );
if ( ('0' <= character) && (character <= '9') ) {
sendfkey(character);
character = GetKey();
}
if (character == '?') {
sendhelp();
}
if (((character < 'A') || (character > 'D')) &&
((character != 'T')
&& (character != 'S')
&& (character != '~')
&& (character != ' ')))
while ( GetKey() != '~');
if (character == ' ') {
GetKey();
}
} /* end if CSI */
} /* end while CheckKey() */
if (keycount && connected) {
send_rexx_msg(portname, command, keystring);
}
/* ---------------- Handle all Messages --------------------*/
while( NewMessage=(struct IntuiMessage *)GetMsg(mywindow->UserPort) )
{
class = NewMessage->Class;
code = NewMessage->Code;
ReplyMsg( NewMessage );
switch( class )
{
case CLOSEWINDOW:
KeepGoing = FALSE;
break;
} /* end of switch (class) */
} /* end of while ( newmessage )*/
} /* end while ( keepgoing ) */
while (outstanding_rexx_commands)
{
printf("dispmod: Outstanding commands: %d\n",outstanding_rexx_commands );
if (( rmptr = (struct RexxMsg *) GetMsg(&RexxPort)) == NULL )
{
Wait( 1L << RexxPort.mp_SigBit );
rmptr = (struct RexxMsg *) GetMsg(&RexxPort);
}
if (rmptr) {
if( rmptr->rm_Node.mn_Node.ln_Type == NT_REPLYMSG ) {
free_rexx_command(rmptr);
}
else {
if (StrcmpN( rmptr->rm_Args[0], "REALLY_DIE", 10L) == NULL)
ReplyMsg(rmptr);
break;
}
}
}
cleanup();
exit( 0 );
} /* end of main */