aboutsummaryrefslogtreecommitdiffstats
path: root/kernel/trace/trace.c
diff options
context:
space:
mode:
Diffstat (limited to 'kernel/trace/trace.c')
-rw-r--r--kernel/trace/trace.c65
1 files changed, 45 insertions, 20 deletions
diff --git a/kernel/trace/trace.c b/kernel/trace/trace.c
index ce11fa50a2f0..1af4f8f2ab5d 100644
--- a/kernel/trace/trace.c
+++ b/kernel/trace/trace.c
@@ -939,19 +939,20 @@ out:
939 return ret; 939 return ret;
940} 940}
941 941
942/* TODO add a seq_buf_to_buffer() */
942static ssize_t trace_seq_to_buffer(struct trace_seq *s, void *buf, size_t cnt) 943static ssize_t trace_seq_to_buffer(struct trace_seq *s, void *buf, size_t cnt)
943{ 944{
944 int len; 945 int len;
945 946
946 if (s->len <= s->readpos) 947 if (trace_seq_used(s) <= s->seq.readpos)
947 return -EBUSY; 948 return -EBUSY;
948 949
949 len = s->len - s->readpos; 950 len = trace_seq_used(s) - s->seq.readpos;
950 if (cnt > len) 951 if (cnt > len)
951 cnt = len; 952 cnt = len;
952 memcpy(buf, s->buffer + s->readpos, cnt); 953 memcpy(buf, s->buffer + s->seq.readpos, cnt);
953 954
954 s->readpos += cnt; 955 s->seq.readpos += cnt;
955 return cnt; 956 return cnt;
956} 957}
957 958
@@ -4313,6 +4314,8 @@ static int tracing_open_pipe(struct inode *inode, struct file *filp)
4313 goto out; 4314 goto out;
4314 } 4315 }
4315 4316
4317 trace_seq_init(&iter->seq);
4318
4316 /* 4319 /*
4317 * We make a copy of the current tracer to avoid concurrent 4320 * We make a copy of the current tracer to avoid concurrent
4318 * changes on it while we are reading. 4321 * changes on it while we are reading.
@@ -4506,18 +4509,18 @@ waitagain:
4506 trace_access_lock(iter->cpu_file); 4509 trace_access_lock(iter->cpu_file);
4507 while (trace_find_next_entry_inc(iter) != NULL) { 4510 while (trace_find_next_entry_inc(iter) != NULL) {
4508 enum print_line_t ret; 4511 enum print_line_t ret;
4509 int len = iter->seq.len; 4512 int save_len = iter->seq.seq.len;
4510 4513
4511 ret = print_trace_line(iter); 4514 ret = print_trace_line(iter);
4512 if (ret == TRACE_TYPE_PARTIAL_LINE) { 4515 if (ret == TRACE_TYPE_PARTIAL_LINE) {
4513 /* don't print partial lines */ 4516 /* don't print partial lines */
4514 iter->seq.len = len; 4517 iter->seq.seq.len = save_len;
4515 break; 4518 break;
4516 } 4519 }
4517 if (ret != TRACE_TYPE_NO_CONSUME) 4520 if (ret != TRACE_TYPE_NO_CONSUME)
4518 trace_consume(iter); 4521 trace_consume(iter);
4519 4522
4520 if (iter->seq.len >= cnt) 4523 if (trace_seq_used(&iter->seq) >= cnt)
4521 break; 4524 break;
4522 4525
4523 /* 4526 /*
@@ -4533,7 +4536,7 @@ waitagain:
4533 4536
4534 /* Now copy what we have to the user */ 4537 /* Now copy what we have to the user */
4535 sret = trace_seq_to_user(&iter->seq, ubuf, cnt); 4538 sret = trace_seq_to_user(&iter->seq, ubuf, cnt);
4536 if (iter->seq.readpos >= iter->seq.len) 4539 if (iter->seq.seq.readpos >= trace_seq_used(&iter->seq))
4537 trace_seq_init(&iter->seq); 4540 trace_seq_init(&iter->seq);
4538 4541
4539 /* 4542 /*
@@ -4567,20 +4570,33 @@ static size_t
4567tracing_fill_pipe_page(size_t rem, struct trace_iterator *iter) 4570tracing_fill_pipe_page(size_t rem, struct trace_iterator *iter)
4568{ 4571{
4569 size_t count; 4572 size_t count;
4573 int save_len;
4570 int ret; 4574 int ret;
4571 4575
4572 /* Seq buffer is page-sized, exactly what we need. */ 4576 /* Seq buffer is page-sized, exactly what we need. */
4573 for (;;) { 4577 for (;;) {
4574 count = iter->seq.len; 4578 save_len = iter->seq.seq.len;
4575 ret = print_trace_line(iter); 4579 ret = print_trace_line(iter);
4576 count = iter->seq.len - count; 4580
4577 if (rem < count) { 4581 if (trace_seq_has_overflowed(&iter->seq)) {
4578 rem = 0; 4582 iter->seq.seq.len = save_len;
4579 iter->seq.len -= count;
4580 break; 4583 break;
4581 } 4584 }
4585
4586 /*
4587 * This should not be hit, because it should only
4588 * be set if the iter->seq overflowed. But check it
4589 * anyway to be safe.
4590 */
4582 if (ret == TRACE_TYPE_PARTIAL_LINE) { 4591 if (ret == TRACE_TYPE_PARTIAL_LINE) {
4583 iter->seq.len -= count; 4592 iter->seq.seq.len = save_len;
4593 break;
4594 }
4595
4596 count = trace_seq_used(&iter->seq) - save_len;
4597 if (rem < count) {
4598 rem = 0;
4599 iter->seq.seq.len = save_len;
4584 break; 4600 break;
4585 } 4601 }
4586 4602
@@ -4661,13 +4677,13 @@ static ssize_t tracing_splice_read_pipe(struct file *filp,
4661 /* Copy the data into the page, so we can start over. */ 4677 /* Copy the data into the page, so we can start over. */
4662 ret = trace_seq_to_buffer(&iter->seq, 4678 ret = trace_seq_to_buffer(&iter->seq,
4663 page_address(spd.pages[i]), 4679 page_address(spd.pages[i]),
4664 iter->seq.len); 4680 trace_seq_used(&iter->seq));
4665 if (ret < 0) { 4681 if (ret < 0) {
4666 __free_page(spd.pages[i]); 4682 __free_page(spd.pages[i]);
4667 break; 4683 break;
4668 } 4684 }
4669 spd.partial[i].offset = 0; 4685 spd.partial[i].offset = 0;
4670 spd.partial[i].len = iter->seq.len; 4686 spd.partial[i].len = trace_seq_used(&iter->seq);
4671 4687
4672 trace_seq_init(&iter->seq); 4688 trace_seq_init(&iter->seq);
4673 } 4689 }
@@ -5667,7 +5683,8 @@ tracing_stats_read(struct file *filp, char __user *ubuf,
5667 cnt = ring_buffer_read_events_cpu(trace_buf->buffer, cpu); 5683 cnt = ring_buffer_read_events_cpu(trace_buf->buffer, cpu);
5668 trace_seq_printf(s, "read events: %ld\n", cnt); 5684 trace_seq_printf(s, "read events: %ld\n", cnt);
5669 5685
5670 count = simple_read_from_buffer(ubuf, count, ppos, s->buffer, s->len); 5686 count = simple_read_from_buffer(ubuf, count, ppos,
5687 s->buffer, trace_seq_used(s));
5671 5688
5672 kfree(s); 5689 kfree(s);
5673 5690
@@ -6630,11 +6647,19 @@ void
6630trace_printk_seq(struct trace_seq *s) 6647trace_printk_seq(struct trace_seq *s)
6631{ 6648{
6632 /* Probably should print a warning here. */ 6649 /* Probably should print a warning here. */
6633 if (s->len >= TRACE_MAX_PRINT) 6650 if (s->seq.len >= TRACE_MAX_PRINT)
6634 s->len = TRACE_MAX_PRINT; 6651 s->seq.len = TRACE_MAX_PRINT;
6652
6653 /*
6654 * More paranoid code. Although the buffer size is set to
6655 * PAGE_SIZE, and TRACE_MAX_PRINT is 1000, this is just
6656 * an extra layer of protection.
6657 */
6658 if (WARN_ON_ONCE(s->seq.len >= s->seq.size))
6659 s->seq.len = s->seq.size - 1;
6635 6660
6636 /* should be zero ended, but we are paranoid. */ 6661 /* should be zero ended, but we are paranoid. */
6637 s->buffer[s->len] = 0; 6662 s->buffer[s->seq.len] = 0;
6638 6663
6639 printk(KERN_TRACE "%s", s->buffer); 6664 printk(KERN_TRACE "%s", s->buffer);
6640 6665