1 // SPDX-License-Identifier: GPL-2.0-or-later 2 /* ZD1211 USB-WLAN driver for Linux 3 * 4 * Copyright (C) 2005-2007 Ulrich Kunitz <kune@deine-taler.de> 5 * Copyright (C) 2006-2007 Daniel Drake <dsd@gentoo.org> 6 */ 7 8 #include <linux/kernel.h> 9 10 #include "zd_rf.h" 11 #include "zd_usb.h" 12 #include "zd_chip.h" 13 14 #define IS_AL2230S(chip) ((chip)->al2230s_bit || (chip)->rf.type == AL2230S_RF) 15 16 static const u32 zd1211_al2230_table[][3] = { 17 RF_CHANNEL( 1) = { 0x03f790, 0x033331, 0x00000d, }, 18 RF_CHANNEL( 2) = { 0x03f790, 0x0b3331, 0x00000d, }, 19 RF_CHANNEL( 3) = { 0x03e790, 0x033331, 0x00000d, }, 20 RF_CHANNEL( 4) = { 0x03e790, 0x0b3331, 0x00000d, }, 21 RF_CHANNEL( 5) = { 0x03f7a0, 0x033331, 0x00000d, }, 22 RF_CHANNEL( 6) = { 0x03f7a0, 0x0b3331, 0x00000d, }, 23 RF_CHANNEL( 7) = { 0x03e7a0, 0x033331, 0x00000d, }, 24 RF_CHANNEL( 8) = { 0x03e7a0, 0x0b3331, 0x00000d, }, 25 RF_CHANNEL( 9) = { 0x03f7b0, 0x033331, 0x00000d, }, 26 RF_CHANNEL(10) = { 0x03f7b0, 0x0b3331, 0x00000d, }, 27 RF_CHANNEL(11) = { 0x03e7b0, 0x033331, 0x00000d, }, 28 RF_CHANNEL(12) = { 0x03e7b0, 0x0b3331, 0x00000d, }, 29 RF_CHANNEL(13) = { 0x03f7c0, 0x033331, 0x00000d, }, 30 RF_CHANNEL(14) = { 0x03e7c0, 0x066661, 0x00000d, }, 31 }; 32 33 static const u32 zd1211b_al2230_table[][3] = { 34 RF_CHANNEL( 1) = { 0x09efc0, 0x8cccc0, 0xb00000, }, 35 RF_CHANNEL( 2) = { 0x09efc0, 0x8cccd0, 0xb00000, }, 36 RF_CHANNEL( 3) = { 0x09e7c0, 0x8cccc0, 0xb00000, }, 37 RF_CHANNEL( 4) = { 0x09e7c0, 0x8cccd0, 0xb00000, }, 38 RF_CHANNEL( 5) = { 0x05efc0, 0x8cccc0, 0xb00000, }, 39 RF_CHANNEL( 6) = { 0x05efc0, 0x8cccd0, 0xb00000, }, 40 RF_CHANNEL( 7) = { 0x05e7c0, 0x8cccc0, 0xb00000, }, 41 RF_CHANNEL( 8) = { 0x05e7c0, 0x8cccd0, 0xb00000, }, 42 RF_CHANNEL( 9) = { 0x0defc0, 0x8cccc0, 0xb00000, }, 43 RF_CHANNEL(10) = { 0x0defc0, 0x8cccd0, 0xb00000, }, 44 RF_CHANNEL(11) = { 0x0de7c0, 0x8cccc0, 0xb00000, }, 45 RF_CHANNEL(12) = { 0x0de7c0, 0x8cccd0, 0xb00000, }, 46 RF_CHANNEL(13) = { 0x03efc0, 0x8cccc0, 0xb00000, }, 47 RF_CHANNEL(14) = { 0x03e7c0, 0x866660, 0xb00000, }, 48 }; 49 50 static const struct zd_ioreq16 zd1211b_ioreqs_shared_1[] = { 51 { ZD_CR240, 0x57 }, { ZD_CR9, 0xe0 }, 52 }; 53 54 static const struct zd_ioreq16 ioreqs_init_al2230s[] = { 55 { ZD_CR47, 0x1e }, /* MARK_002 */ 56 { ZD_CR106, 0x22 }, 57 { ZD_CR107, 0x2a }, /* MARK_002 */ 58 { ZD_CR109, 0x13 }, /* MARK_002 */ 59 { ZD_CR118, 0xf8 }, /* MARK_002 */ 60 { ZD_CR119, 0x12 }, { ZD_CR122, 0xe0 }, 61 { ZD_CR128, 0x10 }, /* MARK_001 from 0xe->0x10 */ 62 { ZD_CR129, 0x0e }, /* MARK_001 from 0xd->0x0e */ 63 { ZD_CR130, 0x10 }, /* MARK_001 from 0xb->0x0d */ 64 }; 65 66 static int zd1211b_al2230_finalize_rf(struct zd_chip *chip) 67 { 68 int r; 69 static const struct zd_ioreq16 ioreqs[] = { 70 { ZD_CR80, 0x30 }, { ZD_CR81, 0x30 }, { ZD_CR79, 0x58 }, 71 { ZD_CR12, 0xf0 }, { ZD_CR77, 0x1b }, { ZD_CR78, 0x58 }, 72 { ZD_CR203, 0x06 }, 73 { }, 74 75 { ZD_CR240, 0x80 }, 76 }; 77 78 r = zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); 79 if (r) 80 return r; 81 82 /* related to antenna selection? */ 83 if (chip->new_phy_layout) { 84 r = zd_iowrite16_locked(chip, 0xe1, ZD_CR9); 85 if (r) 86 return r; 87 } 88 89 return zd_iowrite16_locked(chip, 0x06, ZD_CR203); 90 } 91 92 static int zd1211_al2230_init_hw(struct zd_rf *rf) 93 { 94 int r; 95 struct zd_chip *chip = zd_rf_to_chip(rf); 96 97 static const struct zd_ioreq16 ioreqs_init[] = { 98 { ZD_CR15, 0x20 }, { ZD_CR23, 0x40 }, { ZD_CR24, 0x20 }, 99 { ZD_CR26, 0x11 }, { ZD_CR28, 0x3e }, { ZD_CR29, 0x00 }, 100 { ZD_CR44, 0x33 }, { ZD_CR106, 0x2a }, { ZD_CR107, 0x1a }, 101 { ZD_CR109, 0x09 }, { ZD_CR110, 0x27 }, { ZD_CR111, 0x2b }, 102 { ZD_CR112, 0x2b }, { ZD_CR119, 0x0a }, { ZD_CR10, 0x89 }, 103 /* for newest (3rd cut) AL2300 */ 104 { ZD_CR17, 0x28 }, 105 { ZD_CR26, 0x93 }, { ZD_CR34, 0x30 }, 106 /* for newest (3rd cut) AL2300 */ 107 { ZD_CR35, 0x3e }, 108 { ZD_CR41, 0x24 }, { ZD_CR44, 0x32 }, 109 /* for newest (3rd cut) AL2300 */ 110 { ZD_CR46, 0x96 }, 111 { ZD_CR47, 0x1e }, { ZD_CR79, 0x58 }, { ZD_CR80, 0x30 }, 112 { ZD_CR81, 0x30 }, { ZD_CR87, 0x0a }, { ZD_CR89, 0x04 }, 113 { ZD_CR92, 0x0a }, { ZD_CR99, 0x28 }, { ZD_CR100, 0x00 }, 114 { ZD_CR101, 0x13 }, { ZD_CR102, 0x27 }, { ZD_CR106, 0x24 }, 115 { ZD_CR107, 0x2a }, { ZD_CR109, 0x09 }, { ZD_CR110, 0x13 }, 116 { ZD_CR111, 0x1f }, { ZD_CR112, 0x1f }, { ZD_CR113, 0x27 }, 117 { ZD_CR114, 0x27 }, 118 /* for newest (3rd cut) AL2300 */ 119 { ZD_CR115, 0x24 }, 120 { ZD_CR116, 0x24 }, { ZD_CR117, 0xf4 }, { ZD_CR118, 0xfc }, 121 { ZD_CR119, 0x10 }, { ZD_CR120, 0x4f }, { ZD_CR121, 0x77 }, 122 { ZD_CR122, 0xe0 }, { ZD_CR137, 0x88 }, { ZD_CR252, 0xff }, 123 { ZD_CR253, 0xff }, 124 }; 125 126 static const struct zd_ioreq16 ioreqs_pll[] = { 127 /* shdnb(PLL_ON)=0 */ 128 { ZD_CR251, 0x2f }, 129 /* shdnb(PLL_ON)=1 */ 130 { ZD_CR251, 0x3f }, 131 { ZD_CR138, 0x28 }, { ZD_CR203, 0x06 }, 132 }; 133 134 static const u32 rv1[] = { 135 /* Channel 1 */ 136 0x03f790, 137 0x033331, 138 0x00000d, 139 140 0x0b3331, 141 0x03b812, 142 0x00fff3, 143 }; 144 145 static const u32 rv2[] = { 146 0x000da4, 147 0x0f4dc5, /* fix freq shift, 0x04edc5 */ 148 0x0805b6, 149 0x011687, 150 0x000688, 151 0x0403b9, /* external control TX power (ZD_CR31) */ 152 0x00dbba, 153 0x00099b, 154 0x0bdffc, 155 0x00000d, 156 0x00500f, 157 }; 158 159 static const u32 rv3[] = { 160 0x00d00f, 161 0x004c0f, 162 0x00540f, 163 0x00700f, 164 0x00500f, 165 }; 166 167 r = zd_iowrite16a_locked(chip, ioreqs_init, ARRAY_SIZE(ioreqs_init)); 168 if (r) 169 return r; 170 171 if (IS_AL2230S(chip)) { 172 r = zd_iowrite16a_locked(chip, ioreqs_init_al2230s, 173 ARRAY_SIZE(ioreqs_init_al2230s)); 174 if (r) 175 return r; 176 } 177 178 r = zd_rfwritev_locked(chip, rv1, ARRAY_SIZE(rv1), RF_RV_BITS); 179 if (r) 180 return r; 181 182 /* improve band edge for AL2230S */ 183 if (IS_AL2230S(chip)) 184 r = zd_rfwrite_locked(chip, 0x000824, RF_RV_BITS); 185 else 186 r = zd_rfwrite_locked(chip, 0x0005a4, RF_RV_BITS); 187 if (r) 188 return r; 189 190 r = zd_rfwritev_locked(chip, rv2, ARRAY_SIZE(rv2), RF_RV_BITS); 191 if (r) 192 return r; 193 194 r = zd_iowrite16a_locked(chip, ioreqs_pll, ARRAY_SIZE(ioreqs_pll)); 195 if (r) 196 return r; 197 198 r = zd_rfwritev_locked(chip, rv3, ARRAY_SIZE(rv3), RF_RV_BITS); 199 if (r) 200 return r; 201 202 return 0; 203 } 204 205 static int zd1211b_al2230_init_hw(struct zd_rf *rf) 206 { 207 int r; 208 struct zd_chip *chip = zd_rf_to_chip(rf); 209 210 static const struct zd_ioreq16 ioreqs1[] = { 211 { ZD_CR10, 0x89 }, { ZD_CR15, 0x20 }, 212 { ZD_CR17, 0x2B }, /* for newest(3rd cut) AL2230 */ 213 { ZD_CR23, 0x40 }, { ZD_CR24, 0x20 }, { ZD_CR26, 0x93 }, 214 { ZD_CR28, 0x3e }, { ZD_CR29, 0x00 }, 215 { ZD_CR33, 0x28 }, /* 5621 */ 216 { ZD_CR34, 0x30 }, 217 { ZD_CR35, 0x3e }, /* for newest(3rd cut) AL2230 */ 218 { ZD_CR41, 0x24 }, { ZD_CR44, 0x32 }, 219 { ZD_CR46, 0x99 }, /* for newest(3rd cut) AL2230 */ 220 { ZD_CR47, 0x1e }, 221 222 /* ZD1211B 05.06.10 */ 223 { ZD_CR48, 0x06 }, { ZD_CR49, 0xf9 }, { ZD_CR51, 0x01 }, 224 { ZD_CR52, 0x80 }, { ZD_CR53, 0x7e }, { ZD_CR65, 0x00 }, 225 { ZD_CR66, 0x00 }, { ZD_CR67, 0x00 }, { ZD_CR68, 0x00 }, 226 { ZD_CR69, 0x28 }, 227 228 { ZD_CR79, 0x58 }, { ZD_CR80, 0x30 }, { ZD_CR81, 0x30 }, 229 { ZD_CR87, 0x0a }, { ZD_CR89, 0x04 }, 230 { ZD_CR91, 0x00 }, /* 5621 */ 231 { ZD_CR92, 0x0a }, 232 { ZD_CR98, 0x8d }, /* 4804, for 1212 new algorithm */ 233 { ZD_CR99, 0x00 }, /* 5621 */ 234 { ZD_CR101, 0x13 }, { ZD_CR102, 0x27 }, 235 { ZD_CR106, 0x24 }, /* for newest(3rd cut) AL2230 */ 236 { ZD_CR107, 0x2a }, 237 { ZD_CR109, 0x13 }, /* 4804, for 1212 new algorithm */ 238 { ZD_CR110, 0x1f }, /* 4804, for 1212 new algorithm */ 239 { ZD_CR111, 0x1f }, { ZD_CR112, 0x1f }, { ZD_CR113, 0x27 }, 240 { ZD_CR114, 0x27 }, 241 { ZD_CR115, 0x26 }, /* 24->26 at 4902 for newest(3rd cut) 242 * AL2230 243 */ 244 { ZD_CR116, 0x24 }, 245 { ZD_CR117, 0xfa }, /* for 1211b */ 246 { ZD_CR118, 0xfa }, /* for 1211b */ 247 { ZD_CR119, 0x10 }, 248 { ZD_CR120, 0x4f }, 249 { ZD_CR121, 0x6c }, /* for 1211b */ 250 { ZD_CR122, 0xfc }, /* E0->FC at 4902 */ 251 { ZD_CR123, 0x57 }, /* 5623 */ 252 { ZD_CR125, 0xad }, /* 4804, for 1212 new algorithm */ 253 { ZD_CR126, 0x6c }, /* 5614 */ 254 { ZD_CR127, 0x03 }, /* 4804, for 1212 new algorithm */ 255 { ZD_CR137, 0x50 }, /* 5614 */ 256 { ZD_CR138, 0xa8 }, 257 { ZD_CR144, 0xac }, /* 5621 */ 258 { ZD_CR150, 0x0d }, { ZD_CR252, 0x34 }, { ZD_CR253, 0x34 }, 259 }; 260 261 static const u32 rv1[] = { 262 0x8cccd0, 263 0x481dc0, 264 0xcfff00, 265 0x25a000, 266 }; 267 268 static const u32 rv2[] = { 269 /* To improve AL2230 yield, improve phase noise, 4713 */ 270 0x25a000, 271 0xa3b2f0, 272 273 0x6da010, /* Reg6 update for MP versio */ 274 0xe36280, /* Modified by jxiao for Bor-Chin on 2004/08/02 */ 275 0x116000, 276 0x9dc020, /* External control TX power (ZD_CR31) */ 277 0x5ddb00, /* RegA update for MP version */ 278 0xd99000, /* RegB update for MP version */ 279 0x3ffbd0, /* RegC update for MP version */ 280 0xb00000, /* RegD update for MP version */ 281 282 /* improve phase noise and remove phase calibration,4713 */ 283 0xf01a00, 284 }; 285 286 static const struct zd_ioreq16 ioreqs2[] = { 287 { ZD_CR251, 0x2f }, /* shdnb(PLL_ON)=0 */ 288 { ZD_CR251, 0x7f }, /* shdnb(PLL_ON)=1 */ 289 }; 290 291 static const u32 rv3[] = { 292 /* To improve AL2230 yield, 4713 */ 293 0xf01b00, 294 0xf01e00, 295 0xf01a00, 296 }; 297 298 static const struct zd_ioreq16 ioreqs3[] = { 299 /* related to 6M band edge patching, happens unconditionally */ 300 { ZD_CR128, 0x14 }, { ZD_CR129, 0x12 }, { ZD_CR130, 0x10 }, 301 }; 302 303 r = zd_iowrite16a_locked(chip, zd1211b_ioreqs_shared_1, 304 ARRAY_SIZE(zd1211b_ioreqs_shared_1)); 305 if (r) 306 return r; 307 r = zd_iowrite16a_locked(chip, ioreqs1, ARRAY_SIZE(ioreqs1)); 308 if (r) 309 return r; 310 311 if (IS_AL2230S(chip)) { 312 r = zd_iowrite16a_locked(chip, ioreqs_init_al2230s, 313 ARRAY_SIZE(ioreqs_init_al2230s)); 314 if (r) 315 return r; 316 } 317 318 r = zd_rfwritev_cr_locked(chip, zd1211b_al2230_table[0], 3); 319 if (r) 320 return r; 321 r = zd_rfwritev_cr_locked(chip, rv1, ARRAY_SIZE(rv1)); 322 if (r) 323 return r; 324 325 if (IS_AL2230S(chip)) 326 r = zd_rfwrite_locked(chip, 0x241000, RF_RV_BITS); 327 else 328 r = zd_rfwrite_locked(chip, 0x25a000, RF_RV_BITS); 329 if (r) 330 return r; 331 332 r = zd_rfwritev_cr_locked(chip, rv2, ARRAY_SIZE(rv2)); 333 if (r) 334 return r; 335 r = zd_iowrite16a_locked(chip, ioreqs2, ARRAY_SIZE(ioreqs2)); 336 if (r) 337 return r; 338 r = zd_rfwritev_cr_locked(chip, rv3, ARRAY_SIZE(rv3)); 339 if (r) 340 return r; 341 r = zd_iowrite16a_locked(chip, ioreqs3, ARRAY_SIZE(ioreqs3)); 342 if (r) 343 return r; 344 return zd1211b_al2230_finalize_rf(chip); 345 } 346 347 static int zd1211_al2230_set_channel(struct zd_rf *rf, u8 channel) 348 { 349 int r; 350 const u32 *rv = zd1211_al2230_table[channel-1]; 351 struct zd_chip *chip = zd_rf_to_chip(rf); 352 static const struct zd_ioreq16 ioreqs[] = { 353 { ZD_CR138, 0x28 }, 354 { ZD_CR203, 0x06 }, 355 }; 356 357 r = zd_rfwritev_locked(chip, rv, 3, RF_RV_BITS); 358 if (r) 359 return r; 360 return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); 361 } 362 363 static int zd1211b_al2230_set_channel(struct zd_rf *rf, u8 channel) 364 { 365 int r; 366 const u32 *rv = zd1211b_al2230_table[channel-1]; 367 struct zd_chip *chip = zd_rf_to_chip(rf); 368 369 r = zd_iowrite16a_locked(chip, zd1211b_ioreqs_shared_1, 370 ARRAY_SIZE(zd1211b_ioreqs_shared_1)); 371 if (r) 372 return r; 373 374 r = zd_rfwritev_cr_locked(chip, rv, 3); 375 if (r) 376 return r; 377 378 return zd1211b_al2230_finalize_rf(chip); 379 } 380 381 static int zd1211_al2230_switch_radio_on(struct zd_rf *rf) 382 { 383 struct zd_chip *chip = zd_rf_to_chip(rf); 384 static const struct zd_ioreq16 ioreqs[] = { 385 { ZD_CR11, 0x00 }, 386 { ZD_CR251, 0x3f }, 387 }; 388 389 return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); 390 } 391 392 static int zd1211b_al2230_switch_radio_on(struct zd_rf *rf) 393 { 394 struct zd_chip *chip = zd_rf_to_chip(rf); 395 static const struct zd_ioreq16 ioreqs[] = { 396 { ZD_CR11, 0x00 }, 397 { ZD_CR251, 0x7f }, 398 }; 399 400 return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); 401 } 402 403 static int al2230_switch_radio_off(struct zd_rf *rf) 404 { 405 struct zd_chip *chip = zd_rf_to_chip(rf); 406 static const struct zd_ioreq16 ioreqs[] = { 407 { ZD_CR11, 0x04 }, 408 { ZD_CR251, 0x2f }, 409 }; 410 411 return zd_iowrite16a_locked(chip, ioreqs, ARRAY_SIZE(ioreqs)); 412 } 413 414 int zd_rf_init_al2230(struct zd_rf *rf) 415 { 416 struct zd_chip *chip = zd_rf_to_chip(rf); 417 418 rf->switch_radio_off = al2230_switch_radio_off; 419 if (zd_chip_is_zd1211b(chip)) { 420 rf->init_hw = zd1211b_al2230_init_hw; 421 rf->set_channel = zd1211b_al2230_set_channel; 422 rf->switch_radio_on = zd1211b_al2230_switch_radio_on; 423 } else { 424 rf->init_hw = zd1211_al2230_init_hw; 425 rf->set_channel = zd1211_al2230_set_channel; 426 rf->switch_radio_on = zd1211_al2230_switch_radio_on; 427 } 428 rf->patch_6m_band_edge = zd_rf_generic_patch_6m; 429 rf->patch_cck_gain = 1; 430 return 0; 431 } 432