3131#include <unistd.h>
3232#include <libgen.h>
3333
34+ #include "xbps.h"
3435#include "xbps_api_impl.h"
3536
3637/*
@@ -56,13 +57,17 @@ xbps_transaction_check_replaces(struct xbps_handle *xhp, xbps_array_t pkgs)
5657
5758 obj = xbps_array_get (pkgs , i );
5859 replaces = xbps_dictionary_get (obj , "replaces" );
59- if (replaces == NULL || xbps_array_count (replaces ) == 0 )
60+ if (replaces == NULL || xbps_array_count (replaces ) == 0 ) {
61+ xbps_dbg_printf ("[replaces] 1\n" );
6062 continue ;
63+ }
6164
6265 if (!xbps_dictionary_get_cstring_nocopy (obj , "pkgver" , & pkgver )) {
66+ xbps_dbg_printf ("[replaces] 2\n" );
6367 return false;
6468 }
6569 if (!xbps_pkg_name (pkgname , XBPS_NAME_SIZE , pkgver )) {
70+ xbps_dbg_printf ("[replaces] 3\n" );
6671 return false;
6772 }
6873
@@ -72,29 +77,40 @@ xbps_transaction_check_replaces(struct xbps_handle *xhp, xbps_array_t pkgs)
7277 for (unsigned int j = 0 ; j < xbps_array_count (replaces ); j ++ ) {
7378 const char * curpkgver = NULL , * pattern = NULL ;
7479 char curpkgname [XBPS_NAME_SIZE ] = {0 };
75- bool instd_auto = false, hold = false;
80+ bool instd_auto = false, hold = false, in_trans_install = false ;
7681 xbps_trans_type_t ttype ;
7782
7883 if (!xbps_array_get_cstring_nocopy (replaces , j , & pattern ))
7984 abort ();
8085
8186 /*
8287 * Find the installed package that matches the pattern
83- * to be replaced.
88+ * to be replaced. Also check if the package would be
89+ * installed in the transaction.
8490 */
8591 if (((instd = xbps_pkgdb_get_pkg (xhp , pattern )) == NULL ) &&
86- ((instd = xbps_pkgdb_get_virtualpkg (xhp , pattern )) == NULL ))
87- continue ;
92+ ((instd = xbps_pkgdb_get_virtualpkg (xhp , pattern )) == NULL )) {
93+ if ((instd = xbps_find_pkg_in_array (pkgs , pattern , XBPS_TRANS_INSTALL )) == NULL ) {
94+ xbps_dbg_printf ("[replaces] 4\n" );
95+ continue ;
96+ }
97+ in_trans_install = true;
98+ xbps_dbg_printf ("[replaces] 4.5\n" );
99+ }
88100
89101 if (!xbps_dictionary_get_cstring_nocopy (instd , "pkgver" , & curpkgver )) {
102+ xbps_dbg_printf ("[replaces] 5\n" );
90103 xbps_object_iterator_release (iter );
91104 return false;
92105 }
93106 /* ignore pkgs on hold mode */
94- if (xbps_dictionary_get_bool (instd , "hold" , & hold ) && hold )
107+ if (xbps_dictionary_get_bool (instd , "hold" , & hold ) && hold ) {
108+ xbps_dbg_printf ("[replaces] 6\n" );
95109 continue ;
110+ }
96111
97112 if (!xbps_pkg_name (curpkgname , XBPS_NAME_SIZE , curpkgver )) {
113+ xbps_dbg_printf ("[replaces] 7\n" );
98114 xbps_object_iterator_release (iter );
99115 return false;
100116 }
@@ -103,6 +119,7 @@ xbps_transaction_check_replaces(struct xbps_handle *xhp, xbps_array_t pkgs)
103119 * due to virtual packages.
104120 */
105121 if (strcmp (pkgname , curpkgname ) == 0 ) {
122+ xbps_dbg_printf ("[replaces] 8\n" );
106123 continue ;
107124 }
108125 /*
@@ -111,41 +128,52 @@ xbps_transaction_check_replaces(struct xbps_handle *xhp, xbps_array_t pkgs)
111128 xbps_dictionary_get_bool (instd , "automatic-install" , & instd_auto );
112129 reppkgd = xbps_find_pkg_in_array (pkgs , curpkgname , 0 );
113130 if (reppkgd ) {
131+ xbps_dbg_printf ("[replaces] 9\n" );
114132 ttype = xbps_transaction_pkg_type (reppkgd );
115- if (ttype == XBPS_TRANS_REMOVE || ttype == XBPS_TRANS_HOLD )
133+ if (ttype == XBPS_TRANS_REMOVE || ttype == XBPS_TRANS_HOLD ) {
134+ xbps_dbg_printf ("[replaces] 10\n" );
116135 continue ;
136+ }
117137 if (!xbps_dictionary_get_cstring_nocopy (reppkgd ,
118138 "pkgver" , & curpkgver )) {
139+ xbps_dbg_printf ("[replaces] 11\n" );
119140 xbps_object_iterator_release (iter );
120141 return false;
121142 }
122143 if (!xbps_match_virtual_pkg_in_dict (reppkgd , pattern ) &&
123- !xbps_pkgpattern_match (curpkgver , pattern ))
144+ !xbps_pkgpattern_match (curpkgver , pattern )) {
145+ xbps_dbg_printf ("[replaces] 12\n" );
124146 continue ;
147+ }
125148 /*
126149 * Package contains replaces="pkgpattern", but the
127150 * package that should be replaced is also in the
128151 * transaction and it's going to be updated.
129152 */
130153 if (!instd_auto ) {
154+ xbps_dbg_printf ("[replaces] 13\n" );
131155 xbps_dictionary_remove (obj , "automatic-install" );
132156 }
133157 if (!xbps_dictionary_set_bool (reppkgd , "replaced" , true)) {
158+ xbps_dbg_printf ("[replaces] 14\n" );
134159 xbps_object_iterator_release (iter );
135160 return false;
136161 }
137- if (!xbps_transaction_pkg_type_set (reppkgd , XBPS_TRANS_REMOVE )) {
162+ if (!xbps_transaction_pkg_type_set (reppkgd , in_trans_install ? XBPS_TRANS_REPLACED : XBPS_TRANS_REMOVE )) {
163+ xbps_dbg_printf ("[replaces] 15\n" );
138164 xbps_object_iterator_release (iter );
139165 return false;
140166 }
141167 if (xbps_array_replace_dict_by_name (pkgs , reppkgd , curpkgname ) != 0 ) {
168+ xbps_dbg_printf ("[replaces] 16\n" );
142169 xbps_object_iterator_release (iter );
143170 return false;
144171 }
145172 xbps_dbg_printf (
146173 "Package `%s' in transaction will be "
147174 "replaced by `%s', matched with `%s'\n" ,
148175 curpkgver , pkgver , pattern );
176+ xbps_dbg_printf ("[replaces] 17\n" );
149177 continue ;
150178 }
151179 /*
@@ -154,29 +182,35 @@ xbps_transaction_check_replaces(struct xbps_handle *xhp, xbps_array_t pkgs)
154182 * the automatic-install object.
155183 */
156184 if (xbps_match_virtual_pkg_in_dict (obj , pattern )) {
185+ xbps_dbg_printf ("[replaces] 18\n" );
157186 if (!instd_auto ) {
187+ xbps_dbg_printf ("[replaces] 19\n" );
158188 xbps_dictionary_remove (obj , "automatic-install" );
159189 }
160190 }
161191 /*
162192 * Add package dictionary into the transaction and mark
163193 * it as to be "removed".
164194 */
165- if (!xbps_transaction_pkg_type_set (instd , XBPS_TRANS_REMOVE )) {
195+ if (!xbps_transaction_pkg_type_set (instd , in_trans_install ? XBPS_TRANS_REPLACED : XBPS_TRANS_REMOVE )) {
196+ xbps_dbg_printf ("[replaces] 20\n" );
166197 xbps_object_iterator_release (iter );
167198 return false;
168199 }
169200 if (!xbps_dictionary_set_bool (instd , "replaced" , true)) {
201+ xbps_dbg_printf ("[replaces] 21\n" );
170202 xbps_object_iterator_release (iter );
171203 return false;
172204 }
173205 if (!xbps_array_add_first (pkgs , instd )) {
206+ xbps_dbg_printf ("[replaces] 22\n" );
174207 xbps_object_iterator_release (iter );
175208 return false;
176209 }
177210 xbps_dbg_printf (
178211 "Package `%s' will be replaced by `%s', "
179212 "matched with `%s'\n" , curpkgver , pkgver , pattern );
213+ xbps_dbg_printf ("[replaces] 23\n" );
180214 }
181215 xbps_object_iterator_release (iter );
182216 }
0 commit comments