summaryrefslogtreecommitdiff
path: root/usr/src/uts/sun4u/sys/ppmvar.h
diff options
context:
space:
mode:
authorstevel@tonic-gate <none@none>2005-06-14 00:00:00 -0700
committerstevel@tonic-gate <none@none>2005-06-14 00:00:00 -0700
commit7c478bd95313f5f23a4c958a745db2134aa03244 (patch)
treec871e58545497667cbb4b0a4f2daf204743e1fe7 /usr/src/uts/sun4u/sys/ppmvar.h
downloadillumos-joyent-7c478bd95313f5f23a4c958a745db2134aa03244.tar.gz
OpenSolaris Launch
Diffstat (limited to 'usr/src/uts/sun4u/sys/ppmvar.h')
-rw-r--r--usr/src/uts/sun4u/sys/ppmvar.h378
1 files changed, 378 insertions, 0 deletions
diff --git a/usr/src/uts/sun4u/sys/ppmvar.h b/usr/src/uts/sun4u/sys/ppmvar.h
new file mode 100644
index 0000000000..9b5a2ae1ae
--- /dev/null
+++ b/usr/src/uts/sun4u/sys/ppmvar.h
@@ -0,0 +1,378 @@
+/*
+ * CDDL HEADER START
+ *
+ * The contents of this file are subject to the terms of the
+ * Common Development and Distribution License, Version 1.0 only
+ * (the "License"). You may not use this file except in compliance
+ * with the License.
+ *
+ * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+ * or http://www.opensolaris.org/os/licensing.
+ * See the License for the specific language governing permissions
+ * and limitations under the License.
+ *
+ * When distributing Covered Code, include this CDDL HEADER in each
+ * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+ * If applicable, add the following below this CDDL HEADER, with the
+ * fields enclosed by brackets "[]" replaced with your own identifying
+ * information: Portions Copyright [yyyy] [name of copyright owner]
+ *
+ * CDDL HEADER END
+ */
+/*
+ * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
+ * Use is subject to license terms.
+ */
+
+#ifndef _SYS_PPMVAR_H
+#define _SYS_PPMVAR_H
+
+#pragma ident "%Z%%M% %I% %E% SMI"
+
+#include <sys/epm.h>
+#include <sys/sunldi.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+
+typedef struct ppm_unit {
+ dev_info_t *dip; /* node dev info */
+ kmutex_t lock; /* global driver lock */
+ uint_t states; /* driver states */
+ timeout_id_t led_tid; /* timeout id for LED */
+} ppm_unit_t;
+
+/*
+ * driver states
+ */
+#define PPM_STATE_SUSPENDED 0x1 /* driver is suspended */
+
+/*
+ * Check for domain operational
+ */
+#define PPM_DOMAIN_UP(domp) (!(domp->dflags & PPMD_OFFLINE))
+
+/*
+ * LED constants
+ */
+#define PPM_LED_PULSE (drv_usectohz(250000)) /* 0.25 seconds */
+#define PPM_LEDON_INTERVAL (1 * PPM_LED_PULSE)
+#define PPM_LEDOFF_INTERVAL (8 * PPM_LED_PULSE)
+#define PPM_LEDON 1 /* (s10) */
+#define PPM_LEDOFF 0 /* (s10) */
+
+/*
+ * internal form of "ppm.conf" data
+ */
+struct ppm_db {
+ struct ppm_db *next;
+ char *name; /* device name */
+ int plen; /* strlen before wildcard(s10) */
+ int wccnt; /* upto 2 '*' allowed */
+ int wcpos[2]; /* '*' location in pathname */
+};
+typedef struct ppm_db ppm_db_t;
+
+struct ppm_cdata {
+ char *name; /* property name */
+ char **strings; /* string array */
+ uint_t cnt; /* property count */
+};
+
+/*
+ * ppm device info
+ */
+struct ppm_dev {
+ struct ppm_dev *next;
+ struct ppm_domain *domp;
+ dev_info_t *dip;
+ char *path; /* OBP device pathname */
+ int cmpt; /* component number */
+ int rplvl; /* last requested power level */
+ int level; /* actual current power level */
+ int lowest; /* lowest power level for device */
+ int highest; /* highest power level for device */
+ uint_t flags;
+};
+typedef struct ppm_dev ppm_dev_t;
+
+/*
+ * ppm_dev.flags field
+ */
+#define PPMDEV_PCI66_D2 0x1 /* device support D2 at pci 66mhz */
+#define PPMDEV_PCI_PROP_CLKPM 0x2 /* clock can be power managed */
+#define PPM_PM_POWEROP 0x10 /* power level change, initiated */
+ /* from PM is in progress. */
+#define PPM_PHC_WHILE_SET_POWER 0x20 /* power level of a device is */
+ /* changed through */
+ /* pm_power_has_changed path */
+ /* while power level change, */
+ /* initiated from PM is in */
+ /* progress. */
+
+
+/*
+ * per domain record of device _ever_ managed by ppm
+ */
+struct ppm_owned {
+ struct ppm_owned *next;
+ char *path; /* device pathname */
+ int initializing; /* initializing flag */
+};
+typedef struct ppm_owned ppm_owned_t;
+
+
+/*
+ * domain control data structure -
+ * when you need to do an op for a domain, look up the op in the
+ * cmd member of the struct, and then perform the method on the
+ * path using iowr cmd with the args specified in val or val and
+ * mask or the speed index.
+ */
+struct ppm_dc {
+ struct ppm_dc *next;
+ ldi_handle_t lh; /* layered (ldi) handle */
+ char *path; /* control device prom pathname */
+ uint_t cmd; /* search key: op to be performed */
+ uint_t method; /* control method / union selector */
+ /* one of PPMDC_KIO, PPMDC_I2CKIO, */
+ /* PPMDC_CPUSPEEDKIO */
+
+ union {
+ /* In each sub struct in union, the first three fields */
+ /* must be .iord, .iowr and .val and in such order. */
+ /* The .method field above selects a union sub struct */
+ /* for a particular .cmd operation. */
+ /* The association between .method and .cmd is platform */
+ /* specific, therefore described in ppm.conf file. */
+
+ /* PPMDC_KIO: simple KIO */
+ struct m_kio {
+ uint_t iord; /* IOCTL read cmd */
+ uint_t iowr; /* IOCTL write cmd */
+ uint_t val; /* ioctl arg */
+ uint_t delay; /* total delay before this */
+ /* operation can be carried out */
+ uint_t post_delay; /* post delay, if any */
+ } kio;
+
+ /* PPMDC_I2CKIO: KIO requires 'arg' as struct i2c_gpio */
+ /* (defined in i2c_client.h) */
+ struct m_i2ckio {
+ uint_t iord; /* IOCTL read cmd */
+ uint_t iowr; /* IOCTL write cmd */
+ uint_t val; /* register content */
+ uint_t mask; /* mask to select relevant bits */
+ /* of register content */
+ uint_t delay; /* total delay before this */
+ /* operation can be carried out */
+ uint_t post_delay; /* post delay, if any */
+ } i2c;
+
+ /* PPMDC_CPUSPEEDKIO, PPMDC_VCORE: cpu estar related */
+ /* simple KIO */
+ struct m_cpu {
+ uint_t iord; /* IOCTL read cmd */
+ uint_t iowr; /* IOCTL write cmd */
+ int val; /* new register value */
+ uint_t speeds; /* number of speeds cpu supports */
+ uint_t delay; /* microseconds post op delay */
+ } cpu;
+ } m_un;
+};
+typedef struct ppm_dc ppm_dc_t;
+
+/*
+ * ppm_dc.cmd field -
+ */
+#define PPMDC_CPU_NEXT 2
+#define PPMDC_PRE_CHNG 3
+#define PPMDC_CPU_GO 4
+#define PPMDC_POST_CHNG 5
+#define PPMDC_FET_ON 6
+#define PPMDC_FET_OFF 7
+#define PPMDC_LED_ON 8
+#define PPMDC_LED_OFF 9
+#define PPMDC_CLK_ON 10
+#define PPMDC_CLK_OFF 11
+#define PPMDC_PRE_PWR_OFF 12
+#define PPMDC_PRE_PWR_ON 13
+#define PPMDC_POST_PWR_ON 14
+#define PPMDC_PWR_OFF 15
+#define PPMDC_PWR_ON 16
+#define PPMDC_RESET_OFF 17
+#define PPMDC_RESET_ON 18
+
+/*
+ * ppm_dc.method field - select union element
+ */
+#define PPMDC_KIO 1 /* simple ioctl with val as arg */
+#define PPMDC_CPUSPEEDKIO 2 /* ioctl with speed index arg */
+#define PPMDC_VCORE 3 /* CPU Vcore change operation */
+#define PPMDC_I2CKIO 4 /* ioctl with i2c_gpio_t as arg */
+
+/*
+ * devices that are powered by the same source
+ * are grouped by this struct as a "power domain"
+ */
+struct ppm_domain {
+ char *name; /* domain name */
+ int dflags; /* domain flags */
+ int pwr_cnt; /* number of powered up devices */
+ ppm_db_t *conflist; /* all devices from ppm.conf file */
+ ppm_dev_t *devlist; /* current attached devices */
+ char *propname; /* domain property name */
+ kmutex_t lock; /* domain lock */
+ int refcnt; /* domain lock ref count */
+ int model; /* pm model, CPU, FET or LED */
+ int status; /* domain specific status */
+ ppm_dc_t *dc; /* domain control method */
+ ppm_owned_t *owned; /* list of ever owned devices */
+ struct ppm_domain *next; /* a linked list */
+ clock_t last_off_time; /* last time domain was off */
+
+};
+typedef struct ppm_domain ppm_domain_t;
+
+
+/*
+ * ppm_domain.model field -
+ */
+#define PPMD_CPU 1 /* cpu PM model */
+#define PPMD_FET 2 /* power FET pm model */
+#define PPMD_LED 3 /* LED pm model */
+#define PPMD_PCI 4 /* PCI pm model */
+#define PPMD_PCI_PROP 5 /* PCI_PROP pm model */
+#define PPMD_PCIE 6 /* PCI Express pm model */
+
+#define PPMD_IS_PCI(model) \
+ ((model) == PPMD_PCI || (model) == PPMD_PCI_PROP)
+
+/*
+ * ppm_domain.status field -
+ */
+#define PPMD_OFF 0x0 /* FET/LED/PCI clock: off */
+#define PPMD_ON 0x1 /* FET/LED/PCI clock: on */
+
+/*
+ * ppm_domain.dflags field -
+ */
+#define PPMD_LOCK_ONE 0x1
+#define PPMD_LOCK_ALL 0x4
+#define PPMD_PCI33MHZ 0x1000 /* 33mhz PCI slot */
+#define PPMD_PCI66MHZ 0x2000 /* 66mhz PCI slot */
+#define PPMD_INITCHILD_CLKON 0x4000 /* clk turned on in init_child */
+#define PPMD_OFFLINE 0x10000 /* domain is not functional */
+
+/*
+ * XXppm driver-specific routines called from common code (s10)
+ */
+struct ppm_funcs {
+ void (*dev_init)(ppm_dev_t *);
+ void (*dev_fini)(ppm_dev_t *);
+ void (*iocset)(uint8_t);
+ uint8_t (*iocget)(void);
+};
+
+extern ppm_domain_t *ppm_domain_p;
+extern void *ppm_statep;
+extern int ppm_inst;
+extern ppm_domain_t *ppm_domains[]; /* (s10) */
+extern struct ppm_funcs ppmf; /* (s10) */
+
+extern void ppm_dev_init(ppm_dev_t *);
+extern void ppm_dev_fini(ppm_dev_t *);
+extern int ppm_create_db(dev_info_t *);
+extern int ppm_claim_dev(dev_info_t *);
+extern void ppm_rem_dev(dev_info_t *);
+extern ppm_dev_t *ppm_get_dev(dev_info_t *, ppm_domain_t *);
+extern void ppm_init_cb(dev_info_t *);
+extern int ppm_init_lyr(ppm_dc_t *, dev_info_t *);
+extern ppm_domain_t *ppm_lookup_dev(dev_info_t *);
+extern ppm_domain_t *ppm_lookup_domain(char *);
+extern ppm_dc_t *ppm_lookup_dc(ppm_domain_t *, int);
+extern ppm_dc_t *ppm_lookup_hndl(int, ppm_dc_t *);
+extern ppm_domain_t *ppm_get_domain_by_dev(const char *);
+extern boolean_t ppm_none_else_holds_power(ppm_domain_t *);
+extern ppm_owned_t *ppm_add_owned(dev_info_t *, ppm_domain_t *);
+extern void ppm_lock_one(ppm_dev_t *, power_req_t *, int *);
+extern void ppm_lock_all(ppm_domain_t *, power_req_t *, int *);
+
+#define PPM_GET_PRIVATE(dip) \
+ DEVI(dip)->devi_pm_ppm_private
+#define PPM_SET_PRIVATE(dip, datap) \
+ DEVI(dip)->devi_pm_ppm_private = datap
+
+#define PPM_LOCK_DOMAIN(domp) { \
+ if (!MUTEX_HELD(&(domp)->lock)) \
+ mutex_enter(&(domp)->lock); \
+ (domp)->refcnt++; \
+}
+
+#define PPM_UNLOCK_DOMAIN(domp) { \
+ ASSERT(MUTEX_HELD(&(domp)->lock) && \
+ (domp)->refcnt > 0); \
+ if (--(domp)->refcnt == 0) \
+ mutex_exit(&(domp)->lock); \
+}
+
+/*
+ * debug support
+ */
+#ifdef DEBUG
+#include <sys/promif.h>
+
+extern char *ppm_get_ctlstr(int, uint_t);
+extern void ppm_print_dc(struct ppm_dc *);
+
+extern uint_t ppm_debug;
+
+#define D_CREATEDB 0x00000001
+#define D_CLAIMDEV 0x00000002
+#define D_ADDDEV 0x00000004
+#define D_REMDEV 0x00000008
+#define D_LOWEST 0x00000010
+#define D_SETLVL 0x00000020
+#define D_GPIO 0x00000040
+#define D_CPU 0x00000080
+#define D_FET 0x00000100
+#define D_PCIUPA 0x00000200
+#define D_1394 0x00000400
+#define D_CTLOPS1 0x00000800
+#define D_CTLOPS2 0x00001000
+#define D_SOME 0x00002000
+#define D_LOCKS 0x00004000
+#define D_IOCTL 0x00008000
+#define D_ATTACH 0x00010000
+#define D_DETACH 0x00020000
+#define D_OPEN 0x00040000
+#define D_CLOSE 0x00080000
+#define D_INIT 0x00100000
+#define D_FINI 0x00200000
+#define D_ERROR 0x00400000
+#define D_SETPWR 0x00800000
+#define D_LED 0x01000000
+#define D_PCI 0x02000000
+#define D_PPMDC 0x04000000
+#define D_CPR 0x08000000
+
+#define PPMD(level, arglist) { \
+ if (ppm_debug & (level)) { \
+ pm_log arglist; \
+ } \
+}
+/* (s10) */
+#define DPRINTF PPMD
+
+#else /* DEBUG */
+#define PPMD(level, arglist)
+#define DPRINTF(flag, args) /* (s10) */
+#endif /* DEBUG */
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif /* _SYS_PPMVAR_H */