Coverage Report

Created: 2026-07-20 07:04

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/libwps/src/lib/WPSStringStream.cpp
Line
Count
Source
1
/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: t; c-basic-offset: 4 -*- */
2
/* libwps
3
 * Version: MPL 2.0 / LGPLv2.1+
4
 *
5
 * This Source Code Form is subject to the terms of the Mozilla Public
6
 * License, v. 2.0. If a copy of the MPL was not distributed with this
7
 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8
 *
9
 * Major Contributor(s):
10
 * Copyright (C) 2009, 2011 Alonso Laurent (alonso@loria.fr)
11
 * Copyright (C) 2006, 2007 Andrew Ziem
12
 * Copyright (C) 2004-2006 Fridrich Strba (fridrich.strba@bluewin.ch)
13
 * Copyright (C) 2004 Marc Maurer (uwog@uwog.net)
14
 * Copyright (C) 2003-2005 William Lachance (william.lachance@sympatico.ca)
15
 *
16
 * For minor contributions see the git repository.
17
 *
18
 * Alternatively, the contents of this file may be used under the terms
19
 * of the GNU Lesser General Public License Version 2.1 or later
20
 * (LGPLv2.1+), in which case the provisions of the LGPLv2.1+ are
21
 * applicable instead of those above.
22
 *
23
 * For further information visit http://libwps.sourceforge.net
24
 */
25
26
#include <cstring>
27
#include <vector>
28
29
#include <librevenge-stream/librevenge-stream.h>
30
31
#include "WPSStringStream.h"
32
33
//! internal data of a WPSStringStream
34
class WPSStringStreamPrivate
35
{
36
public:
37
  //! constructor
38
  WPSStringStreamPrivate(const unsigned char *data, unsigned dataSize);
39
  //! destructor
40
  ~WPSStringStreamPrivate();
41
  //! append some data at the end of the actual stream
42
  void append(const unsigned char *data, unsigned dataSize);
43
  //! the stream buffer
44
  std::vector<unsigned char> m_buffer;
45
  //! the stream offset
46
  long m_offset;
47
private:
48
  WPSStringStreamPrivate(const WPSStringStreamPrivate &) = delete;
49
  WPSStringStreamPrivate &operator=(const WPSStringStreamPrivate &) = delete;
50
};
51
52
WPSStringStreamPrivate::WPSStringStreamPrivate(const unsigned char *data, unsigned dataSize)
53
24.4k
  : m_buffer(0)
54
24.4k
  , m_offset(0)
55
24.4k
{
56
24.4k
  if (data && dataSize)
57
24.4k
  {
58
24.4k
    m_buffer.resize(dataSize);
59
24.4k
    std::memcpy(&m_buffer[0], data, dataSize);
60
24.4k
  }
61
24.4k
}
62
63
WPSStringStreamPrivate::~WPSStringStreamPrivate()
64
24.4k
{
65
24.4k
}
66
67
void WPSStringStreamPrivate::append(const unsigned char *data, unsigned dataSize)
68
324
{
69
324
  if (!dataSize) return;
70
324
  size_t actualSize=m_buffer.size();
71
324
  m_buffer.resize(actualSize+size_t(dataSize));
72
324
  std::memcpy(&m_buffer[actualSize], data, dataSize);
73
324
}
74
75
WPSStringStream::WPSStringStream(const unsigned char *data, const unsigned int dataSize) :
76
24.4k
  librevenge::RVNGInputStream(),
77
24.4k
  m_data(new WPSStringStreamPrivate(data, dataSize))
78
24.4k
{
79
24.4k
}
80
81
WPSStringStream::~WPSStringStream()
82
24.4k
{
83
24.4k
}
84
85
void WPSStringStream::append(const unsigned char *data, const unsigned int dataSize)
86
324
{
87
324
  if (m_data) m_data->append(data, dataSize);
88
324
}
89
90
const unsigned char *WPSStringStream::read(unsigned long numBytes, unsigned long &numBytesRead)
91
135M
{
92
135M
  numBytesRead = 0;
93
94
135M
  if (numBytes == 0 || !m_data)
95
125
    return nullptr;
96
97
135M
  if (m_data->m_offset < 0)
98
0
    return nullptr;
99
100
135M
  const unsigned long bufSize = m_data->m_buffer.size();
101
135M
  const unsigned long pos = static_cast<unsigned long>(m_data->m_offset);
102
135M
  const unsigned long remaining = pos < bufSize ? bufSize - pos : 0;
103
135M
  const unsigned long numBytesToRead = numBytes < remaining ? numBytes : remaining;
104
105
135M
  numBytesRead = numBytesToRead; // about as paranoid as we can be..
106
107
135M
  if (numBytesToRead == 0)
108
36.3M
    return nullptr;
109
110
99.2M
  long oldOffset = m_data->m_offset;
111
99.2M
  m_data->m_offset += long(numBytesToRead);
112
113
99.2M
  return &m_data->m_buffer[size_t(oldOffset)];
114
115
135M
}
116
117
long WPSStringStream::tell()
118
30.6M
{
119
30.6M
  return m_data ? m_data->m_offset : 0;
120
30.6M
}
121
122
int WPSStringStream::seek(long offset, librevenge::RVNG_SEEK_TYPE seekType)
123
21.0M
{
124
21.0M
  if (!m_data) return -1;
125
21.0M
  if (seekType == librevenge::RVNG_SEEK_CUR)
126
267k
    m_data->m_offset += offset;
127
20.8M
  else if (seekType == librevenge::RVNG_SEEK_SET)
128
20.8M
    m_data->m_offset = offset;
129
19.0k
  else if (seekType == librevenge::RVNG_SEEK_END)
130
19.0k
    m_data->m_offset = offset+long(m_data->m_buffer.size());
131
132
21.0M
  if (m_data->m_offset < 0)
133
1
  {
134
1
    m_data->m_offset = 0;
135
1
    return -1;
136
1
  }
137
21.0M
  if (long(m_data->m_offset) > long(m_data->m_buffer.size()))
138
1.69M
  {
139
1.69M
    m_data->m_offset = long(m_data->m_buffer.size());
140
1.69M
    return -1;
141
1.69M
  }
142
143
19.4M
  return 0;
144
21.0M
}
145
146
bool WPSStringStream::isEnd()
147
1.91M
{
148
1.91M
  if (!m_data || long(m_data->m_offset) >= long(m_data->m_buffer.size()))
149
1.51k
    return true;
150
151
1.90M
  return false;
152
1.91M
}
153
154
bool WPSStringStream::isStructured()
155
4
{
156
4
  return false;
157
4
}
158
159
unsigned WPSStringStream::subStreamCount()
160
0
{
161
0
  return 0;
162
0
}
163
164
const char *WPSStringStream::subStreamName(unsigned)
165
0
{
166
0
  return nullptr;
167
0
}
168
169
bool WPSStringStream::existsSubStream(const char *)
170
0
{
171
0
  return false;
172
0
}
173
174
librevenge::RVNGInputStream *WPSStringStream::getSubStreamById(unsigned)
175
0
{
176
0
  return nullptr;
177
0
}
178
179
librevenge::RVNGInputStream *WPSStringStream::getSubStreamByName(const char *)
180
0
{
181
0
  return nullptr;
182
0
}
183
184
/* vim:set shiftwidth=4 softtabstop=4 noexpandtab: */