views:

1631

answers:

4

How to refactor c source code that compiles with gcc, preferably a tool that can be used from the command line?

+3  A: 

vim?

Refactoring is improving the readability of code, not something you can just achieve do ./magicrefactor mysource.c

There are tools to reindent code (as BKB mentioned), but a majority of refactoring will probably be moving stuff into sensible functions, renaming badly named variables/functions and so on - things best done in a text editor.

You can quite often get very far using simple find-and-replace search..

Some examples (in vim) to rename the function tempfunctionblah:

:%s/tempfunctionblah/a_descriptive_function_name/;

Be very careful this doesn't break your code - do a regular find and check the matches are actually the function. Keeping with my suggestion of vim (although the actual editor you use is pretty much irrelevant):

:set hlsearch!
/tempfunctionblah

Regular Expressions can help a lot with stuff like this. For example, to slightly more inteligently try and find calls to tempfunctionblah (which checks if you do tempfunctionblah(), and ignoring any space between the function name and the brackets):

:%s/tempfunctionblah[ ]*(/new_func_name(/

Again, you have to be really careful that these mass changes don't break your code (especially if there are multiple source files, headers and so on!). This is where unit-tests and the likes are extremely useful.

Basically, my point is you really don't need any special tools for refactoring, just a good text editor..

dbr
Small improvement on your last regex there: /\<tempfunctionblah\>\s*(/ - start-word and end-word markers avoid matching not_really_tempfunctionblah, and \s also works if your source contains tabs.
Sam Stokes
Is vi/vim released under the GNU license? I know emacs is, but I'm not sure about vi/vim.
Thomas Owens
Vim is Charityware: http://www.vim.org/htmldoc/uganda.html
davitenio
+1  A: 

Refactoring tools for C are hard to develop. C has no introspection (or reflection), which is often used by refactoring tools. Also, the usage of macros do not make it easy for an IDE. Basically, the IDE needs to preprocess the code to be able to reason about the underlying C code. Most of the tools for C can only work on a lexical level.

After dabbling with some IDEs (like CDT for eclipse), I settled on using vim for my C code. You can do a lot with cscope and ctags to find out the usage of a certain method throughout your code. This at least will give you an idea on the complexity of the refactoring exercise you are doing. If you want to refactor a signature of a method used in a lot of places, that means a lot of work in C. For this kind of work I prefer going with 'perl -pi' magic.

However, refactoring within a method, like extracting a variable or method are more localized operations, and should not touch a lot of places in your code. These can easily be done with any IDE/editor.

From my experience, refactoring is only worthwhile if you have a good safety net in place, like test coverage etc... There are C unit test frameworks out there, so why not use them? First writing a test (if it not already exists) for the piece of code you are going to refactor will give you a means to verify correct behavior of your refactoring exercise.

As a summary, refactoring in C is not easy, but vim/csope, sed/awk/perl and a good set of tests are your friend...

Johan
+6  A: 

The people from Mozilla (notably Taras Glek) have peen working on automated refactoring of C/C++ code, developing Pork and DeHydra. I'm not sure that these tools actually can do refactoring by themselves, they help by actually analysing the syntax tree of the source files (and even revert macros), and provide querying abilities, so you might be able to do more safe refactorings than just simple search/replace.

Kim Sullivan
+2  A: 

I find cccc produces quite valuable output, at least for C++ code. It's not a GNU tool but it is open-sourced.

ChrisInEdmonton