Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0-or-later
0002 /*
0003  *  c 2001 PPC 64 Team, IBM Corp
0004  *
0005  * /dev/nvram driver for PPC64
0006  */
0007 
0008 #include <linux/types.h>
0009 #include <linux/errno.h>
0010 #include <linux/fs.h>
0011 #include <linux/miscdevice.h>
0012 #include <linux/fcntl.h>
0013 #include <linux/nvram.h>
0014 #include <linux/init.h>
0015 #include <linux/slab.h>
0016 #include <linux/spinlock.h>
0017 #include <linux/kmsg_dump.h>
0018 #include <linux/pagemap.h>
0019 #include <linux/pstore.h>
0020 #include <linux/zlib.h>
0021 #include <linux/uaccess.h>
0022 #include <linux/of.h>
0023 #include <asm/nvram.h>
0024 #include <asm/rtas.h>
0025 #include <asm/machdep.h>
0026 
0027 #undef DEBUG_NVRAM
0028 
0029 #define NVRAM_HEADER_LEN    sizeof(struct nvram_header)
0030 #define NVRAM_BLOCK_LEN     NVRAM_HEADER_LEN
0031 
0032 /* If change this size, then change the size of NVNAME_LEN */
0033 struct nvram_header {
0034     unsigned char signature;
0035     unsigned char checksum;
0036     unsigned short length;
0037     /* Terminating null required only for names < 12 chars. */
0038     char name[12];
0039 };
0040 
0041 struct nvram_partition {
0042     struct list_head partition;
0043     struct nvram_header header;
0044     unsigned int index;
0045 };
0046 
0047 static LIST_HEAD(nvram_partitions);
0048 
0049 #ifdef CONFIG_PPC_PSERIES
0050 struct nvram_os_partition rtas_log_partition = {
0051     .name = "ibm,rtas-log",
0052     .req_size = 2079,
0053     .min_size = 1055,
0054     .index = -1,
0055     .os_partition = true
0056 };
0057 #endif
0058 
0059 struct nvram_os_partition oops_log_partition = {
0060     .name = "lnx,oops-log",
0061     .req_size = 4000,
0062     .min_size = 2000,
0063     .index = -1,
0064     .os_partition = true
0065 };
0066 
0067 static const char *nvram_os_partitions[] = {
0068 #ifdef CONFIG_PPC_PSERIES
0069     "ibm,rtas-log",
0070 #endif
0071     "lnx,oops-log",
0072     NULL
0073 };
0074 
0075 static void oops_to_nvram(struct kmsg_dumper *dumper,
0076               enum kmsg_dump_reason reason);
0077 
0078 static struct kmsg_dumper nvram_kmsg_dumper = {
0079     .dump = oops_to_nvram
0080 };
0081 
0082 /*
0083  * For capturing and compressing an oops or panic report...
0084 
0085  * big_oops_buf[] holds the uncompressed text we're capturing.
0086  *
0087  * oops_buf[] holds the compressed text, preceded by a oops header.
0088  * oops header has u16 holding the version of oops header (to differentiate
0089  * between old and new format header) followed by u16 holding the length of
0090  * the compressed* text (*Or uncompressed, if compression fails.) and u64
0091  * holding the timestamp. oops_buf[] gets written to NVRAM.
0092  *
0093  * oops_log_info points to the header. oops_data points to the compressed text.
0094  *
0095  * +- oops_buf
0096  * |                                   +- oops_data
0097  * v                                   v
0098  * +-----------+-----------+-----------+------------------------+
0099  * | version   | length    | timestamp | text                   |
0100  * | (2 bytes) | (2 bytes) | (8 bytes) | (oops_data_sz bytes)   |
0101  * +-----------+-----------+-----------+------------------------+
0102  * ^
0103  * +- oops_log_info
0104  *
0105  * We preallocate these buffers during init to avoid kmalloc during oops/panic.
0106  */
0107 static size_t big_oops_buf_sz;
0108 static char *big_oops_buf, *oops_buf;
0109 static char *oops_data;
0110 static size_t oops_data_sz;
0111 
0112 /* Compression parameters */
0113 #define COMPR_LEVEL 6
0114 #define WINDOW_BITS 12
0115 #define MEM_LEVEL 4
0116 static struct z_stream_s stream;
0117 
0118 #ifdef CONFIG_PSTORE
0119 #ifdef CONFIG_PPC_POWERNV
0120 static struct nvram_os_partition skiboot_partition = {
0121     .name = "ibm,skiboot",
0122     .index = -1,
0123     .os_partition = false
0124 };
0125 #endif
0126 
0127 #ifdef CONFIG_PPC_PSERIES
0128 static struct nvram_os_partition of_config_partition = {
0129     .name = "of-config",
0130     .index = -1,
0131     .os_partition = false
0132 };
0133 #endif
0134 
0135 static struct nvram_os_partition common_partition = {
0136     .name = "common",
0137     .index = -1,
0138     .os_partition = false
0139 };
0140 
0141 static enum pstore_type_id nvram_type_ids[] = {
0142     PSTORE_TYPE_DMESG,
0143     PSTORE_TYPE_PPC_COMMON,
0144     -1,
0145     -1,
0146     -1
0147 };
0148 static int read_type;
0149 #endif
0150 
0151 /* nvram_write_os_partition
0152  *
0153  * We need to buffer the error logs into nvram to ensure that we have
0154  * the failure information to decode.  If we have a severe error there
0155  * is no way to guarantee that the OS or the machine is in a state to
0156  * get back to user land and write the error to disk.  For example if
0157  * the SCSI device driver causes a Machine Check by writing to a bad
0158  * IO address, there is no way of guaranteeing that the device driver
0159  * is in any state that is would also be able to write the error data
0160  * captured to disk, thus we buffer it in NVRAM for analysis on the
0161  * next boot.
0162  *
0163  * In NVRAM the partition containing the error log buffer will looks like:
0164  * Header (in bytes):
0165  * +-----------+----------+--------+------------+------------------+
0166  * | signature | checksum | length | name       | data             |
0167  * |0          |1         |2      3|4         15|16        length-1|
0168  * +-----------+----------+--------+------------+------------------+
0169  *
0170  * The 'data' section would look like (in bytes):
0171  * +--------------+------------+-----------------------------------+
0172  * | event_logged | sequence # | error log                         |
0173  * |0            3|4          7|8                  error_log_size-1|
0174  * +--------------+------------+-----------------------------------+
0175  *
0176  * event_logged: 0 if event has not been logged to syslog, 1 if it has
0177  * sequence #: The unique sequence # for each event. (until it wraps)
0178  * error log: The error log from event_scan
0179  */
0180 int nvram_write_os_partition(struct nvram_os_partition *part,
0181                  char *buff, int length,
0182                  unsigned int err_type,
0183                  unsigned int error_log_cnt)
0184 {
0185     int rc;
0186     loff_t tmp_index;
0187     struct err_log_info info;
0188 
0189     if (part->index == -1)
0190         return -ESPIPE;
0191 
0192     if (length > part->size)
0193         length = part->size;
0194 
0195     info.error_type = cpu_to_be32(err_type);
0196     info.seq_num = cpu_to_be32(error_log_cnt);
0197 
0198     tmp_index = part->index;
0199 
0200     rc = ppc_md.nvram_write((char *)&info, sizeof(info), &tmp_index);
0201     if (rc <= 0) {
0202         pr_err("%s: Failed nvram_write (%d)\n", __func__, rc);
0203         return rc;
0204     }
0205 
0206     rc = ppc_md.nvram_write(buff, length, &tmp_index);
0207     if (rc <= 0) {
0208         pr_err("%s: Failed nvram_write (%d)\n", __func__, rc);
0209         return rc;
0210     }
0211 
0212     return 0;
0213 }
0214 
0215 /* nvram_read_partition
0216  *
0217  * Reads nvram partition for at most 'length'
0218  */
0219 int nvram_read_partition(struct nvram_os_partition *part, char *buff,
0220              int length, unsigned int *err_type,
0221              unsigned int *error_log_cnt)
0222 {
0223     int rc;
0224     loff_t tmp_index;
0225     struct err_log_info info;
0226 
0227     if (part->index == -1)
0228         return -1;
0229 
0230     if (length > part->size)
0231         length = part->size;
0232 
0233     tmp_index = part->index;
0234 
0235     if (part->os_partition) {
0236         rc = ppc_md.nvram_read((char *)&info, sizeof(info), &tmp_index);
0237         if (rc <= 0) {
0238             pr_err("%s: Failed nvram_read (%d)\n", __func__, rc);
0239             return rc;
0240         }
0241     }
0242 
0243     rc = ppc_md.nvram_read(buff, length, &tmp_index);
0244     if (rc <= 0) {
0245         pr_err("%s: Failed nvram_read (%d)\n", __func__, rc);
0246         return rc;
0247     }
0248 
0249     if (part->os_partition) {
0250         *error_log_cnt = be32_to_cpu(info.seq_num);
0251         *err_type = be32_to_cpu(info.error_type);
0252     }
0253 
0254     return 0;
0255 }
0256 
0257 /* nvram_init_os_partition
0258  *
0259  * This sets up a partition with an "OS" signature.
0260  *
0261  * The general strategy is the following:
0262  * 1.) If a partition with the indicated name already exists...
0263  *  - If it's large enough, use it.
0264  *  - Otherwise, recycle it and keep going.
0265  * 2.) Search for a free partition that is large enough.
0266  * 3.) If there's not a free partition large enough, recycle any obsolete
0267  * OS partitions and try again.
0268  * 4.) Will first try getting a chunk that will satisfy the requested size.
0269  * 5.) If a chunk of the requested size cannot be allocated, then try finding
0270  * a chunk that will satisfy the minum needed.
0271  *
0272  * Returns 0 on success, else -1.
0273  */
0274 int __init nvram_init_os_partition(struct nvram_os_partition *part)
0275 {
0276     loff_t p;
0277     int size;
0278 
0279     /* Look for ours */
0280     p = nvram_find_partition(part->name, NVRAM_SIG_OS, &size);
0281 
0282     /* Found one but too small, remove it */
0283     if (p && size < part->min_size) {
0284         pr_info("nvram: Found too small %s partition,"
0285                     " removing it...\n", part->name);
0286         nvram_remove_partition(part->name, NVRAM_SIG_OS, NULL);
0287         p = 0;
0288     }
0289 
0290     /* Create one if we didn't find */
0291     if (!p) {
0292         p = nvram_create_partition(part->name, NVRAM_SIG_OS,
0293                     part->req_size, part->min_size);
0294         if (p == -ENOSPC) {
0295             pr_info("nvram: No room to create %s partition, "
0296                 "deleting any obsolete OS partitions...\n",
0297                 part->name);
0298             nvram_remove_partition(NULL, NVRAM_SIG_OS,
0299                     nvram_os_partitions);
0300             p = nvram_create_partition(part->name, NVRAM_SIG_OS,
0301                     part->req_size, part->min_size);
0302         }
0303     }
0304 
0305     if (p <= 0) {
0306         pr_err("nvram: Failed to find or create %s"
0307                " partition, err %d\n", part->name, (int)p);
0308         return -1;
0309     }
0310 
0311     part->index = p;
0312     part->size = nvram_get_partition_size(p) - sizeof(struct err_log_info);
0313 
0314     return 0;
0315 }
0316 
0317 /* Derived from logfs_compress() */
0318 static int nvram_compress(const void *in, void *out, size_t inlen,
0319                             size_t outlen)
0320 {
0321     int err, ret;
0322 
0323     ret = -EIO;
0324     err = zlib_deflateInit2(&stream, COMPR_LEVEL, Z_DEFLATED, WINDOW_BITS,
0325                         MEM_LEVEL, Z_DEFAULT_STRATEGY);
0326     if (err != Z_OK)
0327         goto error;
0328 
0329     stream.next_in = in;
0330     stream.avail_in = inlen;
0331     stream.total_in = 0;
0332     stream.next_out = out;
0333     stream.avail_out = outlen;
0334     stream.total_out = 0;
0335 
0336     err = zlib_deflate(&stream, Z_FINISH);
0337     if (err != Z_STREAM_END)
0338         goto error;
0339 
0340     err = zlib_deflateEnd(&stream);
0341     if (err != Z_OK)
0342         goto error;
0343 
0344     if (stream.total_out >= stream.total_in)
0345         goto error;
0346 
0347     ret = stream.total_out;
0348 error:
0349     return ret;
0350 }
0351 
0352 /* Compress the text from big_oops_buf into oops_buf. */
0353 static int zip_oops(size_t text_len)
0354 {
0355     struct oops_log_info *oops_hdr = (struct oops_log_info *)oops_buf;
0356     int zipped_len = nvram_compress(big_oops_buf, oops_data, text_len,
0357                                 oops_data_sz);
0358     if (zipped_len < 0) {
0359         pr_err("nvram: compression failed; returned %d\n", zipped_len);
0360         pr_err("nvram: logging uncompressed oops/panic report\n");
0361         return -1;
0362     }
0363     oops_hdr->version = cpu_to_be16(OOPS_HDR_VERSION);
0364     oops_hdr->report_length = cpu_to_be16(zipped_len);
0365     oops_hdr->timestamp = cpu_to_be64(ktime_get_real_seconds());
0366     return 0;
0367 }
0368 
0369 #ifdef CONFIG_PSTORE
0370 static int nvram_pstore_open(struct pstore_info *psi)
0371 {
0372     /* Reset the iterator to start reading partitions again */
0373     read_type = -1;
0374     return 0;
0375 }
0376 
0377 /**
0378  * nvram_pstore_write - pstore write callback for nvram
0379  * @record:             pstore record to write, with @id to be set
0380  *
0381  * Called by pstore_dump() when an oops or panic report is logged in the
0382  * printk buffer.
0383  * Returns 0 on successful write.
0384  */
0385 static int nvram_pstore_write(struct pstore_record *record)
0386 {
0387     int rc;
0388     unsigned int err_type = ERR_TYPE_KERNEL_PANIC;
0389     struct oops_log_info *oops_hdr = (struct oops_log_info *) oops_buf;
0390 
0391     /* part 1 has the recent messages from printk buffer */
0392     if (record->part > 1 || (record->type != PSTORE_TYPE_DMESG))
0393         return -1;
0394 
0395     if (clobbering_unread_rtas_event())
0396         return -1;
0397 
0398     oops_hdr->version = cpu_to_be16(OOPS_HDR_VERSION);
0399     oops_hdr->report_length = cpu_to_be16(record->size);
0400     oops_hdr->timestamp = cpu_to_be64(ktime_get_real_seconds());
0401 
0402     if (record->compressed)
0403         err_type = ERR_TYPE_KERNEL_PANIC_GZ;
0404 
0405     rc = nvram_write_os_partition(&oops_log_partition, oops_buf,
0406         (int) (sizeof(*oops_hdr) + record->size), err_type,
0407         record->count);
0408 
0409     if (rc != 0)
0410         return rc;
0411 
0412     record->id = record->part;
0413     return 0;
0414 }
0415 
0416 /*
0417  * Reads the oops/panic report, rtas, of-config and common partition.
0418  * Returns the length of the data we read from each partition.
0419  * Returns 0 if we've been called before.
0420  */
0421 static ssize_t nvram_pstore_read(struct pstore_record *record)
0422 {
0423     struct oops_log_info *oops_hdr;
0424     unsigned int err_type, id_no, size = 0;
0425     struct nvram_os_partition *part = NULL;
0426     char *buff = NULL;
0427     int sig = 0;
0428     loff_t p;
0429 
0430     read_type++;
0431 
0432     switch (nvram_type_ids[read_type]) {
0433     case PSTORE_TYPE_DMESG:
0434         part = &oops_log_partition;
0435         record->type = PSTORE_TYPE_DMESG;
0436         break;
0437     case PSTORE_TYPE_PPC_COMMON:
0438         sig = NVRAM_SIG_SYS;
0439         part = &common_partition;
0440         record->type = PSTORE_TYPE_PPC_COMMON;
0441         record->id = PSTORE_TYPE_PPC_COMMON;
0442         record->time.tv_sec = 0;
0443         record->time.tv_nsec = 0;
0444         break;
0445 #ifdef CONFIG_PPC_PSERIES
0446     case PSTORE_TYPE_PPC_RTAS:
0447         part = &rtas_log_partition;
0448         record->type = PSTORE_TYPE_PPC_RTAS;
0449         record->time.tv_sec = last_rtas_event;
0450         record->time.tv_nsec = 0;
0451         break;
0452     case PSTORE_TYPE_PPC_OF:
0453         sig = NVRAM_SIG_OF;
0454         part = &of_config_partition;
0455         record->type = PSTORE_TYPE_PPC_OF;
0456         record->id = PSTORE_TYPE_PPC_OF;
0457         record->time.tv_sec = 0;
0458         record->time.tv_nsec = 0;
0459         break;
0460 #endif
0461 #ifdef CONFIG_PPC_POWERNV
0462     case PSTORE_TYPE_PPC_OPAL:
0463         sig = NVRAM_SIG_FW;
0464         part = &skiboot_partition;
0465         record->type = PSTORE_TYPE_PPC_OPAL;
0466         record->id = PSTORE_TYPE_PPC_OPAL;
0467         record->time.tv_sec = 0;
0468         record->time.tv_nsec = 0;
0469         break;
0470 #endif
0471     default:
0472         return 0;
0473     }
0474 
0475     if (!part->os_partition) {
0476         p = nvram_find_partition(part->name, sig, &size);
0477         if (p <= 0) {
0478             pr_err("nvram: Failed to find partition %s, "
0479                 "err %d\n", part->name, (int)p);
0480             return 0;
0481         }
0482         part->index = p;
0483         part->size = size;
0484     }
0485 
0486     buff = kmalloc(part->size, GFP_KERNEL);
0487 
0488     if (!buff)
0489         return -ENOMEM;
0490 
0491     if (nvram_read_partition(part, buff, part->size, &err_type, &id_no)) {
0492         kfree(buff);
0493         return 0;
0494     }
0495 
0496     record->count = 0;
0497 
0498     if (part->os_partition)
0499         record->id = id_no;
0500 
0501     if (nvram_type_ids[read_type] == PSTORE_TYPE_DMESG) {
0502         size_t length, hdr_size;
0503 
0504         oops_hdr = (struct oops_log_info *)buff;
0505         if (be16_to_cpu(oops_hdr->version) < OOPS_HDR_VERSION) {
0506             /* Old format oops header had 2-byte record size */
0507             hdr_size = sizeof(u16);
0508             length = be16_to_cpu(oops_hdr->version);
0509             record->time.tv_sec = 0;
0510             record->time.tv_nsec = 0;
0511         } else {
0512             hdr_size = sizeof(*oops_hdr);
0513             length = be16_to_cpu(oops_hdr->report_length);
0514             record->time.tv_sec = be64_to_cpu(oops_hdr->timestamp);
0515             record->time.tv_nsec = 0;
0516         }
0517         record->buf = kmemdup(buff + hdr_size, length, GFP_KERNEL);
0518         kfree(buff);
0519         if (record->buf == NULL)
0520             return -ENOMEM;
0521 
0522         record->ecc_notice_size = 0;
0523         if (err_type == ERR_TYPE_KERNEL_PANIC_GZ)
0524             record->compressed = true;
0525         else
0526             record->compressed = false;
0527         return length;
0528     }
0529 
0530     record->buf = buff;
0531     return part->size;
0532 }
0533 
0534 static struct pstore_info nvram_pstore_info = {
0535     .owner = THIS_MODULE,
0536     .name = "nvram",
0537     .flags = PSTORE_FLAGS_DMESG,
0538     .open = nvram_pstore_open,
0539     .read = nvram_pstore_read,
0540     .write = nvram_pstore_write,
0541 };
0542 
0543 static int __init nvram_pstore_init(void)
0544 {
0545     int rc = 0;
0546 
0547     if (machine_is(pseries)) {
0548         nvram_type_ids[2] = PSTORE_TYPE_PPC_RTAS;
0549         nvram_type_ids[3] = PSTORE_TYPE_PPC_OF;
0550     } else
0551         nvram_type_ids[2] = PSTORE_TYPE_PPC_OPAL;
0552 
0553     nvram_pstore_info.buf = oops_data;
0554     nvram_pstore_info.bufsize = oops_data_sz;
0555 
0556     rc = pstore_register(&nvram_pstore_info);
0557     if (rc && (rc != -EPERM))
0558         /* Print error only when pstore.backend == nvram */
0559         pr_err("nvram: pstore_register() failed, returned %d. "
0560                 "Defaults to kmsg_dump\n", rc);
0561 
0562     return rc;
0563 }
0564 #else
0565 static int __init nvram_pstore_init(void)
0566 {
0567     return -1;
0568 }
0569 #endif
0570 
0571 void __init nvram_init_oops_partition(int rtas_partition_exists)
0572 {
0573     int rc;
0574 
0575     rc = nvram_init_os_partition(&oops_log_partition);
0576     if (rc != 0) {
0577 #ifdef CONFIG_PPC_PSERIES
0578         if (!rtas_partition_exists) {
0579             pr_err("nvram: Failed to initialize oops partition!");
0580             return;
0581         }
0582         pr_notice("nvram: Using %s partition to log both"
0583             " RTAS errors and oops/panic reports\n",
0584             rtas_log_partition.name);
0585         memcpy(&oops_log_partition, &rtas_log_partition,
0586                         sizeof(rtas_log_partition));
0587 #else
0588         pr_err("nvram: Failed to initialize oops partition!");
0589         return;
0590 #endif
0591     }
0592     oops_buf = kmalloc(oops_log_partition.size, GFP_KERNEL);
0593     if (!oops_buf) {
0594         pr_err("nvram: No memory for %s partition\n",
0595                         oops_log_partition.name);
0596         return;
0597     }
0598     oops_data = oops_buf + sizeof(struct oops_log_info);
0599     oops_data_sz = oops_log_partition.size - sizeof(struct oops_log_info);
0600 
0601     rc = nvram_pstore_init();
0602 
0603     if (!rc)
0604         return;
0605 
0606     /*
0607      * Figure compression (preceded by elimination of each line's <n>
0608      * severity prefix) will reduce the oops/panic report to at most
0609      * 45% of its original size.
0610      */
0611     big_oops_buf_sz = (oops_data_sz * 100) / 45;
0612     big_oops_buf = kmalloc(big_oops_buf_sz, GFP_KERNEL);
0613     if (big_oops_buf) {
0614         stream.workspace =  kmalloc(zlib_deflate_workspacesize(
0615                     WINDOW_BITS, MEM_LEVEL), GFP_KERNEL);
0616         if (!stream.workspace) {
0617             pr_err("nvram: No memory for compression workspace; "
0618                 "skipping compression of %s partition data\n",
0619                 oops_log_partition.name);
0620             kfree(big_oops_buf);
0621             big_oops_buf = NULL;
0622         }
0623     } else {
0624         pr_err("No memory for uncompressed %s data; "
0625             "skipping compression\n", oops_log_partition.name);
0626         stream.workspace = NULL;
0627     }
0628 
0629     rc = kmsg_dump_register(&nvram_kmsg_dumper);
0630     if (rc != 0) {
0631         pr_err("nvram: kmsg_dump_register() failed; returned %d\n", rc);
0632         kfree(oops_buf);
0633         kfree(big_oops_buf);
0634         kfree(stream.workspace);
0635     }
0636 }
0637 
0638 /*
0639  * This is our kmsg_dump callback, called after an oops or panic report
0640  * has been written to the printk buffer.  We want to capture as much
0641  * of the printk buffer as possible.  First, capture as much as we can
0642  * that we think will compress sufficiently to fit in the lnx,oops-log
0643  * partition.  If that's too much, go back and capture uncompressed text.
0644  */
0645 static void oops_to_nvram(struct kmsg_dumper *dumper,
0646               enum kmsg_dump_reason reason)
0647 {
0648     struct oops_log_info *oops_hdr = (struct oops_log_info *)oops_buf;
0649     static unsigned int oops_count = 0;
0650     static struct kmsg_dump_iter iter;
0651     static bool panicking = false;
0652     static DEFINE_SPINLOCK(lock);
0653     unsigned long flags;
0654     size_t text_len;
0655     unsigned int err_type = ERR_TYPE_KERNEL_PANIC_GZ;
0656     int rc = -1;
0657 
0658     switch (reason) {
0659     case KMSG_DUMP_SHUTDOWN:
0660         /* These are almost always orderly shutdowns. */
0661         return;
0662     case KMSG_DUMP_OOPS:
0663         break;
0664     case KMSG_DUMP_PANIC:
0665         panicking = true;
0666         break;
0667     case KMSG_DUMP_EMERG:
0668         if (panicking)
0669             /* Panic report already captured. */
0670             return;
0671         break;
0672     default:
0673         pr_err("%s: ignoring unrecognized KMSG_DUMP_* reason %d\n",
0674                __func__, (int) reason);
0675         return;
0676     }
0677 
0678     if (clobbering_unread_rtas_event())
0679         return;
0680 
0681     if (!spin_trylock_irqsave(&lock, flags))
0682         return;
0683 
0684     if (big_oops_buf) {
0685         kmsg_dump_rewind(&iter);
0686         kmsg_dump_get_buffer(&iter, false,
0687                      big_oops_buf, big_oops_buf_sz, &text_len);
0688         rc = zip_oops(text_len);
0689     }
0690     if (rc != 0) {
0691         kmsg_dump_rewind(&iter);
0692         kmsg_dump_get_buffer(&iter, false,
0693                      oops_data, oops_data_sz, &text_len);
0694         err_type = ERR_TYPE_KERNEL_PANIC;
0695         oops_hdr->version = cpu_to_be16(OOPS_HDR_VERSION);
0696         oops_hdr->report_length = cpu_to_be16(text_len);
0697         oops_hdr->timestamp = cpu_to_be64(ktime_get_real_seconds());
0698     }
0699 
0700     (void) nvram_write_os_partition(&oops_log_partition, oops_buf,
0701         (int) (sizeof(*oops_hdr) + text_len), err_type,
0702         ++oops_count);
0703 
0704     spin_unlock_irqrestore(&lock, flags);
0705 }
0706 
0707 #ifdef DEBUG_NVRAM
0708 static void __init nvram_print_partitions(char * label)
0709 {
0710     struct nvram_partition * tmp_part;
0711     
0712     printk(KERN_WARNING "--------%s---------\n", label);
0713     printk(KERN_WARNING "indx\t\tsig\tchks\tlen\tname\n");
0714     list_for_each_entry(tmp_part, &nvram_partitions, partition) {
0715         printk(KERN_WARNING "%4d    \t%02x\t%02x\t%d\t%12.12s\n",
0716                tmp_part->index, tmp_part->header.signature,
0717                tmp_part->header.checksum, tmp_part->header.length,
0718                tmp_part->header.name);
0719     }
0720 }
0721 #endif
0722 
0723 
0724 static int __init nvram_write_header(struct nvram_partition * part)
0725 {
0726     loff_t tmp_index;
0727     int rc;
0728     struct nvram_header phead;
0729 
0730     memcpy(&phead, &part->header, NVRAM_HEADER_LEN);
0731     phead.length = cpu_to_be16(phead.length);
0732 
0733     tmp_index = part->index;
0734     rc = ppc_md.nvram_write((char *)&phead, NVRAM_HEADER_LEN, &tmp_index);
0735 
0736     return rc;
0737 }
0738 
0739 
0740 static unsigned char __init nvram_checksum(struct nvram_header *p)
0741 {
0742     unsigned int c_sum, c_sum2;
0743     unsigned short *sp = (unsigned short *)p->name; /* assume 6 shorts */
0744     c_sum = p->signature + p->length + sp[0] + sp[1] + sp[2] + sp[3] + sp[4] + sp[5];
0745 
0746     /* The sum may have spilled into the 3rd byte.  Fold it back. */
0747     c_sum = ((c_sum & 0xffff) + (c_sum >> 16)) & 0xffff;
0748     /* The sum cannot exceed 2 bytes.  Fold it into a checksum */
0749     c_sum2 = (c_sum >> 8) + (c_sum << 8);
0750     c_sum = ((c_sum + c_sum2) >> 8) & 0xff;
0751     return c_sum;
0752 }
0753 
0754 /*
0755  * Per the criteria passed via nvram_remove_partition(), should this
0756  * partition be removed?  1=remove, 0=keep
0757  */
0758 static int __init nvram_can_remove_partition(struct nvram_partition *part,
0759         const char *name, int sig, const char *exceptions[])
0760 {
0761     if (part->header.signature != sig)
0762         return 0;
0763     if (name) {
0764         if (strncmp(name, part->header.name, 12))
0765             return 0;
0766     } else if (exceptions) {
0767         const char **except;
0768         for (except = exceptions; *except; except++) {
0769             if (!strncmp(*except, part->header.name, 12))
0770                 return 0;
0771         }
0772     }
0773     return 1;
0774 }
0775 
0776 /**
0777  * nvram_remove_partition - Remove one or more partitions in nvram
0778  * @name: name of the partition to remove, or NULL for a
0779  *        signature only match
0780  * @sig: signature of the partition(s) to remove
0781  * @exceptions: When removing all partitions with a matching signature,
0782  *        leave these alone.
0783  */
0784 
0785 int __init nvram_remove_partition(const char *name, int sig,
0786                         const char *exceptions[])
0787 {
0788     struct nvram_partition *part, *prev, *tmp;
0789     int rc;
0790 
0791     list_for_each_entry(part, &nvram_partitions, partition) {
0792         if (!nvram_can_remove_partition(part, name, sig, exceptions))
0793             continue;
0794 
0795         /* Make partition a free partition */
0796         part->header.signature = NVRAM_SIG_FREE;
0797         memset(part->header.name, 'w', 12);
0798         part->header.checksum = nvram_checksum(&part->header);
0799         rc = nvram_write_header(part);
0800         if (rc <= 0) {
0801             printk(KERN_ERR "nvram_remove_partition: nvram_write failed (%d)\n", rc);
0802             return rc;
0803         }
0804     }
0805 
0806     /* Merge contiguous ones */
0807     prev = NULL;
0808     list_for_each_entry_safe(part, tmp, &nvram_partitions, partition) {
0809         if (part->header.signature != NVRAM_SIG_FREE) {
0810             prev = NULL;
0811             continue;
0812         }
0813         if (prev) {
0814             prev->header.length += part->header.length;
0815             prev->header.checksum = nvram_checksum(&prev->header);
0816             rc = nvram_write_header(prev);
0817             if (rc <= 0) {
0818                 printk(KERN_ERR "nvram_remove_partition: nvram_write failed (%d)\n", rc);
0819                 return rc;
0820             }
0821             list_del(&part->partition);
0822             kfree(part);
0823         } else
0824             prev = part;
0825     }
0826     
0827     return 0;
0828 }
0829 
0830 /**
0831  * nvram_create_partition - Create a partition in nvram
0832  * @name: name of the partition to create
0833  * @sig: signature of the partition to create
0834  * @req_size: size of data to allocate in bytes
0835  * @min_size: minimum acceptable size (0 means req_size)
0836  *
0837  * Returns a negative error code or a positive nvram index
0838  * of the beginning of the data area of the newly created
0839  * partition. If you provided a min_size smaller than req_size
0840  * you need to query for the actual size yourself after the
0841  * call using nvram_partition_get_size().
0842  */
0843 loff_t __init nvram_create_partition(const char *name, int sig,
0844                      int req_size, int min_size)
0845 {
0846     struct nvram_partition *part;
0847     struct nvram_partition *new_part;
0848     struct nvram_partition *free_part = NULL;
0849     static char nv_init_vals[16];
0850     loff_t tmp_index;
0851     long size = 0;
0852     int rc;
0853 
0854     BUILD_BUG_ON(NVRAM_BLOCK_LEN != 16);
0855 
0856     /* Convert sizes from bytes to blocks */
0857     req_size = ALIGN(req_size, NVRAM_BLOCK_LEN) / NVRAM_BLOCK_LEN;
0858     min_size = ALIGN(min_size, NVRAM_BLOCK_LEN) / NVRAM_BLOCK_LEN;
0859 
0860     /* If no minimum size specified, make it the same as the
0861      * requested size
0862      */
0863     if (min_size == 0)
0864         min_size = req_size;
0865     if (min_size > req_size)
0866         return -EINVAL;
0867 
0868     /* Now add one block to each for the header */
0869     req_size += 1;
0870     min_size += 1;
0871 
0872     /* Find a free partition that will give us the maximum needed size 
0873        If can't find one that will give us the minimum size needed */
0874     list_for_each_entry(part, &nvram_partitions, partition) {
0875         if (part->header.signature != NVRAM_SIG_FREE)
0876             continue;
0877 
0878         if (part->header.length >= req_size) {
0879             size = req_size;
0880             free_part = part;
0881             break;
0882         }
0883         if (part->header.length > size &&
0884             part->header.length >= min_size) {
0885             size = part->header.length;
0886             free_part = part;
0887         }
0888     }
0889     if (!size)
0890         return -ENOSPC;
0891     
0892     /* Create our OS partition */
0893     new_part = kzalloc(sizeof(*new_part), GFP_KERNEL);
0894     if (!new_part) {
0895         pr_err("%s: kmalloc failed\n", __func__);
0896         return -ENOMEM;
0897     }
0898 
0899     new_part->index = free_part->index;
0900     new_part->header.signature = sig;
0901     new_part->header.length = size;
0902     memcpy(new_part->header.name, name, strnlen(name, sizeof(new_part->header.name)));
0903     new_part->header.checksum = nvram_checksum(&new_part->header);
0904 
0905     rc = nvram_write_header(new_part);
0906     if (rc <= 0) {
0907         pr_err("%s: nvram_write_header failed (%d)\n", __func__, rc);
0908         kfree(new_part);
0909         return rc;
0910     }
0911     list_add_tail(&new_part->partition, &free_part->partition);
0912 
0913     /* Adjust or remove the partition we stole the space from */
0914     if (free_part->header.length > size) {
0915         free_part->index += size * NVRAM_BLOCK_LEN;
0916         free_part->header.length -= size;
0917         free_part->header.checksum = nvram_checksum(&free_part->header);
0918         rc = nvram_write_header(free_part);
0919         if (rc <= 0) {
0920             pr_err("%s: nvram_write_header failed (%d)\n",
0921                    __func__, rc);
0922             return rc;
0923         }
0924     } else {
0925         list_del(&free_part->partition);
0926         kfree(free_part);
0927     } 
0928 
0929     /* Clear the new partition */
0930     for (tmp_index = new_part->index + NVRAM_HEADER_LEN;
0931          tmp_index <  ((size - 1) * NVRAM_BLOCK_LEN);
0932          tmp_index += NVRAM_BLOCK_LEN) {
0933         rc = ppc_md.nvram_write(nv_init_vals, NVRAM_BLOCK_LEN, &tmp_index);
0934         if (rc <= 0) {
0935             pr_err("%s: nvram_write failed (%d)\n",
0936                    __func__, rc);
0937             return rc;
0938         }
0939     }
0940 
0941     return new_part->index + NVRAM_HEADER_LEN;
0942 }
0943 
0944 /**
0945  * nvram_get_partition_size - Get the data size of an nvram partition
0946  * @data_index: This is the offset of the start of the data of
0947  *              the partition. The same value that is returned by
0948  *              nvram_create_partition().
0949  */
0950 int nvram_get_partition_size(loff_t data_index)
0951 {
0952     struct nvram_partition *part;
0953     
0954     list_for_each_entry(part, &nvram_partitions, partition) {
0955         if (part->index + NVRAM_HEADER_LEN == data_index)
0956             return (part->header.length - 1) * NVRAM_BLOCK_LEN;
0957     }
0958     return -1;
0959 }
0960 
0961 
0962 /**
0963  * nvram_find_partition - Find an nvram partition by signature and name
0964  * @name: Name of the partition or NULL for any name
0965  * @sig: Signature to test against
0966  * @out_size: if non-NULL, returns the size of the data part of the partition
0967  */
0968 loff_t nvram_find_partition(const char *name, int sig, int *out_size)
0969 {
0970     struct nvram_partition *p;
0971 
0972     list_for_each_entry(p, &nvram_partitions, partition) {
0973         if (p->header.signature == sig &&
0974             (!name || !strncmp(p->header.name, name, 12))) {
0975             if (out_size)
0976                 *out_size = (p->header.length - 1) *
0977                     NVRAM_BLOCK_LEN;
0978             return p->index + NVRAM_HEADER_LEN;
0979         }
0980     }
0981     return 0;
0982 }
0983 
0984 int __init nvram_scan_partitions(void)
0985 {
0986     loff_t cur_index = 0;
0987     struct nvram_header phead;
0988     struct nvram_partition * tmp_part;
0989     unsigned char c_sum;
0990     char * header;
0991     int total_size;
0992     int err;
0993 
0994     if (ppc_md.nvram_size == NULL || ppc_md.nvram_size() <= 0)
0995         return -ENODEV;
0996     total_size = ppc_md.nvram_size();
0997     
0998     header = kmalloc(NVRAM_HEADER_LEN, GFP_KERNEL);
0999     if (!header) {
1000         printk(KERN_ERR "nvram_scan_partitions: Failed kmalloc\n");
1001         return -ENOMEM;
1002     }
1003 
1004     while (cur_index < total_size) {
1005 
1006         err = ppc_md.nvram_read(header, NVRAM_HEADER_LEN, &cur_index);
1007         if (err != NVRAM_HEADER_LEN) {
1008             printk(KERN_ERR "nvram_scan_partitions: Error parsing "
1009                    "nvram partitions\n");
1010             goto out;
1011         }
1012 
1013         cur_index -= NVRAM_HEADER_LEN; /* nvram_read will advance us */
1014 
1015         memcpy(&phead, header, NVRAM_HEADER_LEN);
1016 
1017         phead.length = be16_to_cpu(phead.length);
1018 
1019         err = 0;
1020         c_sum = nvram_checksum(&phead);
1021         if (c_sum != phead.checksum) {
1022             printk(KERN_WARNING "WARNING: nvram partition checksum"
1023                    " was %02x, should be %02x!\n",
1024                    phead.checksum, c_sum);
1025             printk(KERN_WARNING "Terminating nvram partition scan\n");
1026             goto out;
1027         }
1028         if (!phead.length) {
1029             printk(KERN_WARNING "WARNING: nvram corruption "
1030                    "detected: 0-length partition\n");
1031             goto out;
1032         }
1033         tmp_part = kmalloc(sizeof(*tmp_part), GFP_KERNEL);
1034         err = -ENOMEM;
1035         if (!tmp_part) {
1036             printk(KERN_ERR "nvram_scan_partitions: kmalloc failed\n");
1037             goto out;
1038         }
1039         
1040         memcpy(&tmp_part->header, &phead, NVRAM_HEADER_LEN);
1041         tmp_part->index = cur_index;
1042         list_add_tail(&tmp_part->partition, &nvram_partitions);
1043         
1044         cur_index += phead.length * NVRAM_BLOCK_LEN;
1045     }
1046     err = 0;
1047 
1048 #ifdef DEBUG_NVRAM
1049     nvram_print_partitions("NVRAM Partitions");
1050 #endif
1051 
1052  out:
1053     kfree(header);
1054     return err;
1055 }