arswitch_7240.c revision 235377
190075Sobrien/*- 290075Sobrien * Copyright (c) 2011-2012 Stefan Bethke. 390075Sobrien * Copyright (c) 2012 Adrian Chadd. 490075Sobrien * All rights reserved. 590075Sobrien * 690075Sobrien * Redistribution and use in source and binary forms, with or without 790075Sobrien * modification, are permitted provided that the following conditions 890075Sobrien * are met: 990075Sobrien * 1. Redistributions of source code must retain the above copyright 1090075Sobrien * notice, this list of conditions and the following disclaimer. 1190075Sobrien * 2. Redistributions in binary form must reproduce the above copyright 1290075Sobrien * notice, this list of conditions and the following disclaimer in the 1390075Sobrien * documentation and/or other materials provided with the distribution. 1490075Sobrien * 1590075Sobrien * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 1690075Sobrien * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1790075Sobrien * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 1890075Sobrien * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 1990075Sobrien * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2090075Sobrien * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2190075Sobrien * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2290075Sobrien * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2390075Sobrien * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 2490075Sobrien * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 2590075Sobrien * SUCH DAMAGE. 2690075Sobrien * 2790075Sobrien * $FreeBSD: head/sys/dev/etherswitch/arswitch/arswitch_7240.c 235377 2012-05-12 21:08:07Z adrian $ 2890075Sobrien */ 2990075Sobrien 3090075Sobrien#include <sys/param.h> 3190075Sobrien#include <sys/bus.h> 3290075Sobrien#include <sys/errno.h> 3390075Sobrien#include <sys/kernel.h> 3490075Sobrien#include <sys/module.h> 3590075Sobrien#include <sys/socket.h> 3690075Sobrien#include <sys/sockio.h> 3790075Sobrien#include <sys/sysctl.h> 3890075Sobrien#include <sys/systm.h> 3990075Sobrien 4090075Sobrien#include <net/if.h> 4190075Sobrien#include <net/if_arp.h> 4290075Sobrien#include <net/ethernet.h> 4390075Sobrien#include <net/if_dl.h> 4490075Sobrien#include <net/if_media.h> 4590075Sobrien#include <net/if_types.h> 4690075Sobrien 4790075Sobrien#include <machine/bus.h> 4890075Sobrien#include <dev/iicbus/iic.h> 4990075Sobrien#include <dev/iicbus/iiconf.h> 5090075Sobrien#include <dev/iicbus/iicbus.h> 5190075Sobrien#include <dev/mii/mii.h> 5290075Sobrien#include <dev/mii/miivar.h> 5390075Sobrien#include <dev/etherswitch/mdio.h> 5490075Sobrien 5590075Sobrien#include <dev/etherswitch/etherswitch.h> 5690075Sobrien 5790075Sobrien#include <dev/etherswitch/arswitch/arswitchreg.h> 5890075Sobrien#include <dev/etherswitch/arswitch/arswitchvar.h> 5990075Sobrien#include <dev/etherswitch/arswitch/arswitch_reg.h> 6090075Sobrien#include <dev/etherswitch/arswitch/arswitch_phy.h> /* XXX for probe */ 6190075Sobrien#include <dev/etherswitch/arswitch/arswitch_7240.h> 6290075Sobrien 6390075Sobrien#include "mdio_if.h" 6490075Sobrien#include "miibus_if.h" 6590075Sobrien#include "etherswitch_if.h" 6690075Sobrien 6790075Sobrien/* 6890075Sobrien * AR7240 specific functions 6990075Sobrien */ 7090075Sobrienstatic int 7190075Sobrienar7240_hw_setup(struct arswitch_softc *sc) 7290075Sobrien{ 7390075Sobrien 7490075Sobrien /* Enable CPU port; disable mirror port */ 7590075Sobrien arswitch_writereg(sc->sc_dev, AR8X16_REG_CPU_PORT, 7690075Sobrien AR8X16_CPU_PORT_EN | AR8X16_CPU_MIRROR_DIS); 7790075Sobrien 7890075Sobrien /* 7990075Sobrien * Let things settle; probing PHY4 doesn't seem reliable 8090075Sobrien * without a litle delay. 8190075Sobrien */ 8290075Sobrien DELAY(1000); 8390075Sobrien 8490075Sobrien return (0); 8590075Sobrien} 8690075Sobrien 8790075Sobrien/* 8890075Sobrien * Initialise other global values for the AR7240. 8990075Sobrien */ 9090075Sobrienstatic int 9190075Sobrienar7240_hw_global_setup(struct arswitch_softc *sc) 9290075Sobrien{ 9390075Sobrien 9490075Sobrien /* Setup TAG priority mapping */ 9590075Sobrien arswitch_writereg(sc->sc_dev, AR8X16_REG_TAG_PRIO, 0xfa50); 9690075Sobrien 9790075Sobrien /* Enable broadcast frames transmitted to the CPU */ 9890075Sobrien arswitch_writereg(sc->sc_dev, AR8X16_REG_FLOOD_MASK, 9990075Sobrien AR8X16_FLOOD_MASK_BCAST_TO_CPU | 0x003f003f); 10090075Sobrien 10190075Sobrien /* Setup MTU */ 10290075Sobrien arswitch_modifyreg(sc->sc_dev, AR8X16_REG_GLOBAL_CTRL, 10390075Sobrien AR7240_GLOBAL_CTRL_MTU_MASK, 10490075Sobrien SM(1536, AR7240_GLOBAL_CTRL_MTU_MASK)); 10590075Sobrien 10690075Sobrien /* Service Tag */ 10790075Sobrien arswitch_modifyreg(sc->sc_dev, AR8X16_REG_SERVICE_TAG, 10890075Sobrien AR8X16_SERVICE_TAG_MASK, 0); 10990075Sobrien 11090075Sobrien return (0); 11190075Sobrien} 11290075Sobrien 11390075Sobrien/* 11490075Sobrien * The AR7240 probes the same as the AR8216. 11590075Sobrien * 11690075Sobrien * However, the support is slightly different. 11790075Sobrien * 11890075Sobrien * So instead of checking the PHY revision or mask register contents, 11990075Sobrien * we simply fall back to a hint check. 12090075Sobrien */ 12190075Sobrienint 12290075Sobrienar7240_probe(device_t dev) 12390075Sobrien{ 12490075Sobrien int is_7240 = 0; 12590075Sobrien 12690075Sobrien if (resource_int_value(device_get_name(dev), device_get_unit(dev), 12790075Sobrien "is_7240", &is_7240) != 0) 12890075Sobrien return (ENXIO); 12990075Sobrien 13090075Sobrien if (is_7240 == 0) 13190075Sobrien return (ENXIO); 13290075Sobrien 13390075Sobrien return (0); 13490075Sobrien} 13590075Sobrien 13690075Sobrienvoid 13790075Sobrienar7240_attach(struct arswitch_softc *sc) 13890075Sobrien{ 13990075Sobrien 14090075Sobrien sc->hal.arswitch_hw_setup = ar7240_hw_setup; 14190075Sobrien sc->hal.arswitch_hw_global_setup = ar7240_hw_global_setup; 14290075Sobrien} 14390075Sobrien