Example #1
0
/*
 * _thread_update_node_energy calls _read_ipmi_values and updates all values
 * for node consumption
 */
static int _thread_update_node_energy(void)
{
	int rc = SLURM_SUCCESS;

	if (local_energy->current_watts == NO_VAL)
		return rc;

	rc = _read_ipmi_values();

	if (rc == SLURM_SUCCESS) {
		uint32_t additional_consumption;
		if (previous_update_time == 0) {
			additional_consumption = 0;
			previous_update_time = last_update_time;
		} else {
			additional_consumption =
				_get_additional_consumption(
					previous_update_time, last_update_time,
					local_energy->base_watts,
					local_energy->current_watts);
		}
		if (local_energy->current_watts != 0) {
			local_energy->base_watts = local_energy->current_watts;
			local_energy->current_watts = last_update_watt;
			local_energy->previous_consumed_energy =
				local_energy->consumed_energy;
			local_energy->consumed_energy += additional_consumption;
			local_energy->base_consumed_energy =
				additional_consumption;
		}
		if (local_energy->current_watts == 0) {
			local_energy->consumed_energy = 0;
			local_energy->base_watts = 0;
			local_energy->current_watts = last_update_watt;
		}
		local_energy->poll_time = time(NULL);
	}
	if (debug_flags & DEBUG_FLAG_ENERGY) {
		info("ipmi-thread = %d sec, current %d Watts, "
		     "consumed %d Joules %d new",
		     (int) (last_update_time - previous_update_time),
		     local_energy->current_watts,
		     local_energy->consumed_energy,
		     local_energy->base_consumed_energy);
	}

	return rc;
}
Example #2
0
/*
 * _thread_update_node_energy calls _read_ipmi_values and updates all values
 * for node consumption
 */
static int _thread_update_node_energy(void)
{
	xcc_raw_single_data_t *xcc_raw;
	static uint16_t overflows = 0; /* Number of overflows of the counter */
        int elapsed = 0;
	static uint64_t first_consumed_energy = 0;

	xcc_raw = _read_ipmi_values();

	if (!xcc_raw) {
		error("%s could not read XCC ipmi values", __func__);
		return SLURM_ERROR;
	}

	if (!xcc_energy.poll_time) {
		/*
		 * First number from the slurmd.  We will figure out the usage
		 * by subtracting this each time.
		 */
		first_consumed_energy =	xcc_raw->j;
		xcc_energy.consumed_energy = 0;
		xcc_energy.base_consumed_energy = 0;
		xcc_energy.previous_consumed_energy = 0;
		xcc_energy.ave_watts = 0;
	} else {
		xcc_energy.previous_consumed_energy =
			xcc_energy.consumed_energy;

		/* Detect first overflow */
		if (!overflows && xcc_raw->j < xcc_energy.consumed_energy) {
			xcc_energy.consumed_energy = IPMI_XCC_OVERFLOW -
				                     first_consumed_energy +
				                     xcc_raw->j;
			overflows++;
		} else if (!overflows &&
			   (xcc_raw->j >= xcc_energy.consumed_energy)) {
			xcc_energy.consumed_energy = xcc_raw->j;
			xcc_energy.consumed_energy -= first_consumed_energy;
		} else if (overflows) {
			/*
			 * Offset = First overflow + consecutive overflows
			 * If it happens that the offset + xcc_raw->j is less
			 * than the past consumed energy, it means that we
			 * overflowed and must add a new overflow to the count
			 */
			uint64_t offset = IPMI_XCC_OVERFLOW -
				first_consumed_energy +
				(IPMI_XCC_OVERFLOW * (overflows-1));

			if ((offset + xcc_raw->j) <
			    xcc_energy.consumed_energy) {
				overflows++;
				xcc_energy.consumed_energy = offset +
					IPMI_XCC_OVERFLOW + xcc_raw->j;
			} else {
				xcc_energy.consumed_energy += offset +
					xcc_raw->j;
			}
		}

		xcc_energy.base_consumed_energy =
			xcc_energy.consumed_energy -
			xcc_energy.previous_consumed_energy;

		elapsed = xcc_raw->s - xcc_energy.poll_time;
	}

	xcc_energy.poll_time = xcc_raw->s;

	xfree(xcc_raw);

	if (elapsed && xcc_energy.base_consumed_energy) {
		static uint64_t readings = 0;
		xcc_energy.current_watts =
			round((double)xcc_energy.base_consumed_energy /
			      (double)elapsed);

		/* ave_watts is used as TresUsageOutAve (AvePower) */
		xcc_energy.ave_watts = ((xcc_energy.ave_watts * readings) +
					 xcc_energy.current_watts) /
					 (readings + 1);
		readings++;
	}

	if (debug_flags & DEBUG_FLAG_ENERGY) {
		info("%s: XCC current_watts: %u consumed energy last interval: %"PRIu64"(current reading %"PRIu64") Joules, elapsed time: %u Seconds, first read energy counter val: %"PRIu64" ave watts: %u",
		     __func__,
		     xcc_energy.current_watts,
		     xcc_energy.base_consumed_energy,
		     xcc_energy.consumed_energy,
		     elapsed,
		     first_consumed_energy,
		     xcc_energy.ave_watts);
	}
	return SLURM_SUCCESS;
}