EE485: Introduction to Environments & Tools
for Modern Software Development
EE485: Introduction to Environment and Tools for Modern Software Development
Life of a program
3
Building a C Program
hello.c
#include <stdio.h>
int main(void)
{
/* Write "hello, world\n" to stdout. */
printf("hello, world\n");
return 0;
}
Compile and execute hello.c
ee209@ubuntu:~$ gcc209 hello.c -o hello
ee209@ubuntu:~$ ./hello
hello, world
gcc209 is a script that executes
gcc -Wall -Werror -ansi -pedantic -std=c99
Same
Make all warnings
all warnings hardaserrors
Follow –std=c89
the ISO C standard specified by -std
use c99 standard
4
Preprocess C Code
gcc209 -E hello.c > hello.i
• Preprocessing
• Remove comments
• Processing Macros
• Substitute files in the #include
gcc209 -S hello.i
• Compile; generates an assembler language file (.s file)
gcc209 -c hello.s
• Assemble or compile but do not link
gcc209 hello.o -lc -o hello
• link
5
Shortcut of All Processes
Shortcut
hello.c gcc209 hello.c -o hello hello
C Preprocessor Linker
gcc209 -E hello.c > gcc209 hello.o -lc -o
hello.i hello
hello.i hello.o libc.a
C Compiler C Assembler
gcc209 -S hello.i hello.s gcc209 -c hello.s
6
Basics
% gcc –help
Will get all the options
%gcc [compile options] [input files] [list of libraries]
–o [outputfile]
%gcc hello.c
%gcc hello.c –o hello
7
Library
#include <stdio.h>
int main(void)
{
/* Write "hello, world\n" to stdout. */
printf("hello, world\n");
return 0;
}
Who wrote printf?
Where is the definition of printf()?
It is declared in <stdio.h>
It is defined in standard C library
The name of the standard C library is libc.a (or glibc.a for GNU C library)
8
Using library
-llibrary option
Searches the library of name liblibrary.a or liblibrary.so
Example: Using standard C library libc.so
%gcc hello.c –lc –o hello
Example: Using math libarary libm.so
%gcc hello.c –lm –o hello
Example: Using pthread library libpthread.so
%gcc hello.c –lpthread –o hello
9
Generate Executable Binary
hello.o libc.so
…100101000110100100100… …11100100000100100110…
Linker
gcc209 hello.o -lc -o hello
hello
20160001@eelab1:~$ ./hello
hello, world
10
Optimization
-On
-O0: (default) reduce the cost of compilation and make debugging
-O1: reduce code size and execution time
-O2: performs nearly all supported optimizations that do not involve a
space-speed tradeoff
-O3: optimize more aggressive than O2
-Os: optimize for size
gcc –O3 count.c –o count
11
Optimization
/* count.c */
#include <stdio.h>
#define COUNT 10000000000
int main(void)
{
for ( long int i = 0 ; i < COUNT ; ++i) ;
return 0;
}
%gcc count.c –o count
%time ./count
%gcc –O1 count.c –o count
%time ./count
Directly assign the last value of iteration to i
12
Optimization
/* count.c */
#include <stdio.h>
#define COUNT 10000000000
int main(void)
{
for ( volatile long int i = 0 ; i < COUNT ; ++i) ;
return 0;
}
%gcc count.c –o count
%time ./count
%gcc –O1 count.c –o count
%time ./count
Enforce that the i is read from memory in every iteration
13
$ gcc -v -I/usr/local/include -DDEBUG -Wall -W -O2
-L/usr/local/lib -o hello hello.c -lm
-v : output the messages to the screen
-I : location of the header file
-D : Define the macro. It is the same as writing the #define statement
-Wall : Warning all. Shows all warning
-W : shows all the rest of the warnings that cannot be shown with the –Wall option
-O2 : optimization level
-L : location of the library files
-o : output filename
-lm : link libm.so (math library)
-c : generate *.o file (simply compile and assemble the code without linking)
14
Library
A set of functions
Two types of library
Static library
Library is “statically” included in the binary program
Advantage: no dependency in the libraries installed in the system
Disadvantage: binary size becomes large. Same library can be loaded on to memory
multiple times (waste of memory)
Dynamic shared library
Library is “dynamically” linked when the program is executed
Advantage: small binary size
Disadvantage: dependency in the installed library. Relatively long execution time (to
dynamically load the library in on-demand basis)
15
main.c
#include <stdio.h>
#include "swapper.h"
#define MAX_STR 20
int main(int argc, char *argv[])
{
int a, b;
char name[MAX_STR];
printf("Pleas enter two numbers: ");
scanf("%d %d", &a, &b);
swapper_v1(&a,&b);
printf("Swapping is completed. What's your name? ");
scanf("%19s", name);
printf("Ok, %s. Two values swapped: %d %d Good job!\n",
name, a, b);
return 0;
}
16
swapper.h
#ifndef SWAPPER_H_ /* swapper.h */
#define SWAPPER_H_
void swapper_v1(int *a, int *b);
#endif
/*
swapper.c
*/
#include "swapper.h"
int buf[1024]={1}; // unused, but just to see that the
// compiler allocates memory in the binary
void swapper_v1(int *a, int *b)
{
int temp = *a;
*a = *b;
*b = temp;
}
17
Build a Static Library
$ gcc –c swapper.c
$ ar -cr libswapper.a swapper.o
Create the static library named libswapper.a with swapper.o
$ gcc –o simple-static main.c –L. –lswapper
Create the binary with the static library
-L: location of the library
-l: name of library, libswapper.a
18
Build a Shared Library
$ gcc –c swapper.c
$ gcc –shared –o libswapper.so swapper.o
Build shared library libswapper.so
$ sudo ln –s [path to libswapper.so] /usr/lib/x86_64-linux-gnu/libswapper.so
Install libswapper.so to the system
sudo cp libswapper.so /usr/lib/x86_64-linux-gnu/libswapper.so.1.0
sudo ln –s /usr/lib/x86_64-linux-gnu/libswapper.so.1.0 /usr/lib/x86_64-
linux-gnu/libswapper.so
$ gcc –o simple-shared main.c –L. –lswapper
Build binary with the shared library
Note: without “ln –s”, it would compile but not execute
$ ./simple-shared
./simple-shared: error while loading shared libraries: libswapper.so: cannot open shared object
file: No such file or directory
19
Build a Shared Library (2)
If you have both .a and .so files in –L(dir) then gcc will do dynamic linking.
You can force gcc to use static linking by:
The ldd command
20
Build a Shared Library and Install without sudo
$ gcc –c swapper.c
$ gcc –shared –o libswapper.so swapper.o
Build shared library libswapper.so
$ export USER_LD_PATH=$(dirname $(realpath [path to libswapper.so]))
$ ex) export USER_LD_PATH=$(dirname $(realpath ./libswapper.so))
USER_LD_PATH is a custom env variable to be used in LD_LIBRARY_PATH
$ export LD_LIBRARY_PATH=“$USER_LD_PATH:$LD_LIBRARY_PATH”
Add library path for ld
LD_LIBRARY_PATH is looked up first before the default path for libraries
$ echo $USER_LD_PATH
$ echo $LD_LIBRARY_PATH
You can check the changes
21
Checking symbols in a library
$nm <filename>
22
Checking symbols in an executable
23
Build a Shared Library (without sudo) Continued
Please, replace the variable in command, If you use other OS
LD_LIBRARY_PATH → ???
Windows PATH
Linux LD_LIBRARY_PATH
Mac OS X DYLD_LIBRARY_PATH
$ gcc –o simple-shared main.c –L. –lswapper
Build binary with the shared library
24
Assignment
Build the static library libswapper.a using the code provided in slide #17
Print the files that are in the libswapper.a library. Use the ar –t command
Compile main.c and link with libswapper.a (linking with a static library)
Print (ls -l) the size of the executable and compared it with the size of a dynamically linked
version of the executable. Make this visible in the screen shot.
Run the program and provide the screen shot that shows the results of the program execution
Build the shared library libswapper.so using the code provided in slide #17
Compile main.c with libswapper.so (linking with a shared library)
Print (ls -l) the size of the compiled binary
Run the program and provide the screen shot that shows the result of the program execution
Upload the screen shots (in JPG) of the result by Next Friday 10:25AM
You can combine multiple screenshots into one JPG.
25
26