Must I compile all the kernel source code due to some modification to sched.c? - linux

I'm studying the linux kernel. I have modified sched.c to specify my own scheduling policy. But it takes more than 50 minute to recompile into my custom kernel. Why does I have to compile untouched source code? Is there any way to compile only sched.c?
I type the following commands to recompile the kernel in the directory /usr/src/linux-version.
sudo make
sudo make modules-install
sudo make install
Thank you in advance.

The kernel makefiles are usually quite clever about not rebuilding unless it's really required.
Are you perhaps also modifying sched.h? I'd expect that file to be included all over the place, so rebuilds are likely. If you're only modifying sched.c it shouldn't be rebuilding everything.
PS: If you're interested in learing about advanced (GNU) make those makefiles are gems. There are a couple of really neat ideas in them.

Related

Building Linux Kernel (linux-4.10.10.tar.xz) from source

Can someone explain the process of building linux-4.10.10 from source for a beginner? From my research, the answer to my question theoretically lies in the $src/Documentation/kbuild directory, however, the kbuild.txt and kconfig.txt are kinda complicated to understand assuming these are actually the files containing the instructions I need to follow.
Basically, how is someone suppose to understand how to build a kernel that theoretically contains helpful documentation consisting of hundreds of lines of text and possible configuration options.
The README file in the root directory is definitely worth reading. You can copy an existing config from /boot or make menuconfig to start from scratch or modify the abovementioned existing config. Then make && sudo make modules_install && sudo make install and reboot. But some more in depth reading is indeed recommended.

How can I modify the source code of random.c in Linux? And do I have to recompile the kernel to make it take effect?

I want to add some debug info or printf in the random.c in order to look deeply into the Linux random number generator. The entropy in /dev/random and /dev/urandom are both generated by random.c. My questions are:
1. Where I can find the random.c file in Linux 2.6.32?
2. What is the best way to add my modification of random source code into the kernel? Is it OK to just compile random.c and load it as loadable kernel module? Or do I have to recompile and install the kernel to make the new random.c with debug msg somehow take effect? The key point is to make sure that only one copy of random number generator is running in the kernel.
Thank you. Any kind of suggestion is highly appreciated.
random.c is linked directly into the kernel, it isn't built as a module, so you can't just recompile it alone and load it into your kernel, you need to recompile the whole new kernel.
To build the kernel, make sure you have the usual development tools installed: gcc, GNU make, etc. Some distros provide a "build-essentials" or "Development Tools" or similar metapackage that include all of the usual development tools for building the core system packages.
How you build your kernel depends on whether you have any distribution specific patches that are needed to use your system, or if you want to ensure that you use your distro's packaging system to install the kernel. If so, you should probably follow your distro's instructions for building the kernel. For example, Ubuntu's instructions, Arch's instructioins, Fedora's instructions, CentOS instructions (likely similar on RHEL 6, Red Hat doesn't provide documentation as they don't support building custom kernels), SuSE instructions.
Otherwise, if you don't mind configuring and installing your kernel manually, you can do it by hand. The following instructions should cover most distros reasonable well, but be sure to check your distro docs in case there are any distro-specific gotchas.
Download the appropriate tarball from kernel.org and decompress it somewhere. Or if you prefer, check it out using Git. Since you reference 2.6.32, I've included the latest version of 2.6.32 in the below instructions.
$ curl -O https://www.kernel.org/pub/linux/kernel/v2.6/longterm/v2.6.32/linux-2.6.32.61.tar.xz
$ xzcat linux-2.6.32.61.tar.xz | tar xvf -
$ cd linux-2.6.32.61
# or...
$ git clone git://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable.git
$ cd linux
$ git checkout -b my-branch v2.6.32.61
Now you need to do to configure it, build it, and install it. Greg Kroah-Hartmann, a leading kernel developer and stable kernel maintainer, has a free book on the subject. I'd recommend reading his book, but if you want a quick rundown, I'll summarize the highlights.
There are several ways to configure it. A good way to start is to just copy your current config in, and then run make menuconfig or make xcconfig to get a curses or graphical kernel configuration utility that allows you to easily browse and choose the right options (as there may be new options in the new kernel that you are building). Many distros install the config for a given kernel in /boot/config or /boot/config-version corresponding to the kernel version. Copy that into your source tree as .config, and then run make menuconfig or make xconfig:
$ cp /boot/config .config
$ make xconfig
After configuring it, I'd recommend adding something to the EXTRAVERSION definition in the Makefile. The contents of that are tacked on to the version, to help distinguish your modified kernel from the upstream one. I'd recommend setting it to help keep track of which is your modified kernel.
Once it's configured, just build it like anything else. I recommend using -j to run a parallel build if you have multiple cores.
$ make -j8
Now it's built, and you can install it. On most systems, the following works; if not, check out Greg's book or check your distro's documentation:
$ sudo make modules_install
$ sudo make install
And finally you have to add it to your bootloader (on some systems, make install may do this, on some it may not). Depending on whether you use Lilo, Grub, or Grub2, you may need to edit /etc/lilo.conf (followed by running sudo lilo to install the changes), /boot/grub/menu.lst, or /boot/grub/custom.cfg (followed by sudo grub-mkconfig -o /boot/grub/grub.cfg to install the changes). See the relevant documentation for the given bootloader for more details. Generally you want to copy an existing entry and duplicate it, updating it to point to your new kernel. Make sure you leave the existing entries, so you will be able to boot back into your old kernel if this doesn't work.
Now reboot, select your new kernel, and hope your system boots. Woo! You've built your own kernel.
Now that you've made sure you can do that successfully without modifications, you can make your change. You are going to want to modify drivers/char/random.c. To print out debugging statements, use printk(). It works mostly like printf(), though it's not exactly the same so check out the documentation before using it. After you modify, rebuild, and reinstall your new kernel, and reboot into it, you can see the messages printed out with printk() statements using the dmesg command.
For more information, check out Greg's book that I linked to above, the kernel README, and HOWTO, browse around the kernel's Documentation directory, and various other docs.
If you look at the Makefile for it, char driver is not meant to be compiled as a module (random.o is included as obj-y in drivers/char/Makefile).
You can read more about how to kbuild (kernel build) system works from: https://www.kernel.org/doc/Documentation/kbuild/makefiles.txt
Particularly section --- 3.1 Goal definitions touches this topic.
Generally you can search for files in kernel sources from source cross references (called LXR's). One is for example provided in http://lxr.free-electrons.com/
Indeed, you can add your modifications to the drivers/char/random.c, and recompile the char driver. After that you will have to rebuild the kernel, so that it will link also your new random.o to the kernel. And then you will have to boot that kernel, that process will depend on your distribution.
Most distributions have good/decent instructions around how to recompile/boot your own kernel.

Trying to find all the kernel modules needed for my machine using shell script

I'm developing kernel modules right now, and the build times are starting to get under my skin. As a side effect I'm taking way too many "coffee" breaks during builds.
So I was looking for a way to build only the stuffs I need for my platform. Chapter 7 and 8 of "linux kernel in a nutshell" gave a good detail of how to do that by hand. Its a good read : http://www.kroah.com/lkn/
But Although I understand the stuffs, this is still a lot of tweaks to make that work.
2.6.32 and later kernels added a new target make localmodconfig. which scans through lsmod and change the .config appropriately. So I thought I found my "automation". But this perl script has some problem too.
This thread describes the problems : https://bbs.archlinux.org/viewtopic.php?pid=845113
There was also a proposed solution which apparently worked for others , is to run the script directly instead of using make's target.
Although for me, make localmodconfig does not work at all. its because of the following :
make clean
make mrproper
cp /boo/config-'uname -r' .config
make localmodconfig
and it halts with
vboxguest config not found!!
nf_defrag_ipv6 config not found!!
vboxsf config not found!!
vboxvideo config not found!!
The thing is my kernel development environment is inside virtualbox. These vbox modules were installed when I chose to install "virtualbox guest addtion".
And the netfilter module might be a Distribution specific module(Lot of netfilter modules are not part of the mainline kernel, so its not a shock to me), which is not included in mainline kernel.
Now the workaround this obviously unloading these module and trying again. But I'm thinking if there is patch for the streamline_config.pl which will enable the user to exclude certain modules if s/he wants. Problem is I have zero knowledge about perl and I like it that way.
So my problems in nutshell
Patching streamline_config.pl so I can give a list of module name as argument which it will exclude from processing the config file.
The script is located at kernel.org
EDIT: Removed the stuff about perl script not running. As mugen kenichi pointed out (How dumb I can be?). But still make localmodconfig does not work because of not having some modules code under source tree. patching streamline_config.pl still valid requirement.
Anyone else trying to build a minimum kernel image also looking for reducing build time, should do the following:
1) copy distribution kernel config in your source tree. It can be done with either command given below:
$zcat /proc/config.gz > .config
or
$cp /boot/config-'uname -r' .config
2) Use localmodconfig target.
$make localmodconfig
It will use lsmod to find which modules are loaded at this moment. Then it will search through distribution's .config to enable them and disable others.
Its important to know that it does not always work flawlessly. So you should tweak your config further using make menuconfig. You will see some modules are still marked to be built which is in reality unnecessary for your system.
Sometimes out of tree modules may cause make localmodconfig to fail. If that's the case you can work around that issue in two ways :
a) unload the out of tree modules and try make localmodconfig again.
b) Run the perl script directly:
$chmod +x script/kconfig/streamline_config.pl
$perl script/kconfig/streamline_config.pl > .config
3) Install ccache[1]. It will improve your build time dramatically. It caches objects. So it will reduce subsequent builds.
Its possible that ccache is included in the distribution's repository so that you can install it through apt-get or yum. In CentOS its available in EPEL repo.[2]
4) Give as many cores as possible for the build job
$make -j8 CC="ccache gcc"
My results are :
real 3m10.871s
user 4m36.949s
sys 1m52.656s
[1] http://ccache.samba.org/
[2] http://fedoraproject.org/wiki/EPEL

GHC Install Without Root

So I'd like to set up a linux machine for Haskell development with one huge caveat -- no root privs on this machine. We could of course get the admins to install GHC for us, eventually. However, in the long-term then we need to hassle them when we want to upgrade, etc. So much better to do everything in userland. Which also means that we'll want to install c libs we link to in userland as well, etc. to keep everything as hassle-free as possible.
So, the question is, how, soup-to-nuts, would I go about doing a purely userland install of GHC? The machine will have gcc, and the usual toolchain. If necessary, we can start with a typical ghc install to get the ball rolling, but it would be nice not to.
Additionally, any tips on managing an environment like this would be appreciated, especially involving how such a setup can be manageable with multiple devs/accounts.
I did this too. I created a directory ~/usr and passed --prefix=$HOME/usr to all configure scripts. Using the Haskell Platform makes this process even smoother.
You obviously need a directory that all pertinent users have at least read permission on. Say /home/foo, with subdirectories bin, lib, share, .cabal. Then ./configure --prefix=/home/foo and make && make install, and make sure that /home/foo/* is before /usr/* in everybody's PATH, LIBRARY_PATH etc. You should probably start with installing gcc and c-libs there, and when everything C is installed, install ghc.
I managed to install ghc through stack by following these instructions. It worked like a charm; the only additional thing I had to do was to install the GMP library and to add it to the LD_LIBRARY_PATH.
If you want to use stack to install ghc or ghci, follow this offical manual:
download the tar.gz file from the release link (curl/wget/even scp can upload your local file to a remote server)
extract the file with tar xvzf and enter the folder test if ./stack run properly
add
export PATH="<stack_path>:$PATH"
to ~/.bashrc
Every time you start the terminal, do source ~/.bashrc
install ghci locally
stack ghci
It will install ghci automatically and launch it.

Following instructions to build LLVM to the letter, but executables aren't produced

I am running 64-bit Linux and I am attempting to build the LLVM trunk. I follow the instructions to the letter, and invoke configure with the arguments I want, followed by make. Running make install leaves each directory with no action, and running locate on a name of an llvm executable (such as clang) comes up with no results.
I do not understand what could be wrong here, but I am quite sure that no executables are produced. This exact process works for software in general. Is there some absurdly obvious thing that I am missing?
I'm using gcc 4.5 and 3.81.
Depending on whether you asked for debug or release build, you can check the stuff inside bin subdir of Debug or Release (alternatively, Debug+Assert, Release+Assert) directory in your build directory for the binaries.
If there is still nothing, then you can go to tools/ and invoke make directly to check what's going there. Doing "make VERBOSE=1" might provide some additional information.
You probably want to say what's happening and maybe take a look at what's going on and how exactly you invoked configure and make.
Here is what has been working for me on the last 4 or so Ubuntu 64 bit distros.
svn co http://llvm.org/svn/llvm-project/llvm/trunk llvm
cd llvm
cd tools
svn co http://llvm.org/svn/llvm-project/cfe/trunk clang
cd ..
./configure --enable-optimized --disable-doxygen --prefix=/llvm
make
make install

Resources