Messages in this thread Patch in this message | | | Date | Wed, 27 May 2009 16:12:34 +0800 | From | Li Zefan <> | Subject | Re: [PATCH v2 1/2] tracing/events: make __string() more general |
| |
Christoph Hellwig wrote: > On Wed, May 27, 2009 at 09:43:32AM +0800, Li Zefan wrote: >> I'm not suffering from NULL str, so I'm not quite sure how you want __string() >> deal with it. > > The internals of __string is still magic to me, need to finish my > advance cpp abuse degree first ;-) >
It's no longer magic to me. ;)
> But the expected outcome would be that when we get a NULL pointer as > input we get a NULL pointer as output again. >
The following trick should meet your needs (based on this 1/2 patch):
(Not even compiled!)
diff --git a/include/trace/ftrace.h b/include/trace/ftrace.h index d1c0cc5..c5911d0 100644 --- a/include/trace/ftrace.h +++ b/include/trace/ftrace.h @@ -117,7 +117,10 @@ #define TP_printk(fmt, args...) fmt "\n", args #undef __get_str -#define __get_str(field) ((char *)__entry + __entry->__str_loc_##field) +#define __get_str(field) \ + (__entry->__str_lock_##field != -1) ? \ + ((char *)__entry + __entry->__str_loc_##field) : \ + NULL #undef TRACE_EVENT #define TRACE_EVENT(call, proto, args, tstruct, assign, print) \ @@ -412,8 +415,11 @@ static void ftrace_profile_disable_##call(struct ftrace_event_call *call) \ #undef __string #define __string(item, len) \ - __str_offsets.item = __str_size + \ - offsetof(typeof(*entry), __str_data); \ + if (len) \ + __str_offsets.item = __str_size + \ + offsetof(typeof(*entry), __str_data);\ + else \ + __str_offsets.item = -1; \ __str_size += (len) + 1; #undef __fetch_str > What I currently do is: > > TRACE_EVENT(xfs_dir2, > TP_PROTO(struct xfs_da_args *args, int i, int j, int count), > TP_ARGS(args, i, j, count), > > TP_STRUCT__entry( > __field(xfs_ino_t, ino) > __array(char, name, TRACE_MAXNAMELEN) > __field(int, namelen) > ... > ), > > TP_fast_assign( > __entry->ino = args->dp->i_ino; > if (args->namelen) > memcpy(__entry->name, args->name, > min(args->namelen, TRACE_MAXNAMELEN));
This string is not NULL-terminated?
> __entry->namelen = args->namelen; > ... > ), > > TP_printk("ino 0x%lld %pF name %.*s namelen %d hashval 0x%x " > "inumber 0x%llx op_flags %s i %d j %d count %d", > __entry->ino, > (void *)__entry->caller_ip, > min(__entry->namelen, TRACE_MAXNAMELEN), > __entry->namelen ? __entry->name : NULL, > __entry->namelen, > ...) > ); >
Then the above code can be rewrote:
TRACE_EVENT(xfs_dir2, TP_PROTO(struct xfs_da_args *args, int i, int j, int count), TP_ARGS(args, i, j, count),
TP_STRUCT__entry( __field(xfs_ino_t, ino) __string(name, args->namelen) __field(int, namelen) ... ),
TP_fast_assign( __entry->ino = args->dp->i_ino; memcpy(__fetch_str(name), args->name, args->namelen); __entry->namelen = args->namelen; ... ),
TP_printk("ino 0x%lld %pF name %.*s namelen %d hashval 0x%x " "inumber 0x%llx op_flags %s i %d j %d count %d", __entry->ino, (void *)__entry->caller_ip, __entry->namelen, __get_str(name), __entry->namelen, ...) );
| |