Jump to content

[C] executing mysql prepared statement smashes the stack


jordanwb

Recommended Posts

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.

Archived

This topic is now archived and is closed to further replies.

×
×
  • Create New...

Important Information

We have placed cookies on your device to help make this website better. You can adjust your cookie settings, otherwise we'll assume you're okay to continue.