1700 Add SCSI UNMAP support
[unleashed.git] / usr / src / uts / common / sys / pcmcia.h
blobd313eb1e56aa3e760f97f2927506ec6fb8c7810d
1 /*
2 * CDDL HEADER START
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License, Version 1.0 only
6 * (the "License"). You may not use this file except in compliance
7 * with the License.
9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10 * or http://www.opensolaris.org/os/licensing.
11 * See the License for the specific language governing permissions
12 * and limitations under the License.
14 * When distributing Covered Code, include this CDDL HEADER in each
15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16 * If applicable, add the following below this CDDL HEADER, with the
17 * fields enclosed by brackets "[]" replaced with your own identifying
18 * information: Portions Copyright [yyyy] [name of copyright owner]
20 * CDDL HEADER END
23 * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
24 * Use is subject to license terms.
28 * PCMCIA nexus
31 #ifndef _PCMCIA_H
32 #define _PCMCIA_H
34 #ifdef __cplusplus
35 extern "C" {
36 #endif
38 #if defined(DEBUG)
39 #define PCMCIA_DEBUG
40 #endif
42 #include <sys/modctl.h>
44 #define PCMCIA_MAX_ADAPTERS 8 /* maximum distinct adapters */
45 #define PCMCIA_MAX_SOCKETS 64 /* maximum distinct sockets */
46 #define PCMCIA_MAX_WIN_ADAPT 40
47 #define PCMCIA_MAX_WINDOWS (PCMCIA_MAX_ADAPTERS*PCMCIA_MAX_WIN_ADAPT)
48 #define PCMCIA_MAX_POWER 16 /* maximum power table entries */
50 #define _VERSION(major, minor) ((major)<<16|(minor))
53 * DDI/Nexus stuff
56 #define PCMCIA_NEXUS_NAME "pcmcia"
57 #define PCMCIA_ADAPTER_NODE "ddi_pcmcia:adapter"
58 #define PCMCIA_SOCKET_NODE "ddi_pcmcia:socket"
59 #define PCMCIA_PCCARD_NODE "ddi_pcmcia:pccard"
62 * private interface between nexus and adapter specific driver
63 * This is only an "ops" type structure
66 typedef struct pcmcia_if {
67 uint32_t pcif_magic; /* magic number to verify correct scructure */
68 uint32_t pcif_version;
69 int (*pcif_set_callback)();
70 int (*pcif_get_adapter)();
71 int (*pcif_get_page)();
72 int (*pcif_get_socket)();
73 int (*pcif_get_status)();
74 int (*pcif_get_window)();
75 int (*pcif_inquire_adapter)();
76 int (*pcif_inquire_socket)();
77 int (*pcif_inquire_window)();
78 int (*pcif_reset_socket)();
79 int (*pcif_set_page)();
80 int (*pcif_set_window)();
81 int (*pcif_set_socket)();
82 int (*pcif_set_interrupt)();
83 int (*pcif_clr_interrupt)();
84 int (*pcic_init_dev)();
85 uint32_t (*pcic_get_tstamp)();
86 } pcmcia_if_t;
89 * magic number and version information to identify
90 * variant of the PCMCIA nexus.
92 #define PCIF_MAGIC 0x50434946
93 #define PCIF_VERSION _VERSION(0, 1)
94 #define PCIF_MIN_VERSION _VERSION(0, 1)
95 #define DEFAULT_CS_NAME "cs"
98 * all adapter drivers use a commonly defined structure for
99 * their private data. This structure must be filled in
100 * and set. The an_private member is for the driver writer's
101 * use and is not looked at by the nexus.
103 struct pcmcia_adapter_nexus_private {
104 dev_info_t *an_dip;
105 pcmcia_if_t *an_if;
106 void *an_private;
107 ddi_iblock_cookie_t *an_iblock; /* high priority handler cookies */
108 ddi_idevice_cookie_t *an_idev;
109 uint32_t an_ipl;
112 typedef struct pcmcia_adapter_nexus_private anp_t;
114 struct pcm_regs {
115 uint32_t phys_hi;
116 uint32_t phys_lo;
117 uint32_t phys_len;
121 * shared interrupts are handled by the
122 * nexus going through the list
124 typedef struct inthandler {
125 struct inthandler *next;
126 struct inthandler *prev;
127 int flags;
128 uint32_t (*intr)(caddr_t, caddr_t);
129 unsigned handler_id;
130 void *arg1;
131 void *arg2;
132 unsigned socket;
133 unsigned irq;
134 unsigned priority;
135 ddi_softintr_t softid;
136 ddi_iblock_cookie_t iblk_cookie;
137 ddi_idevice_cookie_t idev_cookie;
138 } inthandler_t;
141 * parent private data area
142 * not using the old style but will adapt on request
143 * this allows better framework handling and 1275 compliance
146 struct pcmcia_parent_private {
147 int ppd_nreg; /* number of regs */
148 struct pcm_regs *ppd_reg; /* array of regs in parsed form */
149 int ppd_intr; /* number intrspecs (always 0 or 1) */
150 struct intrspec *ppd_intrspec;
151 void *pcm_dummy[3]; /* fill for prtconf -v */
152 struct pcm_regs *ppd_assigned; /* array of regs in parsed form */
153 short ppd_socket; /* socket number of this instance */
154 short ppd_function; /* function number */
155 int ppd_active; /* is PC Card in a socket and active */
156 uint32_t ppd_flags;
157 void *ppd_handle; /* client handle */
160 #define PPD_CARD_MULTI 0x0001 /* card is multifunction card */
161 #define PPD_CARD_CARDBUS 0x0002 /* card is CardBus type */
162 #define PPD_CB_BUSMASTER 0x0004 /* card bus card is busmaster */
163 #define PPD_SUSPENDED 0x0008 /* this device was pm suspended */
166 * macros to make indirect functions easier
167 * and shorter (makes cstyle happier)
170 #define GET_SOCKET_STATUS(f, dip, sock, stat)\
171 (*(f)->pcif_get_socket_status)(dip, sock, stat)
172 #define SET_CALLBACK(f, dip, callback, sock)\
173 (*(f)->pcif_set_callback)(dip, callback, sock)
175 #define GET_ADAPTER(f, dip, conf) (*(f)->pcif_get_adapter) (dip, conf)
176 #define GET_SOCKET(f, dip, sock) (*(f)->pcif_get_socket)(dip, sock)
177 #define GET_STATUS(f, dip, status) (*(f)->pcif_get_status)(dip, status)
178 #define GET_WINDOW(f, dip, window) (*(f)->pcif_get_window)(dip, window)
179 #define INQUIRE_ADAPTER(f, dip, inquire) (*(f)->pcif_inquire_adapter)(dip,\
180 inquire)
181 #define GET_CONFIG(f, dip, conf) INQUIRE_ADAPTER(f, dip, conf)
182 #define INQUIRE_SOCKET(f, dip, sock) (*(f)->pcif_inquire_socket)(dip, \
183 sock)
184 #define GET_PAGE(f, dip, page) (*(f)->pcif_get_page)(dip, page)
185 #define INQUIRE_WINDOW(f, dip, window) (*(f)->pcif_inquire_window)(dip, window)
186 #define RESET_SOCKET(f, dip, socket, mode) \
187 (*(f)->pcif_reset_socket)(dip, socket, mode)
188 #define SET_PAGE(f, dip, page) (*(f)->pcif_set_page)(dip, page)
189 #define SET_WINDOW(f, dip, window) (*(f)->pcif_set_window)(dip, window)
190 #define SET_SOCKET(f, dip, socket) (*(f)->pcif_set_socket)(dip, socket)
191 #define SET_IRQ(f, dip, handler) (*(f)->pcif_set_interrupt)(dip, handler)
192 #define CLEAR_IRQ(f, dip, handler) (*(f)->pcif_clr_interrupt)(dip, handler)
194 typedef struct pcmcia_cs {
195 uint32_t pccs_magic; /* magic number of verify correct structure */
196 uint32_t pccs_version;
197 int (*pccs_callback)();
198 int (*pccs_getconfig)();
199 } pcmcia_cs_t;
201 #define PCCS_MAGIC 0x50434353
202 #define PCCS_VERSION _VERSION(2, 1)
204 /* properties used by the nexus for setup */
205 #define ADAPT_PROP "adapters" /* property used to find adapter list */
206 #define CS_PROP "card-services" /* property specifying Card Services */
207 #define DEF_DRV_PROP "default-driver" /* default driver to load if no CIS */
210 * per adapter structure
211 * this structure defines everything necessary for the
212 * the nexus to interact with the adapter specific driver
215 struct pcmcia_adapter {
216 int pca_module; /* adapter major number */
217 int pca_unit; /* adapter minor number */
218 int pca_number; /* canonical adapter number */
219 struct dev_ops *pca_ops;
220 dev_info_t *pca_dip;
221 pcmcia_if_t *pca_if;
222 void *pca_power;
223 ddi_iblock_cookie_t *pca_iblock;
224 ddi_idevice_cookie_t *pca_idev;
225 kmutex_t *pca_mutex;
226 int pca_numpower;
227 int pca_numsockets;
228 int pca_first_socket;
229 uint32_t pca_flags;
230 char pca_name[MODMAXNAMELEN];
231 uint32_t pca_avail_intr;
232 inthandler_t pca_int_handlers;
235 #define PCA_RES_NEED_IRQ 0x0001 /* needs IRQ allocation */
236 #define PCA_RES_NEED_IO 0x0002 /* needs I/O allocation */
237 #define PCA_RES_NEED_MEM 0x0004 /* needs memory allocation */
238 #define PCA_RES_CONSTRAINT 0x0008 /* resource constraints defined */
239 #define PCA_IRQ_SMI_SHARE 0x0010 /* SMI and child share */
240 #define PCA_IRQ_SHAREABLE 0x0020 /* all interrupts sharable */
241 #define PCA_IRQ_ISA 0x0040 /* ISA style (host) interrupts */
243 /* These flags are for open/close -- hot-plug support in future */
244 #define PCMCIA_MAX_FUNCTIONS 8
245 #define PCS_CARD_PRESENT 0x0001 /* card in socket */
246 #define PCS_MULTI_FUNCTION 0x0002 /* indicates dip is multifunction */
247 #define PCS_SOCKET_ADDED 0x0004 /* CS knows about the socket */
248 #define PCS_COOKIES_VALID 0x0008 /* iblk and idev valid */
249 #define PCS_IRQ_ENABLED 0x0010 /* IRQ has been enabled */
250 #define PCS_SUSPENDED 0x0020 /* PM SUSPEND was done */
252 typedef struct pcmcia_logical_window {
253 int lw_window; /* window number */
254 int lw_socket; /* logical socket number assigned */
255 struct pcmcia_adapter *lw_adapter;
256 pcmcia_if_t *lw_if;
257 uint32_t lw_status;
258 baseaddr_t lw_base;
259 int lw_len;
260 } pcmcia_logical_window_t;
262 #define PCS_ENABLED 0x0002 /* window is enabled */
265 * management interface hook
267 #define EM_EVENTSIZE 4
268 struct pcmcia_mif {
269 struct pcmcia_mif *mif_next;
270 void (*mif_function)();
271 uint32_t mif_id;
272 uchar_t mif_events[EM_EVENTSIZE]; /* events registered for */
275 #define PR_WORDSIZE 8 /* bits in word */
276 #define PR_MASK 0x7
277 #define PR_GET(map, bit) (((uchar_t *)(map))[(bit)/PR_WORDSIZE] &\
278 (1 << ((bit) & PR_MASK)))
279 #define PR_SET(map, bit) (((uchar_t *)(map))[(bit)/PR_WORDSIZE] |=\
280 (1 << ((bit) & PR_MASK)))
281 #define PR_CLEAR(map, bit) (((uchar_t *)(map))[(bit)/PR_WORDSIZE] &=\
282 ~(1 << ((bit) & PR_MASK)))
283 #define PR_ADDR(map, bit) (((uchar_t *)(map)) + ((bit)/PR_WORDSIZE))
284 #define PR_ZERO(map) \
285 bzero((caddr_t)map, PCMCIA_MAX_SOCKETS / PR_WORDSIZE)
287 /* socket bit map */
288 typedef uchar_t socket_enum_t[PCMCIA_MAX_SOCKETS/PR_WORDSIZE];
291 * Max resoruce limits - all of these have to be power-of-2 aligned
292 * and the PR_MAX_IO_LEN and PR_MAX_MEM_LEN values must be at
293 * least 64 or the allocators will panic.
295 #define PR_MAX_IO_LEN 1024 /* bytes of IO space */
296 #define PR_MAX_IO_RANGES 4
297 #define PR_MAX_MEM_LEN 1024 /* pages or 4M bytes */
298 #define PR_MAX_MEM_RANGES 32
300 #define PR_MAX_IOADDR 0xffffffff
301 #define PR_MAX_MEMADDR 0xffffffff
302 #define PR_MAX_INTERRUPTS 0xff
306 * structures and definitions used in the private interface
309 /* general values */
310 #define PC_SUCCESS 1
311 #define PC_FAILURE 0
313 /* set_mem() */
314 #define PC_MEM_AM 0
315 #define PC_MEM_CM 1
317 /* device classes */
318 #define PCC_MULTI 0
319 #define PCC_MEMORY 1
320 #define PCC_SERIAL 2
321 #define PCC_PARALLEL 3
322 #define PCC_FIXED_DISK 4
323 #define PCC_VIDEO 5
324 #define PCC_LAN 6
327 * device information structure information
328 * this is what is used for initial construction of a device node
331 struct pcm_device_info {
332 int pd_socket;
333 int pd_function;
334 int pd_type;
335 uint32_t pd_handle;
336 uint32_t pd_tuples;
337 uint32_t pd_flags;
338 char pd_bind_name[MODMAXNAMELEN];
339 char pd_vers1_name[MODMAXNAMELEN*4];
340 char pd_generic_name[MODMAXNAMELEN];
343 #define PCM_GET_SOCKET(socknum) ((socknum) & 0x1F)
344 #define PCM_GET_FUNCTION(socknum) (((socknum) >> 5) & 0x7)
346 #define PCM_DEFAULT_NODEID (-1)
347 #define PCM_DEV_MODEL "model"
348 #define PCM_DEV_ACTIVE "card-active"
349 #define PCM_DEV_SOCKET "socket"
350 #define PCM_DEV_R2TYPE "16bitcard"
351 #define PCM_DEV_CARDBUS "cardbus"
353 typedef
354 struct init_dev {
355 int socket;
356 } init_dev_t;
359 * device descriptions
360 * used to determine what driver to associate with a PC Card
361 * so that automatic creation of device information trees can
362 * be supported.
365 typedef
366 struct pcm_device_node {
367 struct pcm_device_node *pd_next;
368 dev_info_t *pd_dip; /* proto device info */
369 char pd_name[16];
370 int pd_flags;
371 int pd_devtype; /* from device tuple */
372 int pd_funcid;
373 int pd_manfid;
374 int pd_manmask;
375 } pcm_dev_node_t;
377 #define PCMD_DEVTYPE 0x0001 /* match device type */
378 #define PCMD_FUNCID 0x0002 /* match function ID */
379 #define PCMD_MANFID 0x0004 /* match manufacturer ID */
380 #define PCMD_FUNCE 0x0008 /* match function extension */
381 #define PCMD_VERS1 0x0010 /* match VERSION_1 string(s) */
382 #define PCMD_JEDEC 0x0020 /* JEDEC ID */
384 #define PCM_NAME_1275 0x0001
385 #define PCM_NAME_VERS1 0x0002
386 #define PCM_NAME_GENERIC 0x0004
387 #define PCM_NO_CONFIG 0x0008
388 #define PCM_OTHER_NOCIS 0x0100
389 #define PCM_MULTI_FUNCTION 0x0200
391 #define PCM_MAX_R2_MEM 0x3ffffff
393 #define PCMDEV_PREFIX "PC,"
394 #define PCMDEV_NAMEPREF "pccard"
396 /* property names */
397 #define PCM_PROP_DEVICE "device"
398 #define PCM_PROP_FUNCID "funcid"
400 /* 1275 specific properties */
401 #define PCM_1275_NUMWIN "#windows"
402 #define PCM_1275_NUMSOCK "#sockets"
403 #define PCM_1275_SCIC "status-change-int_caps"
405 /* basic device types */
407 #define PCM_TYPE_MULTI 0
408 #define PCM_TYPE_MEMORY 1
409 #define PCM_TYPE_SERIAL 2
410 #define PCM_TYPE_PARALLEL 3
411 #define PCM_TYPE_FIXED 4
412 #define PCM_TYPE_VIDEO 5
413 #define PCM_TYPE_LAN 6
416 typedef
417 struct string_to_int {
418 char *sti_str;
419 uint32_t sti_int;
420 } str_int_t;
423 * PCMCIA nexus/adapter specific ioctl commands
426 #define PCIOC ('P' << 8)
427 /* SS is temporary until design done */
428 #define PC_SS_CMD(cmd) (PCIOC|(cmd))
430 /* stuff that used to be in obpdefs.h but no longer */
431 #define PCM_DEVICETYPE "device_type"
434 * new regspec and other 1275 stuff
436 #define PC_REG_RELOC(x) ((((uint32_t)x) & 0x1) << 31)
437 #define PC_REG_PREFETCH(x) (((x) & 0x1) << 30)
438 #define PC_REG_TYPE(x) (((x) & 0x1) << 29)
439 #define PC_REG_SPACE(x) (((x) & 0x7) << 24)
440 #define PC_REG_SOCKET(x) (((x) & 0x1f) << 11)
441 #define PC_REG_FUNCTION(x) (((x) & 0x7) << 8)
442 #define PC_REG_BASEREG(x) ((x) & 0xff)
443 /* solaris internal only */
444 #define PC_REG_REFCNT(x) (((x) & 0xFF) << 16)
446 #define PC_GET_REG_RELOC(x) (((x) >> 31) & 1)
447 #define PC_GET_REG_PREFETCH(x) (((x) >> 30) & 1)
448 #define PC_GET_REG_TYPE(x) (((x) >> 29) & 1)
449 #define PC_GET_REG_SPACE(x) (((x) >> 24) & 7)
450 #define PC_GET_REG_SOCKET(x) (((x) >> 11) & 0x1f)
451 #define PC_GET_REG_FUNCTION(x) (((x) >> 8) & 0x7)
452 #define PC_GET_REG_BASEREG(x) ((x) & 0xff)
453 /* solaris internal only */
454 #define PC_GET_REG_REFCNT(x) (((x) >> 16) & 0xFF)
455 #define PC_INCR_REFCNT(x) (((x) & 0xFF00FFFF) | \
456 PC_REG_REFCNT(PC_GET_REG_REFCNT(x) + 1))
457 #define PC_DECR_REFCNT(x) (((x) & 0xFF00FFFF) | \
458 PC_REG_REFCNT(PC_GET_REG_REFCNT(x) - 1))
460 #define PC_REG_PHYS_HI(n, p, t, c, s, f, r) (uint32_t)( \
461 PC_REG_RELOC(n) | \
462 PC_REG_PREFETCH(p) | \
463 PC_REG_TYPE(t) | \
464 PC_REG_SPACE(c) | \
465 PC_REG_SOCKET(s) | \
466 PC_REG_FUNCTION(f) | \
467 PC_REG_BASEREG(r))
469 #define PC_REG_TYPE_CARDBUS 0
470 #define PC_REG_TYPE_16BIT 1
472 #define PC_REG_SPACE_CONFIG 0x0
473 #define PC_REG_SPACE_IO 0x1
474 #define PC_REG_SPACE_MEMORY 0x2
475 #define PC_REG_SPACE_ATTRIBUTE 0x4
478 * internal properties and other prop_op defines
481 #define PCMCIA_PROP_UNKNOWN 0x10000 /* pass to DDI decode */
482 #define PCMCIA_PROP_CIS 0x20000 /* need to get the tuple */
484 /* specific known properties */
485 #define PCMCIA_PROP_SOCKET 0 /* "socket" */
486 #define PCMCIA_PROP_COMPAT 1 /* "compatible" */
487 #define PCMCIA_PROP_DEFAULT_PM 2 /* power managment timestamp */
488 #define PCMCIA_PROP_ACTIVE 3 /* card-active property */
489 #define PCMCIA_PROP_R2TYPE 4 /* 16 bit card */
490 #define PCMCIA_PROP_CARDBUS 5 /* card is cardbus */
491 #define PCMCIA_PROP_OLDCS 6 /* old card services property */
492 #define PCMCIA_PROP_REG 7 /* standard reg= property */
493 #define PCMCIA_PROP_INTR 8 /* interrupts property */
495 #ifdef __cplusplus
497 #endif
499 #endif /* _PCMCIA_H */