blob: e8cc82751e45f400a7c26d717445166049b46730 [file] [log] [blame]
TsiChung Liew7b7a8692008-08-06 16:08:41 -05001/*
2 * (C) Copyright 2000-2002
3 * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
4 *
5 * Copyright 2008, Network Appliance Inc.
6 * Jason McMullan <mcmullan@netapp.com>
7 *
8 * Copyright (C) 2004-2007 Freescale Semiconductor, Inc.
9 * TsiChung Liew (Tsi-Chung.Liew@freescale.com)
10 *
Wolfgang Denk1a459662013-07-08 09:37:19 +020011 * SPDX-License-Identifier: GPL-2.0+
TsiChung Liew7b7a8692008-08-06 16:08:41 -050012 */
13
14#include <common.h>
15#include <malloc.h>
16#include <spi_flash.h>
17
18#include "spi_flash_internal.h"
19
20/* M25Pxx-specific commands */
Jagannadha Sutradharudu Tekid0be6162013-05-25 01:13:47 +053021#define CMD_M25PXX_RES 0xab /* Release from DP, and Read Signature */
TsiChung Liew7b7a8692008-08-06 16:08:41 -050022
TsiChung Liew7b7a8692008-08-06 16:08:41 -050023struct stmicro_spi_flash_params {
Stephan Linz63ff6a62012-08-02 20:47:29 +020024 u16 id;
TsiChung Liew7b7a8692008-08-06 16:08:41 -050025 u16 pages_per_sector;
26 u16 nr_sectors;
27 const char *name;
28};
29
TsiChung Liew7b7a8692008-08-06 16:08:41 -050030static const struct stmicro_spi_flash_params stmicro_spi_flash_table[] = {
31 {
Stephan Linz63ff6a62012-08-02 20:47:29 +020032 .id = 0x2011,
Thomas Chou12c2e3b2010-04-30 21:11:20 +080033 .pages_per_sector = 128,
34 .nr_sectors = 4,
35 .name = "M25P10",
36 },
37 {
Stephan Linz63ff6a62012-08-02 20:47:29 +020038 .id = 0x2015,
TsiChung Liew7b7a8692008-08-06 16:08:41 -050039 .pages_per_sector = 256,
40 .nr_sectors = 32,
41 .name = "M25P16",
42 },
43 {
Stephan Linz63ff6a62012-08-02 20:47:29 +020044 .id = 0x2012,
TsiChung Liew7b7a8692008-08-06 16:08:41 -050045 .pages_per_sector = 256,
46 .nr_sectors = 4,
47 .name = "M25P20",
48 },
49 {
Stephan Linz63ff6a62012-08-02 20:47:29 +020050 .id = 0x2016,
TsiChung Liew7b7a8692008-08-06 16:08:41 -050051 .pages_per_sector = 256,
52 .nr_sectors = 64,
53 .name = "M25P32",
54 },
55 {
Stephan Linz63ff6a62012-08-02 20:47:29 +020056 .id = 0x2013,
TsiChung Liew7b7a8692008-08-06 16:08:41 -050057 .pages_per_sector = 256,
58 .nr_sectors = 8,
59 .name = "M25P40",
60 },
61 {
Stephan Linz63ff6a62012-08-02 20:47:29 +020062 .id = 0x2017,
TsiChung Liew7b7a8692008-08-06 16:08:41 -050063 .pages_per_sector = 256,
64 .nr_sectors = 128,
65 .name = "M25P64",
66 },
67 {
Stephan Linz63ff6a62012-08-02 20:47:29 +020068 .id = 0x2014,
TsiChung Liew7b7a8692008-08-06 16:08:41 -050069 .pages_per_sector = 256,
70 .nr_sectors = 16,
71 .name = "M25P80",
72 },
73 {
Stephan Linz63ff6a62012-08-02 20:47:29 +020074 .id = 0x2018,
TsiChung Liew7b7a8692008-08-06 16:08:41 -050075 .pages_per_sector = 1024,
76 .nr_sectors = 64,
77 .name = "M25P128",
78 },
Jérôme Carreterob54d1f22012-04-08 10:55:55 +000079 {
Jagannadha Sutradharudu Tekic75c9212013-01-29 17:13:36 +053080 .id = 0xba16,
81 .pages_per_sector = 256,
82 .nr_sectors = 64,
83 .name = "N25Q32",
84 },
85 {
Jagannadha Sutradharudu Tekib1431da2013-01-29 17:13:37 +053086 .id = 0xbb16,
87 .pages_per_sector = 256,
88 .nr_sectors = 64,
89 .name = "N25Q32A",
90 },
91 {
Jagannadha Sutradharudu Teki3981d022012-12-12 04:48:56 +000092 .id = 0xba17,
93 .pages_per_sector = 256,
94 .nr_sectors = 128,
95 .name = "N25Q064",
96 },
97 {
Jagannadha Sutradharudu Tekif785fcb2013-01-23 18:21:45 +053098 .id = 0xbb17,
99 .pages_per_sector = 256,
100 .nr_sectors = 128,
101 .name = "N25Q64A",
102 },
103 {
Stephan Linz6ad6c6d2012-08-02 20:47:30 +0200104 .id = 0xba18,
105 .pages_per_sector = 256,
106 .nr_sectors = 256,
107 .name = "N25Q128",
108 },
109 {
Michal Simekd945ce92012-08-10 14:21:46 +0200110 .id = 0xbb18,
111 .pages_per_sector = 256,
112 .nr_sectors = 256,
113 .name = "N25Q128A",
114 },
115 {
Stephan Linz63ff6a62012-08-02 20:47:29 +0200116 .id = 0xba19,
Jérôme Carreterob54d1f22012-04-08 10:55:55 +0000117 .pages_per_sector = 256,
118 .nr_sectors = 512,
119 .name = "N25Q256",
120 },
Jagannadha Sutradharudu Tekid62ef562013-01-29 17:13:38 +0530121 {
122 .id = 0xbb19,
123 .pages_per_sector = 256,
124 .nr_sectors = 512,
125 .name = "N25Q256A",
126 },
Jagannadha Sutradharudu Teki0569f3b2013-04-16 20:18:29 +0530127 {
128 .id = 0xba20,
129 .pages_per_sector = 256,
130 .nr_sectors = 1024,
131 .name = "N25Q512",
132 },
Jagannadha Sutradharudu Tekifd60c0a2013-04-16 20:20:12 +0530133 {
134 .id = 0xbb20,
135 .pages_per_sector = 256,
136 .nr_sectors = 1024,
137 .name = "N25Q512A",
138 },
Jagannadha Sutradharudu Teki221cb082013-04-16 20:22:48 +0530139 {
140 .id = 0xba21,
141 .pages_per_sector = 256,
142 .nr_sectors = 2048,
143 .name = "N25Q1024",
144 },
Jagannadha Sutradharudu Teki4e290432013-04-16 20:23:48 +0530145 {
146 .id = 0xbb21,
147 .pages_per_sector = 256,
148 .nr_sectors = 2048,
149 .name = "N25Q1024A",
150 },
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500151};
152
Jagannadha Sutradharudu Tekid0be6162013-05-25 01:13:47 +0530153struct spi_flash *spi_flash_probe_stmicro(struct spi_slave *spi, u8 *idcode)
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500154{
155 const struct stmicro_spi_flash_params *params;
Mike Frysingerb06afa72011-06-28 07:38:10 +0000156 struct spi_flash *flash;
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500157 unsigned int i;
Stephan Linz63ff6a62012-08-02 20:47:29 +0200158 u16 id;
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500159
Thomas Chou12c2e3b2010-04-30 21:11:20 +0800160 if (idcode[0] == 0xff) {
161 i = spi_flash_cmd(spi, CMD_M25PXX_RES,
162 idcode, 4);
163 if (i)
164 return NULL;
165 if ((idcode[3] & 0xf0) == 0x10) {
166 idcode[0] = 0x20;
167 idcode[1] = 0x20;
168 idcode[2] = idcode[3] + 1;
169 } else
170 return NULL;
171 }
172
Stephan Linz63ff6a62012-08-02 20:47:29 +0200173 id = ((idcode[1] << 8) | idcode[2]);
174
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500175 for (i = 0; i < ARRAY_SIZE(stmicro_spi_flash_table); i++) {
176 params = &stmicro_spi_flash_table[i];
Jagannadha Sutradharudu Tekid0be6162013-05-25 01:13:47 +0530177 if (params->id == id)
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500178 break;
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500179 }
180
181 if (i == ARRAY_SIZE(stmicro_spi_flash_table)) {
Stephan Linz63ff6a62012-08-02 20:47:29 +0200182 debug("SF: Unsupported STMicro ID %04x\n", id);
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500183 return NULL;
184 }
185
Simon Glassc0f87dd2013-03-11 06:08:03 +0000186 flash = spi_flash_alloc_base(spi, params->name);
Mike Frysingerb06afa72011-06-28 07:38:10 +0000187 if (!flash) {
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500188 debug("SF: Failed to allocate memory\n");
189 return NULL;
190 }
191
Mike Frysingera4ed3b62012-03-04 22:56:52 -0500192 flash->page_size = 256;
193 flash->sector_size = 256 * params->pages_per_sector;
Mike Frysingerb06afa72011-06-28 07:38:10 +0000194 flash->size = flash->sector_size * params->nr_sectors;
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500195
Jagannadha Sutradharudu Teki615a1562013-06-21 15:56:30 +0530196 /* for >= 512MiB flashes, use flag status instead of read_status */
197 if (flash->size >= 0x4000000)
198 flash->poll_cmd = CMD_FLAG_STATUS;
199
Mike Frysingerb06afa72011-06-28 07:38:10 +0000200 return flash;
TsiChung Liew7b7a8692008-08-06 16:08:41 -0500201}