3
votes

I need to pas two command line arguments and I tried the following:

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

void power(int base, int exp){

    int res=1;

    while(exp!=0){
       res *= base;
        --exp;
    }

    printf("Res = %d",res);
}

int main(int argc, char *argv[]) {
    if (argc != 3) {
        printf("Usage %s arg2 arg2\n(EG: %s 2 3)\n",argv[0],argv[0]);
        exit(1);
    }else{
        power(atoi(argv[1]),atoi(argv[2]));
    }

    printf("\n");
    return 0;
}

Output:

michi@michi-laptop:~$ ./power
Usage ./power arg2 arg2
(EG: ./power 2 3)
michi@michi-laptop:~$ ./power 2 3
Res = 8

Everything until here is ok, but if when save argv[1] and argv[2] in variable like this:

int base = atoi(argv[1]);
int exp = atoi(argv[2]);

I get Segmentation fault

code:

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

void power(int base, int exp){

    int res=1;

    while(exp!=0){
       res *= base;
        --exp;
    }

    printf("Res = %d",res);
}

int main(int argc, char *argv[]) {

    int base = atoi(argv[1]);
    int exp = atoi(argv[2]);

    if (argc != 3) {
        printf("Usage %s arg2 arg2\n(EG: %s 2 3)\n",argv[0],argv[0]);
        exit(1);
    }else{
        power(base, exp);
    }

    printf("\n");
    return 0;
}

But when I use Atoi inside printf everything is OK:

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

void power(int base, int exp){

    int res=1;

    while(exp!=0){
       res *= base;
        --exp;
    }

    printf("Res = %d",res);
}

int main(int argc, char *argv[]) {

    if (argc != 3) {
        printf("Usage %s arg2 arg2\n(EG: %s 2 3)\n",argv[0],argv[0]);
        exit(1);
    }else{
        power(atoi(argv[1]), atoi(argv[2]));
    }

    printf("\n");
    return 0;
}

My question is:

is this issue happen because of Atoi?

is this issue happen because I try to access argv[1] and argv[2] and they are not exists when I type ./program?

If I type ./program 2 3 everything is ok, which makes me think that segmentation fault happens because I try to access a memory location which doesn't belong to me at that point.

3
@amdixon Sir, How does exactly void power() return integer? - Michi
removed as incorrect. - amdixon
"is this issue happen because I try to access argv[1] and argv[2] and they are not exists when I type ./program?" Yes. You can't data that doesn't exist. - Lundin
@Lundin Thank you , i was 99% sure that , that was the reason hence the question. - Michi

3 Answers

4
votes

is this issue happen because I try to access argv[1] and argv[2] and they are not exists when I type ./program?

Yes, the problem is that you are trying to access the command lines arg's before verifying whether they are present or not.

In the second example code snippet, assign the values to the variables base and exp only after making sure that the input is available.

int base;
int exp;

if (argc != 3) {
    printf("Usage %s arg2 arg2\n(EG: %s 2 3)\n",argv[0],argv[0]);
    exit(1);
}else{
    /* Assign the values here, as it is verified that arg's are obtained from cmd line*/
    base = atoi(argv[1]);
    exp = atoi(argv[2]);
    power(base, exp);
}

In the above program it is made sure that I reference the args (argv[1] and argv[2]) only if they are passed as commandline arguments when the program is executed.

2
votes

is this issue happen because I try to access argv[1] and argv[2] and they are not exists when I type ./program?

It is because you're not checking for null. argv[1] and argv[2] could be null if no argument is passed in. This causes segmentation fault.

int base = atoi(argv[1]);
int exp = atoi(argv[2]);

Instead, try this

int base = 0;
int exp  = 0;

if(argv[1] && argv[2])
{
  int base = atoi(argv[1]);
  int exp = atoi(argv[2]);
}

Or you could check the argument count to make sure you have 2 arguments passed in.

if(argc > 2)
{
  int base = atoi(argv[1]);
  int exp = atoi(argv[2]);
}
1
votes

When you call atoi on argv[ > 0] when there's no argument, you're accessing out of bounds memory, which is Undefined Behavior.

By the C Standard definition, accessing out of bounds memory is Undefined Behavior.


Might Interest you