rc

[fork] interactive rc shell
git clone https://hhvn.uk/rc
git clone git://hhvn.uk/rc
Log | Files | Refs | README | LICENSE

edit-edit.c (1600B)


      1 #include "rc.h"
      2 
      3 #include <stdio.h>
      4 
      5 #include <histedit.h>
      6 
      7 #include "edit.h"
      8 
      9 bool editing = 1;
     10 
     11 struct cookie {
     12 	EditLine *el;
     13 	History *hist;
     14 };
     15 
     16 static char *prompt;
     17 
     18 void *edit_begin(int fd) {
     19 	FILE *f;
     20 	HistEvent he;
     21 	struct cookie *c;
     22 
     23 	c = ealloc(sizeof *c);
     24 	if (fd == 0)
     25 		f = stdin;
     26 	else
     27 		f = fdopen(fd, "r");
     28 	c->el = el_init("rc", f, stdout, stderr);
     29 	el_set(c->el, EL_SIGNAL, 0);
     30 	el_source(c->el, NULL);
     31 
     32 	c->hist = history_init();
     33 	history(c->hist, &he, H_SETSIZE, 20);
     34 	el_set(c->el, EL_HIST, history, c->hist);
     35 
     36 	return c;
     37 }
     38 
     39 
     40 static void (*oldint)(int), (*oldquit)(int);
     41 
     42 static void edit_catcher(int sig) {
     43 	sys_signal(SIGINT, oldint);
     44 	sys_signal(SIGQUIT, oldquit);
     45 	write(2, "\n", 1);
     46 	rc_raise(eError);
     47 }
     48 
     49 char *edit_alloc(void *cookie, size_t *count) {
     50 	const char *r;
     51 	HistEvent he;
     52 	struct cookie *c = cookie;
     53 
     54 	oldint = sys_signal(SIGINT, edit_catcher);
     55 	oldquit = sys_signal(SIGQUIT, edit_catcher);
     56 
     57 	r = el_gets(c->el, count);
     58 
     59 	sys_signal(SIGINT, oldint);
     60 	sys_signal(SIGQUIT, oldquit);
     61 
     62 	if (r)
     63 		history(c->hist, &he, H_ENTER, r);
     64 	return (char *)r; /* cast to avoid gcc warning */
     65 }
     66 
     67 static char *edit_prompter(EditLine *e) {
     68 	return prompt;
     69 }
     70 
     71 void edit_prompt(void *cookie, char *pr) {
     72 	struct cookie *c = cookie;
     73 
     74 	prompt = pr;
     75 	el_set(c->el, EL_PROMPT, edit_prompter);
     76 }
     77 
     78 void edit_free(void *cookie) {
     79 	/* this function deliberately left blank */
     80 }
     81 
     82 void edit_end(void *cookie) {
     83 	struct cookie *c = cookie;
     84 
     85 	el_end(c->el);
     86 	history_end(c->hist);
     87 	efree(c);
     88 }
     89 
     90 void edit_reset(void *cookie) {
     91 	struct cookie *c = cookie;
     92 
     93 	el_set(c->el, EL_TERMINAL, NULL);
     94 }