Skip to content
This repository was archived by the owner on May 27, 2026. It is now read-only.

Commit 41444cc

Browse files
committed
BUG: Replace strncpy with snprintf to ensure NUL termination
GCC's -Wstringop-truncation flagged 6 calls in itkScancoImageIO.cxx where strncpy was invoked with a bound equal to the destination size. When the source string is at least as long as the destination, strncpy leaves the buffer without a NUL terminator, causing undefined behavior in subsequent C-string accessors (GetVersion, GetPatientName, etc.). The in-memory header buffers (m_Version[18], m_PatientName[42], m_CreationDate[32], m_ModificationDate[32], m_RescaleUnits[18], m_CalibrationData[66]) are explicitly sized two bytes wider than the on-disk fixed-width fields (16, 40, 8/decoded-32, 32, 16, 64) so that a NUL terminator always fits; itkISQHeaderIO.cxx:137 documents this with an explicit '\\0' write. Switch all six metadata-import sites and the five (six counting ModificationDate) public Set*() inline accessors to std::snprintf(dst, sizeof(dst), "%s", src), which always NUL-terminates and silently truncates oversized input. Add <cstdio> to both translation units.
1 parent 8c51433 commit 41444cc

2 files changed

Lines changed: 27 additions & 12 deletions

File tree

include/itkScancoImageIO.h

Lines changed: 13 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,7 @@
5555
#include "IOScancoExport.h"
5656

5757

58+
#include <cstdio>
5859
#include <fstream>
5960
#include "itkImageIOBase.h"
6061
#include "itkScancoDataManipulation.h"
@@ -167,7 +168,7 @@ class IOScanco_EXPORT ScancoImageIO : public ImageIOBase
167168
void
168169
SetVersion(const char * version)
169170
{
170-
strncpy(this->m_HeaderData.m_Version, version, 18);
171+
std::snprintf(this->m_HeaderData.m_Version, sizeof(this->m_HeaderData.m_Version), "%s", version);
171172
this->Modified();
172173
}
173174

@@ -179,7 +180,8 @@ class IOScanco_EXPORT ScancoImageIO : public ImageIOBase
179180
void
180181
SetCalibrationData(const char * calibrationData)
181182
{
182-
strncpy(this->m_HeaderData.m_CalibrationData, calibrationData, 66);
183+
std::snprintf(
184+
this->m_HeaderData.m_CalibrationData, sizeof(this->m_HeaderData.m_CalibrationData), "%s", calibrationData);
183185
this->Modified();
184186
}
185187

@@ -191,7 +193,8 @@ class IOScanco_EXPORT ScancoImageIO : public ImageIOBase
191193
void
192194
SetRescaleUnits(const char * rescaleUnits)
193195
{
194-
strncpy(this->m_HeaderData.m_RescaleUnits, rescaleUnits, 18);
196+
std::snprintf(
197+
this->m_HeaderData.m_RescaleUnits, sizeof(this->m_HeaderData.m_RescaleUnits), "%s", rescaleUnits);
195198
this->Modified();
196199
}
197200

@@ -284,7 +287,7 @@ class IOScanco_EXPORT ScancoImageIO : public ImageIOBase
284287
void
285288
SetPatientName(const char * patientName)
286289
{
287-
strncpy(this->m_HeaderData.m_PatientName, patientName, 42);
290+
std::snprintf(this->m_HeaderData.m_PatientName, sizeof(this->m_HeaderData.m_PatientName), "%s", patientName);
288291
this->Modified();
289292
}
290293

@@ -296,7 +299,8 @@ class IOScanco_EXPORT ScancoImageIO : public ImageIOBase
296299
void
297300
SetCreationDate(const char * creationDate)
298301
{
299-
strncpy(this->m_HeaderData.m_CreationDate, creationDate, 32);
302+
std::snprintf(
303+
this->m_HeaderData.m_CreationDate, sizeof(this->m_HeaderData.m_CreationDate), "%s", creationDate);
300304
this->Modified();
301305
}
302306

@@ -308,7 +312,10 @@ class IOScanco_EXPORT ScancoImageIO : public ImageIOBase
308312
void
309313
SetModificationDate(const char * modificationDate)
310314
{
311-
strncpy(this->m_HeaderData.m_ModificationDate, modificationDate, 32);
315+
std::snprintf(this->m_HeaderData.m_ModificationDate,
316+
sizeof(this->m_HeaderData.m_ModificationDate),
317+
"%s",
318+
modificationDate);
312319
this->Modified();
313320
}
314321

src/itkScancoImageIO.cxx

Lines changed: 14 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@
4242
#include "itkISQHeaderIO.h"
4343

4444
#include <algorithm>
45+
#include <cstdio>
4546
#include <ctime>
4647
#include <filesystem>
4748

@@ -354,23 +355,28 @@ ScancoImageIO::SetHeaderFromMetaDataDictionary()
354355
std::string stringMeta;
355356
if (ExposeMetaData<std::string>(metaData, "Version", stringMeta))
356357
{
357-
strncpy(this->m_HeaderData.m_Version, stringMeta.c_str(), 18);
358+
std::snprintf(this->m_HeaderData.m_Version, sizeof(this->m_HeaderData.m_Version), "%s", stringMeta.c_str());
358359
}
359360
if (ExposeMetaData<std::string>(metaData, "PatientName", stringMeta))
360361
{
361-
strncpy(this->m_HeaderData.m_PatientName, stringMeta.c_str(), 42);
362+
std::snprintf(
363+
this->m_HeaderData.m_PatientName, sizeof(this->m_HeaderData.m_PatientName), "%s", stringMeta.c_str());
362364
}
363365

364366
ExposeMetaData<int>(metaData, "PatientIndex", this->m_HeaderData.m_PatientIndex);
365367
ExposeMetaData<int>(metaData, "ScannerID", this->m_HeaderData.m_ScannerID);
366368

367369
if (ExposeMetaData<std::string>(metaData, "CreationDate", stringMeta))
368370
{
369-
strncpy(this->m_HeaderData.m_CreationDate, stringMeta.c_str(), 32);
371+
std::snprintf(
372+
this->m_HeaderData.m_CreationDate, sizeof(this->m_HeaderData.m_CreationDate), "%s", stringMeta.c_str());
370373
}
371374
if (ExposeMetaData<std::string>(metaData, "ModificationDate", stringMeta))
372375
{
373-
strncpy(this->m_HeaderData.m_ModificationDate, stringMeta.c_str(), 32);
376+
std::snprintf(this->m_HeaderData.m_ModificationDate,
377+
sizeof(this->m_HeaderData.m_ModificationDate),
378+
"%s",
379+
stringMeta.c_str());
374380
}
375381

376382
ExposeMetaData<double>(metaData, "SliceThickness", this->m_HeaderData.m_SliceThickness);
@@ -399,11 +405,13 @@ ScancoImageIO::SetHeaderFromMetaDataDictionary()
399405
ExposeMetaData<int>(metaData, "RescaleType", this->m_HeaderData.m_RescaleType);
400406
if (ExposeMetaData<std::string>(metaData, "RescaleUnits", stringMeta))
401407
{
402-
strncpy(this->m_HeaderData.m_RescaleUnits, stringMeta.c_str(), 18);
408+
std::snprintf(
409+
this->m_HeaderData.m_RescaleUnits, sizeof(this->m_HeaderData.m_RescaleUnits), "%s", stringMeta.c_str());
403410
}
404411
if (ExposeMetaData<std::string>(metaData, "CalibrationData", stringMeta))
405412
{
406-
strncpy(this->m_HeaderData.m_CalibrationData, stringMeta.c_str(), 66);
413+
std::snprintf(
414+
this->m_HeaderData.m_CalibrationData, sizeof(this->m_HeaderData.m_CalibrationData), "%s", stringMeta.c_str());
407415
}
408416

409417
ExposeMetaData<double>(metaData, "RescaleSlope", this->m_HeaderData.m_RescaleSlope);

0 commit comments

Comments
 (0)