From nobody Thu May 15 07:07:38 2025 Delivered-To: importer@patchew.org Received-SPF: pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) client-ip=209.132.183.28; envelope-from=libvir-list-bounces@redhat.com; helo=mx1.redhat.com; Authentication-Results: mx.zohomail.com; spf=pass (zoho.com: domain of redhat.com designates 209.132.183.28 as permitted sender) smtp.mailfrom=libvir-list-bounces@redhat.com Return-Path: Received: from mx1.redhat.com (mx1.redhat.com [209.132.183.28]) by mx.zohomail.com with SMTPS id 1514913167037884.0659719835537; Tue, 2 Jan 2018 09:12:47 -0800 (PST) Received: from smtp.corp.redhat.com (int-mx05.intmail.prod.int.phx2.redhat.com [10.5.11.15]) (using TLSv1.2 with cipher AECDH-AES256-SHA (256/256 bits)) (No client certificate requested) by mx1.redhat.com (Postfix) with ESMTPS id C2D67C0270A6; Tue, 2 Jan 2018 17:12:45 +0000 (UTC) Received: from colo-mx.corp.redhat.com (colo-mx01.intmail.prod.int.phx2.redhat.com [10.5.11.20]) by smtp.corp.redhat.com (Postfix) with ESMTPS id 91A8D5D756; Tue, 2 Jan 2018 17:12:45 +0000 (UTC) Received: from lists01.pubmisc.prod.ext.phx2.redhat.com (lists01.pubmisc.prod.ext.phx2.redhat.com [10.5.19.33]) by colo-mx.corp.redhat.com (Postfix) with ESMTP id 505051802125; Tue, 2 Jan 2018 17:12:45 +0000 (UTC) Received: from smtp.corp.redhat.com (int-mx06.intmail.prod.int.phx2.redhat.com [10.5.11.16]) by lists01.pubmisc.prod.ext.phx2.redhat.com (8.13.8/8.13.8) with ESMTP id w02HCec1003171 for ; Tue, 2 Jan 2018 12:12:40 -0500 Received: by smtp.corp.redhat.com (Postfix) id DC7B35C3F8; Tue, 2 Jan 2018 17:12:40 +0000 (UTC) Received: from localhost.localdomain (ovpn-204-45.brq.redhat.com [10.40.204.45]) by smtp.corp.redhat.com (Postfix) with ESMTP id 4E96C5C899 for ; Tue, 2 Jan 2018 17:12:37 +0000 (UTC) From: Michal Privoznik To: libvir-list@redhat.com Date: Tue, 2 Jan 2018 18:12:04 +0100 Message-Id: <9e99d6e9069a3c318aca924d9e2580f81839abc1.1514911024.git.mprivozn@redhat.com> In-Reply-To: References: In-Reply-To: References: X-Scanned-By: MIMEDefang 2.79 on 10.5.11.16 X-loop: libvir-list@redhat.com Subject: [libvirt] [PATCH 11/18] vsh: Call vshCmdOptDef completer X-BeenThere: libvir-list@redhat.com X-Mailman-Version: 2.1.12 Precedence: junk List-Id: Development discussions about the libvirt library & tools List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Sender: libvir-list-bounces@redhat.com Errors-To: libvir-list-bounces@redhat.com X-Scanned-By: MIMEDefang 2.79 on 10.5.11.15 X-Greylist: Sender IP whitelisted, not delayed by milter-greylist-4.5.16 (mx1.redhat.com [10.5.110.32]); Tue, 02 Jan 2018 17:12:46 +0000 (UTC) X-ZohoMail: RSF_0 Z_629925259 SPT_0 Content-Type: text/plain; charset="utf-8" Now that we have everything prepared we can call options' completer again. At the same time, pass partially parsed input to the completer callback - it will help the callbacks to narrow down the list of returned options based on user's input. For instance, if the completer is supposed to return list of interfaces depending on user input it may return just those interfaces defined for already specified domain. Of course, completers might ignore this parameter. Signed-off-by: Michal Privoznik --- tools/vsh.c | 51 +++++++++++++++++++++++++++++++++++++++++++++++++-- tools/vsh.h | 1 + 2 files changed, 50 insertions(+), 2 deletions(-) diff --git a/tools/vsh.c b/tools/vsh.c index f99d941d9..10a4ef69c 100644 --- a/tools/vsh.c +++ b/tools/vsh.c @@ -2705,6 +2705,36 @@ vshReadlineOptionsGenerator(const char *text, const = vshCmdDef *cmd) return ret; } =20 + +static const vshCmdOptDef * +vshReadlineCommandFindOpt(const vshCmd *partial, + const char *text) +{ + const vshCmd *tmp =3D partial; + + while (tmp && tmp->next) { + if (tmp->def =3D=3D tmp->next->def && + !tmp->next->opts) + break; + tmp =3D tmp->next; + } + + if (tmp && tmp->opts) { + const vshCmdOpt *opt =3D tmp->opts; + + while (opt) { + if (STREQ_NULLABLE(opt->data, text) || + STREQ_NULLABLE(opt->data, " ")) + return opt->def; + + opt =3D opt->next; + } + } + + return NULL; +} + + static char * vshReadlineParse(const char *text, int state) { @@ -2712,6 +2742,7 @@ vshReadlineParse(const char *text, int state) static char **list; static size_t list_index; const vshCmdDef *cmd =3D NULL; + const vshCmdOptDef *opt =3D NULL; char *ret =3D NULL; =20 if (!state) { @@ -2729,8 +2760,10 @@ vshReadlineParse(const char *text, int state) =20 VIR_FREE(buf); =20 - if (partial) + if (partial) { cmd =3D partial->def; + partial->skipChecks =3D true; + } =20 if (cmd && STREQ(cmd->name, text)) { /* Corner case - some commands share prefix (e.g. @@ -2742,13 +2775,26 @@ vshReadlineParse(const char *text, int state) */ cmd =3D NULL; } + + opt =3D vshReadlineCommandFindOpt(partial, text); } =20 if (!list) { if (!cmd) { list =3D vshReadlineCommandGenerator(text); } else { - list =3D vshReadlineOptionsGenerator(text, cmd); + if (!opt || opt->type !=3D VSH_OT_DATA) + list =3D vshReadlineOptionsGenerator(text, cmd); + + if (opt && opt->completer) { + char **completer_list =3D opt->completer(autoCompleteOpaqu= e, + partial, + opt->completer_flag= s); + if (virStringListMerge(&list, &completer_list) < 0) { + virStringListFree(completer_list); + goto cleanup; + } + } } } =20 @@ -2765,6 +2811,7 @@ vshReadlineParse(const char *text, int state) ret =3D virBufferContentAndReset(&buf); } =20 + cleanup: if (!ret) { vshCommandFree(partial); partial =3D NULL; diff --git a/tools/vsh.h b/tools/vsh.h index 51f8ef213..ae40fb4e8 100644 --- a/tools/vsh.h +++ b/tools/vsh.h @@ -124,6 +124,7 @@ typedef struct _vshCmdOptDef vshCmdOptDef; typedef struct _vshControl vshControl; =20 typedef char **(*vshCompleter)(vshControl *ctl, + const vshCmd *cmd, unsigned int flags); =20 /* --=20 2.13.6 -- libvir-list mailing list libvir-list@redhat.com https://www.redhat.com/mailman/listinfo/libvir-list