1*c88420b3Sdmick /* 2*c88420b3Sdmick * CDDL HEADER START 3*c88420b3Sdmick * 4*c88420b3Sdmick * The contents of this file are subject to the terms of the 5*c88420b3Sdmick * Common Development and Distribution License, Version 1.0 only 6*c88420b3Sdmick * (the "License"). You may not use this file except in compliance 7*c88420b3Sdmick * with the License. 8*c88420b3Sdmick * 9*c88420b3Sdmick * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 10*c88420b3Sdmick * or http://www.opensolaris.org/os/licensing. 11*c88420b3Sdmick * See the License for the specific language governing permissions 12*c88420b3Sdmick * and limitations under the License. 13*c88420b3Sdmick * 14*c88420b3Sdmick * When distributing Covered Code, include this CDDL HEADER in each 15*c88420b3Sdmick * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 16*c88420b3Sdmick * If applicable, add the following below this CDDL HEADER, with the 17*c88420b3Sdmick * fields enclosed by brackets "[]" replaced with your own identifying 18*c88420b3Sdmick * information: Portions Copyright [yyyy] [name of copyright owner] 19*c88420b3Sdmick * 20*c88420b3Sdmick * CDDL HEADER END 21*c88420b3Sdmick */ 22*c88420b3Sdmick /* 23*c88420b3Sdmick * Copyright 2005 Sun Microsystems, Inc. All rights reserved. 24*c88420b3Sdmick * Use is subject to license terms. 25*c88420b3Sdmick */ 26*c88420b3Sdmick 27*c88420b3Sdmick #pragma ident "%Z%%M% %I% %E% SMI" 28*c88420b3Sdmick 29*c88420b3Sdmick /* 30*c88420b3Sdmick * PCI Mechanism 1 low-level routines 31*c88420b3Sdmick */ 32*c88420b3Sdmick 33*c88420b3Sdmick #include <sys/types.h> 34*c88420b3Sdmick #include <sys/pci.h> 35*c88420b3Sdmick #include <sys/pci_impl.h> 36*c88420b3Sdmick #include <sys/sunddi.h> 37*c88420b3Sdmick #include <sys/pci_cfgspace_impl.h> 38*c88420b3Sdmick 39*c88420b3Sdmick /* 40*c88420b3Sdmick * Per PCI 2.1 section 3.7.4.1 and PCI-PCI Bridge Architecture 1.0 section 41*c88420b3Sdmick * 5.3.1.2: dev=31 func=7 reg=0 means a special cycle. We don't want to 42*c88420b3Sdmick * trigger that by accident, so we pretend that dev 31, func 7 doesn't 43*c88420b3Sdmick * exist. If we ever want special cycle support, we'll add explicit 44*c88420b3Sdmick * special cycle support. 45*c88420b3Sdmick */ 46*c88420b3Sdmick 47*c88420b3Sdmick uint8_t 48*c88420b3Sdmick pci_mech1_getb(int bus, int device, int function, int reg) 49*c88420b3Sdmick { 50*c88420b3Sdmick uint8_t val; 51*c88420b3Sdmick if (device == PCI_MECH1_SPEC_CYCLE_DEV && 52*c88420b3Sdmick function == PCI_MECH1_SPEC_CYCLE_FUNC) { 53*c88420b3Sdmick return (0xff); 54*c88420b3Sdmick } 55*c88420b3Sdmick 56*c88420b3Sdmick mutex_enter(&pcicfg_mutex); 57*c88420b3Sdmick outl(PCI_CONFADD, PCI_CADDR1(bus, device, function, reg)); 58*c88420b3Sdmick val = inb(PCI_CONFDATA | (reg & 0x3)); 59*c88420b3Sdmick mutex_exit(&pcicfg_mutex); 60*c88420b3Sdmick return (val); 61*c88420b3Sdmick } 62*c88420b3Sdmick 63*c88420b3Sdmick uint16_t 64*c88420b3Sdmick pci_mech1_getw(int bus, int device, int function, int reg) 65*c88420b3Sdmick { 66*c88420b3Sdmick uint16_t val; 67*c88420b3Sdmick 68*c88420b3Sdmick if (device == PCI_MECH1_SPEC_CYCLE_DEV && 69*c88420b3Sdmick function == PCI_MECH1_SPEC_CYCLE_FUNC) { 70*c88420b3Sdmick return (0xffff); 71*c88420b3Sdmick } 72*c88420b3Sdmick 73*c88420b3Sdmick mutex_enter(&pcicfg_mutex); 74*c88420b3Sdmick outl(PCI_CONFADD, PCI_CADDR1(bus, device, function, reg)); 75*c88420b3Sdmick val = inw(PCI_CONFDATA | (reg & 0x2)); 76*c88420b3Sdmick mutex_exit(&pcicfg_mutex); 77*c88420b3Sdmick return (val); 78*c88420b3Sdmick } 79*c88420b3Sdmick 80*c88420b3Sdmick uint32_t 81*c88420b3Sdmick pci_mech1_getl(int bus, int device, int function, int reg) 82*c88420b3Sdmick { 83*c88420b3Sdmick uint32_t val; 84*c88420b3Sdmick 85*c88420b3Sdmick if (device == PCI_MECH1_SPEC_CYCLE_DEV && 86*c88420b3Sdmick function == PCI_MECH1_SPEC_CYCLE_FUNC) { 87*c88420b3Sdmick return (0xffffffffu); 88*c88420b3Sdmick } 89*c88420b3Sdmick 90*c88420b3Sdmick mutex_enter(&pcicfg_mutex); 91*c88420b3Sdmick outl(PCI_CONFADD, PCI_CADDR1(bus, device, function, reg)); 92*c88420b3Sdmick val = inl(PCI_CONFDATA); 93*c88420b3Sdmick mutex_exit(&pcicfg_mutex); 94*c88420b3Sdmick return (val); 95*c88420b3Sdmick } 96*c88420b3Sdmick 97*c88420b3Sdmick void 98*c88420b3Sdmick pci_mech1_putb(int bus, int device, int function, int reg, uint8_t val) 99*c88420b3Sdmick { 100*c88420b3Sdmick if (device == PCI_MECH1_SPEC_CYCLE_DEV && 101*c88420b3Sdmick function == PCI_MECH1_SPEC_CYCLE_FUNC) { 102*c88420b3Sdmick return; 103*c88420b3Sdmick } 104*c88420b3Sdmick 105*c88420b3Sdmick mutex_enter(&pcicfg_mutex); 106*c88420b3Sdmick outl(PCI_CONFADD, PCI_CADDR1(bus, device, function, reg)); 107*c88420b3Sdmick outb(PCI_CONFDATA | (reg & 0x3), val); 108*c88420b3Sdmick mutex_exit(&pcicfg_mutex); 109*c88420b3Sdmick } 110*c88420b3Sdmick 111*c88420b3Sdmick void 112*c88420b3Sdmick pci_mech1_putw(int bus, int device, int function, int reg, uint16_t val) 113*c88420b3Sdmick { 114*c88420b3Sdmick if (device == PCI_MECH1_SPEC_CYCLE_DEV && 115*c88420b3Sdmick function == PCI_MECH1_SPEC_CYCLE_FUNC) { 116*c88420b3Sdmick return; 117*c88420b3Sdmick } 118*c88420b3Sdmick 119*c88420b3Sdmick mutex_enter(&pcicfg_mutex); 120*c88420b3Sdmick outl(PCI_CONFADD, PCI_CADDR1(bus, device, function, reg)); 121*c88420b3Sdmick outw(PCI_CONFDATA | (reg & 0x2), val); 122*c88420b3Sdmick mutex_exit(&pcicfg_mutex); 123*c88420b3Sdmick } 124*c88420b3Sdmick 125*c88420b3Sdmick void 126*c88420b3Sdmick pci_mech1_putl(int bus, int device, int function, int reg, uint32_t val) 127*c88420b3Sdmick { 128*c88420b3Sdmick if (device == PCI_MECH1_SPEC_CYCLE_DEV && 129*c88420b3Sdmick function == PCI_MECH1_SPEC_CYCLE_FUNC) { 130*c88420b3Sdmick return; 131*c88420b3Sdmick } 132*c88420b3Sdmick 133*c88420b3Sdmick mutex_enter(&pcicfg_mutex); 134*c88420b3Sdmick outl(PCI_CONFADD, PCI_CADDR1(bus, device, function, reg)); 135*c88420b3Sdmick outl(PCI_CONFDATA, val); 136*c88420b3Sdmick mutex_exit(&pcicfg_mutex); 137*c88420b3Sdmick } 138