Системное программное обеспечение персональных ЭВМ


Пример 8



Пример 8

/*== ПРИМЕР 10.5 ==*/ /*============= Чтение корневого оглавления ==============*/ #include <alloc.h> #include <dos.h> #define byte unsigned char #define word unsigned int #define dword unsigned long /* Структура, описывающая элемент оглавления */ struct Dir_Item { char fname[11]; /* имя файла */ byte attr; /* атрибут */ byte reserved[10]; word time; /* время */ word date; /* дата */ word cl; /* номер 1-го кластера */ dword size; /* размер файла */ } *dir; /* Структура корневой записи */ struct RootRec { byte jmp[3], ident[8]; word SectSize; byte ClustSize; word ResSect; byte FatCnt; word RootSize, TotSecs; byte Media; word FatSize, TrkSecs, HeadCnt, HidnSecL, HidnSecH; dword LongTotSecs; byte Drive; byte reserved1; byte DOS4_flag; dword VolNum; char VolLabel[11], FatForm[8]; } *rt; /* Структура параметров для INT 25 */ struct{ dword first_sect; word count; byte *ptr; } parm; union REGS rr; struct SREGS sr; char *attrs[]={"ТОЛЬКО_ЧТЕНИЕ","СКРЫТЫЙ_ФАЙЛ", "СИСТЕМНЫЙ_ФАЙЛ","МЕТКА_ТОМА","ПОДКАТАЛОГ"}; main() { byte *buff; /* адрес буфера в ОП */ byte sys, /* признак диска > 32 Мбайт */ drive; /* идентификатор диска */ int i, j, k, m; byte ms; /* маска атрибутов */ word RootSect, /* номер сектора */ RootCnt, /* число элементов */ RootSects; /* число секторов */

ASK1: printf("\nУкажите идентификатор диска (A,B...) >"); drive=getche(); if (drive>'b') { ASK2:printf("\nОбьем лог. диска больше 32 Мбайт? (y/n) >"); switch(sys=getche()) { case 'y' : sys=1; break; case 'n' : sys=0; break; default: goto ASK2; } } else sys=0; buff=(byte *)malloc(512); /* Чтение boot-сектора */ rr.h.al=drive-'a'; /* Диск */ if (!sys) { rr.x.cx=1; rr.x.dx=0; sr.ds=FP_SEG(buff); rr.x.bx=FP_OFF(buff); } else { parm.first_sect=0; parm.count=1; parm.ptr=buff; sr.ds=FP_SEG(&parm); rr.x.bx=FP_OFF(&parm); rr.x.cx=0xffff; } int86x(0x25,&rr,&rr,&sr); readerror(); rt=(struct RootRec *)buff; /* Параметры корневого каталога */ RootCnt=rt->RootSize; RootSect=rt->ResSect+rt->FatSize*rt->FatCnt; RootSects=rt->RootSize/16; /* Выделение памяти под корневой каталог */ buff=(byte *)realloc(buff,RootSects*512); if (buff==NULL) { printf("Нехватка памяти\n"); exit(); } dir=(struct Dir_Item *)buff; clrscr(); /* Чтение каталога */ rr.h.al=drive-'a'; if (!sys) { /* маленький диск */ rr.x.cx=RootSects; rr.x.dx=RootSect; sr.ds=FP_SEG(buff); rr.x.bx=FP_OFF(buff); } else { /* большой диск */ parm.first_sect=RootSect; parm.count=RootSects; parm.ptr=buff; sr.ds=FP_SEG(&parm); rr.x.bx=FP_OFF(&parm); rr.x.cx=0xffff; } int86x(0x25,&rr,&rr,&sr); readerror(); /* Распечатка оглавления */ for (j=0, k=0; j<RootCnt; j++) { printf("#%3d ",j); if (dir[j].fname[0]!=0) { /* Если элемент оглавления непустой */ for (i=0; i<11; i++) { if (i==8) printf("."); if ((i==0)&&(dir[j].fname[i]==0xe5)) printf("?"); else printf("%c",dir[j].fname[i]); } if (dir[j].fname[0]==0xE5) printf(" ******УДАЛЕН****** "); printf(" атрибут=%02x (",dir[j].attr); if (!(dir[j].attr&0x01f)) printf("ЧТЕНИЕ/ЗАПИСЬ"); else for(ms=1, m=0; m<5; m++,ms<<=1) if (dir[j].attr&ms) printf("%s ",attrs[m]); printf(")\n "); printf(" время=%02d/%02d/%02d", (dir[j].time>>11)&0x001f,(dir[j].time>>5)&0x003f, (dir[j].time&0x001f)*2); printf(" дата=%02d/%02d/%04d", ((dir[j].date>>9)&0x007f)+1980, (dir[j].date>>5)&0x000f, dir[j].date&0x001f); printf(" нач.кластер=%03x",dir[j].cl); printf(" размер=%lu\n",dir[j].size); } else printf(" свободен\n"); if (++k>7) { k=0; if (getch()==27) goto EOJ; } } EOJ:free(buff); } /* Проверка ошибок чтения */ readerror() { if (rr.x.cflag) { printf("\nОшибка чтения: %x. ",rr.h.ah); printf("Нажмите любую клавишу...\n\7"); getch(); exit(); } }




- Начало -  - Назад -  - Вперед -