/* * Can you still remember input that looks like an execute @arg? * @arg must end with a newline. */ int seen_exec_input(char *arg) { size_t len = strlen(arg); int n, i, j, ch; unsigned char buf[RING_SIZE + 1]; assert(len && arg[len - 1] == '\n'); n = 1; for (;;) { /* find next line ending with arg */ n = ring_search(&recent_input, arg, n + 1); if (n <= 0) return 0; /* extract command (same or previous line) */ i = n - 1; if (ring_peek(&recent_input, i) == '\n') i--; j = sizeof(buf); buf[--j] = 0; for (; i >= 0 && (ch = ring_peek(&recent_input, i)) != '\n'; i--) buf[--j] = ch; /* compare command */ for (; isspace(buf[j]); j++) ; for (i = j; buf[i] && !isspace(buf[i]); i++) ; if (i - j >= 2 && !strncmp("execute", (char *)buf + j, i - j)) return 1; } }
/* * Can you still remember a line of input that ends with @tail? * It must end with a newline. */ int seen_input(char *tail) { size_t len = strlen(tail); assert(len && tail[len - 1] == '\n'); return ring_search(&recent_input, tail, 0) >= 0; }
/* * Remember input @inp for a while. */ void save_input(char inp) { int eol; while (ring_putc(&recent_input, inp) < 0) { eol = ring_search(&recent_input, "\n", 0); assert(eol >= 0); ring_discard(&recent_input, eol + 1); } }
/* * Can you still remember a line of input that ends with TAIL? * It must end with a newline. * Return non-zero iff TAIL can be remembered. * Passing that value to forget_input() will forget all input up to * and including this line. */ size_t seen_input(char *tail) { size_t len = strlen(tail); size_t remembered = ring_len(&recent_input); int dist; assert(len && tail[len - 1] == '\n'); dist = ring_search(&recent_input, tail); if (dist < 0) return 0; assert(dist + len <= remembered && remembered <= saved_bytes); return saved_bytes - remembered + dist + len; }
/* * Remember line of input INP for a while. * It must end with a newline. * Return value is suitable for forget_input(): it makes it forget all * input up to and including this line. */ size_t save_input(char *inp) { size_t len = strlen(inp); int eol; assert(len && inp[len - 1] == '\n'); while (ring_putm(&recent_input, inp, len) < 0) { eol = ring_search(&recent_input, "\n"); assert(eol >= 0); ring_discard(&recent_input, eol + 1); } saved_bytes += len; return saved_bytes; }