AWARE [SYSTEMS] Imaging expertise for the Delphi developer
AWare Systems, Imaging expertise for the Delphi developer, Home TIFF and LibTiff Mailing List Archive

LibTiff Mailing List

TIFF and LibTiff Mailing List Archive
May 2011

Previous Thread
Next Thread

Previous by Thread
Next by Thread

Previous by Date
Next by Date

Contact

The TIFF Mailing List Homepage
This list is run by Frank Warmerdam
Archive maintained by AWare Systems



Valid HTML 4.01!



Thread

2011.05.05 16:44 "Is LibTiff 3.9.5 Thread Safe ?", by Katerina Sedivy
2011.05.05 17:42 "Re: Is LibTiff 3.9.5 Thread Safe ?", by Frank Warmerdam
2011.05.05 19:01 "Re: Is LibTiff 3.9.5 Thread Safe ?", by Bob Friesenhahn
2011.05.05 19:49 "Re: Is LibTiff 3.9.5 Thread Safe ?", by Katerina Sedivy
2011.05.05 20:16 "Re: Is LibTiff 3.9.5 Thread Safe ?", by Bob Friesenhahn
2011.05.06 17:07 "Re: Is LibTiff 3.9.5 Thread Safe ?", by Katerina Sedivy
2011.05.12 06:09 "Re: Is LibTiff 3.9.5 Thread Safe ?", by Andreas Kleinert
2011.05.05 19:59 "Re: Is LibTiff 3.9.5 Thread Safe ?", by Katerina Sedivy
2011.05.05 21:08 "Re: Is LibTiff 3.9.5 Thread Safe ?", by Frank Warmerdam

2011.05.05 16:44 "Is LibTiff 3.9.5 Thread Safe ?", by Katerina Sedivy

Hi,

 So I have my LibTiff.dll 3.9.5 compiled and loaded in a multithread
environement.

I have a tiff which I have used with the TiffInfo tool at command line to
see its information (I've attached the file):

TIFF Directory at offset 0x3e30 (15920)
  Subfile Type: (0 = 0x0)
  Image Width: 1224 Image Length: 576
  Resolution: 96, 96 pixels/inch
  Bits/Sample: 1
  Compression Scheme: LZW
  Photometric Interpretation: min-is-black
  Orientation: row 0 top, col 0 lhs
  Samples/Pixel: 1
  Rows/Strip: 80
  Planar Configuration: single image plane
  Predictor: none 1 (0x1)

I successfully retrieve the information with this code:


procedure TMainAppRunnerDlg.Button3Click(Sender: TObject);
var
  l_Tiff: pointer;
  lu_BitsPerSample: Word;
begin

  l_Tiff := DLL_TIFFOpen(PChar('C:\cheque_3533_A.tif'), 'r');
  if l_Tiff <> nil then
  begin
    lu_BitsPerSample := 0;
    if DLL_TIFFGetField(l_Tiff, 258, lu_BitsPerSample) = 0 then   //
TIFFTAG_BITSPERSAMPLE = 258
      if lu_BitsPerSample = 0 then
        OutputDebugString(PChar('WARNING: TIFFGetField returned false and
BitsPerSample = 0'))
      else
        OutputDebugString(PChar('WARNING: TIFFGetField returned false and
BitsPerSample <> 0 '));
    DLL_TIFFClose(l_Tiff);
    outputdebugstring(PChar('Pass!!!'));
  end;
end;


BUT This same file failed in a multithread environement. I run the code
below in a Thread. There are 3 threads created which each execute
TIFFGetField multiple times, once in a while BitsPerSample returned by
TIFFGetField is 0 instead of 1.

I also got this message in my debugger for the Tiff file attached :
ODS: module: TIFF directory is missing required "%s" field | message:
C:\Develop\Tests\Service app\Thread1\cheque_3533_A.tif Process
ServiceTester.exe ($A50)

Which is a warning output by TIFFReadDirectory in tif_dirread.c.



procedure TServiceThread.Execute;
var
  i: Integer;
  l_Config: TConfig;
  l_Filenames: TStringList;
  ls_Filename,ls_otfilename, ls_dir: string;

  lh_ProcRefrence: longint;
  lu_BitsPerSample: Word;
  lh_TiffHandle: Pointer;
  lh_DLLHandle: Cardinal;

begin
  CoInitialize(nil);
  FreeOnTerminate := True;

  l_Filenames := TStringList.Create;
  try
    LoadConfig(l_Config.InPath, l_Config.FileType, l_Config.Output);
    GetFilesToProcess(l_Filenames, l_Config.InPath, l_Config.FileType);

    for i := 0 to l_Filenames.Count - 1 do
    begin
          try
            ls_Filename := l_Config.InPath + l_Filenames.Strings[i];
            lh_ProcRefrence := DLL_TIFFSetErrorHandler(@TiffErrorProc);
            if lh_ProcRefrence = 0 then
            begin
              OutputDebugString(PChar('WARNING: DLL_TIFFSetErrorHandler
failed'));
              exit;
            end;

//            OutputDebugString(PChar(Format('Thread: %d  | File:
%s',[ThreadID, ls_Filename])));

            lh_TiffHandle := nil;
            lh_TiffHandle := DLL_TIFFOpen(ls_Filename, 'r');
            lu_BitsPerSample := 0;
            if DLL_TIFFGetField(lh_TiffHandle, 258, lu_BitsPerSample) = 0
then   //  TIFFTAG_BITSPERSAMPLE = 258
              if lu_BitsPerSample = 0 then
                OutputDebugString(PChar(Format('WARNING: TIFFGetField
returned false and BitsPerSample = 0 | Filename: %s |ThreadID:
%d',[ls_Filename, ThreadID])))
              else
                OutputDebugString(PChar(Format('WARNING: TIFFGetField
returned false and BitsPerSample <> 0 | ThreadID: %d',[ThreadID])));
            if lh_TiffHandle <> nil then
              DLL_TIFFClose(lh_TiffHandle);
          except
            on E: Exception do
            begin
              OutputDebugString(PChar(Format('ERROR: %s with file: %s |
ThreadID: %d',[E.Message, ls_Filename, ThreadID])));
              exit;
            end;
          end;
      end;
  finally
    l_Filenames.Free;
    CoUninitialize;
    FreeLibrary(lh_DLLHandle);
  end;