/**
 * Copyright © 2016 IBM Corporation
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
#include <stdio.h>
#include <stdlib.h>
#include <limits.h>
#include <errno.h>
#include <string.h>
#include <getopt.h>
#include <systemd/sd-bus.h>

#define DBUS_MAX_NAME_LEN 256

const char *objectmapper_service_name =  "xyz.openbmc_project.ObjectMapper";
const char *objectmapper_object_name  =  "/xyz/openbmc_project/object_mapper";
const char *objectmapper_intf_name    =  "xyz.openbmc_project.ObjectMapper";

typedef struct {
	int fan_num;
	int cpu_num;
	int core_num;
	int dimm_num;
	sd_bus *bus;
	char sensor_service[DBUS_MAX_NAME_LEN];
	char inventory_service[DBUS_MAX_NAME_LEN];
} fan_info_t;

/* Get an object's bus name from ObjectMapper */
int get_connection(sd_bus *bus, char *connection, const char *obj_path)
{
	sd_bus_error bus_error = SD_BUS_ERROR_NULL;
	sd_bus_message *m = NULL;
	char *temp_buf = NULL, *intf = NULL;
	int rc;

	rc = sd_bus_call_method(bus,
				objectmapper_service_name,
				objectmapper_object_name,
				objectmapper_intf_name,
				"GetObject",
				&bus_error,
				&m,
				"s",
				obj_path);
	if (rc < 0) {
		fprintf(stderr,
			"Failed to GetObject: %s\n", bus_error.message);
		goto finish;
	}

	/* Get the key, aka, the bus name */
	sd_bus_message_read(m, "a{sas}", 1, &temp_buf, 1, &intf);
	strncpy(connection, temp_buf, DBUS_MAX_NAME_LEN);

finish:
	sd_bus_error_free(&bus_error);
	sd_bus_message_unref(m);
	sd_bus_flush(bus);

	return rc;
}


int set_dbus_sensor(sd_bus *bus, const char *obj_path, int val)
{
	char connection[DBUS_MAX_NAME_LEN];
	sd_bus_error bus_error = SD_BUS_ERROR_NULL;
	sd_bus_message *response = NULL;
	int rc;

	if (!bus || !obj_path)
		return -1;

	rc = get_connection(bus, connection, obj_path);
	if (rc < 0) {
		fprintf(stderr,
			"fanctl: Failed to get bus name for %s\n", obj_path);
		goto finish;
	}

	rc = sd_bus_call_method(bus,
				connection,
				obj_path,
				"org.openbmc.SensorValue",
				"setValue",
				&bus_error,
				&response,
				"i",
				val);
	if (rc < 0)
		fprintf(stderr,
			"fanctl: Failed to set sensor %s:[%s]\n",
			obj_path, strerror(-rc));

finish:
	sd_bus_error_free(&bus_error);
	sd_bus_message_unref(response);
	sd_bus_flush(bus);

	return rc;
}

/* Read sensor value from "org.openbmc.Sensors" */
int read_dbus_sensor(sd_bus *bus, const char *obj_path)
{
	char connection[DBUS_MAX_NAME_LEN];
	sd_bus_error bus_error = SD_BUS_ERROR_NULL;
	sd_bus_message *response = NULL;
	int rc;
	int val = 0;

	if (!bus || !obj_path)
		return 0;

	rc = get_connection(bus, connection, obj_path);
	if (rc < 0) {
		val = 0;
		fprintf(stderr,
			"fanctl: Failed to get bus name for %s\n", obj_path);
		goto finish;
	}

	rc = sd_bus_call_method(bus,
				connection,
				obj_path,
				"org.openbmc.SensorValue",
				"getValue",
				&bus_error,
				&response,
				NULL);
	if (rc < 0) {
		val = 0;
		fprintf(stderr,
			"fanctl: Failed to read sensor value from %s:[%s]\n",
			obj_path, strerror(-rc));
		goto finish;
	}

	rc = sd_bus_message_read(response, "v","i", &val);
	if (rc < 0) {
		val = 0;
		fprintf(stderr,
			"fanctl: Failed to parse sensor value "
			"response message from %s:[%s]\n",
			obj_path, strerror(-rc));
	}

finish:
	sd_bus_error_free(&bus_error);
	sd_bus_message_unref(response);
	sd_bus_flush(bus);

	return val;
}

/* set fan speed with /org/openbmc/sensors/speed/fan* object */
static int fan_set_speed(sd_bus *bus, int fan_id, uint8_t fan_speed)
{
	char obj_path[DBUS_MAX_NAME_LEN];
	int rc;

	if (!bus)
		return -1;

	snprintf(obj_path, sizeof(obj_path),
		"/org/openbmc/sensors/speed/fan%d", fan_id);
	rc = set_dbus_sensor(bus, obj_path, fan_speed);
	if (rc < 0)
		fprintf(stderr, "fanctl: Failed to set fan[%d] speed[%d]\n",
				fan_id, fan_speed);

	return rc;
}

static int fan_set_max_speed(fan_info_t *info)
{
	int i;
	int rc = -1;

	if (!info)
		return -1;
	for (i = 0; i < info->fan_num; i++) {
		rc = fan_set_speed(info->bus, i, 255);
		if (rc < 0)
			break;
		fprintf(stderr, "fanctl: Set fan%d to max speed\n", i);
	}

	return rc;
}
/*
 * FAN_TACH_OFFSET is specific to Barreleye.
 * Barreleye uses NTC7904D HW Monitor as Fan tachometoer.
 * The 13-bit FANIN value is made up Higher part: [12:5],
 * and Lower part: [4:0], which are read from two sensors.
 * see: https://www.nuvoton.com/resource-files/NCT7904D_Datasheet_V1.44.pdf
 */
#define FAN_TACH_OFFSET 5
static int fan_get_speed(sd_bus *bus, int fan_id)
{
	int fan_tach_H = 0, fan_tach_L = 0;
	char obj_path[DBUS_MAX_NAME_LEN];
	int fan_speed;

	/* get fan tach */
	/* The object path is specific to Barreleye */
	snprintf(obj_path, sizeof(obj_path),
		"/org/openbmc/sensors/tach/fan%dH", fan_id);
	fan_tach_H = read_dbus_sensor(bus, obj_path);
	snprintf(obj_path, sizeof(obj_path),
		"/org/openbmc/sensors/tach/fan%dL", fan_id);
	fan_tach_L = read_dbus_sensor(bus, obj_path);

	/* invalid sensor value is -1 */
	if (fan_tach_H <= 0 || fan_tach_L <= 0)
		fan_speed = 0;
	else
		fan_speed = fan_tach_H << FAN_TACH_OFFSET | fan_tach_L;

	fprintf(stderr, "fan%d speed: %d\n", fan_id, fan_speed);
	return fan_speed;
}

/* set Fan Inventory 'Present' status */
int fan_set_present(sd_bus *bus, int fan_id, int val)
{
	sd_bus_error bus_error = SD_BUS_ERROR_NULL;
	sd_bus_message *response = NULL;
	int rc;
	char obj_path[DBUS_MAX_NAME_LEN];
	char connection[DBUS_MAX_NAME_LEN];

	snprintf(obj_path, sizeof(obj_path),
		"/org/openbmc/inventory/system/chassis/fan%d", fan_id);

	rc = get_connection(bus, connection, obj_path);
	if (rc < 0) {
		fprintf(stderr,
			"fanctl: Failed to get bus name for %s\n", obj_path);
		goto finish;
	}

	rc = sd_bus_call_method(bus,
				connection,
				obj_path,
				"org.openbmc.InventoryItem",
				"setPresent",
				&bus_error,
				&response,
				"s",
				(val == 1 ? "True" : "False"));
	if(rc < 0)
		fprintf(stderr,
			"fanctl: Failed to update fan presence via dbus: %s\n",
			bus_error.message);

	fprintf(stderr, "fanctl: Set fan%d present status to: %s\n",
			fan_id, (val == 1 ? "True" : "False"));

finish:
	sd_bus_error_free(&bus_error);
	sd_bus_message_unref(response);
	sd_bus_flush(bus);

	return rc;
}

/*
 * Update Fan Invertory 'Present' status by first reading fan speed.
 * If fan speed is '0', the fan is considerred not 'Present'.
 */
static int fan_update_present(fan_info_t *info)
{
	int i;
	int rc = -1;
	int fan_speed;

	if (!info)
		return -1;

	for (i = 0; i < info->fan_num; i++) {
		fan_speed = fan_get_speed(info->bus, i);
		if (fan_speed > 0)
			rc = fan_set_present(info->bus, i, 1);
		else
			rc = fan_set_present(info->bus, i, 0);

		if (rc < 0) {
			fprintf(stderr,
				"fanctl: Failed to set fan present status\n");
			break;
		}
	}

	return rc;
}
/*
 * Router function for any FAN operations that come via dbus
 */
static int fan_function_router(sd_bus_message *msg, void *user_data,
		sd_bus_error *ret_error)
{
	/* Generic error reporter. */
	int rc = -1;
	fan_info_t *info = user_data;

	/* Get the Operation. */
	const char *fan_function = sd_bus_message_get_member(msg);
	if (fan_function == NULL) {
		fprintf(stderr, "fanctl: Null FAN function specified\n");
		return sd_bus_reply_method_return(msg, "i", rc);
	}

	/* Route the user action to appropriate handlers. */
	if ((strcmp(fan_function, "setMax") == 0)) {
		rc = fan_set_max_speed(info);
		return sd_bus_reply_method_return(msg, "i", rc);
	}
	if ((strcmp(fan_function, "updatePresent") == 0)) {
		rc = fan_update_present(info);
		return sd_bus_reply_method_return(msg, "i", rc);
	}

	return sd_bus_reply_method_return(msg, "i", rc);
}

/* Dbus Services offered by this FAN controller */
static const sd_bus_vtable fan_control_vtable[] =
{
	SD_BUS_VTABLE_START(0),
	SD_BUS_METHOD("setMax", "", "i", &fan_function_router,
			SD_BUS_VTABLE_UNPRIVILEGED),
	SD_BUS_METHOD("updatePresent", "", "i", &fan_function_router,
			SD_BUS_VTABLE_UNPRIVILEGED),
	SD_BUS_VTABLE_END,
};

int start_fan_services(fan_info_t *info)
{
	/* Generic error reporter. */
	int rc = -1;
	/* slot where we are offering the FAN dbus service. */
	sd_bus_slot *fan_slot = NULL;
	const char *fan_object = "/org/openbmc/control/fans";

	info->bus = NULL;
	/* Get a hook onto system bus. */
	rc = sd_bus_open_system(&info->bus);
	if (rc < 0) {
		fprintf(stderr,"fanctl: Error opening system bus.\n");
		return rc;
	}

	/* Install the object */
	rc = sd_bus_add_object_vtable(info->bus,
			&fan_slot,
			fan_object, /* object path */
			"org.openbmc.control.Fans", /* interface name */
			fan_control_vtable,
			info);
	if (rc < 0) {
		fprintf(stderr, "fanctl: Failed to add object to dbus: %s\n",
				strerror(-rc));
		return rc;
	}

	/* If we had success in adding the providers, request for a bus name. */
	rc = sd_bus_request_name(info->bus,
			"org.openbmc.control.Fans", 0);
	if (rc < 0) {
		fprintf(stderr, "fanctl: Failed to acquire service name: %s\n",
				strerror(-rc));
		return rc;
	}

	for (;;) {
		/* Process requests */
		rc = sd_bus_process(info->bus, NULL);
		if (rc < 0) {
			fprintf(stderr, "fanctl: Failed to process bus: %s\n",
					strerror(-rc));
			break;
		}
		if (rc > 0) {
			continue;
		}

		rc = sd_bus_wait(info->bus, (uint64_t) - 1);
		if (rc < 0) {
			fprintf(stderr, "fanctl: Failed to wait on bus: %s\n",
				strerror(-rc));
			break;
		}
	}

	sd_bus_slot_unref(fan_slot);
	sd_bus_unref(info->bus);

	return rc;
}

static int str_to_int(char *str)
{
	long val;
	char *temp;

	val = strtol(str, &temp, 10);
	if (temp == str || *temp != '\0' ||
		((val == LONG_MIN || val == LONG_MAX) && errno == ERANGE))
		return -1;
	if (val < 0)
		return -1;

	return (int)val;
}

static int parse_argument(int argc, char **argv, fan_info_t *info)
{
	int c;
	struct option long_options[] =
	{
		{"fan_num",  required_argument, 0, 'f'},
		{"core_num",    required_argument, 0, 'c'},
		{"cpu_num",    required_argument, 0, 'p'},
		{"dimm_num",    required_argument, 0, 'd'},
		{0, 0, 0, 0}
	};

	while (1) {
		c = getopt_long (argc, argv, "c:d:f:p:", long_options, NULL);

		/* Detect the end of the options. */
		if (c == -1)
			break;

		switch (c) {
		case 'f':
			info->fan_num = str_to_int(optarg);
			if (info->fan_num == -1) {
				fprintf(stderr, "fanctl: Wrong fan_num: %s\n", optarg);
				return -1;
			}
			break;
		case 'c':
			info->core_num = str_to_int(optarg);
			if (info->core_num == -1) {
				fprintf(stderr, "fanctl: Wrong core_num: %s\n", optarg);
				return -1;
			}
			break;
		case 'p':
			info->cpu_num = str_to_int(optarg);
			if (info->cpu_num == -1) {
				fprintf(stderr, "fanctl: Wrong cpu_num: %s\n", optarg);
				return -1;
			}
			break;
		case 'd':
			info->dimm_num = str_to_int(optarg);
			if (info->dimm_num == -1) {
				fprintf(stderr, "fanctl: Wrong dimm_num: %s\n", optarg);
				return -1;
			}
			break;
		default:
			fprintf(stderr, "fanctl: Wrong argument\n");
			return -1;
		}
	}

	return 0;
}

int main(int argc, char **argv)
{
	int rc = 0;
	fan_info_t fan_info;

	memset(&fan_info, 0, sizeof(fan_info));
	rc = parse_argument(argc, argv, &fan_info);
	if (rc < 0) {
		fprintf(stderr, "fanctl: Error parse argument\n");
		return rc;
	}
	/* This call is not supposed to return. If it does, then an error */
	rc = start_fan_services(&fan_info);
	if (rc < 0) {
		fprintf(stderr, "fanctl: Error starting FAN Services. Exiting");
	}

	return rc;
}
