How can I fix this error which causes my other string not to print?

Advertisements

I am trying to run the program below where one contains a date and the other contains the clothes in an outfit. The date structure works fine, but the one about the outfit results in the following error:

main.c: In function ‘main’:
main.c:41:5: warning: ‘__builtin_memcpy’ writing 21 bytes into a region of size 0 overflows the destination [-Wstringop-overflow=]
   41 |     strcpy(&wtywtd.Face[100], "Prescription_Glasses");
      |     ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
main.c:34:19: note: at offset 500 into destination object ‘wtywtd’ of size 500
   34 |     struct Outfit wtywtd;
      |                   ^~~~~~
Todays date is 5/7/2016
*** stack smashing detected ***: terminated

I have followed other questions and realized I must put an ‘&’ in each string copy to make sure strings can be inputted, but I cannot find what is causing the error above. My code is seen below:

//Reviewing structures
#include <stdio.h>
#include <string.h>

int main()
{
    //The following is a structure for a date.
    //A structure can be defined as a group of variables
    
    struct date //Here, a structure called 'data', along with inner variable like the month, the date, and the year are displayed
    {
        int month;
        int day;
        int year;
    };
    
    //A variable must be declared to link the structure:
    struct date DateToday;
    
    //The following below shows how to assign values to inside the structure:
    DateToday.month = 5;
    DateToday.day = 7;
    DateToday.year = 2016;
    
    struct Outfit
    {
        char Footwear[100];
        char Bottoms[100];
        char Tops[100];
        char OverTop[100];
        char Face[100];
    };
    
    struct Outfit wtywtd;
    
    //When declaring strings, you must use double quotes
    strcpy(&wtywtd.Footwear[100], "Dark_Black_and_Gray_Nike_shoes");
    strcpy(&wtywtd.Bottoms[100], "Dark_Beige_Cargo_Shorts");
    strcpy(&wtywtd.Tops[100], "Dark_Red_And_Black_Striped_Tshirt");
    strcpy(&wtywtd.OverTop[100], "Grey_Hooded_Fleece_Jacket");
    strcpy(&wtywtd.Face[100], "Prescription_Glasses");
    
    printf("Todays date is %i/%i/%i", DateToday.month,DateToday.day,DateToday.year);
    printf("\nThe clothes I wore when going out were %s, %s, %s, %s, and %s", wtywtd.Footwear, wtywtd.Bottoms, wtywtd.Tops, wtywtd.OverTop, wtywtd.Face);
    
    return 0;
}

I am trying to print out a string that mentions clothes worn, as shown in the program. However, I get the error listed above.

EDIT: I have removed the ‘&’ symbols, but now I get the errors below:

    main.c: In function ‘main’:
main.c:37:27: warning: passing argument 1 of ‘strcpy’ makes pointer from integer without a cast [-Wint-conversion]
   37 |     strcpy(wtywtd.Footwear[100], "Dark_Black_and_Gray_Nike_shoes");
      |            ~~~~~~~~~~~~~~~^~~~~
      |                           |
      |                           char
In file included from main.c:3:
/usr/include/string.h:141:39: note: expected ‘char * restrict’ but argument is of type ‘char’
  141 | extern char *strcpy (char *__restrict __dest, const char *__restrict __src)
      |                      ~~~~~~~~~~~~~~~~~^~~~~~
main.c:38:26: warning: passing argument 1 of ‘strcpy’ makes pointer from integer without a cast [-Wint-conversion]
   38 |     strcpy(wtywtd.Bottoms[100], "Dark_Beige_Cargo_Shorts");
      |            ~~~~~~~~~~~~~~^~~~~
      |                          |
      |                          char
In file included from main.c:3:
/usr/include/string.h:141:39: note: expected ‘char * restrict’ but argument is of type ‘char’
  141 | extern char *strcpy (char *__restrict __dest, const char *__restrict __src)
      |                      ~~~~~~~~~~~~~~~~~^~~~~~
main.c:39:23: warning: passing argument 1 of ‘strcpy’ makes pointer from integer without a cast [-Wint-conversion]
   39 |     strcpy(wtywtd.Tops[100], "Dark_Red_And_Black_Striped_Tshirt");
      |            ~~~~~~~~~~~^~~~~
      |                       |
      |                       char
In file included from main.c:3:
/usr/include/string.h:141:39: note: expected ‘char * restrict’ but argument is of type ‘char’
  141 | extern char *strcpy (char *__restrict __dest, const char *__restrict __src)
      |                      ~~~~~~~~~~~~~~~~~^~~~~~
main.c:40:26: warning: passing argument 1 of ‘strcpy’ makes pointer from integer without a cast [-Wint-conversion]
   40 |     strcpy(wtywtd.OverTop[100], "Grey_Hooded_Fleece_Jacket");
      |            ~~~~~~~~~~~~~~^~~~~
      |                          |
      |                          char
In file included from main.c:3:
/usr/include/string.h:141:39: note: expected ‘char * restrict’ but argument is of type ‘char’
  141 | extern char *strcpy (char *__restrict __dest, const char *__restrict __src)
      |                      ~~~~~~~~~~~~~~~~~^~~~~~
main.c:41:23: warning: passing argument 1 of ‘strcpy’ makes pointer from integer without a cast [-Wint-conversion]
   41 |     strcpy(wtywtd.Face[100], "Prescription_Glasses");
      |            ~~~~~~~~~~~^~~~~
      |                       |
      |                       char
In file included from main.c:3:
/usr/include/string.h:141:39: note: expected ‘char * restrict’ but argument is of type ‘char’
  141 | extern char *strcpy (char *__restrict __dest, const char *__restrict __src)
      |                      ~~~~~~~~~~~~~~~~~^~~~~~

>Solution :

Looking specifically at the warning, &wtywtd.Face[100] is a pointer to one element past the end of the wtywtd.Face, so you’re telling strcpy to write to memory after the given array. Writing past the bounds of a variable’s memory triggers undefined behavior which in your case manifests in a crash.

You want to pass the starting address of the array to strcpy, i.e.:

strcpy(wtywtd.Footwear, "Dark_Black_and_Gray_Nike_shoes");
strcpy(wtywtd.Bottoms, "Dark_Beige_Cargo_Shorts");
strcpy(wtywtd.Tops, "Dark_Red_And_Black_Striped_Tshirt");
strcpy(wtywtd.OverTop, "Grey_Hooded_Fleece_Jacket");
strcpy(wtywtd.Face, "Prescription_Glasses");

Note that an array when used in an expression decays to a pointer to its first member.

Leave a ReplyCancel reply