Next Previous Contents

5. Vi companions

Generally Vim is used in conjunction with other powerful tools like ctags and gdb. The ctags is for very rapid navigation through millions of lines of "C/C++" code and gdb for debugging the "C/C++" code. A brief introduction of these two indispensable commands will be given in this chapter.

The ctags is the most powerful command available for coding C, C++, Java, Perl, Korn/Bourne shell scripts or Fortran. Developers very extensively use ctags to navigate "to and fro" thousands of functions of C/C++ programs. See 'man ctags' on Unix. It is very important that you MUST learn how to use ctags in order to develop programs in C or C++, Java, etc.. Navigation is the single most important task while doing development of C or C++ code. Using ctags you can very quickly read the code by jumping from calling line to function and drill down deeper into nested function calls and unwind back all the way upto the top. You can go back and forth from function to function very quickly.

Without NAVIGATION you will be completely lost! ctags is like the magnetic COMPASS needle for the programmers.

Usage of ctags :


        ctags *.cpp
        gvim -t foo_function
        gvim -t main

This will edit the C++ program file which contains the function foo_function() and will automatically place the cursor on the first line of the function foo_function(). The second command takes you to line having main() function definition.

Inside the Vim editor, you can jump to a function by typing : (colon) tag < function name >as below -


        :tag sample_function

This will place the cursor on first line of sample_function()

If you want to jump into the function from a line in file which contains the function name, place the cursor just before the function name and press CTRL+] (press control key and left-square-bracket key simultaneously), this will take you right at the line where the function begins automatically!!


                // example code
                switch(id_number) {
                        Case 1:
                                if ( foo_function( 22, "abcef") == 3 )
                                    ^
                                    |
                                    |
                                    |
                  Place the cursor here (just before foo_function) and press CTRL+]
                  This will take you to function by name "foo_function". To come back to this line press CTRL+t

To go back to the calling line press CTRL+t (Control key and letter 't' together). You keep pressing CTRL+t to unwind and go to the first line where you started the navigation. That is you can keep pressing CTRL+] and than keep pressing CTRL+t to go back. You can repeat these as many times you want to have complete navigation through all the functions of C or C++.

5.1 Ctags for ESQL

Since ctags directly does not support the Embedded SQL/C (ESQL) language, the following shell script can be used to create tags for esql. ESQL/C is database SQL commands embedded inside the "C" programs. Oracle's ESQL/C is called Pro*C and Sybase, Informix have ESQL/C and PostgreSQL has product "ecpg".

Save this file as "sqltags.sh" and do chmod a+rx tags_gen.sh.


#!/bin/sh

# Program to create ctags for ESQL, C++ and C files
ESQL_EXTN=pc
tag_file1=tags_file.1
tag_file2=tags_file.2

which_tag=ctags

rm -f $tag_file1 $tag_file2 tags

aa=`ls *.$ESQL_EXTN`
#echo $aa
for ii in $aa 
do
        #echo $ii
        jj=`echo $ii | cut -d'.' -f1`
        #echo $jj

        if [ ! -f $jj.cpp ]; then
                echo " "
                echo " "
                echo "***********************************************"
                echo "ESQL *.cpp files does not exist.. "
                echo "You must generate the *.cpp from *.pc file"
                echo "using the Oracle Pro*C pre-compiler or Sybase"
                echo "or Informix esql/c pre-compiler."
                echo "And than re-run this command"
                echo "***********************************************"
                echo " "
                exit
        fi

        rm -f tags
        $which_tag $jj.cpp
        kk=s/$jj\.cpp/$jj\.pc/g

        #echo $kk > sed.tmp
        #sed -f sed.tmp tags >> $tag_file1

        #sed -e's/sample\.cpp/sample\.pc/g' tags >> $tag_file1
        sed -e $kk tags >> $tag_file1
done

# Now handle all the C++/C files - exclude the ESQL *.cpp files
rm -f tags $tag_file2
bb=`ls *.cpp *.c`
aa=`ls *.$ESQL_EXTN`
for mm in $bb 
do
        ee=`echo $mm | cut -d'.' -f1`
        file_type="NOT_ESQL"
        # Exclude the ESQL *.cpp and *.c files
        for nn in $aa 
        do
                dd=`echo $nn | cut -d'.' -f1`
                if [ "$dd" = "$ee" ]; then
                        file_type="ESQL"
                        break
                fi
        done

        if [ "$file_type" = "ESQL" ]; then
                continue
        fi

        rm -f tags
        $which_tag $mm
        cat tags >> $tag_file2
done

mv -f $tag_file2 tags
cat  $tag_file1 >> tags
rm -f $tag_file1

# Must sort tags file for it work properly ....
sort tags > $tag_file1
mv $tag_file1 tags

5.2 Ctags for Javascript programs, Korn, Bourne shells

The shell script given below can be used to generate tags for a very large variety of programs written in JavasScript, PHP/FI scripts, Korn shell, C shell, Bourne shell and many others. This is a very generic module.

Save this file as tags_gen.sh and do chmod a+rx tags_gen.sh.


#!/bin/sh

tmp_tag=tags_file
tmp_tag2=tags_file2

echo " "
echo " "
echo " "
echo " "
echo " "
echo "Generate tags for ...."
while :
do
        echo "    Enter file extension for which you want to generate tags."
        echo -n "    File-extension should be like sh, js, ksh, etc... : "
        read ans

        if [ "$ans" == "" ]; then
                echo " "
                echo "Wrong entry. Try again!"
        else
                break
        fi
done

\rm -f $tmp_tag

aa=`ls *.$ans`

for ii in $aa
do
        jj=`echo $ii | cut -d'.' -f1`
        #echo $jj
        cp $ii $jj.c
        ctags $jj.c
        echo "s/$jj.c/$ii/g" > $tmp_tag2
        sed -f $tmp_tag2 tags >> $tmp_tag
        \rm -f tags $jj.c
done

sort $tmp_tag > tags

\rm -f $tmp_tag $tmp_tag2

5.3 Debugger gdb

You would be using gdb extensively along with Vi. Debugging is the most important aspect of programming as major cost of software project goes into debugging and testing.

To debug C++/C programs use 'gdb' tool. See 'man gdb'. You must compile your programs with -g3 option like

        gcc -g3 foo.c foo_another.c sample.c

To setup easy aliases do -

  Setup a alias in your ~/.bash_profile
        alias gdb='gdb -directory=/home/src -directory=/usr/myname/src '
  Give -
        gdb foo.cpp
        gdb> dir /hom2/another_src
        This will add to file search path
        gdb> break 'some_class::func<TAB><TAB>
  This will complete the function name saving you typing time... and will output like -
        gdb> break 'some_class::function_foo_some_where(int aa, float bb)'

Pressing TAB key twice is the command line completion, which will save you lots of typing time. This is one of the most important technique of using gdb.

To get online help do -

        gdb> help
  Gives online help
        gdb> help breakpoints
  Gives more details about breakpoints.

To set breakpoints and do debugging

        unixprompt> gdb exe_filename 
        gdb> b main
  This will put breakpoint in main() function
        gdb> b 123
  This will put breakpoint in line 123 of the current file
        gdb> help breakpoints
  Gives more details about breakpoints.

To analyze the core dumps do

        unixprompt> gdb exe_filename  core
        gdb> bt
  Gives backtrace of functions and line numbers where the program failed
        gdb> help backtrace
  Gives more details about backtrace.

You can also use GUI version of gdb called xxgdb.

Memory leak tools -


Next Previous Contents