I am trying to get the first character of my char malloc like this:
char * str = malloc(sizeof(char)*100);
strcpy(str, op_mmin);
char *temp6=NULL;
strcpy(temp6,str[0]);
However, I am getting the following warning:
warning: passing argument 2 of ‘strcpy’ makes pointer from integer without a cast [enabled by default]
strcpy(temp6,str[0]);
^
Why can't I do str[0] to get the first char? I also tried to do this using ordinary arrays (eg. not a malloc) and I get the same error. How do I get the first char of this malloc (or array if you know that way too)?
Because str[0] is a character, not a string. And function strcpy must use two string (char *) as argument.
To resolve your problem, you can set temp[0] = str[0]; or use sprintf function, or use strncpy function
But you must allocate temp array before you want to use it.
Regarding char *temp6=NULL;
Here you're trying to tell the compiler, "Hey ! set up temp6 as a pointer to char but don't allocate memory for it. "
If you do something like strcpy(temp,str); later you will get segmentation fault because you are trying to write to memory you don't own.
In your case you didn't go so far to see the segmentation fault, the compiler caught another error which is mentioned by the other answerer, ie in the line :
strcpy(temp6,str[0]);
where the compiler expected second argument to be char* but you passed char.
You have to allocate memory to the pointer first, or point it to an array.
It is also possible to de-allocate the memory you have allocated for a pointer.
char* temp= malloc(sizeof(char) * 10) ; // allocating memory
temp='\0'; // In essence de-allocating the memory.
Below is a complete example.
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
main()
{
char* temp= malloc(sizeof(char) * 10) ; //allocating memory enough to store 10 chars
char* str="abcdefgh"; // play safely - always store less than 10 characters. Consider that \0 will be appended to the end.
strcpy(temp,str);
printf("Temp : %s\n",temp);
char* str1="ijklmnop";
strcpy(temp,str);
printf("Temp : %s\n",temp);
temp='\0'; // In essence deallocating the memory.
printf("Temp : %s\n",temp);
strcpy(temp,str);
printf("Temp : %s\n",temp);
}
will give you the below result.
Temp : abcdefgh
Temp : abcdefgh
Temp : (null)
Segmentation fault (core dumped)
Also make sure that free(temp6) is placed at the end of your code to clean
up the memory.
Though this doesn't directly answer your question, hope it will be useful.
I solved the problem as follows:
char temp6 = op_mmin[0];
That's it! Now temp6 has the first char in op_mmin. Thank you all for your help.
Related
I have a short snippet where I am passing a char array into another function and changing the size in memory.
// in main
char *str = argv[1];
find(&str);
void func(char **str){
// some code
*str = realloc(*str, 10+1);
}
This gives the error
realloc(): invalid pointer
Aborted (core dumped)
What did I do wrong here? In order to change the value of str in another function, I am using a double pointer.
What did I do wrong here?
*str in realloc(*str, 10+1) was not allocated by this process. #Barmar
Your code could have used the below or equivalent to allocate its own copy to later reallocate it. As strdup() is not in C STL as of C17, a sample implementation.
char *str = strdup(argv[1]);
I'm trying to implement a function that concatenate two strings, but I keep getting the same error.
"pointer being realloc'd was not allocated"
When I compiled the same code on a windows machine it worked, is it something that I'm missing?
The code below is basically what I'm trying to do.
main:
int main() {
int length = 4096;
char *string = malloc(length * sizeof(char));
createString(string, length);
realloc(string, 30);
return 0;
}
createString:
void createString(char * string, int length) {
char *copyAdress = string;
char *temp ="";
int counter2 = 0;
fflush(stdin);
fgets(string, length,stdin);
while(*string != EOF && *string != *temp ) {
string++;
counter++;
}
string = copyAdress;
realloc(string, (counter)*sizeof(char));
}
Thanks!
Edit:
I want createString to change the size of string to the length of the string that I get with fgets, while having the same address as the string that I sent in, so I can allocate more memory to it later when I want to add another string to it.
There are several issues:
realloc(string, (counter)*sizeof(char)); is wrong, you need string = realloc(string, (counter)*sizeof(char)); because realloc may return a different address.
Calling createString(string, length); won't modify string
If you want a more accurate answer you need to tell us what exactly createString is supposed to do. In your code there is no attempt to concatenate two strings.
Let's work through this in order of execution.
fflush(stdin); is undefined behaviour. If you really need to clear everything in the stdin you have to find another way (a loop for example). There are compilers/systems with a defined implementation but I would not count on it.
string++; is superflous as you overwrite string after the loop.
realloc(string, (counter)*sizeof(char));
should be
char *temp = realloc(string, (counter)*sizeof(char));
if (temp != NULL)
string = temp;
This way you get the pointer where your new string is located, but I suggest you read the refecerence for realloc. In essence you do not know if it has been moved and the old address might be invalid from that point on. So dereferencing it is also undefined behaviour.
After this you would have to return the new address of string or pass the address of the pointer to your function.
The same problem repeats with the second realloc. You only got to know your first call was wrong, because the second call noticed that you do not have valid data in what you thought would be your string.
In regards to your comment: It is not possible to use realloc and to be sure that the reallocated memory is in the same place as before.
If you realloc some memory, the pointer pointing to the original memory becomes invalid (unless realloc failed and returned NULL). So calling realloc twice on the same pointer should indeed not work (if it didn't return NULL the first time).
See the answers from others about what you do wrong. However, the eror message means that on MacOS, the realloc in createString deallocated the orignal string and allocated a new one, and now your realloc in main tries to realloc a pointer that is no longer valid (allocated). On Windows, the memory was not deallocated in createString and so the second call of realloc (in main) is given a valid pointer.
Below is the code for a method i made called inputReader it reads input from a textfile and copies it to a struct wordz and from that struct i retrieve the 3 most frequent words which is what is displayed below.
I am trying to concatenate all 3 words as one pointer so i can return it to the main method but whenever i use any method to do with w1, w2, w3, that copies to a new struct or array or pointer i ALWAYS get this error "Segmentation fault(core dumped)"
Any idea why this happens or how I can work around it?
Struct Code:
#define maxLetters 101
typedef struct {
char word[maxLetters];
int freq;
} WordArray; //struct type
Code:
char * w1; // most frequent word
char * w2; // second most frequent word
char * w3; // third most frequent word
// finds w1
for(j = 0; j < uniqueWords; j++)
if(wordz[j].freq == freqz[uniqueWords-2]+1)//excludes whitespace frequency
w1 = wordz[j].word;
// finds w2
for(j = 0; j < uniqueWords; j++)
if(wordz[j].freq == freqz[uniqueWords-3]+1)//excludes whitespace frequency
w2 = wordz[j].word;
// finds w3
for(j = 0; j < uniqueWords; j++)
if(wordz[j].freq == freqz[uniqueWords-4]+1)//excludes whitespace frequency
w3 = wordz[j].word;
char *p;
// if i dont include strcat methods the method runs fine and outputs fine
strcat(p, w1); // once this operation is executed i get the error
strcat(p, " ");
strcat(p, w2);
strcat(p, " ");
strcat(p, w3);
You're trying to concatenate to an uninitialized pointer. Allocate memory to 'p'.
char *p = malloc(size)
It's a good idea to read the documentation of strcat thoroughly to check you are using it properly. You can look here http://man7.org/linux/man-pages/man3/strcat.3.html for example. There are also plenty of answers to similar questions on stackoverflow that you would have found helpful:
Segmentation fault- strcat
strcat causing segmentation fault
strcat segmentation fault
However, to save you some anguish, the fault is because to have not allocated any space for the results string p. strcat does not do this in C like it might in C# or other languages.
You would need:
char p[maxletters];
Better still, you should use strncpy with the size limit to prevent memory corruption:
strncpy(p, w1, maxletters);
The root cause leading to your issue is that p does not point anywhere, so trying to copy data to it invokes the infamous Undefined Behaviour.
So allocate some memory to p, either from the heap or from the stack.
To get it from the heap do:
char * p = malloc(some_size);
When then trying to strcat() data to this pointer be aware that strcat() expects its 1st argument to already point to a valid C-"string", that is a 0-teminated char array, to that it can concatenate what the 2nd argument is pointing to.
To take care this, make sure the data p is pointing to is does at least has its first bytes set to 0:
p[0] = '\0';
if not all bytes:
memset(p, 0, some_size);
If going for the latter you might also like to do:
char * p = calloc(some_size, sizeof *p);
As calloc() does the same as malloc() and addtionally initilaises all memory allocated with 0s.
If you feel initalising is to much effort then you cannot start concatenating using strcat(), but nered to start with strcpy() which does not rely on its 1st argument pointing to a valid C-"string", but simply copies what its 2nd argument is pointing to to where its 1st argement is pointing to.
chart * p = malloc(some_size);
strcpy(p, w1);
strcat(p, " ");
...
Finally:
Do not forget to call free() on p if the memory isn't needed anymore, to avoids a memory leak.
Also always check the outcome of memory allocation, that is check the result of malloc/calloc() against NULL, before using it.
i am new to c programming. i am getting Segmentation fault (core dumped) when i am
trying to print the string. please help.
#include <stdio.h>
#include <string.h>
int main()
{
char *ptr;
strcpy(ptr, "mystring");
printf( "%s\n", ptr);
return 0;
}
You haven't allocated any memory for your pointer to point at.
char array[MAX_LEN + 1];
char *ptr = array;
strncpy(ptr, "Cadence", MAX_LEN);
ptr[MAX_LEN] = '\0';
printf( "%s\n", ptr);
Please note that strncpy() can be a safer way to copy strings, since we specify the maximum number of characters to copy, which makes it harder to overrun the string and 'scribble' memory.
Update in response to comments: I've altered the above code to use a slightly safer pattern. You might also want to investigate strlcpy() (non-standard library).
When you declare char *ptr;, you allocate memory for a pointer to a char. But if you want to put a string inside the char, it will make an overflow.
Therefore, you have to allocate memory for your string :
char str[1024]; // which is the maximum string lenth that you will be able to put in str.
Furthemore, don't forget the null terminator (\0) that terminate every string and has the size of one char
I have the following code.
#include <string.h>
#include <stdio.h>
int main()
{
char * l;
*l = 'c';
*(l+1) = 'g';
*(l+2) = '\0';
char *second;
strcpy(second, l);
printf("string: %s\n", second);
}
When I run it is says:
The output says "Segmentation fault"....any suggestions??
Thanks
l is an uninitialized pointer; you can't dereference it. You should allocate enough space to write its contents (statically (1) or dynamically (2)).
char l[3]; /* (1) */
#include <stdlib.h>
char *l = malloc(3); /* (2) */
It is the same error with strcpy: second is an unitialized pointer, you can't write into it.
You will learn to despise the Segmentation Fault error...
It's usually called when you try to access memory that is not yours. Most common occurrence would be when you try to access an array index that is out of bounds.
char *l just creates a pointer to a char. What you want is a string, which in C is defined as an array of chars. So when you try to access the next location in memory of whatever l is pointing to (which will probably just be garbage), you're going to access memory that isn't yours, thus Segmentation Fault
You could get memory with malloc or point the pointer to an already existing variable.
char word[3];
char *l;
l = word;
Now you can do such assignments:
*l = 'c';
*(l+1) = 'g';
*(l+2) = '\0';
but now that you want to copy it to another pointer, this pointer must be pointing to another string or you should allocate memory for it.
char *pointer_to_second;
char second[3];
pointer_to_second = second;
or if you prefer to get dynamic memory, change the 3 lines above be this one bellow:
char *pointer_to_second = malloc(sizeof(char) * 3);
after that you can do what you wanted:
strcpy(pointer_to_second, l);
But remember, if you are using a C compiler you must declare all variables at the beggining, otherwise you will get an error. If you are using a C++ compiler you won't have to concern about it.
Segmentation fault happens when you try to access a field that doesn't belong to your vector. For example, if you try this:
printf("The value in position 3 of my pointer is %c\n", *(l + 3));
You will probably get an error, because you pointer have 3 positions and you are trying to acess the 4th one.