VOID PrintCommandList(VOID) { LPCOMMAND cmdptr; INT y; y = 0; cmdptr = cmds; while (cmdptr->name) { if (!(cmdptr->flags & CMD_HIDE)) { if (++y == 8) { ConOutPuts(cmdptr->name); y = 0; } else { ConOutPrintf (_T("%-10s"), cmdptr->name); } } cmdptr++; } if (y != 0) ConOutChar(_T('\n')); }
INT CommandEcho (LPTSTR param) { LPTSTR p1; TRACE ("CommandEcho: '%s'\n", debugstr_aw(param)); /* skip all spaces for the check of '/?', 'ON' and 'OFF' */ p1 = param; while(_istspace(*p1)) p1++; if (!_tcsncmp (p1, _T("/?"), 2)) { ConOutResPaging(TRUE,STRING_ECHO_HELP4); return 0; } if (!OnOffCommand(p1, &bEcho, STRING_ECHO_HELP5)) { /* skip the first character */ ConOutPuts(param + 1); ConOutChar(_T('\n')); } return 0; }
static VOID ClearCommandLine(LPTSTR str, INT maxlen, SHORT orgx, SHORT orgy) { INT count; SetCursorXY (orgx, orgy); for (count = 0; count < (INT)_tcslen (str); count++) ConOutChar (_T(' ')); _tcsnset (str, _T('\0'), maxlen); SetCursorXY (orgx, orgy); }
/* * returns 1 if at least one match, else returns 0 */ BOOL ShowCompletionMatches (LPTSTR str, INT charcount) { WIN32_FIND_DATA file; HANDLE hFile; BOOL found_dot = FALSE; INT curplace = 0; INT count; TCHAR path[MAX_PATH]; TCHAR fname[MAX_PATH]; TCHAR directory[MAX_PATH]; SHORT screenwidth; /* expand current file name */ count = charcount - 1; if (count < 0) count = 0; /* find front of word */ if (str[count] == _T('"')) { count--; while (count > 0 && str[count] != _T('"')) count--; } else { while (count > 0 && str[count] != _T(' ')) count--; } /* if not at beginning, go forward 1 */ if (str[count] == _T(' ')) count++; if (str[count] == _T('"')) count++; /* extract directory from word */ _tcscpy (directory, &str[count]); curplace = _tcslen (directory) - 1; if (curplace >= 0 && directory[curplace] == _T('"')) directory[curplace--] = _T('\0'); _tcscpy (path, directory); while (curplace >= 0 && directory[curplace] != _T('\\') && directory[curplace] != _T(':')) { directory[curplace] = 0; curplace--; } /* look for a . in the filename */ for (count = _tcslen (directory); path[count] != _T('\0'); count++) { if (path[count] == _T('.')) { found_dot = TRUE; break; } } if (found_dot) _tcscat (path, _T("*")); else _tcscat (path, _T("*.*")); /* current fname */ curplace = 0; hFile = FindFirstFile (path, &file); if (hFile != INVALID_HANDLE_VALUE) { UINT longestfname = 0; /* Get the size of longest filename first. */ do { if (_tcslen(file.cFileName) > longestfname) { longestfname = _tcslen(file.cFileName); /* Directories get extra brackets around them. */ if (file.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) longestfname += 2; } } while (FindNextFile (hFile, &file)); FindClose (hFile); hFile = FindFirstFile (path, &file); /* Count the highest number of columns */ GetScreenSize(&screenwidth, NULL); /* For counting columns of output */ count = 0; /* Increase by the number of spaces behind file name */ longestfname += 3; /* find anything */ ConOutChar(_T('\n')); do { /* ignore . and .. */ if (!_tcscmp (file.cFileName, _T(".")) || !_tcscmp (file.cFileName, _T(".."))) continue; if (file.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) _stprintf (fname, _T("[%s]"), file.cFileName); else _tcscpy (fname, file.cFileName); ConOutPrintf (_T("%*s"), - longestfname, fname); count++; /* output as much columns as fits on the screen */ if (count >= (screenwidth / longestfname)) { /* print the new line only if we aren't on the * last column, in this case it wraps anyway */ if (count * longestfname != (UINT)screenwidth) ConOutChar(_T('\n')); count = 0; } } while (FindNextFile (hFile, &file)); FindClose (hFile); if (count) ConOutChar(_T('\n')); } else { /* no match found */ MessageBeep (-1); return FALSE; } return TRUE; }
/* * print the command-line prompt */ VOID PrintPrompt(VOID) { static TCHAR default_pr[] = _T("$P$G"); TCHAR szPrompt[256]; LPTSTR pr; if (GetEnvironmentVariable (_T("PROMPT"), szPrompt, 256)) pr = szPrompt; else pr = default_pr; while (*pr) { if (*pr != _T('$')) { ConOutChar (*pr); } else { pr++; switch (_totupper (*pr)) { case _T('A'): ConOutChar (_T('&')); break; case _T('B'): ConOutChar (_T('|')); break; case _T('C'): ConOutChar (_T('(')); break; case _T('D'): ConOutPrintf(_T("%s"), GetDateString()); break; case _T('E'): ConOutChar (_T('\x1B')); break; case _T('F'): ConOutChar (_T(')')); break; case _T('G'): ConOutChar (_T('>')); break; case _T('H'): ConOutChar (_T('\x08')); ConOutChar (_T(' ')); ConOutChar (_T('\x08')); break; case _T('L'): ConOutChar (_T('<')); break; case _T('N'): { TCHAR szPath[MAX_PATH]; GetCurrentDirectory (MAX_PATH, szPath); ConOutChar (szPath[0]); } break; case _T('P'): { TCHAR szPath[MAX_PATH]; GetCurrentDirectory (MAX_PATH, szPath); ConOutPrintf (_T("%s"), szPath); } break; case _T('Q'): ConOutChar (_T('=')); break; case _T('S'): ConOutChar (_T(' ')); break; case _T('T'): ConOutPrintf(_T("%s"), GetTimeString()); break; case _T('V'): switch (osvi.dwPlatformId) { case VER_PLATFORM_WIN32_WINDOWS: if (osvi.dwMajorVersion == 4 && osvi.dwMinorVersion == 1) ConOutPrintf (_T("Windows 98")); else ConOutPrintf (_T("Windows 95")); break; case VER_PLATFORM_WIN32_NT: ConOutPrintf (_T("Windows NT Version %lu.%lu"), osvi.dwMajorVersion, osvi.dwMinorVersion); break; } break; case _T('_'): ConOutChar (_T('\n')); break; case '$': ConOutChar (_T('$')); break; #ifdef FEATURE_DIRECTORY_STACK case '+': { INT i; for (i = 0; i < GetDirectoryStackDepth (); i++) ConOutChar (_T('+')); } break; #endif } } pr++; } }
/* read in a command line */ BOOL ReadCommand(LPTSTR str, INT maxlen) { CONSOLE_SCREEN_BUFFER_INFO csbi; SHORT orgx; /* origin x/y */ SHORT orgy; SHORT curx; /*current x/y cursor position*/ SHORT cury; SHORT tempscreen; INT count; /*used in some for loops*/ INT current = 0; /*the position of the cursor in the string (str)*/ INT charcount = 0;/*chars in the string (str)*/ INPUT_RECORD ir; #ifdef FEATURE_UNIX_FILENAME_COMPLETION WORD wLastKey = 0; #endif TCHAR ch; BOOL bReturn = FALSE; BOOL bCharInput; #ifdef FEATURE_4NT_FILENAME_COMPLETION TCHAR szPath[MAX_PATH]; #endif #ifdef FEATURE_HISTORY //BOOL bContinue=FALSE;/*is TRUE the second case will not be executed*/ TCHAR PreviousChar; #endif if (!GetConsoleScreenBufferInfo(GetStdHandle(STD_OUTPUT_HANDLE), &csbi)) { /* No console */ HANDLE hStdin = GetStdHandle(STD_INPUT_HANDLE); DWORD dwRead; CHAR chr; do { if (!ReadFile(hStdin, &chr, 1, &dwRead, NULL) || !dwRead) return FALSE; #ifdef _UNICODE MultiByteToWideChar(InputCodePage, 0, &chr, 1, &str[charcount++], 1); #endif } while (chr != '\n' && charcount < maxlen); str[charcount] = _T('\0'); return TRUE; } /* get screen size */ maxx = csbi.dwSize.X; maxy = csbi.dwSize.Y; curx = orgx = csbi.dwCursorPosition.X; cury = orgy = csbi.dwCursorPosition.Y; memset (str, 0, maxlen * sizeof (TCHAR)); SetCursorType (bInsert, TRUE); do { bReturn = FALSE; ConInKey (&ir); if (ir.Event.KeyEvent.dwControlKeyState & (RIGHT_ALT_PRESSED |LEFT_ALT_PRESSED| RIGHT_CTRL_PRESSED|LEFT_CTRL_PRESSED) ) { switch (ir.Event.KeyEvent.wVirtualKeyCode) { #ifdef FEATURE_HISTORY case 'K': /*add the current command line to the history*/ if (ir.Event.KeyEvent.dwControlKeyState & (LEFT_CTRL_PRESSED|RIGHT_CTRL_PRESSED)) { if (str[0]) History(0,str); ClearCommandLine (str, maxlen, orgx, orgy); current = charcount = 0; curx = orgx; cury = orgy; //bContinue=TRUE; break; } case 'D': /*delete current history entry*/ if (ir.Event.KeyEvent.dwControlKeyState & (LEFT_CTRL_PRESSED|RIGHT_CTRL_PRESSED)) { ClearCommandLine (str, maxlen, orgx, orgy); History_del_current_entry(str); current = charcount = _tcslen (str); ConOutPrintf (_T("%s"), str); GetCursorXY (&curx, &cury); //bContinue=TRUE; break; } #endif /*FEATURE_HISTORY*/ } } bCharInput = FALSE; switch (ir.Event.KeyEvent.wVirtualKeyCode) { case VK_BACK: /* <BACKSPACE> - delete character to left of cursor */ if (current > 0 && charcount > 0) { if (current == charcount) { /* if at end of line */ str[current - 1] = _T('\0'); if (GetCursorX () != 0) { ConOutPrintf (_T("\b \b")); curx--; } else { SetCursorXY ((SHORT)(maxx - 1), (SHORT)(GetCursorY () - 1)); ConOutChar (_T(' ')); SetCursorXY ((SHORT)(maxx - 1), (SHORT)(GetCursorY () - 1)); cury--; curx = maxx - 1; } } else { for (count = current - 1; count < charcount; count++) str[count] = str[count + 1]; if (GetCursorX () != 0) { SetCursorXY ((SHORT)(GetCursorX () - 1), GetCursorY ()); curx--; } else { SetCursorXY ((SHORT)(maxx - 1), (SHORT)(GetCursorY () - 1)); cury--; curx = maxx - 1; } GetCursorXY (&curx, &cury); ConOutPrintf (_T("%s "), &str[current - 1]); SetCursorXY (curx, cury); } charcount--; current--; } break; case VK_INSERT: /* toggle insert/overstrike mode */ bInsert ^= TRUE; SetCursorType (bInsert, TRUE); break; case VK_DELETE: /* delete character under cursor */ if (current != charcount && charcount > 0) { for (count = current; count < charcount; count++) str[count] = str[count + 1]; charcount--; GetCursorXY (&curx, &cury); ConOutPrintf (_T("%s "), &str[current]); SetCursorXY (curx, cury); } break; case VK_HOME: /* goto beginning of string */ if (current != 0) { SetCursorXY (orgx, orgy); curx = orgx; cury = orgy; current = 0; } break; case VK_END: /* goto end of string */ if (current != charcount) { SetCursorXY (orgx, orgy); ConOutPrintf (_T("%s"), str); GetCursorXY (&curx, &cury); current = charcount; } break; case VK_TAB: #ifdef FEATURE_UNIX_FILENAME_COMPLETION /* expand current file name */ if ((current == charcount) || (current == charcount - 1 && str[current] == _T('"'))) /* only works at end of line*/ { if (wLastKey != VK_TAB) { /* if first TAB, complete filename*/ tempscreen = charcount; CompleteFilename (str, charcount); charcount = _tcslen (str); current = charcount; SetCursorXY (orgx, orgy); ConOutPrintf (_T("%s"), str); if (tempscreen > charcount) { GetCursorXY (&curx, &cury); for (count = tempscreen - charcount; count--; ) ConOutChar (_T(' ')); SetCursorXY (curx, cury); } else { if (((charcount + orgx) / maxx) + orgy > maxy - 1) orgy += maxy - ((charcount + orgx) / maxx + orgy + 1); } /* set cursor position */ SetCursorXY ((orgx + current) % maxx, orgy + (orgx + current) / maxx); GetCursorXY (&curx, &cury); } else { /*if second TAB, list matches*/ if (ShowCompletionMatches (str, charcount)) { PrintPrompt(); GetCursorXY(&orgx, &orgy); ConOutPrintf(_T("%s"), str); /* set cursor position */ SetCursorXY((orgx + current) % maxx, orgy + (orgx + current) / maxx); GetCursorXY(&curx, &cury); } } } else { MessageBeep(-1); } #endif #ifdef FEATURE_4NT_FILENAME_COMPLETION /* used to later see if we went down to the next line */ tempscreen = charcount; szPath[0]=_T('\0'); /* str is the whole things that is on the current line that is and and out. arg 2 is weather it goes back one file or forward one file */ CompleteFilename(str, !(ir.Event.KeyEvent.dwControlKeyState & SHIFT_PRESSED), szPath, current); /* Attempt to clear the line */ ClearCommandLine (str, maxlen, orgx, orgy); curx = orgx; cury = orgy; current = charcount = 0; /* Everything is deleted, lets add it back in */ _tcscpy(str,szPath); /* Figure out where cusor is going to be after we print it */ charcount = _tcslen(str); current = charcount; SetCursorXY(orgx, orgy); /* Print out what we have now */ ConOutPrintf(_T("%s"), str); /* Move cursor accordingly */ if (tempscreen > charcount) { GetCursorXY(&curx, &cury); for(count = tempscreen - charcount; count--; ) ConOutChar(_T(' ')); SetCursorXY(curx, cury); } else { if (((charcount + orgx) / maxx) + orgy > maxy - 1) orgy += maxy - ((charcount + orgx) / maxx + orgy + 1); } SetCursorXY((short)(((int)orgx + current) % maxx), (short)((int)orgy + ((int)orgx + current) / maxx)); GetCursorXY(&curx, &cury); #endif break; case _T('M'): case _T('C'): /* ^M does the same as return */ bCharInput = TRUE; if (!(ir.Event.KeyEvent.dwControlKeyState & (RIGHT_CTRL_PRESSED|LEFT_CTRL_PRESSED))) { break; } case VK_RETURN: /* end input, return to main */ #ifdef FEATURE_HISTORY /* add to the history */ if (str[0]) History (0, str); #endif str[charcount++] = _T('\n'); str[charcount] = _T('\0'); ConOutChar(_T('\n')); bReturn = TRUE; break; case VK_ESCAPE: /* clear str Make this callable! */ ClearCommandLine (str, maxlen, orgx, orgy); curx = orgx; cury = orgy; current = charcount = 0; break; #ifdef FEATURE_HISTORY case VK_F3: History_move_to_bottom(); #endif case VK_UP: #ifdef FEATURE_HISTORY /* get previous command from buffer */ ClearCommandLine (str, maxlen, orgx, orgy); History (-1, str); current = charcount = _tcslen (str); if (((charcount + orgx) / maxx) + orgy > maxy - 1) orgy += maxy - ((charcount + orgx) / maxx + orgy + 1); ConOutPrintf (_T("%s"), str); GetCursorXY (&curx, &cury); #endif break; case VK_DOWN: #ifdef FEATURE_HISTORY /* get next command from buffer */ ClearCommandLine (str, maxlen, orgx, orgy); History (1, str); current = charcount = _tcslen (str); if (((charcount + orgx) / maxx) + orgy > maxy - 1) orgy += maxy - ((charcount + orgx) / maxx + orgy + 1); ConOutPrintf (_T("%s"), str); GetCursorXY (&curx, &cury); #endif break; case VK_LEFT: /* move cursor left */ if (current > 0) { current--; if (GetCursorX () == 0) { SetCursorXY ((SHORT)(maxx - 1), (SHORT)(GetCursorY () - 1)); curx = maxx - 1; cury--; } else { SetCursorXY ((SHORT)(GetCursorX () - 1), GetCursorY ()); curx--; } } else { MessageBeep (-1); } break; case VK_RIGHT: /* move cursor right */ if (current != charcount) { current++; if (GetCursorX () == maxx - 1) { SetCursorXY (0, (SHORT)(GetCursorY () + 1)); curx = 0; cury++; } else { SetCursorXY ((SHORT)(GetCursorX () + 1), GetCursorY ()); curx++; } } #ifdef FEATURE_HISTORY else { LPCTSTR last = PeekHistory(-1); if (last && charcount < (INT)_tcslen (last)) { PreviousChar = last[current]; ConOutChar(PreviousChar); GetCursorXY(&curx, &cury); str[current++] = PreviousChar; charcount++; } } #endif break; default: /* This input is just a normal char */ bCharInput = TRUE; } #ifdef _UNICODE ch = ir.Event.KeyEvent.uChar.UnicodeChar; if (ch >= 32 && (charcount != (maxlen - 2)) && bCharInput) #else ch = ir.Event.KeyEvent.uChar.AsciiChar; if ((UCHAR)ch >= 32 && (charcount != (maxlen - 2)) && bCharInput) #endif /* _UNICODE */ { /* insert character into string... */ if (bInsert && current != charcount) { /* If this character insertion will cause screen scrolling, * adjust the saved origin of the command prompt. */ tempscreen = _tcslen(str + current) + curx; if ((tempscreen % maxx) == (maxx - 1) && (tempscreen / maxx) + cury == (maxy - 1)) { orgy--; cury--; } for (count = charcount; count > current; count--) str[count] = str[count - 1]; str[current++] = ch; if (curx == maxx - 1) curx = 0, cury++; else curx++; ConOutPrintf (_T("%s"), &str[current - 1]); SetCursorXY (curx, cury); charcount++; } else { if (current == charcount) charcount++; str[current++] = ch; if (GetCursorX () == maxx - 1 && GetCursorY () == maxy - 1) orgy--, cury--; if (GetCursorX () == maxx - 1) curx = 0, cury++; else curx++; ConOutChar (ch); } } //wLastKey = ir.Event.KeyEvent.wVirtualKeyCode; } while (!bReturn); SetCursorType (bInsert, TRUE); #ifdef FEATURE_ALIASES /* expand all aliases */ ExpandAlias (str, maxlen); #endif /* FEATURE_ALIAS */ return TRUE; }
/* * display shell version info internal command. */ INT cmd_ver (LPTSTR param) { INT i; nErrorLevel = 0; if (_tcsstr(param, _T("/?")) != NULL) { ConOutResPaging(TRUE,STRING_VERSION_HELP1); return 0; } ConOutResPrintf(STRING_CMD_SHELLINFO, _T(KERNEL_RELEASE_STR), _T(KERNEL_VERSION_BUILD_STR)); ConOutChar(_T('\n')); ConOutResPuts(STRING_VERSION_RUNNING_ON); PrintOSVersion(); /* Basic copyright notice */ if (param[0] != _T('\0')) { ConOutPuts(_T("\n\n")); ConOutPuts(_T("Copyright (C) 1994-1998 Tim Norman and others.\n")); ConOutPuts(_T("Copyright (C) 1998-") _T(COPYRIGHT_YEAR) _T(" ReactOS Team\n")); for (i = 0; param[i]; i++) { /* Skip spaces */ if (param[i] == _T(' ')) continue; if (param[i] == _T('/')) { /* Is this a lone '/' ? */ if (param[i + 1] == 0) { error_invalid_switch(_T(' ')); return 1; } continue; } if (_totupper(param[i]) == _T('W')) { /* Warranty notice */ ConOutResPuts(STRING_VERSION_HELP3); } else if (_totupper(param[i]) == _T('R')) { /* Redistribution notice */ ConOutResPuts(STRING_VERSION_HELP4); } else if (_totupper(param[i]) == _T('C')) { /* Developer listing */ ConOutResPuts(STRING_VERSION_HELP6); ConOutResPuts(STRING_FREEDOS_DEV); ConOutResPuts(STRING_VERSION_HELP7); ConOutResPuts(STRING_REACTOS_DEV); } else { error_invalid_switch(_totupper(param[i])); return 1; } } /* Bug report notice */ ConOutResPuts(STRING_VERSION_HELP5); } ConOutChar(_T('\n')); return 0; }