/* * WINDOW.C * * DNET interactive terminal window. */ #include "dnet.h" #include #include "/server/servers.h" typedef struct IOStdReq IOCON; typedef struct TextAttr TA; typedef struct IntuiText ITEXT; typedef struct MenuItem ITEM; typedef struct Menu MENU; extern void *OpenWindow(); long IntuitionBase; long GfxBase; TA Ta = { (ubyte *)"topaz", 8 }; ITEXT IText[] = { { 0, 1, JAM2, 0, 0, &Ta, (ubyte *)"SendBreak" }, { 0, 1, JAM2, 0, 0, &Ta, (ubyte *)"StartDNET" }, { 0, 1, JAM2, 0, 0, &Ta, (ubyte *)"QUIT" } }; ITEM Item[] = { { &Item[1], 0, 0, 120, 10, ITEMTEXT|COMMSEQ|ITEMENABLED|HIGHCOMP, 0, (APTR)&IText[0], NULL, 'b' }, { &Item[2], 0,10, 120, 10, ITEMTEXT|COMMSEQ|ITEMENABLED|HIGHCOMP, 0, (APTR)&IText[1], NULL, 's' }, { NULL , 0,20, 120, 10, ITEMTEXT|COMMSEQ|ITEMENABLED|HIGHCOMP, 0, (APTR)&IText[2], NULL, 'q' } }; MENU Menu[] = { { NULL , 0, 0, 120, 20, MENUENABLED, "DnetControl", &Item[0] } }; do_dnetwindow() { static struct NewWindow Nw = { 50, 50, 320, 100, -1, -1, CLOSEWINDOW|MENUPICK, WINDOWSIZING|WINDOWDRAG|WINDOWDEPTH|WINDOWCLOSE|NOCAREREFRESH|ACTIVATE, NULL, NULL, (UBYTE *)"DNET V1.10", NULL, NULL, 32, 32, -1, -1, WBENCHSCREEN }; struct Window *win; char RcvBuf[128]; char Cc; char RSync = 0; long imask, smask, conmask, mask, dnet_mask; IOCON *iocr, *iocw; char notdone = 1; int returncode = -1; setparity(0xFF, 0x00, 0); IntuitionBase = OpenLibrary("intuition.library", 0); GfxBase = OpenLibrary("graphics.library", 0); if (IntuitionBase == NULL || GfxBase == NULL) goto e1; win = OpenWindow(&Nw); if (win == NULL) goto e1; SetMenuStrip(win, Menu); OpenConsole(win, &iocr, &iocw); if (iocr == NULL) goto e3; if (Wto_act) { AbortIO(&Wto); WaitIO(&Wto); Wto_act = 0; } AbortIO(RNet); WaitIO(RNet); RNet->io_Data = (APTR)RcvBuf; RNet->io_Length = 1; SendIO(RNet); iocr->io_Data = (APTR)&Cc; iocr->io_Length = 1; SendIO(iocr); NetWrite("\rAT\r", 4, 0); /* cause modem to reset baud rate */ imask = 1 << win->UserPort->mp_SigBit; smask = 1 << RNet->io_Message.mn_ReplyPort->mp_SigBit; conmask = 1 << iocr->io_Message.mn_ReplyPort->mp_SigBit; dnet_mask = 1 << DNetPort->mp_SigBit; while (notdone) { mask = Wait(imask|smask|conmask|dnet_mask); if (mask & dnet_mask) { register IOR *ior; while (ior = (IOR *)GetMsg(DNetPort)) { switch(ior->io_Command) { default: case DNCMD_WRITE: case DNCMD_EOF: case DNCMD_IOCTL: case DNCMD_QUIT: case DNCMD_OPEN: ior->io_Error = 1; break; case DNCMD_CLOSE: Chan[(ulong)ior->io_Unit].state = CHAN_FREE; break; case DNCMD_SOPEN: { uword chan = (ulong)ior->io_Unit; Chan[chan].state = CHAN_FREE; if (!ior->io_Error) { Chan[chan].state = CHAN_CLOSE; Chan[chan].port = (PORT *)ior->io_Offset; Chan[chan].flags = CHANF_RCLOSE; WritePort(Chan[chan].port, DNCMD_CLOSE, NULL, 0, PKT_REQ, chan); } if (ior->io_Length) FreeMem(ior->io_Data, ior->io_Length); FreeMem(ior, sizeof(IOR)); ior = NULL; } break; } if (ior) ReplyMsg(ior); } } if (mask & imask) { struct IntuiMessage *im; while (im = GetMsg(win->UserPort)) { switch(im->Class) { case CLOSEWINDOW: notdone = 0; returncode = -1; break; case MENUPICK: switch((uword)((MENUNUM(im->Code)<<8)|ITEMNUM(im->Code))) { case 0x0000: /* menu 0 item 0 */ NetBreak(); break; case 0x0001: /* menu 0 item 1 */ notdone = 0; returncode = 1; break; case 0x0002: /* menu 0 item 2 */ notdone = 0; returncode = -1; break; case 0x0100: /* menu 1 item 0 */ break; } break; } ReplyMsg(im); } } if (mask & smask) { if (CheckIO(RNet)) { int n; ubyte dummy; WaitIO(RNet); if (RNet->io_Actual > 0) { ubyte c = *(ubyte *)RNet->io_Data; if (RSync && c == PKCMD_RESTART) { returncode = 1; notdone = 0; } RSync = (c == SYNC); for (n = 0; n < RNet->io_Actual; ++n) ((char *)RNet->io_Data)[n] &= 0x7F; iocw->io_Data = RNet->io_Data; iocw->io_Length = RNet->io_Actual; DoIO(iocw); } if ((n = NetReady(RNet, &dummy)) > sizeof(RcvBuf)) n = sizeof(RcvBuf); if (n <= 0) n = 1; RNet->io_Data = (APTR)RcvBuf; RNet->io_Length= n; SendIO(RNet); } } if (mask & conmask) { if (CheckIO(iocr)) { WaitIO(iocr); addparity(iocr->io_Data, iocr->io_Actual); NetWrite(iocr->io_Data, iocr->io_Actual, 0); NetWrite(NULL, 0, 0); iocr->io_Data = (APTR)&Cc; iocr->io_Length = 1; SendIO(iocr); } } } AbortIO(RNet); WaitIO(RNet); RNet->io_Data = (APTR)&Raux->sync; /* Startup the network read */ RNet->io_Length = 3; SendIO(RNet); AbortIO(iocr); WaitIO(iocr); CloseConsole(iocr, iocw); e3: CloseWindow(win); e1: if (IntuitionBase) CloseLibrary(IntuitionBase); if (GfxBase) CloseLibrary(GfxBase); if (returncode > 0) puts("DNET RUNNING"); else puts("DNET EXITING"); return(returncode); } /* * PARITY ROUTINES */ static ubyte Party[256/8]; setparity(pand, por, podd) { register short i, j, k, l; bzero(Party, sizeof(Party)); for (i = 0; i < 128; ++i) { for (j = (~i & 127), k = 0; j; j >>= 1) { /* k = count # of 0's */ if (j & 1) ++k; } k ^= podd; l = (((k & 1) ? 0x01 : 0) | por) & pand; Party[i >> 3] |= l << (i & 7); } } addparity(buf, bytes) register ubyte *buf; { register short i; for (i = bytes - 1; i >= 0; --i) { if (Party[buf[i]>>3] & (1 << (buf[i]&7))) buf[i] |= 0x80; } } OpenConsole(win, piocr, piocw) IOCON **piocr, **piocw; struct Window *win; { PORT *port; static IOCON iocr, iocw; int error; port = CreatePort(NULL, 0); iocr.io_Command = CMD_READ; iocr.io_Data = (APTR)win; iocr.io_Message.mn_Node.ln_Type = NT_MESSAGE; iocr.io_Message.mn_ReplyPort = port; error = OpenDevice("console.device", 0, &iocr, 0); if (!error) { iocw = iocr; iocw.io_Command = CMD_WRITE; *piocr = &iocr; *piocw = &iocw; } else { *piocr = *piocw = NULL; } } CloseConsole(iocr, iocw) IOCON *iocr; IOCON *iocw; { CloseDevice(iocr); DeletePort(iocr->io_Message.mn_ReplyPort); }