PDA

View Full Version : Environment variables in SPEC files



daihard
3rd April 2006, 10:27 AM
Hi.

I have a question about setting environment variables in the SPEC file for rebuilding an RPM package. In the Firefox SPEC file (firefox.spec), there are lines like this:

export RPM_OPT_FLAGS=`echo $RPM_OPT_FLAGS | %{__sed} s/-O2/-Os/`
MAKE="gmake %{?_smp_mflags}" make -f client.mk build
One of the source files uses this RPM_OPT_FLAGS to set the build optimization flags. So I did the following before running "rpm -bb firefox.spec":

# export RPM_OPT_FLAGS="my_own_optimization flags"
However, this new value does not get picked up by the rpmbuild - it still uses the default values set somewhere. I worked it around by hard-coding the values, but I'd rather know the correct way of setting the environment variables so they can be used appropriately in SPEC files. Could anyone help me?

TIA,
Dai

raoul
3rd April 2006, 11:53 AM
Use the provided spec file in order to rebuild a package.

For info on spec file writing, here is some info:

Read the packaging guidelines for general info (http://fedoraproject.org/wiki/Packaging/Guidelines),
the "Building RPM Packages" chapter of the Developer Guide (http://fedora.redhat.com/docs/developers-guide/ch-rpm-building.html) and the draft of the RPM Guide at http://fedora.redhat.com/docs/drafts/rpm-guide-en/.

Generally, you should not need to define any variables


%configure \
--prefix=%{_prefix} \
--with-optionA \
--with-.....

%{__make}

This should be just fine.

To create a building environment for your user, first install the fedora-rpmdevtools


# yum install fedora-rpmdevtools

and then create the directory structure and the ~/.rpmmacros file by issuing the command:


# fedora-buildrpmtree

You can set your options/optimizations either inside the ~/.rpmmacros file or in the spec file.

Hope these help.

daihard
3rd April 2006, 06:41 PM
Hi Raoul.

I am using the spec file that came with the FC5 Firefox SRPM. At the "build" section are the following lines:

%build

export RPM_OPT_FLAGS=`echo $RPM_OPT_FLAGS | %{__sed} s/-O2/-Os/`
MAKE="gmake %{?_smp_mflags}" make -f client.mk build
From what I understand, these lines take the existing RPM_OPT_FLAGS, replace "-O2" with "-Os" if such a string exists within the variable, and set it again.

Now, the default values for the RPM_OPT_FLAGS are like this: "-Os -g -pipe -Wall -Wp,_D_FORTIFY_SOURCE=2 -m32 -march=i386 -fstack-protector ..." Those values are apparently specific to Firefox - I can't find anything like that in /usr/lib/rpm/rpmrc (or anywhere else for that matter). So my take is that there's got to be a way to set this variable somewhere except for /usr/lib/rpm/rpmrc. Once I figure out where, then I can think of a way to overwrite it.

Any ideas? Thanks!

Jman
4th April 2006, 01:02 AM
So I did the following before running "rpm -bb firefox.spec":

# export RPM_OPT_FLAGS="my_own_optimization flags"
However, this new value does not get picked up by the rpmbuild - it still uses the default values set somewhere.

Sounds like in your shell you did the export command, then rpmbuild. This won't work. rpmbuild spawns it's own shell by making what you do in the spec, then running sh on it. Which is not the same environment as the one you typed rpmbuild into.

So edit the spec file and put export your custom flags there like the firefox spec does. Or edit rpmrc to affect all packages.

raoul
4th April 2006, 02:06 AM
daihard, here is an example set of custom CFLAGS inside the SPEC file:



%build

export RPM_OPT_FLAGS="-fno-PIC -O3 -march=pentium3 -mtune=pentium3 -pipe -ffast-math -fomit-frame-pointer -funroll-loops -falign-functions=4"
export CFLAGS="$RPM_OPT_FLAGS"

%configure \
--prefix=%{_prefix} \
--libdir=%{_libdir} \
--with-....

%{__make}


Please do not examine the validity of the options, or whether one overrides the other. Just an example.

Look here for the available options http://gcc.gnu.org/onlinedocs/gcc-4.1.0/gcc/Invoking-GCC.html#Invoking-GCC

raoul
4th April 2006, 02:11 AM
Also, I would recommend searching http://fedoranews.org/ for a posted spec file which can be used to create an RPM package for mozilla.org's Firefox binary.

daihard
4th April 2006, 03:17 AM
Hi guys.

Thanks for the response. However, I'm afraid I may not have been clear enough. What I really want to know is exactly where the RPM_OPT_FLAGS variable is set for the Firefox RPM. The /usr/lib/rpm/rpmrc file contains several default entries, but Firefox does not use any of them. I do not have /root/.rpmrc or ~/.rpmrc either, so where in the world are those Firefox-specific values coming from?

To be more specific, the RPM_OPT_FLAGS variable Firefox uses by default is:

-O2 -g -pipe -Wall -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector --param=ssp-buffer-size=4 -m32 -march=i386 -mtunes=generic -fasynchronous-unwind-tables
Those values must be set somewhere, right? The SPEC file (firefox.spec) simply picks it up and reset it, replacing "-O2" with "-Os".

I could certainly modify the SPEC file and hard-code the values that I want to use, but I wouldn't consider that a very clean way. The ideal for me is to figure out where those values are set and modify THAT method to use my own flags, without touching the SPEC or source files. Am I making sense?

Thanks again,
Dai

Jman
5th April 2006, 12:44 AM
If you want to make opt flag changes for a package, edit the spec file. If you want to make changes to all packages you build on your machine, edit /etc/rpmrc.

You're probably talking about the %{_global_cflags} macro, which is defined in /usr/lib/rpm/redhat/macros. Copy the lines you want to change into /etc/rpmrc and edit them. If you leave them in /usr/lib rpm will overwrite them when it is upgraded.

daihard
5th April 2006, 03:08 AM
IYou're probably talking about the %{_global_cflags} macro, which is defined in /usr/lib/rpm/redhat/macros. Copy the lines you want to change into /etc/rpmrc and edit them. If you leave them in /usr/lib rpm will overwrite them when it is upgraded.
That's it!!! Thank you! :)

So I should create a new file, /etc/rpmrc, and probably make an entry like this:

optflags: i386 %{__global_cflags} -m32 -march=athlon64 -msse2 -fasynchronous-unwind-tables
Then it will be picked up by the rpmbuild process? I will try that to see how it works.

[EDIT] I copied /usr/lib/rpm/redhat/rpmrc to /etc/rpmrc, changed the flags for "athlon," and ran "rpmbuild -bb --target=athlon firefox.spec." The process now uses my flags! I owe you a big one.

I thank everyone else for the help, too. :)

LocutusOfBorg
5th April 2006, 07:28 AM
Sounds like in your shell you did the export command, then rpmbuild. This won't work. rpmbuild spawns it's own shell by making what you do in the spec, then running sh on it. Which is not the same environment as the one you typed rpmbuild into.

I'm curious about this. Sometimes I need to change the compiler - in FC5 for instance I wasn't able to build xine-lib, faad2, mpeg4ip with GCC4, so I used gcc32. I typed in a console window

export CC=gcc32
export CXX=g++32
and then I run rpmbuild. It worked without a problem - I have the same results if I put those variables in the specfile.

If you want to make opt flag changes for a package, edit the spec file. If you want to make changes to all packages you build on your machine, edit /etc/rpmrc.
Actually, I think it is safer to edit the .rpmmacros/.rpmrc in your own home directory - so that you avoid eeven updating problems. I keep my opt_flags in the .rpmrc file.

Jman
6th April 2006, 06:16 AM
Running rpmbuild does not redefine CC or CXX. Those are in the path. It does, however, export RPM_OPT_FLAGS every time. Read the scripts rpmbuild generates as it does stuff and see.

Yes a .rpmrc file also works for just you.

daihard
6th April 2006, 09:20 AM
Yes a .rpmrc file also works for just you.
I have a (hopefully) related question. How do you enable a normal user to run rpmbuild? I mean, I think it's just a matter of pointing your rpm directory to a location inside your $HOME directory, but I don't know of a way to do that. Would you please advise?

EDIT: Nevermind. I figure it out. All I had to do was add my own %_topdir and %_tmppath in ~/.rpmmacros. :)

Jman
7th April 2006, 03:27 AM
Install fedora-rpmdevtools and run fedora-buildrpmtree in your home dir. It will make the whole spec file and rpm tree which rpmbuild can use.

daihard
7th April 2006, 05:49 AM
Install fedora-rpmdevtools and run fedora-buildrpmtree in your home dir. It will make the whole spec file and rpm tree which rpmbuild can use.
Thanks again, Jman. Looks like you're highly knowledgeable. I appreciate your time and effort to help me out. :)

Jman
8th April 2006, 03:09 AM
You're welcome.

If you're not aware of it already you can join the Extras (http://fedoraproject.org/wiki/Extras) project and help with packaging.