LINUX.ORG.RU

Как это вообще такое может быть?

 


0

1

Создаю текстуру, 27 000 х 27 000 пикселей, 32х битный цвет. Мало того, что создается и рисуется, так еще и в top'е не видно, чтобы оно что-то жрало.

Скрин: https://dl.dropboxusercontent.com/u/31471800/p2p/Screenshot - 04.10.2014 - 17...

Кусок кода:

image.data.img.image = XCreateImage(
                warehouse.screen.display,
                DefaultVisual(warehouse.screen.display, warehouse.screen.activescreen),
                DefaultDepth (warehouse.screen.display, warehouse.screen.activescreen),
                ZPixmap, 0, 0, size.x, size.y, SML_IMAGEBITMAPPAD, 0);

    if (!(image.data.img.image))
        SML_RETSET(SML_ERR_BADIMAGE);

    image.data.img.image->data     =
            calloc(image.data.img.image->bytes_per_line * size.y, sizeof(char));

P.S. Памяти у меня всего 2 ГБ, судя по матрасчетам, я даже 23170х23170 создать не должен был.

★★

Ответ на: комментарий от crowbar

Насколько смог нагуглить, то

Display Memory: 1295 MB
Dedicated Memory: 64 MB
Shared Memory: 1231 MB

Mobile Intel 4 Series Chipset

sambist ★★
() автор топика

А ты уверен, что оно *действительно* выделилось, а не только сделало вид. Ты в эту область писать что-либо пробовал?

см. например memory overcommit

grondek
()
Ответ на: комментарий от grondek

А ты уверен, что оно *действительно* выделилось, а не только сделало вид.

Я бы не утверждал этого, если бы текстура на экране не отобразилась.

sambist ★★
() автор топика
Ответ на: комментарий от anonymous

На скриншоте виден рисунок, который я в эту текстуру пишу.

sambist ★★
() автор топика

у тебя NPOT-текстура. вполне может быть, что твой драйвер реально выделяет texture object размером 2^14 x 2^14 пикселей

jtootf ★★★★★
()
Ответ на: комментарий от jtootf

Какой нафиг драйвер, если согласно ману к Xlib я сам выделяю через m/calloc место под текстуру (что, собственно, наверху и происходит).

sambist ★★
() автор топика
Ответ на: комментарий от sambist

malloc тебе скажет «да, нна тебе память», но пока ты в неё реально писать не начнёшь, фактического выделения не произойдёт.

Забей всю текстуру значениями и тогда возможно увидишь OOM

Dark_SavanT ★★★★★
()

так еще и в top'е не видно

Ну, он мог его раз отрендерить в маленький вьюпорт и потом показывать. Попробуй что-нибудь изменять в текстуре и потом ее перерисовывать, это должен быть более спортивный тест. Или попробуй позумить текстуру, теоретически тоже должен перелопачивать

anonymous
()
Ответ на: комментарий от jtootf

Так

void SmlPixelSet(SmlIndex index, SmlColour colour, SmlPoint point)
{
    memcpy(warehouse.elem[index].data.img.image->data +
           point.y * warehouse.elem[index].data.img.image->bytes_per_line +
           point.x * sizeof(SmlColour),
           &colour, sizeof(SmlColour));
}

И так:

void SmlMemoryFill(char * start, int32_t count, SmlColour colour)
{
    SML_UNUSED(start);
    SML_UNUSED(count);
    SML_UNUSED(colour);

    asm volatile(
        "cld\n\t"
        "rep\n\t"
        "stosl"
        : /* no output registers */
        : "c" (count), "a" (colour), "D" (start));
}

sambist ★★
() автор топика
Ответ на: комментарий от sambist

замечания не по делу, а по asm.

во-первых, добавь :«memory» — volatile недостаточно.

во-вторых, чем вообще мотивировано использование stos? непереносимо, и один из самых медленных способов писать в память (если, конечно, у тебя не 386).

anonymous
()
Ответ на: комментарий от sambist

а посоны, зачем все пишут sizeof(x), хотя скобки нужны только в случае, если x — тип, а в любом другом случае можно писать просто sizeof x

anonymous
()
Ответ на: комментарий от sambist

в ~50 раз быстрее простого присваивания

Что-то тут не то.

Попробуй простой memset вместо rep stosl

Deleted
()
Ответ на: комментарий от sambist

Функция что выше в ~50 раз быстрее простого присваивания в цикле и memcpy.

Задача какая? Сменить алгоритм на более эффективный не вариант?

devl547 ★★★★★
()
Ответ на: комментарий от devl547

Вы не поняли. Алгоритм тут не причем. Вот надо строку забить одним цветом[32bit] в памяти. Цикл и memcpy посасывают, rep дает выигрыш по скорости. Причем тут алгоритм?

sambist ★★
() автор топика
Ответ на: комментарий от devl547

Но не в 50 же раз.

Проверьте у себя. У меня эта разница была, ЕМНИП, 52 раза.

sambist ★★
() автор топика
Ответ на: комментарий от sambist

А. Извиняюсь, невнимательно посмотрел.

Но в любом случае что-то не то. Вот две функции заполнения:

void
memset1(void *d, uint32_t p, size_t n)
{
        size_t i;
        uint32_t *ptr = (uint32_t *)d;

        for (i=0; i<n; i++) {
                ptr[i] = p;
        }
}


void
memset2(void *d, uint32_t p, size_t n)
{
        asm volatile (
                "cld\n\t"
                "rep stosl"
                : "+D" (d), "+c" (n)
                : "a" (p)
                : "memory");
}

Они у меня выполняются за практически одинаковое время. Вариант с rep stosl медленнее (тест заполняет несколько раз кусок памяти)

$ time ./memset1 

real	0m2.521s
user	0m2.512s
sys	0m0.008s
$ time ./memset2

real	0m2.623s
user	0m2.616s
sys	0m0.004s
Deleted
()
Ответ на: комментарий от devl547

Анролл и векторизация?

Да там же почти гарантированно ничего не выиграешь?

Ну и профайлер ;)

Да лень, пусть ТС смотрит

Кстати, я похоже понял откуда у него получились такие дикие цифры

    asm volatile(
        "cld\n\t"
        "rep\n\t"
        "stosl"
        : /* no output registers */
        : "c" (count), "a" (colour), "D" (start));

Здесь нет списка сохраняемых регистров. С оптимизацией выше -O1 у меня вообще все перекосило.

На sse делают (делали) более быстрые заливки памяти, но это все какая-то суета, ТСу скорее всего такое не нужно

Deleted
()
Ответ на: комментарий от sambist

Здесь они и не нужны.

У тебя после rep stos изменится edi и ecx. Вот у меня в тесте с оптимизацией -O2 и -O3 gcc начал инлайнить функцию заполнения. Она запускалась внутри цикла, вместо всех итераций отрабатывала только одна.

Ну, я не настаиваю, не нужны так не нужны

Deleted
()
Ответ на: комментарий от Deleted

У тебя после rep stos изменится edi и ecx. Вот у меня в тесте с оптимизацией -O2 и -O3 gcc начал инлайнить функцию заполнения. Она запускалась внутри цикла, вместо всех итераций отрабатывала только одна. Ну, я не настаиваю, не нужны так не нужны

Я когда эту гадость писал, руководствовался мануалом на gccшный асм. Конкретно этот кусок практически целиком скопирован оттуда, он, кажись, даже первым в примерах употребления шел. Там же сказано, что список регистров gcc сам допилит.

Она запускалась внутри цикла, вместо всех итераций отрабатывала только одна.

Компилятор увидел, что заполняется одна и та же область и выкинул к чертям цикл из-за оптимизации.

sambist ★★
() автор топика
Ответ на: комментарий от sambist

руководствовался мануалом на gccшный асм

Скорее всего это был старый мануал

Компилятор увидел, что заполняется одна и та же область и выкинул к чертям цикл из-за оптимизации.

Нет. Я же написал нормальную функцию с rep stos, с ней он ничего не выкинул. Забыл написать, там кроме счетчика цикла еще изменялась переменная с данными (скорее всего из-за измененного edi), я насторожился когда вдруг не стал отрабатывать free(), потом посмотрел в objdump.

Ты бы мог уже несколько раз написать простой тест и не парить мозг. Вот на этом я проверял, можешь сам посмотреть: http://pastebin.com/Kqgp5R7D

Deleted
()
Ответ на: комментарий от Deleted

void memset2(void *d, uint32_t p, size_t n) { memset(d, p, n*sizeof(uint32_t)); }

Бред. Сами поймете или расшифровать, почему?

Про регистры спрашивал тут.

sambist ★★
() автор топика
Ответ на: комментарий от sambist

Бред

Да, точно, он

Поясню на всякий случай: memset это очень неплохо оптимизированная функция, если ты делаешь что-то похожее, неплохо сравнивать производительность своей функции с ней

Сами поймете или расшифровать, почему?

Нет, спасибо, не надо

Лучше расшифруй как у тебя получилось так ловко в 50 раз обогнать компилятор. С минимальным тестом, если можно

Deleted
()
Ответ на: комментарий от Deleted

Да, точно, он. Поясню на всякий случай: memset это очень неплохо оптимизированная функция, если ты делаешь что-то похожее, неплохо сравнивать производительность своей функции с ней

Аллё, почитайте уже мануал к memset'у и посмотрите, как вы его используете.

Лучше расшифруй как у тебя получилось так ловко в 50 раз обогнать компилятор. С минимальным тестом, если можно

Минимальный тест не получится, ибо проект большой и ели начать выдирать, то получится тот же проект. Сейчас тесты такие:

# asm func: 10000 cycles took 4.312439 s
# direct assign func: 10000 cycles took 10.083105 s

Использовался ваш код с прямым присваиванием и моя асм вставка:

void SmlMemoryFill(char * start, int32_t count, SmlColour colour)
{
//    SML_UNUSED(start);
//    SML_UNUSED(count);
//    SML_UNUSED(colour);

//    asm volatile(
//        "cld\n\t"
//        "rep\n\t"
//        "stosl"
//        : /* no output registers */
//        : "c" (count), "a" (colour), "D" (start));

    size_t i;
    uint32_t * ptr = (uint32_t *)start;

    for (i=0; i < count; i++)
    {
        ptr[i] = colour;
    }
}

sambist ★★
() автор топика
Последнее исправление: sambist (всего исправлений: 1)
Ответ на: комментарий от sambist

Аллё, почитайте уже мануал к memset'у и посмотрите, как вы его используете.

П-ц

Минимальный тест не получится

П-ц 2

в 50 раз

4.312439 s

10.083105 s

П-ц 3. Хотя скорее всего это какие-то лукавые цифры, но похоже техническая чать дискуссии уже закончилась, аллёкать мне не интересно

Deleted
()
Ответ на: комментарий от Deleted

П-ц

Ты явно тупой. Цитирую ман:

Value to be set. The value is passed as an int, but the function fills the block of memory using the unsigned char conversion of this value.
but the function fills the block of memory using the unsigned char conversion of this value.
unsigned char

А теперь посмотри, с какой функцией ты свой memset сравниваешь.

П-ц 2

vmx не слышал о проектах на >300 кб кода? Это печально.

П-ц 3

Т.е. ты натурально проигнорировал сейчас двукратный прирост скорости продолжая орать, что специализированная ассемблерная инструкция хуже чем присваивание. Ну молодец, парень, чо.

sambist ★★
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.