Add capability to send sensor limit values to the driver so they can
be programmed into device registers. This way we can let the hardware help us out instead of having to always compare the value against each limit. (Driver updates for some sensors to take advantage of this capability will be forthcoming.)
This commit is contained in:
parent
fdcbe744db
commit
c235777756
@ -1,4 +1,4 @@
|
||||
.\" $NetBSD: envsys.4,v 1.42 2009/03/15 12:33:53 joerg Exp $
|
||||
.\" $NetBSD: envsys.4,v 1.43 2009/06/13 16:08:25 pgoyette Exp $
|
||||
.\"
|
||||
.\" Copyright (c) 2007 The NetBSD Foundation, Inc.
|
||||
.\" All rights reserved.
|
||||
@ -27,7 +27,7 @@
|
||||
.\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
.\" POSSIBILITY OF SUCH DAMAGE.
|
||||
.\"
|
||||
.Dd November 13, 2007
|
||||
.Dd June 12, 2009
|
||||
.Dt ENVSYS 4
|
||||
.Os
|
||||
.Sh NAME
|
||||
@ -135,6 +135,12 @@ dictionary (which contains specific properties for a device):
|
||||
\&\*[Lt]string\&\*[Gt]Ampere hour\&\*[Lt]\&/string\&\*[Gt]
|
||||
\&\*[Lt]key\&\*[Gt]want-percentage\&\*[Lt]\&/key\&\*[Gt]
|
||||
\&\*[Lt]true\&/\&\*[Gt]
|
||||
\&\*[Lt]key\&\*[Gt]warning-capacity\&\*[Lt]\&/key\&\*[Gt]
|
||||
\&\*[Lt]integer\&\*[Gt]19234\&\*[Lt]\&/integer\&\*[Gt]
|
||||
\&\*[Lt]key\&\*[Gt]warning-max\&\*[Lt]\&/key\&\*[Gt]
|
||||
\&\*[Lt]integer\&\*[Gt]323150000\&\*[Lt]\&/integer\&\*[Gt]
|
||||
\&\*[Lt]key\&\*[Gt]warning-min\&\*[Lt]\&/key\&\*[Gt]
|
||||
\&\*[Lt]integer\&\*[Gt]298150000\&\*[Lt]\&/integer\&\*[Gt]
|
||||
\&\*[Lt]\&/dict\&\*[Gt]
|
||||
\&\*[Lt]dict\&\*[Gt]
|
||||
\&\*[Lt]key\&\*[Gt]device-properties\&\*[Lt]\&/key\&\*[Gt]
|
||||
@ -184,19 +190,14 @@ Current max value in the sensor.
|
||||
Current min value in the sensor.
|
||||
.It Fa monitoring-state-critical
|
||||
If true, the driver has enabled the flag to monitor a critical state.
|
||||
.It Fa monitoring-state-critical-over
|
||||
If true, the driver has enabled the flag to monitor a critical over state.
|
||||
.It Fa monitoring-state-critical-under
|
||||
If true, the driver has enabled the flag to monitor a critical under state.
|
||||
.It Fa monitoring-state-hw-range-limits
|
||||
If true, the driver has enabled the flag to monitor warning or critical
|
||||
limits.
|
||||
.It Fa monitoring-state-state-changed
|
||||
If true, the driver has enabled the flag to monitor for state changes in
|
||||
a drive or Battery state sensor.
|
||||
.It Fa monitoring-state-warning-over
|
||||
If true, the driver has enabled the flag to monitor a warning over state.
|
||||
.It Fa monitoring-state-warning-under
|
||||
If true, the driver has enabled the flag to monitor a warning under state.
|
||||
.It Fa monitoring-supported
|
||||
If true, critical capacity/max/min limits may be set by the
|
||||
If true, critical/warning capacity/max/min limits may be set by the
|
||||
.Dv ENVSYS_SETDICTIONARY
|
||||
.Xr ioctl 2 .
|
||||
.It Fa state
|
||||
@ -209,6 +210,21 @@ If true,
|
||||
and
|
||||
.Em cur-value
|
||||
are valid and a percentage may be computed from them.
|
||||
.It Fa warning-capacity
|
||||
Warning capacity set previously by the
|
||||
.Dv ENVSYS_SETDICTIONARY
|
||||
.Xr ioctl 2 .
|
||||
Only available on sensors with the
|
||||
.Em want-percentage
|
||||
object enabled.
|
||||
.It Fa warning-max
|
||||
Warning max limit set previously by the
|
||||
.Dv ENVSYS_SETDICTIONARY
|
||||
.Xr ioctl 2 .
|
||||
.It Fa warning-min
|
||||
Warning min limit set previously by the
|
||||
.Dv ENVSYS_SETDICTIONARY
|
||||
.Xr ioctl 2 .
|
||||
.El
|
||||
.It Dv ENVSYS_REMOVEPROPS Pq prop_dictionary_t
|
||||
.Pp
|
||||
@ -251,6 +267,12 @@ a sensor understands:
|
||||
\&\*[Lt]integer\&\*[Gt]3400\&\*[Lt]\&/integer\&\*[Gt]
|
||||
\&\*[Lt]key\&\*[Gt]critical-min\&\*[Lt]\&/key\&\*[Gt]
|
||||
\&\*[Lt]integer\&\*[Gt]2800\&\*[Lt]\&/integer\&\*[Gt]
|
||||
\&\*[Lt]key\&\*[Gt]warning-capacity\&\*[Lt]\&/key\&\*[Gt]
|
||||
\&\*[Lt]integer\&\*[Gt]15\&\*[Lt]\&/integer\&\*[Gt]
|
||||
\&\*[Lt]key\&\*[Gt]warning-max\&\*[Lt]\&/key\&\*[Gt]
|
||||
\&\*[Lt]integer\&\*[Gt]3200\&\*[Lt]\&/integer\&\*[Gt]
|
||||
\&\*[Lt]key\&\*[Gt]warning-min\&\*[Lt]\&/key\&\*[Gt]
|
||||
\&\*[Lt]integer\&\*[Gt]2900\&\*[Lt]\&/integer\&\*[Gt]
|
||||
\&\*[Lt]\&/dict\&\*[Gt]
|
||||
.Ed
|
||||
.Pp
|
||||
@ -305,12 +327,12 @@ object specifying the sensor that is required for the new properties.
|
||||
If an unknown object was sent with the dictionary,
|
||||
.Er EINVAL
|
||||
will be returned, or if the sensor does not support changing
|
||||
rfact (voltage sensors) or critical/capacity limits,
|
||||
rfact (voltage sensors) or critical/warning/capacity limits,
|
||||
.Er ENOTSUP
|
||||
will be returned.
|
||||
.El
|
||||
.Sh NOTES
|
||||
When setting a critical max or min limit with the
|
||||
When setting a critical/warning max or min limit with the
|
||||
.Dv ENVSYS_SETDICTIONARY
|
||||
.Xr ioctl 2 ,
|
||||
the user must be aware that
|
||||
@ -320,7 +342,7 @@ Please see
|
||||
.Xr sysmon_envsys 9
|
||||
for more information.
|
||||
.Pp
|
||||
Also when setting a critical capacity limit, the formula to send a
|
||||
Also when setting a critical or warning capacity limit, the formula to send a
|
||||
proper value to
|
||||
.Xr sysmon_envsys 9
|
||||
is the following:
|
||||
|
@ -1,4 +1,4 @@
|
||||
.\" $NetBSD: sysmon_envsys.9,v 1.24 2009/06/01 20:08:44 pgoyette Exp $
|
||||
.\" $NetBSD: sysmon_envsys.9,v 1.25 2009/06/13 16:08:25 pgoyette Exp $
|
||||
.\"
|
||||
.\" Copyright (c) 2007, 2008 The NetBSD Foundation, Inc.
|
||||
.\" All rights reserved.
|
||||
@ -27,7 +27,7 @@
|
||||
.\" ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
.\" POSSIBILITY OF SUCH DAMAGE.
|
||||
.\"
|
||||
.Dd June 1, 2009
|
||||
.Dd June 13, 2009
|
||||
.Dt SYSMON_ENVSYS 9
|
||||
.Os
|
||||
.Sh NAME
|
||||
@ -104,6 +104,8 @@ struct sysmon_envsys {
|
||||
uint64_t sme_events_timeout;
|
||||
void *sme_cookie;
|
||||
void (*sme_refresh)(struct sysmon_envsys *, envsys_data_t *);
|
||||
void (*sme_set_limits)(struct sysmon_envsys *, sysmon_envsys_lim_t *);
|
||||
void (*sme_get_limits)(struct sysmon_envsys *, sysmon_envsys_lim_t *);
|
||||
};
|
||||
.Ed
|
||||
.Pp
|
||||
@ -126,14 +128,10 @@ Currently supporting
|
||||
If enabled, the
|
||||
.Ar sme_refresh
|
||||
function callback won't be used
|
||||
to refresh sensors data and the driver will use its own method.
|
||||
Hence
|
||||
.Ar sme_cookie
|
||||
won't be necessary either (OPTIONAL).
|
||||
to refresh sensors data and the driver will use its own method (OPTIONAL).
|
||||
.It Fa sme_events_timeout
|
||||
This is used to specify the default timeout value that will be used to
|
||||
check for critical events if any monitoring flag was set.
|
||||
The value is used as seconds (OPTIONAL).
|
||||
This is used to specify the default timeout value (in seconds) that will be
|
||||
used to check for critical events if any monitoring flag was set (OPTIONAL).
|
||||
.El
|
||||
.Pp
|
||||
If the driver wants to refresh sensors data via the
|
||||
@ -145,8 +143,11 @@ framework, the following members must be specified:
|
||||
Pointer to the device struct (also called
|
||||
.Dq softc ) .
|
||||
This may be used in the
|
||||
.Sy sme_refresh
|
||||
function callback.
|
||||
.Sy sme_refresh ,
|
||||
.Sy sme_get_limits ,
|
||||
or
|
||||
.Sy sme_set_limits
|
||||
function callbacks.
|
||||
.It Fa sme_refresh
|
||||
Pointer to a function that will be used to refresh sensor data in
|
||||
the device.
|
||||
@ -156,6 +157,19 @@ sensor depending of the returned data by the driver.
|
||||
.Em You don't have to refresh all sensors, only the sensor specified by the
|
||||
.Sy edata-\*[Gt]sensor
|
||||
.Em index .
|
||||
.It Fa sme_get_limits
|
||||
Pointer to a function that will be used to obtain from the driver the
|
||||
initial limits (or thresholds) used when monitoring a sensor's value.
|
||||
(See the
|
||||
.Sx SENSOR DETAILS
|
||||
section for more information.)
|
||||
.It Fa sme_set_limits
|
||||
Pointer to a function that alerts the device driver whenever monitoring
|
||||
limits (or thresholds) are updated by the user.
|
||||
Setting this function allows the device driver to reprogram hardware
|
||||
limits (if provided by the device), and gives the driver direct control
|
||||
over setting the sensor's state based on hardware status.
|
||||
XXXX
|
||||
.El
|
||||
.Pp
|
||||
Note that it's not necessary to refresh the sensors data before the
|
||||
@ -203,7 +217,7 @@ of
|
||||
This will be used to report its current state (on/off).
|
||||
.It SME_CLASS_BATTERY
|
||||
.Pp
|
||||
This class is for devices that want to act as an
|
||||
This class is for devices that want to act as a
|
||||
.Em Battery .
|
||||
The device writer must ensure that at least there are two sensors with
|
||||
units of
|
||||
@ -211,14 +225,14 @@ units of
|
||||
and
|
||||
.Sy ENVSYS_BATTERY_CHARGE .
|
||||
.Pp
|
||||
These two sensors are used to ensure that the battery device won't
|
||||
never send a
|
||||
These two sensors are used to ensure that the battery device can
|
||||
send a
|
||||
.Em low-power
|
||||
event to the
|
||||
.Xr powerd 8
|
||||
daemon (if running) when all battery devices are in a critical state.
|
||||
The critical state means that a battery is not currently charging
|
||||
and its charge state is low or critical.
|
||||
(The critical state occurs when a battery is not currently charging
|
||||
and its charge state is low or critical).
|
||||
When the
|
||||
.Em low-power
|
||||
condition is met, an event is sent to the
|
||||
@ -241,7 +255,7 @@ If a
|
||||
.Dv SME_CLASS_ACADAPTER
|
||||
or
|
||||
.Dv SME_CLASS_BATTERY
|
||||
class don't have the sensors required, the
|
||||
class device doesn't have the sensors required, the
|
||||
.Em low-power
|
||||
event will never be sent, and the graceful shutdown won't be possible.
|
||||
.Ss SENSOR DETAILS
|
||||
@ -301,10 +315,13 @@ daemon (if running).
|
||||
The monitoring event will be registered when this flag is
|
||||
.Dv true
|
||||
and one or more of the
|
||||
.Dv ENVSYS_FMONFOO
|
||||
.Dv ENVSYS_FMONxxx
|
||||
flags were set in the
|
||||
.Ar flags
|
||||
member.
|
||||
.Em NOTE
|
||||
.Em that limits (or thresholds) can be set at any time to enable
|
||||
.Em monitoring that the sensor's value remains within those limits.
|
||||
.It Fa desc
|
||||
Used to set the description string.
|
||||
.Em NOTE
|
||||
@ -445,11 +462,11 @@ member is not set to
|
||||
or
|
||||
.Ar ENVSYS_BATTERY_CAPACITY .
|
||||
.It ENVSYS_FMONNOTSUPP
|
||||
Disallows to set a critical limit via the
|
||||
Disallows setting of limits (or thresholds) via the
|
||||
.Dv ENVSYS_SETDICTIONARY
|
||||
.Xr ioctl 2 .
|
||||
This flag has not any effect for monitoring flags set in the driver and it's
|
||||
only meant to disable setting critical limits from userland.
|
||||
This flag has no effect on monitoring flags set in the driver and is
|
||||
only disables setting the limits from userland.
|
||||
.El
|
||||
.Pp
|
||||
.Em If the driver has to use any of the
|
||||
@ -464,10 +481,9 @@ If
|
||||
.Ar units
|
||||
is set to
|
||||
.Ar ENVSYS_DRIVE ,
|
||||
there are some predefined states that must be set (only one)
|
||||
to the
|
||||
the
|
||||
.Ar value_cur
|
||||
member:
|
||||
member must be set to one of the following predefined states:
|
||||
.Pp
|
||||
.Bl -tag -width "ENVSYS_DRIVE_POWERDOWNXX" -compact
|
||||
.It ENVSYS_DRIVE_EMPTY
|
||||
@ -505,10 +521,9 @@ If
|
||||
.Ar units
|
||||
is set to
|
||||
.Ar ENVSYS_BATTERY_CAPACITY ,
|
||||
there are some predefined capacity states that must be set (only one)
|
||||
to the
|
||||
the
|
||||
.Ar value_cur
|
||||
member:
|
||||
member must be set to one of the following predefined capacity states:
|
||||
.Pp
|
||||
.Bl -tag -width "ENVSYS_BATTERY_CAPACITY_CRITICAL" -compact
|
||||
.It ENVSYS_BATTERY_CAPACITY_NORMAL
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: sysmon_envsys.c,v 1.87 2009/06/08 00:55:35 pgoyette Exp $ */
|
||||
/* $NetBSD: sysmon_envsys.c,v 1.88 2009/06/13 16:08:25 pgoyette Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2007, 2008 Juan Romero Pardines.
|
||||
@ -64,7 +64,7 @@
|
||||
*/
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
__KERNEL_RCSID(0, "$NetBSD: sysmon_envsys.c,v 1.87 2009/06/08 00:55:35 pgoyette Exp $");
|
||||
__KERNEL_RCSID(0, "$NetBSD: sysmon_envsys.c,v 1.88 2009/06/13 16:08:25 pgoyette Exp $");
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/types.h>
|
||||
@ -1633,6 +1633,76 @@ sme_update_dictionary(struct sysmon_envsys *sme)
|
||||
if (error)
|
||||
break;
|
||||
}
|
||||
|
||||
#ifdef NOTYET
|
||||
/*
|
||||
* Update limits from driver if they've been changed
|
||||
*/
|
||||
if ((edata->flags & ENVSYS_FLIMITS_CHANGED) == 0)
|
||||
continue;
|
||||
|
||||
if (edata->upropset & PROP_DRVR_CRITMAX) {
|
||||
error = sme_sensor_upint32(dict, "critical-max",
|
||||
edata->lim_critmax);
|
||||
if (error)
|
||||
break;
|
||||
edata->upropset &= ~PROP_USER_CRITMAX;
|
||||
} else if ((edata->upropset & PROP_USER_CRITMAX) == 0)
|
||||
prop_dictionary_remove(dict, "critical-max");
|
||||
|
||||
if (edata->upropset & PROP_DRVR_WARNMAX) {
|
||||
error = sme_sensor_upint32(dict, "warning-max",
|
||||
edata->lim_warnmax);
|
||||
if (error)
|
||||
break;
|
||||
edata->upropset &= ~PROP_USER_WARNMAX;
|
||||
} else if ((edata->upropset & PROP_USER_WARNMAX) == 0)
|
||||
prop_dictionary_remove(dict, "warning-max");
|
||||
|
||||
if (edata->flags & ENVSYS_FPERCENT) {
|
||||
if (edata->upropset & PROP_DRVR_BATTWARN) {
|
||||
error = sme_sensor_upint32(dict,
|
||||
"warning-capacity",
|
||||
edata->lim_warnmin);
|
||||
if (error)
|
||||
break;
|
||||
edata->upropset &= ~PROP_USER_BATTWARN;
|
||||
} else if ((edata->upropset & PROP_USER_BATTWARN) == 0)
|
||||
prop_dictionary_remove(dict,
|
||||
"warning-capacity");
|
||||
|
||||
if (edata->upropset & PROP_DRVR_BATTCAP) {
|
||||
error = sme_sensor_upint32(dict,
|
||||
"critical-capacity",
|
||||
edata->lim_critmin);
|
||||
if (error)
|
||||
break;
|
||||
edata->upropset &= ~PROP_USER_BATTCAP;
|
||||
} else if ((edata->upropset & PROP_USER_BATTCAP) == 0)
|
||||
prop_dictionary_remove(dict,
|
||||
"critical-capacity");
|
||||
} else {
|
||||
if (edata->upropset & PROP_DRVR_WARNMIN) {
|
||||
error = sme_sensor_upint32(dict,
|
||||
"warning-min",
|
||||
edata->lim_warnmin);
|
||||
if (error)
|
||||
break;
|
||||
edata->upropset &= ~PROP_USER_WARNMIN;
|
||||
} else if ((edata->upropset & PROP_USER_WARNMIN) == 0)
|
||||
prop_dictionary_remove(dict, "warning-min");
|
||||
|
||||
if (edata->upropset & PROP_DRVR_CRITMIN) {
|
||||
error = sme_sensor_upint32(dict,
|
||||
"critical-min",
|
||||
edata->lim_critmin);
|
||||
if (error)
|
||||
break;
|
||||
edata->upropset &= ~PROP_USER_CRITMIN;
|
||||
} else if ((edata->upropset & PROP_USER_CRITMIN) == 0)
|
||||
prop_dictionary_remove(dict, "critical-min");
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
return error;
|
||||
@ -1653,8 +1723,7 @@ sme_userset_dictionary(struct sysmon_envsys *sme, prop_dictionary_t udict,
|
||||
prop_dictionary_t dict, tdict = NULL;
|
||||
prop_object_t obj, obj1, obj2, tobj = NULL;
|
||||
uint64_t refresh_timo = 0;
|
||||
int32_t critmax = 0, warnmax = 0, warnmin = 0, critmin = 0;
|
||||
int props = 0;
|
||||
sysmon_envsys_lim_t lims;
|
||||
int i, error = 0;
|
||||
const char *blah;
|
||||
bool targetfound = false;
|
||||
@ -1718,6 +1787,8 @@ sme_userset_dictionary(struct sysmon_envsys *sme, prop_dictionary_t udict,
|
||||
if (!prop_string_equals(obj1, obj))
|
||||
continue;
|
||||
|
||||
lims.sel_flags = 0;
|
||||
|
||||
/*
|
||||
* Check if a new description operation was
|
||||
* requested by the user and set new description.
|
||||
@ -1796,8 +1867,8 @@ sme_userset_dictionary(struct sysmon_envsys *sme, prop_dictionary_t udict,
|
||||
goto out;
|
||||
}
|
||||
|
||||
critmin = prop_number_integer_value(obj2);
|
||||
props |= PROP_BATTCAP;
|
||||
lims.sel_critmin = prop_number_integer_value(obj2);
|
||||
lims.sel_flags |= PROP_BATTCAP;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1812,8 +1883,8 @@ sme_userset_dictionary(struct sysmon_envsys *sme, prop_dictionary_t udict,
|
||||
goto out;
|
||||
}
|
||||
|
||||
warnmin = prop_number_integer_value(obj2);
|
||||
props |= PROP_BATTWARN;
|
||||
lims.sel_warnmin = prop_number_integer_value(obj2);
|
||||
lims.sel_flags |= PROP_BATTWARN;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1829,8 +1900,8 @@ sme_userset_dictionary(struct sysmon_envsys *sme, prop_dictionary_t udict,
|
||||
goto out;
|
||||
}
|
||||
|
||||
critmax = prop_number_integer_value(obj2);
|
||||
props |= PROP_CRITMAX;
|
||||
lims.sel_critmax = prop_number_integer_value(obj2);
|
||||
lims.sel_flags |= PROP_CRITMAX;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1846,8 +1917,8 @@ sme_userset_dictionary(struct sysmon_envsys *sme, prop_dictionary_t udict,
|
||||
goto out;
|
||||
}
|
||||
|
||||
warnmax = prop_number_integer_value(obj2);
|
||||
props |= PROP_WARNMAX;
|
||||
lims.sel_warnmax = prop_number_integer_value(obj2);
|
||||
lims.sel_flags |= PROP_WARNMAX;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1863,8 +1934,8 @@ sme_userset_dictionary(struct sysmon_envsys *sme, prop_dictionary_t udict,
|
||||
goto out;
|
||||
}
|
||||
|
||||
critmin = prop_number_integer_value(obj2);
|
||||
props |= PROP_CRITMIN;
|
||||
lims.sel_critmin = prop_number_integer_value(obj2);
|
||||
lims.sel_flags |= PROP_CRITMIN;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -1880,16 +1951,12 @@ sme_userset_dictionary(struct sysmon_envsys *sme, prop_dictionary_t udict,
|
||||
goto out;
|
||||
}
|
||||
|
||||
warnmin = prop_number_integer_value(obj2);
|
||||
props |= PROP_WARNMIN;
|
||||
lims.sel_warnmin = prop_number_integer_value(obj2);
|
||||
lims.sel_flags |= PROP_WARNMIN;
|
||||
}
|
||||
|
||||
if (props) {
|
||||
error = sme_event_register(dict,
|
||||
edata,
|
||||
sme,
|
||||
critmax, warnmax, warnmin,
|
||||
critmin, props,
|
||||
if (lims.sel_flags) {
|
||||
error = sme_event_register(dict, edata, sme, &lims,
|
||||
(edata->flags & ENVSYS_FPERCENT)?
|
||||
PENVSYS_EVENT_CAPACITY:
|
||||
PENVSYS_EVENT_LIMITS,
|
||||
@ -1900,7 +1967,7 @@ sme_userset_dictionary(struct sysmon_envsys *sme, prop_dictionary_t udict,
|
||||
goto out;
|
||||
|
||||
mutex_enter(&sme->sme_mtx);
|
||||
edata->upropset |= props;
|
||||
edata->upropset |= lims.sel_flags;
|
||||
mutex_exit(&sme->sme_mtx);
|
||||
}
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: sysmon_envsys_events.c,v 1.66 2009/06/08 13:06:33 pgoyette Exp $ */
|
||||
/* $NetBSD: sysmon_envsys_events.c,v 1.67 2009/06/13 16:08:25 pgoyette Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2007, 2008 Juan Romero Pardines.
|
||||
@ -30,7 +30,7 @@
|
||||
*/
|
||||
|
||||
#include <sys/cdefs.h>
|
||||
__KERNEL_RCSID(0, "$NetBSD: sysmon_envsys_events.c,v 1.66 2009/06/08 13:06:33 pgoyette Exp $");
|
||||
__KERNEL_RCSID(0, "$NetBSD: sysmon_envsys_events.c,v 1.67 2009/06/13 16:08:25 pgoyette Exp $");
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/types.h>
|
||||
@ -82,9 +82,8 @@ static bool sme_acadapter_check(void);
|
||||
*/
|
||||
int
|
||||
sme_event_register(prop_dictionary_t sdict, envsys_data_t *edata,
|
||||
struct sysmon_envsys *sme, int32_t critmax,
|
||||
int32_t warnmax, int32_t warnmin, int32_t critmin,
|
||||
int lim_flags, int crittype, int powertype)
|
||||
struct sysmon_envsys *sme, sysmon_envsys_lim_t *lims,
|
||||
int crittype, int powertype)
|
||||
{
|
||||
sme_event_t *see = NULL, *osee = NULL;
|
||||
prop_object_t obj;
|
||||
@ -108,36 +107,36 @@ sme_event_register(prop_dictionary_t sdict, envsys_data_t *edata,
|
||||
__func__, sme->sme_name, edata->desc, lim_flags));
|
||||
|
||||
see = osee;
|
||||
if (lim_flags & PROP_CRITMAX) {
|
||||
if (critmax == see->see_critmax) {
|
||||
if (lims->sel_flags & PROP_CRITMAX) {
|
||||
if (lims->sel_critmax == see->see_lims.sel_critmax) {
|
||||
DPRINTF(("%s: type=%d (critmax exists)\n",
|
||||
__func__, crittype));
|
||||
error = EEXIST;
|
||||
lim_flags &= ~PROP_CRITMAX;
|
||||
lims->sel_flags &= ~PROP_CRITMAX;
|
||||
}
|
||||
}
|
||||
if (lim_flags & PROP_WARNMAX) {
|
||||
if (warnmax == see->see_warnmax) {
|
||||
if (lims->sel_flags & PROP_WARNMAX) {
|
||||
if (lims->sel_warnmax == see->see_lims.sel_warnmax) {
|
||||
DPRINTF(("%s: type=%d (warnmax exists)\n",
|
||||
__func__, crittype));
|
||||
error = EEXIST;
|
||||
lim_flags &= ~PROP_WARNMAX;
|
||||
lims->sel_flags &= ~PROP_WARNMAX;
|
||||
}
|
||||
}
|
||||
if (lim_flags & (PROP_WARNMIN | PROP_BATTWARN)) {
|
||||
if (warnmin == see->see_warnmin) {
|
||||
if (lims->sel_flags & (PROP_WARNMIN | PROP_BATTWARN)) {
|
||||
if (lims->sel_warnmin == see->see_lims.sel_warnmin) {
|
||||
DPRINTF(("%s: type=%d (warnmin exists)\n",
|
||||
__func__, crittype));
|
||||
error = EEXIST;
|
||||
lim_flags &= ~(PROP_WARNMIN | PROP_BATTWARN);
|
||||
lims->sel_flags &= ~(PROP_WARNMIN | PROP_BATTWARN);
|
||||
}
|
||||
}
|
||||
if (lim_flags & (PROP_CRITMIN | PROP_BATTCAP)) {
|
||||
if (critmin == see->see_critmin) {
|
||||
if (lims->sel_flags & (PROP_CRITMIN | PROP_BATTCAP)) {
|
||||
if (lims->sel_critmin == see->see_lims.sel_critmin) {
|
||||
DPRINTF(("%s: type=%d (critmin exists)\n",
|
||||
__func__, crittype));
|
||||
error = EEXIST;
|
||||
lim_flags &= ~(PROP_CRITMIN | PROP_BATTCAP);
|
||||
lims->sel_flags &= ~(PROP_CRITMIN | PROP_BATTCAP);
|
||||
}
|
||||
}
|
||||
break;
|
||||
@ -192,7 +191,7 @@ sme_event_register(prop_dictionary_t sdict, envsys_data_t *edata,
|
||||
/*
|
||||
* Limit operation requested.
|
||||
*/
|
||||
if (lim_flags & PROP_CRITMAX) {
|
||||
if (lims->sel_flags & PROP_CRITMAX) {
|
||||
objkey = "critical-max";
|
||||
obj = prop_dictionary_get(sdict, objkey);
|
||||
if (obj && prop_object_type(obj) != PROP_TYPE_NUMBER) {
|
||||
@ -200,17 +199,19 @@ sme_event_register(prop_dictionary_t sdict, envsys_data_t *edata,
|
||||
__func__, sme->sme_name, objkey));
|
||||
error = ENOTSUP;
|
||||
} else {
|
||||
see->see_critmax = critmax;
|
||||
error = sme_sensor_upint32(sdict, objkey, critmax);
|
||||
see->see_lims.sel_critmax = lims->sel_critmax;
|
||||
error = sme_sensor_upint32(sdict, objkey,
|
||||
lims->sel_critmax);
|
||||
DPRINTF(("%s: (%s) event [sensor=%s type=%d] "
|
||||
"(%s updated)\n", __func__, sme->sme_name,
|
||||
edata->desc, crittype, objkey));
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
see->see_edata->upropset |= PROP_CRITMAX;
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
|
||||
if (lim_flags & PROP_WARNMAX) {
|
||||
if (lims->sel_flags & PROP_WARNMAX) {
|
||||
objkey = "warning-max";
|
||||
obj = prop_dictionary_get(sdict, objkey);
|
||||
if (obj && prop_object_type(obj) != PROP_TYPE_NUMBER) {
|
||||
@ -218,17 +219,19 @@ sme_event_register(prop_dictionary_t sdict, envsys_data_t *edata,
|
||||
__func__, sme->sme_name, objkey));
|
||||
error = ENOTSUP;
|
||||
} else {
|
||||
see->see_warnmax = warnmax;
|
||||
error = sme_sensor_upint32(sdict, objkey, warnmax);
|
||||
see->see_lims.sel_warnmax = lims->sel_warnmax;
|
||||
error = sme_sensor_upint32(sdict, objkey,
|
||||
lims->sel_warnmax);
|
||||
DPRINTF(("%s: (%s) event [sensor=%s type=%d] "
|
||||
"(%s updated)\n", __func__, sme->sme_name,
|
||||
edata->desc, crittype, objkey));
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
see->see_edata->upropset |= PROP_WARNMAX;
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
|
||||
if (lim_flags & PROP_WARNMIN) {
|
||||
if (lims->sel_flags & PROP_WARNMIN) {
|
||||
objkey = "warning-min";
|
||||
obj = prop_dictionary_get(sdict, objkey);
|
||||
if (obj && prop_object_type(obj) != PROP_TYPE_NUMBER) {
|
||||
@ -236,17 +239,19 @@ sme_event_register(prop_dictionary_t sdict, envsys_data_t *edata,
|
||||
__func__, sme->sme_name, objkey));
|
||||
error = ENOTSUP;
|
||||
} else {
|
||||
see->see_warnmin = warnmin;
|
||||
error = sme_sensor_upint32(sdict, objkey, warnmin);
|
||||
see->see_lims.sel_warnmin = lims->sel_warnmin;
|
||||
error = sme_sensor_upint32(sdict, objkey,
|
||||
lims->sel_warnmin);
|
||||
DPRINTF(("%s: (%s) event [sensor=%s type=%d] "
|
||||
"(%s updated)\n", __func__, sme->sme_name,
|
||||
edata->desc, crittype, objkey));
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
see->see_edata->upropset |= PROP_WARNMIN;
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
|
||||
if (lim_flags & PROP_CRITMIN) {
|
||||
if (lims->sel_flags & PROP_CRITMIN) {
|
||||
objkey = "critical-min";
|
||||
obj = prop_dictionary_get(sdict, objkey);
|
||||
if (obj && prop_object_type(obj) != PROP_TYPE_NUMBER) {
|
||||
@ -254,17 +259,19 @@ sme_event_register(prop_dictionary_t sdict, envsys_data_t *edata,
|
||||
__func__, sme->sme_name, objkey));
|
||||
error = ENOTSUP;
|
||||
} else {
|
||||
see->see_critmin = critmin;
|
||||
error = sme_sensor_upint32(sdict, objkey, critmin);
|
||||
see->see_lims.sel_critmin = lims->sel_critmin;
|
||||
error = sme_sensor_upint32(sdict, objkey,
|
||||
lims->sel_critmin);
|
||||
DPRINTF(("%s: (%s) event [sensor=%s type=%d] "
|
||||
"(%s updated)\n", __func__, sme->sme_name,
|
||||
edata->desc, crittype, objkey));
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
see->see_edata->upropset |= PROP_CRITMIN;
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
|
||||
if (lim_flags & PROP_BATTWARN) {
|
||||
if (lims->sel_flags & PROP_BATTWARN) {
|
||||
objkey = "warning-capacity";
|
||||
obj = prop_dictionary_get(sdict, objkey);
|
||||
if (obj && prop_object_type(obj) != PROP_TYPE_NUMBER) {
|
||||
@ -272,17 +279,19 @@ sme_event_register(prop_dictionary_t sdict, envsys_data_t *edata,
|
||||
__func__, sme->sme_name, objkey));
|
||||
error = ENOTSUP;
|
||||
} else {
|
||||
see->see_warnmin = warnmin;
|
||||
error = sme_sensor_upint32(sdict, objkey, warnmin);
|
||||
see->see_lims.sel_warnmin = lims->sel_warnmin;
|
||||
error = sme_sensor_upint32(sdict, objkey,
|
||||
lims->sel_warnmin);
|
||||
DPRINTF(("%s: (%s) event [sensor=%s type=%d] "
|
||||
"(%s updated)\n", __func__, sme->sme_name,
|
||||
edata->desc, crittype, objkey));
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
see->see_edata->upropset |= PROP_BATTWARN;
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
|
||||
if (lim_flags & PROP_BATTCAP) {
|
||||
if (lims->sel_flags & PROP_BATTCAP) {
|
||||
objkey = "critical-capacity";
|
||||
obj = prop_dictionary_get(sdict, objkey);
|
||||
if (obj && prop_object_type(obj) != PROP_TYPE_NUMBER) {
|
||||
@ -290,28 +299,41 @@ sme_event_register(prop_dictionary_t sdict, envsys_data_t *edata,
|
||||
__func__, sme->sme_name, objkey));
|
||||
error = ENOTSUP;
|
||||
} else {
|
||||
see->see_critmin = critmin;
|
||||
error = sme_sensor_upint32(sdict, objkey, critmin);
|
||||
see->see_lims.sel_critmin = lims->sel_critmin;
|
||||
error = sme_sensor_upint32(sdict, objkey,
|
||||
lims->sel_critmin);
|
||||
DPRINTF(("%s: (%s) event [sensor=%s type=%d] "
|
||||
"(%s updated)\n", __func__, sme->sme_name,
|
||||
edata->desc, crittype, objkey));
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
see->see_edata->upropset |= PROP_BATTCAP;
|
||||
}
|
||||
if (error && error != EEXIST)
|
||||
goto out;
|
||||
|
||||
DPRINTF(("%s: (%s) event registered (sensor=%s snum=%d type=%d "
|
||||
"critmin=%" PRIu32 " warnmin=%" PRIu32 " warnmax=%" PRIu32
|
||||
" critmax=%" PRIu32 " props 0x%04x)\n", __func__,
|
||||
see->see_sme->sme_name, see->see_pes.pes_sensname,
|
||||
see->see_edata->sensor, see->see_type, see->see_critmin,
|
||||
see->see_warnmin, see->see_warnmax, see->see_critmax,
|
||||
see->see_edata->upropset));
|
||||
see->see_edata->sensor, see->see_type, see->see_lims.sel_critmin,
|
||||
see->see_lims.sel_warnmin, see->see_lims.sel_warnmax,
|
||||
see->see_lims.sel_critmax, see->see_edata->upropset));
|
||||
/*
|
||||
* Initialize the events framework if it wasn't initialized before.
|
||||
*/
|
||||
if ((sme->sme_flags & SME_CALLOUT_INITIALIZED) == 0)
|
||||
error = sme_events_init(sme);
|
||||
|
||||
/*
|
||||
* If driver requested notification, advise it of new
|
||||
* limit values
|
||||
*/
|
||||
if (sme->sme_set_limits) {
|
||||
see->see_lims.sel_flags = see->see_edata->upropset &
|
||||
PROP_LIMITS;
|
||||
(*sme->sme_set_limits)(sme, &(see->see_lims));
|
||||
}
|
||||
|
||||
out:
|
||||
if ((error == 0 || error == EEXIST) && osee == NULL)
|
||||
LIST_INSERT_HEAD(&sme->sme_events_list, see, see_list);
|
||||
@ -428,6 +450,7 @@ void
|
||||
sme_event_drvadd(void *arg)
|
||||
{
|
||||
sme_event_drv_t *sed_t = arg;
|
||||
sysmon_envsys_lim_t lims;
|
||||
int error = 0;
|
||||
|
||||
KASSERT(sed_t != NULL);
|
||||
@ -440,7 +463,7 @@ do { \
|
||||
error = sme_event_register(sed_t->sed_sdict, \
|
||||
sed_t->sed_edata, \
|
||||
sed_t->sed_sme, \
|
||||
0, 0, 0, 0, 0, \
|
||||
&lims, \
|
||||
(b), \
|
||||
sed_t->sed_powertype); \
|
||||
if (error && error != EEXIST) \
|
||||
@ -457,18 +480,26 @@ do { \
|
||||
} \
|
||||
} while (/* CONSTCOND */ 0)
|
||||
|
||||
if (sed_t->sed_edata->flags & ENVSYS_FMONLIMITS) {
|
||||
if (sed_t->sed_sme->sme_get_limits)
|
||||
(*sed_t->sed_sme->sme_get_limits)(sed_t->sed_sme,
|
||||
&lims);
|
||||
else
|
||||
sed_t->sed_edata->flags &= ~ENVSYS_FMONLIMITS;
|
||||
}
|
||||
|
||||
SEE_REGEVENT(ENVSYS_FMONCRITICAL,
|
||||
PENVSYS_EVENT_CRITICAL,
|
||||
"critical");
|
||||
|
||||
SEE_REGEVENT(ENVSYS_FMONLIMITS,
|
||||
PENVSYS_EVENT_LIMITS,
|
||||
"hw-range-limits");
|
||||
|
||||
SEE_REGEVENT(ENVSYS_FMONSTCHANGED,
|
||||
PENVSYS_EVENT_STATE_CHANGED,
|
||||
"state-changed");
|
||||
|
||||
SEE_REGEVENT(ENVSYS_FMONLIMITS,
|
||||
PENVSYS_EVENT_LIMITS,
|
||||
"hw-range-limits");
|
||||
|
||||
/*
|
||||
* we are done, free memory now.
|
||||
*/
|
||||
@ -604,24 +635,31 @@ sme_events_worker(struct work *wk, void *arg)
|
||||
|
||||
switch (see->see_type) {
|
||||
/*
|
||||
* For user range limits, calculate a new state first
|
||||
* State based on user limits will override any hardware
|
||||
* detected state.
|
||||
* For range limits, if the driver claims responsibility for
|
||||
* limit/range checking, just user driver-supplied status.
|
||||
* Else calculate our own status. Note that driver must
|
||||
* relinquish responsibility for ALL limits if there is even
|
||||
* one limit that it cannot handle!
|
||||
*/
|
||||
case PENVSYS_EVENT_LIMITS:
|
||||
case PENVSYS_EVENT_CAPACITY:
|
||||
#define __EXCEEDED_LIMIT(lim, rel) ((lim) && edata->value_cur rel (lim))
|
||||
if __EXCEEDED_LIMIT(see->see_critmin, <)
|
||||
edata->state = ENVSYS_SCRITUNDER;
|
||||
else if __EXCEEDED_LIMIT(see->see_warnmin, <)
|
||||
edata->state = ENVSYS_SWARNUNDER;
|
||||
else if __EXCEEDED_LIMIT(see->see_warnmax, >)
|
||||
edata->state = ENVSYS_SWARNOVER;
|
||||
else if __EXCEEDED_LIMIT(see->see_critmax, >)
|
||||
edata->state = ENVSYS_SCRITOVER;
|
||||
#define __EXCEED_LIM(lim, rel) ((lim) && edata->value_cur rel (lim))
|
||||
if ((see->see_lims.sel_flags & PROP_DRIVER_LIMITS) == 0) {
|
||||
if __EXCEED_LIM(see->see_lims.sel_critmin, <)
|
||||
edata->state = ENVSYS_SCRITUNDER;
|
||||
else if __EXCEED_LIM(see->see_lims.sel_warnmin, <)
|
||||
edata->state = ENVSYS_SWARNUNDER;
|
||||
else if __EXCEED_LIM(see->see_lims.sel_warnmax, >)
|
||||
edata->state = ENVSYS_SWARNOVER;
|
||||
else if __EXCEED_LIM(see->see_lims.sel_critmax, >)
|
||||
edata->state = ENVSYS_SCRITOVER;
|
||||
}
|
||||
/* FALLTHROUGH */
|
||||
#undef __EXCEEDED_LIMIT
|
||||
#undef __EXCEED_LIM
|
||||
|
||||
/*
|
||||
* Send event if state has changed
|
||||
*/
|
||||
if (edata->state == see->see_evsent)
|
||||
break;
|
||||
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: sysmon_envsysvar.h,v 1.29 2009/06/08 00:55:35 pgoyette Exp $ */
|
||||
/* $NetBSD: sysmon_envsysvar.h,v 1.30 2009/06/13 16:08:25 pgoyette Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2007, 2008 Juan Romero Pardines.
|
||||
@ -73,10 +73,7 @@ typedef struct sme_event {
|
||||
struct sysmon_envsys *see_sme; /* device associated */
|
||||
struct penvsys_state see_pes; /* our power envsys */
|
||||
envsys_data_t *see_edata; /* our sensor data */
|
||||
int32_t see_critmin; /* critical-min value set */
|
||||
int32_t see_warnmin; /* warning-min value set */
|
||||
int32_t see_warnmax; /* warning-max value set */
|
||||
int32_t see_critmax; /* critical-max value set */
|
||||
sysmon_envsys_lim_t see_lims; /* limit values */
|
||||
int see_type; /* type of the event */
|
||||
int see_evsent; /* event already sent */
|
||||
int see_flags; /* see above */
|
||||
@ -128,8 +125,8 @@ void sysmon_envsys_release(struct sysmon_envsys *, bool);
|
||||
* functions to handle sysmon envsys events.
|
||||
*/
|
||||
int sme_event_register(prop_dictionary_t, envsys_data_t *,
|
||||
struct sysmon_envsys *, int32_t, int32_t,
|
||||
int32_t, int32_t, int, int, int);
|
||||
struct sysmon_envsys *, sysmon_envsys_lim_t *,
|
||||
int, int);
|
||||
int sme_event_unregister(struct sysmon_envsys *, const char *, int);
|
||||
void sme_event_unregister_all(struct sysmon_envsys *);
|
||||
void sme_event_drvadd(void *);
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: sysmonvar.h,v 1.27 2008/06/03 15:00:57 jmcneill Exp $ */
|
||||
/* $NetBSD: sysmonvar.h,v 1.28 2009/06/13 16:08:25 pgoyette Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 2000 Zembu Labs, Inc.
|
||||
@ -60,7 +60,6 @@ struct workqueue;
|
||||
*****************************************************************************/
|
||||
|
||||
struct sme_event;
|
||||
struct sme_sensor_names;
|
||||
|
||||
struct sysmon_envsys {
|
||||
const char *sme_name; /* envsys device name */
|
||||
@ -86,6 +85,13 @@ struct sysmon_envsys {
|
||||
*/
|
||||
void (*sme_refresh)(struct sysmon_envsys *, envsys_data_t *);
|
||||
|
||||
/*
|
||||
* Function callbacks to exchange limit/threshold values
|
||||
* with device
|
||||
*/
|
||||
void (*sme_set_limits)(struct sysmon_envsys *, sysmon_envsys_lim_t *);
|
||||
void (*sme_get_limits)(struct sysmon_envsys *, sysmon_envsys_lim_t *);
|
||||
|
||||
struct workqueue *sme_wq; /* the workqueue for the events */
|
||||
struct callout sme_callout; /* for the events */
|
||||
uint64_t sme_events_timeout; /* the timeout used in the callout */
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: envsys.h,v 1.25 2009/06/08 00:55:35 pgoyette Exp $ */
|
||||
/* $NetBSD: envsys.h,v 1.26 2009/06/13 16:08:25 pgoyette Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1999, 2007 The NetBSD Foundation, Inc.
|
||||
@ -145,7 +145,8 @@ enum envsys_battery_capacity_states {
|
||||
#define ENVSYS_REMOVEPROPS _IOWR('E', 2, struct plistref)
|
||||
|
||||
/*
|
||||
* Properties that can be set in upropset
|
||||
* Properties that can be set in upropset (and in the event_limit's
|
||||
* flags field)
|
||||
*/
|
||||
#define PROP_CRITMAX 0x0001
|
||||
#define PROP_CRITMIN 0x0002
|
||||
@ -156,6 +157,22 @@ enum envsys_battery_capacity_states {
|
||||
#define PROP_DESC 0x0040
|
||||
#define PROP_RFACT 0x0080
|
||||
|
||||
#define PROP_DRIVER_LIMITS 0x8000
|
||||
#define PROP_LIMITS 0x003f
|
||||
|
||||
/*
|
||||
* Thresholds/limits that are being monitored
|
||||
*/
|
||||
struct sysmon_envsys_lim {
|
||||
uint32_t sel_flags; /* Flag which limits are present */
|
||||
int32_t sel_critmax;
|
||||
int32_t sel_warnmax;
|
||||
int32_t sel_warnmin;
|
||||
int32_t sel_critmin;
|
||||
};
|
||||
|
||||
typedef struct sysmon_envsys_lim sysmon_envsys_lim_t;
|
||||
|
||||
/*
|
||||
* Compatibility with old interface. Only ENVSYS_GTREDATA
|
||||
* and ENVSYS_GTREINFO ioctls are supported.
|
||||
|
Loading…
Reference in New Issue
Block a user