VISUAL C++ и БИОС-а
13 отговора
614 прегледа
Re: VISUAL C++ и БИОС-а
Много изчерпателен отговор! Поздравления!
Винаги са ми били интересни хора като теб ...
Винаги са ми били интересни хора като теб ...
Re: VISUAL C++ и БИОС-а
какъвто въпроса такъв и отговора...
с мъничката разлика (в моя полза), че въпросът е не особено коректен, но пък отговора е добър.
понякога просто трябва да зададеш правилен въпрос.
[линк]
[линк]
за NT - разбира се, трябва да се мине на Ring0, защото ОС-а няма да ти даде да пишеш по портовете току-така.
за 9X - не зная дали тези портове са 'защитени' - ако са (както портовете на hard-diska)- значи трябва да се мине и там на ring0.
нещо неясно?
с мъничката разлика (в моя полза), че въпросът е не особено коректен, но пък отговора е добър.
понякога просто трябва да зададеш правилен въпрос.
[линк]
[линк]
за NT - разбира се, трябва да се мине на Ring0, защото ОС-а няма да ти даде да пишеш по портовете току-така.
за 9X - не зная дали тези портове са 'защитени' - ако са (както портовете на hard-diska)- значи трябва да се мине и там на ring0.
нещо неясно?
Re: VISUAL C++ и БИОС-а
Е, който си е задал въпроса трябва да си каже, ясно ли му е :)
Сега поне си мисля, че има откъде да тръгне ...
А ти ме извини, ако без да искам съм те обидил нещо. Не ми беше това целта. Просто първият ти отговор ми прозвуча като "ай сиктир, бегай оттука"... А нали трябва да се помага и на по-малко знаещите?


Сега поне си мисля, че има откъде да тръгне ...
А ти ме извини, ако без да искам съм те обидил нещо. Не ми беше това целта. Просто първият ти отговор ми прозвуча като "ай сиктир, бегай оттука"... А нали трябва да се помага и на по-малко знаещите?
Re: VISUAL C++ и БИОС-а
:)
но дали трябва да се помага на мързеливите?
That is the question...
но дали трябва да се помага на мързеливите?
That is the question...
Re: VISUAL C++ и БИОС-а
Това ще го приема като риторичен въпрос :))
И едно предложение - имаш ли нещо против да почистя нашия диалог и да оставя само въпроса и твоя отговор ?
Имам чувството, че с теб се разбрахме, а останалите няма какво да научат от нашия разговор. Всъщност, знам ли ... може и да има ...
Ти решаваш :)
И едно предложение - имаш ли нещо против да почистя нашия диалог и да оставя само въпроса и твоя отговор ?
Имам чувството, че с теб се разбрахме, а останалите няма какво да научат от нашия разговор. Всъщност, знам ли ... може и да има ...
Ти решаваш :)
Re: VISUAL C++ и БИОС-а
Предпочитам да не го изтриваш - всичко е поучително. Освен това, ако някой наистина го мързи, той дори не пита.
А и отговорът (истинският) е такъв, какъвто трябва - не ти дава готово решение, а те кара да прочетеш...
Re: VISUAL C++ и БИОС-а
А сега де (виж по-долу) ?!
Я нека остане...
Току-виж някои въпроси почнат да се формулират правилно :)
А и някои отговори.

Я нека остане...
Току-виж някои въпроси почнат да се формулират правилно :)
А и някои отговори.
Re: VISUAL C++ и БИОС-а
E sega ako ni swetnesh ot kyde da prochetem kak se minawa w ring 0 si pish naprawo!!
nadqwam se che dobre formulirah wyprosa??
nadqwam se che dobre formulirah wyprosa??
Re: VISUAL C++ и БИОС-а
mda. - samo deto tozi nachin s KeI386SetGdtSelector i podobnite funkcii e leko nonportable - niama da trygne na Alpha predpolagam zashtoto tam arhitekturata e druga. ;)
za NT-to obache - pri wsichki polojenia triabwa da se pishe driver - i priwilegia za da se loadne - (obiknoweno samo admin). :)
posle s DeviceIOControl - mojesh da mi dawash zadachi za izpylnenie. :)
za 9X - sushto moje s driver i DeviceIoControl za komunikaciq s ring0, no tam moje da se premine "bezprepiatstweno" :) na ring0 - bez da pishem VXD, zashtoto GDT, IDT, LDT sa free za pisane ot wseki.
eto example-che.
towa neshto prashata komadata 0xEC kym zadadenie controler/hard_disk - toest Identify Drive i wzema info 512 baita - tam e zapisan i serijnia fabrichen nomer na hard diska.
kato gledam sega - wzemam samo 1 i 2-ia kontroler :) - koi da se seti che shte slojat oshte 2 :)) (za 3 i 4 portowete sa 0x1E8 i 0x168)
<pre>
#pragma pack(1)
struct GDT_DESCRIPTOR
{
WORD Limit_0_15;
WORD Base_0_15;
BYTE Base_16_23;
BYTE Type : 4;
BYTE System : 1;
BYTE DPL : 2;
BYTE Present : 1;
BYTE Limit_16_19 : 4;
BYTE Available : 1;
BYTE Reserved : 1;
BYTE D_B : 1;
BYTE Granularity : 1;
BYTE Base_24_31;
};
struct CALLGATE_DESCRIPTOR
{
WORD Offset_0_15;
WORD Selector;
WORD ParamCount : 5;
WORD Unused : 3;
WORD Type : 4;
WORD System : 1;
WORD DPL : 2;
WORD Present : 1;
WORD Offset_16_31;
};
struct GDTR
{
WORD wGDTLimit;
DWORD dwGDTBase;
};
#pragma pack()
static struct GDT_DESCRIPTOR * find_descriptor( WORD* index )
{
struct GDT_DESCRIPTOR *pGDTDescriptor;
struct GDTR gdtr;
WORD wGDTIndex;
_asm Sgdt fword ptr [gdtr]
// Skip the null descriptor
pGDTDescriptor = (struct GDT_DESCRIPTOR *)(gdtr.dwGDTBase + 8);
// Search for a free GDT descriptor
for (wGDTIndex = 1; wGDTIndex < (gdtr.wGDTLimit / 8); wGDTIndex++, pGDTDescriptor++)
{
if (pGDTDescriptor->Type == 0 &&
pGDTDescriptor->System == 0 &&
pGDTDescriptor->DPL == 0 &&
pGDTDescriptor->Present == 0)
{
// ura! ura!
*index = wGDTIndex;
return pGDTDescriptor;
}
}
*index = 0;
return NULL;
}
/*
eax -> al = controller/ ah = drive
edi -> 512 bytes buffer
return 1 - ok.
-1 timeout - wait for drie ready
-2 error - wait for data
-3 timeout - wait for data
*/
static __declspec(naked) void ring0_stuff( void )
{
_asm
{
cli
mov ecx, 20*TIMEOUT // timeout
mov dx, 0x1f7 // controller 0
test al, 1 // controller?
jz @wait_for_ready
mov dx, 0x177 // controller 1
@wait_for_ready:
in al, dx
test al, 0x40
jnz @drive_ready
loop @wait_for_ready
// timeout
sti
mov eax, -1
retf
@drive_ready:
dec edx // 0x1f6/0x176
mov al, 0xa0 // drive 0
test ah, 1 // drive?
jz @select_drive
mov al, 0xb0 // drive 1
@select_drive:
out dx, al // select drive
inc edx // 0x1f7/0x177 base address + 7
mov al, 0xec // command
out dx, al //
mov ecx, TIMEOUT // timeout
@wait_for_data:
in al, dx
test al, 1
jnz @error // error
and al, 0x48
cmp al, 0x48
jz @get_info // incoming data ready!
loop @wait_for_data
jmp @timeout // timeout
@get_info:
mov ecx, 256 // 256 words
sub edx, 7 // base address 1f0/170
rep insw edi, dx //
sti
mov eax, 1 //ok.
retf
@error:
sti
mov eax, -2
retf
@timeout:
sti
mov eax, -3
retf
}
}
int try_drive_9x( int controller, int drive, unsigned char output[512] )
{
WORD wGDTIndex;
struct CALLGATE_DESCRIPTOR *pCallgate;
WORD CallgateAddr[3];
DWORD result;
pCallgate = (struct CALLGATE_DESCRIPTOR *)find_descriptor( &wGDTIndex );
if( !pCallgate ) return -1;
// selector 0x28 is fine :)
pCallgate->Offset_0_15 = LOWORD(ring0_stuff);
pCallgate->Selector = 0x28;
pCallgate->ParamCount = 0;
pCallgate->Unused = 0;
pCallgate->Type = 0xc;
pCallgate->System = 0;
pCallgate->DPL = 3;
pCallgate->Present = 1;
pCallgate->Offset_16_31 = HIWORD(ring0_stuff);
// Prepare the far call parameters
CallgateAddr[0] = 0x0;
CallgateAddr[1] = 0x0;
CallgateAddr[2] = (wGDTIndex << 3) | 3;
// jump to ring 0
_asm mov al, byte ptr [controller]
_asm mov ah, byte ptr [drive]
_asm mov edi, output
_asm call fword ptr [CallgateAddr]
_asm mov result, eax
// free the GDT descriptor
//memset(pCallgate, 0, 8);
*((ULONG*)pCallgate) = 0, *(((ULONG*)pCallgate)+1) = 0;
return result;
}
</pre>
za NT-to obache - pri wsichki polojenia triabwa da se pishe driver - i priwilegia za da se loadne - (obiknoweno samo admin). :)
posle s DeviceIOControl - mojesh da mi dawash zadachi za izpylnenie. :)
za 9X - sushto moje s driver i DeviceIoControl za komunikaciq s ring0, no tam moje da se premine "bezprepiatstweno" :) na ring0 - bez da pishem VXD, zashtoto GDT, IDT, LDT sa free za pisane ot wseki.
eto example-che.
towa neshto prashata komadata 0xEC kym zadadenie controler/hard_disk - toest Identify Drive i wzema info 512 baita - tam e zapisan i serijnia fabrichen nomer na hard diska.
kato gledam sega - wzemam samo 1 i 2-ia kontroler :) - koi da se seti che shte slojat oshte 2 :)) (za 3 i 4 portowete sa 0x1E8 i 0x168)
<pre>
#pragma pack(1)
struct GDT_DESCRIPTOR
{
WORD Limit_0_15;
WORD Base_0_15;
BYTE Base_16_23;
BYTE Type : 4;
BYTE System : 1;
BYTE DPL : 2;
BYTE Present : 1;
BYTE Limit_16_19 : 4;
BYTE Available : 1;
BYTE Reserved : 1;
BYTE D_B : 1;
BYTE Granularity : 1;
BYTE Base_24_31;
};
struct CALLGATE_DESCRIPTOR
{
WORD Offset_0_15;
WORD Selector;
WORD ParamCount : 5;
WORD Unused : 3;
WORD Type : 4;
WORD System : 1;
WORD DPL : 2;
WORD Present : 1;
WORD Offset_16_31;
};
struct GDTR
{
WORD wGDTLimit;
DWORD dwGDTBase;
};
#pragma pack()
static struct GDT_DESCRIPTOR * find_descriptor( WORD* index )
{
struct GDT_DESCRIPTOR *pGDTDescriptor;
struct GDTR gdtr;
WORD wGDTIndex;
_asm Sgdt fword ptr [gdtr]
// Skip the null descriptor
pGDTDescriptor = (struct GDT_DESCRIPTOR *)(gdtr.dwGDTBase + 8);
// Search for a free GDT descriptor
for (wGDTIndex = 1; wGDTIndex < (gdtr.wGDTLimit / 8); wGDTIndex++, pGDTDescriptor++)
{
if (pGDTDescriptor->Type == 0 &&
pGDTDescriptor->System == 0 &&
pGDTDescriptor->DPL == 0 &&
pGDTDescriptor->Present == 0)
{
// ura! ura!
*index = wGDTIndex;
return pGDTDescriptor;
}
}
*index = 0;
return NULL;
}
/*
eax -> al = controller/ ah = drive
edi -> 512 bytes buffer
return 1 - ok.
-1 timeout - wait for drie ready
-2 error - wait for data
-3 timeout - wait for data
*/
static __declspec(naked) void ring0_stuff( void )
{
_asm
{
cli
mov ecx, 20*TIMEOUT // timeout
mov dx, 0x1f7 // controller 0
test al, 1 // controller?
jz @wait_for_ready
mov dx, 0x177 // controller 1
@wait_for_ready:
in al, dx
test al, 0x40
jnz @drive_ready
loop @wait_for_ready
// timeout
sti
mov eax, -1
retf
@drive_ready:
dec edx // 0x1f6/0x176
mov al, 0xa0 // drive 0
test ah, 1 // drive?
jz @select_drive
mov al, 0xb0 // drive 1
@select_drive:
out dx, al // select drive
inc edx // 0x1f7/0x177 base address + 7
mov al, 0xec // command
out dx, al //
mov ecx, TIMEOUT // timeout
@wait_for_data:
in al, dx
test al, 1
jnz @error // error
and al, 0x48
cmp al, 0x48
jz @get_info // incoming data ready!
loop @wait_for_data
jmp @timeout // timeout
@get_info:
mov ecx, 256 // 256 words
sub edx, 7 // base address 1f0/170
rep insw edi, dx //
sti
mov eax, 1 //ok.
retf
@error:
sti
mov eax, -2
retf
@timeout:
sti
mov eax, -3
retf
}
}
int try_drive_9x( int controller, int drive, unsigned char output[512] )
{
WORD wGDTIndex;
struct CALLGATE_DESCRIPTOR *pCallgate;
WORD CallgateAddr[3];
DWORD result;
pCallgate = (struct CALLGATE_DESCRIPTOR *)find_descriptor( &wGDTIndex );
if( !pCallgate ) return -1;
// selector 0x28 is fine :)
pCallgate->Offset_0_15 = LOWORD(ring0_stuff);
pCallgate->Selector = 0x28;
pCallgate->ParamCount = 0;
pCallgate->Unused = 0;
pCallgate->Type = 0xc;
pCallgate->System = 0;
pCallgate->DPL = 3;
pCallgate->Present = 1;
pCallgate->Offset_16_31 = HIWORD(ring0_stuff);
// Prepare the far call parameters
CallgateAddr[0] = 0x0;
CallgateAddr[1] = 0x0;
CallgateAddr[2] = (wGDTIndex << 3) | 3;
// jump to ring 0
_asm mov al, byte ptr [controller]
_asm mov ah, byte ptr [drive]
_asm mov edi, output
_asm call fword ptr [CallgateAddr]
_asm mov result, eax
// free the GDT descriptor
//memset(pCallgate, 0, 8);
*((ULONG*)pCallgate) = 0, *(((ULONG*)pCallgate)+1) = 0;
return result;
}
</pre>