From 662b5acc085eadcc4b499ec01a6eb6f6c7a111d0 Mon Sep 17 00:00:00 2001 From: Juan RP Date: Mon, 7 Nov 2011 20:28:35 +0100 Subject: [PATCH] Implemented "New repository scheme and configuration file" from issue 16. --- NEWS | 6 +++ bin/xbps-repo/index.c | 102 +++++++++++------------------------- etc/repositories.plist | 30 +++++------ include/xbps_api.h | 6 +-- lib/initend.c | 2 +- lib/repository_pool.c | 57 +++++++++++++++----- lib/repository_sync_index.c | 23 ++------ lib/util.c | 15 ++---- 8 files changed, 108 insertions(+), 133 deletions(-) diff --git a/NEWS b/NEWS index d17a9250..f1a162d0 100644 --- a/NEWS +++ b/NEWS @@ -1,5 +1,11 @@ xbps-0.11.0 (???): + * Implemented "New repository scheme and configuration file" from issue 16. + The plist index file has been renamed to "index.plist", version bumped + to 1.3. The configuration file (repositories.plist) now expect the full + path to the directory storing the index.plist file. This will allow us + to use other directories (such as non-free, or alike) for such purpose. + * libxbps: improve xbps_purge_pkg() in case that the process was unexpectedly interrupted, do not error out unless the unregister phase return an error value. diff --git a/bin/xbps-repo/index.c b/bin/xbps-repo/index.c index 92744c48..871ce98d 100644 --- a/bin/xbps-repo/index.c +++ b/bin/xbps-repo/index.c @@ -36,9 +36,6 @@ #include #include "defs.h" -/* Array of valid architectures */ -static const char *archdirs[] = { "i686", "x86_64", "noarch", NULL }; - /* * Removes stalled pkg entries in repository's pkg-index.plist file, if any * binary package cannot be read (unavailable, not enough perms, etc). @@ -48,7 +45,7 @@ remove_missing_binpkg_entries(const char *repodir) { prop_array_t pkgarray; prop_dictionary_t idxd, pkgd; - const char *arch, *filen; + const char *filen; char *binpkg, *plist; size_t i; int rv = 0; @@ -77,9 +74,8 @@ again: for (i = 0; i < prop_array_count(pkgarray); i++) { pkgd = prop_array_get(pkgarray, i); - prop_dictionary_get_cstring_nocopy(pkgd, "architecture", &arch); prop_dictionary_get_cstring_nocopy(pkgd, "filename", &filen); - binpkg = xbps_xasprintf("%s/%s/%s", repodir, arch, filen); + binpkg = xbps_xasprintf("%s/%s", repodir, filen); if (binpkg == NULL) { errno = ENOMEM; rv = -1; @@ -321,16 +317,11 @@ repo_genindex(const char *pkgdir) prop_dictionary_t idxdict = NULL; struct dirent *dp; DIR *dirp; - struct utsname un; uint64_t npkgcnt = 0; - char *binfile, *path, *plist; - size_t i; + char *binfile, *plist; int rv = 0; bool registered_newpkgs = false, foundpkg = false; - if (uname(&un) == -1) - return errno; - /* * Create or read existing package index plist file. */ @@ -343,74 +334,43 @@ repo_genindex(const char *pkgdir) prop_object_release(idxdict); return errno; } - /* - * Iterate over the known architecture directories to find - * binary packages. - */ - for (i = 0; archdirs[i] != NULL; i++) { - if ((strcmp(archdirs[i], un.machine)) && - (strcmp(archdirs[i], "noarch"))) + + dirp = opendir(pkgdir); + if (dirp == NULL) { + xbps_error_printf("xbps-repo: cannot open `%s': %s\n", + pkgdir, strerror(errno)); + exit(EXIT_FAILURE); + } + + while ((dp = readdir(dirp)) != NULL) { + if ((strcmp(dp->d_name, ".") == 0) || + (strcmp(dp->d_name, "..") == 0)) continue; - path = xbps_xasprintf("%s/%s", pkgdir, archdirs[i]); - if (path == NULL) { + /* Ignore unknown files */ + if (strstr(dp->d_name, ".xbps") == NULL) + continue; + + foundpkg = true; + binfile = xbps_xasprintf("%s/%s", pkgdir, dp->d_name); + if (binfile == NULL) { + (void)closedir(dirp); rv = errno; goto out; } - /* - * If repo/ does not exist, - * create it. - */ - if ((access(path, X_OK) == -1) && errno == ENOENT) { - if (xbps_mkpath(path, 0755) == -1) { - xbps_error_printf("xbps-repo: cannot " - "create %s directory: %s\n", - path, strerror(errno)); - return -1; - } - } - - dirp = opendir(path); - if (dirp == NULL) { - xbps_error_printf("xbps-repo: unexistent '%s' " - "directory!\n", path); - free(path); + rv = add_binpkg_to_index(idxdict, pkgdir, binfile); + free(binfile); + if (rv == EEXIST) { + rv = 0; continue; } - - while ((dp = readdir(dirp)) != NULL) { - if ((strcmp(dp->d_name, ".") == 0) || - (strcmp(dp->d_name, "..") == 0)) - continue; - - /* Ignore unknown files */ - if (strstr(dp->d_name, ".xbps") == NULL) - continue; - - foundpkg = true; - binfile = xbps_xasprintf("%s/%s", path, dp->d_name); - if (binfile == NULL) { - (void)closedir(dirp); - free(path); - rv = errno; - goto out; - } - rv = add_binpkg_to_index(idxdict, path, binfile); - free(binfile); - if (rv == EEXIST) { - rv = 0; - continue; - } - else if (rv != 0) { - (void)closedir(dirp); - free(path); - goto out; - } - registered_newpkgs = true; + else if (rv != 0) { + (void)closedir(dirp); + goto out; } - (void)closedir(dirp); - free(path); + registered_newpkgs = true; } + (void)closedir(dirp); if (foundpkg == false) { /* No packages were found in directory */ diff --git a/etc/repositories.plist b/etc/repositories.plist index 364a8f18..0442f12b 100644 --- a/etc/repositories.plist +++ b/etc/repositories.plist @@ -2,24 +2,24 @@ - - http://xbps.nopcode.org/repos/current + By default we use the official "public" repositories. You can add + your own repositories by specifying the path (without the trailing + '/' character) to the directory where the index.plist file is stored. + --> + http://xbps.nopcode.org/repos/current/x86_64 + http://xbps.nopcode.org/repos/current/noarch diff --git a/include/xbps_api.h b/include/xbps_api.h index 9f8b2f10..be90a102 100644 --- a/include/xbps_api.h +++ b/include/xbps_api.h @@ -53,9 +53,9 @@ * @def XBPS_PKGINDEX_VERSION * Current version for the repository package index format. */ -#define XBPS_PKGINDEX_VERSION "1.2" +#define XBPS_PKGINDEX_VERSION "1.3" -#define XBPS_API_VERSION "20111031-1" +#define XBPS_API_VERSION "20111107" #define XBPS_VERSION "0.11.0" /** @@ -100,7 +100,7 @@ * @def XBPS_PKGINDEX * Filename for the repository package index property list. */ -#define XBPS_PKGINDEX "pkg-index.plist" +#define XBPS_PKGINDEX "index.plist" /** * @def XBPS_SYSCONF_PATH diff --git a/lib/initend.c b/lib/initend.c index 3c6b77f5..d3cec9d8 100644 --- a/lib/initend.c +++ b/lib/initend.c @@ -157,7 +157,7 @@ xbps_init(struct xbps_handle *xh) prop_string_cstring_nocopy(repofile)); xbps_dbg_printf("fetch_cache_conn: %zu\n", fetch_cache_conn); - xbps_dbg_printf("fetch_cacche_conn_host: %zu\n", + xbps_dbg_printf("fetch_cache_conn_host: %zu\n", fetch_cache_conn_host); xbps_dbg_printf("fetch_timeout: %zu\n", xhp->fetch_timeout); diff --git a/lib/repository_pool.c b/lib/repository_pool.c index ded34dc0..10e63cfd 100644 --- a/lib/repository_pool.c +++ b/lib/repository_pool.c @@ -23,6 +23,7 @@ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ +#include #include #include #include @@ -47,11 +48,6 @@ static SIMPLEQ_HEAD(rpool_head, repository_pool) rpool_queue = static bool repolist_initialized; -#define FETCH_ERROR(x) ((x == FETCH_UNAVAIL) || \ - (x == FETCH_NETWORK) || \ - (x == FETCH_ABORT) || \ - (x == FETCH_TIMEOUT) || \ - (x == FETCH_DOWN)) static int sync_remote_repo(const char *plist, const char *repourl) { @@ -60,14 +56,36 @@ sync_remote_repo(const char *plist, const char *repourl) return 0; /* file not found, fetch it */ - if (xbps_repository_sync_pkg_index(repourl) == -1) { - if (FETCH_ERROR(fetchLastErrCode)) - return -1; - } + if (xbps_repository_sync_pkg_index(repourl) == -1) + return -1; return 0; } -#undef FETCH_ERROR + +/* + * Returns true if repository URI contains "noarch" or matching architecture + * in last component, false otherwise. + */ +static bool +check_repo_arch(const char *uri) +{ + struct utsname un; + char *p; + + uname(&un); + p = strrchr(uri, '/'); + if (p == NULL) + return false; + p++; + if (*p == '\0') + return false; + else if (strcmp(p, "noarch") == 0) + return true; + else if (strcmp(p, un.machine) == 0) + return true; + + return false; +} int HIDDEN xbps_repository_pool_init(void) @@ -113,20 +131,33 @@ xbps_repository_pool_init(void) if (duprepo) continue; + ntotal++; + /* + * Check if repository doesn't match our architecture. + */ + if (!check_repo_arch(repouri)) { + xbps_dbg_printf("[rpool] `%s' arch not matched, " + "ignoring.\n", repouri); + nmissing++; + continue; + } plist = xbps_pkg_index_plist(repouri); if (plist == NULL) { rv = errno; goto out; } - ntotal++; + /* + * If it's a remote repository and index file is not available, + * fetch it for the first time. + */ if (sync_remote_repo(plist, repouri) == -1) { nmissing++; free(plist); continue; } /* - * Iterate over the repository pool and add the dictionary - * for current repository into the queue. + * Internalize repository's index dictionary and add it + * into the queue. */ rpool = malloc(sizeof(struct repository_pool)); if (rpool == NULL) { diff --git a/lib/repository_sync_index.c b/lib/repository_sync_index.c index 0bc9012e..d6dcd36c 100644 --- a/lib/repository_sync_index.c +++ b/lib/repository_sync_index.c @@ -23,7 +23,6 @@ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -#include #include #include #include @@ -56,11 +55,11 @@ xbps_get_remote_repo_string(const char *uri) * Replace '.' ':' and '/' characters with underscores, so that * provided URL: * - * http://nocturno.local:8080/blah/xbps/binpkg-repo + * http://nocturno.local:8080/repo/x86_64 * * becomes: * - * http___nocturno_local_8080_blah_xbps_binpkg_repo + * http___nocturno_local_8080_repo_x86_64 * */ if (url->port != 0) @@ -92,12 +91,11 @@ xbps_repository_sync_pkg_index(const char *uri) prop_dictionary_t tmpd; struct xbps_handle *xhp; struct url *url = NULL; - struct utsname un; struct stat st; const char *fetch_outputdir; char *rpidx, *lrepodir, *uri_fixedp; char *metadir, *tmp_metafile, *lrepofile; - int sverrno, rv = 0; + int rv = 0; bool only_sync = false; assert(uri != NULL); @@ -108,9 +106,6 @@ xbps_repository_sync_pkg_index(const char *uri) if (!xbps_check_is_repository_uri_remote(uri)) return 0; - if (uname(&un) == -1) - return -1; - if ((url = fetchParseURL(uri)) == NULL) return -1; @@ -119,7 +114,6 @@ xbps_repository_sync_pkg_index(const char *uri) fetchFreeURL(url); return -1; } - /* * Create metadir if necessary. */ @@ -137,7 +131,7 @@ xbps_repository_sync_pkg_index(const char *uri) /* * Remote repository pkg-index.plist full URL. */ - rpidx = xbps_xasprintf("%s/%s/%s", uri, un.machine, XBPS_PKGINDEX); + rpidx = xbps_xasprintf("%s/%s", uri, XBPS_PKGINDEX); if (rpidx == NULL) { rv = -1; goto out; @@ -181,20 +175,13 @@ xbps_repository_sync_pkg_index(const char *uri) * Download pkg-index.plist file from repository. */ if (xbps_fetch_file(rpidx, fetch_outputdir, true, NULL) == -1) { - sverrno = errno; - if (fetchLastErrCode) - rv = fetchLastErrCode; - else - rv = sverrno; - if (xhp->xbps_transaction_err_cb) { xhp->xtcd->state = XBPS_TRANS_STATE_REPOSYNC; xhp->xtcd->repourl = uri; - xhp->xtcd->err = rv; + xhp->xtcd->err = fetchLastErrCode; xhp->xbps_transaction_err_cb(xhp->xtcd); } rv = -1; - errno = sverrno; goto out; } if (only_sync) diff --git a/lib/util.c b/lib/util.c index dfa8329d..f58a764f 100644 --- a/lib/util.c +++ b/lib/util.c @@ -34,7 +34,6 @@ #include #include #include -#include #include "config.h" #include "xbps_api_impl.h" @@ -227,24 +226,19 @@ get_pkg_index_remote_plist(const char *uri) char * xbps_pkg_index_plist(const char *uri) { - struct utsname un; - assert(uri != NULL); - if (uname(&un) == -1) - return NULL; - if (xbps_check_is_repository_uri_remote(uri)) return get_pkg_index_remote_plist(uri); - return xbps_xasprintf("%s/%s/%s", uri, un.machine, XBPS_PKGINDEX); + return xbps_xasprintf("%s/%s", uri, XBPS_PKGINDEX); } char * xbps_path_from_repository_uri(prop_dictionary_t pkg_repod, const char *repoloc) { struct xbps_handle *xhp; - const char *filen, *arch; + const char *filen; char *lbinpkg = NULL; assert(prop_object_type(pkg_repod) == PROP_TYPE_DICTIONARY); @@ -253,9 +247,6 @@ xbps_path_from_repository_uri(prop_dictionary_t pkg_repod, const char *repoloc) if (!prop_dictionary_get_cstring_nocopy(pkg_repod, "filename", &filen)) return NULL; - if (!prop_dictionary_get_cstring_nocopy(pkg_repod, - "architecture", &arch)) - return NULL; xhp = xbps_handle_get(); /* @@ -273,7 +264,7 @@ xbps_path_from_repository_uri(prop_dictionary_t pkg_repod, const char *repoloc) /* * Local and remote repositories use the same path. */ - return xbps_xasprintf("%s/%s/%s", repoloc, arch, filen); + return xbps_xasprintf("%s/%s", repoloc, filen); } bool