Reputation: 334
I'm trying to add a string to the next index of my array, however I'm having this odd issue where when Im adding to any index other than 1 (yes, I'm indexing my array from one, just to match the actual number of the item for simplicity, I'm sorry!). Essentially, if I ass to index 1, everything is fine, however when I add to index 2, the value of index 1 seems to change to the value I'm planning to put into index 2, even before the lines of code where I add the value to index 2. For example:
Say I try to add 'test1' to my array queuedHashed[100][101] at index 1, and I run through all printing all elements of the array, next to index number, I get:
1: test1
However when I go to add 'test2' at index 2 to the array, I would get:
1: test2
2: test2
I've been pulling my hair out for hours trying to fix this, and can't see where I'm going wrong. I'm currently passing my variables around using structs (due to GTK limitations), however this issue also persisted when the variables were global variables, before I changed them to local ones.
Here is my code:
queue_hash function:
static void queue_hash (GtkButton *button, gpointer user_data) {
struct data *dataStruct = user_data;
GtkWidget *hashWid = dataStruct->hash;
GtkWidget *hashTypeWid = dataStruct->hashType;
GtkWidget *hashEntryLabel = dataStruct->hashEntryLabel;
GtkListStore *store;
GtkTreeIter iter;
const char* hash = gtk_entry_get_text(GTK_ENTRY(hashWid));
int hashLen = gtk_entry_get_text_length(GTK_ENTRY(hashWid));
int hashTypeIndex = gtk_combo_box_get_active(GTK_COMBO_BOX(hashTypeWid));
store = GTK_LIST_STORE(gtk_tree_view_get_model(GTK_TREE_VIEW(list)));
// TODO: Update max length to 128
if (hashLen > 100) {
gtk_widget_set_name(hashWid, "fieldsError");
gtk_label_set_text(GTK_LABEL(hashEntryLabel), "Hash exceeds max length of 100");
g_print("Hash length exceeds 100: Exiting.");
return;
}
gtk_widget_set_name(hashWid, "");
gtk_widget_set_name(hashTypeWid, "");
gtk_widget_set_name(hashEntryLabel, "");
gtk_label_set_text(GTK_LABEL(hashEntryLabel), "Hash to be cracked:");
if ((strcmp(hash, "") == 0) || (hashTypeIndex == -1)) {
if (strcmp(hash, "") == 0) {
gtk_widget_set_name(hashWid, "fieldsError");
}
if (hashTypeIndex == -1) {
gtk_widget_set_name(hashTypeWid, "fieldsError");
}
g_print("Invalid Entry \n");
} else {
// Check for spaces in hash - return if found
// TODO: Check for other non-alphabetical chars/symbols
for (int i = 0; i < hashLen; i++) {
if (hash[i] == ' ') {
gtk_widget_set_name(hashWid, "fieldsError");
gtk_widget_set_name(hashEntryLabel, "errorLabel");
gtk_label_set_text(GTK_LABEL(hashEntryLabel), "Please remove all spaces");
g_print("Space found in hash: Exiting\n");
return;
}
}
g_print("//////////////////////////////\n");
g_print("Before: (HashCount: %i)\n", dataStruct->hashCount);
//test_queue(dataStruct->queuedHashes, dataStruct->hashCount);
for (int i = 1; i <= dataStruct->hashCount; i++) {
g_print("%i: %s\n", i, dataStruct->queuedHashes[i][0]);
}
sleep(1);
// Save hash to array
++dataStruct->hashCount;
g_print("After Increment: %i\n", dataStruct->hashCount);
g_print("Hash: %s\n", hash);
dataStruct->queuedHashes[dataStruct->hashCount][0] = hash; // Line to actually add new string to array
dataStruct->queuedHashTypes[dataStruct->hashCount] = hashTypeIndex;
g_print ("Queue Hash: %s %i\n", dataStruct->queuedHashes[dataStruct->hashCount][0], dataStruct->queuedHashTypes[dataStruct->hashCount]);
sleep(1);
g_print("After: (HashCount: %i)\n", dataStruct->hashCount);
//test_queue(dataStruct->queuedHashes, dataStruct->hashCount);
g_print("Manual 1: %s, 2: %s\n", dataStruct->queuedHashes[1][0], dataStruct->queuedHashes[2][0]);
for (int i = 1; i <= dataStruct->hashCount; i++) {
g_print("%i: %s\n", i, dataStruct->queuedHashes[i][0]);
}
}
Part of calling function that calls the above function:
struct data *hash_data = g_new0(struct data, 1);
hash_data->hash = hashEntry;
hash_data->hashType = hashSelect;
hash_data->hashEntryLabel = hashEntryLabel;
g_signal_connect(queueButton, "clicked", G_CALLBACK (queue_hash), hash_data);
Global struct definition:
struct data {
char* queuedHashes[100][101];
int queuedHashTypes[100];
int hashCount;
GtkWidget *hash;
GtkWidget *hashType;
GtkWidget *hashEntryLabel;
GtkTreeSelection *selectedHash;
};
I have a lot of print statements in there to help illustrate where things seem to be changing unexpectedly, here is the output of the program when run, and two values are entered:
//////////////////////////////
Before: (HashCount: 0)
After Increment: 1
Hash: 12357890
Queue Hash: 12357890 1
After: (HashCount: 1)
Manual 1: 12357890, 2: (null)
1: 12357890
//////////////////////////////
Before: (HashCount: 1)
1: asdfghjkl <----- This should be "1: 12357890", as the array has not yet been changed
After Increment: 2
Hash: asdfghjkl
Queue Hash: asdfghjkl 2
After: (HashCount: 2)
Manual 1: asdfghjkl, 2: asdfghjkl
1: asdfghjkl <----- This should be "1: 12357890"
2: asdfghjkl
Here is my full code for all relevant functions: https://pastebin.com/41W3n5W2
Any help would be greatly appreciated, thanks!
Upvotes: 1
Views: 70
Reputation: 34829
The symptom described in the question usually indicates that the code isn't making a copy of the string. As a result, every "string" stored in the array is just a pointer to the same input buffer, and therefore every entry in the array appears to be the last string received from the user.
The fix is to make a copy of the string. On a POSIX system, you can use the strdup
function to make a copy. The strdup
function is essentially a call to malloc
following by a call to strcpy
, which makes a copy of the string, and returns a pointer to the copy. So if your implementation doesn't support strdup
, you can easily write your own function to allocate memory, and copy the string.
Upvotes: 1