WSxM_header.C

Go to the documentation of this file.
00001 /***********************************************************************
00002 *
00003 *       File Name: WSxM_header.C
00004 *
00005 *       Description: functions for managing the WSxM_HEADER structure defined in Header.h
00006 *
00007 ***********************************************************************/
00008 
00009 /* this is not a main PlugIn file and here is no Docu to scan...
00010 % PlugInModuleIgnore
00011 */
00012 
00013 #include <malloc.h>
00014 #include <string.h>
00015 #include <stdlib.h>
00016 #include <math.h>
00017 #include <ctype.h>
00018 #include "WSxM_header.h"
00019 
00020 // Define the max. number of chars in a header argument if not done in WSxM_io.C
00021 #ifndef WSXM_MAXCHARS
00022 #define WSXM_MAXCHARS 1000
00023 #endif
00024 
00025 /***********************************************************************
00026 *
00027 *       FileIdStruc FileId[]
00028 *
00029 *       Description: Used for identification of the file type
00030 *
00031 ***********************************************************************/
00032 
00033 FileIdStruc FileId[] = {
00034     // name, aliasname, id-tag, suffix
00035     {0, "SPM Image", "Topography", "SxM Image file\n", ".top", "-TOPO"}
00036     ,
00037     {1, "SPM Movie", "Topography Movie", "Movie Image file\n", ".mpp", "-MOVIE"}
00038     ,
00039     {2, "CITS File", "Current Imaging Tunneling Spectroscopy", "CITS Image file\n", ".cit", "-CITS"}
00040     ,
00041     {3, "IV File", "IV Curve", "IV curve file\n", ".iv.cur", "-IV"}
00042     ,
00043     {4, "IZ File", "IZ Curve", "IZ curve file\n", ".iz.cur", "-IZ"}
00044     ,
00045     {5, "ZV File", "ZV Curve", "ZV curve file\n", ".zv.cur", "-ZV"}
00046     ,
00047     {6, "FZ File", "FZ Curve", "FZ curve file\n", ".fz.cur", "-FZ"}
00048     ,
00049     {7, "Generic Curves", "Generic Curve", "Generic curve file\n", ".curve", "-generic"}
00050     ,
00051     {8, NULL, NULL, NULL, NULL}
00052 };
00053 
00054 /***********************************************************************
00055 *
00056 *       Function void HeaderInit (WSxM_HEADER *pHeader);
00057 *
00058 *       Description: Initializes the values of the WSxM_HEADER structure. It should
00059 *                    be called always before using any of the other functions
00060 *
00061 ***********************************************************************/
00062 
00063 void HeaderInit(WSxM_HEADER * pHeader)
00064 {
00065     if (pHeader == NULL)
00066         return;
00067 
00068     pHeader->tszTitles = NULL;
00069     pHeader->tszLabels = NULL;
00070     pHeader->tszValues = NULL;
00071 
00072     pHeader->iNumFields = 0;
00073 }
00074 
00075 /***********************************************************************
00076 *
00077 *       Function int HeaderRead (WSxM_HEADER *pHeader, FILE *pFile);
00078 *
00079 *       Description: Reads a WSxM_HEADER from a file. It is important that the file
00080 *                    should have been opened for reading, and the WSxM_HEADER should
00081 *                    have been initializated calling HeaderInit
00082 *
00083 *       Inputs:
00084 *                       - pHeader: pointer to the WSxM_HEADER object to store the data in
00085 *                       - pFile: File pointer to read the header from
00086 *
00087 *       Outputs:
00088 *                       - pHeader: will be filled with the data read from pFile
00089 *                       - pFile: the file pointer will go to the end of the header
00090 *
00091 *       Return value:
00092 *                       0 if the header was correctly read, -1 elsewhere
00093 *
00094 ***********************************************************************/
00095 
00096 int HeaderRead(WSxM_HEADER * pHeader, FILE * pFile)
00097 {
00098     int iStatus = 0;
00099 
00100     if ((pHeader == NULL) || (pFile == NULL))
00101         return -1;
00102 
00103     if (pHeader->iNumFields != 0)
00104         return -1;
00105 
00106     /* Read the file line by line */
00107 
00108     while (iStatus == 0) {
00109         iStatus = HeaderReadLine(pHeader, pFile);
00110     }
00111 
00112     if (iStatus == -1) {        /* Error */
00113         return -1;
00114     }
00115 
00116     return 0;
00117 }
00118 
00119 /* Header write */
00120 
00121 /***********************************************************************
00122 *
00123 *       Function int HeaderWrite (WSxM_HEADER *pHeader, FILE *pFile);
00124 *
00125 *       Description: Writes the WSxM_HEADER object to a file. It is important that the file
00126 *                    should have been opened for writing (not append).
00127 *
00128 *       Inputs:
00129 *                       - pHeader: pointer to the WSxM_HEADER object with the data
00130 *                       - pFile: File pointer to write the data header
00131 *
00132 *
00133 *       Return value:
00134 *                       0 if the header was correctly write, -1 elsewhere
00135 *
00136 ***********************************************************************/
00137 
00138 int HeaderWrite(WSxM_HEADER * pHeader, FILE * pFile)
00139 {
00140     int i, j;
00141     char *pCharAux;             /* for swapping in bubble sort */
00142     char szAuxTitle[100], szAuxLabel[100], szAuxValue[WSXM_MAXCHARS];   /* for writting in file        */
00143 
00144     /* sorts the WSxM_HEADER object by title and label using bubble sort algorithm */
00145 
00146     for (i = 0; i < pHeader->iNumFields; i++) {
00147         for (j = 0; j < (pHeader->iNumFields - i - 1); j++) {
00148             if ((strcmp(pHeader->tszTitles[j], pHeader->tszTitles[j + 1]) >
00149                  0)
00150                 ||
00151                 (strcmp(pHeader->tszTitles[j], pHeader->tszTitles[j + 1])
00152                  == 0)
00153                 &&
00154                 (strcmp(pHeader->tszLabels[j], pHeader->tszLabels[j + 1]) >
00155                  0)) {
00156                 /* the element j is bigger than j+1 one so we swap them    */
00157                 /* we must swap the elements j and j+1 in the three arrays */
00158 
00159                 /* swaps the titles */
00160                 pCharAux = pHeader->tszTitles[j];
00161                 pHeader->tszTitles[j] = pHeader->tszTitles[j + 1];
00162                 pHeader->tszTitles[j + 1] = pCharAux;
00163 
00164                 /* swaps the labels */
00165                 pCharAux = pHeader->tszLabels[j];
00166                 pHeader->tszLabels[j] = pHeader->tszLabels[j + 1];
00167                 pHeader->tszLabels[j + 1] = pCharAux;
00168 
00169                 /* swaps the values */
00170                 pCharAux = pHeader->tszValues[j];
00171                 pHeader->tszValues[j] = pHeader->tszValues[j + 1];
00172                 pHeader->tszValues[j + 1] = pCharAux;
00173             }
00174         }
00175     }
00176 
00177     /* writes the pre-header info in the file */
00178     fprintf(pFile, "%s", TEXT_COPYRIGHT_NANOTEC);
00179     fprintf(pFile, "%s", STM_IMAGE_FILE_ID);
00180     fprintf(pFile, "%s%d\n", IMAGE_HEADER_SIZE_TEXT,
00181             HeaderGetSize(pHeader));
00182 
00183     /* In the first time there is no previous title */
00184     strcpy(szAuxTitle, "");
00185 
00186     /* writes all the fields in the file */
00187     for (i = 0; i < pHeader->iNumFields; i++) {
00188         /* if the title is diferent than the previous one we write the title in the file */
00189         if (strcmp(szAuxTitle, pHeader->tszTitles[i]) != 0) {
00190             /* Special characteres in the title */
00191             strcpy(szAuxTitle, pHeader->tszTitles[i]);
00192             ReplaceStringInString(szAuxTitle, "\\", "\\\\");
00193             ReplaceStringInString(szAuxTitle, "\r\n", "\\n");
00194 
00195             /* writes the title in the file */
00196             fprintf(pFile, "\n[%s]\n\n", szAuxTitle);
00197         }
00198 
00199         /* Special characteres in the label */
00200         strcpy(szAuxLabel, pHeader->tszLabels[i]);
00201         ReplaceStringInString(szAuxLabel, "\\", "\\\\");
00202         ReplaceStringInString(szAuxLabel, "\r\n", "\\n");
00203 
00204         /* Special characteres in the value */
00205         strcpy(szAuxValue, pHeader->tszValues[i]);
00206         ReplaceStringInString(szAuxValue, "\\", "\\\\");
00207         ReplaceStringInString(szAuxValue, "\r\n", "\\n");
00208         RemoveLeftAndRightWhitesFromString(szAuxValue);
00209 
00210         /* writes the label and the value in the file */
00211         fprintf(pFile, "    %s: %s\n", szAuxLabel, szAuxValue);
00212     }
00213 
00214     /* writes the header end */
00215     fprintf(pFile, "\n[%s]\n", IMAGE_HEADER_END_TEXT);
00216 
00217     return 0;
00218 }
00219 
00221 int HeaderWrite(WSxM_HEADER * pHeader, FILE * pFile, gchar * cType)
00222 {
00223     int i, j;
00224     char *pCharAux;             /* for swapping in bubble sort */
00225     char szAuxTitle[100], szAuxLabel[100], szAuxValue[WSXM_MAXCHARS];   /* for writting in file        */
00226     FileIdStruc *FileIdPtr = FileId;
00227     /* sorts the WSxM_HEADER object by title and label using bubble sort algorithm */
00228 
00229     for (i = 0; i < pHeader->iNumFields; i++) {
00230         for (j = 0; j < (pHeader->iNumFields - i - 1); j++) {
00231             if ((strcmp(pHeader->tszTitles[j], pHeader->tszTitles[j + 1]) >
00232                  0)
00233                 ||
00234                 (strcmp(pHeader->tszTitles[j], pHeader->tszTitles[j + 1])
00235                  == 0)
00236                 &&
00237                 (strcmp(pHeader->tszLabels[j], pHeader->tszLabels[j + 1]) >
00238                  0)) {
00239                 /* the element j is bigger than j+1 one so we swap them    */
00240                 /* we must swap the elements j and j+1 in the three arrays */
00241 
00242                 /* swaps the titles */
00243                 pCharAux = pHeader->tszTitles[j];
00244                 pHeader->tszTitles[j] = pHeader->tszTitles[j + 1];
00245                 pHeader->tszTitles[j + 1] = pCharAux;
00246 
00247                 /* swaps the labels */
00248                 pCharAux = pHeader->tszLabels[j];
00249                 pHeader->tszLabels[j] = pHeader->tszLabels[j + 1];
00250                 pHeader->tszLabels[j + 1] = pCharAux;
00251 
00252                 /* swaps the values */
00253                 pCharAux = pHeader->tszValues[j];
00254                 pHeader->tszValues[j] = pHeader->tszValues[j + 1];
00255                 pHeader->tszValues[j + 1] = pCharAux;
00256             }
00257         }
00258     }
00259 
00260     /* writes the pre-header info in the file */
00261     fprintf(pFile, "%s", TEXT_COPYRIGHT_NANOTEC);
00262     for (; FileIdPtr->name != 0; ++FileIdPtr) {
00263         if (strstr(FileIdPtr->name, cType)) {
00264             fprintf(pFile, "%s", FileIdPtr->fileidtag);
00265         }
00266     }
00267     fprintf(pFile, "%s%d\n", IMAGE_HEADER_SIZE_TEXT,
00268             HeaderGetSize(pHeader));
00269 
00270     /* In the first time there is no previous title */
00271     strcpy(szAuxTitle, "");
00272 
00273     /* writes all the fields in the file */
00274     for (i = 0; i < pHeader->iNumFields; i++) {
00275         /* if the title is diferent than the previous one we write the title in the file */
00276         if (strcmp(szAuxTitle, pHeader->tszTitles[i]) != 0) {
00277             /* Special characteres in the title */
00278             strcpy(szAuxTitle, pHeader->tszTitles[i]);
00279             ReplaceStringInString(szAuxTitle, "\\", "\\\\");
00280             ReplaceStringInString(szAuxTitle, "\r\n", "\\n");
00281 
00282             /* writes the title in the file */
00283             fprintf(pFile, "\n[%s]\n\n", szAuxTitle);
00284         }
00285 
00286         /* Special characteres in the label */
00287         strcpy(szAuxLabel, pHeader->tszLabels[i]);
00288         ReplaceStringInString(szAuxLabel, "\\", "\\\\");
00289         ReplaceStringInString(szAuxLabel, "\r\n", "\\n");
00290 
00291         /* Special characteres in the value */
00292         strcpy(szAuxValue, pHeader->tszValues[i]);
00293         ReplaceStringInString(szAuxValue, "\\", "\\\\");
00294         ReplaceStringInString(szAuxValue, "\r\n", "\\n");
00295         RemoveLeftAndRightWhitesFromString(szAuxValue);
00296 
00297         /* writes the label and the value in the file */
00298         fprintf(pFile, "    %s: %s\n", szAuxLabel, szAuxValue);
00299     }
00300 
00301     /* writes the header end */
00302     fprintf(pFile, "\n[%s]\n", IMAGE_HEADER_END_TEXT);
00303 
00304     return 0;
00305 }
00306 
00307 /* Header access to one field */
00308 
00309 /* Read */
00310 
00311 /***********************************************************************
00312 *
00313 *       Function double HeaderGetAsNumber (WSxM_HEADER *pHeader, char *szTitle, char *szLabel);
00314 *
00315 *       Description: gets the title-label couple value as a number from the 
00316 *               WSxM_HEADER object, the WSxM_HEADER should have been initializated
00317 *               calling HeaderInit
00318 *
00319 *       Inputs: 
00320 *               - pHeader: pointer to the WSxM_HEADER object
00321 *               - szTitle: title of the field to be accesed
00322 *               - szLabel: label of the field to be accesed
00323 *
00324 *       Return value:
00325 *                       a double with the title-label couple value, 0 on error
00326 *
00327 ***********************************************************************/
00328 
00329 double HeaderGetAsNumber(WSxM_HEADER * pHeader, char *szTitle,
00330                          char *szLabel)
00331 {
00332     char szValue[WSXM_MAXCHARS] = "";   // the default size of 100 should be okey, but to be consistent ..
00333     if (HeaderGetAsString(pHeader, szTitle, szLabel, szValue) != 0) {   /* error */
00334         return 0;
00335     }
00336     return atof(szValue);
00337 }
00338 
00339 /***********************************************************************
00340 *
00341 *       Function int HeaderGetAsString (WSxM_HEADER *pHeader, char *szTitle, char *szLabel, char *szValue);
00342 *
00343 *       Description: gets the title-label couple value as a string from the 
00344 *               WSxM_HEADER object
00345 *
00346 *       Inputs:
00347 *               - pHeader: pointer to the WSxM_HEADER object
00348 *               - szTitle: title of the field to be accesed
00349 *               - szLabel: label of the field to be accesed
00350 *
00351 *       Outputs:
00352 *               - szValue: will be filled with the title-label couple value as a string
00353 *                 (this must be allocated)
00354 *
00355 *       Return value:
00356 *               0 if the value was correctly accessed, -1 elsewhere
00357 *
00358 ***********************************************************************/
00359 
00360 int HeaderGetAsString(WSxM_HEADER * pHeader, char *szTitle, char *szLabel,
00361                       char *szValue)
00362 {
00363     int iIndex;
00364 
00365     /* seeks the title-label couple */
00366     for (iIndex = 0; iIndex < pHeader->iNumFields; iIndex++) {
00367         if ((strcmp(szTitle, pHeader->tszTitles[iIndex]) == 0)
00368             && (strcmp(szLabel, pHeader->tszLabels[iIndex]) == 0)) {
00369             /* title-label couple found at position iIndex */
00370             break;
00371         }
00372     }
00373 
00374     if (iIndex == pHeader->iNumFields) {
00375         /* the for loop didn't found the title-label couple in WSxM_HEADER object */
00376         return -1;
00377     }
00378 
00379     /* asign the value of the title-label couple to the pointer szValue */
00380     strcpy(szValue, pHeader->tszValues[iIndex]);
00381 
00382     /* access succesful */
00383     return 0;
00384 }
00385 
00386 /***********************************************************************
00387 *
00388 *       Function void HeaderReadTitle (char *szLine, char *szTitle);
00389 *
00390 *       Description: reads a title from a line
00391 *
00392 *       Inputs:
00393 *               - szLine: line with the title
00394 *
00395 *       Outputs:
00396 *               - szTitle: title readed from the line (this must be allocated),
00397 *                 szTitle=="" if there is no title in the line.
00398 *
00399 *       Return value:
00400 *               none
00401 *
00402 ***********************************************************************/
00403 
00404 void HeaderReadTitle(char *szLine, char *szTitle)
00405 {
00406     int iIndex = 0;
00407 
00408     /* If the line don't begin by a left square bracket it isn't a title line */
00409     if (szLine[0] != '[') {
00410         strcpy(szTitle, "");
00411         return;
00412     }
00413 
00414     /* we seek the right square bracket */
00415     while (szLine[iIndex] != ']') {
00416         iIndex++;
00417     }
00418 
00419     /* at this point iIndex is the position of the right square bracket */
00420 
00421     /* szLine[1] to skip the left square bracket */
00422     strncpy(szTitle, &szLine[1], iIndex - 1);
00423     szTitle[iIndex - 1] = '\0';
00424 }
00425 
00426 /***********************************************************************
00427 *
00428 *       Function void HeaderReadLabel (szLine, szLabel);
00429 *
00430 *       Description: reads a label from a line
00431 *
00432 *       Inputs:
00433 *               - szLine: line with the label
00434 *
00435 *       Outputs:
00436 *               - szLabel: label readed from the line (this must be allocated),
00437 *                 szValue=="" if there is no label in the line.
00438 *
00439 *       Return value:
00440 *               none
00441 *
00442 ***********************************************************************/
00443 
00444 void HeaderReadLabel(char *szLine, char *szLabel)
00445 {
00446     unsigned int iIndex = 0;
00447 
00448     /* we seek the ':' character */
00449     while (szLine[iIndex] != ':') {
00450         if (iIndex == strlen(szLine)) {
00451             /* there is no label in this line */
00452             strcpy(szLabel, "");
00453             return;
00454         }
00455         iIndex++;
00456     }
00457 
00458     /* at this point iIndex is the position of the ':' character */
00459 
00460     /* we copy the label from the line */
00461     strncpy(szLabel, szLine, iIndex);
00462     szLabel[iIndex] = '\0';
00463 }
00464 
00465 /***********************************************************************
00466 *
00467 *       Function void HeaderReadValue (char *szLine, char *szValue);
00468 *
00469 *       Description: reads a value from a line
00470 *
00471 *       Inputs:
00472 *               - szLine: line with the value
00473 *
00474 *       Outputs:
00475 *               - szLabel: value readed from the line (this must be allocated),
00476 *                 szValue=="" if there is no value in the line.
00477 *
00478 *       Return value:
00479 *               none
00480 *
00481 ***********************************************************************/
00482 
00483 void HeaderReadValue(char *szLine, char *szValue)
00484 {
00485     unsigned int iIndex = 0;
00486 
00487     /* we seek the ':' character and skip the blank after */
00488     while (szLine[iIndex] != ':') {
00489         if (iIndex == strlen(szLine)) {
00490             /* there is no value in this line */
00491             strcpy(szValue, "");
00492             return;
00493         }
00494         iIndex++;
00495     }
00496 
00497     /* skips the ': ' */
00498     iIndex += 2;
00499 
00500     /* at this point iIndex is the position of the first value character */
00501 
00502     /* szLine[iIndex] to skip the line before ': ' and -1 not to copy return carriage */
00503     strncpy(szValue, &szLine[iIndex], strlen(szLine) - iIndex - 1);
00504     szValue[strlen(szLine) - iIndex - 1] = '\0';
00505 }
00506 
00507 /* Write */
00508 
00509 /***********************************************************************
00510 *
00511 *       Function void HeaderSetAsFloating (WSxM_HEADER *pHeader, char *szTitle, char *szLabel, double lfValue);
00512 *
00513 *       Description: sets a title-label couple value in double format to the
00514 *               WSxM_HEADER object
00515 *
00516 *       Inputs:
00517 *               - pHeader: pointer to the WSxM_HEADER object to set the value in
00518 *               - szTitle: title of the field to be set
00519 *               - szLabel: label of the field to be set
00520 *               - lfValue: value to be set
00521 *
00522 *       Return value:
00523 *               none
00524 *
00525 ***********************************************************************/
00526 
00527 void HeaderSetAsFloating(WSxM_HEADER * pHeader, char *szTitle,
00528                          char *szLabel, double lfValue)
00529 {
00530     char szValue[WSXM_MAXCHARS] = "";
00531 
00532     /* converts the double value to a string value */
00533     sprintf(szValue, "%.61f", lfValue);
00534 
00535     /* sets the value in the WSxM_HEADER object as a string */
00536     HeaderSetAsString(pHeader, szTitle, szLabel, szValue);
00537 }
00538 
00539 /***********************************************************************
00540 *
00541 *       Function void HeaderSetAsInt (WSxM_HEADER *pHeader, char *szTitle, char *szLabel, int iValue);
00542 *
00543 *       Description: sets a title-label couple value in int format to the
00544 *               WSxM_HEADER object
00545 *
00546 *       Inputs:
00547 *               - pHeader: pointer to the WSxM_HEADER object to set the value in
00548 *               - szTitle: title of the field to be set
00549 *               - szLabel: label of the field to be set
00550 *               - iValue: value to be set
00551 *
00552 *       Return value:
00553 *               none
00554 *
00555 ***********************************************************************/
00556 
00557 void HeaderSetAsInt(WSxM_HEADER * pHeader, char *szTitle, char *szLabel,
00558                     int iValue)
00559 {
00560     char szValue[WSXM_MAXCHARS] = "";
00561 
00562     /* converts the int value to a string value */
00563     sprintf(szValue, "%d", iValue);
00564 
00565     /* sets the value in the WSxM_HEADER object as a string */
00566     HeaderSetAsString(pHeader, szTitle, szLabel, szValue);
00567 }
00568 
00569 /***********************************************************************
00570 *
00571 *       Function void HeaderSetAsInt (WSxM_HEADER *pHeader, char *szTitle, char *szLabel, int iValue);
00572 *
00573 *       Description: sets a title-label couple value in string format to the
00574 *               WSxM_HEADER object
00575 *
00576 *       Inputs:
00577 *                       - pHeader: pointer to the WSxM_HEADER object to set the value in
00578 *                       - szTitle: title of the field to be set
00579 *           - szLabel: label of the field to be set
00580 *           - szValue: string value to be set
00581 *
00582 *       Return value:
00583 *                       none
00584 *
00585 ***********************************************************************/
00586 
00587 void HeaderSetAsString(WSxM_HEADER * pHeader, char *szTitle, char *szLabel,
00588                        char *szValue)
00589 {
00590     int iIndex;
00591 
00592     /* sets the value in the WSxM_HEADER object */
00593 
00594     /* seeks the title-label couple */
00595     for (iIndex = 0; iIndex < pHeader->iNumFields; iIndex++) {
00596         if ((strcmp(szTitle, pHeader->tszTitles[iIndex]) == 0)
00597             && (strcmp(szLabel, pHeader->tszLabels[iIndex]) == 0)) {
00598             /* title-label couple found at position iIndex */
00599             /* updates the title-label couple value */
00600             pHeader->tszValues[iIndex] =
00601                 (char *) realloc(pHeader->tszValues[iIndex],
00602                                  (strlen(szValue) + 1) * sizeof(char));
00603             strcpy(pHeader->tszValues[iIndex], szValue);
00604 
00605             return;
00606         }
00607     }
00608 
00609     /* title-label couple not found, is a new field */
00610     HeaderAddValue(pHeader, szTitle, szLabel, szValue);
00611 }
00612 
00613 /***********************************************************************
00614 *
00615 *       Function void HeaderDestroy (WSxM_HEADER *pHeader);
00616 *
00617 *       Description: frees all the allocated memory in the Header
00618 *
00619 ***********************************************************************/
00620 
00621 void HeaderDestroy(WSxM_HEADER * pHeader)
00622 {
00623     int i;                      /* Counter */
00624 
00625     if (pHeader->iNumFields == 0) {     /* No need to destroy */
00626         return;
00627     }
00628 
00629     for (i = 0; i < pHeader->iNumFields; i++) {
00630         free(pHeader->tszTitles[i]);
00631         free(pHeader->tszLabels[i]);
00632         free(pHeader->tszValues[i]);
00633     }
00634 
00635     free(pHeader->tszTitles);
00636     free(pHeader->tszLabels);
00637     free(pHeader->tszValues);
00638 
00639     pHeader->tszTitles = NULL;
00640     pHeader->tszLabels = NULL;
00641     pHeader->tszValues = NULL;
00642 
00643     pHeader->iNumFields = 0;
00644 }
00645 
00646 /* Internally used functions */
00647 
00648 /***********************************************************************
00649 *
00650 *       Function int HeaderReadLine (WSxM_HEADER *pHeader, FILE *pFile);
00651 *
00652 *       Description: Reads a text line from a file. It is important that the file
00653 *                    should have been opened for reading, and the WSxM_HEADER should
00654 *                    have been initializated calling HeaderInit
00655 *
00656 *       Inputs:
00657 *               - pHeader: pointer to the WSxM_HEADER object to store the data in
00658 *               - pFile: File pointer to read the header from
00659 *
00660 *       Outputs:
00661 *               - pHeader: will be filled with the data read from pFile
00662 *               - pFile: the file pointer will go to the end of the header
00663 *
00664 *       Return value:
00665 *               0 if the header was correctly read, -1 elsewhere
00666 *
00667 ***********************************************************************/
00668 
00669 int HeaderReadLine(WSxM_HEADER * pHeader, FILE * pFile)
00670 {
00671     /* multiplication in the string sizes is because the string can grow later */
00672 
00673     static char szTitle[WSXM_MAXCHARS * 2] = "";
00674     char szLine[WSXM_MAXCHARS * 2];
00675     char szTryTitle[WSXM_MAXCHARS * 2];
00676     char szLabel[WSXM_MAXCHARS * 2];
00677     char szValue[WSXM_MAXCHARS * 2];
00678     char *szReturn;
00679 
00680     szReturn = fgets(szLine, WSXM_MAXCHARS, pFile);
00681 
00682     if (szReturn == NULL)
00683         return -1;              /* File Error */
00684 
00685     /* Line read. We see the data it has */
00686 
00687     RemoveLeftAndRightWhitesFromString(szLine);
00688 
00689     /* Special characteres */
00690 
00691     ReplaceStringInString(szLine, "\\n", "\r\n");
00692     ReplaceStringInString(szLine, "\\\\", "\\");
00693 
00694     /* We try to read a label-value couple */
00695 
00696     HeaderReadLabel(szLine, szLabel);
00697     HeaderReadValue(szLine, szValue);
00698 
00699     /* We try to read it as a title */
00700 
00701     HeaderReadTitle(szLine, szTryTitle);
00702 
00703     if (strlen(szTryTitle) > 0) {       /* It is a title */
00704         /* If it indicates the header end, we will return 1 */
00705 
00706         if (strcmp(szTryTitle, IMAGE_HEADER_END_TEXT) == 0)
00707             return 1;
00708         else {
00709             strcpy(szTitle, szTryTitle);
00710             return 0;
00711         }
00712     }
00713 
00714     /* If it is not a header field (we have not read any title yet) we ignore it */
00715 
00716     if (strlen(szTitle) == 0) {
00717         return 0;
00718     }
00719 
00720     /* If it is not a couple label: value, we don't mind about this line */
00721 
00722     if (strlen(szLabel) != 0) {
00723         /* We have a new value. We add it to the header */
00724 
00725         HeaderAddValue(pHeader, szTitle, szLabel, szValue);
00726     }
00727 
00728     return 0;
00729 }
00730 
00731 /***********************************************************************
00732 *
00733 *       Function int HeaderGetSize (WSxM_HEADER *pHeader);
00734 *
00735 *       Description: Gets the size of the image header in the file.
00736 *
00737 *       Inputs:
00738 *               - pHeader: pointer to the WSxM_HEADER object end of the header
00739 *
00740 *       Return value:
00741 *               the size of the header, -1 on error
00742 *
00743 ***********************************************************************/
00744 
00745 int HeaderGetSize(WSxM_HEADER * pHeader)
00746 {
00747     int i;
00748     int iSize = 0;              /* size at this moment                        */
00749     int iNumOfTitles = 0;       /* Number of titles written in the file       */
00750     int iNumDigits;             /* Number of digits for the image header size */
00751     char szTitle[100] = "", szLabel[100], szValue[WSXM_MAXCHARS];
00752 
00753     /* size of the pre-header and the carriage return */
00754     iSize =
00755         sizeof(TEXT_COPYRIGHT_NANOTEC) + sizeof(STM_IMAGE_FILE_ID) +
00756         sizeof(IMAGE_HEADER_SIZE_TEXT);
00757 
00758     /* size of all the fields in the HEADER object */
00759     for (i = 0; i < pHeader->iNumFields; i++) {
00760         /* if there is a new title we increase the number of titles and adds its size */
00761         if (strcmp(szTitle, pHeader->tszTitles[i]) != 0) {
00762             strcpy(szTitle, pHeader->tszTitles[i]);
00763             iNumOfTitles++;
00764             iSize += strlen(szTitle);
00765         }
00766 
00767         strcpy(szLabel, pHeader->tszLabels[i]);
00768 
00769         /* Special characteres in the szLabel string */
00770         ReplaceStringInString(szLabel, "\\n", "\r\n");
00771         ReplaceStringInString(szLabel, "\\\\", "\\");
00772 
00773         strcpy(szValue, pHeader->tszValues[i]);
00774 
00775         /* Special characteres in the szValue string */
00776         ReplaceStringInString(szValue, "\\n", "\r\n");
00777         ReplaceStringInString(szValue, "\\\\", "\\");
00778         RemoveLeftAndRightWhitesFromString(szValue);
00779 
00780         /* adds the size of the label and the value */
00781         iSize += strlen(szLabel) + strlen(szValue);
00782     }
00783 
00784     /* adds the size of the square brackets (2 bytes), the carriage return (3*2 bytes  */
00785     /* for each title)                                                                 */
00786     iSize += iNumOfTitles * (6 + 2);
00787 
00788     /* adds the size of the carriage return (2 bytes for each label) and the blanks (6 bytes for each label) */
00789     iSize += pHeader->iNumFields * (6 + 2);
00790 
00791     /* adds the size of the header end text, the square brackets and the carriage return */
00792     iSize += sizeof(IMAGE_HEADER_END_TEXT) + 2 + 4;
00793 
00794     /* adds the size of the characteres for the image header size in pre-header */
00795     iNumDigits = (int) floor(log10(iSize)) + 1;
00796     iSize += iNumDigits;
00797     if (iNumDigits != (int) floor((log10(iSize)) + 1))
00798         iSize++;
00799 
00800     return iSize;
00801 }
00802 
00803 /***********************************************************************
00804 *
00805 *       Function int HeaderAddValue (WSxM_HEADER *pHeader, char *szTitle, char *szLabel,char *szValue);
00806 *
00807 *       Description: adds the tripla title-label-value to the WSxM_HEADER object
00808 *
00809 *       Inputs:
00810 *               - pHeader: pointer to the WSxM_HEADER object to store the data in
00811 *               - szTitle: title of the field to be added
00812 *               - szLabel: label of the field to be added
00813 *               - szValue: string value to be added
00814 *
00815 *       Return value:
00816 *               0 if the header was correctly updated, -1 elsewhere
00817 *
00818 ***********************************************************************/
00819 
00820 int HeaderAddValue(WSxM_HEADER * pHeader, char *szTitle, char *szLabel,
00821                    char *szValue)
00822 {
00823     /* grows the three arrays for the new title-label-value tripla */
00824     pHeader->tszTitles =
00825         (char **) realloc(pHeader->tszTitles,
00826                           (pHeader->iNumFields + 1) * sizeof(char *));
00827     pHeader->tszLabels =
00828         (char **) realloc(pHeader->tszLabels,
00829                           (pHeader->iNumFields + 1) * sizeof(char *));
00830     pHeader->tszValues =
00831         (char **) realloc(pHeader->tszValues,
00832                           (pHeader->iNumFields + 1) * sizeof(char *));
00833 
00834     /* adds the title in the last position of the titles array allocating memory */
00835     pHeader->tszTitles[pHeader->iNumFields] =
00836         (char *) calloc(strlen(szTitle) + 1, sizeof(char));
00837     if (pHeader->tszTitles[pHeader->iNumFields] == NULL) {      /* error */
00838         return -1;
00839     }
00840     strcpy(pHeader->tszTitles[pHeader->iNumFields], szTitle);
00841 
00842     /* adds the label in the last position of the labels array allocating memory */
00843     pHeader->tszLabels[pHeader->iNumFields] =
00844         (char *) calloc(strlen(szLabel) + 1, sizeof(char));
00845     if (pHeader->tszLabels[pHeader->iNumFields] == NULL) {      /* error */
00846         /* frees the memory allocated in this function */
00847         free(pHeader->tszTitles[pHeader->iNumFields]);
00848 
00849         return -1;
00850     }
00851     strcpy(pHeader->tszLabels[pHeader->iNumFields], szLabel);
00852 
00853     /* adds the value in the last position of the values array allocating memory */
00854     pHeader->tszValues[pHeader->iNumFields] =
00855         (char *) calloc(strlen(szValue) + 1, sizeof(char));
00856     if (pHeader->tszValues[pHeader->iNumFields] == NULL) {      /* error */
00857         /* frees the memory allocated in this function */
00858         free(pHeader->tszTitles[pHeader->iNumFields]);
00859         free(pHeader->tszLabels[pHeader->iNumFields]);
00860 
00861         return -1;
00862     }
00863     strcpy(pHeader->tszValues[pHeader->iNumFields], szValue);
00864 
00865     /* increments the number of fields */
00866     pHeader->iNumFields++;
00867 
00868     return 0;
00869 }
00870 
00871 /***********************************************************************
00872 *
00873 *       Function void RemoveLeftAndRightWhitesFromString (char *szString);
00874 *
00875 *       Description: removes the white-space characteres (0x09, 0x0D or 0x20)
00876 *               at the right and left of the string szString.
00877 *
00878 *       Inputs:
00879 *                       - szString: the string we want to remove the white-space characteres
00880 *
00881 *   Outputs:
00882 *           - szString: the string without white-space character
00883 *
00884 *       Return value:
00885 *                       none
00886 *
00887 ***********************************************************************/
00888 
00889 void RemoveLeftAndRightWhitesFromString(char *szString)
00890 {
00891     char szAuxString[WSXM_MAXCHARS];
00892     int iIndex = 0;
00893 
00894     /* Seeks the first non white-space character (0x09, 0x0D or 0x20) */
00895     while (isspace(szString[iIndex])) {
00896         iIndex++;
00897     }
00898 
00899     /* We copy the string without white-space characters at the left */
00900     strcpy(szAuxString, &szString[iIndex]);
00901 
00902     /* Seeks the last non white-space character (0x09, 0x0D or 0x20) */
00903     iIndex = strlen(szAuxString);
00904     while (isspace(szString[iIndex])) {
00905         iIndex--;
00906     }
00907 
00908     /* Puts the zero (mark of end of string) after the last non white-space character */
00909     szString[iIndex + 1] = '\0';
00910 
00911     /* We copy the new szString without white-space characters */
00912     strcpy(szString, szAuxString);
00913 }
00914 
00915 /***********************************************************************
00916 *
00917 *       Function void ReplaceStringInString (char *szDest, const char *szOld, const char *szNew);
00918 *
00919 *       Description: replaces instances of the substring szOld with 
00920 *               instances of the string szNew.
00921 *
00922 *       Inputs:
00923 *               - szDest: the string where will be made the replacemets
00924 *               - szOld: the substring to be replaced by lpszNew
00925 *               - szNew: the substring replacing lpszOld
00926 *
00927 *      Outputs:
00928 *               - szDest: the string with the replacements
00929 *
00930 *      Return value:
00931 *               none
00932 *
00933 ***********************************************************************/
00934 
00935 void ReplaceStringInString(char *szDest, const char *szOld,
00936                            const char *szNew)
00937 {
00938     int iIndex = 0, iAuxStringIndex = 0;
00939     char szAuxString[WSXM_MAXCHARS];
00940     strcpy(szAuxString, "");
00941     /* We copy the string with the replacements to the auxiliar string */
00942 
00943     /* Searches for the substring szOld */
00944     while (szDest[iIndex] != '\0') {    /* while not end of string */
00945         if (strncmp(&szDest[iIndex], szOld, strlen(szOld)) == 0) {
00946             /* Writes the substring szNew in the substring szOld position */
00947             strcpy(&szAuxString[iAuxStringIndex], szNew);
00948             iAuxStringIndex += strlen(szNew);
00949             iIndex += strlen(szOld);
00950         } else {
00951             /* We copy the character without any change */
00952             szAuxString[iAuxStringIndex] = szDest[iIndex];
00953             iAuxStringIndex++;
00954             iIndex++;
00955         }
00956     }
00957 
00958     /* Puts the zero (mark of end of string) to the auxiliar string */
00959     szAuxString[iAuxStringIndex] = '\0';
00960 
00961     /* We copy the new string to szDest */
00962     strcpy(szDest, szAuxString);
00963 }

Generated on Sat Apr 1 09:04:28 2006 for GXSM by  doxygen 1.4.6