When the parameter of strlen is a non zero terminated string, its return value is unsafe in IF statesments?

140 views Asked by At

I have been troubled by a problem of strlen for a long time, here is the code:

   char stack_protect[1000] = {0};
    char temp[100] = { 0 };
    memset(&temp, 1, 110);
    int len = strlen(temp);
    
    printf("test strlen of temp %d \n", len);
    if (len > 100)
    {
        xxxx;
    }
    else
    {
        xxxx;
    }

   char stack_protect2[1000] = {0};

you can see, I passed a param temp to strlen, and the return value len is surely 110. but the next statements if (len > 100) evaluates to false!

system: linux
CPU architecture: 32 Bit ARM SOC: nt98566

please help me! thank you

something I have test:

  1. if you assign len value to another int variable, things will ok. like below

example:

    char temp[100] = { 0 };
    memset(&temp, 1, 110);
    int len = strlen(temp);
    
    int len1 = len;
    
    if (len1 > 100) ? TRUE!
  1. the every byte of len:
   0x6e, 0x00, 0x00, 0x00
  1. in another soc hisiv300 len:110 if len > 100? TRUE
1

There are 1 answers

3
chux - Reinstate Monica On

memset(&temp , 1, 110); is bad as it attempts to write outside the temp[] array. This is undefined behavior (UB). Anything may happen at this point, in earlier or in later code.

strlen(temp); is also UB as strlen() expects a pointer to a string and array temp is not a string as it lacks a null character.

Do not expect code to behave well when it has UB.
Do not expect code to fail when it has UB.
Do not expect the UB you see today to be the same tomorrow.

Instead, eliminate the UB.

char temp[100] = {0};
//memset(&temp , 1, 110);
memset(temp , 1, 99); // Re-write the first 99, leaving the last as 0
int len = strlen(temp);

I suspect OP's code UB is the writing of len1 by memset(), yet that is only a guess.