Merge branch 'tracing-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip

* 'tracing-fixes-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/linux-2.6-tip:
tracing/filters: Add comment for match callbacks
tracing/filters: Fix MATCH_FULL filter matching for PTR_STRING
tracing/filters: Fix MATCH_MIDDLE_ONLY filter matching
lib: Introduce strnstr()
tracing/filters: Fix MATCH_END_ONLY filter matching
tracing/filters: Fix MATCH_FRONT_ONLY filter matching
ftrace: Fix MATCH_END_ONLY function filter
tracing/x86: Derive arch from bits argument in recordmcount.pl
ring-buffer: Add rb_list_head() wrapper around new reader page next field
ring-buffer: Wrap a list.next reference with rb_list_head()

+56 -17
+4 -1
include/linux/string.h
··· 72 72 } 73 73 74 74 #ifndef __HAVE_ARCH_STRSTR 75 - extern char * strstr(const char *,const char *); 75 + extern char * strstr(const char *, const char *); 76 + #endif 77 + #ifndef __HAVE_ARCH_STRNSTR 78 + extern char * strnstr(const char *, const char *, size_t); 76 79 #endif 77 80 #ifndef __HAVE_ARCH_STRLEN 78 81 extern __kernel_size_t strlen(const char *);
+3 -3
kernel/trace/ftrace.c
··· 1690 1690 static int ftrace_match(char *str, char *regex, int len, int type) 1691 1691 { 1692 1692 int matched = 0; 1693 - char *ptr; 1693 + int slen; 1694 1694 1695 1695 switch (type) { 1696 1696 case MATCH_FULL: ··· 1706 1706 matched = 1; 1707 1707 break; 1708 1708 case MATCH_END_ONLY: 1709 - ptr = strstr(str, regex); 1710 - if (ptr && (ptr[len] == 0)) 1709 + slen = strlen(str); 1710 + if (slen >= len && memcmp(str + slen - len, regex, len) == 0) 1711 1711 matched = 1; 1712 1712 break; 1713 1713 }
+2 -2
kernel/trace/ring_buffer.c
··· 2869 2869 * Splice the empty reader page into the list around the head. 2870 2870 */ 2871 2871 reader = rb_set_head_page(cpu_buffer); 2872 - cpu_buffer->reader_page->list.next = reader->list.next; 2872 + cpu_buffer->reader_page->list.next = rb_list_head(reader->list.next); 2873 2873 cpu_buffer->reader_page->list.prev = reader->list.prev; 2874 2874 2875 2875 /* ··· 2906 2906 * 2907 2907 * Now make the new head point back to the reader page. 2908 2908 */ 2909 - reader->list.next->prev = &cpu_buffer->reader_page->list; 2909 + rb_list_head(reader->list.next)->prev = &cpu_buffer->reader_page->list; 2910 2910 rb_inc_page(cpu_buffer, &cpu_buffer->head_page); 2911 2911 2912 2912 /* Finally update the reader page to the new head */
+20 -9
kernel/trace/trace_events_filter.c
··· 211 211 { 212 212 char **addr = (char **)(event + pred->offset); 213 213 int cmp, match; 214 + int len = strlen(*addr) + 1; /* including tailing '\0' */ 214 215 215 - cmp = pred->regex.match(*addr, &pred->regex, pred->regex.field_len); 216 + cmp = pred->regex.match(*addr, &pred->regex, len); 216 217 217 218 match = cmp ^ pred->not; 218 219 ··· 252 251 return 0; 253 252 } 254 253 255 - /* Basic regex callbacks */ 254 + /* 255 + * regex_match_foo - Basic regex callbacks 256 + * 257 + * @str: the string to be searched 258 + * @r: the regex structure containing the pattern string 259 + * @len: the length of the string to be searched (including '\0') 260 + * 261 + * Note: 262 + * - @str might not be NULL-terminated if it's of type DYN_STRING 263 + * or STATIC_STRING 264 + */ 265 + 256 266 static int regex_match_full(char *str, struct regex *r, int len) 257 267 { 258 268 if (strncmp(str, r->pattern, len) == 0) ··· 273 261 274 262 static int regex_match_front(char *str, struct regex *r, int len) 275 263 { 276 - if (strncmp(str, r->pattern, len) == 0) 264 + if (strncmp(str, r->pattern, r->len) == 0) 277 265 return 1; 278 266 return 0; 279 267 } 280 268 281 269 static int regex_match_middle(char *str, struct regex *r, int len) 282 270 { 283 - if (strstr(str, r->pattern)) 271 + if (strnstr(str, r->pattern, len)) 284 272 return 1; 285 273 return 0; 286 274 } 287 275 288 276 static int regex_match_end(char *str, struct regex *r, int len) 289 277 { 290 - char *ptr = strstr(str, r->pattern); 278 + int strlen = len - 1; 291 279 292 - if (ptr && (ptr[r->len] == 0)) 280 + if (strlen >= r->len && 281 + memcmp(str + strlen - r->len, r->pattern, r->len) == 0) 293 282 return 1; 294 283 return 0; 295 284 } ··· 794 781 pred->regex.field_len = field->size; 795 782 } else if (field->filter_type == FILTER_DYN_STRING) 796 783 fn = filter_pred_strloc; 797 - else { 784 + else 798 785 fn = filter_pred_pchar; 799 - pred->regex.field_len = strlen(pred->regex.pattern); 800 - } 801 786 } else { 802 787 if (field->is_signed) 803 788 ret = strict_strtoll(pred->regex.pattern, 0, &val);
+26 -1
lib/string.c
··· 667 667 */ 668 668 char *strstr(const char *s1, const char *s2) 669 669 { 670 - int l1, l2; 670 + size_t l1, l2; 671 671 672 672 l2 = strlen(s2); 673 673 if (!l2) ··· 682 682 return NULL; 683 683 } 684 684 EXPORT_SYMBOL(strstr); 685 + #endif 686 + 687 + #ifndef __HAVE_ARCH_STRNSTR 688 + /** 689 + * strnstr - Find the first substring in a length-limited string 690 + * @s1: The string to be searched 691 + * @s2: The string to search for 692 + * @len: the maximum number of characters to search 693 + */ 694 + char *strnstr(const char *s1, const char *s2, size_t len) 695 + { 696 + size_t l1 = len, l2; 697 + 698 + l2 = strlen(s2); 699 + if (!l2) 700 + return (char *)s1; 701 + while (l1 >= l2) { 702 + l1--; 703 + if (!memcmp(s1, s2, l2)) 704 + return (char *)s1; 705 + s1++; 706 + } 707 + return NULL; 708 + } 709 + EXPORT_SYMBOL(strnstr); 685 710 #endif 686 711 687 712 #ifndef __HAVE_ARCH_MEMCHR
+1 -1
scripts/recordmcount.pl
··· 194 194 } 195 195 } 196 196 197 - if ($arch eq "x86") { 197 + if ($arch =~ /(x86(_64)?)|(i386)/) { 198 198 if ($bits == 64) { 199 199 $arch = "x86_64"; 200 200 } else {