/ libpkg / pkg.c
pkg.c
   1  /*-
   2   * Copyright (c) 2011-2025 Baptiste Daroussin <bapt@FreeBSD.org>
   3   * Copyright (c) 2011-2012 Julien Laffaye <jlaffaye@FreeBSD.org>
   4   * Copyright (c) 2012 Bryan Drewery <bryan@shatow.net>
   5   * Copyright (c) 2013 Matthew Seaman <matthew@FreeBSD.org>
   6   * Copyright (c) 2017 Vsevolod Stakhov <vsevolod@FreeBSD.org>
   7   * Copyright (c) 2023, Serenity Cyber Security, LLC
   8   *                     Author: Gleb Popov <arrowd@FreeBSD.org>
   9   *
  10   * SPDX-License-Identifier: BSD-2-Clause
  11   */
  12  
  13  #include <archive.h>
  14  #include <archive_entry.h>
  15  #include <assert.h>
  16  #include <errno.h>
  17  #include <fcntl.h>
  18  #include <string.h>
  19  #include <pwd.h>
  20  #include <grp.h>
  21  
  22  #include "pkg.h"
  23  #include "private/event.h"
  24  #include "private/pkg.h"
  25  #include "private/pkgdb.h"
  26  #include "private/utils.h"
  27  #include "xmalloc.h"
  28  
  29  #define dbg(x, ...) pkg_dbg(PKG_DBG_PACKAGE, x, __VA_ARGS__)
  30  
  31  int
  32  pkg_new(struct pkg **pkg, pkg_t type)
  33  {
  34  	*pkg = xcalloc(1, sizeof(struct pkg));
  35  	(*pkg)->type = type;
  36  	(*pkg)->rootfd = -1;
  37  	(*pkg)->list_sorted = false;
  38  
  39  	return (EPKG_OK);
  40  }
  41  
  42  static void
  43  pkg_message_free(struct pkg_message *m)
  44  {
  45  	free(m->str);
  46  	free(m->maximum_version);
  47  	free(m->minimum_version);
  48  	free(m);
  49  }
  50  
  51  void
  52  pkg_free(struct pkg *pkg)
  53  {
  54  	if (pkg == NULL)
  55  		return;
  56  
  57  	free(pkg->name);
  58  	free(pkg->origin);
  59  	free(pkg->old_version);
  60  	free(pkg->version);
  61  	free(pkg->maintainer);
  62  	free(pkg->www);
  63  	free(pkg->altabi);
  64  	free(pkg->abi);
  65  	free(pkg->uid);
  66  	free(pkg->digest);
  67  	free(pkg->old_digest);
  68  	free(pkg->prefix);
  69  	free(pkg->oprefix);
  70  	free(pkg->comment);
  71  	free(pkg->desc);
  72  	free(pkg->sum);
  73  	free(pkg->repopath);
  74  	free(pkg->reponame);
  75  	free(pkg->repourl);
  76  	free(pkg->reason);
  77  	free(pkg->dep_formula);
  78  	free(pkg->rootpath);
  79  
  80  	for (int i = 0; i < PKG_NUM_SCRIPTS; i++)
  81  		xstring_free(pkg->scripts[i]);
  82  	for (int i = 0; i < PKG_NUM_LUA_SCRIPTS; i++)
  83  		vec_free_and_free(&pkg->lua_scripts[i], free);
  84  
  85  	pkg_list_free(pkg, PKG_DEPS);
  86  	pkg_list_free(pkg, PKG_RDEPS);
  87  	pkg_list_free(pkg, PKG_FILES);
  88  	pkg_list_free(pkg, PKG_DIRS);
  89  	pkg_list_free(pkg, PKG_OPTIONS);
  90  	pkg_list_free(pkg, PKG_CONFIG_FILES);
  91  
  92  	vec_free_and_free(&pkg->users, free);
  93  	pkg->flags &= ~PKG_LOAD_USERS;
  94  	vec_free_and_free(&pkg->groups, free);
  95  	pkg->flags &= ~PKG_LOAD_GROUPS;
  96  	vec_free_and_free(&pkg->shlibs_required, free);
  97  	pkg->flags &= ~PKG_LOAD_SHLIBS_REQUIRED;
  98  	vec_free_and_free(&pkg->shlibs_required_ignore, free);
  99  	pkg->flags &= ~PKG_LOAD_SHLIBS_REQUIRED_IGNORE;
 100  	vec_free_and_free(&pkg->shlibs_provided, free);
 101  	pkg->flags &= ~PKG_LOAD_SHLIBS_PROVIDED;
 102  	vec_free_and_free(&pkg->shlibs_provided_ignore, free);
 103  	pkg->flags &= ~PKG_LOAD_SHLIBS_PROVIDED_IGNORE;
 104  	vec_free_and_free(&pkg->provides, free);
 105  	pkg->flags &= ~PKG_LOAD_PROVIDES;
 106  	vec_free_and_free(&pkg->requires, free);
 107  	pkg->flags &= ~PKG_LOAD_REQUIRES;
 108  	vec_free_and_free(&pkg->categories, free);
 109  	pkg->flags &= ~PKG_LOAD_CATEGORIES;
 110  	vec_free_and_free(&pkg->licenses, free);
 111  	pkg->flags &= ~PKG_LOAD_LICENSES;
 112  
 113  	vec_free_and_free(&pkg->message, pkg_message_free);
 114  	vec_free_and_free(&pkg->annotations, pkg_kv_free);
 115  
 116  	vec_free_and_free(&pkg->dir_to_del, free);
 117  
 118  	if (pkg->rootfd != -1)
 119  		close(pkg->rootfd);
 120  
 121  	free(pkg);
 122  }
 123  
 124  pkg_t
 125  pkg_type(const struct pkg * restrict pkg)
 126  {
 127  	assert(pkg != NULL);
 128  
 129  	return (pkg->type);
 130  }
 131  
 132  int
 133  pkg_is_valid(const struct pkg * restrict pkg)
 134  {
 135  	if (pkg == NULL) {
 136  		pkg_emit_error("Invalid package: not allocated");
 137  		return (EPKG_FATAL);
 138  	}
 139  
 140  	if (pkg->origin == NULL) {
 141  		pkg_emit_error("Invalid package: object has missing property origin");
 142  		return (EPKG_FATAL);
 143  	}
 144  
 145  	if (pkg->name == NULL) {
 146  		pkg_emit_error("Invalid package: object has missing property name");
 147  		return (EPKG_FATAL);
 148  	}
 149  
 150  	if (pkg->comment == NULL) {
 151  		pkg_emit_error("Invalid package: object has missing property comment");
 152  		return (EPKG_FATAL);
 153  	}
 154  
 155  	if (pkg->version == NULL) {
 156  		pkg_emit_error("Invalid package: object has missing property version");
 157  		return (EPKG_FATAL);
 158  	}
 159  
 160  	if (pkg->desc == NULL) {
 161  		pkg_emit_error("Invalid package: object has missing property desc");
 162  		return (EPKG_FATAL);
 163  	}
 164  
 165  	if (pkg->maintainer == NULL) {
 166  		pkg_emit_error("Invalid package: object has missing property maintainer");
 167  		return (EPKG_FATAL);
 168  	}
 169  
 170  	if (pkg->www == NULL) {
 171  		pkg_emit_error("Invalid package: object has missing property www");
 172  		return (EPKG_FATAL);
 173  	}
 174  
 175  	if (pkg->prefix == NULL) {
 176  		pkg_emit_error("Invalid package: object has missing property prefix");
 177  		return (EPKG_FATAL);
 178  	}
 179  
 180  	return (EPKG_OK);
 181  }
 182  
 183  int
 184  pkg_set_i(struct pkg *pkg, pkg_attr attr, int64_t val)
 185  {
 186  	switch (attr) {
 187  	case PKG_ATTR_FLATSIZE:
 188  		pkg->flatsize = val;
 189  		break;
 190  	case PKG_ATTR_OLD_FLATSIZE:
 191  		pkg->old_flatsize = val;
 192  		break;
 193  	case PKG_ATTR_PKGSIZE:
 194  		pkg->pkgsize = val;
 195  		break;
 196  	case PKG_ATTR_TIME:
 197  		pkg->timestamp = val;
 198  		break;
 199  	default:
 200  		pkg_emit_error("%d does not accept int64_t values", attr);
 201  		return (EPKG_FATAL);
 202  	}
 203  	return (EPKG_OK);
 204  }
 205  
 206  int
 207  pkg_set_b(struct pkg *pkg, pkg_attr attr, bool boolean)
 208  {
 209  	switch (attr) {
 210  	case PKG_ATTR_AUTOMATIC:
 211  		pkg->automatic = boolean;
 212  		break;
 213  	case PKG_ATTR_LOCKED:
 214  		pkg->locked = boolean;
 215  		break;
 216  	case PKG_ATTR_VITAL:
 217  		pkg->vital = boolean;
 218  		break;
 219  	default:
 220  		pkg_emit_error("%d does not accept bool values", attr);
 221  		return (EPKG_FATAL);
 222  	}
 223  	return (EPKG_OK);
 224  }
 225  
 226  int
 227  pkg_set_s(struct pkg *pkg, pkg_attr attr, const char *str)
 228  {
 229  	char *endptr;
 230  	ucl_object_t *obj;
 231  	int64_t i;
 232  
 233  	switch (attr) {
 234  	case PKG_ATTR_NAME:
 235  		free(pkg->name);
 236  		pkg->name = xstrdup(str);
 237  		free(pkg->uid);
 238  		pkg->uid = xstrdup(str);
 239  		break;
 240  	case PKG_ATTR_ORIGIN:
 241  		free(pkg->origin);
 242  		pkg->origin = xstrdup(str);
 243  		break;
 244  	case PKG_ATTR_VERSION:
 245  		free(pkg->version);
 246  		pkg->version = xstrdup(str);
 247  		break;
 248  	case PKG_ATTR_DESC:
 249  		free(pkg->desc);
 250  		pkg->desc = xstrdup(str);
 251  		break;
 252  	case PKG_ATTR_COMMENT:
 253  		free(pkg->comment);
 254  		pkg->comment = xstrdup(str);
 255  		break;
 256  	case PKG_ATTR_MESSAGE:
 257  		vec_free_and_free(&pkg->message, pkg_message_free);
 258  		if (*str == '[') {
 259  			pkg_message_from_str(pkg, str, strlen(str));
 260  		} else {
 261  			obj = ucl_object_fromstring_common(str, strlen(str),
 262  			    UCL_STRING_RAW|UCL_STRING_TRIM);
 263  			pkg_message_from_ucl(pkg, obj);
 264  			ucl_object_unref(obj);
 265  		}
 266  		break;
 267  	case PKG_ATTR_ARCH:
 268  		free(pkg->altabi);
 269  		pkg->altabi = xstrdup(str);
 270  		break;
 271  	case PKG_ATTR_ABI:
 272  		free(pkg->abi);
 273  		pkg->abi = xstrdup(str);
 274  		break;
 275  	case PKG_ATTR_MAINTAINER:
 276  		free(pkg->maintainer);
 277  		pkg->maintainer = xstrdup(str);
 278  		break;
 279  	case PKG_ATTR_WWW:
 280  		free(pkg->www);
 281  		pkg->www = xstrdup(str);
 282  		break;
 283  	case PKG_ATTR_PREFIX:
 284  		free(pkg->prefix);
 285  		pkg->prefix = xstrdup(str);
 286  		break;
 287  	case PKG_ATTR_REPOPATH:
 288  		free(pkg->repopath);
 289  		pkg->repopath = xstrdup(str);
 290  		break;
 291  	case PKG_ATTR_CKSUM:
 292  		free(pkg->sum);
 293  		pkg->sum = xstrdup(str);
 294  		break;
 295  	case PKG_ATTR_OLD_VERSION:
 296  		free(pkg->old_version);
 297  		pkg->old_version = xstrdup(str);
 298  		break;
 299  	case PKG_ATTR_REPONAME:
 300  		free(pkg->reponame);
 301  		pkg->reponame = xstrdup(str);
 302  		break;
 303  	case PKG_ATTR_REPOURL:
 304  		free(pkg->repourl);
 305  		pkg->repourl = xstrdup(str);
 306  		break;
 307  	case PKG_ATTR_DIGEST:
 308  		free(pkg->digest);
 309  		pkg->digest = xstrdup(str);
 310  		break;
 311  	case PKG_ATTR_REASON:
 312  		free(pkg->reason);
 313  		pkg->reason = xstrdup(str);
 314  		break;
 315  	case PKG_ATTR_DEP_FORMULA:
 316  		free(pkg->dep_formula);
 317  		pkg->dep_formula = xstrdup(str);
 318  		break;
 319  	case PKG_ATTR_FLATSIZE:
 320  		i = strtoimax(str, &endptr, 10);
 321  		if (endptr != NULL) {
 322  			pkg_emit_error("Unable to convert '%s' to int64_t",
 323  			    str);
 324  			return (EPKG_FATAL);
 325  		}
 326  		pkg->flatsize = i;
 327  		break;
 328  	case PKG_ATTR_OLD_FLATSIZE:
 329  		i = strtoimax(str, &endptr, 10);
 330  		if (endptr != NULL) {
 331  			pkg_emit_error("Unable to convert '%s' to int64_t",
 332  			    str);
 333  			return (EPKG_FATAL);
 334  		}
 335  		pkg->old_flatsize = i;
 336  		break;
 337  	case PKG_ATTR_PKGSIZE:
 338  		i = strtoimax(str, &endptr, 10);
 339  		if (endptr != NULL) {
 340  			pkg_emit_error("Unable to convert '%s' to int64_t",
 341  			    str);
 342  			return (EPKG_FATAL);
 343  		}
 344  		pkg->pkgsize = i;
 345  		break;
 346  	case PKG_ATTR_TIME:
 347  		i = strtoimax(str, &endptr, 10);
 348  		if (endptr != NULL) {
 349  			pkg_emit_error("Unable to convert '%s' to int64_t",
 350  			    str);
 351  			return (EPKG_FATAL);
 352  		}
 353  		pkg->timestamp = i;
 354  		break;
 355  	default:
 356  		pkg_emit_error("%d does not accept string values", attr);
 357  		return (EPKG_FATAL);
 358  	}
 359  	return (EPKG_OK);
 360  }
 361  
 362  int
 363  pkg_set_from_fileat(int fd, struct pkg *pkg, pkg_attr attr, const char *path,
 364      bool trimcr)
 365  {
 366  	char *buf = NULL;
 367  	char *cp;
 368  	off_t size = 0;
 369  	int ret = EPKG_OK;
 370  
 371  	assert(pkg != NULL);
 372  	assert(path != NULL);
 373  
 374  	if ((ret = file_to_bufferat(fd, path, &buf, &size)) !=  EPKG_OK)
 375  		return (ret);
 376  
 377  	if (trimcr) {
 378  		cp = buf + strlen(buf) - 1;
 379  		while (cp > buf && *cp == '\n') {
 380  			*cp = 0;
 381  			cp--;
 382  		}
 383  	}
 384  
 385  	ret = pkg_set(pkg, attr, buf);
 386  
 387  	free(buf);
 388  
 389  	return (ret);
 390  }
 391  
 392  #define pkg_each(name, type, field)		\
 393  int						\
 394  pkg_##name(const struct pkg *p, type **t) {	\
 395  	assert(p != NULL);			\
 396  	if ((*t) == NULL)			\
 397  		(*t) = p->field;		\
 398  	else					\
 399  		(*t) = (*t)->next;		\
 400  	if ((*t) == NULL)			\
 401  		return (EPKG_END);		\
 402  	return (EPKG_OK);			\
 403  }
 404  
 405  pkg_each(dirs, struct pkg_dir, dirs);
 406  pkg_each(files, struct pkg_file, files);
 407  pkg_each(deps, struct pkg_dep, depends);
 408  pkg_each(rdeps, struct pkg_dep, rdepends);
 409  pkg_each(options, struct pkg_option, options);
 410  pkg_each(conflicts, struct pkg_conflict, conflicts);
 411  pkg_each(config_files, struct pkg_config_file, config_files);
 412  
 413  int
 414  pkg_adduser(struct pkg *pkg, const char *name)
 415  {
 416  	return (pkg_addstring(&pkg->users, name, "user"));
 417  }
 418  
 419  int
 420  pkg_addgroup(struct pkg *pkg, const char *name)
 421  {
 422  	return (pkg_addstring(&pkg->groups, name, "group"));
 423  }
 424  
 425  int
 426  pkg_adddep(struct pkg *pkg, const char *name, const char *origin, const char *version, bool locked)
 427  {
 428  	if (pkg_adddep_chain(NULL, pkg, name, origin, version, locked) == NULL) {
 429  		return (EPKG_FATAL);
 430  	}
 431  
 432  	return (EPKG_OK);
 433  }
 434  
 435  struct pkg_dep *
 436  pkg_adddep_chain(struct pkg_dep *chain,
 437  		struct pkg *pkg,
 438  		const char *name,
 439  		const char *origin,
 440  		const char *version, bool locked)
 441  {
 442  	struct pkg_dep *d = NULL;
 443  
 444  	assert(pkg != NULL);
 445  	assert(name != NULL && name[0] != '\0');
 446  
 447  	dbg(3, "add a new dependency origin: %s, name: %s", origin ? origin : "", name);
 448  	if (pkghash_get(pkg->depshash, name) != NULL) {
 449  		pkg_emit_error("%s: duplicate dependency listing: %s",
 450  		    pkg->name, name);
 451  		return (NULL);
 452  	}
 453  
 454  	d = xcalloc(1, sizeof(*d));
 455  	if (origin != NULL && origin[0] != '\0')
 456  		d->origin = xstrdup(origin);
 457  	d->name = xstrdup(name);
 458  	if (version != NULL && version[0] != '\0')
 459  		d->version = xstrdup(version);
 460  	d->uid = xstrdup(name);
 461  	d->locked = locked;
 462  
 463  	pkghash_safe_add(pkg->depshash, d->name, d, NULL);
 464  	if (chain == NULL) {
 465  		DL_APPEND(pkg->depends, d);
 466  		chain = pkg->depends;
 467  	}
 468  	else {
 469  		DL_APPEND2(chain, d, alt_prev, alt_next);
 470  	}
 471  
 472  	return (chain);
 473  }
 474  
 475  int
 476  pkg_addrdep(struct pkg *pkg, const char *name, const char *origin, const char *version, bool locked)
 477  {
 478  	struct pkg_dep *d;
 479  
 480  	assert(pkg != NULL);
 481  	assert(name != NULL && name[0] != '\0');
 482  
 483  	dbg(3, "add a new reverse dependency origin: %s, name: %s", origin ? origin : "", name);
 484  
 485  	d = xcalloc(1, sizeof(*d));
 486  	if (origin != NULL && origin[0] != '\0')
 487  		d->origin = xstrdup(origin);
 488  	d->name = xstrdup(name);
 489  	if (version != NULL && version[0] != '\0')
 490  		d->version = xstrdup(version);
 491  	d->uid = xstrdup(name);
 492  	d->locked = locked;
 493  
 494  	pkghash_safe_add(pkg->rdepshash, d->name, d, NULL);
 495  	LL_PREPEND(pkg->rdepends, d);
 496  
 497  	return (EPKG_OK);
 498  }
 499  
 500  int
 501  pkg_addfile(struct pkg *pkg, const char *path, const char *sum, bool check_duplicates)
 502  {
 503  	return (pkg_addfile_attr(pkg, path, sum, NULL, NULL, 0, 0, 0, NULL, check_duplicates));
 504  }
 505  
 506  int
 507  pkg_addfile_attr(struct pkg *pkg, const char *path, const char *sum,
 508  		 const char *uname, const char *gname, mode_t perm,
 509  		 u_long fflags, time_t mtime,
 510  		 const char *symlink_target, bool check_duplicates)
 511  {
 512  	struct pkg_file *f = NULL;
 513  	char abspath[MAXPATHLEN];
 514  
 515  	assert(pkg != NULL);
 516  	assert(path != NULL && path[0] != '\0');
 517  
 518  	path = pkg_absolutepath(path, abspath, sizeof(abspath), false);
 519  	dbg(3, "add new file '%s'", path);
 520  
 521  	if (check_duplicates && pkghash_get(pkg->filehash, path) != NULL) {
 522  		if (ctx.developer_mode) {
 523  			pkg_emit_error("duplicate file listing: %s, fatal (developer mode)", path);
 524  			return (EPKG_FATAL);
 525  		} else {
 526  			pkg_emit_error("duplicate file listing: %s, ignoring", path);
 527  			return (EPKG_OK);
 528  		}
 529  	}
 530  
 531  	f = xcalloc(1, sizeof(*f));
 532  	f->path = xstrdup(path);
 533  
 534  	if (sum != NULL)
 535  		f->sum = xstrdup(sum);
 536  
 537  	if (uname != NULL)
 538  		f->uname = xstrdup(uname);
 539  
 540  	if (gname != NULL)
 541  		f->gname = xstrdup(gname);
 542  
 543  	if (perm != 0)
 544  		f->perm = perm;
 545  
 546  	if (fflags != 0)
 547  		f->fflags = fflags;
 548  
 549  	if (symlink_target != NULL)
 550  		f->symlink_target = xstrdup(symlink_target);
 551  
 552  	if (mtime > 0)
 553  		f->time[1].tv_sec = mtime;
 554  
 555  	pkghash_safe_add(pkg->filehash, f->path, f, NULL);
 556  	DL_APPEND(pkg->files, f);
 557  
 558  	return (EPKG_OK);
 559  }
 560  
 561  /*
 562   * content should be populated later by e.g. pkg_add_common() if NULL
 563   */
 564  int
 565  pkg_addconfig_file(struct pkg *pkg, const char *path, const char *content)
 566  {
 567  	struct pkg_config_file *f = NULL;
 568  	char abspath[MAXPATHLEN];
 569  
 570  	path = pkg_absolutepath(path, abspath, sizeof(abspath), false);
 571  	dbg(3, "add new config file '%s'", path);
 572  
 573  	if (pkghash_get(pkg->config_files_hash, path) != NULL) {
 574  		pkg_emit_error("duplicate file listing: %s", path);
 575  		return (EPKG_FATAL);
 576  	}
 577  	f = xcalloc(1, sizeof(*f));
 578  	f->path = xstrdup(path);
 579  
 580  	if (content != NULL)
 581  		f->content = xstrdup(content);
 582  
 583  	pkghash_safe_add(pkg->config_files_hash, f->path, f, NULL);
 584  	DL_APPEND(pkg->config_files, f);
 585  
 586  	return (EPKG_OK);
 587  }
 588  
 589  int
 590  pkg_addstring(charv_t *list, const char *val, const char *title)
 591  {
 592  	assert(val != NULL);
 593  	assert(title != NULL);
 594  
 595  	char *tmp = xstrdup(val);
 596  	if (charv_insert_sorted(list, tmp) != NULL) {
 597  		free(tmp);
 598  		if (ctx.developer_mode) {
 599  			pkg_emit_error("duplicate %s listing: %s, fatal"
 600  			    " (developer mode)", title, val);
 601  			return (EPKG_FATAL);
 602  		}
 603  		pkg_emit_error("duplicate %s listing: %s, "
 604  		    "ignoring", title, val);
 605  		return (EPKG_OK);
 606  	}
 607  
 608  	return (EPKG_OK);
 609  }
 610  
 611  int
 612  pkg_adddir(struct pkg *pkg, const char *path, bool check_duplicates)
 613  {
 614  	return(pkg_adddir_attr(pkg, path, NULL, NULL, 0, 0, check_duplicates));
 615  }
 616  
 617  int
 618  pkg_adddir_attr(struct pkg *pkg, const char *path, const char *uname,
 619      const char *gname, mode_t perm, u_long fflags, bool check_duplicates)
 620  {
 621  	struct pkg_dir *d = NULL;
 622  	char abspath[MAXPATHLEN];
 623  
 624  	assert(pkg != NULL);
 625  	assert(path != NULL && path[0] != '\0');
 626  
 627  	if (STREQ(path, "/")) {
 628  		pkg_emit_error("skipping useless directory: '%s'\n", path);
 629  		return (EPKG_OK);
 630  	}
 631  	path = pkg_absolutepath(path, abspath, sizeof(abspath), false);
 632  	dbg(3, "add new directory '%s'", path);
 633  	if (check_duplicates && pkghash_get(pkg->dirhash, path) != NULL) {
 634  		if (ctx.developer_mode) {
 635  			pkg_emit_error("duplicate directory listing: %s, fatal (developer mode)", path);
 636  			return (EPKG_FATAL);
 637  		} else {
 638  			pkg_emit_error("duplicate directory listing: %s, ignoring", path);
 639  			return (EPKG_OK);
 640  		}
 641  	}
 642  
 643  	d = xcalloc(1, sizeof(*d));
 644  	d->path = xstrdup(path);
 645  
 646  	if (uname != NULL)
 647  		d->uname = xstrdup(uname);
 648  
 649  	if (gname != NULL)
 650  		d->gname = xstrdup(gname);
 651  
 652  	if (perm != 0)
 653  		d->perm = perm;
 654  
 655  	if (fflags != 0)
 656  		d->fflags = fflags;
 657  
 658  	pkghash_safe_add(pkg->dirhash, d->path, d, NULL);
 659  	DL_APPEND(pkg->dirs, d);
 660  
 661  	return (EPKG_OK);
 662  }
 663  
 664  int
 665  pkg_addscript(struct pkg *pkg, const char *data, pkg_script type)
 666  {
 667  
 668  	assert(pkg != NULL);
 669  	xstring_renew(pkg->scripts[type]);
 670  	fprintf(pkg->scripts[type]->fp, "%s", data);
 671  
 672  	return (EPKG_OK);
 673  }
 674  
 675  int
 676  pkg_add_lua_script(struct pkg *pkg, const char *data, pkg_lua_script type)
 677  {
 678  	assert(pkg != NULL);
 679  
 680  	if (type >= PKG_LUA_UNKNOWN)
 681  		return (EPKG_FATAL);
 682  
 683  	vec_push(&pkg->lua_scripts[type], xstrdup(data));
 684  
 685  	return (EPKG_OK);
 686  }
 687  
 688  int
 689  pkg_addluascript_fileat(int fd, struct pkg *pkg, const char *filename)
 690  {
 691  	char *data;
 692  	pkg_lua_script type;
 693  	int ret = EPKG_OK;
 694  	off_t sz = 0;
 695  
 696  	assert(pkg != NULL);
 697  	assert(filename != NULL);
 698  
 699  	dbg(1, "Adding script from: '%s'", filename);
 700  
 701  	if ((ret = file_to_bufferat(fd, filename, &data, &sz)) != EPKG_OK)
 702  		return (ret);
 703  
 704  	if (STREQ(filename, "pkg-pre-install.lua")) {
 705  		type = PKG_LUA_PRE_INSTALL;
 706  	} else if (STREQ(filename, "pkg-post-install.lua")) {
 707  		type = PKG_LUA_POST_INSTALL;
 708  	} else if (STREQ(filename, "pkg-pre-deinstall.lua")) {
 709  		type = PKG_LUA_PRE_DEINSTALL;
 710  	} else if (STREQ(filename, "pkg-post-deinstall.lua")) {
 711  		type = PKG_LUA_POST_DEINSTALL;
 712  	} else {
 713  		pkg_emit_error("unknown lua script '%s'", filename);
 714  		ret = EPKG_FATAL;
 715  		goto cleanup;
 716  	}
 717  
 718  	ret = pkg_add_lua_script(pkg, data, type);
 719  cleanup:
 720  	free(data);
 721  	return (ret);
 722  }
 723  
 724  int
 725  pkg_addscript_fileat(int fd, struct pkg *pkg, const char *filename)
 726  {
 727  	char *data;
 728  	pkg_script type;
 729  	int ret = EPKG_OK;
 730  	off_t sz = 0;
 731  
 732  	assert(pkg != NULL);
 733  	assert(filename != NULL);
 734  
 735  	dbg(1, "Adding script from: '%s'", filename);
 736  
 737  	if ((ret = file_to_bufferat(fd, filename, &data, &sz)) != EPKG_OK)
 738  		return (ret);
 739  
 740  	if (STREQ(filename, "pkg-pre-install") ||
 741  			STREQ(filename, "+PRE_INSTALL")) {
 742  		type = PKG_SCRIPT_PRE_INSTALL;
 743  	} else if (STREQ(filename, "pkg-post-install") ||
 744  			STREQ(filename, "+POST_INSTALL")) {
 745  		type = PKG_SCRIPT_POST_INSTALL;
 746  	} else if (STREQ(filename, "pkg-install") ||
 747  			STREQ(filename, "+INSTALL")) {
 748  		type = PKG_SCRIPT_INSTALL;
 749  	} else if (STREQ(filename, "pkg-pre-deinstall") ||
 750  			STREQ(filename, "+PRE_DEINSTALL")) {
 751  		type = PKG_SCRIPT_PRE_DEINSTALL;
 752  	} else if (STREQ(filename, "pkg-post-deinstall") ||
 753  			STREQ(filename, "+POST_DEINSTALL")) {
 754  		type = PKG_SCRIPT_POST_DEINSTALL;
 755  	} else if (STREQ(filename, "pkg-deinstall") ||
 756  			STREQ(filename, "+DEINSTALL")) {
 757  		type = PKG_SCRIPT_DEINSTALL;
 758  	} else {
 759  		pkg_emit_error("unknown script '%s'", filename);
 760  		ret = EPKG_FATAL;
 761  		goto cleanup;
 762  	}
 763  
 764  	ret = pkg_addscript(pkg, data, type);
 765  cleanup:
 766  	free(data);
 767  	return (ret);
 768  }
 769  
 770  int
 771  pkg_appendscript(struct pkg *pkg, const char *cmd, pkg_script type)
 772  {
 773  
 774  	assert(pkg != NULL);
 775  	assert(cmd != NULL && cmd[0] != '\0');
 776  
 777  	if (pkg->scripts[type] == NULL)
 778  		pkg->scripts[type] = xstring_new();
 779  
 780  	fprintf(pkg->scripts[type]->fp, "%s", cmd);
 781  
 782  	return (EPKG_OK);
 783  }
 784  
 785  int
 786  pkg_addoption(struct pkg *pkg, const char *key, const char *value)
 787  {
 788  	struct pkg_option	*o = NULL;
 789  
 790  	assert(pkg != NULL);
 791  	assert(key != NULL && key[0] != '\0');
 792  	assert(value != NULL && value[0] != '\0');
 793  
 794  	/* There might be a default or description for the option
 795  	   already, so we only count it as a duplicate if the value
 796  	   field is already set. Which implies there could be a
 797  	   default value or description for an option but no actual
 798  	   value. */
 799  
 800  	dbg(2,"adding options: %s = %s", key, value);
 801  	if (pkghash_get(pkg->optionshash, key) != NULL) {
 802  		if (ctx.developer_mode) {
 803  			pkg_emit_error("duplicate options listing: %s, fatal (developer mode)", key);
 804  			return (EPKG_FATAL);
 805  		} else {
 806  			pkg_emit_error("duplicate options listing: %s, ignoring", key);
 807  			return (EPKG_OK);
 808  		}
 809  	}
 810  	o = xcalloc(1, sizeof(*o));
 811  	o->key = xstrdup(key);
 812  	o->value = xstrdup(value);
 813  	pkghash_safe_add(pkg->optionshash, o->key, o, NULL);
 814  	DL_APPEND(pkg->options, o);
 815  
 816  	return (EPKG_OK);
 817  }
 818  
 819  int
 820  pkg_addoption_default(struct pkg *pkg, const char *key,
 821  		      const char *default_value)
 822  {
 823  	struct pkg_option *o = NULL;
 824  
 825  	assert(pkg != NULL);
 826  	assert(key != NULL && key[0] != '\0');
 827  	assert(default_value != NULL && default_value[0] != '\0');
 828  
 829  	/* There might be a value or description for the option
 830  	   already, so we only count it as a duplicate if the
 831  	   default_value field is already set. Which implies there
 832  	   could be a default value or description for an option but
 833  	   no actual value. */
 834  
 835  	if (pkghash_get(pkg->optionshash, key) != NULL) {
 836  		if (ctx.developer_mode) {
 837  			pkg_emit_error("duplicate default value for option: %s, fatal (developer mode)", key);
 838  			return (EPKG_FATAL);
 839  		} else {
 840  			pkg_emit_error("duplicate default value for option: %s, ignoring", key);
 841  			return (EPKG_OK);
 842  		}
 843  	}
 844  	o = xcalloc(1, sizeof(*o));
 845  	o->key = xstrdup(key);
 846  	o->default_value = xstrdup(default_value);
 847  	pkghash_safe_add(pkg->optionshash, o->key, o, NULL);
 848  	DL_APPEND(pkg->options, o);
 849  
 850  	return (EPKG_OK);
 851  }
 852  
 853  int
 854  pkg_addoption_description(struct pkg *pkg, const char *key,
 855  			  const char *description)
 856  {
 857  	struct pkg_option *o = NULL;
 858  
 859  	assert(pkg != NULL);
 860  	assert(key != NULL && key[0] != '\0');
 861  	assert(description != NULL && description[0] != '\0');
 862  
 863  	/* There might be a value or default for the option already,
 864  	   so we only count it as a duplicate if the description field
 865  	   is already set. Which implies there could be a default
 866  	   value or description for an option but no actual value. */
 867  
 868  	if (pkghash_get(pkg->optionshash, key) != NULL) {
 869  		if (ctx.developer_mode) {
 870  			pkg_emit_error("duplicate description for option: %s, fatal (developer mode)", key);
 871  			return (EPKG_FATAL);
 872  		} else {
 873  			pkg_emit_error("duplicate description for option: %s, ignoring", key);
 874  			return (EPKG_OK);
 875  		}
 876  	}
 877  
 878  	o = xcalloc(1, sizeof(*o));
 879  	o->key = xstrdup(key);
 880  	o->description = xstrdup(description);
 881  	pkghash_safe_add(pkg->optionshash, o->key, o, NULL);
 882  	DL_APPEND(pkg->options, o);
 883  
 884  	return (EPKG_OK);
 885  }
 886  
 887  enum pkg_shlib_flags
 888  pkg_shlib_flags_from_abi(const struct pkg_abi *shlib_abi)
 889  {
 890  	enum pkg_shlib_flags flags = PKG_SHLIB_FLAGS_NONE;
 891  
 892  	if (ctx.abi.os == PKG_OS_FREEBSD) {
 893  		if (shlib_abi->os == PKG_OS_LINUX && ctx.track_linux_compat_shlibs)
 894  			flags |= PKG_SHLIB_FLAGS_COMPAT_LINUX;
 895  
 896  		switch (ctx.abi.arch) {
 897  		case PKG_ARCH_AMD64:
 898  			if (shlib_abi->arch == PKG_ARCH_I386) {
 899  				flags |= PKG_SHLIB_FLAGS_COMPAT_32;
 900  			}
 901  			break;
 902  		case PKG_ARCH_AARCH64:
 903  			if (shlib_abi->arch == PKG_ARCH_ARMV7) {
 904  				flags |= PKG_SHLIB_FLAGS_COMPAT_32;
 905  			}
 906  			break;
 907  		case PKG_ARCH_POWERPC64:
 908  			if (shlib_abi->arch == PKG_ARCH_POWERPC) {
 909  				flags |= PKG_SHLIB_FLAGS_COMPAT_32;
 910  			}
 911  			break;
 912  		case PKG_ARCH_UNKNOWN:
 913  		case PKG_ARCH_I386:
 914  		case PKG_ARCH_ARMV6:
 915  		case PKG_ARCH_ARMV7:
 916  		case PKG_ARCH_POWERPC:
 917  		case PKG_ARCH_POWERPC64LE:
 918  		case PKG_ARCH_RISCV32:
 919  		case PKG_ARCH_RISCV64:
 920  		case PKG_ARCH_ANY:
 921  			break;
 922  		}
 923  	}
 924  
 925  	return (flags);
 926  }
 927  
 928  /*
 929   * Format examples:
 930   *
 931   * libfoo.so.1.0.0          - native
 932   * libfoo.so.1.0.0:32       - compat 32
 933   * libfoo.so.1.0.0:Linux    - compat Linux
 934   * libfoo.so.1.0.0:Linux:32 - compat Linux 32
 935   */
 936  char *
 937  pkg_shlib_name_with_flags(const char *name, enum pkg_shlib_flags flags)
 938  {
 939  	const char *compat_os = "";
 940  	if ((flags & PKG_SHLIB_FLAGS_COMPAT_LINUX) != 0) {
 941  		compat_os = ":Linux";
 942  	}
 943  
 944  	const char *compat_arch = "";
 945  	if ((flags & PKG_SHLIB_FLAGS_COMPAT_32) != 0) {
 946  		compat_arch = ":32";
 947  	}
 948  
 949  	char *ret;
 950  	xasprintf(&ret, "%s%s%s", name, compat_os, compat_arch);
 951  	return (ret);
 952  }
 953  
 954  int
 955  pkg_addshlib_required(struct pkg *pkg, const char *name,
 956      enum pkg_shlib_flags flags)
 957  {
 958  	assert(pkg != NULL);
 959  	assert(name != NULL && name[0] != '\0');
 960  
 961  	char *full_name = pkg_shlib_name_with_flags(name, flags);
 962  
 963  	/* silently ignore duplicates in case of shlibs */
 964  	if (charv_insert_sorted(&pkg->shlibs_required, full_name) != NULL) {
 965  		free(full_name);
 966  		return (EPKG_OK);
 967  	}
 968  
 969  	dbg(3, "added shlib deps for %s on %s", pkg->name, full_name);
 970  
 971  	return (EPKG_OK);
 972  }
 973  
 974  int
 975  pkg_addshlib_required_ignore(struct pkg *pkg, const char *name)
 976  {
 977  	assert(pkg != NULL);
 978  	assert(name != NULL && name[0] != '\0');
 979  
 980  	char *owned_name = xstrdup(name);
 981  
 982  	/* silently ignore duplicates in case of shlibs */
 983  	if (charv_insert_sorted(&pkg->shlibs_required_ignore, owned_name) != NULL) {
 984  		free(owned_name);
 985  		return (EPKG_OK);
 986  	}
 987  
 988  	dbg(3, "added shlib required ignore for %s on %s", pkg->name, owned_name);
 989  
 990  	return (EPKG_OK);
 991  }
 992  
 993  int
 994  pkg_addshlib_provided(struct pkg *pkg, const char *name,
 995      enum pkg_shlib_flags flags)
 996  {
 997  	assert(pkg != NULL);
 998  	assert(name != NULL && name[0] != '\0');
 999  
1000  	char *full_name = pkg_shlib_name_with_flags(name, flags);
1001  
1002  	/* silently ignore duplicates in case of shlibs */
1003  	if (charv_insert_sorted(&pkg->shlibs_provided, full_name) != NULL) {
1004  		free(full_name);
1005  		return (EPKG_OK);
1006  	}
1007  
1008  	dbg(3, "added shlib provide %s for %s", full_name, pkg->name);
1009  
1010  	return (EPKG_OK);
1011  }
1012  
1013  int
1014  pkg_addshlib_provided_ignore(struct pkg *pkg, const char *name)
1015  {
1016  	assert(pkg != NULL);
1017  	assert(name != NULL && name[0] != '\0');
1018  
1019  	char *owned_name = xstrdup(name);
1020  
1021  	/* silently ignore duplicates in case of shlibs */
1022  	if (charv_insert_sorted(&pkg->shlibs_provided_ignore, owned_name) != NULL) {
1023  		free(owned_name);
1024  		return (EPKG_OK);
1025  	}
1026  
1027  	dbg(3, "added shlib provided ignore %s for %s", owned_name, pkg->name);
1028  
1029  	return (EPKG_OK);
1030  }
1031  
1032  int
1033  pkg_addconflict(struct pkg *pkg, const char *uniqueid)
1034  {
1035  	struct pkg_conflict *c = NULL;
1036  
1037  	assert(pkg != NULL);
1038  	assert(uniqueid != NULL && uniqueid[0] != '\0');
1039  
1040  	if (pkghash_get(pkg->conflictshash, uniqueid) != NULL) {
1041  		/* silently ignore duplicates in case of conflicts */
1042  		return (EPKG_OK);
1043  	}
1044  
1045  	c = xcalloc(1, sizeof(*c));
1046  	c->uid = xstrdup(uniqueid);
1047  	dbg(3, "add a new conflict origin: %s, with %s", pkg->uid, uniqueid);
1048  
1049  	pkghash_safe_add(pkg->conflictshash, c->uid, c, NULL);
1050  	DL_APPEND(pkg->conflicts, c);
1051  
1052  	return (EPKG_OK);
1053  }
1054  
1055  int
1056  pkg_addrequire(struct pkg *pkg, const char *name)
1057  {
1058  	assert(pkg != NULL);
1059  	assert(name != NULL && name[0] != '\0');
1060  
1061  	char *tmp = xstrdup(name);
1062  
1063  	if (charv_insert_sorted(&pkg->requires, tmp) != NULL) {
1064  		/* silently ignore duplicates in case of conflicts */
1065  		free(tmp);
1066  		return (EPKG_OK);
1067  	}
1068  
1069  	return (EPKG_OK);
1070  }
1071  
1072  int
1073  pkg_addprovide(struct pkg *pkg, const char *name)
1074  {
1075  	assert(pkg != NULL);
1076  	assert(name != NULL && name[0] != '\0');
1077  
1078  	char *tmp = xstrdup(name);
1079  
1080  	if (charv_insert_sorted(&pkg->provides, tmp) != NULL) {
1081  		/* silently ignore duplicates in case of conflicts */
1082  		free(tmp);
1083  		return (EPKG_OK);
1084  	}
1085  
1086  	return (EPKG_OK);
1087  }
1088  
1089  const char *
1090  pkg_kv_get(const kvlist_t *kv, const char *tag)
1091  {
1092  	assert(tag != NULL);
1093  
1094  	vec_foreach(*kv, i) {
1095  		if (STREQ(kv->d[i]->key, tag))
1096  			return (kv->d[i]->value);
1097  	}
1098  
1099  	return (NULL);
1100  }
1101  
1102  int
1103  pkg_kv_add(kvlist_t *list, const char *key, const char *val, const char *title)
1104  {
1105  	struct pkg_kv *kv;
1106  
1107  	assert(val != NULL);
1108  	assert(title != NULL);
1109  
1110  	kv = pkg_kv_new(key, val);
1111  	if (pkg_kv_insert_sorted(list, kv) != NULL) {
1112  		pkg_kv_free(kv);
1113  		if (ctx.developer_mode) {
1114  			pkg_emit_error("duplicate %s: %s, fatal"
1115  				    " (developer mode)", title, key);
1116  				return (EPKG_FATAL);
1117  		}
1118  		pkg_emit_error("duplicate %s: %s, "
1119  		    "ignoring", title, val);
1120  		return (EPKG_OK);
1121  	}
1122  
1123  	return (EPKG_OK);
1124  }
1125  
1126  int
1127  pkg_list_count(const struct pkg *pkg, pkg_list list)
1128  {
1129  	switch (list) {
1130  	case PKG_DEPS:
1131  		return (pkghash_count(pkg->depshash));
1132  	case PKG_RDEPS:
1133  		return (pkghash_count(pkg->rdepshash));
1134  	case PKG_OPTIONS:
1135  		return (pkghash_count(pkg->optionshash));
1136  	case PKG_FILES:
1137  		return (pkghash_count(pkg->filehash));
1138  	case PKG_DIRS:
1139  		return (pkghash_count(pkg->dirhash));
1140  	case PKG_CONFLICTS:
1141  		return (pkghash_count(pkg->conflictshash));
1142  	case PKG_CONFIG_FILES:
1143  		return (pkghash_count(pkg->config_files_hash));
1144  	case PKG_USERS:
1145  		return (vec_len(&pkg->users));
1146  	case PKG_GROUPS:
1147  		return (vec_len(&pkg->groups));
1148  	case PKG_SHLIBS_REQUIRED:
1149  		return (vec_len(&pkg->shlibs_required));
1150  	case PKG_SHLIBS_PROVIDED:
1151  		return (vec_len(&pkg->shlibs_provided));
1152  	case PKG_REQUIRES:
1153  		return (vec_len(&pkg->requires));
1154  	case PKG_PROVIDES:
1155  		return (vec_len(&pkg->provides));
1156  	}
1157  
1158  	return (0);
1159  }
1160  
1161  void
1162  pkg_list_free(struct pkg *pkg, pkg_list list)  {
1163  	struct pkg_dep *cur;
1164  
1165  	switch (list) {
1166  	case PKG_DEPS:
1167  		DL_FOREACH (pkg->depends, cur) {
1168  			if (cur->alt_next) {
1169  				DL_FREE2(cur->alt_next, pkg_dep_free, alt_prev, alt_next);
1170  			}
1171  		}
1172  		DL_FREE(pkg->depends, pkg_dep_free);
1173  		pkghash_destroy(pkg->depshash);
1174  		pkg->depshash = NULL;
1175  		pkg->flags &= ~PKG_LOAD_DEPS;
1176  		break;
1177  	case PKG_RDEPS:
1178  		LL_FREE(pkg->rdepends, pkg_dep_free);
1179  		pkghash_destroy(pkg->rdepshash);
1180  		pkg->depshash = NULL;
1181  		pkg->flags &= ~PKG_LOAD_RDEPS;
1182  		break;
1183  	case PKG_OPTIONS:
1184  		DL_FREE(pkg->options, pkg_option_free);
1185  		pkghash_destroy(pkg->optionshash);
1186  		pkg->optionshash = NULL;
1187  		pkg->flags &= ~PKG_LOAD_OPTIONS;
1188  		break;
1189  	case PKG_FILES:
1190  	case PKG_CONFIG_FILES:
1191  		DL_FREE(pkg->files, pkg_file_free);
1192  		pkghash_destroy(pkg->filehash);
1193  		pkg->filehash = NULL;
1194  		DL_FREE(pkg->config_files, pkg_config_file_free);
1195  		pkghash_destroy(pkg->config_files_hash);
1196  		pkg->config_files_hash = NULL;
1197  		pkg->flags &= ~PKG_LOAD_FILES;
1198  		break;
1199  	case PKG_DIRS:
1200  		DL_FREE(pkg->dirs, pkg_dir_free);
1201  		pkghash_destroy(pkg->dirhash);
1202  		pkg->dirhash = NULL;
1203  		pkg->flags &= ~PKG_LOAD_DIRS;
1204  		break;
1205  	case PKG_CONFLICTS:
1206  		DL_FREE(pkg->conflicts, pkg_conflict_free);
1207  		pkghash_destroy(pkg->conflictshash);
1208  		pkg->conflictshash = NULL;
1209  		pkg->flags &= ~PKG_LOAD_CONFLICTS;
1210  		break;
1211  	case PKG_USERS:
1212  	case PKG_GROUPS:
1213  	case PKG_SHLIBS_REQUIRED:
1214  	case PKG_SHLIBS_PROVIDED:
1215  	case PKG_PROVIDES:
1216  	case PKG_REQUIRES:
1217  		break;
1218  	}
1219  }
1220  
1221  int
1222  pkg_open(struct pkg **pkg_p, const char *path, int flags)
1223  {
1224  	struct archive *a;
1225  	struct archive_entry *ae;
1226  	int ret;
1227  
1228  	ret = pkg_open2(pkg_p, &a, &ae, path, flags, -1);
1229  
1230  	if (ret != EPKG_OK && ret != EPKG_END)
1231  		return (EPKG_FATAL);
1232  
1233  	archive_read_close(a);
1234  	archive_read_free(a);
1235  
1236  	return (EPKG_OK);
1237  }
1238  
1239  int
1240  pkg_open_fd(struct pkg **pkg_p, int fd, int flags)
1241  {
1242  	struct archive *a;
1243  	struct archive_entry *ae;
1244  	int ret;
1245  
1246  	ret = pkg_open2(pkg_p, &a, &ae, NULL, flags, fd);
1247  
1248  	if (ret != EPKG_OK && ret != EPKG_END)
1249  		return (EPKG_FATAL);
1250  
1251  	archive_read_close(a);
1252  	archive_read_free(a);
1253  
1254  	return (EPKG_OK);
1255  }
1256  
1257  static int
1258  pkg_parse_archive(struct pkg *pkg, struct archive *a, size_t len)
1259  {
1260  	void *buffer;
1261  	int rc;
1262  
1263  	buffer = xmalloc(len);
1264  
1265  	archive_read_data(a, buffer, len);
1266  	rc = pkg_parse_manifest(pkg, buffer, len);
1267  	free(buffer);
1268  	return (rc);
1269  }
1270  
1271  int
1272  pkg_open2(struct pkg **pkg_p, struct archive **a, struct archive_entry **ae,
1273      const char *path, int flags, int fd)
1274  {
1275  	struct pkg	*pkg = NULL;
1276  	pkg_error_t	 retcode = EPKG_OK;
1277  	int		 ret;
1278  	const char	*fpath;
1279  	bool		 manifest = false;
1280  	bool		 read_from_stdin = 0;
1281  
1282  	*a = archive_read_new();
1283  	archive_read_support_filter_all(*a);
1284  	archive_read_support_format_tar(*a);
1285  
1286  	/* archive_read_open_filename() treats a path of NULL as
1287  	 * meaning "read from stdin," but we want this behaviour if
1288  	 * path is exactly "-". In the unlikely event of wanting to
1289  	 * read an on-disk file called "-", just say "./-" or some
1290  	 * other leading path. */
1291  
1292  	if (fd == -1) {
1293  		if (path == NULL) {
1294  			pkg_emit_error("bad usage of pkg_open2");
1295  			retcode = EPKG_FATAL;
1296  			goto cleanup;
1297  		}
1298  		read_from_stdin = (strncmp(path, "-", 2) == 0);
1299  
1300  		if (archive_read_open_filename(*a,
1301  		    read_from_stdin ? NULL : path, 4096) != ARCHIVE_OK) {
1302  			if ((flags & PKG_OPEN_TRY) == 0)
1303  				pkg_emit_error("archive_read_open_filename(%s): %s", path,
1304  					archive_error_string(*a));
1305  
1306  			retcode = EPKG_FATAL;
1307  			goto cleanup;
1308  		}
1309  	} else {
1310  		if (archive_read_open_fd(*a, fd, 4096) != ARCHIVE_OK) {
1311  			if ((flags & PKG_OPEN_TRY) == 0)
1312  				pkg_emit_error("archive_read_open_fd: %s",
1313  					archive_error_string(*a));
1314  
1315  			retcode = EPKG_FATAL;
1316  			goto cleanup;
1317  		}
1318  	}
1319  
1320  	retcode = pkg_new(pkg_p, PKG_FILE);
1321  	if (retcode != EPKG_OK)
1322  		goto cleanup;
1323  
1324  	pkg = *pkg_p;
1325  
1326  	while ((ret = archive_read_next_header(*a, ae)) == ARCHIVE_OK) {
1327  		fpath = archive_entry_pathname(*ae);
1328  		if (fpath[0] != '+')
1329  			break;
1330  
1331  		if (!manifest &&
1332  			(flags & PKG_OPEN_MANIFEST_COMPACT) &&
1333  			STREQ(fpath, "+COMPACT_MANIFEST")) {
1334  			manifest = true;
1335  
1336  			ret = pkg_parse_archive(pkg, *a, archive_entry_size(*ae));
1337  			if (ret != EPKG_OK) {
1338  				retcode = EPKG_FATAL;
1339  				goto cleanup;
1340  			}
1341  			/* Do not read anything more */
1342  			break;
1343  		}
1344  		if (!manifest && STREQ(fpath, "+MANIFEST")) {
1345  			manifest = true;
1346  
1347  			ret = pkg_parse_archive(pkg, *a, archive_entry_size(*ae));
1348  			if (ret != EPKG_OK) {
1349  				if ((flags & PKG_OPEN_TRY) == 0)
1350  					pkg_emit_error("%s is not a valid package: "
1351  						"Invalid manifest", path);
1352  
1353  				retcode = EPKG_FATAL;
1354  				goto cleanup;
1355  			}
1356  
1357  			if (flags & PKG_OPEN_MANIFEST_ONLY)
1358  				break;
1359  		}
1360  	}
1361  
1362  	if (ret != ARCHIVE_OK && ret != ARCHIVE_EOF) {
1363  		if ((flags & PKG_OPEN_TRY) == 0)
1364  			pkg_emit_error("archive_read_next_header(): %s",
1365  				archive_error_string(*a));
1366  
1367  		retcode = EPKG_FATAL;
1368  	}
1369  
1370  	if (ret == ARCHIVE_EOF)
1371  		retcode = EPKG_END;
1372  
1373  	if (!manifest) {
1374  		retcode = EPKG_FATAL;
1375  		if ((flags & PKG_OPEN_TRY) == 0)
1376  			pkg_emit_error("%s is not a valid package: no manifest found", path);
1377  	}
1378  
1379  	cleanup:
1380  	if (retcode != EPKG_OK && retcode != EPKG_END) {
1381  		if (*a != NULL) {
1382  			archive_read_close(*a);
1383  			archive_read_free(*a);
1384  		}
1385  		free(pkg);
1386  		*pkg_p = NULL;
1387  		*a = NULL;
1388  		*ae = NULL;
1389  	}
1390  
1391  	return (retcode);
1392  }
1393  
1394  int
1395  pkg_validate(struct pkg *pkg, struct pkgdb *db)
1396  {
1397  	assert(pkg != NULL);
1398  	unsigned flags = PKG_LOAD_BASIC|PKG_LOAD_OPTIONS|PKG_LOAD_DEPS|
1399  					PKG_LOAD_REQUIRES|PKG_LOAD_PROVIDES|
1400  					PKG_LOAD_SHLIBS_REQUIRED|PKG_LOAD_SHLIBS_PROVIDED|
1401  					PKG_LOAD_ANNOTATIONS|PKG_LOAD_CONFLICTS;
1402  
1403  	if (pkg->uid == NULL) {
1404  		/* Keep that part for the day we have to change it */
1405  		/* Generate uid from name*/
1406  		if (pkg->name == NULL)
1407  			return (EPKG_FATAL);
1408  
1409  		pkg->uid = xstrdup(pkg->name);
1410  	}
1411  
1412  	if (pkg->digest == NULL || !pkg_checksum_is_valid(pkg->digest,
1413  			strlen(pkg->digest))) {
1414  		/* Calculate new digest */
1415  		if (pkgdb_ensure_loaded(db, pkg, flags)) {
1416  			return (pkg_checksum_calculate(pkg, db, false, true, false));
1417  		}
1418  		return (EPKG_FATAL);
1419  	}
1420  
1421  	return (EPKG_OK);
1422  }
1423  
1424  enum {
1425  	FILE_OK = 0,
1426  
1427  	FILE_MISSING = 1 << 0,
1428  	FILE_SUM_MISMATCH = 1 << 1,
1429  
1430  	FILE_META_MISMATCH_TYPE = 1 << 2,
1431  	FILE_META_MISMATCH_UNAME = 1 << 3,
1432  	FILE_META_MISMATCH_GNAME = 1 << 4,
1433  	FILE_META_MISMATCH_MODE = 1 << 5,
1434  	FILE_META_MISMATCH_FFLAGS = 1 << 6,
1435  	FILE_META_MISMATCH_MTIME = 1 << 7,
1436  	FILE_META_MISMATCH_SYMLINK = 1 << 8,
1437  };
1438  
1439  static int
1440  pkg_stat(const char *path, struct stat *st, char *symlink_target,
1441  	 size_t symlink_target_size, unsigned *file_status)
1442  {
1443  	ssize_t linklen;
1444  
1445  	if (fstatat(ctx.rootfd, RELATIVE_PATH(path), st,
1446  		    AT_SYMLINK_NOFOLLOW) == -1) {
1447  
1448  		if (errno == ENOENT)
1449  			*file_status |= FILE_MISSING;
1450  		else
1451  			pkg_emit_errno("fstatat", RELATIVE_PATH(path));
1452  		return (EPKG_FATAL);
1453  	}
1454  
1455  	symlink_target[0] = '\0';
1456  	if (S_ISLNK(st->st_mode)) {
1457  		linklen = readlinkat(ctx.rootfd, RELATIVE_PATH(path),
1458  				     symlink_target, symlink_target_size - 1);
1459  		if (linklen == -1) {
1460  			symlink_target[0] = '\0';
1461  			pkg_emit_errno("readlinkat", RELATIVE_PATH(path));
1462  			return (EPKG_FATAL);
1463  		} else {
1464  			symlink_target[linklen] = '\0';
1465  		}
1466  	}
1467  
1468  	return (EPKG_OK);
1469  }
1470  
1471  static unsigned
1472  pkg_check_meta(struct stat *st, const char *uname, const char *gname,
1473  	       mode_t perm, u_long fflags, time_t mtime_sec,
1474  	       char *db_symlink_target, char *fs_symlink_target)
1475  {
1476  	unsigned file_status = FILE_OK;
1477  	uid_t fs_uid;
1478  	gid_t fs_gid;
1479  
1480  	fs_uid = get_uid_from_uname(uname);
1481  	if (fs_uid != st->st_uid)
1482  		file_status |= FILE_META_MISMATCH_UNAME;
1483  	fs_gid = get_gid_from_gname(gname);
1484  	if (fs_gid != st->st_gid)
1485  		file_status |= FILE_META_MISMATCH_GNAME;
1486  	if (perm != (st->st_mode & ~S_IFMT))
1487  		file_status |= FILE_META_MISMATCH_MODE;
1488  #if defined(HAVE_STRUCT_STAT_ST_FLAGS) && defined(HAVE_FFLAGSTOSTR)
1489  #ifdef __FreeBSD__
1490  /* ZFS sets UF_ARCHIVE implicitly, so we can't check for it. */
1491  #define	IGNORE_FLAGS	UF_ARCHIVE
1492  #else
1493  #define	IGNORE_FLAGS	0
1494  #endif
1495  	if ((fflags & ~IGNORE_FLAGS) != (st->st_flags & ~IGNORE_FLAGS))
1496  		file_status |= FILE_META_MISMATCH_FFLAGS;
1497  #endif
1498  	/* we don't check mtime for directories */
1499  	if (!S_ISDIR(st->st_mode)) {
1500  		if (mtime_sec != st->st_mtim.tv_sec)
1501  			file_status |= FILE_META_MISMATCH_MTIME;
1502  	}
1503  
1504  	if (S_ISLNK(st->st_mode) != (fs_symlink_target[0] != '\0'))
1505  		file_status |= FILE_META_MISMATCH_SYMLINK;
1506  	else if (S_ISLNK(st->st_mode) &&
1507  	    strcmp(db_symlink_target ? db_symlink_target : "", fs_symlink_target) != 0)
1508  		file_status |= FILE_META_MISMATCH_SYMLINK;
1509  
1510  	return file_status;
1511  }
1512  
1513  static const char *
1514  stat_type_tostring(mode_t mode) {
1515  	/* adapted from freebsd-src/usr.bin/stat.c */
1516  	switch (mode & S_IFMT) {
1517  	case S_IFIFO: return "Fifo file";
1518  	case S_IFCHR: return "Character Device";
1519  	case S_IFDIR: return "Directory";
1520  	case S_IFBLK: return "Block Device";
1521  	case S_IFREG: return "Regular File";
1522  	case S_IFLNK: return "Symbolic Link";
1523  	case S_IFSOCK: return "Socket";
1524  #ifdef S_IFWHT
1525  	case S_IFWHT: return "Whiteout File";
1526  #endif
1527  	default: return "???";
1528  	}
1529  }
1530  
1531  static int
1532  pkg_check_file(struct pkg *pkg, struct pkg_file *f, bool metadata, unsigned file_status)
1533  {
1534  	int rc = EPKG_OK;
1535  	int ret;
1536  	struct stat st;
1537  	char symlink_target[MAXPATHLEN];
1538  	struct passwd *pwd;
1539  	struct group *grp;
1540  	char db_str[1024], fs_str[1024];
1541  	char *db_fflags, *fs_fflags;
1542  	time_t tmp_time;
1543  	struct tm *tm;
1544  
1545  	ret = pkg_stat(f->path, &st, symlink_target, sizeof(symlink_target), &file_status);
1546  	if (ret != EPKG_OK) {
1547  		rc = EPKG_FATAL;
1548  		goto emit_status;
1549  	}
1550  
1551  	if (metadata) {
1552  		file_status |= pkg_check_meta(&st, f->uname, f->gname, f->perm, f->fflags,
1553  					      f->time[1].tv_sec, f->symlink_target,
1554  					      symlink_target);
1555  
1556  		if (!S_ISREG(st.st_mode) && !S_ISLNK(st.st_mode))
1557  			file_status |= FILE_META_MISMATCH_TYPE;
1558  		if (S_ISREG(st.st_mode) && (symlink_target[0] != '\0'))
1559  			file_status |= FILE_META_MISMATCH_TYPE;
1560  		if (S_ISLNK(st.st_mode) && (symlink_target[0] == '\0'))
1561  			file_status |= FILE_META_MISMATCH_TYPE;
1562  	}
1563  
1564  
1565  emit_status:
1566  	if (file_status & FILE_MISSING)
1567  		pkg_emit_file_missing(pkg, f);
1568  	if (file_status & FILE_SUM_MISMATCH)
1569  		pkg_emit_file_mismatch(pkg, f, f->sum);
1570  
1571  	if (file_status & FILE_META_MISMATCH_TYPE) {
1572  		pkg_emit_file_meta_mismatch(pkg, f, PKG_META_ATTR_TYPE,
1573  					    f->symlink_target == NULL ? "Regular File" : "Symbolic Link",
1574  					    stat_type_tostring(st.st_mode));
1575  	}
1576  
1577  	if (file_status & FILE_META_MISMATCH_UNAME) {
1578  		pwd = getpwuid(st.st_uid);
1579  		pkg_emit_file_meta_mismatch(pkg, f, PKG_META_ATTR_UNAME,
1580  					    f->uname, pwd != NULL ? pwd->pw_name : NULL);
1581  	}
1582  	if (file_status & FILE_META_MISMATCH_GNAME) {
1583  		grp = getgrgid(st.st_gid);
1584  		pkg_emit_file_meta_mismatch(pkg, f, PKG_META_ATTR_GNAME,
1585  					    f->gname, grp != NULL ? grp->gr_name : NULL);
1586  	}
1587  	if (file_status & FILE_META_MISMATCH_MODE) {
1588  		strmode(f->perm, db_str);
1589  		strmode(st.st_mode, fs_str);
1590  		db_str[10] = '\0'; /* trim last space character */
1591  		fs_str[10] = '\0';
1592  		pkg_emit_file_meta_mismatch(pkg, f, PKG_META_ATTR_PERM,
1593  					    db_str + 1, fs_str + 1);
1594  	}
1595  
1596  #if defined(HAVE_STRUCT_STAT_ST_FLAGS) && defined(HAVE_FFLAGSTOSTR)
1597  	if (file_status & FILE_META_MISMATCH_FFLAGS) {
1598  		db_fflags = fflagstostr(f->fflags);
1599  		fs_fflags = fflagstostr(st.st_flags);
1600  		pkg_emit_file_meta_mismatch(pkg, f, PKG_META_ATTR_FFLAGS,
1601  					    db_fflags, fs_fflags);
1602  		free(db_fflags);
1603  		free(fs_fflags);
1604  	}
1605  #endif
1606  	if (file_status & FILE_META_MISMATCH_MTIME) {
1607  		tmp_time = f->time[1].tv_sec;
1608  		tm = localtime(&tmp_time);
1609  		strftime(db_str, sizeof(db_str), "%c", tm);
1610  		tmp_time = st.st_mtim.tv_sec;
1611  		tm = localtime(&tmp_time);
1612  		strftime(fs_str, sizeof(fs_str), "%c", tm);
1613  		pkg_emit_file_meta_mismatch(pkg, f, PKG_META_ATTR_MTIME,
1614  					    db_str, fs_str);
1615  	}
1616  	if (file_status & FILE_META_MISMATCH_SYMLINK) {
1617  		pkg_emit_file_meta_mismatch(pkg, f, PKG_META_ATTR_SYMLINK,
1618  					    f->symlink_target, symlink_target);
1619  	}
1620  
1621  	if (file_status == FILE_OK) {
1622  		if (metadata)
1623  			pkg_emit_file_meta_ok(pkg, f);
1624  	} else {
1625  		rc = EPKG_FATAL;
1626  	}
1627  
1628  	return rc;
1629  }
1630  
1631  
1632  static int
1633  pkg_check_dir(struct pkg *pkg, struct pkg_dir *d, unsigned file_status)
1634  {
1635  	int rc = EPKG_OK;
1636  	int err;
1637  	struct stat st;
1638  	char *db_symlink_target = "";
1639  	char symlink_target[MAXPATHLEN];
1640  	char db_str[1024], fs_str[1024];
1641  	char *db_fflags, *fs_fflags;
1642  	struct passwd *pwd;
1643  	struct group *grp;
1644  
1645  	err = pkg_stat(d->path, &st, symlink_target, sizeof(symlink_target), &file_status);
1646  	if (err != EPKG_OK) {
1647  		rc = EPKG_FATAL;
1648  		goto emit_status;
1649  	}
1650  
1651  	file_status |= pkg_check_meta(&st, d->uname, d->gname, d->perm, d->fflags,
1652  				      d->time[1].tv_sec, db_symlink_target,
1653  				      symlink_target);
1654  
1655  	if (!S_ISDIR(st.st_mode))
1656  		file_status |= FILE_META_MISMATCH_TYPE;
1657  
1658  emit_status:
1659  	if (file_status & FILE_MISSING)
1660  		pkg_emit_dir_missing(pkg, d);
1661  
1662  	if (file_status & FILE_META_MISMATCH_TYPE) {
1663  		pkg_emit_dir_meta_mismatch(pkg, d, PKG_META_ATTR_TYPE,
1664  					   "Directory", stat_type_tostring(st.st_mode));
1665  	}
1666  
1667  	if (file_status & FILE_META_MISMATCH_UNAME) {
1668  		pwd = getpwuid(st.st_uid);
1669  		pkg_emit_dir_meta_mismatch(pkg, d, PKG_META_ATTR_UNAME,
1670  					   d->uname, pwd != NULL ? pwd->pw_name : NULL);
1671  	}
1672  	if (file_status & FILE_META_MISMATCH_GNAME) {
1673  		grp = getgrgid(st.st_gid);
1674  		pkg_emit_dir_meta_mismatch(pkg, d, PKG_META_ATTR_GNAME,
1675  					   d->gname, grp != NULL ? grp->gr_name : NULL);
1676  	}
1677  	if (file_status & FILE_META_MISMATCH_MODE) {
1678  		strmode(d->perm, db_str);
1679  		strmode(st.st_mode, fs_str);
1680  		db_str[10] = '\0'; /* trim last space character */
1681  		db_str[10] = '\0';
1682  		pkg_emit_dir_meta_mismatch(pkg, d, PKG_META_ATTR_PERM,
1683  					    db_str + 1, fs_str + 1);
1684  	}
1685  #if defined(HAVE_STRUCT_STAT_ST_FLAGS) && defined(HAVE_FFLAGSTOSTR)
1686  	if (file_status & FILE_META_MISMATCH_FFLAGS) {
1687  		db_fflags = fflagstostr(d->fflags);
1688  		fs_fflags = fflagstostr(st.st_flags);
1689  		pkg_emit_dir_meta_mismatch(pkg, d, PKG_META_ATTR_FFLAGS,
1690  					    db_fflags, fs_fflags);
1691  		free(db_fflags);
1692  		free(fs_fflags);
1693  	}
1694  #endif
1695  	if (file_status == FILE_OK)
1696  		pkg_emit_dir_meta_ok(pkg, d);
1697  	else
1698  		rc = EPKG_FATAL;
1699  
1700  	return (rc);
1701  }
1702  
1703  int
1704  pkg_check_files(struct pkg *pkg, bool checksum, bool metadata)
1705  {
1706  	struct pkg_file *f = NULL;
1707  	struct pkg_dir *d = NULL;
1708  	int rc = EPKG_OK;
1709  	int ret;
1710  	unsigned file_status;
1711  
1712  	assert(pkg != NULL);
1713  
1714  	while (pkg_files(pkg, &f) == EPKG_OK) {
1715  		file_status = FILE_OK;
1716  
1717  		if (checksum && f->sum != NULL &&
1718  		    /* skip config files as they can be modified */
1719  		    pkghash_get_value(pkg->config_files_hash, f->path) == NULL) {
1720  			ret = pkg_checksum_validate_fileat(ctx.rootfd,
1721  			    RELATIVE_PATH(f->path), f->sum);
1722  			if (ret != 0) {
1723  				if (ret == ENOENT)
1724  					file_status |= FILE_MISSING;
1725  				else
1726  					file_status |= FILE_SUM_MISMATCH;
1727  				rc = EPKG_FATAL;
1728  			}
1729  		}
1730  
1731  		ret = pkg_check_file(pkg, f, metadata, file_status);
1732  		if (ret != EPKG_OK)
1733  			rc = EPKG_FATAL;
1734  	}
1735  
1736  	if (metadata) {
1737  		while (pkg_dirs(pkg, &d) == EPKG_OK) {
1738  			file_status = FILE_OK;
1739  			ret = pkg_check_dir(pkg, d, file_status);
1740  			if (ret != EPKG_OK)
1741  				rc = EPKG_FATAL;
1742  		}
1743  	}
1744  
1745  	return (rc);
1746  }
1747  
1748  int
1749  pkg_test_filesum(struct pkg *pkg)
1750  {
1751  	return pkg_check_files(pkg, true, false);
1752  }
1753  
1754  int
1755  pkg_try_installed(struct pkgdb *db, const char *name,
1756  		struct pkg **pkg, unsigned flags) {
1757  	struct pkgdb_it *it = NULL;
1758  	int ret = EPKG_FATAL;
1759  
1760  	if ((it = pkgdb_query(db, name, MATCH_INTERNAL)) == NULL)
1761  		return (EPKG_FATAL);
1762  
1763  	ret = pkgdb_it_next(it, pkg, flags);
1764  	pkgdb_it_free(it);
1765  
1766  	return (ret);
1767  }
1768  
1769  int
1770  pkg_is_installed(struct pkgdb *db, const char *name)
1771  {
1772  	struct pkg *pkg = NULL;
1773  	int ret = EPKG_FATAL;
1774  
1775  	ret = pkg_try_installed(db, name, &pkg, PKG_LOAD_BASIC);
1776  	pkg_free(pkg);
1777  
1778  	return (ret);
1779  }
1780  
1781  bool
1782  pkg_has_message(struct pkg *p)
1783  {
1784  	return (vec_len(&p->message) > 0);
1785  }
1786  
1787  bool
1788  pkg_is_locked(const struct pkg * restrict p)
1789  {
1790  	assert(p != NULL);
1791  
1792  	return (p->locked);
1793  }
1794  
1795  bool
1796  pkg_is_config_file(struct pkg *p, const char *path,
1797      const struct pkg_file **file,
1798      struct pkg_config_file **cfile)
1799  {
1800  	*file = NULL;
1801  	*cfile = NULL;
1802  
1803  	if (pkghash_count(p->config_files_hash) == 0)
1804  		return (false);
1805  
1806  	*file = pkghash_get_value(p->filehash, path);
1807  	if (*file == NULL)
1808  		return (false);
1809  	*cfile = pkghash_get_value(p->config_files_hash, path);
1810  	if (*cfile == NULL) {
1811  		*file = NULL;
1812  		return (false);
1813  	}
1814  
1815  	return (true);
1816  }
1817  
1818  struct pkg_dir *
1819  pkg_get_dir(struct pkg *p, const char *path)
1820  {
1821  	return (pkghash_get_value(p->dirhash, path));
1822  }
1823  
1824  struct pkg_file *
1825  pkg_get_file(struct pkg *p, const char *path)
1826  {
1827  	return (pkghash_get_value(p->filehash, path));
1828  }
1829  
1830  bool
1831  pkg_has_file(struct pkg *p, const char *path)
1832  {
1833  	return (pkghash_get(p->filehash, path) != NULL);
1834  }
1835  
1836  bool
1837  pkg_has_dir(struct pkg *p, const char *path)
1838  {
1839  	return (pkghash_get(p->dirhash, path) != NULL);
1840  }
1841  
1842  int
1843  pkg_open_root_fd(struct pkg *pkg)
1844  {
1845  	const char *path;
1846  	char rootpath[MAXPATHLEN];
1847  
1848  	if (pkg->rootfd != -1)
1849  		return (EPKG_OK);
1850  
1851  	path = pkg_kv_get(&pkg->annotations, "relocated");
1852  	if (path == NULL) {
1853  		if ((pkg->rootfd = dup(ctx.rootfd)) == -1) {
1854  			pkg_emit_errno("dup", "rootfd");
1855  			return (EPKG_FATAL);
1856  		}
1857  		return (EPKG_OK);
1858  	}
1859  
1860  	pkg_absolutepath(path, rootpath, sizeof(rootpath), false);
1861  
1862  	if ((pkg->rootfd = openat(ctx.rootfd, RELATIVE_PATH(rootpath), O_DIRECTORY)) >= 0 ) {
1863  		pkg->rootpath = xstrdup(rootpath);
1864  		return (EPKG_OK);
1865  	}
1866  
1867  	pkg_emit_errno("open", path);
1868  
1869  	return (EPKG_FATAL);
1870  }
1871  
1872  int
1873  pkg_message_from_ucl(struct pkg *pkg, const ucl_object_t *obj)
1874  {
1875  	struct pkg_message *msg = NULL;
1876  	const ucl_object_t *elt, *cur;
1877  	ucl_object_iter_t it = NULL;
1878  
1879  	if (ucl_object_type(obj) == UCL_STRING) {
1880  		msg = xcalloc(1, sizeof(*msg));
1881  		msg->str = xstrdup(ucl_object_tostring(obj));
1882  		msg->type = PKG_MESSAGE_ALWAYS;
1883  		vec_push(&pkg->message, msg);
1884  		return (EPKG_OK);
1885  	}
1886  
1887  	/* New format of pkg message */
1888  	if (ucl_object_type(obj) != UCL_ARRAY)
1889  		pkg_emit_error("package message badly formatted, an array was"
1890  		    " expected");
1891  
1892  	while ((cur = ucl_iterate_object(obj, &it, true))) {
1893  		elt = ucl_object_find_key(cur, "message");
1894  
1895  		if (elt == NULL || ucl_object_type(elt) != UCL_STRING) {
1896  			pkg_emit_error("package message lacks 'message' key"
1897  			    " that is required");
1898  
1899  			return (EPKG_FATAL);
1900  		}
1901  
1902  		msg = xcalloc(1, sizeof(*msg));
1903  
1904  		msg->str = xstrdup(ucl_object_tostring(elt));
1905  		msg->type = PKG_MESSAGE_ALWAYS;
1906  		elt = ucl_object_find_key(cur, "type");
1907  		if (elt != NULL && ucl_object_type(elt) == UCL_STRING) {
1908  			if (STRIEQ(ucl_object_tostring(elt), "install"))
1909  				msg->type = PKG_MESSAGE_INSTALL;
1910  			else if (STRIEQ(ucl_object_tostring(elt), "remove"))
1911  				msg->type = PKG_MESSAGE_REMOVE;
1912  			else if (STRIEQ(ucl_object_tostring(elt), "upgrade"))
1913  				msg->type = PKG_MESSAGE_UPGRADE;
1914  			else
1915  				pkg_emit_error("Unknown message type,"
1916  				    " message will always be printed");
1917  		}
1918  		if (msg->type != PKG_MESSAGE_UPGRADE) {
1919  			vec_push(&pkg->message, msg);
1920  			continue;
1921  		}
1922  
1923  		elt = ucl_object_find_key(cur, "minimum_version");
1924  		if (elt != NULL && ucl_object_type(elt) == UCL_STRING) {
1925  			msg->minimum_version = xstrdup(ucl_object_tostring(elt));
1926  		}
1927  
1928  		elt = ucl_object_find_key(cur, "maximum_version");
1929  		if (elt != NULL && ucl_object_type(elt) == UCL_STRING) {
1930  			msg->maximum_version = xstrdup(ucl_object_tostring(elt));
1931  		}
1932  
1933  		vec_push(&pkg->message, msg);
1934  	}
1935  
1936  	return (EPKG_OK);
1937  }
1938  
1939  int
1940  pkg_message_from_str(struct pkg *pkg, const char *str, size_t len)
1941  {
1942  	struct ucl_parser *parser;
1943  	ucl_object_t *obj;
1944  	int ret = EPKG_FATAL;
1945  
1946  	assert(str != NULL);
1947  
1948  	if (len == 0) {
1949  		len = strlen(str);
1950  	}
1951  
1952  	parser = ucl_parser_new(UCL_PARSER_NO_FILEVARS);
1953  	if (pkg->prefix != NULL) {
1954  		ucl_parser_register_variable(parser, "PREFIX", pkg->prefix);
1955  	}
1956  	if (pkg->name != NULL) {
1957  		ucl_parser_register_variable(parser, "PKGNAME", pkg->name);
1958  	}
1959  	if (pkg->origin != NULL) {
1960  		ucl_parser_register_variable(parser, "PKGORIGIN", pkg->origin);
1961  	}
1962  	if (pkg->maintainer != NULL) {
1963  		ucl_parser_register_variable(parser, "MAINTAINER", pkg->maintainer);
1964  	}
1965  
1966  	if (ucl_parser_add_chunk(parser, (const unsigned char*)str, len)) {
1967  		obj = ucl_parser_get_object(parser);
1968  		ucl_parser_free(parser);
1969  
1970  		ret = pkg_message_from_ucl(pkg, obj);
1971  		ucl_object_unref(obj);
1972  
1973  		return (ret);
1974  	}
1975  
1976  	ucl_parser_free (parser);
1977  
1978  	return (ret);
1979  }
1980  
1981  ucl_object_t*
1982  pkg_message_to_ucl(const struct pkg *pkg)
1983  {
1984  	struct pkg_message *msg;
1985  	ucl_object_t *array;
1986  	ucl_object_t *obj;
1987  
1988  	array = ucl_object_typed_new(UCL_ARRAY);
1989  	vec_foreach(pkg->message, i) {
1990  		msg = pkg->message.d[i];
1991  		obj = ucl_object_typed_new (UCL_OBJECT);
1992  
1993  		ucl_object_insert_key(obj,
1994  		    ucl_object_fromstring_common(msg->str, 0,
1995  		    UCL_STRING_RAW|UCL_STRING_TRIM),
1996  		    "message", 0, false);
1997  
1998  		switch (msg->type) {
1999  		case PKG_MESSAGE_ALWAYS:
2000  			break;
2001  		case PKG_MESSAGE_INSTALL:
2002  			ucl_object_insert_key(obj,
2003  			    ucl_object_fromstring("install"),
2004  			    "type", 0, false);
2005  			break;
2006  		case PKG_MESSAGE_UPGRADE:
2007  			ucl_object_insert_key(obj,
2008  			    ucl_object_fromstring("upgrade"),
2009  			    "type", 0, false);
2010  			break;
2011  		case PKG_MESSAGE_REMOVE:
2012  			ucl_object_insert_key(obj,
2013  			    ucl_object_fromstring("remove"),
2014  			    "type", 0, false);
2015  			break;
2016  		}
2017  		if (msg->maximum_version) {
2018  			ucl_object_insert_key(obj,
2019  			    ucl_object_fromstring(msg->maximum_version),
2020  			    "maximum_version", 0, false);
2021  		}
2022  		if (msg->minimum_version) {
2023  			ucl_object_insert_key(obj,
2024  			    ucl_object_fromstring(msg->minimum_version),
2025  			    "minimum_version", 0, false);
2026  		}
2027  		ucl_array_append(array, obj);
2028  	}
2029  
2030  	return (array);
2031  }
2032  
2033  char*
2034  pkg_message_to_str(struct pkg *pkg)
2035  {
2036  	ucl_object_t *obj;
2037  	char *ret = NULL;
2038  
2039  	if (vec_len(&pkg->message) <= 0)
2040  		return (NULL);
2041  
2042  	obj = pkg_message_to_ucl(pkg);
2043  	ret = ucl_object_emit(obj, UCL_EMIT_JSON_COMPACT);
2044  	ucl_object_unref(obj);
2045  
2046  	return (ret);
2047  }
2048  
2049  static int
2050  pkg_dep_cmp(struct pkg_dep *a, struct pkg_dep *b)
2051  {
2052  	return (strcmp(a->name, b->name));
2053  }
2054  
2055  static int
2056  pkg_file_cmp(struct pkg_file *a, struct pkg_file *b)
2057  {
2058  	return (strcmp(a->path, b->path));
2059  }
2060  
2061  static int
2062  pkg_dir_cmp(struct pkg_dir *a, struct pkg_dir *b)
2063  {
2064  	return (strcmp(a->path, b->path));
2065  }
2066  
2067  static int
2068  pkg_option_cmp(struct pkg_option *a, struct pkg_option *b)
2069  {
2070  	return (strcmp(a->key, b->key));
2071  }
2072  
2073  static int
2074  pkg_cf_cmp(struct pkg_config_file *a, struct pkg_config_file *b)
2075  {
2076  	return (strcmp(a->path, b->path));
2077  }
2078  
2079  void
2080  pkg_lists_sort(struct pkg *p)
2081  {
2082  	if (p->list_sorted)
2083  		return;
2084  	p->list_sorted = true;
2085  
2086  	DL_SORT(p->depends, pkg_dep_cmp);
2087  	DL_SORT(p->files, pkg_file_cmp);
2088  	DL_SORT(p->dirs, pkg_dir_cmp);
2089  	DL_SORT(p->options, pkg_option_cmp);
2090  	DL_SORT(p->config_files, pkg_cf_cmp);
2091  }
2092  
2093  static int
2094  pkgs_cmp(const void *a, const void *b)
2095  {
2096  	struct pkg *pa = *(struct pkg **)a;
2097  	struct pkg *pb = *(struct pkg **)b;
2098  
2099  	return (strcmp(pa->name, pb->name));
2100  }
2101  
2102  void
2103  pkgs_sort(pkgs_t *pkgs)
2104  {
2105  	if (pkgs->len == 0)
2106  		return;
2107  	qsort(pkgs->d, pkgs->len, sizeof(pkgs->d[0]), pkgs_cmp);
2108  }
2109  
2110  DEFINE_VEC_INSERT_SORTED_FUNC(pkgs_t, pkgs, struct pkg *, pkgs_cmp)
2111  
2112  struct pkg **
2113  pkgs_search(pkgs_t *pkgs, char *el)
2114  {
2115  	struct pkg target = { .name = el };
2116  	struct pkg *tgt = &target;
2117  	if (pkgs->len == 0)
2118  		return (NULL);
2119  	struct pkg **res = bsearch(&tgt, pkgs->d, pkgs->len, sizeof(pkgs->d[0]), pkgs_cmp);
2120  	return (res);
2121  }