Unreal mode

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

  1. Neuron

    Neuron New Member

    Публикаций:
    0
    Регистрация:
    17 сен 2006
    Сообщения:
    10
    Всем привет. Вот накатал небольшую прогу, которая тестит всю имеющуюся память, для доступа к которой используется unreal mode. Когда отлаживал программу под vmware, все работало. В реальном ДОСе не пашет. В чем тут может быть дело?
    Код (Text):
    1. ?include "lib/write.h--"
    2. ?include "lib/keycodes.h--"
    3.  
    4. byte GDT[16]={0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFF,0xFF,0x00,0x00,0x00,0x92,0xCF,0xF0};
    5. byte GDT_Offs[6]={0x00,0x00,0x00,0x00,0x00,0x00};
    6.  
    7. void main()
    8. {
    9.     struct _MEMBLOCKINFO_{
    10.         dword BaseAddrLow;
    11.         dword BaseAddrHi;
    12.         dword LengthLow;
    13.         dword LengthHi;
    14.         dword Type;
    15.     }mbi;
    16.     dword a, b, memsize, mem_block_start, mem_block_size, offset, errors, total_bytes_checked;
    17.     byte mem_cell;
    18.     memsize = 0;
    19.     errors = 0;
    20.     total_bytes_checked = 0;
    21.  //-------Go to protected mode--------------------
    22.  WriteStr("Go to protected mode...\n");
    23.  GDT_Offs=16;
    24.  EAX=0;
    25.  AX=DS;
    26.  EAX<<=4;
    27.  EAX+=#GDT;
    28.  DSDWORD[#GDT_Offs+2]=EAX;
    29.  $LGDT GDT_Offs;
    30.  DX=8;
    31.  $PUSH DS
    32.  $CLI
    33.  $MOV  EAX,CR0
    34.  EAX|=1;
    35.  $MOV CR0,EAX
    36.  GOTO PROTECTED_MODE_ON;
    37. PROTECTED_MODE_ON:
    38.             GS=DX;
    39.             FS=DX;
    40.             ES=DX;
    41.             DS=DX;
    42.             AL&=0xFE;
    43.             $MOV CR0,EAX
    44.             GOTO REAL_MODE_ON;
    45. REAL_MODE_ON:
    46.             $STI
    47.             $POP DS
    48.             AL=0;
    49. WriteStr("Now we are in flat mode...\n");    
    50.  //-------Start memory test-----------------------
    51.  WriteStr("Checking memory above 1Mb...\n");
    52.  $PUSH CS
    53.  $POP ES
    54.  DI = #mbi;
    55.  $XOR ebx,ebx
    56.  do{
    57.     $MOV edx,534D4150h
    58.     $MOV ecx, sizeof(mbi)
    59.     $MOV eax,0000E820h
    60.     $INT 15h
    61.     a = EAX;
    62.     if(a!=0x534D4150){
    63.         WriteStr("Unexpected error!\n");
    64.         WriteStr("Press any key to continue...\n");
    65.         BIOSREADKEY();
    66.         return;
    67.     }
    68.     $PUSH EBX
    69.     if(mbi.Type==1){               
    70.             mem_block_start = mbi.BaseAddrLow;
    71.             mem_block_size = mbi.LengthLow;
    72.             offset = 0;
    73.             if(mem_block_start>0xFFFFF){
    74.                 WriteStr("Checking memory block...\n");
    75.                 WriteStr("Memory block base address: ");
    76.                 WriteDWordHex(mem_block_start);
    77.                 WriteStr("\nMemory block size: ");
    78.                 WriteDWord(mem_block_size);
    79.                 WriteStr(" bytes\n");
    80.                     do{
    81.                         FSBYTE[mem_block_start+offset] = 0xAA;
    82.                         mem_cell = FSBYTE[mem_block_start+offset];
    83.                         if(mem_cell != 0xAA){
    84.                             errors++;
    85.                             WriteStr("\nWritten: 0xAA\n");
    86.                             WriteStr("Read: ");
    87.                             WriteByteHex(mem_cell);
    88.                         }else{
    89.                             FSBYTE[mem_block_start+offset] = 0x55;
    90.                             mem_cell = FSBYTE[mem_block_start+offset];
    91.                             if(mem_cell != 0x55){
    92.                                 errors++;
    93.                                 WriteStr("\nWritten: 0x55\n");
    94.                                 WriteStr("Read: ");
    95.                                 WriteByteHex(mem_cell);
    96.                             }                          
    97.                         }
    98.                         offset++;
    99.                         total_bytes_checked++;
    100.                     }while(offset<mem_block_size);
    101.                 WriteStr("Memory block checked...\n");
    102.             }
    103.     }
    104.     $POP EBX
    105.     b = EBX;
    106.  }while (b!=0);
    107.  WriteStr("----------------------------\n");
    108.  WriteStr("Total bytes checked: ");
    109.  WriteDWord(total_bytes_checked);
    110.  WriteStr("\nErrors: ");
    111.  WriteDWord(errors);
    112.  WriteStr("\nPress any key to continue...\n");
    113.  BIOSREADKEY();
    114. }
    Компилятор sphinx c-- 0.238. Скомпилированная прога в аттаче.
     
  2. explosion

    explosion Member

    Публикаций:
    0
    Регистрация:
    15 янв 2007
    Сообщения:
    34
    в проге вроде все норм

    попробуй не использовать int 15h
    и какой у тебя проц? случайно не от фирмы AMD? :) насколько я помню молодость, некоторые из них unreal режимов ох как не любят
     
  3. Neuron

    Neuron New Member

    Публикаций:
    0
    Регистрация:
    17 сен 2006
    Сообщения:
    10
    Пробовал на разных процах. Не работает. Как без int 15 определить объем ОЗУ, если ее к примеру 512Mb?
     
  4. Neuron

    Neuron New Member

    Публикаций:
    0
    Регистрация:
    17 сен 2006
    Сообщения:
    10
    Все нашел глюк, GDT неправильно написал. И объем ОЗУ до 4Gb можно определить функцией E801h int 15h. Короче, получилось так, может кому сгодится:
    Код (Text):
    1. ?include "lib/write.h--"
    2. ?include "lib/keycodes.h--"
    3.  
    4. byte GDT[16]={0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0xFF,0xFF,0x00,0x00,0xCF,0x92,0x00,0x00};
    5. byte GDT_Offs[6]={0x00,0x00,0x00,0x00,0x00,0x00};
    6.  
    7. void main(){
    8.     dword mem_size1, mem_size2, total_mem, offset, errors, total_bytes_checked;
    9.     byte mem_cell;
    10.     $MOV eax,0000E801h
    11.     $INT 15h
    12.     mem_size1 = ECX*1024;
    13.     mem_size2 = EDX*65536;
    14.     total_mem = mem_size1 + mem_size2;
    15.     WriteStr("Available memory: ");
    16.     WriteDWord(total_mem);
    17.     WriteStr(" bytes\n");
    18.  
    19.     //-------Go to protected mode--------------------
    20.     WriteStr("Go to protected mode...\n");
    21.     GDT_Offs=16;
    22.     EAX=0;
    23.     AX=DS;
    24.     EAX<<=4;
    25.     EAX+=#GDT;
    26.     DSDWORD[#GDT_Offs+2]=EAX;
    27.     $LGDT GDT_Offs;
    28.     DX=8;
    29.     $PUSH DS
    30.     $CLI
    31.     $MOV  EAX,CR0
    32.     EAX|=1;
    33.     $MOV CR0,EAX
    34.     GOTO PROTECTED_MODE_ON;
    35.     PROTECTED_MODE_ON:
    36.             GS=DX;
    37.             FS=DX;
    38.             ES=DX;
    39.             DS=DX;
    40.             AL&=0xFE;
    41.             $MOV CR0,EAX
    42.             GOTO REAL_MODE_ON;
    43.     REAL_MODE_ON:
    44.             $STI
    45.             $POP DS
    46.             AL=0;
    47.     WriteStr("Now we are in flat mode...\n");
    48.             $IN  al, 92h
    49.             $OR  al, 2
    50.             $OUT 92h, al     
    51.     //-------Start memory test-----------------------
    52.     WriteStr("Checking memory above 1Mb...\n");
    53.     offset = 0x100000;
    54.     errors = 0;
    55.     total_bytes_checked = 0;
    56.     do{
    57.         FSBYTE[offset] = 0xAA;
    58.         mem_cell = FSBYTE[offset];
    59.         if(mem_cell != 0xAA){
    60.             errors++;
    61.             WriteStr("\nWritten: 0xAA\n");
    62.             WriteStr("Read: ");
    63.             WriteByteHex(mem_cell);
    64.         }else{
    65.             FSBYTE[offset] = 0x55;
    66.             mem_cell = FSBYTE[offset];
    67.                 if(mem_cell != 0x55){
    68.                     errors++;
    69.                     WriteStr("\nWritten: 0x55\n");
    70.                     WriteStr("Read: ");
    71.                     WriteByteHex(mem_cell);
    72.                 }                          
    73.         }
    74.         offset++;
    75.         total_bytes_checked++;
    76.         }while(offset<total_mem);
    77.         WriteStr("----------------------------\n");
    78.         WriteStr("Total bytes checked: ");
    79.         WriteDWord(total_bytes_checked);
    80.         WriteStr("\nErrors: ");
    81.         WriteDWord(errors);
    82.         WriteStr("\nPress any key to continue...\n");
    83.         BIOSREADKEY();
    84. }
     
  5. explosion

    explosion Member

    Публикаций:
    0
    Регистрация:
    15 янв 2007
    Сообщения:
    34
    Объем ОЗУ определяется так:

    1 counter = 0x100000
    2 записываем байт в адрес [counter]
    3 читаем байт из адреса [counter]
    4 это тот байт что мы записали?
    5 да - память существует, нет - память не существует, останавливаемся (прыгаем на строку 8)
    6 counter = counter + 1 (чтоб побыстрее можно прыгать через мегабайт +0x100000)
    7 прыгаем на строку 2, продолжаем цикл
    8 count - количество памяти на компе

    Так объем ОЗУ определяет BIOS и операционные системы

    А чтоб протестить память желательно пробежаться по ней 2-3 раза и записывать разные байты