mirror of
git://projects.qi-hardware.com/openwrt-xburst.git
synced 2024-08-19 03:02:26 +03:00
Migrate rt2x00 to the compat-wireless version
git-svn-id: svn://svn.openwrt.org/openwrt/trunk@10753 3c298f89-4303-0410-b956-a3cf2f4a3e73
This commit is contained in:
parent
d600b610a6
commit
d1b1d3c07e
@ -33,12 +33,128 @@ define KernelPackage/mac80211/description
|
|||||||
Linux 802.11 Wireless Networking Stack
|
Linux 802.11 Wireless Networking Stack
|
||||||
endef
|
endef
|
||||||
|
|
||||||
CONFOPTS:=MAC80211 CFG80211 NL80211 MAC80211_RC_DEFAULT_PID MAC80211_RC_PID
|
# Ralink rt2x00 drivers
|
||||||
|
RT61FW:=RT61_Firmware_V1.2.zip
|
||||||
|
RT71FW:=RT71W_Firmware_V1.8.zip
|
||||||
|
|
||||||
|
define Download/rt61
|
||||||
|
FILE:=$(RT61FW)
|
||||||
|
URL:=http://www.ralinktech.com.tw/data/
|
||||||
|
MD5SUM:=d4c690c93b470bc9a681297c2adc6281
|
||||||
|
endef
|
||||||
|
$(eval $(call Download,rt61))
|
||||||
|
|
||||||
|
define Download/rt71w
|
||||||
|
FILE:=$(RT71FW)
|
||||||
|
URL:=http://www.ralinktech.com.tw/data/
|
||||||
|
MD5SUM:=1e7a5dc574e0268574fcda3fd5cf52f7
|
||||||
|
endef
|
||||||
|
$(eval $(call Download,rt71w))
|
||||||
|
|
||||||
|
define KernelPackage/rt2x00/Default
|
||||||
|
SUBMENU:=Wireless Drivers
|
||||||
|
TITLE:=Ralink Drivers for RT2x00 cards
|
||||||
|
DEPENDS:=@LINUX_2_6_24 @!TARGET_atheros @!TARGET_uml
|
||||||
|
endef
|
||||||
|
|
||||||
|
define KernelPackage/rt2x00-lib
|
||||||
|
$(call KernelPackage/rt2x00/Default)
|
||||||
|
DEPENDS+= @PCI_SUPPORT||USB_SUPPORT +kmod-mac80211
|
||||||
|
TITLE+= (LIB)
|
||||||
|
FILES:=$(PKG_BUILD_DIR)/drivers/net/wireless/rt2x00/rt2x00lib.$(LINUX_KMOD_SUFFIX)
|
||||||
|
AUTOLOAD:=$(call AutoLoad,25,blkcipher ecb arc4 rt2x00lib)
|
||||||
|
endef
|
||||||
|
|
||||||
|
define KernelPackage/rt2x00-pci
|
||||||
|
$(call KernelPackage/rt2x00/Default)
|
||||||
|
DEPENDS+= @PCI_SUPPORT +kmod-rt2x00-lib +kmod-eeprom-93cx6
|
||||||
|
TITLE+= (PCI)
|
||||||
|
FILES:=$(PKG_BUILD_DIR)/drivers/net/wireless/rt2x00/rt2x00pci.$(LINUX_KMOD_SUFFIX)
|
||||||
|
AUTOLOAD:=$(call AutoLoad,26,rt2x00pci)
|
||||||
|
endef
|
||||||
|
|
||||||
|
define KernelPackage/rt2x00-usb
|
||||||
|
$(call KernelPackage/rt2x00/Default)
|
||||||
|
DEPENDS+= @USB_SUPPORT +kmod-rt2x00-lib +kmod-usb-core
|
||||||
|
TITLE+= (USB)
|
||||||
|
FILES:=$(PKG_BUILD_DIR)/drivers/net/wireless/rt2x00/rt2x00usb.$(LINUX_KMOD_SUFFIX)
|
||||||
|
AUTOLOAD:=$(call AutoLoad,26,rt2x00usb)
|
||||||
|
endef
|
||||||
|
|
||||||
|
define KernelPackage/rt2400-pci
|
||||||
|
$(call KernelPackage/rt2x00/Default)
|
||||||
|
DEPENDS+= @PCI_SUPPORT +kmod-rt2x00-pci
|
||||||
|
TITLE+= (RT2400 PCI)
|
||||||
|
FILES:=$(PKG_BUILD_DIR)/drivers/net/wireless/rt2x00/rt2400pci.$(LINUX_KMOD_SUFFIX)
|
||||||
|
AUTOLOAD:=$(call AutoLoad,27,rt2400pci)
|
||||||
|
endef
|
||||||
|
|
||||||
|
define KernelPackage/rt2500-pci
|
||||||
|
$(call KernelPackage/rt2x00/Default)
|
||||||
|
DEPENDS+= @PCI_SUPPORT +kmod-rt2x00-pci
|
||||||
|
TITLE+= (RT2500 PCI)
|
||||||
|
FILES:=$(PKG_BUILD_DIR)/drivers/net/wireless/rt2x00/rt2500pci.$(LINUX_KMOD_SUFFIX)
|
||||||
|
AUTOLOAD:=$(call AutoLoad,27,rt2500pci)
|
||||||
|
endef
|
||||||
|
|
||||||
|
define KernelPackage/rt2500-usb
|
||||||
|
$(call KernelPackage/rt2x00/Default)
|
||||||
|
DEPENDS+= @USB_SUPPORT +kmod-rt2x00-usb +kmod-crc-itu-t
|
||||||
|
TITLE+= (RT2500 USB)
|
||||||
|
FILES:=$(PKG_BUILD_DIR)/drivers/net/wireless/rt2x00/rt2500usb.$(LINUX_KMOD_SUFFIX)
|
||||||
|
AUTOLOAD:=$(call AutoLoad,27,rt2500usb)
|
||||||
|
endef
|
||||||
|
|
||||||
|
define KernelPackage/rt61-pci
|
||||||
|
$(call KernelPackage/rt2x00/Default)
|
||||||
|
DEPENDS+= @PCI_SUPPORT +kmod-rt2x00-pci +kmod-crc-itu-t
|
||||||
|
TITLE+= (RT2x61 PCI)
|
||||||
|
FILES:=$(PKG_BUILD_DIR)/drivers/net/wireless/rt2x00/rt61pci.$(LINUX_KMOD_SUFFIX)
|
||||||
|
AUTOLOAD:=$(call AutoLoad,27,rt61pci)
|
||||||
|
endef
|
||||||
|
|
||||||
|
define KernelPackage/rt73-usb
|
||||||
|
$(call KernelPackage/rt2x00/Default)
|
||||||
|
DEPENDS+= @USB_SUPPORT +kmod-rt2x00-usb
|
||||||
|
TITLE+= (RT73 USB)
|
||||||
|
FILES:=$(PKG_BUILD_DIR)/drivers/net/wireless/rt2x00/rt73usb.$(LINUX_KMOD_SUFFIX)
|
||||||
|
AUTOLOAD:=$(call AutoLoad,27,rt73usb)
|
||||||
|
endef
|
||||||
|
|
||||||
|
RT2X00_CONFOPTS:=CONFIG_RT2X00=y \
|
||||||
|
CONFIG_RT2X00_DEBUG=y \
|
||||||
|
CONFIG_RT2X00_LIB_FIRMWARE=y \
|
||||||
|
CONFIG_RT2X00_LIB_LEDS=y
|
||||||
|
|
||||||
|
ifneq ($(CONFIG_PACKAGE_kmod-rt2x00-pci),)
|
||||||
|
RT2X00_CONFOPTS+= CONFIG_RT2X00_LIB_PCI=y
|
||||||
|
endif
|
||||||
|
ifneq ($(CONFIG_PACKAGE_kmod-rt2x00-usb),)
|
||||||
|
RT2X00_CONFOPTS+= CONFIG_RT2X00_LIB_USB=y
|
||||||
|
endif
|
||||||
|
ifneq ($(CONFIG_PACKAGE_kmod-rt2400-pci),)
|
||||||
|
RT2X00_CONFOPTS+= CONFIG_RT2400PCI=y
|
||||||
|
endif
|
||||||
|
ifneq ($(CONFIG_PACKAGE_kmod-rt2500-pci),)
|
||||||
|
RT2X00_CONFOPTS+= CONFIG_RT2500PCI=y
|
||||||
|
endif
|
||||||
|
ifneq ($(CONFIG_PACKAGE_kmod-rt2500-usb),)
|
||||||
|
RT2X00_CONFOPTS+= CONFIG_RT2500USB=y
|
||||||
|
endif
|
||||||
|
ifneq ($(CONFIG_PACKAGE_kmod-rt61-pci),)
|
||||||
|
RT2X00_CONFOPTS+= CONFIG_RT61PCI=y
|
||||||
|
endif
|
||||||
|
ifneq ($(CONFIG_PACKAGE_kmod-rt73-usb),)
|
||||||
|
RT2X00_CONFOPTS+= CONFIG_RT73USB=y
|
||||||
|
endif
|
||||||
|
|
||||||
|
|
||||||
|
CONFOPTS:=MAC80211 CFG80211 NL80211 MAC80211_RC_DEFAULT_PID MAC80211_RC_PID \
|
||||||
|
|
||||||
BUILDFLAGS:= \
|
BUILDFLAGS:= \
|
||||||
$(foreach opt,$(CONFOPTS),-DCONFIG_$(opt)) \
|
$(foreach opt,$(CONFOPTS),-DCONFIG_$(opt)) \
|
||||||
$(if $(CONFIG_LEDS_TRIGGERS), -DCONFIG_MAC80211_LEDS -DCONFIG_LEDS_TRIGGERS) \
|
$(if $(CONFIG_LEDS_TRIGGERS), -DCONFIG_MAC80211_LEDS -DCONFIG_LEDS_TRIGGERS) \
|
||||||
-D__CONFIG_MAC80211_RC_DEFAULT=pid
|
-D__CONFIG_MAC80211_RC_DEFAULT=pid \
|
||||||
|
|
||||||
MAKE_OPTS:= \
|
MAKE_OPTS:= \
|
||||||
CROSS_COMPILE="$(TARGET_CROSS)" \
|
CROSS_COMPILE="$(TARGET_CROSS)" \
|
||||||
@ -56,6 +172,8 @@ define Build/Prepare
|
|||||||
mkdir -p $(PKG_BUILD_DIR)
|
mkdir -p $(PKG_BUILD_DIR)
|
||||||
$(PKG_UNPACK)
|
$(PKG_UNPACK)
|
||||||
$(if $(QUILT),touch $(PKG_BUILD_DIR)/.quilt_used)
|
$(if $(QUILT),touch $(PKG_BUILD_DIR)/.quilt_used)
|
||||||
|
unzip -jod $(PKG_BUILD_DIR) $(DL_DIR)/$(RT61FW)
|
||||||
|
unzip -jod $(PKG_BUILD_DIR) $(DL_DIR)/$(RT71FW)
|
||||||
endef
|
endef
|
||||||
|
|
||||||
define Build/Compile
|
define Build/Compile
|
||||||
@ -72,4 +190,23 @@ define KernelPackage/mac80211/install
|
|||||||
$(INSTALL_DATA) ./files/lib/wifi/mac80211.sh $(1)/lib/wifi
|
$(INSTALL_DATA) ./files/lib/wifi/mac80211.sh $(1)/lib/wifi
|
||||||
endef
|
endef
|
||||||
|
|
||||||
|
define KernelPackage/rt61-pci/install
|
||||||
|
$(INSTALL_DIR) $(1)/lib/firmware
|
||||||
|
$(INSTALL_DATA) $(PKG_BUILD_DIR)/rt2?61*.bin $(1)/lib/firmware/
|
||||||
|
endef
|
||||||
|
|
||||||
|
define KernelPackage/rt73-usb/install
|
||||||
|
$(INSTALL_DIR) $(1)/lib/firmware
|
||||||
|
$(INSTALL_DATA) $(PKG_BUILD_DIR)/rt73.bin $(1)/lib/firmware/
|
||||||
|
endef
|
||||||
|
|
||||||
|
|
||||||
$(eval $(call KernelPackage,mac80211))
|
$(eval $(call KernelPackage,mac80211))
|
||||||
|
$(eval $(call KernelPackage,rt2x00-lib))
|
||||||
|
$(eval $(call KernelPackage,rt2x00-pci))
|
||||||
|
$(eval $(call KernelPackage,rt2x00-usb))
|
||||||
|
$(eval $(call KernelPackage,rt2400-pci))
|
||||||
|
$(eval $(call KernelPackage,rt2500-pci))
|
||||||
|
$(eval $(call KernelPackage,rt2500-usb))
|
||||||
|
$(eval $(call KernelPackage,rt61-pci))
|
||||||
|
$(eval $(call KernelPackage,rt73-usb))
|
||||||
|
@ -1,180 +0,0 @@
|
|||||||
#
|
|
||||||
# Copyright (C) 2007 OpenWrt.org
|
|
||||||
#
|
|
||||||
# This is free software, licensed under the GNU General Public License v2.
|
|
||||||
# See /LICENSE for more information.
|
|
||||||
#
|
|
||||||
# $Id: $
|
|
||||||
|
|
||||||
include $(TOPDIR)/rules.mk
|
|
||||||
include $(INCLUDE_DIR)/kernel.mk
|
|
||||||
|
|
||||||
PKG_NAME:=rt2x00
|
|
||||||
PKG_VERSION:=$(KERNEL_VERSION)
|
|
||||||
|
|
||||||
include $(INCLUDE_DIR)/package.mk
|
|
||||||
|
|
||||||
|
|
||||||
RT61FW:=RT61_Firmware_V1.2.zip
|
|
||||||
RT71FW:=RT71W_Firmware_V1.8.zip
|
|
||||||
|
|
||||||
define Download/rt61
|
|
||||||
FILE:=$(RT61FW)
|
|
||||||
URL:=http://www.ralinktech.com.tw/data/
|
|
||||||
MD5SUM:=d4c690c93b470bc9a681297c2adc6281
|
|
||||||
endef
|
|
||||||
$(eval $(call Download,rt61))
|
|
||||||
|
|
||||||
define Download/rt71w
|
|
||||||
FILE:=$(RT71FW)
|
|
||||||
URL:=http://www.ralinktech.com.tw/data/
|
|
||||||
MD5SUM:=1e7a5dc574e0268574fcda3fd5cf52f7
|
|
||||||
endef
|
|
||||||
$(eval $(call Download,rt71w))
|
|
||||||
|
|
||||||
# XXX: remove @!TARGET_* later when we have PCI & USB support properly detected on all targets
|
|
||||||
define KernelPackage/rt2x00/Default
|
|
||||||
SUBMENU:=Wireless Drivers
|
|
||||||
TITLE:=Ralink Drivers for RT2x00 cards
|
|
||||||
DEPENDS:=@LINUX_2_6_24 @!TARGET_atheros @!TARGET_uml
|
|
||||||
endef
|
|
||||||
|
|
||||||
define KernelPackage/rt2x00-lib
|
|
||||||
$(call KernelPackage/rt2x00/Default)
|
|
||||||
DEPENDS+= @PCI_SUPPORT||USB_SUPPORT +kmod-mac80211
|
|
||||||
TITLE+= (LIB)
|
|
||||||
FILES:=$(PKG_BUILD_DIR)/rt2x00lib.$(LINUX_KMOD_SUFFIX)
|
|
||||||
AUTOLOAD:=$(call AutoLoad,25,blkcipher ecb arc4 rt2x00lib)
|
|
||||||
endef
|
|
||||||
|
|
||||||
define KernelPackage/rt2x00-pci
|
|
||||||
$(call KernelPackage/rt2x00/Default)
|
|
||||||
DEPENDS+= @PCI_SUPPORT +kmod-rt2x00-lib +kmod-eeprom-93cx6
|
|
||||||
TITLE+= (PCI)
|
|
||||||
FILES:=$(PKG_BUILD_DIR)/rt2x00pci.$(LINUX_KMOD_SUFFIX)
|
|
||||||
AUTOLOAD:=$(call AutoLoad,26,rt2x00pci)
|
|
||||||
endef
|
|
||||||
|
|
||||||
define KernelPackage/rt2x00-usb
|
|
||||||
$(call KernelPackage/rt2x00/Default)
|
|
||||||
DEPENDS+= @USB_SUPPORT +kmod-rt2x00-lib +kmod-usb-core
|
|
||||||
TITLE+= (USB)
|
|
||||||
FILES:=$(PKG_BUILD_DIR)/rt2x00usb.$(LINUX_KMOD_SUFFIX)
|
|
||||||
AUTOLOAD:=$(call AutoLoad,26,rt2x00usb)
|
|
||||||
endef
|
|
||||||
|
|
||||||
define KernelPackage/rt2400-pci
|
|
||||||
$(call KernelPackage/rt2x00/Default)
|
|
||||||
DEPENDS+= @PCI_SUPPORT +kmod-rt2x00-pci
|
|
||||||
TITLE+= (RT2400 PCI)
|
|
||||||
FILES:=$(PKG_BUILD_DIR)/rt2400pci.$(LINUX_KMOD_SUFFIX)
|
|
||||||
AUTOLOAD:=$(call AutoLoad,27,rt2400pci)
|
|
||||||
endef
|
|
||||||
|
|
||||||
define KernelPackage/rt2500-pci
|
|
||||||
$(call KernelPackage/rt2x00/Default)
|
|
||||||
DEPENDS+= @PCI_SUPPORT +kmod-rt2x00-pci
|
|
||||||
TITLE+= (RT2500 PCI)
|
|
||||||
FILES:=$(PKG_BUILD_DIR)/rt2500pci.$(LINUX_KMOD_SUFFIX)
|
|
||||||
AUTOLOAD:=$(call AutoLoad,27,rt2500pci)
|
|
||||||
endef
|
|
||||||
|
|
||||||
define KernelPackage/rt2500-usb
|
|
||||||
$(call KernelPackage/rt2x00/Default)
|
|
||||||
DEPENDS+= @USB_SUPPORT +kmod-rt2x00-usb +kmod-crc-itu-t
|
|
||||||
TITLE+= (RT2500 USB)
|
|
||||||
FILES:=$(PKG_BUILD_DIR)/rt2500usb.$(LINUX_KMOD_SUFFIX)
|
|
||||||
AUTOLOAD:=$(call AutoLoad,27,rt2500usb)
|
|
||||||
endef
|
|
||||||
|
|
||||||
define KernelPackage/rt61-pci
|
|
||||||
$(call KernelPackage/rt2x00/Default)
|
|
||||||
DEPENDS+= @PCI_SUPPORT +kmod-rt2x00-pci +kmod-crc-itu-t
|
|
||||||
TITLE+= (RT2x61 PCI)
|
|
||||||
FILES:=$(PKG_BUILD_DIR)/rt61pci.$(LINUX_KMOD_SUFFIX)
|
|
||||||
AUTOLOAD:=$(call AutoLoad,27,rt61pci)
|
|
||||||
endef
|
|
||||||
|
|
||||||
define KernelPackage/rt73-usb
|
|
||||||
$(call KernelPackage/rt2x00/Default)
|
|
||||||
DEPENDS+= @USB_SUPPORT +kmod-rt2x00-usb
|
|
||||||
TITLE+= (RT73 USB)
|
|
||||||
FILES:=$(PKG_BUILD_DIR)/rt73usb.$(LINUX_KMOD_SUFFIX)
|
|
||||||
AUTOLOAD:=$(call AutoLoad,27,rt73usb)
|
|
||||||
endef
|
|
||||||
|
|
||||||
$(STAMP_PREPARED): $(DL_DIR)/$(PKG_FW6X_NAME) $(DL_DIR)/$(PKG_FW7X_NAME)
|
|
||||||
|
|
||||||
PKG_EXTRA_KCONFIG:= \
|
|
||||||
CONFIG_MAC80211=y \
|
|
||||||
CONFIG_RT2X00=y \
|
|
||||||
CONFIG_RT2X00_DEBUG=y \
|
|
||||||
CONFIG_RT2X00_LIB_FIRMWARE=y \
|
|
||||||
|
|
||||||
ifneq ($(CONFIG_PACKAGE_kmod-rt2x00-pci),)
|
|
||||||
PKG_EXTRA_KCONFIG+= CONFIG_RT2X00PCI=y
|
|
||||||
endif
|
|
||||||
ifneq ($(CONFIG_PACKAGE_kmod-rt2x00-usb),)
|
|
||||||
PKG_EXTRA_KCONFIG+= CONFIG_RT2X00USB=y
|
|
||||||
endif
|
|
||||||
ifneq ($(CONFIG_PACKAGE_kmod-rt2400-pci),)
|
|
||||||
PKG_EXTRA_KCONFIG+= CONFIG_RT2400PCI=y
|
|
||||||
endif
|
|
||||||
ifneq ($(CONFIG_PACKAGE_kmod-rt2500-pci),)
|
|
||||||
PKG_EXTRA_KCONFIG+= CONFIG_RT2500PCI=y
|
|
||||||
endif
|
|
||||||
ifneq ($(CONFIG_PACKAGE_kmod-rt2500-usb),)
|
|
||||||
PKG_EXTRA_KCONFIG+= CONFIG_RT2500USB=y
|
|
||||||
endif
|
|
||||||
ifneq ($(CONFIG_PACKAGE_kmod-rt61-pci),)
|
|
||||||
PKG_EXTRA_KCONFIG+= CONFIG_RT61PCI=y
|
|
||||||
endif
|
|
||||||
ifneq ($(CONFIG_PACKAGE_kmod-rt73-usb),)
|
|
||||||
PKG_EXTRA_KCONFIG+= CONFIG_RT73USB=y
|
|
||||||
endif
|
|
||||||
|
|
||||||
PKG_EXTRA_CFLAGS:= \
|
|
||||||
-I$(STAGING_DIR)/usr/include/mac80211 \
|
|
||||||
$(patsubst CONFIG_%, -DCONFIG_%=1, $(patsubst %=m,%,$(filter %=m,$(PKG_EXTRA_KCONFIG)))) \
|
|
||||||
$(patsubst CONFIG_%, -DCONFIG_%=1, $(patsubst %=y,%,$(filter %=y,$(PKG_EXTRA_KCONFIG)))) \
|
|
||||||
|
|
||||||
define Build/Prepare
|
|
||||||
$(call Build/Prepare/Default)
|
|
||||||
$(CP) src/* $(PKG_BUILD_DIR)/
|
|
||||||
unzip -jod $(PKG_BUILD_DIR) $(DL_DIR)/$(RT61FW)
|
|
||||||
unzip -jod $(PKG_BUILD_DIR) $(DL_DIR)/$(RT71FW)
|
|
||||||
endef
|
|
||||||
|
|
||||||
define Build/Configure
|
|
||||||
touch $(PKG_BUILD_DIR)/rt2x00_config.h
|
|
||||||
endef
|
|
||||||
|
|
||||||
define Build/Compile
|
|
||||||
$(MAKE) -C "$(LINUX_DIR)" \
|
|
||||||
ARCH="$(LINUX_KARCH)" \
|
|
||||||
CROSS_COMPILE="$(TARGET_CROSS)" \
|
|
||||||
SUBDIRS="$(PKG_BUILD_DIR)" \
|
|
||||||
$(PKG_EXTRA_KCONFIG) \
|
|
||||||
EXTRA_CFLAGS="$(PKG_EXTRA_CFLAGS)" \
|
|
||||||
V="$(V)" \
|
|
||||||
modules
|
|
||||||
endef
|
|
||||||
|
|
||||||
define KernelPackage/rt61-pci/install
|
|
||||||
$(INSTALL_DIR) $(1)/lib/firmware
|
|
||||||
$(INSTALL_DATA) $(PKG_BUILD_DIR)/rt2?61*.bin $(1)/lib/firmware/
|
|
||||||
endef
|
|
||||||
|
|
||||||
define KernelPackage/rt73-usb/install
|
|
||||||
$(INSTALL_DIR) $(1)/lib/firmware
|
|
||||||
$(INSTALL_DATA) $(PKG_BUILD_DIR)/rt73.bin $(1)/lib/firmware/
|
|
||||||
endef
|
|
||||||
|
|
||||||
$(eval $(call KernelPackage,rt2x00-lib))
|
|
||||||
$(eval $(call KernelPackage,rt2x00-pci))
|
|
||||||
$(eval $(call KernelPackage,rt2x00-usb))
|
|
||||||
$(eval $(call KernelPackage,rt2400-pci))
|
|
||||||
$(eval $(call KernelPackage,rt2500-pci))
|
|
||||||
$(eval $(call KernelPackage,rt2500-usb))
|
|
||||||
$(eval $(call KernelPackage,rt61-pci))
|
|
||||||
$(eval $(call KernelPackage,rt73-usb))
|
|
@ -1,340 +0,0 @@
|
|||||||
GNU GENERAL PUBLIC LICENSE
|
|
||||||
Version 2, June 1991
|
|
||||||
|
|
||||||
Copyright (C) 1989, 1991 Free Software Foundation, Inc.
|
|
||||||
59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
|
||||||
Everyone is permitted to copy and distribute verbatim copies
|
|
||||||
of this license document, but changing it is not allowed.
|
|
||||||
|
|
||||||
Preamble
|
|
||||||
|
|
||||||
The licenses for most software are designed to take away your
|
|
||||||
freedom to share and change it. By contrast, the GNU General Public
|
|
||||||
License is intended to guarantee your freedom to share and change free
|
|
||||||
software--to make sure the software is free for all its users. This
|
|
||||||
General Public License applies to most of the Free Software
|
|
||||||
Foundation's software and to any other program whose authors commit to
|
|
||||||
using it. (Some other Free Software Foundation software is covered by
|
|
||||||
the GNU Library General Public License instead.) You can apply it to
|
|
||||||
your programs, too.
|
|
||||||
|
|
||||||
When we speak of free software, we are referring to freedom, not
|
|
||||||
price. Our General Public Licenses are designed to make sure that you
|
|
||||||
have the freedom to distribute copies of free software (and charge for
|
|
||||||
this service if you wish), that you receive source code or can get it
|
|
||||||
if you want it, that you can change the software or use pieces of it
|
|
||||||
in new free programs; and that you know you can do these things.
|
|
||||||
|
|
||||||
To protect your rights, we need to make restrictions that forbid
|
|
||||||
anyone to deny you these rights or to ask you to surrender the rights.
|
|
||||||
These restrictions translate to certain responsibilities for you if you
|
|
||||||
distribute copies of the software, or if you modify it.
|
|
||||||
|
|
||||||
For example, if you distribute copies of such a program, whether
|
|
||||||
gratis or for a fee, you must give the recipients all the rights that
|
|
||||||
you have. You must make sure that they, too, receive or can get the
|
|
||||||
source code. And you must show them these terms so they know their
|
|
||||||
rights.
|
|
||||||
|
|
||||||
We protect your rights with two steps: (1) copyright the software, and
|
|
||||||
(2) offer you this license which gives you legal permission to copy,
|
|
||||||
distribute and/or modify the software.
|
|
||||||
|
|
||||||
Also, for each author's protection and ours, we want to make certain
|
|
||||||
that everyone understands that there is no warranty for this free
|
|
||||||
software. If the software is modified by someone else and passed on, we
|
|
||||||
want its recipients to know that what they have is not the original, so
|
|
||||||
that any problems introduced by others will not reflect on the original
|
|
||||||
authors' reputations.
|
|
||||||
|
|
||||||
Finally, any free program is threatened constantly by software
|
|
||||||
patents. We wish to avoid the danger that redistributors of a free
|
|
||||||
program will individually obtain patent licenses, in effect making the
|
|
||||||
program proprietary. To prevent this, we have made it clear that any
|
|
||||||
patent must be licensed for everyone's free use or not licensed at all.
|
|
||||||
|
|
||||||
The precise terms and conditions for copying, distribution and
|
|
||||||
modification follow.
|
|
||||||
|
|
||||||
GNU GENERAL PUBLIC LICENSE
|
|
||||||
TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
|
||||||
|
|
||||||
0. This License applies to any program or other work which contains
|
|
||||||
a notice placed by the copyright holder saying it may be distributed
|
|
||||||
under the terms of this General Public License. The "Program", below,
|
|
||||||
refers to any such program or work, and a "work based on the Program"
|
|
||||||
means either the Program or any derivative work under copyright law:
|
|
||||||
that is to say, a work containing the Program or a portion of it,
|
|
||||||
either verbatim or with modifications and/or translated into another
|
|
||||||
language. (Hereinafter, translation is included without limitation in
|
|
||||||
the term "modification".) Each licensee is addressed as "you".
|
|
||||||
|
|
||||||
Activities other than copying, distribution and modification are not
|
|
||||||
covered by this License; they are outside its scope. The act of
|
|
||||||
running the Program is not restricted, and the output from the Program
|
|
||||||
is covered only if its contents constitute a work based on the
|
|
||||||
Program (independent of having been made by running the Program).
|
|
||||||
Whether that is true depends on what the Program does.
|
|
||||||
|
|
||||||
1. You may copy and distribute verbatim copies of the Program's
|
|
||||||
source code as you receive it, in any medium, provided that you
|
|
||||||
conspicuously and appropriately publish on each copy an appropriate
|
|
||||||
copyright notice and disclaimer of warranty; keep intact all the
|
|
||||||
notices that refer to this License and to the absence of any warranty;
|
|
||||||
and give any other recipients of the Program a copy of this License
|
|
||||||
along with the Program.
|
|
||||||
|
|
||||||
You may charge a fee for the physical act of transferring a copy, and
|
|
||||||
you may at your option offer warranty protection in exchange for a fee.
|
|
||||||
|
|
||||||
2. You may modify your copy or copies of the Program or any portion
|
|
||||||
of it, thus forming a work based on the Program, and copy and
|
|
||||||
distribute such modifications or work under the terms of Section 1
|
|
||||||
above, provided that you also meet all of these conditions:
|
|
||||||
|
|
||||||
a) You must cause the modified files to carry prominent notices
|
|
||||||
stating that you changed the files and the date of any change.
|
|
||||||
|
|
||||||
b) You must cause any work that you distribute or publish, that in
|
|
||||||
whole or in part contains or is derived from the Program or any
|
|
||||||
part thereof, to be licensed as a whole at no charge to all third
|
|
||||||
parties under the terms of this License.
|
|
||||||
|
|
||||||
c) If the modified program normally reads commands interactively
|
|
||||||
when run, you must cause it, when started running for such
|
|
||||||
interactive use in the most ordinary way, to print or display an
|
|
||||||
announcement including an appropriate copyright notice and a
|
|
||||||
notice that there is no warranty (or else, saying that you provide
|
|
||||||
a warranty) and that users may redistribute the program under
|
|
||||||
these conditions, and telling the user how to view a copy of this
|
|
||||||
License. (Exception: if the Program itself is interactive but
|
|
||||||
does not normally print such an announcement, your work based on
|
|
||||||
the Program is not required to print an announcement.)
|
|
||||||
|
|
||||||
These requirements apply to the modified work as a whole. If
|
|
||||||
identifiable sections of that work are not derived from the Program,
|
|
||||||
and can be reasonably considered independent and separate works in
|
|
||||||
themselves, then this License, and its terms, do not apply to those
|
|
||||||
sections when you distribute them as separate works. But when you
|
|
||||||
distribute the same sections as part of a whole which is a work based
|
|
||||||
on the Program, the distribution of the whole must be on the terms of
|
|
||||||
this License, whose permissions for other licensees extend to the
|
|
||||||
entire whole, and thus to each and every part regardless of who wrote it.
|
|
||||||
|
|
||||||
Thus, it is not the intent of this section to claim rights or contest
|
|
||||||
your rights to work written entirely by you; rather, the intent is to
|
|
||||||
exercise the right to control the distribution of derivative or
|
|
||||||
collective works based on the Program.
|
|
||||||
|
|
||||||
In addition, mere aggregation of another work not based on the Program
|
|
||||||
with the Program (or with a work based on the Program) on a volume of
|
|
||||||
a storage or distribution medium does not bring the other work under
|
|
||||||
the scope of this License.
|
|
||||||
|
|
||||||
3. You may copy and distribute the Program (or a work based on it,
|
|
||||||
under Section 2) in object code or executable form under the terms of
|
|
||||||
Sections 1 and 2 above provided that you also do one of the following:
|
|
||||||
|
|
||||||
a) Accompany it with the complete corresponding machine-readable
|
|
||||||
source code, which must be distributed under the terms of Sections
|
|
||||||
1 and 2 above on a medium customarily used for software interchange; or,
|
|
||||||
|
|
||||||
b) Accompany it with a written offer, valid for at least three
|
|
||||||
years, to give any third party, for a charge no more than your
|
|
||||||
cost of physically performing source distribution, a complete
|
|
||||||
machine-readable copy of the corresponding source code, to be
|
|
||||||
distributed under the terms of Sections 1 and 2 above on a medium
|
|
||||||
customarily used for software interchange; or,
|
|
||||||
|
|
||||||
c) Accompany it with the information you received as to the offer
|
|
||||||
to distribute corresponding source code. (This alternative is
|
|
||||||
allowed only for noncommercial distribution and only if you
|
|
||||||
received the program in object code or executable form with such
|
|
||||||
an offer, in accord with Subsection b above.)
|
|
||||||
|
|
||||||
The source code for a work means the preferred form of the work for
|
|
||||||
making modifications to it. For an executable work, complete source
|
|
||||||
code means all the source code for all modules it contains, plus any
|
|
||||||
associated interface definition files, plus the scripts used to
|
|
||||||
control compilation and installation of the executable. However, as a
|
|
||||||
special exception, the source code distributed need not include
|
|
||||||
anything that is normally distributed (in either source or binary
|
|
||||||
form) with the major components (compiler, kernel, and so on) of the
|
|
||||||
operating system on which the executable runs, unless that component
|
|
||||||
itself accompanies the executable.
|
|
||||||
|
|
||||||
If distribution of executable or object code is made by offering
|
|
||||||
access to copy from a designated place, then offering equivalent
|
|
||||||
access to copy the source code from the same place counts as
|
|
||||||
distribution of the source code, even though third parties are not
|
|
||||||
compelled to copy the source along with the object code.
|
|
||||||
|
|
||||||
4. You may not copy, modify, sublicense, or distribute the Program
|
|
||||||
except as expressly provided under this License. Any attempt
|
|
||||||
otherwise to copy, modify, sublicense or distribute the Program is
|
|
||||||
void, and will automatically terminate your rights under this License.
|
|
||||||
However, parties who have received copies, or rights, from you under
|
|
||||||
this License will not have their licenses terminated so long as such
|
|
||||||
parties remain in full compliance.
|
|
||||||
|
|
||||||
5. You are not required to accept this License, since you have not
|
|
||||||
signed it. However, nothing else grants you permission to modify or
|
|
||||||
distribute the Program or its derivative works. These actions are
|
|
||||||
prohibited by law if you do not accept this License. Therefore, by
|
|
||||||
modifying or distributing the Program (or any work based on the
|
|
||||||
Program), you indicate your acceptance of this License to do so, and
|
|
||||||
all its terms and conditions for copying, distributing or modifying
|
|
||||||
the Program or works based on it.
|
|
||||||
|
|
||||||
6. Each time you redistribute the Program (or any work based on the
|
|
||||||
Program), the recipient automatically receives a license from the
|
|
||||||
original licensor to copy, distribute or modify the Program subject to
|
|
||||||
these terms and conditions. You may not impose any further
|
|
||||||
restrictions on the recipients' exercise of the rights granted herein.
|
|
||||||
You are not responsible for enforcing compliance by third parties to
|
|
||||||
this License.
|
|
||||||
|
|
||||||
7. If, as a consequence of a court judgment or allegation of patent
|
|
||||||
infringement or for any other reason (not limited to patent issues),
|
|
||||||
conditions are imposed on you (whether by court order, agreement or
|
|
||||||
otherwise) that contradict the conditions of this License, they do not
|
|
||||||
excuse you from the conditions of this License. If you cannot
|
|
||||||
distribute so as to satisfy simultaneously your obligations under this
|
|
||||||
License and any other pertinent obligations, then as a consequence you
|
|
||||||
may not distribute the Program at all. For example, if a patent
|
|
||||||
license would not permit royalty-free redistribution of the Program by
|
|
||||||
all those who receive copies directly or indirectly through you, then
|
|
||||||
the only way you could satisfy both it and this License would be to
|
|
||||||
refrain entirely from distribution of the Program.
|
|
||||||
|
|
||||||
If any portion of this section is held invalid or unenforceable under
|
|
||||||
any particular circumstance, the balance of the section is intended to
|
|
||||||
apply and the section as a whole is intended to apply in other
|
|
||||||
circumstances.
|
|
||||||
|
|
||||||
It is not the purpose of this section to induce you to infringe any
|
|
||||||
patents or other property right claims or to contest validity of any
|
|
||||||
such claims; this section has the sole purpose of protecting the
|
|
||||||
integrity of the free software distribution system, which is
|
|
||||||
implemented by public license practices. Many people have made
|
|
||||||
generous contributions to the wide range of software distributed
|
|
||||||
through that system in reliance on consistent application of that
|
|
||||||
system; it is up to the author/donor to decide if he or she is willing
|
|
||||||
to distribute software through any other system and a licensee cannot
|
|
||||||
impose that choice.
|
|
||||||
|
|
||||||
This section is intended to make thoroughly clear what is believed to
|
|
||||||
be a consequence of the rest of this License.
|
|
||||||
|
|
||||||
8. If the distribution and/or use of the Program is restricted in
|
|
||||||
certain countries either by patents or by copyrighted interfaces, the
|
|
||||||
original copyright holder who places the Program under this License
|
|
||||||
may add an explicit geographical distribution limitation excluding
|
|
||||||
those countries, so that distribution is permitted only in or among
|
|
||||||
countries not thus excluded. In such case, this License incorporates
|
|
||||||
the limitation as if written in the body of this License.
|
|
||||||
|
|
||||||
9. The Free Software Foundation may publish revised and/or new versions
|
|
||||||
of the General Public License from time to time. Such new versions will
|
|
||||||
be similar in spirit to the present version, but may differ in detail to
|
|
||||||
address new problems or concerns.
|
|
||||||
|
|
||||||
Each version is given a distinguishing version number. If the Program
|
|
||||||
specifies a version number of this License which applies to it and "any
|
|
||||||
later version", you have the option of following the terms and conditions
|
|
||||||
either of that version or of any later version published by the Free
|
|
||||||
Software Foundation. If the Program does not specify a version number of
|
|
||||||
this License, you may choose any version ever published by the Free Software
|
|
||||||
Foundation.
|
|
||||||
|
|
||||||
10. If you wish to incorporate parts of the Program into other free
|
|
||||||
programs whose distribution conditions are different, write to the author
|
|
||||||
to ask for permission. For software which is copyrighted by the Free
|
|
||||||
Software Foundation, write to the Free Software Foundation; we sometimes
|
|
||||||
make exceptions for this. Our decision will be guided by the two goals
|
|
||||||
of preserving the free status of all derivatives of our free software and
|
|
||||||
of promoting the sharing and reuse of software generally.
|
|
||||||
|
|
||||||
NO WARRANTY
|
|
||||||
|
|
||||||
11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
|
|
||||||
FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
|
|
||||||
OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
|
|
||||||
PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
|
|
||||||
OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
|
|
||||||
MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
|
|
||||||
TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
|
|
||||||
PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
|
|
||||||
REPAIR OR CORRECTION.
|
|
||||||
|
|
||||||
12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
|
|
||||||
WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
|
|
||||||
REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
|
|
||||||
INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
|
|
||||||
OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
|
|
||||||
TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
|
|
||||||
YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
|
|
||||||
PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
|
|
||||||
POSSIBILITY OF SUCH DAMAGES.
|
|
||||||
|
|
||||||
END OF TERMS AND CONDITIONS
|
|
||||||
|
|
||||||
How to Apply These Terms to Your New Programs
|
|
||||||
|
|
||||||
If you develop a new program, and you want it to be of the greatest
|
|
||||||
possible use to the public, the best way to achieve this is to make it
|
|
||||||
free software which everyone can redistribute and change under these terms.
|
|
||||||
|
|
||||||
To do so, attach the following notices to the program. It is safest
|
|
||||||
to attach them to the start of each source file to most effectively
|
|
||||||
convey the exclusion of warranty; and each file should have at least
|
|
||||||
the "copyright" line and a pointer to where the full notice is found.
|
|
||||||
|
|
||||||
<one line to give the program's name and a brief idea of what it does.>
|
|
||||||
Copyright (C) <year> <name of author>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the Free Software
|
|
||||||
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
|
||||||
|
|
||||||
|
|
||||||
Also add information on how to contact you by electronic and paper mail.
|
|
||||||
|
|
||||||
If the program is interactive, make it output a short notice like this
|
|
||||||
when it starts in an interactive mode:
|
|
||||||
|
|
||||||
Gnomovision version 69, Copyright (C) year name of author
|
|
||||||
Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
|
|
||||||
This is free software, and you are welcome to redistribute it
|
|
||||||
under certain conditions; type `show c' for details.
|
|
||||||
|
|
||||||
The hypothetical commands `show w' and `show c' should show the appropriate
|
|
||||||
parts of the General Public License. Of course, the commands you use may
|
|
||||||
be called something other than `show w' and `show c'; they could even be
|
|
||||||
mouse-clicks or menu items--whatever suits your program.
|
|
||||||
|
|
||||||
You should also get your employer (if you work as a programmer) or your
|
|
||||||
school, if any, to sign a "copyright disclaimer" for the program, if
|
|
||||||
necessary. Here is a sample; alter the names:
|
|
||||||
|
|
||||||
Yoyodyne, Inc., hereby disclaims all copyright interest in the program
|
|
||||||
`Gnomovision' (which makes passes at compilers) written by James Hacker.
|
|
||||||
|
|
||||||
<signature of Ty Coon>, 1 April 1989
|
|
||||||
Ty Coon, President of Vice
|
|
||||||
|
|
||||||
This General Public License does not permit incorporating your program into
|
|
||||||
proprietary programs. If your program is a subroutine library, you may
|
|
||||||
consider it more useful to permit linking proprietary applications with the
|
|
||||||
library. If this is what you want to do, use the GNU Library General
|
|
||||||
Public License instead of this License.
|
|
@ -1,150 +0,0 @@
|
|||||||
# Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
# <http://rt2x00.serialmonkey.com>
|
|
||||||
#
|
|
||||||
# This program is free software; you can redistribute it and/or modify
|
|
||||||
# it under the terms of the GNU General Public License as published by
|
|
||||||
# the Free Software Foundation; either version 2 of the License, or
|
|
||||||
# (at your option) any later version.
|
|
||||||
#
|
|
||||||
# This program is distributed in the hope that it will be useful,
|
|
||||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
# GNU General Public License for more details.
|
|
||||||
#
|
|
||||||
# You should have received a copy of the GNU General Public License
|
|
||||||
# along with this program; if not, write to the
|
|
||||||
# Free Software Foundation, Inc.,
|
|
||||||
# 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
|
|
||||||
# Module: Makefile
|
|
||||||
# Abstract: Makefile for rt2x00 kernel module
|
|
||||||
|
|
||||||
#
|
|
||||||
# Set the enviroment variables.
|
|
||||||
#
|
|
||||||
ifndef SUBDIRS
|
|
||||||
SUBDIRS=$(shell pwd)
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifdef KERNDIR
|
|
||||||
KERNEL_SOURCES := $(KERNDIR)
|
|
||||||
else
|
|
||||||
KERNEL_SOURCES := /lib/modules/$(shell uname -r)/build
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifdef KERNOUT
|
|
||||||
KERNEL_OUTPUT := KBUILD_OUTPUT=$(KERNOUT)
|
|
||||||
else
|
|
||||||
KERNEL_OUTPUT :=
|
|
||||||
endif
|
|
||||||
|
|
||||||
#
|
|
||||||
# Determine if and with what options the rt2x00 drivers should be build
|
|
||||||
#
|
|
||||||
rt2x00lib-objs := rt2x00dev.o rt2x00mac.o rt2x00config.o rt2x00firmware.o
|
|
||||||
|
|
||||||
ifeq ($(CONFIG_RT2X00),y)
|
|
||||||
obj-m += rt2x00lib.o
|
|
||||||
|
|
||||||
ifeq ($(CONFIG_RT2X00PCI),y)
|
|
||||||
obj-m += rt2x00pci.o
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(CONFIG_RT2X00USB),y)
|
|
||||||
obj-m += rt2x00usb.o
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(CONFIG_RT2X00_LIB_DEBUGFS),y)
|
|
||||||
rt2x00lib-objs += rt2x00debug.o
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(CONFIG_RT2400PCI),y)
|
|
||||||
obj-m += rt2400pci.o
|
|
||||||
ifeq ($(CONFIG_RT2400PCI_RFKILL),y)
|
|
||||||
rt2x00lib-objs += rt2x00rfkill.o
|
|
||||||
EXTRA_CFLAGS += -DCONFIG_RT2X00_LIB_RFKILL
|
|
||||||
endif
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(CONFIG_RT2500PCI),y)
|
|
||||||
obj-m += rt2500pci.o
|
|
||||||
ifeq ($(CONFIG_RT2500PCI_RFKILL),y)
|
|
||||||
rt2x00lib-objs += rt2x00rfkill.o
|
|
||||||
EXTRA_CFLAGS += -DCONFIG_RT2X00_LIB_RFKILL
|
|
||||||
endif
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(CONFIG_RT2500USB),y)
|
|
||||||
obj-m += rt2500usb.o
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(CONFIG_RT61PCI),y)
|
|
||||||
EXTRA_CFLAGS += -DCONFIG_RT2X00_LIB_FIRMWARE
|
|
||||||
rt2x00lib-objs += rt2x00firmware.o
|
|
||||||
obj-m += rt61pci.o
|
|
||||||
ifeq ($(CONFIG_RT61PCI_RFKILL),y)
|
|
||||||
rt2x00lib-objs += rt2x00rfkill.o
|
|
||||||
EXTRA_CFLAGS += -DCONFIG_RT2X00_LIB_RFKILL
|
|
||||||
endif
|
|
||||||
endif
|
|
||||||
|
|
||||||
ifeq ($(CONFIG_RT73USB),y)
|
|
||||||
EXTRA_CFLAGS += -DCONFIG_RT2X00_LIB_FIRMWARE
|
|
||||||
rt2x00lib-objs += rt2x00firmware.o
|
|
||||||
obj-m += rt73usb.o
|
|
||||||
endif
|
|
||||||
|
|
||||||
endif
|
|
||||||
|
|
||||||
MAKEFLAGS += --no-print-directory
|
|
||||||
EXTRA_CFLAGS := -include $(SUBDIRS)/rt2x00_compat.h $(CFLAGS)
|
|
||||||
|
|
||||||
all: default
|
|
||||||
|
|
||||||
config_header:
|
|
||||||
@if [ ! -f "rt2x00_config.h" ] || [ "rt2x00_config.h" -ot "config" ]; \
|
|
||||||
then \
|
|
||||||
awk -F = > rt2x00_config.h < config '/^CONFIG.*$\/ \
|
|
||||||
{ \
|
|
||||||
if($$2 == "y") { \
|
|
||||||
print "#ifndef " $$1; \
|
|
||||||
print "#define " $$1; \
|
|
||||||
print "#endif"; \
|
|
||||||
print "" \
|
|
||||||
} else { \
|
|
||||||
print "#undef " $$1; \
|
|
||||||
print ""; \
|
|
||||||
} \
|
|
||||||
}'; \
|
|
||||||
fi
|
|
||||||
|
|
||||||
default: config_header
|
|
||||||
@$(MAKE) -C $(KERNEL_SOURCES) SUBDIRS=$(SUBDIRS) $(KERNEL_OUTPUT) \
|
|
||||||
modules
|
|
||||||
|
|
||||||
sparse: config_header
|
|
||||||
@$(MAKE) -C $(KERNEL_SOURCES) SUBDIRS=$(SUBDIRS) $(KERNEL_OUTPUT) \
|
|
||||||
modules C=1 CF=-D__CHECK_ENDIAN__
|
|
||||||
|
|
||||||
install: config_header
|
|
||||||
@$(MAKE) -C $(KERNEL_SOURCES) SUBDIRS=$(SUBDIRS) $(KERNEL_OUTPUT) \
|
|
||||||
INSTALL_MOD_DIR=rt2x00 $(KERNEL_OUTPUT) modules_install
|
|
||||||
/sbin/depmod -a
|
|
||||||
|
|
||||||
clean:
|
|
||||||
@rm -f rt2x00_config.h
|
|
||||||
@rm -f Modules.symvers Module.symvers
|
|
||||||
@for folder in $(EXTMODDIRS); \
|
|
||||||
do \
|
|
||||||
rm -f $${folder}/*.o \
|
|
||||||
rm -f $${folder}/*.ko \
|
|
||||||
rm -f $${folder}/*.s \
|
|
||||||
rm -f $${folder}/*.mod.c \
|
|
||||||
rm -f $${folder}/.*.cmd \
|
|
||||||
rm -f $${folder}/.*.flags \
|
|
||||||
rm -f $${folder}/.*.o.d \
|
|
||||||
rm -f $${folder}/.*.s.d \
|
|
||||||
rm -f $${folder}/.#* \
|
|
||||||
rm -f $${folder}/*~ \
|
|
||||||
rm -fr $${folder}/.tmp_versions; \
|
|
||||||
done
|
|
@ -1,548 +0,0 @@
|
|||||||
===============================================================================
|
|
||||||
Installation and configuration instructions for the rt2x00 Modules
|
|
||||||
===============================================================================
|
|
||||||
|
|
||||||
===============================================================================
|
|
||||||
Table of contents:
|
|
||||||
========================
|
|
||||||
|
|
||||||
- 1: Minimal requirements
|
|
||||||
- 1.1: kernel
|
|
||||||
- 1.2: gcc
|
|
||||||
- 1.3: make
|
|
||||||
- 2: Hardware
|
|
||||||
- 2.1: Chipsets
|
|
||||||
- 2.2: RF button
|
|
||||||
- 3: Module building & Installation
|
|
||||||
- 3.1: Introduction
|
|
||||||
- 3.2: Configure
|
|
||||||
- 3.3: Build
|
|
||||||
- 3.4: Installation
|
|
||||||
- 4: Firmware
|
|
||||||
- 4.1: Firmware files
|
|
||||||
- 4.2: Firmware installation
|
|
||||||
- 4.3: Firmware requirements
|
|
||||||
- 5: Module loading
|
|
||||||
- 5.1: Module load order
|
|
||||||
- 5.2: Module load options
|
|
||||||
- 6: Interfaces
|
|
||||||
- 6.1: Wireless interfaces
|
|
||||||
- 6.2: Input interface
|
|
||||||
- 7: Interface configuration
|
|
||||||
- 7.1: Minimal configuration
|
|
||||||
- 7.2: Configuration tools
|
|
||||||
- 8: Distribution specific notes
|
|
||||||
- 8.1: Debian & derivatives
|
|
||||||
- 8.2: Fedora
|
|
||||||
- 8.3: Gentoo
|
|
||||||
- 8.4: Mandriva
|
|
||||||
- 9: Problems & Troubleshooting
|
|
||||||
- 9.1: Debug information
|
|
||||||
- 9.2: Debugfs
|
|
||||||
- 9.3: Bug reporting
|
|
||||||
- 10: Problems & Workarounds
|
|
||||||
- 10.1: udev interface naming
|
|
||||||
- 10.2: BUG - ifdown & ifup radio failure
|
|
||||||
- 11: TODO list
|
|
||||||
- 12: Contact us
|
|
||||||
|
|
||||||
|
|
||||||
===============================================================================
|
|
||||||
1: Minimal requirements:
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
===================
|
|
||||||
1.1: kernel
|
|
||||||
=========
|
|
||||||
|
|
||||||
- The minimal required kernel version is 2.6.22-rc1
|
|
||||||
|
|
||||||
- It is important that the installed kernel sources match
|
|
||||||
the running kernel. Unless you are crosscompiling and you
|
|
||||||
know what you are doing.
|
|
||||||
|
|
||||||
- Depending on what rt2x00 components will be built,
|
|
||||||
some kernel configuration options are mandatory.
|
|
||||||
It does however not matter if these options are compiled
|
|
||||||
into the kernel or compiled as module.
|
|
||||||
|
|
||||||
Kernel config option Required for component
|
|
||||||
------------------------------------------------------------------
|
|
||||||
# CONFIG_NET_RADIO all
|
|
||||||
# CONFIG_MAC80211 all
|
|
||||||
# CONFIG_WLAN_80211 all
|
|
||||||
# CONFIG_PCI rt2400pci, rt2500pci, rt61pci
|
|
||||||
# CONFIG_USB rt2500usb, rt73usb
|
|
||||||
# CONFIG_HOTPLUG rt61pci, rt73usb
|
|
||||||
# CONFIG_FW_LOADER rt61pci, rt73usb
|
|
||||||
# CONFIG_CRC_ITU_T rt61pci, rt73usb
|
|
||||||
# CONFIG_DEBUG_FS rt2x00 (optional, only for debug)
|
|
||||||
# CONFIG_RFKILL rt2400pci, rt2500pci, rt61pci (optional,
|
|
||||||
only for button support)
|
|
||||||
|
|
||||||
===================
|
|
||||||
1.2: GCC
|
|
||||||
=========
|
|
||||||
|
|
||||||
- For building the rt2x00 components the same gcc version is required
|
|
||||||
as was used to build your target kernel.
|
|
||||||
|
|
||||||
===================
|
|
||||||
1.3: make
|
|
||||||
=========
|
|
||||||
|
|
||||||
- The program 'make' needs to be installed on the system. There are no
|
|
||||||
further special requirements for this program.
|
|
||||||
|
|
||||||
===============================================================================
|
|
||||||
2: Hardware
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
===================
|
|
||||||
2.1: Chipsets
|
|
||||||
=========
|
|
||||||
|
|
||||||
Support for each Ralink wireless chipset has been split into separate drivers.
|
|
||||||
|
|
||||||
# rt2400pci
|
|
||||||
- chipset: rt2400
|
|
||||||
- supports: rt2460
|
|
||||||
- bus type: PCI/PCMCIA/miniPCI
|
|
||||||
# rt2500pci
|
|
||||||
- chipset: rt2500
|
|
||||||
- supports: rt2560
|
|
||||||
- bus type: PCI/PCMCIA/miniPCI
|
|
||||||
# rt2500usb
|
|
||||||
- chipset: rt2570
|
|
||||||
- supports: rt2570
|
|
||||||
- bus type: USB
|
|
||||||
# rt61pci
|
|
||||||
- chipset: rt61 (or rt2600)
|
|
||||||
- supports: rt2561, rt2561s, rt2661
|
|
||||||
- bus type: PCI/PCMCIA/miniPCI
|
|
||||||
# rt73usb
|
|
||||||
- chipset: rt73
|
|
||||||
- supports: rt2571(w), rt2573, rt2671
|
|
||||||
- bus type: USB
|
|
||||||
|
|
||||||
===================
|
|
||||||
2.2: RF button
|
|
||||||
=========
|
|
||||||
|
|
||||||
On some occasions the Ralink chipset has been built into a laptop.
|
|
||||||
If that is the case, there usually is a hardware button that controls the
|
|
||||||
radio of the wireless interface.
|
|
||||||
If you have such a hardware device, make sure you enable hardware button
|
|
||||||
support for your device in the configuration before building the rt2x00
|
|
||||||
components.
|
|
||||||
Note: This feature requires the enabling of the rfkill driver in the kernel.
|
|
||||||
|
|
||||||
===============================================================================
|
|
||||||
3: Module building & Installation
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
===================
|
|
||||||
3.1: Introduction
|
|
||||||
=========
|
|
||||||
|
|
||||||
The following steps in this chapter concerning module building and
|
|
||||||
installation need to be performed for each kernel. This means that
|
|
||||||
after each kernel upgrade the modules need to be rebuild and
|
|
||||||
reinstalled in order to make them work with the new kernel.
|
|
||||||
|
|
||||||
===================
|
|
||||||
3.2: Configure
|
|
||||||
=========
|
|
||||||
|
|
||||||
Before starting to build the rt2x00 components it is recommended to look into
|
|
||||||
the 'config' file first. In this file you can configure which components of
|
|
||||||
rt2x00 should be built. And even more importantly, you can configure with
|
|
||||||
what options the components will be built.
|
|
||||||
To build all the rt2x00 drivers (with debug capabilities enabled) no changes
|
|
||||||
in the configuration file are required. For most users this would be
|
|
||||||
sufficient to start working with rt2x00.
|
|
||||||
|
|
||||||
===================
|
|
||||||
3.3: Build
|
|
||||||
=========
|
|
||||||
|
|
||||||
To build all rt2x00 components which were enabled in the configuration file
|
|
||||||
simply run (root privileges not required):
|
|
||||||
|
|
||||||
# $ make
|
|
||||||
|
|
||||||
All modules (.ko files) will be created in the current directory.
|
|
||||||
|
|
||||||
===================
|
|
||||||
3.4: Installation
|
|
||||||
=========
|
|
||||||
|
|
||||||
All rt2x00 modules can be installed by doing (with root privileges):
|
|
||||||
|
|
||||||
# $ make install
|
|
||||||
|
|
||||||
With this command all rt2x00 modules (including rfkill and d80211) will be
|
|
||||||
created in a newly created folder named 'rt2x00' inside the kernel modules
|
|
||||||
directory (usually '/lib/modules/$(uname -r)/').
|
|
||||||
|
|
||||||
|
|
||||||
==============================================================================
|
|
||||||
4: Firmware
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
===================
|
|
||||||
4.1: Firmware files
|
|
||||||
=========
|
|
||||||
|
|
||||||
rt61pci and rt73usb require firmware to be available while loading the module.
|
|
||||||
The following firmware files are available for each driver:
|
|
||||||
|
|
||||||
# rt61pci
|
|
||||||
- rt2561.bin
|
|
||||||
- rt2561s.bin
|
|
||||||
- rt2661.bin
|
|
||||||
|
|
||||||
# rt73usb
|
|
||||||
- rt73.bin
|
|
||||||
|
|
||||||
===================
|
|
||||||
4.2: Firmware installation
|
|
||||||
=========
|
|
||||||
|
|
||||||
The latest firmware files are available in a separate .zip archive and can be
|
|
||||||
downloaded from the support page on the Ralink website at
|
|
||||||
http://www.ralinktech.com.
|
|
||||||
Note that by a high level of logic, Ralink has named their firmware for rt73
|
|
||||||
chipsets "rt71W" with a comment that it is for the rt2571W and rt2671 devices.
|
|
||||||
For rt61pci 3 seperate firmware files are available, which one is used depends
|
|
||||||
on which RT chip is on the device. Usually it is best to install all files.
|
|
||||||
To install the firmware the firmware files need to be manually copied to the
|
|
||||||
systems firmware folder (usually '/lib/firmware/') the exact folder depends
|
|
||||||
on the distribution. When in doubt consult the distributions documentation.
|
|
||||||
|
|
||||||
===================
|
|
||||||
4.3: Firmware requirements
|
|
||||||
=========
|
|
||||||
|
|
||||||
To load firmware when the module is loaded the hotplug daemon should be
|
|
||||||
running. Make sure you either enable hotplugging manually before loading the
|
|
||||||
module, or make sure hotplugging is enabled during the system boot process.
|
|
||||||
|
|
||||||
|
|
||||||
==============================================================================
|
|
||||||
5: Module loading
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
===================
|
|
||||||
5.1: Module load order
|
|
||||||
=========
|
|
||||||
|
|
||||||
When the modules have been properly installed by following the installation
|
|
||||||
instructions from the previous section, the module handlers (i.e. modprobe)
|
|
||||||
will automaticly resolve all module dependencies when loading the device
|
|
||||||
specific driver.
|
|
||||||
|
|
||||||
When loading the modules manually with insmod, you should load them in the
|
|
||||||
following order:
|
|
||||||
|
|
||||||
# eeprom_93cx6.ko (optional, only required for pci devices)
|
|
||||||
# rt2x00lib.ko
|
|
||||||
# rt2x00pci.ko (optional, only required for pci devices)
|
|
||||||
# rt2x00usb.ko (optional, only required for usb devices)
|
|
||||||
# rt2400pci.ko (optional, only required for rt2400 support)
|
|
||||||
# rt2500pci.ko (optional, only required for rt2500 support)
|
|
||||||
# rt2500usb.ko (optional, only required for rt2570 support)
|
|
||||||
# rt61pci.ko (optional, only required for rt61 support)
|
|
||||||
# rt73usb.ko (optional, only required for rt73 support)
|
|
||||||
|
|
||||||
===================
|
|
||||||
5.2: Module load options
|
|
||||||
=========
|
|
||||||
|
|
||||||
None.
|
|
||||||
|
|
||||||
|
|
||||||
==============================================================================
|
|
||||||
6: Interfaces
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
===================
|
|
||||||
6.1: Wireless interfaces
|
|
||||||
=========
|
|
||||||
|
|
||||||
After loading the modules two interfaces will now be visible in ifconfig and
|
|
||||||
iwconfig, namely wmaster0 and wlan0. The first device is the so called master
|
|
||||||
device which is can be used by some userspace tools, but normally can be
|
|
||||||
ignored by the user. The second interface wlan0 is the client interface which
|
|
||||||
the user can configure.
|
|
||||||
With rt2x00 it is possible to run multiple client interfaces with
|
|
||||||
only a single device. 1 client interface can run in adhoc, managed or master
|
|
||||||
mode while a second interface can run in monitor mode at the same time.
|
|
||||||
More client interfaces can be added by issuing the following command
|
|
||||||
(with root privileges):
|
|
||||||
|
|
||||||
# $ echo -n <name> > /sys/class/ieee80211/<dev>/add_iface
|
|
||||||
|
|
||||||
where the variable <name> is the name of the client interface that should be
|
|
||||||
added (i.e. wlan1), and <dev> is the physical device where the new client
|
|
||||||
interface should be attached to (i.e. phy0).
|
|
||||||
|
|
||||||
===================
|
|
||||||
6.2: Input interface
|
|
||||||
=========
|
|
||||||
|
|
||||||
When the rfkill driver is being used a new input device with the name of the
|
|
||||||
device specific module where the button belongs to will have been created.
|
|
||||||
Whenever the user presses the hardware button the rfkill driver will
|
|
||||||
automatically make sure the hardware radio is being disabled or enabled
|
|
||||||
accordingly. When the user has opened the input device the radio will
|
|
||||||
not be automatically controlled, but instead the input device will
|
|
||||||
report all button events (KEY_RFKILL) to userspace where the user
|
|
||||||
could have setup script to do all the work that has to be executed.
|
|
||||||
This means that while the input device is opened, the user is responsible
|
|
||||||
for the correct behaviour.
|
|
||||||
|
|
||||||
|
|
||||||
==============================================================================
|
|
||||||
7: Interface configuration
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
===================
|
|
||||||
7.1: Minimal configuration
|
|
||||||
=========
|
|
||||||
|
|
||||||
- After loading the modules the interface should be configured to start
|
|
||||||
an association or work in monitor mode. The following steps are required
|
|
||||||
for a minimal configuration to associate with a non-encrypted access point.
|
|
||||||
|
|
||||||
- Before bringing the client interface up, the working mode should be set:
|
|
||||||
|
|
||||||
# $ iwconfig wlan0 mode managed
|
|
||||||
|
|
||||||
- Configuration parts like essid and channel can be set before or after the
|
|
||||||
client interface has been brought up.
|
|
||||||
|
|
||||||
- It is usually a good idea to set the essid:
|
|
||||||
|
|
||||||
# $ iwconfig wlan0 essid myessid
|
|
||||||
|
|
||||||
- In some situations the device also requires the channel to be manually set:
|
|
||||||
|
|
||||||
# $ iwconfig wlan0 channel mychannel
|
|
||||||
|
|
||||||
- To bring the client interface up:
|
|
||||||
|
|
||||||
# $ ifconfig wlan0 up
|
|
||||||
|
|
||||||
- After the client interface has been brought up, scanning can be performed
|
|
||||||
to check if the desired AP is being detected.
|
|
||||||
|
|
||||||
# $ iwlist wlan0 scan
|
|
||||||
|
|
||||||
- To start an association attempt, the AP address should be set:
|
|
||||||
|
|
||||||
# $ iwconfig wlan0 ap mybssid
|
|
||||||
|
|
||||||
===================
|
|
||||||
7.2: Configuration tools
|
|
||||||
=========
|
|
||||||
|
|
||||||
To configure the interface several tools are possible, the most basic tools
|
|
||||||
are the wireless-tools that provide the iwconfig, iwpriv and iwlist commands.
|
|
||||||
For WPA connections the wireless-tools are not sufficient, to configure the
|
|
||||||
interface for WPA wireless network wpa_supplicant is required.
|
|
||||||
For master mode functionality it is possible to only use the wireless-tools,
|
|
||||||
but it is recommended to use hostapd instead. This tool offers the best
|
|
||||||
functionality.
|
|
||||||
For all configuration tools (wireless-tools, wpa_supplicant and hostapd) are
|
|
||||||
manuals and howto's present in the manpages or on the internet. It is adviced
|
|
||||||
to have at least read the manpages before using the tools for a better
|
|
||||||
understanding on configuring the interface.
|
|
||||||
|
|
||||||
|
|
||||||
==============================================================================
|
|
||||||
8: Distribution specific notes
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
===================
|
|
||||||
8.1: Debian & derivatives
|
|
||||||
=========
|
|
||||||
|
|
||||||
In some instances installing the rt2x00 drivers on debian will result
|
|
||||||
in the problem that the files are being copied into the wrong folder,
|
|
||||||
which results in the fact that the driver cannot be loaded.
|
|
||||||
Installing the drivers should be done manually in this case,
|
|
||||||
please refer to the distributions documentation regarding the proper
|
|
||||||
location of the kernel modules.
|
|
||||||
|
|
||||||
===================
|
|
||||||
8.2: Fedora
|
|
||||||
=========
|
|
||||||
|
|
||||||
Although rt2x00 contains many backward compatibility fixes to ensure
|
|
||||||
that all rt2x00 components will be able to compile and run on all
|
|
||||||
systems that meet the minimal requirements, this does not work in all
|
|
||||||
situations when the Fedora kernels are being used.
|
|
||||||
The problem lies in the fact that Fedora (like most other distributions)
|
|
||||||
heavily patch their kernel for better stability and more features.
|
|
||||||
Unlike the other distributions however, Fedora does not pay attention to
|
|
||||||
compatibility for external kernel drivers. This means that compiling rt2x00
|
|
||||||
while using a Fedora kernel will result in compile errors regarding unknown
|
|
||||||
fields in structures or problems with function arguments.
|
|
||||||
For rt2x00 it is impossible to make all checks to support all Fedora kernel
|
|
||||||
releases. This means that when rt2x00 compilation is failing while using a
|
|
||||||
Fedora kernel we cannot give support for the compilation steps.
|
|
||||||
We recommend the user to complain to the Fedora developers when this problem
|
|
||||||
occurs.
|
|
||||||
If the user has managed to compile rt2x00 for a Fedora kernel we will
|
|
||||||
give support for possible problems while working with rt2x00. So the only
|
|
||||||
part we do not support is the building of rt2x00.
|
|
||||||
Please note that when you have edited the rt2x00 code to make it compile,
|
|
||||||
it is advised to state those changes in bugreports while reporting other
|
|
||||||
problems with rt2x00.
|
|
||||||
|
|
||||||
===================
|
|
||||||
8.3: Gentoo
|
|
||||||
=========
|
|
||||||
|
|
||||||
rt2x00 can also be found in portage, both the beta releases and the cvs tree.
|
|
||||||
Because rt2x00 is still experimental these ebuild are still masked, this means
|
|
||||||
that before you can emerge them they first have to be unmasked.
|
|
||||||
Gentoo provides various instructions on how this can be done on their website.
|
|
||||||
|
|
||||||
===================
|
|
||||||
8.4: Mandriva
|
|
||||||
=========
|
|
||||||
|
|
||||||
In some instances installing the rt2x00 drivers on Mandriva will result
|
|
||||||
in the problem that the files are being copied into the wrong folder,
|
|
||||||
which results in the fact that the driver cannot be loaded.
|
|
||||||
Installing the drivers should be done manually in this case,
|
|
||||||
please refer to the distributions documentation regarding the proper
|
|
||||||
location of the kernel modules.
|
|
||||||
|
|
||||||
|
|
||||||
==============================================================================
|
|
||||||
9: Problems & Troubleshooting
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
===================
|
|
||||||
9.1: Debug information
|
|
||||||
=========
|
|
||||||
|
|
||||||
When reporting problems make sure the driver has been compiled with debug
|
|
||||||
enabled.
|
|
||||||
If you have done so, the debug output can be found in the output
|
|
||||||
of 'dmesg' and also in /var/log/messages and /var/log/syslog.
|
|
||||||
|
|
||||||
===================
|
|
||||||
9.2: Debugfs
|
|
||||||
=========
|
|
||||||
|
|
||||||
rt2x00 provides several debugfs entries which can be used to help
|
|
||||||
provide more information about the interface.
|
|
||||||
To see the rt2x00 debugfs entries, debugfs should first be mounted,
|
|
||||||
to do this you should issue the following command:
|
|
||||||
|
|
||||||
# $ mount -t debugfs none /debug
|
|
||||||
|
|
||||||
Where /debug is the directy on which the debugfs entries should appear,
|
|
||||||
make sure this directory exists when mounting debugfs.
|
|
||||||
With the debugfs folder, the rt2x00 folder with the rt2x00 debugfs entries
|
|
||||||
will be created. Within the rt2x00 folder, each physical device will be
|
|
||||||
represented by a folder named after the interface which belongs to this
|
|
||||||
device. Within the folder the following files can be found:
|
|
||||||
|
|
||||||
# register
|
|
||||||
- This file contains the register contents of the interface.
|
|
||||||
# eeprom
|
|
||||||
- This file contains the eeprom contents of the interface.
|
|
||||||
|
|
||||||
===================
|
|
||||||
9.3: Bug reporting
|
|
||||||
=========
|
|
||||||
|
|
||||||
When reporting a bug or problem with the rt2x00 module,
|
|
||||||
make sure you report the following information:
|
|
||||||
# How to reproduce
|
|
||||||
# RT2x00 debug output, usually found in /var/log/messages
|
|
||||||
# Module version
|
|
||||||
# Wireless card chipset, model and manufacturer
|
|
||||||
# Kernel version (i.e. 2.6.17)
|
|
||||||
# Hardware architecture (i.e. x86, AMD64, Sparc)
|
|
||||||
# rt2x00 code changes done by the user
|
|
||||||
# Anything else you may think will help us resolve the issue
|
|
||||||
|
|
||||||
|
|
||||||
==============================================================================
|
|
||||||
10: Problems & Workarounds
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
===================
|
|
||||||
10.1: udev interface naming
|
|
||||||
=========
|
|
||||||
|
|
||||||
In some cases when loading the rt2x00 drivers the interface names are
|
|
||||||
different from the names used in this README. This is usually caused by the
|
|
||||||
udev handler who has set some rules regarding the interface. These rules
|
|
||||||
are usually set up by the distribution and have been created especially for
|
|
||||||
for the legacy driver and their strange behavior.
|
|
||||||
To change the rules udev applies to your interface you should edit the udev
|
|
||||||
rules stored in /etc/udev/rules.d/ (exact location might be different
|
|
||||||
depending on distribution).
|
|
||||||
When editing this file, search for the line that contains something like this:
|
|
||||||
|
|
||||||
# ACTION=="add", SUBSYSTEM=="net", DRIVERS=="?*",
|
|
||||||
# SYSFS{address}=="<mac address>", NAME="<interface>"
|
|
||||||
(line has been wrapped due to max line length limit)
|
|
||||||
|
|
||||||
Where <mac address> is the hardware address of your wireless networkcard,
|
|
||||||
and <interface> is the interface name the interface takes as soon as the
|
|
||||||
rt2x00 modules are loaded.
|
|
||||||
This line should be changed to look like:
|
|
||||||
|
|
||||||
# ACTION=="add", SUBSYSTEM=="net", DRIVERS=="?*",
|
|
||||||
# SYSFS{address}=="<mac address>", SYSFS{type}=="801",
|
|
||||||
# NAME="wmaster0"
|
|
||||||
# ACTION=="add", SUBSYSTEM=="net", DRIVERS=="?*",
|
|
||||||
# SYSFS{address}=="<mac address>", NAME="wlan0"
|
|
||||||
(the 2 lines have been wrapped due to max line length limit)
|
|
||||||
|
|
||||||
Where <mac address> is the hardware address of your wireless networkcard,
|
|
||||||
and thus should be the same as on the original line.
|
|
||||||
|
|
||||||
===================
|
|
||||||
10.2: BUG - ifdown & ifup radio failure
|
|
||||||
=========
|
|
||||||
|
|
||||||
It is a known issue (and BUG) that the driver will fail to correctly resume
|
|
||||||
its radio operations after the interface has been brought down and up again.
|
|
||||||
It is still unknown what the cause for this issue could be, besides the fact
|
|
||||||
that for some reason the device's registers have been incorrectly initialized.
|
|
||||||
This issue also has impact on the device status after a suspend/resume
|
|
||||||
operation. There is no known workaround for this yet.
|
|
||||||
|
|
||||||
|
|
||||||
==============================================================================
|
|
||||||
11: TODO list
|
|
||||||
=======================================
|
|
||||||
See http://rt2x00.serialmonkey.com/wiki/index.php/Rt2x00_beta
|
|
||||||
|
|
||||||
==============================================================================
|
|
||||||
12: Contact us
|
|
||||||
=======================================
|
|
||||||
|
|
||||||
- Website
|
|
||||||
# http://rt2x00.serialmonkey.com/
|
|
||||||
# http://rt2x00.serialmonkey.com/wiki/index.php/Rt2x00_beta
|
|
||||||
|
|
||||||
- Forums:
|
|
||||||
# http://rt2x00.serialmonkey.com/phpBB2/
|
|
||||||
|
|
||||||
- Mailing list:
|
|
||||||
# general: rt2400-general@lists.sourceforge.net
|
|
||||||
# developers: rt2400-devel@lists.sourceforge.net
|
|
||||||
|
|
||||||
- Sourceforge:
|
|
||||||
# http://sourceforge.net/projects/rt2400
|
|
||||||
|
|
@ -1,54 +0,0 @@
|
|||||||
A big thanks to all the developers, testers and supporters of
|
|
||||||
the rt2x00 Linux source code.
|
|
||||||
|
|
||||||
Thanks to the projects main developers:
|
|
||||||
* Mark Wallis - mwallis@serialmonkey.com
|
|
||||||
* Ivo van Doorn - IvDoorn@gmail.com
|
|
||||||
* Luis Correia - lfcorreia@users.sf.net
|
|
||||||
* Robin Cornelius - robin.cornelius@gmail.com
|
|
||||||
* Gertjan van Wingerde - gwingerde@kpnplanet.nl
|
|
||||||
* Romain - spy84464@hotmail.com
|
|
||||||
|
|
||||||
Special thanks to the contributors of this project:
|
|
||||||
* Adisorn Ermongkonchai - moo7822-wlan@yahoo.com
|
|
||||||
* Amir Shalem - amir@boom.org.il
|
|
||||||
* Bernd Petrovitsch - bernd@firmix.at
|
|
||||||
* Bruno - bruno123@users.sf.net
|
|
||||||
* Chris Houston - chris.houston@atterotech.com
|
|
||||||
* Defekt - defekt@liquid-nexus.net
|
|
||||||
* Edvard - eaglenest@users.sourceforge.net
|
|
||||||
* Flavio Stanchina - flavio@stanchina.net
|
|
||||||
* Gregor Glomm - gg@seh.de
|
|
||||||
* Heikki Pernu - heikki.pernu@nekonet.fi
|
|
||||||
* Jerzy Kozera - nordom@tlen.pl
|
|
||||||
* Joachim Gleißner - jg@suse.de
|
|
||||||
* John Coppens - john@jcoppens.com
|
|
||||||
* Jonathan Hudson
|
|
||||||
* KrissN - krissn@op.pl
|
|
||||||
* Luca Tettamanti - kronos.it@gmail.com
|
|
||||||
* Magnus Damm - magnus.damm@gmail.com
|
|
||||||
* Mags
|
|
||||||
* Mathias Klien - ma_klein@gmx.de
|
|
||||||
* Meelis Roos - mroos@linux.ee
|
|
||||||
* Michal Ludvig - michal@logix.cz
|
|
||||||
* Miguel - miguel.marte2@verizon.net
|
|
||||||
* Mike Skinner
|
|
||||||
* Olivier Cornu - o.cornu@gmail.com
|
|
||||||
* Paul Hampson - Paul.Hampson@anu.edu.au
|
|
||||||
* Philippe Rousselot - amazilia@users.sourceforge.net
|
|
||||||
* Remco - remco@d-compu.dyndns.org
|
|
||||||
* Sergey Vlasov - vsu@altlinux.ru
|
|
||||||
* Stephen Warren - SWarren@nvidia.com
|
|
||||||
* Stuart Rackham - srackham@methods.co.nz
|
|
||||||
* Thor Harald Johansen - thorhajo@gmail.com
|
|
||||||
* Tor Petterson - 2r@manowar.dk
|
|
||||||
|
|
||||||
Special thanks:
|
|
||||||
* Ralink - http://www.ralinktech.com.tw
|
|
||||||
For releasing their rt2400/rt2500/rt2570 drivers under the GPL,
|
|
||||||
and their assistance in providing documentation to help development.
|
|
||||||
* Minitar - www.minitar.com
|
|
||||||
For working together with Ralink on releasing the
|
|
||||||
rt2400/rt2500/rt2570 drivers under the GPL.
|
|
||||||
* All the people that have assisted with the rt2400/rt2500/rt2570 source
|
|
||||||
and hence progressed the rt2x00 along the way.
|
|
File diff suppressed because it is too large
Load Diff
@ -1,943 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2400pci
|
|
||||||
Abstract: Data structures and registers for the rt2400pci module.
|
|
||||||
Supported chipsets: RT2460.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2400PCI_H
|
|
||||||
#define RT2400PCI_H
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RF chip defines.
|
|
||||||
*/
|
|
||||||
#define RF2420 0x0000
|
|
||||||
#define RF2421 0x0001
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Signal information.
|
|
||||||
* Defaul offset is required for RSSI <-> dBm conversion.
|
|
||||||
*/
|
|
||||||
#define MAX_SIGNAL 100
|
|
||||||
#define MAX_RX_SSI -1
|
|
||||||
#define DEFAULT_RSSI_OFFSET 100
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Register layout information.
|
|
||||||
*/
|
|
||||||
#define CSR_REG_BASE 0x0000
|
|
||||||
#define CSR_REG_SIZE 0x014c
|
|
||||||
#define EEPROM_BASE 0x0000
|
|
||||||
#define EEPROM_SIZE 0x0100
|
|
||||||
#define BBP_SIZE 0x0020
|
|
||||||
#define RF_SIZE 0x0010
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Control/Status Registers(CSR).
|
|
||||||
* Some values are set in TU, whereas 1 TU == 1024 us.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR0: ASIC revision number.
|
|
||||||
*/
|
|
||||||
#define CSR0 0x0000
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR1: System control register.
|
|
||||||
* SOFT_RESET: Software reset, 1: reset, 0: normal.
|
|
||||||
* BBP_RESET: Hardware reset, 1: reset, 0, release.
|
|
||||||
* HOST_READY: Host ready after initialization.
|
|
||||||
*/
|
|
||||||
#define CSR1 0x0004
|
|
||||||
#define CSR1_SOFT_RESET FIELD32(0x00000001)
|
|
||||||
#define CSR1_BBP_RESET FIELD32(0x00000002)
|
|
||||||
#define CSR1_HOST_READY FIELD32(0x00000004)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR2: System admin status register (invalid).
|
|
||||||
*/
|
|
||||||
#define CSR2 0x0008
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR3: STA MAC address register 0.
|
|
||||||
*/
|
|
||||||
#define CSR3 0x000c
|
|
||||||
#define CSR3_BYTE0 FIELD32(0x000000ff)
|
|
||||||
#define CSR3_BYTE1 FIELD32(0x0000ff00)
|
|
||||||
#define CSR3_BYTE2 FIELD32(0x00ff0000)
|
|
||||||
#define CSR3_BYTE3 FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR4: STA MAC address register 1.
|
|
||||||
*/
|
|
||||||
#define CSR4 0x0010
|
|
||||||
#define CSR4_BYTE4 FIELD32(0x000000ff)
|
|
||||||
#define CSR4_BYTE5 FIELD32(0x0000ff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR5: BSSID register 0.
|
|
||||||
*/
|
|
||||||
#define CSR5 0x0014
|
|
||||||
#define CSR5_BYTE0 FIELD32(0x000000ff)
|
|
||||||
#define CSR5_BYTE1 FIELD32(0x0000ff00)
|
|
||||||
#define CSR5_BYTE2 FIELD32(0x00ff0000)
|
|
||||||
#define CSR5_BYTE3 FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR6: BSSID register 1.
|
|
||||||
*/
|
|
||||||
#define CSR6 0x0018
|
|
||||||
#define CSR6_BYTE4 FIELD32(0x000000ff)
|
|
||||||
#define CSR6_BYTE5 FIELD32(0x0000ff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR7: Interrupt source register.
|
|
||||||
* Write 1 to clear interrupt.
|
|
||||||
* TBCN_EXPIRE: Beacon timer expired interrupt.
|
|
||||||
* TWAKE_EXPIRE: Wakeup timer expired interrupt.
|
|
||||||
* TATIMW_EXPIRE: Timer of atim window expired interrupt.
|
|
||||||
* TXDONE_TXRING: Tx ring transmit done interrupt.
|
|
||||||
* TXDONE_ATIMRING: Atim ring transmit done interrupt.
|
|
||||||
* TXDONE_PRIORING: Priority ring transmit done interrupt.
|
|
||||||
* RXDONE: Receive done interrupt.
|
|
||||||
*/
|
|
||||||
#define CSR7 0x001c
|
|
||||||
#define CSR7_TBCN_EXPIRE FIELD32(0x00000001)
|
|
||||||
#define CSR7_TWAKE_EXPIRE FIELD32(0x00000002)
|
|
||||||
#define CSR7_TATIMW_EXPIRE FIELD32(0x00000004)
|
|
||||||
#define CSR7_TXDONE_TXRING FIELD32(0x00000008)
|
|
||||||
#define CSR7_TXDONE_ATIMRING FIELD32(0x00000010)
|
|
||||||
#define CSR7_TXDONE_PRIORING FIELD32(0x00000020)
|
|
||||||
#define CSR7_RXDONE FIELD32(0x00000040)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR8: Interrupt mask register.
|
|
||||||
* Write 1 to mask interrupt.
|
|
||||||
* TBCN_EXPIRE: Beacon timer expired interrupt.
|
|
||||||
* TWAKE_EXPIRE: Wakeup timer expired interrupt.
|
|
||||||
* TATIMW_EXPIRE: Timer of atim window expired interrupt.
|
|
||||||
* TXDONE_TXRING: Tx ring transmit done interrupt.
|
|
||||||
* TXDONE_ATIMRING: Atim ring transmit done interrupt.
|
|
||||||
* TXDONE_PRIORING: Priority ring transmit done interrupt.
|
|
||||||
* RXDONE: Receive done interrupt.
|
|
||||||
*/
|
|
||||||
#define CSR8 0x0020
|
|
||||||
#define CSR8_TBCN_EXPIRE FIELD32(0x00000001)
|
|
||||||
#define CSR8_TWAKE_EXPIRE FIELD32(0x00000002)
|
|
||||||
#define CSR8_TATIMW_EXPIRE FIELD32(0x00000004)
|
|
||||||
#define CSR8_TXDONE_TXRING FIELD32(0x00000008)
|
|
||||||
#define CSR8_TXDONE_ATIMRING FIELD32(0x00000010)
|
|
||||||
#define CSR8_TXDONE_PRIORING FIELD32(0x00000020)
|
|
||||||
#define CSR8_RXDONE FIELD32(0x00000040)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR9: Maximum frame length register.
|
|
||||||
* MAX_FRAME_UNIT: Maximum frame length in 128b unit, default: 12.
|
|
||||||
*/
|
|
||||||
#define CSR9 0x0024
|
|
||||||
#define CSR9_MAX_FRAME_UNIT FIELD32(0x00000f80)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR11: Back-off control register.
|
|
||||||
* CWMIN: CWmin. Default cwmin is 31 (2^5 - 1).
|
|
||||||
* CWMAX: CWmax. Default cwmax is 1023 (2^10 - 1).
|
|
||||||
* SLOT_TIME: Slot time, default is 20us for 802.11b.
|
|
||||||
* LONG_RETRY: Long retry count.
|
|
||||||
* SHORT_RETRY: Short retry count.
|
|
||||||
*/
|
|
||||||
#define CSR11 0x002c
|
|
||||||
#define CSR11_CWMIN FIELD32(0x0000000f)
|
|
||||||
#define CSR11_CWMAX FIELD32(0x000000f0)
|
|
||||||
#define CSR11_SLOT_TIME FIELD32(0x00001f00)
|
|
||||||
#define CSR11_LONG_RETRY FIELD32(0x00ff0000)
|
|
||||||
#define CSR11_SHORT_RETRY FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR12: Synchronization configuration register 0.
|
|
||||||
* All units in 1/16 TU.
|
|
||||||
* BEACON_INTERVAL: Beacon interval, default is 100 TU.
|
|
||||||
* CFPMAX_DURATION: Cfp maximum duration, default is 100 TU.
|
|
||||||
*/
|
|
||||||
#define CSR12 0x0030
|
|
||||||
#define CSR12_BEACON_INTERVAL FIELD32(0x0000ffff)
|
|
||||||
#define CSR12_CFP_MAX_DURATION FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR13: Synchronization configuration register 1.
|
|
||||||
* All units in 1/16 TU.
|
|
||||||
* ATIMW_DURATION: Atim window duration.
|
|
||||||
* CFP_PERIOD: Cfp period, default is 0 TU.
|
|
||||||
*/
|
|
||||||
#define CSR13 0x0034
|
|
||||||
#define CSR13_ATIMW_DURATION FIELD32(0x0000ffff)
|
|
||||||
#define CSR13_CFP_PERIOD FIELD32(0x00ff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR14: Synchronization control register.
|
|
||||||
* TSF_COUNT: Enable tsf auto counting.
|
|
||||||
* TSF_SYNC: Tsf sync, 0: disable, 1: infra, 2: ad-hoc/master mode.
|
|
||||||
* TBCN: Enable tbcn with reload value.
|
|
||||||
* TCFP: Enable tcfp & cfp / cp switching.
|
|
||||||
* TATIMW: Enable tatimw & atim window switching.
|
|
||||||
* BEACON_GEN: Enable beacon generator.
|
|
||||||
* CFP_COUNT_PRELOAD: Cfp count preload value.
|
|
||||||
* TBCM_PRELOAD: Tbcn preload value in units of 64us.
|
|
||||||
*/
|
|
||||||
#define CSR14 0x0038
|
|
||||||
#define CSR14_TSF_COUNT FIELD32(0x00000001)
|
|
||||||
#define CSR14_TSF_SYNC FIELD32(0x00000006)
|
|
||||||
#define CSR14_TBCN FIELD32(0x00000008)
|
|
||||||
#define CSR14_TCFP FIELD32(0x00000010)
|
|
||||||
#define CSR14_TATIMW FIELD32(0x00000020)
|
|
||||||
#define CSR14_BEACON_GEN FIELD32(0x00000040)
|
|
||||||
#define CSR14_CFP_COUNT_PRELOAD FIELD32(0x0000ff00)
|
|
||||||
#define CSR14_TBCM_PRELOAD FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR15: Synchronization status register.
|
|
||||||
* CFP: ASIC is in contention-free period.
|
|
||||||
* ATIMW: ASIC is in ATIM window.
|
|
||||||
* BEACON_SENT: Beacon is send.
|
|
||||||
*/
|
|
||||||
#define CSR15 0x003c
|
|
||||||
#define CSR15_CFP FIELD32(0x00000001)
|
|
||||||
#define CSR15_ATIMW FIELD32(0x00000002)
|
|
||||||
#define CSR15_BEACON_SENT FIELD32(0x00000004)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR16: TSF timer register 0.
|
|
||||||
*/
|
|
||||||
#define CSR16 0x0040
|
|
||||||
#define CSR16_LOW_TSFTIMER FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR17: TSF timer register 1.
|
|
||||||
*/
|
|
||||||
#define CSR17 0x0044
|
|
||||||
#define CSR17_HIGH_TSFTIMER FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR18: IFS timer register 0.
|
|
||||||
* SIFS: Sifs, default is 10 us.
|
|
||||||
* PIFS: Pifs, default is 30 us.
|
|
||||||
*/
|
|
||||||
#define CSR18 0x0048
|
|
||||||
#define CSR18_SIFS FIELD32(0x0000ffff)
|
|
||||||
#define CSR18_PIFS FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR19: IFS timer register 1.
|
|
||||||
* DIFS: Difs, default is 50 us.
|
|
||||||
* EIFS: Eifs, default is 364 us.
|
|
||||||
*/
|
|
||||||
#define CSR19 0x004c
|
|
||||||
#define CSR19_DIFS FIELD32(0x0000ffff)
|
|
||||||
#define CSR19_EIFS FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR20: Wakeup timer register.
|
|
||||||
* DELAY_AFTER_TBCN: Delay after tbcn expired in units of 1/16 TU.
|
|
||||||
* TBCN_BEFORE_WAKEUP: Number of beacon before wakeup.
|
|
||||||
* AUTOWAKE: Enable auto wakeup / sleep mechanism.
|
|
||||||
*/
|
|
||||||
#define CSR20 0x0050
|
|
||||||
#define CSR20_DELAY_AFTER_TBCN FIELD32(0x0000ffff)
|
|
||||||
#define CSR20_TBCN_BEFORE_WAKEUP FIELD32(0x00ff0000)
|
|
||||||
#define CSR20_AUTOWAKE FIELD32(0x01000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR21: EEPROM control register.
|
|
||||||
* RELOAD: Write 1 to reload eeprom content.
|
|
||||||
* TYPE_93C46: 1: 93c46, 0:93c66.
|
|
||||||
*/
|
|
||||||
#define CSR21 0x0054
|
|
||||||
#define CSR21_RELOAD FIELD32(0x00000001)
|
|
||||||
#define CSR21_EEPROM_DATA_CLOCK FIELD32(0x00000002)
|
|
||||||
#define CSR21_EEPROM_CHIP_SELECT FIELD32(0x00000004)
|
|
||||||
#define CSR21_EEPROM_DATA_IN FIELD32(0x00000008)
|
|
||||||
#define CSR21_EEPROM_DATA_OUT FIELD32(0x00000010)
|
|
||||||
#define CSR21_TYPE_93C46 FIELD32(0x00000020)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CSR22: CFP control register.
|
|
||||||
* CFP_DURATION_REMAIN: Cfp duration remain, in units of TU.
|
|
||||||
* RELOAD_CFP_DURATION: Write 1 to reload cfp duration remain.
|
|
||||||
*/
|
|
||||||
#define CSR22 0x0058
|
|
||||||
#define CSR22_CFP_DURATION_REMAIN FIELD32(0x0000ffff)
|
|
||||||
#define CSR22_RELOAD_CFP_DURATION FIELD32(0x00010000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Transmit related CSRs.
|
|
||||||
* Some values are set in TU, whereas 1 TU == 1024 us.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXCSR0: TX Control Register.
|
|
||||||
* KICK_TX: Kick tx ring.
|
|
||||||
* KICK_ATIM: Kick atim ring.
|
|
||||||
* KICK_PRIO: Kick priority ring.
|
|
||||||
* ABORT: Abort all transmit related ring operation.
|
|
||||||
*/
|
|
||||||
#define TXCSR0 0x0060
|
|
||||||
#define TXCSR0_KICK_TX FIELD32(0x00000001)
|
|
||||||
#define TXCSR0_KICK_ATIM FIELD32(0x00000002)
|
|
||||||
#define TXCSR0_KICK_PRIO FIELD32(0x00000004)
|
|
||||||
#define TXCSR0_ABORT FIELD32(0x00000008)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXCSR1: TX Configuration Register.
|
|
||||||
* ACK_TIMEOUT: Ack timeout, default = sifs + 2*slottime + acktime @ 1mbps.
|
|
||||||
* ACK_CONSUME_TIME: Ack consume time, default = sifs + acktime @ 1mbps.
|
|
||||||
* TSF_OFFSET: Insert tsf offset.
|
|
||||||
* AUTORESPONDER: Enable auto responder which include ack & cts.
|
|
||||||
*/
|
|
||||||
#define TXCSR1 0x0064
|
|
||||||
#define TXCSR1_ACK_TIMEOUT FIELD32(0x000001ff)
|
|
||||||
#define TXCSR1_ACK_CONSUME_TIME FIELD32(0x0003fe00)
|
|
||||||
#define TXCSR1_TSF_OFFSET FIELD32(0x00fc0000)
|
|
||||||
#define TXCSR1_AUTORESPONDER FIELD32(0x01000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXCSR2: Tx descriptor configuration register.
|
|
||||||
* TXD_SIZE: Tx descriptor size, default is 48.
|
|
||||||
* NUM_TXD: Number of tx entries in ring.
|
|
||||||
* NUM_ATIM: Number of atim entries in ring.
|
|
||||||
* NUM_PRIO: Number of priority entries in ring.
|
|
||||||
*/
|
|
||||||
#define TXCSR2 0x0068
|
|
||||||
#define TXCSR2_TXD_SIZE FIELD32(0x000000ff)
|
|
||||||
#define TXCSR2_NUM_TXD FIELD32(0x0000ff00)
|
|
||||||
#define TXCSR2_NUM_ATIM FIELD32(0x00ff0000)
|
|
||||||
#define TXCSR2_NUM_PRIO FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXCSR3: TX Ring Base address register.
|
|
||||||
*/
|
|
||||||
#define TXCSR3 0x006c
|
|
||||||
#define TXCSR3_TX_RING_REGISTER FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXCSR4: TX Atim Ring Base address register.
|
|
||||||
*/
|
|
||||||
#define TXCSR4 0x0070
|
|
||||||
#define TXCSR4_ATIM_RING_REGISTER FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXCSR5: TX Prio Ring Base address register.
|
|
||||||
*/
|
|
||||||
#define TXCSR5 0x0074
|
|
||||||
#define TXCSR5_PRIO_RING_REGISTER FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXCSR6: Beacon Base address register.
|
|
||||||
*/
|
|
||||||
#define TXCSR6 0x0078
|
|
||||||
#define TXCSR6_BEACON_RING_REGISTER FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXCSR7: Auto responder control register.
|
|
||||||
* AR_POWERMANAGEMENT: Auto responder power management bit.
|
|
||||||
*/
|
|
||||||
#define TXCSR7 0x007c
|
|
||||||
#define TXCSR7_AR_POWERMANAGEMENT FIELD32(0x00000001)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Receive related CSRs.
|
|
||||||
* Some values are set in TU, whereas 1 TU == 1024 us.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RXCSR0: RX Control Register.
|
|
||||||
* DISABLE_RX: Disable rx engine.
|
|
||||||
* DROP_CRC: Drop crc error.
|
|
||||||
* DROP_PHYSICAL: Drop physical error.
|
|
||||||
* DROP_CONTROL: Drop control frame.
|
|
||||||
* DROP_NOT_TO_ME: Drop not to me unicast frame.
|
|
||||||
* DROP_TODS: Drop frame tods bit is true.
|
|
||||||
* DROP_VERSION_ERROR: Drop version error frame.
|
|
||||||
* PASS_CRC: Pass all packets with crc attached.
|
|
||||||
*/
|
|
||||||
#define RXCSR0 0x0080
|
|
||||||
#define RXCSR0_DISABLE_RX FIELD32(0x00000001)
|
|
||||||
#define RXCSR0_DROP_CRC FIELD32(0x00000002)
|
|
||||||
#define RXCSR0_DROP_PHYSICAL FIELD32(0x00000004)
|
|
||||||
#define RXCSR0_DROP_CONTROL FIELD32(0x00000008)
|
|
||||||
#define RXCSR0_DROP_NOT_TO_ME FIELD32(0x00000010)
|
|
||||||
#define RXCSR0_DROP_TODS FIELD32(0x00000020)
|
|
||||||
#define RXCSR0_DROP_VERSION_ERROR FIELD32(0x00000040)
|
|
||||||
#define RXCSR0_PASS_CRC FIELD32(0x00000080)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RXCSR1: RX descriptor configuration register.
|
|
||||||
* RXD_SIZE: Rx descriptor size, default is 32b.
|
|
||||||
* NUM_RXD: Number of rx entries in ring.
|
|
||||||
*/
|
|
||||||
#define RXCSR1 0x0084
|
|
||||||
#define RXCSR1_RXD_SIZE FIELD32(0x000000ff)
|
|
||||||
#define RXCSR1_NUM_RXD FIELD32(0x0000ff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RXCSR2: RX Ring base address register.
|
|
||||||
*/
|
|
||||||
#define RXCSR2 0x0088
|
|
||||||
#define RXCSR2_RX_RING_REGISTER FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RXCSR3: BBP ID register for Rx operation.
|
|
||||||
* BBP_ID#: BBP register # id.
|
|
||||||
* BBP_ID#_VALID: BBP register # id is valid or not.
|
|
||||||
*/
|
|
||||||
#define RXCSR3 0x0090
|
|
||||||
#define RXCSR3_BBP_ID0 FIELD32(0x0000007f)
|
|
||||||
#define RXCSR3_BBP_ID0_VALID FIELD32(0x00000080)
|
|
||||||
#define RXCSR3_BBP_ID1 FIELD32(0x00007f00)
|
|
||||||
#define RXCSR3_BBP_ID1_VALID FIELD32(0x00008000)
|
|
||||||
#define RXCSR3_BBP_ID2 FIELD32(0x007f0000)
|
|
||||||
#define RXCSR3_BBP_ID2_VALID FIELD32(0x00800000)
|
|
||||||
#define RXCSR3_BBP_ID3 FIELD32(0x7f000000)
|
|
||||||
#define RXCSR3_BBP_ID3_VALID FIELD32(0x80000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RXCSR4: BBP ID register for Rx operation.
|
|
||||||
* BBP_ID#: BBP register # id.
|
|
||||||
* BBP_ID#_VALID: BBP register # id is valid or not.
|
|
||||||
*/
|
|
||||||
#define RXCSR4 0x0094
|
|
||||||
#define RXCSR4_BBP_ID4 FIELD32(0x0000007f)
|
|
||||||
#define RXCSR4_BBP_ID4_VALID FIELD32(0x00000080)
|
|
||||||
#define RXCSR4_BBP_ID5 FIELD32(0x00007f00)
|
|
||||||
#define RXCSR4_BBP_ID5_VALID FIELD32(0x00008000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* ARCSR0: Auto Responder PLCP config register 0.
|
|
||||||
* ARCSR0_AR_BBP_DATA#: Auto responder BBP register # data.
|
|
||||||
* ARCSR0_AR_BBP_ID#: Auto responder BBP register # Id.
|
|
||||||
*/
|
|
||||||
#define ARCSR0 0x0098
|
|
||||||
#define ARCSR0_AR_BBP_DATA0 FIELD32(0x000000ff)
|
|
||||||
#define ARCSR0_AR_BBP_ID0 FIELD32(0x0000ff00)
|
|
||||||
#define ARCSR0_AR_BBP_DATA1 FIELD32(0x00ff0000)
|
|
||||||
#define ARCSR0_AR_BBP_ID1 FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* ARCSR1: Auto Responder PLCP config register 1.
|
|
||||||
* ARCSR0_AR_BBP_DATA#: Auto responder BBP register # data.
|
|
||||||
* ARCSR0_AR_BBP_ID#: Auto responder BBP register # Id.
|
|
||||||
*/
|
|
||||||
#define ARCSR1 0x009c
|
|
||||||
#define ARCSR1_AR_BBP_DATA2 FIELD32(0x000000ff)
|
|
||||||
#define ARCSR1_AR_BBP_ID2 FIELD32(0x0000ff00)
|
|
||||||
#define ARCSR1_AR_BBP_DATA3 FIELD32(0x00ff0000)
|
|
||||||
#define ARCSR1_AR_BBP_ID3 FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Miscellaneous Registers.
|
|
||||||
* Some values are set in TU, whereas 1 TU == 1024 us.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PCICSR: PCI control register.
|
|
||||||
* BIG_ENDIAN: 1: big endian, 0: little endian.
|
|
||||||
* RX_TRESHOLD: Rx threshold in dw to start pci access
|
|
||||||
* 0: 16dw (default), 1: 8dw, 2: 4dw, 3: 32dw.
|
|
||||||
* TX_TRESHOLD: Tx threshold in dw to start pci access
|
|
||||||
* 0: 0dw (default), 1: 1dw, 2: 4dw, 3: forward.
|
|
||||||
* BURST_LENTH: Pci burst length 0: 4dw (default, 1: 8dw, 2: 16dw, 3:32dw.
|
|
||||||
* ENABLE_CLK: Enable clk_run, pci clock can't going down to non-operational.
|
|
||||||
*/
|
|
||||||
#define PCICSR 0x008c
|
|
||||||
#define PCICSR_BIG_ENDIAN FIELD32(0x00000001)
|
|
||||||
#define PCICSR_RX_TRESHOLD FIELD32(0x00000006)
|
|
||||||
#define PCICSR_TX_TRESHOLD FIELD32(0x00000018)
|
|
||||||
#define PCICSR_BURST_LENTH FIELD32(0x00000060)
|
|
||||||
#define PCICSR_ENABLE_CLK FIELD32(0x00000080)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* CNT0: FCS error count.
|
|
||||||
* FCS_ERROR: FCS error count, cleared when read.
|
|
||||||
*/
|
|
||||||
#define CNT0 0x00a0
|
|
||||||
#define CNT0_FCS_ERROR FIELD32(0x0000ffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Statistic Register.
|
|
||||||
* CNT1: PLCP error count.
|
|
||||||
* CNT2: Long error count.
|
|
||||||
* CNT3: CCA false alarm count.
|
|
||||||
* CNT4: Rx FIFO overflow count.
|
|
||||||
* CNT5: Tx FIFO underrun count.
|
|
||||||
*/
|
|
||||||
#define TIMECSR2 0x00a8
|
|
||||||
#define CNT1 0x00ac
|
|
||||||
#define CNT2 0x00b0
|
|
||||||
#define TIMECSR3 0x00b4
|
|
||||||
#define CNT3 0x00b8
|
|
||||||
#define CNT4 0x00bc
|
|
||||||
#define CNT5 0x00c0
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Baseband Control Register.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PWRCSR0: Power mode configuration register.
|
|
||||||
*/
|
|
||||||
#define PWRCSR0 0x00c4
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Power state transition time registers.
|
|
||||||
*/
|
|
||||||
#define PSCSR0 0x00c8
|
|
||||||
#define PSCSR1 0x00cc
|
|
||||||
#define PSCSR2 0x00d0
|
|
||||||
#define PSCSR3 0x00d4
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PWRCSR1: Manual power control / status register.
|
|
||||||
* Allowed state: 0 deep_sleep, 1: sleep, 2: standby, 3: awake.
|
|
||||||
* SET_STATE: Set state. Write 1 to trigger, self cleared.
|
|
||||||
* BBP_DESIRE_STATE: BBP desired state.
|
|
||||||
* RF_DESIRE_STATE: RF desired state.
|
|
||||||
* BBP_CURR_STATE: BBP current state.
|
|
||||||
* RF_CURR_STATE: RF current state.
|
|
||||||
* PUT_TO_SLEEP: Put to sleep. Write 1 to trigger, self cleared.
|
|
||||||
*/
|
|
||||||
#define PWRCSR1 0x00d8
|
|
||||||
#define PWRCSR1_SET_STATE FIELD32(0x00000001)
|
|
||||||
#define PWRCSR1_BBP_DESIRE_STATE FIELD32(0x00000006)
|
|
||||||
#define PWRCSR1_RF_DESIRE_STATE FIELD32(0x00000018)
|
|
||||||
#define PWRCSR1_BBP_CURR_STATE FIELD32(0x00000060)
|
|
||||||
#define PWRCSR1_RF_CURR_STATE FIELD32(0x00000180)
|
|
||||||
#define PWRCSR1_PUT_TO_SLEEP FIELD32(0x00000200)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TIMECSR: Timer control register.
|
|
||||||
* US_COUNT: 1 us timer count in units of clock cycles.
|
|
||||||
* US_64_COUNT: 64 us timer count in units of 1 us timer.
|
|
||||||
* BEACON_EXPECT: Beacon expect window.
|
|
||||||
*/
|
|
||||||
#define TIMECSR 0x00dc
|
|
||||||
#define TIMECSR_US_COUNT FIELD32(0x000000ff)
|
|
||||||
#define TIMECSR_US_64_COUNT FIELD32(0x0000ff00)
|
|
||||||
#define TIMECSR_BEACON_EXPECT FIELD32(0x00070000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MACCSR0: MAC configuration register 0.
|
|
||||||
*/
|
|
||||||
#define MACCSR0 0x00e0
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MACCSR1: MAC configuration register 1.
|
|
||||||
* KICK_RX: Kick one-shot rx in one-shot rx mode.
|
|
||||||
* ONESHOT_RXMODE: Enable one-shot rx mode for debugging.
|
|
||||||
* BBPRX_RESET_MODE: Ralink bbp rx reset mode.
|
|
||||||
* AUTO_TXBBP: Auto tx logic access bbp control register.
|
|
||||||
* AUTO_RXBBP: Auto rx logic access bbp control register.
|
|
||||||
* LOOPBACK: Loopback mode. 0: normal, 1: internal, 2: external, 3:rsvd.
|
|
||||||
* INTERSIL_IF: Intersil if calibration pin.
|
|
||||||
*/
|
|
||||||
#define MACCSR1 0x00e4
|
|
||||||
#define MACCSR1_KICK_RX FIELD32(0x00000001)
|
|
||||||
#define MACCSR1_ONESHOT_RXMODE FIELD32(0x00000002)
|
|
||||||
#define MACCSR1_BBPRX_RESET_MODE FIELD32(0x00000004)
|
|
||||||
#define MACCSR1_AUTO_TXBBP FIELD32(0x00000008)
|
|
||||||
#define MACCSR1_AUTO_RXBBP FIELD32(0x00000010)
|
|
||||||
#define MACCSR1_LOOPBACK FIELD32(0x00000060)
|
|
||||||
#define MACCSR1_INTERSIL_IF FIELD32(0x00000080)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RALINKCSR: Ralink Rx auto-reset BBCR.
|
|
||||||
* AR_BBP_DATA#: Auto reset BBP register # data.
|
|
||||||
* AR_BBP_ID#: Auto reset BBP register # id.
|
|
||||||
*/
|
|
||||||
#define RALINKCSR 0x00e8
|
|
||||||
#define RALINKCSR_AR_BBP_DATA0 FIELD32(0x000000ff)
|
|
||||||
#define RALINKCSR_AR_BBP_ID0 FIELD32(0x0000ff00)
|
|
||||||
#define RALINKCSR_AR_BBP_DATA1 FIELD32(0x00ff0000)
|
|
||||||
#define RALINKCSR_AR_BBP_ID1 FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* BCNCSR: Beacon interval control register.
|
|
||||||
* CHANGE: Write one to change beacon interval.
|
|
||||||
* DELTATIME: The delta time value.
|
|
||||||
* NUM_BEACON: Number of beacon according to mode.
|
|
||||||
* MODE: Please refer to asic specs.
|
|
||||||
* PLUS: Plus or minus delta time value.
|
|
||||||
*/
|
|
||||||
#define BCNCSR 0x00ec
|
|
||||||
#define BCNCSR_CHANGE FIELD32(0x00000001)
|
|
||||||
#define BCNCSR_DELTATIME FIELD32(0x0000001e)
|
|
||||||
#define BCNCSR_NUM_BEACON FIELD32(0x00001fe0)
|
|
||||||
#define BCNCSR_MODE FIELD32(0x00006000)
|
|
||||||
#define BCNCSR_PLUS FIELD32(0x00008000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* BBP / RF / IF Control Register.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* BBPCSR: BBP serial control register.
|
|
||||||
* VALUE: Register value to program into BBP.
|
|
||||||
* REGNUM: Selected BBP register.
|
|
||||||
* BUSY: 1: asic is busy execute BBP programming.
|
|
||||||
* WRITE_CONTROL: 1: write BBP, 0: read BBP.
|
|
||||||
*/
|
|
||||||
#define BBPCSR 0x00f0
|
|
||||||
#define BBPCSR_VALUE FIELD32(0x000000ff)
|
|
||||||
#define BBPCSR_REGNUM FIELD32(0x00007f00)
|
|
||||||
#define BBPCSR_BUSY FIELD32(0x00008000)
|
|
||||||
#define BBPCSR_WRITE_CONTROL FIELD32(0x00010000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RFCSR: RF serial control register.
|
|
||||||
* VALUE: Register value + id to program into rf/if.
|
|
||||||
* NUMBER_OF_BITS: Number of bits used in value (i:20, rfmd:22).
|
|
||||||
* IF_SELECT: Chip to program: 0: rf, 1: if.
|
|
||||||
* PLL_LD: Rf pll_ld status.
|
|
||||||
* BUSY: 1: asic is busy execute rf programming.
|
|
||||||
*/
|
|
||||||
#define RFCSR 0x00f4
|
|
||||||
#define RFCSR_VALUE FIELD32(0x00ffffff)
|
|
||||||
#define RFCSR_NUMBER_OF_BITS FIELD32(0x1f000000)
|
|
||||||
#define RFCSR_IF_SELECT FIELD32(0x20000000)
|
|
||||||
#define RFCSR_PLL_LD FIELD32(0x40000000)
|
|
||||||
#define RFCSR_BUSY FIELD32(0x80000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* LEDCSR: LED control register.
|
|
||||||
* ON_PERIOD: On period, default 70ms.
|
|
||||||
* OFF_PERIOD: Off period, default 30ms.
|
|
||||||
* LINK: 0: linkoff, 1: linkup.
|
|
||||||
* ACTIVITY: 0: idle, 1: active.
|
|
||||||
*/
|
|
||||||
#define LEDCSR 0x00f8
|
|
||||||
#define LEDCSR_ON_PERIOD FIELD32(0x000000ff)
|
|
||||||
#define LEDCSR_OFF_PERIOD FIELD32(0x0000ff00)
|
|
||||||
#define LEDCSR_LINK FIELD32(0x00010000)
|
|
||||||
#define LEDCSR_ACTIVITY FIELD32(0x00020000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* ASIC pointer information.
|
|
||||||
* RXPTR: Current RX ring address.
|
|
||||||
* TXPTR: Current Tx ring address.
|
|
||||||
* PRIPTR: Current Priority ring address.
|
|
||||||
* ATIMPTR: Current ATIM ring address.
|
|
||||||
*/
|
|
||||||
#define RXPTR 0x0100
|
|
||||||
#define TXPTR 0x0104
|
|
||||||
#define PRIPTR 0x0108
|
|
||||||
#define ATIMPTR 0x010c
|
|
||||||
|
|
||||||
/*
|
|
||||||
* GPIO and others.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* GPIOCSR: GPIO control register.
|
|
||||||
*/
|
|
||||||
#define GPIOCSR 0x0120
|
|
||||||
#define GPIOCSR_BIT0 FIELD32(0x00000001)
|
|
||||||
#define GPIOCSR_BIT1 FIELD32(0x00000002)
|
|
||||||
#define GPIOCSR_BIT2 FIELD32(0x00000004)
|
|
||||||
#define GPIOCSR_BIT3 FIELD32(0x00000008)
|
|
||||||
#define GPIOCSR_BIT4 FIELD32(0x00000010)
|
|
||||||
#define GPIOCSR_BIT5 FIELD32(0x00000020)
|
|
||||||
#define GPIOCSR_BIT6 FIELD32(0x00000040)
|
|
||||||
#define GPIOCSR_BIT7 FIELD32(0x00000080)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* BBPPCSR: BBP Pin control register.
|
|
||||||
*/
|
|
||||||
#define BBPPCSR 0x0124
|
|
||||||
|
|
||||||
/*
|
|
||||||
* BCNCSR1: Tx BEACON offset time control register.
|
|
||||||
* PRELOAD: Beacon timer offset in units of usec.
|
|
||||||
*/
|
|
||||||
#define BCNCSR1 0x0130
|
|
||||||
#define BCNCSR1_PRELOAD FIELD32(0x0000ffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MACCSR2: TX_PE to RX_PE turn-around time control register
|
|
||||||
* DELAY: RX_PE low width, in units of pci clock cycle.
|
|
||||||
*/
|
|
||||||
#define MACCSR2 0x0134
|
|
||||||
#define MACCSR2_DELAY FIELD32(0x000000ff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* ARCSR2: 1 Mbps ACK/CTS PLCP.
|
|
||||||
*/
|
|
||||||
#define ARCSR2 0x013c
|
|
||||||
#define ARCSR2_SIGNAL FIELD32(0x000000ff)
|
|
||||||
#define ARCSR2_SERVICE FIELD32(0x0000ff00)
|
|
||||||
#define ARCSR2_LENGTH_LOW FIELD32(0x00ff0000)
|
|
||||||
#define ARCSR2_LENGTH FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* ARCSR3: 2 Mbps ACK/CTS PLCP.
|
|
||||||
*/
|
|
||||||
#define ARCSR3 0x0140
|
|
||||||
#define ARCSR3_SIGNAL FIELD32(0x000000ff)
|
|
||||||
#define ARCSR3_SERVICE FIELD32(0x0000ff00)
|
|
||||||
#define ARCSR3_LENGTH FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* ARCSR4: 5.5 Mbps ACK/CTS PLCP.
|
|
||||||
*/
|
|
||||||
#define ARCSR4 0x0144
|
|
||||||
#define ARCSR4_SIGNAL FIELD32(0x000000ff)
|
|
||||||
#define ARCSR4_SERVICE FIELD32(0x0000ff00)
|
|
||||||
#define ARCSR4_LENGTH FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* ARCSR5: 11 Mbps ACK/CTS PLCP.
|
|
||||||
*/
|
|
||||||
#define ARCSR5 0x0148
|
|
||||||
#define ARCSR5_SIGNAL FIELD32(0x000000ff)
|
|
||||||
#define ARCSR5_SERVICE FIELD32(0x0000ff00)
|
|
||||||
#define ARCSR5_LENGTH FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* BBP registers.
|
|
||||||
* The wordsize of the BBP is 8 bits.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* R1: TX antenna control
|
|
||||||
*/
|
|
||||||
#define BBP_R1_TX_ANTENNA FIELD8(0x03)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* R4: RX antenna control
|
|
||||||
*/
|
|
||||||
#define BBP_R4_RX_ANTENNA FIELD8(0x06)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RF registers
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RF 1
|
|
||||||
*/
|
|
||||||
#define RF1_TUNER FIELD32(0x00020000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RF 3
|
|
||||||
*/
|
|
||||||
#define RF3_TUNER FIELD32(0x00000100)
|
|
||||||
#define RF3_TXPOWER FIELD32(0x00003e00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM content.
|
|
||||||
* The wordsize of the EEPROM is 16 bits.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* HW MAC address.
|
|
||||||
*/
|
|
||||||
#define EEPROM_MAC_ADDR_0 0x0002
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE0 FIELD16(0x00ff)
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE1 FIELD16(0xff00)
|
|
||||||
#define EEPROM_MAC_ADDR1 0x0003
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE2 FIELD16(0x00ff)
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE3 FIELD16(0xff00)
|
|
||||||
#define EEPROM_MAC_ADDR_2 0x0004
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE4 FIELD16(0x00ff)
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE5 FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM antenna.
|
|
||||||
* ANTENNA_NUM: Number of antenna's.
|
|
||||||
* TX_DEFAULT: Default antenna 0: diversity, 1: A, 2: B.
|
|
||||||
* RX_DEFAULT: Default antenna 0: diversity, 1: A, 2: B.
|
|
||||||
* RF_TYPE: Rf_type of this adapter.
|
|
||||||
* LED_MODE: 0: default, 1: TX/RX activity,2: Single (ignore link), 3: rsvd.
|
|
||||||
* RX_AGCVGC: 0: disable, 1:enable BBP R13 tuning.
|
|
||||||
* HARDWARE_RADIO: 1: Hardware controlled radio. Read GPIO0.
|
|
||||||
*/
|
|
||||||
#define EEPROM_ANTENNA 0x0b
|
|
||||||
#define EEPROM_ANTENNA_NUM FIELD16(0x0003)
|
|
||||||
#define EEPROM_ANTENNA_TX_DEFAULT FIELD16(0x000c)
|
|
||||||
#define EEPROM_ANTENNA_RX_DEFAULT FIELD16(0x0030)
|
|
||||||
#define EEPROM_ANTENNA_RF_TYPE FIELD16(0x0040)
|
|
||||||
#define EEPROM_ANTENNA_LED_MODE FIELD16(0x0180)
|
|
||||||
#define EEPROM_ANTENNA_RX_AGCVGC_TUNING FIELD16(0x0200)
|
|
||||||
#define EEPROM_ANTENNA_HARDWARE_RADIO FIELD16(0x0400)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM BBP.
|
|
||||||
*/
|
|
||||||
#define EEPROM_BBP_START 0x0c
|
|
||||||
#define EEPROM_BBP_SIZE 7
|
|
||||||
#define EEPROM_BBP_VALUE FIELD16(0x00ff)
|
|
||||||
#define EEPROM_BBP_REG_ID FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM TXPOWER
|
|
||||||
*/
|
|
||||||
#define EEPROM_TXPOWER_START 0x13
|
|
||||||
#define EEPROM_TXPOWER_SIZE 7
|
|
||||||
#define EEPROM_TXPOWER_1 FIELD16(0x00ff)
|
|
||||||
#define EEPROM_TXPOWER_2 FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* DMA descriptor defines.
|
|
||||||
*/
|
|
||||||
#define TXD_DESC_SIZE ( 8 * sizeof(struct data_desc) )
|
|
||||||
#define RXD_DESC_SIZE ( 8 * sizeof(struct data_desc) )
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX descriptor format for TX, PRIO, ATIM and Beacon Ring.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word0
|
|
||||||
*/
|
|
||||||
#define TXD_W0_OWNER_NIC FIELD32(0x00000001)
|
|
||||||
#define TXD_W0_VALID FIELD32(0x00000002)
|
|
||||||
#define TXD_W0_RESULT FIELD32(0x0000001c)
|
|
||||||
#define TXD_W0_RETRY_COUNT FIELD32(0x000000e0)
|
|
||||||
#define TXD_W0_MORE_FRAG FIELD32(0x00000100)
|
|
||||||
#define TXD_W0_ACK FIELD32(0x00000200)
|
|
||||||
#define TXD_W0_TIMESTAMP FIELD32(0x00000400)
|
|
||||||
#define TXD_W0_RTS FIELD32(0x00000800)
|
|
||||||
#define TXD_W0_IFS FIELD32(0x00006000)
|
|
||||||
#define TXD_W0_RETRY_MODE FIELD32(0x00008000)
|
|
||||||
#define TXD_W0_AGC FIELD32(0x00ff0000)
|
|
||||||
#define TXD_W0_R2 FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word1
|
|
||||||
*/
|
|
||||||
#define TXD_W1_BUFFER_ADDRESS FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word2
|
|
||||||
*/
|
|
||||||
#define TXD_W2_BUFFER_LENGTH FIELD32(0x0000ffff)
|
|
||||||
#define TXD_W2_DATABYTE_COUNT FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word3 & 4: PLCP information
|
|
||||||
*/
|
|
||||||
#define TXD_W3_PLCP_SIGNAL FIELD32(0x0000ffff)
|
|
||||||
#define TXD_W3_PLCP_SERVICE FIELD32(0xffff0000)
|
|
||||||
#define TXD_W4_PLCP_LENGTH_LOW FIELD32(0x0000ffff)
|
|
||||||
#define TXD_W4_PLCP_LENGTH_HIGH FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word5
|
|
||||||
*/
|
|
||||||
#define TXD_W5_BBCR4 FIELD32(0x0000ffff)
|
|
||||||
#define TXD_W5_AGC_REG FIELD32(0x007f0000)
|
|
||||||
#define TXD_W5_AGC_REG_VALID FIELD32(0x00800000)
|
|
||||||
#define TXD_W5_XXX_REG FIELD32(0x7f000000)
|
|
||||||
#define TXD_W5_XXX_REG_VALID FIELD32(0x80000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word6
|
|
||||||
*/
|
|
||||||
#define TXD_W6_SK_BUFF FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word7
|
|
||||||
*/
|
|
||||||
#define TXD_W7_RESERVED FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RX descriptor format for RX Ring.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word0
|
|
||||||
*/
|
|
||||||
#define RXD_W0_OWNER_NIC FIELD32(0x00000001)
|
|
||||||
#define RXD_W0_UNICAST_TO_ME FIELD32(0x00000002)
|
|
||||||
#define RXD_W0_MULTICAST FIELD32(0x00000004)
|
|
||||||
#define RXD_W0_BROADCAST FIELD32(0x00000008)
|
|
||||||
#define RXD_W0_MY_BSS FIELD32(0x00000010)
|
|
||||||
#define RXD_W0_CRC_ERROR FIELD32(0x00000020)
|
|
||||||
#define RXD_W0_PHYSICAL_ERROR FIELD32(0x00000080)
|
|
||||||
#define RXD_W0_DATABYTE_COUNT FIELD32(0xffff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word1
|
|
||||||
*/
|
|
||||||
#define RXD_W1_BUFFER_ADDRESS FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word2
|
|
||||||
*/
|
|
||||||
#define RXD_W2_BUFFER_LENGTH FIELD32(0x0000ffff)
|
|
||||||
#define RXD_W2_SIGNAL FIELD32(0x00ff0000)
|
|
||||||
#define RXD_W2_RSSI FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word3
|
|
||||||
*/
|
|
||||||
#define RXD_W3_BBR2 FIELD32(0x000000ff)
|
|
||||||
#define RXD_W3_BBR3 FIELD32(0x0000ff00)
|
|
||||||
#define RXD_W3_BBR4 FIELD32(0x00ff0000)
|
|
||||||
#define RXD_W3_BBR5 FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word4
|
|
||||||
*/
|
|
||||||
#define RXD_W4_RX_END_TIME FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word5 & 6 & 7: Reserved
|
|
||||||
*/
|
|
||||||
#define RXD_W5_RESERVED FIELD32(0xffffffff)
|
|
||||||
#define RXD_W6_RESERVED FIELD32(0xffffffff)
|
|
||||||
#define RXD_W7_RESERVED FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Macro's for converting txpower from EEPROM to dscape value
|
|
||||||
* and from dscape value to register value.
|
|
||||||
* NOTE: Logics in rt2400pci for txpower are reversed
|
|
||||||
* compared to the other rt2x00 drivers. A higher txpower
|
|
||||||
* value means that the txpower must be lowered. This is
|
|
||||||
* important when converting the value coming from the
|
|
||||||
* dscape stack to the rt2400 acceptable value.
|
|
||||||
*/
|
|
||||||
#define MIN_TXPOWER 31
|
|
||||||
#define MAX_TXPOWER 62
|
|
||||||
#define DEFAULT_TXPOWER 39
|
|
||||||
|
|
||||||
#define TXPOWER_FROM_DEV(__txpower) \
|
|
||||||
({ \
|
|
||||||
((__txpower) > MAX_TXPOWER) ? DEFAULT_TXPOWER - MIN_TXPOWER : \
|
|
||||||
((__txpower) < MIN_TXPOWER) ? DEFAULT_TXPOWER - MIN_TXPOWER : \
|
|
||||||
(((__txpower) - MAX_TXPOWER) + MIN_TXPOWER); \
|
|
||||||
})
|
|
||||||
|
|
||||||
#define TXPOWER_TO_DEV(__txpower) \
|
|
||||||
({ \
|
|
||||||
(__txpower) += MIN_TXPOWER; \
|
|
||||||
((__txpower) <= MIN_TXPOWER) ? MAX_TXPOWER : \
|
|
||||||
(((__txpower) >= MAX_TXPOWER) ? MIN_TXPOWER : \
|
|
||||||
(MAX_TXPOWER - ((__txpower) - MIN_TXPOWER))); \
|
|
||||||
})
|
|
||||||
|
|
||||||
#endif /* RT2400PCI_H */
|
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -1,798 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2500usb
|
|
||||||
Abstract: Data structures and registers for the rt2500usb module.
|
|
||||||
Supported chipsets: RT2570.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2500USB_H
|
|
||||||
#define RT2500USB_H
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RF chip defines.
|
|
||||||
*/
|
|
||||||
#define RF2522 0x0000
|
|
||||||
#define RF2523 0x0001
|
|
||||||
#define RF2524 0x0002
|
|
||||||
#define RF2525 0x0003
|
|
||||||
#define RF2525E 0x0005
|
|
||||||
#define RF5222 0x0010
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RT2570 version
|
|
||||||
*/
|
|
||||||
#define RT2570_VERSION_B 2
|
|
||||||
#define RT2570_VERSION_C 3
|
|
||||||
#define RT2570_VERSION_D 4
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Signal information.
|
|
||||||
* Defaul offset is required for RSSI <-> dBm conversion.
|
|
||||||
*/
|
|
||||||
#define MAX_SIGNAL 100
|
|
||||||
#define MAX_RX_SSI -1
|
|
||||||
#define DEFAULT_RSSI_OFFSET 120
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Register layout information.
|
|
||||||
*/
|
|
||||||
#define CSR_REG_BASE 0x0400
|
|
||||||
#define CSR_REG_SIZE 0x0100
|
|
||||||
#define EEPROM_BASE 0x0000
|
|
||||||
#define EEPROM_SIZE 0x006a
|
|
||||||
#define BBP_SIZE 0x0060
|
|
||||||
#define RF_SIZE 0x0014
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Control/Status Registers(CSR).
|
|
||||||
* Some values are set in TU, whereas 1 TU == 1024 us.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR0: ASIC revision number.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR0 0x0400
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR1: System control.
|
|
||||||
* SOFT_RESET: Software reset, 1: reset, 0: normal.
|
|
||||||
* BBP_RESET: Hardware reset, 1: reset, 0, release.
|
|
||||||
* HOST_READY: Host ready after initialization.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR1 0x0402
|
|
||||||
#define MAC_CSR1_SOFT_RESET FIELD16(0x00000001)
|
|
||||||
#define MAC_CSR1_BBP_RESET FIELD16(0x00000002)
|
|
||||||
#define MAC_CSR1_HOST_READY FIELD16(0x00000004)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR2: STA MAC register 0.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR2 0x0404
|
|
||||||
#define MAC_CSR2_BYTE0 FIELD16(0x00ff)
|
|
||||||
#define MAC_CSR2_BYTE1 FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR3: STA MAC register 1.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR3 0x0406
|
|
||||||
#define MAC_CSR3_BYTE2 FIELD16(0x00ff)
|
|
||||||
#define MAC_CSR3_BYTE3 FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR4: STA MAC register 2.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR4 0X0408
|
|
||||||
#define MAC_CSR4_BYTE4 FIELD16(0x00ff)
|
|
||||||
#define MAC_CSR4_BYTE5 FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR5: BSSID register 0.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR5 0x040a
|
|
||||||
#define MAC_CSR5_BYTE0 FIELD16(0x00ff)
|
|
||||||
#define MAC_CSR5_BYTE1 FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR6: BSSID register 1.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR6 0x040c
|
|
||||||
#define MAC_CSR6_BYTE2 FIELD16(0x00ff)
|
|
||||||
#define MAC_CSR6_BYTE3 FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR7: BSSID register 2.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR7 0x040e
|
|
||||||
#define MAC_CSR7_BYTE4 FIELD16(0x00ff)
|
|
||||||
#define MAC_CSR7_BYTE5 FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR8: Max frame length.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR8 0x0410
|
|
||||||
#define MAC_CSR8_MAX_FRAME_UNIT FIELD16(0x0fff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Misc MAC_CSR registers.
|
|
||||||
* MAC_CSR9: Timer control.
|
|
||||||
* MAC_CSR10: Slot time.
|
|
||||||
* MAC_CSR11: IFS.
|
|
||||||
* MAC_CSR12: EIFS.
|
|
||||||
* MAC_CSR13: Power mode0.
|
|
||||||
* MAC_CSR14: Power mode1.
|
|
||||||
* MAC_CSR15: Power saving transition0
|
|
||||||
* MAC_CSR16: Power saving transition1
|
|
||||||
*/
|
|
||||||
#define MAC_CSR9 0x0412
|
|
||||||
#define MAC_CSR10 0x0414
|
|
||||||
#define MAC_CSR11 0x0416
|
|
||||||
#define MAC_CSR12 0x0418
|
|
||||||
#define MAC_CSR13 0x041a
|
|
||||||
#define MAC_CSR14 0x041c
|
|
||||||
#define MAC_CSR15 0x041e
|
|
||||||
#define MAC_CSR16 0x0420
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR17: Manual power control / status register.
|
|
||||||
* Allowed state: 0 deep_sleep, 1: sleep, 2: standby, 3: awake.
|
|
||||||
* SET_STATE: Set state. Write 1 to trigger, self cleared.
|
|
||||||
* BBP_DESIRE_STATE: BBP desired state.
|
|
||||||
* RF_DESIRE_STATE: RF desired state.
|
|
||||||
* BBP_CURRENT_STATE: BBP current state.
|
|
||||||
* RF_CURRENT_STATE: RF current state.
|
|
||||||
* PUT_TO_SLEEP: Put to sleep. Write 1 to trigger, self cleared.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR17 0x0422
|
|
||||||
#define MAC_CSR17_SET_STATE FIELD16(0x0001)
|
|
||||||
#define MAC_CSR17_BBP_DESIRE_STATE FIELD16(0x0006)
|
|
||||||
#define MAC_CSR17_RF_DESIRE_STATE FIELD16(0x0018)
|
|
||||||
#define MAC_CSR17_BBP_CURR_STATE FIELD16(0x0060)
|
|
||||||
#define MAC_CSR17_RF_CURR_STATE FIELD16(0x0180)
|
|
||||||
#define MAC_CSR17_PUT_TO_SLEEP FIELD16(0x0200)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR18: Wakeup timer register.
|
|
||||||
* DELAY_AFTER_BEACON: Delay after Tbcn expired in units of 1/16 TU.
|
|
||||||
* BEACONS_BEFORE_WAKEUP: Number of beacon before wakeup.
|
|
||||||
* AUTO_WAKE: Enable auto wakeup / sleep mechanism.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR18 0x0424
|
|
||||||
#define MAC_CSR18_DELAY_AFTER_BEACON FIELD16(0x00ff)
|
|
||||||
#define MAC_CSR18_BEACONS_BEFORE_WAKEUP FIELD16(0x7f00)
|
|
||||||
#define MAC_CSR18_AUTO_WAKE FIELD16(0x8000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR19: GPIO control register.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR19 0x0426
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR20: LED control register.
|
|
||||||
* ACTIVITY: 0: idle, 1: active.
|
|
||||||
* LINK: 0: linkoff, 1: linkup.
|
|
||||||
* ACTIVITY_POLARITY: 0: active low, 1: active high.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR20 0x0428
|
|
||||||
#define MAC_CSR20_ACTIVITY FIELD16(0x0001)
|
|
||||||
#define MAC_CSR20_LINK FIELD16(0x0002)
|
|
||||||
#define MAC_CSR20_ACTIVITY_POLARITY FIELD16(0x0004)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC_CSR21: LED control register.
|
|
||||||
* ON_PERIOD: On period, default 70ms.
|
|
||||||
* OFF_PERIOD: Off period, default 30ms.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR21 0x042a
|
|
||||||
#define MAC_CSR21_ON_PERIOD FIELD16(0x00ff)
|
|
||||||
#define MAC_CSR21_OFF_PERIOD FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Collision window control register.
|
|
||||||
*/
|
|
||||||
#define MAC_CSR22 0x042c
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Transmit related CSRs.
|
|
||||||
* Some values are set in TU, whereas 1 TU == 1024 us.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR0: Security control register.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR0 0x0440
|
|
||||||
#define TXRX_CSR0_ALGORITHM FIELD16(0x0007)
|
|
||||||
#define TXRX_CSR0_IV_OFFSET FIELD16(0x01f8)
|
|
||||||
#define TXRX_CSR0_KEY_ID FIELD16(0x1e00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR1: TX configuration.
|
|
||||||
* ACK_TIMEOUT: ACK Timeout in unit of 1-us.
|
|
||||||
* TSF_OFFSET: TSF offset in MAC header.
|
|
||||||
* AUTO_SEQUENCE: Let ASIC control frame sequence number.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR1 0x0442
|
|
||||||
#define TXRX_CSR1_ACK_TIMEOUT FIELD16(0x00ff)
|
|
||||||
#define TXRX_CSR1_TSF_OFFSET FIELD16(0x7f00)
|
|
||||||
#define TXRX_CSR1_AUTO_SEQUENCE FIELD16(0x8000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR2: RX control.
|
|
||||||
* DISABLE_RX: Disable rx engine.
|
|
||||||
* DROP_CRC: Drop crc error.
|
|
||||||
* DROP_PHYSICAL: Drop physical error.
|
|
||||||
* DROP_CONTROL: Drop control frame.
|
|
||||||
* DROP_NOT_TO_ME: Drop not to me unicast frame.
|
|
||||||
* DROP_TODS: Drop frame tods bit is true.
|
|
||||||
* DROP_VERSION_ERROR: Drop version error frame.
|
|
||||||
* DROP_MCAST: Drop multicast frames.
|
|
||||||
* DROP_BCAST: Drop broadcast frames.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR2 0x0444
|
|
||||||
#define TXRX_CSR2_DISABLE_RX FIELD16(0x0001)
|
|
||||||
#define TXRX_CSR2_DROP_CRC FIELD16(0x0002)
|
|
||||||
#define TXRX_CSR2_DROP_PHYSICAL FIELD16(0x0004)
|
|
||||||
#define TXRX_CSR2_DROP_CONTROL FIELD16(0x0008)
|
|
||||||
#define TXRX_CSR2_DROP_NOT_TO_ME FIELD16(0x0010)
|
|
||||||
#define TXRX_CSR2_DROP_TODS FIELD16(0x0020)
|
|
||||||
#define TXRX_CSR2_DROP_VERSION_ERROR FIELD16(0x0040)
|
|
||||||
#define TXRX_CSR2_DROP_MULTICAST FIELD16(0x0200)
|
|
||||||
#define TXRX_CSR2_DROP_BROADCAST FIELD16(0x0400)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RX BBP ID registers
|
|
||||||
* TXRX_CSR3: CCK RX BBP ID.
|
|
||||||
* TXRX_CSR4: OFDM RX BBP ID.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR3 0x0446
|
|
||||||
#define TXRX_CSR4 0x0448
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR5: CCK TX BBP ID0.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR5 0x044a
|
|
||||||
#define TXRX_CSR5_BBP_ID0 FIELD16(0x007f)
|
|
||||||
#define TXRX_CSR5_BBP_ID0_VALID FIELD16(0x0080)
|
|
||||||
#define TXRX_CSR5_BBP_ID1 FIELD16(0x7f00)
|
|
||||||
#define TXRX_CSR5_BBP_ID1_VALID FIELD16(0x8000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR6: CCK TX BBP ID1.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR6 0x044c
|
|
||||||
#define TXRX_CSR6_BBP_ID0 FIELD16(0x007f)
|
|
||||||
#define TXRX_CSR6_BBP_ID0_VALID FIELD16(0x0080)
|
|
||||||
#define TXRX_CSR6_BBP_ID1 FIELD16(0x7f00)
|
|
||||||
#define TXRX_CSR6_BBP_ID1_VALID FIELD16(0x8000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR7: OFDM TX BBP ID0.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR7 0x044e
|
|
||||||
#define TXRX_CSR7_BBP_ID0 FIELD16(0x007f)
|
|
||||||
#define TXRX_CSR7_BBP_ID0_VALID FIELD16(0x0080)
|
|
||||||
#define TXRX_CSR7_BBP_ID1 FIELD16(0x7f00)
|
|
||||||
#define TXRX_CSR7_BBP_ID1_VALID FIELD16(0x8000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR5: OFDM TX BBP ID1.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR8 0x0450
|
|
||||||
#define TXRX_CSR8_BBP_ID0 FIELD16(0x007f)
|
|
||||||
#define TXRX_CSR8_BBP_ID0_VALID FIELD16(0x0080)
|
|
||||||
#define TXRX_CSR8_BBP_ID1 FIELD16(0x7f00)
|
|
||||||
#define TXRX_CSR8_BBP_ID1_VALID FIELD16(0x8000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR9: TX ACK time-out.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR9 0x0452
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR10: Auto responder control.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR10 0x0454
|
|
||||||
#define TXRX_CSR10_AUTORESPOND_PREAMBLE FIELD16(0x0004)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR11: Auto responder basic rate.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR11 0x0456
|
|
||||||
|
|
||||||
/*
|
|
||||||
* ACK/CTS time registers.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR12 0x0458
|
|
||||||
#define TXRX_CSR13 0x045a
|
|
||||||
#define TXRX_CSR14 0x045c
|
|
||||||
#define TXRX_CSR15 0x045e
|
|
||||||
#define TXRX_CSR16 0x0460
|
|
||||||
#define TXRX_CSR17 0x0462
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR18: Synchronization control register.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR18 0x0464
|
|
||||||
#define TXRX_CSR18_OFFSET FIELD16(0x000f)
|
|
||||||
#define TXRX_CSR18_INTERVAL FIELD16(0xfff0)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR19: Synchronization control register.
|
|
||||||
* TSF_COUNT: Enable TSF auto counting.
|
|
||||||
* TSF_SYNC: Tsf sync, 0: disable, 1: infra, 2: ad-hoc/master mode.
|
|
||||||
* TBCN: Enable Tbcn with reload value.
|
|
||||||
* BEACON_GEN: Enable beacon generator.
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR19 0x0466
|
|
||||||
#define TXRX_CSR19_TSF_COUNT FIELD16(0x0001)
|
|
||||||
#define TXRX_CSR19_TSF_SYNC FIELD16(0x0006)
|
|
||||||
#define TXRX_CSR19_TBCN FIELD16(0x0008)
|
|
||||||
#define TXRX_CSR19_BEACON_GEN FIELD16(0x0010)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR20: Tx BEACON offset time control register.
|
|
||||||
* OFFSET: In units of usec.
|
|
||||||
* BCN_EXPECT_WINDOW: Default: 2^CWmin
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR20 0x0468
|
|
||||||
#define TXRX_CSR20_OFFSET FIELD16(0x1fff)
|
|
||||||
#define TXRX_CSR20_BCN_EXPECT_WINDOW FIELD16(0xe000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TXRX_CSR21
|
|
||||||
*/
|
|
||||||
#define TXRX_CSR21 0x046a
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Encryption related CSRs.
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* SEC_CSR0-SEC_CSR7: Shared key 0, word 0-7
|
|
||||||
*/
|
|
||||||
#define SEC_CSR0 0x0480
|
|
||||||
#define SEC_CSR1 0x0482
|
|
||||||
#define SEC_CSR2 0x0484
|
|
||||||
#define SEC_CSR3 0x0486
|
|
||||||
#define SEC_CSR4 0x0488
|
|
||||||
#define SEC_CSR5 0x048a
|
|
||||||
#define SEC_CSR6 0x048c
|
|
||||||
#define SEC_CSR7 0x048e
|
|
||||||
|
|
||||||
/*
|
|
||||||
* SEC_CSR8-SEC_CSR15: Shared key 1, word 0-7
|
|
||||||
*/
|
|
||||||
#define SEC_CSR8 0x0490
|
|
||||||
#define SEC_CSR9 0x0492
|
|
||||||
#define SEC_CSR10 0x0494
|
|
||||||
#define SEC_CSR11 0x0496
|
|
||||||
#define SEC_CSR12 0x0498
|
|
||||||
#define SEC_CSR13 0x049a
|
|
||||||
#define SEC_CSR14 0x049c
|
|
||||||
#define SEC_CSR15 0x049e
|
|
||||||
|
|
||||||
/*
|
|
||||||
* SEC_CSR16-SEC_CSR23: Shared key 2, word 0-7
|
|
||||||
*/
|
|
||||||
#define SEC_CSR16 0x04a0
|
|
||||||
#define SEC_CSR17 0x04a2
|
|
||||||
#define SEC_CSR18 0X04A4
|
|
||||||
#define SEC_CSR19 0x04a6
|
|
||||||
#define SEC_CSR20 0x04a8
|
|
||||||
#define SEC_CSR21 0x04aa
|
|
||||||
#define SEC_CSR22 0x04ac
|
|
||||||
#define SEC_CSR23 0x04ae
|
|
||||||
|
|
||||||
/*
|
|
||||||
* SEC_CSR24-SEC_CSR31: Shared key 3, word 0-7
|
|
||||||
*/
|
|
||||||
#define SEC_CSR24 0x04b0
|
|
||||||
#define SEC_CSR25 0x04b2
|
|
||||||
#define SEC_CSR26 0x04b4
|
|
||||||
#define SEC_CSR27 0x04b6
|
|
||||||
#define SEC_CSR28 0x04b8
|
|
||||||
#define SEC_CSR29 0x04ba
|
|
||||||
#define SEC_CSR30 0x04bc
|
|
||||||
#define SEC_CSR31 0x04be
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PHY control registers.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PHY_CSR0: RF switching timing control.
|
|
||||||
*/
|
|
||||||
#define PHY_CSR0 0x04c0
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PHY_CSR1: TX PA configuration.
|
|
||||||
*/
|
|
||||||
#define PHY_CSR1 0x04c2
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC configuration registers.
|
|
||||||
* PHY_CSR2: TX MAC configuration.
|
|
||||||
* PHY_CSR3: RX MAC configuration.
|
|
||||||
*/
|
|
||||||
#define PHY_CSR2 0x04c4
|
|
||||||
#define PHY_CSR3 0x04c6
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PHY_CSR4: Interface configuration.
|
|
||||||
*/
|
|
||||||
#define PHY_CSR4 0x04c8
|
|
||||||
#define PHY_CSR4_LOW_RF_LE FIELD16(0x0001)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* BBP pre-TX registers.
|
|
||||||
* PHY_CSR5: BBP pre-TX CCK.
|
|
||||||
*/
|
|
||||||
#define PHY_CSR5 0x04ca
|
|
||||||
#define PHY_CSR5_CCK FIELD16(0x0003)
|
|
||||||
#define PHY_CSR5_CCK_FLIP FIELD16(0x0004)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* BBP pre-TX registers.
|
|
||||||
* PHY_CSR6: BBP pre-TX OFDM.
|
|
||||||
*/
|
|
||||||
#define PHY_CSR6 0x04cc
|
|
||||||
#define PHY_CSR6_OFDM FIELD16(0x0003)
|
|
||||||
#define PHY_CSR6_OFDM_FLIP FIELD16(0x0004)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PHY_CSR7: BBP access register 0.
|
|
||||||
* BBP_DATA: BBP data.
|
|
||||||
* BBP_REG_ID: BBP register ID.
|
|
||||||
* BBP_READ_CONTROL: 0: write, 1: read.
|
|
||||||
*/
|
|
||||||
#define PHY_CSR7 0x04ce
|
|
||||||
#define PHY_CSR7_DATA FIELD16(0x00ff)
|
|
||||||
#define PHY_CSR7_REG_ID FIELD16(0x7f00)
|
|
||||||
#define PHY_CSR7_READ_CONTROL FIELD16(0x8000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PHY_CSR8: BBP access register 1.
|
|
||||||
* BBP_BUSY: ASIC is busy execute BBP programming.
|
|
||||||
*/
|
|
||||||
#define PHY_CSR8 0x04d0
|
|
||||||
#define PHY_CSR8_BUSY FIELD16(0x0001)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PHY_CSR9: RF access register.
|
|
||||||
* RF_VALUE: Register value + id to program into rf/if.
|
|
||||||
*/
|
|
||||||
#define PHY_CSR9 0x04d2
|
|
||||||
#define PHY_CSR9_RF_VALUE FIELD16(0xffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PHY_CSR10: RF access register.
|
|
||||||
* RF_VALUE: Register value + id to program into rf/if.
|
|
||||||
* RF_NUMBER_OF_BITS: Number of bits used in value (i:20, rfmd:22).
|
|
||||||
* RF_IF_SELECT: Chip to program: 0: rf, 1: if.
|
|
||||||
* RF_PLL_LD: Rf pll_ld status.
|
|
||||||
* RF_BUSY: 1: asic is busy execute rf programming.
|
|
||||||
*/
|
|
||||||
#define PHY_CSR10 0x04d4
|
|
||||||
#define PHY_CSR10_RF_VALUE FIELD16(0x00ff)
|
|
||||||
#define PHY_CSR10_RF_NUMBER_OF_BITS FIELD16(0x1f00)
|
|
||||||
#define PHY_CSR10_RF_IF_SELECT FIELD16(0x2000)
|
|
||||||
#define PHY_CSR10_RF_PLL_LD FIELD16(0x4000)
|
|
||||||
#define PHY_CSR10_RF_BUSY FIELD16(0x8000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* STA_CSR0: FCS error count.
|
|
||||||
* FCS_ERROR: FCS error count, cleared when read.
|
|
||||||
*/
|
|
||||||
#define STA_CSR0 0x04e0
|
|
||||||
#define STA_CSR0_FCS_ERROR FIELD16(0xffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* STA_CSR1: PLCP error count.
|
|
||||||
*/
|
|
||||||
#define STA_CSR1 0x04e2
|
|
||||||
|
|
||||||
/*
|
|
||||||
* STA_CSR2: LONG error count.
|
|
||||||
*/
|
|
||||||
#define STA_CSR2 0x04e4
|
|
||||||
|
|
||||||
/*
|
|
||||||
* STA_CSR3: CCA false alarm.
|
|
||||||
* FALSE_CCA_ERROR: False CCA error count, cleared when read.
|
|
||||||
*/
|
|
||||||
#define STA_CSR3 0x04e6
|
|
||||||
#define STA_CSR3_FALSE_CCA_ERROR FIELD16(0xffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* STA_CSR4: RX FIFO overflow.
|
|
||||||
*/
|
|
||||||
#define STA_CSR4 0x04e8
|
|
||||||
|
|
||||||
/*
|
|
||||||
* STA_CSR5: Beacon sent counter.
|
|
||||||
*/
|
|
||||||
#define STA_CSR5 0x04ea
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Statistics registers
|
|
||||||
*/
|
|
||||||
#define STA_CSR6 0x04ec
|
|
||||||
#define STA_CSR7 0x04ee
|
|
||||||
#define STA_CSR8 0x04f0
|
|
||||||
#define STA_CSR9 0x04f2
|
|
||||||
#define STA_CSR10 0x04f4
|
|
||||||
|
|
||||||
/*
|
|
||||||
* BBP registers.
|
|
||||||
* The wordsize of the BBP is 8 bits.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* R2: TX antenna control
|
|
||||||
*/
|
|
||||||
#define BBP_R2_TX_ANTENNA FIELD8(0x03)
|
|
||||||
#define BBP_R2_TX_IQ_FLIP FIELD8(0x04)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* R14: RX antenna control
|
|
||||||
*/
|
|
||||||
#define BBP_R14_RX_ANTENNA FIELD8(0x03)
|
|
||||||
#define BBP_R14_RX_IQ_FLIP FIELD8(0x04)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RF registers.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RF 1
|
|
||||||
*/
|
|
||||||
#define RF1_TUNER FIELD32(0x00020000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RF 3
|
|
||||||
*/
|
|
||||||
#define RF3_TUNER FIELD32(0x00000100)
|
|
||||||
#define RF3_TXPOWER FIELD32(0x00003e00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM contents.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* HW MAC address.
|
|
||||||
*/
|
|
||||||
#define EEPROM_MAC_ADDR_0 0x0002
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE0 FIELD16(0x00ff)
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE1 FIELD16(0xff00)
|
|
||||||
#define EEPROM_MAC_ADDR1 0x0003
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE2 FIELD16(0x00ff)
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE3 FIELD16(0xff00)
|
|
||||||
#define EEPROM_MAC_ADDR_2 0x0004
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE4 FIELD16(0x00ff)
|
|
||||||
#define EEPROM_MAC_ADDR_BYTE5 FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM antenna.
|
|
||||||
* ANTENNA_NUM: Number of antenna's.
|
|
||||||
* TX_DEFAULT: Default antenna 0: diversity, 1: A, 2: B.
|
|
||||||
* RX_DEFAULT: Default antenna 0: diversity, 1: A, 2: B.
|
|
||||||
* LED_MODE: 0: default, 1: TX/RX activity, 2: Single (ignore link), 3: rsvd.
|
|
||||||
* DYN_TXAGC: Dynamic TX AGC control.
|
|
||||||
* HARDWARE_RADIO: 1: Hardware controlled radio. Read GPIO0.
|
|
||||||
* RF_TYPE: Rf_type of this adapter.
|
|
||||||
*/
|
|
||||||
#define EEPROM_ANTENNA 0x000b
|
|
||||||
#define EEPROM_ANTENNA_NUM FIELD16(0x0003)
|
|
||||||
#define EEPROM_ANTENNA_TX_DEFAULT FIELD16(0x000c)
|
|
||||||
#define EEPROM_ANTENNA_RX_DEFAULT FIELD16(0x0030)
|
|
||||||
#define EEPROM_ANTENNA_LED_MODE FIELD16(0x01c0)
|
|
||||||
#define EEPROM_ANTENNA_DYN_TXAGC FIELD16(0x0200)
|
|
||||||
#define EEPROM_ANTENNA_HARDWARE_RADIO FIELD16(0x0400)
|
|
||||||
#define EEPROM_ANTENNA_RF_TYPE FIELD16(0xf800)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM NIC config.
|
|
||||||
* CARDBUS_ACCEL: 0: enable, 1: disable.
|
|
||||||
* DYN_BBP_TUNE: 0: enable, 1: disable.
|
|
||||||
* CCK_TX_POWER: CCK TX power compensation.
|
|
||||||
*/
|
|
||||||
#define EEPROM_NIC 0x000c
|
|
||||||
#define EEPROM_NIC_CARDBUS_ACCEL FIELD16(0x0001)
|
|
||||||
#define EEPROM_NIC_DYN_BBP_TUNE FIELD16(0x0002)
|
|
||||||
#define EEPROM_NIC_CCK_TX_POWER FIELD16(0x000c)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM geography.
|
|
||||||
* GEO: Default geography setting for device.
|
|
||||||
*/
|
|
||||||
#define EEPROM_GEOGRAPHY 0x000d
|
|
||||||
#define EEPROM_GEOGRAPHY_GEO FIELD16(0x0f00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM BBP.
|
|
||||||
*/
|
|
||||||
#define EEPROM_BBP_START 0x000e
|
|
||||||
#define EEPROM_BBP_SIZE 16
|
|
||||||
#define EEPROM_BBP_VALUE FIELD16(0x00ff)
|
|
||||||
#define EEPROM_BBP_REG_ID FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM TXPOWER
|
|
||||||
*/
|
|
||||||
#define EEPROM_TXPOWER_START 0x001e
|
|
||||||
#define EEPROM_TXPOWER_SIZE 7
|
|
||||||
#define EEPROM_TXPOWER_1 FIELD16(0x00ff)
|
|
||||||
#define EEPROM_TXPOWER_2 FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM Tuning threshold
|
|
||||||
*/
|
|
||||||
#define EEPROM_BBPTUNE 0x0030
|
|
||||||
#define EEPROM_BBPTUNE_THRESHOLD FIELD16(0x00ff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM BBP R24 Tuning.
|
|
||||||
*/
|
|
||||||
#define EEPROM_BBPTUNE_R24 0x0031
|
|
||||||
#define EEPROM_BBPTUNE_R24_LOW FIELD16(0x00ff)
|
|
||||||
#define EEPROM_BBPTUNE_R24_HIGH FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM BBP R25 Tuning.
|
|
||||||
*/
|
|
||||||
#define EEPROM_BBPTUNE_R25 0x0032
|
|
||||||
#define EEPROM_BBPTUNE_R25_LOW FIELD16(0x00ff)
|
|
||||||
#define EEPROM_BBPTUNE_R25_HIGH FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM BBP R24 Tuning.
|
|
||||||
*/
|
|
||||||
#define EEPROM_BBPTUNE_R61 0x0033
|
|
||||||
#define EEPROM_BBPTUNE_R61_LOW FIELD16(0x00ff)
|
|
||||||
#define EEPROM_BBPTUNE_R61_HIGH FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM BBP VGC Tuning.
|
|
||||||
*/
|
|
||||||
#define EEPROM_BBPTUNE_VGC 0x0034
|
|
||||||
#define EEPROM_BBPTUNE_VGCUPPER FIELD16(0x00ff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM BBP R17 Tuning.
|
|
||||||
*/
|
|
||||||
#define EEPROM_BBPTUNE_R17 0x0035
|
|
||||||
#define EEPROM_BBPTUNE_R17_LOW FIELD16(0x00ff)
|
|
||||||
#define EEPROM_BBPTUNE_R17_HIGH FIELD16(0xff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RSSI <-> dBm offset calibration
|
|
||||||
*/
|
|
||||||
#define EEPROM_CALIBRATE_OFFSET 0x0036
|
|
||||||
#define EEPROM_CALIBRATE_OFFSET_RSSI FIELD16(0x00ff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* DMA descriptor defines.
|
|
||||||
*/
|
|
||||||
#define TXD_DESC_SIZE ( 5 * sizeof(struct data_desc) )
|
|
||||||
#define RXD_DESC_SIZE ( 4 * sizeof(struct data_desc) )
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX descriptor format for TX, PRIO, ATIM and Beacon Ring.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word0
|
|
||||||
*/
|
|
||||||
#define TXD_W0_PACKET_ID FIELD32(0x0000000f)
|
|
||||||
#define TXD_W0_RETRY_LIMIT FIELD32(0x000000f0)
|
|
||||||
#define TXD_W0_MORE_FRAG FIELD32(0x00000100)
|
|
||||||
#define TXD_W0_ACK FIELD32(0x00000200)
|
|
||||||
#define TXD_W0_TIMESTAMP FIELD32(0x00000400)
|
|
||||||
#define TXD_W0_OFDM FIELD32(0x00000800)
|
|
||||||
#define TXD_W0_NEW_SEQ FIELD32(0x00001000)
|
|
||||||
#define TXD_W0_IFS FIELD32(0x00006000)
|
|
||||||
#define TXD_W0_DATABYTE_COUNT FIELD32(0x0fff0000)
|
|
||||||
#define TXD_W0_CIPHER FIELD32(0x20000000)
|
|
||||||
#define TXD_W0_KEY_ID FIELD32(0xc0000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word1
|
|
||||||
*/
|
|
||||||
#define TXD_W1_IV_OFFSET FIELD32(0x0000003f)
|
|
||||||
#define TXD_W1_AIFS FIELD32(0x000000c0)
|
|
||||||
#define TXD_W1_CWMIN FIELD32(0x00000f00)
|
|
||||||
#define TXD_W1_CWMAX FIELD32(0x0000f000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word2: PLCP information
|
|
||||||
*/
|
|
||||||
#define TXD_W2_PLCP_SIGNAL FIELD32(0x000000ff)
|
|
||||||
#define TXD_W2_PLCP_SERVICE FIELD32(0x0000ff00)
|
|
||||||
#define TXD_W2_PLCP_LENGTH_LOW FIELD32(0x00ff0000)
|
|
||||||
#define TXD_W2_PLCP_LENGTH_HIGH FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word3
|
|
||||||
*/
|
|
||||||
#define TXD_W3_IV FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word4
|
|
||||||
*/
|
|
||||||
#define TXD_W4_EIV FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RX descriptor format for RX Ring.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word0
|
|
||||||
*/
|
|
||||||
#define RXD_W0_UNICAST_TO_ME FIELD32(0x00000002)
|
|
||||||
#define RXD_W0_MULTICAST FIELD32(0x00000004)
|
|
||||||
#define RXD_W0_BROADCAST FIELD32(0x00000008)
|
|
||||||
#define RXD_W0_MY_BSS FIELD32(0x00000010)
|
|
||||||
#define RXD_W0_CRC_ERROR FIELD32(0x00000020)
|
|
||||||
#define RXD_W0_OFDM FIELD32(0x00000040)
|
|
||||||
#define RXD_W0_PHYSICAL_ERROR FIELD32(0x00000080)
|
|
||||||
#define RXD_W0_CIPHER FIELD32(0x00000100)
|
|
||||||
#define RXD_W0_CIPHER_ERROR FIELD32(0x00000200)
|
|
||||||
#define RXD_W0_DATABYTE_COUNT FIELD32(0x0fff0000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word1
|
|
||||||
*/
|
|
||||||
#define RXD_W1_RSSI FIELD32(0x000000ff)
|
|
||||||
#define RXD_W1_SIGNAL FIELD32(0x0000ff00)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word2
|
|
||||||
*/
|
|
||||||
#define RXD_W2_IV FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Word3
|
|
||||||
*/
|
|
||||||
#define RXD_W3_EIV FIELD32(0xffffffff)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Macro's for converting txpower from EEPROM to dscape value
|
|
||||||
* and from dscape value to register value.
|
|
||||||
*/
|
|
||||||
#define MIN_TXPOWER 0
|
|
||||||
#define MAX_TXPOWER 31
|
|
||||||
#define DEFAULT_TXPOWER 24
|
|
||||||
|
|
||||||
#define TXPOWER_FROM_DEV(__txpower) \
|
|
||||||
({ \
|
|
||||||
((__txpower) > MAX_TXPOWER) ? \
|
|
||||||
DEFAULT_TXPOWER : (__txpower); \
|
|
||||||
})
|
|
||||||
|
|
||||||
#define TXPOWER_TO_DEV(__txpower) \
|
|
||||||
({ \
|
|
||||||
((__txpower) <= MIN_TXPOWER) ? MIN_TXPOWER : \
|
|
||||||
(((__txpower) >= MAX_TXPOWER) ? MAX_TXPOWER : \
|
|
||||||
(__txpower)); \
|
|
||||||
})
|
|
||||||
|
|
||||||
#endif /* RT2500USB_H */
|
|
@ -1,845 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00
|
|
||||||
Abstract: rt2x00 global information.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2X00_H
|
|
||||||
#define RT2X00_H
|
|
||||||
|
|
||||||
#include <linux/bitops.h>
|
|
||||||
#include <linux/prefetch.h>
|
|
||||||
#include <linux/skbuff.h>
|
|
||||||
#include <linux/workqueue.h>
|
|
||||||
#include <linux/firmware.h>
|
|
||||||
|
|
||||||
#include <net/mac80211.h>
|
|
||||||
|
|
||||||
#include "rt2x00debug.h"
|
|
||||||
#include "rt2x00reg.h"
|
|
||||||
#include "rt2x00ring.h"
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Module information.
|
|
||||||
* DRV_NAME should be set within the individual module source files.
|
|
||||||
*/
|
|
||||||
#define DRV_VERSION "2.0.10"
|
|
||||||
#define DRV_PROJECT "http://rt2x00.serialmonkey.com"
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Debug definitions.
|
|
||||||
* Debug output has to be enabled during compile time.
|
|
||||||
*/
|
|
||||||
#define DEBUG_PRINTK_MSG(__dev, __kernlvl, __lvl, __msg, __args...) \
|
|
||||||
printk(__kernlvl "%s -> %s: %s - " __msg, \
|
|
||||||
wiphy_name((__dev)->hw->wiphy), __FUNCTION__, __lvl, ##__args)
|
|
||||||
|
|
||||||
#define DEBUG_PRINTK_PROBE(__kernlvl, __lvl, __msg, __args...) \
|
|
||||||
printk(__kernlvl "%s -> %s: %s - " __msg, \
|
|
||||||
DRV_NAME, __FUNCTION__, __lvl, ##__args)
|
|
||||||
|
|
||||||
#ifdef CONFIG_RT2X00_DEBUG
|
|
||||||
#define DEBUG_PRINTK(__dev, __kernlvl, __lvl, __msg, __args...) \
|
|
||||||
DEBUG_PRINTK_MSG(__dev, __kernlvl, __lvl, __msg, ##__args);
|
|
||||||
#else
|
|
||||||
#define DEBUG_PRINTK(__dev, __kernlvl, __lvl, __msg, __args...) \
|
|
||||||
do { } while (0)
|
|
||||||
#endif /* CONFIG_RT2X00_DEBUG */
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Various debug levels.
|
|
||||||
* The debug levels PANIC and ERROR both indicate serious problems,
|
|
||||||
* for this reason they should never be ignored.
|
|
||||||
* The special ERROR_PROBE message is for messages that are generated
|
|
||||||
* when the rt2x00_dev is not yet initialized.
|
|
||||||
*/
|
|
||||||
#define PANIC(__dev, __msg, __args...) \
|
|
||||||
DEBUG_PRINTK_MSG(__dev, KERN_CRIT, "Panic", __msg, ##__args)
|
|
||||||
#define ERROR(__dev, __msg, __args...) \
|
|
||||||
DEBUG_PRINTK_MSG(__dev, KERN_ERR, "Error", __msg, ##__args)
|
|
||||||
#define ERROR_PROBE(__msg, __args...) \
|
|
||||||
DEBUG_PRINTK_PROBE(KERN_ERR, "Error", __msg, ##__args)
|
|
||||||
#define WARNING(__dev, __msg, __args...) \
|
|
||||||
DEBUG_PRINTK(__dev, KERN_WARNING, "Warning", __msg, ##__args)
|
|
||||||
#define NOTICE(__dev, __msg, __args...) \
|
|
||||||
DEBUG_PRINTK(__dev, KERN_NOTICE, "Notice", __msg, ##__args)
|
|
||||||
#define INFO(__dev, __msg, __args...) \
|
|
||||||
DEBUG_PRINTK(__dev, KERN_INFO, "Info", __msg, ##__args)
|
|
||||||
#define DEBUG(__dev, __msg, __args...) \
|
|
||||||
DEBUG_PRINTK(__dev, KERN_DEBUG, "Debug", __msg, ##__args)
|
|
||||||
#define EEPROM(__dev, __msg, __args...) \
|
|
||||||
DEBUG_PRINTK(__dev, KERN_DEBUG, "EEPROM recovery", __msg, ##__args)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Ring sizes.
|
|
||||||
* Ralink PCI devices demand the Frame size to be a multiple of 128 bytes.
|
|
||||||
* DATA_FRAME_SIZE is used for TX, RX, ATIM and PRIO rings.
|
|
||||||
* MGMT_FRAME_SIZE is used for the BEACON ring.
|
|
||||||
*/
|
|
||||||
#define DATA_FRAME_SIZE 2432
|
|
||||||
#define MGMT_FRAME_SIZE 256
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Number of entries in a packet ring.
|
|
||||||
* PCI devices only need 1 Beacon entry,
|
|
||||||
* but USB devices require a second because they
|
|
||||||
* have to send a Guardian byte first.
|
|
||||||
*/
|
|
||||||
#define RX_ENTRIES 12
|
|
||||||
#define TX_ENTRIES 12
|
|
||||||
#define ATIM_ENTRIES 1
|
|
||||||
#define BEACON_ENTRIES 2
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Standard timing and size defines.
|
|
||||||
* These values should follow the ieee80211 specifications.
|
|
||||||
*/
|
|
||||||
#define ACK_SIZE 14
|
|
||||||
#define IEEE80211_HEADER 24
|
|
||||||
#define PLCP 48
|
|
||||||
#define BEACON 100
|
|
||||||
#define PREAMBLE 144
|
|
||||||
#define SHORT_PREAMBLE 72
|
|
||||||
#define SLOT_TIME 20
|
|
||||||
#define SHORT_SLOT_TIME 9
|
|
||||||
#define SIFS 10
|
|
||||||
#define PIFS ( SIFS + SLOT_TIME )
|
|
||||||
#define SHORT_PIFS ( SIFS + SHORT_SLOT_TIME )
|
|
||||||
#define DIFS ( PIFS + SLOT_TIME )
|
|
||||||
#define SHORT_DIFS ( SHORT_PIFS + SHORT_SLOT_TIME )
|
|
||||||
#define EIFS ( SIFS + (8 * (IEEE80211_HEADER + ACK_SIZE)) )
|
|
||||||
|
|
||||||
/*
|
|
||||||
* IEEE802.11 header defines
|
|
||||||
*/
|
|
||||||
static inline int is_rts_frame(u16 fc)
|
|
||||||
{
|
|
||||||
return !!(((fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_CTL) &&
|
|
||||||
((fc & IEEE80211_FCTL_STYPE) == IEEE80211_STYPE_RTS));
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline int is_cts_frame(u16 fc)
|
|
||||||
{
|
|
||||||
return !!(((fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_CTL) &&
|
|
||||||
((fc & IEEE80211_FCTL_STYPE) == IEEE80211_STYPE_CTS));
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline int is_probe_resp(u16 fc)
|
|
||||||
{
|
|
||||||
return !!(((fc & IEEE80211_FCTL_FTYPE) == IEEE80211_FTYPE_MGMT) &&
|
|
||||||
((fc & IEEE80211_FCTL_STYPE) == IEEE80211_STYPE_PROBE_RESP));
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Chipset identification
|
|
||||||
* The chipset on the device is composed of a RT and RF chip.
|
|
||||||
* The chipset combination is important for determining device capabilities.
|
|
||||||
*/
|
|
||||||
struct rt2x00_chip {
|
|
||||||
u16 rt;
|
|
||||||
#define RT2460 0x0101
|
|
||||||
#define RT2560 0x0201
|
|
||||||
#define RT2570 0x1201
|
|
||||||
#define RT2561s 0x0301 /* Turbo */
|
|
||||||
#define RT2561 0x0302
|
|
||||||
#define RT2661 0x0401
|
|
||||||
#define RT2571 0x1300
|
|
||||||
|
|
||||||
u16 rf;
|
|
||||||
u32 rev;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RF register values that belong to a particular channel.
|
|
||||||
*/
|
|
||||||
struct rf_channel {
|
|
||||||
int channel;
|
|
||||||
u32 rf1;
|
|
||||||
u32 rf2;
|
|
||||||
u32 rf3;
|
|
||||||
u32 rf4;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* To optimize the quality of the link we need to store
|
|
||||||
* the quality of received frames and periodically
|
|
||||||
* optimize the link.
|
|
||||||
*/
|
|
||||||
struct link {
|
|
||||||
/*
|
|
||||||
* Link tuner counter
|
|
||||||
* The number of times the link has been tuned
|
|
||||||
* since the radio has been switched on.
|
|
||||||
*/
|
|
||||||
u32 count;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Statistics required for Link tuning.
|
|
||||||
* For the average RSSI value we use the "Walking average" approach.
|
|
||||||
* When adding RSSI to the average value the following calculation
|
|
||||||
* is needed:
|
|
||||||
*
|
|
||||||
* avg_rssi = ((avg_rssi * 7) + rssi) / 8;
|
|
||||||
*
|
|
||||||
* The advantage of this approach is that we only need 1 variable
|
|
||||||
* to store the average in (No need for a count and a total).
|
|
||||||
* But more importantly, normal average values will over time
|
|
||||||
* move less and less towards newly added values this results
|
|
||||||
* that with link tuning, the device can have a very good RSSI
|
|
||||||
* for a few minutes but when the device is moved away from the AP
|
|
||||||
* the average will not decrease fast enough to compensate.
|
|
||||||
* The walking average compensates this and will move towards
|
|
||||||
* the new values correctly allowing a effective link tuning.
|
|
||||||
*/
|
|
||||||
int avg_rssi;
|
|
||||||
int vgc_level;
|
|
||||||
int false_cca;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Statistics required for Signal quality calculation.
|
|
||||||
* For calculating the Signal quality we have to determine
|
|
||||||
* the total number of success and failed RX and TX frames.
|
|
||||||
* After that we also use the average RSSI value to help
|
|
||||||
* determining the signal quality.
|
|
||||||
* For the calculation we will use the following algorithm:
|
|
||||||
*
|
|
||||||
* rssi_percentage = (avg_rssi * 100) / rssi_offset
|
|
||||||
* rx_percentage = (rx_success * 100) / rx_total
|
|
||||||
* tx_percentage = (tx_success * 100) / tx_total
|
|
||||||
* avg_signal = ((WEIGHT_RSSI * avg_rssi) +
|
|
||||||
* (WEIGHT_TX * tx_percentage) +
|
|
||||||
* (WEIGHT_RX * rx_percentage)) / 100
|
|
||||||
*
|
|
||||||
* This value should then be checked to not be greated then 100.
|
|
||||||
*/
|
|
||||||
int rx_percentage;
|
|
||||||
int rx_success;
|
|
||||||
int rx_failed;
|
|
||||||
int tx_percentage;
|
|
||||||
int tx_success;
|
|
||||||
int tx_failed;
|
|
||||||
#define WEIGHT_RSSI 20
|
|
||||||
#define WEIGHT_RX 40
|
|
||||||
#define WEIGHT_TX 40
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Work structure for scheduling periodic link tuning.
|
|
||||||
*/
|
|
||||||
struct delayed_work work;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Clear all counters inside the link structure.
|
|
||||||
* This can be easiest achieved by memsetting everything
|
|
||||||
* except for the work structure at the end.
|
|
||||||
*/
|
|
||||||
static inline void rt2x00_clear_link(struct link *link)
|
|
||||||
{
|
|
||||||
memset(link, 0x00, sizeof(*link) - sizeof(link->work));
|
|
||||||
link->rx_percentage = 50;
|
|
||||||
link->tx_percentage = 50;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Update the rssi using the walking average approach.
|
|
||||||
*/
|
|
||||||
static inline void rt2x00_update_link_rssi(struct link *link, int rssi)
|
|
||||||
{
|
|
||||||
if (!link->avg_rssi)
|
|
||||||
link->avg_rssi = rssi;
|
|
||||||
else
|
|
||||||
link->avg_rssi = ((link->avg_rssi * 7) + rssi) / 8;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* When the avg_rssi is unset or no frames have been received),
|
|
||||||
* we need to return the default value which needs to be less
|
|
||||||
* than -80 so the device will select the maximum sensitivity.
|
|
||||||
*/
|
|
||||||
static inline int rt2x00_get_link_rssi(struct link *link)
|
|
||||||
{
|
|
||||||
return (link->avg_rssi && link->rx_success) ? link->avg_rssi : -128;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Interface structure
|
|
||||||
* Configuration details about the current interface.
|
|
||||||
*/
|
|
||||||
struct interface {
|
|
||||||
/*
|
|
||||||
* Interface identification. The value is assigned
|
|
||||||
* to us by the 80211 stack, and is used to request
|
|
||||||
* new beacons.
|
|
||||||
*/
|
|
||||||
int id;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Current working type (IEEE80211_IF_TYPE_*).
|
|
||||||
* When set to INVALID_INTERFACE, no interface is configured.
|
|
||||||
*/
|
|
||||||
int type;
|
|
||||||
#define INVALID_INTERFACE IEEE80211_IF_TYPE_INVALID
|
|
||||||
|
|
||||||
/*
|
|
||||||
* MAC of the device.
|
|
||||||
*/
|
|
||||||
u8 mac[ETH_ALEN];
|
|
||||||
|
|
||||||
/*
|
|
||||||
* BBSID of the AP to associate with.
|
|
||||||
*/
|
|
||||||
u8 bssid[ETH_ALEN];
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Store the packet filter mode for the current interface.
|
|
||||||
*/
|
|
||||||
unsigned int filter;
|
|
||||||
};
|
|
||||||
|
|
||||||
static inline int is_interface_present(struct interface *intf)
|
|
||||||
{
|
|
||||||
return !!intf->id;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline int is_interface_type(struct interface *intf, int type)
|
|
||||||
{
|
|
||||||
return intf->type == type;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Details about the supported modes, rates and channels
|
|
||||||
* of a particular chipset. This is used by rt2x00lib
|
|
||||||
* to build the ieee80211_hw_mode array for mac80211.
|
|
||||||
*/
|
|
||||||
struct hw_mode_spec {
|
|
||||||
/*
|
|
||||||
* Number of modes, rates and channels.
|
|
||||||
*/
|
|
||||||
int num_modes;
|
|
||||||
int num_rates;
|
|
||||||
int num_channels;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* txpower values.
|
|
||||||
*/
|
|
||||||
const u8 *tx_power_a;
|
|
||||||
const u8 *tx_power_bg;
|
|
||||||
u8 tx_power_default;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device/chipset specific value.
|
|
||||||
*/
|
|
||||||
const struct rf_channel *channels;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Configuration structure wrapper around the
|
|
||||||
* mac80211 configuration structure.
|
|
||||||
* When mac80211 configures the driver, rt2x00lib
|
|
||||||
* can precalculate values which are equal for all
|
|
||||||
* rt2x00 drivers. Those values can be stored in here.
|
|
||||||
*/
|
|
||||||
struct rt2x00lib_conf {
|
|
||||||
struct ieee80211_conf *conf;
|
|
||||||
struct rf_channel rf;
|
|
||||||
|
|
||||||
int phymode;
|
|
||||||
|
|
||||||
int basic_rates;
|
|
||||||
int slot_time;
|
|
||||||
|
|
||||||
short sifs;
|
|
||||||
short pifs;
|
|
||||||
short difs;
|
|
||||||
short eifs;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* rt2x00lib callback functions.
|
|
||||||
*/
|
|
||||||
struct rt2x00lib_ops {
|
|
||||||
/*
|
|
||||||
* Interrupt handlers.
|
|
||||||
*/
|
|
||||||
irq_handler_t irq_handler;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device init handlers.
|
|
||||||
*/
|
|
||||||
int (*probe_hw) (struct rt2x00_dev *rt2x00dev);
|
|
||||||
char *(*get_firmware_name) (struct rt2x00_dev *rt2x00dev);
|
|
||||||
int (*load_firmware) (struct rt2x00_dev *rt2x00dev, void *data,
|
|
||||||
const size_t len);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device initialization/deinitialization handlers.
|
|
||||||
*/
|
|
||||||
int (*initialize) (struct rt2x00_dev *rt2x00dev);
|
|
||||||
void (*uninitialize) (struct rt2x00_dev *rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Radio control handlers.
|
|
||||||
*/
|
|
||||||
int (*set_device_state) (struct rt2x00_dev *rt2x00dev,
|
|
||||||
enum dev_state state);
|
|
||||||
int (*rfkill_poll) (struct rt2x00_dev *rt2x00dev);
|
|
||||||
void (*link_stats) (struct rt2x00_dev *rt2x00dev);
|
|
||||||
void (*reset_tuner) (struct rt2x00_dev *rt2x00dev);
|
|
||||||
void (*link_tuner) (struct rt2x00_dev *rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX control handlers
|
|
||||||
*/
|
|
||||||
void (*write_tx_desc) (struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_desc *txd,
|
|
||||||
struct txdata_entry_desc *desc,
|
|
||||||
struct ieee80211_hdr *ieee80211hdr,
|
|
||||||
unsigned int length,
|
|
||||||
struct ieee80211_tx_control *control);
|
|
||||||
int (*write_tx_data) (struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_ring *ring, struct sk_buff *skb,
|
|
||||||
struct ieee80211_tx_control *control);
|
|
||||||
int (*get_tx_data_len) (struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct sk_buff *skb);
|
|
||||||
void (*kick_tx_queue) (struct rt2x00_dev *rt2x00dev,
|
|
||||||
unsigned int queue);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RX control handlers
|
|
||||||
*/
|
|
||||||
void (*fill_rxdone) (struct data_entry *entry,
|
|
||||||
struct rxdata_entry_desc *desc);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Configuration handlers.
|
|
||||||
*/
|
|
||||||
void (*config_mac_addr) (struct rt2x00_dev *rt2x00dev, __le32 *mac);
|
|
||||||
void (*config_bssid) (struct rt2x00_dev *rt2x00dev, __le32 *bssid);
|
|
||||||
void (*config_type) (struct rt2x00_dev *rt2x00dev, const int type,
|
|
||||||
const int tsf_sync);
|
|
||||||
void (*config_preamble) (struct rt2x00_dev *rt2x00dev,
|
|
||||||
const int short_preamble,
|
|
||||||
const int ack_timeout,
|
|
||||||
const int ack_consume_time);
|
|
||||||
void (*config) (struct rt2x00_dev *rt2x00dev, const unsigned int flags,
|
|
||||||
struct rt2x00lib_conf *libconf);
|
|
||||||
#define CONFIG_UPDATE_PHYMODE ( 1 << 1 )
|
|
||||||
#define CONFIG_UPDATE_CHANNEL ( 1 << 2 )
|
|
||||||
#define CONFIG_UPDATE_TXPOWER ( 1 << 3 )
|
|
||||||
#define CONFIG_UPDATE_ANTENNA ( 1 << 4 )
|
|
||||||
#define CONFIG_UPDATE_SLOT_TIME ( 1 << 5 )
|
|
||||||
#define CONFIG_UPDATE_BEACON_INT ( 1 << 6 )
|
|
||||||
#define CONFIG_UPDATE_ALL 0xffff
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* rt2x00 driver callback operation structure.
|
|
||||||
*/
|
|
||||||
struct rt2x00_ops {
|
|
||||||
const char *name;
|
|
||||||
const unsigned int rxd_size;
|
|
||||||
const unsigned int txd_size;
|
|
||||||
const unsigned int eeprom_size;
|
|
||||||
const unsigned int rf_size;
|
|
||||||
const struct rt2x00lib_ops *lib;
|
|
||||||
const struct ieee80211_ops *hw;
|
|
||||||
#ifdef CONFIG_RT2X00_LIB_DEBUGFS
|
|
||||||
const struct rt2x00debug *debugfs;
|
|
||||||
#endif /* CONFIG_RT2X00_LIB_DEBUGFS */
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* rt2x00 device flags
|
|
||||||
*/
|
|
||||||
enum rt2x00_flags {
|
|
||||||
/*
|
|
||||||
* Device state flags
|
|
||||||
*/
|
|
||||||
DEVICE_PRESENT,
|
|
||||||
DEVICE_REGISTERED_HW,
|
|
||||||
DEVICE_INITIALIZED,
|
|
||||||
DEVICE_STARTED,
|
|
||||||
DEVICE_STARTED_SUSPEND,
|
|
||||||
DEVICE_ENABLED_RADIO,
|
|
||||||
DEVICE_DISABLED_RADIO_HW,
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Driver features
|
|
||||||
*/
|
|
||||||
DRIVER_REQUIRE_FIRMWARE,
|
|
||||||
DRIVER_REQUIRE_BEACON_RING,
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Driver configuration
|
|
||||||
*/
|
|
||||||
CONFIG_SUPPORT_HW_BUTTON,
|
|
||||||
CONFIG_FRAME_TYPE,
|
|
||||||
CONFIG_RF_SEQUENCE,
|
|
||||||
CONFIG_EXTERNAL_LNA_A,
|
|
||||||
CONFIG_EXTERNAL_LNA_BG,
|
|
||||||
CONFIG_DOUBLE_ANTENNA,
|
|
||||||
CONFIG_DISABLE_LINK_TUNING,
|
|
||||||
CONFIG_SHORT_PREAMBLE,
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* rt2x00 device structure.
|
|
||||||
*/
|
|
||||||
struct rt2x00_dev {
|
|
||||||
/*
|
|
||||||
* Device structure.
|
|
||||||
* The structure stored in here depends on the
|
|
||||||
* system bus (PCI or USB).
|
|
||||||
* When accessing this variable, the rt2x00dev_{pci,usb}
|
|
||||||
* macro's should be used for correct typecasting.
|
|
||||||
*/
|
|
||||||
void *dev;
|
|
||||||
#define rt2x00dev_pci(__dev) ( (struct pci_dev*)(__dev)->dev )
|
|
||||||
#define rt2x00dev_usb(__dev) ( (struct usb_interface*)(__dev)->dev )
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Callback functions.
|
|
||||||
*/
|
|
||||||
const struct rt2x00_ops *ops;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* IEEE80211 control structure.
|
|
||||||
*/
|
|
||||||
struct ieee80211_hw *hw;
|
|
||||||
struct ieee80211_hw_mode *hwmodes;
|
|
||||||
unsigned int curr_hwmode;
|
|
||||||
#define HWMODE_B 0
|
|
||||||
#define HWMODE_G 1
|
|
||||||
#define HWMODE_A 2
|
|
||||||
|
|
||||||
/*
|
|
||||||
* rfkill structure for RF state switching support.
|
|
||||||
* This will only be compiled in when required.
|
|
||||||
*/
|
|
||||||
#ifdef CONFIG_RT2X00_LIB_RFKILL
|
|
||||||
struct rfkill *rfkill;
|
|
||||||
struct input_polled_dev *poll_dev;
|
|
||||||
#endif /* CONFIG_RT2X00_LIB_RFKILL */
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If enabled, the debugfs interface structures
|
|
||||||
* required for deregistration of debugfs.
|
|
||||||
*/
|
|
||||||
#ifdef CONFIG_RT2X00_LIB_DEBUGFS
|
|
||||||
const struct rt2x00debug_intf *debugfs_intf;
|
|
||||||
#endif /* CONFIG_RT2X00_LIB_DEBUGFS */
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device flags.
|
|
||||||
* In these flags the current status and some
|
|
||||||
* of the device capabilities are stored.
|
|
||||||
*/
|
|
||||||
unsigned long flags;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Chipset identification.
|
|
||||||
*/
|
|
||||||
struct rt2x00_chip chip;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* hw capability specifications.
|
|
||||||
*/
|
|
||||||
struct hw_mode_spec spec;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Register pointers
|
|
||||||
* csr_addr: Base register address. (PCI)
|
|
||||||
* csr_cache: CSR cache for usb_control_msg. (USB)
|
|
||||||
*/
|
|
||||||
void __iomem *csr_addr;
|
|
||||||
void *csr_cache;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Interface configuration.
|
|
||||||
*/
|
|
||||||
struct interface interface;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Link quality
|
|
||||||
*/
|
|
||||||
struct link link;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* EEPROM data.
|
|
||||||
*/
|
|
||||||
__le16 *eeprom;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Active RF register values.
|
|
||||||
* These are stored here so we don't need
|
|
||||||
* to read the rf registers and can directly
|
|
||||||
* use this value instead.
|
|
||||||
* This field should be accessed by using
|
|
||||||
* rt2x00_rf_read() and rt2x00_rf_write().
|
|
||||||
*/
|
|
||||||
u32 *rf;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* USB Max frame size (for rt2500usb & rt73usb).
|
|
||||||
*/
|
|
||||||
u16 usb_maxpacket;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Current TX power value.
|
|
||||||
*/
|
|
||||||
u16 tx_power;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* LED register (for rt61pci & rt73usb).
|
|
||||||
*/
|
|
||||||
u16 led_reg;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Led mode (LED_MODE_*)
|
|
||||||
*/
|
|
||||||
u8 led_mode;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Rssi <-> Dbm offset
|
|
||||||
*/
|
|
||||||
u8 rssi_offset;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Frequency offset (for rt61pci & rt73usb).
|
|
||||||
*/
|
|
||||||
u8 freq_offset;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Low level statistics which will have
|
|
||||||
* to be kept up to date while device is running.
|
|
||||||
*/
|
|
||||||
struct ieee80211_low_level_stats low_level_stats;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RX configuration information.
|
|
||||||
*/
|
|
||||||
struct ieee80211_rx_status rx_status;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Scheduled work.
|
|
||||||
*/
|
|
||||||
struct work_struct beacon_work;
|
|
||||||
struct work_struct filter_work;
|
|
||||||
struct work_struct config_work;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Data ring arrays for RX, TX and Beacon.
|
|
||||||
* The Beacon array also contains the Atim ring
|
|
||||||
* if that is supported by the device.
|
|
||||||
*/
|
|
||||||
int data_rings;
|
|
||||||
struct data_ring *rx;
|
|
||||||
struct data_ring *tx;
|
|
||||||
struct data_ring *bcn;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Firmware image.
|
|
||||||
*/
|
|
||||||
const struct firmware *fw;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* For-each loop for the ring array.
|
|
||||||
* All rings have been allocated as a single array,
|
|
||||||
* this means we can create a very simply loop macro
|
|
||||||
* that is capable of looping through all rings.
|
|
||||||
* ring_end(), txring_end() and ring_loop() are helper macro's which
|
|
||||||
* should not be used directly. Instead the following should be used:
|
|
||||||
* ring_for_each() - Loops through all rings (RX, TX, Beacon & Atim)
|
|
||||||
* txring_for_each() - Loops through TX data rings (TX only)
|
|
||||||
* txringall_for_each() - Loops through all TX rings (TX, Beacon & Atim)
|
|
||||||
*/
|
|
||||||
#define ring_end(__dev) \
|
|
||||||
&(__dev)->rx[(__dev)->data_rings]
|
|
||||||
|
|
||||||
#define txring_end(__dev) \
|
|
||||||
&(__dev)->tx[(__dev)->hw->queues]
|
|
||||||
|
|
||||||
#define ring_loop(__entry, __start, __end) \
|
|
||||||
for ((__entry) = (__start); \
|
|
||||||
prefetch(&(__entry)[1]), (__entry) != (__end); \
|
|
||||||
(__entry) = &(__entry)[1])
|
|
||||||
|
|
||||||
#define ring_for_each(__dev, __entry) \
|
|
||||||
ring_loop(__entry, (__dev)->rx, ring_end(__dev))
|
|
||||||
|
|
||||||
#define txring_for_each(__dev, __entry) \
|
|
||||||
ring_loop(__entry, (__dev)->tx, txring_end(__dev))
|
|
||||||
|
|
||||||
#define txringall_for_each(__dev, __entry) \
|
|
||||||
ring_loop(__entry, (__dev)->tx, ring_end(__dev))
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Generic RF access.
|
|
||||||
* The RF is being accessed by word index.
|
|
||||||
*/
|
|
||||||
static inline void rt2x00_rf_read(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const unsigned int word, u32 *data)
|
|
||||||
{
|
|
||||||
*data = rt2x00dev->rf[word];
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00_rf_write(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const unsigned int word, u32 data)
|
|
||||||
{
|
|
||||||
rt2x00dev->rf[word] = data;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Generic EEPROM access.
|
|
||||||
* The EEPROM is being accessed by word index.
|
|
||||||
*/
|
|
||||||
static inline void *rt2x00_eeprom_addr(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const unsigned int word)
|
|
||||||
{
|
|
||||||
return (void *)&rt2x00dev->eeprom[word];
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00_eeprom_read(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const unsigned int word, u16 *data)
|
|
||||||
{
|
|
||||||
*data = le16_to_cpu(rt2x00dev->eeprom[word]);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00_eeprom_write(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const unsigned int word, u16 data)
|
|
||||||
{
|
|
||||||
rt2x00dev->eeprom[word] = cpu_to_le16(data);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Chipset handlers
|
|
||||||
*/
|
|
||||||
static inline void rt2x00_set_chip(struct rt2x00_dev *rt2x00dev,
|
|
||||||
const u16 rt, const u16 rf, const u32 rev)
|
|
||||||
{
|
|
||||||
INFO(rt2x00dev,
|
|
||||||
"Chipset detected - rt: %04x, rf: %04x, rev: %08x.\n",
|
|
||||||
rt, rf, rev);
|
|
||||||
|
|
||||||
rt2x00dev->chip.rt = rt;
|
|
||||||
rt2x00dev->chip.rf = rf;
|
|
||||||
rt2x00dev->chip.rev = rev;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline char rt2x00_rt(const struct rt2x00_chip *chipset, const u16 chip)
|
|
||||||
{
|
|
||||||
return (chipset->rt == chip);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline char rt2x00_rf(const struct rt2x00_chip *chipset, const u16 chip)
|
|
||||||
{
|
|
||||||
return (chipset->rf == chip);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline u16 rt2x00_rev(const struct rt2x00_chip *chipset)
|
|
||||||
{
|
|
||||||
return chipset->rev;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline u16 rt2x00_check_rev(const struct rt2x00_chip *chipset,
|
|
||||||
const u32 rev)
|
|
||||||
{
|
|
||||||
return (((chipset->rev & 0xffff0) == rev) &&
|
|
||||||
!!(chipset->rev & 0x0000f));
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Duration calculations
|
|
||||||
* The rate variable passed is: 100kbs.
|
|
||||||
* To convert from bytes to bits we multiply size with 8,
|
|
||||||
* then the size is multiplied with 10 to make the
|
|
||||||
* real rate -> rate argument correction.
|
|
||||||
*/
|
|
||||||
static inline u16 get_duration(const unsigned int size, const u8 rate)
|
|
||||||
{
|
|
||||||
return ((size * 8 * 10) / rate);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline u16 get_duration_res(const unsigned int size, const u8 rate)
|
|
||||||
{
|
|
||||||
return ((size * 8 * 10) % rate);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Library functions.
|
|
||||||
*/
|
|
||||||
struct data_ring *rt2x00lib_get_ring(struct rt2x00_dev *rt2x00dev,
|
|
||||||
const unsigned int queue);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Interrupt context handlers.
|
|
||||||
*/
|
|
||||||
void rt2x00lib_beacondone(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_txdone(struct data_entry *entry,
|
|
||||||
const int status, const int retry);
|
|
||||||
void rt2x00lib_rxdone(struct data_entry *entry, struct sk_buff *skb,
|
|
||||||
struct rxdata_entry_desc *desc);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX descriptor initializer
|
|
||||||
*/
|
|
||||||
void rt2x00lib_write_tx_desc(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_desc *txd,
|
|
||||||
struct ieee80211_hdr *ieee80211hdr,
|
|
||||||
unsigned int length,
|
|
||||||
struct ieee80211_tx_control *control);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* mac80211 handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00mac_tx(struct ieee80211_hw *hw, struct sk_buff *skb,
|
|
||||||
struct ieee80211_tx_control *control);
|
|
||||||
int rt2x00mac_start(struct ieee80211_hw *hw);
|
|
||||||
void rt2x00mac_stop(struct ieee80211_hw *hw);
|
|
||||||
int rt2x00mac_add_interface(struct ieee80211_hw *hw,
|
|
||||||
struct ieee80211_if_init_conf *conf);
|
|
||||||
void rt2x00mac_remove_interface(struct ieee80211_hw *hw,
|
|
||||||
struct ieee80211_if_init_conf *conf);
|
|
||||||
int rt2x00mac_config(struct ieee80211_hw *hw, struct ieee80211_conf *conf);
|
|
||||||
int rt2x00mac_config_interface(struct ieee80211_hw *hw, int if_id,
|
|
||||||
struct ieee80211_if_conf *conf);
|
|
||||||
int rt2x00mac_get_stats(struct ieee80211_hw *hw,
|
|
||||||
struct ieee80211_low_level_stats *stats);
|
|
||||||
int rt2x00mac_get_tx_stats(struct ieee80211_hw *hw,
|
|
||||||
struct ieee80211_tx_queue_stats *stats);
|
|
||||||
void rt2x00mac_erp_ie_changed(struct ieee80211_hw *hw, u8 changes,
|
|
||||||
int cts_protection, int preamble);
|
|
||||||
int rt2x00mac_conf_tx(struct ieee80211_hw *hw, int queue,
|
|
||||||
const struct ieee80211_tx_queue_params *params);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Driver allocation handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00lib_probe_dev(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_remove_dev(struct rt2x00_dev *rt2x00dev);
|
|
||||||
#ifdef CONFIG_PM
|
|
||||||
int rt2x00lib_suspend(struct rt2x00_dev *rt2x00dev, pm_message_t state);
|
|
||||||
int rt2x00lib_resume(struct rt2x00_dev *rt2x00dev);
|
|
||||||
#endif /* CONFIG_PM */
|
|
||||||
|
|
||||||
#endif /* RT2X00_H */
|
|
@ -1,66 +0,0 @@
|
|||||||
/*
|
|
||||||
* RT2X00 Compatability fixes for specific kernels.
|
|
||||||
*/
|
|
||||||
#ifndef RT2X00_COMPAT_H
|
|
||||||
#define RT2X00_COMPAT_H
|
|
||||||
|
|
||||||
/*
|
|
||||||
* First include the 2 config headers.
|
|
||||||
* The rt2x00_config.h should overrule
|
|
||||||
* the kernel configuration.
|
|
||||||
*/
|
|
||||||
#include <linux/autoconf.h>
|
|
||||||
#include "rt2x00_config.h"
|
|
||||||
|
|
||||||
#include <linux/kernel.h>
|
|
||||||
#include <linux/module.h>
|
|
||||||
#include <linux/version.h>
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Check minimal requirements.
|
|
||||||
*/
|
|
||||||
#if (!defined(CONFIG_MAC80211) && !defined(CONFIG_MAC80211_MODULE))
|
|
||||||
#error mac80211 support not enabled in kernel!
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if !defined(CONFIG_WLAN_80211)
|
|
||||||
#error 802.11 wlan card support not enabled in kernel!
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if (defined(CONFIG_RT2400PCI) || defined(CONFIG_RT2500PCI) || defined(CONFIG_RT61PCI))
|
|
||||||
#if (!defined(CONFIG_PCI) && !defined(CONFIG_PCI_MODULE))
|
|
||||||
#error PCI has been disabled in your kernel!
|
|
||||||
#endif
|
|
||||||
#if (!defined(CONFIG_EEPROM_93CX6) && !defined(CONFIG_EEPROM_93CX6_MODULE))
|
|
||||||
#error EEPROM_93CX6 has been disabled in your kernel!
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if (defined(CONFIG_RT2500USB) || defined(CONFIG_RT73USB))
|
|
||||||
#if (!defined(CONFIG_USB) && !defined(CONFIG_USB_MODULE))
|
|
||||||
#error USB has been disabled in your kernel!
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if (defined(CONFIG_RT61PCI) || defined(CONFIG_RT73USB))
|
|
||||||
#if (!defined(CONFIG_FW_LOADER) && !defined(CONFIG_FW_LOADER_MODULE))
|
|
||||||
#error Firmware loading has been disabled in your kernel!
|
|
||||||
#endif
|
|
||||||
#if (!defined(CONFIG_CRC_ITU_T) && !defined(CONFIG_CRC_ITU_T_MODULE))
|
|
||||||
#error CRC_ITU_T loading has been disabled in your kernel!
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if (defined(CONFIG_RT2X00_DEBUGFS))
|
|
||||||
#if (!defined(CONFIG_MAC80211_DEBUGFS) && !defined(CONFIG_MAC80211_DEBUGFS_MODULE))
|
|
||||||
#error mac80211 debugfs support has been disabled in your kernel!
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#if (defined(CONFIG_RT2400PCI_BUTTON) || defined(CONFIG_RT2500PCI_BUTTON) || defined(CONFIG_RT61PCI_BUTTON))
|
|
||||||
#if (!defined(CONFIG_RFKILL) && !defined (CONFIG_RFKILL_MODULE))
|
|
||||||
#error RFKILL has been disabled in your kernel!
|
|
||||||
#endif
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#endif /* RT2X00_COMPAT_H */
|
|
@ -1,205 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00lib
|
|
||||||
Abstract: rt2x00 generic configuration routines.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Set enviroment defines for rt2x00.h
|
|
||||||
*/
|
|
||||||
#define DRV_NAME "rt2x00lib"
|
|
||||||
|
|
||||||
#include <linux/kernel.h>
|
|
||||||
#include <linux/module.h>
|
|
||||||
|
|
||||||
#include "rt2x00.h"
|
|
||||||
#include "rt2x00lib.h"
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
* The MAC and BSSID addressess are simple array of bytes,
|
|
||||||
* these arrays are little endian, so when sending the addressess
|
|
||||||
* to the drivers, copy the it into a endian-signed variable.
|
|
||||||
*
|
|
||||||
* Note that all devices (except rt2500usb) have 32 bits
|
|
||||||
* register word sizes. This means that whatever variable we
|
|
||||||
* pass _must_ be a multiple of 32 bits. Otherwise the device
|
|
||||||
* might not accept what we are sending to it.
|
|
||||||
* This will also make it easier for the driver to write
|
|
||||||
* the data to the device.
|
|
||||||
*
|
|
||||||
* Also note that when NULL is passed as address the
|
|
||||||
* we will send 00:00:00:00:00 to the device to clear the address.
|
|
||||||
* This will prevent the device being confused when it wants
|
|
||||||
* to ACK frames or consideres itself associated.
|
|
||||||
*/
|
|
||||||
void rt2x00lib_config_mac_addr(struct rt2x00_dev *rt2x00dev, u8 *mac)
|
|
||||||
{
|
|
||||||
__le32 reg[2];
|
|
||||||
|
|
||||||
memset(®, 0, sizeof(reg));
|
|
||||||
if (mac)
|
|
||||||
memcpy(®, mac, ETH_ALEN);
|
|
||||||
|
|
||||||
rt2x00dev->ops->lib->config_mac_addr(rt2x00dev, ®[0]);
|
|
||||||
}
|
|
||||||
|
|
||||||
void rt2x00lib_config_bssid(struct rt2x00_dev *rt2x00dev, u8 *bssid)
|
|
||||||
{
|
|
||||||
__le32 reg[2];
|
|
||||||
|
|
||||||
memset(®, 0, sizeof(reg));
|
|
||||||
if (bssid)
|
|
||||||
memcpy(®, bssid, ETH_ALEN);
|
|
||||||
|
|
||||||
rt2x00dev->ops->lib->config_bssid(rt2x00dev, ®[0]);
|
|
||||||
}
|
|
||||||
|
|
||||||
void rt2x00lib_config_type(struct rt2x00_dev *rt2x00dev, const int type)
|
|
||||||
{
|
|
||||||
int tsf_sync;
|
|
||||||
|
|
||||||
switch (type) {
|
|
||||||
case IEEE80211_IF_TYPE_IBSS:
|
|
||||||
case IEEE80211_IF_TYPE_AP:
|
|
||||||
tsf_sync = TSF_SYNC_BEACON;
|
|
||||||
break;
|
|
||||||
case IEEE80211_IF_TYPE_STA:
|
|
||||||
tsf_sync = TSF_SYNC_INFRA;
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
tsf_sync = TSF_SYNC_NONE;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
rt2x00dev->ops->lib->config_type(rt2x00dev, type, tsf_sync);
|
|
||||||
}
|
|
||||||
|
|
||||||
void rt2x00lib_config(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct ieee80211_conf *conf, const int force_config)
|
|
||||||
{
|
|
||||||
struct rt2x00lib_conf libconf;
|
|
||||||
struct ieee80211_hw_mode *mode;
|
|
||||||
struct ieee80211_rate *rate;
|
|
||||||
int flags = 0;
|
|
||||||
int short_slot_time;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* In some situations we want to force all configurations
|
|
||||||
* to be reloaded (When resuming for instance).
|
|
||||||
*/
|
|
||||||
if (force_config) {
|
|
||||||
flags = CONFIG_UPDATE_ALL;
|
|
||||||
goto config;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Check which configuration options have been
|
|
||||||
* updated and should be send to the device.
|
|
||||||
*/
|
|
||||||
if (rt2x00dev->rx_status.phymode != conf->phymode)
|
|
||||||
flags |= CONFIG_UPDATE_PHYMODE;
|
|
||||||
if (rt2x00dev->rx_status.channel != conf->channel)
|
|
||||||
flags |= CONFIG_UPDATE_CHANNEL;
|
|
||||||
if (rt2x00dev->tx_power != conf->power_level)
|
|
||||||
flags |= CONFIG_UPDATE_TXPOWER;
|
|
||||||
if (rt2x00dev->rx_status.antenna == conf->antenna_sel_rx)
|
|
||||||
flags |= CONFIG_UPDATE_ANTENNA;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* The following configuration options are never
|
|
||||||
* stored anywhere and will always be updated.
|
|
||||||
*/
|
|
||||||
flags |= CONFIG_UPDATE_SLOT_TIME;
|
|
||||||
flags |= CONFIG_UPDATE_BEACON_INT;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* We have determined what options should be updated,
|
|
||||||
* now precalculate device configuration values depending
|
|
||||||
* on what configuration options need to be updated.
|
|
||||||
*/
|
|
||||||
config:
|
|
||||||
memset(&libconf, 0, sizeof(libconf));
|
|
||||||
|
|
||||||
if (flags & CONFIG_UPDATE_PHYMODE) {
|
|
||||||
switch (conf->phymode) {
|
|
||||||
case MODE_IEEE80211A:
|
|
||||||
libconf.phymode = HWMODE_A;
|
|
||||||
break;
|
|
||||||
case MODE_IEEE80211B:
|
|
||||||
libconf.phymode = HWMODE_B;
|
|
||||||
break;
|
|
||||||
case MODE_IEEE80211G:
|
|
||||||
libconf.phymode = HWMODE_G;
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
ERROR(rt2x00dev,
|
|
||||||
"Attempt to configure unsupported mode (%d)"
|
|
||||||
"Defaulting to 802.11b", conf->phymode);
|
|
||||||
libconf.phymode = HWMODE_B;
|
|
||||||
}
|
|
||||||
|
|
||||||
mode = &rt2x00dev->hwmodes[libconf.phymode];
|
|
||||||
rate = &mode->rates[mode->num_rates - 1];
|
|
||||||
|
|
||||||
libconf.basic_rates =
|
|
||||||
DEVICE_GET_RATE_FIELD(rate->val, RATEMASK) & DEV_BASIC_RATEMASK;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (flags & CONFIG_UPDATE_CHANNEL) {
|
|
||||||
memcpy(&libconf.rf,
|
|
||||||
&rt2x00dev->spec.channels[conf->channel_val],
|
|
||||||
sizeof(libconf.rf));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (flags & CONFIG_UPDATE_SLOT_TIME) {
|
|
||||||
short_slot_time = conf->flags & IEEE80211_CONF_SHORT_SLOT_TIME;
|
|
||||||
|
|
||||||
libconf.slot_time =
|
|
||||||
short_slot_time ? SHORT_SLOT_TIME : SLOT_TIME;
|
|
||||||
libconf.sifs = SIFS;
|
|
||||||
libconf.pifs = short_slot_time ? SHORT_PIFS : PIFS;
|
|
||||||
libconf.difs = short_slot_time ? SHORT_DIFS : DIFS;
|
|
||||||
libconf.eifs = EIFS;
|
|
||||||
}
|
|
||||||
|
|
||||||
libconf.conf = conf;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Start configuration.
|
|
||||||
*/
|
|
||||||
rt2x00dev->ops->lib->config(rt2x00dev, flags, &libconf);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Some configuration changes affect the link quality
|
|
||||||
* which means we need to reset the link tuner.
|
|
||||||
*/
|
|
||||||
if (flags & (CONFIG_UPDATE_CHANNEL | CONFIG_UPDATE_ANTENNA))
|
|
||||||
rt2x00lib_reset_link_tuner(rt2x00dev);
|
|
||||||
|
|
||||||
rt2x00dev->curr_hwmode = libconf.phymode;
|
|
||||||
rt2x00dev->rx_status.phymode = conf->phymode;
|
|
||||||
rt2x00dev->rx_status.freq = conf->freq;
|
|
||||||
rt2x00dev->rx_status.channel = conf->channel;
|
|
||||||
rt2x00dev->tx_power = conf->power_level;
|
|
||||||
rt2x00dev->rx_status.antenna = conf->antenna_sel_rx;
|
|
||||||
}
|
|
@ -1,368 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00lib
|
|
||||||
Abstract: rt2x00 debugfs specific routines.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Set enviroment defines for rt2x00.h
|
|
||||||
*/
|
|
||||||
#define DRV_NAME "rt2x00lib"
|
|
||||||
|
|
||||||
#include <linux/debugfs.h>
|
|
||||||
#include <linux/kernel.h>
|
|
||||||
#include <linux/module.h>
|
|
||||||
#include <linux/uaccess.h>
|
|
||||||
|
|
||||||
#include "rt2x00.h"
|
|
||||||
#include "rt2x00lib.h"
|
|
||||||
|
|
||||||
#define PRINT_LINE_LEN_MAX 32
|
|
||||||
|
|
||||||
struct rt2x00debug_intf {
|
|
||||||
/*
|
|
||||||
* Pointer to driver structure where
|
|
||||||
* this debugfs entry belongs to.
|
|
||||||
*/
|
|
||||||
struct rt2x00_dev *rt2x00dev;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Reference to the rt2x00debug structure
|
|
||||||
* which can be used to communicate with
|
|
||||||
* the registers.
|
|
||||||
*/
|
|
||||||
const struct rt2x00debug *debug;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Debugfs entries for:
|
|
||||||
* - driver folder
|
|
||||||
* - driver file
|
|
||||||
* - chipset file
|
|
||||||
* - device flags file
|
|
||||||
* - register offset/value files
|
|
||||||
* - eeprom offset/value files
|
|
||||||
* - bbp offset/value files
|
|
||||||
* - rf offset/value files
|
|
||||||
*/
|
|
||||||
struct dentry *driver_folder;
|
|
||||||
struct dentry *driver_entry;
|
|
||||||
struct dentry *chipset_entry;
|
|
||||||
struct dentry *dev_flags;
|
|
||||||
struct dentry *csr_off_entry;
|
|
||||||
struct dentry *csr_val_entry;
|
|
||||||
struct dentry *eeprom_off_entry;
|
|
||||||
struct dentry *eeprom_val_entry;
|
|
||||||
struct dentry *bbp_off_entry;
|
|
||||||
struct dentry *bbp_val_entry;
|
|
||||||
struct dentry *rf_off_entry;
|
|
||||||
struct dentry *rf_val_entry;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Driver and chipset files will use a data buffer
|
|
||||||
* that has been created in advance. This will simplify
|
|
||||||
* the code since we can use the debugfs functions.
|
|
||||||
*/
|
|
||||||
struct debugfs_blob_wrapper driver_blob;
|
|
||||||
struct debugfs_blob_wrapper chipset_blob;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Requested offset for each register type.
|
|
||||||
*/
|
|
||||||
unsigned int offset_csr;
|
|
||||||
unsigned int offset_eeprom;
|
|
||||||
unsigned int offset_bbp;
|
|
||||||
unsigned int offset_rf;
|
|
||||||
};
|
|
||||||
|
|
||||||
static int rt2x00debug_file_open(struct inode *inode, struct file *file)
|
|
||||||
{
|
|
||||||
struct rt2x00debug_intf *intf = inode->i_private;
|
|
||||||
|
|
||||||
file->private_data = inode->i_private;
|
|
||||||
|
|
||||||
if (!try_module_get(intf->debug->owner))
|
|
||||||
return -EBUSY;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int rt2x00debug_file_release(struct inode *inode, struct file *file)
|
|
||||||
{
|
|
||||||
struct rt2x00debug_intf *intf = file->private_data;
|
|
||||||
|
|
||||||
module_put(intf->debug->owner);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
#define RT2X00DEBUGFS_OPS_READ(__name, __format, __type) \
|
|
||||||
static ssize_t rt2x00debug_read_##__name(struct file *file, \
|
|
||||||
char __user *buf, \
|
|
||||||
size_t length, \
|
|
||||||
loff_t *offset) \
|
|
||||||
{ \
|
|
||||||
struct rt2x00debug_intf *intf = file->private_data; \
|
|
||||||
const struct rt2x00debug *debug = intf->debug; \
|
|
||||||
char line[16]; \
|
|
||||||
size_t size; \
|
|
||||||
__type value; \
|
|
||||||
\
|
|
||||||
if (*offset) \
|
|
||||||
return 0; \
|
|
||||||
\
|
|
||||||
if (intf->offset_##__name >= debug->__name.word_count) \
|
|
||||||
return -EINVAL; \
|
|
||||||
\
|
|
||||||
debug->__name.read(intf->rt2x00dev, \
|
|
||||||
intf->offset_##__name, &value); \
|
|
||||||
\
|
|
||||||
size = sprintf(line, __format, value); \
|
|
||||||
\
|
|
||||||
if (copy_to_user(buf, line, size)) \
|
|
||||||
return -EFAULT; \
|
|
||||||
\
|
|
||||||
*offset += size; \
|
|
||||||
return size; \
|
|
||||||
}
|
|
||||||
|
|
||||||
#define RT2X00DEBUGFS_OPS_WRITE(__name, __type) \
|
|
||||||
static ssize_t rt2x00debug_write_##__name(struct file *file, \
|
|
||||||
const char __user *buf,\
|
|
||||||
size_t length, \
|
|
||||||
loff_t *offset) \
|
|
||||||
{ \
|
|
||||||
struct rt2x00debug_intf *intf = file->private_data; \
|
|
||||||
const struct rt2x00debug *debug = intf->debug; \
|
|
||||||
char line[16]; \
|
|
||||||
size_t size; \
|
|
||||||
__type value; \
|
|
||||||
\
|
|
||||||
if (*offset) \
|
|
||||||
return 0; \
|
|
||||||
\
|
|
||||||
if (!capable(CAP_NET_ADMIN)) \
|
|
||||||
return -EPERM; \
|
|
||||||
\
|
|
||||||
if (intf->offset_##__name >= debug->__name.word_count) \
|
|
||||||
return -EINVAL; \
|
|
||||||
\
|
|
||||||
if (copy_from_user(line, buf, length)) \
|
|
||||||
return -EFAULT; \
|
|
||||||
\
|
|
||||||
size = strlen(line); \
|
|
||||||
value = simple_strtoul(line, NULL, 0); \
|
|
||||||
\
|
|
||||||
debug->__name.write(intf->rt2x00dev, \
|
|
||||||
intf->offset_##__name, value); \
|
|
||||||
\
|
|
||||||
*offset += size; \
|
|
||||||
return size; \
|
|
||||||
}
|
|
||||||
|
|
||||||
#define RT2X00DEBUGFS_OPS(__name, __format, __type) \
|
|
||||||
RT2X00DEBUGFS_OPS_READ(__name, __format, __type); \
|
|
||||||
RT2X00DEBUGFS_OPS_WRITE(__name, __type); \
|
|
||||||
\
|
|
||||||
static const struct file_operations rt2x00debug_fop_##__name = {\
|
|
||||||
.owner = THIS_MODULE, \
|
|
||||||
.read = rt2x00debug_read_##__name, \
|
|
||||||
.write = rt2x00debug_write_##__name, \
|
|
||||||
.open = rt2x00debug_file_open, \
|
|
||||||
.release = rt2x00debug_file_release, \
|
|
||||||
};
|
|
||||||
|
|
||||||
RT2X00DEBUGFS_OPS(csr, "0x%.8x\n", u32);
|
|
||||||
RT2X00DEBUGFS_OPS(eeprom, "0x%.4x\n", u16);
|
|
||||||
RT2X00DEBUGFS_OPS(bbp, "0x%.2x\n", u8);
|
|
||||||
RT2X00DEBUGFS_OPS(rf, "0x%.8x\n", u32);
|
|
||||||
|
|
||||||
static ssize_t rt2x00debug_read_dev_flags(struct file *file,
|
|
||||||
char __user *buf,
|
|
||||||
size_t length,
|
|
||||||
loff_t *offset)
|
|
||||||
{
|
|
||||||
struct rt2x00debug_intf *intf = file->private_data;
|
|
||||||
char line[16];
|
|
||||||
size_t size;
|
|
||||||
|
|
||||||
if (*offset)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
size = sprintf(line, "0x%.8x\n", (unsigned int)intf->rt2x00dev->flags);
|
|
||||||
|
|
||||||
if (copy_to_user(buf, line, size))
|
|
||||||
return -EFAULT;
|
|
||||||
|
|
||||||
*offset += size;
|
|
||||||
return size;
|
|
||||||
}
|
|
||||||
|
|
||||||
static const struct file_operations rt2x00debug_fop_dev_flags = {
|
|
||||||
.owner = THIS_MODULE,
|
|
||||||
.read = rt2x00debug_read_dev_flags,
|
|
||||||
.open = rt2x00debug_file_open,
|
|
||||||
.release = rt2x00debug_file_release,
|
|
||||||
};
|
|
||||||
|
|
||||||
static struct dentry *rt2x00debug_create_file_driver(const char *name,
|
|
||||||
struct rt2x00debug_intf
|
|
||||||
*intf,
|
|
||||||
struct debugfs_blob_wrapper
|
|
||||||
*blob)
|
|
||||||
{
|
|
||||||
char *data;
|
|
||||||
|
|
||||||
data = kzalloc(3 * PRINT_LINE_LEN_MAX, GFP_KERNEL);
|
|
||||||
if (!data)
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
blob->data = data;
|
|
||||||
data += sprintf(data, "driver: %s\n", intf->rt2x00dev->ops->name);
|
|
||||||
data += sprintf(data, "version: %s\n", DRV_VERSION);
|
|
||||||
data += sprintf(data, "compiled: %s %s\n", __DATE__, __TIME__);
|
|
||||||
blob->size = strlen(blob->data);
|
|
||||||
|
|
||||||
return debugfs_create_blob(name, S_IRUGO, intf->driver_folder, blob);
|
|
||||||
}
|
|
||||||
|
|
||||||
static struct dentry *rt2x00debug_create_file_chipset(const char *name,
|
|
||||||
struct rt2x00debug_intf
|
|
||||||
*intf,
|
|
||||||
struct
|
|
||||||
debugfs_blob_wrapper
|
|
||||||
*blob)
|
|
||||||
{
|
|
||||||
const struct rt2x00debug *debug = intf->debug;
|
|
||||||
char *data;
|
|
||||||
|
|
||||||
data = kzalloc(4 * PRINT_LINE_LEN_MAX, GFP_KERNEL);
|
|
||||||
if (!data)
|
|
||||||
return NULL;
|
|
||||||
|
|
||||||
blob->data = data;
|
|
||||||
data += sprintf(data, "csr length: %d\n", debug->csr.word_count);
|
|
||||||
data += sprintf(data, "eeprom length: %d\n", debug->eeprom.word_count);
|
|
||||||
data += sprintf(data, "bbp length: %d\n", debug->bbp.word_count);
|
|
||||||
data += sprintf(data, "rf length: %d\n", debug->rf.word_count);
|
|
||||||
blob->size = strlen(blob->data);
|
|
||||||
|
|
||||||
return debugfs_create_blob(name, S_IRUGO, intf->driver_folder, blob);
|
|
||||||
}
|
|
||||||
|
|
||||||
void rt2x00debug_register(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
const struct rt2x00debug *debug = rt2x00dev->ops->debugfs;
|
|
||||||
struct rt2x00debug_intf *intf;
|
|
||||||
|
|
||||||
intf = kzalloc(sizeof(struct rt2x00debug_intf), GFP_KERNEL);
|
|
||||||
if (!intf) {
|
|
||||||
ERROR(rt2x00dev, "Failed to allocate debug handler.\n");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
intf->debug = debug;
|
|
||||||
intf->rt2x00dev = rt2x00dev;
|
|
||||||
rt2x00dev->debugfs_intf = intf;
|
|
||||||
|
|
||||||
intf->driver_folder =
|
|
||||||
debugfs_create_dir(intf->rt2x00dev->ops->name,
|
|
||||||
rt2x00dev->hw->wiphy->debugfsdir);
|
|
||||||
if (IS_ERR(intf->driver_folder))
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
intf->driver_entry =
|
|
||||||
rt2x00debug_create_file_driver("driver", intf, &intf->driver_blob);
|
|
||||||
if (IS_ERR(intf->driver_entry))
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
intf->chipset_entry =
|
|
||||||
rt2x00debug_create_file_chipset("chipset",
|
|
||||||
intf, &intf->chipset_blob);
|
|
||||||
if (IS_ERR(intf->chipset_entry))
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
intf->dev_flags = debugfs_create_file("dev_flags", S_IRUGO,
|
|
||||||
intf->driver_folder, intf,
|
|
||||||
&rt2x00debug_fop_dev_flags);
|
|
||||||
if (IS_ERR(intf->dev_flags))
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
#define RT2X00DEBUGFS_CREATE_ENTRY(__intf, __name) \
|
|
||||||
({ \
|
|
||||||
(__intf)->__name##_off_entry = \
|
|
||||||
debugfs_create_u32(__stringify(__name) "_offset", \
|
|
||||||
S_IRUGO | S_IWUSR, \
|
|
||||||
(__intf)->driver_folder, \
|
|
||||||
&(__intf)->offset_##__name); \
|
|
||||||
if (IS_ERR((__intf)->__name##_off_entry)) \
|
|
||||||
goto exit; \
|
|
||||||
\
|
|
||||||
(__intf)->__name##_val_entry = \
|
|
||||||
debugfs_create_file(__stringify(__name) "_value", \
|
|
||||||
S_IRUGO | S_IWUSR, \
|
|
||||||
(__intf)->driver_folder, \
|
|
||||||
(__intf), &rt2x00debug_fop_##__name);\
|
|
||||||
if (IS_ERR((__intf)->__name##_val_entry)) \
|
|
||||||
goto exit; \
|
|
||||||
})
|
|
||||||
|
|
||||||
RT2X00DEBUGFS_CREATE_ENTRY(intf, csr);
|
|
||||||
RT2X00DEBUGFS_CREATE_ENTRY(intf, eeprom);
|
|
||||||
RT2X00DEBUGFS_CREATE_ENTRY(intf, bbp);
|
|
||||||
RT2X00DEBUGFS_CREATE_ENTRY(intf, rf);
|
|
||||||
|
|
||||||
#undef RT2X00DEBUGFS_CREATE_ENTRY
|
|
||||||
|
|
||||||
return;
|
|
||||||
|
|
||||||
exit:
|
|
||||||
rt2x00debug_deregister(rt2x00dev);
|
|
||||||
ERROR(rt2x00dev, "Failed to register debug handler.\n");
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
void rt2x00debug_deregister(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
const struct rt2x00debug_intf *intf = rt2x00dev->debugfs_intf;
|
|
||||||
|
|
||||||
if (unlikely(!intf))
|
|
||||||
return;
|
|
||||||
|
|
||||||
debugfs_remove(intf->rf_val_entry);
|
|
||||||
debugfs_remove(intf->rf_off_entry);
|
|
||||||
debugfs_remove(intf->bbp_val_entry);
|
|
||||||
debugfs_remove(intf->bbp_off_entry);
|
|
||||||
debugfs_remove(intf->eeprom_val_entry);
|
|
||||||
debugfs_remove(intf->eeprom_off_entry);
|
|
||||||
debugfs_remove(intf->csr_val_entry);
|
|
||||||
debugfs_remove(intf->csr_off_entry);
|
|
||||||
debugfs_remove(intf->dev_flags);
|
|
||||||
debugfs_remove(intf->chipset_entry);
|
|
||||||
debugfs_remove(intf->driver_entry);
|
|
||||||
debugfs_remove(intf->driver_folder);
|
|
||||||
kfree(intf->chipset_blob.data);
|
|
||||||
kfree(intf->driver_blob.data);
|
|
||||||
kfree(intf);
|
|
||||||
|
|
||||||
rt2x00dev->debugfs_intf = NULL;
|
|
||||||
}
|
|
@ -1,57 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00debug
|
|
||||||
Abstract: Data structures for the rt2x00debug.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2X00DEBUG_H
|
|
||||||
#define RT2X00DEBUG_H
|
|
||||||
|
|
||||||
struct rt2x00_dev;
|
|
||||||
|
|
||||||
#define RT2X00DEBUGFS_REGISTER_ENTRY(__name, __type) \
|
|
||||||
struct reg##__name { \
|
|
||||||
void (*read)(const struct rt2x00_dev *rt2x00dev, \
|
|
||||||
const unsigned int word, __type *data); \
|
|
||||||
void (*write)(const struct rt2x00_dev *rt2x00dev, \
|
|
||||||
const unsigned int word, __type data); \
|
|
||||||
\
|
|
||||||
unsigned int word_size; \
|
|
||||||
unsigned int word_count; \
|
|
||||||
} __name
|
|
||||||
|
|
||||||
struct rt2x00debug {
|
|
||||||
/*
|
|
||||||
* Reference to the modules structure.
|
|
||||||
*/
|
|
||||||
struct module *owner;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Register access entries.
|
|
||||||
*/
|
|
||||||
RT2X00DEBUGFS_REGISTER_ENTRY(csr, u32);
|
|
||||||
RT2X00DEBUGFS_REGISTER_ENTRY(eeprom, u16);
|
|
||||||
RT2X00DEBUGFS_REGISTER_ENTRY(bbp, u8);
|
|
||||||
RT2X00DEBUGFS_REGISTER_ENTRY(rf, u32);
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif /* RT2X00DEBUG_H */
|
|
File diff suppressed because it is too large
Load Diff
@ -1,60 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00lib
|
|
||||||
Abstract: Data structures for the rt2x00lib module.
|
|
||||||
Supported chipsets: RT2460, RT2560, RT2570,
|
|
||||||
rt2561, rt2561s, rt2661, rt2571W & rt2671.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2X00DEV_H
|
|
||||||
#define RT2X00DEV_H
|
|
||||||
|
|
||||||
#include "rt2x00debug.h"
|
|
||||||
#include "rt2x00firmware.h"
|
|
||||||
#include "rt2x00rfkill.h"
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Radio control.
|
|
||||||
*/
|
|
||||||
int rt2x00lib_enable_radio(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_disable_radio(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_toggle_rx(struct rt2x00_dev *rt2x00dev, int enable);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Initialization/uninitialization handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00lib_initialize(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_uninitialize(struct rt2x00_dev *rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Config handlers.
|
|
||||||
*/
|
|
||||||
void rt2x00lib_config_type(struct rt2x00_dev *rt2x00dev, const int type);
|
|
||||||
void rt2x00lib_config_phymode(struct rt2x00_dev *rt2x00dev, const int phymode);
|
|
||||||
void rt2x00lib_config_channel(struct rt2x00_dev *rt2x00dev, const int value,
|
|
||||||
const int channel, const int freq, const int txpower);
|
|
||||||
void rt2x00lib_config_promisc(struct rt2x00_dev *rt2x00dev, const int promisc);
|
|
||||||
void rt2x00lib_config_txpower(struct rt2x00_dev *rt2x00dev, const int txpower);
|
|
||||||
void rt2x00lib_config_antenna(struct rt2x00_dev *rt2x00dev,
|
|
||||||
const int antenna_tx, const int antenna_rx);
|
|
||||||
|
|
||||||
#endif /* RT2X00DEV_H */
|
|
@ -1,124 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00lib
|
|
||||||
Abstract: rt2x00 firmware loading routines.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Set enviroment defines for rt2x00.h
|
|
||||||
*/
|
|
||||||
#define DRV_NAME "rt2x00lib"
|
|
||||||
|
|
||||||
#include <linux/crc-itu-t.h>
|
|
||||||
#include <linux/kernel.h>
|
|
||||||
#include <linux/module.h>
|
|
||||||
|
|
||||||
#include "rt2x00.h"
|
|
||||||
#include "rt2x00lib.h"
|
|
||||||
|
|
||||||
static int rt2x00lib_request_firmware(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
struct device *device = wiphy_dev(rt2x00dev->hw->wiphy);
|
|
||||||
const struct firmware *fw;
|
|
||||||
char *fw_name;
|
|
||||||
int retval;
|
|
||||||
u16 crc;
|
|
||||||
u16 tmp;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Read correct firmware from harddisk.
|
|
||||||
*/
|
|
||||||
fw_name = rt2x00dev->ops->lib->get_firmware_name(rt2x00dev);
|
|
||||||
if (!fw_name) {
|
|
||||||
ERROR(rt2x00dev,
|
|
||||||
"Invalid firmware filename.\n"
|
|
||||||
"Please file bug report to %s.\n", DRV_PROJECT);
|
|
||||||
return -EINVAL;
|
|
||||||
}
|
|
||||||
|
|
||||||
INFO(rt2x00dev, "Loading firmware file '%s'.\n", fw_name);
|
|
||||||
|
|
||||||
retval = request_firmware(&fw, fw_name, device);
|
|
||||||
if (retval) {
|
|
||||||
ERROR(rt2x00dev, "Failed to request Firmware.\n");
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!fw || !fw->size || !fw->data) {
|
|
||||||
ERROR(rt2x00dev, "Failed to read Firmware.\n");
|
|
||||||
return -ENOENT;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Validate the firmware using 16 bit CRC.
|
|
||||||
* The last 2 bytes of the firmware are the CRC
|
|
||||||
* so substract those 2 bytes from the CRC checksum,
|
|
||||||
* and set those 2 bytes to 0 when calculating CRC.
|
|
||||||
*/
|
|
||||||
tmp = 0;
|
|
||||||
crc = crc_itu_t(0, fw->data, fw->size - 2);
|
|
||||||
crc = crc_itu_t(crc, (u8 *)&tmp, 2);
|
|
||||||
|
|
||||||
if (crc != (fw->data[fw->size - 2] << 8 | fw->data[fw->size - 1])) {
|
|
||||||
ERROR(rt2x00dev, "Firmware CRC error.\n");
|
|
||||||
retval = -ENOENT;
|
|
||||||
goto exit;
|
|
||||||
}
|
|
||||||
|
|
||||||
INFO(rt2x00dev, "Firmware detected - version: %d.%d.\n",
|
|
||||||
fw->data[fw->size - 4], fw->data[fw->size - 3]);
|
|
||||||
|
|
||||||
rt2x00dev->fw = fw;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
exit:
|
|
||||||
release_firmware(fw);
|
|
||||||
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
|
|
||||||
int rt2x00lib_load_firmware(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
int retval;
|
|
||||||
|
|
||||||
if (!rt2x00dev->fw) {
|
|
||||||
retval = rt2x00lib_request_firmware(rt2x00dev);
|
|
||||||
if (retval)
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Send firmware to the device.
|
|
||||||
*/
|
|
||||||
retval = rt2x00dev->ops->lib->load_firmware(rt2x00dev,
|
|
||||||
rt2x00dev->fw->data,
|
|
||||||
rt2x00dev->fw->size);
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
|
|
||||||
void rt2x00lib_free_firmware(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
release_firmware(rt2x00dev->fw);
|
|
||||||
rt2x00dev->fw = NULL;
|
|
||||||
}
|
|
||||||
|
|
@ -1,49 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00lib
|
|
||||||
Abstract: Data structures for the firmware loader.
|
|
||||||
Supported chipsets: rt2561, rt2561s, rt2661, rt2571W & rt2671.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2X00FIRMWARE_H
|
|
||||||
#define RT2X00FIRMWARE_H
|
|
||||||
|
|
||||||
#ifdef CONFIG_RT2X00_LIB_FIRMWARE
|
|
||||||
int rt2x00lib_load_firmware(struct rt2x00_dev *rt2x00dev);
|
|
||||||
int rt2x00lib_load_firmware_wait(struct rt2x00_dev *rt2x00dev);
|
|
||||||
#else /* CONFIG_RT2X00_LIB_FIRMWARE */
|
|
||||||
static inline int rt2x00lib_load_firmware(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
/*
|
|
||||||
* This shouldn't happen.
|
|
||||||
*/
|
|
||||||
BUG();
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline int rt2x00lib_load_firmware_wait(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
#endif /* CONFIG_RT2X00_LIB_FIRMWARE */
|
|
||||||
|
|
||||||
#endif /* RT2X00FIRMWARE_H */
|
|
@ -1,119 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00lib
|
|
||||||
Abstract: Data structures and definitions for the rt2x00lib module.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2X00LIB_H
|
|
||||||
#define RT2X00LIB_H
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Interval defines
|
|
||||||
* Both the link tuner as the rfkill will be called once per second.
|
|
||||||
*/
|
|
||||||
#define LINK_TUNE_INTERVAL ( round_jiffies_relative(HZ) )
|
|
||||||
#define RFKILL_POLL_INTERVAL ( 1000 )
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Radio control handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00lib_enable_radio(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_disable_radio(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_toggle_rx(struct rt2x00_dev *rt2x00dev, enum dev_state state);
|
|
||||||
void rt2x00lib_reset_link_tuner(struct rt2x00_dev *rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Initialization handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00lib_initialize(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_uninitialize(struct rt2x00_dev *rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Configuration handlers.
|
|
||||||
*/
|
|
||||||
void rt2x00lib_config_mac_addr(struct rt2x00_dev *rt2x00dev, u8 *mac);
|
|
||||||
void rt2x00lib_config_bssid(struct rt2x00_dev *rt2x00dev, u8 *bssid);
|
|
||||||
void rt2x00lib_config_type(struct rt2x00_dev *rt2x00dev, const int type);
|
|
||||||
void rt2x00lib_config(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct ieee80211_conf *conf, const int force_config);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Firmware handlers.
|
|
||||||
*/
|
|
||||||
#ifdef CONFIG_RT2X00_LIB_FIRMWARE
|
|
||||||
int rt2x00lib_load_firmware(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_free_firmware(struct rt2x00_dev *rt2x00dev);
|
|
||||||
#else
|
|
||||||
static inline int rt2x00lib_load_firmware(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
static inline void rt2x00lib_free_firmware(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
#endif /* CONFIG_RT2X00_LIB_FIRMWARE */
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Debugfs handlers.
|
|
||||||
*/
|
|
||||||
#ifdef CONFIG_RT2X00_LIB_DEBUGFS
|
|
||||||
void rt2x00debug_register(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00debug_deregister(struct rt2x00_dev *rt2x00dev);
|
|
||||||
#else
|
|
||||||
static inline void rt2x00debug_register(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00debug_deregister(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
#endif /* CONFIG_RT2X00_LIB_DEBUGFS */
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RFkill handlers.
|
|
||||||
*/
|
|
||||||
#ifdef CONFIG_RT2X00_LIB_RFKILL
|
|
||||||
int rt2x00rfkill_register(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00rfkill_unregister(struct rt2x00_dev *rt2x00dev);
|
|
||||||
int rt2x00rfkill_allocate(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00rfkill_free(struct rt2x00_dev *rt2x00dev);
|
|
||||||
#else
|
|
||||||
static inline int rt2x00rfkill_register(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00rfkill_unregister(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline int rt2x00rfkill_allocate(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00rfkill_free(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
#endif /* CONFIG_RT2X00_LIB_RFKILL */
|
|
||||||
|
|
||||||
#endif /* RT2X00LIB_H */
|
|
@ -1,446 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00mac
|
|
||||||
Abstract: rt2x00 generic mac80211 routines.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Set enviroment defines for rt2x00.h
|
|
||||||
*/
|
|
||||||
#define DRV_NAME "rt2x00lib"
|
|
||||||
|
|
||||||
#include <linux/kernel.h>
|
|
||||||
#include <linux/module.h>
|
|
||||||
|
|
||||||
#include "rt2x00.h"
|
|
||||||
#include "rt2x00lib.h"
|
|
||||||
|
|
||||||
static int rt2x00mac_tx_rts_cts(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_ring *ring,
|
|
||||||
struct sk_buff *frag_skb,
|
|
||||||
struct ieee80211_tx_control *control)
|
|
||||||
{
|
|
||||||
struct sk_buff *skb;
|
|
||||||
int size;
|
|
||||||
|
|
||||||
if (control->flags & IEEE80211_TXCTL_USE_CTS_PROTECT)
|
|
||||||
size = sizeof(struct ieee80211_cts);
|
|
||||||
else
|
|
||||||
size = sizeof(struct ieee80211_rts);
|
|
||||||
|
|
||||||
skb = dev_alloc_skb(size + rt2x00dev->hw->extra_tx_headroom);
|
|
||||||
if (!skb) {
|
|
||||||
WARNING(rt2x00dev, "Failed to create RTS/CTS frame.\n");
|
|
||||||
return NETDEV_TX_BUSY;
|
|
||||||
}
|
|
||||||
|
|
||||||
skb_reserve(skb, rt2x00dev->hw->extra_tx_headroom);
|
|
||||||
skb_put(skb, size);
|
|
||||||
|
|
||||||
if (control->flags & IEEE80211_TXCTL_USE_CTS_PROTECT)
|
|
||||||
ieee80211_ctstoself_get(rt2x00dev->hw, rt2x00dev->interface.id,
|
|
||||||
frag_skb->data, frag_skb->len, control,
|
|
||||||
(struct ieee80211_cts *)(skb->data));
|
|
||||||
else
|
|
||||||
ieee80211_rts_get(rt2x00dev->hw, rt2x00dev->interface.id,
|
|
||||||
frag_skb->data, frag_skb->len, control,
|
|
||||||
(struct ieee80211_rts *)(skb->data));
|
|
||||||
|
|
||||||
if (rt2x00dev->ops->lib->write_tx_data(rt2x00dev, ring, skb, control)) {
|
|
||||||
WARNING(rt2x00dev, "Failed to send RTS/CTS frame.\n");
|
|
||||||
return NETDEV_TX_BUSY;
|
|
||||||
}
|
|
||||||
|
|
||||||
return NETDEV_TX_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
int rt2x00mac_tx(struct ieee80211_hw *hw, struct sk_buff *skb,
|
|
||||||
struct ieee80211_tx_control *control)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
struct ieee80211_hdr *ieee80211hdr = (struct ieee80211_hdr *)skb->data;
|
|
||||||
struct data_ring *ring;
|
|
||||||
u16 frame_control;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Mac80211 might be calling this function while we are trying
|
|
||||||
* to remove the device or perhaps suspending it.
|
|
||||||
* Note that we can only stop the TX queues inside the TX path
|
|
||||||
* due to possible race conditions in mac80211.
|
|
||||||
*/
|
|
||||||
if (!test_bit(DEVICE_PRESENT, &rt2x00dev->flags)) {
|
|
||||||
ieee80211_stop_queues(hw);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Determine which ring to put packet on.
|
|
||||||
*/
|
|
||||||
ring = rt2x00lib_get_ring(rt2x00dev, control->queue);
|
|
||||||
if (unlikely(!ring)) {
|
|
||||||
ERROR(rt2x00dev,
|
|
||||||
"Attempt to send packet over invalid queue %d.\n"
|
|
||||||
"Please file bug report to %s.\n",
|
|
||||||
control->queue, DRV_PROJECT);
|
|
||||||
dev_kfree_skb_any(skb);
|
|
||||||
return NETDEV_TX_OK;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If CTS/RTS is required. and this frame is not CTS or RTS,
|
|
||||||
* create and queue that frame first. But make sure we have
|
|
||||||
* at least enough entries available to send this CTS/RTS
|
|
||||||
* frame as well as the data frame.
|
|
||||||
*/
|
|
||||||
frame_control = le16_to_cpu(ieee80211hdr->frame_control);
|
|
||||||
if (!is_rts_frame(frame_control) && !is_cts_frame(frame_control) &&
|
|
||||||
(control->flags & (IEEE80211_TXCTL_USE_RTS_CTS |
|
|
||||||
IEEE80211_TXCTL_USE_CTS_PROTECT))) {
|
|
||||||
if (rt2x00_ring_free(ring) <= 1)
|
|
||||||
return NETDEV_TX_BUSY;
|
|
||||||
|
|
||||||
if (rt2x00mac_tx_rts_cts(rt2x00dev, ring, skb, control))
|
|
||||||
return NETDEV_TX_BUSY;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (rt2x00dev->ops->lib->write_tx_data(rt2x00dev, ring, skb, control))
|
|
||||||
return NETDEV_TX_BUSY;
|
|
||||||
|
|
||||||
if (rt2x00dev->ops->lib->kick_tx_queue)
|
|
||||||
rt2x00dev->ops->lib->kick_tx_queue(rt2x00dev, control->queue);
|
|
||||||
|
|
||||||
return NETDEV_TX_OK;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_tx);
|
|
||||||
|
|
||||||
int rt2x00mac_start(struct ieee80211_hw *hw)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
int status;
|
|
||||||
|
|
||||||
if (!test_bit(DEVICE_PRESENT, &rt2x00dev->flags) ||
|
|
||||||
test_bit(DEVICE_STARTED, &rt2x00dev->flags))
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If this is the first interface which is added,
|
|
||||||
* we should load the firmware now.
|
|
||||||
*/
|
|
||||||
if (test_bit(DRIVER_REQUIRE_FIRMWARE, &rt2x00dev->flags)) {
|
|
||||||
status = rt2x00lib_load_firmware(rt2x00dev);
|
|
||||||
if (status)
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Initialize the device.
|
|
||||||
*/
|
|
||||||
status = rt2x00lib_initialize(rt2x00dev);
|
|
||||||
if (status)
|
|
||||||
return status;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Enable radio.
|
|
||||||
*/
|
|
||||||
status = rt2x00lib_enable_radio(rt2x00dev);
|
|
||||||
if (status) {
|
|
||||||
rt2x00lib_uninitialize(rt2x00dev);
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
|
|
||||||
__set_bit(DEVICE_STARTED, &rt2x00dev->flags);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_start);
|
|
||||||
|
|
||||||
void rt2x00mac_stop(struct ieee80211_hw *hw)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
|
|
||||||
if (!test_bit(DEVICE_PRESENT, &rt2x00dev->flags))
|
|
||||||
return;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Perhaps we can add something smarter here,
|
|
||||||
* but for now just disabling the radio should do.
|
|
||||||
*/
|
|
||||||
rt2x00lib_disable_radio(rt2x00dev);
|
|
||||||
|
|
||||||
__clear_bit(DEVICE_STARTED, &rt2x00dev->flags);
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_stop);
|
|
||||||
|
|
||||||
int rt2x00mac_add_interface(struct ieee80211_hw *hw,
|
|
||||||
struct ieee80211_if_init_conf *conf)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
struct interface *intf = &rt2x00dev->interface;
|
|
||||||
|
|
||||||
/* FIXME: Beaconing is broken in rt2x00. */
|
|
||||||
if (conf->type == IEEE80211_IF_TYPE_IBSS ||
|
|
||||||
conf->type == IEEE80211_IF_TYPE_AP) {
|
|
||||||
ERROR(rt2x00dev,
|
|
||||||
"rt2x00 does not support Adhoc or Master mode");
|
|
||||||
return -EOPNOTSUPP;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Don't allow interfaces to be added while
|
|
||||||
* either the device has disappeared or when
|
|
||||||
* another interface is already present.
|
|
||||||
*/
|
|
||||||
if (!test_bit(DEVICE_PRESENT, &rt2x00dev->flags) ||
|
|
||||||
is_interface_present(intf))
|
|
||||||
return -ENOBUFS;
|
|
||||||
|
|
||||||
intf->id = conf->if_id;
|
|
||||||
intf->type = conf->type;
|
|
||||||
if (conf->type == IEEE80211_IF_TYPE_AP)
|
|
||||||
memcpy(&intf->bssid, conf->mac_addr, ETH_ALEN);
|
|
||||||
memcpy(&intf->mac, conf->mac_addr, ETH_ALEN);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* The MAC adddress must be configured after the device
|
|
||||||
* has been initialized. Otherwise the device can reset
|
|
||||||
* the MAC registers.
|
|
||||||
*/
|
|
||||||
rt2x00lib_config_mac_addr(rt2x00dev, intf->mac);
|
|
||||||
rt2x00lib_config_type(rt2x00dev, conf->type);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_add_interface);
|
|
||||||
|
|
||||||
void rt2x00mac_remove_interface(struct ieee80211_hw *hw,
|
|
||||||
struct ieee80211_if_init_conf *conf)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
struct interface *intf = &rt2x00dev->interface;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Don't allow interfaces to be remove while
|
|
||||||
* either the device has disappeared or when
|
|
||||||
* no interface is present.
|
|
||||||
*/
|
|
||||||
if (!test_bit(DEVICE_PRESENT, &rt2x00dev->flags) ||
|
|
||||||
!is_interface_present(intf))
|
|
||||||
return;
|
|
||||||
|
|
||||||
intf->id = 0;
|
|
||||||
intf->type = INVALID_INTERFACE;
|
|
||||||
memset(&intf->bssid, 0x00, ETH_ALEN);
|
|
||||||
memset(&intf->mac, 0x00, ETH_ALEN);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Make sure the bssid and mac address registers
|
|
||||||
* are cleared to prevent false ACKing of frames.
|
|
||||||
*/
|
|
||||||
rt2x00lib_config_mac_addr(rt2x00dev, intf->mac);
|
|
||||||
rt2x00lib_config_bssid(rt2x00dev, intf->bssid);
|
|
||||||
rt2x00lib_config_type(rt2x00dev, intf->type);
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_remove_interface);
|
|
||||||
|
|
||||||
int rt2x00mac_config(struct ieee80211_hw *hw, struct ieee80211_conf *conf)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Mac80211 might be calling this function while we are trying
|
|
||||||
* to remove the device or perhaps suspending it.
|
|
||||||
*/
|
|
||||||
if (!test_bit(DEVICE_PRESENT, &rt2x00dev->flags))
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Check if we need to disable the radio,
|
|
||||||
* if this is not the case, at least the RX must be disabled.
|
|
||||||
*/
|
|
||||||
if (test_bit(DEVICE_ENABLED_RADIO, &rt2x00dev->flags)) {
|
|
||||||
if (!conf->radio_enabled)
|
|
||||||
rt2x00lib_disable_radio(rt2x00dev);
|
|
||||||
else
|
|
||||||
rt2x00lib_toggle_rx(rt2x00dev, STATE_RADIO_RX_OFF);
|
|
||||||
}
|
|
||||||
|
|
||||||
rt2x00lib_config(rt2x00dev, conf, 0);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Reenable RX only if the radio should be on.
|
|
||||||
*/
|
|
||||||
if (test_bit(DEVICE_ENABLED_RADIO, &rt2x00dev->flags))
|
|
||||||
rt2x00lib_toggle_rx(rt2x00dev, STATE_RADIO_RX_ON);
|
|
||||||
else if (conf->radio_enabled)
|
|
||||||
return rt2x00lib_enable_radio(rt2x00dev);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_config);
|
|
||||||
|
|
||||||
int rt2x00mac_config_interface(struct ieee80211_hw *hw, int if_id,
|
|
||||||
struct ieee80211_if_conf *conf)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
struct interface *intf = &rt2x00dev->interface;
|
|
||||||
int status;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Mac80211 might be calling this function while we are trying
|
|
||||||
* to remove the device or perhaps suspending it.
|
|
||||||
*/
|
|
||||||
if (!test_bit(DEVICE_PRESENT, &rt2x00dev->flags))
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If the given type does not match the configured type,
|
|
||||||
* there has been a problem.
|
|
||||||
*/
|
|
||||||
if (conf->type != intf->type)
|
|
||||||
return -EINVAL;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If the interface does not work in master mode,
|
|
||||||
* then the bssid value in the interface structure
|
|
||||||
* should now be set.
|
|
||||||
*/
|
|
||||||
if (conf->type != IEEE80211_IF_TYPE_AP)
|
|
||||||
memcpy(&intf->bssid, conf->bssid, ETH_ALEN);
|
|
||||||
rt2x00lib_config_bssid(rt2x00dev, intf->bssid);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* We only need to initialize the beacon when master mode is enabled.
|
|
||||||
*/
|
|
||||||
if (conf->type != IEEE80211_IF_TYPE_AP || !conf->beacon)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
status = rt2x00dev->ops->hw->beacon_update(rt2x00dev->hw,
|
|
||||||
conf->beacon,
|
|
||||||
conf->beacon_control);
|
|
||||||
if (status)
|
|
||||||
dev_kfree_skb(conf->beacon);
|
|
||||||
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_config_interface);
|
|
||||||
|
|
||||||
int rt2x00mac_get_stats(struct ieee80211_hw *hw,
|
|
||||||
struct ieee80211_low_level_stats *stats)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* The dot11ACKFailureCount, dot11RTSFailureCount and
|
|
||||||
* dot11RTSSuccessCount are updated in interrupt time.
|
|
||||||
* dot11FCSErrorCount is updated in the link tuner.
|
|
||||||
*/
|
|
||||||
memcpy(stats, &rt2x00dev->low_level_stats, sizeof(*stats));
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_get_stats);
|
|
||||||
|
|
||||||
int rt2x00mac_get_tx_stats(struct ieee80211_hw *hw,
|
|
||||||
struct ieee80211_tx_queue_stats *stats)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
for (i = 0; i < hw->queues; i++)
|
|
||||||
memcpy(&stats->data[i], &rt2x00dev->tx[i].stats,
|
|
||||||
sizeof(rt2x00dev->tx[i].stats));
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_get_tx_stats);
|
|
||||||
|
|
||||||
void rt2x00mac_erp_ie_changed(struct ieee80211_hw *hw, u8 changes,
|
|
||||||
int cts_protection, int preamble)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
int short_preamble;
|
|
||||||
int ack_timeout;
|
|
||||||
int ack_consume_time;
|
|
||||||
int difs;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* We only support changing preamble mode.
|
|
||||||
*/
|
|
||||||
if (!(changes & IEEE80211_ERP_CHANGE_PREAMBLE))
|
|
||||||
return;
|
|
||||||
|
|
||||||
short_preamble = !preamble;
|
|
||||||
preamble = !!(preamble) ? PREAMBLE : SHORT_PREAMBLE;
|
|
||||||
|
|
||||||
difs = (hw->conf.flags & IEEE80211_CONF_SHORT_SLOT_TIME) ?
|
|
||||||
SHORT_DIFS : DIFS;
|
|
||||||
ack_timeout = difs + PLCP + preamble + get_duration(ACK_SIZE, 10);
|
|
||||||
|
|
||||||
ack_consume_time = SIFS + PLCP + preamble + get_duration(ACK_SIZE, 10);
|
|
||||||
|
|
||||||
if (short_preamble)
|
|
||||||
__set_bit(CONFIG_SHORT_PREAMBLE, &rt2x00dev->flags);
|
|
||||||
else
|
|
||||||
__clear_bit(CONFIG_SHORT_PREAMBLE, &rt2x00dev->flags);
|
|
||||||
|
|
||||||
rt2x00dev->ops->lib->config_preamble(rt2x00dev, short_preamble,
|
|
||||||
ack_timeout, ack_consume_time);
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_erp_ie_changed);
|
|
||||||
|
|
||||||
int rt2x00mac_conf_tx(struct ieee80211_hw *hw, int queue,
|
|
||||||
const struct ieee80211_tx_queue_params *params)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
struct data_ring *ring;
|
|
||||||
|
|
||||||
ring = rt2x00lib_get_ring(rt2x00dev, queue);
|
|
||||||
if (unlikely(!ring))
|
|
||||||
return -EINVAL;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* The passed variables are stored as real value ((2^n)-1).
|
|
||||||
* Ralink registers require to know the bit number 'n'.
|
|
||||||
*/
|
|
||||||
if (params->cw_min)
|
|
||||||
ring->tx_params.cw_min = fls(params->cw_min);
|
|
||||||
else
|
|
||||||
ring->tx_params.cw_min = 5; /* cw_min: 2^5 = 32. */
|
|
||||||
|
|
||||||
if (params->cw_max)
|
|
||||||
ring->tx_params.cw_max = fls(params->cw_max);
|
|
||||||
else
|
|
||||||
ring->tx_params.cw_max = 10; /* cw_min: 2^10 = 1024. */
|
|
||||||
|
|
||||||
if (params->aifs)
|
|
||||||
ring->tx_params.aifs = params->aifs;
|
|
||||||
else
|
|
||||||
ring->tx_params.aifs = 2;
|
|
||||||
|
|
||||||
INFO(rt2x00dev,
|
|
||||||
"Configured TX ring %d - CWmin: %d, CWmax: %d, Aifs: %d.\n",
|
|
||||||
queue, ring->tx_params.cw_min, ring->tx_params.cw_max,
|
|
||||||
ring->tx_params.aifs);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00mac_conf_tx);
|
|
@ -1,486 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00pci
|
|
||||||
Abstract: rt2x00 generic pci device routines.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Set enviroment defines for rt2x00.h
|
|
||||||
*/
|
|
||||||
#define DRV_NAME "rt2x00pci"
|
|
||||||
|
|
||||||
#include <linux/dma-mapping.h>
|
|
||||||
#include <linux/kernel.h>
|
|
||||||
#include <linux/module.h>
|
|
||||||
#include <linux/pci.h>
|
|
||||||
|
|
||||||
#include "rt2x00.h"
|
|
||||||
#include "rt2x00pci.h"
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Beacon handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00pci_beacon_update(struct ieee80211_hw *hw, struct sk_buff *skb,
|
|
||||||
struct ieee80211_tx_control *control)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
struct data_ring *ring =
|
|
||||||
rt2x00lib_get_ring(rt2x00dev, IEEE80211_TX_QUEUE_BEACON);
|
|
||||||
struct data_entry *entry = rt2x00_get_data_entry(ring);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Just in case mac80211 doesn't set this correctly,
|
|
||||||
* but we need this queue set for the descriptor
|
|
||||||
* initialization.
|
|
||||||
*/
|
|
||||||
control->queue = IEEE80211_TX_QUEUE_BEACON;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Update the beacon entry.
|
|
||||||
*/
|
|
||||||
memcpy(entry->data_addr, skb->data, skb->len);
|
|
||||||
rt2x00lib_write_tx_desc(rt2x00dev, entry->priv,
|
|
||||||
(struct ieee80211_hdr *)skb->data,
|
|
||||||
skb->len, control);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Enable beacon generation.
|
|
||||||
*/
|
|
||||||
rt2x00dev->ops->lib->kick_tx_queue(rt2x00dev, control->queue);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00pci_beacon_update);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX data handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00pci_write_tx_data(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_ring *ring, struct sk_buff *skb,
|
|
||||||
struct ieee80211_tx_control *control)
|
|
||||||
{
|
|
||||||
struct ieee80211_hdr *ieee80211hdr = (struct ieee80211_hdr *)skb->data;
|
|
||||||
struct data_entry *entry = rt2x00_get_data_entry(ring);
|
|
||||||
struct data_desc *txd = entry->priv;
|
|
||||||
u32 word;
|
|
||||||
|
|
||||||
if (rt2x00_ring_full(ring)) {
|
|
||||||
ieee80211_stop_queue(rt2x00dev->hw, control->queue);
|
|
||||||
return -EINVAL;
|
|
||||||
}
|
|
||||||
|
|
||||||
rt2x00_desc_read(txd, 0, &word);
|
|
||||||
|
|
||||||
if (rt2x00_get_field32(word, TXD_ENTRY_OWNER_NIC) ||
|
|
||||||
rt2x00_get_field32(word, TXD_ENTRY_VALID)) {
|
|
||||||
ERROR(rt2x00dev,
|
|
||||||
"Arrived at non-free entry in the non-full queue %d.\n"
|
|
||||||
"Please file bug report to %s.\n",
|
|
||||||
control->queue, DRV_PROJECT);
|
|
||||||
ieee80211_stop_queue(rt2x00dev->hw, control->queue);
|
|
||||||
return -EINVAL;
|
|
||||||
}
|
|
||||||
|
|
||||||
entry->skb = skb;
|
|
||||||
memcpy(&entry->tx_status.control, control, sizeof(*control));
|
|
||||||
memcpy(entry->data_addr, skb->data, skb->len);
|
|
||||||
rt2x00lib_write_tx_desc(rt2x00dev, txd, ieee80211hdr,
|
|
||||||
skb->len, control);
|
|
||||||
|
|
||||||
rt2x00_ring_index_inc(ring);
|
|
||||||
|
|
||||||
if (rt2x00_ring_full(ring))
|
|
||||||
ieee80211_stop_queue(rt2x00dev->hw, control->queue);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00pci_write_tx_data);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RX data handlers.
|
|
||||||
*/
|
|
||||||
void rt2x00pci_rxdone(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
struct data_ring *ring = rt2x00dev->rx;
|
|
||||||
struct data_entry *entry;
|
|
||||||
struct data_desc *rxd;
|
|
||||||
struct sk_buff *skb;
|
|
||||||
struct ieee80211_hdr *hdr;
|
|
||||||
struct rxdata_entry_desc desc;
|
|
||||||
int header_size;
|
|
||||||
int align;
|
|
||||||
u32 word;
|
|
||||||
|
|
||||||
while (1) {
|
|
||||||
entry = rt2x00_get_data_entry(ring);
|
|
||||||
rxd = entry->priv;
|
|
||||||
rt2x00_desc_read(rxd, 0, &word);
|
|
||||||
|
|
||||||
if (rt2x00_get_field32(word, RXD_ENTRY_OWNER_NIC))
|
|
||||||
break;
|
|
||||||
|
|
||||||
memset(&desc, 0x00, sizeof(desc));
|
|
||||||
rt2x00dev->ops->lib->fill_rxdone(entry, &desc);
|
|
||||||
|
|
||||||
hdr = (struct ieee80211_hdr *)entry->data_addr;
|
|
||||||
header_size =
|
|
||||||
ieee80211_get_hdrlen(le16_to_cpu(hdr->frame_control));
|
|
||||||
|
|
||||||
/*
|
|
||||||
* The data behind the ieee80211 header must be
|
|
||||||
* aligned on a 4 byte boundary.
|
|
||||||
*/
|
|
||||||
align = header_size % 4;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Allocate the sk_buffer, initialize it and copy
|
|
||||||
* all data into it.
|
|
||||||
*/
|
|
||||||
skb = dev_alloc_skb(desc.size + align);
|
|
||||||
if (!skb)
|
|
||||||
return;
|
|
||||||
|
|
||||||
skb_reserve(skb, align);
|
|
||||||
memcpy(skb_put(skb, desc.size), entry->data_addr, desc.size);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Send the frame to rt2x00lib for further processing.
|
|
||||||
*/
|
|
||||||
rt2x00lib_rxdone(entry, skb, &desc);
|
|
||||||
|
|
||||||
if (test_bit(DEVICE_ENABLED_RADIO, &ring->rt2x00dev->flags)) {
|
|
||||||
rt2x00_set_field32(&word, RXD_ENTRY_OWNER_NIC, 1);
|
|
||||||
rt2x00_desc_write(rxd, 0, word);
|
|
||||||
}
|
|
||||||
|
|
||||||
rt2x00_ring_index_inc(ring);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00pci_rxdone);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device initialization handlers.
|
|
||||||
*/
|
|
||||||
#define priv_offset(__ring, __i) \
|
|
||||||
({ \
|
|
||||||
ring->data_addr + (i * ring->desc_size); \
|
|
||||||
})
|
|
||||||
|
|
||||||
#define data_addr_offset(__ring, __i) \
|
|
||||||
({ \
|
|
||||||
(__ring)->data_addr + \
|
|
||||||
((__ring)->stats.limit * (__ring)->desc_size) + \
|
|
||||||
((__i) * (__ring)->data_size); \
|
|
||||||
})
|
|
||||||
|
|
||||||
#define data_dma_offset(__ring, __i) \
|
|
||||||
({ \
|
|
||||||
(__ring)->data_dma + \
|
|
||||||
((__ring)->stats.limit * (__ring)->desc_size) + \
|
|
||||||
((__i) * (__ring)->data_size); \
|
|
||||||
})
|
|
||||||
|
|
||||||
static int rt2x00pci_alloc_dma(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_ring *ring)
|
|
||||||
{
|
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Allocate DMA memory for descriptor and buffer.
|
|
||||||
*/
|
|
||||||
ring->data_addr = pci_alloc_consistent(rt2x00dev_pci(rt2x00dev),
|
|
||||||
rt2x00_get_ring_size(ring),
|
|
||||||
&ring->data_dma);
|
|
||||||
if (!ring->data_addr)
|
|
||||||
return -ENOMEM;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Initialize all ring entries to contain valid
|
|
||||||
* addresses.
|
|
||||||
*/
|
|
||||||
for (i = 0; i < ring->stats.limit; i++) {
|
|
||||||
ring->entry[i].priv = priv_offset(ring, i);
|
|
||||||
ring->entry[i].data_addr = data_addr_offset(ring, i);
|
|
||||||
ring->entry[i].data_dma = data_dma_offset(ring, i);
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void rt2x00pci_free_dma(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_ring *ring)
|
|
||||||
{
|
|
||||||
if (ring->data_addr)
|
|
||||||
pci_free_consistent(rt2x00dev_pci(rt2x00dev),
|
|
||||||
rt2x00_get_ring_size(ring),
|
|
||||||
ring->data_addr, ring->data_dma);
|
|
||||||
ring->data_addr = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
int rt2x00pci_initialize(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
struct pci_dev *pci_dev = rt2x00dev_pci(rt2x00dev);
|
|
||||||
struct data_ring *ring;
|
|
||||||
int status;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Allocate DMA
|
|
||||||
*/
|
|
||||||
ring_for_each(rt2x00dev, ring) {
|
|
||||||
status = rt2x00pci_alloc_dma(rt2x00dev, ring);
|
|
||||||
if (status)
|
|
||||||
goto exit;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Register interrupt handler.
|
|
||||||
*/
|
|
||||||
status = request_irq(pci_dev->irq, rt2x00dev->ops->lib->irq_handler,
|
|
||||||
IRQF_SHARED, pci_name(pci_dev), rt2x00dev);
|
|
||||||
if (status) {
|
|
||||||
ERROR(rt2x00dev, "IRQ %d allocation failed (error %d).\n",
|
|
||||||
pci_dev->irq, status);
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
exit:
|
|
||||||
rt2x00pci_uninitialize(rt2x00dev);
|
|
||||||
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00pci_initialize);
|
|
||||||
|
|
||||||
void rt2x00pci_uninitialize(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
struct data_ring *ring;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Free irq line.
|
|
||||||
*/
|
|
||||||
free_irq(rt2x00dev_pci(rt2x00dev)->irq, rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Free DMA
|
|
||||||
*/
|
|
||||||
ring_for_each(rt2x00dev, ring)
|
|
||||||
rt2x00pci_free_dma(rt2x00dev, ring);
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00pci_uninitialize);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PCI driver handlers.
|
|
||||||
*/
|
|
||||||
static void rt2x00pci_free_reg(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
kfree(rt2x00dev->rf);
|
|
||||||
rt2x00dev->rf = NULL;
|
|
||||||
|
|
||||||
kfree(rt2x00dev->eeprom);
|
|
||||||
rt2x00dev->eeprom = NULL;
|
|
||||||
|
|
||||||
if (rt2x00dev->csr_addr) {
|
|
||||||
iounmap(rt2x00dev->csr_addr);
|
|
||||||
rt2x00dev->csr_addr = NULL;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static int rt2x00pci_alloc_reg(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
struct pci_dev *pci_dev = rt2x00dev_pci(rt2x00dev);
|
|
||||||
|
|
||||||
rt2x00dev->csr_addr = ioremap(pci_resource_start(pci_dev, 0),
|
|
||||||
pci_resource_len(pci_dev, 0));
|
|
||||||
if (!rt2x00dev->csr_addr)
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
rt2x00dev->eeprom = kzalloc(rt2x00dev->ops->eeprom_size, GFP_KERNEL);
|
|
||||||
if (!rt2x00dev->eeprom)
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
rt2x00dev->rf = kzalloc(rt2x00dev->ops->rf_size, GFP_KERNEL);
|
|
||||||
if (!rt2x00dev->rf)
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
exit:
|
|
||||||
ERROR_PROBE("Failed to allocate registers.\n");
|
|
||||||
|
|
||||||
rt2x00pci_free_reg(rt2x00dev);
|
|
||||||
|
|
||||||
return -ENOMEM;
|
|
||||||
}
|
|
||||||
|
|
||||||
int rt2x00pci_probe(struct pci_dev *pci_dev, const struct pci_device_id *id)
|
|
||||||
{
|
|
||||||
struct rt2x00_ops *ops = (struct rt2x00_ops *)id->driver_data;
|
|
||||||
struct ieee80211_hw *hw;
|
|
||||||
struct rt2x00_dev *rt2x00dev;
|
|
||||||
int retval;
|
|
||||||
|
|
||||||
retval = pci_request_regions(pci_dev, pci_name(pci_dev));
|
|
||||||
if (retval) {
|
|
||||||
ERROR_PROBE("PCI request regions failed.\n");
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
|
|
||||||
retval = pci_enable_device(pci_dev);
|
|
||||||
if (retval) {
|
|
||||||
ERROR_PROBE("Enable device failed.\n");
|
|
||||||
goto exit_release_regions;
|
|
||||||
}
|
|
||||||
|
|
||||||
pci_set_master(pci_dev);
|
|
||||||
|
|
||||||
if (pci_set_mwi(pci_dev))
|
|
||||||
ERROR_PROBE("MWI not available.\n");
|
|
||||||
|
|
||||||
if (pci_set_dma_mask(pci_dev, DMA_64BIT_MASK) &&
|
|
||||||
pci_set_dma_mask(pci_dev, DMA_32BIT_MASK)) {
|
|
||||||
ERROR_PROBE("PCI DMA not supported.\n");
|
|
||||||
retval = -EIO;
|
|
||||||
goto exit_disable_device;
|
|
||||||
}
|
|
||||||
|
|
||||||
hw = ieee80211_alloc_hw(sizeof(struct rt2x00_dev), ops->hw);
|
|
||||||
if (!hw) {
|
|
||||||
ERROR_PROBE("Failed to allocate hardware.\n");
|
|
||||||
retval = -ENOMEM;
|
|
||||||
goto exit_disable_device;
|
|
||||||
}
|
|
||||||
|
|
||||||
pci_set_drvdata(pci_dev, hw);
|
|
||||||
|
|
||||||
rt2x00dev = hw->priv;
|
|
||||||
rt2x00dev->dev = pci_dev;
|
|
||||||
rt2x00dev->ops = ops;
|
|
||||||
rt2x00dev->hw = hw;
|
|
||||||
|
|
||||||
retval = rt2x00pci_alloc_reg(rt2x00dev);
|
|
||||||
if (retval)
|
|
||||||
goto exit_free_device;
|
|
||||||
|
|
||||||
retval = rt2x00lib_probe_dev(rt2x00dev);
|
|
||||||
if (retval)
|
|
||||||
goto exit_free_reg;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
exit_free_reg:
|
|
||||||
rt2x00pci_free_reg(rt2x00dev);
|
|
||||||
|
|
||||||
exit_free_device:
|
|
||||||
ieee80211_free_hw(hw);
|
|
||||||
|
|
||||||
exit_disable_device:
|
|
||||||
if (retval != -EBUSY)
|
|
||||||
pci_disable_device(pci_dev);
|
|
||||||
|
|
||||||
exit_release_regions:
|
|
||||||
pci_release_regions(pci_dev);
|
|
||||||
|
|
||||||
pci_set_drvdata(pci_dev, NULL);
|
|
||||||
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00pci_probe);
|
|
||||||
|
|
||||||
void rt2x00pci_remove(struct pci_dev *pci_dev)
|
|
||||||
{
|
|
||||||
struct ieee80211_hw *hw = pci_get_drvdata(pci_dev);
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Free all allocated data.
|
|
||||||
*/
|
|
||||||
rt2x00lib_remove_dev(rt2x00dev);
|
|
||||||
rt2x00pci_free_reg(rt2x00dev);
|
|
||||||
ieee80211_free_hw(hw);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Free the PCI device data.
|
|
||||||
*/
|
|
||||||
pci_set_drvdata(pci_dev, NULL);
|
|
||||||
pci_disable_device(pci_dev);
|
|
||||||
pci_release_regions(pci_dev);
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00pci_remove);
|
|
||||||
|
|
||||||
#ifdef CONFIG_PM
|
|
||||||
int rt2x00pci_suspend(struct pci_dev *pci_dev, pm_message_t state)
|
|
||||||
{
|
|
||||||
struct ieee80211_hw *hw = pci_get_drvdata(pci_dev);
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
int retval;
|
|
||||||
|
|
||||||
retval = rt2x00lib_suspend(rt2x00dev, state);
|
|
||||||
if (retval)
|
|
||||||
return retval;
|
|
||||||
|
|
||||||
rt2x00pci_free_reg(rt2x00dev);
|
|
||||||
|
|
||||||
pci_save_state(pci_dev);
|
|
||||||
pci_disable_device(pci_dev);
|
|
||||||
return pci_set_power_state(pci_dev, pci_choose_state(pci_dev, state));
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00pci_suspend);
|
|
||||||
|
|
||||||
int rt2x00pci_resume(struct pci_dev *pci_dev)
|
|
||||||
{
|
|
||||||
struct ieee80211_hw *hw = pci_get_drvdata(pci_dev);
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
int retval;
|
|
||||||
|
|
||||||
if (pci_set_power_state(pci_dev, PCI_D0) ||
|
|
||||||
pci_enable_device(pci_dev) ||
|
|
||||||
pci_restore_state(pci_dev)) {
|
|
||||||
ERROR(rt2x00dev, "Failed to resume device.\n");
|
|
||||||
return -EIO;
|
|
||||||
}
|
|
||||||
|
|
||||||
retval = rt2x00pci_alloc_reg(rt2x00dev);
|
|
||||||
if (retval)
|
|
||||||
return retval;
|
|
||||||
|
|
||||||
retval = rt2x00lib_resume(rt2x00dev);
|
|
||||||
if (retval)
|
|
||||||
goto exit_free_reg;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
exit_free_reg:
|
|
||||||
rt2x00pci_free_reg(rt2x00dev);
|
|
||||||
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00pci_resume);
|
|
||||||
#endif /* CONFIG_PM */
|
|
||||||
|
|
||||||
/*
|
|
||||||
* rt2x00pci module information.
|
|
||||||
*/
|
|
||||||
MODULE_AUTHOR(DRV_PROJECT);
|
|
||||||
MODULE_VERSION(DRV_VERSION);
|
|
||||||
MODULE_DESCRIPTION("rt2x00 library");
|
|
||||||
MODULE_LICENSE("GPL");
|
|
@ -1,127 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00pci
|
|
||||||
Abstract: Data structures for the rt2x00pci module.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2X00PCI_H
|
|
||||||
#define RT2X00PCI_H
|
|
||||||
|
|
||||||
#include <linux/io.h>
|
|
||||||
|
|
||||||
/*
|
|
||||||
* This variable should be used with the
|
|
||||||
* pci_driver structure initialization.
|
|
||||||
*/
|
|
||||||
#define PCI_DEVICE_DATA(__ops) .driver_data = (kernel_ulong_t)(__ops)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Register defines.
|
|
||||||
* Some registers require multiple attempts before success,
|
|
||||||
* in those cases REGISTER_BUSY_COUNT attempts should be
|
|
||||||
* taken with a REGISTER_BUSY_DELAY interval.
|
|
||||||
*/
|
|
||||||
#define REGISTER_BUSY_COUNT 5
|
|
||||||
#define REGISTER_BUSY_DELAY 100
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Descriptor availability flags.
|
|
||||||
* All PCI device descriptors have these 2 flags
|
|
||||||
* with the exact same definition.
|
|
||||||
* By storing them here we can use them inside rt2x00pci
|
|
||||||
* for some simple entry availability checking.
|
|
||||||
*/
|
|
||||||
#define TXD_ENTRY_OWNER_NIC FIELD32(0x00000001)
|
|
||||||
#define TXD_ENTRY_VALID FIELD32(0x00000002)
|
|
||||||
#define RXD_ENTRY_OWNER_NIC FIELD32(0x00000001)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Register access.
|
|
||||||
*/
|
|
||||||
static inline void rt2x00pci_register_read(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const unsigned long offset,
|
|
||||||
u32 *value)
|
|
||||||
{
|
|
||||||
*value = readl(rt2x00dev->csr_addr + offset);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void
|
|
||||||
rt2x00pci_register_multiread(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const unsigned long offset,
|
|
||||||
void *value, const u16 length)
|
|
||||||
{
|
|
||||||
memcpy_fromio(value, rt2x00dev->csr_addr + offset, length);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00pci_register_write(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const unsigned long offset,
|
|
||||||
u32 value)
|
|
||||||
{
|
|
||||||
writel(value, rt2x00dev->csr_addr + offset);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void
|
|
||||||
rt2x00pci_register_multiwrite(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const unsigned long offset,
|
|
||||||
void *value, const u16 length)
|
|
||||||
{
|
|
||||||
memcpy_toio(rt2x00dev->csr_addr + offset, value, length);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Beacon handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00pci_beacon_update(struct ieee80211_hw *hw, struct sk_buff *skb,
|
|
||||||
struct ieee80211_tx_control *control);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX data handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00pci_write_tx_data(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_ring *ring, struct sk_buff *skb,
|
|
||||||
struct ieee80211_tx_control *control);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RX data handlers.
|
|
||||||
*/
|
|
||||||
void rt2x00pci_rxdone(struct rt2x00_dev *rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device initialization handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00pci_initialize(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00pci_uninitialize(struct rt2x00_dev *rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PCI driver handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00pci_probe(struct pci_dev *pci_dev, const struct pci_device_id *id);
|
|
||||||
void rt2x00pci_remove(struct pci_dev *pci_dev);
|
|
||||||
#ifdef CONFIG_PM
|
|
||||||
int rt2x00pci_suspend(struct pci_dev *pci_dev, pm_message_t state);
|
|
||||||
int rt2x00pci_resume(struct pci_dev *pci_dev);
|
|
||||||
#else
|
|
||||||
#define rt2x00pci_suspend NULL
|
|
||||||
#define rt2x00pci_resume NULL
|
|
||||||
#endif /* CONFIG_PM */
|
|
||||||
|
|
||||||
#endif /* RT2X00PCI_H */
|
|
@ -1,292 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00
|
|
||||||
Abstract: rt2x00 generic register information.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2X00REG_H
|
|
||||||
#define RT2X00REG_H
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX result flags.
|
|
||||||
*/
|
|
||||||
enum TX_STATUS {
|
|
||||||
TX_SUCCESS = 0,
|
|
||||||
TX_SUCCESS_RETRY = 1,
|
|
||||||
TX_FAIL_RETRY = 2,
|
|
||||||
TX_FAIL_INVALID = 3,
|
|
||||||
TX_FAIL_OTHER = 4,
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Antenna values
|
|
||||||
*/
|
|
||||||
enum antenna {
|
|
||||||
ANTENNA_SW_DIVERSITY = 0,
|
|
||||||
ANTENNA_A = 1,
|
|
||||||
ANTENNA_B = 2,
|
|
||||||
ANTENNA_HW_DIVERSITY = 3,
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Led mode values.
|
|
||||||
*/
|
|
||||||
enum led_mode {
|
|
||||||
LED_MODE_DEFAULT = 0,
|
|
||||||
LED_MODE_TXRX_ACTIVITY = 1,
|
|
||||||
LED_MODE_SIGNAL_STRENGTH = 2,
|
|
||||||
LED_MODE_ASUS = 3,
|
|
||||||
LED_MODE_ALPHA = 4,
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TSF sync values
|
|
||||||
*/
|
|
||||||
enum tsf_sync {
|
|
||||||
TSF_SYNC_NONE = 0,
|
|
||||||
TSF_SYNC_INFRA = 1,
|
|
||||||
TSF_SYNC_BEACON = 2,
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device states
|
|
||||||
*/
|
|
||||||
enum dev_state {
|
|
||||||
STATE_DEEP_SLEEP = 0,
|
|
||||||
STATE_SLEEP = 1,
|
|
||||||
STATE_STANDBY = 2,
|
|
||||||
STATE_AWAKE = 3,
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Additional device states, these values are
|
|
||||||
* not strict since they are not directly passed
|
|
||||||
* into the device.
|
|
||||||
*/
|
|
||||||
STATE_RADIO_ON,
|
|
||||||
STATE_RADIO_OFF,
|
|
||||||
STATE_RADIO_RX_ON,
|
|
||||||
STATE_RADIO_RX_OFF,
|
|
||||||
STATE_RADIO_IRQ_ON,
|
|
||||||
STATE_RADIO_IRQ_OFF,
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* IFS backoff values
|
|
||||||
*/
|
|
||||||
enum ifs {
|
|
||||||
IFS_BACKOFF = 0,
|
|
||||||
IFS_SIFS = 1,
|
|
||||||
IFS_NEW_BACKOFF = 2,
|
|
||||||
IFS_NONE = 3,
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Cipher types for hardware encryption
|
|
||||||
*/
|
|
||||||
enum cipher {
|
|
||||||
CIPHER_NONE = 0,
|
|
||||||
CIPHER_WEP64 = 1,
|
|
||||||
CIPHER_WEP128 = 2,
|
|
||||||
CIPHER_TKIP = 3,
|
|
||||||
CIPHER_AES = 4,
|
|
||||||
/*
|
|
||||||
* The following fields were added by rt61pci and rt73usb.
|
|
||||||
*/
|
|
||||||
CIPHER_CKIP64 = 5,
|
|
||||||
CIPHER_CKIP128 = 6,
|
|
||||||
CIPHER_TKIP_NO_MIC = 7,
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Register handlers.
|
|
||||||
* We store the position of a register field inside a field structure,
|
|
||||||
* This will simplify the process of setting and reading a certain field
|
|
||||||
* inside the register while making sure the process remains byte order safe.
|
|
||||||
*/
|
|
||||||
struct rt2x00_field8 {
|
|
||||||
u8 bit_offset;
|
|
||||||
u8 bit_mask;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct rt2x00_field16 {
|
|
||||||
u16 bit_offset;
|
|
||||||
u16 bit_mask;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct rt2x00_field32 {
|
|
||||||
u32 bit_offset;
|
|
||||||
u32 bit_mask;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Power of two check, this will check
|
|
||||||
* if the mask that has been given contains
|
|
||||||
* and contiguous set of bits.
|
|
||||||
*/
|
|
||||||
#define is_power_of_two(x) ( !((x) & ((x)-1)) )
|
|
||||||
#define low_bit_mask(x) ( ((x)-1) & ~(x) )
|
|
||||||
#define is_valid_mask(x) is_power_of_two(1 + (x) + low_bit_mask(x))
|
|
||||||
|
|
||||||
#define FIELD8(__mask) \
|
|
||||||
({ \
|
|
||||||
BUILD_BUG_ON(!(__mask) || \
|
|
||||||
!is_valid_mask(__mask) || \
|
|
||||||
(__mask) != (u8)(__mask)); \
|
|
||||||
(struct rt2x00_field8) { \
|
|
||||||
__ffs(__mask), (__mask) \
|
|
||||||
}; \
|
|
||||||
})
|
|
||||||
|
|
||||||
#define FIELD16(__mask) \
|
|
||||||
({ \
|
|
||||||
BUILD_BUG_ON(!(__mask) || \
|
|
||||||
!is_valid_mask(__mask) || \
|
|
||||||
(__mask) != (u16)(__mask));\
|
|
||||||
(struct rt2x00_field16) { \
|
|
||||||
__ffs(__mask), (__mask) \
|
|
||||||
}; \
|
|
||||||
})
|
|
||||||
|
|
||||||
#define FIELD32(__mask) \
|
|
||||||
({ \
|
|
||||||
BUILD_BUG_ON(!(__mask) || \
|
|
||||||
!is_valid_mask(__mask) || \
|
|
||||||
(__mask) != (u32)(__mask));\
|
|
||||||
(struct rt2x00_field32) { \
|
|
||||||
__ffs(__mask), (__mask) \
|
|
||||||
}; \
|
|
||||||
})
|
|
||||||
|
|
||||||
static inline void rt2x00_set_field32(u32 *reg,
|
|
||||||
const struct rt2x00_field32 field,
|
|
||||||
const u32 value)
|
|
||||||
{
|
|
||||||
*reg &= ~(field.bit_mask);
|
|
||||||
*reg |= (value << field.bit_offset) & field.bit_mask;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline u32 rt2x00_get_field32(const u32 reg,
|
|
||||||
const struct rt2x00_field32 field)
|
|
||||||
{
|
|
||||||
return (reg & field.bit_mask) >> field.bit_offset;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00_set_field16(u16 *reg,
|
|
||||||
const struct rt2x00_field16 field,
|
|
||||||
const u16 value)
|
|
||||||
{
|
|
||||||
*reg &= ~(field.bit_mask);
|
|
||||||
*reg |= (value << field.bit_offset) & field.bit_mask;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline u16 rt2x00_get_field16(const u16 reg,
|
|
||||||
const struct rt2x00_field16 field)
|
|
||||||
{
|
|
||||||
return (reg & field.bit_mask) >> field.bit_offset;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00_set_field8(u8 *reg,
|
|
||||||
const struct rt2x00_field8 field,
|
|
||||||
const u8 value)
|
|
||||||
{
|
|
||||||
*reg &= ~(field.bit_mask);
|
|
||||||
*reg |= (value << field.bit_offset) & field.bit_mask;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline u8 rt2x00_get_field8(const u8 reg,
|
|
||||||
const struct rt2x00_field8 field)
|
|
||||||
{
|
|
||||||
return (reg & field.bit_mask) >> field.bit_offset;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device specific rate value.
|
|
||||||
* We will have to create the device specific rate value
|
|
||||||
* passed to the ieee80211 kernel. We need to make it a consist of
|
|
||||||
* multiple fields because we want to store more then 1 device specific
|
|
||||||
* values inside the value.
|
|
||||||
* 1 - rate, stored as 100 kbit/s.
|
|
||||||
* 2 - preamble, short_preamble enabled flag.
|
|
||||||
* 3 - MASK_RATE, which rates are enabled in this mode, this mask
|
|
||||||
* corresponds with the TX register format for the current device.
|
|
||||||
* 4 - plcp, 802.11b rates are device specific,
|
|
||||||
* 802.11g rates are set according to the ieee802.11a-1999 p.14.
|
|
||||||
* The bit to enable preamble is set in a seperate define.
|
|
||||||
*/
|
|
||||||
#define DEV_RATE FIELD32(0x000007ff)
|
|
||||||
#define DEV_PREAMBLE FIELD32(0x00000800)
|
|
||||||
#define DEV_RATEMASK FIELD32(0x00fff000)
|
|
||||||
#define DEV_PLCP FIELD32(0xff000000)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Bitfields
|
|
||||||
*/
|
|
||||||
#define DEV_RATEBIT_1MB ( 1 << 0 )
|
|
||||||
#define DEV_RATEBIT_2MB ( 1 << 1 )
|
|
||||||
#define DEV_RATEBIT_5_5MB ( 1 << 2 )
|
|
||||||
#define DEV_RATEBIT_11MB ( 1 << 3 )
|
|
||||||
#define DEV_RATEBIT_6MB ( 1 << 4 )
|
|
||||||
#define DEV_RATEBIT_9MB ( 1 << 5 )
|
|
||||||
#define DEV_RATEBIT_12MB ( 1 << 6 )
|
|
||||||
#define DEV_RATEBIT_18MB ( 1 << 7 )
|
|
||||||
#define DEV_RATEBIT_24MB ( 1 << 8 )
|
|
||||||
#define DEV_RATEBIT_36MB ( 1 << 9 )
|
|
||||||
#define DEV_RATEBIT_48MB ( 1 << 10 )
|
|
||||||
#define DEV_RATEBIT_54MB ( 1 << 11 )
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Bitmasks for DEV_RATEMASK
|
|
||||||
*/
|
|
||||||
#define DEV_RATEMASK_1MB ( (DEV_RATEBIT_1MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_2MB ( (DEV_RATEBIT_2MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_5_5MB ( (DEV_RATEBIT_5_5MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_11MB ( (DEV_RATEBIT_11MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_6MB ( (DEV_RATEBIT_6MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_9MB ( (DEV_RATEBIT_9MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_12MB ( (DEV_RATEBIT_12MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_18MB ( (DEV_RATEBIT_18MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_24MB ( (DEV_RATEBIT_24MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_36MB ( (DEV_RATEBIT_36MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_48MB ( (DEV_RATEBIT_48MB << 1) -1 )
|
|
||||||
#define DEV_RATEMASK_54MB ( (DEV_RATEBIT_54MB << 1) -1 )
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Bitmask groups of bitrates
|
|
||||||
*/
|
|
||||||
#define DEV_BASIC_RATEMASK \
|
|
||||||
( DEV_RATEMASK_11MB | \
|
|
||||||
DEV_RATEBIT_6MB | DEV_RATEBIT_12MB | DEV_RATEBIT_24MB )
|
|
||||||
|
|
||||||
#define DEV_CCK_RATEMASK ( DEV_RATEMASK_11MB )
|
|
||||||
#define DEV_OFDM_RATEMASK ( DEV_RATEMASK_54MB & ~DEV_CCK_RATEMASK )
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Macro's to set and get specific fields from the device specific val and val2
|
|
||||||
* fields inside the ieee80211_rate entry.
|
|
||||||
*/
|
|
||||||
#define DEVICE_SET_RATE_FIELD(__value, __mask) \
|
|
||||||
(int)( ((__value) << DEV_##__mask.bit_offset) & DEV_##__mask.bit_mask )
|
|
||||||
|
|
||||||
#define DEVICE_GET_RATE_FIELD(__value, __mask) \
|
|
||||||
(int)( ((__value) & DEV_##__mask.bit_mask) >> DEV_##__mask.bit_offset )
|
|
||||||
|
|
||||||
#endif /* RT2X00REG_H */
|
|
@ -1,146 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00rfkill
|
|
||||||
Abstract: rt2x00 rfkill routines.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Set enviroment defines for rt2x00.h
|
|
||||||
*/
|
|
||||||
#define DRV_NAME "rt2x00lib"
|
|
||||||
|
|
||||||
#include <linux/input-polldev.h>
|
|
||||||
#include <linux/kernel.h>
|
|
||||||
#include <linux/module.h>
|
|
||||||
#include <linux/rfkill.h>
|
|
||||||
|
|
||||||
#include "rt2x00.h"
|
|
||||||
#include "rt2x00lib.h"
|
|
||||||
|
|
||||||
static int rt2x00rfkill_toggle_radio(void *data, enum rfkill_state state)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = data;
|
|
||||||
int retval = 0;
|
|
||||||
|
|
||||||
if (unlikely(!rt2x00dev))
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Only continue if there are enabled interfaces.
|
|
||||||
*/
|
|
||||||
if (!test_bit(DEVICE_STARTED, &rt2x00dev->flags))
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if (state == RFKILL_STATE_ON) {
|
|
||||||
INFO(rt2x00dev, "Hardware button pressed, enabling radio.\n");
|
|
||||||
__clear_bit(DEVICE_DISABLED_RADIO_HW, &rt2x00dev->flags);
|
|
||||||
retval = rt2x00lib_enable_radio(rt2x00dev);
|
|
||||||
} else if (state == RFKILL_STATE_OFF) {
|
|
||||||
INFO(rt2x00dev, "Hardware button pressed, disabling radio.\n");
|
|
||||||
__set_bit(DEVICE_DISABLED_RADIO_HW, &rt2x00dev->flags);
|
|
||||||
rt2x00lib_disable_radio(rt2x00dev);
|
|
||||||
}
|
|
||||||
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void rt2x00rfkill_poll(struct input_polled_dev *poll_dev)
|
|
||||||
{
|
|
||||||
struct rt2x00_dev *rt2x00dev = poll_dev->private;
|
|
||||||
int state = rt2x00dev->ops->lib->rfkill_poll(rt2x00dev);
|
|
||||||
|
|
||||||
if (rt2x00dev->rfkill->state != state)
|
|
||||||
input_report_key(poll_dev->input, KEY_WLAN, 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
int rt2x00rfkill_register(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
int retval;
|
|
||||||
|
|
||||||
if (!test_bit(CONFIG_SUPPORT_HW_BUTTON, &rt2x00dev->flags))
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
retval = rfkill_register(rt2x00dev->rfkill);
|
|
||||||
if (retval) {
|
|
||||||
ERROR(rt2x00dev, "Failed to register rfkill handler.\n");
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
|
|
||||||
retval = input_register_polled_device(rt2x00dev->poll_dev);
|
|
||||||
if (retval) {
|
|
||||||
ERROR(rt2x00dev, "Failed to register polled device.\n");
|
|
||||||
rfkill_unregister(rt2x00dev->rfkill);
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void rt2x00rfkill_unregister(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
if (!test_bit(CONFIG_SUPPORT_HW_BUTTON, &rt2x00dev->flags))
|
|
||||||
return;
|
|
||||||
|
|
||||||
input_unregister_polled_device(rt2x00dev->poll_dev);
|
|
||||||
rfkill_unregister(rt2x00dev->rfkill);
|
|
||||||
}
|
|
||||||
|
|
||||||
int rt2x00rfkill_allocate(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
struct device *device = wiphy_dev(rt2x00dev->hw->wiphy);
|
|
||||||
|
|
||||||
if (!test_bit(CONFIG_SUPPORT_HW_BUTTON, &rt2x00dev->flags))
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
rt2x00dev->rfkill = rfkill_allocate(device, RFKILL_TYPE_WLAN);
|
|
||||||
if (!rt2x00dev->rfkill) {
|
|
||||||
ERROR(rt2x00dev, "Failed to allocate rfkill handler.\n");
|
|
||||||
return -ENOMEM;
|
|
||||||
}
|
|
||||||
|
|
||||||
rt2x00dev->rfkill->name = rt2x00dev->ops->name;
|
|
||||||
rt2x00dev->rfkill->data = rt2x00dev;
|
|
||||||
rt2x00dev->rfkill->state = rt2x00dev->ops->lib->rfkill_poll(rt2x00dev);
|
|
||||||
rt2x00dev->rfkill->toggle_radio = rt2x00rfkill_toggle_radio;
|
|
||||||
|
|
||||||
rt2x00dev->poll_dev = input_allocate_polled_device();
|
|
||||||
if (!rt2x00dev->poll_dev) {
|
|
||||||
ERROR(rt2x00dev, "Failed to allocate polled device.\n");
|
|
||||||
rfkill_free(rt2x00dev->rfkill);
|
|
||||||
return -ENOMEM;
|
|
||||||
}
|
|
||||||
|
|
||||||
rt2x00dev->poll_dev->private = rt2x00dev;
|
|
||||||
rt2x00dev->poll_dev->poll = rt2x00rfkill_poll;
|
|
||||||
rt2x00dev->poll_dev->poll_interval = RFKILL_POLL_INTERVAL;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void rt2x00rfkill_free(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
if (!test_bit(CONFIG_SUPPORT_HW_BUTTON, &rt2x00dev->flags))
|
|
||||||
return;
|
|
||||||
|
|
||||||
input_free_polled_device(rt2x00dev->poll_dev);
|
|
||||||
rfkill_free(rt2x00dev->rfkill);
|
|
||||||
}
|
|
@ -1,51 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00lib
|
|
||||||
Abstract: Data structures for the rfkill.
|
|
||||||
Supported chipsets: RT2460, RT2560, rt2561, rt2561s, rt2661.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2X00RFKILL_H
|
|
||||||
#define RT2X00RFKILL_H
|
|
||||||
|
|
||||||
#ifdef CONFIG_RT2X00_LIB_RFKILL
|
|
||||||
int rt2x00lib_register_rfkill(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_unregister_rfkill(struct rt2x00_dev *rt2x00dev);
|
|
||||||
int rt2x00lib_allocate_rfkill(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00lib_free_rfkill(struct rt2x00_dev *rt2x00dev);
|
|
||||||
#else /* CONFIG_RT2X00_LIB_RFKILL */
|
|
||||||
static inline int rt2x00lib_register_rfkill(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00lib_unregister_rfkill(struct rt2x00_dev *rt2x00dev){}
|
|
||||||
|
|
||||||
static inline int rt2x00lib_allocate_rfkill(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00lib_free_rfkill(struct rt2x00_dev *rt2x00dev){}
|
|
||||||
#endif /* CONFIG_RT2X00_LIB_RFKILL */
|
|
||||||
|
|
||||||
#endif /* RT2X00RFKILL_H */
|
|
@ -1,268 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00
|
|
||||||
Abstract: rt2x00 ring datastructures and routines
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2X00RING_H
|
|
||||||
#define RT2X00RING_H
|
|
||||||
|
|
||||||
/*
|
|
||||||
* data_desc
|
|
||||||
* Each data entry also contains a descriptor which is used by the
|
|
||||||
* device to determine what should be done with the packet and
|
|
||||||
* what the current status is.
|
|
||||||
* This structure is greatly simplified, but the descriptors
|
|
||||||
* are basically a list of little endian 32 bit values.
|
|
||||||
* Make the array by default 1 word big, this will allow us
|
|
||||||
* to use sizeof() correctly.
|
|
||||||
*/
|
|
||||||
struct data_desc {
|
|
||||||
__le32 word[1];
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* rxdata_entry_desc
|
|
||||||
* Summary of information that has been read from the
|
|
||||||
* RX frame descriptor.
|
|
||||||
*/
|
|
||||||
struct rxdata_entry_desc {
|
|
||||||
int signal;
|
|
||||||
int rssi;
|
|
||||||
int ofdm;
|
|
||||||
int size;
|
|
||||||
int flags;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* txdata_entry_desc
|
|
||||||
* Summary of information that should be written into the
|
|
||||||
* descriptor for sending a TX frame.
|
|
||||||
*/
|
|
||||||
struct txdata_entry_desc {
|
|
||||||
unsigned long flags;
|
|
||||||
#define ENTRY_TXDONE 1
|
|
||||||
#define ENTRY_TXD_RTS_FRAME 2
|
|
||||||
#define ENTRY_TXD_OFDM_RATE 3
|
|
||||||
#define ENTRY_TXD_MORE_FRAG 4
|
|
||||||
#define ENTRY_TXD_REQ_TIMESTAMP 5
|
|
||||||
#define ENTRY_TXD_BURST 6
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Queue ID. ID's 0-4 are data TX rings
|
|
||||||
*/
|
|
||||||
int queue;
|
|
||||||
#define QUEUE_MGMT 13
|
|
||||||
#define QUEUE_RX 14
|
|
||||||
#define QUEUE_OTHER 15
|
|
||||||
|
|
||||||
/*
|
|
||||||
* PLCP values.
|
|
||||||
*/
|
|
||||||
u16 length_high;
|
|
||||||
u16 length_low;
|
|
||||||
u16 signal;
|
|
||||||
u16 service;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Timing information
|
|
||||||
*/
|
|
||||||
int aifs;
|
|
||||||
int ifs;
|
|
||||||
int cw_min;
|
|
||||||
int cw_max;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* data_entry
|
|
||||||
* The data ring is a list of data entries.
|
|
||||||
* Each entry holds a reference to the descriptor
|
|
||||||
* and the data buffer. For TX rings the reference to the
|
|
||||||
* sk_buff of the packet being transmitted is also stored here.
|
|
||||||
*/
|
|
||||||
struct data_entry {
|
|
||||||
/*
|
|
||||||
* Status flags
|
|
||||||
*/
|
|
||||||
unsigned long flags;
|
|
||||||
#define ENTRY_OWNER_NIC 1
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Ring we belong to.
|
|
||||||
*/
|
|
||||||
struct data_ring *ring;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* sk_buff for the packet which is being transmitted
|
|
||||||
* in this entry (Only used with TX related rings).
|
|
||||||
*/
|
|
||||||
struct sk_buff *skb;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Store a ieee80211_tx_status structure in each
|
|
||||||
* ring entry, this will optimize the txdone
|
|
||||||
* handler.
|
|
||||||
*/
|
|
||||||
struct ieee80211_tx_status tx_status;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* private pointer specific to driver.
|
|
||||||
*/
|
|
||||||
void *priv;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Data address for this entry.
|
|
||||||
*/
|
|
||||||
void *data_addr;
|
|
||||||
dma_addr_t data_dma;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* data_ring
|
|
||||||
* Data rings are used by the device to send and receive packets.
|
|
||||||
* The data_addr is the base address of the data memory.
|
|
||||||
* To determine at which point in the ring we are,
|
|
||||||
* have to use the rt2x00_ring_index_*() functions.
|
|
||||||
*/
|
|
||||||
struct data_ring {
|
|
||||||
/*
|
|
||||||
* Pointer to main rt2x00dev structure where this
|
|
||||||
* ring belongs to.
|
|
||||||
*/
|
|
||||||
struct rt2x00_dev *rt2x00dev;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Base address for the device specific data entries.
|
|
||||||
*/
|
|
||||||
struct data_entry *entry;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX queue statistic info.
|
|
||||||
*/
|
|
||||||
struct ieee80211_tx_queue_stats_data stats;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX Queue parameters.
|
|
||||||
*/
|
|
||||||
struct ieee80211_tx_queue_params tx_params;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Base address for data ring.
|
|
||||||
*/
|
|
||||||
dma_addr_t data_dma;
|
|
||||||
void *data_addr;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Index variables.
|
|
||||||
*/
|
|
||||||
u16 index;
|
|
||||||
u16 index_done;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Size of packet and descriptor in bytes.
|
|
||||||
*/
|
|
||||||
u16 data_size;
|
|
||||||
u16 desc_size;
|
|
||||||
};
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Handlers to determine the address of the current device specific
|
|
||||||
* data entry, where either index or index_done points to.
|
|
||||||
*/
|
|
||||||
static inline struct data_entry *rt2x00_get_data_entry(struct data_ring *ring)
|
|
||||||
{
|
|
||||||
return &ring->entry[ring->index];
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline struct data_entry *rt2x00_get_data_entry_done(struct data_ring
|
|
||||||
*ring)
|
|
||||||
{
|
|
||||||
return &ring->entry[ring->index_done];
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Total ring memory
|
|
||||||
*/
|
|
||||||
static inline int rt2x00_get_ring_size(struct data_ring *ring)
|
|
||||||
{
|
|
||||||
return ring->stats.limit * (ring->desc_size + ring->data_size);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Ring index manipulation functions.
|
|
||||||
*/
|
|
||||||
static inline void rt2x00_ring_index_inc(struct data_ring *ring)
|
|
||||||
{
|
|
||||||
ring->index++;
|
|
||||||
if (ring->index >= ring->stats.limit)
|
|
||||||
ring->index = 0;
|
|
||||||
ring->stats.len++;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00_ring_index_done_inc(struct data_ring *ring)
|
|
||||||
{
|
|
||||||
ring->index_done++;
|
|
||||||
if (ring->index_done >= ring->stats.limit)
|
|
||||||
ring->index_done = 0;
|
|
||||||
ring->stats.len--;
|
|
||||||
ring->stats.count++;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00_ring_index_clear(struct data_ring *ring)
|
|
||||||
{
|
|
||||||
ring->index = 0;
|
|
||||||
ring->index_done = 0;
|
|
||||||
ring->stats.len = 0;
|
|
||||||
ring->stats.count = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline int rt2x00_ring_empty(struct data_ring *ring)
|
|
||||||
{
|
|
||||||
return ring->stats.len == 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline int rt2x00_ring_full(struct data_ring *ring)
|
|
||||||
{
|
|
||||||
return ring->stats.len == ring->stats.limit;
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline int rt2x00_ring_free(struct data_ring *ring)
|
|
||||||
{
|
|
||||||
return ring->stats.limit - ring->stats.len;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX/RX Descriptor access functions.
|
|
||||||
*/
|
|
||||||
static inline void rt2x00_desc_read(struct data_desc *desc,
|
|
||||||
const u8 word, u32 *value)
|
|
||||||
{
|
|
||||||
*value = le32_to_cpu(desc->word[word]);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline void rt2x00_desc_write(struct data_desc *desc,
|
|
||||||
const u8 word, const u32 value)
|
|
||||||
{
|
|
||||||
desc->word[word] = cpu_to_le32(value);
|
|
||||||
}
|
|
||||||
|
|
||||||
#endif /* RT2X00RING_H */
|
|
@ -1,615 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00usb
|
|
||||||
Abstract: rt2x00 generic usb device routines.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Set enviroment defines for rt2x00.h
|
|
||||||
*/
|
|
||||||
#define DRV_NAME "rt2x00usb"
|
|
||||||
|
|
||||||
#include <linux/kernel.h>
|
|
||||||
#include <linux/module.h>
|
|
||||||
#include <linux/usb.h>
|
|
||||||
|
|
||||||
#include "rt2x00.h"
|
|
||||||
#include "rt2x00usb.h"
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Interfacing with the HW.
|
|
||||||
*/
|
|
||||||
int rt2x00usb_vendor_request(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const u8 request, const u8 requesttype,
|
|
||||||
const u16 offset, const u16 value,
|
|
||||||
void *buffer, const u16 buffer_length,
|
|
||||||
const int timeout)
|
|
||||||
{
|
|
||||||
struct usb_device *usb_dev =
|
|
||||||
interface_to_usbdev(rt2x00dev_usb(rt2x00dev));
|
|
||||||
int status;
|
|
||||||
unsigned int i;
|
|
||||||
unsigned int pipe =
|
|
||||||
(requesttype == USB_VENDOR_REQUEST_IN) ?
|
|
||||||
usb_rcvctrlpipe(usb_dev, 0) : usb_sndctrlpipe(usb_dev, 0);
|
|
||||||
|
|
||||||
for (i = 0; i < REGISTER_BUSY_COUNT; i++) {
|
|
||||||
status = usb_control_msg(usb_dev, pipe, request, requesttype,
|
|
||||||
value, offset, buffer, buffer_length,
|
|
||||||
timeout);
|
|
||||||
if (status >= 0)
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Check for errors
|
|
||||||
* -ENODEV: Device has disappeared, no point continuing.
|
|
||||||
* All other errors: Try again.
|
|
||||||
*/
|
|
||||||
else if (status == -ENODEV)
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
ERROR(rt2x00dev,
|
|
||||||
"Vendor Request 0x%02x failed for offset 0x%04x with error %d.\n",
|
|
||||||
request, offset, status);
|
|
||||||
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_vendor_request);
|
|
||||||
|
|
||||||
int rt2x00usb_vendor_request_buff(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const u8 request, const u8 requesttype,
|
|
||||||
const u16 offset, void *buffer,
|
|
||||||
const u16 buffer_length, const int timeout)
|
|
||||||
{
|
|
||||||
int status;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Check for Cache availability.
|
|
||||||
*/
|
|
||||||
if (unlikely(!rt2x00dev->csr_cache || buffer_length > CSR_CACHE_SIZE)) {
|
|
||||||
ERROR(rt2x00dev, "CSR cache not available.\n");
|
|
||||||
return -ENOMEM;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (requesttype == USB_VENDOR_REQUEST_OUT)
|
|
||||||
memcpy(rt2x00dev->csr_cache, buffer, buffer_length);
|
|
||||||
|
|
||||||
status = rt2x00usb_vendor_request(rt2x00dev, request, requesttype,
|
|
||||||
offset, 0, rt2x00dev->csr_cache,
|
|
||||||
buffer_length, timeout);
|
|
||||||
|
|
||||||
if (!status && requesttype == USB_VENDOR_REQUEST_IN)
|
|
||||||
memcpy(buffer, rt2x00dev->csr_cache, buffer_length);
|
|
||||||
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_vendor_request_buff);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX data handlers.
|
|
||||||
*/
|
|
||||||
static void rt2x00usb_interrupt_txdone(struct urb *urb)
|
|
||||||
{
|
|
||||||
struct data_entry *entry = (struct data_entry *)urb->context;
|
|
||||||
struct data_ring *ring = entry->ring;
|
|
||||||
struct rt2x00_dev *rt2x00dev = ring->rt2x00dev;
|
|
||||||
struct data_desc *txd = (struct data_desc *)entry->skb->data;
|
|
||||||
u32 word;
|
|
||||||
int tx_status;
|
|
||||||
|
|
||||||
if (!test_bit(DEVICE_ENABLED_RADIO, &rt2x00dev->flags) ||
|
|
||||||
!__test_and_clear_bit(ENTRY_OWNER_NIC, &entry->flags))
|
|
||||||
return;
|
|
||||||
|
|
||||||
rt2x00_desc_read(txd, 0, &word);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Remove the descriptor data from the buffer.
|
|
||||||
*/
|
|
||||||
skb_pull(entry->skb, ring->desc_size);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Obtain the status about this packet.
|
|
||||||
*/
|
|
||||||
tx_status = !urb->status ? TX_SUCCESS : TX_FAIL_RETRY;
|
|
||||||
|
|
||||||
rt2x00lib_txdone(entry, tx_status, 0);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Make this entry available for reuse.
|
|
||||||
*/
|
|
||||||
entry->flags = 0;
|
|
||||||
rt2x00_ring_index_done_inc(entry->ring);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* If the data ring was full before the txdone handler
|
|
||||||
* we must make sure the packet queue in the mac80211 stack
|
|
||||||
* is reenabled when the txdone handler has finished.
|
|
||||||
*/
|
|
||||||
if (!rt2x00_ring_full(ring))
|
|
||||||
ieee80211_wake_queue(rt2x00dev->hw,
|
|
||||||
entry->tx_status.control.queue);
|
|
||||||
}
|
|
||||||
|
|
||||||
int rt2x00usb_write_tx_data(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_ring *ring, struct sk_buff *skb,
|
|
||||||
struct ieee80211_tx_control *control)
|
|
||||||
{
|
|
||||||
struct usb_device *usb_dev =
|
|
||||||
interface_to_usbdev(rt2x00dev_usb(rt2x00dev));
|
|
||||||
struct data_entry *entry = rt2x00_get_data_entry(ring);
|
|
||||||
int pipe = usb_sndbulkpipe(usb_dev, 1);
|
|
||||||
u32 length;
|
|
||||||
|
|
||||||
if (rt2x00_ring_full(ring)) {
|
|
||||||
ieee80211_stop_queue(rt2x00dev->hw, control->queue);
|
|
||||||
return -EINVAL;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (test_bit(ENTRY_OWNER_NIC, &entry->flags)) {
|
|
||||||
ERROR(rt2x00dev,
|
|
||||||
"Arrived at non-free entry in the non-full queue %d.\n"
|
|
||||||
"Please file bug report to %s.\n",
|
|
||||||
control->queue, DRV_PROJECT);
|
|
||||||
ieee80211_stop_queue(rt2x00dev->hw, control->queue);
|
|
||||||
return -EINVAL;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Add the descriptor in front of the skb.
|
|
||||||
*/
|
|
||||||
skb_push(skb, ring->desc_size);
|
|
||||||
memset(skb->data, 0, ring->desc_size);
|
|
||||||
|
|
||||||
rt2x00lib_write_tx_desc(rt2x00dev, (struct data_desc *)skb->data,
|
|
||||||
(struct ieee80211_hdr *)(skb->data +
|
|
||||||
ring->desc_size),
|
|
||||||
skb->len - ring->desc_size, control);
|
|
||||||
memcpy(&entry->tx_status.control, control, sizeof(*control));
|
|
||||||
entry->skb = skb;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* USB devices cannot blindly pass the skb->len as the
|
|
||||||
* length of the data to usb_fill_bulk_urb. Pass the skb
|
|
||||||
* to the driver to determine what the length should be.
|
|
||||||
*/
|
|
||||||
length = rt2x00dev->ops->lib->get_tx_data_len(rt2x00dev, skb);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Initialize URB and send the frame to the device.
|
|
||||||
*/
|
|
||||||
__set_bit(ENTRY_OWNER_NIC, &entry->flags);
|
|
||||||
usb_fill_bulk_urb(entry->priv, usb_dev, pipe,
|
|
||||||
skb->data, length, rt2x00usb_interrupt_txdone, entry);
|
|
||||||
usb_submit_urb(entry->priv, GFP_ATOMIC);
|
|
||||||
|
|
||||||
rt2x00_ring_index_inc(ring);
|
|
||||||
|
|
||||||
if (rt2x00_ring_full(ring))
|
|
||||||
ieee80211_stop_queue(rt2x00dev->hw, control->queue);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_write_tx_data);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* RX data handlers.
|
|
||||||
*/
|
|
||||||
static void rt2x00usb_interrupt_rxdone(struct urb *urb)
|
|
||||||
{
|
|
||||||
struct data_entry *entry = (struct data_entry *)urb->context;
|
|
||||||
struct data_ring *ring = entry->ring;
|
|
||||||
struct rt2x00_dev *rt2x00dev = ring->rt2x00dev;
|
|
||||||
struct sk_buff *skb;
|
|
||||||
struct ieee80211_hdr *hdr;
|
|
||||||
struct rxdata_entry_desc desc;
|
|
||||||
int header_size;
|
|
||||||
int frame_size;
|
|
||||||
|
|
||||||
if (!test_bit(DEVICE_ENABLED_RADIO, &rt2x00dev->flags) ||
|
|
||||||
!test_and_clear_bit(ENTRY_OWNER_NIC, &entry->flags))
|
|
||||||
return;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Check if the received data is simply too small
|
|
||||||
* to be actually valid, or if the urb is signaling
|
|
||||||
* a problem.
|
|
||||||
*/
|
|
||||||
if (urb->actual_length < entry->ring->desc_size || urb->status)
|
|
||||||
goto skip_entry;
|
|
||||||
|
|
||||||
memset(&desc, 0x00, sizeof(desc));
|
|
||||||
rt2x00dev->ops->lib->fill_rxdone(entry, &desc);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Allocate a new sk buffer to replace the current one.
|
|
||||||
* If allocation fails, we should drop the current frame
|
|
||||||
* so we can recycle the existing sk buffer for the new frame.
|
|
||||||
* As alignment we use 2 and not NET_IP_ALIGN because we need
|
|
||||||
* to be sure we have 2 bytes room in the head. (NET_IP_ALIGN
|
|
||||||
* can be 0 on some hardware). We use these 2 bytes for frame
|
|
||||||
* alignment later, we assume that the chance that
|
|
||||||
* header_size % 4 == 2 is bigger then header_size % 2 == 0
|
|
||||||
* and thus optimize alignment by reserving the 2 bytes in
|
|
||||||
* advance.
|
|
||||||
*/
|
|
||||||
frame_size = entry->ring->data_size + entry->ring->desc_size;
|
|
||||||
skb = dev_alloc_skb(frame_size + 2);
|
|
||||||
if (!skb)
|
|
||||||
goto skip_entry;
|
|
||||||
|
|
||||||
skb_reserve(skb, 2);
|
|
||||||
skb_put(skb, frame_size);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* The data behind the ieee80211 header must be
|
|
||||||
* aligned on a 4 byte boundary.
|
|
||||||
* After that trim the entire buffer down to only
|
|
||||||
* contain the valid frame data excluding the device
|
|
||||||
* descriptor.
|
|
||||||
*/
|
|
||||||
hdr = (struct ieee80211_hdr *)entry->skb->data;
|
|
||||||
header_size =
|
|
||||||
ieee80211_get_hdrlen(le16_to_cpu(hdr->frame_control));
|
|
||||||
|
|
||||||
if (header_size % 4 == 0) {
|
|
||||||
skb_push(entry->skb, 2);
|
|
||||||
memmove(entry->skb->data, entry->skb->data + 2, skb->len - 2);
|
|
||||||
}
|
|
||||||
skb_trim(entry->skb, desc.size);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Send the frame to rt2x00lib for further processing.
|
|
||||||
*/
|
|
||||||
rt2x00lib_rxdone(entry, entry->skb, &desc);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Replace current entry's skb with the newly allocated one,
|
|
||||||
* and reinitialize the urb.
|
|
||||||
*/
|
|
||||||
entry->skb = skb;
|
|
||||||
urb->transfer_buffer = entry->skb->data;
|
|
||||||
urb->transfer_buffer_length = entry->skb->len;
|
|
||||||
|
|
||||||
skip_entry:
|
|
||||||
if (test_bit(DEVICE_ENABLED_RADIO, &ring->rt2x00dev->flags)) {
|
|
||||||
__set_bit(ENTRY_OWNER_NIC, &entry->flags);
|
|
||||||
usb_submit_urb(urb, GFP_ATOMIC);
|
|
||||||
}
|
|
||||||
|
|
||||||
rt2x00_ring_index_inc(ring);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Radio handlers
|
|
||||||
*/
|
|
||||||
void rt2x00usb_enable_radio(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
struct usb_device *usb_dev =
|
|
||||||
interface_to_usbdev(rt2x00dev_usb(rt2x00dev));
|
|
||||||
struct data_ring *ring;
|
|
||||||
struct data_entry *entry;
|
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Initialize the TX rings
|
|
||||||
*/
|
|
||||||
txringall_for_each(rt2x00dev, ring) {
|
|
||||||
for (i = 0; i < ring->stats.limit; i++)
|
|
||||||
ring->entry[i].flags = 0;
|
|
||||||
|
|
||||||
rt2x00_ring_index_clear(ring);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Initialize and start the RX ring.
|
|
||||||
*/
|
|
||||||
rt2x00_ring_index_clear(rt2x00dev->rx);
|
|
||||||
|
|
||||||
for (i = 0; i < rt2x00dev->rx->stats.limit; i++) {
|
|
||||||
entry = &rt2x00dev->rx->entry[i];
|
|
||||||
|
|
||||||
usb_fill_bulk_urb(entry->priv, usb_dev,
|
|
||||||
usb_rcvbulkpipe(usb_dev, 1),
|
|
||||||
entry->skb->data, entry->skb->len,
|
|
||||||
rt2x00usb_interrupt_rxdone, entry);
|
|
||||||
|
|
||||||
__set_bit(ENTRY_OWNER_NIC, &entry->flags);
|
|
||||||
usb_submit_urb(entry->priv, GFP_ATOMIC);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_enable_radio);
|
|
||||||
|
|
||||||
void rt2x00usb_disable_radio(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
struct data_ring *ring;
|
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
rt2x00usb_vendor_request_sw(rt2x00dev, USB_RX_CONTROL, 0x0000, 0x0000,
|
|
||||||
REGISTER_TIMEOUT);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Cancel all rings.
|
|
||||||
*/
|
|
||||||
ring_for_each(rt2x00dev, ring) {
|
|
||||||
for (i = 0; i < ring->stats.limit; i++)
|
|
||||||
usb_kill_urb(ring->entry[i].priv);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_disable_radio);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device initialization handlers.
|
|
||||||
*/
|
|
||||||
static int rt2x00usb_alloc_urb(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_ring *ring)
|
|
||||||
{
|
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Allocate the URB's
|
|
||||||
*/
|
|
||||||
for (i = 0; i < ring->stats.limit; i++) {
|
|
||||||
ring->entry[i].priv = usb_alloc_urb(0, GFP_KERNEL);
|
|
||||||
if (!ring->entry[i].priv)
|
|
||||||
return -ENOMEM;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
static void rt2x00usb_free_urb(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_ring *ring)
|
|
||||||
{
|
|
||||||
unsigned int i;
|
|
||||||
|
|
||||||
if (!ring->entry)
|
|
||||||
return;
|
|
||||||
|
|
||||||
for (i = 0; i < ring->stats.limit; i++) {
|
|
||||||
usb_kill_urb(ring->entry[i].priv);
|
|
||||||
usb_free_urb(ring->entry[i].priv);
|
|
||||||
if (ring->entry[i].skb)
|
|
||||||
kfree_skb(ring->entry[i].skb);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int rt2x00usb_initialize(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
struct data_ring *ring;
|
|
||||||
struct sk_buff *skb;
|
|
||||||
unsigned int entry_size;
|
|
||||||
unsigned int i;
|
|
||||||
int status;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Allocate DMA
|
|
||||||
*/
|
|
||||||
ring_for_each(rt2x00dev, ring) {
|
|
||||||
status = rt2x00usb_alloc_urb(rt2x00dev, ring);
|
|
||||||
if (status)
|
|
||||||
goto exit;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* For the RX ring, skb's should be allocated.
|
|
||||||
*/
|
|
||||||
entry_size = rt2x00dev->rx->data_size + rt2x00dev->rx->desc_size;
|
|
||||||
for (i = 0; i < rt2x00dev->rx->stats.limit; i++) {
|
|
||||||
skb = dev_alloc_skb(NET_IP_ALIGN + entry_size);
|
|
||||||
if (!skb)
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
skb_reserve(skb, NET_IP_ALIGN);
|
|
||||||
skb_put(skb, entry_size);
|
|
||||||
|
|
||||||
rt2x00dev->rx->entry[i].skb = skb;
|
|
||||||
}
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
exit:
|
|
||||||
rt2x00usb_uninitialize(rt2x00dev);
|
|
||||||
|
|
||||||
return status;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_initialize);
|
|
||||||
|
|
||||||
void rt2x00usb_uninitialize(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
struct data_ring *ring;
|
|
||||||
|
|
||||||
ring_for_each(rt2x00dev, ring)
|
|
||||||
rt2x00usb_free_urb(rt2x00dev, ring);
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_uninitialize);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* USB driver handlers.
|
|
||||||
*/
|
|
||||||
static void rt2x00usb_free_reg(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
kfree(rt2x00dev->rf);
|
|
||||||
rt2x00dev->rf = NULL;
|
|
||||||
|
|
||||||
kfree(rt2x00dev->eeprom);
|
|
||||||
rt2x00dev->eeprom = NULL;
|
|
||||||
|
|
||||||
kfree(rt2x00dev->csr_cache);
|
|
||||||
rt2x00dev->csr_cache = NULL;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int rt2x00usb_alloc_reg(struct rt2x00_dev *rt2x00dev)
|
|
||||||
{
|
|
||||||
rt2x00dev->csr_cache = kzalloc(CSR_CACHE_SIZE, GFP_KERNEL);
|
|
||||||
if (!rt2x00dev->csr_cache)
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
rt2x00dev->eeprom = kzalloc(rt2x00dev->ops->eeprom_size, GFP_KERNEL);
|
|
||||||
if (!rt2x00dev->eeprom)
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
rt2x00dev->rf = kzalloc(rt2x00dev->ops->rf_size, GFP_KERNEL);
|
|
||||||
if (!rt2x00dev->rf)
|
|
||||||
goto exit;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
exit:
|
|
||||||
ERROR_PROBE("Failed to allocate registers.\n");
|
|
||||||
|
|
||||||
rt2x00usb_free_reg(rt2x00dev);
|
|
||||||
|
|
||||||
return -ENOMEM;
|
|
||||||
}
|
|
||||||
|
|
||||||
int rt2x00usb_probe(struct usb_interface *usb_intf,
|
|
||||||
const struct usb_device_id *id)
|
|
||||||
{
|
|
||||||
struct usb_device *usb_dev = interface_to_usbdev(usb_intf);
|
|
||||||
struct rt2x00_ops *ops = (struct rt2x00_ops *)id->driver_info;
|
|
||||||
struct ieee80211_hw *hw;
|
|
||||||
struct rt2x00_dev *rt2x00dev;
|
|
||||||
int retval;
|
|
||||||
|
|
||||||
usb_dev = usb_get_dev(usb_dev);
|
|
||||||
|
|
||||||
hw = ieee80211_alloc_hw(sizeof(struct rt2x00_dev), ops->hw);
|
|
||||||
if (!hw) {
|
|
||||||
ERROR_PROBE("Failed to allocate hardware.\n");
|
|
||||||
retval = -ENOMEM;
|
|
||||||
goto exit_put_device;
|
|
||||||
}
|
|
||||||
|
|
||||||
usb_set_intfdata(usb_intf, hw);
|
|
||||||
|
|
||||||
rt2x00dev = hw->priv;
|
|
||||||
rt2x00dev->dev = usb_intf;
|
|
||||||
rt2x00dev->ops = ops;
|
|
||||||
rt2x00dev->hw = hw;
|
|
||||||
|
|
||||||
rt2x00dev->usb_maxpacket =
|
|
||||||
usb_maxpacket(usb_dev, usb_sndbulkpipe(usb_dev, 1), 1);
|
|
||||||
if (!rt2x00dev->usb_maxpacket)
|
|
||||||
rt2x00dev->usb_maxpacket = 1;
|
|
||||||
|
|
||||||
retval = rt2x00usb_alloc_reg(rt2x00dev);
|
|
||||||
if (retval)
|
|
||||||
goto exit_free_device;
|
|
||||||
|
|
||||||
retval = rt2x00lib_probe_dev(rt2x00dev);
|
|
||||||
if (retval)
|
|
||||||
goto exit_free_reg;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
exit_free_reg:
|
|
||||||
rt2x00usb_free_reg(rt2x00dev);
|
|
||||||
|
|
||||||
exit_free_device:
|
|
||||||
ieee80211_free_hw(hw);
|
|
||||||
|
|
||||||
exit_put_device:
|
|
||||||
usb_put_dev(usb_dev);
|
|
||||||
|
|
||||||
usb_set_intfdata(usb_intf, NULL);
|
|
||||||
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_probe);
|
|
||||||
|
|
||||||
void rt2x00usb_disconnect(struct usb_interface *usb_intf)
|
|
||||||
{
|
|
||||||
struct ieee80211_hw *hw = usb_get_intfdata(usb_intf);
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Free all allocated data.
|
|
||||||
*/
|
|
||||||
rt2x00lib_remove_dev(rt2x00dev);
|
|
||||||
rt2x00usb_free_reg(rt2x00dev);
|
|
||||||
ieee80211_free_hw(hw);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Free the USB device data.
|
|
||||||
*/
|
|
||||||
usb_set_intfdata(usb_intf, NULL);
|
|
||||||
usb_put_dev(interface_to_usbdev(usb_intf));
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_disconnect);
|
|
||||||
|
|
||||||
#ifdef CONFIG_PM
|
|
||||||
int rt2x00usb_suspend(struct usb_interface *usb_intf, pm_message_t state)
|
|
||||||
{
|
|
||||||
struct ieee80211_hw *hw = usb_get_intfdata(usb_intf);
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
int retval;
|
|
||||||
|
|
||||||
retval = rt2x00lib_suspend(rt2x00dev, state);
|
|
||||||
if (retval)
|
|
||||||
return retval;
|
|
||||||
|
|
||||||
rt2x00usb_free_reg(rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Decrease usbdev refcount.
|
|
||||||
*/
|
|
||||||
usb_put_dev(interface_to_usbdev(usb_intf));
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_suspend);
|
|
||||||
|
|
||||||
int rt2x00usb_resume(struct usb_interface *usb_intf)
|
|
||||||
{
|
|
||||||
struct ieee80211_hw *hw = usb_get_intfdata(usb_intf);
|
|
||||||
struct rt2x00_dev *rt2x00dev = hw->priv;
|
|
||||||
int retval;
|
|
||||||
|
|
||||||
usb_get_dev(interface_to_usbdev(usb_intf));
|
|
||||||
|
|
||||||
retval = rt2x00usb_alloc_reg(rt2x00dev);
|
|
||||||
if (retval)
|
|
||||||
return retval;
|
|
||||||
|
|
||||||
retval = rt2x00lib_resume(rt2x00dev);
|
|
||||||
if (retval)
|
|
||||||
goto exit_free_reg;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
exit_free_reg:
|
|
||||||
rt2x00usb_free_reg(rt2x00dev);
|
|
||||||
|
|
||||||
return retval;
|
|
||||||
}
|
|
||||||
EXPORT_SYMBOL_GPL(rt2x00usb_resume);
|
|
||||||
#endif /* CONFIG_PM */
|
|
||||||
|
|
||||||
/*
|
|
||||||
* rt2x00pci module information.
|
|
||||||
*/
|
|
||||||
MODULE_AUTHOR(DRV_PROJECT);
|
|
||||||
MODULE_VERSION(DRV_VERSION);
|
|
||||||
MODULE_DESCRIPTION("rt2x00 library");
|
|
||||||
MODULE_LICENSE("GPL");
|
|
@ -1,180 +0,0 @@
|
|||||||
/*
|
|
||||||
Copyright (C) 2004 - 2007 rt2x00 SourceForge Project
|
|
||||||
<http://rt2x00.serialmonkey.com>
|
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
|
||||||
it under the terms of the GNU General Public License as published by
|
|
||||||
the Free Software Foundation; either version 2 of the License, or
|
|
||||||
(at your option) any later version.
|
|
||||||
|
|
||||||
This program is distributed in the hope that it will be useful,
|
|
||||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
GNU General Public License for more details.
|
|
||||||
|
|
||||||
You should have received a copy of the GNU General Public License
|
|
||||||
along with this program; if not, write to the
|
|
||||||
Free Software Foundation, Inc.,
|
|
||||||
59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
||||||
*/
|
|
||||||
|
|
||||||
/*
|
|
||||||
Module: rt2x00usb
|
|
||||||
Abstract: Data structures for the rt2x00usb module.
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef RT2X00USB_H
|
|
||||||
#define RT2X00USB_H
|
|
||||||
|
|
||||||
/*
|
|
||||||
* This variable should be used with the
|
|
||||||
* usb_driver structure initialization.
|
|
||||||
*/
|
|
||||||
#define USB_DEVICE_DATA(__ops) .driver_info = (kernel_ulong_t)(__ops)
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Register defines.
|
|
||||||
* Some registers require multiple attempts before success,
|
|
||||||
* in those cases REGISTER_BUSY_COUNT attempts should be
|
|
||||||
* taken with a REGISTER_BUSY_DELAY interval.
|
|
||||||
* For USB vendor requests we need to pass a timeout
|
|
||||||
* time in ms, for this we use the REGISTER_TIMEOUT,
|
|
||||||
* however when loading firmware a higher value is
|
|
||||||
* required. In that case we use the REGISTER_TIMEOUT_FIRMWARE.
|
|
||||||
*/
|
|
||||||
#define REGISTER_BUSY_COUNT 5
|
|
||||||
#define REGISTER_BUSY_DELAY 100
|
|
||||||
#define REGISTER_TIMEOUT 500
|
|
||||||
#define REGISTER_TIMEOUT_FIRMWARE 1000
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Cache size
|
|
||||||
*/
|
|
||||||
#define CSR_CACHE_SIZE 8
|
|
||||||
#define CSR_CACHE_SIZE_FIRMWARE 64
|
|
||||||
|
|
||||||
/*
|
|
||||||
* USB request types.
|
|
||||||
*/
|
|
||||||
#define USB_VENDOR_REQUEST ( USB_TYPE_VENDOR | USB_RECIP_DEVICE )
|
|
||||||
#define USB_VENDOR_REQUEST_IN ( USB_DIR_IN | USB_VENDOR_REQUEST )
|
|
||||||
#define USB_VENDOR_REQUEST_OUT ( USB_DIR_OUT | USB_VENDOR_REQUEST )
|
|
||||||
|
|
||||||
/*
|
|
||||||
* USB vendor commands.
|
|
||||||
*/
|
|
||||||
#define USB_DEVICE_MODE 0x01
|
|
||||||
#define USB_SINGLE_WRITE 0x02
|
|
||||||
#define USB_SINGLE_READ 0x03
|
|
||||||
#define USB_MULTI_WRITE 0x06
|
|
||||||
#define USB_MULTI_READ 0x07
|
|
||||||
#define USB_EEPROM_WRITE 0x08
|
|
||||||
#define USB_EEPROM_READ 0x09
|
|
||||||
#define USB_LED_CONTROL 0x0a /* RT73USB */
|
|
||||||
#define USB_RX_CONTROL 0x0c
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device modes offset
|
|
||||||
*/
|
|
||||||
#define USB_MODE_RESET 0x01
|
|
||||||
#define USB_MODE_UNPLUG 0x02
|
|
||||||
#define USB_MODE_FUNCTION 0x03
|
|
||||||
#define USB_MODE_TEST 0x04
|
|
||||||
#define USB_MODE_SLEEP 0x07 /* RT73USB */
|
|
||||||
#define USB_MODE_FIRMWARE 0x08 /* RT73USB */
|
|
||||||
#define USB_MODE_WAKEUP 0x09 /* RT73USB */
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Used to read/write from/to the device.
|
|
||||||
* This is the main function to communicate with the device,
|
|
||||||
* the buffer argument _must_ either be NULL or point to
|
|
||||||
* a buffer allocated by kmalloc. Failure to do so can lead
|
|
||||||
* to unexpected behavior depending on the architecture.
|
|
||||||
*/
|
|
||||||
int rt2x00usb_vendor_request(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const u8 request, const u8 requesttype,
|
|
||||||
const u16 offset, const u16 value,
|
|
||||||
void *buffer, const u16 buffer_length,
|
|
||||||
const int timeout);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Used to read/write from/to the device.
|
|
||||||
* This function will use a previously with kmalloc allocated cache
|
|
||||||
* to communicate with the device. The contents of the buffer pointer
|
|
||||||
* will be copied to this cache when writing, or read from the cache
|
|
||||||
* when reading.
|
|
||||||
* Buffers send to rt2x00usb_vendor_request _must_ be allocated with
|
|
||||||
* kmalloc. Hence the reason for using a previously allocated cache
|
|
||||||
* which has been allocated properly.
|
|
||||||
*/
|
|
||||||
int rt2x00usb_vendor_request_buff(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
const u8 request, const u8 requesttype,
|
|
||||||
const u16 offset, void *buffer,
|
|
||||||
const u16 buffer_length, const int timeout);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Simple wrapper around rt2x00usb_vendor_request to write a single
|
|
||||||
* command to the device. Since we don't use the buffer argument we
|
|
||||||
* don't have to worry about kmalloc here.
|
|
||||||
*/
|
|
||||||
static inline int rt2x00usb_vendor_request_sw(const struct rt2x00_dev
|
|
||||||
*rt2x00dev,
|
|
||||||
const u8 request,
|
|
||||||
const u16 offset,
|
|
||||||
const u16 value,
|
|
||||||
const int timeout)
|
|
||||||
{
|
|
||||||
return rt2x00usb_vendor_request(rt2x00dev, request,
|
|
||||||
USB_VENDOR_REQUEST_OUT, offset,
|
|
||||||
value, NULL, 0, timeout);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Simple wrapper around rt2x00usb_vendor_request to read the eeprom
|
|
||||||
* from the device. Note that the eeprom argument _must_ be allocated using
|
|
||||||
* kmalloc for correct handling inside the kernel USB layer.
|
|
||||||
*/
|
|
||||||
static inline int rt2x00usb_eeprom_read(const struct rt2x00_dev *rt2x00dev,
|
|
||||||
__le16 *eeprom, const u16 lenght)
|
|
||||||
{
|
|
||||||
int timeout = REGISTER_TIMEOUT * (lenght / sizeof(u16));
|
|
||||||
|
|
||||||
return rt2x00usb_vendor_request(rt2x00dev, USB_EEPROM_READ,
|
|
||||||
USB_VENDOR_REQUEST_IN, 0x0000,
|
|
||||||
0x0000, eeprom, lenght, timeout);
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Radio handlers
|
|
||||||
*/
|
|
||||||
void rt2x00usb_enable_radio(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00usb_disable_radio(struct rt2x00_dev *rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* TX data handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00usb_write_tx_data(struct rt2x00_dev *rt2x00dev,
|
|
||||||
struct data_ring *ring, struct sk_buff *skb,
|
|
||||||
struct ieee80211_tx_control *control);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Device initialization handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00usb_initialize(struct rt2x00_dev *rt2x00dev);
|
|
||||||
void rt2x00usb_uninitialize(struct rt2x00_dev *rt2x00dev);
|
|
||||||
|
|
||||||
/*
|
|
||||||
* USB driver handlers.
|
|
||||||
*/
|
|
||||||
int rt2x00usb_probe(struct usb_interface *usb_intf,
|
|
||||||
const struct usb_device_id *id);
|
|
||||||
void rt2x00usb_disconnect(struct usb_interface *usb_intf);
|
|
||||||
#ifdef CONFIG_PM
|
|
||||||
int rt2x00usb_suspend(struct usb_interface *usb_intf, pm_message_t state);
|
|
||||||
int rt2x00usb_resume(struct usb_interface *usb_intf);
|
|
||||||
#else
|
|
||||||
#define rt2x00usb_suspend NULL
|
|
||||||
#define rt2x00usb_resume NULL
|
|
||||||
#endif /* CONFIG_PM */
|
|
||||||
|
|
||||||
#endif /* RT2X00USB_H */
|
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue
Block a user