Ask Ubuntu is a question and answer site for Ubuntu users and developers. Join them; it only takes a minute:

Sign up
Here's how it works:
  1. Anybody can ask a question
  2. Anybody can answer
  3. The best answers are voted up and rise to the top

The backstory is that the normal Intel GPU drivers don't do the various OpenGL extensions that my hobby coding and some games want. So I have to install xorg-edgers and then its happy. However, last Wednesday or so there was an update to xorg-edgers - lots of packages - and it broke badly; the drivers lock up and take the whole computer with them; hard reset required.

So how can you downgrade - select package versions in a PPA that represent a point in the past, ignoring versions newer than that?

share|improve this question

Using xorg-edgers ppa for daily work could be a pretty bad idea.

It may gives you latest drivers, true, but you can also get not working drivers.

To remove a PPA and downgrade the packages replaced by it (so going back to the ones available on the official repositories), first install ppa-purge:

sudo apt-get install ppa-purge

And then remove the PPA, downgrading gracefully to official packages:

sudo ppa-purge ppaname

This should downgrade your packages back to official ones.

Other packages that were in PPA but not in official repositories won't be uninstalled. You should manually tell the package manager to remove them, for example using apt:

sudo apt-get purge packagename

You can find the name of the ppa looking at the "Software Sources" section of Ubuntu Settings, and see a list of packages it provides on its launchpad page (or looking at the "Origin" section of Synaptic Package Manager, if installed).

share|improve this answer
As I said, the normal drivers don't work for me. I need xorg-edgers. I just want to sidestep the very latest version of my drivers. – Will Jun 27 '11 at 19:47
ten the next time you use xorg edgers ppa (and works) just disable the ppa and stick with those package versions – xangua Jul 4 '11 at 19:24
sudo ppa-purge ppa:someppa/ppa – DmitrySandalov Dec 22 '14 at 15:25

I had the same problem today, I noticed that ~2 weeks ago I installed updates to my system and still had ubuntu-x-swat ppa enabled which had a new nvidia driver. The old one was fine, the new one broke my system (only slightly, it took me a while to notice).

So I looked in /var/log/apt/history.log to find the previous version number of the nvidia driver package I had installed and then tried to find the package in /var/cache/apt/archives, where you'll normally find all packages downloaded by apt, but it wasn't there. And the ppa does not keep previous version of its packages around once they are superseded by a newer version so I couldn't get it from there either.

But, the diff from the previous package version to the newer is kept in the ppa for all versions, and together with the original tarball and its debian patches it is possible to reverse all changes of the newer version and get the previous version sources.

I'll briefly describe the neccessary steps:

  • Go to the ppa, find the newest package version and download the original tarball and the (optional) debian patches, in my case those were found on that page:

    The original tarball is named:


    The debian patches that make a buildable package out of the tarball is:

  • Extract those somewhere preferably in a new and empty directory, then apply the patches to the source tree

    ~/nvidia> tar xvzf nvidia-graphics-drivers_290.10.orig.tar.gz
    ~/nvidia> gzip -d nvidia-graphics-drivers_290.10-0ubuntu1\~lucid\~xup1.diff.gz
    ~/nvidia> patch -p0 < nvidia-graphics-drivers_290.10-0ubuntu1\~lucid\~xup1.diff

    You should not get any rejected chunks when patching.

  • On the same ppa page you'll find a diff from the previous package version to the one you are looking at, under the "Available Diffs" secton.

    For me that was:

    diff from 285.05.09-0ubuntu1~lucid~xup1 to 290.10-0ubuntu1~lucid~xup1
  • Download that, extract and reverse apply it to the patched original sources:

    ~/nvidia> gzip -d nvidia-graphics-drivers_285.05.09-0ubuntu1\~lucid\~xup1_290.10-0ubuntu1\~lucid\~xup1.diff.gz
    ~/nvidia> patch -R -p0 < nvidia-settings_285.05.09-0ubuntu1\~lucid\~xup1_290.10-0ubuntu1\~lucid\~xup1.diff
  • Presto! Now you should have the previous version source tree ready to build a package:

    ~/nvidia> mv nvidia-settings-290.10/ nvidia-settings-285.05.09
    ~/nvidia> cd nvidia-settings-285.05.09/
    ~/n/nvidia-settings-285.05.09> dpkg-buildpackage
  • Which should give you a the previous version package that can be installed with dpkg:

     ~/n/nvidia-settings-285.05.09> cd ..
     ~/nvidia> sudo dpkg -i nvidia-current_285.05.09-0ubuntu1\~lucid\~xup1_amd64.deb
share|improve this answer

In the future, if you're using synaptic (assuming you can boot into X) you can select from the available versions by highlighting the package to be changed and then selecting 'force version' from the menu. From there you should be able to downgrade.

share|improve this answer

[Original Poster]

Not having much fun, I wrote a script to compute the difference and execute the restore command; there were about 100 packages involved. Sadly my downgrade failed as many packages are no longer available :(

#!/usr/bin/env python

import sys, getopt, os
from datetime import datetime
datefmt = "%Y-%m-%d %H:%M:%S"

dry_run = True
    opts,args = getopt.getopt(sys.argv[1:],"y")
    if not args:
        raise Exception("no date specified")
    elif len(args) == 1:
        args.append("00:00:00") # default time
    elif len(args) != 2:
        raise Exception("unexpected arguments")
    snapshot = datetime.strptime(" ".join(args),datefmt)
    for opt,_ in opts:
        if opt == "-y":
            dry_run = False
            raise Exception("unsupported option %s"%opt)
except Exception as e:
    print "error:",e
    print "usage:",sys.argv[0],"[flags] YYYY-MM-DD [HH:MM:SS]"
    print "flags: -y = for real; don\'t just show it, restore it"

# work out what to do
history = {}
restore = set()
remove = set()
with open("/var/log/dpkg.log","r") as log:
    for line in log:
        date,time,action,line = line.split(None,3)       
        when = datetime.strptime("%s %s"%(date,time),datefmt)
        package,ver = line.strip().split(None,1)
        if when <= snapshot:
            if action in ("upgrade","install"):
                prev_ver,new_ver = ver.split()
                history[package] = new_ver
            elif action == "remove":
                if package in history:
                    del history[package]
                    print "(cannot remove %s)"%line
            if action == "install":
            elif action == "upgrade":
                if package in history:
                elif package not in remove:
                    print "(cannot revert %s)"%line
            elif action == "remove":
                if package in history:
                elif package in remove:
                    print "(cannot revert %s)"%line

# show what to do
for package in restore:
    print "restore",package,history[package]
for package in remove:
    print "remove",package

# do it
if not dry_run:
    print "======"
    def execute(cmd):
        print cmd
    #execute("apt-get remove "+" ".join(remove))
    execute("apt-get install "+" ".join("%s=%s"%(package,history[package]) for package in restore))
share|improve this answer
Poor you. Did you know that the installation history is just available in /var/log/apt/history.log? – Lekensteyn Jun 27 '11 at 21:13
dpkg.log is the same info but also including other apps than apt. – Will Jun 27 '11 at 21:15
What other apps use dpkg directly then? Synaptic is a front-end of apt-get. – Lekensteyn Jun 27 '11 at 21:21
the user can use dpkg directly; the user may use gdebi or some other tool instead too. I had to pick a file to parse, so I picked the one proper file - dpkg.log. It happens I use apt exclusively, but same difference. – Will Jun 27 '11 at 21:30

Your Answer


By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.