проблемы с многомерными массивами на асм.

Тема в разделе "WASM.BEGINNERS", создана пользователем witcher, 19 сен 2007.

  1. witcher

    witcher New Member

    Публикаций:
    0
    Регистрация:
    13 сен 2006
    Сообщения:
    73
    Добрый день.
    Такая проблема.
    Надо в С++ используя ассамблерные вставки написать прогу по суммированию эллементов в многомерном массиве.

    Возникла проблема с адрессацией на много мерный массив.
    Как это правильно делается?
    Вот код того что я навоял.

    Код (Text):
    1. int main(int argc, char* argv[])
    2. {
    3.     cout<<"\n"<<sizeof(short int)<<"\n";
    4.     int mas[5][5];
    5.     short int otr[5];
    6.     short int a;
    7.     short int i=0,j=0;
    8.     for(i=0;i<5;i++)
    9.     {
    10.         for(j=0; j<5; j++)
    11.         {
    12.             cout<<"enter mas["<<i<<"]["<<j<<"]->";
    13.             cin>> mas[i][j];
    14.         }
    15.     }
    16.     __asm
    17.     {  
    18.         mov SI,0              
    19.         mov AX,0            
    20.         mov CX,5  
    21.         mov bx, 0
    22.         label_i:
    23.         mov  dx, cx
    24.             mov di,0;
    25.             mov  cx,5
    26.             mov     j, 0       
    27.             label_j:
    28.                 xor   ax, ax
    29.                 mov   al, mas[bx][di]
    30.                 add a,ax
    31.                 inc di
    32.             loop    label_j
    33.             mov     cx, dx
    34.             inc bx
    35.         loop    label_i
    36.                    
    37.     }
    38.     cout<<"a=="<<a;
    39.     return 0;
    40. }
    при компиляции в VC6.0 получаю следующую ошиби.

    error C2402: 'bx' : register must be index in 'second operand'
    error C2432: illegal reference to 16-bit data in 'second operand'
     
  2. slow

    slow New Member

    Публикаций:
    0
    Регистрация:
    27 дек 2004
    Сообщения:
    615
    времена DOS прошли, для индексации используйте 32-битные регистры EBX,ECX,EDX и пр.
     
  3. witcher

    witcher New Member

    Публикаций:
    0
    Регистрация:
    13 сен 2006
    Сообщения:
    73
    А пример можно этого куска?
     
  4. slow

    slow New Member

    Публикаций:
    0
    Регистрация:
    27 дек 2004
    Сообщения:
    615
    попробуй тупо заменить bx->ebx,cx->ecx и т.п.
     
  5. witcher

    witcher New Member

    Публикаций:
    0
    Регистрация:
    13 сен 2006
    Сообщения:
    73
    Не помогло.
     
  6. slow

    slow New Member

    Публикаций:
    0
    Регистрация:
    27 дек 2004
    Сообщения:
    615
    Значит делаешь че-то не то.. VC6 у меня к сож нет, проверить не на чем
     
  7. l_inc

    l_inc New Member

    Публикаций:
    0
    Регистрация:
    29 сен 2005
    Сообщения:
    2.566
    slow
    Ясно дело не то. Массив-то в стэке объявлен.
    witcher
    Массив нужно объявлять глобально. Тогда его смещение будет известно еще на стадии компиляции.
     
  8. Mika0x65

    Mika0x65 New Member

    Публикаций:
    0
    Регистрация:
    30 июл 2005
    Сообщения:
    1.384
    Если я правильно понял автора, то ему требуется примерно следующее:
    Код (Text):
    1. #include <stdio.h>
    2.  
    3. #define M 5
    4. #define N 5
    5.  
    6. int main(int argc, char **argv)
    7. {
    8.     int summ = 0, i, j, arr[M][N];
    9.  
    10.     for (i = 0; i < M; i++)
    11.         for (j = 0; j < N; j++)
    12.             arr[i][j] = i;
    13.  
    14.     __asm
    15.     {
    16.         xor edx, edx
    17.         mov i, 0
    18.     l00p1:
    19.         cmp i, M
    20.         jge exit1
    21.         mov j,0
    22.     l00p2:
    23.         cmp j, N
    24.         jge exit2
    25.         lea ebx, dword ptr [arr]
    26.         mov eax, i
    27.         imul eax, N
    28.         add eax, j
    29.         add edx, [ebx + eax * 4]
    30.         inc j
    31.         jmp l00p2
    32.     exit2:
    33.         inc i
    34.         jmp l00p1
    35.     exit1:
    36.         mov dword ptr [summ], edx
    37.     }
    38.  
    39.     printf("%d\n", summ);
    40.  
    41.     return 0;
    42. }
     
  9. l_inc

    l_inc New Member

    Публикаций:
    0
    Регистрация:
    29 сен 2005
    Сообщения:
    2.566
    Mika0x65
    Вообще автор должен был бы сам дойти до того, что mas[ebx][edi] не даст элемент массива с координатами ebx, edi. А основным камнем преткновения были ошибки компиляции.
    И... если не возражаете, пара замечаний от чайника:
    Макроопределения для M и N Вы сделали, а условие выхода из вложенного цикла все равно cmp j, 5. И еще... summ объявлен, как int, а Вы по его адресу целых четыре байта пишете!
     
  10. 10110111

    10110111 New Member

    Публикаций:
    0
    Регистрация:
    13 июл 2006
    Сообщения:
    319
    Адрес:
    Санкт-Петербург
    AFAIK, sizeof(int)=4...
     
  11. l_inc

    l_inc New Member

    Публикаций:
    0
    Регистрация:
    29 сен 2005
    Сообщения:
    2.566
    10110111
    Блин. Внатуре. В принципе в разных компиляторах по разному, но я всегда думал, что в VC6 именно два. Спасибо.
    Ну собсно какой спрос с чайника... :)
     
  12. Mika0x65

    Mika0x65 New Member

    Публикаций:
    0
    Регистрация:
    30 июл 2005
    Сообщения:
    1.384
    l_inc
    Пардон, исправил. Просто я константы потом уже добавил, ну и забыл все поменять, естественно :).
     
  13. Mikl_

    Mikl_ New Member

    Публикаций:
    0
    Регистрация:
    14 ноя 2006
    Сообщения:
    907
    witcher
    Код (Text):
    1. int mas[M][N];
    2.       xor eax,eax; место под сумму eax и edx
    3.       cdq; очищаем edx
    4.       mov ecx,M*N; общее количество элементов
    5. a1: add eax,mas[ecx*4-4]
    6.      adc edx,0; если перенос -- заполняем edx
    7.      loop a1
    Массив любого порядка на самом деле в памяти представлен как одномерный.
    И всё!:))
     
  14. l_inc

    l_inc New Member

    Публикаций:
    0
    Регистрация:
    29 сен 2005
    Сообщения:
    2.566
    Mikl__
    Да ну! Даже такой?
    Код (Text):
    1. matrPtr = (double**) new double[maxH];
    2. for (par1=0; par1<maxH; par1++)
    3.     matrPtr[par1] = new double[maxW];
     
  15. wsd

    wsd New Member

    Публикаций:
    0
    Регистрация:
    8 авг 2007
    Сообщения:
    2.824
    l_inc
    Mikl__ правильно сказал.
    Так во всех чтивах пишут!
    А указатели на указатели это отдельная тема:)
     
  16. Mikl_

    Mikl_ New Member

    Публикаций:
    0
    Регистрация:
    14 ноя 2006
    Сообщения:
    907
    l_inc
    Честно скажу, с массивами, которые содержат указатели на указатели других массивов не сталкивался. Но вот для задач по поиску минимума/максимума, либо для нахождения суммы/произведения всех элементов массива, либо по заполнению массива каким-нибудь значением -- во вложенных циклах обращаться к каждому элементу массива, через сложное вычисление его индекса, как это делает топикстартер -- IMHO проще обработать весь массив как одномерный, результат будет одним и тем же!