Kernel sources

Hi.

I am new to openWrt, and I want to make some changes in the kernel sources (I have a new driver I want to add to an external device).
I understand that only after I run the initial 'make', the sources are downloaded and compiled.
Where are the sources files are downloaded to? I found several instances of the same files... which should I change?
After I update my driver, how do I compile the kernel only (if possible)? would it create a new image file?

Thanks.

make target/linux/{clean,prepare} QUILT=1

Patches are managed using quilt and git.

make target/linux/{clean,install}

I generally run make -jN clean download world to generate an image, once I know my patches "work".

Enabling ccache under Developer Options speeds subsequent builds. Enabling logs there as well can help speed diagnosis, generally without having to re-run with V=s.

4 Likes

Thanks for you reply Jeff.

Once I compiled the KERNEL only, I just copy zImage ?

And one more question:
I noticed that my sources are duplicated in two instances:
./build_dir/target-XXXX/linux-4.14.122/drivers/...
./build_dir/toolchain-XXXXX_gcc-7.4.0_musl/linux-4.14.122/drivers/....

Which of those I should change?
If I want to handle my kernel changes in a source control, which directory should I manage?

No, zImage is not enough. Run a complete build to get firmware.

You manage the patches in git, not the edited sources. Those sources get downloaded, extracted, and patched each time. See the linked page for more.

The target build files are generally the ones needed to change what is built for the device.

3 Likes

Thanks again for your fast reply.
I followed the link you mentions, but it seems that I am still missing something, so I'll be more specific with my question.

Let's say I want to change an existing driver file. For the example, let's talk about file named usb-serial.c, which is located in /drivers/usb/serial

First, I change the original file, which is located in build_dir/target-XXX/linux-XX/linux-4.14.122/drivers/usb/serial.
Then, I understand, I have to run "make" - with "quilt=1". but according to the link you pointed, there I should run it on the package directory?
I am certainly missing something here, and I would be thankful if you could help me out here.

Thanks

Very, very roughly, as a sketch of what to look into for quilt (there is a section on that page for kernel patches too

make target/linux/{clean,prepare} QUILT=1
pushd build_dir/target-XXX/linux-XX/linux-4.14.122/drivers/usb/serial/
quilt series  # To decide where in the series to add your patch
quilt push generic-hack/835-misc-owl_loader.patch  # picking one "at random"
quilt new generic-hack/840-fix-a-problem-in-abc1234-usb-driver
quilt add usb-serial.c . # record the current state of the file
# edit the file
quilt diff # if you want to see diffs
quilt refresh
popd
make target/linux/update
git status  # should see new patch
git add path/to/your/new/patch
git commit
make -jN target/linux/{clean,install}  # Confirm that it works
make -jN clean download world   # build a complete image

You can edit multiple files in the same patch

You can add files to a patch that don't exist yet

3 Likes

The overall workflow is generally
Activate quilt
Edit source file(s) in build_dir
Run quilt push to generate a patch file in target/linux
Build

The files in target/ will not be changed by a make clean, so your patch persists (although git operations can remove it unless you also git commit like @jeff shows). The build_dir is re-constructed after make clean, and will incorporate your patch.

If you're writing or porting a driver for an entirely new device look at the documentation on how to add a kernel package.

1 Like

Thank you for your detailed reply, again.
Just i noticed that you used:

make target/kernel/{clean,prepare} QUILT=1

where it should be linux instead of kernel. isn't it?

in your last reply, you mention to push a specific patch, and In the link you mentioned earlier in this thread, they mentioned pushing all available patches. Should I push them all ?

quilt push -a

Thanks in advance.

My error, it should be target/linux

Patches are ordered when they are applied, so if you're going to put in a patch on the MTD subsystem that should be in the 400s (numbering guide on the wiki link), let's say "450" to pick a number. Then you'd want to push all the patches in the series up through 449 so that your new 450 sees the source tree as it would when the patch gets applied. One of those "earlier" patches may have already patched the files you are going to patch, changing the context of your "diff". Similarly, patches after yours may change those files yet again meaning that they need to be "refreshed" too.

Thankfully that mess doesn't happen much when you're working in your "own" directory or with relatively simple packages. It happens all the time with the Linux kernel and drivers, as well as complex, heavily patched packages.

Thank you so much for your help, Jeff.
It looks like I am starting to get things in mind.
Hopefully I will manage from here, but if not, great to know there are nice and willing to help people here.

Hi Jeff.

Following the stages here, after:

make target/linux/update

when I check GIT status, I get that the branch is up to date. it doesn't recognize the patch I have just created (and I can see it in ./ptaches/ directory).
What am I missing?
(I've created the patch, with quilt new from build_dir/target-XXX/linux-XX/linux-4.14.122/)

Thanks

Hmmm, quilt isn't the friendliest bit of software, but from what I can figure, when a patch is about to be "on top", it needs the state of the files it is going to modify. It seems like it looks through the existing patch (if any) and "adds" those, capturing the "before" state of the file in its "hidden" root/of/quilt/source/.pc/ directory (as I recall). So, if you've created a "new" patch or are working with an existing patch you need to tell quilt to remember its before state with quilt add path/to/file. If you're going introduce a new file, you need to do the same before the file is in place, so it adds "empty file" as the starting point.

Hi Jeff.
It is indeed what I did.
Each file I changed (or if added a new file) - I i did type quilt add path/filename. When I finished editing the files, and type quilt diff or quilt files, I had the list of the files.
Then I type quilt refresh, and after make taret/linux/update, I expected to see my patch as a new file for git, and I didn't.
Obviously, after a new make, all my changes were gone... :frowning:

When you created the patch, did you use one of the "standard" prefixes? I don't know what happens without one, or with one that is different.

$ quilt series | cut -d / -f 1 | sort | uniq
generic
generic-backport
generic-hack
platform

There may be more, but that's what I've got for ath79 Linux/kernel in my work tree right now. It might be different for packages.

I tried a new prefix, and when I saw it is not recognized, I tried to use quilt rename to the platform prefix. it didn't help.
I'll try now to create the patch from scratch, under the platform prefix.

Thanks for your help, Jeff.
It really helped a lot. I finally made it.
Now, if I may (should I start a new thread for that?), I want to change the kernel config as part of my patch. The config file is not located in the linux kernel directory, but under

target/linux/ramips/mt76x8/config-4.14

can I add a file to a kernel patch with the following:

quilt add ../../../../target/linux/ramips/mt76x8/config-4.14

Thanks

That config is just in “regular” git

Thanks. I noticed that, but I wasn't sure if it should be added to the patch.