1 /*#############################################################################
3 # Pakfire - The IPFire package management system #
4 # Copyright (C) 2013 Pakfire development team #
6 # This program is free software: you can redistribute it and/or modify #
7 # it under the terms of the GNU General Public License as published by #
8 # the Free Software Foundation, either version 3 of the License, or #
9 # (at your option) any later version. #
11 # This program is distributed in the hope that it will be useful, #
12 # but WITHOUT ANY WARRANTY; without even the implied warranty of #
13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the #
14 # GNU General Public License for more details. #
16 # You should have received a copy of the GNU General Public License #
17 # along with this program. If not, see <http://www.gnu.org/licenses/>. #
19 #############################################################################*/
27 #include <solv/pool.h>
28 #include <solv/pooltypes.h>
29 #include <solv/repo.h>
30 #include <solv/solvable.h>
32 #include <pakfire/cache.h>
33 #include <pakfire/constants.h>
34 #include <pakfire/file.h>
35 #include <pakfire/i18n.h>
36 #include <pakfire/package.h>
37 #include <pakfire/packagecache.h>
38 #include <pakfire/pool.h>
39 #include <pakfire/private.h>
40 #include <pakfire/relation.h>
41 #include <pakfire/relationlist.h>
42 #include <pakfire/repo.h>
43 #include <pakfire/repocache.h>
44 #include <pakfire/util.h>
46 static Pool
* pakfire_package_get_solv_pool(PakfirePackage pkg
) {
47 return pakfire_pool_get_solv_pool(pkg
->pool
);
50 static void pakfire_package_add_self_provides(PakfirePool pool
, PakfirePackage pkg
, const char* name
, const char* evr
) {
51 PakfireRelation relation
= pakfire_relation_create(pool
, name
, PAKFIRE_EQ
, evr
);
52 pakfire_package_add_provides(pkg
, relation
);
54 pakfire_relation_free(relation
);
57 PAKFIRE_EXPORT PakfirePackage
pakfire_package_create(PakfirePool pool
, Id id
) {
58 PakfirePackage pkg
= pakfire_calloc(1, sizeof(*pkg
));
60 pkg
->pool
= pakfire_pool_ref(pool
);
63 // Initialize reference counter
70 PAKFIRE_EXPORT PakfirePackage
pakfire_package_create2(PakfirePool pool
, PakfireRepo repo
, const char* name
, const char* evr
, const char* arch
) {
71 PakfirePackage pkg
= pakfire_repo_add_package(repo
);
73 pakfire_package_set_name(pkg
, name
);
74 pakfire_package_set_evr(pkg
, evr
);
75 pakfire_package_set_arch(pkg
, arch
);
77 pakfire_package_add_self_provides(pool
, pkg
, name
, evr
);
82 static void pakfire_package_free(PakfirePackage pkg
) {
83 pakfire_pool_unref(pkg
->pool
);
84 pakfire_package_filelist_remove(pkg
);
88 PAKFIRE_EXPORT PakfirePackage
pakfire_package_ref(PakfirePackage pkg
) {
94 PAKFIRE_EXPORT PakfirePackage
pakfire_package_unref(PakfirePackage pkg
) {
101 pakfire_package_free(pkg
);
105 static Solvable
* get_solvable(PakfirePackage pkg
) {
106 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
108 return pool_id2solvable(pool
, pkg
->id
);
111 static Repo
* pakfire_package_solv_repo(PakfirePackage pkg
) {
112 Solvable
* s
= get_solvable(pkg
);
117 static Id
pakfire_package_get_handle(PakfirePackage pkg
) {
118 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
119 Solvable
* s
= get_solvable(pkg
);
121 return s
- pool
->solvables
;
124 PAKFIRE_EXPORT
int pakfire_package_identical(PakfirePackage pkg1
, PakfirePackage pkg2
) {
125 return pkg1
->id
== pkg2
->id
;
128 PAKFIRE_EXPORT
int pakfire_package_cmp(PakfirePackage pkg1
, PakfirePackage pkg2
) {
129 Pool
* pool
= pakfire_package_get_solv_pool(pkg1
);
131 Solvable
* s1
= get_solvable(pkg1
);
132 Solvable
* s2
= get_solvable(pkg2
);
135 const char* str1
= pool_id2str(pool
, s1
->name
);
136 const char* str2
= pool_id2str(pool
, s2
->name
);
138 int ret
= strcmp(str1
, str2
);
142 // Check the version string
143 ret
= pakfire_package_evr_cmp(pkg1
, pkg2
);
147 // Check repositories
148 PakfireRepo repo1
= pakfire_package_get_repo(pkg1
);
149 PakfireRepo repo2
= pakfire_package_get_repo(pkg2
);
151 if (repo1
&& repo2
) {
152 ret
= pakfire_repo_cmp(repo1
, repo2
);
154 pakfire_repo_free(repo1
);
155 pakfire_repo_free(repo2
);
161 // Check package architectures
162 str1
= pool_id2str(pool
, s1
->arch
);
163 str2
= pool_id2str(pool
, s2
->arch
);
165 return strcmp(str1
, str2
);
168 PAKFIRE_EXPORT
int pakfire_package_evr_cmp(PakfirePackage pkg1
, PakfirePackage pkg2
) {
169 Pool
* pool
= pakfire_package_get_solv_pool(pkg1
);
171 Solvable
* s1
= get_solvable(pkg1
);
172 Solvable
* s2
= get_solvable(pkg2
);
174 return pool_evrcmp(pool
, s1
->evr
, s2
->evr
, EVRCMP_COMPARE
);
177 PAKFIRE_EXPORT Id
pakfire_package_id(PakfirePackage pkg
) {
181 PAKFIRE_EXPORT
char* pakfire_package_get_nevra(PakfirePackage pkg
) {
182 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
183 Solvable
* s
= get_solvable(pkg
);
185 const char* nevra
= pool_solvable2str(pool
, s
);
187 return pakfire_strdup(nevra
);
190 PAKFIRE_EXPORT
const char* pakfire_package_get_name(PakfirePackage pkg
) {
191 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
192 Solvable
* s
= get_solvable(pkg
);
194 return pool_id2str(pool
, s
->name
);
197 PAKFIRE_EXPORT
void pakfire_package_set_name(PakfirePackage pkg
, const char* name
) {
198 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
199 Solvable
* s
= get_solvable(pkg
);
201 s
->name
= pool_str2id(pool
, name
, 1);
204 PAKFIRE_EXPORT
const char* pakfire_package_get_evr(PakfirePackage pkg
) {
205 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
206 Solvable
* s
= get_solvable(pkg
);
208 return pool_id2str(pool
, s
->evr
);
211 PAKFIRE_EXPORT
void pakfire_package_set_evr(PakfirePackage pkg
, const char* evr
) {
212 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
213 Solvable
* s
= get_solvable(pkg
);
215 s
->evr
= pool_str2id(pool
, evr
, 1);
218 static void split_evr(Pool
* pool
, const char* evr_c
, char** epoch
, char** version
, char** release
) {
219 char* evr
= pakfire_pool_tmpdup(pool
, evr_c
);
222 for (e
= evr
+ 1; *e
!= ':' && *e
!= '-'; ++e
)
230 } else { /* *e == ':' */
234 for (r
= v
+ 1; *r
!= '-'; ++r
)
245 PAKFIRE_EXPORT
unsigned long pakfire_package_get_epoch(PakfirePackage pkg
) {
246 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
247 char *e
, *v
, *r
, *endptr
;
249 unsigned long epoch
= 0;
251 split_evr(pool
, pakfire_package_get_evr(pkg
), &e
, &v
, &r
);
254 long int converted
= strtol(e
, &endptr
, 10);
255 assert(converted
> 0);
256 assert(*endptr
== '\0');
263 PAKFIRE_EXPORT
const char* pakfire_package_get_version(PakfirePackage pkg
) {
264 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
267 split_evr(pool
, pakfire_package_get_evr(pkg
), &e
, &v
, &r
);
268 return pakfire_strdup(v
);
271 PAKFIRE_EXPORT
const char* pakfire_package_get_release(PakfirePackage pkg
) {
272 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
275 split_evr(pool
, pakfire_package_get_evr(pkg
), &e
, &v
, &r
);
276 return pakfire_strdup(r
);
279 PAKFIRE_EXPORT
const char* pakfire_package_get_arch(PakfirePackage pkg
) {
280 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
281 Solvable
* s
= get_solvable(pkg
);
283 return pool_id2str(pool
, s
->arch
);
286 PAKFIRE_EXPORT
void pakfire_package_set_arch(PakfirePackage pkg
, const char* arch
) {
287 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
288 Solvable
* s
= get_solvable(pkg
);
290 s
->arch
= pool_str2id(pool
, arch
, 1);
293 static void pakfire_package_internalize_repo(PakfirePackage pkg
) {
294 PakfireRepo repo
= pakfire_package_get_repo(pkg
);
296 pakfire_repo_internalize(repo
);
297 pakfire_repo_free(repo
);
301 static const char* pakfire_package_get_string(PakfirePackage pkg
, int key
) {
302 pakfire_package_internalize_repo(pkg
);
304 Solvable
* s
= get_solvable(pkg
);
305 const char* str
= solvable_lookup_str(s
, key
);
310 if (strlen(str
) == 0)
316 static void pakfire_package_set_string(PakfirePackage pkg
, int key
, const char* value
) {
317 Solvable
* s
= get_solvable(pkg
);
322 solvable_set_str(s
, key
, value
);
325 PAKFIRE_EXPORT
const char* pakfire_package_get_uuid(PakfirePackage pkg
) {
326 return pakfire_package_get_string(pkg
, SOLVABLE_PKGID
);
329 PAKFIRE_EXPORT
void pakfire_package_set_uuid(PakfirePackage pkg
, const char* uuid
) {
330 pakfire_package_set_string(pkg
, SOLVABLE_PKGID
, uuid
);
333 PAKFIRE_EXPORT
const char* pakfire_package_get_checksum(PakfirePackage pkg
) {
334 return pakfire_package_get_string(pkg
, SOLVABLE_CHECKSUM
);
337 PAKFIRE_EXPORT
void pakfire_package_set_checksum(PakfirePackage pkg
, const char* checksum
) {
338 pakfire_package_set_string(pkg
, SOLVABLE_CHECKSUM
, checksum
);
341 PAKFIRE_EXPORT
const char* pakfire_package_get_summary(PakfirePackage pkg
) {
342 return pakfire_package_get_string(pkg
, SOLVABLE_SUMMARY
);
345 PAKFIRE_EXPORT
void pakfire_package_set_summary(PakfirePackage pkg
, const char* summary
) {
346 pakfire_package_set_string(pkg
, SOLVABLE_SUMMARY
, summary
);
349 PAKFIRE_EXPORT
const char* pakfire_package_get_description(PakfirePackage pkg
) {
350 return pakfire_package_get_string(pkg
, SOLVABLE_DESCRIPTION
);
353 PAKFIRE_EXPORT
void pakfire_package_set_description(PakfirePackage pkg
, const char* description
) {
354 pakfire_package_set_string(pkg
, SOLVABLE_DESCRIPTION
, description
);
357 PAKFIRE_EXPORT
const char* pakfire_package_get_license(PakfirePackage pkg
) {
358 return pakfire_package_get_string(pkg
, SOLVABLE_LICENSE
);
361 PAKFIRE_EXPORT
void pakfire_package_set_license(PakfirePackage pkg
, const char* license
) {
362 pakfire_package_set_string(pkg
, SOLVABLE_LICENSE
, license
);
365 PAKFIRE_EXPORT
const char* pakfire_package_get_url(PakfirePackage pkg
) {
366 return pakfire_package_get_string(pkg
, SOLVABLE_URL
);
369 PAKFIRE_EXPORT
void pakfire_package_set_url(PakfirePackage pkg
, const char* url
) {
370 pakfire_package_set_string(pkg
, SOLVABLE_URL
, url
);
373 #warning the groups functions need to be refactored
375 PAKFIRE_EXPORT
const char** pakfire_package_get_groups(PakfirePackage pkg
) {
376 const char* groups
= pakfire_package_get_string(pkg
, SOLVABLE_GROUP
);
378 const char** grouplist
= NULL
;
379 char* group
= strtok((char *)groups
, " ");
382 while (group
!= NULL
) {
383 grouplist
= realloc(grouplist
, sizeof(char *) * ++i
);
385 grouplist
[i
- 1] = group
;
387 group
= strtok(NULL
, " ");
394 PAKFIRE_EXPORT
void pakfire_package_set_groups(PakfirePackage pkg
, const char** grouplist
) {
395 char groups
[2048] = "";
399 while ((group
= *grouplist
++) != NULL
) {
403 strcat(groups
, group
);
405 groups
[sizeof(groups
) - 1] = '\0';
409 pakfire_package_set_string(pkg
, SOLVABLE_GROUP
, (const char *)&groups
);
412 PAKFIRE_EXPORT
const char* pakfire_package_get_vendor(PakfirePackage pkg
) {
413 return pakfire_package_get_string(pkg
, SOLVABLE_VENDOR
);
416 PAKFIRE_EXPORT
void pakfire_package_set_vendor(PakfirePackage pkg
, const char* vendor
) {
417 pakfire_package_set_string(pkg
, SOLVABLE_VENDOR
, vendor
);
420 PAKFIRE_EXPORT
const char* pakfire_package_get_maintainer(PakfirePackage pkg
) {
421 return pakfire_package_get_string(pkg
, SOLVABLE_PACKAGER
);
424 PAKFIRE_EXPORT
void pakfire_package_set_maintainer(PakfirePackage pkg
, const char* maintainer
) {
425 pakfire_package_set_string(pkg
, SOLVABLE_PACKAGER
, maintainer
);
428 PAKFIRE_EXPORT
const char* pakfire_package_get_filename(PakfirePackage pkg
) {
429 return pakfire_package_get_string(pkg
, SOLVABLE_MEDIAFILE
);
432 PAKFIRE_EXPORT
void pakfire_package_set_filename(PakfirePackage pkg
, const char* filename
) {
433 pakfire_package_set_string(pkg
, SOLVABLE_MEDIAFILE
, filename
);
436 PAKFIRE_EXPORT
int pakfire_package_is_installed(PakfirePackage pkg
) {
437 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
438 Solvable
* s
= get_solvable(pkg
);
440 return pool
->installed
== s
->repo
;
443 static unsigned long long pakfire_package_get_num(PakfirePackage pkg
, Id type
) {
444 pakfire_package_internalize_repo(pkg
);
446 Solvable
* s
= get_solvable(pkg
);
447 return solvable_lookup_num(s
, type
, 0);
450 static void pakfire_package_set_num(PakfirePackage pkg
, Id type
, unsigned long long value
) {
451 Solvable
* s
= get_solvable(pkg
);
453 solvable_set_num(s
, type
, value
);
456 PAKFIRE_EXPORT
unsigned long long pakfire_package_get_downloadsize(PakfirePackage pkg
) {
457 return pakfire_package_get_num(pkg
, SOLVABLE_DOWNLOADSIZE
);
460 PAKFIRE_EXPORT
void pakfire_package_set_downloadsize(PakfirePackage pkg
, unsigned long long downloadsize
) {
461 return pakfire_package_set_num(pkg
, SOLVABLE_DOWNLOADSIZE
, downloadsize
);
464 PAKFIRE_EXPORT
unsigned long long pakfire_package_get_installsize(PakfirePackage pkg
) {
465 return pakfire_package_get_num(pkg
, SOLVABLE_INSTALLSIZE
);
468 PAKFIRE_EXPORT
void pakfire_package_set_installsize(PakfirePackage pkg
, unsigned long long installsize
) {
469 return pakfire_package_set_num(pkg
, SOLVABLE_INSTALLSIZE
, installsize
);
472 PAKFIRE_EXPORT
unsigned long long pakfire_package_get_size(PakfirePackage pkg
) {
473 if (pakfire_package_is_installed(pkg
))
474 return pakfire_package_get_installsize(pkg
);
476 return pakfire_package_get_downloadsize(pkg
);
479 PAKFIRE_EXPORT
const char* pakfire_package_get_buildhost(PakfirePackage pkg
) {
480 return pakfire_package_get_string(pkg
, SOLVABLE_BUILDHOST
);
483 PAKFIRE_EXPORT
void pakfire_package_set_buildhost(PakfirePackage pkg
, const char* buildhost
) {
484 pakfire_package_set_string(pkg
, SOLVABLE_BUILDHOST
, buildhost
);
487 PAKFIRE_EXPORT
unsigned long long pakfire_package_get_buildtime(PakfirePackage pkg
) {
488 return pakfire_package_get_num(pkg
, SOLVABLE_BUILDTIME
);
491 PAKFIRE_EXPORT
void pakfire_package_set_buildtime(PakfirePackage pkg
, unsigned long long buildtime
) {
492 pakfire_package_set_num(pkg
, SOLVABLE_BUILDTIME
, buildtime
);
495 PAKFIRE_EXPORT
unsigned long long pakfire_package_get_installtime(PakfirePackage pkg
) {
496 return pakfire_package_get_num(pkg
, SOLVABLE_INSTALLTIME
);
499 static PakfireRelationList
pakfire_package_get_relationlist(PakfirePackage pkg
, Id type
) {
503 Solvable
* s
= get_solvable(pkg
);
504 solvable_lookup_idarray(s
, type
, &q
);
506 PakfireRelationList relationlist
= pakfire_relationlist_from_queue(pkg
->pool
, q
);
513 static void pakfire_package_set_relationlist(PakfirePackage pkg
, Id type
, PakfireRelationList relationlist
) {
515 // This implemention should be the fastest, but unfortunately does not work.
517 pakfire_relationlist_clone_to_queue(relationlist
, &q
);
519 Solvable
* s
= get_solvable(pkg
);
520 solvable_set_idarray(s
, type
, &q
);
525 Solvable
* s
= get_solvable(pkg
);
526 solvable_unset(s
, type
);
528 int count
= pakfire_relationlist_count(relationlist
);
529 for (int i
= 0; i
< count
; i
++) {
530 PakfireRelation relation
= pakfire_relationlist_get_clone(relationlist
, i
);
531 solvable_add_idarray(s
, type
, relation
->id
);
533 pakfire_relation_free(relation
);
537 static void pakfire_package_add_relation(PakfirePackage pkg
, Id type
, PakfireRelation relation
) {
538 Solvable
* s
= get_solvable(pkg
);
540 solvable_add_idarray(s
, type
, relation
->id
);
543 PAKFIRE_EXPORT PakfireRelationList
pakfire_package_get_provides(PakfirePackage pkg
) {
544 return pakfire_package_get_relationlist(pkg
, SOLVABLE_PROVIDES
);
547 PAKFIRE_EXPORT
void pakfire_package_set_provides(PakfirePackage pkg
, PakfireRelationList relationlist
) {
548 pakfire_package_set_relationlist(pkg
, SOLVABLE_PROVIDES
, relationlist
);
551 PAKFIRE_EXPORT
void pakfire_package_add_provides(PakfirePackage pkg
, PakfireRelation relation
) {
552 pakfire_package_add_relation(pkg
, SOLVABLE_PROVIDES
, relation
);
555 PAKFIRE_EXPORT PakfireRelationList
pakfire_package_get_prerequires(PakfirePackage pkg
) {
560 PAKFIRE_EXPORT PakfireRelationList
pakfire_package_get_requires(PakfirePackage pkg
) {
561 return pakfire_package_get_relationlist(pkg
, SOLVABLE_REQUIRES
);
564 PAKFIRE_EXPORT
void pakfire_package_set_requires(PakfirePackage pkg
, PakfireRelationList relationlist
) {
565 pakfire_package_set_relationlist(pkg
, SOLVABLE_REQUIRES
, relationlist
);
568 PAKFIRE_EXPORT
void pakfire_package_add_requires(PakfirePackage pkg
, PakfireRelation relation
) {
569 pakfire_package_add_relation(pkg
, SOLVABLE_REQUIRES
, relation
);
572 PAKFIRE_EXPORT PakfireRelationList
pakfire_package_get_conflicts(PakfirePackage pkg
) {
573 return pakfire_package_get_relationlist(pkg
, SOLVABLE_CONFLICTS
);
576 PAKFIRE_EXPORT
void pakfire_package_set_conflicts(PakfirePackage pkg
, PakfireRelationList relationlist
) {
577 pakfire_package_set_relationlist(pkg
, SOLVABLE_CONFLICTS
, relationlist
);
580 PAKFIRE_EXPORT
void pakfire_package_add_conflicts(PakfirePackage pkg
, PakfireRelation relation
) {
581 pakfire_package_add_relation(pkg
, SOLVABLE_CONFLICTS
, relation
);
584 PAKFIRE_EXPORT PakfireRelationList
pakfire_package_get_obsoletes(PakfirePackage pkg
) {
585 return pakfire_package_get_relationlist(pkg
, SOLVABLE_OBSOLETES
);
588 PAKFIRE_EXPORT
void pakfire_package_set_obsoletes(PakfirePackage pkg
, PakfireRelationList relationlist
) {
589 pakfire_package_set_relationlist(pkg
, SOLVABLE_OBSOLETES
, relationlist
);
592 PAKFIRE_EXPORT
void pakfire_package_add_obsoletes(PakfirePackage pkg
, PakfireRelation relation
) {
593 pakfire_package_add_relation(pkg
, SOLVABLE_OBSOLETES
, relation
);
596 PAKFIRE_EXPORT PakfireRelationList
pakfire_package_get_recommends(PakfirePackage pkg
) {
597 return pakfire_package_get_relationlist(pkg
, SOLVABLE_RECOMMENDS
);
600 PAKFIRE_EXPORT
void pakfire_package_set_recommends(PakfirePackage pkg
, PakfireRelationList relationlist
) {
601 pakfire_package_set_relationlist(pkg
, SOLVABLE_RECOMMENDS
, relationlist
);
604 PAKFIRE_EXPORT
void pakfire_package_add_recommends(PakfirePackage pkg
, PakfireRelation relation
) {
605 pakfire_package_add_relation(pkg
, SOLVABLE_RECOMMENDS
, relation
);
608 PAKFIRE_EXPORT PakfireRelationList
pakfire_package_get_suggests(PakfirePackage pkg
) {
609 return pakfire_package_get_relationlist(pkg
, SOLVABLE_SUGGESTS
);
612 PAKFIRE_EXPORT
void pakfire_package_set_suggests(PakfirePackage pkg
, PakfireRelationList relationlist
) {
613 pakfire_package_set_relationlist(pkg
, SOLVABLE_SUGGESTS
, relationlist
);
616 PAKFIRE_EXPORT
void pakfire_package_add_suggests(PakfirePackage pkg
, PakfireRelation relation
) {
617 pakfire_package_add_relation(pkg
, SOLVABLE_SUGGESTS
, relation
);
620 PAKFIRE_EXPORT PakfireRepo
pakfire_package_get_repo(PakfirePackage pkg
) {
621 Solvable
* s
= get_solvable(pkg
);
623 return pakfire_repo_create_from_repo(pkg
->pool
, s
->repo
);
626 PAKFIRE_EXPORT
void pakfire_package_set_repo(PakfirePackage pkg
, PakfireRepo repo
) {
627 Solvable
* s
= get_solvable(pkg
);
629 s
->repo
= pakfire_repo_get_solv_repo(repo
);
632 PAKFIRE_EXPORT
char* pakfire_package_get_location(PakfirePackage pkg
) {
633 pakfire_package_internalize_repo(pkg
);
635 Solvable
* s
= get_solvable(pkg
);
637 const char* location
= solvable_get_location(s
, NULL
);
638 return pakfire_strdup(location
);
641 static void pakfire_package_dump_add_line(char** str
, const char* key
, const char* val
) {
643 asprintf(str
, "%s%-15s: %s\n", *str
, key
? key
: "", val
);
646 static void pakfire_package_dump_add_lines(char** str
, const char* key
, const char* val
) {
647 const char* string
= val
;
650 char line
[STRING_SIZE
];
654 if (*string
== '\n') {
659 line
[counter
++] = *string
++;
661 line
[counter
] = '\0';
664 pakfire_package_dump_add_line(str
, key
, line
);
670 static void pakfire_package_dump_add_line_date(char** str
, const char* key
, unsigned long long date
) {
671 // Convert from integer to tm struct.
672 struct tm
* timer
= gmtime((time_t *)&date
);
674 char val
[STRING_SIZE
];
675 strftime(val
, STRING_SIZE
, "%a, %d %b %Y %T %z", timer
);
677 pakfire_package_dump_add_line(str
, key
, val
);
680 static void pakfire_package_dump_add_line_relations(char** str
, const char* key
, PakfireRelationList deps
) {
681 int count
= pakfire_relationlist_count(deps
);
682 for (int i
= 0; i
< count
; i
++) {
683 PakfireRelation relation
= pakfire_relationlist_get_clone(deps
, i
);
686 char* dep
= pakfire_relation_str(relation
);
687 pakfire_relation_free(relation
);
689 // Stop here and don't list any files.
690 if (strcmp(PAKFIRE_SOLVABLE_FILEMARKER
, dep
) == 0)
694 pakfire_package_dump_add_line(str
, (i
== 0) ? key
: "", dep
);
701 static void pakfire_package_dump_add_line_size(char** str
, const char* key
, unsigned long long size
) {
702 char* val
= pakfire_format_size(size
);
705 pakfire_package_dump_add_line(str
, key
, val
);
710 PAKFIRE_EXPORT
char* pakfire_package_dump(PakfirePackage pkg
, int flags
) {
714 const char* name
= pakfire_package_get_name(pkg
);
715 pakfire_package_dump_add_line(&string
, _("Name"), name
);
718 const char* version
= pakfire_package_get_version(pkg
);
719 pakfire_package_dump_add_line(&string
, _("Version"), version
);
722 const char* release
= pakfire_package_get_release(pkg
);
723 pakfire_package_dump_add_line(&string
, _("Release"), release
);
726 unsigned long long size
= pakfire_package_get_size(pkg
);
727 pakfire_package_dump_add_line_size(&string
, _("Size"), size
);
730 if (pakfire_package_is_installed(pkg
)) {
731 unsigned long long installsize
= pakfire_package_get_installsize(pkg
);
732 pakfire_package_dump_add_line_size(&string
, _("Installed size"), installsize
);
736 unsigned long long downloadsize
= pakfire_package_get_downloadsize(pkg
);
737 pakfire_package_dump_add_line_size(&string
, _("Download size"), downloadsize
);
740 PakfireRepo repo
= pakfire_package_get_repo(pkg
);
742 const char* repo_name
= pakfire_repo_get_name(repo
);
743 pakfire_package_dump_add_line(&string
, _("Repo"), repo_name
);
745 pakfire_repo_free(repo
);
749 const char* summary
= pakfire_package_get_summary(pkg
);
750 pakfire_package_dump_add_line(&string
, _("Summary"), summary
);
753 const char* description
= pakfire_package_get_description(pkg
);
754 pakfire_package_dump_add_lines(&string
, _("Description"), description
);
760 const char* url
= pakfire_package_get_url(pkg
);
761 pakfire_package_dump_add_line(&string
, _("URL"), url
);
764 const char* license
= pakfire_package_get_license(pkg
);
765 pakfire_package_dump_add_line(&string
, _("License"), license
);
767 if (flags
& PAKFIRE_PKG_DUMP_LONG
) {
769 const char* maintainer
= pakfire_package_get_maintainer(pkg
);
770 pakfire_package_dump_add_line(&string
, _("Maintainer"), maintainer
);
773 const char* vendor
= pakfire_package_get_vendor(pkg
);
774 pakfire_package_dump_add_line(&string
, _("Vendor"), vendor
);
777 const char* uuid
= pakfire_package_get_uuid(pkg
);
778 pakfire_package_dump_add_line(&string
, _("UUID"), uuid
);
781 unsigned long long buildtime
= pakfire_package_get_buildtime(pkg
);
782 pakfire_package_dump_add_line_date(&string
, _("Build date"), buildtime
);
785 const char* buildhost
= pakfire_package_get_buildhost(pkg
);
786 pakfire_package_dump_add_line(&string
, _("Build host"), buildhost
);
788 PakfireRelationList provides
= pakfire_package_get_provides(pkg
);
790 pakfire_package_dump_add_line_relations(&string
, _("Provides"), provides
);
791 pakfire_relationlist_free(provides
);
794 PakfireRelationList requires
= pakfire_package_get_requires(pkg
);
796 pakfire_package_dump_add_line_relations(&string
, _("Requires"), requires
);
797 pakfire_relationlist_free(requires
);
800 PakfireRelationList conflicts
= pakfire_package_get_conflicts(pkg
);
802 pakfire_package_dump_add_line_relations(&string
, _("Conflicts"), conflicts
);
803 pakfire_relationlist_free(conflicts
);
806 PakfireRelationList obsoletes
= pakfire_package_get_obsoletes(pkg
);
808 pakfire_package_dump_add_line_relations(&string
, _("Obsoletes"), obsoletes
);
809 pakfire_relationlist_free(obsoletes
);
812 PakfireRelationList recommends
= pakfire_package_get_recommends(pkg
);
814 pakfire_package_dump_add_line_relations(&string
, _("Recommends"), recommends
);
815 pakfire_relationlist_free(recommends
);
818 PakfireRelationList suggests
= pakfire_package_get_suggests(pkg
);
820 pakfire_package_dump_add_line_relations(&string
, _("Suggests"), suggests
);
821 pakfire_relationlist_free(suggests
);
825 if (flags
& PAKFIRE_PKG_DUMP_FILELIST
) {
826 PakfireFile file
= pakfire_package_get_filelist(pkg
);
828 char* prefix
= _("Filelist");
830 const char* name
= pakfire_file_get_name(file
);
831 pakfire_package_dump_add_line(&string
, prefix
, name
);
833 file
= pakfire_file_get_next(file
);
835 // Only prefix the first line.
843 PAKFIRE_EXPORT
int pakfire_package_is_cached(PakfirePackage pkg
) {
844 PakfireCache cache
= pakfire_pool_get_cache(pkg
->pool
);
848 return pakfire_cache_has_package(cache
, pkg
);
851 PAKFIRE_EXPORT
char* pakfire_package_get_cache_path(PakfirePackage pkg
) {
852 PakfireCache cache
= pakfire_pool_get_cache(pkg
->pool
);
856 return pakfire_cache_get_package_path(cache
, pkg
);
859 PAKFIRE_EXPORT
char* pakfire_package_get_cache_full_path(PakfirePackage pkg
) {
860 char* cache_path
= NULL
;
862 char* pkg_cache_path
= pakfire_package_get_cache_path(pkg
);
866 PakfireRepo repo
= pakfire_package_get_repo(pkg
);
870 PakfireRepoCache repo_cache
= pakfire_repo_get_cache(repo
);
875 cache_path
= pakfire_repocache_get_full_path(repo_cache
, pkg_cache_path
);
879 pakfire_repo_free(repo
);
884 static PakfireFile
pakfire_package_fetch_legacy_filelist(PakfirePackage pkg
) {
885 pakfire_package_internalize_repo(pkg
);
887 PakfireFile file
= NULL
;
888 PakfireRepo repo
= pakfire_package_get_repo(pkg
);
889 Solvable
* s
= get_solvable(pkg
);
890 Pool
* p
= pakfire_package_get_solv_pool(pkg
);
891 Repo
* r
= pakfire_repo_get_solv_repo(repo
);
893 int found_marker
= 0;
896 ids
= r
->idarraydata
+ s
->provides
;
897 while((id
= *ids
++) != 0) {
898 const char* filename
= pool_dep2str(p
, id
);
902 file
= pakfire_file_append(file
);
904 file
= pakfire_file_create();
907 pakfire_file_set_name(file
, filename
);
911 if (strcmp(filename
, PAKFIRE_SOLVABLE_FILEMARKER
) == 0)
916 file
= pakfire_file_get_first(file
);
919 file
= pakfire_file_sort(file
);
925 static PakfireFile
pakfire_package_fetch_filelist(PakfirePackage pkg
) {
926 pakfire_package_internalize_repo(pkg
);
928 PakfireFile file
= NULL
;
929 Pool
* pool
= pakfire_package_get_solv_pool(pkg
);
930 Repo
* repo
= pakfire_package_solv_repo(pkg
);
931 Id handle
= pakfire_package_get_handle(pkg
);
934 dataiterator_init(&di
, pool
, repo
, handle
,
935 SOLVABLE_FILELIST
, NULL
, SEARCH_FILES
| SEARCH_COMPLETE_FILELIST
);
936 while (dataiterator_step(&di
)) {
938 file
= pakfire_file_append(file
);
940 file
= pakfire_file_create();
943 pakfire_file_set_name(file
, di
.kv
.str
);
945 dataiterator_free(&di
);
948 file
= pakfire_file_get_first(file
);
951 file
= pakfire_file_sort(file
);
954 // If the file list is empty, we fall back to read files
955 // in the older format.
957 file
= pakfire_package_fetch_legacy_filelist(pkg
);
962 PAKFIRE_EXPORT PakfireFile
pakfire_package_get_filelist(PakfirePackage pkg
) {
963 if (!pkg
->filelist
) {
964 pkg
->filelist
= pakfire_package_fetch_filelist(pkg
);
967 return pkg
->filelist
;
970 PAKFIRE_EXPORT PakfireFile
pakfire_package_filelist_append(PakfirePackage pkg
, const char* filename
) {
971 PakfireRepo repo
= pakfire_package_get_repo(pkg
);
973 Id handle
= pakfire_package_get_handle(pkg
);
975 char* dirname
= pakfire_dirname(filename
);
976 char* basename
= pakfire_basename(filename
);
978 Id did
= repodata_str2dir(repo
->filelist
, dirname
, 1);
980 did
= repodata_str2dir(repo
->filelist
, "/", 1);
982 repodata_add_dirstr(repo
->filelist
, handle
,
983 SOLVABLE_FILELIST
, did
, basename
);
989 PakfireFile
pakfire_package_filelist_append(PakfirePackage pkg
) {
991 return pakfire_file_append(pkg
->filelist
);
994 PakfireFile file
= pakfire_file_create();
995 pkg
->filelist
= file
;
1001 PAKFIRE_EXPORT
void pakfire_package_filelist_remove(PakfirePackage pkg
) {
1003 pakfire_file_free_all(pkg
->filelist
);