it87spi.c 8.42 KB
Newer Older
1 2 3
/*
 * This file is part of the flashrom project.
 *
4
 * Copyright (C) 2007, 2008, 2009 Carl-Daniel Hailfinger
5
 * Copyright (C) 2008 Ronald Hoogenboom <ronald@zonnet.nl>
6
 * Copyright (C) 2008 coresystems GmbH
7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; version 2 of the License.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301 USA
 */

/*
 * Contains the ITE IT87* SPI specific routines
 */

#include <string.h>
27
#include <stdlib.h>
28 29 30 31 32 33
#include "flash.h"
#include "spi.h"

#define ITE_SUPERIO_PORT1	0x2e
#define ITE_SUPERIO_PORT2	0x4e

34
char *it87opts = NULL;
35 36 37 38 39 40 41
uint16_t it8716f_flashport = 0;
/* use fast 33MHz SPI (<>0) or slow 16MHz (0) */
int fast_spi = 1;

/* Helper functions for most recent ITE IT87xx Super I/O chips */
#define CHIP_ID_BYTE1_REG	0x20
#define CHIP_ID_BYTE2_REG	0x21
42
void enter_conf_mode_ite(uint16_t port)
43
{
44 45 46
	OUTB(0x87, port);
	OUTB(0x01, port);
	OUTB(0x55, port);
47
	if (port == ITE_SUPERIO_PORT1)
48
		OUTB(0x55, port);
49
	else
50
		OUTB(0xaa, port);
51 52
}

53
void exit_conf_mode_ite(uint16_t port)
54
{
55
	sio_write(port, 0x02, 0x02);
56 57 58 59 60
}

static uint16_t find_ite_spi_flash_port(uint16_t port)
{
	uint8_t tmp = 0;
61
	char *portpos = NULL;
62 63 64 65
	uint16_t id, flashport = 0;

	enter_conf_mode_ite(port);

66 67
	id = sio_read(port, CHIP_ID_BYTE1_REG) << 8;
	id |= sio_read(port, CHIP_ID_BYTE2_REG);
68 69

	/* TODO: Handle more IT87xx if they support flash translation */
Peter Stuge's avatar
Peter Stuge committed
70
	if (0x8716 == id || 0x8718 == id) {
71
		/* NOLDN, reg 0x24, mask out lowest bit (suspend) */
72
		tmp = sio_read(port, 0x24) & 0xFE;
73
		printf("Serial flash segment 0x%08x-0x%08x %sabled\n",
74
		       0xFFFE0000, 0xFFFFFFFF, (tmp & 1 << 1) ? "en" : "dis");
75
		printf("Serial flash segment 0x%08x-0x%08x %sabled\n",
76
		       0x000E0000, 0x000FFFFF, (tmp & 1 << 1) ? "en" : "dis");
77
		printf("Serial flash segment 0x%08x-0x%08x %sabled\n",
78
		       0xFFEE0000, 0xFFEFFFFF, (tmp & 1 << 2) ? "en" : "dis");
79
		printf("Serial flash segment 0x%08x-0x%08x %sabled\n",
80
		       0xFFF80000, 0xFFFEFFFF, (tmp & 1 << 3) ? "en" : "dis");
81
		printf("LPC write to serial flash %sabled\n",
82
		       (tmp & 1 << 4) ? "en" : "dis");
83 84 85
		/* The LPC->SPI force write enable below only makes sense for
		 * non-programmer mode.
		 */
86 87 88 89
		/* If any serial flash segment is enabled, enable writing. */
		if ((tmp & 0xe) && (!(tmp & 1 << 4))) {
			printf("Enabling LPC write to serial flash\n");
			tmp |= 1 << 4;
90
			sio_write(port, 0x24, tmp);
91
		}
92
		printf("Serial flash pin %i\n", (tmp & 1 << 5) ? 87 : 29);
93
		/* LDN 0x7, reg 0x64/0x65 */
94 95 96
		sio_write(port, 0x07, 0x7);
		flashport = sio_read(port, 0x64) << 8;
		flashport |= sio_read(port, 0x65);
97
		printf("Serial flash port 0x%04x\n", flashport);
98 99 100 101 102 103 104 105 106 107 108
		if (it87opts && !strlen(it87opts)) {
			free(it87opts);
			it87opts = NULL;
		}
		if (it87opts && (portpos = strstr(it87opts, "port="))) {
			portpos += 5;
			flashport = strtol(portpos, (char **)NULL, 0);
			printf("Forcing serial flash port 0x%04x\n", flashport);
			sio_write(port, 0x64, (flashport >> 8));
			sio_write(port, 0x65, (flashport & 0xff));
		}
109 110 111 112 113
	}
	exit_conf_mode_ite(port);
	return flashport;
}

114
int it87spi_common_init(void)
115 116
{
	it8716f_flashport = find_ite_spi_flash_port(ITE_SUPERIO_PORT1);
117

118 119
	if (!it8716f_flashport)
		it8716f_flashport = find_ite_spi_flash_port(ITE_SUPERIO_PORT2);
120 121

	if (it8716f_flashport)
122
		spi_controller = SPI_CONTROLLER_IT87XX;
123

124 125 126
	return (!it8716f_flashport);
}

127 128 129

int it87spi_init(void)
{
130
	int ret;
131

132 133
	get_io_perms();
	ret = it87spi_common_init();
134
	if (!ret) {
135
		buses_supported = CHIP_BUSTYPE_SPI;
136 137 138
	} else {
		buses_supported = CHIP_BUSTYPE_NONE;
	}
139
	return ret;
140 141 142 143
}

int it87xx_probe_spi_flash(const char *name)
{
144 145 146 147 148 149
	int ret;

	ret = it87spi_common_init();
	if (!ret)
		buses_supported |= CHIP_BUSTYPE_SPI;
	return ret;
150 151
}

152 153 154 155 156 157 158 159 160
/*
 * The IT8716F only supports commands with length 1,2,4,5 bytes including
 * command byte and can not read more than 3 bytes from the device.
 *
 * This function expects writearr[0] to be the first byte sent to the device,
 * whereas the IT8716F splits commands internally into address and non-address
 * commands with the address in inverse wire order. That's why the register
 * ordering in case 4 and 5 may seem strange.
 */
161
int it8716f_spi_send_command(unsigned int writecnt, unsigned int readcnt,
162
			const unsigned char *writearr, unsigned char *readarr)
163 164 165 166 167
{
	uint8_t busy, writeenc;
	int i;

	do {
168
		busy = INB(it8716f_flashport) & 0x80;
169 170 171
	} while (busy);
	if (readcnt > 3) {
		printf("%s called with unsupported readcnt %i.\n",
172
		       __FUNCTION__, readcnt);
173
		return SPI_INVALID_LENGTH;
174 175 176
	}
	switch (writecnt) {
	case 1:
177
		OUTB(writearr[0], it8716f_flashport + 1);
178 179 180
		writeenc = 0x0;
		break;
	case 2:
181 182
		OUTB(writearr[0], it8716f_flashport + 1);
		OUTB(writearr[1], it8716f_flashport + 7);
183 184 185
		writeenc = 0x1;
		break;
	case 4:
186 187 188 189
		OUTB(writearr[0], it8716f_flashport + 1);
		OUTB(writearr[1], it8716f_flashport + 4);
		OUTB(writearr[2], it8716f_flashport + 3);
		OUTB(writearr[3], it8716f_flashport + 2);
190 191 192
		writeenc = 0x2;
		break;
	case 5:
193 194 195 196 197
		OUTB(writearr[0], it8716f_flashport + 1);
		OUTB(writearr[1], it8716f_flashport + 4);
		OUTB(writearr[2], it8716f_flashport + 3);
		OUTB(writearr[3], it8716f_flashport + 2);
		OUTB(writearr[4], it8716f_flashport + 7);
198 199 200 201
		writeenc = 0x3;
		break;
	default:
		printf("%s called with unsupported writecnt %i.\n",
202
		       __FUNCTION__, writecnt);
203
		return SPI_INVALID_LENGTH;
204
	}
205 206
	/*
	 * Start IO, 33 or 16 MHz, readcnt input bytes, writecnt output bytes.
207 208
	 * Note:
	 * We can't use writecnt directly, but have to use a strange encoding.
209 210 211
	 */
	OUTB(((0x4 + (fast_spi ? 1 : 0)) << 4)
		| ((readcnt & 0x3) << 2) | (writeenc), it8716f_flashport);
212 213 214

	if (readcnt > 0) {
		do {
215
			busy = INB(it8716f_flashport) & 0x80;
216 217
		} while (busy);

218
		for (i = 0; i < readcnt; i++)
219
			readarr[i] = INB(it8716f_flashport + 5 + i);
220 221 222 223 224 225
	}

	return 0;
}

/* Page size is usually 256 bytes */
226
static int it8716f_spi_page_program(struct flashchip *flash, int block, uint8_t *buf)
227
{
228
	int i;
229
	int result;
230
	chipaddr bios = flash->virtual_memory;
231

232 233 234
	result = spi_write_enable();
	if (result)
		return result;
235
	/* FIXME: The command below seems to be redundant or wrong. */
236
	OUTB(0x06, it8716f_flashport + 1);
237
	OUTB(((2 + (fast_spi ? 1 : 0)) << 4), it8716f_flashport);
238
	for (i = 0; i < 256; i++) {
239
		chip_writeb(buf[256 * block + i], bios + 256 * block + i);
240
	}
241
	OUTB(0, it8716f_flashport);
242 243 244 245
	/* Wait until the Write-In-Progress bit is cleared.
	 * This usually takes 1-10 ms, so wait in 1 ms steps.
	 */
	while (spi_read_status_register() & JEDEC_RDSR_BIT_WIP)
246
		programmer_delay(1000);
247
	return 0;
248 249 250 251
}

/*
 * Program chip using firmware cycle byte programming. (SLOW!)
252 253 254
 * This is for chips which can only handle one byte writes
 * and for chips where memory mapped programming is impossible due to
 * size constraints in IT87* (over 512 kB)
255
 */
256
int it8716f_spi_chip_write_1(struct flashchip *flash, uint8_t *buf)
257 258 259
{
	int total_size = 1024 * flash->total_size;
	int i;
260
	int result;
261

262 263 264 265
	fast_spi = 0;

	spi_disable_blockprotect();
	for (i = 0; i < total_size; i++) {
266
		result = spi_byte_program(i, buf[i]);
267
		while (spi_read_status_register() & JEDEC_RDSR_BIT_WIP)
268
			programmer_delay(10);
269 270
	}
	/* resume normal ops... */
271
	OUTB(0x20, it8716f_flashport);
272

273 274 275 276 277 278 279
	return 0;
}

/*
 * IT8716F only allows maximum of 512 kb SPI mapped to LPC memory cycles
 * Need to read this big flash using firmware cycles 3 byte at a time.
 */
280
int it8716f_spi_chip_read(struct flashchip *flash, uint8_t *buf, int start, int len)
281 282 283 284
{
	int total_size = 1024 * flash->total_size;
	fast_spi = 0;

285
	if ((programmer == PROGRAMMER_IT87SPI) || (total_size > 512 * 1024)) {
286
		spi_read_chunked(flash, buf, start, len, 3);
287
	} else {
288
		read_memmapped(flash, buf, start, len);
289
	}
290

291 292 293
	return 0;
}

294
int it8716f_spi_chip_write_256(struct flashchip *flash, uint8_t *buf)
295
{
296 297
	int total_size = 1024 * flash->total_size;
	int i;
298

299 300 301 302
	/*
	 * IT8716F only allows maximum of 512 kb SPI chip size for memory
	 * mapped access.
	 */
303
	if ((programmer == PROGRAMMER_IT87SPI) || (total_size > 512 * 1024)) {
304
		it8716f_spi_chip_write_1(flash, buf);
305 306
	} else {
		for (i = 0; i < total_size / 256; i++) {
307
			it8716f_spi_page_program(flash, i, buf);
308 309
		}
	}
310

311 312
	return 0;
}