root/drivers/net/wireless/realtek/rtl818x/rtl8187/rtl8225.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. rtl818x_ioread8_idx
  2. rtl818x_ioread16_idx
  3. rtl818x_ioread32_idx
  4. rtl818x_iowrite8_idx
  5. rtl818x_iowrite16_idx
  6. rtl818x_iowrite32_idx
  7. rtl8225_write_bitbang
  8. rtl8225_write_8051
  9. rtl8225_write
  10. rtl8225_read
  11. rtl8225_rf_set_tx_power
  12. rtl8225_rf_init
  13. rtl8225z2_rf_set_tx_power
  14. rtl8225z2_b_rf_set_tx_power
  15. rtl8225z2_rf_init
  16. rtl8225z2_b_rf_init
  17. rtl8225_rf_stop
  18. rtl8225_rf_set_channel
  19. rtl8187_detect_rf

   1 // SPDX-License-Identifier: GPL-2.0-only
   2 /*
   3  * Radio tuning for RTL8225 on RTL8187
   4  *
   5  * Copyright 2007 Michael Wu <flamingice@sourmilk.net>
   6  * Copyright 2007 Andrea Merello <andrea.merello@gmail.com>
   7  *
   8  * Based on the r8187 driver, which is:
   9  * Copyright 2005 Andrea Merello <andrea.merello@gmail.com>, et al.
  10  *
  11  * Magic delays, register offsets, and phy value tables below are
  12  * taken from the original r8187 driver sources.  Thanks to Realtek
  13  * for their support!
  14  */
  15 
  16 #include <linux/usb.h>
  17 #include <net/mac80211.h>
  18 
  19 #include "rtl8187.h"
  20 #include "rtl8225.h"
  21 
  22 u8 rtl818x_ioread8_idx(struct rtl8187_priv *priv,
  23                                 u8 *addr, u8 idx)
  24 {
  25         u8 val;
  26 
  27         mutex_lock(&priv->io_mutex);
  28         usb_control_msg(priv->udev, usb_rcvctrlpipe(priv->udev, 0),
  29                         RTL8187_REQ_GET_REG, RTL8187_REQT_READ,
  30                         (unsigned long)addr, idx & 0x03,
  31                         &priv->io_dmabuf->bits8, sizeof(val), HZ / 2);
  32 
  33         val = priv->io_dmabuf->bits8;
  34         mutex_unlock(&priv->io_mutex);
  35 
  36         return val;
  37 }
  38 
  39 u16 rtl818x_ioread16_idx(struct rtl8187_priv *priv,
  40                                 __le16 *addr, u8 idx)
  41 {
  42         __le16 val;
  43 
  44         mutex_lock(&priv->io_mutex);
  45         usb_control_msg(priv->udev, usb_rcvctrlpipe(priv->udev, 0),
  46                         RTL8187_REQ_GET_REG, RTL8187_REQT_READ,
  47                         (unsigned long)addr, idx & 0x03,
  48                         &priv->io_dmabuf->bits16, sizeof(val), HZ / 2);
  49 
  50         val = priv->io_dmabuf->bits16;
  51         mutex_unlock(&priv->io_mutex);
  52 
  53         return le16_to_cpu(val);
  54 }
  55 
  56 u32 rtl818x_ioread32_idx(struct rtl8187_priv *priv,
  57                                 __le32 *addr, u8 idx)
  58 {
  59         __le32 val;
  60 
  61         mutex_lock(&priv->io_mutex);
  62         usb_control_msg(priv->udev, usb_rcvctrlpipe(priv->udev, 0),
  63                         RTL8187_REQ_GET_REG, RTL8187_REQT_READ,
  64                         (unsigned long)addr, idx & 0x03,
  65                         &priv->io_dmabuf->bits32, sizeof(val), HZ / 2);
  66 
  67         val = priv->io_dmabuf->bits32;
  68         mutex_unlock(&priv->io_mutex);
  69 
  70         return le32_to_cpu(val);
  71 }
  72 
  73 void rtl818x_iowrite8_idx(struct rtl8187_priv *priv,
  74                                 u8 *addr, u8 val, u8 idx)
  75 {
  76         mutex_lock(&priv->io_mutex);
  77 
  78         priv->io_dmabuf->bits8 = val;
  79         usb_control_msg(priv->udev, usb_sndctrlpipe(priv->udev, 0),
  80                         RTL8187_REQ_SET_REG, RTL8187_REQT_WRITE,
  81                         (unsigned long)addr, idx & 0x03,
  82                         &priv->io_dmabuf->bits8, sizeof(val), HZ / 2);
  83 
  84         mutex_unlock(&priv->io_mutex);
  85 }
  86 
  87 void rtl818x_iowrite16_idx(struct rtl8187_priv *priv,
  88                                 __le16 *addr, u16 val, u8 idx)
  89 {
  90         mutex_lock(&priv->io_mutex);
  91 
  92         priv->io_dmabuf->bits16 = cpu_to_le16(val);
  93         usb_control_msg(priv->udev, usb_sndctrlpipe(priv->udev, 0),
  94                         RTL8187_REQ_SET_REG, RTL8187_REQT_WRITE,
  95                         (unsigned long)addr, idx & 0x03,
  96                         &priv->io_dmabuf->bits16, sizeof(val), HZ / 2);
  97 
  98         mutex_unlock(&priv->io_mutex);
  99 }
 100 
 101 void rtl818x_iowrite32_idx(struct rtl8187_priv *priv,
 102                                 __le32 *addr, u32 val, u8 idx)
 103 {
 104         mutex_lock(&priv->io_mutex);
 105 
 106         priv->io_dmabuf->bits32 = cpu_to_le32(val);
 107         usb_control_msg(priv->udev, usb_sndctrlpipe(priv->udev, 0),
 108                         RTL8187_REQ_SET_REG, RTL8187_REQT_WRITE,
 109                         (unsigned long)addr, idx & 0x03,
 110                         &priv->io_dmabuf->bits32, sizeof(val), HZ / 2);
 111 
 112         mutex_unlock(&priv->io_mutex);
 113 }
 114 
 115 static void rtl8225_write_bitbang(struct ieee80211_hw *dev, u8 addr, u16 data)
 116 {
 117         struct rtl8187_priv *priv = dev->priv;
 118         u16 reg80, reg84, reg82;
 119         u32 bangdata;
 120         int i;
 121 
 122         bangdata = (data << 4) | (addr & 0xf);
 123 
 124         reg80 = rtl818x_ioread16(priv, &priv->map->RFPinsOutput) & 0xfff3;
 125         reg82 = rtl818x_ioread16(priv, &priv->map->RFPinsEnable);
 126 
 127         rtl818x_iowrite16(priv, &priv->map->RFPinsEnable, reg82 | 0x7);
 128 
 129         reg84 = rtl818x_ioread16(priv, &priv->map->RFPinsSelect);
 130         rtl818x_iowrite16(priv, &priv->map->RFPinsSelect, reg84 | 0x7);
 131         udelay(10);
 132 
 133         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg80 | (1 << 2));
 134         udelay(2);
 135         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg80);
 136         udelay(10);
 137 
 138         for (i = 15; i >= 0; i--) {
 139                 u16 reg = reg80 | (bangdata & (1 << i)) >> i;
 140 
 141                 if (i & 1)
 142                         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg);
 143 
 144                 rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg | (1 << 1));
 145                 rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg | (1 << 1));
 146 
 147                 if (!(i & 1))
 148                         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg);
 149         }
 150 
 151         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg80 | (1 << 2));
 152         udelay(10);
 153 
 154         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg80 | (1 << 2));
 155         rtl818x_iowrite16(priv, &priv->map->RFPinsSelect, reg84);
 156 }
 157 
 158 static void rtl8225_write_8051(struct ieee80211_hw *dev, u8 addr, __le16 data)
 159 {
 160         struct rtl8187_priv *priv = dev->priv;
 161         u16 reg80, reg82, reg84;
 162 
 163         reg80 = rtl818x_ioread16(priv, &priv->map->RFPinsOutput);
 164         reg82 = rtl818x_ioread16(priv, &priv->map->RFPinsEnable);
 165         reg84 = rtl818x_ioread16(priv, &priv->map->RFPinsSelect);
 166 
 167         reg80 &= ~(0x3 << 2);
 168         reg84 &= ~0xF;
 169 
 170         rtl818x_iowrite16(priv, &priv->map->RFPinsEnable, reg82 | 0x0007);
 171         rtl818x_iowrite16(priv, &priv->map->RFPinsSelect, reg84 | 0x0007);
 172         udelay(10);
 173 
 174         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg80 | (1 << 2));
 175         udelay(2);
 176 
 177         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg80);
 178         udelay(10);
 179 
 180         mutex_lock(&priv->io_mutex);
 181 
 182         priv->io_dmabuf->bits16 = data;
 183         usb_control_msg(priv->udev, usb_sndctrlpipe(priv->udev, 0),
 184                         RTL8187_REQ_SET_REG, RTL8187_REQT_WRITE,
 185                         addr, 0x8225, &priv->io_dmabuf->bits16, sizeof(data),
 186                         HZ / 2);
 187 
 188         mutex_unlock(&priv->io_mutex);
 189 
 190         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg80 | (1 << 2));
 191         udelay(10);
 192 
 193         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg80 | (1 << 2));
 194         rtl818x_iowrite16(priv, &priv->map->RFPinsSelect, reg84);
 195 }
 196 
 197 static void rtl8225_write(struct ieee80211_hw *dev, u8 addr, u16 data)
 198 {
 199         struct rtl8187_priv *priv = dev->priv;
 200 
 201         if (priv->asic_rev)
 202                 rtl8225_write_8051(dev, addr, cpu_to_le16(data));
 203         else
 204                 rtl8225_write_bitbang(dev, addr, data);
 205 }
 206 
 207 static u16 rtl8225_read(struct ieee80211_hw *dev, u8 addr)
 208 {
 209         struct rtl8187_priv *priv = dev->priv;
 210         u16 reg80, reg82, reg84, out;
 211         int i;
 212 
 213         reg80 = rtl818x_ioread16(priv, &priv->map->RFPinsOutput);
 214         reg82 = rtl818x_ioread16(priv, &priv->map->RFPinsEnable);
 215         reg84 = rtl818x_ioread16(priv, &priv->map->RFPinsSelect);
 216 
 217         reg80 &= ~0xF;
 218 
 219         rtl818x_iowrite16(priv, &priv->map->RFPinsEnable, reg82 | 0x000F);
 220         rtl818x_iowrite16(priv, &priv->map->RFPinsSelect, reg84 | 0x000F);
 221 
 222         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg80 | (1 << 2));
 223         udelay(4);
 224         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg80);
 225         udelay(5);
 226 
 227         for (i = 4; i >= 0; i--) {
 228                 u16 reg = reg80 | ((addr >> i) & 1);
 229 
 230                 if (!(i & 1)) {
 231                         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg);
 232                         udelay(1);
 233                 }
 234 
 235                 rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 236                                   reg | (1 << 1));
 237                 udelay(2);
 238                 rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 239                                   reg | (1 << 1));
 240                 udelay(2);
 241 
 242                 if (i & 1) {
 243                         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, reg);
 244                         udelay(1);
 245                 }
 246         }
 247 
 248         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 249                           reg80 | (1 << 3) | (1 << 1));
 250         udelay(2);
 251         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 252                           reg80 | (1 << 3));
 253         udelay(2);
 254         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 255                           reg80 | (1 << 3));
 256         udelay(2);
 257 
 258         out = 0;
 259         for (i = 11; i >= 0; i--) {
 260                 rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 261                                   reg80 | (1 << 3));
 262                 udelay(1);
 263                 rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 264                                   reg80 | (1 << 3) | (1 << 1));
 265                 udelay(2);
 266                 rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 267                                   reg80 | (1 << 3) | (1 << 1));
 268                 udelay(2);
 269                 rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 270                                   reg80 | (1 << 3) | (1 << 1));
 271                 udelay(2);
 272 
 273                 if (rtl818x_ioread16(priv, &priv->map->RFPinsInput) & (1 << 1))
 274                         out |= 1 << i;
 275 
 276                 rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 277                                   reg80 | (1 << 3));
 278                 udelay(2);
 279         }
 280 
 281         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput,
 282                           reg80 | (1 << 3) | (1 << 2));
 283         udelay(2);
 284 
 285         rtl818x_iowrite16(priv, &priv->map->RFPinsEnable, reg82);
 286         rtl818x_iowrite16(priv, &priv->map->RFPinsSelect, reg84);
 287         rtl818x_iowrite16(priv, &priv->map->RFPinsOutput, 0x03A0);
 288 
 289         return out;
 290 }
 291 
 292 static const u16 rtl8225bcd_rxgain[] = {
 293         0x0400, 0x0401, 0x0402, 0x0403, 0x0404, 0x0405, 0x0408, 0x0409,
 294         0x040a, 0x040b, 0x0502, 0x0503, 0x0504, 0x0505, 0x0540, 0x0541,
 295         0x0542, 0x0543, 0x0544, 0x0545, 0x0580, 0x0581, 0x0582, 0x0583,
 296         0x0584, 0x0585, 0x0588, 0x0589, 0x058a, 0x058b, 0x0643, 0x0644,
 297         0x0645, 0x0680, 0x0681, 0x0682, 0x0683, 0x0684, 0x0685, 0x0688,
 298         0x0689, 0x068a, 0x068b, 0x068c, 0x0742, 0x0743, 0x0744, 0x0745,
 299         0x0780, 0x0781, 0x0782, 0x0783, 0x0784, 0x0785, 0x0788, 0x0789,
 300         0x078a, 0x078b, 0x078c, 0x078d, 0x0790, 0x0791, 0x0792, 0x0793,
 301         0x0794, 0x0795, 0x0798, 0x0799, 0x079a, 0x079b, 0x079c, 0x079d,
 302         0x07a0, 0x07a1, 0x07a2, 0x07a3, 0x07a4, 0x07a5, 0x07a8, 0x07a9,
 303         0x07aa, 0x07ab, 0x07ac, 0x07ad, 0x07b0, 0x07b1, 0x07b2, 0x07b3,
 304         0x07b4, 0x07b5, 0x07b8, 0x07b9, 0x07ba, 0x07bb, 0x07bb
 305 };
 306 
 307 static const u8 rtl8225_agc[] = {
 308         0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e, 0x9e,
 309         0x9d, 0x9c, 0x9b, 0x9a, 0x99, 0x98, 0x97, 0x96,
 310         0x95, 0x94, 0x93, 0x92, 0x91, 0x90, 0x8f, 0x8e,
 311         0x8d, 0x8c, 0x8b, 0x8a, 0x89, 0x88, 0x87, 0x86,
 312         0x85, 0x84, 0x83, 0x82, 0x81, 0x80, 0x3f, 0x3e,
 313         0x3d, 0x3c, 0x3b, 0x3a, 0x39, 0x38, 0x37, 0x36,
 314         0x35, 0x34, 0x33, 0x32, 0x31, 0x30, 0x2f, 0x2e,
 315         0x2d, 0x2c, 0x2b, 0x2a, 0x29, 0x28, 0x27, 0x26,
 316         0x25, 0x24, 0x23, 0x22, 0x21, 0x20, 0x1f, 0x1e,
 317         0x1d, 0x1c, 0x1b, 0x1a, 0x19, 0x18, 0x17, 0x16,
 318         0x15, 0x14, 0x13, 0x12, 0x11, 0x10, 0x0f, 0x0e,
 319         0x0d, 0x0c, 0x0b, 0x0a, 0x09, 0x08, 0x07, 0x06,
 320         0x05, 0x04, 0x03, 0x02, 0x01, 0x01, 0x01, 0x01,
 321         0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,
 322         0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,
 323         0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01
 324 };
 325 
 326 static const u8 rtl8225_gain[] = {
 327         0x23, 0x88, 0x7c, 0xa5, /* -82dBm */
 328         0x23, 0x88, 0x7c, 0xb5, /* -82dBm */
 329         0x23, 0x88, 0x7c, 0xc5, /* -82dBm */
 330         0x33, 0x80, 0x79, 0xc5, /* -78dBm */
 331         0x43, 0x78, 0x76, 0xc5, /* -74dBm */
 332         0x53, 0x60, 0x73, 0xc5, /* -70dBm */
 333         0x63, 0x58, 0x70, 0xc5, /* -66dBm */
 334 };
 335 
 336 static const u8 rtl8225_threshold[] = {
 337         0x8d, 0x8d, 0x8d, 0x8d, 0x9d, 0xad, 0xbd
 338 };
 339 
 340 static const u8 rtl8225_tx_gain_cck_ofdm[] = {
 341         0x02, 0x06, 0x0e, 0x1e, 0x3e, 0x7e
 342 };
 343 
 344 static const u8 rtl8225_tx_power_cck[] = {
 345         0x18, 0x17, 0x15, 0x11, 0x0c, 0x08, 0x04, 0x02,
 346         0x1b, 0x1a, 0x17, 0x13, 0x0e, 0x09, 0x04, 0x02,
 347         0x1f, 0x1e, 0x1a, 0x15, 0x10, 0x0a, 0x05, 0x02,
 348         0x22, 0x21, 0x1d, 0x18, 0x11, 0x0b, 0x06, 0x02,
 349         0x26, 0x25, 0x21, 0x1b, 0x14, 0x0d, 0x06, 0x03,
 350         0x2b, 0x2a, 0x25, 0x1e, 0x16, 0x0e, 0x07, 0x03
 351 };
 352 
 353 static const u8 rtl8225_tx_power_cck_ch14[] = {
 354         0x18, 0x17, 0x15, 0x0c, 0x00, 0x00, 0x00, 0x00,
 355         0x1b, 0x1a, 0x17, 0x0e, 0x00, 0x00, 0x00, 0x00,
 356         0x1f, 0x1e, 0x1a, 0x0f, 0x00, 0x00, 0x00, 0x00,
 357         0x22, 0x21, 0x1d, 0x11, 0x00, 0x00, 0x00, 0x00,
 358         0x26, 0x25, 0x21, 0x13, 0x00, 0x00, 0x00, 0x00,
 359         0x2b, 0x2a, 0x25, 0x15, 0x00, 0x00, 0x00, 0x00
 360 };
 361 
 362 static const u8 rtl8225_tx_power_ofdm[] = {
 363         0x80, 0x90, 0xa2, 0xb5, 0xcb, 0xe4
 364 };
 365 
 366 static const u32 rtl8225_chan[] = {
 367         0x085c, 0x08dc, 0x095c, 0x09dc, 0x0a5c, 0x0adc, 0x0b5c,
 368         0x0bdc, 0x0c5c, 0x0cdc, 0x0d5c, 0x0ddc, 0x0e5c, 0x0f72
 369 };
 370 
 371 static void rtl8225_rf_set_tx_power(struct ieee80211_hw *dev, int channel)
 372 {
 373         struct rtl8187_priv *priv = dev->priv;
 374         u8 cck_power, ofdm_power;
 375         const u8 *tmp;
 376         u32 reg;
 377         int i;
 378 
 379         cck_power = priv->channels[channel - 1].hw_value & 0xF;
 380         ofdm_power = priv->channels[channel - 1].hw_value >> 4;
 381 
 382         cck_power = min(cck_power, (u8)11);
 383         if (ofdm_power > (u8)15)
 384                 ofdm_power = 25;
 385         else
 386                 ofdm_power += 10;
 387 
 388         rtl818x_iowrite8(priv, &priv->map->TX_GAIN_CCK,
 389                          rtl8225_tx_gain_cck_ofdm[cck_power / 6] >> 1);
 390 
 391         if (channel == 14)
 392                 tmp = &rtl8225_tx_power_cck_ch14[(cck_power % 6) * 8];
 393         else
 394                 tmp = &rtl8225_tx_power_cck[(cck_power % 6) * 8];
 395 
 396         for (i = 0; i < 8; i++)
 397                 rtl8225_write_phy_cck(dev, 0x44 + i, *tmp++);
 398 
 399         msleep(1); // FIXME: optional?
 400 
 401         /* anaparam2 on */
 402         rtl818x_iowrite8(priv, &priv->map->EEPROM_CMD, RTL818X_EEPROM_CMD_CONFIG);
 403         reg = rtl818x_ioread8(priv, &priv->map->CONFIG3);
 404         rtl818x_iowrite8(priv, &priv->map->CONFIG3,
 405                         reg | RTL818X_CONFIG3_ANAPARAM_WRITE);
 406         rtl818x_iowrite32(priv, &priv->map->ANAPARAM2,
 407                           RTL8187_RTL8225_ANAPARAM2_ON);
 408         rtl818x_iowrite8(priv, &priv->map->CONFIG3,
 409                         reg & ~RTL818X_CONFIG3_ANAPARAM_WRITE);
 410         rtl818x_iowrite8(priv, &priv->map->EEPROM_CMD, RTL818X_EEPROM_CMD_NORMAL);
 411 
 412         rtl8225_write_phy_ofdm(dev, 2, 0x42);
 413         rtl8225_write_phy_ofdm(dev, 6, 0x00);
 414         rtl8225_write_phy_ofdm(dev, 8, 0x00);
 415 
 416         rtl818x_iowrite8(priv, &priv->map->TX_GAIN_OFDM,
 417                          rtl8225_tx_gain_cck_ofdm[ofdm_power / 6] >> 1);
 418 
 419         tmp = &rtl8225_tx_power_ofdm[ofdm_power % 6];
 420 
 421         rtl8225_write_phy_ofdm(dev, 5, *tmp);
 422         rtl8225_write_phy_ofdm(dev, 7, *tmp);
 423 
 424         msleep(1);
 425 }
 426 
 427 static void rtl8225_rf_init(struct ieee80211_hw *dev)
 428 {
 429         struct rtl8187_priv *priv = dev->priv;
 430         int i;
 431 
 432         rtl8225_write(dev, 0x0, 0x067);
 433         rtl8225_write(dev, 0x1, 0xFE0);
 434         rtl8225_write(dev, 0x2, 0x44D);
 435         rtl8225_write(dev, 0x3, 0x441);
 436         rtl8225_write(dev, 0x4, 0x486);
 437         rtl8225_write(dev, 0x5, 0xBC0);
 438         rtl8225_write(dev, 0x6, 0xAE6);
 439         rtl8225_write(dev, 0x7, 0x82A);
 440         rtl8225_write(dev, 0x8, 0x01F);
 441         rtl8225_write(dev, 0x9, 0x334);
 442         rtl8225_write(dev, 0xA, 0xFD4);
 443         rtl8225_write(dev, 0xB, 0x391);
 444         rtl8225_write(dev, 0xC, 0x050);
 445         rtl8225_write(dev, 0xD, 0x6DB);
 446         rtl8225_write(dev, 0xE, 0x029);
 447         rtl8225_write(dev, 0xF, 0x914); msleep(100);
 448 
 449         rtl8225_write(dev, 0x2, 0xC4D); msleep(200);
 450         rtl8225_write(dev, 0x2, 0x44D); msleep(200);
 451 
 452         if (!(rtl8225_read(dev, 6) & (1 << 7))) {
 453                 rtl8225_write(dev, 0x02, 0x0c4d);
 454                 msleep(200);
 455                 rtl8225_write(dev, 0x02, 0x044d);
 456                 msleep(100);
 457                 if (!(rtl8225_read(dev, 6) & (1 << 7)))
 458                         wiphy_warn(dev->wiphy, "RF Calibration Failed! %x\n",
 459                                    rtl8225_read(dev, 6));
 460         }
 461 
 462         rtl8225_write(dev, 0x0, 0x127);
 463 
 464         for (i = 0; i < ARRAY_SIZE(rtl8225bcd_rxgain); i++) {
 465                 rtl8225_write(dev, 0x1, i + 1);
 466                 rtl8225_write(dev, 0x2, rtl8225bcd_rxgain[i]);
 467         }
 468 
 469         rtl8225_write(dev, 0x0, 0x027);
 470         rtl8225_write(dev, 0x0, 0x22F);
 471 
 472         for (i = 0; i < ARRAY_SIZE(rtl8225_agc); i++) {
 473                 rtl8225_write_phy_ofdm(dev, 0xB, rtl8225_agc[i]);
 474                 rtl8225_write_phy_ofdm(dev, 0xA, 0x80 + i);
 475         }
 476 
 477         msleep(1);
 478 
 479         rtl8225_write_phy_ofdm(dev, 0x00, 0x01);
 480         rtl8225_write_phy_ofdm(dev, 0x01, 0x02);
 481         rtl8225_write_phy_ofdm(dev, 0x02, 0x42);
 482         rtl8225_write_phy_ofdm(dev, 0x03, 0x00);
 483         rtl8225_write_phy_ofdm(dev, 0x04, 0x00);
 484         rtl8225_write_phy_ofdm(dev, 0x05, 0x00);
 485         rtl8225_write_phy_ofdm(dev, 0x06, 0x40);
 486         rtl8225_write_phy_ofdm(dev, 0x07, 0x00);
 487         rtl8225_write_phy_ofdm(dev, 0x08, 0x40);
 488         rtl8225_write_phy_ofdm(dev, 0x09, 0xfe);
 489         rtl8225_write_phy_ofdm(dev, 0x0a, 0x09);
 490         rtl8225_write_phy_ofdm(dev, 0x0b, 0x80);
 491         rtl8225_write_phy_ofdm(dev, 0x0c, 0x01);
 492         rtl8225_write_phy_ofdm(dev, 0x0e, 0xd3);
 493         rtl8225_write_phy_ofdm(dev, 0x0f, 0x38);
 494         rtl8225_write_phy_ofdm(dev, 0x10, 0x84);
 495         rtl8225_write_phy_ofdm(dev, 0x11, 0x06);
 496         rtl8225_write_phy_ofdm(dev, 0x12, 0x20);
 497         rtl8225_write_phy_ofdm(dev, 0x13, 0x20);
 498         rtl8225_write_phy_ofdm(dev, 0x14, 0x00);
 499         rtl8225_write_phy_ofdm(dev, 0x15, 0x40);
 500         rtl8225_write_phy_ofdm(dev, 0x16, 0x00);
 501         rtl8225_write_phy_ofdm(dev, 0x17, 0x40);
 502         rtl8225_write_phy_ofdm(dev, 0x18, 0xef);
 503         rtl8225_write_phy_ofdm(dev, 0x19, 0x19);
 504         rtl8225_write_phy_ofdm(dev, 0x1a, 0x20);
 505         rtl8225_write_phy_ofdm(dev, 0x1b, 0x76);
 506         rtl8225_write_phy_ofdm(dev, 0x1c, 0x04);
 507         rtl8225_write_phy_ofdm(dev, 0x1e, 0x95);
 508         rtl8225_write_phy_ofdm(dev, 0x1f, 0x75);
 509         rtl8225_write_phy_ofdm(dev, 0x20, 0x1f);
 510         rtl8225_write_phy_ofdm(dev, 0x21, 0x27);
 511         rtl8225_write_phy_ofdm(dev, 0x22, 0x16);
 512         rtl8225_write_phy_ofdm(dev, 0x24, 0x46);
 513         rtl8225_write_phy_ofdm(dev, 0x25, 0x20);
 514         rtl8225_write_phy_ofdm(dev, 0x26, 0x90);
 515         rtl8225_write_phy_ofdm(dev, 0x27, 0x88);
 516 
 517         rtl8225_write_phy_ofdm(dev, 0x0d, rtl8225_gain[2 * 4]);
 518         rtl8225_write_phy_ofdm(dev, 0x1b, rtl8225_gain[2 * 4 + 2]);
 519         rtl8225_write_phy_ofdm(dev, 0x1d, rtl8225_gain[2 * 4 + 3]);
 520         rtl8225_write_phy_ofdm(dev, 0x23, rtl8225_gain[2 * 4 + 1]);
 521 
 522         rtl8225_write_phy_cck(dev, 0x00, 0x98);
 523         rtl8225_write_phy_cck(dev, 0x03, 0x20);
 524         rtl8225_write_phy_cck(dev, 0x04, 0x7e);
 525         rtl8225_write_phy_cck(dev, 0x05, 0x12);
 526         rtl8225_write_phy_cck(dev, 0x06, 0xfc);
 527         rtl8225_write_phy_cck(dev, 0x07, 0x78);
 528         rtl8225_write_phy_cck(dev, 0x08, 0x2e);
 529         rtl8225_write_phy_cck(dev, 0x10, 0x9b);
 530         rtl8225_write_phy_cck(dev, 0x11, 0x88);
 531         rtl8225_write_phy_cck(dev, 0x12, 0x47);
 532         rtl8225_write_phy_cck(dev, 0x13, 0xd0);
 533         rtl8225_write_phy_cck(dev, 0x19, 0x00);
 534         rtl8225_write_phy_cck(dev, 0x1a, 0xa0);
 535         rtl8225_write_phy_cck(dev, 0x1b, 0x08);
 536         rtl8225_write_phy_cck(dev, 0x40, 0x86);
 537         rtl8225_write_phy_cck(dev, 0x41, 0x8d);
 538         rtl8225_write_phy_cck(dev, 0x42, 0x15);
 539         rtl8225_write_phy_cck(dev, 0x43, 0x18);
 540         rtl8225_write_phy_cck(dev, 0x44, 0x1f);
 541         rtl8225_write_phy_cck(dev, 0x45, 0x1e);
 542         rtl8225_write_phy_cck(dev, 0x46, 0x1a);
 543         rtl8225_write_phy_cck(dev, 0x47, 0x15);
 544         rtl8225_write_phy_cck(dev, 0x48, 0x10);
 545         rtl8225_write_phy_cck(dev, 0x49, 0x0a);
 546         rtl8225_write_phy_cck(dev, 0x4a, 0x05);
 547         rtl8225_write_phy_cck(dev, 0x4b, 0x02);
 548         rtl8225_write_phy_cck(dev, 0x4c, 0x05);
 549 
 550         rtl818x_iowrite8(priv, &priv->map->TESTR, 0x0D);
 551 
 552         rtl8225_rf_set_tx_power(dev, 1);
 553 
 554         /* RX antenna default to A */
 555         rtl8225_write_phy_cck(dev, 0x10, 0x9b);                 /* B: 0xDB */
 556         rtl8225_write_phy_ofdm(dev, 0x26, 0x90);                /* B: 0x10 */
 557 
 558         rtl818x_iowrite8(priv, &priv->map->TX_ANTENNA, 0x03);   /* B: 0x00 */
 559         msleep(1);
 560         rtl818x_iowrite32(priv, (__le32 *)0xFF94, 0x3dc00002);
 561 
 562         /* set sensitivity */
 563         rtl8225_write(dev, 0x0c, 0x50);
 564         rtl8225_write_phy_ofdm(dev, 0x0d, rtl8225_gain[2 * 4]);
 565         rtl8225_write_phy_ofdm(dev, 0x1b, rtl8225_gain[2 * 4 + 2]);
 566         rtl8225_write_phy_ofdm(dev, 0x1d, rtl8225_gain[2 * 4 + 3]);
 567         rtl8225_write_phy_ofdm(dev, 0x23, rtl8225_gain[2 * 4 + 1]);
 568         rtl8225_write_phy_cck(dev, 0x41, rtl8225_threshold[2]);
 569 }
 570 
 571 static const u8 rtl8225z2_agc[] = {
 572         0x5e, 0x5e, 0x5e, 0x5e, 0x5d, 0x5b, 0x59, 0x57, 0x55, 0x53, 0x51, 0x4f,
 573         0x4d, 0x4b, 0x49, 0x47, 0x45, 0x43, 0x41, 0x3f, 0x3d, 0x3b, 0x39, 0x37,
 574         0x35, 0x33, 0x31, 0x2f, 0x2d, 0x2b, 0x29, 0x27, 0x25, 0x23, 0x21, 0x1f,
 575         0x1d, 0x1b, 0x19, 0x17, 0x15, 0x13, 0x11, 0x0f, 0x0d, 0x0b, 0x09, 0x07,
 576         0x05, 0x03, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01,
 577         0x01, 0x01, 0x01, 0x01, 0x19, 0x19, 0x19, 0x19, 0x19, 0x19, 0x19, 0x19,
 578         0x19, 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x26, 0x27, 0x27, 0x28,
 579         0x28, 0x29, 0x2a, 0x2a, 0x2a, 0x2b, 0x2b, 0x2b, 0x2c, 0x2c, 0x2c, 0x2d,
 580         0x2d, 0x2d, 0x2d, 0x2e, 0x2e, 0x2e, 0x2e, 0x2f, 0x2f, 0x2f, 0x30, 0x30,
 581         0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31,
 582         0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31, 0x31
 583 };
 584 static const u8 rtl8225z2_ofdm[] = {
 585         0x10, 0x0d, 0x01, 0x00, 0x14, 0xfb, 0xfb, 0x60,
 586         0x00, 0x60, 0x00, 0x00, 0x00, 0x5c, 0x00, 0x00,
 587         0x40, 0x00, 0x40, 0x00, 0x00, 0x00, 0xa8, 0x26,
 588         0x32, 0x33, 0x07, 0xa5, 0x6f, 0x55, 0xc8, 0xb3,
 589         0x0a, 0xe1, 0x2C, 0x8a, 0x86, 0x83, 0x34, 0x0f,
 590         0x4f, 0x24, 0x6f, 0xc2, 0x6b, 0x40, 0x80, 0x00,
 591         0xc0, 0xc1, 0x58, 0xf1, 0x00, 0xe4, 0x90, 0x3e,
 592         0x6d, 0x3c, 0xfb, 0x07
 593 };
 594 
 595 static const u8 rtl8225z2_tx_power_cck_ch14[] = {
 596         0x36, 0x35, 0x2e, 0x1b, 0x00, 0x00, 0x00, 0x00,
 597         0x30, 0x2f, 0x29, 0x15, 0x00, 0x00, 0x00, 0x00,
 598         0x30, 0x2f, 0x29, 0x15, 0x00, 0x00, 0x00, 0x00,
 599         0x30, 0x2f, 0x29, 0x15, 0x00, 0x00, 0x00, 0x00
 600 };
 601 
 602 static const u8 rtl8225z2_tx_power_cck[] = {
 603         0x36, 0x35, 0x2e, 0x25, 0x1c, 0x12, 0x09, 0x04,
 604         0x30, 0x2f, 0x29, 0x21, 0x19, 0x10, 0x08, 0x03,
 605         0x2b, 0x2a, 0x25, 0x1e, 0x16, 0x0e, 0x07, 0x03,
 606         0x26, 0x25, 0x21, 0x1b, 0x14, 0x0d, 0x06, 0x03
 607 };
 608 
 609 static const u8 rtl8225z2_tx_power_ofdm[] = {
 610         0x42, 0x00, 0x40, 0x00, 0x40
 611 };
 612 
 613 static const u8 rtl8225z2_tx_gain_cck_ofdm[] = {
 614         0x00, 0x01, 0x02, 0x03, 0x04, 0x05,
 615         0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b,
 616         0x0c, 0x0d, 0x0e, 0x0f, 0x10, 0x11,
 617         0x12, 0x13, 0x14, 0x15, 0x16, 0x17,
 618         0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d,
 619         0x1e, 0x1f, 0x20, 0x21, 0x22, 0x23
 620 };
 621 
 622 static void rtl8225z2_rf_set_tx_power(struct ieee80211_hw *dev, int channel)
 623 {
 624         struct rtl8187_priv *priv = dev->priv;
 625         u8 cck_power, ofdm_power;
 626         const u8 *tmp;
 627         u32 reg;
 628         int i;
 629 
 630         cck_power = priv->channels[channel - 1].hw_value & 0xF;
 631         ofdm_power = priv->channels[channel - 1].hw_value >> 4;
 632 
 633         cck_power = min(cck_power, (u8)15);
 634         cck_power += priv->txpwr_base & 0xF;
 635         cck_power = min(cck_power, (u8)35);
 636 
 637         if (ofdm_power > (u8)15)
 638                 ofdm_power = 25;
 639         else
 640                 ofdm_power += 10;
 641         ofdm_power += priv->txpwr_base >> 4;
 642         ofdm_power = min(ofdm_power, (u8)35);
 643 
 644         if (channel == 14)
 645                 tmp = rtl8225z2_tx_power_cck_ch14;
 646         else
 647                 tmp = rtl8225z2_tx_power_cck;
 648 
 649         for (i = 0; i < 8; i++)
 650                 rtl8225_write_phy_cck(dev, 0x44 + i, *tmp++);
 651 
 652         rtl818x_iowrite8(priv, &priv->map->TX_GAIN_CCK,
 653                          rtl8225z2_tx_gain_cck_ofdm[cck_power]);
 654         msleep(1);
 655 
 656         /* anaparam2 on */
 657         rtl818x_iowrite8(priv, &priv->map->EEPROM_CMD, RTL818X_EEPROM_CMD_CONFIG);
 658         reg = rtl818x_ioread8(priv, &priv->map->CONFIG3);
 659         rtl818x_iowrite8(priv, &priv->map->CONFIG3,
 660                         reg | RTL818X_CONFIG3_ANAPARAM_WRITE);
 661         rtl818x_iowrite32(priv, &priv->map->ANAPARAM2,
 662                           RTL8187_RTL8225_ANAPARAM2_ON);
 663         rtl818x_iowrite8(priv, &priv->map->CONFIG3,
 664                         reg & ~RTL818X_CONFIG3_ANAPARAM_WRITE);
 665         rtl818x_iowrite8(priv, &priv->map->EEPROM_CMD, RTL818X_EEPROM_CMD_NORMAL);
 666 
 667         rtl8225_write_phy_ofdm(dev, 2, 0x42);
 668         rtl8225_write_phy_ofdm(dev, 5, 0x00);
 669         rtl8225_write_phy_ofdm(dev, 6, 0x40);
 670         rtl8225_write_phy_ofdm(dev, 7, 0x00);
 671         rtl8225_write_phy_ofdm(dev, 8, 0x40);
 672 
 673         rtl818x_iowrite8(priv, &priv->map->TX_GAIN_OFDM,
 674                          rtl8225z2_tx_gain_cck_ofdm[ofdm_power]);
 675         msleep(1);
 676 }
 677 
 678 static void rtl8225z2_b_rf_set_tx_power(struct ieee80211_hw *dev, int channel)
 679 {
 680         struct rtl8187_priv *priv = dev->priv;
 681         u8 cck_power, ofdm_power;
 682         const u8 *tmp;
 683         int i;
 684 
 685         cck_power = priv->channels[channel - 1].hw_value & 0xF;
 686         ofdm_power = priv->channels[channel - 1].hw_value >> 4;
 687 
 688         cck_power += (priv->hw_rev == RTL8187BvB) ? 0 : 7;
 689         cck_power += priv->txpwr_base & 0xF;
 690         cck_power = min(cck_power, (u8)35);
 691 
 692         if (ofdm_power > 15)
 693                 ofdm_power = (priv->hw_rev == RTL8187BvB) ? 17 : 25;
 694         else
 695                 ofdm_power += (priv->hw_rev == RTL8187BvB) ? 2 : 10;
 696         ofdm_power += (priv->txpwr_base >> 4) & 0xF;
 697         ofdm_power = min(ofdm_power, (u8)35);
 698 
 699         if (channel == 14)
 700                 tmp = rtl8225z2_tx_power_cck_ch14;
 701         else
 702                 tmp = rtl8225z2_tx_power_cck;
 703 
 704         if (priv->hw_rev == RTL8187BvB) {
 705                 if (cck_power <= 6)
 706                         ; /* do nothing */
 707                 else if (cck_power <= 11)
 708                         tmp += 8;
 709                 else
 710                         tmp += 16;
 711         } else {
 712                 if (cck_power <= 5)
 713                         ; /* do nothing */
 714                 else if (cck_power <= 11)
 715                         tmp += 8;
 716                 else if (cck_power <= 17)
 717                         tmp += 16;
 718                 else
 719                         tmp += 24;
 720         }
 721 
 722         for (i = 0; i < 8; i++)
 723                 rtl8225_write_phy_cck(dev, 0x44 + i, *tmp++);
 724 
 725         rtl818x_iowrite8(priv, &priv->map->TX_GAIN_CCK,
 726                          rtl8225z2_tx_gain_cck_ofdm[cck_power] << 1);
 727         msleep(1);
 728 
 729         rtl818x_iowrite8(priv, &priv->map->TX_GAIN_OFDM,
 730                          rtl8225z2_tx_gain_cck_ofdm[ofdm_power] << 1);
 731         if (priv->hw_rev == RTL8187BvB) {
 732                 if (ofdm_power <= 11) {
 733                         rtl8225_write_phy_ofdm(dev, 0x87, 0x60);
 734                         rtl8225_write_phy_ofdm(dev, 0x89, 0x60);
 735                 } else {
 736                         rtl8225_write_phy_ofdm(dev, 0x87, 0x5c);
 737                         rtl8225_write_phy_ofdm(dev, 0x89, 0x5c);
 738                 }
 739         } else {
 740                 if (ofdm_power <= 11) {
 741                         rtl8225_write_phy_ofdm(dev, 0x87, 0x5c);
 742                         rtl8225_write_phy_ofdm(dev, 0x89, 0x5c);
 743                 } else if (ofdm_power <= 17) {
 744                         rtl8225_write_phy_ofdm(dev, 0x87, 0x54);
 745                         rtl8225_write_phy_ofdm(dev, 0x89, 0x54);
 746                 } else {
 747                         rtl8225_write_phy_ofdm(dev, 0x87, 0x50);
 748                         rtl8225_write_phy_ofdm(dev, 0x89, 0x50);
 749                 }
 750         }
 751         msleep(1);
 752 }
 753 
 754 static const u16 rtl8225z2_rxgain[] = {
 755         0x0400, 0x0401, 0x0402, 0x0403, 0x0404, 0x0405, 0x0408, 0x0409,
 756         0x040a, 0x040b, 0x0502, 0x0503, 0x0504, 0x0505, 0x0540, 0x0541,
 757         0x0542, 0x0543, 0x0544, 0x0545, 0x0580, 0x0581, 0x0582, 0x0583,
 758         0x0584, 0x0585, 0x0588, 0x0589, 0x058a, 0x058b, 0x0643, 0x0644,
 759         0x0645, 0x0680, 0x0681, 0x0682, 0x0683, 0x0684, 0x0685, 0x0688,
 760         0x0689, 0x068a, 0x068b, 0x068c, 0x0742, 0x0743, 0x0744, 0x0745,
 761         0x0780, 0x0781, 0x0782, 0x0783, 0x0784, 0x0785, 0x0788, 0x0789,
 762         0x078a, 0x078b, 0x078c, 0x078d, 0x0790, 0x0791, 0x0792, 0x0793,
 763         0x0794, 0x0795, 0x0798, 0x0799, 0x079a, 0x079b, 0x079c, 0x079d,
 764         0x07a0, 0x07a1, 0x07a2, 0x07a3, 0x07a4, 0x07a5, 0x07a8, 0x07a9,
 765         0x03aa, 0x03ab, 0x03ac, 0x03ad, 0x03b0, 0x03b1, 0x03b2, 0x03b3,
 766         0x03b4, 0x03b5, 0x03b8, 0x03b9, 0x03ba, 0x03bb, 0x03bb
 767 };
 768 
 769 static const u8 rtl8225z2_gain_bg[] = {
 770         0x23, 0x15, 0xa5, /* -82-1dBm */
 771         0x23, 0x15, 0xb5, /* -82-2dBm */
 772         0x23, 0x15, 0xc5, /* -82-3dBm */
 773         0x33, 0x15, 0xc5, /* -78dBm */
 774         0x43, 0x15, 0xc5, /* -74dBm */
 775         0x53, 0x15, 0xc5, /* -70dBm */
 776         0x63, 0x15, 0xc5  /* -66dBm */
 777 };
 778 
 779 static void rtl8225z2_rf_init(struct ieee80211_hw *dev)
 780 {
 781         struct rtl8187_priv *priv = dev->priv;
 782         int i;
 783 
 784         rtl8225_write(dev, 0x0, 0x2BF);
 785         rtl8225_write(dev, 0x1, 0xEE0);
 786         rtl8225_write(dev, 0x2, 0x44D);
 787         rtl8225_write(dev, 0x3, 0x441);
 788         rtl8225_write(dev, 0x4, 0x8C3);
 789         rtl8225_write(dev, 0x5, 0xC72);
 790         rtl8225_write(dev, 0x6, 0x0E6);
 791         rtl8225_write(dev, 0x7, 0x82A);
 792         rtl8225_write(dev, 0x8, 0x03F);
 793         rtl8225_write(dev, 0x9, 0x335);
 794         rtl8225_write(dev, 0xa, 0x9D4);
 795         rtl8225_write(dev, 0xb, 0x7BB);
 796         rtl8225_write(dev, 0xc, 0x850);
 797         rtl8225_write(dev, 0xd, 0xCDF);
 798         rtl8225_write(dev, 0xe, 0x02B);
 799         rtl8225_write(dev, 0xf, 0x114);
 800         msleep(100);
 801 
 802         rtl8225_write(dev, 0x0, 0x1B7);
 803 
 804         for (i = 0; i < ARRAY_SIZE(rtl8225z2_rxgain); i++) {
 805                 rtl8225_write(dev, 0x1, i + 1);
 806                 rtl8225_write(dev, 0x2, rtl8225z2_rxgain[i]);
 807         }
 808 
 809         rtl8225_write(dev, 0x3, 0x080);
 810         rtl8225_write(dev, 0x5, 0x004);
 811         rtl8225_write(dev, 0x0, 0x0B7);
 812         rtl8225_write(dev, 0x2, 0xc4D);
 813 
 814         msleep(200);
 815         rtl8225_write(dev, 0x2, 0x44D);
 816         msleep(100);
 817 
 818         if (!(rtl8225_read(dev, 6) & (1 << 7))) {
 819                 rtl8225_write(dev, 0x02, 0x0C4D);
 820                 msleep(200);
 821                 rtl8225_write(dev, 0x02, 0x044D);
 822                 msleep(100);
 823                 if (!(rtl8225_read(dev, 6) & (1 << 7)))
 824                         wiphy_warn(dev->wiphy, "RF Calibration Failed! %x\n",
 825                                    rtl8225_read(dev, 6));
 826         }
 827 
 828         msleep(200);
 829 
 830         rtl8225_write(dev, 0x0, 0x2BF);
 831 
 832         for (i = 0; i < ARRAY_SIZE(rtl8225_agc); i++) {
 833                 rtl8225_write_phy_ofdm(dev, 0xB, rtl8225_agc[i]);
 834                 rtl8225_write_phy_ofdm(dev, 0xA, 0x80 + i);
 835         }
 836 
 837         msleep(1);
 838 
 839         rtl8225_write_phy_ofdm(dev, 0x00, 0x01);
 840         rtl8225_write_phy_ofdm(dev, 0x01, 0x02);
 841         rtl8225_write_phy_ofdm(dev, 0x02, 0x42);
 842         rtl8225_write_phy_ofdm(dev, 0x03, 0x00);
 843         rtl8225_write_phy_ofdm(dev, 0x04, 0x00);
 844         rtl8225_write_phy_ofdm(dev, 0x05, 0x00);
 845         rtl8225_write_phy_ofdm(dev, 0x06, 0x40);
 846         rtl8225_write_phy_ofdm(dev, 0x07, 0x00);
 847         rtl8225_write_phy_ofdm(dev, 0x08, 0x40);
 848         rtl8225_write_phy_ofdm(dev, 0x09, 0xfe);
 849         rtl8225_write_phy_ofdm(dev, 0x0a, 0x08);
 850         rtl8225_write_phy_ofdm(dev, 0x0b, 0x80);
 851         rtl8225_write_phy_ofdm(dev, 0x0c, 0x01);
 852         rtl8225_write_phy_ofdm(dev, 0x0d, 0x43);
 853         rtl8225_write_phy_ofdm(dev, 0x0e, 0xd3);
 854         rtl8225_write_phy_ofdm(dev, 0x0f, 0x38);
 855         rtl8225_write_phy_ofdm(dev, 0x10, 0x84);
 856         rtl8225_write_phy_ofdm(dev, 0x11, 0x07);
 857         rtl8225_write_phy_ofdm(dev, 0x12, 0x20);
 858         rtl8225_write_phy_ofdm(dev, 0x13, 0x20);
 859         rtl8225_write_phy_ofdm(dev, 0x14, 0x00);
 860         rtl8225_write_phy_ofdm(dev, 0x15, 0x40);
 861         rtl8225_write_phy_ofdm(dev, 0x16, 0x00);
 862         rtl8225_write_phy_ofdm(dev, 0x17, 0x40);
 863         rtl8225_write_phy_ofdm(dev, 0x18, 0xef);
 864         rtl8225_write_phy_ofdm(dev, 0x19, 0x19);
 865         rtl8225_write_phy_ofdm(dev, 0x1a, 0x20);
 866         rtl8225_write_phy_ofdm(dev, 0x1b, 0x15);
 867         rtl8225_write_phy_ofdm(dev, 0x1c, 0x04);
 868         rtl8225_write_phy_ofdm(dev, 0x1d, 0xc5);
 869         rtl8225_write_phy_ofdm(dev, 0x1e, 0x95);
 870         rtl8225_write_phy_ofdm(dev, 0x1f, 0x75);
 871         rtl8225_write_phy_ofdm(dev, 0x20, 0x1f);
 872         rtl8225_write_phy_ofdm(dev, 0x21, 0x17);
 873         rtl8225_write_phy_ofdm(dev, 0x22, 0x16);
 874         rtl8225_write_phy_ofdm(dev, 0x23, 0x80);
 875         rtl8225_write_phy_ofdm(dev, 0x24, 0x46);
 876         rtl8225_write_phy_ofdm(dev, 0x25, 0x00);
 877         rtl8225_write_phy_ofdm(dev, 0x26, 0x90);
 878         rtl8225_write_phy_ofdm(dev, 0x27, 0x88);
 879 
 880         rtl8225_write_phy_ofdm(dev, 0x0b, rtl8225z2_gain_bg[4 * 3]);
 881         rtl8225_write_phy_ofdm(dev, 0x1b, rtl8225z2_gain_bg[4 * 3 + 1]);
 882         rtl8225_write_phy_ofdm(dev, 0x1d, rtl8225z2_gain_bg[4 * 3 + 2]);
 883         rtl8225_write_phy_ofdm(dev, 0x21, 0x37);
 884 
 885         rtl8225_write_phy_cck(dev, 0x00, 0x98);
 886         rtl8225_write_phy_cck(dev, 0x03, 0x20);
 887         rtl8225_write_phy_cck(dev, 0x04, 0x7e);
 888         rtl8225_write_phy_cck(dev, 0x05, 0x12);
 889         rtl8225_write_phy_cck(dev, 0x06, 0xfc);
 890         rtl8225_write_phy_cck(dev, 0x07, 0x78);
 891         rtl8225_write_phy_cck(dev, 0x08, 0x2e);
 892         rtl8225_write_phy_cck(dev, 0x10, 0x9b);
 893         rtl8225_write_phy_cck(dev, 0x11, 0x88);
 894         rtl8225_write_phy_cck(dev, 0x12, 0x47);
 895         rtl8225_write_phy_cck(dev, 0x13, 0xd0);
 896         rtl8225_write_phy_cck(dev, 0x19, 0x00);
 897         rtl8225_write_phy_cck(dev, 0x1a, 0xa0);
 898         rtl8225_write_phy_cck(dev, 0x1b, 0x08);
 899         rtl8225_write_phy_cck(dev, 0x40, 0x86);
 900         rtl8225_write_phy_cck(dev, 0x41, 0x8d);
 901         rtl8225_write_phy_cck(dev, 0x42, 0x15);
 902         rtl8225_write_phy_cck(dev, 0x43, 0x18);
 903         rtl8225_write_phy_cck(dev, 0x44, 0x36);
 904         rtl8225_write_phy_cck(dev, 0x45, 0x35);
 905         rtl8225_write_phy_cck(dev, 0x46, 0x2e);
 906         rtl8225_write_phy_cck(dev, 0x47, 0x25);
 907         rtl8225_write_phy_cck(dev, 0x48, 0x1c);
 908         rtl8225_write_phy_cck(dev, 0x49, 0x12);
 909         rtl8225_write_phy_cck(dev, 0x4a, 0x09);
 910         rtl8225_write_phy_cck(dev, 0x4b, 0x04);
 911         rtl8225_write_phy_cck(dev, 0x4c, 0x05);
 912 
 913         rtl818x_iowrite8(priv, (u8 *)0xFF5B, 0x0D); msleep(1);
 914 
 915         rtl8225z2_rf_set_tx_power(dev, 1);
 916 
 917         /* RX antenna default to A */
 918         rtl8225_write_phy_cck(dev, 0x10, 0x9b);                 /* B: 0xDB */
 919         rtl8225_write_phy_ofdm(dev, 0x26, 0x90);                /* B: 0x10 */
 920 
 921         rtl818x_iowrite8(priv, &priv->map->TX_ANTENNA, 0x03);   /* B: 0x00 */
 922         msleep(1);
 923         rtl818x_iowrite32(priv, (__le32 *)0xFF94, 0x3dc00002);
 924 }
 925 
 926 static void rtl8225z2_b_rf_init(struct ieee80211_hw *dev)
 927 {
 928         struct rtl8187_priv *priv = dev->priv;
 929         int i;
 930 
 931         rtl8225_write(dev, 0x0, 0x0B7);
 932         rtl8225_write(dev, 0x1, 0xEE0);
 933         rtl8225_write(dev, 0x2, 0x44D);
 934         rtl8225_write(dev, 0x3, 0x441);
 935         rtl8225_write(dev, 0x4, 0x8C3);
 936         rtl8225_write(dev, 0x5, 0xC72);
 937         rtl8225_write(dev, 0x6, 0x0E6);
 938         rtl8225_write(dev, 0x7, 0x82A);
 939         rtl8225_write(dev, 0x8, 0x03F);
 940         rtl8225_write(dev, 0x9, 0x335);
 941         rtl8225_write(dev, 0xa, 0x9D4);
 942         rtl8225_write(dev, 0xb, 0x7BB);
 943         rtl8225_write(dev, 0xc, 0x850);
 944         rtl8225_write(dev, 0xd, 0xCDF);
 945         rtl8225_write(dev, 0xe, 0x02B);
 946         rtl8225_write(dev, 0xf, 0x114);
 947 
 948         rtl8225_write(dev, 0x0, 0x1B7);
 949 
 950         for (i = 0; i < ARRAY_SIZE(rtl8225z2_rxgain); i++) {
 951                 rtl8225_write(dev, 0x1, i + 1);
 952                 rtl8225_write(dev, 0x2, rtl8225z2_rxgain[i]);
 953         }
 954 
 955         rtl8225_write(dev, 0x3, 0x080);
 956         rtl8225_write(dev, 0x5, 0x004);
 957         rtl8225_write(dev, 0x0, 0x0B7);
 958 
 959         rtl8225_write(dev, 0x2, 0xC4D);
 960 
 961         rtl8225_write(dev, 0x2, 0x44D);
 962         rtl8225_write(dev, 0x0, 0x2BF);
 963 
 964         rtl818x_iowrite8(priv, &priv->map->TX_GAIN_CCK, 0x03);
 965         rtl818x_iowrite8(priv, &priv->map->TX_GAIN_OFDM, 0x07);
 966         rtl818x_iowrite8(priv, &priv->map->TX_ANTENNA, 0x03);
 967 
 968         rtl8225_write_phy_ofdm(dev, 0x80, 0x12);
 969         for (i = 0; i < ARRAY_SIZE(rtl8225z2_agc); i++) {
 970                 rtl8225_write_phy_ofdm(dev, 0xF, rtl8225z2_agc[i]);
 971                 rtl8225_write_phy_ofdm(dev, 0xE, 0x80 + i);
 972                 rtl8225_write_phy_ofdm(dev, 0xE, 0);
 973         }
 974         rtl8225_write_phy_ofdm(dev, 0x80, 0x10);
 975 
 976         for (i = 0; i < ARRAY_SIZE(rtl8225z2_ofdm); i++)
 977                 rtl8225_write_phy_ofdm(dev, i, rtl8225z2_ofdm[i]);
 978 
 979         rtl8225_write_phy_ofdm(dev, 0x97, 0x46);
 980         rtl8225_write_phy_ofdm(dev, 0xa4, 0xb6);
 981         rtl8225_write_phy_ofdm(dev, 0x85, 0xfc);
 982         rtl8225_write_phy_cck(dev, 0xc1, 0x88);
 983 }
 984 
 985 static void rtl8225_rf_stop(struct ieee80211_hw *dev)
 986 {
 987         rtl8225_write(dev, 0x4, 0x1f);
 988 }
 989 
 990 static void rtl8225_rf_set_channel(struct ieee80211_hw *dev,
 991                                    struct ieee80211_conf *conf)
 992 {
 993         struct rtl8187_priv *priv = dev->priv;
 994         int chan =
 995                 ieee80211_frequency_to_channel(conf->chandef.chan->center_freq);
 996 
 997         if (priv->rf->init == rtl8225_rf_init)
 998                 rtl8225_rf_set_tx_power(dev, chan);
 999         else if (priv->rf->init == rtl8225z2_rf_init)
1000                 rtl8225z2_rf_set_tx_power(dev, chan);
1001         else
1002                 rtl8225z2_b_rf_set_tx_power(dev, chan);
1003 
1004         rtl8225_write(dev, 0x7, rtl8225_chan[chan - 1]);
1005         msleep(10);
1006 }
1007 
1008 static const struct rtl818x_rf_ops rtl8225_ops = {
1009         .name           = "rtl8225",
1010         .init           = rtl8225_rf_init,
1011         .stop           = rtl8225_rf_stop,
1012         .set_chan       = rtl8225_rf_set_channel
1013 };
1014 
1015 static const struct rtl818x_rf_ops rtl8225z2_ops = {
1016         .name           = "rtl8225z2",
1017         .init           = rtl8225z2_rf_init,
1018         .stop           = rtl8225_rf_stop,
1019         .set_chan       = rtl8225_rf_set_channel
1020 };
1021 
1022 static const struct rtl818x_rf_ops rtl8225z2_b_ops = {
1023         .name           = "rtl8225z2",
1024         .init           = rtl8225z2_b_rf_init,
1025         .stop           = rtl8225_rf_stop,
1026         .set_chan       = rtl8225_rf_set_channel
1027 };
1028 
1029 const struct rtl818x_rf_ops * rtl8187_detect_rf(struct ieee80211_hw *dev)
1030 {
1031         u16 reg8, reg9;
1032         struct rtl8187_priv *priv = dev->priv;
1033 
1034         if (!priv->is_rtl8187b) {
1035                 rtl8225_write(dev, 0, 0x1B7);
1036 
1037                 reg8 = rtl8225_read(dev, 8);
1038                 reg9 = rtl8225_read(dev, 9);
1039 
1040                 rtl8225_write(dev, 0, 0x0B7);
1041 
1042                 if (reg8 != 0x588 || reg9 != 0x700)
1043                         return &rtl8225_ops;
1044 
1045                 return &rtl8225z2_ops;
1046         } else
1047                 return &rtl8225z2_b_ops;
1048 }

/* [<][>][^][v][top][bottom][index][help] */