Радио-86РК/Радио 07-90/Обработка файлов на компьютерах IBM/Листинг 2
Данный материал защищён авторскими правами!
Использование материала заявлено как добросовестное, исключительно для образовательных некоммерческих целей. Автор: Ю. ЛЕСНЫХ Источник: http://retro.h1.ru/RK86/RK_PC/RK86-PC.C |
#include <stdlib.h> #include <fcntl.h> #include <sys/stat.h> /* for mode definitions */ #include <io.h> #include <stdio.h> #include <string.h> #define TRUE 0 /* Boolean constants */ #define FALSE -1 int l,I,J,RD, R,Ind, msim[17], Size = 512, Byt = 1, Final; unsigned int ErrCnt,LineCnt,LineNr; unsigned char Buf[512], TFmp[100000]; char Rname[14], KeyBas1[4] = {0xd3,0xd3,0xd3,0xd3}, KeyBas2[4] = {0xd3,0xd3,0xd3,0x00}, KeyEd[4] = {0xe6,0xe6,0xe6,0xe6}, Sname[14], Tname[14], Ename[14], CrLf[] = "\r\n", TransRus[] = "ЮАБЦДЕФГХИЙКЛМНОПЯРСТУЖВЬЫЗШЭЩЧ", Hch[2], Hin[5], strk[5]; char Key[4], Line[72], adrs[4]; FILE *FilIn, *FilOut, *FLst, *FErr; void endgo(void); int simhex(char[]); main() { int k, kl, P1,Ch,Klen; Final = FALSE; fprintf(stdout,"\nПрограмма преобразования файлов RK86. v1.0\n"); while (Final) { strcpy(Line,"Нет имени "); Size = 512; fprintf(stdout,"\nКакой файл обработать ?"); gets(Rname); if (*Rname == 0) { Final = TRUE; continue; } R = open(Rname, O_RDONLY | O_BINARY); if (R < 0) { fprintf(stderr,"Ошибка открытия файла ->%s\n",Rname); continue; } Ind = 0; P1 = 0; clestr(Tname); clestr(Ename); Klen = strpos(Rname,'.',14); strncpy(Tname,Rname,Klen); strncpy(Ename,Rname,Klen); RD = read(R,Buf,Size); if ((Buf[0] == 0xe6) && (Buf[1] != 0xe6)) { P1 = 1; } else { if ((Buf[0] == 0xe6) && (Buf[4] == 0xe6)) { P1 = 1; } } if (RD == 0) { fprintf(stderr,"Буфер пуст !!!!!!\n"); continue; } clestr(Key); strncpy(Key,Buf + P1,4); J = P1; if(strncmp(Key,KeyBas1,4) == NULL || strncmp(Key,KeyEd,4) == NULL) { clestr(Line); P1 = P1 + 4; kl = strpos(Buf,0x00,RD); strncpy(Line,Buf + P1,kl + 1); while ((J = strpos(Buf + P1,0xe6,RD - P1)) == 0) { RD = read(R,Buf,Size); if (RD == 0) { fprintf(stdout,"Не найден синхробайт\n"); break; } P1 = 0; } /* J = strpos(Buf,0xe6) + 1; */ J = J + 1; } while (RD != NULL) { for (I = J; I < Size; I++) { TFmp[Ind] = Buf[I]; Ind++; } RD = read(R,Buf,Size); if (RD < Size) Size = RD; J = 0; } close(R); clestr(Rname); /* strncpy(Key,TFmp,4); */ if (strncmp(Key,KeyBas2,3) == NULL) BasicMicron(); else if (strncmp(Key,KeyEd,4) == NULL) EdMicron(); else Monitor(); } return; } BasicMicron() { static char *Token[] = {"Cls","For","Next","Data","Input","Dim","Read","Cur","Goto","Run", "If","Restore","GoSub","Return","Rem","Stop","Out","On","Plot","Line", "Poke","Print ","Def","Cont","List","Clear","Cload","Csave","New","Tab(", "To","SPC("," Fn","Then","NOT","Step","+","-","*","/","^","AND", "OR",">","=","<","SGN", "Int","ABS","Usr","Fre","Inp","POS","SQR","RND","LOG","EXP", "COS","SIN","TAN","ATN","Peek","Len","STR$","VAL","ASC","CHR$", "LEFT$","RIGHT$","MID$","SCREEN$(","InKey$","AT","&","Beep","Pause", "Verify","Home","Edit","Delete","Merge","Auto","Himem","@","ASN", "Addr","PI","Renum","ACS","LG","Lprint","Llist"}; unsigned char B, *ErrStr; unsigned int Csum, Csumr, Adr; /* N; */ int Finish, Pos = 4; fprintf(stdout,"Программа на Basic Micron имя файла -> %s\n",Line); Finish = FALSE; strcat(Tname,".bas"); strcat(Ename,".err"); fprintf(stdout,"Программа записывается в файл %s\n",Tname); FLst = fopen(Tname,"wb"); if (FLst == 0) { fprintf(stderr,"Ошибка открытия файла %s \n",Tname); } /* B = TFmp[Pos]; Pos++; */ FErr = fopen(Ename,"wb"); if (FErr == 0) { fprintf(stderr,"Ошибка открытия файла %s \n",Ename); } Csum = 0; LineCnt = 0; Adr = 0; ErrCnt = 0; while (Finish) { RD = FALSE; B = TFmp[Pos]; Pos++; Csum = Csum + B; Adr = B; B = TFmp[Pos]; Pos++; Csum = Csum + B; Adr = Adr + (B * 256); if (Adr == 0) { B = TFmp[Pos]; Pos++; Csumr = B + (TFmp[Pos] << 8); Pos++; Finish = TRUE; continue; /* I = 0; */ } B = TFmp[Pos]; Pos++; Csum = Csum + B; LineNr = B; B = TFmp[Pos]; Pos++; Csum = Csum + B; LineNr = LineNr + (B * 256); fprintf(FLst,"%4d ",LineNr); LineCnt++; while (RD) { B = TFmp[Pos]; Pos++; Csum = Csum + B; if(B == 0) { RD = TRUE; fprintf(FLst,"%s",CrLf); if (Pos > Ind) { Pos = Ind - 5; } continue; } if(B != 0x00 && B < 0x20) { HexByte(B); ErrMSG(2,Hch); continue; /*break; */ } if(B >= 0x20 && B < 0x80) { if (B >= 0x60) { fprintf(FLst,"%c",TransRus[B-0x60]); continue; /* break; */ } else { fprintf(FLst,"%c",B & 0x7f); continue; /*break; */ } } if (B >= 0xdc) { fprintf(FLst,"%s","#"); HexByte(B); ErrMSG(2,Hch); continue; /*break; */ } switch (B) { case 128: case 135: case 146: case 147: case 154: case 155: case 198: case 200: case 205: case 208: case 211: case 217: fprintf(FLst,"%s",Token[B&0x7f]); ErrMSG(3,Token[B&0x7f]); break; case 144: case 148: case 153: case 177: case 179: case 189: case 218: fprintf(FLst,"%s",Token[B&0x7f]); ErrMSG(4,Token[B&0x7f]); break; case 137: case 151: case 152: case 156: case 206: case 207: case 209: case 210: case 215: case 219: fprintf(FLst,"%s",Token[B&0x7f]); ErrMSG(5,Token[B&0x7f]); break; default: fprintf(FLst,"%s",Token[B & 0x7f]); break; } }/* break; */ /* } I++; */ } fprintf(stdout,"В файл %s записано %d строк\n",Tname,LineCnt); fprintf(stdout,"Номер последней строки %4d \n",LineNr); if (Finish != 0) { fprintf(stdout,"Конец у программы не найден \n"); fprintf(FLst,"%s",CrLf); } fclose(FLst); if (ErrCnt > 0) { fprintf(stdout," %3d ошибок и предупреждений\n",ErrCnt); fprintf(stdout,"Ошибки записаны в файл ->%s\n",Ename); fclose(FErr); } else { fclose(FErr); remove(Ename); } fprintf(stdout,"Контрольная сумма -> %4X \n",Csum & 0xffff); if ((Csum & 0xffff) != Csumr) { if (Csumr == 0) { fprintf(stdout,"Контрольная сумма не задана\n"); } else { fprintf(stdout,"Ошибка контрольной суммы ****************\n"); fprintf(stdout,"Прочитанная %4X разность ->%4X\n",Csumr,Csumr - Csum & 0xffff); } } return; } int strpos(char *Str,char S,int Lpos) { int Nps,Ik; Nps = 0; for (Ik = 0; Ik <= Lpos; Ik++ ) { if(S == Str[Ik]) { Nps = Ik; break; } } return(Nps); } int clestr(char *Str) { int Ppos,Il; Ppos = strlen(Str); for (Il = 0; Il <= Ppos; Il++) { Str[Il] = 0x00; } return; } int HexByte(char Cs) { static char Mhex[] = "0123456789ABCDEF"; int Hb,Lb; Lb = Cs & 0x0f; Hb = (Cs >> 4) & 0x0f; Hch[0] = Mhex[Hb]; Hch[1] = Mhex[Lb]; Hch[2] = 0x00; return; } ErrMSG(TT,Bc) int TT; char *Bc; { if (ErrCnt == 0) { fprintf(FErr,"\t Ошибки и предупреждения :\n"); } fprintf(FErr,"Строка %4d ",LineNr); switch(TT) { case 1: fprintf(FErr,"%s - псевдографический код, заменен на Ш\n",Bc); break; case 2: fprintf(FErr,"%s - Непечатный символ, заменен на # \n",Bc); break; case 3: fprintf(FErr,"%s - в Basic-80 не реализован\n",Bc); break; case 4: fprintf(FErr,"%s - в Basic-80 работает иначе чем в Basic Micron\n",Bc); break; case 5: fprintf(FErr,"%s - директива оператора в программе\n",Bc); break; } ErrCnt++; return; } EdMicron() { unsigned int Csum,Csumr; int Len,Exit, Pos = 0; unsigned char B; Csum = 0; B = TFmp[Pos]; Pos++; Len = B + (TFmp[Pos] << 8); Pos++; Len = 0 - Len; fprintf(stdout,"Файл редактора MICRON имя файла ->%s\n",Line); fprintf(stdout,"Длина файла -> %4d Байт\n",Len&0xffff); Exit = FALSE; strcat(Tname,".asm"); fprintf(stdout,"Программа записывается в файл %s\n",Tname); FLst = fopen(Tname,"wb"); if (FLst == 0) { fprintf(stderr,"Ошибка открытия файла %s \n",Tname); } while(Exit) { RD = Ind - Pos; while (B != 0xff && RD != 0) { B = TFmp[Pos]; Pos++; Csum = Csum + B; RD = Ind - Pos; if (B == 0xff) { Csum = Csum - B; B = TFmp[Pos]; Pos++; RD--; Csumr = B + (TFmp[Pos] << 8); RD--; B = 0xff; fprintf(stdout,"Контрольная сумма ->%4X \n",Csum & 0xffff); if (Csumr != (Csum & 0xffff)) { fprintf(stdout,"Ошибка контрольной суммы или она не задана\n"); fprintf(stdout,"Прочитана %4X разность -> %4X\n",Csumr,Csumr - Csum & 0xffff); } Exit = TRUE; close(FLst); clestr(Tname); continue; } if(B != 0x00 && B < 0x20) { if(B == 0x0d) { fprintf(FLst,"%s",CrLf); continue; } else { HexByte(B); ErrMSG(2,Hch); continue; } } if(B >= 0x20 && B < 0x80) { if (B >= 0x60) { fprintf(FLst,"%c",TransRus[B-0x60]); continue; } else { fprintf(FLst,"%c",B & 0x7f); continue; } } if (B != 0xff) { fprintf(FLst,"%s",CrLf); fprintf(stdout,"Не найден конец текста \n"); Exit =TRUE; B = 0xff; } } } return; } Monitor() { unsigned int Adr,BegAdr,EndAdr,Csum, Csumr; int Fi,La,Ct,Cs,Fsize,Ps,Iu,Ip, Er,Pos = 0, Sh,Sl,Pps; char NAdr[3], Str4[3], Bt[3], Ch, D; unsigned char B; Sl = Sh = 0; RD = FALSE; Csum = Csumr = 0; Fsize = Ind - 3; B = TFmp[Pos]; Pos++; BegAdr = TFmp[Pos] + (B << 8); /* Sl = TFmp[Pos]; */ Pos++; B = TFmp[Pos]; Pos++; EndAdr = TFmp[Pos] + (B << 8); /* Sl = Sl + TFmp[Pos]; */ Pos++; BegAdr = BegAdr & 0xffff; EndAdr = EndAdr & 0xffff; Pps = Pos; if (EndAdr < BegAdr) { fprintf(stdout,"Размер -> %d байт, тип файла не определен \n",Fsize); while (! Er) { fprintf(stdout,"Введите начальный адрес (HEX)\n"); gets(NAdr); BegAdr = 0; Er = FALSE; BegAdr = simhex(NAdr); EndAdr = BegAdr + Fsize; Er = Er || (EndAdr < BegAdr); if (Er) { fprintf(stdout,"Ошибка !!!\n"); } } } else { fprintf(stdout,"Файл МОНИТОРА RK86\n"); if ((Fsize - Pos) < (EndAdr - BegAdr)) { fprintf(stdout,"Данных меньше, чем задано адресами %4X %4X \n",BegAdr,EndAdr); EndAdr = Fsize - BegAdr - Pos; } strcat(Tname,".hex"); strcat(Ename,".dmp"); } fprintf(stdout,"Начало программы -> %4X\n",BegAdr); fprintf(stdout,"Окончание программы -> %4X\n",EndAdr); for (Iu = Pps; Iu < Ind - 3; Iu++) { B = TFmp[Iu]; Sl = Sl + B; /* Sh = Sh + B + (Sl >> 8) & 0xff; */ Sh = Sh + B; if (((Sh >> 8) & 0xff) > 0) Sh = Sh + 1; Sh = Sh & 0xff; Sl = Sl & 0xff; } Csum = Sl + ((Sh & 0xff) << 8); fprintf(stdout,"Контрольная суммма -> %4X\n",Csum & 0xffff); B = TFmp[Ind - 2]; Csumr = TFmp[Ind - 1] + (B << 8); if (Csumr != (Csum & 0xffff)) { fprintf(stdout,"Ошибка контрольной суммы или она отсутствует\n"); fprintf(stdout,"\tСумма в файле -> %4X \n",Csumr); fprintf(stdout,"\tЦиклическая сумма -> %2X\n",Sh); fprintf(stdout,"\t Сумма -> %2X\n",Sl); fprintf(stdout,"\t Разность -> %2X\n",B - Sh); fprintf(stdout,"\t Разность -> %2X\n",Sh - B); fprintf(stdout,"\t Инверсия -> %2X\n",0 - Sh); fprintf(stdout,"\t Инверсия -> %2X\n",0 - B); } fprintf(stdout,"Dump записывается в файл %s\n",Ename); FErr = fopen(Ename,"wb"); if (FErr == 0) { fprintf(stderr,"Ошибка открытия файла %s \n",Ename); } Adr = BegAdr; clestr(Line); strcat(Line,"*"); while(RD) { HexInt(Adr); fprintf(FErr,"%s ",Hin); Fi = Adr & 0x0f; La = EndAdr - Adr; if (La > 0x0f) { La = 0x0f; } else if (La < 0) La = 0; for (Iu = 0; Iu <= La; Iu++) { B = TFmp[Pos]; Pos++; HexByte(B); fprintf(FErr,"%s ",Hch); Adr++; if(B >= 0x20 && B < 0x80) { if (B >= 0x60) { Bt[0] = TransRus[B-0x60]; Bt[1] = 0x00; strcat(Line,Bt); } else { Bt[0] = B; Bt[1] = 0x00; strcat(Line,Bt); } } else strcat(Line,"."); if (Adr > EndAdr) { RD = TRUE; break; } } strcat(Line,"*"); fprintf(FErr," %s\r\n",Line); clestr(Line); strcat(Line,"*"); } close(FErr); clestr(Ename); RD = FALSE; Pos = Pps; fprintf(stdout,"Программа в Intel формате в файле %s\n",Tname); FLst = fopen(Tname,"wb"); if (FLst == 0) { fprintf(stderr,"Ошибка открытия файла %s \n",Tname); } Adr = BegAdr; while (RD) { Fi = Adr & 0x0f; La = EndAdr - Adr; if (La > 0x0f) { La = 0x0f; } Ct = La - Fi + 1; HexByte(Ct); fprintf(FLst,":%s",Hch); HexInt(Adr); fprintf(FLst,"%s00",Hin); Cs = Ct + Adr/256; Cs = Cs + (Adr - (Adr/256)*256); for (Iu = 1; Iu <= Ct; Iu++) { B = TFmp[Pos]; Pos++; Adr++; HexByte(B); fprintf(FLst,"%s",Hch); Cs = Cs + B; if (Adr > EndAdr) { RD = TRUE; break; } } Cs = 256 - (Cs & 0x00ff); HexByte(Cs); fprintf(FLst,"%s\r\n",Hch); } fprintf(FLst,":00000001FF\r\n"); close(FLst); clestr(Tname); return; } int HexInt(unsigned int Ad) { int Hb,Lb; Lb = Ad & 0x0ff; Hb = (Ad >> 8) & 0x0ff; HexByte(Hb); strcpy(Hin,Hch); HexByte(Lb); strcat(Hin,Hch); Hin[5] = 0x00; return; } int simhex(stnrk) char stnrk[]; { static char Mhex[] = "0123456789ABCDEF"; unsigned int ch1; int j,k[4],m; for (j = 0; j <= 3; j++) { k[j] = 0; ch1 = stnrk[j]; if( ch1 > 0x5f) ch1 = ch1 & 0x5f; if(ch1 < 0x30 || ch1 > 0x46) { fprintf(stderr,"Неправильный байт -> |%c|%x|\n",ch1,ch1); ch1 = Correct(ch1); } for (m = 0; m < 16; m++) { if (Mhex[m] == ch1) { k[j] = m; break; } } } ch1 = (k[0] * 4096 + k[1] * 256 + k[2] * 16 + k[3]); return(ch1); } int Correct(ss) int ss; { switch(ss) { case 0x4f: case 0x51: fprintf(stderr,"Замена %c на 0\n",ss); ss = '0'; break; case 0x49: case 0x4c: fprintf(stderr,"Замена %c на 1\n",ss); ss = '1'; break; case 0x5a: fprintf(stderr,"Замена %c на 2\n",ss); ss = '2'; break; default: fprintf(stderr,"Замена %c на 0\n",ss); ss = '0'; break; } return(ss); }