summaryrefslogtreecommitdiffstats
path: root/src/pacman/util.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/pacman/util.c')
-rw-r--r--src/pacman/util.c654
1 files changed, 499 insertions, 155 deletions
diff --git a/src/pacman/util.c b/src/pacman/util.c
index 53dbd637..e8c0a299 100644
--- a/src/pacman/util.c
+++ b/src/pacman/util.c
@@ -31,12 +31,14 @@
#include <stdint.h> /* intmax_t */
#include <string.h>
#include <errno.h>
-#include <fcntl.h>
#include <ctype.h>
#include <dirent.h>
#include <unistd.h>
#include <limits.h>
#include <wchar.h>
+#ifdef HAVE_TERMIOS_H
+#include <termios.h> /* tcflush */
+#endif
#include <alpm.h>
#include <alpm_list.h>
@@ -47,74 +49,121 @@
#include "callback.h"
-int trans_init(pmtransflag_t flags)
+int trans_init(alpm_transflag_t flags, int check_valid)
{
int ret;
+
+ check_syncdbs(0, check_valid);
+
if(config->print) {
- ret = alpm_trans_init(flags, NULL, NULL, NULL);
+ ret = alpm_trans_init(config->handle, flags, NULL, NULL, NULL);
} else {
- ret = alpm_trans_init(flags, cb_trans_evt, cb_trans_conv,
+ ret = alpm_trans_init(config->handle, flags, cb_trans_evt, cb_trans_conv,
cb_trans_progress);
}
if(ret == -1) {
- pm_fprintf(stderr, PM_LOG_ERROR, _("failed to init transaction (%s)\n"),
- alpm_strerrorlast());
- if(pm_errno == PM_ERR_HANDLE_LOCK) {
+ enum _alpm_errno_t err = alpm_errno(config->handle);
+ pm_fprintf(stderr, ALPM_LOG_ERROR, _("failed to init transaction (%s)\n"),
+ alpm_strerror(err));
+ if(err == ALPM_ERR_HANDLE_LOCK) {
fprintf(stderr, _(" if you're sure a package manager is not already\n"
- " running, you can remove %s\n"), alpm_option_get_lockfile());
- }
- else if(pm_errno == PM_ERR_DB_VERSION) {
- fprintf(stderr, _(" try running pacman-db-upgrade\n"));
+ " running, you can remove %s\n"),
+ alpm_option_get_lockfile(config->handle));
}
- return(-1);
+ return -1;
}
- return(0);
+ return 0;
}
int trans_release(void)
{
- if(alpm_trans_release() == -1) {
- pm_fprintf(stderr, PM_LOG_ERROR, _("failed to release transaction (%s)\n"),
- alpm_strerrorlast());
- return(-1);
+ if(alpm_trans_release(config->handle) == -1) {
+ pm_fprintf(stderr, ALPM_LOG_ERROR, _("failed to release transaction (%s)\n"),
+ alpm_strerror(alpm_errno(config->handle)));
+ return -1;
}
- return(0);
+ return 0;
}
int needs_root(void)
{
switch(config->op) {
case PM_OP_DATABASE:
- return(1);
+ return 1;
case PM_OP_UPGRADE:
case PM_OP_REMOVE:
- return(!config->print);
+ return !config->print;
case PM_OP_SYNC:
- return(config->op_s_clean || config->op_s_sync ||
+ return (config->op_s_clean || config->op_s_sync ||
(!config->group && !config->op_s_info && !config->op_q_list &&
!config->op_s_search && !config->print));
default:
- return(0);
+ return 0;
+ }
+}
+
+int check_syncdbs(size_t need_repos, int check_valid)
+{
+ int ret = 0;
+ alpm_list_t *i;
+ alpm_list_t *sync_dbs = alpm_option_get_syncdbs(config->handle);
+
+ if(need_repos && sync_dbs == NULL) {
+ pm_printf(ALPM_LOG_ERROR, _("no usable package repositories configured.\n"));
+ return 1;
+ }
+
+ if(check_valid) {
+ /* ensure all known dbs are valid */
+ for(i = sync_dbs; i; i = alpm_list_next(i)) {
+ alpm_db_t *db = i->data;
+ if(alpm_db_get_valid(db)) {
+ pm_printf(ALPM_LOG_ERROR, _("database '%s' is not valid (%s)\n"),
+ alpm_db_get_name(db), alpm_strerror(alpm_errno(config->handle)));
+ ret = 1;
+ }
+ }
+ }
+ return ret;
+}
+
+/* discard unhandled input on the terminal's input buffer */
+static int flush_term_input(void) {
+#ifdef HAVE_TCFLUSH
+ if(isatty(fileno(stdin))) {
+ return tcflush(fileno(stdin), TCIFLUSH);
}
+#endif
+
+ /* fail silently */
+ return 0;
}
/* gets the current screen column width */
-int getcols(int def)
+int getcols()
{
+ int termwidth = -1;
+ const int default_tty = 80;
+ const int default_notty = 0;
+
+ if(!isatty(fileno(stdout))) {
+ return default_notty;
+ }
+
#ifdef TIOCGSIZE
struct ttysize win;
if(ioctl(1, TIOCGSIZE, &win) == 0) {
- return win.ts_cols;
+ termwidth = win.ts_cols;
}
#elif defined(TIOCGWINSZ)
struct winsize win;
if(ioctl(1, TIOCGWINSZ, &win) == 0) {
- return win.ws_col;
+ termwidth = win.ws_col;
}
#endif
- return def;
+ return termwidth <= 0 ? default_tty : termwidth;
}
/* does the same thing as 'rm -rf' */
@@ -125,24 +174,24 @@ int rmrf(const char *path)
DIR *dirp;
if(!unlink(path)) {
- return(0);
+ return 0;
} else {
if(errno == ENOENT) {
- return(0);
+ return 0;
} else if(errno == EPERM) {
/* fallthrough */
} else if(errno == EISDIR) {
/* fallthrough */
} else if(errno == ENOTDIR) {
- return(1);
+ return 1;
} else {
/* not a directory */
- return(1);
+ return 1;
}
dirp = opendir(path);
if(!dirp) {
- return(1);
+ return 1;
}
for(dp = readdir(dirp); dp != NULL; dp = readdir(dirp)) {
if(dp->d_ino) {
@@ -157,7 +206,7 @@ int rmrf(const char *path)
if(rmdir(path)) {
errflag++;
}
- return(errflag);
+ return errflag;
}
}
@@ -170,9 +219,9 @@ const char *mbasename(const char *path)
{
const char *last = strrchr(path, '/');
if(last) {
- return(last + 1);
+ return last + 1;
}
- return(path);
+ return path;
}
/** Parse the dirname of a program from a path.
@@ -187,7 +236,7 @@ char *mdirname(const char *path)
/* null or empty path */
if(path == NULL || path == '\0') {
- return(strdup("."));
+ return strdup(".");
}
ret = strdup(path);
@@ -196,11 +245,11 @@ char *mdirname(const char *path)
if(last != NULL) {
/* we found a '/', so terminate our string */
*last = '\0';
- return(ret);
+ return ret;
}
/* no slash found */
free(ret);
- return(strdup("."));
+ return strdup(".");
}
/* output a string, but wrap words properly with a specified indentation
@@ -210,7 +259,7 @@ void indentprint(const char *str, int indent)
wchar_t *wcstr;
const wchar_t *p;
int len, cidx;
- const int cols = getcols(0);
+ const int cols = getcols();
if(!str) {
return;
@@ -286,7 +335,7 @@ char *strtrim(char *str)
if(str == NULL || *str == '\0') {
/* string is empty, so we're done. */
- return(str);
+ return str;
}
while(isspace((unsigned char)*pch)) {
@@ -298,7 +347,7 @@ char *strtrim(char *str)
/* check if there wasn't anything but whitespace in the string. */
if(*str == '\0') {
- return(str);
+ return str;
}
pch = (str + (strlen(str) - 1));
@@ -307,7 +356,7 @@ char *strtrim(char *str)
}
*++pch = '\0';
- return(str);
+ return str;
}
/* Replace all occurances of 'needle' with 'replace' in 'str', returning
@@ -321,7 +370,7 @@ char *strreplace(const char *str, const char *needle, const char *replace)
size_t newsz;
if(!str) {
- return(NULL);
+ return NULL;
}
p = str;
@@ -334,28 +383,27 @@ char *strreplace(const char *str, const char *needle, const char *replace)
/* no occurences of needle found */
if(!list) {
- return(strdup(str));
+ return strdup(str);
}
/* size of new string = size of old string + "number of occurences of needle"
* x "size difference between replace and needle" */
newsz = strlen(str) + 1 +
alpm_list_count(list) * (replacesz - needlesz);
- newstr = malloc(newsz);
+ newstr = calloc(newsz, sizeof(char));
if(!newstr) {
- return(NULL);
+ return NULL;
}
- *newstr = '\0';
p = str;
newp = newstr;
for(i = list; i; i = alpm_list_next(i)) {
q = alpm_list_getdata(i);
- if(q > p){
+ if(q > p) {
/* add chars between this occurence and last occurence, if any */
- strncpy(newp, p, (size_t)(q - p));
+ memcpy(newp, p, (size_t)(q - p));
newp += q - p;
}
- strncpy(newp, replace, replacesz);
+ memcpy(newp, replace, replacesz);
newp += replacesz;
p = q + needlesz;
}
@@ -364,11 +412,9 @@ char *strreplace(const char *str, const char *needle, const char *replace)
if(*p) {
/* add the rest of 'p' */
strcpy(newp, p);
- newp += strlen(p);
}
- *newp = '\0';
- return(newstr);
+ return newstr;
}
/** Splits a string into a list of strings using the chosen character as
@@ -388,7 +434,7 @@ alpm_list_t *strsplit(const char *str, const char splitchar)
while((str = strchr(str, splitchar))) {
dup = strndup(prev, (size_t)(str - prev));
if(dup == NULL) {
- return(NULL);
+ return NULL;
}
list = alpm_list_add(list, dup);
@@ -398,11 +444,11 @@ alpm_list_t *strsplit(const char *str, const char splitchar)
dup = strdup(prev);
if(dup == NULL) {
- return(NULL);
+ return NULL;
}
list = alpm_list_add(list, dup);
- return(list);
+ return list;
}
static int string_length(const char *s)
@@ -411,7 +457,7 @@ static int string_length(const char *s)
wchar_t *wcstr;
if(!s) {
- return(0);
+ return 0;
}
/* len goes from # bytes -> # chars -> # cols */
len = strlen(s) + 1;
@@ -420,7 +466,7 @@ static int string_length(const char *s)
len = wcswidth(wcstr, len);
free(wcstr);
- return(len);
+ return len;
}
void string_display(const char *title, const char *string)
@@ -438,6 +484,117 @@ void string_display(const char *title, const char *string)
printf("\n");
}
+static void table_print_line(const alpm_list_t *line,
+ const alpm_list_t *formats)
+{
+ const alpm_list_t *curformat = formats;
+ const alpm_list_t *curcell = line;
+
+ while(curcell && curformat) {
+ printf(alpm_list_getdata(curformat), alpm_list_getdata(curcell));
+ curcell = alpm_list_next(curcell);
+ curformat = alpm_list_next(curformat);
+ }
+
+ printf("\n");
+}
+
+/* creates format strings by checking max cell lengths in cols */
+static alpm_list_t *table_create_format(const alpm_list_t *header,
+ const alpm_list_t *rows)
+{
+ alpm_list_t *longest_str, *longest_strs = NULL;
+ alpm_list_t *formats = NULL;
+ const alpm_list_t *i, *row, *cell;
+ char *str, *formatstr;
+ const int padding = 2;
+ int colwidth, totalwidth = 0;
+ int curcol = 0;
+
+ /* header determines column count and initial values of longest_strs */
+ for(i = header; i; i = alpm_list_next(i)) {
+ longest_strs = alpm_list_add(longest_strs, alpm_list_getdata(i));
+ }
+
+ /* now find the longest string in each column */
+ for(longest_str = longest_strs; longest_str;
+ longest_str = alpm_list_next(longest_str), curcol++) {
+ for(i = rows; i; i = alpm_list_next(i)) {
+ row = alpm_list_getdata(i);
+ cell = alpm_list_nth(row, curcol);
+ str = alpm_list_getdata(cell);
+
+ if(strlen(str) > strlen(alpm_list_getdata(longest_str))) {
+ longest_str->data = str;
+ }
+ }
+ }
+
+ /* now use the column width info to generate format strings */
+ for(i = longest_strs; i; i = alpm_list_next(i)) {
+ const char *display;
+ colwidth = strlen(alpm_list_getdata(i)) + padding;
+ totalwidth += colwidth;
+
+ /* right align the last column for a cleaner table display */
+ display = (alpm_list_next(i) != NULL) ? "%%-%ds" : "%%%ds";
+ pm_asprintf(&formatstr, display, colwidth);
+
+ formats = alpm_list_add(formats, formatstr);
+ }
+
+ alpm_list_free(longest_strs);
+
+ /* return NULL if terminal is not wide enough */
+ if(totalwidth > getcols()) {
+ fprintf(stderr, _("insufficient columns available for table display\n"));
+ FREELIST(formats);
+ return NULL;
+ }
+
+ return formats;
+}
+
+/** Displays the list in table format
+ *
+ * @param title the tables title
+ * @param header the column headers. column count is determined by the nr
+ * of headers
+ * @param rows the rows to display as a list of lists of strings. the outer
+ * list represents the rows, the inner list the cells (= columns)
+ *
+ * @return -1 if not enough terminal cols available, else 0
+ */
+int table_display(const char *title, const alpm_list_t *header,
+ const alpm_list_t *rows)
+{
+ const alpm_list_t *i;
+ alpm_list_t *formats;
+
+ if(rows == NULL || header == NULL) {
+ return 0;
+ }
+
+ formats = table_create_format(header, rows);
+ if(formats == NULL) {
+ return -1;
+ }
+
+ if(title != NULL) {
+ printf("%s\n\n", title);
+ }
+
+ table_print_line(header, formats);
+ printf("\n");
+
+ for(i = rows; i; i = alpm_list_next(i)) {
+ table_print_line(alpm_list_getdata(i), formats);
+ }
+
+ FREELIST(formats);
+ return 0;
+}
+
void list_display(const char *title, const alpm_list_t *list)
{
const alpm_list_t *i;
@@ -451,13 +608,13 @@ void list_display(const char *title, const alpm_list_t *list)
if(!list) {
printf("%s\n", _("None"));
} else {
- const int maxcols = getcols(0);
+ const int maxcols = getcols();
int cols = len;
const char *str = alpm_list_getdata(list);
printf("%s", str);
cols += string_length(str);
for(i = alpm_list_next(list); i; i = alpm_list_next(i)) {
- const char *str = alpm_list_getdata(i);
+ str = alpm_list_getdata(i);
int s = string_length(str);
/* wrap only if we have enough usable column space */
if(maxcols > len && cols + s + 2 >= maxcols) {
@@ -467,7 +624,7 @@ void list_display(const char *title, const alpm_list_t *list)
for (j = 1; j <= len; j++) {
printf(" ");
}
- } else if (cols != len) {
+ } else if(cols != len) {
/* 2 spaces are added if this is not the first element on a line. */
printf(" ");
cols += 2;
@@ -481,7 +638,6 @@ void list_display(const char *title, const alpm_list_t *list)
void list_display_linebreak(const char *title, const alpm_list_t *list)
{
- const alpm_list_t *i;
int len = 0;
if(title) {
@@ -492,6 +648,7 @@ void list_display_linebreak(const char *title, const alpm_list_t *list)
if(!list) {
printf("%s\n", _("None"));
} else {
+ const alpm_list_t *i;
/* Print the first element */
indentprint((const char *) alpm_list_getdata(list), len);
printf("\n");
@@ -506,102 +663,283 @@ void list_display_linebreak(const char *title, const alpm_list_t *list)
}
}
}
+
+void signature_display(const char *title, alpm_sigresult_t *result)
+{
+ int len = 0;
+
+ if(title) {
+ len = string_length(title) + 1;
+ printf("%s ", title);
+ }
+ if(result->count == 0) {
+ printf(_("None"));
+ } else {
+ int i;
+ for(i = 0; i < result->count; i++) {
+ char sigline[PATH_MAX];
+ const char *status, *validity, *name;
+ /* Don't re-indent the first result */
+ if(i != 0) {
+ int j;
+ for(j = 1; j <= len; j++) {
+ printf(" ");
+ }
+ }
+ switch(result->status[i]) {
+ case ALPM_SIGSTATUS_VALID:
+ status = _("Valid");
+ break;
+ case ALPM_SIGSTATUS_KEY_EXPIRED:
+ status = _("Key expired");
+ break;
+ case ALPM_SIGSTATUS_SIG_EXPIRED:
+ status = _("Expired");
+ break;
+ case ALPM_SIGSTATUS_INVALID:
+ status = _("Invalid");
+ break;
+ case ALPM_SIGSTATUS_KEY_UNKNOWN:
+ status = _("Key unknown");
+ break;
+ default:
+ status = _("Signature error");
+ break;
+ }
+ switch(result->validity[i]) {
+ case ALPM_SIGVALIDITY_FULL:
+ validity = _("fully trusted");
+ break;
+ case ALPM_SIGVALIDITY_MARGINAL:
+ validity = _("marginal trusted");
+ break;
+ case ALPM_SIGVALIDITY_NEVER:
+ validity = _("never trusted");
+ break;
+ case ALPM_SIGVALIDITY_UNKNOWN:
+ default:
+ validity = _("unknown trust");
+ break;
+ }
+ name = result->uid[i] ? result->uid[i] : _("{Key Unknown}");
+ snprintf(sigline, PATH_MAX, _("%s, %s from \"%s\""),
+ status, validity, name);
+ indentprint(sigline, len);
+ printf("\n");
+ }
+ }
+}
+
+/* creates a header row for use with table_display */
+static alpm_list_t *create_verbose_header(int install)
+{
+ alpm_list_t *res = NULL;
+ char *str;
+
+ pm_asprintf(&str, "%s", _("Name"));
+ res = alpm_list_add(res, str);
+ pm_asprintf(&str, "%s", _("Old Version"));
+ res = alpm_list_add(res, str);
+ if(install) {
+ pm_asprintf(&str, "%s", _("New Version"));
+ res = alpm_list_add(res, str);
+ }
+ pm_asprintf(&str, "%s", _("Size"));
+ res = alpm_list_add(res, str);
+
+ return res;
+}
+
+/* returns package info as list of strings */
+static alpm_list_t *create_verbose_row(alpm_pkg_t *pkg, int install)
+{
+ char *str;
+ double size;
+ const char *label;
+ alpm_list_t *ret = NULL;
+ alpm_db_t *ldb = alpm_option_get_localdb(config->handle);
+
+ /* a row consists of the package name, */
+ pm_asprintf(&str, "%s", alpm_pkg_get_name(pkg));
+ ret = alpm_list_add(ret, str);
+
+ /* old and new versions */
+ if(install) {
+ alpm_pkg_t *oldpkg = alpm_db_get_pkg(ldb, alpm_pkg_get_name(pkg));
+ pm_asprintf(&str, "%s",
+ oldpkg != NULL ? alpm_pkg_get_version(oldpkg) : "");
+ ret = alpm_list_add(ret, str);
+ }
+
+ pm_asprintf(&str, "%s", alpm_pkg_get_version(pkg));
+ ret = alpm_list_add(ret, str);
+
+ /* and size */
+ size = humanize_size(alpm_pkg_get_size(pkg), 'M', 1, &label);
+ pm_asprintf(&str, "%.2f %s", size, label);
+ ret = alpm_list_add(ret, str);
+
+ return ret;
+}
+
/* prepare a list of pkgs to display */
void display_targets(const alpm_list_t *pkgs, int install)
{
char *str;
+ const char *title, *label;
+ double size;
const alpm_list_t *i;
- off_t isize = 0, dlsize = 0;
- double mbisize = 0.0, mbdlsize = 0.0;
- alpm_list_t *targets = NULL;
+ off_t isize = 0, rsize = 0, dlsize = 0;
+ alpm_list_t *j, *lp, *header = NULL, *targets = NULL;
+ alpm_db_t *db_local = alpm_option_get_localdb(config->handle);
if(!pkgs) {
return;
}
- printf("\n");
+ /* gather pkg infos */
for(i = pkgs; i; i = alpm_list_next(i)) {
- pmpkg_t *pkg = alpm_list_getdata(i);
+ alpm_pkg_t *pkg = alpm_list_getdata(i);
if(install) {
+ alpm_pkg_t *lpkg = alpm_db_get_pkg(db_local, alpm_pkg_get_name(pkg));
dlsize += alpm_pkg_download_size(pkg);
+ if(lpkg) {
+ /* add up size of all removed packages */
+ rsize += alpm_pkg_get_isize(lpkg);
+ }
}
isize += alpm_pkg_get_isize(pkg);
- /* print the package size with the output if ShowSize option set */
- if(config->showsize) {
- double mbsize = (double)alpm_pkg_get_size(pkg) / (1024.0 * 1024.0);
-
- pm_asprintf(&str, "%s-%s [%.2f MB]", alpm_pkg_get_name(pkg),
- alpm_pkg_get_version(pkg), mbsize);
+ if(config->verbosepkglists) {
+ targets = alpm_list_add(targets, create_verbose_row(pkg, install));
} else {
pm_asprintf(&str, "%s-%s", alpm_pkg_get_name(pkg),
alpm_pkg_get_version(pkg));
+ targets = alpm_list_add(targets, str);
}
- targets = alpm_list_add(targets, str);
}
- /* Convert byte sizes to MB */
- mbdlsize = (double)dlsize / (1024.0 * 1024.0);
- mbisize = (double)isize / (1024.0 * 1024.0);
+ /* print to screen */
+ title = install ? _("Targets (%d):") : _("Remove (%d):");
+ pm_asprintf(&str, title, alpm_list_count(pkgs));
- if(install) {
- pm_asprintf(&str, _("Targets (%d):"), alpm_list_count(targets));
- list_display(str, targets);
- free(str);
- printf("\n");
-
- printf(_("Total Download Size: %.2f MB\n"), mbdlsize);
- if(!(config->flags & PM_TRANS_FLAG_DOWNLOADONLY)) {
- printf(_("Total Installed Size: %.2f MB\n"), mbisize);
+ printf("\n");
+ if(config->verbosepkglists) {
+ header = create_verbose_header(install);
+ if(table_display(str, header, targets) != 0) {
+ config->verbosepkglists = 0;
+ display_targets(pkgs, install);
+ goto out;
}
} else {
- pm_asprintf(&str, _("Remove (%d):"), alpm_list_count(targets));
list_display(str, targets);
- free(str);
- printf("\n");
+ }
+ printf("\n");
- printf(_("Total Removed Size: %.2f MB\n"), mbisize);
+ if(install) {
+ size = humanize_size(dlsize, 'M', 1, &label);
+ printf(_("Total Download Size: %.2f %s\n"), size, label);
+ if(!(config->flags & ALPM_TRANS_FLAG_DOWNLOADONLY)) {
+ size = humanize_size(isize, 'M', 1, &label);
+ printf(_("Total Installed Size: %.2f %s\n"), size, label);
+ /* only show this net value if different from raw installed size */
+ if(rsize > 0) {
+ size = humanize_size(isize - rsize, 'M', 1, &label);
+ printf(_("Net Upgrade Size: %.2f %s\n"), size, label);
+ }
+ }
+ } else {
+ size = humanize_size(isize, 'M', 1, &label);
+ printf(_("Total Removed Size: %.2f %s\n"), size, label);
}
- FREELIST(targets);
+out:
+ /* cleanup */
+ if(config->verbosepkglists) {
+ /* targets is a list of lists of strings, free inner lists here */
+ for(j = targets; j; j = alpm_list_next(j)) {
+ lp = alpm_list_getdata(j);
+ FREELIST(lp);
+ }
+ alpm_list_free(targets);
+ FREELIST(header);
+ } else {
+ FREELIST(targets);
+ }
+ free(str);
}
-static off_t pkg_get_size(pmpkg_t *pkg)
+static off_t pkg_get_size(alpm_pkg_t *pkg)
{
switch(config->op) {
case PM_OP_SYNC:
- return(alpm_pkg_download_size(pkg));
+ return alpm_pkg_download_size(pkg);
case PM_OP_UPGRADE:
- return(alpm_pkg_get_size(pkg));
+ return alpm_pkg_get_size(pkg);
default:
- return(alpm_pkg_get_isize(pkg));
+ return alpm_pkg_get_isize(pkg);
}
}
-static char *pkg_get_location(pmpkg_t *pkg)
+static char *pkg_get_location(alpm_pkg_t *pkg)
{
- pmdb_t *db;
- const char *dburl;
- char *string;
+ alpm_list_t *servers;
+ char *string = NULL;
switch(config->op) {
case PM_OP_SYNC:
- db = alpm_pkg_get_db(pkg);
- dburl = alpm_db_get_url(db);
- if(dburl) {
- char *pkgurl = NULL;
- pm_asprintf(&pkgurl, "%s/%s", dburl, alpm_pkg_get_filename(pkg));
- return(pkgurl);
+ servers = alpm_db_get_servers(alpm_pkg_get_db(pkg));
+ if(servers) {
+ pm_asprintf(&string, "%s/%s", alpm_list_getdata(servers),
+ alpm_pkg_get_filename(pkg));
+ return string;
}
case PM_OP_UPGRADE:
- return(strdup(alpm_pkg_get_filename(pkg)));
+ return strdup(alpm_pkg_get_filename(pkg));
default:
- string = NULL;
pm_asprintf(&string, "%s-%s", alpm_pkg_get_name(pkg), alpm_pkg_get_version(pkg));
- return(string);
+ return string;
}
}
+/** Converts sizes in bytes into human readable units.
+ *
+ * @param bytes the size in bytes
+ * @param target_unit '\0' or a short label. If equal to one of the short unit
+ * labels ('B', 'K', ...) bytes is converted to target_unit; if '\0', the first
+ * unit which will bring the value to below a threshold of 2048 will be chosen.
+ * @param long_labels whether to use short ("K") or long ("KiB") unit labels
+ * @param label will be set to the appropriate unit label
+ *
+ * @return the size in the appropriate unit
+ */
+double humanize_size(off_t bytes, const char target_unit, int long_labels,
+ const char **label)
+{
+ static const char *shortlabels[] = {"B", "K", "M", "G", "T", "P"};
+ static const char *longlabels[] = {"B", "KiB", "MiB", "GiB", "TiB", "PiB"};
+ static const int unitcount = sizeof(shortlabels) / sizeof(shortlabels[0]);
+
+ const char **labels = long_labels ? longlabels : shortlabels;
+ double val = (double)bytes;
+ int index;
+
+ for(index = 0; index < unitcount - 1; index++) {
+ if(target_unit != '\0' && shortlabels[index][0] == target_unit) {
+ break;
+ } else if(target_unit == '\0' && val <= 2048.0 && val >= -2048.0) {
+ break;
+ }
+ val /= 1024.0;
+ }
+
+ if(label) {
+ *label = labels[index];
+ }
+
+ return val;
+}
+
void print_packages(const alpm_list_t *packages)
{
const alpm_list_t *i;
@@ -609,7 +947,7 @@ void print_packages(const alpm_list_t *packages)
config->print_format = strdup("%l");
}
for(i = packages; i; i = alpm_list_next(i)) {
- pmpkg_t *pkg = alpm_list_getdata(i);
+ alpm_pkg_t *pkg = alpm_list_getdata(i);
char *string = strdup(config->print_format);
char *temp = string;
/* %n : pkgname */
@@ -635,7 +973,7 @@ void print_packages(const alpm_list_t *packages)
/* %r : repo */
if(strstr(temp,"%r")) {
const char *repo = "local";
- pmdb_t *db = alpm_pkg_get_db(pkg);
+ alpm_db_t *db = alpm_pkg_get_db(pkg);
if(db) {
repo = alpm_db_get_name(db);
}
@@ -660,10 +998,10 @@ void print_packages(const alpm_list_t *packages)
* alpm "compare func" signature */
int str_cmp(const void *s1, const void *s2)
{
- return(strcmp(s1, s2));
+ return strcmp(s1, s2);
}
-void display_new_optdepends(pmpkg_t *oldpkg, pmpkg_t *newpkg)
+void display_new_optdepends(alpm_pkg_t *oldpkg, alpm_pkg_t *newpkg)
{
alpm_list_t *old = alpm_pkg_get_optdepends(oldpkg);
alpm_list_t *new = alpm_pkg_get_optdepends(newpkg);
@@ -675,7 +1013,7 @@ void display_new_optdepends(pmpkg_t *oldpkg, pmpkg_t *newpkg)
alpm_list_free(optdeps);
}
-void display_optdepends(pmpkg_t *pkg)
+void display_optdepends(alpm_pkg_t *pkg)
{
alpm_list_t *optdeps = alpm_pkg_get_optdepends(pkg);
if(optdeps) {
@@ -702,8 +1040,8 @@ void select_display(const alpm_list_t *pkglist)
const char *dbname = NULL;
for (i = pkglist; i; i = i->next) {
- pmpkg_t *pkg = alpm_list_getdata(i);
- pmdb_t *db = alpm_pkg_get_db(pkg);
+ alpm_pkg_t *pkg = alpm_list_getdata(i);
+ alpm_db_t *db = alpm_pkg_get_db(pkg);
if(!dbname)
dbname = alpm_db_get_name(db);
@@ -729,13 +1067,13 @@ static int parseindex(char *s, int *val, int min, int max)
if(n < min || n > max) {
fprintf(stderr, _("Invalid value: %d is not between %d and %d\n"),
n, min, max);
- return(-1);
+ return -1;
}
*val = n;
- return(0);
+ return 0;
} else {
fprintf(stderr, _("Invalid number: %s\n"), s);
- return(-1);
+ return -1;
}
}
@@ -749,7 +1087,7 @@ static int multiselect_parse(char *array, int count, char *response)
char *ends = NULL;
char *starts = strtok_r(str, " ", &saveptr);
- if (starts == NULL) {
+ if(starts == NULL) {
break;
}
strtrim(starts);
@@ -757,7 +1095,7 @@ static int multiselect_parse(char *array, int count, char *response)
if(len == 0)
continue;
- if (*starts == '^') {
+ if(*starts == '^') {
starts++;
len--;
include = 0;
@@ -776,14 +1114,14 @@ static int multiselect_parse(char *array, int count, char *response)
}
if(parseindex(starts, &start, 1, count) != 0)
- return(-1);
+ return -1;
if(!ends) {
array[start-1] = include;
} else {
int d;
if(parseindex(ends, &end, start, count) != 0) {
- return(-1);
+ return -1;
}
for(d = start; d <= end; d++) {
array[d-1] = include;
@@ -791,7 +1129,7 @@ static int multiselect_parse(char *array, int count, char *response)
}
}
- return(0);
+ return 0;
}
int multiselect_question(char *array, int count)
@@ -828,6 +1166,8 @@ int multiselect_question(char *array, int count)
break;
}
+ flush_term_input();
+
if(fgets(response, response_len, stdin)) {
const size_t response_incr = 64;
/* handle buffer not being large enough to read full line case */
@@ -861,7 +1201,7 @@ int multiselect_question(char *array, int count)
}
free(response);
- return(0);
+ return 0;
}
int select_question(int count)
@@ -887,19 +1227,21 @@ int select_question(int count)
break;
}
+ flush_term_input();
+
if(fgets(response, sizeof(response), stdin)) {
strtrim(response);
if(strlen(response) > 0) {
int n;
if(parseindex(response, &n, 1, count) != 0)
continue;
- return(n-1);
+ return (n - 1);
}
}
break;
}
- return(preset-1);
+ return (preset - 1);
}
@@ -930,23 +1272,25 @@ static int question(short preset, char *fmt, va_list args)
if(config->noconfirm) {
fprintf(stream, "\n");
- return(preset);
+ return preset;
}
fflush(stream);
+ flush_term_input();
+
if(fgets(response, sizeof(response), stdin)) {
strtrim(response);
if(strlen(response) == 0) {
- return(preset);
+ return preset;
}
if(strcasecmp(response, _("Y")) == 0 || strcasecmp(response, _("YES")) == 0) {
- return(1);
- } else if (strcasecmp(response, _("N")) == 0 || strcasecmp(response, _("NO")) == 0) {
- return(0);
+ return 1;
+ } else if(strcasecmp(response, _("N")) == 0 || strcasecmp(response, _("NO")) == 0) {
+ return 0;
}
}
- return(0);
+ return 0;
}
int yesno(char *fmt, ...)
@@ -958,7 +1302,7 @@ int yesno(char *fmt, ...)
ret = question(1, fmt, args);
va_end(args);
- return(ret);
+ return ret;
}
int noyes(char *fmt, ...)
@@ -970,10 +1314,10 @@ int noyes(char *fmt, ...)
ret = question(0, fmt, args);
va_end(args);
- return(ret);
+ return ret;
}
-int pm_printf(pmloglevel_t level, const char *format, ...)
+int pm_printf(alpm_loglevel_t level, const char *format, ...)
{
int ret;
va_list args;
@@ -983,10 +1327,10 @@ int pm_printf(pmloglevel_t level, const char *format, ...)
ret = pm_vfprintf(stdout, level, format, args);
va_end(args);
- return(ret);
+ return ret;
}
-int pm_fprintf(FILE *stream, pmloglevel_t level, const char *format, ...)
+int pm_fprintf(FILE *stream, alpm_loglevel_t level, const char *format, ...)
{
int ret;
va_list args;
@@ -996,7 +1340,7 @@ int pm_fprintf(FILE *stream, pmloglevel_t level, const char *format, ...)
ret = pm_vfprintf(stream, level, format, args);
va_end(args);
- return(ret);
+ return ret;
}
int pm_asprintf(char **string, const char *format, ...)
@@ -1007,15 +1351,15 @@ int pm_asprintf(char **string, const char *format, ...)
/* print the message using va_arg list */
va_start(args, format);
if(vasprintf(string, format, args) == -1) {
- pm_fprintf(stderr, PM_LOG_ERROR, _("failed to allocate string\n"));
+ pm_fprintf(stderr, ALPM_LOG_ERROR, _("failed to allocate string\n"));
ret = -1;
}
va_end(args);
- return(ret);
+ return ret;
}
-int pm_vasprintf(char **string, pmloglevel_t level, const char *format, va_list args)
+int pm_vasprintf(char **string, alpm_loglevel_t level, const char *format, va_list args)
{
int ret = 0;
char *msg = NULL;
@@ -1030,16 +1374,16 @@ int pm_vasprintf(char **string, pmloglevel_t level, const char *format, va_list
/* print a prefix to the message */
switch(level) {
- case PM_LOG_ERROR:
+ case ALPM_LOG_ERROR:
pm_asprintf(string, _("error: %s"), msg);
break;
- case PM_LOG_WARNING:
+ case ALPM_LOG_WARNING:
pm_asprintf(string, _("warning: %s"), msg);
break;
- case PM_LOG_DEBUG:
+ case ALPM_LOG_DEBUG:
pm_asprintf(string, "debug: %s", msg);
break;
- case PM_LOG_FUNCTION:
+ case ALPM_LOG_FUNCTION:
pm_asprintf(string, "function: %s", msg);
break;
default:
@@ -1048,10 +1392,10 @@ int pm_vasprintf(char **string, pmloglevel_t level, const char *format, va_list
}
free(msg);
- return(ret);
+ return ret;
}
-int pm_vfprintf(FILE *stream, pmloglevel_t level, const char *format, va_list args)
+int pm_vfprintf(FILE *stream, alpm_loglevel_t level, const char *format, va_list args)
{
int ret = 0;
@@ -1062,7 +1406,7 @@ int pm_vfprintf(FILE *stream, pmloglevel_t level, const char *format, va_list ar
#if defined(PACMAN_DEBUG)
/* If debug is on, we'll timestamp the output */
- if(config->logmask & PM_LOG_DEBUG) {
+ if(config->logmask & ALPM_LOG_DEBUG) {
time_t t;
struct tm *tmp;
char timestr[10] = {0};
@@ -1078,16 +1422,16 @@ int pm_vfprintf(FILE *stream, pmloglevel_t level, const char *format, va_list ar
/* print a prefix to the message */
switch(level) {
- case PM_LOG_ERROR:
+ case ALPM_LOG_ERROR:
fprintf(stream, _("error: "));
break;
- case PM_LOG_WARNING:
+ case ALPM_LOG_WARNING:
fprintf(stream, _("warning: "));
break;
- case PM_LOG_DEBUG:
+ case ALPM_LOG_DEBUG:
fprintf(stream, "debug: ");
break;
- case PM_LOG_FUNCTION:
+ case ALPM_LOG_FUNCTION:
fprintf(stream, "function: ");
break;
default:
@@ -1096,7 +1440,7 @@ int pm_vfprintf(FILE *stream, pmloglevel_t level, const char *format, va_list ar
/* print the message using va_arg list */
ret = vfprintf(stream, format, args);
- return(ret);
+ return ret;
}
#ifndef HAVE_STRNDUP
@@ -1105,7 +1449,7 @@ static size_t strnlen(const char *s, size_t max)
{
register const char *p;
for(p = s; *p && max--; ++p);
- return(p - s);
+ return (p - s);
}
char *strndup(const char *s, size_t n)
@@ -1113,11 +1457,11 @@ char *strndup(const char *s, size_t n)
size_t len = strnlen(s, n);
char *new = (char *) malloc(len + 1);
- if (new == NULL)
+ if(new == NULL)
return NULL;
new[len] = '\0';
- return (char *) memcpy(new, s, len);
+ return (char *)memcpy(new, s, len);
}
#endif