[pacman-dev] [PATCH] Support reading package args from stdin
Allan McRae
allan at archlinux.org
Thu Nov 4 15:42:54 CET 2010
On 05/11/10 00:20, Dave Reisner wrote:
> Only occurs if no arguments were provided directly. Arguments can be
> separated by any amount of valid whitespace. This allows for piping into
> pacman from other programs or from itself, e.g.:
>
> pacman -Qdtq | pacman -Rs
>
> This is better than using xargs, as xargs will not reconnect stdin to
> the terminal. The above operation performed using xargs would require
> the --noconfirm flag to be passed to pacman.
Dan: this sold the patch to me.
> Revised from the original 7/24 submission at Allan's request to check
> the return value of freopen().
FYI, comments like this can go below the "---" two lines down. That way
they do not get included in the actual git commit.
> Signed-off-by: Dave Reisner<d at falconindy.com>
> ---
> src/pacman/pacman.c | 27 +++++++++++++++++++++++++++
> 1 files changed, 27 insertions(+), 0 deletions(-)
>
> diff --git a/src/pacman/pacman.c b/src/pacman/pacman.c
> index 15abecc..6f40a97 100644
> --- a/src/pacman/pacman.c
> +++ b/src/pacman/pacman.c
> @@ -26,6 +26,7 @@
> #define PACKAGE_VERSION GIT_VERSION
> #endif
>
> +#include<ctype.h> /* isspace */
> #include<stdlib.h> /* atoi */
> #include<stdio.h>
> #include<limits.h>
> @@ -1305,6 +1306,32 @@ int main(int argc, char *argv[])
> cleanup(ret);
> }
>
> + /* read package arguments from stdin if we have none yet */
> + if(!pm_targets&& !isatty(0)) {
> + char line[BUFSIZ];
> + int i = 0;
> + while((line[i] = fgetc(stdin)) != EOF) {
> + if(isspace(line[i])) {
> + line[i] = 0;
> + /* avoid adding zero length arg when multiple spaces separate args */
> + if(i> 0) {
> + pm_targets = alpm_list_add(pm_targets, strdup(line));
> + i = 0;
> + }
> + } else {
> + ++i;
> + }
> + }
> + /* end of stream -- check for data still in line buffer */
> + if(i> 0) {
> + pm_targets = alpm_list_add(pm_targets, strdup(line));
> + }
> + if (!freopen(ctermid(NULL), "r", stdin)) {
Two things here. The HACKING file says to use if(foo() == 0) rather
than if(!foo()). But freopen returns a FILE*. So we really should be
checking if that == NULL? Also, does the FILE* that freopen returns
need closed here or is that fine as is? I get slight confused...
> + pm_printf(PM_LOG_ERROR, _("failed to reopen stdin for reading: (%s)\n"),
> + strerror(errno));
> + }
> + }
> +
> /* parse the config file */
> ret = parseconfig(config->configfile);
> if(ret != 0) {
More information about the pacman-dev
mailing list