ipanic_pstore.c 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126
  1. #include <linux/kernel.h>
  2. #include <linux/mm.h>
  3. #include <linux/slab.h>
  4. #include <linux/err.h>
  5. #include <linux/pstore_ram.h>
  6. #include <linux/pstore.h>
  7. #include "ipanic.h"
  8. static struct ipanic_header *aee_poweroff_logs;
  9. static unsigned int aee_active_index;
  10. #define AEE_POWEROFF_NR 4
  11. #define AEE_POWEROFF_OFFSET 0x00700000
  12. #define AEE_POWEROFF_MAGIC 0x43474244 /* DBGC */
  13. struct ipanic_data_zone {
  14. struct ipanic_data_header *header;
  15. };
  16. void ipanic_kmsg_hdr(struct ipanic_data_header *hdr, unsigned int id, unsigned int offset)
  17. {
  18. struct timespec timestamp;
  19. hdr->id = id;
  20. hdr->valid = 1;
  21. hdr->offset = offset;
  22. hdr->total = __LOG_BUF_LEN;
  23. hdr->encrypt = 0;
  24. if (__getnstimeofday(&timestamp)) {
  25. timestamp.tv_sec = 0;
  26. timestamp.tv_nsec = 0;
  27. }
  28. snprintf(hdr->name, 32, "kmsg_%lu", (long)timestamp.tv_sec);
  29. }
  30. void ipanic_kmsg_init(void)
  31. {
  32. aee_poweroff_logs = ipanic_header_from_sd(AEE_POWEROFF_OFFSET, AEE_POWEROFF_MAGIC);
  33. if (!aee_poweroff_logs) {
  34. aee_poweroff_logs = kzalloc(sizeof(struct ipanic_header), GFP_KERNEL);
  35. if (ipanic_msdc_info(aee_poweroff_logs)) {
  36. LOGE("aee poweroff logs init msdc fail");
  37. kfree(aee_poweroff_logs);
  38. aee_poweroff_logs = NULL;
  39. return;
  40. }
  41. aee_poweroff_logs->magic = AEE_POWEROFF_MAGIC;
  42. aee_poweroff_logs->size = sizeof(struct ipanic_header);
  43. }
  44. }
  45. void ipanic_kmsg_hdr_write(void)
  46. {
  47. ipanic_mem_write(aee_poweroff_logs, AEE_POWEROFF_OFFSET, sizeof(struct ipanic_header), 0);
  48. }
  49. void ipanic_kmsg_next(void)
  50. {
  51. int i;
  52. struct ipanic_data_header *hdr;
  53. int last_id = 0;
  54. if (!aee_poweroff_logs)
  55. return;
  56. aee_active_index = 0;
  57. for (i = 0; i < AEE_POWEROFF_NR; i++) {
  58. if (aee_poweroff_logs->data_hdr[i].id <
  59. aee_poweroff_logs->data_hdr[aee_active_index].id)
  60. aee_active_index = i;
  61. if (aee_poweroff_logs->data_hdr[i].id > aee_poweroff_logs->data_hdr[last_id].id)
  62. last_id = i;
  63. }
  64. hdr = &aee_poweroff_logs->data_hdr[aee_active_index];
  65. ipanic_kmsg_hdr(hdr, aee_poweroff_logs->data_hdr[last_id].id + 1,
  66. AEE_POWEROFF_OFFSET + ALIGN(sizeof(struct ipanic_header),
  67. aee_poweroff_logs->blksize) +
  68. aee_active_index * __LOG_BUF_LEN);
  69. hdr->used = hdr->total;
  70. ipanic_kmsg_hdr_write();
  71. hdr->used = 0;
  72. }
  73. int ipanic_kmsg_write(unsigned int part, const char *buf, size_t size)
  74. {
  75. struct ipanic_data_header *hdr;
  76. int offset;
  77. if (part == 1)
  78. ipanic_kmsg_next();
  79. hdr = &aee_poweroff_logs->data_hdr[aee_active_index];
  80. offset = hdr->offset + hdr->total - hdr->used - ALIGN(size, aee_poweroff_logs->blksize);
  81. if (offset < hdr->offset)
  82. return -EINVAL;
  83. hdr->used += ALIGN(size, aee_poweroff_logs->blksize);
  84. ipanic_mem_write((void *)buf, offset, size, hdr->encrypt);
  85. return 0;
  86. }
  87. int ipanic_kmsg_get_next(int *count, u64 *id, enum pstore_type_id *type, struct timespec *time,
  88. char **buf, struct pstore_info *psi)
  89. {
  90. char *data;
  91. int i, size = 0;
  92. struct ipanic_data_header *hdr;
  93. if (*count == 0)
  94. ipanic_kmsg_init();
  95. for (i = *count; i < AEE_POWEROFF_NR; i++) {
  96. hdr = &aee_poweroff_logs->data_hdr[i];
  97. if (!hdr->valid)
  98. continue;
  99. data = ipanic_data_from_sd(hdr, 0);
  100. if (data) {
  101. *buf = data;
  102. size = hdr->used;
  103. *type = PSTORE_TYPE_DMESG;
  104. *id = hdr->id;
  105. i++;
  106. break;
  107. }
  108. }
  109. LOGD("ipanic_kmsg_get_next: count %d, buf %p, size %x\n", *count, *buf, size);
  110. *count = i;
  111. return size;
  112. }