Coverage Report

Created: 2025-06-13 06:18

/src/gdal/frmts/gtiff/gtiffsplitbitmapband.cpp
Line
Count
Source (jump to first uncovered line)
1
/******************************************************************************
2
 *
3
 * Project:  GeoTIFF Driver
4
 * Purpose:  GDAL GeoTIFF support.
5
 * Author:   Frank Warmerdam, warmerdam@pobox.com
6
 *
7
 ******************************************************************************
8
 * Copyright (c) 1998, 2002, Frank Warmerdam <warmerdam@pobox.com>
9
 * Copyright (c) 2007-2015, Even Rouault <even dot rouault at spatialys dot com>
10
 *
11
 * SPDX-License-Identifier: MIT
12
 ****************************************************************************/
13
14
#include "gtiffsplitbitmapband.h"
15
16
#include "gtiffdataset.h"
17
18
#include "cpl_error_internal.h"
19
20
/************************************************************************/
21
/*                       GTiffSplitBitmapBand()                         */
22
/************************************************************************/
23
24
GTiffSplitBitmapBand::GTiffSplitBitmapBand(GTiffDataset *poDSIn, int nBandIn)
25
0
    : GTiffBitmapBand(poDSIn, nBandIn)
26
27
0
{
28
0
    nBlockXSize = poDS->GetRasterXSize();
29
0
    nBlockYSize = 1;
30
0
}
31
32
/************************************************************************/
33
/*                      ~GTiffSplitBitmapBand()                         */
34
/************************************************************************/
35
36
GTiffSplitBitmapBand::~GTiffSplitBitmapBand()
37
0
{
38
0
}
39
40
/************************************************************************/
41
/*                       IGetDataCoverageStatus()                       */
42
/************************************************************************/
43
44
int GTiffSplitBitmapBand::IGetDataCoverageStatus(int, int, int, int, int,
45
                                                 double *)
46
0
{
47
0
    return GDAL_DATA_COVERAGE_STATUS_UNIMPLEMENTED |
48
0
           GDAL_DATA_COVERAGE_STATUS_DATA;
49
0
}
50
51
/************************************************************************/
52
/*                             IReadBlock()                             */
53
/************************************************************************/
54
55
CPLErr GTiffSplitBitmapBand::IReadBlock(int /* nBlockXOff */, int nBlockYOff,
56
                                        void *pImage)
57
58
0
{
59
0
    m_poGDS->Crystalize();
60
61
0
    if (m_nLastLineValid >= 0 && nBlockYOff > m_nLastLineValid)
62
0
        return CE_Failure;
63
64
0
    if (m_poGDS->m_pabyBlockBuf == nullptr)
65
0
    {
66
0
        m_poGDS->m_pabyBlockBuf = static_cast<GByte *>(
67
0
            VSI_MALLOC_VERBOSE(TIFFScanlineSize(m_poGDS->m_hTIFF)));
68
0
        if (m_poGDS->m_pabyBlockBuf == nullptr)
69
0
        {
70
0
            return CE_Failure;
71
0
        }
72
0
    }
73
74
    /* -------------------------------------------------------------------- */
75
    /*      Read through to target scanline.                                */
76
    /* -------------------------------------------------------------------- */
77
0
    if (m_poGDS->m_nLoadedBlock >= nBlockYOff)
78
0
        m_poGDS->m_nLoadedBlock = -1;
79
80
    // Set to 1 to allow GTiffErrorHandler to implement limitation on error
81
    // messages
82
0
    GTIFFGetThreadLocalLibtiffError() = 1;
83
0
    while (m_poGDS->m_nLoadedBlock < nBlockYOff)
84
0
    {
85
0
        ++m_poGDS->m_nLoadedBlock;
86
87
0
        CPLErrorAccumulator oErrorAccumulator;
88
0
        int nRet;
89
0
        {
90
0
            auto oAccumulator = oErrorAccumulator.InstallForCurrentScope();
91
0
            nRet = TIFFReadScanline(m_poGDS->m_hTIFF, m_poGDS->m_pabyBlockBuf,
92
0
                                    m_poGDS->m_nLoadedBlock, 0);
93
0
        }
94
95
0
        for (const auto &oError : oErrorAccumulator.GetErrors())
96
0
        {
97
0
            ReportError(oError.type, oError.no, "%s", oError.msg.c_str());
98
            // FAX decoding only handles EOF condition as a warning, so
99
            // catch it so as to turn on error when attempting to read
100
            // following lines, to avoid performance issues.
101
0
            if (!m_poGDS->m_bIgnoreReadErrors &&
102
0
                oError.msg.find("Premature EOF") != std::string::npos)
103
0
            {
104
0
                m_nLastLineValid = nBlockYOff;
105
0
                nRet = -1;
106
0
            }
107
0
        }
108
109
0
        if (nRet == -1 && !m_poGDS->m_bIgnoreReadErrors)
110
0
        {
111
0
            ReportError(CE_Failure, CPLE_AppDefined,
112
0
                        "TIFFReadScanline() failed.");
113
0
            m_poGDS->m_nLoadedBlock = -1;
114
0
            GTIFFGetThreadLocalLibtiffError() = 0;
115
0
            return CE_Failure;
116
0
        }
117
0
    }
118
0
    GTIFFGetThreadLocalLibtiffError() = 0;
119
120
    /* -------------------------------------------------------------------- */
121
    /*      Translate 1bit data to eight bit.                               */
122
    /* -------------------------------------------------------------------- */
123
0
    int iSrcOffset = 0;
124
0
    int iDstOffset = 0;
125
126
0
    for (int iPixel = 0; iPixel < nBlockXSize; ++iPixel, ++iSrcOffset)
127
0
    {
128
0
        if (m_poGDS->m_pabyBlockBuf[iSrcOffset >> 3] &
129
0
            (0x80 >> (iSrcOffset & 0x7)))
130
0
            static_cast<GByte *>(pImage)[iDstOffset++] = 1;
131
0
        else
132
0
            static_cast<GByte *>(pImage)[iDstOffset++] = 0;
133
0
    }
134
135
0
    return CE_None;
136
0
}
137
138
/************************************************************************/
139
/*                            IWriteBlock()                             */
140
/************************************************************************/
141
142
CPLErr GTiffSplitBitmapBand::IWriteBlock(int /* nBlockXOff */,
143
                                         int /* nBlockYOff */,
144
                                         void * /* pImage */)
145
146
0
{
147
0
    ReportError(CE_Failure, CPLE_AppDefined,
148
0
                "Split bitmap bands are read-only.");
149
0
    return CE_Failure;
150
0
}