This is HostListManager.m in view mode; [Download] [Up]
/*--------------------------------------------------------------------------- HostListManager.m -- Copyright (c) 1991 Rex Pruess This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 1, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA or send electronic mail to the the author. This is the methods file for the HostListManager (HLM) class. A HLM object is responsible for managing the internal linked host list and the host configuration file. Rex Pruess <rpruess@umaxc.weeg.uiowa.edu> $Header: /rpruess/apps/Remotes3.0/RCS/HostListManager.m,v 3.0 92/09/23 21:49:40 rpruess Exp $ ----------------------------------------------------------------------------- $Log: HostListManager.m,v $ Revision 3.0 92/09/23 21:49:40 rpruess Upgraded for NeXT System Release 3.0. Primary changes were to support the Terminal application under NeXT System Release 3.0. Revision 2.1 92/09/21 11:20:13 rpruess Added code to set the window title and mini-window titles for Stuart sessions. Revision 2.0 91/01/22 15:32:47 rpruess Remotes-2.0 was upgraded for NeXT System Release 2.0 (standard or extended). Remotes-2.0 supports the NeXT supplied Terminal application and the Stuart shareware product. Revision 1.1 90/04/10 14:25:48 rpruess Initial revision -----------------------------------------------------------------------------*/ /* Standard C header files */ #include <ctype.h> #include <libc.h> #include <stdio.h> #include <stdlib.h> #include <strings.h> #include <sys/file.h> /* Private C header files */ #include "remsubs.h" /* Host List Manager class header files */ #import "HostListManager.h" #import "StuartSpeaker.h" /* Appkit header files */ #import <appkit/Application.h> #import <appkit/Control.h> #import <appkit/Panel.h> #import <appkit/PopUpList.h> #import <defaults/defaults.h> @implementation HostListManager /*--------------------------------------------------------------------------- Override the new method so the object can be properly initialized. This initialization includes reading the configuration file & loading the hosts into the internal linked list. -----------------------------------------------------------------------------*/ - init { self = [super init]; [self initHLMObject:self]; /* Initialize linked host lists */ return self; } /*--------------------------------------------------------------------------- Initialize the host list. -----------------------------------------------------------------------------*/ - initHLMObject:sender { short int appType; short int autoLaunch; char buffer[MAXRECLEN + 1]; char *bufPtr; char buttonName[MAXPOPLEN + 1]; const char *defaultsDebugLevel; int code; short int columns; char field[MAXRECLEN + 1]; unsigned int flagValues; short int fontType; short int fontSize; char hName[MAXHOSTNAMELEN + 1]; int i; short int lines; short int metaNum; BOOL oldStyle; short int protocolType; int recordNum; NXSize screenSize; /* Screen width/height */ char userID[MAXIDLEN + 1]; short int versionNum; short int x; short int y; FILE *fp; /* Set debugging value from defaults data base */ defaultsDebugLevel = NXGetDefaultValue ([NXApp appName], "DebugLevel"); if (strcmp (defaultsDebugLevel, "low") == 0) debugLevel = DEBUGLOW; else if (strcmp (defaultsDebugLevel, "high") == 0) debugLevel = DEBUGHIGH; else if (strcmp (defaultsDebugLevel, "max") == 0) debugLevel = DEBUGMAX; else debugLevel = DEBUGOFF; /* Load linked host list. */ recordNum = 0; nHosts = 0; fp = [self openConfigFile:"r"]; if (fp == NULL) { /* In no hosts found, then force one! */ code = [self addLocalHost:self]; return self; } /* Read & process each record from the config file */ while (fgets (buffer, MAXRECLEN, fp) != NULL) { bufPtr = buffer; /* Pointer to next field in buffer */ recordNum++; if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"version number" recNum:recordNum]; continue; } field[MAXPOPLEN] = '\0'; oldStyle = NO; /* Old style config file has no version # */ for (i = 0; i < strlen (field); i++) { if (isdigit (field[i])) continue; else { oldStyle = YES; break; } } if (oldStyle) { versionNum = 0; strcpy (buttonName, field); } else { versionNum = atoi (field); if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"button name" recNum:recordNum]; continue; } field[MAXPOPLEN] = '\0'; strcpy (buttonName, field); } if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"hostname" recNum:recordNum]; continue; } field[MAXHOSTNAMELEN] = '\0'; strcpy (hName, field); if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"user ID" recNum:recordNum]; continue; } field[MAXIDLEN] = '\0'; strcpy (userID, field); if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"application" recNum:recordNum]; continue; } appType = atoi (field); if (appType != TERMINAL && appType != STUART) { [self errPrint:"application" recNum:recordNum]; continue; } if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"protocol" recNum:recordNum]; continue; } protocolType = atoi (field); if (protocolType != RLOGIN && protocolType != TELNET && protocolType != TN3270) { [self errPrint:"protocol" recNum:recordNum]; continue; } if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"x" recNum:recordNum]; continue; } x = atoi (field); if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"y" recNum:recordNum]; continue; } y = atoi (field); /* In old version, Y was measured from top of display. */ if (versionNum == 0 && y < 300) { [NXApp getScreenSize:&screenSize]; y = screenSize.height - y; } if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"lines" recNum:recordNum]; continue; } lines = atoi (field); if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"columns" recNum:recordNum]; continue; } columns = atoi (field); if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"font type" recNum:recordNum]; continue; } fontType = atoi (field); if (fontType != COURIER && fontType != OHLFS) { [self errPrint:"font type" recNum:recordNum]; continue; } if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"font size" recNum:recordNum]; continue; } fontSize = atoi (field); if ((bufPtr = getfield (bufPtr, field)) == NULL) autoLaunch = NO; else autoLaunch = atoi (field); if (appType == TERMINAL) flagValues = TTRANSLAT | TAUTOWRAP | TSCROLLBK; else flagValues = SSCROLLBK | STRANSLAT | STERMSPAC; metaNum = METAESC; if (versionNum == CFGVERSION) { if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"flag values" recNum:recordNum]; continue; } flagValues = atoi (field); if ((bufPtr = getfield (bufPtr, field)) == NULL) { [self errPrint:"meta number" recNum:recordNum]; continue; } metaNum = atoi (field); } code = [self addHost:buttonName fullHostName:hName loginName:userID application:appType protocol:protocolType locX:x locY:y nLines:lines nCols:columns font:fontType fontSize:fontSize autoStart:autoLaunch flags:flagValues meta:metaNum updateConfigFile:NO]; if (debugLevel == DEBUGMAX) { printf ("%s:(read #%d okay) version:%d\t%s\t%s\n",[NXApp appName], recordNum, versionNum, buttonName, hName); printf ("\tID:%s", userID); printf ("\tapp:%d", appType); printf ("\tprot:%d", protocolType); printf ("\tx:%d", x); printf ("\ty:%d", y); printf ("\n"); printf ("\tlines:%d", lines); printf ("\tcols:%d", columns); printf ("\tfont:%d", fontType); printf ("\tfontsize:%d", fontSize); printf ("\n"); printf ("\tautostart:%d", autoLaunch); printf ("\tflags:%u", flagValues); printf ("\tmeta:%d", metaNum); printf ("\n"); } } fclose (fp); if (debugLevel >= DEBUGHIGH) printf ("%s: %d records successfully read from config file.\n", [NXApp appName], nHosts); return self; } /*--------------------------------------------------------------------------- Stuff an entry into the doubly linked circular list of hosts. The head and tail entries point to each other so a true circular loop is maintained & thus simplifies coding. Duplicates are not entered. This routine returns the slot number where the host was inserted. The list is maintained in alphabetical order. -----------------------------------------------------------------------------*/ - (int)insert:(struct hostEntry *) newEntry { int slotNum; /* Slot position of host in linked list */ struct hostEntry *hostPtr; /* Pointer to host entry */ /* First entry in the list. Point to myself. */ if (nHosts == 0) { newEntry -> nextHost = newEntry; newEntry -> prevHost = newEntry; begHost = newEntry; /* Set beginning host pointer too. */ nHosts++; return 0; } /* Find spot that this entry must be inserted at. */ hostPtr = begHost; for (slotNum = 0; slotNum < nHosts; slotNum++) { if (strcmp (newEntry -> popUpName, hostPtr -> popUpName) < 0) break; if (strcmp (newEntry -> popUpName, hostPtr -> popUpName) == 0) return -1; hostPtr = hostPtr -> nextHost; } /* Entry is at head of list. Adjust beginning host pointer too. */ if (slotNum == 0) begHost = newEntry; /* Set new entry's next & previous pointers */ newEntry -> nextHost = hostPtr; newEntry -> prevHost = hostPtr -> prevHost; /* Set previous host's "next pointer" */ hostPtr -> prevHost -> nextHost = newEntry; /* Set next host's "previous pointer" */ hostPtr -> prevHost = newEntry; nHosts++; return slotNum; } /*--------------------------------------------------------------------------- Print error message about bad input record in configuration file. -----------------------------------------------------------------------------*/ - errPrint:(char *)fieldName recNum:(int)recordNum { printf ("%s:Invalid %s field in record %d in config file.\n", [NXApp appName], fieldName, recordNum); return self; } /*--------------------------------------------------------------------------- Add a host into the internal linked list. -----------------------------------------------------------------------------*/ - (int)addHost:(const char *)buttonName fullHostName:(const char *)fullName loginName:(const char *)userID application:(short int)app protocol:(short int)prot locX:(short int)x locY:(short int)y nLines:(short int)lines nCols:(short int)columns font:(short int)aFont fontSize:(short int)fontNum autoStart:(short int)autoLaunch flags:(unsigned int)flagValues meta:(short int)metaNum updateConfigFile:(short int)updConfigFile { int slotNum; /* Slot position of host in linked list */ struct hostEntry *newEntry; /* Pointer to host entry */ FILE *fp; newEntry = malloc (HOSTENTRYLEN); strcpy (newEntry -> popUpName, buttonName); strcpy (newEntry -> hostName, fullName); strcpy (newEntry -> loginName, userID); newEntry -> appType = app; newEntry -> protocolType = prot; newEntry -> locX = x; newEntry -> locY = y; newEntry -> nLines = lines; newEntry -> nCols = columns; newEntry -> fontType = aFont; newEntry -> fontSize = fontNum; newEntry -> autoStart = autoLaunch; newEntry -> flags = flagValues; newEntry -> meta = metaNum; slotNum = [self insert:newEntry]; if (slotNum < 0 || updConfigFile == NO) return slotNum; fp = [self openConfigFile:"a"]; if (fp != NULL) { fprintf (fp, "%d", CFGVERSION); fprintf (fp, "\t%s", buttonName); fprintf (fp, "\t%s", fullName); fprintf (fp, "\t%s", userID); fprintf (fp, "\t%d", app); fprintf (fp, "\t%d", prot); fprintf (fp, "\t%d", x); fprintf (fp, "\t%d", y); fprintf (fp, "\t%d", lines); fprintf (fp, "\t%d", columns); fprintf (fp, "\t%d", aFont); fprintf (fp, "\t%d", fontNum); fprintf (fp, "\t%d", autoLaunch); fprintf (fp, "\t%u", flagValues); fprintf (fp, "\t%d", metaNum); fprintf (fp, "\n"); } fclose (fp); if (debugLevel >= DEBUGHIGH) printf ("%s: Record added to config file.\n",[NXApp appName]); if (debugLevel == DEBUGMAX) { printf ("%s:(append okay) version:%d\t%s\t%s\n", [NXApp appName], CFGVERSION, buttonName, fullName); printf ("\tID:%s", userID); printf ("\tapp:%d", app); printf ("\tprot:%d", prot); printf ("\tx:%d", x); printf ("\ty:%d", y); printf ("\n"); printf ("\tlines:%d", lines); printf ("\tcols:%d", columns); printf ("\tfont:%d", aFont); printf ("\tfontsize:%d", fontNum); printf ("\n"); printf ("\tautostart:%d", autoLaunch); printf ("\tflags:%u", flagValues); printf ("\tmeta:%d", metaNum); printf ("\n"); } return slotNum; } /*--------------------------------------------------------------------------- Add a default Terminal & Stuart entry. Use values in the defaults data base for the various fields. -----------------------------------------------------------------------------*/ - (int)addLocalHost:sender { short int columns; short int lines; unsigned int flagValues; short int fontNum; short int fontStyle; int slotNum; /* Slot position of host in linked list */ const char *string; /* Temporary variable */ string = NXGetDefaultValue ("Terminal", "Columns"); columns = atoi (string); string = NXGetDefaultValue ("Terminal", "Rows"); lines = atoi (string); string = NXGetDefaultValue ("Terminal", "NXFixedPitchFontSize"); fontNum = atoi (string); string = NXGetDefaultValue ("Terminal", "NXFixedPitchFont"); if (strcmp (string, "Courier") == 0) fontStyle = COURIER; else fontStyle = OHLFS; flagValues = TTRANSLAT | TAUTOWRAP | TSCROLLBK | TSOURCEDL; slotNum = [self addHost:"Terminal" fullHostName:"localhost" loginName:"" application:TERMINAL protocol:RLOGIN locX:120 locY:832 nLines:lines nCols:columns font:fontStyle fontSize:fontNum autoStart:NO flags:flagValues meta:METAESC updateConfigFile:YES]; string = NXGetDefaultValue ("Stuart", "Columns"); columns = atoi (string); string = NXGetDefaultValue ("Stuart", "Lines"); lines = atoi (string); string = NXGetDefaultValue ("Stuart", "NXFixedPitchFontSize"); fontNum = atoi (string); string = NXGetDefaultValue ("Stuart", "NXFixedPitchFont"); if (strcmp (string, "Courier") == 0) fontStyle = COURIER; else fontStyle = OHLFS; flagValues = SSCROLLBK | STRANSLAT | STERMSPAC | SSOURCEDL; slotNum = [self addHost:"Stuart" fullHostName:"localhost" loginName:"" application:STUART protocol:RLOGIN locX:130 locY:832 nLines:lines nCols:columns font:fontStyle fontSize:fontNum autoStart:NO flags:flagValues meta:METAESC updateConfigFile:YES]; return slotNum; } /*--------------------------------------------------------------------------- Change values in an existing host entry. -----------------------------------------------------------------------------*/ - (int)changeHost:(const char *)buttonName fullHostName:(const char *)fullName loginName:(const char *)userID application:(short int)app protocol:(short int)prot locX:(short int)x locY:(short int)y nLines:(short int)lines nCols:(short int)columns font:(short int)aFont fontSize:(short int)fontNum autoStart:(short int)autoLaunch flags:(unsigned int)flagValues meta:(short int)metaNum { int i; int slotNum; /* Slot position of host in linked list */ struct hostEntry *hostPtr; /* Pointer to host entry */ slotNum = [self getHostSlotNum:buttonName]; if (slotNum < 0) return slotNum; /* Find the host in our list */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; strcpy (hostPtr -> popUpName, buttonName); strcpy (hostPtr -> hostName, fullName); strcpy (hostPtr -> loginName, userID); hostPtr -> appType = app; hostPtr -> protocolType = prot; hostPtr -> locX = x; hostPtr -> locY = y; hostPtr -> nLines = lines; hostPtr -> nCols = columns; hostPtr -> fontType = aFont; hostPtr -> fontSize = fontNum; hostPtr -> autoStart = autoLaunch; hostPtr -> flags = flagValues; hostPtr -> meta = metaNum; [self writeConfigFile:self]; return slotNum; } /*--------------------------------------------------------------------------- Delete a host entry from the internal linked list & from the file. -----------------------------------------------------------------------------*/ - (int)deleteHost:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; if (slotNum == 0) begHost = hostPtr -> nextHost; /* Head entry deletion */ else for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; hostPtr -> nextHost -> prevHost = hostPtr -> prevHost; hostPtr -> prevHost -> nextHost = hostPtr -> nextHost; free (hostPtr); nHosts--; [self writeConfigFile:self]; return slotNum; } /*--------------------------------------------------------------------------- Return the application type (e.g., Terminal, Stuart) for this slot. -----------------------------------------------------------------------------*/ - (int)getAppType:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> appType; } /*--------------------------------------------------------------------------- Return the auto launch value for this slot. -----------------------------------------------------------------------------*/ - (int)getAutoStart:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> autoStart; } /*--------------------------------------------------------------------------- Return the button name for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (char *)getButtonName:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> popUpName; } /*--------------------------------------------------------------------------- Return the width for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (int)getColumns:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> nCols; } /*--------------------------------------------------------------------------- Return the configuration pathname for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (const char *)getConfigFile:sender { return NXGetDefaultValue ([NXApp appName], "ConfigFile"); } /*--------------------------------------------------------------------------- Return the debugging level. -----------------------------------------------------------------------------*/ - (int)getDebugLevel:sender { return debugLevel; } /*--------------------------------------------------------------------------- Return the Stuart/Terminal flag values. -----------------------------------------------------------------------------*/ - (unsigned int)getFlags:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> flags; } /*--------------------------------------------------------------------------- Return the font type for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (int)getFontType:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> fontType; } /*--------------------------------------------------------------------------- Return the font size for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (int)getFontSize:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> fontSize; } /*--------------------------------------------------------------------------- Return the complete host name for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (char *)getFullHostName:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> hostName; } /*--------------------------------------------------------------------------- Return the host slot number for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (int)getHostSlotNum:(const char *)buttonName { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < nHosts; i++) { if (strcmp (buttonName, hostPtr -> popUpName) == 0) return i; hostPtr = hostPtr -> nextHost; } return -1; } /*--------------------------------------------------------------------------- Return the number of lines in the window for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (int)getLines:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> nLines; } /*--------------------------------------------------------------------------- Return the meta value. -----------------------------------------------------------------------------*/ - (int)getMeta:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> meta; } /*--------------------------------------------------------------------------- Return the number of hosts in list. -----------------------------------------------------------------------------*/ - (int)getNumHosts:sender { return nHosts; } /*--------------------------------------------------------------------------- Return the popup button name for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (char *)getPopUpName:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> popUpName; } /*--------------------------------------------------------------------------- Return the protocol type (e.g., rlogin, telnet, tn3270). -----------------------------------------------------------------------------*/ - (int)getProtocolType:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> protocolType; } /*--------------------------------------------------------------------------- Return the user ID for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (char *)getUserID:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> loginName; } /*--------------------------------------------------------------------------- Return the X coordinate for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (int)getX:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> locX; } /*--------------------------------------------------------------------------- Return the Y coordinate for the entry at the specified slot. -----------------------------------------------------------------------------*/ - (int)getY:(int)slotNum { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; return hostPtr -> locY; } /*--------------------------------------------------------------------------- Load a popuplist. This could be either the hosts popup list or the configuration pulldown list. -----------------------------------------------------------------------------*/ - loadPopUpList:aPopUpList { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < nHosts; i++) { [aPopUpList addItem:hostPtr -> popUpName]; hostPtr = hostPtr -> nextHost; } return self; } /*--------------------------------------------------------------------------- Remotes is coming to life. Launch those automatic startup guys. -----------------------------------------------------------------------------*/ - autoStart:sender { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ hostPtr = begHost; for (i = 0; i < nHosts; i++) { if (hostPtr -> autoStart == YES) [self loginToHost:hostPtr -> popUpName activate:NO]; hostPtr = hostPtr -> nextHost; } return self; } /*--------------------------------------------------------------------------- Fire up a Terminal or Stuart session for the user. -----------------------------------------------------------------------------*/ - loginToHost:(const char *)buttonName activate:(BOOL)actWindow { char colsStr[16]; char *comArgs[MAXCOMARGS]; char command[1024]; char errMsg[256]; int i; int ind; char fontStr[16]; char linesStr[16]; char loginStr[256]; char metaStr[16]; int pid; char *shellPtr; id stuart; int slotNum; char **tempPtr; char xStr[16]; char yStr[16]; int vfork (void); struct hostEntry *hostPtr; /* Pointer to host entry */ slotNum = [self getHostSlotNum:buttonName]; if (slotNum < 0) { NXRunAlertPanel (NULL, "Button name '%s' not found.", NULL, NULL, NULL, buttonName); return self; } ind = 0; hostPtr = begHost; for (i = 0; i < slotNum; i++) hostPtr = hostPtr -> nextHost; if (hostPtr -> appType == TERMINAL) { strcpy (command, "/NextApps/Terminal.app/Terminal"); comArgs[ind++] = "Terminal"; comArgs[ind++] = "-Shell"; if (strcmp (hostPtr -> hostName, "localhost") == 0) { shellPtr = getenv ("SHELL"); if (shellPtr == NULL) comArgs[ind++] = "/bin/csh"; else comArgs[ind++] = shellPtr; } else { switch (hostPtr -> protocolType) { case RLOGIN: strcpy (loginStr, "\"/usr/ucb/rlogin "); strcat (loginStr, hostPtr -> hostName); if (*hostPtr -> loginName != '\0') { strcat (loginStr, " -l "); strcat (loginStr, hostPtr -> loginName); } break; case TELNET: strcpy (loginStr, "\"/usr/ucb/telnet "); strcat (loginStr, hostPtr -> hostName); break; case TN3270: strcpy (loginStr, "\"/usr/ucb/tn3270 "); strcat (loginStr, hostPtr -> hostName); break; default: break; } strcat (loginStr, "\""); comArgs[ind++] = loginStr; } comArgs[ind++] = "-WinLocX"; sprintf (xStr, "%d", hostPtr -> locX); comArgs[ind++] = xStr; comArgs[ind++] = "-WinLocY"; sprintf (yStr, "%d", hostPtr -> locY); comArgs[ind++] = yStr; comArgs[ind++] = "-Rows"; sprintf (linesStr, "%d", hostPtr -> nLines); comArgs[ind++] = linesStr; comArgs[ind++] = "-Columns"; sprintf (colsStr, "%d", hostPtr -> nCols); comArgs[ind++] = colsStr; comArgs[ind++] = "-NXFixedPitchFont"; if (hostPtr -> fontType == COURIER) comArgs[ind++] = "Courier"; else comArgs[ind++] = "Ohlfs"; comArgs[ind++] = "-NXFixedPitchFontSize"; sprintf (fontStr, "%d", hostPtr -> fontSize); comArgs[ind++] = fontStr; if (hostPtr -> meta != TMETADEF) { comArgs[ind++] = "-Meta"; sprintf (metaStr, "%d", hostPtr -> meta); comArgs[ind++] = metaStr; } comArgs[ind++] = "-Translate"; comArgs[ind++] = (hostPtr -> flags & TTRANSLAT) ? "YES" : "NO"; comArgs[ind++] = "-Keypad"; comArgs[ind++] = (hostPtr -> flags & TKEYPAD) ? "YES" : "NO"; comArgs[ind++] = "-StrictEmulation"; comArgs[ind++] = (hostPtr -> flags & TSTRICTEM) ? "YES" : "NO"; comArgs[ind++] = "-Autowrap"; comArgs[ind++] = (hostPtr -> flags & TAUTOWRAP) ? "YES" : "NO"; comArgs[ind++] = "-Scrollback"; comArgs[ind++] = (hostPtr -> flags & TSCROLLBK) ? "YES" : "NO"; comArgs[ind++] = "-AutoFocus"; comArgs[ind++] = (hostPtr -> flags & TAUTOFOCS) ? "YES" : "NO"; comArgs[ind++] = "-SourceDotLogin"; comArgs[ind++] = (hostPtr -> flags & TSOURCEDL) ? "YES" : "NO"; comArgs[ind++] = "-CustomTitle"; comArgs[ind++] = hostPtr -> hostName; comArgs[ind++] = NULL; /*** Gotta build a shell-like command under NeXT Release 3.1. */ tempPtr = comArgs; while (*++tempPtr != NULL) { strcat (command, " "); strcat (command, *tempPtr); } if (debugLevel != DEBUGOFF) printf ("%s: %s\n",[NXApp appName], command); pid = vfork (); if (pid == 0) { system (command); exit (0); #if 0 /*** execve worked under NeXT Release 2.x. Doesn't work now. */ code = execve (command, comArgs, environ); perror ([NXApp appName]); fprintf (stderr, "%s: Execve error code=%d.\n",[NXApp appName], code); _exit (0); #endif } } else { stuart = [StuartSpeaker new]; if (debugLevel != DEBUGOFF) printf ("Stuart"); if (strcmp (hostPtr -> hostName, "localhost") != 0) { switch (hostPtr -> protocolType) { case RLOGIN: strcpy (loginStr, "rlogin "); strcat (loginStr, hostPtr -> hostName); if (*hostPtr -> loginName != '\0') { strcat (loginStr, " -l "); strcat (loginStr, hostPtr -> loginName); } break; case TELNET: strcpy (loginStr, "telnet "); strcat (loginStr, hostPtr -> hostName); break; case TN3270: strcpy (loginStr, "tn3270 "); strcat (loginStr, hostPtr -> hostName); break; default: break; } [self setStuartDefault:stuart default:"Shell" as:loginStr]; } sprintf (xStr, "%d", hostPtr -> locX); [self setStuartDefault:stuart default:"WinLocX" as:xStr]; sprintf (yStr, "%d", hostPtr -> locY); [self setStuartDefault:stuart default:"WinLocY" as:yStr]; sprintf (linesStr, "%d", hostPtr -> nLines); [self setStuartDefault:stuart default:"Lines" as:linesStr]; sprintf (colsStr, "%d", hostPtr -> nCols); [self setStuartDefault:stuart default:"Columns" as:colsStr]; if (hostPtr -> fontType == COURIER) [self setStuartDefault:stuart default:"NXFixedPitchFont" as:"Courier"]; else [self setStuartDefault:stuart default:"NXFixedPitchFont" as:"Ohlfs"]; sprintf (fontStr, "%d", hostPtr -> fontSize); [self setStuartDefault:stuart default:"NXFixedPitchFontSize" as:fontStr]; if (hostPtr -> meta != SMETADEF) { sprintf (metaStr, "%d", hostPtr -> meta); [self setStuartDefault:stuart default:"Meta" as:metaStr]; } [self setStuartDefault:stuart default:"Strict" as:(hostPtr -> flags & SSTRICTEM) ? "YES" : "NO"]; [self setStuartDefault:stuart default:"Keypad" as:(hostPtr -> flags & SKEYPAD) ? "YES" : "NO"]; [self setStuartDefault:stuart default:"Scrollback" as:(hostPtr -> flags & SSCROLLBK) ? "YES" : "NO"]; [self setStuartDefault:stuart default:"Translate" as:(hostPtr -> flags & STRANSLAT) ? "YES" : "NO"]; [self setStuartDefault:stuart default:"Reverse" as:(hostPtr -> flags & SREVERSE) ? "YES" : "NO"]; [self setStuartDefault:stuart default:"KeyboardFocus" as:(hostPtr -> flags & SKEYBDFOC) ? "YES" : "NO"]; [self setStuartDefault:stuart default:"TerminalSpacing" as:(hostPtr -> flags & STERMSPAC) ? "YES" : "NO"]; [self setStuartDefault:stuart default:"MouseFocus" as:(hostPtr -> flags & SMOUSEFOC) ? "YES" : "NO"]; [self setStuartDefault:stuart default:"SourceDotLogin" as:(hostPtr -> flags & SSOURCEDL) ? "YES" : "NO"]; [self setStuartDefault:stuart default:"TestExit" as:(hostPtr -> flags & STESTEXIT) ? "YES" : "NO"]; [self setStuartDefault:stuart default:"WriteStuartrc" as:"NO"]; [self setStuartDefault:stuart default:"Title" as:hostPtr -> hostName]; [self setStuartDefault:stuart default:"MiniTitle" as:buttonName]; [self setStuartDefault:stuart default:"Activate" as:actWindow ? "YES" : "NO"]; if (debugLevel != DEBUGOFF) printf("\n"); if ([stuart stuartConnectAndNew]) { strcpy (errMsg, "There was a problem communicating with the Stuart "); strcat (errMsg, "application. (Speaker port unavailable.) This may "); strcat (errMsg, "have occurred because Stuart is not installed on "); strcat (errMsg, "your system or because Stuart was slow in starting."); NXRunAlertPanel (NULL, errMsg, NULL, NULL, NULL, NULL); } [stuart free]; } return self; } /*--------------------------------------------------------------------------- Set specified Stuart default value. -----------------------------------------------------------------------------*/ - setStuartDefault:aStuart default:(const char *)defaultV as:(const char *)asV { if (debugLevel != DEBUGOFF) printf(" -%s %s", defaultV, asV); [aStuart default:defaultV as:asV]; return self; } /*--------------------------------------------------------------------------- Set debugging variable within object & in defaults data base. -----------------------------------------------------------------------------*/ - setDebugLevel:(short int)debugNum { int code; char defaultsDebugLevel[5]; debugLevel = debugNum; /* Update object's setting */ if (debugNum == 1) strcpy (defaultsDebugLevel, "low"); else if (debugNum == 2) strcpy (defaultsDebugLevel, "high"); else strcpy (defaultsDebugLevel, "off"); code = NXWriteDefault ([NXApp appName], "DebugLevel", defaultsDebugLevel); return self; } /*--------------------------------------------------------------------------- Open the configuration file. -----------------------------------------------------------------------------*/ - (FILE *) openConfigFile:(const char *)mode { const char *configFile; /* Configuration pathname */ FILE *fp; configFile = NXGetDefaultValue ([NXApp appName], "ConfigFile"); if ((fp = fopen (configFile, mode)) == NULL) { if (debugLevel >= DEBUGHIGH) printf ("%s:Unable to open config file '%s' with mode '%s'.\n", [NXApp appName], configFile, mode); return NULL; } if (debugLevel >= DEBUGHIGH) printf ("%s:'%s' opened with mode '%s'.\n", [NXApp appName], configFile, mode); return fp; } /*--------------------------------------------------------------------------- Set configuration path variable within object & in defaults data base. -----------------------------------------------------------------------------*/ - setConfigFile:(const char *)configFile { const char *configFileOld; FILE *fp; if (strcmp (configFile,[self getConfigFile:self]) == 0) return self; if (index (configFile, ' ') != 0) { NXRunAlertPanel (NULL, "Blanks not allowed in pathname.", NULL, NULL, NULL); return self; } fp = fopen (configFile, "r"); if (fp != NULL) { fclose (fp); if (NXRunAlertPanel (NULL, "The config file '%s' exists; OK to overwrite?", "Cancel", "OK", NULL, configFile) == NX_ALERTDEFAULT) return self; } fp = fopen (configFile, "w"); if (fp == NULL) { NXRunAlertPanel (NULL, "Unable to open the config file '%s'.", NULL, NULL, NULL, configFile); return self; } configFileOld = NXGetDefaultValue ([NXApp appName], "ConfigFile"); if (NXWriteDefault ([NXApp appName], "ConfigFile", configFile) == 0) { NXRunAlertPanel (NULL, "Unable to write to defaults data base.", NULL, NULL, NULL); return self; } [self writeConfigFile:self]; unlink (configFileOld); return self; } /*--------------------------------------------------------------------------- Write the configuration file from our internal list. -----------------------------------------------------------------------------*/ - writeConfigFile:sender { int i; struct hostEntry *hostPtr; /* Pointer to host entry */ FILE *fp; fp = [self openConfigFile:"w"]; hostPtr = begHost; for (i = 0; i < nHosts; i++) { fprintf (fp, "%d", CFGVERSION); fprintf( fp, "\t%s", hostPtr -> popUpName); fprintf( fp, "\t%s", hostPtr -> hostName); fprintf (fp, "\t%s", hostPtr -> loginName); fprintf (fp, "\t%d", hostPtr -> appType); fprintf (fp, "\t%d", hostPtr -> protocolType); fprintf (fp, "\t%d", hostPtr -> locX); fprintf (fp, "\t%d", hostPtr -> locY); fprintf (fp, "\t%d", hostPtr -> nLines); fprintf (fp, "\t%d", hostPtr -> nCols); fprintf (fp, "\t%d", hostPtr -> fontType); fprintf (fp, "\t%d", hostPtr -> fontSize); fprintf (fp, "\t%d", hostPtr -> autoStart); fprintf (fp, "\t%u", hostPtr -> flags); fprintf (fp, "\t%d", hostPtr -> meta); fprintf (fp, "\n"); if (debugLevel == DEBUGMAX) { printf ("%s:(write #%d okay) version:%d\t%s\t%s\n", [NXApp appName], i + 1, CFGVERSION, hostPtr -> popUpName, hostPtr -> hostName); printf ("\tID:%s", hostPtr -> loginName); printf ("\tapp:%d", hostPtr -> appType); printf ("\tprot:%d", hostPtr -> protocolType); printf ("\tx:%d", hostPtr -> locX); printf ("\ty:%d", hostPtr -> locY); printf ("\n"); printf ("\tlines:%d", hostPtr -> nLines); printf ("\tcols:%d", hostPtr -> nCols); printf ("\tfont:%d", hostPtr -> fontType); printf ("\tfontsize:%d", hostPtr -> fontSize); printf ("\n"); printf ("\tautostart:%d", hostPtr -> autoStart); printf ("\tflags:%u", hostPtr -> flags); printf ("\tmeta:%d", hostPtr -> meta); printf ("\n"); } hostPtr = hostPtr -> nextHost; } fclose (fp); if (debugLevel >= DEBUGHIGH) printf ("%s: Config file written. %d records in the file.\n", [NXApp appName], nHosts); return self; } @end
These are the contents of the former NiCE NeXT User Group NeXTSTEP/OpenStep software archive, currently hosted by Netfuture.ch.