wl1271: skip 3 unused bytes from the NVS
[linux-2.6/libata-dev.git] / drivers / net / wireless / wl12xx / wl1271_boot.c
blobfb3090c3ed1561f4c3a77c709d52172eb1201ddf
1 /*
2 * This file is part of wl1271
4 * Copyright (C) 2008-2009 Nokia Corporation
6 * Contact: Luciano Coelho <luciano.coelho@nokia.com>
8 * This program is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU General Public License
10 * version 2 as published by the Free Software Foundation.
12 * This program is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with this program; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
20 * 02110-1301 USA
24 #include <linux/gpio.h>
26 #include "wl1271_acx.h"
27 #include "wl1271_reg.h"
28 #include "wl1271_boot.h"
29 #include "wl1271_spi.h"
30 #include "wl1271_event.h"
32 static struct wl1271_partition_set part_table[PART_TABLE_LEN] = {
33 [PART_DOWN] = {
34 .mem = {
35 .start = 0x00000000,
36 .size = 0x000177c0
38 .reg = {
39 .start = REGISTERS_BASE,
40 .size = 0x00008800
42 .mem2 = {
43 .start = 0x00000000,
44 .size = 0x00000000
46 .mem3 = {
47 .start = 0x00000000,
48 .size = 0x00000000
52 [PART_WORK] = {
53 .mem = {
54 .start = 0x00040000,
55 .size = 0x00014fc0
57 .reg = {
58 .start = REGISTERS_BASE,
59 .size = 0x0000a000
61 .mem2 = {
62 .start = 0x003004f8,
63 .size = 0x00000004
65 .mem3 = {
66 .start = 0x00040404,
67 .size = 0x00000000
71 [PART_DRPW] = {
72 .mem = {
73 .start = 0x00040000,
74 .size = 0x00014fc0
76 .reg = {
77 .start = DRPW_BASE,
78 .size = 0x00006000
80 .mem2 = {
81 .start = 0x00000000,
82 .size = 0x00000000
84 .mem3 = {
85 .start = 0x00000000,
86 .size = 0x00000000
91 static void wl1271_boot_set_ecpu_ctrl(struct wl1271 *wl, u32 flag)
93 u32 cpu_ctrl;
95 /* 10.5.0 run the firmware (I) */
96 cpu_ctrl = wl1271_spi_read32(wl, ACX_REG_ECPU_CONTROL);
98 /* 10.5.1 run the firmware (II) */
99 cpu_ctrl |= flag;
100 wl1271_spi_write32(wl, ACX_REG_ECPU_CONTROL, cpu_ctrl);
103 static void wl1271_boot_fw_version(struct wl1271 *wl)
105 struct wl1271_static_data static_data;
107 wl1271_spi_read(wl, wl->cmd_box_addr,
108 &static_data, sizeof(static_data), false);
110 strncpy(wl->chip.fw_ver, static_data.fw_version,
111 sizeof(wl->chip.fw_ver));
113 /* make sure the string is NULL-terminated */
114 wl->chip.fw_ver[sizeof(wl->chip.fw_ver) - 1] = '\0';
117 static int wl1271_boot_upload_firmware_chunk(struct wl1271 *wl, void *buf,
118 size_t fw_data_len, u32 dest)
120 struct wl1271_partition_set partition;
121 int addr, chunk_num, partition_limit;
122 u8 *p, *chunk;
124 /* whal_FwCtrl_LoadFwImageSm() */
126 wl1271_debug(DEBUG_BOOT, "starting firmware upload");
128 wl1271_debug(DEBUG_BOOT, "fw_data_len %zd chunk_size %d",
129 fw_data_len, CHUNK_SIZE);
131 if ((fw_data_len % 4) != 0) {
132 wl1271_error("firmware length not multiple of four");
133 return -EIO;
136 chunk = kmalloc(CHUNK_SIZE, GFP_KERNEL);
137 if (!chunk) {
138 wl1271_error("allocation for firmware upload chunk failed");
139 return -ENOMEM;
142 memcpy(&partition, &part_table[PART_DOWN], sizeof(partition));
143 partition.mem.start = dest;
144 wl1271_set_partition(wl, &partition);
146 /* 10.1 set partition limit and chunk num */
147 chunk_num = 0;
148 partition_limit = part_table[PART_DOWN].mem.size;
150 while (chunk_num < fw_data_len / CHUNK_SIZE) {
151 /* 10.2 update partition, if needed */
152 addr = dest + (chunk_num + 2) * CHUNK_SIZE;
153 if (addr > partition_limit) {
154 addr = dest + chunk_num * CHUNK_SIZE;
155 partition_limit = chunk_num * CHUNK_SIZE +
156 part_table[PART_DOWN].mem.size;
157 partition.mem.start = addr;
158 wl1271_set_partition(wl, &partition);
161 /* 10.3 upload the chunk */
162 addr = dest + chunk_num * CHUNK_SIZE;
163 p = buf + chunk_num * CHUNK_SIZE;
164 memcpy(chunk, p, CHUNK_SIZE);
165 wl1271_debug(DEBUG_BOOT, "uploading fw chunk 0x%p to 0x%x",
166 p, addr);
167 wl1271_spi_write(wl, addr, chunk, CHUNK_SIZE, false);
169 chunk_num++;
172 /* 10.4 upload the last chunk */
173 addr = dest + chunk_num * CHUNK_SIZE;
174 p = buf + chunk_num * CHUNK_SIZE;
175 memcpy(chunk, p, fw_data_len % CHUNK_SIZE);
176 wl1271_debug(DEBUG_BOOT, "uploading fw last chunk (%zd B) 0x%p to 0x%x",
177 fw_data_len % CHUNK_SIZE, p, addr);
178 wl1271_spi_write(wl, addr, chunk, fw_data_len % CHUNK_SIZE, false);
180 kfree(chunk);
181 return 0;
184 static int wl1271_boot_upload_firmware(struct wl1271 *wl)
186 u32 chunks, addr, len;
187 int ret = 0;
188 u8 *fw;
190 fw = wl->fw;
191 chunks = be32_to_cpup((__be32 *) fw);
192 fw += sizeof(u32);
194 wl1271_debug(DEBUG_BOOT, "firmware chunks to be uploaded: %u", chunks);
196 while (chunks--) {
197 addr = be32_to_cpup((__be32 *) fw);
198 fw += sizeof(u32);
199 len = be32_to_cpup((__be32 *) fw);
200 fw += sizeof(u32);
202 if (len > 300000) {
203 wl1271_info("firmware chunk too long: %u", len);
204 return -EINVAL;
206 wl1271_debug(DEBUG_BOOT, "chunk %d addr 0x%x len %u",
207 chunks, addr, len);
208 ret = wl1271_boot_upload_firmware_chunk(wl, fw, len, addr);
209 if (ret != 0)
210 break;
211 fw += len;
214 return ret;
217 static int wl1271_boot_upload_nvs(struct wl1271 *wl)
219 size_t nvs_len, burst_len;
220 int i;
221 u32 dest_addr, val;
222 u8 *nvs_ptr, *nvs_aligned;
224 if (wl->nvs == NULL)
225 return -ENODEV;
227 /* only the first part of the NVS needs to be uploaded */
228 nvs_len = sizeof(wl->nvs->nvs);
229 nvs_ptr = (u8 *)wl->nvs->nvs;
232 * Layout before the actual NVS tables:
233 * 1 byte : burst length.
234 * 2 bytes: destination address.
235 * n bytes: data to burst copy.
237 * This is ended by a 0 length, then the NVS tables.
240 /* FIXME: Do we need to check here whether the LSB is 1? */
241 while (nvs_ptr[0]) {
242 burst_len = nvs_ptr[0];
243 dest_addr = (nvs_ptr[1] & 0xfe) | ((u32)(nvs_ptr[2] << 8));
245 /* FIXME: Due to our new wl1271_translate_reg_addr function,
246 we need to add the REGISTER_BASE to the destination */
247 dest_addr += REGISTERS_BASE;
249 /* We move our pointer to the data */
250 nvs_ptr += 3;
252 for (i = 0; i < burst_len; i++) {
253 val = (nvs_ptr[0] | (nvs_ptr[1] << 8)
254 | (nvs_ptr[2] << 16) | (nvs_ptr[3] << 24));
256 wl1271_debug(DEBUG_BOOT,
257 "nvs burst write 0x%x: 0x%x",
258 dest_addr, val);
259 wl1271_spi_write32(wl, dest_addr, val);
261 nvs_ptr += 4;
262 dest_addr += 4;
267 * We've reached the first zero length, the first NVS table
268 * is 7 bytes further.
270 nvs_ptr += 7;
271 nvs_len -= nvs_ptr - (u8 *)wl->nvs->nvs;
272 nvs_len = ALIGN(nvs_len, 4);
274 /* FIXME: The driver sets the partition here, but this is not needed,
275 since it sets to the same one as currently in use */
276 /* Now we must set the partition correctly */
277 wl1271_set_partition(wl, &part_table[PART_WORK]);
279 /* Copy the NVS tables to a new block to ensure alignment */
280 /* FIXME: We jump 3 more bytes before uploading the NVS. It seems
281 that our NVS files have three extra zeros here. I'm not sure whether
282 the problem is in our NVS generation or we should really jumpt these
283 3 bytes here */
284 nvs_ptr += 3;
286 nvs_aligned = kmemdup(nvs_ptr, nvs_len, GFP_KERNEL); if
287 (!nvs_aligned) return -ENOMEM;
289 /* And finally we upload the NVS tables */
290 /* FIXME: In wl1271, we upload everything at once.
291 No endianness handling needed here?! The ref driver doesn't do
292 anything about it at this point */
293 wl1271_spi_write(wl, CMD_MBOX_ADDRESS, nvs_aligned, nvs_len, false);
295 kfree(nvs_aligned);
296 return 0;
299 static void wl1271_boot_enable_interrupts(struct wl1271 *wl)
301 enable_irq(wl->irq);
302 wl1271_spi_write32(wl, ACX_REG_INTERRUPT_MASK,
303 WL1271_ACX_INTR_ALL & ~(WL1271_INTR_MASK));
304 wl1271_spi_write32(wl, HI_CFG, HI_CFG_DEF_VAL);
307 static int wl1271_boot_soft_reset(struct wl1271 *wl)
309 unsigned long timeout;
310 u32 boot_data;
312 /* perform soft reset */
313 wl1271_spi_write32(wl, ACX_REG_SLV_SOFT_RESET,
314 ACX_SLV_SOFT_RESET_BIT);
316 /* SOFT_RESET is self clearing */
317 timeout = jiffies + usecs_to_jiffies(SOFT_RESET_MAX_TIME);
318 while (1) {
319 boot_data = wl1271_spi_read32(wl, ACX_REG_SLV_SOFT_RESET);
320 wl1271_debug(DEBUG_BOOT, "soft reset bootdata 0x%x", boot_data);
321 if ((boot_data & ACX_SLV_SOFT_RESET_BIT) == 0)
322 break;
324 if (time_after(jiffies, timeout)) {
325 /* 1.2 check pWhalBus->uSelfClearTime if the
326 * timeout was reached */
327 wl1271_error("soft reset timeout");
328 return -1;
331 udelay(SOFT_RESET_STALL_TIME);
334 /* disable Rx/Tx */
335 wl1271_spi_write32(wl, ENABLE, 0x0);
337 /* disable auto calibration on start*/
338 wl1271_spi_write32(wl, SPARE_A2, 0xffff);
340 return 0;
343 static int wl1271_boot_run_firmware(struct wl1271 *wl)
345 int loop, ret;
346 u32 chip_id, interrupt;
348 wl1271_boot_set_ecpu_ctrl(wl, ECPU_CONTROL_HALT);
350 chip_id = wl1271_spi_read32(wl, CHIP_ID_B);
352 wl1271_debug(DEBUG_BOOT, "chip id after firmware boot: 0x%x", chip_id);
354 if (chip_id != wl->chip.id) {
355 wl1271_error("chip id doesn't match after firmware boot");
356 return -EIO;
359 /* wait for init to complete */
360 loop = 0;
361 while (loop++ < INIT_LOOP) {
362 udelay(INIT_LOOP_DELAY);
363 interrupt = wl1271_spi_read32(wl,
364 ACX_REG_INTERRUPT_NO_CLEAR);
366 if (interrupt == 0xffffffff) {
367 wl1271_error("error reading hardware complete "
368 "init indication");
369 return -EIO;
371 /* check that ACX_INTR_INIT_COMPLETE is enabled */
372 else if (interrupt & WL1271_ACX_INTR_INIT_COMPLETE) {
373 wl1271_spi_write32(wl, ACX_REG_INTERRUPT_ACK,
374 WL1271_ACX_INTR_INIT_COMPLETE);
375 break;
379 if (loop > INIT_LOOP) {
380 wl1271_error("timeout waiting for the hardware to "
381 "complete initialization");
382 return -EIO;
385 /* get hardware config command mail box */
386 wl->cmd_box_addr = wl1271_spi_read32(wl, REG_COMMAND_MAILBOX_PTR);
388 /* get hardware config event mail box */
389 wl->event_box_addr = wl1271_spi_read32(wl, REG_EVENT_MAILBOX_PTR);
391 /* set the working partition to its "running" mode offset */
392 wl1271_set_partition(wl, &part_table[PART_WORK]);
394 wl1271_debug(DEBUG_MAILBOX, "cmd_box_addr 0x%x event_box_addr 0x%x",
395 wl->cmd_box_addr, wl->event_box_addr);
397 wl1271_boot_fw_version(wl);
400 * in case of full asynchronous mode the firmware event must be
401 * ready to receive event from the command mailbox
404 /* unmask required mbox events */
405 wl->event_mask = BSS_LOSE_EVENT_ID |
406 SCAN_COMPLETE_EVENT_ID |
407 PS_REPORT_EVENT_ID;
409 ret = wl1271_event_unmask(wl);
410 if (ret < 0) {
411 wl1271_error("EVENT mask setting failed");
412 return ret;
415 wl1271_event_mbox_config(wl);
417 /* firmware startup completed */
418 return 0;
421 static int wl1271_boot_write_irq_polarity(struct wl1271 *wl)
423 u32 polarity;
425 polarity = wl1271_top_reg_read(wl, OCP_REG_POLARITY);
427 /* We use HIGH polarity, so unset the LOW bit */
428 polarity &= ~POLARITY_LOW;
429 wl1271_top_reg_write(wl, OCP_REG_POLARITY, polarity);
431 return 0;
434 int wl1271_boot(struct wl1271 *wl)
436 int ret = 0;
437 u32 tmp, clk, pause;
439 if (REF_CLOCK == 0 || REF_CLOCK == 2 || REF_CLOCK == 4)
440 /* ref clk: 19.2/38.4/38.4-XTAL */
441 clk = 0x3;
442 else if (REF_CLOCK == 1 || REF_CLOCK == 3)
443 /* ref clk: 26/52 */
444 clk = 0x5;
446 if (REF_CLOCK != 0) {
447 u16 val;
448 /* Set clock type */
449 val = wl1271_top_reg_read(wl, OCP_REG_CLK_TYPE);
450 val &= FREF_CLK_TYPE_BITS;
451 val |= CLK_REQ_PRCM;
452 wl1271_top_reg_write(wl, OCP_REG_CLK_TYPE, val);
453 } else {
454 u16 val;
455 /* Set clock polarity */
456 val = wl1271_top_reg_read(wl, OCP_REG_CLK_POLARITY);
457 val &= FREF_CLK_POLARITY_BITS;
458 val |= CLK_REQ_OUTN_SEL;
459 wl1271_top_reg_write(wl, OCP_REG_CLK_POLARITY, val);
462 wl1271_spi_write32(wl, PLL_PARAMETERS, clk);
464 pause = wl1271_spi_read32(wl, PLL_PARAMETERS);
466 wl1271_debug(DEBUG_BOOT, "pause1 0x%x", pause);
468 pause &= ~(WU_COUNTER_PAUSE_VAL); /* FIXME: This should probably be
469 * WU_COUNTER_PAUSE_VAL instead of
470 * 0x3ff (magic number ). How does
471 * this work?! */
472 pause |= WU_COUNTER_PAUSE_VAL;
473 wl1271_spi_write32(wl, WU_COUNTER_PAUSE, pause);
475 /* Continue the ELP wake up sequence */
476 wl1271_spi_write32(wl, WELP_ARM_COMMAND, WELP_ARM_COMMAND_VAL);
477 udelay(500);
479 wl1271_set_partition(wl, &part_table[PART_DRPW]);
481 /* Read-modify-write DRPW_SCRATCH_START register (see next state)
482 to be used by DRPw FW. The RTRIM value will be added by the FW
483 before taking DRPw out of reset */
485 wl1271_debug(DEBUG_BOOT, "DRPW_SCRATCH_START %08x", DRPW_SCRATCH_START);
486 clk = wl1271_spi_read32(wl, DRPW_SCRATCH_START);
488 wl1271_debug(DEBUG_BOOT, "clk2 0x%x", clk);
490 /* 2 */
491 clk |= (REF_CLOCK << 1) << 4;
492 wl1271_spi_write32(wl, DRPW_SCRATCH_START, clk);
494 wl1271_set_partition(wl, &part_table[PART_WORK]);
496 /* Disable interrupts */
497 wl1271_spi_write32(wl, ACX_REG_INTERRUPT_MASK, WL1271_ACX_INTR_ALL);
499 ret = wl1271_boot_soft_reset(wl);
500 if (ret < 0)
501 goto out;
503 /* 2. start processing NVS file */
504 ret = wl1271_boot_upload_nvs(wl);
505 if (ret < 0)
506 goto out;
508 /* write firmware's last address (ie. it's length) to
509 * ACX_EEPROMLESS_IND_REG */
510 wl1271_debug(DEBUG_BOOT, "ACX_EEPROMLESS_IND_REG");
512 wl1271_spi_write32(wl, ACX_EEPROMLESS_IND_REG,
513 ACX_EEPROMLESS_IND_REG);
515 tmp = wl1271_spi_read32(wl, CHIP_ID_B);
517 wl1271_debug(DEBUG_BOOT, "chip id 0x%x", tmp);
519 /* 6. read the EEPROM parameters */
520 tmp = wl1271_spi_read32(wl, SCR_PAD2);
522 ret = wl1271_boot_write_irq_polarity(wl);
523 if (ret < 0)
524 goto out;
526 /* FIXME: Need to check whether this is really what we want */
527 wl1271_spi_write32(wl, ACX_REG_INTERRUPT_MASK,
528 WL1271_ACX_ALL_EVENTS_VECTOR);
530 /* WL1271: The reference driver skips steps 7 to 10 (jumps directly
531 * to upload_fw) */
533 ret = wl1271_boot_upload_firmware(wl);
534 if (ret < 0)
535 goto out;
537 /* 10.5 start firmware */
538 ret = wl1271_boot_run_firmware(wl);
539 if (ret < 0)
540 goto out;
542 /* Enable firmware interrupts now */
543 wl1271_boot_enable_interrupts(wl);
545 /* set the wl1271 default filters */
546 wl->rx_config = WL1271_DEFAULT_RX_CONFIG;
547 wl->rx_filter = WL1271_DEFAULT_RX_FILTER;
549 wl1271_event_mbox_config(wl);
551 out:
552 return ret;