1/* 2 * Copyright (C) 2002 Benjamin Herrenschmidt (benh@kernel.crashing.org) 3 * 4 * This program is free software; you can redistribute it and/or 5 * modify it under the terms of the GNU General Public License 6 * as published by the Free Software Foundation; either version 7 * 2 of the License, or (at your option) any later version. 8 * 9 * Todo: - add support for the OF persistent properties 10 */ 11#include <linux/module.h> 12#include <linux/kernel.h> 13#include <linux/stddef.h> 14#include <linux/string.h> 15#include <linux/nvram.h> 16#include <linux/init.h> 17#include <linux/delay.h> 18#include <linux/errno.h> 19#include <linux/adb.h> 20#include <linux/pmu.h> 21#include <linux/bootmem.h> 22#include <linux/completion.h> 23#include <linux/spinlock.h> 24#include <asm/sections.h> 25#include <asm/io.h> 26#include <asm/system.h> 27#include <asm/prom.h> 28#include <asm/machdep.h> 29#include <asm/nvram.h> 30 31#include "pmac.h" 32 33#define DEBUG 34 35#ifdef DEBUG 36#define DBG(x...) printk(x) 37#else 38#define DBG(x...) 39#endif 40 41#define NVRAM_SIZE 0x2000 /* 8kB of non-volatile RAM */ 42 43#define CORE99_SIGNATURE 0x5a 44#define CORE99_ADLER_START 0x14 45 46/* On Core99, nvram is either a sharp, a micron or an AMD flash */ 47#define SM_FLASH_STATUS_DONE 0x80 48#define SM_FLASH_STATUS_ERR 0x38 49 50#define SM_FLASH_CMD_ERASE_CONFIRM 0xd0 51#define SM_FLASH_CMD_ERASE_SETUP 0x20 52#define SM_FLASH_CMD_RESET 0xff 53#define SM_FLASH_CMD_WRITE_SETUP 0x40 54#define SM_FLASH_CMD_CLEAR_STATUS 0x50 55#define SM_FLASH_CMD_READ_STATUS 0x70 56 57/* CHRP NVRAM header */ 58struct chrp_header { 59 u8 signature; 60 u8 cksum; 61 u16 len; 62 char name[12]; 63 u8 data[0]; 64}; 65 66struct core99_header { 67 struct chrp_header hdr; 68 u32 adler; 69 u32 generation; 70 u32 reserved[2]; 71}; 72 73/* 74 * Read and write the non-volatile RAM on PowerMacs and CHRP machines. 75 */ 76static int nvram_naddrs; 77static volatile unsigned char __iomem *nvram_data; 78static int is_core_99; 79static int core99_bank = 0; 80static int nvram_partitions[3]; 81static DEFINE_RAW_SPINLOCK(nv_lock); 82 83static int (*core99_write_bank)(int bank, u8* datas); 84static int (*core99_erase_bank)(int bank); 85 86static char *nvram_image; 87 88 89static unsigned char core99_nvram_read_byte(int addr) 90{ 91 if (nvram_image == NULL) 92 return 0xff; 93 return nvram_image[addr]; 94} 95 96static void core99_nvram_write_byte(int addr, unsigned char val) 97{ 98 if (nvram_image == NULL) 99 return; 100 nvram_image[addr] = val; 101} 102 103static ssize_t core99_nvram_read(char *buf, size_t count, loff_t *index) 104{ 105 int i; 106 107 if (nvram_image == NULL) 108 return -ENODEV; 109 if (*index > NVRAM_SIZE) 110 return 0; 111 112 i = *index; 113 if (i + count > NVRAM_SIZE) 114 count = NVRAM_SIZE - i; 115 116 memcpy(buf, &nvram_image[i], count); 117 *index = i + count; 118 return count; 119} 120 121static ssize_t core99_nvram_write(char *buf, size_t count, loff_t *index) 122{ 123 int i; 124 125 if (nvram_image == NULL) 126 return -ENODEV; 127 if (*index > NVRAM_SIZE) 128 return 0; 129 130 i = *index; 131 if (i + count > NVRAM_SIZE) 132 count = NVRAM_SIZE - i; 133 134 memcpy(&nvram_image[i], buf, count); 135 *index = i + count; 136 return count; 137} 138 139static ssize_t core99_nvram_size(void) 140{ 141 if (nvram_image == NULL) 142 return -ENODEV; 143 return NVRAM_SIZE; 144} 145 146#ifdef CONFIG_PPC32 147static volatile unsigned char __iomem *nvram_addr; 148static int nvram_mult; 149 150static unsigned char direct_nvram_read_byte(int addr) 151{ 152 return in_8(&nvram_data[(addr & (NVRAM_SIZE - 1)) * nvram_mult]); 153} 154 155static void direct_nvram_write_byte(int addr, unsigned char val) 156{ 157 out_8(&nvram_data[(addr & (NVRAM_SIZE - 1)) * nvram_mult], val); 158} 159 160 161static unsigned char indirect_nvram_read_byte(int addr) 162{ 163 unsigned char val; 164 unsigned long flags; 165 166 raw_spin_lock_irqsave(&nv_lock, flags); 167 out_8(nvram_addr, addr >> 5); 168 val = in_8(&nvram_data[(addr & 0x1f) << 4]); 169 raw_spin_unlock_irqrestore(&nv_lock, flags); 170 171 return val; 172} 173 174static void indirect_nvram_write_byte(int addr, unsigned char val) 175{ 176 unsigned long flags; 177 178 raw_spin_lock_irqsave(&nv_lock, flags); 179 out_8(nvram_addr, addr >> 5); 180 out_8(&nvram_data[(addr & 0x1f) << 4], val); 181 raw_spin_unlock_irqrestore(&nv_lock, flags); 182} 183 184 185#ifdef CONFIG_ADB_PMU 186 187static void pmu_nvram_complete(struct adb_request *req) 188{ 189 if (req->arg) 190 complete((struct completion *)req->arg); 191} 192 193static unsigned char pmu_nvram_read_byte(int addr) 194{ 195 struct adb_request req; 196 DECLARE_COMPLETION_ONSTACK(req_complete); 197 198 req.arg = system_state == SYSTEM_RUNNING ? &req_complete : NULL; 199 if (pmu_request(&req, pmu_nvram_complete, 3, PMU_READ_NVRAM, 200 (addr >> 8) & 0xff, addr & 0xff)) 201 return 0xff; 202 if (system_state == SYSTEM_RUNNING) 203 wait_for_completion(&req_complete); 204 while (!req.complete) 205 pmu_poll(); 206 return req.reply[0]; 207} 208 209static void pmu_nvram_write_byte(int addr, unsigned char val) 210{ 211 struct adb_request req; 212 DECLARE_COMPLETION_ONSTACK(req_complete); 213 214 req.arg = system_state == SYSTEM_RUNNING ? &req_complete : NULL; 215 if (pmu_request(&req, pmu_nvram_complete, 4, PMU_WRITE_NVRAM, 216 (addr >> 8) & 0xff, addr & 0xff, val)) 217 return; 218 if (system_state == SYSTEM_RUNNING) 219 wait_for_completion(&req_complete); 220 while (!req.complete) 221 pmu_poll(); 222} 223 224#endif /* CONFIG_ADB_PMU */ 225#endif /* CONFIG_PPC32 */ 226 227static u8 chrp_checksum(struct chrp_header* hdr) 228{ 229 u8 *ptr; 230 u16 sum = hdr->signature; 231 for (ptr = (u8 *)&hdr->len; ptr < hdr->data; ptr++) 232 sum += *ptr; 233 while (sum > 0xFF) 234 sum = (sum & 0xFF) + (sum>>8); 235 return sum; 236} 237 238static u32 core99_calc_adler(u8 *buffer) 239{ 240 int cnt; 241 u32 low, high; 242 243 buffer += CORE99_ADLER_START; 244 low = 1; 245 high = 0; 246 for (cnt=0; cnt<(NVRAM_SIZE-CORE99_ADLER_START); cnt++) { 247 if ((cnt % 5000) == 0) { 248 high %= 65521UL; 249 high %= 65521UL; 250 } 251 low += buffer[cnt]; 252 high += low; 253 } 254 low %= 65521UL; 255 high %= 65521UL; 256 257 return (high << 16) | low; 258} 259 260static u32 core99_check(u8* datas) 261{ 262 struct core99_header* hdr99 = (struct core99_header*)datas; 263 264 if (hdr99->hdr.signature != CORE99_SIGNATURE) { 265 DBG("Invalid signature\n"); 266 return 0; 267 } 268 if (hdr99->hdr.cksum != chrp_checksum(&hdr99->hdr)) { 269 DBG("Invalid checksum\n"); 270 return 0; 271 } 272 if (hdr99->adler != core99_calc_adler(datas)) { 273 DBG("Invalid adler\n"); 274 return 0; 275 } 276 return hdr99->generation; 277} 278 279static int sm_erase_bank(int bank) 280{ 281 int stat, i; 282 unsigned long timeout; 283 284 u8 __iomem *base = (u8 __iomem *)nvram_data + core99_bank*NVRAM_SIZE; 285 286 DBG("nvram: Sharp/Micron Erasing bank %d...\n", bank); 287 288 out_8(base, SM_FLASH_CMD_ERASE_SETUP); 289 out_8(base, SM_FLASH_CMD_ERASE_CONFIRM); 290 timeout = 0; 291 do { 292 if (++timeout > 1000000) { 293 printk(KERN_ERR "nvram: Sharp/Micron flash erase timeout !\n"); 294 break; 295 } 296 out_8(base, SM_FLASH_CMD_READ_STATUS); 297 stat = in_8(base); 298 } while (!(stat & SM_FLASH_STATUS_DONE)); 299 300 out_8(base, SM_FLASH_CMD_CLEAR_STATUS); 301 out_8(base, SM_FLASH_CMD_RESET); 302 303 for (i=0; i<NVRAM_SIZE; i++) 304 if (base[i] != 0xff) { 305 printk(KERN_ERR "nvram: Sharp/Micron flash erase failed !\n"); 306 return -ENXIO; 307 } 308 return 0; 309} 310 311static int sm_write_bank(int bank, u8* datas) 312{ 313 int i, stat = 0; 314 unsigned long timeout; 315 316 u8 __iomem *base = (u8 __iomem *)nvram_data + core99_bank*NVRAM_SIZE; 317 318 DBG("nvram: Sharp/Micron Writing bank %d...\n", bank); 319 320 for (i=0; i<NVRAM_SIZE; i++) { 321 out_8(base+i, SM_FLASH_CMD_WRITE_SETUP); 322 udelay(1); 323 out_8(base+i, datas[i]); 324 timeout = 0; 325 do { 326 if (++timeout > 1000000) { 327 printk(KERN_ERR "nvram: Sharp/Micron flash write timeout !\n"); 328 break; 329 } 330 out_8(base, SM_FLASH_CMD_READ_STATUS); 331 stat = in_8(base); 332 } while (!(stat & SM_FLASH_STATUS_DONE)); 333 if (!(stat & SM_FLASH_STATUS_DONE)) 334 break; 335 } 336 out_8(base, SM_FLASH_CMD_CLEAR_STATUS); 337 out_8(base, SM_FLASH_CMD_RESET); 338 for (i=0; i<NVRAM_SIZE; i++) 339 if (base[i] != datas[i]) { 340 printk(KERN_ERR "nvram: Sharp/Micron flash write failed !\n"); 341 return -ENXIO; 342 } 343 return 0; 344} 345 346static int amd_erase_bank(int bank) 347{ 348 int i, stat = 0; 349 unsigned long timeout; 350 351 u8 __iomem *base = (u8 __iomem *)nvram_data + core99_bank*NVRAM_SIZE; 352 353 DBG("nvram: AMD Erasing bank %d...\n", bank); 354 355 /* Unlock 1 */ 356 out_8(base+0x555, 0xaa); 357 udelay(1); 358 /* Unlock 2 */ 359 out_8(base+0x2aa, 0x55); 360 udelay(1); 361 362 /* Sector-Erase */ 363 out_8(base+0x555, 0x80); 364 udelay(1); 365 out_8(base+0x555, 0xaa); 366 udelay(1); 367 out_8(base+0x2aa, 0x55); 368 udelay(1); 369 out_8(base, 0x30); 370 udelay(1); 371 372 timeout = 0; 373 do { 374 if (++timeout > 1000000) { 375 printk(KERN_ERR "nvram: AMD flash erase timeout !\n"); 376 break; 377 } 378 stat = in_8(base) ^ in_8(base); 379 } while (stat != 0); 380 381 /* Reset */ 382 out_8(base, 0xf0); 383 udelay(1); 384 385 for (i=0; i<NVRAM_SIZE; i++) 386 if (base[i] != 0xff) { 387 printk(KERN_ERR "nvram: AMD flash erase failed !\n"); 388 return -ENXIO; 389 } 390 return 0; 391} 392 393static int amd_write_bank(int bank, u8* datas) 394{ 395 int i, stat = 0; 396 unsigned long timeout; 397 398 u8 __iomem *base = (u8 __iomem *)nvram_data + core99_bank*NVRAM_SIZE; 399 400 DBG("nvram: AMD Writing bank %d...\n", bank); 401 402 for (i=0; i<NVRAM_SIZE; i++) { 403 /* Unlock 1 */ 404 out_8(base+0x555, 0xaa); 405 udelay(1); 406 /* Unlock 2 */ 407 out_8(base+0x2aa, 0x55); 408 udelay(1); 409 410 /* Write single word */ 411 out_8(base+0x555, 0xa0); 412 udelay(1); 413 out_8(base+i, datas[i]); 414 415 timeout = 0; 416 do { 417 if (++timeout > 1000000) { 418 printk(KERN_ERR "nvram: AMD flash write timeout !\n"); 419 break; 420 } 421 stat = in_8(base) ^ in_8(base); 422 } while (stat != 0); 423 if (stat != 0) 424 break; 425 } 426 427 /* Reset */ 428 out_8(base, 0xf0); 429 udelay(1); 430 431 for (i=0; i<NVRAM_SIZE; i++) 432 if (base[i] != datas[i]) { 433 printk(KERN_ERR "nvram: AMD flash write failed !\n"); 434 return -ENXIO; 435 } 436 return 0; 437} 438 439static void __init lookup_partitions(void) 440{ 441 u8 buffer[17]; 442 int i, offset; 443 struct chrp_header* hdr; 444 445 if (pmac_newworld) { 446 nvram_partitions[pmac_nvram_OF] = -1; 447 nvram_partitions[pmac_nvram_XPRAM] = -1; 448 nvram_partitions[pmac_nvram_NR] = -1; 449 hdr = (struct chrp_header *)buffer; 450 451 offset = 0; 452 buffer[16] = 0; 453 do { 454 for (i=0;i<16;i++) 455 buffer[i] = ppc_md.nvram_read_val(offset+i); 456 if (!strcmp(hdr->name, "common")) 457 nvram_partitions[pmac_nvram_OF] = offset + 0x10; 458 if (!strcmp(hdr->name, "APL,MacOS75")) { 459 nvram_partitions[pmac_nvram_XPRAM] = offset + 0x10; 460 nvram_partitions[pmac_nvram_NR] = offset + 0x110; 461 } 462 offset += (hdr->len * 0x10); 463 } while(offset < NVRAM_SIZE); 464 } else { 465 nvram_partitions[pmac_nvram_OF] = 0x1800; 466 nvram_partitions[pmac_nvram_XPRAM] = 0x1300; 467 nvram_partitions[pmac_nvram_NR] = 0x1400; 468 } 469 DBG("nvram: OF partition at 0x%x\n", nvram_partitions[pmac_nvram_OF]); 470 DBG("nvram: XP partition at 0x%x\n", nvram_partitions[pmac_nvram_XPRAM]); 471 DBG("nvram: NR partition at 0x%x\n", nvram_partitions[pmac_nvram_NR]); 472} 473 474static void core99_nvram_sync(void) 475{ 476 struct core99_header* hdr99; 477 unsigned long flags; 478 479 if (!is_core_99 || !nvram_data || !nvram_image) 480 return; 481 482 raw_spin_lock_irqsave(&nv_lock, flags); 483 if (!memcmp(nvram_image, (u8*)nvram_data + core99_bank*NVRAM_SIZE, 484 NVRAM_SIZE)) 485 goto bail; 486 487 DBG("Updating nvram...\n"); 488 489 hdr99 = (struct core99_header*)nvram_image; 490 hdr99->generation++; 491 hdr99->hdr.signature = CORE99_SIGNATURE; 492 hdr99->hdr.cksum = chrp_checksum(&hdr99->hdr); 493 hdr99->adler = core99_calc_adler(nvram_image); 494 core99_bank = core99_bank ? 0 : 1; 495 if (core99_erase_bank) 496 if (core99_erase_bank(core99_bank)) { 497 printk("nvram: Error erasing bank %d\n", core99_bank); 498 goto bail; 499 } 500 if (core99_write_bank) 501 if (core99_write_bank(core99_bank, nvram_image)) 502 printk("nvram: Error writing bank %d\n", core99_bank); 503 bail: 504 raw_spin_unlock_irqrestore(&nv_lock, flags); 505 506#ifdef DEBUG 507 mdelay(2000); 508#endif 509} 510 511static int __init core99_nvram_setup(struct device_node *dp, unsigned long addr) 512{ 513 int i; 514 u32 gen_bank0, gen_bank1; 515 516 if (nvram_naddrs < 1) { 517 printk(KERN_ERR "nvram: no address\n"); 518 return -EINVAL; 519 } 520 nvram_image = alloc_bootmem(NVRAM_SIZE); 521 if (nvram_image == NULL) { 522 printk(KERN_ERR "nvram: can't allocate ram image\n"); 523 return -ENOMEM; 524 } 525 nvram_data = ioremap(addr, NVRAM_SIZE*2); 526 nvram_naddrs = 1; /* Make sure we get the correct case */ 527 528 DBG("nvram: Checking bank 0...\n"); 529 530 gen_bank0 = core99_check((u8 *)nvram_data); 531 gen_bank1 = core99_check((u8 *)nvram_data + NVRAM_SIZE); 532 core99_bank = (gen_bank0 < gen_bank1) ? 1 : 0; 533 534 DBG("nvram: gen0=%d, gen1=%d\n", gen_bank0, gen_bank1); 535 DBG("nvram: Active bank is: %d\n", core99_bank); 536 537 for (i=0; i<NVRAM_SIZE; i++) 538 nvram_image[i] = nvram_data[i + core99_bank*NVRAM_SIZE]; 539 540 ppc_md.nvram_read_val = core99_nvram_read_byte; 541 ppc_md.nvram_write_val = core99_nvram_write_byte; 542 ppc_md.nvram_read = core99_nvram_read; 543 ppc_md.nvram_write = core99_nvram_write; 544 ppc_md.nvram_size = core99_nvram_size; 545 ppc_md.nvram_sync = core99_nvram_sync; 546 ppc_md.machine_shutdown = core99_nvram_sync; 547 /* 548 * Maybe we could be smarter here though making an exclusive list 549 * of known flash chips is a bit nasty as older OF didn't provide us 550 * with a useful "compatible" entry. A solution would be to really 551 * identify the chip using flash id commands and base ourselves on 552 * a list of known chips IDs 553 */ 554 if (of_device_is_compatible(dp, "amd-0137")) { 555 core99_erase_bank = amd_erase_bank; 556 core99_write_bank = amd_write_bank; 557 } else { 558 core99_erase_bank = sm_erase_bank; 559 core99_write_bank = sm_write_bank; 560 } 561 return 0; 562} 563 564int __init pmac_nvram_init(void) 565{ 566 struct device_node *dp; 567 struct resource r1, r2; 568 unsigned int s1 = 0, s2 = 0; 569 int err = 0; 570 571 nvram_naddrs = 0; 572 573 dp = of_find_node_by_name(NULL, "nvram"); 574 if (dp == NULL) { 575 printk(KERN_ERR "Can't find NVRAM device\n"); 576 return -ENODEV; 577 } 578 579 /* Try to obtain an address */ 580 if (of_address_to_resource(dp, 0, &r1) == 0) { 581 nvram_naddrs = 1; 582 s1 = (r1.end - r1.start) + 1; 583 if (of_address_to_resource(dp, 1, &r2) == 0) { 584 nvram_naddrs = 2; 585 s2 = (r2.end - r2.start) + 1; 586 } 587 } 588 589 is_core_99 = of_device_is_compatible(dp, "nvram,flash"); 590 if (is_core_99) { 591 err = core99_nvram_setup(dp, r1.start); 592 goto bail; 593 } 594 595#ifdef CONFIG_PPC32 596 if (machine_is(chrp) && nvram_naddrs == 1) { 597 nvram_data = ioremap(r1.start, s1); 598 nvram_mult = 1; 599 ppc_md.nvram_read_val = direct_nvram_read_byte; 600 ppc_md.nvram_write_val = direct_nvram_write_byte; 601 } else if (nvram_naddrs == 1) { 602 nvram_data = ioremap(r1.start, s1); 603 nvram_mult = (s1 + NVRAM_SIZE - 1) / NVRAM_SIZE; 604 ppc_md.nvram_read_val = direct_nvram_read_byte; 605 ppc_md.nvram_write_val = direct_nvram_write_byte; 606 } else if (nvram_naddrs == 2) { 607 nvram_addr = ioremap(r1.start, s1); 608 nvram_data = ioremap(r2.start, s2); 609 ppc_md.nvram_read_val = indirect_nvram_read_byte; 610 ppc_md.nvram_write_val = indirect_nvram_write_byte; 611 } else if (nvram_naddrs == 0 && sys_ctrler == SYS_CTRLER_PMU) { 612#ifdef CONFIG_ADB_PMU 613 nvram_naddrs = -1; 614 ppc_md.nvram_read_val = pmu_nvram_read_byte; 615 ppc_md.nvram_write_val = pmu_nvram_write_byte; 616#endif /* CONFIG_ADB_PMU */ 617 } else { 618 printk(KERN_ERR "Incompatible type of NVRAM\n"); 619 err = -ENXIO; 620 } 621#endif /* CONFIG_PPC32 */ 622bail: 623 of_node_put(dp); 624 if (err == 0) 625 lookup_partitions(); 626 return err; 627} 628 629int pmac_get_partition(int partition) 630{ 631 return nvram_partitions[partition]; 632} 633 634u8 pmac_xpram_read(int xpaddr) 635{ 636 int offset = pmac_get_partition(pmac_nvram_XPRAM); 637 638 if (offset < 0 || xpaddr < 0 || xpaddr > 0x100) 639 return 0xff; 640 641 return ppc_md.nvram_read_val(xpaddr + offset); 642} 643 644void pmac_xpram_write(int xpaddr, u8 data) 645{ 646 int offset = pmac_get_partition(pmac_nvram_XPRAM); 647 648 if (offset < 0 || xpaddr < 0 || xpaddr > 0x100) 649 return; 650 651 ppc_md.nvram_write_val(xpaddr + offset, data); 652} 653 654EXPORT_SYMBOL(pmac_get_partition); 655EXPORT_SYMBOL(pmac_xpram_read); 656EXPORT_SYMBOL(pmac_xpram_write); 657