Monday, 26 March 2012

What are the different ways to install any Linux Software?


There are many ways to install the software in Linux machine . Some of the ways I would like to mention here.

Case 1:  If your system is connected to Internet  then you can install any new software using the following commands.

YUM ( YellowDog Updater, Modified)

Know More about YUM
======================
This is not an exhaustive list of all yum commands but it is a list of the basic/common/important ones. For a complete list see the yum man page.

   yum list [available|installed|extras|updates|obsoletes|all|recent] [pkgspec]

    This command lets you list packages in any repository enabled on your system or installed. It also lets you list specific types of packages as well as refine your list with a package specification of any of the package's name, arch, version, release, epoch.

   yum list

    By default 'yum list' without any options will list all packages in all the repositories and all the packages installed on your system. Note: 'yum list all' and 'yum list' give the same output.

   yum list available

    Lists all the packages available to be installed in any enabled repository on your system.

   yum list installed

    This is equivalent to rpm -qa. It lists all the packages installed on the system.

  yum list extras

    This command lists any installed package which no longer appears in any of your enabled repositories. Useful for finding packages which linger between upgrades or things installed not from a repo.

   yum list obsoletes

    This command lists any obsoleting relationships between any available package and any installed package.

   yum list updates

    This command lists any package in an enabled repository which is an update for any installed package.

   yum list recent

    This command lists any package added to any enabled repository in the last seven(7) days.

   yum list pkgspec

    This command allows you to refine your listing for particular packages.

    Examples of pkgspecs:

          yum list zsh
          yum list joe\*
          yum list \*.i386
          yum list dovecot-1.0.15

   yum install/remove/update


Case 2: How to install Package using RPM
===============================

RPM command is used for installing, uninstalling, upgrading, querying, listing, and checking RPM packages on your Linux system.

RPM stands for Red Hat Package Manager.

1. Installing a RPM package Using rpm -ivh

rpm -ivh <.rpm package>

< Install rpm Package with out dependencies with --nodeps command >
rpm  --nodeps -ivh  <.rpm package>

ex: rpm –ivh panda-2.0-1.i386.rpm

If you have GUI, then double click on RPM Package then will install respective software automatically.

2. Query all the RPM Packages using rpm -qa

You can use rpm command to query all the packages installed in your system.

rpm –qa

rpm –qa | grep ‘cdrecord’

3. Query a Particular RPM Package using rpm –q

rpm –q Mysqlclient

4. Information about Installed RPM Package using rpm –qi

# rpm -qi MySQL-client
Name        : MySQL-client                 Relocations: (not relocatable)
Version     : 3.23.57                           Vendor: MySQL AB
Release     : 1                             Build Date: Mon 09 Jun 2003 11:08:28 PM CEST
Install Date: Mon 06 Feb 2010 03:19:16 AM PST               Build Host: build.mysql.com
Group       : Applications/Databases        Source RPM: MySQL-3.23.57-1.src.rpm
Size        : 5305109                          License: GPL / LGPL

5. If you have an RPM file that you would like to install, but want to know more information about it before installing, you can do the following:

# rpm -qip MySQL-client-3.23.57-1.i386.rpm

6.  Upgrading a RPM Package using rpm –Uvh
                                                                                                                                                                                                              
Upgrading a package is similar to installing one, but RPM automatically un-installs existing versions of the package before installing the new one.
If an old version of the package is not found, the upgrade option will still install it.

# rpm -Uvh MySQL-client-3.23.57-1.i386.rpm

7. Uninstalling a RPM Package using rpm -e

To remove an installed rpm package using -e as shown below. After uninstallation, you can query using rpm -qa and verify the uninstallation.

# rpm -ev MySQL-client

8. List the Dependency Packages using rpm -qRP

To view the list of packages on which this package depends,

# rpm -qRp MySQL-client-3.23.57-1.i386.rpm
/bin/sh
/usr/bin/perl

Case 3: How to install .tar package or .tar.gz package.
========================================

Step 1: First untar (Extract) the package  using the following commands.
    
       .tar         ->      tar –xvf  <package.tar>

        .tar.gz   ->     tar  -zxvf  <package.tar.gz>

       
Step2:  Change directory to the package source directory.

Step3:  Run
./configure
Step 4:     make
Step 5:   make install

Small Example:

Try installing wireshark using the above procedure.

1.Download wireshark-1.7-tar.gz from wireshark.org

2. Unpack the source from its gzip'd tar file. If you are using Linux, or your version of UNIX uses GNU tar, you can use the following command:

tar zxvf wireshark-1.7-tar.gz
3. Change directory to the Wireshark source directory.

4. Configure your source so it will build correctly for your version of UNIX. You can do this with the following command:

./configure
                   
5. Build the sources into a binary, with the make command. For example:

make
                   
6. Install the software in its final destination, using the command:

make install
7. Once you have installed Wireshark with make install above, you should be able to run it by entering wireshark.
Wireshark &

References:
http://www.wireshark.org/docs/wsug_html_chunked/ChBuildInstallUnixBuild.html
http://www.thegeekstuff.com/2010/07/rpm-command-examples/


How to install Guest additions in Ubuntu Machine
---------------------------------------------------------------
If you already downloaded a VBoxGuestAdditions.iso file to your host filesystem, you should be able to install the image from the VM's Devices menu using Insert Guest Additions CD Image...
Note that does not actually install the guest addition components, it just makes the ISO available as a virtual CD. On Ubuntu Server guest OSes, it does not even mount the virtual CD within the guest system.
Alternatively, you can download the ISO straight into the guest system from the repository, using
sudo apt-get update
sudo apt-get install virtualbox-guest-additions-iso

Once you have made the ISO available by one of the above methods, you must mount it somewhere in the filesystem. I am going to assume you want to use mountpoint /mnt for that, but you can create a different mountpoint if you wish.
If you inserted the ISO image as a virtual CD:
sudo mount /dev/cdrom /mnt
If you installed the guest additions ISO package from inside Ubuntu:
sudo mount /usr/share/virtualbox/VBoxGuestAdditions.iso /mnt
Finally, navigate to the mount point and run the installer:
cd /mnt

sudo ./VBoxLinuxAdditions.run
 
Source:
http://askubuntu.com/questions/565919/process-to-install-virtual-box-guest-additions-virtual-box 

Tuesday, 14 February 2012

How to write Make files for real time applications? What is Static Library and Dynamic(Shared) library?

Writing make files needs some understanding and practice. Once you understand how to write Makefiles, then it will be simple.

What is Makefile:
     When there are many source files and some source files has dependency on other files. Compilation of these source code files can be difficult. In order to build these files auto magically, makefiles came in to existence.

Makefiles are special format files that together with the make utility will help  to auto magically build and manage projects.

Build Process

  1. Compiler takes the source files and outputs object files

  2. Linker takes the object files and creates an executable 

How to use "make" utility?
run
 > make -f  myMakefile
 or
> make        < In turn it will run the Makefile present in the directory >


clean:
> make clean

How to write small makefile?


mainFile.c

#include<stdio.h>
#include "def.h"
int main()
{
   int result;
   result= function1(3) + FUNC_VALUE;

   printf(" The Result of the program is :%d\n", result);
   return 0;
}

def.h

#define FUNC_VALUE 8

int function1(int a);

fun.c

int function1(int a)
{
   /* Return Value of a */
   return (a);
}


How to compile files with out Makefile?

gcc mainFile.c fun.c -o test

How to compile files with Makefile ?

Makefile    (With Out Dependencies)

all:
        gcc mainFile.c fun.c -o test.exe
clean:
        rm -f *.o
        rm -f *.exe

This makefile generates only test.exe, there won't be mainFile.o, fun.o  files. This is compilation and as well as link these objects(.o objects) to generate .exe file.

all:
        gcc -c mainFile.c fun.c
clean:
        rm -f *.o
        rm -f *.exe

This makefile generates only .o files, there won't be .exe file. This is just compilation and generates .o files. 

On this first example we see that our target is called all. This is the default target for makefiles. The make utility will execute this target if no other one is specified.
We also see that there are no dependencies for target
all, so make safely executes the system commands specified.
Finally, make compiles the program according to the command line we gave it.

Makefile    (With  Dependencies)

all : test

test : mainFile.o fun.o
        gcc mainFile.o fun.o -o test.exe
#mainFile.o : (with out file name also work)

mainFile.o : mainFile.c 
        gcc -c mainFile.c

fun.o : fun.c
        gcc -c fun.c

clean:
        rm -f *.o
        rm -f *.exe

Explanation:
First Makefile will see "all". all is having dependency as test 
step1: all is having dependency as test 
step2: Go to test. "test" is having dependencies as mainFile.o fun.o 
step3: Go to first dependency mainFile.o. 
step4: Then we define a rule "mainFile.o : mainFile.c" that applies to mainFile ending in the .o    suffix.  The rule says that the .o file depends upon the .c version of the mainFile.c file. The rule then says that to generate the .o file, make needs to compile the .c file using the compiler(gcc). 
step5: Go to second dependency fun.o.The rule says generate the fun.o file using compiler. 
step6: Once it found the dependecies, then it will execute the command present in the "all".
 gcc mainFile.o fun.o -o test.exe.

 In other words,  the target all has only dependencies, but no system commands. In order for make to execute correctly, it has to meet all the dependencies of the called target (in this case all).
Each of the dependencies are searched through all the targets available and executed if found.



Makefile With Macros -> Procedure 1:

# step1: define the Compiler as gcc. $(CC) is the variable. $ represents variable.

CC = gcc

# step2: define compiler flags "CFLAGS"  if you mention -g option it is for GDB, -wall to display all
# warnings

CFLAGS = -g -Wall

# Whenever you give Make, it will come to all, then checks the label test
# step3:

all : test

# test is having dependencies as mainFile.o and fun.o
# step4:
# returns from step5 and step4

test : mainFile.o fun.o
        $(CC) $(CFLAGS) mainFile.o fun.o -o test.exe

#step5:
# mainFile.o will have dependency on "mainFile.c"

mainFile.o : mainFile.c
        $(CC) -c mainFile.c

#step6:
# fun.o will have dependency on "fun.c"

fun.o : fun.c
        $(CC) -c fun.c

clean:
        rm -f *.o
        rm -f *.exe


Makefile With Macros -> Procedure 2:


#  define the Compiler as gcc. $(CC) is the variable. $ represents variable.
CC = gcc

#  define compiler flags "CFLAGS"  if you -g option it is for GDB, -wall to display all
# warnings

CFLAGS = -g -Wall

#step3:
# Return to step2

OBJS =  $(PWD)/mainFile.o \
          $(PWD)/fun.o


#step1:

all : test

#step2:

test : $(OBJS)
        $(CC) $(CFLAGS) $(OBJS) -o test.exe

#step4:
#Return to step3
# It will compile all the files and generate .o's.
# or  $(PWD)/*.o : *.c

$(PWD)/%.o : %.c
        $(CC) $(CFLAGS) -c $< -o $@


clean:
        rm -f *.o
        rm -f *.exe

How to Generate Static Library and Dynamic Library(Shared Libaries) Using Makefile:

First of all i would like give some introduction about static library and dynamic library.

What is Static Library?

Static libraries are simply a collection of ordinary object files; conventionally, static libraries end with the ``.a'' suffix. This collection is created using the ar (archiver) program.  

In static linking, the size of the executable becomes greater than in dynamic linking, as the library code is stored within the executable rather than in separate files

Static libraries permit users to link to programs without having to recompile its code, saving recompilation time. Note that recompilation time is less important given today's faster compilers, so this reason is not as strong as it once was. Static libraries are often useful for developers if they wish to permit programmers to link to their library, but don't want to give the library source code.

To create a static library, or to add additional object files to an existing static library, use a command like this:

                   ar rcs library.a File1.o File2.o
or 
                   ar -qcs library.a File1.o File2.o 



Makefile to Generate Static Library.

Let's take small example, suppose there are two files and generate the static library and link it to main file.

file1.c

int fun1(int a, int b)
{
  int c;

  /* add the Two Variables */
  c= a+b;
  return(c);
}

file2.c

int fun2(int a, int b)
{
  int c;

  /* add the Two Variables */
  c= a+b;
  return(c);
}
 Above there are two files, here you can find the Makefile to generate the library using file1.o and file2.o

Makefile to generate MyLibrary.a using file1.o and file2.o

CC = gcc

CFLAGS = -g -Wall

# .a extension for static library
# .so extension for dynamic library
# step 1:
# it goes to step2:

all: libMylibrary.a


#step 3:
# Return to step 2
# Declare this OBJS before it is used, Here OBJS is a variable.

OBJS = $(PWD)/file1.o \
       $(PWD)/file2.o

#step 2:

libMylibrary.a : $(OBJS)
        ar -qcs libMylibrary.a $(OBJS)


# step 4:
# Return to step 3

$(PWD)/%.o : %.c
        $(CC) $(CFLAGS) -c $< -o $@

clean:
        rm -f *.o
        rm -f *.a


How to Link this library to the Main function file to get .exe

mainFile.c

#include<stdio.h>
#include<stdlib.h>

extern int fun1(int a, int b);
extern int fun2(int a, int b);

int main()
{

  printf("The value of Function1: %d", fun1(4,5));
  printf("The value of Function2: %d", fun2(6,7));

  return 0;
}

Makefile links library and generate the test.exe

CC = gcc

CFLAGS = -g -Wall

# .a extension for static library
# .so extension for dynamic library
# step 1:
# it goes to step2:

all: test


#step 3:
# Return to step 2

OBJS = $(PWD)/mainFile.o \

#step 2:

test : $(OBJS)
        $(CC) $(CFLAGS) $(OBJS) $(LIBDIR) $(LIBLOG) -o test.exe


#step 4:
# Return to Step 3

$(PWD)/mainFile.o : mainFile.c
        $(CC) $(CFLAGS) -c mainFile.c

# Step 5:
# For static library, always include LIB DIR
# This is Mandatory
LIBDIR =  -L./
LIBLOG = -lMylibrary

clean:
        rm -f *.o
        rm -f *.a

 Important Point:
When ever you are linking static library to mainFile,  it is mandatory to mention the LIBDIR( where the library is present) using -L option. This $(LIBDIR) should be included when generating .exe file. 

Note: How to run your own makefile, suppose i have makefile as Makefile_org, then run using the below command.
make -f Makefile_org
clean :
 make -f Makefile_org clean

Real Time Example.
Suppose there are three modules BMODULE, CMODULE , DMODULE. BMODULE  is having dependency upon other two modules i.e. CMODULE , DMODULE
Hence, first compile CMODULE  and DMODULE and link their objects to BMODULE to generate the .exe.
Here  DMODULE generates the static library and CMODULE generates the object files(o's)

Step1:  Create Directories of BModule, DModule, CModule

-bash-3.2#  mkdir mreddya
-bash-3.2#  mkdir MAKEFILE_EXERCISE  

create directories under /root/mreddya/MAKEFILE_EXERCISE/as shown below.
-bash-3.2#  mkdir BMODULE
-bash-3.2#  mkdir CMODULE 
-bash-3.2#  mkdir DMODULE
 
Step2:  Create sub-directories of BModule, DModule, CModule
create sub directories under each module as shown below.
-bash-3.2# cd DMODULE/
-bash-3.2#  mkdir src
-bash-3.2#  mkdir inc
-bash-3.2#  mkdir obj 

-bash-3.2# cd CMODULE/
-bash-3.2#  mkdir src
-bash-3.2#  mkdir inc
-bash-3.2#  mkdir obj 

-bash-3.2# cd BMODULE/
-bash-3.2#  mkdir src
-bash-3.2#  mkdir inc
-bash-3.2#  mkdir obj 

Step 3:  Generate Library for DModule for the below files

-bash-3.2# cd DMODULE/
-bash-3.2# cd
Create four files under source directory, dModulefile1.c  dModulefile2.c  dModulefile3.c, Makefile
-bash-3.2# cd DMODULE/
-bash-3.2# cd inc
Create three files under inc,dModulefile1.h  dModulefile2.h  dModulefile3.h


dModulefile1.c

#include "dModulefile1.h"

int DModuleFunction1(int a)
{
   printf("I am in DModuleFunction1 and its Value:%d", a);
   a = a + FUNC_VALUE4;
   return(a);
}

dModulefile2.c

#include "dModulefile2.h"

int DModuleFunction2(int b)
{
   printf("I am in DModuleFunction2 and its Value:%d", b);
   b = b + FUNC_VALUE5;
   return(b);
}

dModulefile3.c

#include "dModulefile3.h"

int DModuleFunction3(int c)
{
   printf("I am in DModuleFunction3 and its Value:%d", c);
   c = c + FUNC_VALUE6;
   return(c);
}

dModulefile1.h
#include<stdio.h>
#define FUNC_VALUE4 14

dModulefile2.h
#include<stdio.h>
#define FUNC_VALUE5 11

dModulefile3.h
#include<stdio.h>
#define FUNC_VALUE6 13

Step 4:  Makefile for DMODULE (Makefile place in src directory)

# define the Compiler as gcc
CC = gcc

# define compiler flags "CFLAGS"  if you -g option it is for GDB, -wall to display all
# warnings

CFLAGS= -g -Wall

# TO include Directories, To include any directories give -I/Path Directory
# e.g: INCLUDEDIR = -I/VOBS/CMODULE/INC/, to include one more directory
# then Syntax will be INCLUDEDIR += -I/VOBS/CMODULE/INC/
#                     INCLUDEDIR  = -I/VOBS/BMODULE/INC/

INCLUDEDIR = -I/root/mreddya/MAKEFILE_EXERCISE/DMODULE/inc

# define MACRO for OBJECT DIRETORY
OBJ-DIR = /root/mreddya/MAKEFILE_EXERCISE/DMODULE/obj

# copy all .o( Objects) in to object directory
# All Objects are stored in OBJ-DIR
#
OBJS = $(OBJ-DIR)/dModulefile1.o \
        $(OBJ-DIR)/dModulefile2.o \
        $(OBJ-DIR)/dModulefile3.o \


# First whenever we give Make, it comes here, and Check OBJS
# Then It will check what and all .o are required from 
# OBJS directory
# then it will go Command to generate the .o's.

all:    libDmodule.a

# Generate the Library

libDmodule.a: $(OBJS)
        ar -qcs libDmodule.a $(OBJS)

#To Generate %.o means same directory.
# target ( It tells $(OBJ-DIR)/%.o : %.c, generate the %.c files # to .o files using command.)
# To get the Target the below command should be executed, 
# otherwise Linker error will be there.

$(OBJ-DIR)/%.o : %.c
        $(CC) $(CFLAGS) $(INCLUDEDIR) -c $< -o $@


clean:
        rm -f $(OBJ-DIR)/*.o
        rm -f *.a

Step 5:  Run the Makefile and check the results

-bash-3.2# pwd
/root/mreddya/MAKEFILE_EXERCISE/DMODULE/src
-bash-3.2# make
gcc -g -Wall -I/root/mreddya/MAKEFILE_EXERCISE/DMODULE/inc -c dModulefile1.c -o /root/mreddya/MAKEFILE_EXERCISE/DMODULE/obj/dModulefile1.o
gcc -g -Wall -I/root/mreddya/MAKEFILE_EXERCISE/DMODULE/inc -c dModulefile2.c -o /root/mreddya/MAKEFILE_EXERCISE/DMODULE/obj/dModulefile2.o
gcc -g -Wall -I/root/mreddya/MAKEFILE_EXERCISE/DMODULE/inc -c dModulefile3.c -o /root/mreddya/MAKEFILE_EXERCISE/DMODULE/obj/dModulefile3.o
ar -qcs libDmodule.a /root/mreddya/MAKEFILE_EXERCISE/DMODULE/obj/dModulefile1.o /root/mreddya/MAKEFILE_EXERCISE/DMODULE/obj/dModulefile2.o /root/mreddya/MAKEFILE_EXERCISE/DMODULE/obj/dModulefile3.o

-bash-3.2# ls
dModulefile1.c  dModulefile2.c  dModulefile3.c  libDmodule.a  Makefile

-bash-3.2# pwd
/root/mreddya/MAKEFILE_EXERCISE/DMODULE/obj
-bash-3.2# ls
dModulefile1.o  dModulefile2.o  dModulefile3.o
Step 6:  Generate objects for CMODULE

-bash-3.2# cd CMODULE/
-bash-3.2# cd
Create four files under source directory, cModulefile1.c  cModulefile2.c  cModulefile3.c, Makefile
-bash-3.2# cd CMODULE/
-bash-3.2# cd inc
Create three files under inc,cModulefile1.h  cModulefile2.h  cModulefile3.h

cModulefile1.c

#include "cModulefile1.h"

int CModuleFunction1(int a)
{
   printf("I am in CModuleFunction1 and its Value:%d", a);
   a = a + FUNC_VALUE1;
   return(a);
}
cModulefile2.c

#include "cModulefile2.h"

int CModuleFunction2(int b)
{
   printf("I am in CModuleFunction2 and its Value:%d", b);
   b = b + FUNC_VALUE2;
   return(b);
}

dModulefile3.c

#include "cModulefile3.h"

int CModuleFunction3(int c)
{
   printf("I am in CModuleFunction3 and its Value:%d", c);
   c = c + FUNC_VALUE3;
   return(c);
}

cModulefile1.h
#include<stdio.h>
#define FUNC_VALUE1 10

cModulefile2.h
#include<stdio.h>
#define FUNC_VALUE2 11

cModulefile2.h
#include<stdio.h>
#define FUNC_VALUE3 11


Step 7:  Makefile for CMODULE (Makefile place in src directory)

# define the Compiler as gcc
CC = gcc

# define compiler flags "CFLAGS"  if you -g option it is for GDB, -wall to display all
# warnings

CFLAGS= -g -Wall

# TO include Directories, To include any directories give -I/Path Directory
# e.g: INCLUDEDIR = -I/VOBS/CMODULE/INC/, to include one more directory
# then Syntax will be INCLUDEDIR += -I/VOBS/CMODULE/INC/
#                     INCLUDEDIR  = -I/VOBS/BMODULE/INC/

INCLUDEDIR = -I/root/mreddya/MAKEFILE_EXERCISE/CMODULE/inc

# define MACRO for OBJECT DIRETORY
OBJ-DIR = /root/mreddya/MAKEFILE_EXERCISE/CMODULE/obj

# copy all .o( Objects) in to object directory
# All Objects are stored in OBJ-DIR
#
OBJS = $(OBJ-DIR)/cModulefile1.o \
        $(OBJ-DIR)/cModulefile2.o \
        $(OBJ-DIR)/cModulefile3.o \


# First whenever we give Make, it comes here, and Check OBJS
# Then It will check what and all .o are required from 
# OBJS directory
# then it will go Command to generate the .o's.

all: $(OBJS)

#To Generate %.o means same directory.
# target ( It tells $(OBJ-DIR)/%.o : %.c, generate the %.c files to .o files using command.)
#    command.
#To Generate %.o means same directory.
# target ( It tells $(OBJ-DIR)/%.o : %.c, generate the %.c files to .o files using command.)
#    command.
# To get the Target the below command should be executed, otherwise
# Linker error will be there.

$(OBJ-DIR)/%.o : %.c
        $(CC) $(CFLAGS) $(INCLUDEDIR) -c $< -o $@


clean:
        rm -f $(OBJ-DIR)/*.o


Step 8:  Run the Makefile and check the results

-bash-3.2# pwd
/root/mreddya/MAKEFILE_EXERCISE/CMODULE/src

-bash-3.2# make clean
rm -f /root/mreddya/MAKEFILE_EXERCISE/CMODULE/obj/*.o

-bash-3.2# make
gcc -g -Wall -I/root/mreddya/MAKEFILE_EXERCISE/CMODULE/inc -c cModulefile1.c -o /root/mreddya/MAKEFILE_EXERCISE/CMODULE/obj/cModulefile1.o
gcc -g -Wall -I/root/mreddya/MAKEFILE_EXERCISE/CMODULE/inc -c cModulefile2.c -o /root/mreddya/MAKEFILE_EXERCISE/CMODULE/obj/cModulefile2.o
gcc -g -Wall -I/root/mreddya/MAKEFILE_EXERCISE/CMODULE/inc -c cModulefile3.c -o /root/mreddya/MAKEFILE_EXERCISE/CMODULE/obj/cModulefile3.o
-bash-3.2# pwd
/root/mreddya/MAKEFILE_EXERCISE/CMODULE/obj

-bash-3.2# ls
cModulefile1.o  cModulefile2.o  cModulefile3.o

Step 9: Get .exe by Linking the CMODULE and DMODULE to BMODULE 

-bash-3.2# cd BMODULE/
-bash-3.2# cd
Create two files under source directory, bModulefile.c,  Makefile
-bash-3.2# cd BMODULE/
-bash-3.2# cd inc
Create one file under inc,bModulefile.h

bModulefile.c

#include<stdio.h>

#include "bModulefile.h"

/* extern the Functions */
extern int CModuleFunction1(int );
extern int CModuleFunction2(int );
extern int CModuleFunction3(int );
extern int DModuleFunction1(int );
extern int DModuleFunction2(int );
extern int DModuleFunction3(int );


void getFunValue(void)
{
  int result = 0;

  result = CModuleFunction1(3)* FUNC_VALUE8;
  printf("The Result value with CModuleFunction1:%d\n", result);
  result = CModuleFunction2(4)* FUNC_VALUE8;
  printf("The Result value with CModuleFunction2:%d\n", result);
  result = CModuleFunction3(5)* FUNC_VALUE8;
  printf("The Result value with CModuleFunction3:%d\n", result);
  result = DModuleFunction1(3)* FUNC_VALUE8;
  printf("The Result value with DModuleFunction1:%d\n", result);
  result = DModuleFunction2(4)* FUNC_VALUE8;
  printf("The Result value with DModuleFunction2:%d\n", result);
  result = DModuleFunction3(5)* FUNC_VALUE8;
  printf("The Result value with DModuleFunction3:%d\n", result);
}
int main()
{
   /* call the getFunValue Function */
   getFunValue();
   return 0;
}

bModulefile.h


#define FUNC_VALUE8 1

Step 10:  Makefile for BMODULE (Makefile place in src directory)
This Makefile links both CMODULE and DMODULE and generates the test.exe


Some points to be Noted here:
Before compiling BMODULE, first it is mandate to compile CMODULE and DMODULE.
Once CMODULE and DMODULE compiled and run the Makefile of BMODULE.

Step 11:  Makefile compiles first CMODULE and DMODULE then BMODULE
Run this Makefile using make all command


# This is the Main Make file which incorporates all the files and
# generates the .exe file.

# define the Compiler Macro as gcc
CC = gcc

# define any Flags whether to compile as 64 bit(-m64) or with -g option
# to debug in gdb and also to show file name with warnings.
CFLAGS = -g -Wall

# Include the Directories which you want to link here.
# Include the .h directories.
# Whenever multiple directories are included then use +=  with -I option
INCL_DIR += -I/root/mreddya/MAKEFILE_EXERCISE/BMODULE/inc

# define MACRO for OBJECT DIRETORY
OBJ-DIR = /root/mreddya/MAKEFILE_EXERCISE/BMODULE/obj

EXE-DIR = /root/mreddya/MAKEFILE_EXERCISE/BMODULE/src

COBJ-DIR = /root/mreddya/MAKEFILE_EXERCISE/CMODULE/obj

DLIB_DIR = /root/mreddya/MAKEFILE_EXERCISE/DMODULE/src


OBJS = $(OBJ-DIR)/bModulefile.o

COBJS = $(COBJ-DIR)/cModulefile1.o \
        $(COBJ-DIR)/cModulefile2.o \
       $(COBJ-DIR)/cModulefile3.o \


EXTERNALLIBS = -L$(DLIB_DIR)
LIBLOG       = -lDmodule



CMODULE_COMPILE:
        cd /root/mreddya/MAKEFILE_EXERCISE/CMODULE/src && make
DMODULE_COMPILE:
        cd /root/mreddya/MAKEFILE_EXERCISE/DMODULE/src && make
BMODULE_COMPILE:
        $(CC) $(CFLAGS) $(INCL_DIR) -c *.c -o $(OBJS)

all:
        make all_modules

all_modules:
        make CMODULE_COMPILE
        make DMODULE_COMPILE
        make BMODULE_COMPILE
        $(CC) -o test.exe $(OBJS) $(EXTERNALLIBS) $(LIBLOG) $(COBJS)


clean:
        rm -f $(OBJ-DIR)/*.o
        rm -f $(EXE-DIR)/*.exe
        rm -f $(COBJ-DIR)/*.o
        rm -f $(DOBJ-DIR)/*.o

There are several ways to write make files, this is one way.
write small script and compile the Makefiles like show below.

build.sh script

cd /root/mreddya/MAKEFILE_EXERCISE/CMODULE/src
make
cd /root/mreddya/MAKEFILE_EXERCISE/DMODULE/src
make

cd /root/mreddya/MAKEFILE_EXERCISE/BMODULE/src
make

What is Dynamic Library or Shared Library (.so)?

Dynamic library is also called as Shared Library. 
Shared Library is a binary file(.so file) contains object (.o) files. All object files form as shared library  and this library can be loaded or unloaded dynamically.

By using shared library concept, one can make the code is position-independent, meaning that the code may be loaded anywhere in memory. Applications linked to shared objects at run time.
 
How to generate a shared library:

Step 1: Create object code, it means generate object files (.o files) 

 gcc -fPIC -c <filename.c>

The -fPIC option tells gcc to create position independent code which is necessary for shared libraries.
  e.g: gcc -fPIC -c myfilename.c

Step 2: Create shared library 

 gcc -g -Wall -shared -o  <library Name>  <objectfile1.o,  objectfile2.o>

 It will create the library with .so extension.
e.g: gcc -g -Wall -shared -o  libMyfuncs.so file1.o  file2.o


How to use the shared library to your application

Step 1:
Set the environment for Library using 
 export LD_LIBRARY_PATH=.

The above indicates the path directory where the library is present. ./ or  .  indicates the present directory

Step 3:
Compile your Main file and generate the object code.
e.g: gcc -c mainFile

And then Link the shared library  to the main file as mentioned below.


 e.g: gcc  -L./ -lMyfuncs mainFile.o -o test.exe

 Notes:
suppose if  "-L/opt/exp", means library is present in this directory and link the library using -llibName. The name of the library is Myfuncs.so.
The libraries will NOT be included in the executable but will be dynamically linked during run time execution.
That's reason size of .exe is small when we compare with static library.

How to check the list of shared libraries using by the application.

Use simple command.
ldd <.exe>

 -bash-3.2# ldd test.exe
        libMyFun.so => ./libMyFun.so (0x00002ab25d70f000)
        libc.so.6 => /lib64/libc.so.6 (0x0000003ef7c00000)
        /lib64/ld-linux-x86-64.so.2 (0x0000003ef6c00000)



Simple Makefile to generate shared library

file1.c

int func1(int a, int b)
{
    int c;
    /* Add */
    c= a+b;
    return(c);
}

file2.c

 int func1(int a, int b)
{
    int c;
    /* Add */
    c= a+b;
    return(c);
}

Makefile to generate shared library as lib

CC = gcc

CFLAGS = -g -Wall

OBJS = $(PWD)/file1.o \
        $(PWD)/file2.o

all: libMyFun.so

libMyFun.so : $(OBJS)
        $(CC) $(CFLAGS) -shared -o libMyFun.so $(OBJS)

$(PWD)/%.o : %.c
        $(CC) $(CFLAGS) -fPIC -c *.c
clean:
        rm -f *.o
        rm -f *.so


 How to Link this shared library to the mainFile.c

mainFile.c


#include<stdio.h>

extern int func1(int, int);
extern int func2(int, int);

int main()
{

  printf("The result of Function 1 is: %d\n", func1(4,5));
  printf("The result of Function 1 is: %d\n", func2(10,20));
  return 0;
}


Build.sh  <Generate the test.exe using small script>

#step 1: clean the Library
make clean

#step 2: Generated the Library
make

#step 3: Generates the mainFile.o

gcc -c mainFile.c

#step 4: clean the .exe
rm -f *.exe

#step 5: Link the Shared library to mainFile.o and
#generates the test.exe file.

gcc -L./ -lMyFun mainFile.o -o test.exe


Run the Build.sh

chmod +x Build.sh
./Build.sh