Subversion Repositories Kolibri OS

Rev

Rev 9705 | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1. #define _MAIN_
  2.  
  3. #ifdef _UNIX_
  4. #define DIV_PATH ':'                    //äåëèòåëü ïóòåé â ïåðåìåííîé îêðóæåíèÿ PATH
  5. #define DIV_FOLD '/'                    //ýòèì ñèìâîëîì ðàçäåëÿþòñÿ ïàïêè â ïóòè ê ôàéëó
  6. #endif
  7.  
  8. #ifdef _WIN32_
  9. #define DIV_PATH ';'
  10. #define DIV_FOLD '\\'
  11. #endif
  12.  
  13. #ifdef _KOS_
  14. #define DIV_PATH ';'
  15. #define DIV_FOLD '/'
  16. #endif
  17.  
  18. #include <sys/stat.h>
  19. #include <string.h>
  20. #include <unistd.h>
  21. #include <fcntl.h>
  22. #include "tok.h"
  23.  
  24. #ifdef _KOS_
  25. #include <conio.h>
  26. #endif
  27.  
  28. static char **_Argv; //!!! simplest way to make your own variable
  29.  
  30. unsigned char compilerstr[]="SPHINX C-- 0.239";
  31. char *rawfilename;                                      /* file name */
  32. char *rawext;
  33. LISTCOM *listcom;
  34. EWAR wartype={NULL,NULL},errfile={NULL,NULL};
  35. int numfindpath=0;
  36. char *findpath[16];
  37. char modelmem=TINY;
  38. char *stubfile=NULL;
  39. char *winstub=NULL;
  40. FILE *hout=NULL;
  41. const char *namestartupfile="startup.h--";
  42.  
  43. char outext[4] = "com";
  44. short extflag=TRUE;//ðàñøèðåíèå ìîæíî ïðèñâîèòü
  45. //int scrsize;
  46. unsigned char gwarning=FALSE;
  47. unsigned char sobj=FALSE;
  48. unsigned char usestub=TRUE;
  49. unsigned char dpmistub=FALSE;
  50. short dllflag=FALSE;
  51. static int numstr;
  52.  
  53. char meinfo[]=
  54.         "\nEdition of this version by\n"
  55.         "    Mishel Sheker\n"
  56.         "    Fido 2:5021/3.40\n"
  57.         "    E-Mail sheker@mail.ru\n"
  58.         "    Russia";
  59.  
  60. time_t systime;
  61. struct tm timeptr;
  62. char comsymbios=FALSE;
  63. char fobj=FALSE;        //ïðèçíàê ãåíåðàöèè obj
  64. unsigned int    startptr = 0x100;                       // start address
  65. unsigned char wconsole=FALSE;   //ïðèçíàê ãåíåðàöèè êîíñîëüíîãî ïðèëîæåíèÿ windows
  66. unsigned char optstr=FALSE;     //îïòèìèçàöèÿ ñòðîêîâûõ êîíñòàíò
  67. unsigned char crif=TRUE;        //check reply include file
  68. unsigned char idasm=FALSE;      //àññåìáëåðíûå èíñòðóêöèè ñ÷èòàòü èäåíòèôèêàòîðàìè
  69. unsigned char wbss=2;   //ïîñò ïåðåìåííûå â îòäåëüíóþ ñåêöèþ
  70. unsigned char use_env=FALSE;    //ïåðåìåííàÿ îêðóæåíèÿ
  71. int numrel=0;   //÷èñëî ýëåìåíòîâ â òàáëèöå ïåðåìåùåíèé
  72. unsigned char useordinal=FALSE;
  73. unsigned char useDOS4GW=FALSE;
  74. unsigned char clearpost=FALSE;
  75. unsigned char uselea=TRUE;
  76. unsigned char regoverstack=TRUE;
  77. unsigned char shortimport=FALSE;
  78. unsigned char useinline=2;
  79. unsigned char ocoff=FALSE;
  80. unsigned char ESPloc=FALSE;
  81.  
  82. int startupfile=-1;
  83. int alignproc=8,aligncycle=8;
  84.  
  85. const char *usage[]={
  86. "USAGE: C-- [options] [FILE_NAME.INI] [SOURCE_FILE_NAME]",
  87. "",
  88. "                       C-- COMPILER OPTIONS",
  89. "",
  90. "                           OPTIMIZATION",
  91. "-OC  optimize for code size           -DE  enable temporary expansion variable",
  92. "-OS  optimize for speed               -OST enable optimization string",
  93. "-ON  enable optimization number       -AP[=n] align start function",
  94. "-UST use startup code for variables   -AC[=n] align start cycles",
  95. #ifdef OPTVARCONST
  96. "-ORV replace variable on constant     -OIR skip repeated initializing register",
  97. #else
  98. "                                      -OIR skip repeated initializing register",
  99. #endif
  100. "",
  101. "                          CODE GENERATION",
  102. "-2   80286 code optimizations         -SA=#### start code address",
  103. "-3   80386 code optimizations         -AL=## set value insert byte",
  104. "-4   80486 code optimizations         -WFA fast call API functions",
  105. "-5   pentium code optimizations       -IV  initial all variables",
  106. "-A   enable address alignment         -SUV=#### start address variables",
  107. "-AS[=n] def. alignment in structures  -LRS load in registers over stack",
  108. "-UL  use 'lea' for adding registers   -JS  join stack calling functions",
  109. "-BA  byte access to array",//             -ASP addressing local variable via ESP",
  110. "",
  111. "                           PREPROCESSOR",
  112. "-IP=<path>  include file path         -IA   assembly instructions as identifier",
  113. "-D=<idname> defined identifier        -CRI- not check include file on repeated",
  114. "-MIF=<file> main input file           -IND=<name> import name from dll",
  115. "-SF=<file>  other startup file",
  116. "",
  117. "                              LINKING",
  118. "-AT    insert ATEXIT support block    -NS    disable stub",
  119. "-ARGC  insert parse command line      -S=#####  set stack size",
  120. "-P     insert parse command line      -WIB=##### set image base address",
  121. "-C     insert CTRL<C> ignoring code   -WFU   add Fix Up table, for Windows",
  122. "-R     insert resize memory block     -WMB   create Windows mono block",
  123. "-ENV   insert variable with environ   -WS=<name> set name stub file for win32",
  124. "-J0    disable initial jump to main() -WBSS  set post data in bss section",
  125. "-J1    initial jump to main() short   -WO    call API functions on ordinals",
  126. "-J2    initial jump to main() near    -CPA   clear post area",
  127. "-STUB= <name> set name stub file      -WSI   short import table, for Windows",
  128. "-DOS4GW file running with DOS4GW      -WAF=#### align Windows file (def 512)",
  129. "-STM   startup code in main function",
  130. "",
  131. "                           OUTPUT FILES",
  132. "-TEXE DOS EXE file (model TINY)       -D32  EXE file (32bit code for DOS)",
  133. "-EXE  DOS EXE file (model SMALL)      -W32  EXE for Windows32 GUI",
  134. "-OBJ  OBJ output file                 -W32C EXE for Windows32 console",
  135. "-SOBJ slave OBJ output file           -DLL  DLL for Windows32",
  136. "-COFF OBJ COFF output file            -DBG  create debug information",
  137. "-SYM  COM file symbiosis              -LST  create assembly listing",
  138. "-SYS  device (SYS) file               -B32  32bit binary files",
  139. "-MEOS executable file for MeOS        -MAP  create function map file",
  140. "-EXT= <ext> set file extension",
  141. "",
  142. "                           MISCELLANEOUS",
  143. "-HELP -H -? help, this info           -WORDS list of C-- reserved words",
  144. "-W         enable warning             -LAI   list of assembler instructions",
  145. "-WF=<file> direct warnings to a file  -ME    display my name and my address",
  146. "-MER=##    set maximum number errors  -X     disable SPHINX C-- header in output",
  147. "-NW=##     disable selected warnings  -WE=## selected warning will be error",
  148. //" -SCD        split code and date",
  149. NULL};
  150.  
  151. const char *dir[]={
  152.         "ME",    "WORDS",   "SYM",   "LAI",
  153.  
  154.         "OBJ",   "SOBJ",    "J0",                "J1",     "J2",    "C",     "R",
  155.         "P",     "X",       "EXE",   "S",      "SYS",   "ARGC",  "TEXE",
  156.         "ROM",   "W32",     "D32",   "W32C",   "AT",    "WFA",   "SA",
  157.         "STM",   "SUV",     "UST",   "MIF",    "DLL",   "DOS4GW","ENV",
  158.         "CPA",   "WBSS",    "MEOS",  "SF",     "B32",   "WIB",   "DBG",
  159.  
  160.         "OS",    "OC",      "A",     "0",      "1",     "2",     "3",
  161.         "4",     "5",       "6",     "7",      "8",     "9",     "W",
  162.         "WF",    "DE",
  163.         "ON",    "IP",      "STUB",  "NS",     "AP",    "D",     "OST",
  164.         "CRI",   "IA",      "SCD",   "AL",     "WFU",   "IV",
  165.         "MER",   "WMB",     "HELP",  "H",      "?",     "AC",    "WS",
  166.         "IND",   "WO",      "NW",    "LST",    "AS",    "UL",    "LRS",
  167.         "WSI",   "WAF",     "OIR",   "COFF",   "JS",    "BA",    "ASP",
  168. #ifdef OPTVARCONST
  169.         "ORV",
  170. #endif
  171.    "MAP",  "WE",   "EXT",   NULL};
  172.  
  173. enum {
  174.         c_me,    c_key,     c_sym,   c_lasm,   c_endinfo=c_lasm,
  175.  
  176.         c_obj,   c_sobj,    c_j0,    c_j1,     c_j2,    c_ctrlc, c_r,
  177.         c_p,     c_x,               c_exe,   c_s,      c_sys,   c_arg,   c_texe,
  178.         c_rom,   c_w32,     c_d32,   c_w32c,   c_at,    c_wfa,   c_sa,
  179.         c_stm,   c_suv,     c_ust,   c_mif,    c_dll,   c_d4g,   c_env,
  180.         c_cpa,   c_wbss,    c_meos,  c_sf,     c_b32,   c_wib,   c_dbg,
  181.         c_endstart=c_dbg,
  182.  
  183.         c_os,    c_oc,      c_a,     c_0,      c_1,     c_2,     c_3,
  184.         c_4,     c_5,       c_6,     c_7,      c_8,     c_9,     c_w,
  185.         c_wf,    c_de,
  186.         c_opnum, c_ip,      c_stub,  c_ns,     c_ap,    c_define,c_ost,
  187.         c_cri,   c_ia,      c_scd,   c_al,     c_wfu,   c_iv,
  188.         c_mer,   c_wmb,     c_help,  c_h,      c_hh,    c_ac,    c_ws,
  189.         c_ind,   c_wo,      c_nw,    c_lst,    c_as,    c_ul,    c_lrs,
  190.         c_wsi,   c_waf,     c_oir,   c_coff,   c_js,    c_ba,    c_asp,
  191. #ifdef OPTVARCONST
  192.         c_orv,
  193. #endif
  194.         c_map,   c_we,      c_ext,   c_end};
  195.  
  196. #define NUMEXT 6        //÷èñëî ðàçðåøåííûõ ðàñøèðåíèé êîìïèëèðóåìîãî ôàéëà
  197. char extcompile[NUMEXT][4]={"c--","cmm","c","h--","hmm","h"};
  198.  
  199. #ifdef _KOS_
  200. char __pgmname[256];
  201. char __cmdline[256];
  202. #endif
  203.  
  204. char *bufstr=NULL;      //áóôåð äëÿ ñòðîê èç ïðîöåäóð
  205. int sbufstr=SIZEBUF;    //íà÷àëüíûé ðàçìåð ýòîãî áóôåðà
  206.  
  207. void compile();
  208. void PrintInfo(char **str);
  209. void LoadIni(char *name);
  210. //void CheckNumStr();
  211. void ListId(int num,unsigned char *list,unsigned short *ofs);
  212. void printmemsizes();
  213. void print8item(char *str);
  214. void doposts(void);
  215. void GetMemExeDat();
  216. void AddJmpApi();
  217. void startsymbiosys(char *symfile);
  218. int writeoutput();
  219. void BadCommandLine(char *str);
  220. void  CheckExtenshions();
  221. void ImportName(char *name);
  222. void WarnUnusedVar();//ïðåäóïðåæäåíèÿ î íåèñïîëüçîâàííûõ ïðîöåäóðàõ è ïåðåìåííûõ
  223. void MakeExeHeader(EXE_DOS_HEADER *exeheader);
  224. void CheckPageCode(unsigned int ofs);
  225. int MakePE();
  226. int MakeObj();
  227. void CheckUndefClassProc();
  228.  
  229. // Added by Coldy
  230. void ParseObjCommand(int cmd);
  231.  
  232. void ListId(int numfirstchar,unsigned char *list,unsigned short *ofs)
  233. {
  234. char buf[40];
  235.         for(int i=0;i<numfirstchar;i++){
  236.                 if((short)ofs[i]!=-1){
  237.                         if(i<26)buf[0]=(char)('A'+i);
  238.                         else if(i==26)buf[0]='_';
  239.                         else buf[0]=(char)(i-27+'a');
  240.                         unsigned char *ii=(unsigned char *)(list+ofs[i]);
  241.                         while(*(short *)&*ii!=-1){
  242.                                 ii+=2;
  243.                                 strcpy(buf+1,(char *)ii);
  244.                                 ii+=strlen((char *)ii)+1;
  245.                                 puts(buf);
  246. //                              CheckNumStr();
  247.                         }
  248.                 }
  249.         }
  250. }
  251.  
  252. /*
  253. void PrintTegList(structteg *tteg)
  254. {
  255.         if(tteg){
  256.                 PrintTegList(tteg->left);
  257.                 PrintTegList(tteg->right);
  258.                 puts(tteg->name);
  259.         }
  260. } */
  261.  
  262. //unsigned long maxusedmem=0;
  263.  
  264. void ErrOpenFile(char *str)
  265. {
  266.         printf("Unable to open file %s.\n",str);
  267. }
  268.  
  269. int main(int argc,char *argv[])
  270. {
  271. int count;
  272. unsigned char pari=FALSE;
  273.         char *buffer;
  274.  
  275.         char compiler_ver[64];
  276.         snprintf(compiler_ver, 64, "\nSPHINX C-- Compiler   Version %d.%d%s   %s\r\n",ver1,ver2,betta,__DATE__);
  277.         puts(compiler_ver);
  278. #ifdef _KOS_
  279.         con_set_title(compiler_ver);
  280. #endif
  281. //      scrsize=24;
  282.         if(argc>1){
  283.                 _Argv=argv;// This make portable code
  284.                 bufstr=(char *)MALLOC(SIZEBUF);
  285.                 output=(unsigned char *)MALLOC((size_t)MAXDATA);
  286.                 outputdata=output;
  287.                 postbuf=(postinfo *)MALLOC(MAXPOSTS*sizeof(postinfo));
  288.                 strcpy((char *)string,argv[0]);
  289.                 rawext=strrchr((char *)string,DIV_FOLD);
  290.                
  291.                 if(rawext!=NULL){
  292.                         rawext[0]=0;
  293.                         IncludePath((char *)string);
  294.                 }
  295.                 rawfilename=getenv("C--");
  296.                 if(rawfilename!=NULL)IncludePath(rawfilename);
  297.                
  298.                 rawfilename=rawext=NULL;
  299.                 LoadIni((char *)"c--.ini");      
  300.                
  301.                 for(count=1;count<argc;count++){ //îáðàáîòêà êîìàíäíîé ñòðîêè
  302.                         if(argv[count][0]=='/'||argv[count][0]=='-'){
  303.                         //if(argv[count][0]=='-'){
  304.                                 if(SelectComand(argv[count]+1,&count)==c_end) BadCommandLine(argv[count]);
  305.                         }
  306.                         else{
  307.                                 if(pari==FALSE){
  308.                                         rawfilename=argv[count];
  309.                                         pari=TRUE;
  310.                                         if((rawext=strrchr(rawfilename,'.'))!=NULL){
  311.                                                 if(stricmp(rawext,".ini")==0){  //óêàçàí ini ôàéë
  312.                                                         rawfilename=NULL;
  313.                                                         rawext=NULL;
  314.                                                         LoadIni(argv[count]);
  315.                                                         if(rawfilename==NULL)pari=FALSE;
  316.                                                 }
  317.                                                 else{
  318.                                                         *rawext++=0;
  319.                                                         CheckExtenshions();
  320.                                                 }
  321.                                         }
  322.                                 }
  323.                         }
  324.                 }
  325.         }
  326.   //{   Added by Coldy
  327.         //      If -coff (for fully mscoff)
  328.         if (ocoff && !sobj) {
  329.                 am32 = TRUE;
  330.                 ParseObjCommand(c_sobj);
  331.  
  332.         }
  333.         //}
  334.         if(rawfilename==NULL){
  335.                 PrintInfo((char **)usage);
  336.                 exit( e_noinputspecified );
  337.         }
  338.         time(&systime); //òåêóùåå âðåìÿ
  339.         memcpy(&timeptr,localtime(&systime),sizeof(tm));
  340.         InitDefineConst();
  341.         compile();
  342.         if(error==0)exit(e_ok);
  343.         exit(e_someerrors);
  344.         return 0;
  345. }
  346.  
  347. void CheckExtenshions()
  348. {
  349. int i;
  350.         for(i=0;i<NUMEXT;i++){
  351.                 if(stricmp(rawext,extcompile[i])==0)break;
  352.         }
  353.         if(i==NUMEXT){
  354.                 printf("Bad input file extension '%s'.",rawext);
  355.           exit(e_badinputfilename);
  356.         }
  357. }
  358.  
  359. void compile()
  360. {
  361. long segments_required;
  362. union{
  363.         long longhold;
  364.         void *nextstr;
  365. };
  366. //ñîçäàòü èìÿ ôàéëà ñ ïðåäóïðåæäåíèÿìè è åñëè îí åñòü óäàëèòü
  367.         errfile.name=(char *)MALLOC(strlen(rawfilename)+5);
  368.         sprintf(errfile.name,"%s.err",rawfilename);
  369.         if(stat(errfile.name,(struct stat *)string2)==0)remove(errfile.name);
  370. //åñëè åñòü èìÿ ôàéëà äëÿ ïðåäóïðåæäåíèé ïðîâåðèòü åãî ñóùåñòâîâàíèå è óäàëèòü.
  371.         if(wartype.name!=NULL){
  372.                 if(stat(wartype.name,(struct stat *)string2)==0)remove(wartype.name);
  373.         }
  374.         puts("Compiling Commenced . . .");
  375.         if(rawext!=NULL)sprintf((char *)string,"%s.%s",rawfilename,rawext);
  376.         else{
  377.                 for(unsigned int i=0;i<NUMEXT;i++){
  378.                         sprintf((char *)string,"%s.%s",rawfilename,extcompile[i]);
  379.                         if(stat((char *)string,(struct stat *)string2)==0)break;
  380.                 }
  381.         }
  382.         linenumber=0;
  383.         initregstat();
  384. #ifdef OPTVARCONST
  385.         CreateMainLVIC();
  386. #endif
  387. #ifdef __NEWLEX__
  388.         inittokn();
  389. #endif
  390.         compilefile((char *)string,2); //ñîáñòâåííî ðàçáîðêà è êîìïèëÿöèÿ
  391.         puts("Link . . .");
  392.         if(comfile==file_w32&&wbss==2){
  393.                 wbss=FALSE;
  394.                 if(wconsole==FALSE)wbss=TRUE;
  395.         }
  396.         if(notdoneprestuff==TRUE)doprestuff();  //startup code
  397.         if(endifcount>=0)preerror("?endif expected before end of file");
  398.         AddObj();
  399.         docalls();      //äîáàâèòü âíåøíèå ïðîöåäóðû
  400.         addinitvar();
  401.         CheckUndefClassProc();
  402.         if(undefoffstart!=NULL){        //âûäàòü ñïèñîê íåèçâåñòíûõ ññûëîê
  403.                 UNDEFOFF *curptr=undefoffstart;
  404.                 for(;;){
  405.                         char holdstr[80];
  406.                         UNDEFOFF *ocurptr;
  407.                         linenumber=curptr->pos->line;
  408.                         sprintf(holdstr,"\'%s\' offset undefined",curptr->name);
  409.                         currentfileinfo=curptr->pos->file;
  410.                         preerror(holdstr);
  411.                         free(curptr->pos);
  412.                         if(curptr->next==NULL)break;
  413.                         ocurptr=curptr->next;
  414.                         free(curptr);
  415.                         curptr=ocurptr;
  416.                 }
  417.                 free(curptr);
  418.         }
  419.         while(liststring!=NULL){
  420.                 STRING_LIST *ins;
  421.                 ins=(STRING_LIST *)liststring;
  422.                 nextstr=ins->next;
  423.                 free(liststring);
  424.                 liststring=nextstr;
  425.         }
  426.         free(bufstr);
  427.         if(warning==TRUE&&wact[7].usewarn)WarnUnusedVar();//ïðåäóïðåæäåíèÿ î íåèñïîëüçîâàííûõ ïðîöåäóðàõ è ïåðåìåííûõ
  428.         if(numstrtbl)CreatStrTabRes();  //çàâåðøèòü ñîçäàíèå ðåñóðñîâ
  429.         if(fobj==FALSE){
  430.                 if(comfile==file_w32&&error==0){
  431.                         AddJmpApi();    //êîñâåííûå âûçîâû API
  432.                         CreatWinStub();
  433.                 }
  434.                 longhold=outptr;
  435.                 if(comfile==file_rom){
  436.                         ooutptr=outptr;
  437.                         if(modelmem==SMALL){
  438.                                 *(short *)&output[stackstartaddress]=(short)(((outptrdata+postsize+stacksize)/4+1)*4);
  439.                                 *(short *)&output[dataromstart]=(short)(outptr+4);
  440.                                 *(short *)&output[dataromsize]=(short)(outptrdata/2);
  441. //                              printf("outptr=%d outptrdate=%d outptrsize=%d\n",outptr,outptrdata,outptrsize);
  442.                                 for(unsigned int i=0;i<outptrdata;i++)op(outputdata[i]);
  443.                         }
  444.                         if(romsize==0){
  445.                                 unsigned int i=outptr/1024;
  446.                                 if((outptr%1024)!=0)i++;
  447.                                 if(i>32)i=64;
  448.                                 else if(i>16)i=32;
  449.                                 else if(i>8)i=16;
  450.                                 else if(i>4)i=8;
  451.                                 else if(i>2)i=4;
  452.                                 romsize=i*1024;
  453.                                 output[2]=(unsigned char)(romsize/512);
  454.                         }
  455.                         if(outptr>=romsize)preerror("The size of a code is more than the size of the ROM");
  456.                         for(;outptr<romsize;)op(aligner);
  457.                         unsigned char summa=0;
  458.                         for(unsigned int i=0;i<romsize;i++)summa+=output[i];
  459.                         output[romsize-1]-=summa;
  460.                         outptr=ooutptr;
  461.                 }
  462.                 else if(modelmem==SMALL&&comfile==file_exe){ // if an EXE file
  463.                         longhold+=AlignCD(CS,16);
  464. //                      if((outptr%16)!=0)outptr+=16-outptr%16;// paragraph align the end of the code seg
  465.                         if(((long)outptrdata+(long)postsize+(long)stacksize)>65535L)
  466.                                         preerror("Data and stack total exceeds 64k");
  467.                 }
  468.                 else if(comfile==file_sys){
  469.                         for(int i=0;i<sysnumcom;i++){
  470.                                 searchvar((listcom+i)->name);
  471.                                 *(short *)&output[syscom+i*2]=(unsigned short)itok.number;
  472.                         }
  473.                         free(listcom);
  474.                 }
  475.                 else longhold+=(long)postsize+(long)(stacksize);
  476.                 if(am32==0&&longhold>65535L&&!(modelmem==TINY&&(!resizemem)))preerror("Code, data and stack total exceeds 64k");
  477.                 if(posts>0)doposts();  //Óñòàíîâèòü àäðåñà âûçîâîâ ïðîöåäóð è ïåðåõîäîâ
  478.                 if(resizemem&&comfile==file_com){
  479.                         segments_required=(outptr+postsize+stacksize+15)/16;
  480.                         *(short *)&output[resizesizeaddress]=(short)segments_required;
  481.                         *(short *)&output[stackstartaddress]=(short)(segments_required*16);
  482.                 }
  483.         }
  484.         deinitregstat();
  485. #ifdef OPTVARCONST
  486.         KillMainLVIC();
  487. #endif
  488. //      puts("List Teg name:");
  489. //      PrintTegList(tegtree);
  490.         printf("COMPILING FINISHED.  Errors: %d\n",error);
  491.         if(error==0){
  492.                 if(cpu>=1){
  493.                         char m1[12];
  494.                         switch(cpu){
  495.                                 case 5:
  496.                                         strcpy(m1,"Pentium");
  497.                                         break;
  498.                                 case 6:
  499.                                         strcpy(m1,"MMX");
  500.                                         break;
  501.                                 case 7:
  502.                                         strcpy(m1,"Pentium II");
  503.                                         break;
  504.                                 case 8:
  505.                                         strcpy(m1,"Pentium III");
  506.                                         break;
  507.                                 case 9:
  508.                                         strcpy(m1,"Pentium IV");
  509.                                         break;
  510.                                 default: sprintf(m1,"80%d86",cpu);
  511.                         }
  512.                         printf("CPU required: %s or greater.\n",m1);
  513.                 }
  514.                 runfilesize=outptr-startptr;
  515.                 if(comfile==file_rom)runfilesize=romsize;
  516.                 else if(modelmem==SMALL&&comfile==file_exe){
  517.                         runfilesize+=outptrdata-startptrdata+0x20;
  518.                         postsize+=postsize%2;
  519.                         stacksize=(stacksize+15)/16*16;
  520.                 }
  521.                 else if((comfile==file_exe||comfile==file_d32)&&modelmem==TINY)
  522.                                 runfilesize+=0x20;
  523.                 printmemsizes();
  524.                 endinptr=outptr;
  525.                 if(writeoutput()==0)printf("Run File Saved (%ld bytes).\n",runfilesize);
  526.                 if(comfile==file_w32&&fobj==FALSE)printf("Created file of a format PE for Windows.\nFor alignment section code, added %u zero bytes.\n",filingzerope);
  527. //              else if(FILEALIGN&&fobj==FALSE)printf("For alignment file, added %u zero bytes.\n",filingzerope);
  528.         }
  529.                 if(pdbg)DoTDS();
  530. }
  531.  
  532. void printmemsizes()
  533. {
  534. long stacklong;
  535. unsigned int stackword;
  536. unsigned int postword,codeword;
  537.         postword=postsize;
  538.         codeword=outptr-startptr;
  539.         stackword=stacksize;
  540.         if(comfile==file_com||(comfile==file_exe&&modelmem==TINY)){
  541.                 if(resizemem==0){
  542.                         stacklong=0xFFFE - outptr - postsize;
  543.                         stackword=stacklong;
  544.                 }
  545.                 codeword=codeword-datasize-alignersize;
  546.         }
  547.         else if(comfile==file_sys)stackword=sysstack;
  548.         else if(comfile==file_exe||comfile==file_rom)datasize=outptrdata;
  549.         else if(comfile==file_d32)codeword-=datasize;
  550.         printf("Code: %u bytes, Data: %u bytes, Post: %u bytes, Stack: %u bytes\n"
  551.                         ,codeword,datasize,postword,stackword);
  552.         for(int i=0;i<posts;i++){
  553.                 switch((postbuf+i)->type){
  554.                         case CODE_SIZE:
  555.                                 *(short *)&output[(postbuf+i)->loc]+=codeword;
  556.                                 break;
  557.                         case CODE_SIZE32:
  558.                                 *(long *)&output[(postbuf+i)->loc]+=codeword;
  559.                                 break;
  560.                         case DATA_SIZE:
  561.                                 *(short *)&output[(postbuf+i)->loc]+=datasize;
  562.                                 break;
  563.                         case DATA_SIZE32:
  564.                                 *(long *)&output[(postbuf+i)->loc]+=datasize;
  565.                                 break;
  566.                         case POST_SIZE:
  567.                                 *(short *)&output[(postbuf+i)->loc]+=postword;
  568.                                 break;
  569.                         case POST_SIZE32:
  570.                                 *(long *)&output[(postbuf+i)->loc]+=postword;
  571.                                 break;
  572.                         case STACK_SIZE:
  573.                                 *(short *)&output[(postbuf+i)->loc]+=stackword;
  574.                                 break;
  575.                         case STACK_SIZE32:
  576.                                 *(long *)&output[(postbuf+i)->loc]+=stackword;
  577.                                 break;
  578.                 }
  579.         }
  580. }
  581.  
  582. void PrintInfo(char **str)
  583. {
  584.         numstr=1;
  585.         for(int i=0;str[i]!=NULL;i++){
  586.                 puts(str[i]);
  587. //              CheckNumStr();
  588.         }
  589. }
  590.  
  591. /*void CheckNumStr()
  592. {
  593. #ifndef _UNIX_
  594.         if(((numstr+1)%(scrsize-1))==0&&outfile!=0){
  595.                 puts("Press any key...");
  596.                 getch();
  597.         }
  598.         numstr++;
  599. #endif
  600. } */
  601.  
  602. void strbtrim(char *st)
  603. {
  604. int i;
  605. char *p,*q;
  606.         p=q=st;
  607.         while(isspace(*p))p++;  //ïîêà íåçíà÷àùèå ñèìâîëû
  608.         while(*p)*q++=*p++;     //ïåðåìåñòèòü ñòðîêó
  609.         *q='\0';
  610.         for(i=strlen(st)-1;isspace(st[i])&&i>=0;i--);
  611.         st[i+1]='\0';
  612. }
  613.  
  614. unsigned long getnumber(unsigned char *buf)
  615. {
  616. int temp2;
  617. unsigned long retnum;
  618. unsigned char *oinput;
  619. unsigned int oinptr,oendinptr;
  620.         if(!isdigit(buf[0]))return 0;
  621.         oinptr=inptr;
  622.         oinput=input;
  623.         oendinptr=endinptr;
  624.         input=buf;
  625.         inptr=0;
  626.         endinptr=256;
  627.         retnum=scannumber(&temp2);
  628.         inptr=oinptr;
  629.         input=oinput;
  630.         endinptr=oendinptr;
  631.         return retnum;
  632. }
  633.  
  634. void ParseObjCommand(int cmd){
  635.         switch (cmd) {
  636.         case c_sobj:
  637.                 sobj = TRUE;
  638.                 FixUp = TRUE;
  639.                 jumptomain = CALL_NONE;
  640.         case c_obj:
  641.                 fobj = TRUE;
  642.                 //                                      if(comfile==file_d32)FixUp=TRUE;
  643.                 FastCallApi = FALSE;
  644.         }
  645. }
  646.  
  647. int SelectComand(char *pptr,int *count)
  648. {
  649. int i;
  650. unsigned char neg=FALSE;
  651. char *ptr;
  652. int len;
  653.         if((ptr=strchr(pptr,';'))!=NULL)*ptr=0;// èùåì êîììåíòàðèé îòñåêàåì âñå ïîñëå íåãî
  654.         if((ptr=strchr(pptr,'='))!=NULL){ // èùåì çíàê ðàâåíñòâà
  655.                 *ptr=0; // äåëèì
  656.                 ptr++;
  657.           strbtrim(ptr);        //óáðàòü ëèøíèå ïðîáåëû
  658.         }
  659.   strbtrim(pptr);       //óáðàòü ëèøíèå ïðîáåëû
  660.         if(*pptr==0)return c_end+1;     //ïóñòàÿ ñòðîêà
  661.         if((i=strlen(pptr))>1&&pptr[i-1]=='-'){
  662.                 neg=TRUE;
  663.                 pptr[i-1]=0;
  664.         }
  665.         strupr(pptr);
  666.         for(i=0;dir[i]!=NULL;i++){
  667.                 if(strcmp(dir[i],pptr)==0){
  668.                         if((i<=c_endinfo)&&count==0){
  669.                                 char buf[80];
  670.                                 sprintf(buf,"Option '%s' is used only in command line",dir[i]);
  671.                                 preerror(buf);
  672.                                 return i;
  673.                         }
  674.                         if(i<=c_endstart&&notdoneprestuff!=TRUE){
  675. errlate:
  676.                                 char buf[80];
  677.                                 sprintf(buf,"Too late used '#pragma option %s'",dir[i]);
  678.                                 preerror(buf);
  679.                                 return i;
  680.                         }
  681.                         switch(i){
  682.                                 case c_j0: jumptomain=(unsigned char)(neg!=FALSE?CALL_NEAR:CALL_NONE); header=(unsigned char)0^neg; break;
  683.                                 case c_j1: jumptomain=(unsigned char)CALL_SHORT; header=(unsigned char)1; break;
  684.                                 case c_j2: jumptomain=(unsigned char)(neg==FALSE?CALL_NEAR:CALL_NONE); header=(unsigned char)1^neg; break;
  685.                                 case c_ctrlc: killctrlc=(unsigned char)1^neg; break;
  686.                                 case c_os: optimizespeed=(unsigned char)1^neg; break;
  687.                                 case c_oc: optimizespeed=(unsigned char)0^neg; break;
  688.                                 case c_r: resizemem=(unsigned char)1^neg; break;
  689.                                 case c_p: parsecommandline=(unsigned char)1^neg; break;
  690.                                 case c_a: alignword=(unsigned char)1^neg; break;
  691.                                 case c_sym:
  692.                                         startptr=0x100;
  693.                                         comsymbios=TRUE;
  694.                                         *count=*count+1;
  695.           startsymbiosys(_Argv[*count]);
  696.                                         break;
  697.                                 case c_0: chip=0; break;
  698.                                 case c_1: chip=1; break;
  699.                                 case c_2: chip=2; break;
  700.                                 case c_3: chip=3; break;
  701.                                 case c_4: chip=4; break;
  702.                                 case c_5: chip=5; break;
  703.                                 case c_6: chip=6; break;        //MMX
  704.                                 case c_7: chip=7; break;  //Pro
  705.                                 case c_8: chip=8; break;  //PII
  706.                                 case c_9: chip=9; break;  //PIII
  707.                                 case c_x: header=(unsigned char)0^neg; break;
  708.                                 case c_exe:
  709.                                         comfile=file_exe;
  710.                                         modelmem=SMALL;
  711.                                         splitdata=TRUE;
  712.                                         GetMemExeDat();
  713.                                         if(extflag) strcpy(outext,"exe");
  714.                                         startptr=0;                     // start address
  715.                                         startptrdata=0;         // data start address
  716.                                         dos1=2;
  717.                                         dos2=0;
  718.                                         break;
  719.                                 case c_sys:
  720.                                         comfile=file_sys;
  721.                                         if(extflag) strcpy(outext,"sys");
  722.                                         startptr=0;             // start address
  723.                                         startptrdata=0;         // data start address
  724.                                         jumptomain=CALL_NONE;
  725.                                         header=0;
  726.                                         break;
  727.                                 case c_sobj:
  728. /*                                      sobj=TRUE;
  729.                                         FixUp=TRUE;
  730.                                         jumptomain=CALL_NONE;
  731. */                      case c_obj:
  732. /*                                      fobj=TRUE;
  733. //                                      if(comfile==file_d32)FixUp=TRUE;
  734.                                         FastCallApi=FALSE;
  735. */
  736.           ParseObjCommand(i);
  737.                                         break;
  738.                                 case c_me:
  739.                                         puts(meinfo);
  740.                                         exit( e_ok );
  741.                                 case c_key:
  742.                                         int j,jj;
  743.                                         puts("LIST OF RESERVED IDENTIFIERS:");
  744.                                         numstr=1;
  745.                                         ListId(53,(unsigned char *)id,idofs);
  746.                                         for(j=0;j<ID2S;j++){
  747.                                                 puts(id2[j]);
  748. //                                              CheckNumStr();
  749.                                         }
  750.                                         for(jj=0;jj<2;jj++){
  751.                                                 for(j=0;j<8;j++)printf("%s ",regs[jj][j]);
  752.                                                 puts("");
  753. //                                              CheckNumStr();
  754.                                         }
  755.                                         for(j=0;j<8;j++)printf("%s ",begs[j]);
  756.                                         puts("");
  757. //                                      CheckNumStr();
  758.                                         for(j=0;j<6;j++)printf("%s ",segs[j]);
  759.                                         print8item("ST(%d) ");
  760.                                         puts("ST");
  761.                                         print8item("st(%d) ");
  762.                                         puts("st");
  763.                                         exit(e_ok);
  764.                                 case c_lasm:
  765.                                         puts("LIST OF SUPPORTED ASSEMBLER INSTRUCTIONS:");
  766.                                         numstr=1;
  767.                                         ListId(26,asmMnem,ofsmnem);
  768.                                         exit(e_ok);
  769.                                 case c_s:
  770.                                         if(ptr==NULL)return c_end;
  771.                                         if((stacksize=getnumber((unsigned char *)ptr))==0){
  772.                                                 puts("Bad stack size.");
  773.                                                 exit(e_unknowncommandline);
  774.                                         }
  775.                                         stacksize=Align(stacksize,4);
  776.                                         break;
  777.                                 case c_w:
  778.                                         gwarning=(unsigned char)TRUE^neg;
  779.                                         break;
  780.                                 case c_wf:
  781.                                         if(wartype.name)free(wartype.name);
  782.                                         wartype.name=BackString(ptr);
  783.                                         break;
  784.                                 case c_de:
  785.                                         divexpand=(unsigned char)TRUE^neg;
  786.                                         break;
  787.                                 case c_opnum:
  788.                                         optnumber=(unsigned char)TRUE^neg;
  789.                                         break;
  790.                                 case c_ip:
  791.                                         IncludePath(ptr);
  792.                                         break;
  793.                                 case c_arg:
  794.                                         parsecommandline=(unsigned char)TRUE^neg;
  795.                                         fargc=(unsigned char)TRUE^neg;
  796.                                         break;
  797.                                 case c_texe:
  798.                                         if(extflag) strcpy(outext,"exe");
  799.                                         comfile=file_exe;
  800.                                         break;
  801.                                 case c_rom:
  802.                                         if(extflag) strcpy(outext,"rom");
  803.                                         comfile=file_rom;
  804.                                         startptr=0;
  805.                                         startptrdata=0;         // data start address
  806.                                         GetMemExeDat();
  807.                                         break;
  808.                                 case c_dll:
  809.                                         wconsole=TRUE;
  810.                                         dllflag=TRUE;
  811.                                         if(extflag) strcpy(outext,"dll");
  812.                                         comfile=file_w32;
  813.                                         FixUpTable=TRUE;
  814.                                         goto nexpardll;
  815.  
  816. /*                                      FixUp=TRUE;
  817.                                         startptrdata=startptr=0;
  818.                                         am32=TRUE;
  819.                                         if(chip<3)chip=3;
  820.                                         if(FILEALIGN==0)FILEALIGN=512;
  821.                                         break;*/
  822.                                 case c_w32c:
  823.                                         wconsole=TRUE;
  824.                                         goto init_w32;
  825.                                 case c_w32:
  826.                                         wconsole=FALSE;
  827.                                         dllflag=FALSE;
  828. init_w32:
  829.                                         comfile=file_w32;
  830.                                         goto nexpar;
  831.                                 case c_d32:
  832.                                         comfile=file_d32;
  833. nexpar:
  834.                                         if(extflag) strcpy(outext,"exe");
  835. nexpardll:
  836.                                         FixUp=TRUE;
  837.                                         startptrdata=startptr=0;
  838.                                         am32=TRUE;
  839.                                         if(chip<3)chip=3;
  840.                                         if(FILEALIGN==0)FILEALIGN=512;
  841.                                         break;
  842.                                 case c_meos:
  843.                                         comfile=file_meos;
  844.                                         am32=TRUE;
  845.                                         startptrdata=startptr=0;
  846.                                         if(extflag) strcpy(outext,"");
  847.                                         if(chip<3)chip=3;
  848.                                         break;
  849.                                 case c_b32:
  850.                                         comfile=file_bin;
  851.                                         am32=TRUE;
  852.                                         startptrdata=startptr=0;
  853.                                         if(extflag) strcpy(outext,"bin");
  854.                                         FixUp=TRUE;
  855.                                         ImageBase=0;
  856.                                         if(chip<3)chip=3;
  857.                                         break;
  858.                                 case c_stub:
  859.                                         if(stubfile)free(stubfile);
  860.                                         stubfile=BackString(ptr);
  861.                                         dpmistub=FALSE;
  862.                                         if(stricmp(stubfile,"dpmi")==0){
  863.                                                 if(notdoneprestuff!=TRUE)goto errlate;
  864.                                                 dpmistub=TRUE;
  865.                                                 usestub=FALSE;
  866.                                         }
  867.                                         break;
  868.                                 case c_ns:
  869.                                         usestub=(unsigned char)0^neg;
  870.                                         break;
  871.                                 case c_ap:
  872.                                         AlignProc=(unsigned char)1^neg;
  873.                                         if(ptr!=NULL){
  874.                                                 alignproc=getnumber((unsigned char *)ptr);
  875.                                                 if(alignproc<1||alignproc>4096)alignproc=8;
  876.                                         }
  877.                                         break;
  878.                                 case c_define:
  879.                                         addconsttotree(ptr,TRUE);
  880.                                         break;
  881.                                 case c_ost:
  882.                                         optstr=(unsigned char)TRUE^neg;
  883.                                         break;
  884.                                 case c_cri:
  885.                                         crif=(unsigned char)1^neg;
  886.                                         break;
  887.                                 case c_ia:
  888.                                         idasm=(unsigned char)1^neg;
  889.                                         break;
  890.                                 case c_dbg:
  891.                                         dbg&=0xFE;
  892.                                         char c;
  893.                                         c=(unsigned char)1^neg;
  894.                                         dbg|=c;
  895.                                         if(!neg)InitDbg();
  896.                                         break;
  897.                                 case c_scd:
  898. /*-----------------13.08.00 23:01-------------------
  899.  áóäåò ââåäåíà ïîñëå äîðàáîòêè äèíàìè÷åñêèõ ïðîöåäóð
  900.         --------------------------------------------------*/
  901.                                         splitdata=(unsigned char)1^neg;
  902.                                         if(modelmem==SMALL)splitdata=TRUE;
  903.                                         break;
  904.                                 case c_al:
  905.                                         if(ptr==NULL)return c_end;
  906.                                         aligner=(unsigned char)getnumber((unsigned char *)ptr);
  907.                                         break;
  908.                                 case c_at:
  909.                                         atex=(unsigned char)1^neg;
  910.                                         break;
  911.                                 case c_wfa:
  912.                                         FastCallApi=(unsigned char)1^neg;
  913.                                         break;
  914.                                 case c_wfu:
  915.                                         FixUpTable=(unsigned char)1^neg;
  916.                                         break;
  917.                                 case c_wib:
  918.                                         if(ptr==NULL)return c_end;
  919.                                         ImageBase=getnumber((unsigned char *)ptr);
  920.                                         break;
  921.                                 case c_iv:
  922.                                         notpost=(unsigned char)1^neg;
  923.                                         break;
  924.                                 case c_mer:
  925.                                         if(ptr==NULL)return c_end;
  926.                                         if((maxerrors=getnumber((unsigned char *)ptr))==0)maxerrors=16;
  927.                                         break;
  928.                                 case c_sa:
  929.                                         if(ptr==NULL)return c_end;
  930.                                         startptrdata=startptr=getnumber((unsigned char *)ptr);
  931.                                         break;
  932.                                 case c_stm:
  933.                                         startuptomain=(unsigned char)1^neg;
  934.                                         break;
  935.                                 case c_suv:
  936.                                         if(ptr==NULL)return c_end;
  937.                                         startStartup=getnumber((unsigned char *)ptr);
  938.                                         break;
  939.                                 case c_wmb:
  940.                                         WinMonoBlock=(unsigned char)1^neg;
  941.                                         break;
  942.                                 case c_ust:
  943.                                         useStartup=(unsigned char)1^neg;
  944.                                         break;
  945.                                 case c_help:
  946.                                 case c_h:
  947.                                 case c_hh:
  948.                                         PrintInfo((char **)usage);
  949.                                         exit(e_ok);
  950.                                 case c_mif:
  951.                                         if(ptr==NULL)return c_end;
  952.                                         if(rawfilename!=NULL){
  953.                                                 free(rawfilename);
  954.                                                 rawfilename=NULL;
  955.                                         }
  956.                                         if(rawext!=NULL){
  957.                                                 free(rawext);
  958.                                                 rawext=NULL;
  959.                                         }
  960.                                         char *temp;
  961.                 if((temp=strrchr(ptr,'.'))!=NULL){
  962.                                                 *temp++=0;
  963.                                                 rawext=BackString(temp);
  964.                                                 CheckExtenshions();
  965.                     }
  966.                                         rawfilename=BackString(ptr);
  967.                                         break;
  968.                                 case c_ac:
  969.                                         AlignCycle=(unsigned char)1^neg;
  970.                                         if(ptr!=NULL){
  971.                                                 aligncycle=getnumber((unsigned char *)ptr);
  972.                                                 if(aligncycle<1&&aligncycle>4096)aligncycle=8;
  973.                                         }
  974.                                         break;
  975.                                 case c_ws:      //dos-stub for windows programs
  976.                                         if(winstub)free(winstub);
  977.                                         winstub=BackString(ptr);
  978.                                         break;
  979.                                 case c_ind:
  980.                                         ImportName(ptr);
  981.                                         break;
  982.                                 case c_wbss:
  983.                                         wbss=(unsigned char)1^neg;
  984.                                         break;
  985.                                 case c_wo:
  986.                                         useordinal=(unsigned char)1^neg;
  987.                                         break;
  988.                                 case c_nw:
  989.                                         if(ptr==NULL)return c_end;
  990.                                         len=getnumber((unsigned char *)ptr);
  991.                                         if(len>0&&len<=WARNCOUNT)wact[len-1].usewarn=(unsigned char)0^neg;
  992.                                         break;
  993.                                 case c_we:
  994.                                         if(ptr==NULL)return c_end;
  995.                                         len=getnumber((unsigned char *)ptr);
  996.                                         if(len>0&&len<=WARNCOUNT){
  997.                                                 if(neg)wact[len-1].fwarn=warningprint;
  998.                                                 else wact[len-1].fwarn=preerror3;
  999.                                         }
  1000.                                         break;
  1001.                                 case c_lst:
  1002.                                         SetLST(neg);
  1003.                                         break;
  1004.                                 case c_d4g:
  1005.                                         useDOS4GW=(unsigned char)1^neg;
  1006.                                         break;
  1007.                                 case c_env:
  1008.                                         use_env=(unsigned char)1^neg;
  1009.                                         break;
  1010.                                 case c_cpa:
  1011.                                         clearpost=(unsigned char)1^neg;
  1012.                                         break;
  1013.                                 case c_ul:
  1014.                                         uselea=(unsigned char)1^neg;
  1015.                                         break;
  1016.                                 case c_as:
  1017.                                         if(ptr){
  1018.                                                 len=getnumber((unsigned char *)ptr);
  1019.                                                 if(caselong(len)!=NUMNUM)strpackdef=len;
  1020.                                         }
  1021.                                         else strpackdef=(neg==FALSE?8:1);
  1022.                                         strpackcur=strpackdef;
  1023.                                         break;
  1024.                                 case c_lrs:
  1025.                                         regoverstack=(unsigned char)1^neg;
  1026.                                         break;
  1027.                                 case c_wsi:
  1028.                                         shortimport=(unsigned char)1^neg;
  1029.                                         break;
  1030.                                 case c_waf:
  1031.                                         if(ptr!=NULL){
  1032.                                                 FILEALIGN=Align(getnumber((unsigned char *)ptr),16);
  1033.                                         }
  1034.                                         break;
  1035.                                 case c_sf:
  1036.                                         if(ptr==NULL)return c_end;
  1037.                                         namestartupfile=BackString(ptr);
  1038.                                         break;
  1039.                                 case c_oir:
  1040.                                         optinitreg=(unsigned char)1^neg;
  1041.                                         break;
  1042.                                 case c_coff:
  1043.                                         ocoff=(unsigned char)1^neg;
  1044.                                         break;
  1045.                                 case c_js:
  1046.                                         addstack=(unsigned char)1^neg;
  1047.                                         if(addstack==0)RestoreStack();
  1048.                                         break;
  1049.                                 case c_ba:
  1050.                                         bytesize=(unsigned char)1^neg;
  1051.                                         break;
  1052.                                 case c_asp:
  1053.                                         if(blockproc)goto errlate;
  1054.                                         else ESPloc=(unsigned char)1^neg;
  1055.                                         break;
  1056. #ifdef OPTVARCONST
  1057.                                 case c_orv:
  1058.                                         replasevar=(unsigned char)1^neg;
  1059.                                         if(replasevar&&listvic)ClearLVIC();
  1060.                                         break;
  1061.                                 case c_map:
  1062.                                         mapfile=(unsigned char)1^neg;
  1063.                                         break;
  1064. #endif
  1065.                                 case c_ext:     //***lev***
  1066.                                         strcpy(outext,BackString(ptr)); //***lev***
  1067.                                         extflag=FALSE; //÷òîáû ðàñøèðåíèå íå ïåðåçàáèâàëîñü äðóãèìè êëþ÷àìè, åñëè îíè èäóò ïîçæå
  1068.                                         break;  //***lev***
  1069.                         }
  1070.                         break;
  1071.                 }
  1072.         }
  1073.         return i;
  1074. }
  1075.  
  1076. void SetLST(unsigned char neg)
  1077. {
  1078.         if(((dbg&2)>>1)==neg){
  1079.                 dbg&=0xFD;
  1080.                 unsigned char c=(unsigned char)((1^neg)<<1);
  1081.                 dbg|=c;
  1082.                 if(neg){
  1083.                         if((dbg&0xFE)==0)dbgact=TRUE;
  1084.                         AddEndLine();
  1085.                 }
  1086.                 else{
  1087.                         InitDbg();
  1088.                         if(notdoneprestuff!=TRUE)dbgact=FALSE;  //startup cod
  1089.                 }
  1090.         }
  1091. }
  1092.  
  1093. void print8item(char *str)
  1094. {
  1095. //      CheckNumStr();
  1096.         for(int j=0;j<8;j++)printf(str,j);
  1097.         puts("");
  1098. }
  1099.  
  1100.  
  1101.  
  1102.  
  1103. void _loadIni(FILE *inih)
  1104. {
  1105.         char m1[256];
  1106.         for(;;){
  1107.                 if(fgets(m1,255,inih)==NULL)break;
  1108.                 if(SelectComand(m1,0)==c_end)BadCommandLine(m1);
  1109.         }
  1110.         fclose(inih);
  1111. }
  1112.  
  1113. void LoadIni(char *name)
  1114. {
  1115. FILE *inih;
  1116. char m1[256];
  1117.  
  1118.                                                         // load name
  1119.         if (inih = fopen(name,"rb"))
  1120.         {_loadIni(inih);return;}
  1121.        
  1122.         if(strcmp(name,"c--.ini")!=0)
  1123.                         return;
  1124.  
  1125.                                                         //load findpath[0]\c--.ini
  1126.         if (findpath[0]!=0)
  1127.         {
  1128.                 sprintf(m1,"%s%s",findpath[0],name);
  1129.                 if (inih = fopen(m1,"rb"))
  1130.                 {_loadIni(inih);return;}
  1131.         }
  1132.                                                         //load PATH[i=0..end]/c--.ini
  1133.         char* pth = getenv("PATH");    
  1134.         if (pth != 0)
  1135.         {
  1136.                 char* start;
  1137.                 int size;
  1138.                 start = pth;   
  1139.                 while(*start)
  1140.                 {
  1141.                         size = 0;
  1142.                         char* endp = strchr(start, DIV_PATH);
  1143.                         size = (endp == 0)? strlen(start): endp-start;
  1144.                         strncpy(m1, start, size);
  1145.                         start += size + 1;
  1146.                         if (m1[size - 1] != DIV_FOLD)
  1147.                                 m1[size++] = '/';
  1148.                        
  1149.                         strcpy(m1 + size,"c--.ini");
  1150.                         if (inih = fopen(m1,"rb"))
  1151.                         {_loadIni(inih);return;}
  1152.                 }
  1153.         }
  1154. #ifdef _KOS_
  1155.                                                                 //for KolibriOS: load program_dir/c--.ini
  1156.         int p;
  1157.         strcpy(m1,__pgmname);
  1158.         p = strlen(m1);
  1159.         while ((*(m1+p)!='/') && (p != 0))
  1160.                 p--;
  1161.         if (p){
  1162.                 p++;
  1163.                 strcpy(m1+p,"c--.ini");
  1164.                 if (inih = fopen(m1,"rb"))
  1165.                 {_loadIni(inih);return;}
  1166.         }
  1167.                                                                 //for KolibriOS: load /sys/settings/c--.ini
  1168.         inih = fopen("/sys/settings/c--.ini","rb");
  1169.         for(;;){
  1170.                 if(fgets(m1,255,inih)==NULL)break;
  1171.                 if(SelectComand(m1,0)==c_end)BadCommandLine(m1);
  1172.         }
  1173.         fclose(inih);
  1174.         return;
  1175. #endif //_KOS_         
  1176. }
  1177.                        
  1178. /*****************************************************************************
  1179. * .NAME   : MALLOC
  1180. * .TITLE  : Âûäåëÿåò ïàìÿòü ñ îáðàáîòêîé îøèáîê.
  1181. *****************************************************************************/
  1182. void OutMemory()
  1183. {
  1184.         preerror("Compiler out of memory");
  1185.         exit(e_outofmemory);
  1186. }
  1187.  
  1188. void * MALLOC (unsigned long size)
  1189. {
  1190. void *mem;
  1191.         mem=malloc(size);
  1192.         if(mem==NULL)OutMemory();
  1193. #ifdef _UNIX_
  1194.         else memset(mem,0,size);
  1195. #endif
  1196.  
  1197. //      if(((unsigned long)mem+size)>maxusedmem)maxusedmem=(unsigned long)mem+size;
  1198.  
  1199.         return mem;
  1200. }
  1201.  
  1202. void *REALLOC(void *block,unsigned long size)
  1203. {
  1204. void *mem;
  1205.         mem=realloc(block,size);
  1206.         if(mem==NULL)OutMemory();
  1207.  
  1208. //      if(((unsigned long)mem+size)>maxusedmem)maxusedmem=(unsigned long)mem+size;
  1209.  
  1210.         return mem;
  1211. }
  1212.  
  1213. void IncludePath(char *buf)
  1214. {
  1215.         char divfold[3];
  1216.         sprintf(divfold,"%c",DIV_FOLD);
  1217.         if(numfindpath<MAXNUMPATH-1){
  1218.                 int len=strlen(buf);
  1219.                 if(buf[len-1]==DIV_FOLD)buf[len-1]=0;
  1220.                 else len++;
  1221.                 char *a=(char *)MALLOC(len+1);
  1222.                 strcpy(a,buf);
  1223.                 strcat(a,divfold);
  1224.                 findpath[numfindpath]=a;
  1225.                 numfindpath++;
  1226.                 findpath[numfindpath]="";
  1227.         }
  1228.         else puts("Too many include paths");
  1229. }
  1230.  
  1231. void doposts()
  1232. {
  1233. unsigned long addvalue,i,addval,addvalw32=0,addvalbss=0;
  1234.         if(splitdata&&modelmem==TINY&&outptrdata){
  1235.                 memcpy((char *)&output[outptr],(char *)&outputdata[0],outptrdata);
  1236.                 addval=outptr;
  1237.                 outptr+=outptrdata;
  1238.                 outptrdata=outptr;
  1239.         }
  1240.         addvalue=outptrdata;
  1241.         if(comfile==file_bin)addvalbss=addvalw32=ImageBase;
  1242.         else if(comfile==file_w32){
  1243.                 addvalbss=addvalw32=ImageBase+vsizeheader;
  1244.                 if(postsize&&wbss){
  1245.                         addvalw32+=Align(postsize,OBJECTALIGN);
  1246.                         addvalue=0;
  1247.                 }
  1248.         }
  1249.         else{
  1250.                 if((outptrdata%2)==1){  /* alignment of entire post data block manditory */
  1251.                         addvalue++;     //íà÷àëî íåèíèö.äàííûõ
  1252.                         postsize++;
  1253.                 }
  1254. /*              if(am32&&(outptrdata%4)==2){
  1255.                         addvalue+=2;    //íà÷àëî íåèíèö.äàííûõ
  1256.                         postsize+=2;
  1257.                 }*/
  1258.         }
  1259.         if(am32==0&&(MAXDATA-outptrdata)<postsize)preerror("post variable size exceeds size left in data segment");
  1260.         for(i=0;i<posts;i++){
  1261.                 switch((postbuf+i)->type){
  1262.                         case POST_VAR:
  1263.                                 *(short *)&output[(postbuf+i)->loc]+=(short)addvalue;
  1264.                                 break;
  1265.                         case POST_VAR32:
  1266.                                 *(long *)&output[(postbuf+i)->loc]+=addvalue+addvalbss;
  1267.                                 numrel++;
  1268.                                 break;
  1269.                         case FIX_VAR32:
  1270.                         case FIX_CODE32:
  1271.                                 *(long *)&output[(postbuf+i)->loc]+=addvalw32;
  1272.                                 numrel++;
  1273.                                 break;
  1274.                         case FIX_CODE_ADD:
  1275.                                 if(am32){
  1276.                                         *(long *)&output[(postbuf+i)->loc]+=addvalw32+(postbuf+i)->num;
  1277.                                         (postbuf+i)->type=(unsigned short)FIX_VAR32;
  1278.                                 }
  1279.                                 else{
  1280.                                         *(short *)&output[(postbuf+i)->loc]+=(short)(addval+(postbuf+i)->num);
  1281.                                         (postbuf+i)->type=(unsigned short)FIX_VAR;
  1282.                                 }
  1283.                                 numrel++;
  1284.                                 break;
  1285.                         case DATABLOCK_VAR:
  1286.                                 *(short *)&output[(postbuf+i)->loc]+=(short)addval;
  1287.                                 if(FixUp)(postbuf+i)->type=(unsigned short)FIX_VAR;
  1288.                                 break;
  1289.                         case DATABLOCK_VAR32:
  1290.                                 *(long *)&output[(postbuf+i)->loc]+=addval+addvalw32;
  1291.                                 if(FixUp)(postbuf+i)->type=(unsigned short)FIX_VAR32;
  1292.                                 numrel++;
  1293.                                 break;
  1294.                 }
  1295.         }
  1296.         ooutptr=addvalue;       //ñîõðàíèòü íà÷àëî post äëÿ debug;
  1297. }
  1298.  
  1299. void GetMemExeDat()
  1300. {
  1301.         if(outputdata==output&&outputdata!=0)outputdata=(unsigned char *)MALLOC((size_t)MAXDATA);
  1302. }
  1303.  
  1304.  
  1305.  
  1306. int writeoutput()
  1307. {
  1308. EXE_DOS_HEADER exeheader;  // header for EXE format
  1309.         if(fobj){
  1310.                 if(comfile==file_w32&&ocoff
  1311.        // Edited by Coldy
  1312.                         ||ocoff&&sobj)return MakeCoff();
  1313.                 return MakeObj();
  1314.         }
  1315.         if(comfile==file_w32)return MakePE();
  1316.         if(comfile==file_meos)return MakeMEOS();
  1317.         if(comfile==file_bin)return MakeBin32();
  1318.         memset(&exeheader,0,sizeof(EXE_DOS_HEADER));
  1319.         if(comfile==file_d32){
  1320.                 if(usestub){
  1321.                         MakeLE();
  1322.                         runfilesize+=ftell(hout)-32;
  1323.                         goto savecode;
  1324.                 }
  1325.                 else goto exefile;
  1326.         }
  1327.         if(comfile==file_com||comfile==file_sys||comfile==file_rom){
  1328.                 hout=CreateOutPut(outext,"wb");
  1329.                 if(fwrite(output+startptr,comfile==file_rom?romsize:outptr-startptr,1,hout)!=1){
  1330.                         ErrWrite();
  1331.                         return(-1);
  1332.                 }
  1333.         }
  1334.         else if(comfile==file_exe){
  1335. exefile:
  1336.                 hout=CreateOutPut(outext,"wb");
  1337.                 MakeExeHeader(&exeheader);
  1338.                 if(fwrite(&exeheader,sizeof(EXE_DOS_HEADER),1,hout)!=1){
  1339. errwr:
  1340.                         fclose(hout);
  1341.                         hout=NULL;
  1342.                         ErrWrite();
  1343.                         return(-1);
  1344.                 }
  1345.                 outputcodestart=ftell(hout);
  1346. savecode:
  1347.                 if(fwrite(output+startptr,outptr-startptr,1,hout)!=1)goto errwr;
  1348.                 if(modelmem==SMALL&&outptrdata!=0){
  1349.                         if(fwrite(outputdata,outptrdata,1,hout)!=1)goto errwr;
  1350.                 }
  1351.         }
  1352.         fclose(hout);
  1353.         hout=NULL;
  1354.         return(0);
  1355. }
  1356.  
  1357. long CopyFile(FILE *in,FILE *out)
  1358. {
  1359. char tbuf[1024];
  1360. long loads=0;
  1361. unsigned int len;
  1362.         do{
  1363.                 len=fread(tbuf,1,1024,in);
  1364.                 if(fwrite(tbuf,1,len,out)!=len){
  1365.                         ErrWrite();
  1366.                         return -1;
  1367.                 }
  1368.                 loads+=len;
  1369.         }while(len==1024);
  1370.         return loads;
  1371. }
  1372.  
  1373. unsigned int EntryPoint()
  1374. {
  1375. ITOK btok;
  1376. int bb=tk_id;
  1377. unsigned char bufmain[]="main";
  1378. unsigned char buf2[]="__startupproc";
  1379. unsigned char *buf;
  1380.         if(comfile==file_com)return startptr;
  1381.         btok.number=0;
  1382. //      if(jumptomain!=CALL_NONE||(comfile==file_w32&&dllflag))buf=buf2;
  1383. //      else buf=bufmain;
  1384.  
  1385.         if(jumptomain==CALL_NONE){
  1386.                 if(useDOS4GW)buf=buf2;
  1387.                 else buf=bufmain;
  1388.         }
  1389.         else buf=buf2;
  1390.  
  1391.         searchtree(&btok,&bb,buf);
  1392.         if(bb==tk_id){
  1393.                 if(comfile==file_w32&&dllflag)return 0xffffffff;
  1394.                 printf("Error! Entry point '%s' is not found.\n",buf);
  1395.                 exit(e_entrynotfound);
  1396.         }
  1397.         return btok.number;
  1398. }
  1399.  
  1400. void MakeExeHeader(EXE_DOS_HEADER *exeheader)
  1401. {
  1402. long paragraphsrequired;
  1403. unsigned short count,i;
  1404. int pointstart;
  1405.         exeheader->sign=0x5a4D;                          // MZ
  1406. //      if(modelmem==TINY&&comfile==file_exe)pointstart=0x100;
  1407. /*      else*/ pointstart=EntryPoint();
  1408.         count=(unsigned short)(runfilesize%512);
  1409.         i=(unsigned short)(runfilesize/512);
  1410.         exeheader->numlastbyte=count;
  1411.         exeheader->numpage=(unsigned short)(count==0?i:i+1);
  1412.         exeheader->headsize=2;          // size of header in paragraphs (2 paragraphs)
  1413.         exeheader->initIP=(unsigned short)pointstart;    // IP at entry (0x0000)
  1414.         paragraphsrequired=(outptr+outptrdata+postsize+stacksize+15)/16;
  1415.         if(modelmem==TINY&&comfile==file_exe){
  1416.                 exeheader->initSS=0xFFF0;                // displacement of SS
  1417.                 exeheader->initSP=0xFFFE; // intial value of SP
  1418.                 exeheader->initCS=0xfff0;                                                // displacement of CS (0x0000)
  1419.                 if(!resizemem){
  1420.                         exeheader->minmem=0xfff;        // min-paragraphs
  1421.                         exeheader->maxmem=0xffff;       // max-paragraphs
  1422.                 }
  1423.                 else{
  1424.                         paragraphsrequired-=0x10;
  1425.                         exeheader->initSP=(unsigned short)(paragraphsrequired*16); // intial value of SP
  1426.                         exeheader->minmem=(unsigned short)paragraphsrequired;   // min-paragraphs
  1427.                         exeheader->maxmem=(unsigned short)paragraphsrequired;   // max-paragraphs
  1428.                 }
  1429.         }
  1430.         else if(comfile==file_d32){
  1431.                 exeheader->initSP=(unsigned short)stacksize; // intial value of SP
  1432.                 exeheader->initSS=(unsigned short)((outptr+postsize+15)/16); // displacement of SS
  1433.                 exeheader->initCS=(unsigned short)((pointstart/65536)*4096);
  1434.                 if(resizemem){
  1435.                         exeheader->minmem=(unsigned short)paragraphsrequired;   // min-paragraphs
  1436.                         exeheader->maxmem=(unsigned short)paragraphsrequired;   // max-paragraphs
  1437.                 }
  1438.                 else exeheader->maxmem=(unsigned short)0xFFFF;  // max-paragraphs
  1439.         }
  1440.         else{
  1441.                 exeheader->initSS=(unsigned short)(outptr/16);           // displacement of SS
  1442.                 exeheader->initSP=(unsigned short)(outptrdata+postsize+stacksize); // intial value of SP
  1443.                 exeheader->minmem=(unsigned short)paragraphsrequired;   // min-paragraphs
  1444.                 exeheader->maxmem=(unsigned short)paragraphsrequired;   // max-paragraphs
  1445.         }
  1446.         exeheader->ofsreloc=0x1c;                                                // offset of first relocation item (0x0000)
  1447. }
  1448.  
  1449. void startsymbiosys(char *symfile)
  1450. {
  1451. unsigned int size;
  1452. int filehandle;
  1453. long filesize;
  1454.         outptr=startptr;
  1455.         if((filehandle=open(symfile,O_BINARY|O_RDONLY))==-1){;
  1456.                 ErrOpenFile(symfile);
  1457.                 exit(e_symbioerror);
  1458.         }
  1459.         if((filesize=getfilelen(filehandle))!=-1L){
  1460.                 if(filesize+outptr<MAXDATA){
  1461.                         size=filesize;
  1462.                         if((unsigned int)read(filehandle,output+outptr,size)!=size){
  1463.                                 close(filehandle);
  1464.                                 puts("Error reading symbio COM file.");
  1465.                                 exit(e_symbioerror);
  1466.                         }
  1467.                         outptr+=size;
  1468.                 }
  1469.                 else{
  1470.                         puts("Symbio COM file is too large.");
  1471.                         exit(e_symbioerror);
  1472.                 }
  1473.         }
  1474.         else{
  1475.                 puts("Unable to determine symbio COM file size.");
  1476.                 exit(e_symbioerror);
  1477.         }
  1478.         close(filehandle);
  1479.         outptrdata=outptr;
  1480.         outputcodestart=outptr-startptr;
  1481.         addconsttotree("__comsymbios",TRUE);
  1482. }
  1483.  
  1484. void BadCommandLine(char *str)
  1485. {
  1486.         printf("Unknown or bad command line option '%s'.\n",str);
  1487. //                                      PrintInfo(usage);
  1488.         exit(e_unknowncommandline);
  1489. }
  1490.  
  1491. void warnunused(struct idrec *ptr)
  1492. {
  1493. //static count=0;
  1494.         if(ptr!=NULL){
  1495.                 if(ptr->count==0&&startupfile!=ptr->file){
  1496.                         linenumber=ptr->line;
  1497.                         currentfileinfo=ptr->file;
  1498.                         int i=0;
  1499.                         switch(ptr->rectok){
  1500.                                 case tk_proc:
  1501.                                         if(ptr->recsegm!=NOT_DYNAMIC||strcmp(ptr->recid,mesmain)==0)break;
  1502.                                         i++;
  1503.                                 case tk_structvar:
  1504.                                         i++;
  1505.                                 case tk_charvar:
  1506.                                 case tk_bytevar:
  1507.                                 case tk_intvar:
  1508.                                 case tk_wordvar:
  1509.                                 case tk_longvar:
  1510.                                 case tk_dwordvar:
  1511.                                 case tk_floatvar:
  1512.                                 case tk_pointer:
  1513.                                 case tk_qword:
  1514.                                 case tk_double:
  1515.                                         if(i<=1&&(ptr->recpost==DYNAMIC_VAR||ptr->recpost==DYNAMIC_POST))break;
  1516.                                         warningnotused(ptr->recid,i);
  1517.                                         break;
  1518.                         }
  1519.                 }
  1520.                 warnunused(ptr ->left);
  1521.                 warnunused(ptr ->right);
  1522.         }
  1523. }
  1524.  
  1525. void WarnUnusedVar()//ïðåäóïðåæäåíèÿ î íåèñïîëüçîâàííûõ ïðîöåäóðàõ è ïåðåìåííûõ
  1526. {
  1527.         warnunused(treestart);
  1528.         for(unsigned int i=0;i<totalmodule;i++)warnunused((startfileinfo+i)->stlist);
  1529. }
  1530.  
  1531. void addinitvar()
  1532. {
  1533. unsigned int i;
  1534.         if(numfloatconst){      //âñòàâèòü êîíñòàíòû float è ïðèâÿçàòü èõ
  1535.                 if(alignword||optimizespeed)AlignCD(DS,chip>5?16:4);
  1536.                 for(i=0;i<posts;i++){
  1537.                         if((postbuf+i)->type==POST_FLOATNUM){
  1538.                                 if(am32)*(unsigned long *)&output[(postbuf+i)->loc]=outptrdata+(postbuf+i)->num;
  1539.                                 else *(unsigned short *)&output[(postbuf+i)->loc]=(unsigned short)(outptrdata+(postbuf+i)->num);
  1540.                                 if(FixUp)(postbuf+i)->type=FIX_VAR32;
  1541.                                 else killpost(i--);
  1542.                         }
  1543.                 }
  1544.                 for(i=0;i<numfloatconst;i++){
  1545.                         if(dbg&2){
  1546.                                 if((floatnum+i)->type==tk_float)sprintf((char *)string,"const float %f",(floatnum+i)->fnum);
  1547.                                 else sprintf((char *)string,"const double %f",(floatnum+i)->dnum);
  1548.                                 AddDataNullLine(4,(char *)string);
  1549.                         }
  1550.                         outdwordd((floatnum+i)->num[0]);
  1551.                         if((floatnum+i)->type!=tk_float){
  1552.                                 outdwordd((floatnum+i)->num[1]);
  1553.                                 datasize+=4;
  1554.                         }
  1555.                         datasize+=4;
  1556.                 }
  1557.                 free(floatnum);
  1558.                 numfloatconst=0;
  1559.                 floatnum=NULL;
  1560.         }
  1561.         for(i=0;i<(unsigned int)numswtable;i++){        //ñîçäàòü è âñòàâèòü òàáëèöû switch
  1562.                 int j;
  1563.                 FSWI *swt=swtables+i;
  1564.                 if(alignword)AlignCD(DS,swt->type);
  1565.                 if(dbg&2)AddDataNullLine((char)swt->type,"switch table address");
  1566.                 if(am32==FALSE){        //âñòàâèòü â êîä àäðåñ òàáëèöû
  1567.                         *(unsigned short *)&output[swt->ptb]=(unsigned short)outptrdata;
  1568.                 }
  1569.                 else *(unsigned long *)&output[swt->ptb]=outptrdata;
  1570.                 unsigned char oam32=am32;
  1571.                 am32=(unsigned char)(swt->type/2-1);
  1572.  
  1573.                 unsigned long val=swt->defal;
  1574.                 int oline=outptrdata;
  1575.                 for(j=0;j<swt->sizetab;j++){    //çàïîëíèòü òàáëèöó çíà÷åíèÿìè ïî óìîë÷àíèþ
  1576. //                      if((swt->info+jj)->type==singlcase)
  1577.                         AddReloc(DS);
  1578.                         if(am32)outdwordd(val);
  1579.                         else outwordd(val);
  1580.                 }
  1581.                 if(swt->mode==2){
  1582.                         if(dbg&2)AddDataNullLine((char)swt->razr,"switch table value");
  1583.                         if(oam32==FALSE){       //âñòàâèòü â êîä àäðåñ òàáëèöû
  1584.                                 *(unsigned short *)&output[swt->ptv]=(unsigned short)outptrdata;
  1585.                         }
  1586.                         else *(unsigned long *)&output[swt->ptv]=outptrdata;
  1587.                 }
  1588.                 int ii=0;       //ñ÷åò÷èê case
  1589.                 for(int jj=0;jj<swt->numcase;jj++){
  1590.                         j=(swt->info+jj)->value;        //çíà÷åíèå
  1591.                         val=(swt->info+jj)->postcase;
  1592.                         if((swt->info+jj)->type==singlcase){
  1593.                                 if(swt->mode==1){
  1594.                                         if(am32==FALSE)*(unsigned short *)&outputdata[oline+j*2]=(unsigned short)val;
  1595.                                         else *(unsigned long *)&outputdata[oline+j*4]=val;
  1596.                                 }
  1597.                                 else{
  1598.                                         if(am32==FALSE)*(unsigned short *)&outputdata[oline+ii*2]=(unsigned short)val;
  1599.                                         else *(unsigned long *)&outputdata[oline+ii*4]=val;
  1600.                                         switch(swt->razr){
  1601.                                                 case r8: opd(j); break;
  1602.                                                 case r16: outwordd(j); break;
  1603.                                                 case r32: outdwordd(j); break;
  1604.                                         }
  1605.                                         ii++;
  1606.                                 }
  1607.                         }
  1608.                         else{
  1609.                                 jj++;
  1610.                                 for(;(unsigned int)j<=(swt->info+jj)->value;j++){
  1611.                                         if(swt->mode==1){
  1612.                                                 if(am32==FALSE)*(unsigned short *)&outputdata[oline+j*2]=(unsigned short)val;
  1613.                                                 else *(unsigned long *)&outputdata[oline+j*4]=val;
  1614.                                         }
  1615.                                         else{
  1616.                                                 if(am32==FALSE)*(unsigned short *)&outputdata[oline+ii*2]=(unsigned short)val;
  1617.                                                 else *(unsigned long *)&outputdata[oline+ii*4]=val;
  1618.                                                 switch(swt->razr){
  1619.                                                         case r8: opd(j); break;
  1620.                                                         case r16: outwordd(j); break;
  1621.                                                         case r32: outdwordd(j); break;
  1622.                                                 }
  1623.                                                 ii++;
  1624.                                         }
  1625.                                 }
  1626.                         }
  1627.                 }
  1628.                 am32=oam32;
  1629.                 free(swt->info);
  1630.         }
  1631.         if(numswtable){
  1632.                 free(swtables);
  1633.                 numswtable=0;
  1634.         }
  1635.  
  1636.         for(i=0;i<posts;i++){
  1637.                 if((postbuf+i)->type==DIN_VAR||(postbuf+i)->type==DIN_VAR32){
  1638.                         idrec *ptr=(idrec *)(postbuf+i)->num;
  1639. //                      printf("post=%u num=%08X %s\n",ptr->recpost,ptr->recnumber,ptr->recid);
  1640.                         if(ptr->recpost==USED_DIN_VAR)setdindata(ptr,i);
  1641.                         else{
  1642.                                 if((postbuf+i)->type==DIN_VAR){
  1643.                                         *(unsigned short *)&output[(postbuf+i)->loc]+=(unsigned short)(ptr->recnumber);
  1644.                                 }
  1645.                                 else{
  1646. //                                      printf("loc=%08X num=%08X\n",*(unsigned long *)&output[(postbuf+i)->loc],ptr->recnumber);
  1647.                                         *(unsigned long *)&output[(postbuf+i)->loc]+=ptr->recnumber;
  1648.                                 }
  1649.                         }
  1650.                         if(FixUp)(postbuf+i)->type=(unsigned short)((postbuf+i)->type==DIN_VAR?FIX_VAR:FIX_VAR32);
  1651.                         else killpost(i--);
  1652.                 }
  1653.         }
  1654.         dopoststrings();
  1655. }
  1656.  
  1657. void setdindata(idrec *ptr,int i)
  1658. {
  1659. unsigned char *oldinput;
  1660. unsigned int oldinptr,oldendinptr;
  1661. unsigned char bcha;
  1662. unsigned int oline,ofile;
  1663. char *ostartline;
  1664.         if(alignword){
  1665.                 if(ptr->rectok==tk_structvar)alignersize+=AlignCD(DS,2);        //âûðîâíÿòü
  1666.                 else alignersize+=AlignCD(DS,GetVarSize(ptr->rectok));
  1667.         }
  1668. //      printf("loc=%08X out=%08X num=%08X\n",*(unsigned long *)&output[(postbuf+i)->loc],outptrdata,ptr->recnumber);
  1669.         if((postbuf+i)->type==DIN_VAR)*(unsigned short *)&output[(postbuf+i)->loc]+=(unsigned short)(outptrdata);
  1670.         else *(unsigned long *)&output[(postbuf+i)->loc]+=outptrdata;
  1671.         ptr->recpost=0;
  1672.         ptr->recnumber+=outptrdata;
  1673.         oline=linenum2;
  1674.         ofile=currentfileinfo;
  1675.         oldinput=input;
  1676.         oldinptr=inptr2;
  1677.         bcha=cha2;
  1678.         oldendinptr=endinptr;
  1679.         input=(unsigned char *)ptr->sbuf;
  1680.         inptr2=1;
  1681.         ostartline=startline;
  1682.         startline=(char*)input;
  1683.         cha2=input[0];
  1684.         linenum2=ptr->line;
  1685.         currentfileinfo=ptr->file;
  1686.         endinptr=strlen((char *)input);
  1687.         endinput=startline+endinptr;
  1688.         endoffile=0;
  1689.         tok=ptr->rectok;
  1690.         if(tok==tk_structvar)datasize+=initstructvar((structteg *)ptr->newid,ptr->recrm);
  1691.         else{
  1692. long type = 0,ssize = 0;
  1693. unsigned char typev = 0;
  1694.                 if(tok>=tk_charvar&&tok<=tk_doublevar){
  1695.                         type=tok-(tk_charvar-tk_char);
  1696.                         typev=variable;
  1697.                         ssize=typesize(type);
  1698.                 }
  1699.                 else if(tok==tk_pointer){
  1700.                         typev=pointer;
  1701.                         type=itok.type;
  1702.                         if(am32==FALSE&&((itok.flag&f_far)==0))ssize=2;
  1703.                         else ssize=4;
  1704.                 }
  1705.                 datasize+=initglobalvar(type,ptr->recsize/ssize,ssize,typev);
  1706.         }
  1707.         free(input);
  1708.         linenum2=oline;
  1709.         currentfileinfo=ofile;
  1710.         input=oldinput;
  1711.         inptr2=oldinptr;
  1712.         cha2=bcha;
  1713.         endinptr=oldendinptr;
  1714.         endoffile=0;
  1715.         startline=ostartline;
  1716. }
  1717.  
  1718. FILE *CreateOutPut(char *ext,char *mode)
  1719. {
  1720. char buf[256];
  1721. FILE *diskout;
  1722.     if(ext && strlen(ext)) {
  1723.         sprintf(buf,"%s.%s",rawfilename,ext);
  1724.     } else {
  1725.         strcpy(buf, rawfilename);
  1726.     }
  1727.    
  1728.         if((diskout=fopen(buf,mode))==NULL){
  1729.                 ErrOpenFile(buf);
  1730.                 exit(e_notcreateoutput);
  1731.         }
  1732.         return diskout;
  1733. }
  1734.  
  1735. int numundefclassproc=0;
  1736. idrec **undefclassproc;
  1737.  
  1738. void AddUndefClassProc()
  1739. {
  1740.         if(numundefclassproc==0)undefclassproc=(idrec **)MALLOC(sizeof(idrec **));
  1741.         else undefclassproc=(idrec **)REALLOC(undefclassproc,sizeof(idrec **)*(numundefclassproc+1));
  1742.         undefclassproc[numundefclassproc]=itok.rec;
  1743.         numundefclassproc++;
  1744. }
  1745.  
  1746. void CheckUndefClassProc()
  1747. {
  1748.         for(int i=0;i<numundefclassproc;i++){
  1749.                 idrec *ptr=undefclassproc[i];
  1750.                 if(ptr->rectok==tk_undefproc){
  1751.                         currentfileinfo=ptr->file;
  1752.                         linenumber=ptr->line;
  1753.                         thisundefined(ptr->recid);
  1754.                 }
  1755.         }
  1756. }
  1757.