mirror of https://lore.kernel.org/lkml/
 help / color / mirror / Atom feed
From: Steven Rostedt <rostedt@goodmis.org>
To: Vladislav Valtchev <vladislav.valtchev@gmail.com>
Cc: linux-kernel@vger.kernel.org, y.karadz@gmail.com
Subject: Re: [PATCH 08/11] trace-cmd: Making start,extract,stream,profile separate funcs
Date: Wed, 29 Nov 2017 07:48:00 -0500	[thread overview]
Message-ID: <20171129074800.07cb970e@gandalf.local.home> (raw)
In-Reply-To: <1511949794.4897.49.camel@gmail.com>

On Wed, 29 Nov 2017 12:03:14 +0200
Vladislav Valtchev <vladislav.valtchev@gmail.com> wrote:

> On Tue, 2017-11-28 at 14:35 -0500, Steven Rostedt wrote:
> > 
> > Yes. Simply because we lost the fact that we can do it better.
> >   
> 
> Hi Steven,
> of course we can do better, if we make a step further than just
> a mechanical refactoring. I'm used to intentionally limit myself
> to do such kind of mechanical refactoring, in order to reduce to the minimum
> possible the chance of introducing bugs. And it really works pretty well for me.
> 
> I intentionally did not even consider to check whether events = 1 was
> needed there or not: for me that kind of simplifications should be done
> *after* the mechanical refactoring, not while doing it. This way, while
> searching for a bug, I can order the commits by likelihood of being the
> root-cause of the bug and, when possible, I'm happy to put changes as this one
> at the bottom.

I totally agree that one shouldn't think about this level of factoring
when doing only mechanical refactoring. But the issue is what's the
best mechanical refactoring you can do to let you see new changes like
this? Note, this is not a bug fix, it becomes another clean up. Having
it as an if statement within one function, makes it stick out more than
breaking up a function into two and having all users call two
functions. The two function approach will "hide" this issue. Again,
it's not a bug in the way it was done, but we miss the change because
it is more likely not to be seen.

> 
> Also, I learned that lesson while working in vSphere, by observing (and a few
> times doing myself) "innocent" refactoring changes breaking CI and system tests
> because of super-subtle side-effects.
> 
> In this concrete case, the original code was:
> 
> 	if ((record = (strcmp(argv[1], "record") == 0)))
> 		; /* do nothing */
> 	else if ((start = strcmp(argv[1], "start") == 0))
> 		; /* do nothing */
> 	else if ((extract = strcmp(argv[1], "extract") == 0))
> 		; /* do nothing */
> 	else if ((stream = strcmp(argv[1], "stream") == 0))
> 		; /* do nothing */
> 	else if ((profile = strcmp(argv[1], "profile") == 0)) {
> 		handle_init = trace_init_profile;
> 		events = 1;
> 	} else
> 		usage(argv);
> 
> at the beginning of trace_record().
> After that, it followed the big "for" loop with its big "switch".
> During the refactoring, I followed this order *strictly* and I'm sure
> that my change is correct exactly as much as the original code: I just
> moved the things around, but the state (ctx and global variables)
> continued to change (evolve) exactly in the same order as in the original
> code did.
> 
> That's why, from that point-of-view, "it was there before" was the
> right answer to me.

And I agree.
> 
> 
> > There's a reason I asked about why the "events = 1" was needed? And
> > saying "it was there before" is not the right answer. You are changing
> > the flow of the code. These are not subtle changes. These are
> > legitimate changes to the flow. Even though they are only to make it
> > easier to understand. The algorithm is changing. Look again, and tell
> > me, why is "events = 1" needed? And for that matter, the setting of
> > handle_init. If it is needed, why?
> >   
> 
> Of course, I understand that the level of code improvement with my algorithm
> is certainly not the best we can do: it's just the most conservative approach.
> I hope that you at least appreciate my effort to make "big" changes like
> this one, without even a single minor bug, thanks to a strict approach: it
> still seems to me the less evil thing if compared to the introduction of a
> subtle bug in a corner case because of a "too smart move".
> 
> Returning back to 'events=1', yes I agree that actually parse_record_options()
> never reads its value. The same is true for handle_init. Both the variables
> are used in the record_trace() part. The "events" flag is checked before doing
> expand_event_list() and before:
> 
> for_all_instances(ctx->instance)
> 	enable_events(ctx->instance);
> 
> handle_init is used by start_thread(), which is called by record_trace().
> 
> Therefore:
> 
> 	handle_init = trace_init_profile;
> 	ctx.events = 1;
> 
> can be safely moved after parse_record_options() and, the call of
> init_common_record_context() could be moved at the beginning of
> parse_record_options().
> 
> Are you fine with me doing that in a patch the follows immediately
> this patch 8 ?

Yes, but I would like init_common_record_context() to be merged into
parse_record_options() in the previous patches and we add that if
statement to make profile different :-)

I see that you see many of the parts of this elephant. Some looks like
a rope, some a fire hose, some a tree trunk, and some a wall. But when
you put it all together, you see the elephant as a whole. I'm trying to
have you see the whole elephant ;-)

The point I'm making is that the way something is refactored, should
start out not breaking the flow of logic. The original code technically
had an if statement for the profile (but it was in a switch statement).
That if statement should have stayed throughout the mechanical
refactoring. And then after the refactoring was done, we could look at
seeing if more can be cleaned up. And then we would see that the if
statement was not necessary. But by breaking up the flow into two
functions, that extra code would be hidden, and we would have
unnecessarily have two functions.

The way mechanical updates happen does matter, to help improve the
less trivial updates. That's the point I'm trying to make.

-- Steve

  reply	other threads:[~2017-11-29 12:48 UTC|newest]

Thread overview: 30+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2017-11-23 16:33 [PATCH 00/11] trace-cmd: Refactoring trace_record() Vladislav Valtchev (VMware)
2017-11-23 16:33 ` [PATCH 01/11] trace-cmd: Extract trace_stop() from trace_record() Vladislav Valtchev (VMware)
2017-11-23 16:33 ` [PATCH 02/11] trace-cmd: Extract trace_restart() " Vladislav Valtchev (VMware)
2017-11-23 16:33 ` [PATCH 03/11] trace-cmd: Extract trace_reset() " Vladislav Valtchev (VMware)
2017-11-23 16:33 ` [PATCH 04/11] trace-cmd: Extract parse_record_options() " Vladislav Valtchev (VMware)
2017-11-28 16:48   ` Steven Rostedt
2017-11-28 18:17     ` Vladislav Valtchev
2017-11-28 18:30       ` Steven Rostedt
2017-11-28 18:57         ` Vladislav Valtchev
2017-11-28 19:15           ` Steven Rostedt
2017-11-29 14:53       ` Steven Rostedt
2017-11-29 15:18         ` Vladislav Valtchev
2017-11-23 16:33 ` [PATCH 05/11] trace-cmd: Rename trace_profile() to trace_profile_int() Vladislav Valtchev (VMware)
2017-11-28 17:05   ` Steven Rostedt
2017-11-28 19:00     ` Vladislav Valtchev
2017-11-23 16:33 ` [PATCH 06/11] trace-cmd: Replacing cmd flags w/ a trace_cmd enum Vladislav Valtchev (VMware)
2017-11-23 16:33 ` [PATCH 07/11] trace-cmd: Extracting record_trace() Vladislav Valtchev (VMware)
2017-11-23 16:33 ` [PATCH 08/11] trace-cmd: Making start,extract,stream,profile separate funcs Vladislav Valtchev (VMware)
2017-11-28 17:14   ` Steven Rostedt
2017-11-28 18:34     ` Vladislav Valtchev
2017-11-28 19:35       ` Steven Rostedt
2017-11-29 10:03         ` Vladislav Valtchev
2017-11-29 12:48           ` Steven Rostedt [this message]
2017-11-23 16:33 ` [PATCH 09/11] trace-cmd: Consolidate ARRAY_SIZE() in trace-cmd.h Vladislav Valtchev (VMware)
2017-11-28 17:16   ` Steven Rostedt
2017-11-23 16:33 ` [PATCH 10/11] trace-cmd: Making the "die" functions noreturn Vladislav Valtchev (VMware)
2017-11-23 16:33 ` [PATCH 11/11] trace-cmd: Introducing get_trace_cmd_type() Vladislav Valtchev (VMware)
2017-11-28 17:17   ` Steven Rostedt
2017-11-28 18:32     ` Steven Rostedt
2017-11-28 19:04       ` Vladislav Valtchev

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20171129074800.07cb970e@gandalf.local.home \
    --to=rostedt@goodmis.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=vladislav.valtchev@gmail.com \
    --cc=y.karadz@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox

all inboxes | Powered by JetHome®