дамп ядра при переборе массивов

У меня возникли проблемы со следующим кодом. newrows - это параметр, который напрямую передается функции, в которой я работаю. elements вычисляются немного раньше с использованием другого параметра. Каким-то образом для некоторых комбинаций значений для новых строк и элементов я получаю дамп ядра, в то время как другие комбинации работают нормально. Обычно, когда происходит создание дампа ядра, было выполнено от 20 000 до 25 000 итераций. Однако, когда все работает нормально, было до 40000 итераций.

int32_t newimage[newrows][elements][3];
    int32_t pixelcounter[newrows][elements];

    //int32_t norm, angle, rohmax;
    //double r, alpha, beta, m, mu;



    //initialize arrays

    for(i=0; i<newrows; i++){
        for(j=0; j<elements; j++){
            pixelcounter[i][j] = 0;
            newimage[i][j][0] = 0;
            newimage[i][j][1] = 0;
            newimage[i][j][2] = 0;

        }
    }

комбинация, которая работает нормально: 200 : 188

комбинация, приводящая к дампу ядра: 200 : 376

Я использую линукс кстати :-)


person user3224065    schedule 22.01.2014    source источник


Ответы (1)


Скорее всего, это проблема с местом в стеке. Обратите внимание, что newimage и pixelcounter размещаются в кадре стека любой функции, в которой они объявлены. Вы можете быстро исчерпать пространство, пытаясь выделить большой объем данных. Ваш трехмерный массив newimage растет как

#bytes = newrows * elemets * 3

Я почистил вашу программу (хороший совет — попробуйте представить программы, которые компилируются, чтобы люди могли помочь вам быстрее!):

#include <stdio.h>
#include <stdint.h>

void test(size_t newrows, size_t elements) {
    int32_t newimage[newrows][elements][3];
    int32_t pixelcounter[newrows][elements];

    //initialize arrays

    for(size_t i=0; i<newrows; i++) {
        for(size_t j=0; j<elements; j++) {
            pixelcounter[i][j] = 0;
            newimage[i][j][0] = 0;
            newimage[i][j][1] = 0;
            newimage[i][j][2] = 0;
        }
    }
}

int main(void) {
    printf("Size of integer = %ld\n", sizeof(int));
    for (size_t i = 700; ; i += 10) {
            printf("Testing (%ld, %ld)\n", i, i);
            test(i, i);
    }
    return 0;
}

И запустив это, я вижу:

Size of integer = 4
Testing (700, 700)
Testing (710, 710)
Testing (720, 720)
Testing (730, 730)
[3]    13482 segmentation fault (core dumped)  ./a.out

Таким образом, где-то между 720^2 * 3 * 4 и 730^2 * 3 * 4 байтами, что составляет около 6 МБ на моем 64-битном компьютере с Linux, на вашем компьютере может быть иначе.

Решение в этом случае — разместить ваши массивы в куче, где у вас будет гораздо больше памяти для работы. Дополнительную информацию о многомерных массивах с выделением кучи можно найти в Как C выделяет пространство для 2D (3D...) массива при использовании malloc?.

person Charles    schedule 02.02.2014