Year: 2010

Backing out multiple consecutive changesets in Mercurial

As landing multiple patches together has become common practice on mozilla-central, we’ve started a semi-official policy of requiring people to back out all of the changesets in their push if something breaks.  This is a good thing, because mozilla-central is not a very good place to test bustage fixes, and it helps the tree to get to a good state very soon.

However, when you want to back out multiple patches in a push, backing them out individually using hg backout is a real pain, it basically means that you have to merge N times if you have N patches to back out.  There is an easy way to back out multiple patches in Mercurial though, and I’ve been asked about this by people in IRC several times recently, so I figured I’d blog about it since people seem to need it.

Let’s say you’ve pushed N consecutive changesets, with the first one having the changeset ID cset1 and the last one having the changeset ID csetN.  You also need to know the the ID of the parent changeset for cset1.  Let’s call that csetP.  To back out everything from cset1 to csetN (inclusive), you should do something like this:

hg pull # make sure you have a recent tree
hg update csetN # update to the last changeset in the range
hg revert -a -r csetP # revert to the parent of the first changeset
hg commit -m "Back out bug xxxxxx, bug yyyyyy, ..." # commit the backout
hg merge # if csetN is the repository's tip, merging is not necessary
hg commit -m "Merge backout, a=bustage fix" # commit the merge
hg push # push the backout

Tagged with: , ,

Bugzilla Tweaks now available as an extension

Some of you might remember reading my blog post on my experience about porting the Bugzilla Tweaks jetpack to the Jetpack SDK.  I talked about almost everything in that post except where you can find the actual extension!  That was intentional, because there were quite a few bugs in the early versions, and I didn’t want to release something which is basically broken.  But those issues have been mostly solved now, and I’m releasing the jetpack as a Firefox extension.

You can find the extension’s home page here, or you can grab the extension directly from AMO.  Please note that this extension can be installed in Firefox nightly versions without having to restart the browser!  Also, please note that once you install this extension, you can safely uninstall the Jetpack Prototype extension (if you don’t use it for other purposes of course) as this extension is self-contained and does not depend on any other extensions.

The source code for this extension has been moved to my extensions repository.  The old source code respositry for the Jetpack Prototype based script is still available, but is not going to be maintained any more.  All future updates will be made to the new repository.  The source code is being released under the MPL/GPL/LGPL tri-license.

I’m eagerly looking for your feedback, especially if you can find something which is broken.  Please comment here or contact me directly!

Tagged with: , ,

Bugzilla Tweaks Extension

Bugzilla Tweaks

Bugzilla Tweaks is an extension for Firefox, which is aimed at people involved in the Mozilla project.  Bugzilla Tweaks modifies bugzilla.mozilla.org to make it smarter and easier to use.

Bugzilla Tweaks Preview

Rationale

Bugzilla (the issue management software used by the Mozilla project) is a great tool.  But it’s not perfect.  This is an attempt to change that!

For example, bugzilla by default shows you the comments made on a bug in one page, and the other changes made to it (such as flags, status, assignee, etc.) in another page.  It makes it very hard to figure out when a flag was set.  It doesn’t help you a lot in finding a user when you want to CC them on a bug.  And many other small or big problems which annoy you everyday.

These problems could be solved both on the client side or the server side.  I didn’t know Perl, so that’s why I attempted to solve these problems on the client side instead.

How to Get It?

Installing Bugzilla Tweaks is as simple as installing any other Firefox extension.  Simply, view the Bugzilla Tweaks extension’s page on AMO, and grab the latest version from there.  The latest version currently is 1.8.  Installing this extension doesn’t even require you to restart your browser!

How It Works

After installing the extension, just open any page in bugzilla.mozilla.org, and you’ll notice the differences.  I’ve written some posts in the past which talk about some of the enhancements that this extension makes to Bugzilla, and there are even some enhancements which I have not had the time to mention yet!

Source Code

The source code for this add-on is available on bitbucket.  Feel free to grab it and read it, or change something and send me pull requests!

Known Problems

None so far!

Acknowledgments

Thanks to Johnathan Nightingale for starting the original version of this extension in form of a jetpack, and Steve Fink and Heather Arthur for their code contributions.  Also, thanks to the Jetpack team for providing a rich platform on which you can develop extensions.  And thanks to all the wonderful people who provided me with feedback on what they wanted to see in this extension, and what they liked or didn’t like about it!

My experience with the Jetpack SDK

Recently, I decided to convert my Bugzilla Tweaks jetpack to an extension based on the Jetpack SDK, which is still under development.  This post is meant to be a document of my experience with the Jetpack SDK for creating a real-world and useful extension for Firefox.

As the very first step, I needed to actually get the SDK set up and running.  So, I went straight to the Getting Started guide.  Here is how I set it up.  I cloned the hg repository (to make sure that the process of updaring my extension to future versions of the Jetpack SDK is as easy as just updating the repo and rebuilding the extension).  At this point, you can make a choice.  You may either want to stay on tip, or update to a release version (which may be a little more stable than tip — but remember that the Jetpack SDK is still under development).  I chose to update to 0.4, which is the latest released version as of this writing.

Then, I went ahead with . bin/activate and cfx testall, to make sure that I’ve get a working environment up and running.  I sat there and watched the command prompt waiting for the tests to be completed, but I got tired and pressed Ctrl+C to cancel the operation after about 5 minutes.  Then, I decided to run cfx testall –verbose to see what’s happening, but again, it just went yoohoo after running some tests.  I canceled again and decided to just assume that everything is working correctly, for lack of a better way to actually verify that.

Then I proceeded to read the Packages documentation.  I skimmed over it, and then proceeded to the Programs documentation.  That seemed to be interesting, so I read that more thoroughly.  It all seemed easy enough.  The only strange part was that I seemed to have to create my packages under the Jetpack SDK directory.  That seems less than ideal to me, but I decided to try to create a real directory for my extension somewhere, and just add a symlink to it under the packages directory.  That worked, which was nice.

After this point, I just copied the old bugzilla-tweaks.js file as lib/main.js, and started to figure out how to make the extension do something useful.  Before anything else, I’d need something equivalent to the Jetpack Prototype’s pageMods facility.  So, I grabbed Atul’s persistent-page-mods.js module, and started looking at it (he’d pointed me to it here).  Soon I figured out that I needed to have the dependencies of this package available as well.  I searched for "require" in that file, and found out that it depends on timer, errors and unload-2.  The only one not available in jetpack-core was the latter, so I grabbed it as well.  unload-2 itself didn’t have any dependencies besides unload, which ships in jetpack-core, so the dependency search was done.  One thing that I wish we had was a tool to recursively extract the dependencies from any given package.  Atul also told me that I needed the tab-browser package, but I noticed that it’s there in 0.4.

Then I stole this code to get the pageMods functionality hooked up.  This far into the process, I’m loving how easy it is to use other people’s packages and code in your new Jetpacks.  I think that’s going to blow away how people write extensions for Firefox and other Mozilla-based applications.

For the most part, the Bugzilla Tweaks jetpack is a bunch of DOM API calls, and I expected those parts to just work.  I only needed to port my Jetpack Prototype API usage over to Jetpack SDK APIs.  In addition to pageMods, I used jetpack.menu to add context menu items, and jetpack.clipboard to modify the clipboard.

The context-menu API documentation was straightforward, and I ported my usage of the jetpack.menu API to context-menu very quickly.  Porting jetpack.clipboard was a bit more involved, though, because jetpack-core does not include a clipboard module yet, so I had to write my own.

I decided to go with the JEP specification of the clipboard API, which has not been implemented yet.  This is a relatively simple API, providing three methods: get, set and getCurrentFlavors.  For this extension, I only needed the set method, so that’s what I implemented for now.

I also had two direct XPCOM call sites in my original Jetpack, one for reading a preference, and the other for reading a cookie.  Jetpack SDK comes with a preferences-service package, so I decided to use it.  I also created a small cookiemanager package and switched to using it.  The benefit of this is that if in the future, the Jetpack SDK does not allow direct usage of XPCOM components, I can just modify one package.  Also, I can use the package in my other projects, and so can others!

Now was the time to try the extension for the first time!  Before generating the XPI, I added a few more fields to the package.json manifest, and then I ran cfx xpi.  It told me that I needed to remove the id field from the manifest, which I did.  The next time I ran cfx xpi, it told me that the manifest is updated, and I need to run the cfx xpi again.  This was kind of strange, and less than ideal (why didn’t the tool do what’s needed on its own?).  Anyway, I re-ran cfx xpi, and finally I had an XPI, waiting to be tested.

But before testing, I was curious to see for myself what the generated XPI contains.  So, I unzipped the package, and started looking around.  The generated install.rdf contained entries for Firefox, Fennec and Thunderbird.  I found that strange.  I was never asked which applications this extension is compatible with.  I’m pretty sure that it won’t be compatible with Thunderbird, and I don’t even know what will happen if I try to install the XPI on Fennec.  And if the goal is for the extension to be compatible on all Mozilla-based applications, it should be a toolkit extension, right?

I also noticed that the install.rdf contains a bootstrap element, which means that the extension can be installed without Firefox being restarted if you use a trunk version.  Nifty!

Then, there was the resources directory, which contained a copy of all the Jetpack packages, both in bugzillatweaks, and in jetpack-core.  What I found really broken was that .main.js.swp, which is the Vim swap file which was around because I had main.js open in Vim made its way to the XPI package.  Not so nice.

There was also a components directory, containing a harness.js file, which I didn’t look at very carefully.

So, I went ahead and opened up a development profile that I had set up to develop and test the old version of the jetpack in Firefox 3.6.  I disabled the original jetpack, dropped the XPI into Firefox, and restarted.  Lo, and behold!  I had my extension installed, but it didn’t work!  There was no error logged to the error console, and no possible way to tell what was going wrong.  I felt clueless as how to proceed.  I decided that having Jetpack Prototype installed might be conflicting with something, so I disabled that extension and restarted.  Still no luck.

So, I went ahead and added a bunch of console.log calls in the beginning of the main function, to see if it’s called, but apparently it wasn’t.  I decided to give things a shot with a nightly.  So, I launched a nightly Firefox from the console, and boy was I lucky to have done that!  I got this error on the console (that is, the OS X Terminal application):

error: An exception occurred.
Traceback (most recent call last):
  File "resource://jid0-qbniplfdfa4lpdrjhac6vbqn20q-bugzillatweaks-lib/main.js", line 340, in null
    });
SyntaxError: syntax error

OK, that explains a lot.  But I found this out completely out of luck.  The SDK really needs to expose such errors in a more discoverable way.

So, I went ahead and fixed the syntax error, re-generated the XPI, and opened it in Firefox.  Because it’s a rebootless add-on, it didn’t require the browser to restart, and I got "info: main" on the console (again, the OS X Terminal application), which was the debugging message I had added to my main function, so the jetpack was correctly loaded!  

But apparently I have to watch the Terminal window instead of Firefox’s error console, which sucks.

From there on, I spent some time debugging using console.log calls, and finally I managed to have a working Jetpack.

The entire process was rather pleasant.  I hit a few bumps along the road, as I explained above, but hopefully others will read this post and know how to avoid them while the amazing guys in the Jetpack SDK team fix those issues.

Tagged with: , , ,

Making sense of Firefox startup time

One of the things that we at Mozilla would like to do better at is the amount of time it takes between when you launch Firefox, and when it starts up and is usable.  We’ve been tackling this problem for quite a while, and have already made tremendous improvements.  But we think we can still do better.

Last week, Vlad landed the function timer API, which can be used for producing a log of how much time it takes to execute any given code block.  This is a very useful framework for measuring how much time different things consume at Firefox startup.  On Monday, I, Vlad, Shawn, Johnathan, and Shaver started to look into instrumenting Firefox to produce a useful log of what goes on at Firefox startup, to be able to analyze it to identify the areas that we’re being slow at, in order to focus our attention to improve those pieces of code.

I set up a clone of mozilla-central here to so that we can focus on adding probes to the code without being slowed down by trying to lands things on mozilla-central for now.  Then, we started to add probes like crazy.  The probing work is really finished now, and I think that we’ll spend some time tomorrow to try to analyze the logs, in order to be able to make some sense out of them, and identify the areas where we can attack in order to get the most gain in reducing the startup time.

If you want to create your own startup logs, here are the steps to do that.  Please note that these instructions are for Windows.  Other platforms can be measured similarly, but we’re trying to focus our attention to Windows for now.

  1. Clone the repository.
  2. Your measurement would be most useful if you create a build similar to our release versions of Firefox.  In order to do that, you can grab a copy of the mozconfig file which we use for our release builds.  Make sure that you add ac_add_options –enable-functiontimer so that your build actually includes the probes, and remove the –enable-update-channel and –enable-update-packaging options, to make sure that you don’t mess with the release update channels.
  3. Build firefox, and create an installer:
    make -f client.mk build
    make -C objdir package
    make -C objdir installer
  4. Go to objdir/dist/install/sea, you will find a file named something like firefox-3.7a5pre.en-US.win32.installer.exe there.  This is a normal installer.  Use that to install this version of Firefox somewhere on your system.  Please note that you don’t want to replace this with your default Firefox install, since it’s built from a random revision off of mozilla-central, and it’s subject to all the usual warnings when running experimental builds.
  5. Set the MOZ_FT environment variable to the full path of a file which will be used as a log file, for example: C:\Users\ehsan\startup.log.
  6. Execute the installed version of Firefox.  As soon as you see the window on screen, type an address like mozilla.com inside the location bar, press enter, wait for the page to load, and then close Firefox.
  7. Open the log file you specified in step 5.  Try to find the address that you entered in step 6 in that file.  Anything before the first occurence of the address is what happened before Firefox started up and became usable on your system.

Here is a bit of information about the format of the log.  On each line, you will see a pattern like this:

[   123.45] >5)       |nsContentDLF::CreateBlankDocument (line 349)
[   244.43] * (  2)   |        0.50 ms (     0.65 ms total)NS_InitXPCOM3_P (line 480) [Next: timer startup]
[   330.21] < ( 10)           |      3.48 ms (     3.48 ms total)mozJSComponentLoader::Import (line 1444)
(file: resource://gre/modules/XPCOMUtils.js)

Here is what each of these items mean:

  • Time stamp in ms.  This is the time passed since Firefox was started when this message was being added to the log.
  • >, *, or <.  These include three types of logs: function entry, function marker, and function exit, respectively.  The first and last ones are obvious.  The function marker is used for a few very large functions in order to enable us split up the function’s execution time in chunks, so that we can know how much time a function took to execute.
  • Call nesting depth.  It is a number indicating the depth of the call.  It can be used to show whether a function has been called (directly or indirectly) by another one.
  • Function name and line number.  It shows the function in which the log was recorded, and which line in the respective source code it has been defined on.
  • Elapsed time and total time.  These two numbers show how much time has been elapsed inside the function, and how much total time the function has been executed so far.  Note that these numbers are not applicable to function entries.  Also, note that they will be equal on function exit, because the log is generated as the last step inside the function.
  • Marker identifiers.  These are only used for function markers, and usually show what is going to happen next inside the function.
  • Extra information.  Some of the log lines have some extra information associated with them.  For example, the third line in the sample above shows that the module being loaded was XPCOMUtils.js.

Johnath has also adapted a script to generate graphs from the logs, but at this point, we’re thinking that the graphs are misleading, and therefore I’m not going to talk more about this, but check the bug for more information (including how to create such graphs, and some graph samples.)

The next steps probably include finding out where there are gaps in our logs, and try to add probes to cover those areas.  We also need to generate logs for a range of different profiles, including blank and heavy ones.  We need to generate a variety of logs to ensure that we’re not missing any obvious use case of Firefox.  We are also trying to figure out which types of visualizations for this data would be helpful, to be able to better filter/present the generated logs.  Hopefully, we’ll soon have a number of actionable tasks which we can pursue to reduce Firefox startup time to a significant degree.

If you have any ideas how to improve things, or have any logs which we need to see, either comment here or in the bug.

Tagged with: , , ,

Assisted starring of oranges

As a good citizen in the Mozilla developer community, you need to watch the tree, and star any random oranges with bug numbers, and put a comment inside the relevant bugs with a link to the log of the orange in order to help debugging the problem.  That’s too much work, and worse, it’s repetitive and boring.  Last weekend, I got sick of it, and decided to hack Tinderboxpushlog to make this a bit easier.  That work is now deployed on Markus‘ instance of Tinderboxpushlog for you all to enjoy.

How to use it?

It’s easy.  Click on a machine name in a build.  A summary of the log appears.  If there are any suggestions available, they will be listed inside the summary, like below.

Bug suggestions inside the log summary

Here, Tinderboxpushlog has found three suggestions for the test failure.  It’s your job to go and read the bugs to figure out which one of the three this failure is related to.  Also, note that the third suggestion has been marked as strike-through, that’s because it’s a resolved bug (I chose to show the suggestions for bugs which have already been resolved because sometimes they need to be reopened, and sometimes there are not resolved on the branch that you’re watching.)  The status of each bug appears as a tooltip of its link.

After you choose which bug is relevant, and you want to star it, you press the Add a comment link as usual.  The dialog which appears should contain suggestions in addition to the usual fields, like below:

Suggestions in the Add Comemnt dialog

You can click on any of the suggestions, and Tinderboxpushlog will add that bug to the comment box.  From that point, you can modify the comment text if needed, and click Add Comment when you’re done.  The orange will be starred as usual, but something else happens as well:

TinderboxPushlog Robot making a comment on the bug

We have hired a robot whose only job is to watch the tinderbox, and go ahead and add a comment to the bug with the log link and a bunch of helpful info.  Please meet TinderboxPushlog Robot, or as his friends call him, tbplbot.  He’s not that smart, but he knows not to comment on the same bug about the same log twice.  I’m posting a picture of him due to popular demand:

TinderboxPushlog Robot

Are there any insider tips?

Just one.  If for some reason you don’t want to add a comment to the bug, you should avoid clicking on the bug link in the Add a Comment dialog (and type in the bug number if you want).  tbplbot is smart enough to honor your request and not comment in the bug.

Wait, I don’t get suggestions in my summary logs!

In order to maximize the performance, and minimize the chance of double-starring, we don’t show suggestions for already-starred logs.  Also, the suggestions are made by looking at the log summary for file names, and looking them up in Bugzilla, so they won’t work for things which typically don’t have those in the log summary, such as leaks and crashes.  If there is a file name, the log is not starred, and still no suggestions appear, there might be a good chance that there’s no bug on file for that orange.  But remember, you should go ahead and search Bugzilla yourself to make sure that the algorithm has not missed something.

I want to help!

Great!  Clone Markus’ repository, file a bug for what you want to do, and hack away!

That’s it!  Go and star some oranges.  Or better yet, try to fix a few of them!

Tagged with: , ,

Text field lazy initialization

I just landed a set of patches on mozilla-central which makes the initialization of the editor for text fields (input type="text" and input type="password" in HTML terms) lazy.  What we used to do was to initialize the editor component for text fields as soon as we created frames for those elements.  This was not ideal, because users don’t usually use all of those fields on web pages (think about the "search" text fields you see on every website nowadays, for example.)  It also made Gecko significantly slow for pages which included a lot of those elements.

What these patches do is that they defer the initialization of the editor component (which actually allows you to type into the fields, copy and paste stuff, undo/redo your edits, etc.) until when the user is most likely to use it (for example, when the control is focused, or receives keyboard input.)

The work to make this happen was a lot more than I originally anticipated.  It uncovered a number of other problems, which I’ve already fixed or I’m going to.  It also proved to be a long journey as I saw different changes in the tree break my work a lot.  Overall, those problems should have made the patches more robust, but I thought I’d post this change here so that nightly testers can have it in their minds in order to track any possible regressions.  These changes will be in tomorrow’s nightly build.

Update: Actually, I spoke too soon.  The changes caused a problem and I had to back them out.  Hopefully the problem is resolved soon and I’ll re-land the patches.

Update 2: The code has landed and  has been stabilized on trunk now.

Tagged with: , ,

User name autocomplete in Bugzilla

Atul Varma has built an user name autocomplete tool for Bugzilla.  This reminded me that it’s been a long time since I wanted to add this functionality to the Bugzilla Tweaks jetpack.  Last week I added this feature, but I didn’t get the time to blog about it!

Here is how it looks on a a sample bug:

User name autocomplete for the Assignee field

It is also smart enough to handle multiple users for fields which accept it.

User name autocomplete for multiple users

It works on almost everywhere in Bugzilla where you can enter a user name.  Here is the full list for the curious:

  • CC field on bug pages (both when viewing and filing a new bug)
  • Assignee field on bug pages (both when viewing and filing a new bug)
  • Requestee field on attachments (when you request a flag, like review, from someone)
  • User name entry fields on the advanced search page
  • Add user watch field on the preferences page

This is providing the same functionality of Atul’s tool, with two added benefits: it provides the functionality right where you need it, and doesn’t require you to enter your user name and password.

No more memorizing people’s email addresses!  No more asking around for their email addresses!  No more bugzilla error pages telling you that the user name you entered doesn’t exist, or couldn’t be matched exactly!  I hope you like the idea.

The jetpack lives here.  If you have already installed it, you can either rely on Jetpack Prototype’s auto-update feature, or refresh it manually.

Tagged with: , ,

Jetpack Prototype with trunk support

If you use Firefox nightly builds, and you had the Jetpack Prototype installed, you might have noticed that about two weeks ago, your jetpacks had started to get disabled a short while after you had opened your browser.  This issue was really frustrating, since some of us run jetpacks which are very important in our daily work.

I filed bug 554169 about this issue.  Paul O’Shannessy fixed this, and earlier this week, the Jetpack team released a new version of the Jetpack Prototype which fixes this issue.  You can install it from AMO, and your jetpacks will resume working reliably on nightly builds.

Thanks a lot to Paul, Myk and Atul for making this happen!

Tagged with: , ,

C++ AutoComplete feature in VIM

I really needed a context-sensitive C++ autocomplete feature for Vim, which would allow me to do crazy things like autocompleting class member names.  As it turns out, there is a way to do that, and it works pretty well.  I decided to write up how I set things up myself, in hopes that this will help others as well.

Here is what you need in order to set things up:

So, you need to install Vim and Ctags (which is platform dependent, and I leave it to you to figure out how to do that in your own platform).  Once you get those set up, grab the OmniCppComplete plugin, and extract it to the .vim directory under your home directory (create it if it doesn’t exist).  After that, you want to put the following inside your ~/.vimrc:

" omnicppcomplete options
map  :!ctags -R --c++-kinds=+p --fields=+iaS --extra=+q -f ~/.vim/commontags /usr/include /usr/local/include ~/moz/obj-ff-dbg/dist/include
set tags+=~/.vim/commontags

" --- OmniCppComplete ---
" -- required --
set nocp " non vi compatible mode
filetype plugin on " enable plugins

" -- optional --
" auto close options when exiting insert mode or moving away
autocmd CursorMovedI * if pumvisible() == 0|pclose|endif
autocmd InsertLeave * if pumvisible() == 0|pclose|endif
set completeopt=menu,menuone

" -- configs --
let OmniCpp_MayCompleteDot = 1 " autocomplete with .
let OmniCpp_MayCompleteArrow = 1 " autocomplete with ->
let OmniCpp_MayCompleteScope = 1 " autocomplete with ::
let OmniCpp_SelectFirstItem = 2 " select first item (but don't insert)
let OmniCpp_NamespaceSearch = 2 " search namespaces in this and included files
let OmniCpp_ShowPrototypeInAbbr = 1 " show function prototype (i.e. parameters) in popup window
let OmniCpp_LocalSearchDecl = 1 " don't require special style of function opening braces

" -- ctags --
" map +F12 to generate ctags for current folder:
map  :!ctags -R --c++-kinds=+p --fields=+iaS --extra=+q .
" add current directory's generated tags file to available tags
set tags+=./tags

" Setup the tab key to do autocompletion
function! CompleteTab()
  let prec = strpart( getline('.'), 0, col('.')-1 )
  if prec =~ '^\s*$' || prec =~ '\s$'
    return "\"
  else
    return "\\"
  endif
endfunction

inoremap  =CompleteTab()

You can of course customize this however you like, but the only part that you really need to customize is the second line.  You would probably want to leave /usr/include and /usr/local/include there, but you can replace ~/moz/obj-ff-dbg/dist/include to whatever project specific directory which contains header files which contain definitions which you want to include in the C++ autocompletion.  ~/moz/obj-ff-dbg/dist/include is a path on my system which contains all header files we use in Mozilla.

The autocompletion functionality is based on the ctags database.  This is a list of all symbols found in header files.  With this setup, you have two separate ctags databases, one is for your system-wide headers (which should change rarely), and the other is for your project-specific symbols.  The former is stored in ~/.vim/commontags, and the latter is stored as a file named tags in your current directory.  To update the system-wide ctags database, you can use Ctrl+X, Ctrl+X, Ctrl+T.  To update the local ctags database (which is created from the contents of the current directory, recursively), you can use Ctrl+X Ctrl+T.  You would usually update the local ctags database from time to time to make sure that the latest changes in your source files are reflected in the ctags database.

Now, open a C++ file inside Vim.  Let’s say you type the beginning of a symbol, and then press Tab.  A list of symbols matching what you have types appear on the screen, like this:

Autocompletion using tab

Also, if you type ., -> or ::, you will be presented with a list of autocomplete options as well.

Autocompletion after .Autocompletion after ->Autocompletion after ::

And that’s it! If you feel adventurous, you can type :help omnicpp in Vim and start exploring what else you can do, but this setup is working perfectly fine for me.

Tagged with: ,
Top