Esempio n. 1
0
File: pool.c Progetto: mslusarz/nvml
/*
 * pool_set_map -- (internal) map poolset
 */
static int
pool_set_map(const char *fname, struct pool_set **poolset, int rdonly)
{
	ASSERTeq(util_is_poolset_file(fname), 1);

	struct pool_hdr hdr;
	if (pool_set_read_header(fname, &hdr))
		return -1;

	util_convert2h_hdr_nocheck(&hdr);

	/* parse pool type from first pool set file */
	enum pool_type type = pool_hdr_get_type(&hdr);
	if (type == POOL_TYPE_UNKNOWN) {
		ERR("cannot determine pool type from poolset");
		return -1;
	}

	/* get minimum size based on pool type for util_pool_open */
	size_t minsize = pool_get_min_size(type);

	/*
	 * Open the poolset, the values passed to util_pool_open are read
	 * from the first poolset file, these values are then compared with
	 * the values from all headers of poolset files.
	 */
	if (util_pool_open(poolset, fname, rdonly, minsize, hdr.signature,
			hdr.major, hdr.compat_features, hdr.incompat_features,
			hdr.ro_compat_features, NULL)) {
		ERR("opening poolset failed");
		return -1;
	}

	return 0;
}
Esempio n. 2
0
File: pool.c Progetto: krzycz/nvml
/*
 * pool_set_map -- (internal) map poolset
 */
static int
pool_set_map(const char *fname, struct pool_set **poolset, unsigned flags)
{
	ASSERTeq(util_is_poolset_file(fname), 1);

	struct pool_hdr hdr;
	if (pool_set_read_header(fname, &hdr))
		return -1;

	util_convert2h_hdr_nocheck(&hdr);

	/* parse pool type from first pool set file */
	enum pool_type type = pool_hdr_get_type(&hdr);
	if (type == POOL_TYPE_UNKNOWN) {
		ERR("cannot determine pool type from poolset");
		return -1;
	}

	/*
	 * Open the poolset, the values passed to util_pool_open are read
	 * from the first poolset file, these values are then compared with
	 * the values from all headers of poolset files.
	 */
	struct pool_attr attr;
	util_pool_hdr2attr(&attr, &hdr);
	if (util_pool_open(poolset, fname, 0 /* minpartsize */, &attr,
				NULL, NULL, flags | POOL_OPEN_IGNORE_SDS |
						POOL_OPEN_IGNORE_BAD_BLOCKS)) {
		ERR("opening poolset failed");
		return -1;
	}

	return 0;
}
Esempio n. 3
0
/*
 * pool_set_type -- get pool type of a poolset
 */
enum pool_type
pool_set_type(struct pool_set *set)
{
	struct pool_hdr hdr;

	/* open the first part file to read the pool header values */
	const struct pool_set_part *part = &PART(REP(set, 0), 0);
	int fdp = util_file_open(part->path, NULL, 0, O_RDONLY);
	if (fdp < 0) {
		ERR("cannot open poolset part file");
		return POOL_TYPE_UNKNOWN;
	}

	/* read the pool header from first pool set file */
	if (read(fdp, &hdr, sizeof(hdr)) != sizeof(hdr)) {
		ERR("cannot read pool header from poolset");
		close(fdp);
		return POOL_TYPE_UNKNOWN;
	}

	close(fdp);
	util_convert2h_hdr_nocheck(&hdr);
	enum pool_type type = pool_hdr_get_type(&hdr);
	return type;
}
Esempio n. 4
0
/*
 * pool_hdr_preliminary_check -- (internal) check pool header checksum and pool
 *	parameters
 */
static int
pool_hdr_preliminary_check(PMEMpoolcheck *ppc, location *loc)
{
	LOG(3, NULL);

	CHECK_INFO(ppc, "%schecking pool header", loc->prefix);

	if (util_is_zeroed((void *)&loc->hdr, sizeof(loc->hdr))) {
		if (CHECK_IS_NOT(ppc, REPAIR)) {
			check_end(ppc->data);
			ppc->result = CHECK_RESULT_NOT_CONSISTENT;
			return CHECK_ERR(ppc, "%sempty pool hdr", loc->prefix);
		}
	} else if (loc->hdr_valid) {
		enum pool_type type = pool_hdr_get_type(&loc->hdr);
		if (type == POOL_TYPE_UNKNOWN) {
			if (CHECK_IS_NOT(ppc, REPAIR)) {
				check_end(ppc->data);
				ppc->result = CHECK_RESULT_NOT_CONSISTENT;
				return CHECK_ERR(ppc, "%sinvalid signature",
					loc->prefix);
			}

			CHECK_INFO(ppc, "%sinvalid signature", loc->prefix);
		} else {
			/* valid check sum */
			CHECK_INFO(ppc, "%spool header correct",
				loc->prefix);
			loc->step = CHECK_STEP_COMPLETE;
			return 0;
		}
	} else if (CHECK_IS_NOT(ppc, REPAIR)) {
		check_end(ppc->data);
		ppc->result = CHECK_RESULT_NOT_CONSISTENT;
		return CHECK_ERR(ppc, "%sincorrect pool header", loc->prefix);
	} else {
		CHECK_INFO(ppc, "%sincorrect pool header", loc->prefix);
	}

	ASSERT(CHECK_IS(ppc, REPAIR));

	if (ppc->pool->params.type == POOL_TYPE_UNKNOWN) {
		ppc->pool->params.type = pool_hdr_possible_type(ppc);
		if (ppc->pool->params.type == POOL_TYPE_UNKNOWN) {
			ppc->result = CHECK_RESULT_CANNOT_REPAIR;
			return CHECK_ERR(ppc, "cannot determine pool type");
		}
	}

	if (!pool_supported(ppc->pool->params.type)) {
		ppc->result = CHECK_RESULT_CANNOT_REPAIR;
		return CHECK_ERR(ppc, "the repair of %s pools is not supported",
			pool_get_pool_type_str(ppc->pool->params.type));
	}

	return 0;
}
Esempio n. 5
0
/*
 * check_replica_sizes -- (internal) check if all replicas are large
 *	enough to hold data from a healthy replica
 */
static int
check_replica_sizes(struct pool_set *set, struct poolset_health_status *set_hs)
{
	LOG(3, "set %p, set_hs %p", set, set_hs);
	ssize_t pool_size = -1;
	for (unsigned r = 0; r < set->nreplicas; ++r) {
		/* skip broken replicas */
		if (!replica_is_replica_healthy(r, set_hs))
			continue;

		/* get the size of a pool in the replica */
		ssize_t replica_pool_size;
		if (REP(set, r)->remote)
			/* XXX: no way to get the size of a remote pool yet */
			replica_pool_size = (ssize_t)set->poolsize;
		else
			replica_pool_size = replica_get_pool_size(set, r);

		if (replica_pool_size < 0) {
			LOG(1, "getting pool size from replica %u failed", r);
			set_hs->replica[r]->flags |= IS_BROKEN;
			continue;
		}

		/* check if the pool is bigger than minimum size */
		enum pool_type type = pool_hdr_get_type(HDR(REP(set, r), 0));
		if ((size_t)replica_pool_size < pool_get_min_size(type)) {
			LOG(1,
			"pool size from replica %u is smaller than the minimum size allowed for the pool",
			r);
			set_hs->replica[r]->flags |= IS_BROKEN;
			continue;
		}

		/* check if each replica is big enough to hold the pool data */
		if (set->poolsize < (size_t)replica_pool_size) {
			ERR(
			"some replicas are too small to hold synchronized data");
			return -1;
		}

		if (pool_size < 0) {
			pool_size = replica_pool_size;
			continue;
		}

		/* check if pools in all healthy replicas are of equal size */
		if (pool_size != replica_pool_size) {
			ERR("pool sizes from different replicas differ");
			return -1;
		}
	}
	return 0;
}
Esempio n. 6
0
File: pool.c Progetto: mslusarz/nvml
/*
 * pool_params_from_header -- parse pool params from pool header
 */
void
pool_params_from_header(struct pool_params *params, const struct pool_hdr *hdr)
{
	memcpy(params->signature, hdr->signature, sizeof(params->signature));

	/*
	 * Check if file is a part of pool set by comparing the UUID with the
	 * next part UUID. If it is the same it means the pool consist of a
	 * single file.
	 */
	int uuid_eq_next = uuidcmp(hdr->uuid, hdr->next_part_uuid);
	int uuid_eq_prev = uuidcmp(hdr->uuid, hdr->prev_part_uuid);
	params->is_part = !params->is_poolset && (uuid_eq_next || uuid_eq_prev);

	params->type = pool_hdr_get_type(hdr);
}
Esempio n. 7
0
File: pool.c Progetto: mslusarz/nvml
/*
 * pool_set_type -- get pool type of a poolset
 */
enum pool_type
pool_set_type(struct pool_set *set)
{
	struct pool_hdr hdr;

	/* open the first part file to read the pool header values */
	const struct pool_set_part *part = &PART(REP(set, 0), 0);

	if (util_file_pread(part->path, &hdr, sizeof(hdr), 0) !=
			sizeof(hdr)) {
		ERR("cannot read pool header from poolset");
		return POOL_TYPE_UNKNOWN;
	}

	util_convert2h_hdr_nocheck(&hdr);
	enum pool_type type = pool_hdr_get_type(&hdr);
	return type;
}