问题
if(strcmp(argv[2], NULL) == 0)
I'm passing 3 command line arguments but I also want to run it with only 2 command line arguments with the above statement. But a segmentation fault error is being displayed.
I also tried with
if(argc < 3)
but it also didn't work...same segmentation fault...
回答1:
Why segmentation fault?
Because of code if(strcmp(argv[2], NULL) == 0)
, you are passing NULL as string pointer to strcmp()
function; that try to deference at NULL to compare chars codes (e.g. acsii code) this cause undefined behavior at run time.
You should compare a string pointer with NULL using ==
as if(argv[2] == NULL)
I'm passing 3 command line arguments but I also want to run it with only 2 command line arguments with the above statement.
You can implement this in two ways:
The main syntax is:
int main(int argc, char* argv[])
The first argument
argc
is argument counter that is total number of arguments passed to your process including process name.So when you pass no extra argument then
argc == 1
e.g../exe
Suppose if you pass three arguments as follows:
./exe firstname lastname
Then
argc == 3
, it looks like you are passing two arguments but including executable name you are actually passing three arguments to process.So you can use of
argc
value to iterate in a loop to print arguments passed (other then executable)printf("Process name is: %s", argv[0]); for(i = 1; i < argc; i++ ){ printf("argv[%d] %s\n", argv[i]); }
Second technique is using second argument:
argv[]
is NULL terminated array of string strings soargv[argc]
is always equals to NULL. You can use this information in loop to iterate and process of arguments passed.To understand this suppose you are executing function as:
./exe firstname lastname
then
argv[0] == ./exe
,argv[1] == firstname
andargv[2] == lastname
andargv[3] == NULL
, Note this timeargc == 3
(argv[argc]
meansargv[3]
== NULL).For example to print all arguments, you can write you code like:
int i = 1; printf("Process name is: %s", argv[0]); while(argv[i]){// terminates when argv[i] == NULL printf("argv[%d] %s\n", argv[i]); i++; }
Do you notice argv[0]
is always your executable name! this means whenever you need to print your executable name use argv[0]
instead of hard code name of your executable while writing code, so that if you recompile and give new name to your executable then argv[0]
always prints correct name. You should write code as follows:
int main(int argc, char* argv[]){
:
:// some other code
if(argc < min_number_of_arguments){
fprintf(stderr, "Error: wrong number of arguments passed!\n");
fprintf(stderr, "Usage: %s [first] [second] \n", argv[0]);
exit(EXIT_FAILURE);
}
:
:// some other code
return EXIT_SUCCESS;
}
回答2:
Firstly, you shall always use strcmp(some_string, "")
instead of strcmp(some_string, NULL)
to check if a string is empty.
However in your problem you shall test
if (argc < 4)
That's because the executable itself is also in the array argv
. Consider you're invoking something like ./a.out param0 param1
, then argc
would be 3
and argv[0]="./a.out"
, argv[1]="param0"
, argv[2]="param1"
.
EDITED:
Also, never test if(strcmp(argv[2], NULL) == 0)
directly. Always test argc
first. Since there is no grantee that what value would be stored in argv[argc+n]
for n >= 0
回答3:
You can't use strcmp()
to compare to NULL
. Neither argument can be null. In this situation it doesn't make sense anyway. If the argument isn't present, argc
will be < 3, and if it is somehow empty it will be zero length. Never null.
来源:https://stackoverflow.com/questions/19108368/segmentation-fault-with-strcmp