Leptonica  1.82.0
Image processing and image analysis suite
regutils.c
Go to the documentation of this file.
1 /*====================================================================*
2  - Copyright (C) 2001 Leptonica. All rights reserved.
3  -
4  - Redistribution and use in source and binary forms, with or without
5  - modification, are permitted provided that the following conditions
6  - are met:
7  - 1. Redistributions of source code must retain the above copyright
8  - notice, this list of conditions and the following disclaimer.
9  - 2. Redistributions in binary form must reproduce the above
10  - copyright notice, this list of conditions and the following
11  - disclaimer in the documentation and/or other materials
12  - provided with the distribution.
13  -
14  - THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
15  - ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
16  - LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
17  - A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL ANY
18  - CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
19  - EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
20  - PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
21  - PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
22  - OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
23  - NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
24  - SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
25  *====================================================================*/
26 
27 
68 #ifdef HAVE_CONFIG_H
69 #include <config_auto.h>
70 #endif /* HAVE_CONFIG_H */
71 
72 #include <string.h>
73 #include "allheaders.h"
74 
75 extern l_int32 NumImageFileFormatExtensions;
76 extern const char *ImageFileFormatExtensions[];
77 
78 static char *getRootNameFromArgv0(const char *argv0);
79 
80 
81 /*--------------------------------------------------------------------*
82  * Regression test utilities *
83  *--------------------------------------------------------------------*/
122 l_ok
123 regTestSetup(l_int32 argc,
124  char **argv,
125  L_REGPARAMS **prp)
126 {
127 char *testname, *vers;
128 char errormsg[64];
129 L_REGPARAMS *rp;
130 
131  PROCNAME("regTestSetup");
132 
133  if (argc != 1 && argc != 2) {
134  snprintf(errormsg, sizeof(errormsg),
135  "Syntax: %s [ [compare] | generate | display ]", argv[0]);
136  return ERROR_INT(errormsg, procName, 1);
137  }
138 
139  if ((testname = getRootNameFromArgv0(argv[0])) == NULL)
140  return ERROR_INT("invalid root", procName, 1);
141 
142  setLeptDebugOK(1); /* required for testing */
143 
144  rp = (L_REGPARAMS *)LEPT_CALLOC(1, sizeof(L_REGPARAMS));
145  *prp = rp;
146  rp->testname = testname;
147  rp->index = -1; /* increment before each test */
148 
149  /* Initialize to true. A failure in any test is registered
150  * as a failure of the regression test. */
151  rp->success = TRUE;
152 
153  /* Make sure the lept/regout subdirectory exists */
154  lept_mkdir("lept/regout");
155 
156  /* Only open a stream to a temp file for the 'compare' case */
157  if (argc == 1 || !strcmp(argv[1], "compare")) {
158  rp->mode = L_REG_COMPARE;
159  rp->tempfile = stringNew("/tmp/lept/regout/regtest_output.txt");
160  rp->fp = fopenWriteStream(rp->tempfile, "wb");
161  if (rp->fp == NULL) {
162  rp->success = FALSE;
163  return ERROR_INT("stream not opened for tempfile", procName, 1);
164  }
165  } else if (!strcmp(argv[1], "generate")) {
166  rp->mode = L_REG_GENERATE;
167  lept_mkdir("lept/golden");
168  } else if (!strcmp(argv[1], "display")) {
169  rp->mode = L_REG_DISPLAY;
170  rp->display = TRUE;
171  } else {
172  LEPT_FREE(rp);
173  snprintf(errormsg, sizeof(errormsg),
174  "Syntax: %s [ [generate] | compare | display ]", argv[0]);
175  return ERROR_INT(errormsg, procName, 1);
176  }
177 
178  /* Print out test name and both the leptonica and
179  * image library versions */
180  lept_stderr("\n////////////////////////////////////////////////\n"
181  "//////////////// %s_reg ///////////////\n"
182  "////////////////////////////////////////////////\n",
183  rp->testname);
184  vers = getLeptonicaVersion();
185  lept_stderr("%s : ", vers);
186  LEPT_FREE(vers);
187  vers = getImagelibVersions();
188  lept_stderr("%s\n", vers);
189  LEPT_FREE(vers);
190 
191  rp->tstart = startTimerNested();
192  return 0;
193 }
194 
195 
208 l_ok
210 {
211 char result[512];
212 char *results_file; /* success/failure output in 'compare' mode */
213 char *text, *message;
214 l_int32 retval;
215 size_t nbytes;
216 
217  PROCNAME("regTestCleanup");
218 
219  if (!rp)
220  return ERROR_INT("rp not defined", procName, 1);
221 
222  lept_stderr("Time: %7.3f sec\n", stopTimerNested(rp->tstart));
223 
224  /* If generating golden files or running in display mode, release rp */
225  if (!rp->fp) {
226  LEPT_FREE(rp->testname);
227  LEPT_FREE(rp->tempfile);
228  LEPT_FREE(rp);
229  return 0;
230  }
231 
232  /* Compare mode: read back data from temp file */
233  fclose(rp->fp);
234  text = (char *)l_binaryRead(rp->tempfile, &nbytes);
235  LEPT_FREE(rp->tempfile);
236  if (!text) {
237  rp->success = FALSE;
238  LEPT_FREE(rp->testname);
239  LEPT_FREE(rp);
240  return ERROR_INT("text not returned", procName, 1);
241  }
242 
243  /* Prepare result message */
244  if (rp->success)
245  snprintf(result, sizeof(result), "SUCCESS: %s_reg\n", rp->testname);
246  else
247  snprintf(result, sizeof(result), "FAILURE: %s_reg\n", rp->testname);
248  message = stringJoin(text, result);
249  LEPT_FREE(text);
250  results_file = stringNew("/tmp/lept/reg_results.txt");
251  fileAppendString(results_file, message);
252  retval = (rp->success) ? 0 : 1;
253  LEPT_FREE(results_file);
254  LEPT_FREE(message);
255 
256  LEPT_FREE(rp->testname);
257  LEPT_FREE(rp);
258  return retval;
259 }
260 
261 
272 l_ok
274  l_float32 val1,
275  l_float32 val2,
276  l_float32 delta)
277 {
278 l_float32 diff;
279 
280  PROCNAME("regTestCompareValues");
281 
282  if (!rp)
283  return ERROR_INT("rp not defined", procName, 1);
284 
285  rp->index++;
286  diff = L_ABS(val2 - val1);
287 
288  /* Record on failure */
289  if (diff > delta) {
290  if (rp->fp) {
291  fprintf(rp->fp,
292  "Failure in %s_reg: value comparison for index %d\n"
293  "difference = %f but allowed delta = %f\n",
294  rp->testname, rp->index, diff, delta);
295  }
296  lept_stderr("Failure in %s_reg: value comparison for index %d\n"
297  "difference = %f but allowed delta = %f\n",
298  rp->testname, rp->index, diff, delta);
299  rp->success = FALSE;
300  }
301  return 0;
302 }
303 
304 
316 l_ok
318  l_uint8 *string1,
319  size_t bytes1,
320  l_uint8 *string2,
321  size_t bytes2)
322 {
323 l_int32 same;
324 char buf[256];
325 
326  PROCNAME("regTestCompareStrings");
327 
328  if (!rp)
329  return ERROR_INT("rp not defined", procName, 1);
330 
331  rp->index++;
332  l_binaryCompare(string1, bytes1, string2, bytes2, &same);
333 
334  /* Output on failure */
335  if (!same) {
336  /* Write the two strings to file */
337  snprintf(buf, sizeof(buf), "/tmp/lept/regout/string1_%d_%zu",
338  rp->index, bytes1);
339  l_binaryWrite(buf, "w", string1, bytes1);
340  snprintf(buf, sizeof(buf), "/tmp/lept/regout/string2_%d_%zu",
341  rp->index, bytes2);
342  l_binaryWrite(buf, "w", string2, bytes2);
343 
344  /* Report comparison failure */
345  snprintf(buf, sizeof(buf), "/tmp/lept/regout/string*_%d_*", rp->index);
346  if (rp->fp) {
347  fprintf(rp->fp,
348  "Failure in %s_reg: string comp for index %d; "
349  "written to %s\n", rp->testname, rp->index, buf);
350  }
351  lept_stderr("Failure in %s_reg: string comp for index %d; "
352  "written to %s\n", rp->testname, rp->index, buf);
353  rp->success = FALSE;
354  }
355  return 0;
356 }
357 
358 
373 l_ok
375  PIX *pix1,
376  PIX *pix2)
377 {
378 l_int32 same;
379 
380  PROCNAME("regTestComparePix");
381 
382  if (!rp)
383  return ERROR_INT("rp not defined", procName, 1);
384  if (!pix1 || !pix2) {
385  rp->success = FALSE;
386  return ERROR_INT("pix1 and pix2 not both defined", procName, 1);
387  }
388 
389  rp->index++;
390  pixEqual(pix1, pix2, &same);
391 
392  /* Record on failure */
393  if (!same) {
394  if (rp->fp) {
395  fprintf(rp->fp, "Failure in %s_reg: pix comparison for index %d\n",
396  rp->testname, rp->index);
397  }
398  lept_stderr("Failure in %s_reg: pix comparison for index %d\n",
399  rp->testname, rp->index);
400  rp->success = FALSE;
401  }
402  return 0;
403 }
404 
405 
433 l_ok
435  PIX *pix1,
436  PIX *pix2,
437  l_int32 mindiff,
438  l_float32 maxfract,
439  l_int32 printstats)
440 {
441 l_int32 w, h, factor, similar;
442 
443  PROCNAME("regTestCompareSimilarPix");
444 
445  if (!rp)
446  return ERROR_INT("rp not defined", procName, 1);
447  if (!pix1 || !pix2) {
448  rp->success = FALSE;
449  return ERROR_INT("pix1 and pix2 not both defined", procName, 1);
450  }
451 
452  rp->index++;
453  pixGetDimensions(pix1, &w, &h, NULL);
454  factor = L_MAX(w, h) / 400;
455  factor = L_MAX(1, L_MIN(factor, 4)); /* between 1 and 4 */
456  pixTestForSimilarity(pix1, pix2, factor, mindiff, maxfract, 0.0,
457  &similar, printstats);
458 
459  /* Record on failure */
460  if (!similar) {
461  if (rp->fp) {
462  fprintf(rp->fp,
463  "Failure in %s_reg: pix similarity comp for index %d\n",
464  rp->testname, rp->index);
465  }
466  lept_stderr("Failure in %s_reg: pix similarity comp for index %d\n",
467  rp->testname, rp->index);
468  rp->success = FALSE;
469  }
470  return 0;
471 }
472 
473 
500 l_ok
502  const char *localname)
503 {
504 char *ext;
505 char namebuf[256];
506 l_int32 ret, same, format;
507 PIX *pix1, *pix2;
508 
509  PROCNAME("regTestCheckFile");
510 
511  if (!rp)
512  return ERROR_INT("rp not defined", procName, 1);
513  if (!localname) {
514  rp->success = FALSE;
515  return ERROR_INT("local name not defined", procName, 1);
516  }
517  if (rp->mode != L_REG_GENERATE && rp->mode != L_REG_COMPARE &&
518  rp->mode != L_REG_DISPLAY) {
519  rp->success = FALSE;
520  return ERROR_INT("invalid mode", procName, 1);
521  }
522  rp->index++;
523 
524  /* If display mode, no generation and no testing */
525  if (rp->mode == L_REG_DISPLAY) return 0;
526 
527  /* Generate the golden file name; used in 'generate' and 'compare' */
528  splitPathAtExtension(localname, NULL, &ext);
529  snprintf(namebuf, sizeof(namebuf), "/tmp/lept/golden/%s_golden.%02d%s",
530  rp->testname, rp->index, ext);
531  LEPT_FREE(ext);
532 
533  /* Generate mode. No testing. */
534  if (rp->mode == L_REG_GENERATE) {
535  /* Save the file as a golden file */
536  ret = fileCopy(localname, namebuf);
537 #if 0 /* Enable for details on writing of golden files */
538  if (!ret) {
539  char *local = genPathname(localname, NULL);
540  char *golden = genPathname(namebuf, NULL);
541  L_INFO("Copy: %s to %s\n", procName, local, golden);
542  LEPT_FREE(local);
543  LEPT_FREE(golden);
544  }
545 #endif
546  return ret;
547  }
548 
549  /* Compare mode: test and record on failure. This can be used
550  * for all image formats, as well as for all files of serialized
551  * data, such as boxa, pta, etc. In all cases except for
552  * GIF compressed images, we compare the files to see if they
553  * are identical. GIF doesn't support RGB images; to write
554  * a 32 bpp RGB image in GIF, we do a lossy quantization to
555  * 256 colors, so the cycle read-RGB/write-GIF is not idempotent.
556  * And although the read/write cycle for GIF images with bpp <= 8
557  * is idempotent in the image pixels, it is not idempotent in the
558  * actual file bytes; tests comparing file bytes before and after
559  * a GIF read/write cycle will fail. So for GIF we uncompress
560  * the two images and compare the actual pixels. PNG is both
561  * lossless and idempotent in file bytes on read/write, so it is
562  * not necessary to compare pixels. (Comparing pixels requires
563  * decompression, and thus would increase the regression test
564  * time. JPEG is lossy and not idempotent in the image pixels,
565  * so no tests are constructed that would require it. */
566  findFileFormat(localname, &format);
567  if (format == IFF_GIF) {
568  same = 0;
569  pix1 = pixRead(localname);
570  pix2 = pixRead(namebuf);
571  pixEqual(pix1, pix2, &same);
572  pixDestroy(&pix1);
573  pixDestroy(&pix2);
574  } else {
575  filesAreIdentical(localname, namebuf, &same);
576  }
577  if (!same) {
578  fprintf(rp->fp, "Failure in %s_reg, index %d: comparing %s with %s\n",
579  rp->testname, rp->index, localname, namebuf);
580  lept_stderr("Failure in %s_reg, index %d: comparing %s with %s\n",
581  rp->testname, rp->index, localname, namebuf);
582  rp->success = FALSE;
583  }
584 
585  return 0;
586 }
587 
588 
608 l_ok
610  l_int32 index1,
611  l_int32 index2)
612 {
613 char *name1, *name2;
614 char namebuf[256];
615 l_int32 same;
616 SARRAY *sa;
617 
618  PROCNAME("regTestCompareFiles");
619 
620  if (!rp)
621  return ERROR_INT("rp not defined", procName, 1);
622  if (index1 < 0 || index2 < 0) {
623  rp->success = FALSE;
624  return ERROR_INT("index1 and/or index2 is negative", procName, 1);
625  }
626  if (index1 == index2) {
627  rp->success = FALSE;
628  return ERROR_INT("index1 must differ from index2", procName, 1);
629  }
630 
631  rp->index++;
632  if (rp->mode != L_REG_COMPARE) return 0;
633 
634  /* Generate the golden file names */
635  snprintf(namebuf, sizeof(namebuf), "%s_golden.%02d", rp->testname, index1);
636  sa = getSortedPathnamesInDirectory("/tmp/lept/golden", namebuf, 0, 0);
637  if (sarrayGetCount(sa) != 1) {
638  sarrayDestroy(&sa);
639  rp->success = FALSE;
640  L_ERROR("golden file %s not found\n", procName, namebuf);
641  return 1;
642  }
643  name1 = sarrayGetString(sa, 0, L_COPY);
644  sarrayDestroy(&sa);
645 
646  snprintf(namebuf, sizeof(namebuf), "%s_golden.%02d", rp->testname, index2);
647  sa = getSortedPathnamesInDirectory("/tmp/lept/golden", namebuf, 0, 0);
648  if (sarrayGetCount(sa) != 1) {
649  sarrayDestroy(&sa);
650  rp->success = FALSE;
651  LEPT_FREE(name1);
652  L_ERROR("golden file %s not found\n", procName, namebuf);
653  return 1;
654  }
655  name2 = sarrayGetString(sa, 0, L_COPY);
656  sarrayDestroy(&sa);
657 
658  /* Test and record on failure */
659  filesAreIdentical(name1, name2, &same);
660  if (!same) {
661  fprintf(rp->fp,
662  "Failure in %s_reg, index %d: comparing %s with %s\n",
663  rp->testname, rp->index, name1, name2);
664  lept_stderr("Failure in %s_reg, index %d: comparing %s with %s\n",
665  rp->testname, rp->index, name1, name2);
666  rp->success = FALSE;
667  }
668 
669  LEPT_FREE(name1);
670  LEPT_FREE(name2);
671  return 0;
672 }
673 
674 
701 l_ok
703  PIX *pix,
704  l_int32 format)
705 {
706 char namebuf[256];
707 
708  PROCNAME("regTestWritePixAndCheck");
709 
710  if (!rp)
711  return ERROR_INT("rp not defined", procName, 1);
712  if (!pix) {
713  rp->success = FALSE;
714  return ERROR_INT("pix not defined", procName, 1);
715  }
716  if (format < 0 || format >= NumImageFileFormatExtensions) {
717  rp->success = FALSE;
718  return ERROR_INT("invalid format", procName, 1);
719  }
720 
721  /* Use bmp format for testing if library for requested
722  * format for jpeg, png or tiff is not available */
723  changeFormatForMissingLib(&format);
724 
725  /* Generate the local file name */
726  snprintf(namebuf, sizeof(namebuf), "/tmp/lept/regout/%s.%02d.%s",
727  rp->testname, rp->index + 1, ImageFileFormatExtensions[format]);
728 
729  /* Write the local file */
730  if (pixGetDepth(pix) < 8)
731  pixSetPadBits(pix, 0);
732  pixWrite(namebuf, pix, format);
733 
734  /* Either write the golden file ("generate") or check the
735  local file against an existing golden file ("compare") */
736  regTestCheckFile(rp, namebuf);
737 
738  return 0;
739 }
740 
741 
772 l_ok
774  void *data,
775  size_t nbytes,
776  const char *ext)
777 {
778 char namebuf[256];
779 
780  PROCNAME("regTestWriteDataAndCheck");
781 
782  if (!rp)
783  return ERROR_INT("rp not defined", procName, 1);
784  if (!data || nbytes == 0) {
785  rp->success = FALSE;
786  return ERROR_INT("data not defined or size == 0", procName, 1);
787  }
788 
789  /* Generate the local file name */
790  snprintf(namebuf, sizeof(namebuf), "/tmp/lept/regout/%s.%02d.%s",
791  rp->testname, rp->index + 1, ext);
792 
793  /* Write the local file */
794  l_binaryWrite(namebuf, "w", data, nbytes);
795 
796  /* Either write the golden file ("generate") or check the
797  local file against an existing golden file ("compare") */
798  regTestCheckFile(rp, namebuf);
799  return 0;
800 }
801 
802 
823 char *
825  l_int32 index,
826  l_int32 format)
827 {
828 char buf[64];
829 l_int32 ind;
830 
831  PROCNAME("regTestGenLocalFilename");
832 
833  if (!rp)
834  return (char *)ERROR_PTR("rp not defined", procName, NULL);
835 
836  ind = (index >= 0) ? index : rp->index;
837  snprintf(buf, sizeof(buf), "/tmp/lept/regout/%s.%02d.%s",
838  rp->testname, ind, ImageFileFormatExtensions[format]);
839  return stringNew(buf);
840 }
841 
842 
859 static char *
860 getRootNameFromArgv0(const char *argv0)
861 {
862 l_int32 len;
863 char *root;
864 
865  PROCNAME("getRootNameFromArgv0");
866 
867  splitPathAtDirectory(argv0, NULL, &root);
868  if ((len = strlen(root)) <= 4) {
869  LEPT_FREE(root);
870  return (char *)ERROR_PTR("invalid argv0; too small", procName, NULL);
871  }
872 
873 #ifndef _WIN32
874  {
875  char *newroot;
876  l_int32 loc;
877  if (stringFindSubstr(root, "-", &loc)) {
878  newroot = stringNew(root + loc + 1); /* strip out "lt-" */
879  LEPT_FREE(root);
880  root = newroot;
881  len = strlen(root);
882  }
883  len -= 4; /* remove the "_reg" suffix */
884  }
885 #else
886  if (strstr(root, ".exe") != NULL)
887  len -= 4;
888  if (strstr(root, "_reg") == root + len - 4)
889  len -= 4;
890 #endif /* ! _WIN32 */
891 
892  root[len] = '\0'; /* terminate */
893  return root;
894 }
l_ok pixEqual(PIX *pix1, PIX *pix2, l_int32 *psame)
pixEqual()
Definition: compare.c:156
l_ok pixTestForSimilarity(PIX *pix1, PIX *pix2, l_int32 factor, l_int32 mindiff, l_float32 maxfract, l_float32 maxave, l_int32 *psimilar, l_int32 details)
pixTestForSimilarity()
Definition: compare.c:1326
char * getImagelibVersions(void)
getImagelibVersions()
Definition: libversions.c:102
void pixDestroy(PIX **ppix)
pixDestroy()
Definition: pix1.c:621
l_ok pixGetDimensions(const PIX *pix, l_int32 *pw, l_int32 *ph, l_int32 *pd)
pixGetDimensions()
Definition: pix1.c:1113
l_ok pixSetPadBits(PIX *pix, l_int32 val)
pixSetPadBits()
Definition: pix2.c:1382
@ L_COPY
Definition: pix.h:712
l_ok findFileFormat(const char *filename, l_int32 *pformat)
findFileFormat()
Definition: readfile.c:584
PIX * pixRead(const char *filename)
pixRead()
Definition: readfile.c:193
l_ok regTestSetup(l_int32 argc, char **argv, L_REGPARAMS **prp)
regTestSetup()
Definition: regutils.c:123
l_ok regTestCompareSimilarPix(L_REGPARAMS *rp, PIX *pix1, PIX *pix2, l_int32 mindiff, l_float32 maxfract, l_int32 printstats)
regTestCompareSimilarPix()
Definition: regutils.c:434
l_ok regTestCompareFiles(L_REGPARAMS *rp, l_int32 index1, l_int32 index2)
regTestCompareFiles()
Definition: regutils.c:609
l_ok regTestCompareStrings(L_REGPARAMS *rp, l_uint8 *string1, size_t bytes1, l_uint8 *string2, size_t bytes2)
regTestCompareStrings()
Definition: regutils.c:317
l_ok regTestWritePixAndCheck(L_REGPARAMS *rp, PIX *pix, l_int32 format)
regTestWritePixAndCheck()
Definition: regutils.c:702
static char * getRootNameFromArgv0(const char *argv0)
getRootNameFromArgv0()
Definition: regutils.c:860
l_ok regTestCheckFile(L_REGPARAMS *rp, const char *localname)
regTestCheckFile()
Definition: regutils.c:501
l_ok regTestComparePix(L_REGPARAMS *rp, PIX *pix1, PIX *pix2)
regTestComparePix()
Definition: regutils.c:374
char * regTestGenLocalFilename(L_REGPARAMS *rp, l_int32 index, l_int32 format)
regTestGenLocalFilename()
Definition: regutils.c:824
l_ok regTestCompareValues(L_REGPARAMS *rp, l_float32 val1, l_float32 val2, l_float32 delta)
regTestCompareValues()
Definition: regutils.c:273
l_ok regTestCleanup(L_REGPARAMS *rp)
regTestCleanup()
Definition: regutils.c:209
l_ok regTestWriteDataAndCheck(L_REGPARAMS *rp, void *data, size_t nbytes, const char *ext)
regTestWriteDataAndCheck()
Definition: regutils.c:773
char * sarrayGetString(SARRAY *sa, l_int32 index, l_int32 copyflag)
sarrayGetString()
Definition: sarray1.c:703
l_int32 sarrayGetCount(SARRAY *sa)
sarrayGetCount()
Definition: sarray1.c:643
void sarrayDestroy(SARRAY **psa)
sarrayDestroy()
Definition: sarray1.c:362
SARRAY * getSortedPathnamesInDirectory(const char *dirname, const char *substr, l_int32 first, l_int32 nfiles)
getSortedPathnamesInDirectory()
Definition: sarray1.c:1848
char * testname
Definition: regutils.h:120
l_int32 success
Definition: regutils.h:124
char * tempfile
Definition: regutils.h:121
l_int32 display
Definition: regutils.h:125
l_int32 index
Definition: regutils.h:123
l_int32 mode
Definition: regutils.h:122
L_TIMER tstart
Definition: regutils.h:126
FILE * fp
Definition: regutils.h:119
Definition: pix.h:139
Definition: array.h:127
l_ok filesAreIdentical(const char *fname1, const char *fname2, l_int32 *psame)
filesAreIdentical()
Definition: utils1.c:333
void lept_stderr(const char *fmt,...)
lept_stderr()
Definition: utils1.c:306
L_TIMER startTimerNested(void)
startTimerNested(), stopTimerNested()
Definition: utils1.c:1073
char * getLeptonicaVersion(void)
getLeptonicaVersion()
Definition: utils1.c:982
char * stringNew(const char *src)
stringNew()
Definition: utils2.c:223
l_ok fileAppendString(const char *filename, const char *str)
fileAppendString()
Definition: utils2.c:1805
l_ok splitPathAtExtension(const char *pathname, char **pbasename, char **pextension)
splitPathAtExtension()
Definition: utils2.c:2894
l_ok l_binaryCompare(const l_uint8 *data1, size_t size1, const l_uint8 *data2, size_t size2, l_int32 *psame)
l_binaryCompare()
Definition: utils2.c:1711
l_ok splitPathAtDirectory(const char *pathname, char **pdir, char **ptail)
splitPathAtDirectory()
Definition: utils2.c:2824
FILE * fopenWriteStream(const char *filename, const char *modestring)
fopenWriteStream()
Definition: utils2.c:1975
l_int32 stringFindSubstr(const char *src, const char *sub, l_int32 *ploc)
stringFindSubstr()
Definition: utils2.c:1027
char * genPathname(const char *dir, const char *fname)
genPathname()
Definition: utils2.c:3173
l_int32 lept_mkdir(const char *subdir)
lept_mkdir()
Definition: utils2.c:2218
char * stringJoin(const char *src1, const char *src2)
stringJoin()
Definition: utils2.c:518
l_ok l_binaryWrite(const char *filename, const char *operation, const void *data, size_t nbytes)
l_binaryWrite()
Definition: utils2.c:1569
l_uint8 * l_binaryRead(const char *filename, size_t *pnbytes)
l_binaryRead()
Definition: utils2.c:1352
l_ok fileCopy(const char *srcfile, const char *newfile)
fileCopy()
Definition: utils2.c:1747