Skip to content

Commit 16a5830

Browse files
committed
pstore/ftrace: Provide ftrace log merging routine
Move the ftrace log merging logic out of pstore/ram into pstore/ftrace so other backends can use it, like pstore/zone. Link: https://lore.kernel.org/lkml/[email protected]/ Signed-off-by: Kees Cook <[email protected]>
1 parent df9bf19 commit 16a5830

File tree

3 files changed

+66
-54
lines changed

3 files changed

+66
-54
lines changed

fs/pstore/ftrace.c

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616
#include <linux/debugfs.h>
1717
#include <linux/err.h>
1818
#include <linux/cache.h>
19+
#include <linux/slab.h>
1920
#include <asm/barrier.h>
2021
#include "internal.h"
2122

@@ -132,3 +133,56 @@ void pstore_unregister_ftrace(void)
132133

133134
debugfs_remove_recursive(pstore_ftrace_dir);
134135
}
136+
137+
ssize_t pstore_ftrace_combine_log(char **dest_log, size_t *dest_log_size,
138+
const char *src_log, size_t src_log_size)
139+
{
140+
size_t dest_size, src_size, total, dest_off, src_off;
141+
size_t dest_idx = 0, src_idx = 0, merged_idx = 0;
142+
void *merged_buf;
143+
struct pstore_ftrace_record *drec, *srec, *mrec;
144+
size_t record_size = sizeof(struct pstore_ftrace_record);
145+
146+
dest_off = *dest_log_size % record_size;
147+
dest_size = *dest_log_size - dest_off;
148+
149+
src_off = src_log_size % record_size;
150+
src_size = src_log_size - src_off;
151+
152+
total = dest_size + src_size;
153+
merged_buf = kmalloc(total, GFP_KERNEL);
154+
if (!merged_buf)
155+
return -ENOMEM;
156+
157+
drec = (struct pstore_ftrace_record *)(*dest_log + dest_off);
158+
srec = (struct pstore_ftrace_record *)(src_log + src_off);
159+
mrec = (struct pstore_ftrace_record *)(merged_buf);
160+
161+
while (dest_size > 0 && src_size > 0) {
162+
if (pstore_ftrace_read_timestamp(&drec[dest_idx]) <
163+
pstore_ftrace_read_timestamp(&srec[src_idx])) {
164+
mrec[merged_idx++] = drec[dest_idx++];
165+
dest_size -= record_size;
166+
} else {
167+
mrec[merged_idx++] = srec[src_idx++];
168+
src_size -= record_size;
169+
}
170+
}
171+
172+
while (dest_size > 0) {
173+
mrec[merged_idx++] = drec[dest_idx++];
174+
dest_size -= record_size;
175+
}
176+
177+
while (src_size > 0) {
178+
mrec[merged_idx++] = srec[src_idx++];
179+
src_size -= record_size;
180+
}
181+
182+
kfree(*dest_log);
183+
*dest_log = merged_buf;
184+
*dest_log_size = total;
185+
186+
return 0;
187+
}
188+
EXPORT_SYMBOL_GPL(pstore_ftrace_combine_log);

fs/pstore/internal.h

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,18 @@ extern unsigned long kmsg_bytes;
1212
#ifdef CONFIG_PSTORE_FTRACE
1313
extern void pstore_register_ftrace(void);
1414
extern void pstore_unregister_ftrace(void);
15+
ssize_t pstore_ftrace_combine_log(char **dest_log, size_t *dest_log_size,
16+
const char *src_log, size_t src_log_size);
1517
#else
1618
static inline void pstore_register_ftrace(void) {}
1719
static inline void pstore_unregister_ftrace(void) {}
20+
static inline ssize_t
21+
pstore_ftrace_combine_log(char **dest_log, size_t *dest_log_size,
22+
const char *src_log, size_t src_log_size)
23+
{
24+
*dest_log_size = 0;
25+
return 0;
26+
}
1827
#endif
1928

2029
#ifdef CONFIG_PSTORE_PMSG

fs/pstore/ram.c

Lines changed: 3 additions & 54 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
#include <linux/pstore_ram.h>
2222
#include <linux/of.h>
2323
#include <linux/of_address.h>
24+
#include "internal.h"
2425

2526
#define RAMOOPS_KERNMSG_HDR "===="
2627
#define MIN_MEM_SIZE 4096UL
@@ -168,59 +169,6 @@ static bool prz_ok(struct persistent_ram_zone *prz)
168169
persistent_ram_ecc_string(prz, NULL, 0));
169170
}
170171

171-
static
172-
ssize_t ftrace_log_combine(char **dest_log, size_t *dest_log_size,
173-
const char *src_log, size_t src_log_size)
174-
{
175-
size_t dest_size, src_size, total, dest_off, src_off;
176-
size_t dest_idx = 0, src_idx = 0, merged_idx = 0;
177-
void *merged_buf;
178-
struct pstore_ftrace_record *drec, *srec, *mrec;
179-
size_t record_size = sizeof(struct pstore_ftrace_record);
180-
181-
dest_off = *dest_log_size % record_size;
182-
dest_size = *dest_log_size - dest_off;
183-
184-
src_off = src_log_size % record_size;
185-
src_size = src_log_size - src_off;
186-
187-
total = dest_size + src_size;
188-
merged_buf = kmalloc(total, GFP_KERNEL);
189-
if (!merged_buf)
190-
return -ENOMEM;
191-
192-
drec = (struct pstore_ftrace_record *)(*dest_log + dest_off);
193-
srec = (struct pstore_ftrace_record *)(src_log + src_off);
194-
mrec = (struct pstore_ftrace_record *)(merged_buf);
195-
196-
while (dest_size > 0 && src_size > 0) {
197-
if (pstore_ftrace_read_timestamp(&drec[dest_idx]) <
198-
pstore_ftrace_read_timestamp(&srec[src_idx])) {
199-
mrec[merged_idx++] = drec[dest_idx++];
200-
dest_size -= record_size;
201-
} else {
202-
mrec[merged_idx++] = srec[src_idx++];
203-
src_size -= record_size;
204-
}
205-
}
206-
207-
while (dest_size > 0) {
208-
mrec[merged_idx++] = drec[dest_idx++];
209-
dest_size -= record_size;
210-
}
211-
212-
while (src_size > 0) {
213-
mrec[merged_idx++] = srec[src_idx++];
214-
src_size -= record_size;
215-
}
216-
217-
kfree(*dest_log);
218-
*dest_log = merged_buf;
219-
*dest_log_size = total;
220-
221-
return 0;
222-
}
223-
224172
static ssize_t ramoops_pstore_read(struct pstore_record *record)
225173
{
226174
ssize_t size = 0;
@@ -293,7 +241,8 @@ static ssize_t ramoops_pstore_read(struct pstore_record *record)
293241
prz_next->corrected_bytes;
294242
tmp_prz->bad_blocks += prz_next->bad_blocks;
295243

296-
size = ftrace_log_combine(&tmp_prz->old_log,
244+
size = pstore_ftrace_combine_log(
245+
&tmp_prz->old_log,
297246
&tmp_prz->old_log_size,
298247
prz_next->old_log,
299248
prz_next->old_log_size);

0 commit comments

Comments
 (0)