diff options
author | Luciano Coelho <coelho@ti.com> | 2011-11-21 13:37:14 -0500 |
---|---|---|
committer | Luciano Coelho <coelho@ti.com> | 2012-04-12 01:43:56 -0400 |
commit | 25a43d78eb63281294793fdaab6108bef81d7648 (patch) | |
tree | 72504d547dde54d573fcbe314d50ea203d6f032d /drivers/net/wireless/ti | |
parent | c31be25a7144ebc9b7a22128909bac7654d4c46b (diff) |
wlcore/wl12xx: implement chip-specific partition tables
Add partition tables to wlcore, move and reorganize partition setting
functions. Move wl12xx partition table to use the wlcore partition
table instead.
Signed-off-by: Luciano Coelho <coelho@ti.com>
Diffstat (limited to 'drivers/net/wireless/ti')
-rw-r--r-- | drivers/net/wireless/ti/wl12xx/main.c | 62 | ||||
-rw-r--r-- | drivers/net/wireless/ti/wlcore/boot.c | 20 | ||||
-rw-r--r-- | drivers/net/wireless/ti/wlcore/debug.h | 1 | ||||
-rw-r--r-- | drivers/net/wireless/ti/wlcore/io.c | 126 | ||||
-rw-r--r-- | drivers/net/wireless/ti/wlcore/io.h | 43 | ||||
-rw-r--r-- | drivers/net/wireless/ti/wlcore/main.c | 8 | ||||
-rw-r--r-- | drivers/net/wireless/ti/wlcore/wl12xx.h | 20 | ||||
-rw-r--r-- | drivers/net/wireless/ti/wlcore/wlcore.h | 27 |
8 files changed, 168 insertions, 139 deletions
diff --git a/drivers/net/wireless/ti/wl12xx/main.c b/drivers/net/wireless/ti/wl12xx/main.c index 0d30150a3de2..0d3ed7d7893d 100644 --- a/drivers/net/wireless/ti/wl12xx/main.c +++ b/drivers/net/wireless/ti/wl12xx/main.c | |||
@@ -27,9 +27,70 @@ | |||
27 | #include "../wlcore/wlcore.h" | 27 | #include "../wlcore/wlcore.h" |
28 | #include "../wlcore/debug.h" | 28 | #include "../wlcore/debug.h" |
29 | 29 | ||
30 | #include "../wlcore/reg.h" | ||
31 | |||
30 | static struct wlcore_ops wl12xx_ops = { | 32 | static struct wlcore_ops wl12xx_ops = { |
31 | }; | 33 | }; |
32 | 34 | ||
35 | static struct wlcore_partition_set wl12xx_ptable[PART_TABLE_LEN] = { | ||
36 | [PART_DOWN] = { | ||
37 | .mem = { | ||
38 | .start = 0x00000000, | ||
39 | .size = 0x000177c0 | ||
40 | }, | ||
41 | .reg = { | ||
42 | .start = REGISTERS_BASE, | ||
43 | .size = 0x00008800 | ||
44 | }, | ||
45 | .mem2 = { | ||
46 | .start = 0x00000000, | ||
47 | .size = 0x00000000 | ||
48 | }, | ||
49 | .mem3 = { | ||
50 | .start = 0x00000000, | ||
51 | .size = 0x00000000 | ||
52 | }, | ||
53 | }, | ||
54 | |||
55 | [PART_WORK] = { | ||
56 | .mem = { | ||
57 | .start = 0x00040000, | ||
58 | .size = 0x00014fc0 | ||
59 | }, | ||
60 | .reg = { | ||
61 | .start = REGISTERS_BASE, | ||
62 | .size = 0x0000a000 | ||
63 | }, | ||
64 | .mem2 = { | ||
65 | .start = 0x003004f8, | ||
66 | .size = 0x00000004 | ||
67 | }, | ||
68 | .mem3 = { | ||
69 | .start = 0x00040404, | ||
70 | .size = 0x00000000 | ||
71 | }, | ||
72 | }, | ||
73 | |||
74 | [PART_DRPW] = { | ||
75 | .mem = { | ||
76 | .start = 0x00040000, | ||
77 | .size = 0x00014fc0 | ||
78 | }, | ||
79 | .reg = { | ||
80 | .start = DRPW_BASE, | ||
81 | .size = 0x00006000 | ||
82 | }, | ||
83 | .mem2 = { | ||
84 | .start = 0x00000000, | ||
85 | .size = 0x00000000 | ||
86 | }, | ||
87 | .mem3 = { | ||
88 | .start = 0x00000000, | ||
89 | .size = 0x00000000 | ||
90 | } | ||
91 | } | ||
92 | }; | ||
93 | |||
33 | static int __devinit wl12xx_probe(struct platform_device *pdev) | 94 | static int __devinit wl12xx_probe(struct platform_device *pdev) |
34 | { | 95 | { |
35 | struct wl1271 *wl; | 96 | struct wl1271 *wl; |
@@ -43,6 +104,7 @@ static int __devinit wl12xx_probe(struct platform_device *pdev) | |||
43 | 104 | ||
44 | wl = hw->priv; | 105 | wl = hw->priv; |
45 | wl->ops = &wl12xx_ops; | 106 | wl->ops = &wl12xx_ops; |
107 | wl->ptable = wl12xx_ptable; | ||
46 | 108 | ||
47 | return wlcore_probe(wl, pdev); | 109 | return wlcore_probe(wl, pdev); |
48 | } | 110 | } |
diff --git a/drivers/net/wireless/ti/wlcore/boot.c b/drivers/net/wireless/ti/wlcore/boot.c index 88d60c40b7e3..da37c59552b3 100644 --- a/drivers/net/wireless/ti/wlcore/boot.c +++ b/drivers/net/wireless/ti/wlcore/boot.c | |||
@@ -108,7 +108,7 @@ static void wl1271_boot_fw_version(struct wl1271 *wl) | |||
108 | static int wl1271_boot_upload_firmware_chunk(struct wl1271 *wl, void *buf, | 108 | static int wl1271_boot_upload_firmware_chunk(struct wl1271 *wl, void *buf, |
109 | size_t fw_data_len, u32 dest) | 109 | size_t fw_data_len, u32 dest) |
110 | { | 110 | { |
111 | struct wl1271_partition_set partition; | 111 | struct wlcore_partition_set partition; |
112 | int addr, chunk_num, partition_limit; | 112 | int addr, chunk_num, partition_limit; |
113 | u8 *p, *chunk; | 113 | u8 *p, *chunk; |
114 | 114 | ||
@@ -130,13 +130,13 @@ static int wl1271_boot_upload_firmware_chunk(struct wl1271 *wl, void *buf, | |||
130 | return -ENOMEM; | 130 | return -ENOMEM; |
131 | } | 131 | } |
132 | 132 | ||
133 | memcpy(&partition, &wl12xx_part_table[PART_DOWN], sizeof(partition)); | 133 | memcpy(&partition, &wl->ptable[PART_DOWN], sizeof(partition)); |
134 | partition.mem.start = dest; | 134 | partition.mem.start = dest; |
135 | wl1271_set_partition(wl, &partition); | 135 | wlcore_set_partition(wl, &partition); |
136 | 136 | ||
137 | /* 10.1 set partition limit and chunk num */ | 137 | /* 10.1 set partition limit and chunk num */ |
138 | chunk_num = 0; | 138 | chunk_num = 0; |
139 | partition_limit = wl12xx_part_table[PART_DOWN].mem.size; | 139 | partition_limit = wl->ptable[PART_DOWN].mem.size; |
140 | 140 | ||
141 | while (chunk_num < fw_data_len / CHUNK_SIZE) { | 141 | while (chunk_num < fw_data_len / CHUNK_SIZE) { |
142 | /* 10.2 update partition, if needed */ | 142 | /* 10.2 update partition, if needed */ |
@@ -144,9 +144,9 @@ static int wl1271_boot_upload_firmware_chunk(struct wl1271 *wl, void *buf, | |||
144 | if (addr > partition_limit) { | 144 | if (addr > partition_limit) { |
145 | addr = dest + chunk_num * CHUNK_SIZE; | 145 | addr = dest + chunk_num * CHUNK_SIZE; |
146 | partition_limit = chunk_num * CHUNK_SIZE + | 146 | partition_limit = chunk_num * CHUNK_SIZE + |
147 | wl12xx_part_table[PART_DOWN].mem.size; | 147 | wl->ptable[PART_DOWN].mem.size; |
148 | partition.mem.start = addr; | 148 | partition.mem.start = addr; |
149 | wl1271_set_partition(wl, &partition); | 149 | wlcore_set_partition(wl, &partition); |
150 | } | 150 | } |
151 | 151 | ||
152 | /* 10.3 upload the chunk */ | 152 | /* 10.3 upload the chunk */ |
@@ -332,7 +332,7 @@ static int wl1271_boot_upload_nvs(struct wl1271 *wl) | |||
332 | nvs_len -= nvs_ptr - (u8 *)wl->nvs; | 332 | nvs_len -= nvs_ptr - (u8 *)wl->nvs; |
333 | 333 | ||
334 | /* Now we must set the partition correctly */ | 334 | /* Now we must set the partition correctly */ |
335 | wl1271_set_partition(wl, &wl12xx_part_table[PART_WORK]); | 335 | wlcore_set_partition(wl, &wl->ptable[PART_WORK]); |
336 | 336 | ||
337 | /* Copy the NVS tables to a new block to ensure alignment */ | 337 | /* Copy the NVS tables to a new block to ensure alignment */ |
338 | nvs_aligned = kmemdup(nvs_ptr, nvs_len, GFP_KERNEL); | 338 | nvs_aligned = kmemdup(nvs_ptr, nvs_len, GFP_KERNEL); |
@@ -441,7 +441,7 @@ static int wl1271_boot_run_firmware(struct wl1271 *wl) | |||
441 | wl->event_box_addr = wl1271_read32(wl, REG_EVENT_MAILBOX_PTR); | 441 | wl->event_box_addr = wl1271_read32(wl, REG_EVENT_MAILBOX_PTR); |
442 | 442 | ||
443 | /* set the working partition to its "running" mode offset */ | 443 | /* set the working partition to its "running" mode offset */ |
444 | wl1271_set_partition(wl, &wl12xx_part_table[PART_WORK]); | 444 | wlcore_set_partition(wl, &wl->ptable[PART_WORK]); |
445 | 445 | ||
446 | wl1271_debug(DEBUG_MAILBOX, "cmd_box_addr 0x%x event_box_addr 0x%x", | 446 | wl1271_debug(DEBUG_MAILBOX, "cmd_box_addr 0x%x event_box_addr 0x%x", |
447 | wl->cmd_box_addr, wl->event_box_addr); | 447 | wl->cmd_box_addr, wl->event_box_addr); |
@@ -702,7 +702,7 @@ int wl1271_load_firmware(struct wl1271 *wl) | |||
702 | wl1271_write32(wl, WELP_ARM_COMMAND, WELP_ARM_COMMAND_VAL); | 702 | wl1271_write32(wl, WELP_ARM_COMMAND, WELP_ARM_COMMAND_VAL); |
703 | udelay(500); | 703 | udelay(500); |
704 | 704 | ||
705 | wl1271_set_partition(wl, &wl12xx_part_table[PART_DRPW]); | 705 | wlcore_set_partition(wl, &wl->ptable[PART_DRPW]); |
706 | 706 | ||
707 | /* Read-modify-write DRPW_SCRATCH_START register (see next state) | 707 | /* Read-modify-write DRPW_SCRATCH_START register (see next state) |
708 | to be used by DRPw FW. The RTRIM value will be added by the FW | 708 | to be used by DRPw FW. The RTRIM value will be added by the FW |
@@ -721,7 +721,7 @@ int wl1271_load_firmware(struct wl1271 *wl) | |||
721 | 721 | ||
722 | wl1271_write32(wl, DRPW_SCRATCH_START, clk); | 722 | wl1271_write32(wl, DRPW_SCRATCH_START, clk); |
723 | 723 | ||
724 | wl1271_set_partition(wl, &wl12xx_part_table[PART_WORK]); | 724 | wlcore_set_partition(wl, &wl->ptable[PART_WORK]); |
725 | 725 | ||
726 | /* Disable interrupts */ | 726 | /* Disable interrupts */ |
727 | wl1271_write32(wl, ACX_REG_INTERRUPT_MASK, WL1271_ACX_INTR_ALL); | 727 | wl1271_write32(wl, ACX_REG_INTERRUPT_MASK, WL1271_ACX_INTR_ALL); |
diff --git a/drivers/net/wireless/ti/wlcore/debug.h b/drivers/net/wireless/ti/wlcore/debug.h index ec0fdc25b280..6b800b3cbea5 100644 --- a/drivers/net/wireless/ti/wlcore/debug.h +++ b/drivers/net/wireless/ti/wlcore/debug.h | |||
@@ -52,6 +52,7 @@ enum { | |||
52 | DEBUG_ADHOC = BIT(16), | 52 | DEBUG_ADHOC = BIT(16), |
53 | DEBUG_AP = BIT(17), | 53 | DEBUG_AP = BIT(17), |
54 | DEBUG_PROBE = BIT(18), | 54 | DEBUG_PROBE = BIT(18), |
55 | DEBUG_IO = BIT(19), | ||
55 | DEBUG_MASTER = (DEBUG_ADHOC | DEBUG_AP), | 56 | DEBUG_MASTER = (DEBUG_ADHOC | DEBUG_AP), |
56 | DEBUG_ALL = ~0, | 57 | DEBUG_ALL = ~0, |
57 | }; | 58 | }; |
diff --git a/drivers/net/wireless/ti/wlcore/io.c b/drivers/net/wireless/ti/wlcore/io.c index b0701fb9dbdc..65c562c40f8e 100644 --- a/drivers/net/wireless/ti/wlcore/io.c +++ b/drivers/net/wireless/ti/wlcore/io.c | |||
@@ -45,65 +45,6 @@ | |||
45 | #define OCP_STATUS_REQ_FAILED 0x20000 | 45 | #define OCP_STATUS_REQ_FAILED 0x20000 |
46 | #define OCP_STATUS_RESP_ERROR 0x30000 | 46 | #define OCP_STATUS_RESP_ERROR 0x30000 |
47 | 47 | ||
48 | struct wl1271_partition_set wl12xx_part_table[PART_TABLE_LEN] = { | ||
49 | [PART_DOWN] = { | ||
50 | .mem = { | ||
51 | .start = 0x00000000, | ||
52 | .size = 0x000177c0 | ||
53 | }, | ||
54 | .reg = { | ||
55 | .start = REGISTERS_BASE, | ||
56 | .size = 0x00008800 | ||
57 | }, | ||
58 | .mem2 = { | ||
59 | .start = 0x00000000, | ||
60 | .size = 0x00000000 | ||
61 | }, | ||
62 | .mem3 = { | ||
63 | .start = 0x00000000, | ||
64 | .size = 0x00000000 | ||
65 | }, | ||
66 | }, | ||
67 | |||
68 | [PART_WORK] = { | ||
69 | .mem = { | ||
70 | .start = 0x00040000, | ||
71 | .size = 0x00014fc0 | ||
72 | }, | ||
73 | .reg = { | ||
74 | .start = REGISTERS_BASE, | ||
75 | .size = 0x0000a000 | ||
76 | }, | ||
77 | .mem2 = { | ||
78 | .start = 0x003004f8, | ||
79 | .size = 0x00000004 | ||
80 | }, | ||
81 | .mem3 = { | ||
82 | .start = 0x00040404, | ||
83 | .size = 0x00000000 | ||
84 | }, | ||
85 | }, | ||
86 | |||
87 | [PART_DRPW] = { | ||
88 | .mem = { | ||
89 | .start = 0x00040000, | ||
90 | .size = 0x00014fc0 | ||
91 | }, | ||
92 | .reg = { | ||
93 | .start = DRPW_BASE, | ||
94 | .size = 0x00006000 | ||
95 | }, | ||
96 | .mem2 = { | ||
97 | .start = 0x00000000, | ||
98 | .size = 0x00000000 | ||
99 | }, | ||
100 | .mem3 = { | ||
101 | .start = 0x00000000, | ||
102 | .size = 0x00000000 | ||
103 | } | ||
104 | } | ||
105 | }; | ||
106 | |||
107 | bool wl1271_set_block_size(struct wl1271 *wl) | 48 | bool wl1271_set_block_size(struct wl1271 *wl) |
108 | { | 49 | { |
109 | if (wl->if_ops->set_block_size) { | 50 | if (wl->if_ops->set_block_size) { |
@@ -124,7 +65,41 @@ void wl1271_enable_interrupts(struct wl1271 *wl) | |||
124 | enable_irq(wl->irq); | 65 | enable_irq(wl->irq); |
125 | } | 66 | } |
126 | 67 | ||
127 | /* Set the SPI partitions to access the chip addresses | 68 | int wlcore_translate_addr(struct wl1271 *wl, int addr) |
69 | { | ||
70 | struct wlcore_partition_set *part = &wl->curr_part; | ||
71 | |||
72 | /* | ||
73 | * To translate, first check to which window of addresses the | ||
74 | * particular address belongs. Then subtract the starting address | ||
75 | * of that window from the address. Then, add offset of the | ||
76 | * translated region. | ||
77 | * | ||
78 | * The translated regions occur next to each other in physical device | ||
79 | * memory, so just add the sizes of the preceding address regions to | ||
80 | * get the offset to the new region. | ||
81 | */ | ||
82 | if ((addr >= part->mem.start) && | ||
83 | (addr < part->mem.start + part->mem.size)) | ||
84 | return addr - part->mem.start; | ||
85 | else if ((addr >= part->reg.start) && | ||
86 | (addr < part->reg.start + part->reg.size)) | ||
87 | return addr - part->reg.start + part->mem.size; | ||
88 | else if ((addr >= part->mem2.start) && | ||
89 | (addr < part->mem2.start + part->mem2.size)) | ||
90 | return addr - part->mem2.start + part->mem.size + | ||
91 | part->reg.size; | ||
92 | else if ((addr >= part->mem3.start) && | ||
93 | (addr < part->mem3.start + part->mem3.size)) | ||
94 | return addr - part->mem3.start + part->mem.size + | ||
95 | part->reg.size + part->mem2.size; | ||
96 | |||
97 | WARN(1, "HW address 0x%x out of range", addr); | ||
98 | return 0; | ||
99 | } | ||
100 | EXPORT_SYMBOL_GPL(wlcore_translate_addr); | ||
101 | |||
102 | /* Set the partitions to access the chip addresses | ||
128 | * | 103 | * |
129 | * To simplify driver code, a fixed (virtual) memory map is defined for | 104 | * To simplify driver code, a fixed (virtual) memory map is defined for |
130 | * register and memory addresses. Because in the chipset, in different stages | 105 | * register and memory addresses. Because in the chipset, in different stages |
@@ -158,33 +133,43 @@ void wl1271_enable_interrupts(struct wl1271 *wl) | |||
158 | * | | | 133 | * | | |
159 | * | 134 | * |
160 | */ | 135 | */ |
161 | int wl1271_set_partition(struct wl1271 *wl, | 136 | void wlcore_set_partition(struct wl1271 *wl, |
162 | struct wl1271_partition_set *p) | 137 | const struct wlcore_partition_set *p) |
163 | { | 138 | { |
164 | /* copy partition info */ | 139 | /* copy partition info */ |
165 | memcpy(&wl->part, p, sizeof(*p)); | 140 | memcpy(&wl->curr_part, p, sizeof(*p)); |
166 | 141 | ||
167 | wl1271_debug(DEBUG_SPI, "mem_start %08X mem_size %08X", | 142 | wl1271_debug(DEBUG_IO, "mem_start %08X mem_size %08X", |
168 | p->mem.start, p->mem.size); | 143 | p->mem.start, p->mem.size); |
169 | wl1271_debug(DEBUG_SPI, "reg_start %08X reg_size %08X", | 144 | wl1271_debug(DEBUG_IO, "reg_start %08X reg_size %08X", |
170 | p->reg.start, p->reg.size); | 145 | p->reg.start, p->reg.size); |
171 | wl1271_debug(DEBUG_SPI, "mem2_start %08X mem2_size %08X", | 146 | wl1271_debug(DEBUG_IO, "mem2_start %08X mem2_size %08X", |
172 | p->mem2.start, p->mem2.size); | 147 | p->mem2.start, p->mem2.size); |
173 | wl1271_debug(DEBUG_SPI, "mem3_start %08X mem3_size %08X", | 148 | wl1271_debug(DEBUG_IO, "mem3_start %08X mem3_size %08X", |
174 | p->mem3.start, p->mem3.size); | 149 | p->mem3.start, p->mem3.size); |
175 | 150 | ||
176 | /* write partition info to the chipset */ | ||
177 | wl1271_raw_write32(wl, HW_PART0_START_ADDR, p->mem.start); | 151 | wl1271_raw_write32(wl, HW_PART0_START_ADDR, p->mem.start); |
178 | wl1271_raw_write32(wl, HW_PART0_SIZE_ADDR, p->mem.size); | 152 | wl1271_raw_write32(wl, HW_PART0_SIZE_ADDR, p->mem.size); |
179 | wl1271_raw_write32(wl, HW_PART1_START_ADDR, p->reg.start); | 153 | wl1271_raw_write32(wl, HW_PART1_START_ADDR, p->reg.start); |
180 | wl1271_raw_write32(wl, HW_PART1_SIZE_ADDR, p->reg.size); | 154 | wl1271_raw_write32(wl, HW_PART1_SIZE_ADDR, p->reg.size); |
181 | wl1271_raw_write32(wl, HW_PART2_START_ADDR, p->mem2.start); | 155 | wl1271_raw_write32(wl, HW_PART2_START_ADDR, p->mem2.start); |
182 | wl1271_raw_write32(wl, HW_PART2_SIZE_ADDR, p->mem2.size); | 156 | wl1271_raw_write32(wl, HW_PART2_SIZE_ADDR, p->mem2.size); |
157 | /* | ||
158 | * We don't need the size of the last partition, as it is | ||
159 | * automatically calculated based on the total memory size and | ||
160 | * the sizes of the previous partitions. | ||
161 | */ | ||
183 | wl1271_raw_write32(wl, HW_PART3_START_ADDR, p->mem3.start); | 162 | wl1271_raw_write32(wl, HW_PART3_START_ADDR, p->mem3.start); |
163 | } | ||
164 | EXPORT_SYMBOL_GPL(wlcore_set_partition); | ||
184 | 165 | ||
185 | return 0; | 166 | void wlcore_select_partition(struct wl1271 *wl, u8 part) |
167 | { | ||
168 | wl1271_debug(DEBUG_IO, "setting partition %d", part); | ||
169 | |||
170 | wlcore_set_partition(wl, &wl->ptable[part]); | ||
186 | } | 171 | } |
187 | EXPORT_SYMBOL_GPL(wl1271_set_partition); | 172 | EXPORT_SYMBOL_GPL(wlcore_select_partition); |
188 | 173 | ||
189 | void wl1271_io_reset(struct wl1271 *wl) | 174 | void wl1271_io_reset(struct wl1271 *wl) |
190 | { | 175 | { |
@@ -241,4 +226,3 @@ u16 wl1271_top_reg_read(struct wl1271 *wl, int addr) | |||
241 | return 0xffff; | 226 | return 0xffff; |
242 | } | 227 | } |
243 | } | 228 | } |
244 | |||
diff --git a/drivers/net/wireless/ti/wlcore/io.h b/drivers/net/wireless/ti/wlcore/io.h index 4fb3dab8c3b2..495ab335b465 100644 --- a/drivers/net/wireless/ti/wlcore/io.h +++ b/drivers/net/wireless/ti/wlcore/io.h | |||
@@ -43,8 +43,6 @@ | |||
43 | 43 | ||
44 | #define HW_ACCESS_PRAM_MAX_RANGE 0x3c000 | 44 | #define HW_ACCESS_PRAM_MAX_RANGE 0x3c000 |
45 | 45 | ||
46 | extern struct wl1271_partition_set wl12xx_part_table[PART_TABLE_LEN]; | ||
47 | |||
48 | struct wl1271; | 46 | struct wl1271; |
49 | 47 | ||
50 | void wl1271_disable_interrupts(struct wl1271 *wl); | 48 | void wl1271_disable_interrupts(struct wl1271 *wl); |
@@ -52,6 +50,7 @@ void wl1271_enable_interrupts(struct wl1271 *wl); | |||
52 | 50 | ||
53 | void wl1271_io_reset(struct wl1271 *wl); | 51 | void wl1271_io_reset(struct wl1271 *wl); |
54 | void wl1271_io_init(struct wl1271 *wl); | 52 | void wl1271_io_init(struct wl1271 *wl); |
53 | int wlcore_translate_addr(struct wl1271 *wl, int addr); | ||
55 | 54 | ||
56 | /* Raw target IO, address is not translated */ | 55 | /* Raw target IO, address is not translated */ |
57 | static inline void wl1271_raw_write(struct wl1271 *wl, int addr, void *buf, | 56 | static inline void wl1271_raw_write(struct wl1271 *wl, int addr, void *buf, |
@@ -81,36 +80,12 @@ static inline void wl1271_raw_write32(struct wl1271 *wl, int addr, u32 val) | |||
81 | sizeof(wl->buffer_32), false); | 80 | sizeof(wl->buffer_32), false); |
82 | } | 81 | } |
83 | 82 | ||
84 | /* Translated target IO */ | ||
85 | static inline int wl1271_translate_addr(struct wl1271 *wl, int addr) | ||
86 | { | ||
87 | /* | ||
88 | * To translate, first check to which window of addresses the | ||
89 | * particular address belongs. Then subtract the starting address | ||
90 | * of that window from the address. Then, add offset of the | ||
91 | * translated region. | ||
92 | * | ||
93 | * The translated regions occur next to each other in physical device | ||
94 | * memory, so just add the sizes of the preceding address regions to | ||
95 | * get the offset to the new region. | ||
96 | * | ||
97 | * Currently, only the two first regions are addressed, and the | ||
98 | * assumption is that all addresses will fall into either of those | ||
99 | * two. | ||
100 | */ | ||
101 | if ((addr >= wl->part.reg.start) && | ||
102 | (addr < wl->part.reg.start + wl->part.reg.size)) | ||
103 | return addr - wl->part.reg.start + wl->part.mem.size; | ||
104 | else | ||
105 | return addr - wl->part.mem.start; | ||
106 | } | ||
107 | |||
108 | static inline void wl1271_read(struct wl1271 *wl, int addr, void *buf, | 83 | static inline void wl1271_read(struct wl1271 *wl, int addr, void *buf, |
109 | size_t len, bool fixed) | 84 | size_t len, bool fixed) |
110 | { | 85 | { |
111 | int physical; | 86 | int physical; |
112 | 87 | ||
113 | physical = wl1271_translate_addr(wl, addr); | 88 | physical = wlcore_translate_addr(wl, addr); |
114 | 89 | ||
115 | wl1271_raw_read(wl, physical, buf, len, fixed); | 90 | wl1271_raw_read(wl, physical, buf, len, fixed); |
116 | } | 91 | } |
@@ -120,7 +95,7 @@ static inline void wl1271_write(struct wl1271 *wl, int addr, void *buf, | |||
120 | { | 95 | { |
121 | int physical; | 96 | int physical; |
122 | 97 | ||
123 | physical = wl1271_translate_addr(wl, addr); | 98 | physical = wlcore_translate_addr(wl, addr); |
124 | 99 | ||
125 | wl1271_raw_write(wl, physical, buf, len, fixed); | 100 | wl1271_raw_write(wl, physical, buf, len, fixed); |
126 | } | 101 | } |
@@ -134,19 +109,19 @@ static inline void wl1271_read_hwaddr(struct wl1271 *wl, int hwaddr, | |||
134 | /* Addresses are stored internally as addresses to 32 bytes blocks */ | 109 | /* Addresses are stored internally as addresses to 32 bytes blocks */ |
135 | addr = hwaddr << 5; | 110 | addr = hwaddr << 5; |
136 | 111 | ||
137 | physical = wl1271_translate_addr(wl, addr); | 112 | physical = wlcore_translate_addr(wl, addr); |
138 | 113 | ||
139 | wl1271_raw_read(wl, physical, buf, len, fixed); | 114 | wl1271_raw_read(wl, physical, buf, len, fixed); |
140 | } | 115 | } |
141 | 116 | ||
142 | static inline u32 wl1271_read32(struct wl1271 *wl, int addr) | 117 | static inline u32 wl1271_read32(struct wl1271 *wl, int addr) |
143 | { | 118 | { |
144 | return wl1271_raw_read32(wl, wl1271_translate_addr(wl, addr)); | 119 | return wl1271_raw_read32(wl, wlcore_translate_addr(wl, addr)); |
145 | } | 120 | } |
146 | 121 | ||
147 | static inline void wl1271_write32(struct wl1271 *wl, int addr, u32 val) | 122 | static inline void wl1271_write32(struct wl1271 *wl, int addr, u32 val) |
148 | { | 123 | { |
149 | wl1271_raw_write32(wl, wl1271_translate_addr(wl, addr), val); | 124 | wl1271_raw_write32(wl, wlcore_translate_addr(wl, addr), val); |
150 | } | 125 | } |
151 | 126 | ||
152 | static inline void wl1271_power_off(struct wl1271 *wl) | 127 | static inline void wl1271_power_off(struct wl1271 *wl) |
@@ -169,8 +144,8 @@ static inline int wl1271_power_on(struct wl1271 *wl) | |||
169 | void wl1271_top_reg_write(struct wl1271 *wl, int addr, u16 val); | 144 | void wl1271_top_reg_write(struct wl1271 *wl, int addr, u16 val); |
170 | u16 wl1271_top_reg_read(struct wl1271 *wl, int addr); | 145 | u16 wl1271_top_reg_read(struct wl1271 *wl, int addr); |
171 | 146 | ||
172 | int wl1271_set_partition(struct wl1271 *wl, | 147 | void wlcore_set_partition(struct wl1271 *wl, |
173 | struct wl1271_partition_set *p); | 148 | const struct wlcore_partition_set *p); |
174 | 149 | ||
175 | bool wl1271_set_block_size(struct wl1271 *wl); | 150 | bool wl1271_set_block_size(struct wl1271 *wl); |
176 | 151 | ||
@@ -178,4 +153,6 @@ bool wl1271_set_block_size(struct wl1271 *wl); | |||
178 | 153 | ||
179 | int wl1271_tx_dummy_packet(struct wl1271 *wl); | 154 | int wl1271_tx_dummy_packet(struct wl1271 *wl); |
180 | 155 | ||
156 | void wlcore_select_partition(struct wl1271 *wl, u8 part); | ||
157 | |||
181 | #endif | 158 | #endif |
diff --git a/drivers/net/wireless/ti/wlcore/main.c b/drivers/net/wireless/ti/wlcore/main.c index 194a8b00de1e..30d47b239ab5 100644 --- a/drivers/net/wireless/ti/wlcore/main.c +++ b/drivers/net/wireless/ti/wlcore/main.c | |||
@@ -1330,7 +1330,7 @@ static int wl12xx_set_power_on(struct wl1271 *wl) | |||
1330 | wl1271_io_reset(wl); | 1330 | wl1271_io_reset(wl); |
1331 | wl1271_io_init(wl); | 1331 | wl1271_io_init(wl); |
1332 | 1332 | ||
1333 | wl1271_set_partition(wl, &wl12xx_part_table[PART_DOWN]); | 1333 | wlcore_set_partition(wl, &wl->ptable[PART_DOWN]); |
1334 | 1334 | ||
1335 | /* ELP module wake up */ | 1335 | /* ELP module wake up */ |
1336 | wl1271_fw_wakeup(wl); | 1336 | wl1271_fw_wakeup(wl); |
@@ -5085,7 +5085,7 @@ static void wl12xx_get_fuse_mac(struct wl1271 *wl) | |||
5085 | { | 5085 | { |
5086 | u32 mac1, mac2; | 5086 | u32 mac1, mac2; |
5087 | 5087 | ||
5088 | wl1271_set_partition(wl, &wl12xx_part_table[PART_DRPW]); | 5088 | wlcore_set_partition(wl, &wl->ptable[PART_DRPW]); |
5089 | 5089 | ||
5090 | mac1 = wl1271_read32(wl, WL12XX_REG_FUSE_BD_ADDR_1); | 5090 | mac1 = wl1271_read32(wl, WL12XX_REG_FUSE_BD_ADDR_1); |
5091 | mac2 = wl1271_read32(wl, WL12XX_REG_FUSE_BD_ADDR_2); | 5091 | mac2 = wl1271_read32(wl, WL12XX_REG_FUSE_BD_ADDR_2); |
@@ -5095,7 +5095,7 @@ static void wl12xx_get_fuse_mac(struct wl1271 *wl) | |||
5095 | ((mac1 & 0xff000000) >> 24); | 5095 | ((mac1 & 0xff000000) >> 24); |
5096 | wl->fuse_nic_addr = mac1 & 0xffffff; | 5096 | wl->fuse_nic_addr = mac1 & 0xffffff; |
5097 | 5097 | ||
5098 | wl1271_set_partition(wl, &wl12xx_part_table[PART_DOWN]); | 5098 | wlcore_set_partition(wl, &wl->ptable[PART_DOWN]); |
5099 | } | 5099 | } |
5100 | 5100 | ||
5101 | static int wl12xx_get_hw_info(struct wl1271 *wl) | 5101 | static int wl12xx_get_hw_info(struct wl1271 *wl) |
@@ -5485,7 +5485,7 @@ int __devinit wlcore_probe(struct wl1271 *wl, struct platform_device *pdev) | |||
5485 | unsigned long irqflags; | 5485 | unsigned long irqflags; |
5486 | int ret; | 5486 | int ret; |
5487 | 5487 | ||
5488 | if (!wl->ops) { | 5488 | if (!wl->ops || !wl->ptable) { |
5489 | ret = -EINVAL; | 5489 | ret = -EINVAL; |
5490 | goto out_free_hw; | 5490 | goto out_free_hw; |
5491 | } | 5491 | } |
diff --git a/drivers/net/wireless/ti/wlcore/wl12xx.h b/drivers/net/wireless/ti/wlcore/wl12xx.h index 37b2d64b5b5b..c979920d964d 100644 --- a/drivers/net/wireless/ti/wlcore/wl12xx.h +++ b/drivers/net/wireless/ti/wlcore/wl12xx.h | |||
@@ -105,26 +105,6 @@ enum wl12xx_fw_type { | |||
105 | WL12XX_FW_TYPE_PLT, | 105 | WL12XX_FW_TYPE_PLT, |
106 | }; | 106 | }; |
107 | 107 | ||
108 | enum wl1271_partition_type { | ||
109 | PART_DOWN, | ||
110 | PART_WORK, | ||
111 | PART_DRPW, | ||
112 | |||
113 | PART_TABLE_LEN | ||
114 | }; | ||
115 | |||
116 | struct wl1271_partition { | ||
117 | u32 size; | ||
118 | u32 start; | ||
119 | }; | ||
120 | |||
121 | struct wl1271_partition_set { | ||
122 | struct wl1271_partition mem; | ||
123 | struct wl1271_partition reg; | ||
124 | struct wl1271_partition mem2; | ||
125 | struct wl1271_partition mem3; | ||
126 | }; | ||
127 | |||
128 | struct wl1271; | 108 | struct wl1271; |
129 | 109 | ||
130 | enum { | 110 | enum { |
diff --git a/drivers/net/wireless/ti/wlcore/wlcore.h b/drivers/net/wireless/ti/wlcore/wlcore.h index 0bcc6adcbc15..84f05a4d3cdc 100644 --- a/drivers/net/wireless/ti/wlcore/wlcore.h +++ b/drivers/net/wireless/ti/wlcore/wlcore.h | |||
@@ -30,6 +30,29 @@ | |||
30 | struct wlcore_ops { | 30 | struct wlcore_ops { |
31 | }; | 31 | }; |
32 | 32 | ||
33 | enum wlcore_partitions { | ||
34 | PART_DOWN, | ||
35 | PART_WORK, | ||
36 | PART_BOOT, | ||
37 | PART_DRPW, | ||
38 | PART_TOP_PRCM_ELP_SOC, | ||
39 | PART_PHY_INIT, | ||
40 | |||
41 | PART_TABLE_LEN, | ||
42 | }; | ||
43 | |||
44 | struct wlcore_partition { | ||
45 | u32 size; | ||
46 | u32 start; | ||
47 | }; | ||
48 | |||
49 | struct wlcore_partition_set { | ||
50 | struct wlcore_partition mem; | ||
51 | struct wlcore_partition reg; | ||
52 | struct wlcore_partition mem2; | ||
53 | struct wlcore_partition mem3; | ||
54 | }; | ||
55 | |||
33 | struct wl1271 { | 56 | struct wl1271 { |
34 | struct ieee80211_hw *hw; | 57 | struct ieee80211_hw *hw; |
35 | bool mac80211_registered; | 58 | bool mac80211_registered; |
@@ -54,7 +77,7 @@ struct wl1271 { | |||
54 | 77 | ||
55 | unsigned long flags; | 78 | unsigned long flags; |
56 | 79 | ||
57 | struct wl1271_partition_set part; | 80 | struct wlcore_partition_set curr_part; |
58 | 81 | ||
59 | struct wl1271_chip chip; | 82 | struct wl1271_chip chip; |
60 | 83 | ||
@@ -241,6 +264,8 @@ struct wl1271 { | |||
241 | struct delayed_work tx_watchdog_work; | 264 | struct delayed_work tx_watchdog_work; |
242 | 265 | ||
243 | struct wlcore_ops *ops; | 266 | struct wlcore_ops *ops; |
267 | /* pointer to the lower driver partition table */ | ||
268 | const struct wlcore_partition_set *ptable; | ||
244 | }; | 269 | }; |
245 | 270 | ||
246 | int __devinit wlcore_probe(struct wl1271 *wl, struct platform_device *pdev); | 271 | int __devinit wlcore_probe(struct wl1271 *wl, struct platform_device *pdev); |