obs-studio/build_dependencies/aja/include/ajalibraries/ajabase/common/dpx_hdr.h
Ward Nakchbandi b48576284b first commit
2023-03-04 20:33:16 +03:00

486 lines
15 KiB
C++

/* SPDX-License-Identifier: MIT */
/**
@file dpx_hdr.h
@brief Declaration of DpxHdr class adapted from STwo's dpx file I/O.
@copyright (C) 2015-2021 AJA Video Systems, Inc. All rights reserved.
**/
#ifndef DPX_HDR_H
#define DPX_HDR_H
#include "public.h"
#include "ajabase/common/types.h"
#include "ajabase/system/system.h"
#include <string>
#define DPX_C_MAGIC 0x53445058 /**< little-endian magic number */
#define DPX_C_MAGIC_BE 0x58504453 /**< big-endian magic number */
#define DPX_C_VERSION "V1.0"
#define DPX_C_UNDEFINED_FLOAT 0xffffffff /**< DPX undefined float */
#define SWAP16(e,v) ((e) ? htons(v) : (v))
#define SWAP32(e,v) ((e) ? htonl(v) : (v))
#define SWAPR32(e,v) ((e) ? htonf(v) : (v))
#define UNSWAP16(e,v) ((e) ? ntohs(v) : (v))
#define UNSWAP32(e,v) ((e) ? ntohl(v) : (v))
#define UNSWAPR32(e,v) ((e) ? ntohf(v) : (v))
#define DPX_VALID(p) \
((p) && (((p)->file_info.magic_num==DPX_C_MAGIC) || \
((p)->file_info.magic_num==DPX_C_MAGIC_BE)))
#define DPX_IS_BE(p) \
((p) && ((p)->file_info.magic_num == DPX_C_MAGIC_BE))
#define DPX_C_IMAGE_ELEM_DESC_RGB 50
#define DPX_C_IMAGE_ELEM_DESC_RGBA 51
#define DPX_C_IMAGE_ELEM_DESC_ARGB 52
#define DPX_C_IMAGE_ELEM_DESC_422 100
#define DPX_C_IMAGE_ELEM_DESC_444 102
typedef struct dpx_file_info_struct
{
uint32_t magic_num; /* magic number 0x53445058 (SDPX) or 0x58504453 (XPDS) */
uint32_t offset; /* offset to image data in bytes */
uint8_t vers[8]; /* which header format version is being used (v1.0)*/
uint32_t file_size; /* file size in bytes */
uint32_t ditto_key; /* read time short cut - 0 = same, 1 = new */
uint32_t gen_hdr_size; /* generic header length in bytes */
uint32_t ind_hdr_size; /* industry header length in bytes */
uint32_t user_data_size;/* user-defined data length in bytes */
uint8_t file_name[100]; /* iamge file name */
uint8_t create_time[24]; /* file creation date "yyyy:mm:dd:hh:mm:ss:LTZ" */
uint8_t creator[100]; /* file creator's name */
uint8_t project[200]; /* project name */
uint8_t copyright[200]; /* right to use or copyright info */
uint32_t key; /* encryption ( FFFFFFFF = unencrypted ) */
union
{
uint8_t Reserved[104]; /* reserved field TBD (need to pad) */
struct
{
uint32_t tcFrame; /* Timecode as a frame number */
uint32_t filenum; /* FileNumber of preallocated files */
uint8_t rid;
uint8_t sid;
uint8_t tid;
uint8_t pad;
} s2;
} resv;
} DPX_file_info_t;
typedef struct dpx_image_element_struct
{
uint32_t data_sign; /* data sign (0 = unsigned, 1 = signed ) */
/* "Core set images are unsigned" */
uint32_t ref_low_data; /* reference low data code value */
float ref_low_quantity; /* reference low quantity represented */
uint32_t ref_high_data; /* reference high data code value */
float ref_high_quantity; /* reference high quantity represented */
uint8_t descriptor; /* descriptor for image element */
uint8_t transfer; /* transfer uint8_tacteristics for element */
uint8_t colorimetric; /* colormetric specification for element */
uint8_t bit_size; /* bit size for element */
uint16_t packing; /* packing for element */
uint16_t encoding; /* encoding for element */
uint32_t data_offset; /* offset to data of element */
uint32_t eol_padding; /* end of line padding used in element */
uint32_t eo_image_padding; /* end of image padding used in element */
uint8_t description[32]; /* description of element */
} DPX_image_element_t;
typedef struct dpx_image_info_struct
{
uint16_t orientation; /* image orientation */
uint16_t element_number; /* number of image elements */
uint32_t pixels_per_line; /* or x value */
uint32_t lines_per_image_ele; /* or y value, per element */
DPX_image_element_t image_element[8];
uint8_t reserved[52]; /* reserved for future use (padding) */
} DPX_image_info_t;
typedef struct dpx_image_source_struct
{
uint32_t x_offset; /* X offset */
uint32_t y_offset; /* Y offset */
float x_center; /* X center */
float y_center; /* Y center */
uint32_t x_orig_size; /* X original size */
uint32_t y_orig_size; /* Y original size */
uint8_t file_name[100]; /* source image file name */
uint8_t creation_time[24]; /* source image creation date and time */
uint8_t input_dev[32]; /* input device name */
uint8_t input_serial[32]; /* input device serial number */
uint16_t border[4]; /* border validity (XL, XR, YT, YB) */
uint32_t pixel_aspect[2]; /* pixel aspect ratio (H:V) */
uint8_t reserved[28]; /* reserved for future use (padding) */
} DPX_image_source_t;
typedef struct dpx_motion_picture_film_header_struct
{
uint8_t film_mfg_id[2]; /* film manufacturer ID code (2 digits from film edge code) */
uint8_t film_type[2]; /* file type (2 digits from film edge code) */
uint8_t offset[2]; /* offset in perfs (2 digits from film edge code)*/
uint8_t prefix[6]; /* prefix (6 digits from film edge code) */
uint8_t count[4]; /* count (4 digits from film edge code)*/
uint8_t format[32]; /* format (i.e. academy) */
uint32_t frame_position; /* frame position in sequence */
uint32_t sequence_len; /* sequence length in frames */
uint32_t held_count; /* held count (1 = default) */
float frame_rate; /* frame rate of original in frames/sec */
float shutter_angle; /* shutter angle of camera in degrees */
uint8_t frame_id[32]; /* frame identification (i.e. keyframe) */
uint8_t slate_info[100]; /* slate information */
uint8_t reserved[56]; /* reserved for future use (padding) */
} DPX_film_t;
typedef struct dpx_television_header_struct
{
uint32_t tim_code; /* SMPTE time code */
uint32_t userBits; /* SMPTE user bits */
uint8_t interlace; /* interlace ( 0 = noninterlaced, 1 = 2:1 interlace*/
uint8_t field_num; /* field number */
uint8_t video_signal; /* video signal standard (table 4)*/
uint8_t unused; /* used for byte alignment only */
float hor_sample_rate; /* horizontal sampling rate in Hz */
float ver_sample_rate; /* vertical sampling rate in Hz */
float frame_rate; /* temporal sampling rate or frame rate in Hz */
float time_offset; /* time offset from sync to first pixel */
float gamma; /* gamma value */
float black_level; /* black level code value */
float black_gain; /* black gain */
float break_point; /* breakpoint */
float white_level; /* reference white level code value */
float integration_times; /* integration time(s) */
uint8_t reserved[76]; /* reserved for future use (padding) */
} DPX_television_t;
typedef struct dpx_header_struct
{
DPX_file_info_t file_info;
DPX_image_info_t image_info;
DPX_image_source_t image_source;
DPX_film_t film_header;
DPX_television_t tv_header;
#ifdef NTV4_RAID_SUPPORT
uint8_t reserved[2048];
#endif
} DPX_header_t;
uint32_t AJA_EXPORT dpx_get_u32(const uint32_t *ptr, bool BE );
void AJA_EXPORT dpx_set_u32(uint32_t *ptr, bool BE, uint32_t val );
uint16_t AJA_EXPORT dpx_get_u16(const uint16_t *ptr, bool BE );
void AJA_EXPORT dpx_set_u16(uint16_t *ptr, bool BE, uint16_t val );
float AJA_EXPORT dpx_get_r32(const float *ptr, bool BE );
void AJA_EXPORT dpx_set_r32(float *ptr, bool BE, float val );
#define FLD_OFFET( TYPE,field) \
((uint32_t)(&(((TYPE *)0)->field)))
#define DPX_GET_U32(hdr,fld) \
DPX_VALID(hdr) ? \
dpx_get_u32(&(hdr)->fld,DPX_IS_BE(hdr)) : \
(uint32_t)(-1)
#define DPX_SET_U32(hdr,fld,val) \
do { \
if ( DPX_VALID(hdr)) \
dpx_set_u32(&(hdr)->fld,DPX_IS_BE(hdr),val); \
} while(0)
#define DPX_GET_R32(hdr,fld) \
DPX_VALID(hdr) ? \
dpx_get_r32(&(hdr)->fld,DPX_IS_BE(hdr)) : \
(float)(0xffffffff)
#define DPX_SET_R32(hdr,fld,val) \
do { \
if ( DPX_VALID(hdr)) \
dpx_set_r32(&(hdr)->fld,DPX_IS_BE(hdr),val); \
} while(0)
#define DPX_GET_U16(hdr,fld) \
DPX_VALID(hdr) ? \
dpx_get_u16(&(hdr)->fld,DPX_IS_BE(hdr)) : \
(uint16_t)(-1)
#define DPX_SET_U16(hdr,fld,val) \
do { \
if ( DPX_VALID(hdr)) \
dpx_set_u16(&(hdr)->fld,DPX_IS_BE(hdr),val); \
} while(0)
#define DPX_GET_U8(hdr,fld) \
DPX_VALID(hdr) ? (hdr)->fld : (uint8_t)(-1)
#define DPX_SET_U8(hdr,fld,val) \
if ( DPX_VALID(hdr)) \
(hdr)->fld = val
#define DPX_SET_TEXT(hdr,fld,buf,len) \
if ( DPX_VALID(hdr)) \
memcpy((void*)&((hdr)->fld),(const void*)buf,len)
#define DPX_GET_TEXT(hdr,fld,buf,len) \
DPX_VALID(hdr) ? \
memcpy((void*)buf,(const void*)&((hdr)->fld),len) : \
memset((void*)buf,0xff,len)
class AJA_EXPORT DpxHdr
{
public:
DpxHdr(void) { init(DPX_C_MAGIC_BE); }
~DpxHdr();
DpxHdr& operator=(const DpxHdr& rhs);
void init(uint32_t endianness);
bool valid() const;
bool IsBigEndian() { return DPX_IS_BE(&m_hdr); }
std::string get_fi_time_stamp() const;
void set_fi_time_stamp();
void set_s2_tcframe(uint32_t frame);
size_t get_s2_tcframe() const;
uint32_t get_s2_filenumber() const;
void set_s2_filenumber(uint32_t fr);
void set_s2_ids(uint8_t rid, uint8_t sid, uint8_t tid);
void get_s2_ids(uint8_t *rid, uint8_t *sid, uint8_t *tid) const;
size_t get_file_size();
size_t get_generic_hdr_size();
size_t get_industry_hdr_size();
size_t get_user_hdr_size();
// File Info access
//
size_t get_fi_image_offset() const;
void set_fi_image_offset(size_t offs );
size_t get_fi_file_size() const;
void set_fi_file_size(size_t offs );
std::string get_fi_version() const;
void set_fi_version(const std::string& str);
std::string get_fi_file_name() const;
void set_fi_file_name(const std::string& str);
std::string get_fi_creator() const;
void set_fi_creator(const std::string& str);
std::string get_fi_create_time() const;
void set_fi_create_time(const std::string& str);
std::string get_fi_project() const;
void set_fi_project(const std::string& str);
std::string get_fi_copyright() const;
void set_fi_copyright(const std::string& str);
// Image Info
void set_ii_orientation(uint16_t orientation );
uint16_t get_ii_orientation() const;
void set_ii_element_number(uint16_t element_number );
uint16_t get_ii_element_number() const;
void set_ii_pixels(uint32_t pixels );
size_t get_ii_pixels() const;
void set_ii_lines(uint32_t lines );
size_t get_ii_lines(void ) const;
size_t get_ii_image_size()
{
// Note: Incorrect for some configs
uint32_t expectedSize = -1;
if (get_ie_descriptor() == 50)
{
if ( get_ie_bit_size() == 10 )
expectedSize = (uint32_t)(get_ii_pixels() * get_ii_lines() * 4);
else
expectedSize = (uint32_t)(get_ii_pixels() * get_ii_lines() * 6); // 16 bit
}
else if (get_ie_descriptor() == 100)
{
if (get_ii_pixels() % 48 == 0)
expectedSize = (uint32_t)(get_ii_pixels() * get_ii_lines() * 8 / 3);
else
expectedSize = (uint32_t)(((get_ii_pixels()/48+1)*48) * get_ii_lines() * 8 / 3);
}
// rowBytes = (( width % 48 == 0 ) ? width : (((width / 48 ) + 1) * 48)) * 8 / 3;
if (0 == get_fi_file_size())
{
return (0);
}
uint32_t sizeInFile = (uint32_t)(get_fi_file_size() - get_fi_image_offset());
if ( sizeInFile < expectedSize)
return sizeInFile;
else
return expectedSize;
}
// Image Element
void set_ie_data_sign (uint32_t sign, int i=0);
size_t get_ie_data_sign(int i = 0);
void set_ie_ref_low_data(uint32_t data, int i=0);
size_t get_ie_ref_low_data(int i = 0) const;
void set_ie_ref_high_data(uint32_t data, int i=0);
size_t get_ie_ref_high_data(int i = 0) const;
void set_ie_ref_low_quantity(float data, int i=0);
float get_ie_ref_low_quantity(int i = 0) const;
void set_ie_ref_high_quantity(float data, int i=0);
float get_ie_ref_high_quantity(int i = 0) const;
void set_ie_descriptor(uint8_t desc, int i = 0);
uint8_t get_ie_descriptor(int i = 0) const;
void set_ie_transfer(uint8_t trans, int i = 0);
uint8_t get_ie_transfer(int i = 0) const;
void set_ie_colorimetric(uint8_t c, int i = 0);
uint8_t get_ie_colorimetric(int i = 0) const;
void set_ie_bit_size(uint8_t bits, int i = 0);
uint8_t get_ie_bit_size(int i = 0) const;
void set_ie_packing(uint16_t pack, int i = 0);
uint16_t get_ie_packing (int i = 0) const;
void set_ie_encoding(uint16_t enc, int i = 0);
uint16_t get_ie_encoding(int i = 0) const;
void set_ie_data_offset(uint32_t offs, int i = 0);
uint32_t get_ie_data_offset (int i = 0) const;
void set_ie_eol_padding(uint32_t padding, int i = 0);
uint32_t get_ie_eol_padding(int i = 0) const;
void set_ie_eo_image_padding(uint32_t padding, int i = 0);
uint32_t get_ie_eo_image_padding(int i = 0) const;
std::string get_ie_description(int i=0) const;
void set_ie_description(const std::string& str, int i = 0);
// Image Source access.
std::string get_is_filename() const;
void set_is_filename(const std::string& str);
std::string get_is_creation_time() const;
void set_is_creation_time(const std::string& str);
std::string get_is_input_device() const;
void set_is_input_device(const std::string& str);
std::string get_is_input_serial() const;
void set_is_input_serial(const std::string& str);
// Film header
std::string get_film_mfg_id() const;
void set_film_mfg_id(const std::string& str);
std::string get_film_type() const;
void set_film_type(const std::string& str);
std::string get_film_offset() const;
void set_film_offset(const std::string& str);
std::string get_film_prefix() const;
void set_film_prefix(const std::string& str);
std::string get_film_count() const;
void set_film_count(const std::string& str);
std::string get_film_format() const;
void set_film_format(const std::string& str);
size_t get_film_frame_position() const;
void set_film_frame_position(size_t pos );
size_t get_film_sequence_len() const;
void set_film_sequence_len(size_t len );
size_t get_film_held_count() const;
void set_film_held_count(size_t count );
float get_film_frame_rate () const;
void set_film_frame_rate (float len );
float get_film_shutter_angle() const;
void set_film_shutter_angle(float );
std::string get_film_frame_id() const;
void set_film_frame_id(const std::string& str);
std::string get_film_slate_info() const;
void set_film_slate_info(const std::string& str);
// TV header
size_t get_tv_timecode() const;
void set_tv_timecode(size_t tc);
size_t get_tv_userbits() const;
void set_tv_userbits(size_t tc);
float get_tv_frame_rate() const;
void set_tv_frame_rate(float fr);
uint8_t get_tv_interlace() const;
void set_tv_interlace(uint8_t interlace);
const DPX_header_t& GetHdr(void) const
{
return (m_hdr);
}
DPX_header_t& GetHdr(void)
{
return (m_hdr);
}
size_t GetHdrSize(void) const
{
return (sizeof(DPX_header_t));
}
private:
DPX_header_t m_hdr;
};
#endif // DPX_HDR_H