opkg: make gpg support optional
[oweals/opkg-lede.git] / opkg_install.c
1 /* opkg_install.c - the itsy package management system
2
3    Carl D. Worth
4
5    Copyright (C) 2001 University of Southern California
6
7    This program is free software; you can redistribute it and/or
8    modify it under the terms of the GNU General Public License as
9    published by the Free Software Foundation; either version 2, or (at
10    your option) any later version.
11
12    This program is distributed in the hope that it will be useful, but
13    WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15    General Public License for more details.
16 */
17
18 #include "opkg.h"
19 #include <errno.h>
20 #include <dirent.h>
21 #include <glob.h>
22 #include <time.h>
23 #include <signal.h>
24 typedef void (*sighandler_t)(int);
25
26 #include "pkg.h"
27 #include "pkg_hash.h"
28 #include "pkg_extract.h"
29
30 #include "opkg_install.h"
31 #include "opkg_configure.h"
32 #include "opkg_download.h"
33 #include "opkg_remove.h"
34
35 #include "opkg_utils.h"
36 #include "opkg_message.h"
37 #include "opkg_state.h"
38
39 #include "sprintf_alloc.h"
40 #include "file_util.h"
41 #include "str_util.h"
42 #include "xsystem.h"
43 #include "user.h"
44
45 int satisfy_dependencies_for(opkg_conf_t *conf, pkg_t *pkg);
46 static int verify_pkg_installable(opkg_conf_t *conf, pkg_t *pkg);
47 static int unpack_pkg_control_files(opkg_conf_t *conf, pkg_t *pkg);
48
49 static int prerm_upgrade_old_pkg(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
50 static int prerm_upgrade_old_pkg_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
51 static int prerm_deconfigure_conflictors(opkg_conf_t *conf, pkg_t *pkg, pkg_vec_t *conflictors);
52 static int prerm_deconfigure_conflictors_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_vec_t *conflictors);
53 static int preinst_configure(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
54 static int preinst_configure_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
55 static int check_data_file_clashes(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
56 static int check_data_file_clashes_change(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
57 static int check_data_file_clashes_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
58 static int backup_modified_conffiles(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
59 static int backup_modified_conffiles_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
60 static int postrm_upgrade_old_pkg(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
61 static int postrm_upgrade_old_pkg_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
62
63 static int remove_obsolesced_files(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
64 static int install_maintainer_scripts(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg);
65 static int remove_disappeared(opkg_conf_t *conf, pkg_t *pkg);
66 static int install_data_files(opkg_conf_t *conf, pkg_t *pkg);
67 static int resolve_conffiles(opkg_conf_t *conf, pkg_t *pkg);
68
69 static int cleanup_temporary_files(opkg_conf_t *conf, pkg_t *pkg);
70
71 static int user_prefers_old_conffile(const char *file, const char *backup);
72
73 static char *backup_filename_alloc(const char *file_name);
74 static int backup_make_backup(opkg_conf_t *conf, const char *file_name);
75 static int backup_exists_for(const char *file_name);
76 static int backup_remove(const char *file_name);
77
78
79 int opkg_install_from_file(opkg_conf_t *conf, const char *filename)
80 {
81      int err, cmp;
82      pkg_t *pkg, *old;
83      char *old_version, *new_version;
84
85      pkg = pkg_new();
86      if (pkg == NULL) {
87           return ENOMEM;
88      }
89
90      err = pkg_init_from_file(pkg, filename);
91      if (err) {
92           return err;
93      }
94
95      if (!pkg->architecture) {
96           opkg_message(conf, OPKG_ERROR, "Package %s has no Architecture defined.\n", pkg->name);
97           return -EINVAL;
98      }
99
100      /* XXX: CLEANUP: hash_insert_pkg has a nasty side effect of possibly
101         freeing the pkg that we pass in. It might be nice to clean this up
102         if possible.  */
103      pkg = hash_insert_pkg(&conf->pkg_hash, pkg, 1,conf);
104      old = pkg_hash_fetch_installed_by_name(&conf->pkg_hash, pkg->name);
105
106      pkg->local_filename = strdup(filename);
107
108      if (old) {
109           old_version = pkg_version_str_alloc(old);
110           new_version = pkg_version_str_alloc(pkg);
111
112           cmp = pkg_compare_versions(old, pkg);
113           if ( (conf->force_downgrade==1) && (cmp > 0) ){     /* We've been asked to allow downgrade  and version is precedent */
114              cmp = -1 ;                                       /* then we force opkg to downgrade */ 
115                                                               /* We need to use a value < 0 because in the 0 case we are asking to */
116                                                               /* reinstall, and some check could fail asking the "force-reinstall" option */
117           } 
118           if (cmp > 0) {
119                  opkg_message(conf, OPKG_NOTICE,
120                               "Not downgrading package %s on %s from %s to %s.\n",
121                               old->name, old->dest->name, old_version, new_version);
122                  pkg->state_want = SW_DEINSTALL;
123                  pkg->state_flag |= SF_OBSOLETE;
124                  free(old_version);
125                  free(new_version);
126                  return 0;
127           } else {
128                free(old_version);
129                free(new_version);
130           }
131      }
132
133      opkg_message(conf, OPKG_DEBUG2,"Function: %s calling opkg_install_pkg \n",__FUNCTION__);
134      return opkg_install_pkg(conf, pkg,0);
135 }
136
137 opkg_error_t opkg_install_by_name(opkg_conf_t *conf, const char *pkg_name)
138 {
139      int cmp;
140      pkg_t *old, *new;
141      char *old_version, *new_version;
142
143      opkg_message(conf, OPKG_DEBUG2, " Getting old  from pkg_hash_fetch \n" );
144      old = pkg_hash_fetch_installed_by_name(&conf->pkg_hash, pkg_name);
145      if ( old ) 
146         opkg_message(conf, OPKG_DEBUG2, " Old versions from pkg_hash_fetch %s \n",  old->version );
147     
148      opkg_message(conf, OPKG_DEBUG2, " Getting new  from pkg_hash_fetch \n" );
149      new = pkg_hash_fetch_best_installation_candidate_by_name(conf, pkg_name);
150      if ( new ) 
151         opkg_message(conf, OPKG_DEBUG2, " New versions from pkg_hash_fetch %s \n",  new->version );
152
153 /* Pigi Basically here is broken the version stuff.
154    What's happening is that nothing provide the version to differents 
155    functions, so the returned struct is always the latest.
156    That's why the install by name don't work.
157 */
158      opkg_message(conf, OPKG_DEBUG2, " Versions from pkg_hash_fetch in %s ", __FUNCTION__ );
159
160      if ( old ) 
161         opkg_message(conf, OPKG_DEBUG2, " old %s ", old->version );
162      if ( new ) 
163         opkg_message(conf, OPKG_DEBUG2, " new %s ", new->version );
164      opkg_message(conf, OPKG_DEBUG2, " \n");
165
166      if (new == NULL) {
167           return OPKG_PKG_HAS_NO_CANDIDATE;
168      }
169
170      new->state_flag |= SF_USER;
171      if (old) {
172           old_version = pkg_version_str_alloc(old);
173           new_version = pkg_version_str_alloc(new);
174
175           cmp = pkg_compare_versions(old, new);
176           if ( (conf->force_downgrade==1) && (cmp > 0) ){     /* We've been asked to allow downgrade  and version is precedent */
177              opkg_message(conf, OPKG_DEBUG, " Forcing downgrade \n");
178              cmp = -1 ;                                       /* then we force opkg to downgrade */ 
179                                                               /* We need to use a value < 0 because in the 0 case we are asking to */
180                                                               /* reinstall, and some check could fail asking the "force-reinstall" option */
181           } 
182           opkg_message(conf, OPKG_DEBUG, 
183                        "Comparing visible versions of pkg %s:"
184                        "\n\t%s is installed "
185                        "\n\t%s is available "
186                        "\n\t%d was comparison result\n",
187                        pkg_name, old_version, new_version, cmp);
188           if (cmp == 0 && !conf->force_reinstall) {
189                opkg_message(conf, OPKG_NOTICE,
190                             "Package %s (%s) installed in %s is up to date.\n",
191                             old->name, old_version, old->dest->name);
192                free(old_version);
193                free(new_version);
194                return 0;
195           } else if (cmp > 0) {
196                opkg_message(conf, OPKG_NOTICE,
197                             "Not downgrading package %s on %s from %s to %s.\n",
198                             old->name, old->dest->name, old_version, new_version);
199                free(old_version);
200                free(new_version);
201                return 0;
202           } else if (cmp < 0) {
203                new->dest = old->dest;
204                old->state_want = SW_DEINSTALL;    /* Here probably the problem for bug 1277 */
205           }
206      }
207
208      /* XXX: CLEANUP: The error code of opkg_install_by_name is really
209         supposed to be an opkg_error_t, but opkg_install_pkg could
210         return any kind of integer, (might be errno from a syscall,
211         etc.). This is a real mess and will need to be cleaned up if
212         anyone ever wants to make a nice libopkg. */
213
214      opkg_message(conf, OPKG_DEBUG2,"Function: %s calling opkg_install_pkg \n",__FUNCTION__);
215      return opkg_install_pkg(conf, new,0);
216 }
217
218 opkg_error_t opkg_install_multi_by_name(opkg_conf_t *conf, const char *pkg_name)
219 {
220      abstract_pkg_vec_t *providers = pkg_hash_fetch_all_installation_candidates (&conf->pkg_hash, pkg_name);
221      int i;
222      opkg_error_t err;
223      abstract_pkg_t *ppkg ;
224
225      if (providers == NULL)
226           return OPKG_PKG_HAS_NO_CANDIDATE;
227
228      for (i = 0; i < providers->len; i++) {
229           ppkg = abstract_pkg_vec_get(providers, i);
230           opkg_message(conf, OPKG_DEBUG2,"Function: %s calling opkg_install_by_name %d \n",__FUNCTION__, i);
231           err = opkg_install_by_name(conf, ppkg->name);
232           if (err)
233                return err;
234 /* XXX Maybe ppkg should be freed ? */
235      }
236      return 0;
237 }
238
239 /*
240  * Walk dependence graph starting with pkg, collect packages to be
241  * installed into pkgs_needed, in dependence order.
242  */
243 int pkg_mark_dependencies_for_installation(opkg_conf_t *conf, pkg_t *pkg, pkg_vec_t *pkgs_needed)
244 {
245      int i, err;
246      pkg_vec_t *depends = pkg_vec_alloc();
247      char **unresolved = NULL;
248      int ndepends;
249
250      ndepends = pkg_hash_fetch_unsatisfied_dependencies(conf, 
251                                                         pkg, depends, 
252                                                         &unresolved);
253
254      if (unresolved) {
255           opkg_message(conf, OPKG_ERROR,
256                        "%s: Cannot satisfy the following dependencies for %s:\n\t",
257                        conf->force_depends ? "Warning" : "ERROR", pkg->name);
258           while (*unresolved) {
259                opkg_message(conf, OPKG_ERROR, " %s", *unresolved);
260                unresolved++;
261           }
262           opkg_message(conf, OPKG_ERROR, "\n");
263           if (! conf->force_depends) {
264                opkg_message(conf, OPKG_INFO,
265                             "This could mean that your package list is out of date or that the packages\n"
266                             "mentioned above do not yet exist (try 'opkg update'). To proceed in spite\n"
267                             "of this problem try again with the '-force-depends' option.\n");
268                pkg_vec_free(depends);
269                return OPKG_PKG_DEPS_UNSATISFIED;
270           }
271      }
272
273      if (ndepends <= 0) {
274           pkg_vec_free(depends);
275           return 0;
276      }
277
278      for (i = 0; i < depends->len; i++) {
279           pkg_t *dep = depends->pkgs[i];
280           /* The package was uninstalled when we started, but another
281              dep earlier in this loop may have depended on it and pulled
282              it in, so check first. */
283           if ((dep->state_status != SS_INSTALLED)
284               && (dep->state_status != SS_UNPACKED)
285               && (dep->state_want != SW_INSTALL)) {
286
287                /* Mark packages as to-be-installed */
288                dep->state_want = SW_INSTALL;
289
290                /* Dependencies should be installed the same place as pkg */
291                if (dep->dest == NULL) {
292                     dep->dest = pkg->dest;
293                }
294
295                err = pkg_mark_dependencies_for_installation(conf, dep, pkgs_needed);
296                if (err) {
297                     pkg_vec_free(depends);
298                     return err;
299                }
300           }
301      }
302      if (pkgs_needed)
303           pkg_vec_insert(pkgs_needed, pkg);
304
305      pkg_vec_free(depends);
306
307      return 0;
308 }
309
310 int name_mark_dependencies_for_installation(opkg_conf_t *conf, const char *pkg_name, pkg_vec_t *pkgs_needed)
311 {
312      int cmp;
313      pkg_t *old, *new;
314      char *old_version, *new_version;
315
316      old = pkg_hash_fetch_installed_by_name(&conf->pkg_hash, pkg_name);
317     
318      new = pkg_hash_fetch_best_installation_candidate_by_name(conf, pkg_name);
319      if (new == NULL) {
320           return OPKG_PKG_HAS_NO_CANDIDATE;
321      }
322      if (old) {
323           old_version = pkg_version_str_alloc(old);
324           new_version = pkg_version_str_alloc(new);
325
326           cmp = pkg_compare_versions(old, new);
327           if ( (conf->force_downgrade==1) && (cmp > 0) ){     /* We've been asked to allow downgrade  and version is precedent */
328             opkg_message(conf, OPKG_DEBUG, " Forcing downgrade ");
329              cmp = -1 ;                                       /* then we force opkg to downgrade */ 
330                                                               /* We need to use a value < 0 because in the 0 case we are asking to */
331                                                               /* reinstall, and some check could fail asking the "force-reinstall" option */
332           } 
333           opkg_message(conf, OPKG_DEBUG, 
334                        "comparing visible versions of pkg %s:"
335                        "\n\t%s is installed "
336                        "\n\t%s is available "
337                        "\n\t%d was comparison result\n",
338                        pkg_name, old_version, new_version, cmp);
339           if (cmp == 0 && !conf->force_reinstall) {
340                opkg_message(conf, OPKG_NOTICE,
341                             "Package %s (%s) installed in %s is up to date.\n",
342                             old->name, old_version, old->dest->name);
343                free(old_version);
344                free(new_version);
345                return 0;
346           } else if (cmp > 0) {
347                opkg_message(conf, OPKG_NOTICE,
348                             "Not downgrading package %s on %s from %s to %s.\n",
349                             old->name, old->dest->name, old_version, new_version);
350                free(old_version);
351                free(new_version);
352                return 0;
353           } else if (cmp < 0) {
354                new->dest = old->dest;
355                old->state_want = SW_DEINSTALL;
356                old->state_flag |= SF_OBSOLETE;
357           }
358      }
359      return pkg_mark_dependencies_for_installation(conf, new, pkgs_needed);
360 }
361
362 \f
363
364 int satisfy_dependencies_for(opkg_conf_t *conf, pkg_t *pkg)
365 {
366      int i, err;
367      pkg_vec_t *depends = pkg_vec_alloc();
368      pkg_t *dep;
369      char **unresolved = NULL;
370      int ndepends;
371
372      ndepends = pkg_hash_fetch_unsatisfied_dependencies(conf, 
373                                                         pkg, depends, 
374                                                         &unresolved);
375
376      if (unresolved) {
377           opkg_message(conf, OPKG_ERROR,
378                        "%s: Cannot satisfy the following dependencies for %s:\n\t",
379                        conf->force_depends ? "Warning" : "ERROR", pkg->name);
380           while (*unresolved) {
381                opkg_message(conf, OPKG_ERROR, " %s", *unresolved);
382                unresolved++;
383           }
384           opkg_message(conf, OPKG_ERROR, "\n");
385           if (! conf->force_depends) {
386                opkg_message(conf, OPKG_INFO,
387                             "This could mean that your package list is out of date or that the packages\n"
388                             "mentioned above do not yet exist (try 'opkg update'). To proceed in spite\n"
389                             "of this problem try again with the '-force-depends' option.\n");
390                pkg_vec_free(depends);
391                return OPKG_PKG_DEPS_UNSATISFIED;
392           }
393      }
394
395      if (ndepends <= 0) {
396           return 0;
397      }
398
399      /* Mark packages as to-be-installed */
400      for (i=0; i < depends->len; i++) {
401           /* Dependencies should be installed the same place as pkg */
402           if (depends->pkgs[i]->dest == NULL) {
403                depends->pkgs[i]->dest = pkg->dest;
404           }
405           depends->pkgs[i]->state_want = SW_INSTALL;
406      }
407
408      for (i = 0; i < depends->len; i++) {
409           dep = depends->pkgs[i];
410           /* The package was uninstalled when we started, but another
411              dep earlier in this loop may have depended on it and pulled
412              it in, so check first. */
413           if ((dep->state_status != SS_INSTALLED)
414               && (dep->state_status != SS_UNPACKED)) {
415                opkg_message(conf, OPKG_DEBUG2,"Function: %s calling opkg_install_pkg \n",__FUNCTION__);
416                err = opkg_install_pkg(conf, dep,0);
417                /* mark this package as having been automatically installed to
418                 * satisfy a dependancy */
419                dep->auto_installed = 1;
420                if (err) {
421                     pkg_vec_free(depends);
422                     return err;
423                }
424           }
425      }
426
427      pkg_vec_free(depends);
428
429      return 0;
430 }
431
432
433 /* check all packages have their dependences satisfied, e.g., in case an upgraded package split */ 
434 int opkg_satisfy_all_dependences(opkg_conf_t *conf)
435 {
436      if (conf->nodeps == 0) {
437           int i;
438           pkg_vec_t *installed = pkg_vec_alloc();
439           pkg_hash_fetch_all_installed(&conf->pkg_hash, installed);
440           for (i = 0; i < installed->len; i++) {
441                pkg_t *pkg = installed->pkgs[i];
442                satisfy_dependencies_for(conf, pkg);
443           }
444           pkg_vec_free(installed);
445      }
446      return 0;
447 }
448
449 \f
450
451 static int check_conflicts_for(opkg_conf_t *conf, pkg_t *pkg)
452 {
453      int i;
454      pkg_vec_t *conflicts = NULL;
455      int level;
456      const char *prefix;
457      if (conf->force_depends) {
458           level = OPKG_NOTICE;
459           prefix = "Warning";
460      } else {
461           level = OPKG_ERROR;
462           prefix = "ERROR";
463      }
464
465      if (!conf->force_depends)
466           conflicts = (pkg_vec_t *)pkg_hash_fetch_conflicts(&conf->pkg_hash, pkg);
467
468      if (conflicts) {
469           opkg_message(conf, level,
470                        "%s: The following packages conflict with %s:\n\t", prefix, pkg->name);
471           i = 0;
472           while (i < conflicts->len)
473                opkg_message(conf, level, " %s", conflicts->pkgs[i++]->name);
474           opkg_message(conf, level, "\n");
475           pkg_vec_free(conflicts);
476           return OPKG_PKG_DEPS_UNSATISFIED;
477      }
478      return 0;
479 }
480
481 static int update_file_ownership(opkg_conf_t *conf, pkg_t *new_pkg, pkg_t *old_pkg)
482 {
483      str_list_t *new_list = pkg_get_installed_files(new_pkg);
484      str_list_elt_t *iter;
485
486      for (iter = new_list->head; iter; iter = iter->next) {
487           char *new_file = iter->data;
488           pkg_t *owner = file_hash_get_file_owner(conf, new_file);
489           if (!new_file)
490                opkg_message(conf, OPKG_ERROR, "Null new_file for new_pkg=%s\n", new_pkg->name);
491           if (!owner || (owner == old_pkg))
492                file_hash_set_file_owner(conf, new_file, new_pkg);
493      }
494      if (old_pkg) {
495           str_list_t *old_list = pkg_get_installed_files(old_pkg);
496           for (iter = old_list->head; iter; iter = iter->next) {
497                char *old_file = iter->data;
498                pkg_t *owner = file_hash_get_file_owner(conf, old_file);
499                if (owner == old_pkg) {
500                     /* obsolete */
501                     hash_table_insert(&conf->obs_file_hash, old_file, old_pkg);
502                }
503           }
504      }
505      return 0;
506 }
507
508 static int verify_pkg_installable(opkg_conf_t *conf, pkg_t *pkg)
509 {
510     /* XXX: FEATURE: Anything else needed here? Maybe a check on free space? */
511
512     /* sma 6.20.02:  yup; here's the first bit */
513     /* 
514      * XXX: BUG easy for cworth
515      * 1) please point the call below to the correct current root destination
516      * 2) we need to resolve how to check the required space for a pending pkg, 
517      *    my diddling with the .ipk file size below isn't going to cut it.
518      * 3) return a proper error code instead of 1
519      */
520      int comp_size, blocks_available;
521     
522      if (!conf->force_space && pkg->installed_size != NULL) {
523           blocks_available = get_available_blocks(conf->default_dest->root_dir);
524
525           comp_size = strtoul(pkg->installed_size, NULL, 0);
526           /* round up a blocks count without doing fancy-but-slow casting jazz */ 
527           comp_size = (int)((comp_size + 1023) / 1024);
528
529           if (comp_size >= blocks_available) {
530                opkg_message(conf, OPKG_ERROR,
531                             "Only have %d available blocks on filesystem %s, pkg %s needs %d\n", 
532                             blocks_available, conf->default_dest->root_dir, pkg->name, comp_size);
533                return ENOSPC;
534           }
535      }
536      return 0;
537 }
538
539 static int unpack_pkg_control_files(opkg_conf_t *conf, pkg_t *pkg)
540 {
541      int err;
542      char *conffiles_file_name;
543      char *root_dir;
544      FILE *conffiles_file;
545
546      sprintf_alloc(&pkg->tmp_unpack_dir, "%s/%s-XXXXXX", conf->tmp_dir, pkg->name);
547
548      pkg->tmp_unpack_dir = mkdtemp(pkg->tmp_unpack_dir);
549      if (pkg->tmp_unpack_dir == NULL) {
550           opkg_message(conf, OPKG_ERROR,
551                        "%s: Failed to create temporary directory '%s': %s\n",
552                        __FUNCTION__, pkg->tmp_unpack_dir, strerror(errno));
553           return errno;
554      }
555
556      err = pkg_extract_control_files_to_dir(pkg, pkg->tmp_unpack_dir);
557      if (err) {
558           return err;
559      }
560
561      /* XXX: CLEANUP: There might be a cleaner place to read in the
562         conffiles. Seems like I should be able to get everything to go
563         through pkg_init_from_file. If so, maybe it would make sense to
564         move all of unpack_pkg_control_files to that function. */
565
566      /* Don't need to re-read conffiles if we already have it */
567      if (pkg->conffiles.head) {
568           return 0;
569      }
570
571      sprintf_alloc(&conffiles_file_name, "%s/conffiles", pkg->tmp_unpack_dir);
572      if (! file_exists(conffiles_file_name)) {
573           free(conffiles_file_name);
574           return 0;
575      }
576     
577      conffiles_file = fopen(conffiles_file_name, "r");
578      if (conffiles_file == NULL) {
579           fprintf(stderr, "%s: failed to open %s: %s\n",
580                   __FUNCTION__, conffiles_file_name, strerror(errno));
581           free(conffiles_file_name);
582           return errno;
583      }
584      free(conffiles_file_name);
585
586      while (1) {
587           char *cf_name;
588           char *cf_name_in_dest;
589
590           cf_name = file_read_line_alloc(conffiles_file);
591           if (cf_name == NULL) {
592                break;
593           }
594           str_chomp(cf_name);
595           if (cf_name[0] == '\0') {
596                continue;
597           }
598
599           /* Prepend dest->root_dir to conffile name.
600              Take pains to avoid multiple slashes. */
601           root_dir = pkg->dest->root_dir;
602           if (conf->offline_root)
603                /* skip the offline_root prefix */
604                root_dir = pkg->dest->root_dir + strlen(conf->offline_root);
605           sprintf_alloc(&cf_name_in_dest, "%s%s", root_dir,
606                         cf_name[0] == '/' ? (cf_name + 1) : cf_name);
607
608           /* Can't get an md5sum now, (file isn't extracted yet).
609              We'll wait until resolve_conffiles */
610           conffile_list_append(&pkg->conffiles, cf_name_in_dest, NULL);
611
612           free(cf_name);
613           free(cf_name_in_dest);
614      }
615
616      fclose(conffiles_file);
617
618      return 0;
619 }
620
621 /* returns number of installed replacees */
622 int pkg_get_installed_replacees(opkg_conf_t *conf, pkg_t *pkg, pkg_vec_t *installed_replacees)
623 {
624      abstract_pkg_t **replaces = pkg->replaces;
625      int replaces_count = pkg->replaces_count;
626      int i, j;
627      for (i = 0; i < replaces_count; i++) {
628           abstract_pkg_t *ab_pkg = replaces[i];
629           pkg_vec_t *pkg_vec = ab_pkg->pkgs;
630           if (pkg_vec) {
631                for (j = 0; j < pkg_vec->len; j++) {
632                     pkg_t *replacee = pkg_vec->pkgs[j];
633                     if (!pkg_conflicts(pkg, replacee))
634                          continue;
635                     if (replacee->state_status == SS_INSTALLED) {
636                          pkg_vec_insert(installed_replacees, replacee);
637                     }
638                }
639           }
640      }
641      return installed_replacees->len;
642 }
643
644 int pkg_remove_installed_replacees(opkg_conf_t *conf, pkg_vec_t *replacees)
645 {
646      int i;
647      int replaces_count = replacees->len;
648      for (i = 0; i < replaces_count; i++) {
649           pkg_t *replacee = replacees->pkgs[i];
650           int err;
651           replacee->state_flag |= SF_REPLACE; /* flag it so remove won't complain */
652           err = opkg_remove_pkg(conf, replacee,0);
653           if (err)
654                return err;
655      }
656      return 0;
657 }
658
659 /* to unwind the removal: make sure they are installed */
660 int pkg_remove_installed_replacees_unwind(opkg_conf_t *conf, pkg_vec_t *replacees)
661 {
662      int i, err;
663      int replaces_count = replacees->len;
664      for (i = 0; i < replaces_count; i++) {
665           pkg_t *replacee = replacees->pkgs[i];
666           if (replacee->state_status != SS_INSTALLED) {
667                opkg_message(conf, OPKG_DEBUG2,"Function: %s calling opkg_install_pkg \n",__FUNCTION__);
668                err = opkg_install_pkg(conf, replacee,0);
669                if (err)
670                     return err;
671           }
672      }
673      return 0;
674 }
675
676 int caught_sigint = 0;
677 static void opkg_install_pkg_sigint_handler(int sig)
678 {
679      caught_sigint = sig;
680 }
681
682 /* compares versions of pkg and old_pkg, returns 0 if OK to proceed with installation of pkg, 1 otherwise */
683 static int opkg_install_check_downgrade(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg, int message)
684 {         
685      if (old_pkg) {
686           char message_out[15];
687           char *old_version = pkg_version_str_alloc(old_pkg);
688           char *new_version = pkg_version_str_alloc(pkg);
689           int cmp = pkg_compare_versions(old_pkg, pkg);
690           int rc = 0;
691
692           memset(message_out,'\x0',15);
693           strncpy (message_out,"Upgrading ",strlen("Upgrading ")); 
694           if ( (conf->force_downgrade==1) && (cmp > 0) ){     /* We've been asked to allow downgrade  and version is precedent */
695              cmp = -1 ;                                       /* then we force opkg to downgrade */ 
696              strncpy (message_out,"Downgrading ",strlen("Downgrading "));         /* We need to use a value < 0 because in the 0 case we are asking to */
697                                                               /* reinstall, and some check could fail asking the "force-reinstall" option */
698           } 
699
700           if (cmp > 0) {
701                opkg_message(conf, OPKG_NOTICE,
702                             "Not downgrading package %s on %s from %s to %s.\n",
703                             old_pkg->name, old_pkg->dest->name, old_version, new_version);
704                rc = 1;
705           } else if (cmp < 0) {
706                opkg_message(conf, OPKG_NOTICE,
707                             "%s%s on %s from %s to %s...\n",
708                             message_out, pkg->name, old_pkg->dest->name, old_version, new_version);
709                pkg->dest = old_pkg->dest;
710                rc = 0;
711           } else /* cmp == 0 */ {
712                if (conf->force_reinstall) {
713                     opkg_message(conf, OPKG_NOTICE,
714                                  "Reinstalling %s (%s) on %s...\n",
715                                  pkg->name, new_version, old_pkg->dest->name);
716                     pkg->dest = old_pkg->dest;
717                     rc = 0;
718                } else {
719                     opkg_message(conf, OPKG_NOTICE,
720                                  "Not installing %s (%s) on %s -- already installed.\n",
721                                  pkg->name, new_version, old_pkg->dest->name);
722                     rc = 1;
723                }
724           } 
725           free(old_version);
726           free(new_version);
727           return rc;
728      } else {
729       char message_out[15] ;
730       memset(message_out,'\x0',15);
731       if ( message ) 
732           strncpy( message_out,"Upgrading ",strlen("Upgrading ") );
733       else
734           strncpy( message_out,"Installing ",strlen("Installing ") );
735           char *version = pkg_version_str_alloc(pkg);
736       
737           opkg_message(conf, OPKG_NOTICE,
738                        "%s%s (%s) to %s...\n", message_out,
739                        pkg->name, version, pkg->dest->name);
740           free(version);
741           return 0;
742      }
743 }
744
745 /* and now the meat... */
746 int opkg_install_pkg(opkg_conf_t *conf, pkg_t *pkg, int from_upgrade)
747 {
748      int err = 0;
749      int message = 0;
750      pkg_t *old_pkg = NULL;
751      pkg_vec_t *replacees;
752      abstract_pkg_t *ab_pkg = NULL;
753      int old_state_flag;
754      char* file_md5;
755      char *pkgid;
756
757     
758      if ( from_upgrade ) 
759         message = 1;            /* Coming from an upgrade, and should change the output message */
760
761      if (!pkg) {
762           opkg_message(conf, OPKG_ERROR,
763                        "INTERNAL ERROR: null pkg passed to opkg_install_pkg\n");
764           return -EINVAL;
765      }
766
767      opkg_message(conf, OPKG_DEBUG2, "Function: %s calling pkg_arch_supported %s \n", __FUNCTION__, __FUNCTION__);
768
769      if (!pkg_arch_supported(conf, pkg)) {
770           opkg_message(conf, OPKG_ERROR, "INTERNAL ERROR: architecture %s for pkg %s is unsupported.\n",
771                        pkg->architecture, pkg->name);
772           return -EINVAL;
773      }
774      if (pkg->state_status == SS_INSTALLED && conf->force_reinstall == 0 && conf->nodeps == 0) {
775           err = satisfy_dependencies_for(conf, pkg);
776           if (err) { return err; }
777
778           opkg_message(conf, OPKG_NOTICE,
779                        "Package %s is already installed in %s.\n", 
780                        pkg->name, pkg->dest->name);
781           return 0;
782      }
783
784      if (pkg->dest == NULL) {
785           pkg->dest = conf->default_dest;
786      }
787
788      old_pkg = pkg_hash_fetch_installed_by_name(&conf->pkg_hash, pkg->name);
789
790      err = opkg_install_check_downgrade(conf, pkg, old_pkg, message);
791      if (err) { return err; }
792
793      pkg->state_want = SW_INSTALL;
794      if (old_pkg){                          
795          old_pkg->state_want = SW_DEINSTALL; /* needed for check_data_file_clashes of dependences */
796      }
797
798
799      /* Abhaya: conflicts check */
800      err = check_conflicts_for(conf, pkg);
801      if (err) { return err; }
802     
803      /* this setup is to remove the upgrade scenario in the end when
804         installing pkg A, A deps B & B deps on A. So both B and A are
805         installed. Then A's installation is started resulting in an
806         uncecessary upgrade */ 
807      if (pkg->state_status == SS_INSTALLED
808          && conf->force_reinstall == 0) return 0;
809     
810      err = verify_pkg_installable(conf, pkg);
811      if (err) { return err; }
812
813      if (pkg->local_filename == NULL) {
814           err = opkg_download_pkg(conf, pkg, conf->tmp_dir);
815           if (err) {
816                opkg_message(conf, OPKG_ERROR,
817                             "Failed to download %s. Perhaps you need to run 'opkg update'?\n",
818                             pkg->name);
819                return err;
820           }
821      }
822
823 /* Check for md5 values */
824      if (pkg->md5sum)
825      {
826          file_md5 = file_md5sum_alloc(pkg->local_filename);
827          if (strcmp(file_md5, pkg->md5sum))
828          {
829               opkg_message(conf, OPKG_ERROR,
830                            "Package %s md5sum mismatch. Either the opkg or the package index are corrupt. Try 'opkg update'.\n",
831                            pkg->name);
832               free(file_md5);
833               return err;
834          }
835          free(file_md5);
836      }
837
838      if (pkg->tmp_unpack_dir == NULL) {
839           unpack_pkg_control_files(conf, pkg);
840      }
841
842      /* We should update the filelist here, so that upgrades of packages that split will not fail. -Jamey 27-MAR-03 */
843 /* Pigi: check if it will pass from here when replacing. It seems to fail */
844 /* That's rather strange that files don't change owner. Investigate !!!!!!*/
845      err = update_file_ownership(conf, pkg, old_pkg);
846      if (err) { return err; }
847
848      if (conf->nodeps == 0) {
849           err = satisfy_dependencies_for(conf, pkg);
850           if (err) { return err; }
851      }
852
853      replacees = pkg_vec_alloc();
854      pkg_get_installed_replacees(conf, pkg, replacees);
855
856      sprintf_alloc (&pkgid, "%s;%s;%s;", pkg->name, pkg->version, pkg->architecture);
857      opkg_set_current_state (OPKG_STATE_INSTALLING_PKG, pkgid);
858      free (pkgid);
859
860      /* this next section we do with SIGINT blocked to prevent inconsistency between opkg database and filesystem */
861      {
862           sigset_t newset, oldset;
863           sighandler_t old_handler = NULL;
864           int use_signal = 0;
865           caught_sigint = 0;
866           if (use_signal) {
867                old_handler = signal(SIGINT, opkg_install_pkg_sigint_handler);
868           } else {
869                sigemptyset(&newset);
870                sigaddset(&newset, SIGINT);
871                sigprocmask(SIG_BLOCK, &newset, &oldset);
872           }
873
874           opkg_state_changed++;
875           pkg->state_flag |= SF_FILELIST_CHANGED;
876
877           /* XXX: BUG: we really should treat replacement more like an upgrade
878            *      Instead, we're going to remove the replacees 
879            */
880           err = pkg_remove_installed_replacees(conf, replacees);
881           if (err) goto UNWIND_REMOVE_INSTALLED_REPLACEES;
882
883           err = prerm_upgrade_old_pkg(conf, pkg, old_pkg);
884           if (err) goto UNWIND_PRERM_UPGRADE_OLD_PKG;
885
886           err = prerm_deconfigure_conflictors(conf, pkg, replacees);
887           if (err) goto UNWIND_PRERM_DECONFIGURE_CONFLICTORS;
888
889           err = preinst_configure(conf, pkg, old_pkg);
890           if (err) goto UNWIND_PREINST_CONFIGURE;
891
892           err = backup_modified_conffiles(conf, pkg, old_pkg);
893           if (err) goto UNWIND_BACKUP_MODIFIED_CONFFILES;
894
895           err = check_data_file_clashes(conf, pkg, old_pkg);
896           if (err) goto UNWIND_CHECK_DATA_FILE_CLASHES;
897
898           err = postrm_upgrade_old_pkg(conf, pkg, old_pkg);
899           if (err) goto UNWIND_POSTRM_UPGRADE_OLD_PKG;
900
901           if (conf->noaction) return 0;
902
903           /* point of no return: no unwinding after this */
904           if (old_pkg && !conf->force_reinstall) {
905                old_pkg->state_want = SW_DEINSTALL;
906
907                if (old_pkg->state_flag & SF_NOPRUNE) {
908                     opkg_message(conf, OPKG_INFO,
909                                  "  not removing obsolesced files because package marked noprune\n");
910                } else {
911                     opkg_message(conf, OPKG_INFO,
912                                  "  removing obsolesced files\n");
913                     remove_obsolesced_files(conf, pkg, old_pkg);
914                }
915                /* removing files from old package, to avoid ghost files */ 
916                remove_data_files_and_list(conf, old_pkg);
917 /* Pigi : It should be better to remove also maintainer and postrem scripts here, just in case*/
918                remove_maintainer_scripts_except_postrm(conf, old_pkg);
919                remove_postrm(conf, old_pkg);
920 /* Pigi */
921
922           }
923
924
925           opkg_message(conf, OPKG_INFO,
926                        "  installing maintainer scripts\n");
927           install_maintainer_scripts(conf, pkg, old_pkg);
928
929           /* the following just returns 0 */
930           remove_disappeared(conf, pkg);
931
932           opkg_message(conf, OPKG_INFO,
933                        "  installing data files\n");
934           install_data_files(conf, pkg);
935
936 /* read comments from function for detail but I will execute this here as all other tests are ok.*/
937           err = check_data_file_clashes_change(conf, pkg, old_pkg);
938
939           opkg_message(conf, OPKG_INFO,
940                        "  resolving conf files\n");
941           resolve_conffiles(conf, pkg);
942
943           pkg->state_status = SS_UNPACKED;
944           old_state_flag = pkg->state_flag;
945           pkg->state_flag &= ~SF_PREFER;
946           opkg_message(conf, OPKG_DEBUG, "   pkg=%s old_state_flag=%x state_flag=%x\n", pkg->name, old_state_flag, pkg->state_flag);
947
948           if (old_pkg && !conf->force_reinstall) {
949                old_pkg->state_status = SS_NOT_INSTALLED;
950           }
951
952           time(&pkg->installed_time);
953
954           opkg_message(conf, OPKG_INFO,
955                        "  cleanup temp files\n");
956           cleanup_temporary_files(conf, pkg);
957
958           ab_pkg = pkg->parent;
959           if (ab_pkg)
960                ab_pkg->state_status = pkg->state_status;
961
962           opkg_message(conf, OPKG_INFO, "Done.\n");
963
964           if (use_signal)
965                signal(SIGINT, old_handler);
966           else
967                sigprocmask(SIG_UNBLOCK, &newset, &oldset);
968
969           return 0;
970      
971
972      UNWIND_POSTRM_UPGRADE_OLD_PKG:
973           postrm_upgrade_old_pkg_unwind(conf, pkg, old_pkg);
974      UNWIND_CHECK_DATA_FILE_CLASHES:
975           check_data_file_clashes_unwind(conf, pkg, old_pkg);
976      UNWIND_BACKUP_MODIFIED_CONFFILES:
977           backup_modified_conffiles_unwind(conf, pkg, old_pkg);
978      UNWIND_PREINST_CONFIGURE:
979           preinst_configure_unwind(conf, pkg, old_pkg);
980      UNWIND_PRERM_DECONFIGURE_CONFLICTORS:
981           prerm_deconfigure_conflictors_unwind(conf, pkg, replacees);
982      UNWIND_PRERM_UPGRADE_OLD_PKG:
983           prerm_upgrade_old_pkg_unwind(conf, pkg, old_pkg);
984      UNWIND_REMOVE_INSTALLED_REPLACEES:
985           pkg_remove_installed_replacees_unwind(conf, replacees);
986
987           opkg_message(conf, OPKG_INFO,
988                        "  cleanup temp files\n");
989           cleanup_temporary_files(conf, pkg);
990
991           opkg_message(conf, OPKG_INFO,
992                        "Failed.\n");
993           if (use_signal)
994                signal(SIGINT, old_handler);
995           else
996                sigprocmask(SIG_UNBLOCK, &newset, &oldset);
997
998           return err;
999      }
1000      opkg_set_current_state (OPKG_STATE_NONE, NULL);
1001 }
1002
1003 static int prerm_upgrade_old_pkg(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1004 {
1005      /* DPKG_INCOMPATIBILITY:
1006         dpkg does some things here that we don't do yet. Do we care?
1007         
1008         1. If a version of the package is already installed, call
1009            old-prerm upgrade new-version
1010         2. If the script runs but exits with a non-zero exit status
1011            new-prerm failed-upgrade old-version
1012            Error unwind, for both the above cases:
1013            old-postinst abort-upgrade new-version
1014      */
1015      return 0;
1016 }
1017
1018 static int prerm_upgrade_old_pkg_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1019 {
1020      /* DPKG_INCOMPATIBILITY:
1021         dpkg does some things here that we don't do yet. Do we care?
1022         (See prerm_upgrade_old_package for details)
1023      */
1024      return 0;
1025 }
1026
1027 static int prerm_deconfigure_conflictors(opkg_conf_t *conf, pkg_t *pkg, pkg_vec_t *conflictors)
1028 {
1029      /* DPKG_INCOMPATIBILITY:
1030         dpkg does some things here that we don't do yet. Do we care?
1031         2. If a 'conflicting' package is being removed at the same time:
1032                 1. If any packages depended on that conflicting package and
1033                    --auto-deconfigure is specified, call, for each such package:
1034                    deconfigured's-prerm deconfigure \
1035                    in-favour package-being-installed version \
1036                    removing conflicting-package version
1037                 Error unwind:
1038                    deconfigured's-postinst abort-deconfigure \
1039                    in-favour package-being-installed-but-failed version \
1040                    removing conflicting-package version
1041
1042                    The deconfigured packages are marked as requiring
1043                    configuration, so that if --install is used they will be
1044                    configured again if possible.
1045                 2. To prepare for removal of the conflicting package, call:
1046                    conflictor's-prerm remove in-favour package new-version
1047                 Error unwind:
1048                    conflictor's-postinst abort-remove in-favour package new-version
1049      */
1050      return 0;
1051 }
1052
1053 static int prerm_deconfigure_conflictors_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_vec_t *conflictors)
1054 {
1055      /* DPKG_INCOMPATIBILITY: dpkg does some things here that we don't
1056         do yet. Do we care?  (See prerm_deconfigure_conflictors for
1057         details) */
1058      return 0;
1059 }
1060
1061 static int preinst_configure(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1062 {
1063      int err;
1064      char *preinst_args;
1065
1066      if (old_pkg) {
1067           char *old_version = pkg_version_str_alloc(old_pkg);
1068           sprintf_alloc(&preinst_args, "upgrade %s", old_version);
1069           free(old_version);
1070      } else if (pkg->state_status == SS_CONFIG_FILES) {
1071           char *pkg_version = pkg_version_str_alloc(pkg);
1072           sprintf_alloc(&preinst_args, "install %s", pkg_version);
1073           free(pkg_version);
1074      } else {
1075           preinst_args = strdup("install");
1076      }
1077
1078      err = pkg_run_script(conf, pkg, "preinst", preinst_args);
1079      if (err) {
1080           opkg_message(conf, OPKG_ERROR,
1081                        "Aborting installation of %s\n", pkg->name);
1082           return 1;
1083      }
1084
1085      free(preinst_args);
1086
1087      return 0;
1088 }
1089
1090 static int preinst_configure_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1091 {
1092      /* DPKG_INCOMPATIBILITY:
1093         dpkg does the following error unwind, should we?
1094         pkg->postrm abort-upgrade old-version
1095         OR pkg->postrm abort-install old-version
1096         OR pkg->postrm abort-install
1097      */
1098      return 0;
1099 }
1100
1101 static int backup_modified_conffiles(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1102 {
1103      int err;
1104      conffile_list_elt_t *iter;
1105      conffile_t *cf;
1106
1107      if (conf->noaction) return 0;
1108
1109      /* Backup all modified conffiles */
1110      if (old_pkg) {
1111           for (iter = old_pkg->conffiles.head; iter; iter = iter->next) {
1112                char *cf_name;
1113                
1114                cf = iter->data;
1115                cf_name = root_filename_alloc(conf, cf->name);
1116
1117                /* Don't worry if the conffile is just plain gone */
1118                if (file_exists(cf_name) && conffile_has_been_modified(conf, cf)) {
1119                     err = backup_make_backup(conf, cf_name);
1120                     if (err) {
1121                          return err;
1122                     }
1123                }
1124                free(cf_name);
1125           }
1126      }
1127
1128      /* Backup all conffiles that were not conffiles in old_pkg */
1129      for (iter = pkg->conffiles.head; iter; iter = iter->next) {
1130           char *cf_name;
1131           cf = iter->data;
1132           cf_name = root_filename_alloc(conf, cf->name);
1133           /* Ignore if this was a conffile in old_pkg as well */
1134           if (pkg_get_conffile(old_pkg, cf->name)) {
1135                continue;
1136           }
1137
1138           if (file_exists(cf_name) && (! backup_exists_for(cf_name))) {
1139                err = backup_make_backup(conf, cf_name);
1140                if (err) {
1141                     return err;
1142                }
1143           }
1144           free(cf_name);
1145      }
1146
1147      return 0;
1148 }
1149
1150 static int backup_modified_conffiles_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1151 {
1152      conffile_list_elt_t *iter;
1153
1154      if (old_pkg) {
1155           for (iter = old_pkg->conffiles.head; iter; iter = iter->next) {
1156                backup_remove(iter->data->name);
1157           }
1158      }
1159
1160      for (iter = pkg->conffiles.head; iter; iter = iter->next) {
1161           backup_remove(iter->data->name);
1162      }
1163
1164      return 0;
1165 }
1166
1167
1168 static int check_data_file_clashes(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1169 {
1170      /* DPKG_INCOMPATIBILITY:
1171         opkg takes a slightly different approach than dpkg at this
1172         point.  dpkg installs each file in the new package while
1173         creating a backup for any file that is replaced, (so that it
1174         can unwind if necessary).  To avoid complexity and redundant
1175         storage, opkg doesn't do any installation until later, (at the
1176         point at which dpkg removes the backups.
1177         
1178         But, we do have to check for data file clashes, since after
1179         installing a package with a file clash, removing either of the
1180         packages involved in the clash has the potential to break the
1181         other package.
1182      */
1183      str_list_t *files_list;
1184      str_list_elt_t *iter;
1185
1186      int clashes = 0;
1187
1188      files_list = pkg_get_installed_files(pkg);
1189      for (iter = files_list->head; iter; iter = iter->next) {
1190           char *root_filename;
1191           char *filename = iter->data;
1192           root_filename = root_filename_alloc(conf, filename);
1193           if (file_exists(root_filename) && (! file_is_dir(root_filename))) {
1194                pkg_t *owner;
1195                pkg_t *obs;
1196                /* Pre-existing conffiles are OK */
1197                /* @@@@ should have way to check that it is a conffile -Jamey */
1198                if (backup_exists_for(root_filename)) {
1199                     continue;
1200                }
1201
1202                /* Pre-existing files are OK if force-overwrite was asserted. */ 
1203                if (conf->force_overwrite) {
1204                     /* but we need to change who owns this file */
1205                     file_hash_set_file_owner(conf, filename, pkg);
1206                     continue;
1207                }
1208
1209                owner = file_hash_get_file_owner(conf, filename);
1210
1211                /* Pre-existing files are OK if owned by the pkg being upgraded. */
1212                if (owner && old_pkg) {
1213                     if (strcmp(owner->name, old_pkg->name) == 0) {
1214                          continue;
1215                     }
1216                }
1217
1218                /* Pre-existing files are OK if owned by a package replaced by new pkg. */
1219                if (owner) {
1220                     opkg_message(conf, OPKG_DEBUG2, "Checking for replaces for %s in package %s\n", filename, owner->name);
1221                     if (pkg_replaces(pkg, owner)) {
1222                          continue;
1223                     }
1224 /* If the file that would be installed is owned by the same package, ( as per a reinstall or similar )
1225    then it's ok to overwrite. */
1226                     if (strcmp(owner->name,pkg->name)==0){
1227                          opkg_message(conf, OPKG_INFO, "Replacing pre-existing file %s owned by package %s\n", filename, owner->name);
1228                          continue;
1229                     }
1230                }
1231
1232                /* Pre-existing files are OK if they are obsolete */
1233                obs = hash_table_get(&conf->obs_file_hash, filename);
1234                if (obs) {
1235                     opkg_message(conf, OPKG_INFO, "Pre-exiting file %s is obsolete.  obs_pkg=%s\n", filename, obs->name);
1236                     continue;
1237                }
1238
1239                /* We have found a clash. */
1240                opkg_message(conf, OPKG_ERROR,
1241                             "Package %s wants to install file %s\n"
1242                             "\tBut that file is already provided by package ",
1243                             pkg->name, filename);
1244                if (owner) {
1245                     opkg_message(conf, OPKG_ERROR,
1246                                  "%s\n", owner->name);
1247                } else {
1248                     opkg_message(conf, OPKG_ERROR,
1249                                  "<no package>\nPlease move this file out of the way and try again.\n");
1250                }
1251                clashes++;
1252           }
1253           free(root_filename);
1254      }
1255      pkg_free_installed_files(pkg);
1256
1257      return clashes;
1258 }
1259
1260 static int check_data_file_clashes_change(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1261 {
1262     /* Basically that's the worst hack I could do to be able to change ownership of
1263        file list, but, being that we have no way to unwind the mods, due to structure
1264        of hash table, probably is the quickest hack too, whishing it would not slow-up thing too much.
1265        What we do here is change the ownership of file in hash if a replace ( or similar events
1266        happens )
1267        Only the action that are needed to change name should be considered.
1268        @@@ To change after 1.0 release.
1269      */
1270      str_list_t *files_list;
1271      str_list_elt_t *iter;
1272
1273      int clashes = 0;
1274
1275      files_list = pkg_get_installed_files(pkg);
1276      for (iter = files_list->head; iter; iter = iter->next) {
1277           char *root_filename;
1278           char *filename = iter->data;
1279           root_filename = root_filename_alloc(conf, filename);
1280           if (file_exists(root_filename) && (! file_is_dir(root_filename))) {
1281                pkg_t *owner;
1282
1283                if (conf->force_overwrite) {
1284                     /* but we need to change who owns this file */
1285                     file_hash_set_file_owner(conf, filename, pkg);
1286                     continue;
1287                }
1288
1289                owner = file_hash_get_file_owner(conf, filename);
1290
1291                /* Pre-existing files are OK if owned by a package replaced by new pkg. */
1292                if (owner) {
1293                     if (pkg_replaces(pkg, owner)) {
1294 /* It's now time to change the owner of that file. 
1295    It has been "replaced" from the new "Replaces", then I need to inform lists file about that.  */
1296                          opkg_message(conf, OPKG_INFO, "Replacing pre-existing file %s owned by package %s\n", filename, owner->name);
1297                          file_hash_set_file_owner(conf, filename, pkg);
1298                          continue;
1299                     }
1300                }
1301
1302           }
1303           free(root_filename);
1304      }
1305      pkg_free_installed_files(pkg);
1306
1307      return clashes;
1308 }
1309
1310 static int check_data_file_clashes_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1311 {
1312      /* Nothing to do since check_data_file_clashes doesn't change state */
1313      return 0;
1314 }
1315
1316 static int postrm_upgrade_old_pkg(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1317 {
1318      /* DPKG_INCOMPATIBILITY: dpkg does the following here, should we?
1319         1. If the package is being upgraded, call
1320            old-postrm upgrade new-version
1321         2. If this fails, attempt:
1322            new-postrm failed-upgrade old-version
1323         Error unwind, for both cases:
1324            old-preinst abort-upgrade new-version    */
1325      return 0;
1326 }
1327
1328 static int postrm_upgrade_old_pkg_unwind(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1329 {
1330      /* DPKG_INCOMPATIBILITY:
1331         dpkg does some things here that we don't do yet. Do we care?
1332         (See postrm_upgrade_old_pkg for details)
1333      */
1334     return 0;
1335 }
1336
1337 static int remove_obsolesced_files(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1338 {
1339      int err;
1340      str_list_t *old_files;
1341      str_list_elt_t *of;
1342      str_list_t *new_files;
1343      str_list_elt_t *nf;
1344
1345      if (old_pkg == NULL) {
1346           return 0;
1347      }
1348
1349      old_files = pkg_get_installed_files(old_pkg);
1350      new_files = pkg_get_installed_files(pkg);
1351
1352      for (of = old_files->head; of; of = of->next) {
1353           pkg_t *owner;
1354           char *old, *new;
1355           old = of->data;
1356           for (nf = new_files->head; nf; nf = nf->next) {
1357                new = nf->data;
1358                if (strcmp(old, new) == 0) {
1359                     goto NOT_OBSOLETE;
1360                }
1361           }
1362           if (file_is_dir(old)) {
1363                continue;
1364           }
1365           owner = file_hash_get_file_owner(conf, old);
1366           if (owner != old_pkg) {
1367                /* in case obsolete file no longer belongs to old_pkg */
1368                continue;
1369           }
1370  
1371           /* old file is obsolete */
1372           opkg_message(conf, OPKG_INFO,
1373                        "    removing obsolete file %s\n", old);
1374           if (!conf->noaction) {
1375                err = unlink(old);
1376                if (err) {
1377                     opkg_message(conf, OPKG_ERROR, "    Warning: remove %s failed: %s\n", old,
1378                                  strerror(errno));
1379                }
1380           }
1381
1382      NOT_OBSOLETE:
1383           ;
1384      }
1385
1386      pkg_free_installed_files(old_pkg);
1387      pkg_free_installed_files(pkg);
1388
1389      return 0;
1390 }
1391
1392 static int remove_obsolete_maintainer_scripts(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1393 {
1394      int i;
1395      int err = 0;
1396      char *globpattern;
1397      glob_t globbuf;
1398      if (0) {
1399           if (!pkg->dest) {
1400                opkg_message(conf, OPKG_ERROR, "%s: no dest for package %s\n", __FUNCTION__, pkg->name);
1401                return -1;
1402           }
1403           sprintf_alloc(&globpattern, "%s/%s.*", pkg->dest->info_dir, pkg->name);
1404           err = glob(globpattern, 0, NULL, &globbuf);
1405           free(globpattern);
1406           if (err) {
1407                return err;
1408           }
1409           /* XXXX this should perhaps only remove the ones that are not overwritten in new package.  Jamey 11/11/2003 */
1410           for (i = 0; i < globbuf.gl_pathc; i++) {
1411                opkg_message(conf, OPKG_DEBUG, "Removing control file %s from old_pkg %s\n",
1412                             globbuf.gl_pathv[i], old_pkg->name);
1413                if (!conf->noaction)
1414                     unlink(globbuf.gl_pathv[i]);
1415           }
1416           globfree(&globbuf);
1417      }
1418      return err;
1419 }
1420
1421 static int install_maintainer_scripts(opkg_conf_t *conf, pkg_t *pkg, pkg_t *old_pkg)
1422 {
1423      int ret;
1424      char *prefix;
1425
1426      if (old_pkg)
1427           remove_obsolete_maintainer_scripts(conf, pkg, old_pkg);
1428      sprintf_alloc(&prefix, "%s.", pkg->name);
1429      ret = pkg_extract_control_files_to_dir_with_prefix(pkg,
1430                                                         pkg->dest->info_dir,
1431                                                         prefix);
1432      free(prefix);
1433      return ret;
1434 }
1435
1436 static int remove_disappeared(opkg_conf_t *conf, pkg_t *pkg)
1437 {
1438      /* DPKG_INCOMPATIBILITY:
1439         This is a fairly sophisticated dpkg operation. Shall we
1440         skip it? */
1441      
1442      /* Any packages all of whose files have been overwritten during the
1443         installation, and which aren't required for dependencies, are
1444         considered to have been removed. For each such package
1445         1. disappearer's-postrm disappear overwriter overwriter-version
1446         2. The package's maintainer scripts are removed
1447         3. It is noted in the status database as being in a sane state,
1448            namely not installed (any conffiles it may have are ignored,
1449            rather than being removed by dpkg). Note that disappearing
1450            packages do not have their prerm called, because dpkg doesn't
1451            know in advance that the package is going to vanish.
1452      */
1453      return 0;
1454 }
1455
1456 static int install_data_files(opkg_conf_t *conf, pkg_t *pkg)
1457 {
1458      int err;
1459
1460      /* opkg takes a slightly different approach to data file backups
1461         than dpkg. Rather than removing backups at this point, we
1462         actually do the data file installation now. See comments in
1463         check_data_file_clashes() for more details. */
1464     
1465      opkg_message(conf, OPKG_INFO,
1466                   "    extracting data files to %s\n", pkg->dest->root_dir);
1467      err = pkg_extract_data_files_to_dir(pkg, pkg->dest->root_dir);
1468      if (err) {
1469           return err;
1470      }
1471
1472      /* XXX: BUG or FEATURE : We are actually loosing the Essential flag,
1473         so we can't save ourself from removing important packages
1474         At this point we (should) have extracted the .control file, so it
1475         would be a good idea to reload the data in it, and set the Essential 
1476         state in *pkg. From now on the Essential is back in status file and
1477         we can protect again.
1478         We should operate this way:
1479         fopen the file ( pkg->dest->root_dir/pkg->name.control )
1480         check for "Essential" in it 
1481         set the value in pkg->essential.
1482         This new routine could be useful also for every other flag
1483         Pigi: 16/03/2004 */
1484      set_flags_from_control(conf, pkg) ;
1485      
1486      opkg_message(conf, OPKG_DEBUG, "    Calling pkg_write_filelist from %s\n", __FUNCTION__);
1487      err = pkg_write_filelist(conf, pkg);
1488      if (err)
1489           return err;
1490
1491      /* XXX: FEATURE: opkg should identify any files which existed
1492         before installation and which were overwritten, (see
1493         check_data_file_clashes()). What it must do is remove any such
1494         files from the filelist of the old package which provided the
1495         file. Otherwise, if the old package were removed at some point
1496         it would break the new package. Removing the new package will
1497         also break the old one, but this cannot be helped since the old
1498         package's file has already been deleted. This is the importance
1499         of check_data_file_clashes(), and only allowing opkg to install
1500         a clashing package with a user force. */
1501
1502      return 0;
1503 }
1504
1505 static int resolve_conffiles(opkg_conf_t *conf, pkg_t *pkg)
1506 {
1507      conffile_list_elt_t *iter;
1508      conffile_t *cf;
1509      char *cf_backup;
1510
1511     char *md5sum;
1512
1513     
1514      if (conf->noaction) return 0;
1515
1516      for (iter = pkg->conffiles.head; iter; iter = iter->next) {
1517           char *root_filename;
1518           cf = iter->data;
1519           root_filename = root_filename_alloc(conf, cf->name);
1520
1521           /* Might need to initialize the md5sum for each conffile */
1522           if (cf->value == NULL) {
1523                cf->value = file_md5sum_alloc(root_filename);
1524           }
1525
1526           if (!file_exists(root_filename)) {
1527                free(root_filename);
1528                continue;
1529           }
1530
1531           cf_backup = backup_filename_alloc(root_filename);
1532
1533
1534           if (file_exists(cf_backup)) {
1535  /* Let's compute md5 to test if files are changed */
1536               md5sum = file_md5sum_alloc(cf_backup);
1537                if (strcmp( cf->value,md5sum) != 0 ) {
1538                   if (conf->force_defaults
1539                       || user_prefers_old_conffile(cf->name, cf_backup) ) {
1540                        rename(cf_backup, root_filename);
1541                   }
1542                }
1543                unlink(cf_backup);
1544                free(md5sum);
1545           }
1546
1547           free(cf_backup);
1548           free(root_filename);
1549      }
1550
1551      return 0;
1552 }
1553
1554 static int user_prefers_old_conffile(const char *file_name, const char *backup)
1555 {
1556      char *response;
1557      const char *short_file_name;
1558
1559      short_file_name = strrchr(file_name, '/');
1560      if (short_file_name) {
1561           short_file_name++;
1562      } else {
1563           short_file_name = file_name;
1564      }
1565
1566      while (1) {
1567           response = get_user_response("    Configuration file '%s'\n"
1568                                        "    ==> File on system created by you or by a script.\n"
1569                                        "    ==> File also in package provided by package maintainer.\n"
1570                                        "       What would you like to do about it ?  Your options are:\n"
1571                                        "        Y or I  : install the package maintainer's version\n"
1572                                        "        N or O  : keep your currently-installed version\n"
1573                                        "          D     : show the differences between the versions (if diff is installed)\n"
1574                                        "     The default action is to keep your current version.\n"
1575                                        "    *** %s (Y/I/N/O/D) [default=N] ? ", file_name, short_file_name);
1576           if (strcmp(response, "y") == 0
1577               || strcmp(response, "i") == 0
1578               || strcmp(response, "yes") == 0) {
1579                free(response);
1580                return 0;
1581           }
1582
1583           if (strcmp(response, "d") == 0) {
1584                char *cmd;
1585
1586                free(response);
1587                /* XXX: BUG rewrite to use exec or busybox's internal diff */
1588                sprintf_alloc(&cmd, "diff -u %s %s", backup, file_name);
1589                xsystem(cmd);
1590                free(cmd);
1591                printf("    [Press ENTER to continue]\n");
1592                response = file_read_line_alloc(stdin);
1593                free(response);
1594                continue;
1595           }
1596
1597           free(response);
1598           return 1;
1599      }
1600 }
1601
1602 /* XXX: CLEANUP: I'd like to move all of the code for
1603    creating/cleaning pkg->tmp_unpack_dir directly into pkg.c. (Then,
1604    it would make sense to cleanup pkg->tmp_unpack_dir directly from
1605    pkg_deinit for example). */
1606 static int cleanup_temporary_files(opkg_conf_t *conf, pkg_t *pkg)
1607 {
1608      DIR *tmp_dir;
1609      struct dirent *dirent;
1610      char *tmp_file;
1611
1612 #ifdef OPKG_DEBUG_NO_TMP_CLEANUP
1613 #error
1614      opkg_message(conf, OPKG_DEBUG,
1615                   "%s: Not cleaning up %s since opkg compiled with OPKG_DEBUG_NO_TMP_CLEANUP\n",
1616                   __FUNCTION__, pkg->tmp_unpack_dir);
1617      return 0;
1618 #endif
1619
1620      if (pkg->tmp_unpack_dir && file_is_dir(pkg->tmp_unpack_dir)) {
1621           tmp_dir = opendir(pkg->tmp_unpack_dir);
1622           if (tmp_dir) {
1623                while (1) {
1624                     dirent = readdir(tmp_dir);
1625                     if (dirent == NULL) {
1626                          break;
1627                     }
1628                     sprintf_alloc(&tmp_file, "%s/%s",
1629                                   pkg->tmp_unpack_dir, dirent->d_name);
1630                     if (! file_is_dir(tmp_file)) {
1631                          unlink(tmp_file);
1632                     }
1633                     free(tmp_file);
1634                }
1635                closedir(tmp_dir);
1636                rmdir(pkg->tmp_unpack_dir);
1637                free(pkg->tmp_unpack_dir);
1638                pkg->tmp_unpack_dir = NULL;
1639           }
1640      }
1641
1642      opkg_message(conf, OPKG_INFO, "cleanup_temporary_files: pkg=%s local_filename=%s tmp_dir=%s\n",
1643                   pkg->name, pkg->local_filename, conf->tmp_dir);
1644      if (pkg->local_filename && strncmp(pkg->local_filename, conf->tmp_dir, strlen(conf->tmp_dir)) == 0) {
1645           unlink(pkg->local_filename);
1646           free(pkg->local_filename);
1647           pkg->local_filename = NULL;
1648      }
1649
1650      return 0;
1651 }
1652
1653 static char *backup_filename_alloc(const char *file_name)
1654 {
1655      char *backup;
1656
1657      sprintf_alloc(&backup, "%s%s", file_name, OPKG_BACKUP_SUFFIX);
1658
1659      return backup;
1660 }
1661
1662 int backup_make_backup(opkg_conf_t *conf, const char *file_name)
1663 {
1664      int err;
1665      char *backup;
1666     
1667      backup = backup_filename_alloc(file_name);
1668      err = file_copy(file_name, backup);
1669      if (err) {
1670           opkg_message(conf, OPKG_ERROR,
1671                        "%s: Failed to copy %s to %s\n",
1672                        __FUNCTION__, file_name, backup);
1673      }
1674
1675      free(backup);
1676
1677      return err;
1678 }
1679
1680 static int backup_exists_for(const char *file_name)
1681 {
1682      int ret;
1683      char *backup;
1684
1685      backup = backup_filename_alloc(file_name);
1686
1687      ret = file_exists(backup);
1688
1689      free(backup);
1690
1691      return ret;
1692 }
1693
1694 static int backup_remove(const char *file_name)
1695 {
1696      char *backup;
1697
1698      backup = backup_filename_alloc(file_name);
1699      unlink(backup);
1700      free(backup);
1701
1702      return 0;
1703 }
1704
1705 \f
1706
1707 #ifdef CONFIG_OPKG_PROCESS_ACTIONS
1708
1709 int opkg_remove_packages(opkg_conf_t *conf, pkg_vec_t *pkgs_to_remove) 
1710 {
1711      /* first, remove the packages that need removing */
1712      for (i = 0 ; i < pkgs_to_remove->len; i++ ) {
1713           pkg_t *pkg = pkgs_to_remove->pkgs[i];
1714           err = opkg_remove_pkg(conf, pkg,0);
1715           if (err) return err;
1716      }
1717      return 0;
1718 }
1719
1720 int opkg_process_actions_sanity_check(opkg_conf_t *conf, pkg_vec_t *pkgs_to_remove, pkg_vec_t *pkgs_superseded, pkg_vec_t *pkgs_to_install)
1721 {
1722      int i;
1723      /* now one more pass checking on the ones that need to be installed */
1724      for (i = 0 ; i < pkgs_to_install->len; i++ ) {
1725           pkg_t *pkg = pkgs_to_install->pkgs[i];
1726           if (pkg->dest == NULL)
1727                pkg->dest = conf->default_dest;
1728
1729           pkg->state_want = SW_INSTALL;
1730
1731           /* Abhaya: conflicts check */
1732           err = check_conflicts_for(conf, pkg);
1733           if (err) { return err; }
1734      }
1735      return 0;
1736 }
1737
1738 int opkg_process_actions_unpack_packages(opkg_conf_t *conf, pkg_vec_t *pkgs_to_remove, pkg_vec_t *pkgs_to_install)
1739 {
1740      int i;
1741      /* now one more pass checking on the ones that need to be installed */
1742      for (i = 0 ; i < pkgs_to_install->len; i++ ) {
1743           pkg_t *pkg = pkgs_to_install->pkgs[i];
1744
1745           /* XXX: FEATURE: Need to really support Provides/Replaces: here at some point */
1746           pkg_vec_t *replacees = pkg_vec_alloc();
1747           pkg_get_installed_replacees(conf, pkg, replacees);
1748
1749           /* XXX: BUG: we really should treat replacement more like an upgrade
1750            *      Instead, we're going to remove the replacees 
1751            */
1752           err = pkg_remove_installed_replacees(conf, replacees);
1753           if (err) return err;
1754           pkg->state_flag |= SF_REMOVED_REPLACEES;
1755      }
1756      return 0;
1757 }
1758
1759 int opkg_process_actions_unpack_packages(opkg_conf_t *conf, pkg_vec_t *pkgs_to_remove, pkg_vec_t *pkgs_to_install)
1760 {
1761      int i;
1762      /* now one more pass checking on the ones that need to be installed */
1763      for (i = 0 ; i < pkgs_to_install->len; i++ ) {
1764           pkg_t *pkg = pkgs_to_install->pkgs[i];
1765           if (pkg->local_filename == NULL) {
1766                err = opkg_download_pkg(conf, pkg, conf->tmp_dir);
1767                if (err) {
1768                     opkg_message(conf, OPKG_ERROR,
1769                                  "Failed to download %s. Perhaps you need to run 'opkg update'?\n",
1770                                  pkg->name);
1771                     return err;
1772                }
1773           }
1774           if (pkg->tmp_unpack_dir == NULL) {
1775                err = unpack_pkg_control_files(conf, pkg);
1776                if (err) return err;
1777           }
1778      }
1779      return 0;
1780 }
1781
1782 int opkg_process_actions_prerm(opkg_conf_t *conf, pkg_vec_t *pkgs_to_install)
1783 {
1784      int i;
1785      /* now one more pass checking on the ones that need to be installed */
1786      for (i = 0 ; i < pkgs_to_install->len; i++ ) {
1787           pkg_t *pkg = pkgs_to_install->pkgs[i];
1788           pkg_t *old_pkg = pkg->old_pkg;
1789
1790           err = prerm_upgrade_old_pkg(conf, pkg, old_pkg);
1791           if (err) return err;
1792
1793           err = prerm_deconfigure_conflictors(conf, pkg, replacees);
1794           if (err) return err;
1795
1796           err = preinst_configure(conf, pkg, old_pkg);
1797           if (err) return err;
1798
1799           err = backup_modified_conffiles(conf, pkg, old_pkg);
1800           if (err) return err;
1801
1802           err = postrm_upgrade_old_pkg(conf, pkg, old_pkg);
1803           if (err) return err;
1804      }
1805      return 0;
1806 }
1807
1808 int opkg_process_actions_install(opkg_conf_t *conf, pkg_vec_t *pkgs_to_install)
1809 {
1810      int i;
1811      /* now one more pass checking on the ones that need to be installed */
1812      for (i = 0 ; i < pkgs_to_install->len; i++ ) {
1813           pkg_t *pkg = pkgs_to_install->pkgs[i];
1814           pkg_t *old_pkg = pkg->old_pkg;
1815
1816           if (old_pkg) {
1817                old_pkg->state_want = SW_DEINSTALL;
1818
1819                if (old_pkg->state_flag & SF_NOPRUNE) {
1820                     opkg_message(conf, OPKG_INFO,
1821                                  "  not removing obsolesced files because package marked noprune\n");
1822                } else {
1823                     opkg_message(conf, OPKG_INFO,
1824                                  "  removing obsolesced files\n");
1825                     remove_obsolesced_files(conf, pkg, old_pkg);
1826                }
1827           }
1828
1829           opkg_message(conf, OPKG_INFO,
1830                        "  installing maintainer scripts\n");
1831           install_maintainer_scripts(conf, pkg, old_pkg);
1832
1833           /* the following just returns 0 */
1834           remove_disappeared(conf, pkg);
1835
1836           opkg_message(conf, OPKG_INFO,
1837                        "  installing data files\n");
1838           install_data_files(conf, pkg);
1839
1840           opkg_message(conf, OPKG_INFO,
1841                        "  resolving conf files\n");
1842           resolve_conffiles(conf, pkg);
1843
1844           pkg->state_status = SS_UNPACKED;
1845
1846           if (old_pkg) {
1847                old_pkg->state_status = SS_NOT_INSTALLED;
1848           }
1849
1850           time(&pkg->installed_time);
1851
1852           opkg_message(conf, OPKG_INFO,
1853                        "  cleanup temp files\n");
1854           cleanup_temporary_files(conf, pkg);
1855
1856           if (pkg->parent)
1857                pkg->parent->state_status = pkg->state_status;
1858      }
1859      return 0;
1860 }
1861
1862 int opkg_process_actions_unwind_prerm(opkg_conf_t *conf, pkg_vec_t *pkgs_to_install)
1863 {
1864      int i;
1865      /* now one more pass checking on the ones that need to be installed */
1866      for (i = 0 ; i < pkgs_to_install->len; i++ ) {
1867           pkg_t *pkg = pkgs_to_install->pkgs[i];
1868           pkg_t *old_pkg = pkg->old_pkg;
1869
1870           if (old_pkg) {
1871                if (old_pkg->state_flags & SF_POSTRM_UPGRADE)
1872                     postrm_upgrade_old_pkg_unwind(conf, pkg, old_pkg);
1873                if (old_pkg->state_flags & SF_CHECK_DATA_FILE_CLASHES)
1874                     check_data_file_clashes_unwind(conf, pkg, old_pkg);
1875                if (old_pkg->state_flags & SF_BACKUP_MODIFIED_CONFFILES)
1876                     backup_modified_conffiles_unwind(conf, pkg, old_pkg);
1877                if (old_pkg->state_flags & SF_PREINST_CONFIGURE)
1878                     preinst_configure_unwind(conf, pkg, old_pkg);
1879                if (old_pkg->state_flags & SF_DECONFIGURE_CONFLICTORS)
1880                     prerm_deconfigure_conflictors_unwind(conf, pkg, replacees);
1881                if (old_pkg->state_flags & SF_PRERM_UPGRADE)
1882                     prerm_upgrade_old_pkg_unwind(conf, pkg, old_pkg);
1883
1884                if (old_pkg->state_flags & SF_REMOVED_REPLACEES)
1885                     remove_installed_replacees_unwind(conf, pkg, old_pkg);
1886
1887           }
1888      }
1889      return 0;
1890 }
1891
1892 /* 
1893  * Perform all the actions.
1894  *
1895  * pkgs_to_remove are packages marked for removal.
1896  * pkgs_superseded are the old packages being replaced by upgrades.
1897  *
1898  * Assumes pkgs_to_install includes all dependences, recursively, sorted in installable order.
1899  */
1900 int opkg_process_actions(opkg_conf_t *conf, pkg_vec_t *pkgs_to_remove, pkg_vec_t *pkgs_superseded, pkg_vec_t *pkgs_to_install)
1901 {
1902      int err;
1903      int i;
1904
1905      err = opkg_remove_packages(conf, pkgs_to_remove);
1906      if (err) return err;
1907
1908      err = opkg_process_actions_sanity_check(conf, pkgs_superseded, pkgs_to_install);
1909      if (err) return err;
1910
1911      err = opkg_process_actions_remove_replacees(conf, pkgs_to_install);
1912      if (err) goto UNWIND;
1913
1914      /* @@@@ look at opkg_install_pkg for handling replacements */
1915      err = opkg_process_actions_unpack_packages(conf, pkgs_to_install);
1916      if (err) goto UNWIND;
1917
1918      /* 
1919       * Now that we have the packages unpacked, we can look for data
1920       * file clashes.  First, we mark the files from the superseded
1921       * packages as obsolete.  Then we scan the files in
1922       * pkgs_to_install, and only complain about clashes with
1923       * non-obsolete files.
1924       */
1925
1926      err = opkg_process_actions_check_data_file_clashes(conf, pkgs_superseded, pkgs_to_install);
1927      if (err) goto UNWIND;
1928
1929      /* this was before checking data file clashes */
1930      err = opkg_process_actions_prerm(conf, pkgs_superseded, pkgs_to_install);
1931      if (err) goto UNWIND;
1932
1933      /* point of no return: no unwinding after this */
1934      err = opkg_process_actions_install(conf, pkgs_to_install);
1935      if (err) return err;
1936
1937      opkg_message(conf, OPKG_INFO, "Done.\n");
1938      return 0;
1939
1940  UNWIND:
1941      opkg_process_actions_unwind(conf, pkgs_to_install);
1942
1943      opkg_message(conf, OPKG_INFO,
1944                   "  cleanup temp files\n");
1945      cleanup_temporary_files(conf, pkg);
1946
1947      opkg_message(conf, OPKG_INFO,
1948                   "Failed.\n");
1949      return err;
1950 }
1951
1952 #endif