home *** CD-ROM | disk | FTP | other *** search
/ Chip 1999 June / Chip_1999-06_cd.bin / ctenari / Kvarda / source / FILE_CPCONVERT.C < prev    next >
Encoding:
C/C++ Source or Header  |  1996-01-30  |  12.6 KB  |  447 lines

  1. /************************************************************************\
  2. *
  3. * MODULE    : FILE_CPCONVERT.C
  4. *
  5. * PROGRAMS  : CPCONV
  6. *
  7. * PURPOSE   : Conversion of source file in source encoding (code page)
  8. *             to target file in target encoding (code page) and 
  9. *             supporting variables and functions
  10. *
  11. \************************************************************************/
  12.  
  13. #include <windows.h>
  14. #include <stdio.h>
  15. #include <string.h>
  16.  
  17. #include "FILE_CPCONVERT.H"
  18. #include "CONV_SUB.H"
  19.  
  20. /************************************************************************\
  21. * Conversion mode setting
  22. *   DifferentTimeOnly=TRUE   convert only files with different date/time
  23. *                            (if Target<>Source)          
  24. \************************************************************************/
  25.  
  26. static int DifferentTimeOnly = FALSE;
  27.  
  28. void SetDifferentTimeOnly (BOOL different)
  29. {
  30.    DifferentTimeOnly=different;
  31. }
  32.  
  33. /************************************************************************\
  34. * Time mode setting
  35. *   current   set date/time of the target file to the current file
  36. *   original  set date/time of the target file to be the same as
  37. *             of the source (original) file
  38. \************************************************************************/
  39.  
  40. enum {original, current};
  41.  
  42. static int TimeMode = original;
  43. FILETIME CurrentTime;
  44.  
  45. void SetOriginalFileTime (void)
  46. {
  47.    TimeMode=original;
  48. }
  49.  
  50. void SetCurrentFileTime (void)
  51. {
  52.    TimeMode=current;
  53.    CoFileTimeNow(&CurrentTime);
  54. }
  55.  
  56. /************************************************************************\
  57. * Encoding setting
  58. *   EncDir    encoding directory (directory of the code page tables)
  59. *   CodePage  target code page
  60. \************************************************************************/
  61.  
  62. static char EncDir[_MAX_PATH];
  63. static char SourceCodePage[_MAX_FNAME]={"CP1250"};
  64. static char TargetCodePage[_MAX_FNAME]={"CP1250"};
  65.  
  66. void SetEncodingDirectory (char *directory)
  67. {
  68.    int n;
  69.    strncpy(EncDir,directory,_MAX_PATH);
  70.    EncDir[_MAX_PATH-1]='\0';
  71.    n=strlen(EncDir);
  72.    while (n>0 && EncDir[n]=='\\')
  73.      {
  74.       EncDir[n]='\0';
  75.       n--;
  76.      }
  77. }
  78.  
  79. void SetSourceCodePage (char *cp)
  80. {
  81.    strncpy (SourceCodePage,cp,_MAX_FNAME);
  82.    SourceCodePage[_MAX_FNAME-1]='\0';
  83. }
  84.  
  85. void SetTargetCodePage (char *cp)
  86. {
  87.    strncpy (TargetCodePage,cp,_MAX_FNAME);
  88.    TargetCodePage[_MAX_FNAME-1]='\0';
  89. }
  90.  
  91. /************************************************************************\
  92. * Directory for temporary files
  93. \************************************************************************/
  94.  
  95. static char TempDir[_MAX_PATH]={""};
  96.  
  97. /************************************************************************\
  98. * Conversion tables
  99. *   Conv0,nConv0    structure for creation of conversion table
  100. *   Conv            conversion character string for one-to-one conversion
  101. *   ConvTable,nChar conversion string table for one-to-more conversion
  102. *   DefChar         default replace character
  103. *   OneToMore       TRUE if one-to-more allowed
  104. *   UseTable        TRUE if one-to-more table has to be used
  105. *   Copy            TRUE if there is no difference between source and
  106. *                   target code page
  107. \************************************************************************/
  108.  
  109. static struct {
  110.    int  ischar;
  111.    char description[30];
  112.    char tchar;
  113.    char tstring[20];
  114.    BOOL set;
  115.   } Conv0[384];
  116.  
  117. static int nConv0=0;
  118.  
  119. static char Conv[258];
  120. static char ConvTable[256][20];
  121. static int  nChar[256];
  122.  
  123. static char DefChar=' ';
  124. static BOOL OneToMore=FALSE;
  125. static BOOL UseTable=FALSE; 
  126. static BOOL Copy=FALSE;
  127.  
  128. void SetOneToMoreConversion (BOOL onetomore)
  129. {
  130.    OneToMore=onetomore;
  131. }
  132.  
  133. void SetDefaultCharacter (char defchar)
  134. {
  135.    DefChar=defchar;
  136. }
  137.  
  138. /************************************************************************\
  139. *
  140. * FUNCTION    : InitConversionTable
  141. *
  142. * LOCAL VARS  : fname          - code page table filename
  143. *               f              - code page table file handle
  144. *               line           - buffer for code page table line
  145. *               description    - character description
  146. *               noaccentstring - string for character replace if there 
  147. *                                isn't target character
  148. *               ichar          - character code
  149. *
  150. \************************************************************************/
  151.  
  152. BOOL InitConversionTable (void)
  153. {
  154.    int  i,j,n,ichar;
  155.    char description[30],noaccentstring[20],line[100];
  156.    char fname[_MAX_FNAME];
  157.    FILE *f;
  158.  
  159. // check if source and target CP are different
  160.  
  161.    if (stricmp(SourceCodePage,TargetCodePage)==0)
  162.      {
  163.       Copy=TRUE;
  164.       printf("\n Warning: Source and target code page are the same.");
  165.      }
  166.     
  167.    if (GetTempPath((DWORD)sizeof(TempDir),TempDir)==0)
  168.       return (FALSE);
  169.  
  170. // source code page reading
  171.  
  172.    strcat(strcat(strcat(strcpy(fname,EncDir),"\\"),SourceCodePage),".ENC");
  173.    f=fopen(fname,"rt");
  174.    if (f==NULL)
  175.      {
  176.       printf("\n Error: Unable to find %s",fname);
  177.       return(FALSE);
  178.      }
  179.    while(!feof(f))
  180.      {
  181.       if (fgets(line,100,f)==NULL)
  182.          break;
  183.       if (line[0]==';')
  184.          continue;
  185.       line[99]='\0';
  186.       memset(description,0,30);
  187.       sscanf(line,"%d %s",&ichar,description);
  188.       if (strlen(description)<1)
  189.          continue;
  190.       Conv0[nConv0].ischar=ichar;
  191.       strcpy(Conv0[nConv0].description,description);
  192.       Conv0[nConv0].tchar=DefChar;
  193.       memset(Conv0[nConv0].tstring,0,20);
  194.       Conv0[nConv0].tstring[0]=DefChar;
  195.       Conv0[nConv0].set=FALSE;
  196.       nConv0++;
  197.      }
  198.    fclose(f);
  199.  
  200. // target code page table reading and assignment to the source
  201. // code page characters  
  202.  
  203.    strcat(strcat(strcat(strcpy(fname,EncDir),"\\"),TargetCodePage),".ENC");
  204.    f=fopen(fname,"rt");
  205.    if (f==NULL)
  206.      {
  207.       printf("\nError: Unable to find %s",fname);
  208.       return (FALSE);
  209.      }
  210.    while(!feof(f))
  211.      {
  212.       if (fgets(line,100,f)==NULL)
  213.          break;
  214.       if (line[0]==';')
  215.          continue;
  216.       line[99]='\0';
  217.       memset(description,0,30);
  218.       sscanf(line,"%d %s",&ichar,description);
  219.       if (strlen(description)<1)
  220.          continue;
  221.       for(i=0; i<nConv0; i++)
  222.         {
  223.          if (Conv0[i].set==TRUE)
  224.             continue;
  225.          if (strcmp(description,Conv0[i].description)==0)
  226.            {
  227.             Conv0[i].tchar=(char)ichar; 
  228.             Conv0[i].tstring[0]=(char)ichar;
  229.             Conv0[i].set=TRUE;
  230.             break;
  231.            }
  232.         }
  233.      }
  234.    fclose(f);
  235.  
  236. // not-accented strings assignment to source code page characters
  237. // if there is no other assignment
  238.  
  239.    strcat(strcpy(fname,EncDir),"\\ACCENT.CONV");
  240.    f=fopen(fname,"rt");
  241.    if (f==NULL)
  242.      {
  243.       printf("\n Warning: Unable to find %s."
  244.              "\n          Remaining accented characters cannot be replaced"
  245.              "\n          by non-accented characters.",fname);
  246.       goto finish;
  247.      }
  248.    while(!feof(f))
  249.      {
  250.       if (fgets(line,100,f)==NULL)
  251.          break;
  252.       if (line[0]==';')
  253.          continue;
  254.       line[99]='\0';
  255.       memset(description,0,30);
  256.       memset(noaccentstring,0,20);
  257.       sscanf(line,"%s %s",description,noaccentstring);
  258.       if (strlen(description)<1)
  259.          continue;
  260.       for (i=0; i<nConv0; i++)
  261.         {
  262.          if (Conv0[i].set==TRUE)
  263.             continue; 
  264.          if (strcmp(description,Conv0[i].description)==0)
  265.            {
  266.             n=strlen(noaccentstring);
  267.             if (n==1)
  268.               {
  269.                Conv0[i].tchar=noaccentstring[0];
  270.                Conv0[i].tstring[0]=noaccentstring[0];
  271.                Conv0[i].set=TRUE;
  272.               }
  273.             else if (n>1 && OneToMore)
  274.               {
  275.                strcpy(Conv0[i].tstring,noaccentstring);
  276.                UseTable=TRUE;
  277.                Conv0[i].set=TRUE;
  278.               }
  279.            }
  280.         }
  281.      }
  282.    fclose(f);
  283.  
  284. // finishing file conversion tables
  285.  
  286. finish:
  287.    if (UseTable)
  288.      {
  289.       for (i=0; i<256; i++)
  290.         {
  291.          ConvTable[i][0]=(char)i;
  292.          ConvTable[i][1]='\0';
  293.          nChar[i]=1;
  294.         }
  295.       for (i=0; i<nConv0; i++)
  296.         {
  297.          j=Conv0[i].ischar;
  298.          strcpy(ConvTable[j],Conv0[i].tstring);
  299.          nChar[j]=strlen(ConvTable[j]);
  300.         }
  301.      }
  302.    else
  303.      {
  304.       BOOL Convert=FALSE;
  305.       for (i=0; i<256; i++)
  306.          Conv[i]=(char)i;
  307.       Conv[256]='\0';
  308.       for (i=0; i<nConv0; i++)
  309.         {
  310.          j=Conv0[i].ischar;
  311.          if (Conv[j]!=Conv0[i].tchar)
  312.            {
  313.             Convert=TRUE;
  314.             Conv[j]=Conv0[i].tchar;
  315.            }
  316.         }
  317.       if (Convert==FALSE)
  318.          Copy=TRUE;
  319.      }
  320.  
  321.    return (TRUE);
  322. }
  323.  
  324. /************************************************************************\
  325. *
  326. * FUNCTION    : ConvertFile
  327. *
  328. * INPUTS      : SourceDir  - source file name
  329. *               TargetDir  - target file name
  330. *
  331. * RETURNS     : None
  332. *
  333. * LOCAL VARS  : hSFile         - source file handle
  334. *               hTFile         - target file handle
  335. *               hTempFile      - temporary file handle
  336. *               TempName       - temporary file name
  337. *               stime          - source file time
  338. *               ttime          - target file time
  339. *               buff           - buffer
  340. *               dwBytesRead    - number of read bytes
  341. *               dwBytesWritten - number of written bytes
  342. *               dwPos          - file pointer
  343. *
  344. \************************************************************************/
  345.  
  346. void ConvertFile(char *SFileName, char *TFileName)
  347. {
  348.    HANDLE hSFile, hTFile, hTempFile;
  349.    char TempName[_MAX_FNAME];
  350.    char buff[16384];
  351.    DWORD dwBytesRead,dwBytesWritten,dwPos;
  352.    FILETIME stime,ttime;
  353.    int i,j;
  354.  
  355.    hSFile= CreateFile(SFileName,GENERIC_READ,0,
  356.                       (LPSECURITY_ATTRIBUTES) NULL,OPEN_EXISTING,
  357.                       FILE_ATTRIBUTE_NORMAL,(HANDLE)NULL);
  358.    if (hSFile==INVALID_HANDLE_VALUE)
  359.       return;
  360.    GetFileTime(hSFile,NULL,NULL,&stime);
  361.  
  362.    if (DifferentTimeOnly && stricmp(SFileName,TFileName)!=0)
  363.      {
  364.       hTFile= CreateFile(TFileName,GENERIC_READ,0,
  365.                          (LPSECURITY_ATTRIBUTES) NULL,OPEN_EXISTING,
  366.                          FILE_ATTRIBUTE_NORMAL,(HANDLE)NULL);
  367.       if (hTFile!=INVALID_HANDLE_VALUE)
  368.         {
  369.          GetFileTime(hTFile,NULL,NULL,&ttime);
  370.          CloseHandle(hTFile);
  371.  
  372.          if (stime.dwLowDateTime==ttime.dwLowDateTime &&
  373.             stime.dwHighDateTime==ttime.dwHighDateTime)
  374.          return;
  375.         }
  376.      }
  377.  
  378.    if (Copy)
  379.      {
  380.       CloseHandle(hSFile);
  381.       CopyFile(SFileName,TFileName,FALSE);
  382.       printf("\n     Copied target file: %s", TFileName);
  383.       goto settime;
  384.      }
  385.  
  386.    if (GetTempFileName(TempDir,"CPC",0,TempName)==0)
  387.       return;
  388.    hTempFile= CreateFile(TempName,GENERIC_WRITE,0,
  389.                          (LPSECURITY_ATTRIBUTES)NULL,CREATE_ALWAYS,
  390.                          FILE_ATTRIBUTE_NORMAL,(HANDLE)NULL);
  391.    if (hTempFile==INVALID_HANDLE_VALUE)
  392.       return;
  393.  
  394.    do 
  395.      {
  396.       if (ReadFile(hSFile, (LPSTR)buff, 16384, &dwBytesRead, NULL)) 
  397.         {
  398.          if (!UseTable)
  399.            { 
  400.             for (i=0; i<(int)dwBytesRead; i++)
  401.               {
  402.                j=(int)buff[i];
  403.                if (j<0)
  404.                   j+=256; 
  405.                buff[i]=Conv[j];
  406.               }
  407.             dwPos=SetFilePointer(hTempFile,0,(LPLONG)NULL,FILE_END);
  408.             LockFile(hTempFile,dwPos,0,dwPos+dwBytesRead,0);
  409.             WriteFile(hTempFile,(LPSTR)buff,dwBytesRead,&dwBytesWritten,NULL);
  410.             UnlockFile(hTempFile,dwPos,0,dwPos+dwBytesRead,0);
  411.            }
  412.          else
  413.            {
  414.             for (i=0; i<(int)dwBytesRead; i++)
  415.               {
  416.                j=(int)buff[i];
  417.                if (j<0)
  418.                   j+=256;
  419.                WriteFile(hTempFile,(LPSTR)ConvTable[j],nChar[j],
  420.                          &dwBytesWritten,NULL);
  421.               }
  422.            }
  423.         }
  424.      }
  425.    while (dwBytesRead==16384);
  426.    CloseHandle(hSFile);
  427.    CloseHandle(hTempFile);
  428.  
  429.    CopyFile(TempName,TFileName,FALSE);
  430.    DeleteFile(TempName);
  431.    printf("\n  Converted target file: %s", TFileName);
  432.  
  433. settime:
  434.    hTFile= CreateFile(TFileName,GENERIC_WRITE,0,
  435.                       (LPSECURITY_ATTRIBUTES) NULL,OPEN_EXISTING,
  436.                       FILE_ATTRIBUTE_NORMAL,(HANDLE)NULL);
  437.    if (hTFile==INVALID_HANDLE_VALUE)
  438.       return;
  439.    if (TimeMode==current)
  440.       SetFileTime(hTFile,NULL,NULL,&CurrentTime);
  441.    else
  442.       SetFileTime(hTFile,NULL,NULL,&stime);
  443.    CloseHandle(hTFile);
  444.    return;
  445. }
  446.  
  447.