mirror of the now-defunct rocklinux.org
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

656 lines
19 KiB

  1. Stefan Fiedler:
  2. Add support for automated run-time dependency checks (partial).
  3. Implementation in rocket.sh is missing.
  4. diff -dur mine-0.25/create.c mine-0.25-p/create.c
  5. --- mine-0.25/create.c 2005-03-23 09:51:06.000000000 +0100
  6. +++ mine-0.25-p/create.c 2006-12-29 19:12:05.000000000 +0100
  7. @@ -94,6 +94,7 @@
  8. exit(1);
  9. }
  10. +/* All subtrees are optional. */
  11. char * varadm_subtrees[] =
  12. {
  13. "packages",
  14. @@ -102,6 +103,9 @@
  15. "cksums",
  16. "dependencies",
  17. "descs",
  18. + "provides",
  19. + "requires",
  20. + "conflicts",
  21. NULL
  22. };
  23. @@ -128,7 +132,8 @@
  24. for (i=0; varadm_subtrees[i]; i++) {
  25. snprintf(filename, 1024, "%s/%s/%s", varadm,
  26. varadm_subtrees[i], package);
  27. - gem_create_addfile(&c, varadm_subtrees[i], filename);
  28. + if (!access(filename, R_OK))
  29. + gem_create_addfile(&c, varadm_subtrees[i], filename);
  30. }
  31. snprintf(filename, 1024, "%s/descs/%s", varadm, package);
  32. diff -dur mine-0.25/gasgui.h mine-0.25-p/gasgui.h
  33. --- mine-0.25/gasgui.h 2005-03-23 09:51:06.000000000 +0100
  34. +++ mine-0.25-p/gasgui.h 2006-12-29 19:12:05.000000000 +0100
  35. @@ -25,6 +25,9 @@
  36. struct dependency {
  37. char *name;
  38. + char *version;
  39. + /* The enumeration denotes no op, <, <=, >, >=, =, or @ (string compare). */
  40. + enum { null, lt, le, gt, ge, eq, at } cmp_op;
  41. struct package *pkg;
  42. struct dependency *next;
  43. };
  44. @@ -36,7 +39,7 @@
  45. int action; /* -1=remove, 0=nothing, 2=install */
  46. int *size; /* filesystem_count + 1 elements */
  47. struct package *next;
  48. - struct dependency *deps;
  49. + struct dependency *provides, *requires, *conflicts;
  50. };
  51. struct directory_entry {
  52. diff -dur mine-0.25/mkpdb.c mine-0.25-p/mkpdb.c
  53. --- mine-0.25/mkpdb.c 2005-03-23 09:51:06.000000000 +0100
  54. +++ mine-0.25-p/mkpdb.c 2006-12-29 19:12:05.000000000 +0100
  55. @@ -72,6 +72,15 @@
  56. if ( dump_field(&c, "descs") == -1 ) goto error;
  57. if ( dump_field(&c, "dependencies") == -1 ) goto error;
  58. if ( dump_field(&c, "cksums") == -1 ) goto error;
  59. + if ( dump_field(&c, "provides") == -1) {
  60. + putchar('\027'); putchar('\n');
  61. + }
  62. + if ( dump_field(&c, "requires") == -1) {
  63. + putchar('\027'); putchar('\n');
  64. + }
  65. + if ( dump_field(&c, "conflicts") == -1) {
  66. + putchar('\027'); putchar('\n');
  67. + }
  68. putchar('\004');
  69. putchar('\n');
  70. diff -dur mine-0.25/readdb.c mine-0.25-p/readdb.c
  71. --- mine-0.25/readdb.c 2005-10-04 18:35:32.000000000 +0200
  72. +++ mine-0.25-p/readdb.c 2006-12-29 20:27:16.000000000 +0100
  73. @@ -40,7 +40,6 @@
  74. int filesystem_count;
  75. struct memdb_t files_on_disks;
  76. -struct memdb_t pkg_addr_hash;
  77. struct directory *
  78. get_create_directory(struct directory * base, char *name)
  79. @@ -137,9 +136,6 @@
  80. if ( last_p ) last_p->next = p;
  81. (last_p=p)->next = NULL;
  82. - snprintf(line, 1024, "%p", p);
  83. - memdb_put(&pkg_addr_hash, packagename, line);
  84. -
  85. d = get_create_directory(rootdir, "all");
  86. e = calloc(1, sizeof(struct directory_entry));
  87. e->next = d->list; d->list = e; e->content.pkg = p;
  88. @@ -165,10 +165,13 @@
  89. p->version = malloc(line_length-3);
  90. sscanf(line+4, "%s", p->version);
  91. #else
  92. - p->version = strdup(line+4);
  93. - for (i=0; p->version[i]; i++)
  94. - if (p->version[i] == ' ')
  95. - p->version[i] = '-';
  96. + char *ver, *extraver;
  97. + ver = strtok(line+4, " ");
  98. + extraver = strtok(NULL, " ");
  99. + if (ver == NULL) ver = "0000";
  100. + if (extraver == NULL) extraver = "0";
  101. + sprintf(line,"%s-%s", ver, extraver);
  102. + p->version = strdup(line);
  103. #endif
  104. continue;
  105. }
  106. @@ -191,30 +187,6 @@
  107. }
  108. if ( !dbf ) fclose(f);
  109. - /* read package dependencies */
  110. - if ( !dbf ) {
  111. - snprintf(filename, PATH_MAX, "%s/%s/info/dependencies/%s",
  112. - sourcedir, config, packagename);
  113. - f = fopen(filename, "r");
  114. - if ( f == NULL ) {
  115. - fprintf(stderr, "Can't open %s: %s\n",
  116. - filename, strerror(errno));
  117. - return -1;
  118. - }
  119. - }
  120. -
  121. - while ( fgets(line, 1024, f) != NULL && strcmp(line,"\027\n") ) {
  122. - if ( (t = strchr(line, '\n')) != NULL ) *t=0;
  123. - if ( (t = strchr(line, ' ')) == NULL ) continue;
  124. - t++;
  125. -
  126. - if ( !strcmp(t, packagename) ) continue;
  127. - dep = calloc(1, sizeof(struct dependency));
  128. - dep->name = malloc(strlen(t)+1); strcpy(dep->name, t);
  129. - dep->next = p->deps; p->deps = dep;
  130. - }
  131. - if ( !dbf ) fclose(f);
  132. -
  133. snprintf(line, 1024, "%s/pkgs/%s-%s.gem", config, p->name, p->version);
  134. if ( memdb_get(&files_on_disks, line) ) {
  135. p->disk_number = atoi(memdb_search_result);
  136. @@ -253,6 +225,11 @@
  137. fclose(f);
  138. }
  139. + /* Skip var/adm/dependencies section. */
  140. + if ( dbf ) {
  141. + while ( fgets(line, 1024, dbf) != NULL && strcmp(line,"\027\n") );
  142. + }
  143. +
  144. if ( !dbf ) {
  145. snprintf(filename, PATH_MAX, "%s/%s/info/cksums/%s",
  146. sourcedir, config, packagename);
  147. @@ -288,6 +265,92 @@
  148. if ( !dbf ) fclose(f);
  149. }
  150. + /* Read run-time dependencies sections. */
  151. + if ( !dbf ) {
  152. + snprintf(filename, PATH_MAX, "%s/%s/info/provides/%s",
  153. + sourcedir, config, packagename);
  154. + f = fopen(filename, "r");
  155. + } else {
  156. + f = dbf;
  157. + }
  158. + if ( f != NULL )
  159. + while ( fgets(line, 1024, f) != NULL && strcmp(line,"\027\n") ) {
  160. + t=strtok(line, " \n"); if ( t == NULL ) continue;
  161. +
  162. + dep = calloc(1, sizeof(struct dependency));
  163. + dep->name = malloc(strlen(t)+1); strcpy(dep->name, t);
  164. + t=strtok(NULL, " \n"); if ( t != NULL ) {
  165. + dep->version = malloc(strlen(t)+1);
  166. + strcpy(dep->version, t);
  167. + };
  168. + dep->next = p->provides; p->provides = dep;
  169. + }
  170. + if ( !dbf ) fclose(f);
  171. +
  172. + if ( !dbf ) {
  173. + snprintf(filename, PATH_MAX, "%s/%s/info/requires/%s",
  174. + sourcedir, config, packagename);
  175. + f = fopen(filename, "r");
  176. + } else {
  177. + f = dbf;
  178. + }
  179. + if ( f != NULL )
  180. + while ( fgets(line, 1024, f) != NULL && strcmp(line,"\027\n") ) {
  181. + t=strtok(line, " \n"); if ( t == NULL ) continue;
  182. +
  183. + dep = calloc(1, sizeof(struct dependency));
  184. + dep->name = malloc(strlen(t)+1); strcpy(dep->name, t);
  185. + t=strtok(NULL, " \n"); if ( t != NULL ) {
  186. + if (strlen(t) == 1)
  187. + switch (t[0]) {
  188. + case '<': dep->cmp_op=lt; break;
  189. + case '>': dep->cmp_op=gt; break;
  190. + case '=': dep->cmp_op=eq; break;
  191. + case '@': dep->cmp_op=at; break;
  192. + }
  193. + else if (!strcmp(t, "<=")) dep->cmp_op=le;
  194. + else if (!strcmp(t, ">=")) dep->cmp_op=ge;
  195. + };
  196. + t=strtok(NULL, " \n"); if ( t != NULL ) {
  197. + dep->version = malloc(strlen(t)+1);
  198. + strcpy(dep->version, t);
  199. + };
  200. + dep->next = p->requires; p->requires = dep;
  201. + }
  202. + if ( !dbf ) fclose(f);
  203. +
  204. + if ( !dbf ) {
  205. + snprintf(filename, PATH_MAX, "%s/%s/info/conflicts/%s",
  206. + sourcedir, config, packagename);
  207. + f = fopen(filename, "r");
  208. + } else {
  209. + f = dbf;
  210. + }
  211. + if ( f != NULL )
  212. + while ( fgets(line, 1024, f) != NULL && strcmp(line,"\027\n") ) {
  213. + t=strtok(line, " \n"); if ( t == NULL ) continue;
  214. +
  215. + dep = calloc(1, sizeof(struct dependency));
  216. + dep->name = malloc(strlen(t)+1); strcpy(dep->name, t);
  217. + t=strtok(NULL, " \n"); if ( t != NULL ) {
  218. + if (strlen(t) == 1)
  219. + switch (t[0]) {
  220. + case '<': dep->cmp_op=lt; break;
  221. + case '>': dep->cmp_op=gt; break;
  222. + case '=': dep->cmp_op=eq; break;
  223. + case '@': dep->cmp_op=at; break;
  224. + }
  225. + else if (!strcmp(t, "<=")) dep->cmp_op=le;
  226. + else if (!strcmp(t, ">=")) dep->cmp_op=ge;
  227. + };
  228. + t=strtok(NULL, " \n"); if ( t != NULL ) {
  229. + dep->version = malloc(strlen(t)+1);
  230. + strcpy(dep->version, t);
  231. + };
  232. + dep->next = p->conflicts; p->conflicts = dep;
  233. + }
  234. + if ( !dbf ) fclose(f);
  235. +
  236. /* seek until EOF mark for this package */
  237. if ( dbf ) {
  238. while ( fgets(line, 1024, f) != NULL && strcmp(line,"\004\n") ) continue;
  239. @@ -396,6 +459,54 @@
  240. fclose(f);
  241. }
  242. +/*
  243. + Match provided and required dependencies.
  244. + Returns true if a provided dependency prov matches a required
  245. + dependency req.
  246. + Matching dependencies always have the same name. If the comparation
  247. + operator cmp_op is null, equal names are sufficient for a match.
  248. + For other cmp_op values, the return value depends on a comparison
  249. + between the versions of prov and req:
  250. + @ (at) compares if versions are equal strings;
  251. + other values compare the order of versions in major.minor
  252. + format (e.g. 0.7.9 < 0.7.10).
  253. +*/
  254. +int match_dependency(struct dependency *req, struct dependency *prov)
  255. +{
  256. + int result=0;
  257. + char * part1, *part2;
  258. +
  259. + if (strcmp(req->name, prov->name)) return 0;
  260. + if (req->cmp_op == null) return 1;
  261. + if (req->cmp_op == at) return (prov->version != NULL) && !strcmp(req->version, prov->version);
  262. +
  263. + char *saveptr1, *saveptr2;
  264. + part1=strtok_r(prov->version, ".", &saveptr1);
  265. + part2=strtok_r(req->version, ".", &saveptr2);
  266. +
  267. + while (part1 != NULL || part2 != NULL)
  268. + {
  269. + int i1 = (part1 == NULL) ? 0 : atoi(part1);
  270. + int i2 = (part2 == NULL) ? 0 : atoi(part2);
  271. + if (i1 < i2) { result=-1 ; break ; }
  272. + else if (i1 > i2) { result=1 ; break ; }
  273. + if (part1 != NULL) part1=strtok_r(NULL, ".", &saveptr1);
  274. + if (part2 != NULL) part2=strtok_r(NULL, ".", &saveptr2);
  275. +
  276. + }
  277. + switch (req->cmp_op) {
  278. + case lt: return result==-1;
  279. + case gt: return result==1;
  280. + case eq: return result==0;
  281. + case le: return result==0 || result==-1;
  282. + case ge: return result==0 || result==1;
  283. + case null:
  284. + case at: ;
  285. + }
  286. +
  287. + return 0;
  288. +}
  289. +
  290. int read_packages()
  291. {
  292. struct dirent **namelist;
  293. @@ -407,7 +518,6 @@
  294. int i;
  295. memdb_init(&files_on_disks);
  296. - memdb_init(&pkg_addr_hash);
  297. get_filesystem_info();
  298. printf("Reading package database. Please wait...\n");
  299. @@ -460,7 +570,7 @@
  300. return -1;
  301. } else {
  302. /* read packages in reversed order so the linked list is
  303. - * ordered well (new entries are insterted at the begin) */
  304. + * ordered well (new entries are inserted at the begin) */
  305. while (i--) {
  306. if ( namelist[i]->d_name[0] != '.' &&
  307. strcmp(namelist[i]->d_name, "TRANS.TBL") )
  308. @@ -479,25 +589,33 @@
  309. for (d = directories; d != NULL; d = d->next) sort_directory(d);
  310. for (p = packages; p != NULL; p = p->next) {
  311. - /* fill the dependenies with references to the individual packges */
  312. - for (next_dep = &(p->deps); *next_dep != NULL;) {
  313. - char* pkg_ptr_str = memdb_get(&pkg_addr_hash, (*next_dep)->name);
  314. - if (pkg_ptr_str)
  315. - sscanf(pkg_ptr_str, "%p", &(*next_dep)->pkg);
  316. - if ((*next_dep)->pkg) {
  317. - next_dep = &((*next_dep)->next);
  318. - } else {
  319. - /* drop dependency since it is not in db - this can happend
  320. - if multiple builds are run with modified packages */
  321. - struct dependency *tbd_dep = *next_dep;
  322. - *next_dep = tbd_dep->next;
  323. - free (tbd_dep->name);
  324. - free (tbd_dep);
  325. + /* Fill the dependencies with references to the individual packages. */
  326. + for (next_dep = &(p->requires); *next_dep != NULL;) {
  327. + struct package *prov;
  328. + for (prov = packages; prov != NULL; prov = prov->next) {
  329. + struct dependency *next_prov;
  330. + for (next_prov = prov->provides; next_prov != NULL; next_prov = next_prov->next) {
  331. + if (match_dependency(*next_dep, next_prov))
  332. + {
  333. + (*next_dep)->pkg=prov;
  334. + next_dep=&((*next_dep)->next);
  335. + goto dep_matched;
  336. + }
  337. + }
  338. }
  339. - }
  340. +
  341. + /* drop dependency since it is not in db - this can happen
  342. + if multiple builds are run with modified packages */
  343. + struct dependency *tbd_dep = *next_dep;
  344. + *next_dep = tbd_dep->next;
  345. + free (tbd_dep->name);
  346. + free (tbd_dep);
  347. +
  348. + dep_matched: ;
  349. + }
  350. }
  351. +
  352. memdb_free(&files_on_disks);
  353. - memdb_init(&pkg_addr_hash);
  354. return 0;
  355. }
  356. diff -dur mine-0.25/rocket.sh mine-0.25-p/rocket.sh
  357. --- mine-0.25/rocket.sh 2006-07-15 01:42:48.000000000 +0200
  358. +++ mine-0.25-p/rocket.sh 2006-12-29 19:12:05.000000000 +0100
  359. @@ -32,7 +32,6 @@
  360. update .............. update the package cache
  361. upgrade ............. update all packages to newest version
  362. install <pkg> ....... install/update package
  363. - inst-nodeps <pkg> ... install without dependencies
  364. remove <pkg> ........ remove package
  365. search <regex> ...... search package descriptions for this regex
  366. @@ -118,6 +117,9 @@
  367. close("/var/adm/rocket/descs/" pkg);
  368. close("/var/adm/rocket/dependencies/" pkg);
  369. close("/var/adm/rocket/cksums/" pkg);
  370. + close("/var/adm/rocket/provides/" pkg);
  371. + close("/var/adm/rocket/requires/" pkg);
  372. + close("/var/adm/rocket/conflicts/" pkg);
  373. print pkg " '"$1"'/" pkg "-" ver ".gem" \
  374. >> "/var/adm/rocket/locations.tmp";
  375. }
  376. @@ -133,7 +135,9 @@
  377. if (match($2, "^'$4'$") == 0)
  378. print > "/var/adm/rocket/dependencies/" pkg;
  379. }
  380. -chunk == 3 && !ignore { print > "/var/adm/rocket/cksums/" pkg; }
  381. +chunk == 4 && !ignore { print > "/var/adm/rocket/provides/" pkg; }
  382. +chunk == 5 && !ignore { print > "/var/adm/rocket/requires/" pkg; }
  383. +chunk == 6 && !ignore { print > "/var/adm/rocket/conflicts/" pkg; }
  384. chunk == 1 && $1 == "[V]" { ver = $2 "-" $3; }
  385. @@ -220,7 +224,9 @@
  386. update)
  387. rm -rf /var/adm/rocket/{descs,dependencies,cksums}
  388. + rm -rf /var/adm/rocket/{provides,requires,conflicts}
  389. mkdir -p /var/adm/rocket/{descs,dependencies,cksums,dbs}
  390. + mkdir -p /var/adm/rocket/{provides,requires,conflicts}
  391. touch /var/adm/rocket/locations.tmp
  392. gen_a_list() {
  393. grep '^[ ]*'$1'[ ]\+' /etc/rocket.conf | \
  394. @@ -360,8 +366,10 @@
  395. install)
  396. shift
  397. - if [ $nodeps = 0 ]
  398. + if [ $nodeps = 1 ]
  399. then
  400. + deps=""
  401. + else
  402. deps=$( echo $( echo "$*" | tr ' ' '\n' |
  403. gawk '
  404. @@ -405,8 +413,6 @@
  405. }
  406. '; ); )
  407. - else
  408. - deps=""
  409. fi
  410. if [ -n "$deps" ]; then
  411. diff -dur mine-0.25/selector.c mine-0.25-p/selector.c
  412. --- mine-0.25/selector.c 2005-12-27 20:21:48.000000000 +0100
  413. +++ mine-0.25-p/selector.c 2006-12-29 19:12:05.000000000 +0100
  414. @@ -110,7 +110,6 @@
  415. assert_ptr(listitems, "dialog_menu");
  416. for (i = 0; i < item_no; ++i) {
  417. -
  418. listitems[i].name = ItemName(i);
  419. listitems[i].text = ItemText(i);
  420. listitems[i].help = (dialog_vars.item_help) ? ItemHelp(i) : "";
  421. @@ -130,7 +129,7 @@
  422. {
  423. struct dependency *dep;
  424. - for (dep = p->deps; dep != NULL; dep = dep->next)
  425. + for (dep = p->requires; dep != NULL; dep = dep->next)
  426. if ( (dep->pkg->is_installed && dep->pkg->action < 0) ||
  427. (!dep->pkg->is_installed && !dep->pkg->action) ) {
  428. if ( dep->pkg->is_dependency ) {
  429. @@ -402,8 +401,8 @@
  430. "You can navigate through the menu by using either the arrow keys\n"
  431. "or +/-/btab/tab (for up, down, left, right).\n"
  432. "\n"
  433. -"Furthermore you can entry directories (de/select packages respect-\n"
  434. -"ively) by pressing the return-key while the button focus is on the\n"
  435. +"Furthermore you can enter directories (de/select packages respect-\n"
  436. +"ively) by pressing the return key while the button focus is on the\n"
  437. "`Select' button.\n"
  438. "\n"
  439. "There are also a few extra commands for additional information and\n"
  440. @@ -574,7 +573,7 @@
  441. int rc, pkgcount;
  442. char *main_item;
  443. - /* Create enought space for the items[] and entries[] arrays */
  444. + /* Create enough space for the items[] and entries[] arrays */
  445. items = malloc( (directory_entry_count+20) * sizeof(char*) * 2 );
  446. entries = malloc( (directory_entry_count+20) * sizeof(void*) );
  447. main_item = malloc(10);
  448. --- mine-0.25/rocket.sh 2007-05-17 23:14:19.000000000 +0200
  449. +++ mine-0.25/rocket 2007-05-17 23:13:02.000000000 +0200
  450. @@ -1,5 +1,7 @@
  451. #!/bin/bash
  452. +export LC_ALL=C
  453. +
  454. help()
  455. {
  456. cat << EOT
  457. @@ -60,6 +62,8 @@
  458. esac
  459. done
  460. +var_adm_dir="$root/var/adm/"
  461. +
  462. upd_archive() {
  463. filename="$( echo "$2" | tr "/:" __; )"
  464. refetch=0
  465. @@ -153,6 +157,71 @@
  466. fi
  467. }
  468. +# resolve_dep <library> <comparation-operator> <version> <pkg-set>
  469. +#
  470. +# return all packages in <pkg_set> that provide <library> meeting <version> requirement.
  471. +# <comparation-operator> is one of <, >, <=, >=, =, or @.
  472. +#
  473. +resolve_dep ()
  474. +{
  475. + local library="$1" cmp_op="$2" version="$3" var_adm_dir="$4" pkg_set="$5"
  476. + local pkg lib ver
  477. +
  478. + if [ -z "$cmp_op" -o "$cmp_op" == "@" ] ; then
  479. + cd $var_adm_dir/provides
  480. + grep -m1 -e "^$library${version:+ }$version\( \|$\)" $pkg_set 2>/dev/null |
  481. + sed -e"s,\(.*\):\(.*\),\1," | tr "\n" " "
  482. + else
  483. + while read pkg lib ver ; do
  484. + version_compare "$ver" "$version" "$cmp_op" || continue
  485. + echo -n "$pkg "
  486. + done < <( cd $var_adm_dir/provides ; grep "^$library " $pkg_set 2>/dev/null | sed -e"s,\(.*\):\(.*\),\1 \2," )
  487. + fi
  488. +}
  489. +
  490. +# get_requires <pkg1> ... <pkgN>
  491. +#
  492. +# get shared library requirements of the given packages
  493. +#
  494. +get_requires ()
  495. +{
  496. + ( cd $var_adm_dir/rocket/requires ; cat $* 2>/dev/null | sort -u )
  497. +}
  498. +
  499. +version_compare() {
  500. + local ver1="$1" ver2="$2" cmp_op="$3" result=0
  501. + local part1 part2 delim1 delim2
  502. +
  503. + if [ "$cmp_op" == "@" ] ; then
  504. + [ "$ver1" == "$ver2" ] && return 0 || return 1
  505. + fi
  506. +
  507. + while [ "$ver1" -o "$ver2" ] ; do
  508. + part1="${ver1%%[^0-9]*}" ; ver1="${ver1#$part1}"
  509. + part2="${ver2%%[^0-9]*}" ; ver2="${ver2#$part2}"
  510. + delim1="${ver1%%[0-9]*}" ; ver1="${ver1#$delim1}"
  511. + delim2="${ver2%%[0-9]*}" ; ver2="${ver2#$delim2}"
  512. +
  513. + # 1.2.0 == 1.2
  514. + [ ! "$part1" ] && part1=0
  515. + [ ! "$part2" ] && part2=0
  516. +
  517. + if [ "$part1" -lt "$part2" ] ; then
  518. + result=2 ; break
  519. + elif [ "$part1" -gt "$part2" ] ; then
  520. + result=1 ; break
  521. + fi
  522. + done
  523. +
  524. + case $cmp_op in
  525. + "=") [ "$result" == 0 ] ;;
  526. + ">") [ "$result" == 1 ] ;;
  527. + "<") [ "$result" == 2 ] ;;
  528. + ">=") [ "$result" == 1 -o $result == 0 ] ;;
  529. + "<=") [ "$result" == 2 -o $result == 0 ] ;;
  530. + esac ; return $?
  531. +}
  532. +
  533. case "$1" in
  534. updsrc)
  535. @@ -370,49 +439,52 @@
  536. then
  537. deps=""
  538. else
  539. - deps=$( echo $( echo "$*" | tr ' ' '\n' |
  540. -gawk '
  541. + # for each required library of each selected pkg:
  542. + # 1) check if the library is in the installed or selected pkg set:
  543. + # 1a) if yes, the dependency is resolved.
  544. + # 2) If no, check if the library is in the installable set:
  545. + # 2a) if there is one pkg providing this library, add that pkg to the selected set.
  546. + # 2b) if there is more than one pkg providing this library, ask the user which ones to install.
  547. + # 3) If the library isn't in any set, issue a warning. The dependency is not resolved.
  548. -function get_deps(p,
  549. - depsfn) {
  550. - if (A[p]) return;
  551. - A[p] = 1;
  552. + INSTALLED_PKGS="$( cd $var_adm_dir/descs ; ls )"
  553. + SELECTED_PKGS="$*"
  554. + INSTALLABLE_PKGS="$( cd $var_adm_dir/rocket/descs ; ls )"
  555. + ADDED_PKGS=""
  556. - depsfn = "/var/adm/rocket/dependencies/" p;
  557. + # Initialize the shared library dependency queue.
  558. + # Each library in this queue is checked for open dependencies.
  559. + dep_queue="$( mktemp -t dep_queue.XXXXXX )"
  560. + dep_checked="$( mktemp -t dep_checked.XXXXXX )"
  561. + get_requires $SELECTED_PKGS > $dep_queue
  562. + echo > $dep_checked
  563. - while ((getline < depsfn) > 0) {
  564. - if (!D[$2]) {
  565. - D[$2] = 1;
  566. - get_deps($2);
  567. - }
  568. - }
  569. + while read lib cmp ver ; do
  570. + # Skip if we already checked this library.
  571. + [[ "`grep -m 1 -c "^$lib${cmp:+ }$cmp${ver:+ }$ver$" $dep_checked`" -gt 0 ]] && continue
  572. + echo "$lib${cmp:+ }$cmp${ver:+ }$ver" >> $dep_checked
  573. - close(depsfn);
  574. -}
  575. + deps="`resolve_dep "$lib" "$cmp" "$ver" "$var_adm_dir" "$INSTALLED_PKGS"`"
  576. + if [ -z "$deps" ] ; then
  577. + deps="`resolve_dep "$lib" "$cmp" "$ver" "$var_adm_dir/rocket" "$SELECTED_PKGS $ADDED_PKGS"`"
  578. + fi
  579. + if [ -z "$deps" ] ; then
  580. + deps="`resolve_dep "$lib" "$cmp" "$ver" "$var_adm_dir/rocket" "$INSTALLABLE_PKGS"`"
  581. -{
  582. - P[$1] = 1;
  583. - get_deps($1);
  584. -}
  585. + [ -z "$deps" ] && continue
  586. -END {
  587. - for (d in D) {
  588. - if (!P[d]) {
  589. - pkgfn = "/var/adm/packages/" d;
  590. - if ((getline < pkgfn) > 0)
  591. - close(pkgfn);
  592. - else {
  593. - descfn = "/var/adm/rocket/descs/" d;
  594. - if ((getline < descfn) > 0) {
  595. - close(descfn);
  596. - print d;
  597. - }
  598. - }
  599. - }
  600. - }
  601. -}
  602. + # adding pkg to selected set
  603. + # user input required here; for now the first pkg is selected
  604. + ADDED_PKGS="$ADDED_PKGS ${deps%% *}"
  605. -'; ); )
  606. + # adding requirements of pkg to dependency queue
  607. + get_requires $deps >> $dep_queue
  608. + fi
  609. +# echo "$lib (\"$cmp\" \"$ver\")... ${deps:-NO PROVIDER FOUND}"
  610. + done < $dep_queue
  611. + rm -f $dep_queue $dep_checked
  612. +
  613. + deps="$ADDED_PKGS"
  614. fi
  615. if [ -n "$deps" ]; then