diff options
author | hvozda <hvozda@cvs.openbsd.org> | 1996-04-29 13:07:06 +0000 |
---|---|---|
committer | hvozda <hvozda@cvs.openbsd.org> | 1996-04-29 13:07:06 +0000 |
commit | 66dbdef25563581a0d393d8d919df22c43de70c7 (patch) | |
tree | 4cfdb17adf8be1fdf71a7e416fdc352fc014c3f3 /sbin | |
parent | fc0fd904cb2c0308afe4ec749ac0a2e82b1cf240 (diff) |
Pull in John Kohl's most recent (15Apr96) APM and PCMCIA work
(original PCMCIA framework by Stefan Grefen).
Diffstat (limited to 'sbin')
-rw-r--r-- | sbin/Makefile | 6 | ||||
-rw-r--r-- | sbin/config_slot/Makefile | 15 | ||||
-rw-r--r-- | sbin/config_slot/config_slot.c | 233 | ||||
-rw-r--r-- | sbin/config_slot/read_conf.c | 288 | ||||
-rw-r--r-- | sbin/pcmcia_cntrl/Makefile | 9 | ||||
-rw-r--r-- | sbin/pcmcia_cntrl/pcmcia_cntrl.1 | 77 | ||||
-rw-r--r-- | sbin/pcmcia_cntrl/pcmcia_cntrl.c | 165 |
7 files changed, 791 insertions, 2 deletions
diff --git a/sbin/Makefile b/sbin/Makefile index 3c87a070c83..1b8b46a7875 100644 --- a/sbin/Makefile +++ b/sbin/Makefile @@ -1,4 +1,4 @@ -# $OpenBSD: Makefile,v 1.5 1996/04/22 20:21:52 hannken Exp $ +# $OpenBSD: Makefile,v 1.6 1996/04/29 13:07:00 hvozda Exp $ # $NetBSD: Makefile,v 1.28 1996/04/05 01:44:24 cgd Exp $ # @(#)Makefile 8.5 (Berkeley) 3/31/94 @@ -27,9 +27,11 @@ SUBDIR+= mount_umap SUBDIR+= mount_union .if make(clean) || make(cleandir) -SUBDIR+= bim edlabel fdisk +SUBDIR+= bim config_slot edlabel fdisk pcmcia_cntrl .elif ${MACHINE} == "i386" +SUBDIR+= config_slot SUBDIR+= fdisk +SUBDIR+= pcmcia_cntrl .elif ${MACHINE} == "pc532" SUBDIR+= bim .elif ${MACHINE} == "sun3" diff --git a/sbin/config_slot/Makefile b/sbin/config_slot/Makefile new file mode 100644 index 00000000000..74e14e35e1f --- /dev/null +++ b/sbin/config_slot/Makefile @@ -0,0 +1,15 @@ +# $Id: Makefile,v 1.1 1996/04/29 13:07:01 hvozda Exp $ + +SRCS = config_slot.c pcmcia_conf.c +VPATH = ${.CURDIR}/../../sys/dev/pcmcia +#dumpreg.c + +CFLAGS+= -g -O2 -Wmissing-prototypes -I${.CURDIR}/../../sys +PROG=config_slot +NOMAN= + +pcmcia_conf.o: pcmcia_conf.c + $(CC) $(CFLAGS) -D_KERNEL -c $< + +.include <bsd.prog.mk> +# DO NOT DELETE THIS LINE -- make depend depends on it. diff --git a/sbin/config_slot/config_slot.c b/sbin/config_slot/config_slot.c new file mode 100644 index 00000000000..a24c387eff9 --- /dev/null +++ b/sbin/config_slot/config_slot.c @@ -0,0 +1,233 @@ +/* + * Copyright (c) 1993, 1994 Stefan Grefen. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following dipclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Stefan Grefen. + * 4. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ +#include <stdio.h> +#include <errno.h> +#include <sys/types.h> +#include <sys/file.h> +#include <sys/ioctl.h> +#include <sys/device.h> + +#include <dev/pcmcia/pcmciareg.h> +#include <dev/pcmcia/pcmciavar.h> +#include <dev/pcmcia/pcmcia_ioctl.h> + +void parse_device(u_char *, int, int); +void parse_ver1(u_char *, int, int); +void parse_config(u_char *, int, int); +void read_extended_speed(u_char *, int *); +const char *tuple_name(int), *dtype_name(int), *dsize_name(int), + *dspeed_name(int); +void parse_tuples(u_char *buf, int print_tuples); +int dumpcf(struct pcmcia_conf *pc_cf); +void usage(void); +int readiowin(char **argv,struct iowin *io); +void dcp(char **argv,char *target); +void parse_cmdline(int argc,char **argv,struct pcmcia_conf *pc_cf); + +int iowins=0; + +dumpcf(struct pcmcia_conf *pc_cf) { + int i; + static char *ios[]= { + "auto","8bit","16bit","illegal" + }; + printf("Driver name '%s'\n",pc_cf->driver_name); + printf("CFG offset %x\n",pc_cf->cfg_off ); + printf("IRQ type %s\n",pc_cf->irq_level?"Level":pc_cf->irq_pulse?"Pulse":"None"); + printf("CFG Entry %x %s\n",pc_cf->cfgtype,pc_cf->cfgtype&DOSRESET?"dosreset":""); + printf("IRQ num %x\n",pc_cf->irq_num&0xf); + printf("Cardtype %s\n",pc_cf->iocard?"IO":"MEM"); + for (i=0;i<pc_cf->iowin;i++) { + printf("iowin %x-%x %s\n",pc_cf->io[i].start, + pc_cf->io[i].start+pc_cf->io[i].len-1, + ios[(pc_cf->io[i].flags&(PCMCIA_MAP_8|PCMCIA_MAP_16))>>8]); + } + for (i=0;i<pc_cf->memwin;i++) { + printf("memwin (%x)%x-%x %x\n", + pc_cf->mem[i].caddr, + pc_cf->mem[i].start, + pc_cf->mem[i].start+pc_cf->mem[i].len-1, + pc_cf->mem[i].flags); + } +} + +void +usage(void) { + fprintf(stderr,"usage: config_slot <slotid> [driver name][iocard]\\\n"); + fprintf(stderr," [irq num][lirq][iowin start len width]\n"); + fprintf(stderr," [** not yet memwin start offs len width]\n"); +} + + +main(int argc,char **argv) { + char namebuf[64]; + struct pcmcia_status stbuf; + struct pcmcia_info inbuf; + struct pcmcia_conf pc_cf; + char manu[MAX_CIS_NAMELEN]; + char model[MAX_CIS_NAMELEN]; + char addinf1[MAX_CIS_NAMELEN]; + char addinf2[MAX_CIS_NAMELEN]; + int sockid; + int fd,cfg; + + if(argc<2 || !isdigit(argv[1][0])) { + usage(); + exit(1); + } + + sockid=atoi(argv[1]); + + bzero(pc_cf,sizeof(pc_cf)); + + argc-=2;argv+=2; + sprintf(namebuf,"/dev/pcmcia/slot%d",sockid); + + if((fd=open(namebuf,O_RDWR))<0) { + printf("errno %d\n",errno); + perror("open"); + exit(1); + } + if(ioctl(fd,PCMCIAIO_GET_STATUS,&stbuf)<0) { + printf("errno %d\n",errno); + perror("ioctl PCMCIAIO_GET_STATUS"); + exit(1); + } + if(!(stbuf.status&PCMCIA_CARD_PRESENT)) { + printf("No card in slot %d\n",stbuf.slot); + exit(1); + } + if(!(stbuf.status&PCMCIA_POWER)) { + int pw=PCMCIA_POWER_5V; + printf("Card in slot %d no power\n",stbuf.slot); + if(ioctl(fd,PCMCIAIO_SET_POWER,&pw)<0) { + printf("errno %d\n",errno); + perror("ioctl PCMCIAIO_SET_POWER"); + exit(1); + } + /*exit(1);/**/ + } + if(ioctl(fd,PCMCIAIO_GET_STATUS,&stbuf)<0) { + printf("errno %d\n",errno); + perror("ioctl PCMCIAIO_GET_STATUS"); + exit(1); + } + printf("Status slot %d %x\n",stbuf.slot,stbuf.status); + if(!(stbuf.status&PCMCIA_READY)) { + printf("Card in slot %d not ready\n",stbuf.slot); + /*exit(1);/**/ + } + if(ioctl(fd,PCMCIAIO_GET_INFO,&inbuf)<0) { + printf("errno %d\n",errno); + perror("ioctl PCMCIAIO_GET_INFO"); + exit(1); + } + /*dbuf(inbuf.cis_data,512);/**/ + bzero(&pc_cf,sizeof(pc_cf)); + /*parse_cmdline(argc,argv,&pc_cf);/**/ + printf("* %x\n",pc_cf.cfgtype); + cfg=pc_cf.cfgtype&CFGENTRYMASK; + if(pcmcia_get_cf(0, inbuf.cis_data,512,CFGENTRYMASK,&pc_cf)) { + fprintf(stderr,"read_conf failed\n"); + exit(1); + } + if(pc_cf.cfgtype&CFGENTRYID) { + if(pcmcia_get_cf(0, inbuf.cis_data,512,cfg,&pc_cf)) { + fprintf(stderr,"read_conf failed\n"); + exit(1); + } + } + parse_cmdline(argc,argv,&pc_cf); + if(iowins && pc_cf.iowin!=iowins) { + pc_cf.iowin=iowins; + } + dumpcf(&pc_cf); + if (pcmcia_get_cisver1(0, (u_char *)&inbuf.cis_data, 512, + manu, model, addinf1, addinf2) == 0) { + printf(" <%s, %s", manu, model); + if (addinf1[0]) + printf(", %s", addinf1); + if (addinf2[0]) + printf(", %s", addinf2); + printf(">\n"); + } + printf("PCMCIAIO_CONFIGURE==%x\n",PCMCIAIO_CONFIGURE); + if(ioctl(fd,PCMCIAIO_CONFIGURE,&pc_cf)<0) { + printf("errno %d\n",errno); + perror("ioctl PCMCIAIO_CONFIGURE"); + exit(1); + } + + exit(0); + +} +#define OPT_ARG(opt,arg,func) if(argc>1 && !strcmp(argv[0],opt)) { \ + arg=func(argv[1]); argv+=2;argc-=2 ;continue;} +#define OPT(opt,arg) if(!strcmp(argv[0],opt)) { \ + arg=1; argv++;argc-- ;continue;} +#define OPTOV_ARG(opt,op,func,arg) if(!strcmp(argv[0],opt)) { \ + arg op func(argv[1]); argv+=2;argc-=2 ;continue;} +#define OPTOV(opt,op,val,arg) if(!strcmp(argv[0],opt)) { \ + arg op val; argv++;argc-- ;continue;} +#define OPT_ARGN(opt,n,arg,func) if(argc>n && !strcmp(argv[0],opt)) { \ + func(&argv[1],&(arg)); argv+=n+1;argc-=n+1 ;continue;} +readiowin(char **argv,struct iowin *io) { + io->start=strtol(argv[0],NULL,0); + io->len=strtol(argv[1],NULL,0); + if(!strcmp(argv[2],"auto")) { + io->flags=0; + } else if(!strcmp(argv[2],"8bit")) { + io->flags=PCMCIA_MAP_8; + } else if(!strcmp(argv[2],"16bit")) { + io->flags=PCMCIA_MAP_16; + } +} + +void +dcp(char **argv,char *target) { + strcpy(target,argv[0]); +} + +void +parse_cmdline(int argc,char **argv,struct pcmcia_conf *pc_cf) { + int memwin=0; + while(argc>0) { + OPT_ARG("irq", pc_cf->irq_num,atoi); + OPT_ARGN("iowin",3,pc_cf->io[iowins++],readiowin); + /*OPT_ARGN("-memwin",4,pc_cf->mem,readmem,win);/**/ + OPT("pirq", pc_cf->irq_pulse); + OPT("lirq", pc_cf->irq_level); + OPT("iocard", pc_cf->iocard); + OPTOV("dosreset", |= ,DOSRESET,pc_cf->cfgtype); + OPTOV_ARG("configid",|= CFGENTRYID |,atoi,pc_cf->cfgtype); + OPT_ARGN("driver",1, pc_cf->driver_name[0][0],dcp); + printf("illegal option '%s'\n",argv[0]); + argc--;argv++; + } +} diff --git a/sbin/config_slot/read_conf.c b/sbin/config_slot/read_conf.c new file mode 100644 index 00000000000..9e4a60cb569 --- /dev/null +++ b/sbin/config_slot/read_conf.c @@ -0,0 +1,288 @@ +/* + * Copyright (c) 1993, 1994 Stefan Grefen. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following dipclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Stefan Grefen. + * 4. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ +/* With 'help' of Barry Jaspan's code */ + +#include <stdio.h> +#include <errno.h> +#include <sys/types.h> +#include <sys/file.h> +#include <sys/ioctl.h> +#include <sys/device.h> + +#include <dev/pcmcia/pcmcia.h> +#include <dev/pcmcia/pcmciabus.h> +#include <dev/pcmcia/pcmcia_ioctl.h> + +read_conf(u_char *buf, int blen,int cfidx,struct pcmcia_conf *pc_cf) +{ + u_char code, len,*tbuf,*endp=buf+blen; + int done; + + done = 0; + while (!done && buf<endp) { + code=*buf++; + if (code == CIS_NULL) { + continue; + } + + len=*buf++; + + tbuf=buf; + buf+=len; + switch (code) { + case CIS_END: + done = 1; + break; + case CIS_CFG_INFO: + read_cfg_info(tbuf, len, pc_cf); + break; + case CIS_CFG_ENT: + parse_cfent(tbuf, len,cfidx, pc_cf); + break; + default: + break; + } + } + return 0; +} + +read_cfg_info(u_char *tbuf, int len, struct pcmcia_conf *pc_cf) +{ + int i, rasz, rmsz; + + i = 0; + rasz = (tbuf[i] & TPCC_RASZ) >> TPCC_RASZ_SHIFT; + rmsz = (tbuf[i] & TPCC_RMSZ) >> TPCC_RMSZ_SHIFT; + + i+=2; + pc_cf->cfg_off = 0; + switch (rasz) { + case 3: + pc_cf->cfg_off |= (tbuf[i+3] << 24); + case 2: + pc_cf->cfg_off |= (tbuf[i+2] << 16); + case 1: + pc_cf->cfg_off |= (tbuf[i+1] << 8); + case 0: + pc_cf->cfg_off |= tbuf[i]; + } + i+=rasz; + pc_cf->cfg_regmask = 0; + switch (rmsz) { + default: + case 3: + pc_cf->cfg_regmask |= (tbuf[i+3] << 24); + case 2: + pc_cf->cfg_regmask |= (tbuf[i+2] << 16); + case 1: + pc_cf->cfg_regmask |= (tbuf[i+1] << 8); + case 0: + pc_cf->cfg_regmask |= tbuf[i]; + } + +} + +parse_cfent(u_char *tbuf, int len,int slotid, struct pcmcia_conf *pc_cf) +{ + int i, idx,defp,iop,io_16,ios,ftrs,intface,k; + int host_addr_p, addr_size, len_size; + + i = 0; + intface = (tbuf[i] & TPCE_INDX_INT); + idx = (tbuf[i] & TPCE_INDX_ENTRY); + defp = (tbuf[i] & TPCE_INDX_DEF); + printf("%x %x\n",idx,slotid); + if((idx==slotid) ||(defp && slotid==-1)) { + int j; + printf("** %x %x\n",idx,slotid); + if (intface) { + i++; + pc_cf->iocard=(tbuf[i] & TPCE_IF_TYPE)==1; + } + + i++; + ftrs = tbuf[i++]; + for (j = 0; j < (ftrs & TPCE_FS_PWR); j++) { + int pwr_desc = tbuf[i++]; + /* for each struct, skip all parameter defns */ + for (k = 0; k < 8; pwr_desc >>= 1, k++) { + if (pwr_desc & 0x01) { + /* skip bytes until non-ext found */ + while (tbuf[i++] & 0x80) + ; + } + } + } + + if (ftrs & TPCE_FS_TD) { + i++; + } + + if (ftrs & TPCE_FS_IO) { + int io_addrs[16],io_lens[16]; + int io_16,io_block_len, io_block_size; + iop = 1; + io_16 = tbuf[i] & TPCE_FS_IO_BUS16; + i++; + ios--; /*TMPFIX*/; + io_block_len = (tbuf[i] & TPCE_FS_IO_LEN) >> + TPCE_FS_IO_LEN_SHIFT; + io_block_size = (tbuf[i] & TPCE_FS_IO_SIZE) >> + TPCE_FS_IO_SIZE_SHIFT; + ios = (tbuf[i] & TPCE_FS_IO_NUM) + 1; + i++; + for (j = 0; j < ios; j++) { + io_addrs[j] = io_lens[j] = 0; + switch (io_block_size) { + case 3: + io_addrs[j] |= tbuf[i+3] << 24; + io_addrs[j] |= tbuf[i+2] << 16; + case 2: + io_addrs[j] |= tbuf[i+1] << 8; + case 1: + io_addrs[j] |= tbuf[i]; + break; + } + pc_cf->io[j].start=io_addrs[j]; + i += io_block_size + (io_block_size == 3 ? 1 + : 0); + switch (io_block_len) { + case 3: + io_lens[j] |= tbuf[i+3] << 24; + io_lens[j] |= tbuf[i+2] << 16; + case 2: + io_lens[j] |= tbuf[i+1] << 8; + case 1: + io_lens[j] |= tbuf[i]; + break; + } + /* io_lens[j]++; /*TMPFIX*/; + pc_cf->io[j].len=io_lens[j]; + pc_cf->io[j].flags=io_16?PCMCIA_MAP_16:PCMCIA_MAP_8; + i += io_block_len + (io_block_len == 3 ? 1 + : 0); + + } + pc_cf->iowin=ios; + } + + if (ftrs & TPCE_FS_IRQ) { + int irq_mask,irqp,irq; + pc_cf->irq_level=!!(tbuf[i] & TPCE_FS_IRQ_LEVEL); + pc_cf->irq_pulse=!!(tbuf[i] & TPCE_FS_IRQ_PULSE); + pc_cf->irq_share=!!(tbuf[i] & TPCE_FS_IRQ_SHARE); + if (tbuf[i] & TPCE_FS_IRQ_MASK) { + irq_mask = (tbuf[i+2] << 8) + tbuf[i+1]; + i += 2; + } else { + pc_cf->irq_num = tbuf[i] & TPCE_FS_IRQ_IRQN; + } + + i++; + } + + if (ftrs & TPCE_FS_MEM) { + int memp,mems,mem_lens[16],mem_caddrs[16],mem_haddrs[16]; + memp = 1; + switch ((ftrs & TPCE_FS_MEM) >> TPCE_FS_MEM_SHIFT) { + case 1: + mems = 1; + mem_lens[0] = (tbuf[i+1] << 8) + tbuf[i]; + mem_lens[0] <<= 8; + printf("\tmem: len %d\n", mem_lens[0]); + + break; + case 2: + mems = 1; + mem_lens[0] = (tbuf[i+1] << 8) + tbuf[i]; + mem_caddrs[0] = mem_haddrs[0] = + (tbuf[i+3] << 8) + tbuf[i+2]; + + mem_lens[0] <<= 8; + mem_caddrs[0] <<= 8; + + break; + case 3: + host_addr_p = tbuf[i] & TPCE_FS_MEM_HOST; + addr_size = (tbuf[i] & TPCE_FS_MEM_ADDR) >> + TPCE_FS_MEM_ADDR_SHIFT; + len_size = (tbuf[i] & TPCE_FS_MEM_LEN) >> + TPCE_FS_MEM_LEN_SHIFT; + mems = (tbuf[i] & TPCE_FS_MEM_WINS) + 1; + i++; + for (j = 0; j < mems; j++) { + mem_lens[j] = 0; + mem_caddrs[j] = 0; + mem_haddrs[j] = 0; + switch (len_size) { + case 3: + mem_lens[j] |= (tbuf[i+2] << 16); + case 2: + mem_lens[j] |= (tbuf[i+1] << 8); + case 1: + mem_lens[j] |= tbuf[i]; + } + i += len_size; + switch (addr_size) { + case 3: + mem_caddrs[j] |= (tbuf[i+2] << 16); + case 2: + mem_caddrs[j] |= (tbuf[i+1] << 8); + case 1: + mem_caddrs[j] |= tbuf[i]; + } + i += addr_size; + if (host_addr_p) { + switch (addr_size) { + case 3: + mem_haddrs[j] |= + (tbuf[i+2] << 16); + case 2: + mem_haddrs[j] |= + (tbuf[i+1] << 8); + case 1: + mem_haddrs[j] |= + tbuf[i]; + } + i += addr_size; + } + + mem_lens[j] <<= 8; + mem_caddrs[j] <<= 8; + mem_haddrs[j] <<= 8; + + } + } + } + } +} + + + + diff --git a/sbin/pcmcia_cntrl/Makefile b/sbin/pcmcia_cntrl/Makefile new file mode 100644 index 00000000000..a231297e9ae --- /dev/null +++ b/sbin/pcmcia_cntrl/Makefile @@ -0,0 +1,9 @@ +# $Id: Makefile,v 1.1 1996/04/29 13:07:04 hvozda Exp $ + +SRCS = pcmcia_cntrl.c + +CFLAGS += -g +PROG=pcmcia_cntrl + +.include <bsd.prog.mk> +# DO NOT DELETE THIS LINE -- make depend depends on it. diff --git a/sbin/pcmcia_cntrl/pcmcia_cntrl.1 b/sbin/pcmcia_cntrl/pcmcia_cntrl.1 new file mode 100644 index 00000000000..0ad4cadae2d --- /dev/null +++ b/sbin/pcmcia_cntrl/pcmcia_cntrl.1 @@ -0,0 +1,77 @@ +.\" Copyright (c) 1994 Stefan Grefen +.\" All rights reserved. +.\" +.\" This code is derived from software contributed to Berkeley by +.\" the Institute of Electrical and Electronics Engineers, Inc. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. All advertising materials mentioning features or use of this software +.\" must display the following acknowledgement: +.\" This product includes software developed by the University of +.\" California, Berkeley and its contributors. +.\" 4. Neither the name of the University nor the names of its contributors +.\" may be used to endorse or promote products derived from this software +.\" without specific prior written permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" from: @(#)pwd.1 6.5 (Berkeley) 6/27/91 +.\" $Id: pcmcia_cntrl.1,v 1.1 1996/04/29 13:07:04 hvozda Exp $ +.\" +.Dd May 31, 1994 +.Dt PWD 1 +.Os BSD 4 +.Sh NAME +.Nm pcmcia_cntrl +.Nd Change the status of a pcmcia slot +.Sh SYNOPSIS +.Nm pcmcia_cntrl +.Ar slotid +.Op on | off | unmap | probe +.Sh DESCRIPTION +.Nm Pcmcia_cntrl +controls the operation of a PCMCIA card. It operates on the card in slot +.Ar slotid . +\. +.Pp +The options are as follows: +.Bl -tag -width flag +.It Fl on +Turns power on +.It Fl off +Turns power off +.It Fl unmap +Unmaps and unconfigures a active card (not all drivers may support this). +.It Fl probe +Probes and attaches the card found in the slot. Works only for devices that +have kernel support for mapping. +Use config_slot for other devices. +.El +.Pp +If an error occurs, +.Nm pcmcia_cntrl +exits with a value >0. +.Sh SEE ALSO +.Xr config_slot 1 , +.Xr pcmcia 4 +.Sh BUGS +To numerous to mention. + + diff --git a/sbin/pcmcia_cntrl/pcmcia_cntrl.c b/sbin/pcmcia_cntrl/pcmcia_cntrl.c new file mode 100644 index 00000000000..e01e754177b --- /dev/null +++ b/sbin/pcmcia_cntrl/pcmcia_cntrl.c @@ -0,0 +1,165 @@ +/* + * Copyright (c) 1993, 1994 Stefan Grefen. All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following dipclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. All advertising materials mentioning features or use of this software + * must display the following acknowledgement: + * This product includes software developed by Stefan Grefen. + * 4. The name of the author may not be used to endorse or promote products + * derived from this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR + * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. + * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT + * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, + * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY + * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF + * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#include <stdio.h> +#include <errno.h> +#include <sys/types.h> +#include <sys/file.h> +#include <sys/ioctl.h> +#include <sys/device.h> + +#include <dev/pcmcia/pcmciavar.h> +#include <dev/pcmcia/pcmciareg.h> +#include <dev/pcmcia/pcmcia_ioctl.h> + +#define HAS_POWER(a) (!!(a&(PCMCIA_POWER))) + +void +usage(void) { + fprintf(stderr,"usage: pcmcia_cntrl [-f fd] <slotid> on|off|unmap|unconf|probe\n"); +} + +main(int argc,char **argv) { + int fd = -1; + char namebuf[64]; + int sockid; + struct pcmcia_status stbuf; + struct pcmcia_info inbuf; + int onoff=-1; + int unmap=-1; + int unconf=-1; + int probe=-1; + int force=-1; + + if (argv[1] && strcmp(argv[1], "-f") == 0 && + argv[2]) { + fd = atoi(argv[2]); + argv += 2; + argc -= 2; + } + + if(argc!=3 || !isdigit(argv[1][0])) { + usage(); + exit(1); + } + sockid=atoi(argv[1]); + + + if(!strcmp(argv[2],"on")) { + onoff=1; + } else if(!strcmp(argv[2],"off")) { + onoff=0; + } else if(!strcmp(argv[2],"unconf")) { + unmap=1; + unconf=1; + } else if(!strcmp(argv[2],"unconfforce")) { + unmap=1; + unconf=1; + force=1; + } else if(!strcmp(argv[2],"unmap")) { + unmap=1; + } else if(!strcmp(argv[2],"probe")) { + probe=1; + } else { + usage(); + exit(1); + } + + sprintf(namebuf,"/dev/pcmcia/slot%d",sockid); + + if (fd == -1 && (fd=open(namebuf,O_RDWR))<0) { + perror("open"); + exit(1); + } + if(ioctl(fd,PCMCIAIO_GET_STATUS,&stbuf)<0) { + perror("ioctl PCMCIAIO_GET_STATUS"); + exit(1); + } + if(!(stbuf.status&PCMCIA_CARD_PRESENT) && force < 0) { + fprintf(stderr,"No card in slot %d\n",stbuf.slot); + exit(1); + } + if(onoff>=0) { + if(stbuf.status&PCMCIA_CARD_IS_MAPPED) { + fprintf(stderr,"Card in slot %d is mapped, can't turn it %s\n",stbuf.slot,onoff?"on":"off"); + exit(1); + } + if((HAS_POWER(stbuf.status&PCMCIA_POWER))^(!!onoff)) { + int pw=onoff?PCMCIASIO_POWER_5V:PCMCIASIO_POWER_OFF; + printf("Card in slot %d power %s\n",stbuf.slot,onoff?"on":"off" ); + if(ioctl(fd,PCMCIAIO_SET_POWER,&pw)<0) { + printf("errno %d\n",errno); + perror("ioctl PCMCIAIO_SET_POWER"); + exit(1); + } + /*exit(1);/**/ + } + } + if (unconf >= 0) { + int o; + if(!(stbuf.status&PCMCIA_CARD_IS_MAPPED)) { + fprintf(stderr,"Card in slot %d is not mapped\n",stbuf.slot); + exit(1); + } + if(ioctl(fd,PCMCIAIO_UNCONFIGURE,0)<0) { + perror("ioctl PCMCIAIO_UNCONFIGURE"); + exit(1); + } + } + if (unmap >= 0) { + if (!unconf && (stbuf.status&PCMCIA_CARD_INUSE)) { + fprintf(stderr, "Card in slot %d is configured--unconfigure before unmapping.\n", stbuf.slot); + exit(1); + } + if(!(stbuf.status&PCMCIA_CARD_IS_MAPPED)) { + fprintf(stderr,"Card in slot %d is not mapped\n",stbuf.slot); + exit(1); + } + if(ioctl(fd,PCMCIAIO_UNMAP,0)<0) { + perror("ioctl PCMCIAIO_UNMAP"); + exit(1); + } + } + if(probe>=0) { + struct pcmcia_conf pc_cf; + if(stbuf.status&PCMCIA_CARD_IS_MAPPED) { + fprintf(stderr,"Card in slot %d is mapped, can't probe it\n", + stbuf.slot); + exit(1); + } + bzero(pc_cf,sizeof(pc_cf)); + if(ioctl(fd,PCMCIAIO_CONFIGURE,&pc_cf)<0) { + perror("ioctl PCMCIAIO_CONFIGURE"); + exit(1); + } + } + exit(0); +} + |