jordanwb Posted January 11, 2012 Share Posted January 11, 2012 I'm going to cut straight to the chase, this is my function: void client_job_results (client *c, json_object *obj) { char *tripcode_insert_query = "INSERT INTO tah_tripcodes VALUES ('', ?, ?, ?, ?)"; int job_id, results_count; unsigned long tripcode_len = 10; MYSQL_STMT *tripcode_stmt = mysql_stmt_init(conn); MYSQL_BIND tripcode_params[4]; mysql_stmt_prepare(tripcode_stmt, tripcode_insert_query, strlen(tripcode_insert_query)); memset (tripcode_params, 0, sizeof (tripcode_params)); json_object *jobs_array = json_object_object_get (obj, "jobs"), *job, *results_array, *result_pair; char *password, *tripcode, *utf8_password_orig, *salt = alloca(3), *c_password = alloca (9), *des_result = alloca (14), *utf8_password = alloca (20); // is 20 enough? memset (utf8_password, 0, 20); size_t sjis_pass_len; size_t utf8_pass_len; if (jobs_array == NULL) return; iconv_t cd = iconv_open ("UTF8", "SHIFT_JIS"); for (int i = 0; i < json_object_array_length (jobs_array); i++) { job = json_object_array_get_idx (jobs_array, i); if (job == NULL) { continue; } results_array = json_object_object_get (job, "results"); results_count = json_object_array_length (results_array); if (results_count == 0) continue; job_id = json_object_get_int (json_object_object_get (job, "job-id")); if (job_id == 0) { continue; } for (int j = 0; j < results_count; j++) { result_pair = json_object_array_get_idx (results_array, j); password = json_object_get_string (json_object_object_get (result_pair, "password")); tripcode = json_object_get_string (json_object_object_get (result_pair, "tripcode")); // check to make sure password is correct make_correct_password (password, c_password); make_salt (c_password, salt); DES_fcrypt (c_password, salt, des_result); if (strcmp (des_result + 3, tripcode) != 0) { printf ("Client gave invalid password/tripcode pair; claimed \"%s\" gave \"%s\", but got \"%s\" as a result.\n", password, tripcode, des_result + 3); continue; } // // convert to unicode sjis_pass_len = strlen (password); utf8_pass_len = sjis_pass_len * 2; utf8_password_orig = utf8_password; if (iconv (cd, &password, &sjis_pass_len, &utf8_password, &utf8_pass_len) == -1) { printf ("iconv could not convert password. Error is: %s\n", strerror(errno)); continue; } utf8_pass_len = strlen(utf8_password_orig); // tripcode_params[0].buffer_type = MYSQL_TYPE_LONG; tripcode_params[0].buffer = (void*)&job_id; tripcode_params[1].buffer_type = MYSQL_TYPE_STRING; tripcode_params[1].buffer = (void*)utf8_password_orig; tripcode_params[1].length = &utf8_pass_len; // this param is the number of bytes used in the buffer (# of single byte chars) tripcode_params[2].buffer_type = MYSQL_TYPE_STRING; tripcode_params[2].buffer = (void*)tripcode; tripcode_params[2].length = &tripcode_len; tripcode_params[3].buffer_type = MYSQL_TYPE_LONG; tripcode_params[3].buffer = (void*)&(c->user_id); mysql_stmt_bind_param(tripcode_stmt, (MYSQL_BIND *)&tripcode_params); mysql_stmt_execute (tripcode_stmt); } } iconv_close (cd); mysql_stmt_free_result (tripcode_stmt); } When the program reaches mysql_stmt_bind_param the program crashes and I don't know why. iconv does properly convert the shift_jis strings to UTF8 and the program crashes only when I try to insert unicode characters into the table. Quote Link to comment https://forums.phpfreaks.com/topic/254765-c-executing-mysql-prepared-statement-smashes-the-stack/ Share on other sites More sharing options...
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.