Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 3e138675 authored by Ram Chandrasekar's avatar Ram Chandrasekar
Browse files

msm: limits: A new LMH monitor driver



Add a new Limits management hardware (LMH) monitor driver.
The LMH hardware driver, which interacts with the LMH hardware
via a secure image like TZ or hypervisor should register all
the LMH sensors with this driver. LMH monitor driver in turn
registers the sensors with the thermal sysfs framework.

The LMH monitor driver, when notified of a hardware throttling
interrupt by the hardware driver, will read the throttling
intensity and notify the thermal sysfs framework when
thresholds are crossed.

If the LMH hardware is capable of supporting multiple operating
profiles, then it can register itself separately as LMH
profile device. LMH Monitor driver exposes APIs to get/set the
LMH profiles.

LMH monitor driver exposes the below debugfs interfaces.

/sys/kernel/debug/lmh_monitor/interrupt_poll_delay_msec
  - Configures the interrupt polling interval in the LMH
    monitor driver. This value can be used by the hardware
    driver also.
/sys/kernel/debug/lmh_monitor/hw_trace_enable
  - Enable/disable LMH trace
/sys/kernel/debug/lmh_monitor/hw_trace_interval
  - Interval in XO clock ticks for adding timestamp in the
    trace logs.
/sys/kernel/debug/lmh_monitor/lmh-profile/level
  - Set or get the current LMH operating profile
/sys/kernel/debug/lmh_monitor/lmh-profile/total_levels
  - Total operating profile levels supported in this platform
/sys/kernel/debug/lmh_monitor/lmh-profile/available_levels
  - Lists the available profile levels for this platform.

CRs-Fixed: 704088
CRs-Fixed: 698387
Change-Id: I9afb9b8ef8532d8af383b9afc039654a2d550af4
Signed-off-by: default avatarRam Chandrasekar <rkumbako@codeaurora.org>
parent c3b06b92
Loading
Loading
Loading
Loading
+9 −0
Original line number Diff line number Diff line
@@ -100,6 +100,15 @@ config THERMAL_TSENS8974
	  thermal userspace client when a threshold is reached. Warm/Cool
	  temperature thresholds can be set independently for each sensor.

config LIMITS_MONITOR
	bool "LMH monitor driver"
	depends on THERMAL
	help
	  Enable this to manage the limits hardware for interrupts, throttling
	  intensities, and LMH device profiles. This driver also registers the
	  Limits hardware's monitoring entities as sensors with the thermal
	  framework.

config THERMAL_MONITOR
	bool "Monitor thermal state and limit CPU Frequency"
	depends on THERMAL_TSENS8960 || THERMAL_TSENS8974
+1 −0
Original line number Diff line number Diff line
@@ -27,3 +27,4 @@ obj-$(CONFIG_THERMAL_TSENS8974) += msm8974-tsens.o
obj-$(CONFIG_THERMAL_QPNP)	+= qpnp-temp-alarm.o
obj-$(CONFIG_THERMAL_QPNP_ADC_TM)	+= qpnp-adc-tm.o
obj-$(CONFIG_THERMAL_MONITOR)	+= msm_thermal.o msm_thermal-dev.o
obj-$(CONFIG_LIMITS_MONITOR)	+= lmh_interface.o
+952 −0

File added.

Preview size limit exceeded, changes collapsed.

+95 −0
Original line number Diff line number Diff line
/*
 * Copyright (c) 2014, The Linux Foundation. All rights reserved.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 and
 * only version 2 as published by the Free Software Foundation.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 */

#ifndef __LMH_INTERFACE_H
#define __LMH_INTERFACE_H

#define LMH_NAME_MAX			20
#define LMH_POLLING_MSEC		30

enum lmh_trip_type {
	LMH_LOW_TRIP,
	LMH_HIGH_TRIP,
	LMH_TRIP_MAX,
};

enum lmh_monitor_state {
	LMH_ISR_DISABLED,
	LMH_ISR_MONITOR,
	LMH_ISR_POLLING,
	LMH_ISR_NR,
};

struct lmh_sensor_ops {
	int (*read) (struct lmh_sensor_ops *, long *);
	int (*reset_interrupt) (struct lmh_sensor_ops *);
	int (*enable_hw_log) (uint32_t, uint32_t);
	int (*disable_hw_log) (void);
	void (*interrupt_notify) (struct lmh_sensor_ops *, long);
};

struct lmh_device_ops {
	int (*get_available_levels) (struct lmh_device_ops *, int *);
	int (*get_curr_level) (struct lmh_device_ops *, int *);
	int (*set_level) (struct lmh_device_ops *, int);
};

static int lmh_poll_interval = LMH_POLLING_MSEC;
#ifdef CONFIG_LIMITS_MONITOR
int lmh_get_all_dev_levels(char *, int *);
int lmh_set_dev_level(char *, int);
int lmh_get_curr_level(char *, int *);
int lmh_sensor_register(char *, struct lmh_sensor_ops *);
void lmh_sensor_deregister(struct lmh_sensor_ops *);
int lmh_device_register(char *, struct lmh_device_ops *);
void lmh_device_deregister(struct lmh_device_ops *);
#else
static inline int lmh_get_all_dev_levels(char *device_name, int *level)
{
	return -ENOSYS;
}

static inline int lmh_set_dev_level(char *device_name, int level)
{
	return -ENOSYS;
}

static inline int lmh_get_curr_level(char *device_name, int *level)
{
	return -ENOSYS;
}

static inline int lmh_sensor_register(char *sensor_name,
	struct lmh_sensor_ops *ops)
{
	return -ENOSYS;
}

static inline void lmh_sensor_deregister(struct lmh_sensor_ops *ops)
{
	return;
}

static inline int lmh_device_register(char *device_name,
	struct lmh_device_ops *ops)
{
	return -ENOSYS;
}

static inline void lmh_device_deregister(struct lmh_device_ops *ops)
{
	return;
}
#endif

#endif /*__LMH_INTERFACE_H*/