Thread: Strcpy makes pointer from integer without a cast?

  1. #1
    Registered User
    Join Date
    Jan 2012
    Posts
    9

    Unhappy Strcpy makes pointer from integer without a cast?

    Hello again, I'm sorry for my newbie-ness at C.


    I'm trying my best to learn, and I've been doing nothing but study the last week!
    But I'm afraid pointers were just a major wall to me...I was hoping someone could help me with this program - I've made a thread a couple days ago, but I greatly corrected the code, started from scratch, and I think I've done some improvements, but again, I've hit a wall.

    So, I'll try to explain the purpose of this program -This program is intended to read a .TXT file which contains a large database of car brands, price, model of the gar, how many doors it has, etc...

    This is in the database under the form of:
    Code:
      BRAND  MODEL  VERSION  DOORS  FUELTYPE  PRICE €
    You can see it HERE

    So, that said, I tried making a program which did this:
    Shows a menu of things to do, many I haven't even gotten to, so I'll talk about only the important options.

    Code:
    0 - Exits the program
    1 - Asks you what file to read
    2 - Shows all the brands of cars the file possesses
    3 - Shows you the price of a target car, after you giving him the BRAND and MODEL.
    INFO : Using gcc from CYGWIN to compile the program, and Notepad++ to write it.


    Here goes the code, I'll try and split it into the functions I did

    Code:
    #include <stdio.h>#include <stdlib.h>
    #include <string.h>
    
    
    #define MAX_AUTO 6000
    #define BRAND 20
    #define MODEL 25
    #define VERSION 100
    #define FUELTYPE 15


    Initialize a structure to put the file after it's read in.

    Code:
    typedef struct
    {					
    	char Brand[BRAND]; 
    	char Model[MODEL];
    	char Version[VERSION];
    	int Doors;
    	char Fueltype[FUELTYPE];
    	int Price;
    } AUTOMOBILE;


    This function is supposed to put all the structure entries at /0 before reading the file
    Code:
    void clean_database(AUTOMOBILE *ptr)
    {
    	int i;
    	
    	for(i=0;i < MAX_AUTO; i++)
    		{
    			strcpy(ptr[i].Brand,"\0");
    			strcpy(ptr[i].Model,"\0");				
    			strcpy(ptr[i].Version,"\0");
    			ptr[i].Doors = 0;
    			strcpy(ptr[i].Fueltype,"\0");
    			ptr[i].Price= 0.0;
    		}
    }


    Shows the menu
    Code:
    void show_menu()
    {
    	int esc;
    
    
    	printf("\t\tC PROGRAMMING IS HARD\n\n");
    	printf("\t0 - Exit program\n");
    	printf("\t1 - Read database file\n");
    	printf("\t2 - Show all brands in database file\n");
    	printf("\t3 - Show price\n");
    
    
    	while(1)
    	{
    		printf("Choose option:");
    		scanf(" %d",&esc);
    		
    		if(esc < 0 || esc > 12)
    			printf("Wrong Input\n");
    		else
    			break;
    	}
    	
    	
    	switch(esc)
    	{
    		case 0: printf("Program terminated.\nGoodbye"); exit(0);
    		case 1: printf("1"); break;
    		case 2: printf("2"); break;
    		case 3: printf("3"); break;
    	}
    }


    And the one giving me all the problems - the read file
    Code:
    void  read_file(int argc, char *argv[])
    {
      int i=0,cont=0,contr=0;
      char ch[500];
      
      
      AUTOMOBILE car[MAX_AUTO];
      
      FILE *fp;
      
      clean_database(car);
      
      if(argc==2)
        {
          if((strcmp(argv[1],"bd.txt"))==0)    
        
          {
            fp=fopen(argv[1],"r");
            
            if(fp==NULL)
              {
                printf("Opening the file %s was not possible\n",argv[1]);
                exit(1);
              }
            
            while((fgets(ch,500,fp))!=NULL)
              {
                for(i=0;i!='\0';i++)
                  {
                    if(ch[i]==' ' && ch[i+1]==' ')
                      {
                        switch(cont)
                        {
                          case 0:{
                                while(ch[i+2] != *strstr(ch,"  "))
                                  {
                                    strcpy(car->Brand, ch[i+2]);
                                    cont++;
                                  } break;
                              }
                              
                          case 1:{
                                while(ch[i+2]!= *strstr(ch,"  "))
                                  {
                                    strcpy(car->Model, ch[i+2]);
                                    cont++;
                                  } break;
                              }
                              
                          case 2:{
                                while(ch[i+2]!= *strstr(ch,"  "))
                                  {
                                    strcpy(car->Version, ch[i+2]);
                                    cont++;
                                  } break;
                              }
                              
                          case 3:{
                                while(ch[i+2]!= *strstr(ch,"  "))
                                  {
                                    strcpy(car->Doors, ch[i+2]);
                                    cont++;
                                  } break;
                              }
                                
                          case 4:{
                                while(ch[i+2]!= *strstr(ch,"  "))
                                  {
                                    strcpy(car->Fueltype, ch[i+2]);
                                    cont++;
                                  } break;
                              }
                                
                          case 5:{
                                while(ch[i+2]!= *strstr(ch,"  "))
                                  {
                                    strcpy(car->Price, ch[i+2]);
                                  } break;
                              }            
                            
                        }
                      }
                    
                    else
                      continue;
                  }
              }
      
              
            printf("%d parameters have been read and saved into the programs structure",i);
            show_menu ();
          }
        }
      else
        
        if(argc>2)
          {
            printf("Sintax: \n\n%s File\n\nou\n\n%s",argv[0],argv[0]);
            exit(2);
          }
        else
          
          if(argc==1)
            {
              contr++;
              show_menu(contr);  
      
      
              fclose(fp);
            }
    }
    I've attached the complete file on the thread, I don't want to make the thread too long, which it already is.


    Almost forgot - errors I get are
    Code:
    tentar.c: In function `read_file':tentar.c:111: warning: passing arg 2 of `strcpy' makes pointer from integer without a cast
    tentar.c:119: warning: passing arg 2 of `strcpy' makes pointer from integer without a cast
    tentar.c:127: warning: passing arg 2 of `strcpy' makes pointer from integer without a cast
    tentar.c:135: warning: passing arg 1 of `strcpy' makes pointer from integer without a cast
    tentar.c:135: warning: passing arg 2 of `strcpy' makes pointer from integer without a cast
    tentar.c:143: warning: passing arg 2 of `strcpy' makes pointer from integer without a cast
    tentar.c:151: warning: passing arg 1 of `strcpy' makes pointer from integer without a cast
    tentar.c:151: warning: passing arg 2 of `strcpy' makes pointer from integer without a cast

    And those are all in the read_file function, in each and every strcpy...THANKS FOR YOUR HELP IF YOU CAN Regards,Bruno
    Attached Files Attached Files
    Last edited by Kalastrian; 01-06-2012 at 06:21 PM.

  2. #2
    Registered User
    Join Date
    Nov 2010
    Location
    Long Beach, CA
    Posts
    5,909
    ch is a char array. ch[i+2] is a individual char (it gets promoted to an int when passed to a function, hence the "from integer" part). What exactly are you trying to do there? Copy everything from the 3rd letter on, or copy only 2 characters from the string, or something else?

  3. #3
    Registered User
    Join Date
    Jan 2012
    Posts
    9
    Well, what I wanted to do was copy the information from the file into the structure, in good order.

    So, since the brand, version, etc of the cars is separated by 2 spaces, I tried that way...

    Major failure I guess.

    What do you suggest to fix it?

    Thank you so much for your answer, really appreciate it.


    EDIT:
    I just want to copy the file into my struct, while still assigning them to the correct places, so I can later go on the struct and easily get the brands, etc. Or would you recommend not using a struct at all, leaving the file open in read mode and then just do a function to search the strings for the brand version etc?
    Last edited by Kalastrian; 01-06-2012 at 06:41 PM.

  4. #4
    Registered User
    Join Date
    Nov 2010
    Location
    Long Beach, CA
    Posts
    5,909
    sscanf, or if that wont work, maybe strtok.

  5. #5
    Banned
    Join Date
    Aug 2010
    Location
    Ontario Canada
    Posts
    9,547
    Read up on fscanf() ... this is an input routine that does pattern matching... and returns the number of successful conversions, so you can monitor it for failures.

    If that doesn't get it... load the entire line as a single string using fgets(), run through it looking for double spaces, replace one of the spaces with a coma or some other suitable deliminter... then unleash sscanf() on it...

    And if THAT doesn't get it, use strtok() to break the thing into separate strings and extract the data that way.


    What you have is a very nasty problem, whatever programmer wrote that data file should probably be flipping burgers at some greasy spoon franchise... Even if it's written for human readability a few comas would have still been a really good idea.

  6. #6
    Registered User
    Join Date
    Jan 2012
    Posts
    9
    How would I do this with a sscanf?

  7. #7
    Registered User
    Join Date
    Jan 2012
    Posts
    9
    Quote Originally Posted by CommonTater View Post
    Read up on fscanf() ... this is an input routine that does pattern matching... and returns the number of successful conversions, so you can monitor it for failures.

    If that doesn't get it... load the entire line as a single string using fgets(), run through it looking for double spaces, replace one of the spaces with a coma or some other suitable deliminter... then unleash sscanf() on it...

    And if THAT doesn't get it, use strtok() to break the thing into separate strings and extract the data that way.


    What you have is a very nasty problem, whatever programmer wrote that data file should probably be flipping burgers at some greasy spoon franchise... Even if it's written for human readability a few comas would have still been a really good idea.

    Data file was written by my C Programming teacher, this is basically my final work so I can pass the class...

  8. #8
    Registered User
    Join Date
    Nov 2010
    Location
    Long Beach, CA
    Posts
    5,909
    Read the scanf documentation: fscanf man page. You're probably mostly interested in the %s format specifier. Also, Google for some scanf tutorials.

  9. #9
    Banned
    Join Date
    Aug 2010
    Location
    Ontario Canada
    Posts
    9,547
    Quote Originally Posted by Kalastrian View Post
    How would I do this with a sscanf?
    I'm happy to point you in the right direction or give you some alternatives, but --this being homework, and all-- the code is entirely your problem.

    You pass or fail on your own merrits my friend...

  10. #10
    Registered User
    Join Date
    Jan 2012
    Posts
    9
    Quote Originally Posted by CommonTater View Post
    I'm happy to point you in the right direction or give you some alternatives, but --this being homework, and all-- the code is entirely your problem.

    You pass or fail on your own merrits my friend...
    Shouldn't have mentioned it, uh?

    I'm cracking my skull at this code, trust me, but it just ain't happening... I'mma hit the hay now, 2 am, my head can't take it no more...
    I'll try tomorrow, I guess...
    Thanks anyway :\

  11. #11
    Registered User
    Join Date
    Mar 2010
    Posts
    583
    I think I can see what you were trying to do with the strcpys. I also think that something from the scanf family will make your life easier.

    You could make it work your way though. I'll point out your mistakes, so you can hopefully learn something:

    Code:
            while((fgets(ch,500,fp))!=NULL)
              {               
                for(i=0;i!='\0';i++)
    This will never execute -- '\0' == 0. I guess you mean ch[i] != '\0'

    Code:
                  {
                    if(ch[i]==' ' && ch[i+1]==' ')
                      {
                        switch(cont)
                        {
                          case 0:{
                                while(ch[i+2] != *strstr(ch,"  "))
    This is a bit bizarre. strstr will return a pointer to the first " " in ch. Using * to dereference this gives just the character " ". This seems a very long winded way of saying
    Code:
       while (ch[i+2] != ' ')
    Code:
                                  {
                                    strcpy(car->Brand, ch[i+2]);
    As a couple of people said already, ch[i+2] is a character. strcpy takes as arguments a destination buffer and a source buffer. It will keep copying until it encounters a NULL terminator '\0'.
    If you wanted to start copying the string at i+2, you could use the & operator:
    Code:
                                    strcpy(car->Brand, &ch[i+2]);
    Or you can just add directly to ch:
    Code:
                                    strcpy(car->Brand, ch+i+2);
    Since strcpy will keep going until it sees a NULL terminator, it won't just copy the brand. It looks like you expected strcpy to copy character by character? You can do that without strcpy:

    Code:
                   int d = 0; //destination position
                   while <not double space>
                          car->Brand[d] = ch[i];
                          d++; i++;
    Or, you could use strstr to determine the length until the next double space, and strncpy up to there (with strncpy you specify the number of bytes).

    Code:
    // strstr gives a pointer to the next double space. &ch[i] is a pointer to where we are now
    int length = strstr(&ch[i],"  ") - &ch[i];
    
    // strncat rather than strncpy to preserve the NULL terminator
    strncat(car->Brand, ch+i, length);
    
    // advance past the string and the double space
    i = i + 2 + length;
    
    
    .. similar for other fields
    I don't actually think you should do that. I think you should use scanf. But I think that the above might be roughly what you were trying to do, so thought I'd mention it.

  12. #12
    Registered User
    Join Date
    Jan 2012
    Posts
    9
    Quote Originally Posted by smokeyangel View Post
    I think I can see what you were trying to do with the strcpys. I also think that something from the scanf family will make your life easier.

    You could make it work your way though. I'll point out your mistakes, so you can hopefully learn something:

    Code:
            while((fgets(ch,500,fp))!=NULL)
              {               
                for(i=0;i!='\0';i++)
    This will never execute -- '\0' == 0. I guess you mean ch[i] != '\0'

    Code:
                  {
                    if(ch[i]==' ' && ch[i+1]==' ')
                      {
                        switch(cont)
                        {
                          case 0:{
                                while(ch[i+2] != *strstr(ch,"  "))
    This is a bit bizarre. strstr will return a pointer to the first " " in ch. Using * to dereference this gives just the character " ". This seems a very long winded way of saying
    Code:
       while (ch[i+2] != ' ')
    Code:
                                  {
                                    strcpy(car->Brand, ch[i+2]);
    As a couple of people said already, ch[i+2] is a character. strcpy takes as arguments a destination buffer and a source buffer. It will keep copying until it encounters a NULL terminator '\0'.
    If you wanted to start copying the string at i+2, you could use the & operator:
    Code:
                                    strcpy(car->Brand, &ch[i+2]);
    Or you can just add directly to ch:
    Code:
                                    strcpy(car->Brand, ch+i+2);
    Since strcpy will keep going until it sees a NULL terminator, it won't just copy the brand. It looks like you expected strcpy to copy character by character? You can do that without strcpy:

    Code:
                   int d = 0; //destination position
                   while <not double space>
                          car->Brand[d] = ch[i];
                          d++; i++;
    Or, you could use strstr to determine the length until the next double space, and strncpy up to there (with strncpy you specify the number of bytes).

    Code:
    // strstr gives a pointer to the next double space. &ch[i] is a pointer to where we are now
    int length = strstr(&ch[i],"  ") - &ch[i];
    
    // strncat rather than strncpy to preserve the NULL terminator
    strncat(car->Brand, ch+i, length);
    
    // advance past the string and the double space
    i = i + 2 + length;
    .. similar for other fields

    I don't actually think you should do that. I think you should use scanf. But I think that the above might be roughly what you were trying to do, so thought I'd mention it.

    Yes, that was what I was going for. Thanks so much for your post, made me realize my mistakes.

    I'll try and read up on scanf, see if I can change it to fit.

    Thanks

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Replies: 13
    Last Post: 12-29-2010, 05:44 PM
  2. 'Makes pointer from integer without a cast'
    By idlackage in forum C Programming
    Replies: 5
    Last Post: 06-10-2010, 05:48 AM
  3. makes pointer from integer without a cast
    By nyquil in forum C Programming
    Replies: 5
    Last Post: 05-06-2010, 06:40 AM
  4. Help: makes pointer from integer without a cast
    By steffi in forum C Programming
    Replies: 4
    Last Post: 11-14-2007, 04:38 AM
  5. passing arg makes pointer to integer without a cast
    By Rad_Turnip in forum C Programming
    Replies: 4
    Last Post: 07-11-2006, 05:37 PM