/* GStreamer * Copyright (C) <1999> Erik Walthinsen * Copyright (C) <2003> David A. Schleef * Copyright (C) <2006> Wim Taymans * Copyright (C) <2007> Julien Moutte * Copyright (C) <2009> Tim-Philipp Müller * Copyright (C) <2009> STEricsson * Copyright (C) <2013> Sreerenj Balachandran * Copyright (C) <2013> Intel Corporation * Copyright (C) <2014> Centricular Ltd * Copyright (C) <2015> YouView TV Ltd. * Copyright (C) <2016> British Broadcasting Corporation * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Library General Public * License as published by the Free Software Foundation; either * version 2 of the License, or (at your option) any later version. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Library General Public License for more details. * * You should have received a copy of the GNU Library General Public * License along with this library; if not, write to the * Free Software Foundation, Inc., 51 Franklin St, Fifth Floor, * Boston, MA 02110-1301, USA. */ #ifdef HAVE_CONFIG_H #include "config.h" #endif #include "qtdemux_tree.h" #include "qtdemux_types.h" #include "fourcc.h" GNode * qtdemux_tree_get_child_by_type (GNode * node, guint32 fourcc) { GNode *child; guint8 *buffer; guint32 child_fourcc; for (child = g_node_first_child (node); child; child = g_node_next_sibling (child)) { buffer = (guint8 *) child->data; child_fourcc = QT_FOURCC (buffer + 4); if (G_UNLIKELY (child_fourcc == fourcc)) { return child; } } return NULL; } GNode * qtdemux_tree_get_child_by_type_full (GNode * node, guint32 fourcc, GstByteReader * parser) { GNode *child; guint8 *buffer; guint32 child_fourcc, child_len; for (child = g_node_first_child (node); child; child = g_node_next_sibling (child)) { buffer = (guint8 *) child->data; child_len = QT_UINT32 (buffer); child_fourcc = QT_FOURCC (buffer + 4); if (G_UNLIKELY (child_fourcc == fourcc)) { if (G_UNLIKELY (child_len < (4 + 4))) return NULL; /* FIXME: must verify if atom length < parent atom length */ gst_byte_reader_init (parser, buffer + (4 + 4), child_len - (4 + 4)); return child; } } return NULL; } GNode * qtdemux_tree_get_child_by_index (GNode * node, guint index) { return g_node_nth_child (node, index); } GNode * qtdemux_tree_get_sibling_by_type_full (GNode * node, guint32 fourcc, GstByteReader * parser) { GNode *child; guint8 *buffer; guint32 child_fourcc, child_len; for (child = g_node_next_sibling (node); child; child = g_node_next_sibling (child)) { buffer = (guint8 *) child->data; child_fourcc = QT_FOURCC (buffer + 4); if (child_fourcc == fourcc) { if (parser) { child_len = QT_UINT32 (buffer); if (G_UNLIKELY (child_len < (4 + 4))) return NULL; /* FIXME: must verify if atom length < parent atom length */ gst_byte_reader_init (parser, buffer + (4 + 4), child_len - (4 + 4)); } return child; } } return NULL; } GNode * qtdemux_tree_get_sibling_by_type (GNode * node, guint32 fourcc) { return qtdemux_tree_get_sibling_by_type_full (node, fourcc, NULL); }