📄 nc.c
字号:
nextArg(argc, argv, &i); geometry = argv[i]; copyCommandLineArg(commandLine, argv[i]); } else if (opts && !strcmp(argv[i], "-read")) { read = 1; } else if (opts && !strcmp(argv[i], "-create")) { create = 1; } else if (opts && (!strcmp(argv[i], "-iconic") || !strcmp(argv[i], "-icon"))) { iconic = 1; copyCommandLineArg(commandLine, argv[i]); } else if (opts && !strcmp(argv[i], "-line")) { nextArg(argc, argv, &i); nRead = sscanf(argv[i], "%d", &lineArg); if (nRead != 1) fprintf(stderr, "nc: argument to line should be a number\n"); else lineNum = lineArg; } else if (opts && (*argv[i] == '+')) { nRead = sscanf((argv[i]+1), "%d", &lineArg); if (nRead != 1) fprintf(stderr, "nc: argument to + should be a number\n"); else lineNum = lineArg; } else if (opts && (!strcmp(argv[i], "-ask") || !strcmp(argv[i], "-noask"))) { ; /* Ignore resource-based arguments which are processed later */ } else if (opts && (!strcmp(argv[i], "-svrname") || !strcmp(argv[i], "-svrcmd"))) { nextArg(argc, argv, &i); /* Ignore rsrc args with data */ } else if (opts && (!strcmp(argv[i], "-xrm") || !strcmp(argv[i], "-display"))) { copyCommandLineArg(commandLine, argv[i]); nextArg(argc, argv, &i); /* Ignore rsrc args with data */ copyCommandLineArg(commandLine, argv[i]); } else if (opts && (!strcmp(argv[i], "-version") || !strcmp(argv[i], "-V"))) { printNcVersion(); exit(EXIT_SUCCESS); } else if (opts && (*argv[i] == '-')) {#ifdef VMS *argv[i] = '/';#endif /*VMS*/ fprintf(stderr, "nc: Unrecognized option %s\n%s", argv[i], cmdLineHelp); exit(EXIT_FAILURE); } else {#ifdef VMS int numFiles, j, oldLength; char **nameList = NULL, *newCommandString; /* Use VMS's LIB$FILESCAN for filename in argv[i] to process */ /* wildcards and to obtain a full VMS file specification */ numFiles = VMSFileScan(argv[i], &nameList, NULL, INCLUDE_FNF); /* for each expanded file name do: */ for (j = 0; j < numFiles; ++j) { oldLength = outPtr-commandString; newCommandString = XtMalloc(oldLength+length+1); strncpy(newCommandString, commandString, oldLength); XtFree(commandString); commandString = newCommandString; outPtr = newCommandString + oldLength; if (ParseFilename(nameList[j], name, path) != 0) { /* An Error, most likely too long paths/strings given */ commandLine->serverRequest = NULL; return; } strcat(path, name); /* See below for casts */ sprintf(outPtr, "%d %d %d %d %ld %ld %ld %ld\n%s\n%s\n%s\n%s\n%n", lineNum, read, create, iconic, (long) strlen(path), (long) strlen(toDoCommand), (long) strlen(langMode), (long) strlen(geometry), path, toDoCommand, langMode, geometry, &charsWritten); outPtr += charsWritten; free(nameList[j]); /* Create the file open atoms for the paths supplied */ addToFileList(path); fileCount++; } if (nameList != NULL) free(nameList);#else if (ParseFilename(argv[i], name, path) != 0) { /* An Error, most likely too long paths/strings given */ commandLine->serverRequest = NULL; return; } strcat(path, name); /* SunOS 4 acc or acc and/or its runtime library has a bug such that %n fails (segv) if it follows a string in a printf or sprintf. The silly code below avoids this. The "long" cast on strlen() is necessary because size_t is 64 bit on Alphas, and 32-bit on most others. There is no printf format specifier for "size_t", thanx, ANSI. */ sprintf(outPtr, "%d %d %d %d %ld %ld %ld %ld\n%n", lineNum, read, create, iconic, (long) strlen(path), (long) strlen(toDoCommand), (long) strlen(langMode), (long) strlen(geometry), &charsWritten); outPtr += charsWritten; strcpy(outPtr, path); outPtr += strlen(path); *outPtr++ = '\n'; strcpy(outPtr, toDoCommand); outPtr += strlen(toDoCommand); *outPtr++ = '\n'; strcpy(outPtr, langMode); outPtr += strlen(langMode); *outPtr++ = '\n'; strcpy(outPtr, geometry); outPtr += strlen(geometry); *outPtr++ = '\n'; toDoCommand = ""; /* Create the file open atoms for the paths supplied */ addToFileList(path); fileCount++;#endif /* VMS */ } }#ifdef VMS VMSFileScanDone();#endif /*VMS*/ /* If there's an un-written -do command, * or user has requested iconic state, but not provided a file name, * create a server request with an empty file name and requested * iconic state (and optional language mode and geometry). */ if (toDoCommand[0] != '\0' || fileCount == 0) { sprintf(outPtr, "0 0 0 %d 0 %ld %ld %ld\n\n%n", iconic, (long) strlen(toDoCommand), (long) strlen(langMode), (long) strlen(geometry), &charsWritten); outPtr += charsWritten; strcpy(outPtr, toDoCommand); outPtr += strlen(toDoCommand); *outPtr++ = '\n'; strcpy(outPtr, langMode); outPtr += strlen(langMode); *outPtr++ = '\n'; strcpy(outPtr, geometry); outPtr += strlen(geometry); *outPtr++ = '\n'; } *outPtr = '\0'; commandLine->serverRequest = commandString;}static void waitUntilRequestProcessed(XtAppContext context, Window rootWindow, char* commandString, Atom serverRequestAtom){ XtIntervalId timerId; Boolean timeOut = False; /* Set the NEDIT_SERVER_REQUEST_<user>_<host> property on the root window to activate the server */ XChangeProperty(TheDisplay, rootWindow, serverRequestAtom, XA_STRING, 8, PropModeReplace, (unsigned char *)commandString, strlen(commandString)); /* Set up a timeout proc in case the server is dead. The standard selection timeout is probably a good guess at how long to wait for this style of inter-client communication as well */ timerId = XtAppAddTimeOut(context, REQUEST_TIMEOUT, (XtTimerCallbackProc)timeOutProc, &timeOut); currentWaitForAtom = serverRequestAtom; /* Wait for the property to be deleted to know the request was processed */ while (!timeOut) { XEvent event; const XPropertyEvent *e = (const XPropertyEvent *)&event; XtAppNextEvent(context, &event); if (e->window == rootWindow && e->atom == serverRequestAtom && e->state == PropertyDelete) break; XtDispatchEvent(&event); } /* Exit if the timeout expired. */ if (timeOut) { fprintf(stderr, "%s: The server did not respond to the request.\n", APP_NAME); XtCloseDisplay(TheDisplay); exit(EXIT_FAILURE); } else { XtRemoveTimeOut(timerId); }} static void waitUntilFilesOpenedOrClosed(XtAppContext context, Window rootWindow){ XtIntervalId timerId; Boolean timeOut = False; /* Set up a timeout proc so we don't wait forever if the server is dead. The standard selection timeout is probably a good guess at how long to wait for this style of inter-client communication as well */ timerId = XtAppAddTimeOut(context, FILE_OPEN_TIMEOUT, (XtTimerCallbackProc)timeOutProc, &timeOut); currentWaitForAtom = noAtom; /* Wait for all of the windows to be opened by server, * and closed if -wait was supplied */ while (fileListHead.fileList) { XEvent event; const XPropertyEvent *e = (const XPropertyEvent *)&event; XtAppNextEvent(context, &event); /* Update the fileList and check if all files have been closed. */ if (e->type == PropertyNotify && e->window == rootWindow) { FileListEntry *item; if (e->state == PropertyDelete) { for (item = fileListHead.fileList; item; item = item->next) { if (e->atom == item->waitForFileOpenAtom) { /* The 'waitForFileOpen' property is deleted when the file is opened */ fileListHead.waitForOpenCount--; item->waitForFileOpenAtom = None; /* Reset the timer while we wait for all files to be opened. */ XtRemoveTimeOut(timerId); timerId = XtAppAddTimeOut(context, FILE_OPEN_TIMEOUT, (XtTimerCallbackProc)timeOutProc, &timeOut); } else if (e->atom == item->waitForFileClosedAtom) { /* When file is opened in -wait mode the property * is deleted when the file is closed. */ fileListHead.waitForCloseCount--; item->waitForFileClosedAtom = None; } } if (fileListHead.waitForOpenCount == 0 && !timeOut) { XtRemoveTimeOut(timerId); } if (fileListHead.waitForOpenCount == 0 && fileListHead.waitForCloseCount == 0) { break; } } } /* We are finished if we are only waiting for files to open and ** the file open timeout has expired. */ if (!Preferences.waitForClose && timeOut) { break; } XtDispatchEvent(&event); }} static void nextArg(int argc, char **argv, int *argIndex){ if (*argIndex + 1 >= argc) {#ifdef VMS *argv[*argIndex] = '/';#endif /*VMS*/ fprintf(stderr, "nc: %s requires an argument\n%s", argv[*argIndex], cmdLineHelp); exit(EXIT_FAILURE); } (*argIndex)++;}/* Copies a given nc command line argument to the server startup command** line (-icon, -geometry, -xrm, ...) Special characters are protected from** the shell by escaping EVERYTHING with \ ** Note that the .shell string in the command line structure is large enough** to hold the escaped characters.*/static void copyCommandLineArg(CommandLine *commandLine, const char *arg){ const char *c; char *outPtr = commandLine->shell + strlen(commandLine->shell);#if defined(VMS) || defined(__EMX__) /* Non-Unix shells don't want/need esc */ for (c=arg; *c!='\0'; c++) { *outPtr++ = *c; } *outPtr++ = ' '; *outPtr = '\0';#else *outPtr++ = '\''; for (c=arg; *c!='\0'; c++) { if (*c == '\'') { *outPtr++ = '\''; *outPtr++ = '\\'; } *outPtr++ = *c; if (*c == '\'') { *outPtr++ = '\''; } } *outPtr++ = '\''; *outPtr++ = ' '; *outPtr = '\0';#endif /* VMS */}/* Print version of 'nc' */static void printNcVersion(void ) { static const char *const ncHelpText = \ "nc (NEdit) Version 5.4 (November 2003)\n\n\ Built on: %s, %s, %s\n\ Built at: %s, %s\n"; fprintf(stdout, ncHelpText, COMPILE_OS, COMPILE_MACHINE, COMPILE_COMPILER, __DATE__, __TIME__);}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -