void* ipanic_next_write(void* (*next)(void *data, unsigned char *buffer, size_t sz_buf, int *size), void *data, int off, size_t *sz_total) { void* errno = 0; size_t size = 0; unsigned char *ipanic_buffer = emmc_bounce; size_t sz_ipanic_buffer = PAGE_SIZE; errno = next(data, ipanic_buffer, sz_ipanic_buffer, &size); if (IS_ERR(errno)) return errno; for (*sz_total = 0; size != 0; *sz_total += size) { if (off & (EMMC_BLOCK_SIZE - 1)) return ERR_PTR(-2); /*invalid offset, not block aligned*/ ipanic_block_scramble(ipanic_buffer, size); if (size != sz_ipanic_buffer) { memset(ipanic_buffer + size, 0, sz_ipanic_buffer - size); } if (card_dump_func_write(ipanic_buffer, ALIGN(size, EMMC_BLOCK_SIZE), off, DUMP_INTO_BOOT_CARD_IPANIC)) return ERR_PTR(-1); off += size; errno = next(data, ipanic_buffer, sz_ipanic_buffer, &size); if (IS_ERR(errno)) return errno; } return 0; }
static int emmc_ipanic_write(void *buf, int off, int len) { int rem = len & (EMMC_BLOCK_SIZE - 1); len = len & ~(EMMC_BLOCK_SIZE - 1); ipanic_block_scramble(buf, len + rem); if (len > 0) { if (card_dump_func_write((unsigned char *)buf, len, off, EMMC_ID)) return -1; } if (rem != 0) { memcpy(emmc_bounce, buf + len, rem); memset(emmc_bounce + rem, 0, EMMC_BLOCK_SIZE - rem); if (card_dump_func_write(buf, EMMC_BLOCK_SIZE, off + len, EMMC_ID)) return -1; } return len + rem; }
int ipanic_write_size(void *buf, int off, int len) { if (len & (EMMC_BLOCK_SIZE - 1)) return -2; if (len > 0) { if (card_dump_func_write ((unsigned char *)buf, len, off, DUMP_INTO_BOOT_CARD_IPANIC)) return -1; } return len; }
void last_kmsg_store_to_emmc(void) { int buff_size; struct wd_api*wd_api = NULL; get_wd_api(&wd_api); // if(num_online_cpus() > 1){ if(wd_api->wd_get_check_bit() > 1){ printk(KERN_ERR"ram_console: online cpu %d!\n",wd_api->wd_get_check_bit()); if(boot_finish == 0) return; } /* save log to emmc */ buff_size = ram_console_buffer->sz_buffer; card_dump_func_write((unsigned char *)ram_console_buffer, buff_size, EMMC_ADDR, DUMP_INTO_BOOT_CARD_IPANIC); pr_err("ram_console: save kernel log (0x%x) to emmc!\n", buff_size); }
static int ipanic_write_android_buf(unsigned int off, int type) { unsigned int copy_count = 0; while (1) { int rc = panic_dump_android_log(emmc_bounce, PAGE_SIZE, type); BUG_ON(rc < 0); if (rc <= 0) break; if (rc < PAGE_SIZE) { memset(emmc_bounce + rc, 0, PAGE_SIZE - rc); } ipanic_block_scramble(emmc_bounce, PAGE_SIZE); if (card_dump_func_write(emmc_bounce, PAGE_SIZE, off, EMMC_ID)) { xlog_printk(ANDROID_LOG_ERROR, IPANIC_LOG_TAG, "aee-ipanic-emmc(%s): android log %d write failed, offset %d\n", __FUNCTION__, type, off); return -1; } copy_count += rc; off += PAGE_SIZE; } xlog_printk(ANDROID_LOG_DEBUG, IPANIC_LOG_TAG, "%s: dump droid log type %d, count %d\n", __FUNCTION__, type, copy_count); return copy_count; }