blob: 2c3c99472a2119a2160e3749c4d9e8a65c8e38ba [file] [log] [blame]
#include "globalhandler.h"
#include "host-ipmid/ipmid-api.h"
#include <stdio.h>
#include <string.h>
#include <stdint.h>
const char *control_object_name = "/org/openbmc/control/bmc0";
const char *control_intf_name = "org.openbmc.control.Bmc";
const char *objectmapper_service_name = "org.openbmc.ObjectMapper";
const char *objectmapper_object_name = "/org/openbmc/ObjectMapper";
const char *objectmapper_intf_name = "org.openbmc.ObjectMapper";
void register_netfn_global_functions() __attribute__((constructor));
int obj_mapper_get_connection(char** buf, const char* obj_path)
{
sd_bus_error error = SD_BUS_ERROR_NULL;
sd_bus_message *m = NULL;
sd_bus *bus = NULL;
char *temp_buf = NULL, *intf = NULL;
size_t buf_size = 0;
int r;
//Get the system bus where most system services are provided.
bus = ipmid_get_sd_bus_connection();
/*
* Bus, service, object path, interface and method are provided to call
* the method.
* Signatures and input arguments are provided by the arguments at the
* end.
*/
r = sd_bus_call_method(bus,
objectmapper_service_name, /* service to contact */
objectmapper_object_name, /* object path */
objectmapper_intf_name, /* interface name */
"GetObject", /* method name */
&error, /* object to return error in */
&m, /* return message on success */
"s", /* input signature */
obj_path /* first argument */
);
if (r < 0) {
fprintf(stderr, "Failed to issue method call: %s\n", error.message);
goto finish;
}
// Get the key, aka, the connection name
sd_bus_message_read(m, "a{sas}", 1, &temp_buf, 1, &intf);
/*
* TODO: check the return code. Currently for no reason the message
* parsing of object mapper is always complaining about
* "Device or resource busy", but the result seems OK for now. Need
* further checks.
*/
buf_size = strlen(temp_buf) + 1;
printf("IPMID connection name: %s\n", temp_buf);
*buf = (char*)malloc(buf_size);
if (*buf == NULL) {
fprintf(stderr, "Malloc failed for warm reset");
r = -1;
goto finish;
}
memcpy(*buf, temp_buf, buf_size);
finish:
sd_bus_error_free(&error);
sd_bus_message_unref(m);
return r;
}
int dbus_reset(const char *method)
{
sd_bus_error error = SD_BUS_ERROR_NULL;
sd_bus_message *m = NULL;
sd_bus *bus = NULL;
char* connection = NULL;
int r;
r = obj_mapper_get_connection(&connection, control_object_name);
if (r < 0) {
fprintf(stderr, "Failed to get connection, return value: %d.\n", r);
goto finish;
}
printf("connection: %s\n", connection);
// Open the system bus where most system services are provided.
bus = ipmid_get_sd_bus_connection();
/*
* Bus, service, object path, interface and method are provided to call
* the method.
* Signatures and input arguments are provided by the arguments at the
* end.
*/
r = sd_bus_call_method(bus,
connection, /* service to contact */
control_object_name, /* object path */
control_intf_name, /* interface name */
method, /* method name */
&error, /* object to return error in */
&m, /* return message on success */
NULL,
NULL
);
if (r < 0) {
fprintf(stderr, "Failed to issue method call: %s\n", error.message);
goto finish;
}
finish:
sd_bus_error_free(&error);
sd_bus_message_unref(m);
free(connection);
return r;
}
ipmi_ret_t ipmi_global_warm_reset(ipmi_netfn_t netfn, ipmi_cmd_t cmd,
ipmi_request_t request, ipmi_response_t response,
ipmi_data_len_t data_len, ipmi_context_t context)
{
printf("Handling GLOBAL warmReset Netfn:[0x%X], Cmd:[0x%X]\n",netfn, cmd);
// TODO: call the correct dbus method for warmReset.
dbus_reset("warmReset");
// Status code.
ipmi_ret_t rc = IPMI_CC_OK;
*data_len = 0;
return rc;
}
ipmi_ret_t ipmi_global_cold_reset(ipmi_netfn_t netfn, ipmi_cmd_t cmd,
ipmi_request_t request, ipmi_response_t response,
ipmi_data_len_t data_len, ipmi_context_t context)
{
printf("Handling GLOBAL coldReset Netfn:[0x%X], Cmd:[0x%X]\n",netfn, cmd);
// TODO: call the correct dbus method for coldReset.
dbus_reset("coldReset");
// Status code.
ipmi_ret_t rc = IPMI_CC_OK;
*data_len = 0;
return rc;
}
void register_netfn_global_functions()
{
printf("Registering NetFn:[0x%X], Cmd:[0x%X]\n",NETFUN_APP, IPMI_CMD_COLD_RESET);
ipmi_register_callback(NETFUN_APP, IPMI_CMD_COLD_RESET, NULL, ipmi_global_cold_reset);
printf("Registering NetFn:[0x%X], Cmd:[0x%X]\n",NETFUN_APP, IPMI_CMD_WARM_RESET);
ipmi_register_callback(NETFUN_APP, IPMI_CMD_WARM_RESET, NULL, ipmi_global_warm_reset);
return;
}