aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--core/sensor.c78
-rw-r--r--doc/opal-api/opal-sensor-read-u64-158.rst16
-rw-r--r--hw/dts.c9
-rw-r--r--hw/fsp/fsp-sensor.c7
-rw-r--r--hw/occ-sensor.c2
-rw-r--r--include/cpu.h2
-rw-r--r--include/dts.h2
-rw-r--r--include/fsp.h2
-rw-r--r--include/opal-api.h3
-rw-r--r--include/platform.h2
-rw-r--r--include/sensor.h1
-rw-r--r--include/skiboot.h2
-rw-r--r--platforms/ibm-fsp/common.c2
-rw-r--r--platforms/ibm-fsp/ibm-fsp.h2
14 files changed, 112 insertions, 18 deletions
diff --git a/core/sensor.c b/core/sensor.c
index ff72636..b128964 100644
--- a/core/sensor.c
+++ b/core/sensor.c
@@ -20,11 +20,63 @@
#include <device.h>
#include <opal.h>
#include <dts.h>
+#include <lock.h>
struct dt_node *sensor_node;
-static int64_t opal_sensor_read(uint32_t sensor_hndl, int token,
- uint32_t *sensor_data)
+static struct lock async_read_list_lock = LOCK_UNLOCKED;
+static LIST_HEAD(async_read_list);
+
+struct sensor_async_read {
+ struct list_node link;
+ u64 *sensor_data64;
+ u32 *sensor_data32;
+ int token;
+};
+
+static int add_to_async_read_list(int token, u32 *data32, u64 *data64)
+{
+ struct sensor_async_read *req;
+
+ req = zalloc(sizeof(*req));
+ if (!req)
+ return OPAL_NO_MEM;
+
+ req->token = token;
+ req->sensor_data64 = data64;
+ req->sensor_data32 = data32;
+
+ lock(&async_read_list_lock);
+ list_add_tail(&async_read_list, &req->link);
+ unlock(&async_read_list_lock);
+
+ return OPAL_ASYNC_COMPLETION;
+}
+
+void check_sensor_read(int token)
+{
+ struct sensor_async_read *req = NULL;
+
+ lock(&async_read_list_lock);
+ if (list_empty(&async_read_list))
+ goto out;
+
+ list_for_each(&async_read_list, req, link) {
+ if (req->token == token)
+ break;
+ }
+ if (!req)
+ goto out;
+
+ *req->sensor_data32 = *req->sensor_data64;
+ free(req->sensor_data64);
+ list_del(&req->link);
+ free(req);
+out:
+ unlock(&async_read_list_lock);
+}
+
+static s64 opal_sensor_read_u64(u32 sensor_hndl, int token, u64 *sensor_data)
{
switch (sensor_get_family(sensor_hndl)) {
case SENSOR_DTS:
@@ -41,6 +93,27 @@ static int64_t opal_sensor_read(uint32_t sensor_hndl, int token,
return OPAL_UNSUPPORTED;
}
+static int64_t opal_sensor_read(uint32_t sensor_hndl, int token,
+ uint32_t *sensor_data)
+{
+ u64 *val;
+ s64 ret;
+
+ val = zalloc(sizeof(*val));
+ if (!val)
+ return OPAL_NO_MEM;
+
+ ret = opal_sensor_read_u64(sensor_hndl, token, val);
+ if (!ret) {
+ *sensor_data = *val;
+ free(val);
+ } else if (ret == OPAL_ASYNC_COMPLETION) {
+ ret = add_to_async_read_list(token, sensor_data, val);
+ }
+
+ return ret;
+}
+
static int opal_sensor_group_clear(u32 group_hndl, int token)
{
switch (sensor_get_family(group_hndl)) {
@@ -65,4 +138,5 @@ void sensor_init(void)
/* Register OPAL interface */
opal_register(OPAL_SENSOR_READ, opal_sensor_read, 3);
opal_register(OPAL_SENSOR_GROUP_CLEAR, opal_sensor_group_clear, 2);
+ opal_register(OPAL_SENSOR_READ_U64, opal_sensor_read_u64, 3);
}
diff --git a/doc/opal-api/opal-sensor-read-u64-158.rst b/doc/opal-api/opal-sensor-read-u64-158.rst
new file mode 100644
index 0000000..b75bcbc
--- /dev/null
+++ b/doc/opal-api/opal-sensor-read-u64-158.rst
@@ -0,0 +1,16 @@
+OPAL_SENSOR_READ_U64
+====================
+
+The OPAL sensor call to read sensor data of type u64. Unlike
+opal_sensor_read which reads upto u32 this call can be used to
+read values of sensors upto 64bits. The calling conventions and
+return values are same as OPAL_SENSOR_READ.
+(ref: doc/opal-api/opal-sensor-read-88.rst)
+
+Parameters
+----------
+::
+
+ u32 sensor_handler
+ int token
+ u64 *sensor_data
diff --git a/hw/dts.c b/hw/dts.c
index 881d66e..ecfe847 100644
--- a/hw/dts.c
+++ b/hw/dts.c
@@ -276,14 +276,15 @@ static void dts_async_read_temp(struct timer *t __unused, void *data,
rc = dts_read_core_temp_p9(cpu->pir, &dts);
if (!rc) {
if (cpu->sensor_attr == SENSOR_DTS_ATTR_TEMP_MAX)
- *(u32 *)cpu->sensor_data = dts.temp;
+ *cpu->sensor_data = dts.temp;
else if (cpu->sensor_attr == SENSOR_DTS_ATTR_TEMP_TRIP)
- *(u32 *)cpu->sensor_data = dts.trip;
+ *cpu->sensor_data = dts.trip;
}
if (!swkup_rc)
dctl_clear_special_wakeup(cpu);
+ check_sensor_read(cpu->token);
rc = opal_queue_msg(OPAL_MSG_ASYNC_COMP, NULL, NULL, cpu->token, rc);
if (rc)
prerror("Failed to queue async message\n");
@@ -292,7 +293,7 @@ static void dts_async_read_temp(struct timer *t __unused, void *data,
}
static int dts_read_core_temp(u32 pir, struct dts *dts, u8 attr,
- int token, u32 *sensor_data)
+ int token, u64 *sensor_data)
{
struct cpu_thread *cpu;
int rc;
@@ -390,7 +391,7 @@ enum sensor_dts_class {
*/
#define centaur_get_id(rid) (0x80000000 | ((rid) & 0x3ff))
-int64_t dts_sensor_read(u32 sensor_hndl, int token, u32 *sensor_data)
+int64_t dts_sensor_read(u32 sensor_hndl, int token, u64 *sensor_data)
{
uint8_t attr = sensor_get_attr(sensor_hndl);
uint32_t rid = sensor_get_rid(sensor_hndl);
diff --git a/hw/fsp/fsp-sensor.c b/hw/fsp/fsp-sensor.c
index 6363530..eff5d21 100644
--- a/hw/fsp/fsp-sensor.c
+++ b/hw/fsp/fsp-sensor.c
@@ -87,7 +87,7 @@ enum spcn_attr {
/* Parsed sensor attributes, passed through OPAL */
struct opal_sensor_data {
uint64_t async_token; /* Asynchronous token */
- uint32_t *sensor_data; /* Kernel pointer to copy data */
+ uint64_t *sensor_data; /* Kernel pointer to copy data */
enum spcn_attr spcn_attr; /* Modifier attribute */
uint16_t rid; /* Sensor RID */
uint8_t frc; /* Sensor resource class */
@@ -306,8 +306,9 @@ static int fsp_sensor_process_read(struct fsp_msg *resp_msg)
static void queue_msg_for_delivery(int rc, struct opal_sensor_data *attr)
{
- prlog(PR_INSANE, "%s: rc:%d, data:%d\n",
+ prlog(PR_INSANE, "%s: rc:%d, data:%lld\n",
__func__, rc, *(attr->sensor_data));
+ check_sensor_read(attr->async_token);
opal_queue_msg(OPAL_MSG_ASYNC_COMP, NULL, NULL,
attr->async_token, rc);
spcn_mod_data[attr->mod_index].entry_count = 0;
@@ -512,7 +513,7 @@ static int64_t parse_sensor_id(uint32_t handler, struct opal_sensor_data *attr)
int64_t fsp_opal_read_sensor(uint32_t sensor_hndl, int token,
- uint32_t *sensor_data)
+ uint64_t *sensor_data)
{
struct opal_sensor_data *attr;
int64_t rc;
diff --git a/hw/occ-sensor.c b/hw/occ-sensor.c
index 1e103cb..4a25a9b 100644
--- a/hw/occ-sensor.c
+++ b/hw/occ-sensor.c
@@ -322,7 +322,7 @@ static inline u32 sensor_handler(int occ_num, int sensor_id, int attr)
return sensor_make_handler(SENSOR_OCC, occ_num, sensor_id, attr);
}
-int occ_sensor_read(u32 handle, u32 *data)
+int occ_sensor_read(u32 handle, u64 *data)
{
struct occ_sensor_data_header *hb;
struct occ_sensor_name *md;
diff --git a/include/cpu.h b/include/cpu.h
index bec4b03..2ec6f03 100644
--- a/include/cpu.h
+++ b/include/cpu.h
@@ -116,7 +116,7 @@ struct cpu_thread {
*/
struct lock dts_lock;
struct timer dts_timer;
- void *sensor_data;
+ u64 *sensor_data;
u32 sensor_attr;
u32 token;
bool dts_read_in_progress;
diff --git a/include/dts.h b/include/dts.h
index 17e2e15..30188ac 100644
--- a/include/dts.h
+++ b/include/dts.h
@@ -19,7 +19,7 @@
#include <stdint.h>
-extern int64_t dts_sensor_read(u32 sensor_hndl, int token, u32 *sensor_data);
+extern int64_t dts_sensor_read(u32 sensor_hndl, int token, u64 *sensor_data);
extern bool dts_sensor_create_nodes(struct dt_node *sensors);
#endif /* __DTS_H */
diff --git a/include/fsp.h b/include/fsp.h
index c34a518..9b96d5d 100644
--- a/include/fsp.h
+++ b/include/fsp.h
@@ -822,7 +822,7 @@ extern void fsp_memory_err_init(void);
/* Sensor */
extern void fsp_init_sensor(void);
extern int64_t fsp_opal_read_sensor(uint32_t sensor_hndl, int token,
- uint32_t *sensor_data);
+ uint64_t *sensor_data);
/* Diagnostic */
extern void fsp_init_diag(void);
diff --git a/include/opal-api.h b/include/opal-api.h
index 0bd5f17..05fe767 100644
--- a/include/opal-api.h
+++ b/include/opal-api.h
@@ -215,7 +215,8 @@
#define OPAL_SENSOR_GROUP_CLEAR 156
#define OPAL_PCI_SET_P2P 157
#define OPAL_QUIESCE 158
-#define OPAL_LAST 158
+#define OPAL_SENSOR_READ_U64 159
+#define OPAL_LAST 159
#define QUIESCE_HOLD 1 /* Spin all calls at entry */
#define QUIESCE_REJECT 2 /* Fail all calls with OPAL_BUSY */
diff --git a/include/platform.h b/include/platform.h
index f3af390..e6ece27 100644
--- a/include/platform.h
+++ b/include/platform.h
@@ -183,7 +183,7 @@ struct platform {
* Read a sensor value
*/
int64_t (*sensor_read)(uint32_t sensor_hndl, int token,
- uint32_t *sensor_data);
+ uint64_t *sensor_data);
/*
* Return the heartbeat time
*/
diff --git a/include/sensor.h b/include/sensor.h
index 445a6bc..40b275a 100644
--- a/include/sensor.h
+++ b/include/sensor.h
@@ -63,5 +63,6 @@ enum {
extern struct dt_node *sensor_node;
extern void sensor_init(void);
+extern void check_sensor_read(int token);
#endif /* __SENSOR_H */
diff --git a/include/skiboot.h b/include/skiboot.h
index 2f81a05..d140ab2 100644
--- a/include/skiboot.h
+++ b/include/skiboot.h
@@ -352,7 +352,7 @@ extern int fake_nvram_write(uint32_t offset, void *src, uint32_t size);
/* OCC Inband Sensors */
extern void occ_sensors_init(void);
-extern int occ_sensor_read(u32 handle, u32 *data);
+extern int occ_sensor_read(u32 handle, u64 *data);
extern int occ_sensor_group_clear(u32 group_hndl, int token);
extern void occ_add_sensor_groups(struct dt_node *sg, u32 *phandles,
int nr_phandles, int chipid);
diff --git a/platforms/ibm-fsp/common.c b/platforms/ibm-fsp/common.c
index e916c39..87afbb6 100644
--- a/platforms/ibm-fsp/common.c
+++ b/platforms/ibm-fsp/common.c
@@ -230,7 +230,7 @@ int64_t ibm_fsp_cec_power_down(uint64_t request)
}
int64_t ibm_fsp_sensor_read(uint32_t sensor_hndl, int token,
- uint32_t *sensor_data)
+ uint64_t *sensor_data)
{
return fsp_opal_read_sensor(sensor_hndl, token, sensor_data);
}
diff --git a/platforms/ibm-fsp/ibm-fsp.h b/platforms/ibm-fsp/ibm-fsp.h
index 3f6e9c5..6c19978 100644
--- a/platforms/ibm-fsp/ibm-fsp.h
+++ b/platforms/ibm-fsp/ibm-fsp.h
@@ -28,7 +28,7 @@ struct errorlog;
extern int elog_fsp_commit(struct errorlog *buf);
extern int64_t ibm_fsp_sensor_read(uint32_t sensor_hndl, int token,
- uint32_t *sensor_data);
+ uint64_t *sensor_data);
/* Apollo PCI support */
extern void apollo_pci_setup_phb(struct phb *phb,