Subversion Repositories Kolibri OS

Rev

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

  1. //visual text comparer
  2. //by den po - jdp@bk.ru
  3.  
  4. #define MEMSIZE 1024 * 60
  5. #define ENTRY_POINT #main
  6. #include "../lib/fs.h"
  7. #include "../lib/strings.h"
  8. #include "../lib/obj/console.h"
  9.  
  10. #define MAX_PATH 260
  11.  
  12. #include "32user32.h"
  13. #include "objects.h"
  14. #include "diff_gui.h"
  15.  
  16. #define mincmpstrings 2
  17. #define maxcmpstrings 10
  18. #define maxcmpoffset  100
  19.  
  20. char window_title[] = "Kolibri Diff tool (Visual Text Comparer)";
  21.  
  22. char* srcfilename;
  23. char* dstfilename;
  24. dword srcfile;
  25. dword dstfile;
  26. dword srcfilesize;
  27. dword dstfilesize;
  28. TCollection srcfilelines; //file lines
  29. TCollection dstfilelines;
  30. TCollection srcfilenums; //lines numbers
  31. TCollection dstfilenums;
  32.  
  33. struct TSimpleCollection:TSortedCollection
  34. {
  35.   TSimpleCollection();
  36.   int  Compare( int Key1, Key2 );
  37. };
  38. int TSimpleCollection::Compare( int Key1, Key2 ){
  39.   return Key1-Key2;
  40. }
  41. TSimpleCollection::TSimpleCollection():TSortedCollection(1000,1000);
  42. {
  43.   comparemethod=#Compare;
  44. }
  45.  
  46. TSimpleCollection diffs;   //list of differing strings
  47. dword srcfilelinks;     //pointer to the previos line with the same first symbol
  48. dword dstfilelinks;     //
  49.  
  50. getstrings(dword srcfile,srcfilesize,srcfilelines){
  51.   ECX=srcfilesize;
  52.   ESI=srcfile;
  53.   WHILE(ECX){
  54.         $push ECX,ESI
  55.         EAX=srcfilelines;
  56.         EAX.TCollection.Insert(ESI);
  57.         $pop ESI,ECX
  58.         WHILE(ECX){
  59.           $cld $lodsb ECX--;
  60.           if(AL==0x0D)||(AL==0x0A)DSBYTE[ESI-1]=0;
  61.           if(AL==0x0D)&&(DSBYTE[ESI]==0x0A){$lodsb;ECX--;}
  62.           if(AL==0x0D)||(AL==0x0A)BREAK;
  63.         }
  64.   }
  65. }
  66.  
  67. #include "if.h"
  68.  
  69. bool getparam()
  70. {
  71.         int i, param_len = strlen(#param);
  72.         if (param[0]=='"') {
  73.                 for (i=1; i<param_len; i++) if (param[i]=='"') param[i]=NULL;
  74.                 srcfilename = #param + 1;
  75.                 dstfilename = #param + strlen(#param) + 3;
  76.                 return true;
  77.         }
  78.         notify("'Wrong params! Use format:\nAPPPATH \"PARAM1\" \"PARAM2\"' -E");
  79.         return false;
  80. }
  81.  
  82. main(){
  83.         mem_init();
  84.         if (param[0]) getparam();
  85.         if (!srcfilename) || (!dstfilename) gui(); else console();
  86. }
  87.  
  88. console() {
  89.         int i;
  90.         int p;
  91.         int bs,bd,bsc,bdc,bsp,bdp;
  92.         int cache[256];
  93.         char s1;
  94.         int s2;
  95.  
  96.         read_file(srcfilename, #srcfile, #srcfilesize);
  97.         read_file(dstfilename, #dstfile, #dstfilesize);
  98.  
  99.         if (!srcfile) die("'First file not found' -E");
  100.         if (!dstfile) die("'Second file not found' -E");
  101.        
  102.         srcfilelines.TCollection(srcfilesize/40,8192);
  103.         dstfilelines.TCollection(dstfilesize/40,8192);
  104.         //fill line pointers
  105.         getstrings(srcfile,srcfilesize,#srcfilelines);
  106.         getstrings(dstfile,dstfilesize,#dstfilelines);
  107.         srcfilenums.TCollection(srcfilelines.Count,1000);
  108.         dstfilenums.TCollection(dstfilelines.Count,1000);
  109.  
  110.         srcfilelinks=malloc(srcfilelines.Count*4);
  111.         dstfilelinks=malloc(dstfilelines.Count*4);
  112.  
  113.         //fill links on the next strings with the same first symbols
  114.         FillMemory(#cache,sizeof(cache),-1); i=srcfilelines.Count;
  115.         WHILE(i){
  116.           i--;
  117.           EBX=srcfilelines.At(i); EBX=DSBYTE[EBX];
  118.           DSDWORD[i<<2+srcfilelinks]=cache[EBX*4];
  119.           cache[EBX*4]=i;
  120.         }
  121.         FillMemory(#cache,sizeof(cache),-1); i=dstfilelines.Count;
  122.         WHILE(i){
  123.           i--;
  124.           EBX=dstfilelines.At(i); EBX=DSBYTE[EBX];
  125.           DSDWORD[i<<2+dstfilelinks]=cache[EBX*4];
  126.           cache[EBX*4]=i;
  127.         }
  128.  
  129.         diffs.TSimpleCollection();
  130.  
  131.         while( bsp < srcfilelines.Count ) || ( bdp < dstfilelines.Count )
  132.         {
  133.           ////////////////////////////////////////////////////////
  134.           bsc=0;
  135.           p=dstfilelines.At(bdp);//current dst position
  136.           s1=DSBYTE[p];
  137.           bs=bsp+1;//foundĀ src line, bsc - number of matched
  138.           while( bs != -1 )//no next line starting with the same symbols
  139.                  &&(bs-bsp<=maxcmpoffset)//check for 100 lines depth
  140.                  &&(bs<srcfilelines.Count)
  141.           {
  142.                 s2=srcfilelines.At(bs);
  143.                 if(!strcmp(p,s2))
  144.                 {//line found
  145.                   bsc=1;
  146.                   WHILE(bsc<maxcmpstrings)//counting number of matching lines
  147.                          &&(bdp+bsc<dstfilelines.Count)
  148.                          &&(bs+bsc<srcfilelines.Count)
  149.                          &&(!strcmp(dstfilelines.At(bdp+bsc),srcfilelines.At(bs+bsc)))bsc++;
  150.                   BREAK;
  151.                 }
  152.                 if(DSBYTE[s2]==s1)bs=DSDWORD[bs<<2+srcfilelinks];else bs++;
  153.           }
  154.           bdc=0;
  155.           p=srcfilelines.At(bsp);//current src position
  156.           s1=DSBYTE[p];
  157.           bd=bdp+1;//foundĀ dst line, bsc - number of matched
  158.           while( bd != -1 )//no next line starting with the same symbols
  159.                  &&(bd-bdp<=maxcmpoffset)//check for 100 lines depth
  160.                  &&(bd<dstfilelines.Count)
  161.           {
  162.                 s2=dstfilelines.At(bd);
  163.                 if(!strcmp(p,s2))
  164.                 {
  165.                   bdc=1;
  166.                   WHILE(bdc<maxcmpstrings)//counting number of matching lines
  167.                          &&(bsp+bdc<srcfilelines.Count)
  168.                          &&(bd+bdc<dstfilelines.Count)
  169.                          &&(!strcmp(srcfilelines.At(bsp+bdc),dstfilelines.At(bd+bdc)))bdc++;
  170.                   BREAK;
  171.                 }
  172.                 if(DSBYTE[s2]==s1)bd=DSDWORD[bd<<2+dstfilelinks];else bd++;
  173.           }
  174.  
  175.           if(bsc<bdc)
  176.            if(bd-bdp<bdc)
  177.            ||(bdc>=mincmpstrings)
  178.           {
  179.                 WHILE(bdp<bd){
  180.                   diffs.Insert(srcfilenums.Count);
  181.                   srcfilenums.Insert(-1); dstfilenums.Insert(bdp); bdp++;
  182.                 }
  183.                 continue;
  184.           }
  185.  
  186.           if(strcmp(srcfilelines.At(bsp),dstfilelines.At(bdp)))diffs.Insert(srcfilenums.Count);
  187.           //lines are equal
  188.           srcfilenums.Insert(bsp); bsp++;
  189.           dstfilenums.Insert(bdp); bdp++;
  190.           CONTINUE;
  191.         }
  192.  
  193.         free(srcfilelinks);
  194.         free(dstfilelinks);
  195.  
  196.         if(!diffs.Count)
  197.                 notify("'Nothing to compare' -E");
  198.         else ifinit();
  199.  
  200.         con_exit stdcall (0);
  201.         diffs.DeleteAll();        delete diffs;
  202.         dstfilenums.DeleteAll();  delete dstfilenums;
  203.         srcfilenums.DeleteAll();  delete srcfilenums;
  204.         dstfilelines.DeleteAll(); delete dstfilelines;
  205.         srcfilelines.DeleteAll(); delete srcfilelines;
  206.         free(dstfile);
  207.         free(srcfile);
  208. }
  209.