uboot/board/kup/common/pcmcia.c
<<
>>
Prefs
   1#include <common.h>
   2#include <mpc8xx.h>
   3#include <pcmcia.h>
   4
   5#undef  CONFIG_PCMCIA
   6
   7#if defined(CONFIG_CMD_PCMCIA)
   8#define CONFIG_PCMCIA
   9#endif
  10
  11#if defined(CONFIG_CMD_IDE) && defined(CONFIG_IDE_8xx_PCCARD)
  12#define CONFIG_PCMCIA
  13#endif
  14
  15#ifdef  CONFIG_PCMCIA
  16
  17#define PCMCIA_BOARD_MSG "KUP"
  18
  19#define KUP4K_PCMCIA_B_3V3 (0x00020000)
  20
  21int pcmcia_hardware_enable(int slot)
  22{
  23        volatile immap_t        *immap;
  24        volatile cpm8xx_t       *cp;
  25        volatile pcmconf8xx_t   *pcmp;
  26        volatile sysconf8xx_t   *sysp;
  27        uint reg, mask;
  28
  29        debug ("hardware_enable: " PCMCIA_BOARD_MSG " Slot %c\n", 'A'+slot);
  30
  31        udelay(10000);
  32
  33        immap = (immap_t *)CONFIG_SYS_IMMR;
  34        sysp  = (sysconf8xx_t *)(&(((immap_t *)CONFIG_SYS_IMMR)->im_siu_conf));
  35        pcmp  = (pcmconf8xx_t *)(&(((immap_t *)CONFIG_SYS_IMMR)->im_pcmcia));
  36        cp    = (cpm8xx_t *)(&(((immap_t *)CONFIG_SYS_IMMR)->im_cpm));
  37
  38        /*
  39        * Configure SIUMCR to enable PCMCIA port B
  40        * (VFLS[0:1] are not used for debugging, we connect FRZ# instead)
  41        */
  42        sysp->sc_siumcr &= ~SIUMCR_DBGC11;      /* set DBGC to 00 */
  43
  44        /* clear interrupt state, and disable interrupts */
  45        pcmp->pcmc_pscr =  PCMCIA_MASK(slot);
  46        pcmp->pcmc_per &= ~PCMCIA_MASK(slot);
  47
  48        /*
  49        * Disable interrupts, DMA, and PCMCIA buffers
  50        * (isolate the interface) and assert RESET signal
  51        */
  52        debug ("Disable PCMCIA buffers and assert RESET\n");
  53        reg  = 0;
  54        reg |= __MY_PCMCIA_GCRX_CXRESET;        /* active high */
  55        reg |= __MY_PCMCIA_GCRX_CXOE;           /* active low  */
  56        PCMCIA_PGCRX(slot) = reg;
  57        udelay(2500);
  58
  59        /*
  60        * Configure Port B pins for
  61        * 3 Volts enable
  62        */
  63        if (slot) { /* Slot A is built-in */
  64                cp->cp_pbdir |=  KUP4K_PCMCIA_B_3V3;
  65                cp->cp_pbpar &= ~KUP4K_PCMCIA_B_3V3;
  66                /* remove all power */
  67                cp->cp_pbdat |=  KUP4K_PCMCIA_B_3V3; /* active low */
  68        }
  69        /*
  70        * Make sure there is a card in the slot, then configure the interface.
  71        */
  72        udelay(10000);
  73        debug ("[%d] %s: PIPR(%p)=0x%x\n",
  74               __LINE__,__FUNCTION__,
  75               &(pcmp->pcmc_pipr),pcmp->pcmc_pipr);
  76        if (pcmp->pcmc_pipr & (0x18000000 >> (slot << 4))) {
  77                printf ("   No Card found\n");
  78                return (1);
  79        }
  80
  81        /*
  82        * Power On.
  83        */
  84        printf("%s  Slot %c:", slot ? "" : "\n", 'A' + slot);
  85        mask = PCMCIA_VS1(slot) | PCMCIA_VS2(slot);
  86        reg  = pcmp->pcmc_pipr;
  87        debug ("PIPR: 0x%x ==> VS1=o%s, VS2=o%s\n",
  88               reg,
  89               (reg&PCMCIA_VS1(slot))?"n":"ff",
  90               (reg&PCMCIA_VS2(slot))?"n":"ff");
  91        if ((reg & mask) == mask) {
  92                puts (" 5.0V card found: NOT SUPPORTED !!!\n");
  93        } else {
  94                if(slot)
  95                        cp->cp_pbdat &= ~KUP4K_PCMCIA_B_3V3;
  96                puts (" 3.3V card found: ");
  97        }
  98#if 0
  99        /*  VCC switch error flag, PCMCIA slot INPACK_ pin */
 100        cp->cp_pbdir &= ~(0x0020 | 0x0010);
 101        cp->cp_pbpar &= ~(0x0020 | 0x0010);
 102        udelay(500000);
 103#endif
 104        debug ("Enable PCMCIA buffers and stop RESET\n");
 105        reg  =  PCMCIA_PGCRX(slot);
 106        reg &= ~__MY_PCMCIA_GCRX_CXRESET;       /* active high */
 107        reg &= ~__MY_PCMCIA_GCRX_CXOE;          /* active low  */
 108        PCMCIA_PGCRX(slot) = reg;
 109
 110        udelay(250000); /* some cards need >150 ms to come up :-( */
 111
 112        debug ("# hardware_enable done\n");
 113
 114        return (0);
 115}
 116
 117
 118#if defined(CONFIG_CMD_PCMCIA)
 119int pcmcia_hardware_disable(int slot)
 120{
 121        volatile immap_t        *immap;
 122        volatile cpm8xx_t       *cp;
 123        volatile pcmconf8xx_t   *pcmp;
 124        u_long reg;
 125
 126        debug ("hardware_disable: " PCMCIA_BOARD_MSG " Slot %c\n", 'A'+slot);
 127
 128        immap = (immap_t *)CONFIG_SYS_IMMR;
 129        pcmp = (pcmconf8xx_t *)(&(((immap_t *)CONFIG_SYS_IMMR)->im_pcmcia));
 130        cp    = (cpm8xx_t *)(&(((immap_t *)CONFIG_SYS_IMMR)->im_cpm));
 131
 132        /* remove all power */
 133        if (slot)
 134                cp->cp_pbdat |= KUP4K_PCMCIA_B_3V3;
 135
 136        /* Configure PCMCIA General Control Register */
 137        debug ("Disable PCMCIA buffers and assert RESET\n");
 138        reg  = 0;
 139        reg |= __MY_PCMCIA_GCRX_CXRESET;        /* active high */
 140        reg |= __MY_PCMCIA_GCRX_CXOE;           /* active low  */
 141        PCMCIA_PGCRX(slot) = reg;
 142
 143        udelay(10000);
 144
 145        return (0);
 146}
 147#endif
 148
 149
 150int pcmcia_voltage_set(int slot, int vcc, int vpp)
 151{
 152        volatile immap_t        *immap;
 153        volatile cpm8xx_t       *cp;
 154        volatile pcmconf8xx_t   *pcmp;
 155        u_long reg;
 156
 157        debug ("voltage_set: "  \
 158                        PCMCIA_BOARD_MSG        \
 159                        " Slot %c, Vcc=%d.%d, Vpp=%d.%d\n",
 160        'A'+slot, vcc/10, vcc%10, vpp/10, vcc%10);
 161
 162        if (!slot) /* Slot A is not configurable */
 163                return 0;
 164
 165        immap = (immap_t *)CONFIG_SYS_IMMR;
 166        pcmp = (pcmconf8xx_t *)(&(((immap_t *)CONFIG_SYS_IMMR)->im_pcmcia));
 167        cp    = (cpm8xx_t *)(&(((immap_t *)CONFIG_SYS_IMMR)->im_cpm));
 168
 169        /*
 170        * Disable PCMCIA buffers (isolate the interface)
 171        * and assert RESET signal
 172        */
 173        debug ("Disable PCMCIA buffers and assert RESET\n");
 174        reg  = PCMCIA_PGCRX(slot);
 175        reg |= __MY_PCMCIA_GCRX_CXRESET;        /* active high */
 176        reg |= __MY_PCMCIA_GCRX_CXOE;           /* active low  */
 177        PCMCIA_PGCRX(slot) = reg;
 178        udelay(500);
 179
 180        debug ("PCMCIA power OFF\n");
 181        /*
 182        * Configure Port B pins for
 183        * 3 Volts enable
 184        */
 185        cp->cp_pbdir |=  KUP4K_PCMCIA_B_3V3;
 186        cp->cp_pbpar &= ~KUP4K_PCMCIA_B_3V3;
 187        /* remove all power */
 188        cp->cp_pbdat |=  KUP4K_PCMCIA_B_3V3; /* active low */
 189
 190        switch(vcc) {
 191                case  0:                break;
 192                case 33:
 193                        cp->cp_pbdat &= ~KUP4K_PCMCIA_B_3V3;
 194                        debug ("PCMCIA powered at 3.3V\n");
 195                        break;
 196                case 50:
 197                        debug ("PCMCIA: 5Volt vcc not supported\n");
 198                        break;
 199                default:
 200                        puts("PCMCIA: vcc not supported");
 201                        break;
 202        }
 203        udelay(10000);
 204        /* Checking supported voltages */
 205
 206        debug ("PIPR: 0x%x --> %s\n",
 207               pcmp->pcmc_pipr,
 208               (pcmp->pcmc_pipr & (0x80000000 >> (slot << 4)))
 209                               ? "only 5 V --> NOT SUPPORTED"
 210        : "can do 3.3V");
 211
 212
 213        debug ("Enable PCMCIA buffers and stop RESET\n");
 214        reg  =  PCMCIA_PGCRX(slot);
 215        reg &= ~__MY_PCMCIA_GCRX_CXRESET;       /* active high */
 216        reg &= ~__MY_PCMCIA_GCRX_CXOE;          /* active low  */
 217        PCMCIA_PGCRX(slot) = reg;
 218        udelay(500);
 219
 220        debug ("voltage_set: " PCMCIA_BOARD_MSG " Slot %c, DONE\n",
 221               slot+'A');
 222        return (0);
 223}
 224
 225#endif  /* CONFIG_PCMCIA */
 226