Cleanup: simplify logic for copying vector button as text

An arbitrary size offsets was used in float_array_to_string,
simplify the loop, use exact size limits.

Also rename variables so it's clear which array the length apply to.
This commit is contained in:
Campbell Barton 2021-05-27 17:44:30 +10:00
parent 41f2ea4045
commit fd0bb24e4a
1 changed files with 24 additions and 41 deletions

View File

@ -2346,16 +2346,16 @@ static int get_but_property_array_length(uiBut *but)
}
static void ui_but_set_float_array(
bContext *C, uiBut *but, uiHandleButtonData *data, float *values, int array_length)
bContext *C, uiBut *but, uiHandleButtonData *data, const float *values, const int values_len)
{
button_activate_state(C, but, BUTTON_STATE_NUM_EDITING);
for (int i = 0; i < array_length; i++) {
for (int i = 0; i < values_len; i++) {
RNA_property_float_set_index(&but->rnapoin, but->rnaprop, i, values[i]);
}
if (data) {
if (but->type == UI_BTYPE_UNITVEC) {
BLI_assert(array_length == 3);
BLI_assert(values_len == 3);
copy_v3_v3(data->vec, values);
}
else {
@ -2366,56 +2366,39 @@ static void ui_but_set_float_array(
button_activate_state(C, but, BUTTON_STATE_EXIT);
}
static void float_array_to_string(float *values,
int array_length,
static void float_array_to_string(const float *values,
const int values_len,
char *output,
int output_len_max)
{
/* to avoid buffer overflow attacks; numbers are quite arbitrary */
BLI_assert(output_len_max > 15);
output_len_max -= 10;
int current_index = 0;
output[current_index] = '[';
current_index++;
for (int i = 0; i < array_length; i++) {
int length = BLI_snprintf_rlen(
output + current_index, output_len_max - current_index, "%f", values[i]);
current_index += length;
if (i < array_length - 1) {
if (current_index < output_len_max) {
output[current_index + 0] = ',';
output[current_index + 1] = ' ';
current_index += 2;
}
}
const int values_end = values_len - 1;
int ofs = 0;
output[ofs++] = '[';
for (int i = 0; i < values_len; i++) {
ofs += BLI_snprintf_rlen(
output + ofs, output_len_max - ofs, (i != values_end) ? "%f, " : "%f]", values[i]);
}
output[current_index + 0] = ']';
output[current_index + 1] = '\0';
}
static void ui_but_copy_numeric_array(uiBut *but, char *output, int output_len_max)
{
const int array_length = get_but_property_array_length(but);
float *values = alloca(array_length * sizeof(float));
const int values_len = get_but_property_array_length(but);
float *values = alloca(values_len * sizeof(float));
RNA_property_float_get_array(&but->rnapoin, but->rnaprop, values);
float_array_to_string(values, array_length, output, output_len_max);
float_array_to_string(values, values_len, output, output_len_max);
}
static bool parse_float_array(char *text, float *values, int expected_length)
static bool parse_float_array(char *text, float *values, int values_len_expected)
{
/* can parse max 4 floats for now */
BLI_assert(0 <= expected_length && expected_length <= 4);
BLI_assert(0 <= values_len_expected && values_len_expected <= 4);
float v[5];
const int actual_length = sscanf(
const int values_len_actual = sscanf(
text, "[%f, %f, %f, %f, %f]", &v[0], &v[1], &v[2], &v[3], &v[4]);
if (actual_length == expected_length) {
memcpy(values, v, sizeof(float) * expected_length);
if (values_len_actual == values_len_expected) {
memcpy(values, v, sizeof(float) * values_len_expected);
return true;
}
return false;
@ -2426,16 +2409,16 @@ static void ui_but_paste_numeric_array(bContext *C,
uiHandleButtonData *data,
char *buf_paste)
{
const int array_length = get_but_property_array_length(but);
if (array_length > 4) {
const int values_len = get_but_property_array_length(but);
if (values_len > 4) {
/* not supported for now */
return;
}
float *values = alloca(sizeof(float) * array_length);
float *values = alloca(sizeof(float) * values_len);
if (parse_float_array(buf_paste, values, array_length)) {
ui_but_set_float_array(C, but, data, values, array_length);
if (parse_float_array(buf_paste, values, values_len)) {
ui_but_set_float_array(C, but, data, values, values_len);
}
else {
WM_report(RPT_ERROR, "Expected an array of numbers: [n, n, ...]");