ALPM

 view release on metacpan or  search on metacpan

types.c  view on Meta::CPAN

}

SV*
c2p_filelist(void *flistPtr){
	alpm_filelist_t *flist;
	AV *av;
	int i;

	flist = flistPtr;
	av = newAV();
	for(i = 0; i < flist->count; i++){
		av_push(av, c2p_file(flist->files + i));
	}
	return newRV_noinc((SV*)av);
}

/*
This deals with only raw bits, which is bad form, but I prefer the design.
If the alpm_siglevel_t bitflag enum was not so strange, I wouldn't have
chosen to do this.

The bit flags are separated into two halves with a special case of the
"default value" where bit 32 (the MSB) is on. Reading from LSB to MSB,
the package flags consist of the first four bits. 6 unused bits follow.
The database flags consist of the next four bits. 17 unused bits follow.
Finally, the bit flag for ALPM_USE_DEFAULT is the MSB.

Here is the form of the package and database bitmask. Remember the
database flags are shifted to the left by 10 places.

BIT	DESCRIPTION
1	Signature checking is enabled for packages or databases respectively.
2	Signature checking is optional, used only when available.
3	MARGINAL_OK?
4	UNKNOWN_OK?

A setting of TrustAll in pacman.conf enables MARGINAL_OK and UNKNOWN_OK.
These two flags are not enabled separately from one another.

ALPM_SIG_USE_DEFAULT is the default value when set_default_siglevel is never
called but I have no idea what that could mean when this is the value of the default.
This seems to be a circular argument with no end.

*/

#define MASK_ENABLE 1
#define MASK_OPT 3
#define MASK_TRUSTALL 12
#define MASK_ALL 15
#define OFFSET_DB 10

static
SV* truststring(unsigned long siglvl)
{
	SV *str;
	if(!(siglvl & MASK_ENABLE)){
		return newSVpv("never", 0);
	}else if(!(~siglvl & MASK_OPT)){
		str = newSVpv("optional", 0);
	}else{
		str = newSVpv("required", 0);
	}
	if(!(~siglvl & MASK_TRUSTALL)){
		sv_catpv(str, " trustall");
	}
	return str;
}

/* converts siglevel bitflags into a string (default/never) or hashref of strings */
SV*
c2p_siglevel(alpm_siglevel_t sig)
{
	HV *hv;

	if(sig & ALPM_SIG_USE_DEFAULT){
		return newSVpv("default", 7);
	}

	hv = newHV();
	hv_store(hv, "pkg", 3, truststring(sig & MASK_ALL), 0);
	hv_store(hv, "db", 2, truststring((sig >> OFFSET_DB) & MASK_ALL), 0);
	return newRV_noinc((SV*)hv);
}

static unsigned long
trustmask(char *str, STRLEN len)
{
	unsigned long flags;

	if(len == 5 && strncmp(str, "never", 5) == 0){
		return 0;
	}

	if(len < 8){
		goto badstr;
	}else if(strncmp(str, "required", 8) == 0){
		flags = MASK_ENABLE;
	}else if(strncmp(str, "optional", 8) == 0){
		flags = MASK_OPT;
	}else {
		goto badstr;
	}

	if(len == 8){
		/* Conveniently, the strings "required" and "optional" are both 8 characters long. */
		return flags;
	}else if(len != 17 || strncmp(str + 8, " trustall", 8) != 0){
		goto badstr;
	}
	return flags | MASK_TRUSTALL;

	badstr:
	croak("Unrecognized signature level string: %s", str);
}

static unsigned long
fetch_trustmask(HV *hv, const char *key){
	SV **val;
	char *str;
	STRLEN len;

	val = hv_fetch(hv, key, strlen(key), 0);
	if(val == NULL){
		croak("Invalid signature level hash: %s key is missing", key);
	}
	str = SvPV(*val, len);
	return trustmask(str, len);
}

/* converts a siglevel string or hashref into bitflags. */
alpm_siglevel_t
p2c_siglevel(SV *sig)
{
	char *str;
	STRLEN len;
	alpm_siglevel_t ret;
	HV *hv;

	if(SvPOK(sig)){
		str = SvPV(sig, len);
		if(len == 7 && strncmp(str, "default", len) == 0){
			return ALPM_SIG_USE_DEFAULT;
		}else {
			/* XXX: might not be null terminated? */
			croak("Unrecognized global signature level string: %s", str);
		}
	}else if(SvROK(sig) && SvTYPE(SvRV(sig)) == SVt_PVHV){
		hv = (HV*)SvRV(sig);
		ret = fetch_trustmask(hv, "pkg");
		ret |= fetch_trustmask(hv, "db") << OFFSET_DB;
		return ret;
	}
	croak("A global signature level must be a string or hash reference");
}

#undef MASK_ENABLE
#undef MASK_OPT
#undef MASK_TRUSTALL
#undef MASK_ALL
#undef OFFSET_DB

SV*
c2p_pkgreason(alpm_pkgreason_t rsn)
{
	switch(rsn){



( run in 0.492 second using v1.01-cache-2.11-cpan-5837b0d9d2c )