Command-Line Arguments
argc, argv, and reading words typed after the program's name.
6 minute read
Big idea
When you start a program from a terminal you can pass it words: ./greet Asha. C hands them to main as argc (how many) and argv (the words themselves, as strings).
The idea
So far main has taken nothing: int main(void). It can instead take two parameters:
int main(int argc, char *argv[])
argc— argument count: how many words were typed, including the program's name.argv— argument vector: an array of strings.argv[0]is the program name,argv[1]the first real argument, and so on.argv[argc]is alwaysNULL.
Running ./greet Asha 21 gives:
| value | |
|---|---|
argc | 3 |
argv[0] | "./greet" |
argv[1] | "Asha" |
argv[2] | "21" — still a string, not a number |
What argv looks like in memory
argv is an array of pointers; each points to the first character of one word. The lesson runner can't type a command line, so this program builds the same thing by hand and passes it on:
In a real program you'd write int main(int argc, char *argv[]) and use them directly — the code inside is the same.
Always check argc first
If the user forgets an argument, argv[1] might not exist. Check argc and print a usage message:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int run(int argc, char *argv[]) {
if (argc != 4) {
printf("usage: %s <number> <add|mul> <number>\n", argv[0]);
return 1;
}
int a = atoi(argv[1]);
int b = atoi(argv[3]);
if (strcmp(argv[2], "add") == 0) {
printf("%d\n", a + b);
} else if (strcmp(argv[2], "mul") == 0) {
printf("%d\n", a * b);
} else {
printf("unknown operation: %s\n", argv[2]);
return 1;
}
return 0;
}
int main(void) {
char *good[] = {"calc", "6", "mul", "7", NULL};
char *short_one[] = {"calc", "6", NULL};
char *bad_op[] = {"calc", "6", "pow", "7", NULL};
run(4, good);
run(2, short_one);
run(4, bad_op);
return 0;
}output
42
usage: calc <number> <add|mul> <number>
unknown operation: powRun and edit it in the app.
Notice strcmp to compare strings — argv[2] == "add" compares addresses, not text, and is almost always false.
Watch it
Looping over all the arguments
#include <stdio.h>
#include <stdlib.h>
int run(int argc, char *argv[]) {
int total = 0;
for (int i = 1; i < argc; i++) {
total += atoi(argv[i]);
}
printf("%d numbers, total %d\n", argc - 1, total);
return 0;
}
int main(void) {
char *args[] = {"sum", "4", "10", "x", "6", NULL};
return run(5, args);
}What does it print? Show the answer
4 numbers, total 20Run and edit it in the app.
The loop starts at 1, skipping the program name. And atoi("x") is 0, silently — for real input, check with strtol as in Error Handling.
Running it for real
On your own machine:
gcc calc.c -o calc
./calc 6 mul 7
42
./calc "hello world" # quotes make one argument with a space in it
main returns its status to the terminal: 0 means success, anything else means failure. Scripts check that number.
You run ./copy a.txt b.txt — what is argc?
Common mistake
Reading argv[1] without checking argc. Run the program with no arguments and argv[1] is NULL — passing it to printf("%s") or atoi can crash. Check argc before touching argv.
Think of it like
Ordering at a counter: "Coffee, large, oat milk." The barista (your program) gets the order as separate words, in order — and should ask again if you only said "Coffee".
Key terms
- Command-line argument — A word typed after the program's name when starting it.
argc— How many arguments, including the program name.argv— The arguments, as an array of strings ending inNULL.- Usage message — A line telling the user how to run the program correctly.
- Exit status — The number
mainreturns; 0 means success.
Check yourself
What is argv[0]?
For ./tool 5 7 , what type is argv[1]?
What should a program check before reading argv[2]?