1 /* GStreamer 2 * Copyright (C) 2008-2009 Sebastian Dröge <sebastian.droege@collabora.co.uk> 3 * 4 * This library is free software; you can redistribute it and/or 5 * modify it under the terms of the GNU Library General Public 6 * License as published by the Free Software Foundation; either 7 * version 2 of the License, or (at your option) any later version. 8 * 9 * This library is distributed in the hope that it will be useful, 10 * but WITHOUT ANY WARRANTY; without even the implied warranty of 11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 12 * Library General Public License for more details. 13 * 14 * You should have received a copy of the GNU Library General Public 15 * License along with this library; if not, write to the 16 * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, 17 * Boston, MA 02110-1301, USA. 18 */ 19 20 #ifndef __MXF_DEMUX_H__ 21 #define __MXF_DEMUX_H__ 22 23 #include <gst/gst.h> 24 #include <gst/base/gstadapter.h> 25 #include <gst/base/gstflowcombiner.h> 26 #include <gst/video/video.h> 27 28 #include "mxfessence.h" 29 30 G_BEGIN_DECLS 31 32 #define GST_TYPE_MXF_DEMUX \ 33 (gst_mxf_demux_get_type()) 34 #define GST_MXF_DEMUX(obj) \ 35 (G_TYPE_CHECK_INSTANCE_CAST((obj),GST_TYPE_MXF_DEMUX,GstMXFDemux)) 36 #define GST_MXF_DEMUX_CLASS(klass) \ 37 (G_TYPE_CHECK_CLASS_CAST((klass),GST_TYPE_MXF_DEMUX,GstMXFDemuxClass)) 38 #define GST_IS_MXF_DEMUX(obj) \ 39 (G_TYPE_CHECK_INSTANCE_TYPE((obj),GST_TYPE_MXF_DEMUX)) 40 #define GST_IS_MXF_DEMUX_CLASS(klass) \ 41 (G_TYPE_CHECK_CLASS_TYPE((klass),GST_TYPE_MXF_DEMUX)) 42 typedef struct _GstMXFDemux GstMXFDemux; 43 typedef struct _GstMXFDemuxClass GstMXFDemuxClass; 44 45 #define GST_TYPE_MXF_DEMUX_PAD (gst_mxf_demux_pad_get_type()) 46 #define GST_MXF_DEMUX_PAD(pad) (G_TYPE_CHECK_INSTANCE_CAST((pad),GST_TYPE_MXF_DEMUX_PAD,GstMXFDemuxPad)) 47 #define GST_MXF_DEMUX_PAD_CAST(pad) ((GstMXFDemuxPad *) pad) 48 #define GST_IS_MXF_DEMUX_PAD(pad) (G_TYPE_CHECK_INSTANCE_TYPE((pad),GST_TYPE_MXF_DEMUX_PAD)) 49 typedef struct _GstMXFDemuxPad GstMXFDemuxPad; 50 typedef struct _GstMXFDemuxPadClass GstMXFDemuxPadClass; 51 52 53 /* 54 * GstMXFKLV is used to pass around information about a KLV. 55 * 56 * It optionally contains the content of the klv (data field). 57 */ 58 typedef struct { 59 MXFUL key; 60 guint64 offset; /* absolute offset of K */ 61 gsize length; /* Size of data (i.e. V) */ 62 guint64 data_offset; /* relative offset of data (i.e. size of 'KL') */ 63 GstBuffer *data; /* Can be NULL in pull-mode. */ 64 65 /* For partial reads (ex: clip/custom wrapping essence), the amount of data 66 * already consumed within. If 0, all of length+data_offset was consumed */ 67 guint64 consumed; 68 } GstMXFKLV; 69 70 71 typedef enum { 72 GST_MXF_DEMUX_STATE_UNKNOWN, /* Still looking for run-in/klv */ 73 GST_MXF_DEMUX_STATE_KLV, /* Next read/fetch is a KLV */ 74 GST_MXF_DEMUX_STATE_ESSENCE /* Next read/fetch is within a KLV (i.e. non-frame-wrapped) */ 75 } GstMXFDemuxState; 76 77 typedef struct _GstMXFDemuxPartition GstMXFDemuxPartition; 78 typedef struct _GstMXFDemuxEssenceTrack GstMXFDemuxEssenceTrack; 79 80 struct _GstMXFDemuxPartition 81 { 82 MXFPartitionPack partition; 83 MXFPrimerPack primer; 84 gboolean parsed_metadata; 85 86 /* Relative offset at which essence starts within this partition. 87 * 88 * For Frame wrapping, the position of the first KLV 89 * For Clip/Custom wrapping, the position of the first byte of essence in the KLV 90 **/ 91 guint64 essence_container_offset; 92 93 /* If the partition contains a single essence track, point to it */ 94 GstMXFDemuxEssenceTrack *single_track; 95 96 /* For clip-based wrapping, the essence KLV */ 97 GstMXFKLV clip_klv; 98 }; 99 100 #define MXF_INDEX_DELTA_ID_UNKNOWN -1 101 #define MXF_INDEX_DELTA_ID_IGNORE -2 102 103 struct _GstMXFDemuxEssenceTrack 104 { 105 guint32 body_sid; 106 guint32 index_sid; 107 guint32 track_number; 108 109 /* delta id, the position of this track in the container package delta table 110 * (if the track is in an interleaved essence container) 111 * 112 * Special values: 113 * * -1 Not discovered yet 114 * * -2 Ignore delta entry (if index table is not present or not complete) 115 */ 116 gint32 delta_id; 117 118 guint32 track_id; 119 MXFUMID source_package_uid; 120 121 /* Position and duration in edit units */ 122 gint64 position; 123 gint64 duration; 124 125 GArray *offsets; 126 127 MXFMetadataSourcePackage *source_package; 128 MXFMetadataTimelineTrack *source_track; 129 130 gpointer mapping_data; 131 const MXFEssenceElementHandler *handler; 132 MXFEssenceElementHandleFunc handle_func; 133 134 GstTagList *tags; 135 136 GstCaps *caps; 137 gboolean intra_only; 138 139 MXFEssenceWrapping wrapping; 140 141 /* Minimum number of edit unit to send in one go. 142 * Default : 1 143 * Used for raw audio track */ 144 guint min_edit_units; 145 }; 146 147 typedef struct 148 { 149 /* absolute byte offset excluding run_in, 0 if uninitialized */ 150 guint64 offset; 151 152 /* PTS edit unit number or G_MAXUINT64 */ 153 guint64 pts; 154 155 /* DTS edit unit number if we got here via PTS */ 156 guint64 dts; 157 158 /* Duration in edit units */ 159 guint64 duration; 160 161 gboolean keyframe; 162 gboolean initialized; 163 164 /* Size, used for non-frame-wrapped content */ 165 guint64 size; 166 } GstMXFDemuxIndex; 167 168 typedef struct 169 { 170 guint32 body_sid; 171 guint32 index_sid; 172 173 /* Array of MXFIndexTableSegment, sorted by DTS 174 * Note: Can be empty and can be sparse (i.e. not cover every edit unit) */ 175 GArray *segments; 176 177 /* Delta entry to which reordering should be applied (-1 == no reordering) */ 178 gint reordered_delta_entry; 179 180 /* Array of gint8 reverse temporal offsets. 181 * Contains the shift to apply to an entry DTS to get the PTS 182 * 183 * Can be NULL if the content doesn't have temporal shifts (i.e. all present 184 * entries have a temporal offset of 0) */ 185 GArray *reverse_temporal_offsets; 186 187 /* Greatest temporal offset value contained within offsets. 188 * Unsigned because the smallest value is 0 (no reordering) */ 189 guint max_temporal_offset; 190 } GstMXFDemuxIndexTable; 191 192 struct _GstMXFDemuxPad 193 { 194 GstPad parent; 195 196 guint32 track_id; 197 gboolean need_segment; 198 199 GstClockTime position; 200 gdouble position_accumulated_error; 201 /* Current position in the material track (in edit units) */ 202 gint64 current_material_track_position; 203 204 gboolean eos, discont; 205 206 GstTagList *tags; 207 208 MXFMetadataGenericPackage *material_package; 209 MXFMetadataTimelineTrack *material_track; 210 211 GstVideoTimeCode start_timecode; 212 213 guint current_component_index; 214 MXFMetadataSourceClip *current_component; 215 216 /* Position in the material track where this component started */ 217 gint64 current_component_start_position; 218 219 /* Position/duration in the source track */ 220 gint64 current_component_start; 221 gint64 current_component_duration; 222 223 /* Current essence track and position (in edit units) */ 224 GstMXFDemuxEssenceTrack *current_essence_track; 225 gint64 current_essence_track_position; 226 }; 227 228 struct _GstMXFDemuxPadClass 229 { 230 GstPadClass parent; 231 }; 232 233 struct _GstMXFDemux 234 { 235 GstElement element; 236 237 GstPad *sinkpad; 238 GPtrArray *src; 239 240 /* < private > */ 241 GstMXFDemuxState state; 242 243 gboolean have_group_id; 244 guint group_id; 245 246 GstAdapter *adapter; 247 248 GstFlowCombiner *flowcombiner; 249 250 GstSegment segment; 251 guint32 seqnum; 252 253 GstEvent *close_seg_event; 254 255 guint64 offset; 256 257 gboolean random_access; 258 gboolean flushing; 259 260 guint64 run_in; 261 262 guint64 header_partition_pack_offset; 263 guint64 footer_partition_pack_offset; 264 265 /* MXF file state */ 266 GList *partitions; 267 GstMXFDemuxPartition *current_partition; 268 269 GArray *essence_tracks; 270 271 GList *pending_index_table_segments; 272 GList *index_tables; /* one per BodySID / IndexSID */ 273 gboolean index_table_segments_collected; 274 275 GArray *random_index_pack; 276 277 /* Metadata */ 278 GRWLock metadata_lock; 279 gboolean update_metadata; 280 gboolean pull_footer_metadata; 281 282 gboolean metadata_resolved; 283 MXFMetadataPreface *preface; 284 GHashTable *metadata; 285 286 /* Current Material Package */ 287 MXFUMID current_package_uid; 288 MXFMetadataGenericPackage *current_package; 289 gchar *current_package_string; 290 291 GstTagList *tags; 292 293 /* Properties */ 294 gchar *requested_package_string; 295 GstClockTime max_drift; 296 297 /* Quirks */ 298 gboolean temporal_order_misuse; 299 }; 300 301 struct _GstMXFDemuxClass 302 { 303 GstElementClass parent_class; 304 }; 305 306 GType gst_mxf_demux_get_type (void); 307 308 G_END_DECLS 309 310 #endif /* __MXF_DEMUX_H__ */ 311