Segmentation fault (core dumped) while creeating and inseting information to a Tiff file

0

I am trying to create a (640*360) gray Tiff image but at some point a pointer is heading to an incorrect location, perhaps someone can tell me what is wrong with my code. The image is created at the end of the execution, but is 0 KB and is corrupted.

I would appreciate any advice regarding opening and working with binary files.

#include "TIFF.h"
#include "TiffImage.h"
#include <string>
#include <iostream>
#include <fstream>

int CTIFF::write(/*std::string origFilename, Hobject Image*/)
{
    std::string filename = "Result.tiff";
    std::ofstream tiffstream(filename, std::ios::binary);//open the file

    TiffHeader tiff_header_image;

    tiff_header_image.ifh.byte_order   = 0x4949; //0x4949 little indian endian OR 0x4D4D big endian
    tiff_header_image.ifh.const_0x002a = 0x002a; //Version number (always 42)
    tiff_header_image.ifh.ifd0_offset  = 0x000a; //offset from beginning of file to 'ifd0_num_entries'

    tiff_header_image.ifd0[IFD0_INDEX_IMAGEWIDTH].tag      = 0x0100;  // TIFFTAG_IMAGEWIDTH
    tiff_header_image.ifd0[IFD0_INDEX_IMAGEWIDTH].typ      = 0x0004;  // TIFFTYPE_LONG
    tiff_header_image.ifd0[IFD0_INDEX_IMAGEWIDTH].count    = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_IMAGEWIDTH].value    = 640;

    tiff_header_image.ifd0[IFD0_INDEX_IMAGELENGTH].tag     = 0x0101;  // TIFFTAG_IMAGELENGTH
    tiff_header_image.ifd0[IFD0_INDEX_IMAGELENGTH].typ     = 0x0004;  // TIFFTYPE_LONG
    tiff_header_image.ifd0[IFD0_INDEX_IMAGELENGTH].count   = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_IMAGELENGTH].value   = 360;

    tiff_header_image.ifd0[IFD0_INDEX_BITSPERSAMPLE].tag   = 0x0102;  // TIFFTAG_BITSPERSAMPLE
    tiff_header_image.ifd0[IFD0_INDEX_BITSPERSAMPLE].typ   = 0x0003;  // TIFFTYPE_SHORT
    tiff_header_image.ifd0[IFD0_INDEX_BITSPERSAMPLE].count = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_BITSPERSAMPLE].value = 8;

    tiff_header_image.ifd0[IFD0_INDEX_STRIPOFFSETS].tag    = 0x0111;  // TIFFTAG_STRIPOFFSETS
    tiff_header_image.ifd0[IFD0_INDEX_STRIPOFFSETS].typ    = 0x0004;  // TIFFTYPE_LONG
    tiff_header_image.ifd0[IFD0_INDEX_STRIPOFFSETS].count  = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_STRIPOFFSETS].value  = 1;       // "BlackIsZero"

    tiff_header_image.ifd0[IFD0_INDEX_STRIPBYTECOUNTS].tag   = 0x0117;  // TIFFTAG_STRIPBYTECOUNTS
    tiff_header_image.ifd0[IFD0_INDEX_STRIPBYTECOUNTS].typ   = 0x0004;  // TIFFTYPE_LONG
    tiff_header_image.ifd0[IFD0_INDEX_STRIPBYTECOUNTS].count = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_STRIPBYTECOUNTS].value = 230400;  //width x length

    tiff_header_image.ifd0_x_resolution.numerator   = 0x00000008; // 8 [cm / pixel] 
    tiff_header_image.ifd0_x_resolution.denominator = 0x00002710; // 10000 = 8 [um / pixel]

    tiff_header_image.ifd0_y_resolution.numerator   = 0x00000008; // 8 [cm / pixel] 
    tiff_header_image.ifd0_y_resolution.denominator = 0x00002710; // 10000 = 8 [um / pixel]

    tiff_header_image.exif_ifd[EXIFIFD_NUM_ENTRIES].tag     = 0x8769;  // EXIFTAG_EXPOSURE
    tiff_header_image.exif_ifd[EXIFIFD_NUM_ENTRIES].typ     = 0x0005;  // TIFFTYPE_RATIONAL
    tiff_header_image.exif_ifd[EXIFIFD_NUM_ENTRIES].count   = 0x0001;
    tiff_header_image.exif_ifd[EXIFIFD_NUM_ENTRIES].value   = 0x00FE;  // offset to 'exif_ifd_exposure_time'

    tiff_header_image.exif_ifd[EXIFIFD_SUBSETIME_STRLEN].tag   = 0x8769;  // EXIFTAG_SUBSECTIME
    tiff_header_image.exif_ifd[EXIFIFD_SUBSETIME_STRLEN].typ   = 0x0002;  // TIFFTYPE_ASCII
    tiff_header_image.exif_ifd[EXIFIFD_SUBSETIME_STRLEN].count = 0x000a;  // 10 bytes: 9 decimals + '\0'
    tiff_header_image.exif_ifd[EXIFIFD_SUBSETIME_STRLEN].value = 0x0108;  // offset to 'exif_ifd_subsec_time'

    tiff_header_image.exif_ifd_exposure_time.numerator   = 0x00000000;  // exposure-time in [usec]
    tiff_header_image.exif_ifd_exposure_time.denominator = 0x000F4240;  // 1000000 -> numerator in micro-seconds

    if (tiffstream.is_open())
    {
        tiffstream.write(reinterpret_cast<const char*>(&tiff_header_image), sizeof(tiff_header_image));

        int   width  = 640;
        int   height = 360;

        unsigned char pixelValue = 128; //gray
        for (int r = 0; r < height; r++)
            for (int c = 0; c < width; c++)
            {
                tiffstream.write(reinterpret_cast<const char*>(&pixelValue), sizeof(unsigned char));
            }
        std::cout << "Output operation successfully performed\n";
        tiffstream.close();

    }
    else
    {
        std::cout << "Error opening file";
    }
    return 0;
};
c++
tiff
asked on Stack Overflow Feb 23, 2018 by Alejandro Rubio • edited Jan 8, 2019 by Cœur

2 Answers

0

The problem you face may be caused by ofstream::ofstream: This constructor waits an const char* as first parameter, so write:

std::string filename = "Result.tiff";
std::ofstream tiffstream(filename.c_str(), std::ios::binary);//open the file

Or

std::ofstream tiffstream("Result.tiff", std::ios::binary);//open the file

To prevent the problem.

You should have seen this I you compiled with warnings turns on (-Wall on gcc or clang).

Moreover, you original post in not complete enough to be sure that this answer is adapted to your question: ignoring what TiffHeader is, we can't be sure there is not another issue.

answered on Stack Overflow Feb 26, 2018 by Mathieu
0

I solve it just paying attention to the information declared, info was being written in worng places. Here's the code:

#include "TIFF.h"
#include "TiffImage.h"
#include <string>
#include <iostream>
#include <fstream>

std::wstring s2ws(const std::string& s);

int CTIFF::write(/*std::string origFilename Hobject Image*/)
{


  std::string filename = "Result.tiff";

    std::ofstream tiffstream(filename, std::ios::binary);//open the file

    TiffHeader tiff_header_image;

    tiff_header_image.ifh.byte_order   = 0x4949; //0x4949 little indian endian OR 0x4D4D big endian
    tiff_header_image.ifh.const_0x002a = 0x002a; //Version number (always 42)
    tiff_header_image.ifh.ifd0_offset  = 0x000a; //offset from beginning of file to 'ifd0_num_entries'

    tiff_header_image.ifd0_num_entries = 14;

    tiff_header_image.ifd0[IFD0_INDEX_IMAGEWIDTH].tag      = 0x0100;  // TIFFTAG_IMAGEWIDTH
    tiff_header_image.ifd0[IFD0_INDEX_IMAGEWIDTH].typ      = 0x0004;  // TIFFTYPE_LONG
    tiff_header_image.ifd0[IFD0_INDEX_IMAGEWIDTH].count    = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_IMAGEWIDTH].value    = 640;

    tiff_header_image.ifd0[IFD0_INDEX_IMAGELENGTH].tag     = 0x0101;  // TIFFTAG_IMAGELENGTH
    tiff_header_image.ifd0[IFD0_INDEX_IMAGELENGTH].typ     = 0x0004;  // TIFFTYPE_LONG
    tiff_header_image.ifd0[IFD0_INDEX_IMAGELENGTH].count   = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_IMAGELENGTH].value   = 360;

    tiff_header_image.ifd0[IFD0_INDEX_BITSPERSAMPLE].tag   = 0x0102;  // TIFFTAG_BITSPERSAMPLE
    tiff_header_image.ifd0[IFD0_INDEX_BITSPERSAMPLE].typ   = 0x0003;  // TIFFTYPE_SHORT
    tiff_header_image.ifd0[IFD0_INDEX_BITSPERSAMPLE].count = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_BITSPERSAMPLE].value = 8;

    tiff_header_image.ifd0[IFD0_INDEX_COMPRESSION].tag   = 0x0103;  // TIFFTAG_COMPRESSION
tiff_header_image.ifd0[IFD0_INDEX_COMPRESSION].typ   = 0x0003;  // TIFFTYPE_SHORT
tiff_header_image.ifd0[IFD0_INDEX_COMPRESSION].count = 0x0001;
tiff_header_image.ifd0[IFD0_INDEX_COMPRESSION].value = 1;       // "No compression"

tiff_header_image.ifd0[IFD0_INDEX_PHOTOMETRICINTERPRETATION].tag   = 0x0106;  // TIFFTAG_PHOTOMETRIC
tiff_header_image.ifd0[IFD0_INDEX_PHOTOMETRICINTERPRETATION].typ   = 0x0003;  // TIFFTYPE_SHORT
tiff_header_image.ifd0[IFD0_INDEX_PHOTOMETRICINTERPRETATION].count = 0x0001;
tiff_header_image.ifd0[IFD0_INDEX_PHOTOMETRICINTERPRETATION].value = 1;       // "BlackIsZero"

tiff_header_image.ifd0[IFD0_INDEX_STRIPOFFSETS].tag   = 0x0111;  // TIFFTAG_STRIPOFFSETS
tiff_header_image.ifd0[IFD0_INDEX_STRIPOFFSETS].typ   = 0x0004;  // TIFFTYPE_LONG
tiff_header_image.ifd0[IFD0_INDEX_STRIPOFFSETS].count = 0x0001;
tiff_header_image.ifd0[IFD0_INDEX_STRIPOFFSETS].value = 0x0110;  // offset to image data from beginning of file

tiff_header_image.ifd0[IFD0_INDEX_SAMPLESPERPIXEL].tag   = 0x0115;  // TIFFTAG_SAMPLESPERPIXEL
tiff_header_image.ifd0[IFD0_INDEX_SAMPLESPERPIXEL].typ   = 0x0003;  // TIFFTYPE_SHORT
tiff_header_image.ifd0[IFD0_INDEX_SAMPLESPERPIXEL].count = 0x0001;
tiff_header_image.ifd0[IFD0_INDEX_SAMPLESPERPIXEL].value = 1;

    tiff_header_image.ifd0[IFD0_INDEX_ROWSPERSTRIP].tag   = 0x0116;  // TIFFTAG_ROWSPERSTRIP
    tiff_header_image.ifd0[IFD0_INDEX_ROWSPERSTRIP].typ   = 0x0004;  // TIFFTYPE_LONG
    tiff_header_image.ifd0[IFD0_INDEX_ROWSPERSTRIP].count = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_ROWSPERSTRIP].value = 360;      // same as TIFFTAG_IMAGELENGTH, usually 360

    tiff_header_image.ifd0[IFD0_INDEX_STRIPBYTECOUNTS].tag   = 0x0117;  // TIFFTAG_STRIPBYTECOUNTS
    tiff_header_image.ifd0[IFD0_INDEX_STRIPBYTECOUNTS].typ   = 0x0004;  // TIFFTYPE_LONG
    tiff_header_image.ifd0[IFD0_INDEX_STRIPBYTECOUNTS].count = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_STRIPBYTECOUNTS].value = 230400;  //width x length

    tiff_header_image.ifd0[IFD0_INDEX_XRESOLUTION].tag   = 0x011a;  // TIFFTAG_XRESOLUTION
    tiff_header_image.ifd0[IFD0_INDEX_XRESOLUTION].typ   = 0x0005;  // TIFFTYPE_RATIONAL
    tiff_header_image.ifd0[IFD0_INDEX_XRESOLUTION].count = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_XRESOLUTION].value = 0x00CC; // offset to 'ifd0_x_resolution'

    tiff_header_image.ifd0[IFD0_INDEX_YRESOLUTION].tag   = 0x011b;  // TIFFTAG_XRESOLUTION
    tiff_header_image.ifd0[IFD0_INDEX_YRESOLUTION].typ   = 0x0005;  // TIFFTYPE_RATIONAL
    tiff_header_image.ifd0[IFD0_INDEX_YRESOLUTION].count = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_YRESOLUTION].value = 0x00D4;  // offset to 'ifd0_y_resolution'

    tiff_header_image.ifd0[IFD0_INDEX_RESOLUTIONUNIT].tag   = 0x0128;  // TIFFTAG_RESOLUTIONUNIT
    tiff_header_image.ifd0[IFD0_INDEX_RESOLUTIONUNIT].typ   = 0x0003;  // TIFFTYPE_SHORT
    tiff_header_image.ifd0[IFD0_INDEX_RESOLUTIONUNIT].count = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_RESOLUTIONUNIT].value = 3;       // "Centimeter"

    tiff_header_image.ifd0[IFD0_INDEX_DATE_TIME].tag   = 0x0132;  // TIFFTAG_DATETIME
    tiff_header_image.ifd0[IFD0_INDEX_DATE_TIME].typ   = 0x0002;  // TIFFTYPE_ASCII
    tiff_header_image.ifd0[IFD0_INDEX_DATE_TIME].count = 0x0014;  // 20 bytes string, format: "YYYY:MM:DD HH:MM:SS"
    tiff_header_image.ifd0[IFD0_INDEX_DATE_TIME].value = 0x00B8;  // offset to 'ifd0_date_time'

    tiff_header_image.ifd0[IFD0_INDEX_EXIFIFD].tag   = 0x8769;  // TIFFTAG_EXIFIFD
    tiff_header_image.ifd0[IFD0_INDEX_EXIFIFD].typ   = 0x0004;  // TIFFTYPE_LONG
    tiff_header_image.ifd0[IFD0_INDEX_EXIFIFD].count = 0x0001;
    tiff_header_image.ifd0[IFD0_INDEX_EXIFIFD].value = 0x00DC;  // offset to 'exif_ifd_num_entries'

    tiff_header_image.ifd0_next_offset = 0; 

    tiff_header_image.ifd0_x_resolution.numerator   = 0x00000008; // 8 [cm / pixel] 
    tiff_header_image.ifd0_x_resolution.denominator = 0x00002710; // 10000 = 8 [um / pixel]

    tiff_header_image.ifd0_y_resolution.numerator   = 0x00000008; // 8 [cm / pixel] 
    tiff_header_image.ifd0_y_resolution.denominator = 0x00002710; // 10000 = 8 [um / pixel]

    tiff_header_image.exif_ifd_num_entries = 2; 

    tiff_header_image.exif_ifd[0].tag     = 0x8769;  // EXIFTAG_EXPOSURE
  tiff_header_image.exif_ifd[0].typ     = 0x0005;  // TIFFTYPE_RATIONAL
  tiff_header_image.exif_ifd[0].count   = 0x0001;
    tiff_header_image.exif_ifd[0].value   = 0x0102;  // offset to 'exif_ifd_exposure_time'

    tiff_header_image.exif_ifd[0].tag     = 0x9290;  // EXIFTAG_SUBSECTIME
  tiff_header_image.exif_ifd[0].typ     = 0x0002;  // TIFFTYPE_ASCII
  tiff_header_image.exif_ifd[0].count   = 0x000a;  // 10 bytes: 9 decimals + '\0'
    tiff_header_image.exif_ifd[0].value   = 0x010C;  // offset to 'exif_ifd_subsec_time'

    tiff_header_image.exif_ifd_next_offset = 0; 

    tiff_header_image.exif_ifd_exposure_time.numerator   = 0x00000000;  // exposure-time in [usec]
    tiff_header_image.exif_ifd_exposure_time.denominator = 0x000F4240;  // 1000000 -> numerator in micro-seconds

    if(tiffstream.is_open()){

      tiffstream.write(reinterpret_cast<const char*>(&tiff_header_image), sizeof(tiff_header_image));

      int      width  = 640;
      int      height = 360;

      unsigned char pixelValue = 128; //gray
      for (int r = 0; r < height; r++)
        for (int c = 0; c < width; c++){
          tiffstream.write(reinterpret_cast<const char*>(&pixelValue), sizeof(unsigned char));
        }
      std::cout << "Output operation successfully performed\n";
      tiffstream.close();

    }
    else{
      std::cout << "Error opening file";
  }

  return 0;
};
answered on Stack Overflow Feb 27, 2018 by Alejandro Rubio

User contributions licensed under CC BY-SA 3.0