/* Read a string, and return a pointer to it. Returns NULL on EOF. */ char * vtysh_rl_gets () { HIST_ENTRY *last; /* If the buffer has already been allocated, return the memory * to the free pool. */ if (line_read) { free (line_read); line_read = NULL; } /* Get a line from the user. Change prompt according to node. XXX. */ line_read = readline (vtysh_prompt ()); /* If the line has any text in it, save it on the history. But only if * last command in history isn't the same one. */ if (line_read && *line_read) { using_history(); last = previous_history(); if (!last || strcmp (last->line, line_read) != 0) { add_history (line_read); append_history(1,history_file); } } return (line_read); }
/* Process and free undo lists attached to each history entry prior to the current entry, inclusive, reverting each line to its saved state. This is destructive, and state about the current line is lost. This is not intended to be called while actively editing, and the current line is not assumed to have been added to the history list. */ void _rl_revert_all_lines (void) { int hpos; HIST_ENTRY *entry; UNDO_LIST *ul, *saved_undo_list; char *lbuf; lbuf = savestring (rl_line_buffer); saved_undo_list = rl_undo_list; hpos = where_history (); entry = (hpos == history_length) ? previous_history () : current_history (); while (entry) { if (ul = (UNDO_LIST *)entry->data) { if (ul == saved_undo_list) saved_undo_list = 0; /* Set up rl_line_buffer and other variables from history entry */ rl_replace_from_history (entry, 0); /* entry->line is now current */ entry->data = 0; /* entry->data is now current undo list */ /* Undo all changes to this history entry */ while (rl_undo_list) rl_do_undo (); /* And copy the reverted line back to the history entry, preserving the timestamp. */ FREE (entry->line); entry->line = savestring (rl_line_buffer); } entry = previous_history (); } /* Restore history state */ rl_undo_list = saved_undo_list; /* may have been set to null */ history_set_pos (hpos); /* reset the line buffer */ rl_replace_line (lbuf, 0); _rl_set_the_line (); /* and clean up */ xfree (lbuf); }
static int previoushistory(lua_State *L) { HIST_ENTRY *hist; if (!where_history()) hist = current_history(); else hist = previous_history(); push_history(L, hist); return 1; }
int _el_display_first_hist() { if (where_history() > 0) { if (!_el_w2mb(_el_line_buffer, &rl_line_buffer)) { return -1; } replace_history_entry(where_history(), rl_line_buffer, NULL); while (previous_history()); _el_display_history(); } return 0; }
/* finds and print all occurencies of commands from the history which * start with <cmd> * Returns the number of found entries on success, * and 0 if no such entry exists * * Peter Weilbacher 28Jun2004 */ int history_find_all(char *cmd) { int len; int found; int number = 0; /* each found entry increases this */ /* quote removal, copied from non-readline version */ if (*cmd == '"') cmd++; if (!*cmd) return 0; len = strlen(cmd); if (cmd[len - 1] == '"') cmd[--len] = 0; if (!*cmd) return 0; /* printf ("searching for all occurrences of '%s'\n", cmd); */ /* Output matching history entries in chronological order (not backwards * so we have to start at the beginning of the history list. */ #if defined(HAVE_LIBREADLINE) found = history_set_pos(0); if (found == -1) { fprintf(stderr, "ERROR (history_find_all): could not rewind history\n"); return 0; } #else /* HAVE_LIBEDITLINE */ /* libedit's history_set_pos() does not work properly, so we manually go to oldest entry */ while (next_history()); #endif do { found = history_search_prefix(cmd, 1); /* Anchored backward search for prefix */ if (found == 0) { number++; #if defined(HAVE_LIBREADLINE) printf("%5i %s\n", where_history() + history_base, current_history()->line); /* go one step back or you find always the same entry. */ if (!history_set_pos(where_history() + 1)) break; /* finished if stepping didn't work */ #else /* HAVE_LIBEDITLINE */ /* libedit's history indices are reversed wrt GNU readline */ printf("%5i %s\n", history_length - where_history() + history_base, current_history()->line); /* go one step back or you find always the same entry. */ if (!previous_history()) break; /* finished if stepping didn't work */ #endif } /* (found == 0) */ } while (found > -1); return number; }
/* Get the previous item out of our interactive history, making it the current line. If there is no previous history, just ding. */ int rl_get_previous_history (int count, int key) { HIST_ENTRY *old_temp, *temp; if (count < 0) return (rl_get_next_history (-count, key)); if (count == 0 || history_list () == 0) return 0; /* either not saved by rl_newline or at end of line, so set appropriately. */ if (_rl_history_saved_point == -1 && (rl_point || rl_end)) _rl_history_saved_point = (rl_point == rl_end) ? -1 : rl_point; /* If we don't have a line saved, then save this one. */ rl_maybe_save_line (); /* If the current line has changed, save the changes. */ rl_maybe_replace_line (); temp = old_temp = (HIST_ENTRY *)NULL; while (count) { temp = previous_history (); if (temp == 0) break; old_temp = temp; --count; } /* If there was a large argument, and we moved back to the start of the history, that is not an error. So use the last value found. */ if (!temp && old_temp) temp = old_temp; if (temp == 0) { rl_maybe_unsave_line (); rl_ding (); } else { rl_replace_from_history (temp, 0); _rl_history_set_point (); } return 0; }
//------------------------------------------------------------------------------ static int find_duplicate(const char* line) { HIST_ENTRY* hist_entry; using_history(); while (hist_entry = previous_history()) { if (strcmp(hist_entry->line, line) == 0) { return where_history(); } } return -1; }
char *gnu_history_entry(int ind, int time) { HIST_ENTRY *entry = NULL; if (ind == 0) entry = current_history(); else if (ind < 0) entry = previous_history(); else if (ind > 0) entry = next_history(); if (entry == NULL) return NULL; return (time == 0 ? entry->line : entry->timestamp); }
static int rl_history_search_internal (int count, int direction) { HIST_ENTRY *temp, *old_temp; int line_len; maybe_save_line (); temp = old_temp = (HIST_ENTRY *)NULL; while (count) { temp = (direction < 0) ? previous_history () : next_history (); if (!temp) break; if (STREQN (rl_line_buffer, temp->line, rl_point)) { /* Don't find multiple instances of the same line. */ if (prev_line_found && STREQ (prev_line_found, temp->line)) continue; if (direction < 0) old_temp = temp; prev_line_found = temp->line; count--; } } if (!temp) { if (direction < 0 && old_temp) temp = old_temp; else { maybe_unsave_line (); DING (); return 1; } } line_len = strlen (temp->line); if (line_len >= rl_line_buffer_len) rl_extend_line_buffer (line_len); strcpy (rl_line_buffer, temp->line); rl_undo_list = (UNDO_LIST *)temp->data; rl_end = line_len; return 0; }
static void readline_cmd_handler(char *cmd) { if (cmd && *cmd) { HIST_ENTRY *h; while (next_history()) ; h = previous_history(); if (h == NULL || os_strcmp(cmd, h->line) != 0) add_history(cmd); next_history(); } if (cmd == NULL) { edit_eof_cb(edit_cb_ctx); return; } trunc_nl(cmd); edit_cmd_cb(edit_cb_ctx, cmd); }
//------------------------------------------------------------------------------ static void add_to_history(const char* line) { const unsigned char* c; HIST_ENTRY* hist_entry; // Skip leading whitespace c = (const unsigned char*)line; while (*c) { if (!isspace(*c)) { break; } ++c; } // Skip empty lines if (*c == '\0') { return; } // Check the line's not a duplicate of the last in the history. using_history(); hist_entry = previous_history(); if (hist_entry != NULL) { if (strcmp(hist_entry->line, c) == 0) { return; } } // All's well. Add the line. using_history(); add_history(line); ++g_new_history_count; }
static void ProcessEvent() { char intext[10]; KeySym keysym; XComposeStatus cs; int i, n, count; XEvent ev; HIST_ENTRY *hist; /* History entry */ char is_hist; XNextEvent (condpy, &ev); is_hist = 0; switch (ev.type) { case Expose: if (ev.xexpose.count == 0) Redraw (); break; case ConfigureNotify: width = ev.xconfigure.width; height = ev.xconfigure.height; Resize (width / font_width, height / font_height); break; case KeyPress: // count = XLookupString (&ev.xkey, intext, 10, &keysym, &cs); // intext[count] = 0; count = 1; intext[0] = ev.xkey.keycode; intext[1] = 0; if (count == 1) { switch (intext[0]) { case '\r': intext[0] = '\n'; break; #if !defined(STNDALN) case '': hist = previous_history(); is_hist = 1; break; case '': hist = next_history(); is_hist = 1; break; #endif } } #if !defined(STNDALN) /* Process history */ if ( is_hist ) { if(hist) { char *dst = text + ncols * row + 4; memset(dst,' ',col-3); /* clean to EOL */ col = 4; PutString(hist->line); PutChar (0); RedrawRow(); } break; } #endif #ifdef OBSOLETE /* as XLookupString is broken */ else switch (keysym) { case XK_Return: case XK_Linefeed: intext[0] = '\n'; intext[1] = 0; break; case XK_Tab: intext[0] = '\t'; intext[1] = 0; break; case XK_BackSpace: intext[0] = '\b'; intext[1] = 0; break; case XK_Delete: break; case XK_Left: break; case XK_Right: break; case XK_Down: break; case XK_Up: break; } #endif /* OBSOLETE */ if (intext[0] ) { if (intext[0] == '\n') { char *dst = text + ncols * row + plen; strncpy(grads_cmd,dst,1024); got_grads_cmd = 1; /* signal nxtcmd() that we got a command */ } PutChar (intext[0]); RedrawRow(); strcat (my_stdin_buf, intext); if ( intext[0] == '\n' ) { ProcessOutput (my_stdin_buf); my_stdin_buf[0] = 0; } } break; } }
static void wpa_cli_interactive(void) { #define max_args 10 char cmdbuf[256], *cmd, *argv[max_args], *pos; int argc; #ifdef CONFIG_READLINE char *home, *hfile = NULL; #endif /* CONFIG_READLINE */ printf("\nInteractive mode\n\n"); #ifdef CONFIG_READLINE rl_attempted_completion_function = wpa_cli_completion; home = getenv("HOME"); if (home) { const char *fname = ".wpa_cli_history"; int hfile_len = os_strlen(home) + 1 + os_strlen(fname) + 1; hfile = os_malloc(hfile_len); if (hfile) { os_snprintf(hfile, hfile_len, "%s/%s", home, fname); hfile[hfile_len - 1] = '\0'; read_history(hfile); stifle_history(100); } } #endif /* CONFIG_READLINE */ do { wpa_cli_recv_pending(monitor_conn, 0, 0); #ifndef CONFIG_NATIVE_WINDOWS alarm(1); #endif /* CONFIG_NATIVE_WINDOWS */ #ifdef CONFIG_READLINE cmd = readline("> "); if (cmd && *cmd) { HIST_ENTRY *h; while (next_history()) ; h = previous_history(); if (h == NULL || os_strcmp(cmd, h->line) != 0) add_history(cmd); next_history(); } #else /* CONFIG_READLINE */ printf("> "); cmd = fgets(cmdbuf, sizeof(cmdbuf), stdin); #endif /* CONFIG_READLINE */ #ifndef CONFIG_NATIVE_WINDOWS alarm(0); #endif /* CONFIG_NATIVE_WINDOWS */ if (cmd == NULL) break; wpa_cli_recv_pending(monitor_conn, 0, 0); pos = cmd; while (*pos != '\0') { if (*pos == '\n') { *pos = '\0'; break; } pos++; } argc = 0; pos = cmd; for (;;) { while (*pos == ' ') pos++; if (*pos == '\0') break; argv[argc] = pos; argc++; if (argc == max_args) break; if (*pos == '"') { char *pos2 = os_strrchr(pos, '"'); if (pos2) pos = pos2 + 1; } while (*pos != '\0' && *pos != ' ') pos++; if (*pos == ' ') *pos++ = '\0'; } if (argc) wpa_request(ctrl_conn, argc, argv); if (cmd != cmdbuf) os_free(cmd); } while (!wpa_cli_quit); #ifdef CONFIG_READLINE if (hfile) { /* Save command history, excluding lines that may contain * passwords. */ HIST_ENTRY *h; history_set_pos(0); h = next_history(); while (h) { char *p = h->line; while (*p == ' ' || *p == '\t') p++; if (os_strncasecmp(p, "pa", 2) == 0 || os_strncasecmp(p, "o", 1) == 0 || os_strncasecmp(p, "n", 1)) { h = remove_history(where_history()); if (h) { os_free(h->line); os_free(h->data); os_free(h); } h = current_history(); } else { h = next_history(); } } write_history(hfile); os_free(hfile); } #endif /* CONFIG_READLINE */ }
/* main readline function */ char *readline(const char *prompt) { wchar_t buf[_EL_CONSOLE_BUF_LEN]; char **array = NULL; char *ret_string = NULL; int start = 0; int end = 0; int compl_pos = -1; int n = 0; int index = 0; int len = 0; int line_len = 0; int old_width = 0; int width = 0; UINT32 ctrl = 0; UINT32 special = 0; COORD coord; DWORD count = 0; INPUT_RECORD irBuffer; CONSOLE_SCREEN_BUFFER_INFO sbInfo; _el_ctrl_c_pressed = FALSE; _el_line_buffer = NULL; _el_temp_print = NULL; _el_next_compl = NULL; rl_line_buffer = NULL; _el_file_name = NULL; _el_dir_name = NULL; _el_old_arg = NULL; _el_wide = NULL; _el_text = NULL; _el_text_mb = NULL; _el_compl_array = NULL; _el_completer_word_break_characters = NULL; rl_point = 0; rl_attempted_completion_over = 0; _el_compl_index = 0; _el_n_compl = 0; _el_h_in = NULL; _el_h_out = NULL; wcscpy_s(_el_basic_file_break_characters, _EL_MAX_FILE_BREAK_CHARACTERS, _EL_BASIC_FILE_BREAK_CHARACTERS); memset(&coord, 0, sizeof(COORD)); memset(buf, 0, _EL_CONSOLE_BUF_LEN * sizeof(wchar_t)); memset(&irBuffer, 0, sizeof(INPUT_RECORD)); /* allocate buffers */ _el_line_buffer_size = _EL_BUF_LEN + 1; _el_line_buffer = (wchar_t *)malloc(_el_line_buffer_size * sizeof(wchar_t)); if (!_el_mb2w((char *)rl_basic_word_break_characters, &_el_basic_word_break_characters)) { _el_clean_exit(); return NULL; } if (rl_completer_word_break_characters) { if (!_el_mb2w((char *)rl_completer_word_break_characters, &_el_completer_word_break_characters)) { _el_clean_exit(); return NULL; } } if (!(_el_line_buffer)) { _el_clean_exit(); return NULL; } memset(_el_line_buffer, 0, _el_line_buffer_size * sizeof(wchar_t)); rl_attempted_completion_over = 0; _el_print = (wchar_t *)malloc(_el_line_buffer_size * sizeof(wchar_t)); if (!(_el_print)) { _el_clean_exit(); return NULL; } memset(_el_print, 0, _el_line_buffer_size * sizeof(wchar_t)); rl_prompt = _strdup(prompt); if (!(rl_prompt)) { _el_clean_exit(); return NULL; } if (!_el_mb2w((char *)prompt, &_el_prompt)) { _el_clean_exit(); return NULL; } _el_prompt_len = (int)wcslen(_el_prompt); /* get I/O handles for current console */ _el_h_in = GetStdHandle(STD_INPUT_HANDLE); _el_h_out = GetStdHandle(STD_OUTPUT_HANDLE); if ((!(_el_h_in)) || (!(_el_h_out))) { _el_clean_exit(); return NULL; } /* set console modes */ _el_prev_in_cm_saved = GetConsoleMode(_el_h_in, &_el_prev_in_cm); _el_prev_out_cm_saved = GetConsoleMode(_el_h_out, &_el_prev_out_cm); SetConsoleMode(_el_h_in, ENABLE_PROCESSED_INPUT | ENABLE_EXTENDED_FLAGS | ENABLE_INSERT_MODE | ENABLE_QUICK_EDIT_MODE); SetConsoleMode(_el_h_out, ENABLE_PROCESSED_OUTPUT); SetConsoleCtrlHandler((PHANDLER_ROUTINE) _el_signal_handler, TRUE); rl_point = 0; while ((buf[0] != VK_RETURN) && (!_el_ctrl_c_pressed) && _el_line_buffer) { /* get screen buffer info from the current console */ if (!GetConsoleScreenBufferInfo(_el_h_out, &sbInfo)) { _el_clean_exit(); return NULL; } _el_temp_print_size = sbInfo.dwSize.X + 1; if (!(_el_temp_print = realloc(_el_temp_print, _el_temp_print_size * sizeof(wchar_t)))) { _el_clean_exit(); return NULL; } _el_temp_print[0] = _T('\0'); /* compute the current visible console width */ width = sbInfo.srWindow.Right - sbInfo.srWindow.Left + 1; /* if the user has changed the window size update the view */ if (old_width != width) { line_len = (int)wcslen(_el_line_buffer); sbInfo.dwCursorPosition.X = 0; if (old_width) { n = (_el_prompt_len + line_len - 1) / old_width; sbInfo.dwCursorPosition.Y -= n; coord.Y = sbInfo.dwCursorPosition.Y; } if (!SetConsoleCursorPosition(_el_h_out, sbInfo.dwCursorPosition)) { _el_clean_exit(); return NULL; } if (_el_print_string(_el_prompt)) { _el_clean_exit(); return NULL; } if (_el_set_cursor(_el_prompt_len)) { _el_clean_exit(); return NULL; } if (_el_print_string(_el_line_buffer)) { _el_clean_exit(); return NULL; } if (_el_set_cursor(line_len)) { _el_clean_exit(); return NULL; } if (old_width && (old_width < width)) { coord.X = 0; coord.Y += (_el_prompt_len + line_len - 1) / width + 1; FillConsoleOutputCharacter(_el_h_out, _T(' '), sbInfo.dwSize.X * (n + 2), coord, &count); } } old_width = width; /* wait for console events */ if (!PeekConsoleInput(_el_h_in, &irBuffer, 1, &count)) { _el_clean_exit(); return NULL; } if (count) { if ((irBuffer.EventType == KEY_EVENT) && irBuffer.Event.KeyEvent.bKeyDown) { /* the user pressed a key */ ctrl = (irBuffer.Event.KeyEvent.dwControlKeyState & (LEFT_CTRL_PRESSED | RIGHT_CTRL_PRESSED)); if (irBuffer.Event.KeyEvent.uChar.UnicodeChar == _T('\n')) { if (!ReadConsoleInput(_el_h_in, &irBuffer, 1, &count)) { _el_clean_exit(); return NULL; } buf[0] = VK_RETURN; continue; } if (irBuffer.Event.KeyEvent.uChar.UnicodeChar == _T('\0')) { /* if it is a special key, just remove it from the buffer */ if (!ReadConsoleInput(_el_h_in, &irBuffer, 1, &count)) { _el_clean_exit(); return NULL; } special = irBuffer.Event.KeyEvent.wVirtualKeyCode; /* parse the special key */ switch (special) { /* arrow left, arrow right HOME and END keys */ case VK_LEFT: case VK_RIGHT: case VK_HOME: case VK_END: if (_el_move_cursor(special, ctrl)) { _el_clean_exit(); return NULL; } break; /* arrow up: display previous history element (if any) after recording the current command line */ case VK_UP: if (_el_display_prev_hist()) { _el_clean_exit(); return NULL; } break; /* page up: display the first history element (if any) after recording the current command line */ case VK_PRIOR: if (_el_display_first_hist()) { _el_clean_exit(); return NULL; } break; /* arrow down: display next history element (if any) after recording the current command line */ case VK_DOWN: if (_el_display_next_hist()) { _el_clean_exit(); return NULL; } break; case VK_NEXT: /* page down: display last history element (if any) after recording the current command line */ if (_el_display_last_hist()) { _el_clean_exit(); return NULL; } break; /* delete char */ case VK_DELETE: if (rl_point != wcslen(_el_line_buffer)) { if (_el_delete_char(VK_DELETE, 1)) { _el_clean_exit(); return NULL; } _el_compl_index = 0; compl_pos = -1; } break; } } else { /* if it is a normal key, remove it from the buffer */ memset(buf, 0, _EL_CONSOLE_BUF_LEN * sizeof(wchar_t)); if (!ReadConsole(_el_h_in, buf, 1, &count, NULL)) { _el_clean_exit(); return NULL; } /* then parse it */ switch (buf[0]) { /* backspace */ case VK_BACK: if (rl_point) { _el_compl_index = 0; compl_pos = -1; if (_el_delete_char(VK_BACK, 1)) { _el_clean_exit(); return NULL; } } break; /* TAB: do completion */ case VK_TAB: if ((!array) || (rl_point != compl_pos)) { _el_free_array(array); index = 0; if (_el_text) { free(_el_text); _el_text = NULL; } if (!(_el_text = _el_get_compl_text(&start, &end))) { _el_clean_exit(); return NULL; } if (_el_old_arg) { _el_old_arg[0] = _T('\0'); } if (!_el_w2mb(_el_text, &_el_text_mb)) { _el_clean_exit(); return NULL; } if (!_el_w2mb(_el_line_buffer, &rl_line_buffer)) { _el_clean_exit(); return NULL; } array = (rl_attempted_completion_function ? rl_attempted_completion_function(_el_text_mb, start, end) : rl_completion_matches(_el_text_mb, (rl_completion_entry_function ? rl_completion_entry_function : rl_filename_completion_function))); if (!array) { _el_clean_exit(); return NULL; } } if (!array[index]) { index = 0; } if (array[index]) { if (!_el_mb2w(array[index], &_el_next_compl)) { _el_clean_exit(); return NULL; } len = 0; if (_el_old_arg) { len = (int)wcslen(_el_old_arg); #if 0 fwprintf(stderr, _T("VK_TAB) _el_old_arg = '%s', len = %d\n"), _el_old_arg, len); fflush(stderr); #endif } if (!len) { len = (int)wcslen(_el_text); } if (len) { if (_el_delete_char(VK_BACK, len)) { _el_clean_exit(); return NULL; } } len = (int)wcslen(_el_next_compl); if (!(_el_old_arg = realloc(_el_old_arg, (len + 1) * sizeof(wchar_t)))) { return NULL; } _el_old_arg[len] = _T('\0'); memcpy(_el_old_arg, _el_next_compl, len * sizeof(wchar_t)); line_len = (int)wcslen(_el_line_buffer); if (_el_insert_char(_el_next_compl, len)) { _el_clean_exit(); return NULL; } free(_el_next_compl); _el_next_compl = NULL; compl_pos = ((rl_point && (!wcschr(_el_completer_word_break_characters ? _el_completer_word_break_characters : _el_basic_word_break_characters, _el_line_buffer[rl_point - 1]))) ? rl_point : -1); ++index; } break; /* ENTER: move the cursor to end of line, then return to the caller program */ case VK_RETURN: if (_el_set_cursor((int)wcslen(_el_line_buffer) - rl_point)) { _el_clean_exit(); return NULL; } break; /* delete word */ case 0x17: /* CTRL + W */ if (ctrl) { if (!rl_point) { break; } n = 1; while (((rl_point - n) > 0) && (iswspace(_el_line_buffer[rl_point - n]))) { ++n; } while ((rl_point - n) && (!iswspace(_el_line_buffer[rl_point - n]))) { ++n; } if (rl_point - n) { --n; } _el_compl_index = 0; compl_pos = -1; if (_el_delete_char(VK_BACK, n)) { _el_clean_exit(); return NULL; } break; } /* delete until end of line */ case 0x0B: /* CTRL + K */ if (ctrl) { line_len = (int)wcslen(_el_line_buffer); if (rl_point < line_len) { _el_compl_index = 0; compl_pos = -1; if (_el_delete_char(VK_DELETE, line_len - rl_point)) { _el_clean_exit(); return NULL; } } break; } /* beginning-of-line */ case 0x01: /* CTRL + A */ if (_el_move_cursor(VK_HOME, 0)) { _el_clean_exit(); return NULL; } break; /* end-of-line */ case 0x05: /* CTRL + E */ if (_el_move_cursor(VK_END, 0)) { _el_clean_exit(); return NULL; } break; /* forward-char */ case 0x06: /* CTRL + F */ if (_el_move_cursor(VK_RIGHT, 0)) { _el_clean_exit(); return NULL; } break; /* backward-char */ case 0x02: /* CTRL + B */ if (_el_move_cursor(VK_LEFT, 0)) { _el_clean_exit(); return NULL; } break; /* previous-line */ case 0x10: /* CTRL + P */ if (_el_display_prev_hist()) { _el_clean_exit(); return NULL; } break; /* next-line */ case 0x0E: /* CTRL + N */ if (_el_display_next_hist()) { _el_clean_exit(); return NULL; } break; /* delete char */ case 0x04: /* CTRL + D */ if (rl_point != wcslen(_el_line_buffer)) { if (_el_delete_char(VK_DELETE, 1)) { _el_clean_exit(); return NULL; } _el_compl_index = 0; compl_pos = -1; } break; /* if it is a printable character, print it NOTE: I have later commented out the iswprint() check since for instance it prevents the euro sign from being printed */ default: /*if (iswprint(buf[0])) {*/ _el_compl_index = 0; compl_pos = -1; if (_el_insert_char(buf, 1)) { _el_clean_exit(); return NULL; } /*}*/ } } } /* if it was not a keyboard event, just remove it from buffer */ else if (!ReadConsoleInput(_el_h_in, &irBuffer, 1, &count)) { _el_clean_exit(); return NULL; } } else { /* wait for console input */ WaitForSingleObject(_el_h_in, INFINITE); } } printf("\n"); while (next_history()); previous_history(); /* if CTRL+C has been pressed, return an empty string */ if (_el_line_buffer) { if (_el_ctrl_c_pressed) { n = (int)wcslen(_el_line_buffer) - rl_point; if (n) { _el_set_cursor(n); } _el_line_buffer[0] = _T('\0'); } _el_w2mb(_el_line_buffer, &rl_line_buffer); ret_string = _strdup(rl_line_buffer); } _el_clean_exit(); return ret_string; }
/** * Binds the up arrow key to be used to return previous commands * ran in the shell. * Note: Params and returned int are unused. */ int bindUp(int count, int key) { HIST_ENTRY * prev = previous_history(); printf(prev->line); return 0; }
static void wpa_cli_reconnect(void) { wpa_cli_close_connection(); ctrl_conn = wpa_cli_open_connection(ctrl_ifname); if (ctrl_conn) { printf("Connection to wpa_supplicant re-established\n"); #ifdef ANDROID if (wpa_ctrl_attach(monitor_conn) == 0) { #else if (wpa_ctrl_attach(ctrl_conn) == 0) { #endif wpa_cli_attached = 1; } else { printf("Warning: Failed to attach to " "wpa_supplicant.\n"); } } } static void wpa_cli_recv_pending(struct wpa_ctrl *ctrl, int in_read, int action_monitor) { int first = 1; #ifdef ANDROID if (ctrl == NULL) { #else if (ctrl_conn == NULL) { #endif wpa_cli_reconnect(); return; } while (wpa_ctrl_pending(ctrl) > 0) { char buf[256]; size_t len = sizeof(buf) - 1; if (wpa_ctrl_recv(ctrl, buf, &len) == 0) { buf[len] = '\0'; if (action_monitor) wpa_cli_action_process(buf); else { if (in_read && first) printf("\n"); first = 0; printf("%s\n", buf); } } else { printf("Could not read pending message.\n"); break; } } if (wpa_ctrl_pending(ctrl) < 0) { printf("Connection to wpa_supplicant lost - trying to " "reconnect\n"); wpa_cli_reconnect(); } } #ifdef CONFIG_READLINE static char * wpa_cli_cmd_gen(const char *text, int state) { static int i, len; const char *cmd; if (state == 0) { i = 0; len = os_strlen(text); } while ((cmd = wpa_cli_commands[i].cmd)) { i++; if (os_strncasecmp(cmd, text, len) == 0) return os_strdup(cmd); } return NULL; } static char * wpa_cli_dummy_gen(const char *text, int state) { return NULL; } static char ** wpa_cli_completion(const char *text, int start, int end) { return rl_completion_matches(text, start == 0 ? wpa_cli_cmd_gen : wpa_cli_dummy_gen); } #endif /* CONFIG_READLINE */ static void wpa_cli_interactive(void) { #define max_args 10 char cmdbuf[256], *cmd, *argv[max_args], *pos; int argc; #ifdef CONFIG_READLINE char *home, *hfile = NULL; #endif /* CONFIG_READLINE */ printf("\nInteractive mode\n\n"); #ifdef CONFIG_READLINE rl_attempted_completion_function = wpa_cli_completion; home = getenv("HOME"); if (home) { const char *fname = ".wpa_cli_history"; int hfile_len = os_strlen(home) + 1 + os_strlen(fname) + 1; hfile = os_malloc(hfile_len); if (hfile) { int res; res = os_snprintf(hfile, hfile_len, "%s/%s", home, fname); if (res >= 0 && res < hfile_len) { hfile[hfile_len - 1] = '\0'; read_history(hfile); stifle_history(100); } } } #endif /* CONFIG_READLINE */ do { #ifdef ANDROID wpa_cli_recv_pending(monitor_conn, 0, 0); #else wpa_cli_recv_pending(ctrl_conn, 0, 0); #endif #ifndef CONFIG_NATIVE_WINDOWS alarm(ping_interval); #endif /* CONFIG_NATIVE_WINDOWS */ #ifdef CONFIG_READLINE cmd = readline("> "); if (cmd && *cmd) { HIST_ENTRY *h; while (next_history()) ; h = previous_history(); if (h == NULL || os_strcmp(cmd, h->line) != 0) add_history(cmd); next_history(); } #else /* CONFIG_READLINE */ printf("> "); cmd = fgets(cmdbuf, sizeof(cmdbuf), stdin); #endif /* CONFIG_READLINE */ #ifndef CONFIG_NATIVE_WINDOWS alarm(0); #endif /* CONFIG_NATIVE_WINDOWS */ if (cmd == NULL) break; #ifdef ANDROID wpa_cli_recv_pending(monitor_conn, 0, 0); #else wpa_cli_recv_pending(ctrl_conn, 0, 0); #endif pos = cmd; while (*pos != '\0') { if (*pos == '\n') { *pos = '\0'; break; } pos++; } argc = 0; pos = cmd; for (;;) { while (*pos == ' ') pos++; if (*pos == '\0') break; argv[argc] = pos; argc++; if (argc == max_args) break; if (*pos == '"') { char *pos2 = os_strrchr(pos, '"'); if (pos2) pos = pos2 + 1; } while (*pos != '\0' && *pos != ' ') pos++; if (*pos == ' ') *pos++ = '\0'; } if (argc) wpa_request(ctrl_conn, argc, argv); if (cmd != cmdbuf) os_free(cmd); } while (!wpa_cli_quit); #ifdef CONFIG_READLINE if (hfile) { /* Save command history, excluding lines that may contain * passwords. */ HIST_ENTRY *h; history_set_pos(0); while ((h = current_history())) { char *p = h->line; while (*p == ' ' || *p == '\t') p++; if (cmd_has_sensitive_data(p)) { h = remove_history(where_history()); if (h) { os_free(h->line); os_free(h->data); os_free(h); } else next_history(); } else next_history(); } write_history(hfile); os_free(hfile); } #endif /* CONFIG_READLINE */ }