I am attempting to shift the elements of a char array to the right in C on Linux (Ubuntu 18.04) and attempted to make a function for this. I basically want to prepend x amount of elements to the beginning of the array and shift the rest of the data by x (to the right). If the new elements + old valid elements exceed the char size, I would like the function to return an error and don't do any shifting. I also made a char pointer that points towards the char array and I use structures to set the char data.
Here is a program I made as a test:
#include <stdio.h>
#include <unistd.h>
#include <stdlib.h>
#include <string.h>
struct struct1
{
char str[10];
int myNum;
};
struct struct2
{
char str[5];
};
int shiftChar(char *arr, int size, int length)
{
for (int i = 0; i < length; i++)
{
// I know I am calculating this incorrectly. Though, not sure how I should go about checking if the new size will exceed the length of the char array.
if (length < ((i + 1) + size))
{
return -1;
}
// If element is 0, we shouldn't shift it (usually represents garbage value?). Not sure how to detect whether an element of a char array was filled with actual data or not.
if (arr[i] == 0)
{
continue;
}
arr[i + size] = arr[i];
fprintf(stdout, "Replacing %c with %c at %d => %d\n\n", arr[i + size], arr[i], i, i + size);
}
for (int i = 0; i < size; i++)
{
arr[i] = 0;
}
return 0;
}
int main()
{
char buffer[256];
struct struct1 *struct1 = (struct struct1 *) (buffer);
struct struct2 *struct2 = (struct struct2 *) (buffer + sizeof(struct struct1));
struct1->myNum = 5;
strncpy(struct1->str, "Hello!", 6);
strncpy(struct2->str, "TST", 3);
fprintf(stdout, "Buffer => ");
for (int i = 0; i < (sizeof (struct struct1) + sizeof(struct struct2)); i++)
{
fprintf(stdout, "%c", buffer[i]);
}
fprintf(stdout, "\n\n");
if (shiftChar(buffer, 6, 256) != 0)
{
fprintf(stdout, "Error shifting char array.\n");
//exit(1);
}
struct1 = (struct struct1 *) (buffer + 6);
struct2 = (struct struct2 *) (buffer + sizeof(struct struct1) + 6);
fprintf(stdout, "struct1->str => %s\n", struct1->str);
exit(0);
}
Here's an example output:
...
Error shifting char array.
struct1->str => Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hello!Hell`����
I know I am doing this incorrectly, but I'm unsure what I'm doing wrong or if I should be going about this differently.
My main questions are:
What am I doing wrong with the
shiftChar()function?Is there a better/easier way to achieve what I am trying to do?
Is there a way to check if elements in a
chararray have a garbage value (e.g. a value that hasn't been filled in yet)? I suppose I could set the buffer to all0's using something likememset(), but what happens if I have a structure with anintpointing to the buffer data with the value '0'. I'd imagine that would be excluded with the shifting if I checked if the value equals '0' or not.
I've done research on this as well, but most of the threads I've came across were for C++ or shifting elements to the left. I wasn't able to find a solid solution for my issue. I will be using the solution (if any) in another program I am making where I'll need to add the size of a struct iphdr to an existing buffer char at the beginning (with data already filled in via struct iphdr and struct udphdr) so I can create and send IPIP packets (network programming). I also understand I could make an entirely new char and just copy data over from the old buffer (while keeping the first sizeof(struct iphdr) elements free), but I'd imagine that would be quite a performance hit in my situation since I'm going to be having to do this thousands of times per second and it'd be better to just modify the existing buffer char.
I am new to C programming. Therefore, I'm sure there are things I'm missing.
If you need any additional information, please let me know and any help is highly appreciated!
Thank you for your time.
memmove()is the best way to shift the bytes over.memmove()andmemcpy().