es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

Fallo de segmentación con matrices intrínsecas

Sigo recibiendo errores de segmentación con el siguiente código cada vez que intento escribir en “result”. El propósito del código es convertir una matriz de dobles “data” en un arreglo de __m256d, agregando buffers de columnas de 0’s si es necesario mientras se transpone simultáneamente. Ejemplo:

[[0, 1, 2, 3, 4, 5]
 [6, 7, 8, 9, 10, 11]]

se transpone a

[{0, 1, 2, 3}, {6, 7, 8, 9},
 {4, 5, 0, 0}, {10, 11, 0, 0}]

La función es la siguiente:

void transpose<em>alter(<strong>m256d *result, matrix *mat) {
for (int r = 0; r < mat->rows; r++) {
double *mat</strong></em>data<em>offset = (double *) mat->data + r * mat->cols;
int c</em>block;
for (c<em>block = 0; c</em>block < mat->cols / 4; c<em>block++) {
result[c</em>block * mat->rows + r] = <em>mm256</em>loadu<em>pd(mat</em>data<em>offset + c</em>block * 4);
}
if (mat->cols % 4 > 0) {
double buffer[4] = {0, 0, 0, 0};
memcpy(buffer, mat<em>data</em>offset + c<em>block * 4, (mat->cols % 4) * sizeof(double));
result[c</em>block * mat->rows + r] = <em>mm256</em>loadu<em>pd(buffer);
}
}
}

El argumento pasado en “result” cuando se producen errores de segmentación es:
_</em>m256d *alt = (m256d *) malloc((mat->cols + 3) / 4 * mat->rows * sizeof(__m256d));

Tags:  , , ,

Answer

  1. Avatar for davy.ai

    El segfault probablemente está ocurriendo porque se está accediendo al array result fuera de los límites. Específicamente, la memoria asignada para result puede que no sea lo suficientemente grande como para contener todos los elementos que se están escribiendo en ella.

    En el código proporcionado, result se asigna utilizando malloc con un tamaño de (mat->cols + 3) / 4 * mat->rows * sizeof(__m256d). La expresión (mat->cols + 3) / 4 calcula el número de bloques de 4 elementos necesarios para contener todas las columnas de la matriz. Sin embargo, esta expresión no tiene en cuenta la posibilidad de necesitar un bloque extra para contener cualquier columna restante que no encaje uniformemente en bloques de 4 elementos.

    Para solucionar el problema, el tamaño de result debe calcularse de la siguiente manera:

    int num_blocks = (mat->cols + 3) / 4;
    int num_extra_cols = mat->cols % 4;
    if (num_extra_cols > 0) {
        num_blocks++;
    }
    __m256d *alt = (__m256d *) malloc(num_blocks * mat->rows * sizeof(__m256d));
    

    Este código calcula el número de bloques de 4 elementos necesarios como antes, pero también comprueba si hay columnas restantes que no encajan uniformemente en bloques (num_extra_cols). Si las hay, incrementa el número de bloques necesarios.

    Con este cambio, result debería ser lo suficientemente grande como para contener todos los elementos que se están escribiendo en ella, y el segfault debería resolverse.

Comments are closed.