Skip to content
geeksforgeeks
  • Tutorials
    • Python
    • Java
    • Data Structures & Algorithms
    • ML & Data Science
    • Interview Corner
    • Programming Languages
    • Web Development
    • CS Subjects
    • DevOps And Linux
    • School Learning
    • Practice Coding Problems
  • Courses
    • DSA to Development
    • Get IBM Certification
    • Newly Launched!
      • Master Django Framework
      • Become AWS Certified
    • For Working Professionals
      • Interview 101: DSA & System Design
      • Data Science Training Program
      • JAVA Backend Development (Live)
      • DevOps Engineering (LIVE)
      • Data Structures & Algorithms in Python
    • For Students
      • Placement Preparation Course
      • Data Science (Live)
      • Data Structure & Algorithm-Self Paced (C++/JAVA)
      • Master Competitive Programming (Live)
      • Full Stack Development with React & Node JS (Live)
    • Full Stack Development
    • Data Science Program
    • All Courses
  • C++ Data Types
  • C++ Input/Output
  • C++ Arrays
  • C++ Pointers
  • C++ OOPs
  • C++ STL
  • C++ Interview Questions
  • C++ Programs
  • C++ Cheatsheet
  • C++ MCQ
  • C++ Projects
  • C++ Exception Handling
  • C++ Memory Management
Open In App
Next Article:
Executing main() in C/C++ - behind the scene
Next article icon

Executing main() in C/C++ - behind the scene

Last Updated : 13 Sep, 2023
Comments
Improve
Suggest changes
Like Article
Like
Report
How to write a C program to print "Hello world" without main() function? At first, it seems impractical to execute a program without a main() function because the main() function is the entry point of any program. Let us first understand what happens under the hood while executing a C program in Linux system, how main() is called and how to execute a program without main(). Following setup is considered for the demonstration.
  • Ubuntu 16.4 LTS operating system
  • GCC 5.4.0 compiler
  • objdump utility
From C/C++ programming perspective, the program entry point is main() function. From the perspective of program execution, however, it is not. Prior to the point when the execution flow reaches to the main(), calls to few other functions are made, which setup arguments, prepare environment variables for program execution etc. The executable file created after compiling a C source code is a Executable and Linkable Format (ELF) file. Every ELF file have a ELF header where there is a e_entry field which contains the program memory address from which the execution of executable will start. This memory address point to the _start() function. After loading the program, loader looks for the e_entry field from the ELF file header. Executable and Linkable Format (ELF) is a common standard file format used in UNIX system for executable files, object code, shared libraries, and core dumps. Let's see this using an example. I'm creating a example.c file to demonstrate this. C
int main() {    return(0); } 
Now compiling this using following commands
  gcc -o example example.c  
Now an example executable is created, let us examine this using objdump utility
  objdump -f example  
This outputs following critical information of executable on my machine. Have a look at start address below, this is the address pointing to _start() function.
  example:     file format elf64-x86-64  architecture: i386:x86-64, flags 0x00000112:  EXEC_P, HAS_SYMS, D_PAGED  start address 0x00000000004003e0  
We can cross check this address by deassembling the executable, the output is long so I'm just pasting the output which shows where this address 0x00000000004003e0 is pointing
  objdump --disassemble  example  
Output :
  00000000004003e0 <_start>:    4003e0:    31 ed                    xor    %ebp,%ebp    4003e2:    49 89 d1                 mov    %rdx,%r9    4003e5:    5e                       pop    %rsi    4003e6:    48 89 e2                 mov    %rsp,%rdx    4003e9:    48 83 e4 f0              and    $0xfffffffffffffff0,%rsp    4003ed:    50                       push   %rax    4003ee:    54                       push   %rsp    4003ef:    49 c7 c0 60 05 40 00     mov    $0x400560,%r8    4003f6:    48 c7 c1 f0 04 40 00     mov    $0x4004f0,%rcx    4003fd:    48 c7 c7 d6 04 40 00     mov    $0x4004d6,%rdi    400404:    e8 b7 ff ff ff           callq  4003c0     400409:    f4                       hlt        40040a:    66 0f 1f 44 00 00        nopw   0x0(%rax,%rax,1)  
As we can clearly see this is pointing to the _start() function.

The role of _start() function

The _start() function prepare the input arguments for another function _libc_start_main() which will be called next. This is prototype of _libc_start_main() function. Here we can see the arguments which were prepared by _start() function. C
int __libc_start_main(int (*main) (int, char * *, char * *), /* address of main function*/ int argc, /* number of command line args*/ char ** ubp_av, /* command line arg array*/ void (*init) (void), /* address of init function*/ void (*fini) (void), /* address of fini function*/ void (*rtld_fini) (void), /* address of dynamic linker fini function */ void (* stack_end) /* end of the stack address*/ ); 

The role of _libc_start_main() function

The role of _libc_start_main() function is following -
  • Preparing environment variables for program execution
  • Calls _init() function which performs initialization before the main() function start.
  • Register _fini() and _rtld_fini() functions to perform cleanup after program terminates
    • After all the prerequisite actions has been completed, _libc_start_main() calls the main() function.

      Writing program without main()

      Now we know how the call to the main() is made.To make it clear, main() is nothing but a agreed term for startup code. We can have any name for startup code it doesn't necessarily have to be "main". As _start() function by default calls main(), we have to change it if we want to execute our custom startup code. We can override the _start() function to make it call our custom startup code not main(). Let's have an example, save it as nomain.c - C
      #include<stdio.h> #include<stdlib.h> void _start() {     int x = my_fun(); //calling custom main function     exit(x); }  int my_fun() // our custom main function {     printf("Hello world!\n");     return 0; } 
      Now we have to force compiler to not use it's own implementation of _start().In GCC we can do this using -nostartfiles
  gcc -nostartfiles -o nomain nomain.c  
Execute the executable nomain
  ./nomain  
Output:
  Hello world!  
References
  • http://dbp-consulting.com/tutorials/debugging/linuxProgramStartup.html
  • Advanced C/C++ Compiling by Milan Stevanovic

Next Article
Executing main() in C/C++ - behind the scene

K

kartik
Improve
Article Tags :
  • C Language
  • C++
  • system-programming
Practice Tags :
  • CPP

Similar Reads

    Compiling a C Program: Behind the Scenes
    The compilation is the process of converting the source code of the C language into machine code. As C is a mid-level language, it needs a compiler to convert it into an executable code so that the program can be run on our machine.The C program goes through the following phases during compilation:C
    4 min read
    Name Mangling and extern "C" in C++
    C++ supports function overloading, i.e., there can be more than one function with the same name but, different parameters. How does the C++ compiler distinguish between different functions when it generates object code - it changes names by adding information about arguments. This technique of addin
    3 min read
    Functions that are executed before and after main() in C
    With GCC family of C compilers, we can mark some functions to execute before and after main(). So some startup code can be executed before main() starts, and some cleanup code can be executed after main() ends. For example, in the following program, myStartupFun() is called before main() and myClean
    1 min read
    How to call some function before main() function in C++?
    Since it is known that main() method is the entry point of the program. Hence it is the first method that will get executed by the compiler. But this article explains how to call some function before the main() method gets executed in C++. How to call some function before main() function? To call so
    3 min read
    Return Statement vs Exit() in main() in C++
    The return statement in C++ is a keyword used to return the program control from the called function to the calling function. On the other hand, the exit() function in C is a standard library function of <stdlib.h> that is used to terminate the process explicitly. The operation of the two may
    3 min read
geeksforgeeks-footer-logo
Corporate & Communications Address:
A-143, 7th Floor, Sovereign Corporate Tower, Sector- 136, Noida, Uttar Pradesh (201305)
Registered Address:
K 061, Tower K, Gulshan Vivante Apartment, Sector 137, Noida, Gautam Buddh Nagar, Uttar Pradesh, 201305
GFG App on Play Store GFG App on App Store
Advertise with us
  • Company
  • About Us
  • Legal
  • Privacy Policy
  • In Media
  • Contact Us
  • Advertise with us
  • GFG Corporate Solution
  • Placement Training Program
  • Languages
  • Python
  • Java
  • C++
  • PHP
  • GoLang
  • SQL
  • R Language
  • Android Tutorial
  • Tutorials Archive
  • DSA
  • Data Structures
  • Algorithms
  • DSA for Beginners
  • Basic DSA Problems
  • DSA Roadmap
  • Top 100 DSA Interview Problems
  • DSA Roadmap by Sandeep Jain
  • All Cheat Sheets
  • Data Science & ML
  • Data Science With Python
  • Data Science For Beginner
  • Machine Learning
  • ML Maths
  • Data Visualisation
  • Pandas
  • NumPy
  • NLP
  • Deep Learning
  • Web Technologies
  • HTML
  • CSS
  • JavaScript
  • TypeScript
  • ReactJS
  • NextJS
  • Bootstrap
  • Web Design
  • Python Tutorial
  • Python Programming Examples
  • Python Projects
  • Python Tkinter
  • Python Web Scraping
  • OpenCV Tutorial
  • Python Interview Question
  • Django
  • Computer Science
  • Operating Systems
  • Computer Network
  • Database Management System
  • Software Engineering
  • Digital Logic Design
  • Engineering Maths
  • Software Development
  • Software Testing
  • DevOps
  • Git
  • Linux
  • AWS
  • Docker
  • Kubernetes
  • Azure
  • GCP
  • DevOps Roadmap
  • System Design
  • High Level Design
  • Low Level Design
  • UML Diagrams
  • Interview Guide
  • Design Patterns
  • OOAD
  • System Design Bootcamp
  • Interview Questions
  • Inteview Preparation
  • Competitive Programming
  • Top DS or Algo for CP
  • Company-Wise Recruitment Process
  • Company-Wise Preparation
  • Aptitude Preparation
  • Puzzles
  • School Subjects
  • Mathematics
  • Physics
  • Chemistry
  • Biology
  • Social Science
  • English Grammar
  • Commerce
  • World GK
  • GeeksforGeeks Videos
  • DSA
  • Python
  • Java
  • C++
  • Web Development
  • Data Science
  • CS Subjects
@GeeksforGeeks, Sanchhaya Education Private Limited, All rights reserved
We use cookies to ensure you have the best browsing experience on our website. By using our site, you acknowledge that you have read and understood our Cookie Policy & Privacy Policy
Lightbox
Improvement
Suggest Changes
Help us improve. Share your suggestions to enhance the article. Contribute your expertise and make a difference in the GeeksforGeeks portal.
geeksforgeeks-suggest-icon
Create Improvement
Enhance the article with your expertise. Contribute to the GeeksforGeeks community and help create better learning resources for all.
geeksforgeeks-improvement-icon
Suggest Changes
min 4 words, max Words Limit:1000

Thank You!

Your suggestions are valuable to us.

What kind of Experience do you want to share?

Interview Experiences
Admission Experiences
Career Journeys
Work Experiences
Campus Experiences
Competitive Exam Experiences