int boot_(Module m) { char* dummy = NULL; controller_init(&rwcli_controller); // Authenticate in case of RW.MSG mode rwcli_user_mode_t user_mode = RWCLI_USER_MODE_NONE; if (rwcli_controller.agent_type == RWCLI_TRANSPORT_MODE_RWMSG) { user_mode = rift_authenticate(&rift_cmdargs); if (user_mode == RWCLI_USER_MODE_INVALID) { printf("\nERROR: Invalid username/password\n"); exit(-1); } } rwcli_zsh_plugin_init(rwcli_controller.agent_type, user_mode); rwcli_set_messaging_hook(messaging_hook); rwcli_set_history_hook(history_hook); // Always load the rwmsg_agent module, If netconf is enabled then // this module will only receive logging notifications if (load_module("zsh/rwmsg_agent", NULL, 0) != 0) { printf("\nCRITICAL: Loading the messaging agent module failed\n"); fflush(stdout); return -1; } // Load the agent that is required if (rwcli_controller.agent_type == RWCLI_TRANSPORT_MODE_NETCONF) { if (load_module("zsh/rwnetconf_agent", NULL, 0) != 0) { printf("\nCRITICAL: Loading the netconf agent module failed\n"); fflush(stdout); return -1; } rwcli_controller.is_netconf_agent_loaded = true; } /* Register the completion widget */ rwcli_controller.w_comp = addzlefunction("rift-complete", rift_complete, 0); Keymap km = openkeymap("main"); rwcli_controller.t_orig_tab_bind = keybind(km, "\t", &dummy); bindkey(km, "\t", refthingy(rwcli_controller.w_comp->first), NULL); /* Bind ? to generate help */ rwcli_controller.w_gen_help = addzlefunction("rift-gen-help", rift_generate_help, 0); bindkey(km, "?", refthingy(rwcli_controller.w_gen_help->first), NULL); /* Set the lookup hook */ rw_lookup_fn = rift_lookup; /* Set the prompt hook */ addprepromptfn(rift_prompt); return 0; }
static int savekeymap(char *cmdname, char *oldname, char *newname, Keymap *savemapptr) { Keymap km = openkeymap(newname); if (km) { *savemapptr = openkeymap(oldname); /* I love special cases */ if (*savemapptr == km) *savemapptr = NULL; else { /* make sure this doesn't get deleted. */ if (*savemapptr) refkeymap(*savemapptr); linkkeymap(km, oldname, 0); } return 0; } else { zwarnnam(cmdname, "no such keymap: %s", newname); return 1; } }
ZLE_INT_T vigetkey(void) { Keymap mn = openkeymap("main"); char m[3], *str; Thingy cmd; if (getbyte(0L, NULL) == EOF) return ZLEEOF; m[0] = lastchar; metafy(m, 1, META_NOALLOC); if(mn) cmd = keybind(mn, m, &str); else cmd = t_undefinedkey; if (!cmd || cmd == Th(z_sendbreak)) { return ZLEEOF; } else if (cmd == Th(z_quotedinsert)) { if (getfullchar(0) == ZLEEOF) return ZLEEOF; } else if(cmd == Th(z_viquotedinsert)) { ZLE_CHAR_T sav = zleline[zlecs]; zleline[zlecs] = '^'; zrefresh(); getfullchar(0); zleline[zlecs] = sav; if(LASTFULLCHAR == ZLEEOF) return ZLEEOF; } else if (cmd == Th(z_vicmdmode)) { return ZLEEOF; } #ifdef MULTIBYTE_SUPPORT if (!lastchar_wide_valid) { getrestchar(lastchar); } #endif return LASTFULLCHAR; }
char * zleread(char **lp, char **rp, int flags, int context, char *init, char *finish) { char *s, **bracket; int old_errno = errno; int tmout = getiparam("TMOUT"); #if defined(HAVE_POLL) || defined(HAVE_SELECT) /* may not be set, but that's OK since getiparam() returns 0 == off */ baud = getiparam("BAUD"); costmult = (baud) ? 3840000L / baud : 0; #endif /* ZLE doesn't currently work recursively. This is needed in case a * * select loop is used in a function called from ZLE. vared handles * * this differently itself. */ if(zleactive) { char *pptbuf; int pptlen; pptbuf = unmetafy(promptexpand(lp ? *lp : NULL, 0, NULL, NULL, &pmpt_attr), &pptlen); write_loop(2, pptbuf, pptlen); free(pptbuf); return shingetline(); } /* * The current status is what we need if we are going * to display a prompt. We'll remember it here for * use further in. */ pre_zle_status = lastval; keytimeout = (time_t)getiparam("KEYTIMEOUT"); if (!shout) { if (SHTTY != -1) init_shout(); if (!shout) return NULL; /* We could be smarter and default to a system read. */ /* If we just got a new shout, make sure the terminal is set up. */ if (termflags & TERM_UNKNOWN) init_term(); } fflush(shout); fflush(stderr); intr(); insmode = unset(OVERSTRIKE); eofsent = 0; resetneeded = 0; fetchttyinfo = 0; trashedzle = 0; raw_lp = lp; lpromptbuf = promptexpand(lp ? *lp : NULL, 1, NULL, NULL, &pmpt_attr); raw_rp = rp; rpmpt_attr = pmpt_attr; rpromptbuf = promptexpand(rp ? *rp : NULL, 1, NULL, NULL, &rpmpt_attr); free_prepostdisplay(); zlereadflags = flags; zlecontext = context; histline = curhist; vistartchange = -1; zleline = (ZLE_STRING_T)zalloc(((linesz = 256) + 2) * ZLE_CHAR_SIZE); *zleline = ZWC('\0'); virangeflag = lastcmd = done = zlecs = zlell = mark = 0; vichgflag = 0; viinsbegin = 0; statusline = NULL; selectkeymap("main", 1); initundo(); fixsuffix(); if ((s = getlinknode(bufstack))) { setline(s, ZSL_TOEND); zsfree(s); if (stackcs != -1) { zlecs = stackcs; stackcs = -1; if (zlecs > zlell) zlecs = zlell; CCLEFT(); } if (stackhist != -1) { histline = stackhist; stackhist = -1; } handleundo(); } /* * If main is linked to the viins keymap, we need to register * explicitly that we're now in vi insert mode as there's * no user operation to indicate this. */ if (openkeymap("main") == openkeymap("viins")) viinsert_init(); selectlocalmap(NULL); if (isset(PROMPTCR)) putc('\r', shout); if (tmout) alarm(tmout); /* * On some windowing systems we may enter this function before the * terminal is fully opened and sized, resulting in an infinite * series of SIGWINCH when the handler prints the prompt before we * have done so here. Therefore, hold any such signal until the * first full refresh has completed. The important bit is that the * handler must not see zleactive = 1 until ZLE really is active. * See the end of adjustwinsize() in Src/utils.c */ queue_signals(); zleactive = 1; resetneeded = 1; /* * Start of the main zle read. * Fully reset error conditions, including user interrupt. */ errflag = retflag = 0; lastcol = -1; initmodifier(&zmod); prefixflag = 0; zrefresh(); unqueue_signals(); /* Should now be safe to acknowledge SIGWINCH */ zlecallhook(init, NULL); if ((bracket = getaparam("zle_bracketed_paste")) && arrlen(bracket) == 2) fputs(*bracket, shout); zrefresh(); zlecore(); if (errflag) setsparam((zlecontext == ZLCON_VARED) ? "ZLE_VARED_ABORTED" : "ZLE_LINE_ABORTED", zlegetline(NULL, NULL)); if ((bracket = getaparam("zle_bracketed_paste")) && arrlen(bracket) == 2) fputs(bracket[1], shout); if (done && !exit_pending && !errflag) zlecallhook(finish, NULL); statusline = NULL; invalidatelist(); trashzle(); free(lpromptbuf); free(rpromptbuf); zleactive = zlereadflags = lastlistlen = zlecontext = 0; alarm(0); freeundo(); if (eofsent || errflag || exit_pending) { s = NULL; } else { zleline[zlell++] = ZWC('\n'); s = zlegetline(NULL, NULL); } free(zleline); zleline = NULL; forget_edits(); errno = old_errno; /* highlight no longer valid */ set_region_highlight(NULL, NULL); return s; }
void zlecore(void) { Keymap km; #if !defined(HAVE_POLL) && defined(HAVE_SELECT) struct timeval tv; fd_set foofd; FD_ZERO(&foofd); #endif pushheap(); /* * A widget function may decide to exit the shell. * We never exit directly from functions, to allow * the shell to tidy up, so we have to test for * that explicitly. */ while (!done && !errflag && !exit_pending) { UNMETACHECK(); statusline = NULL; vilinerange = 0; reselectkeymap(); selectlocalmap(invicmdmode() && region_active && (km = openkeymap("visual")) ? km : NULL); bindk = getkeycmd(); selectlocalmap(NULL); if (bindk) { if (!zlell && isfirstln && !(zlereadflags & ZLRF_IGNOREEOF) && lastchar == eofchar) { /* * Slight hack: this relies on getkeycmd returning * a value for the EOF character. However, * undefined-key is fine. That's necessary because * otherwise we can't distinguish this case from * a ^C. */ eofsent = 1; break; } if (execzlefunc(bindk, zlenoargs, 0)) { handlefeep(zlenoargs); if (eofsent) break; } handleprefixes(); /* for vi mode, make sure the cursor isn't somewhere illegal */ if (invicmdmode() && zlecs > findbol() && (zlecs == zlell || zleline[zlecs] == ZWC('\n'))) DECCS(); handleundo(); } else { errflag |= ERRFLAG_ERROR; break; } #ifdef HAVE_POLL if (baud && !(lastcmd & ZLE_MENUCMP)) { struct pollfd pfd; int to = cost * costmult / 1000; /* milliseconds */ if (to > 500) to = 500; pfd.fd = SHTTY; pfd.events = POLLIN; if (!kungetct && poll(&pfd, 1, to) <= 0) zrefresh(); } else #else # ifdef HAVE_SELECT if (baud && !(lastcmd & ZLE_MENUCMP)) { FD_SET(SHTTY, &foofd); tv.tv_sec = 0; if ((tv.tv_usec = cost * costmult) > 500000) tv.tv_usec = 500000; if (!kungetct && select(SHTTY+1, (SELECT_ARG_2_T) & foofd, NULL, NULL, &tv) <= 0) zrefresh(); } else # endif #endif if (!kungetct) zrefresh(); freeheap(); } region_active = 0; popheap(); }
static int getvirange(int wf) { int pos = zlecs, mpos = mark, ret = 0; int visual = region_active; /* movement command might set it */ int mult1 = zmult, hist1 = histline; Thingy k2; if (visual) { pos = mark; vilinerange = (visual == 2); region_active = 0; } else { virangeflag = 1; wordflag = wf; mark = -1; /* use operator-pending keymap if one exists */ Keymap km = openkeymap("viopp"); if (km) selectlocalmap(km); /* Now we need to execute the movement command, to see where it * * actually goes. virangeflag here indicates to the movement * * function that it should place the cursor at the end of the * * range, rather than where the cursor would actually go if it * * were executed normally. This makes a difference to some * * commands, but not all. For example, if searching forward * * for a character, under normal circumstances the cursor lands * * on the character. For a range, the range must include the * * character, so the cursor gets placed after the character if * * virangeflag is set. vi-match-bracket needs to change the * * value of virangeflag under some circumstances, meaning that * * we need to change the *starting* position. */ zmod.flags &= ~MOD_TMULT; do { vilinerange = 0; prefixflag = 0; if (!(k2 = getkeycmd()) || (k2->flags & DISABLED) || k2 == Th(z_sendbreak)) { wordflag = 0; virangeflag = 0; mark = mpos; return -1; } /* * With k2 == bindk, the command key is repeated: * a number of lines is used. If the function used * returns 1, we fail. */ if ((k2 == bindk) ? dovilinerange() : execzlefunc(k2, zlenoargs, 1)) ret = -1; if(vichgrepeat) zmult = mult1; else zmult = mult1 * zmod.tmult; } while(prefixflag && !ret); wordflag = 0; selectlocalmap(NULL); /* It is an error to use a non-movement command to delimit the * * range. We here reject the case where the command modified * * the line, or selected a different history line. */ if (histline != hist1 || zlell != lastll || memcmp(zleline, lastline, zlell)) { histline = hist1; ZS_memcpy(zleline, lastline, zlell = lastll); zlecs = pos; mark = mpos; return -1; } /* Can't handle an empty file. Also, if the movement command * * failed, or didn't move, it is an error. */ if (!zlell || (zlecs == pos && mark == -1 && virangeflag != 2) || ret == -1) { mark = mpos; return -1; } /* vi-match-bracket changes the value of virangeflag when * * moving to the opening bracket, meaning that we need to * * change the *starting* position. */ if (virangeflag == -1) INCPOS(pos); virangeflag = 0; /* if the mark has moved, ignore the original cursor position * * and use the mark. */ if (mark != -1) pos = mark; } mark = mpos; /* Get the range the right way round. zlecs is placed at the * * start of the range, and pos (the return value of this * * function) is the end. */ if (zlecs > pos) { int tmp = zlecs; zlecs = pos; pos = tmp; } /* visual selection mode needs to include additional position */ if (visual == 1 && invicmdmode()) INCPOS(pos); /* Was it a line-oriented move? If so, the command will have set * * the vilinerange flag. In this case, entire lines are taken, * * rather than just the sequence of characters delimited by pos * * and zlecs. The terminating newline is left out of the range, * * which the real command must deal with appropriately. At this * * point we just need to make the range encompass entire lines. */ if(vilinerange) { int newcs = findbol(); lastcol = zlecs - newcs; zlecs = pos; pos = findeol(); zlecs = newcs; } return pos; }
int boot_(Module m) { char* dummy = NULL; // Initialize the trace module and set appropriate severity rift_init_trace(); recv_buf = (uint8_t*)calloc(sizeof(uint8_t), RW_CLI_MAX_BUF); recv_buf_len = RW_CLI_MAX_BUF; // Decide the RW.CLI communication mode with RW.MgmtAgent if (rift_cmdargs.use_netconf == -1) { const char* agent_mode = rw_getenv("RWMGMT_AGENT_MODE"); if (agent_mode && strcmp(agent_mode, "XML") == 0) { // If the agent mode is XML only RW.MSG mode is possible. Override the // command line option for netconf and opt for RW.MSG mode. rift_cmdargs.use_netconf = 0; } else { // Transport mode not chosen in command line and not XML mode. Choose // Netconf mode by default. rift_cmdargs.use_netconf = 1; } } // Authenticate in case of RW.MSG mode rwcli_transport_mode_t transport_mode = RWCLI_TRANSPORT_MODE_NETCONF; rwcli_user_mode_t user_mode = RWCLI_USER_MODE_NONE; if (!rift_cmdargs.use_netconf) { user_mode = rift_authenticate(&rift_cmdargs); if (user_mode == RWCLI_USER_MODE_INVALID) { printf("\nERROR: Invalid username/password\n"); exit(-1); } transport_mode = RWCLI_TRANSPORT_MODE_RWMSG; } rwcli_zsh_plugin_init(transport_mode, user_mode); rwcli_set_messaging_hook(messaging_hook); rwcli_set_history_hook(history_hook); // To support background processes and job control, there should // be multiple channels available msg_channel_init(&rwcli_agent_ch); msg_channel_create(&rwcli_agent_ch); // Always load the rwmsg_agent module, If netconf is enabled then // this module will only receive logging notifications if (load_module("zsh/rwmsg_agent", NULL, 0) != 0) { printf("\nCRITICAL: Loading the messaging agent module failed\n"); fflush(stdout); return -1; } // Load the agent that is required if (rift_cmdargs.use_netconf) { if (load_module("zsh/rwnetconf_agent", NULL, 0) != 0) { printf("\nCRITICAL: Loading the netconf agent module failed\n"); fflush(stdout); return -1; } } /* Register the completion widget */ w_comp = addzlefunction("rift-complete", rift_complete, 0); Keymap km = openkeymap("main"); t_orig_tab_bind = keybind(km, "\t", &dummy); bindkey(km, "\t", refthingy(w_comp->first), NULL); /* Bind ? to generate help */ w_gen_help = addzlefunction("rift-gen-help", rift_generate_help, 0); bindkey(km, "?", refthingy(w_gen_help->first), NULL); /* Set the lookup hook */ rw_lookup_fn = rift_lookup; /* Set the prompt hook */ addprepromptfn(rift_prompt); return 0; }