From mboxrd@z Thu Jan  1 00:00:00 1970
Return-Path: <ffmpeg-devel-bounces@ffmpeg.org>
Received: from ffbox0-bg.mplayerhq.hu (ffbox0-bg.ffmpeg.org [79.124.17.100])
	by master.gitmailbox.com (Postfix) with ESMTPS id 4FEFA4CE09
	for <ffmpegdev@gitmailbox.com>; Mon, 14 Apr 2025 12:48:05 +0000 (UTC)
Received: from [127.0.1.1] (localhost [127.0.0.1])
	by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTP id 78A1E687CEF;
	Mon, 14 Apr 2025 15:47:39 +0300 (EEST)
Received: from mail-pf1-f176.google.com (mail-pf1-f176.google.com
 [209.85.210.176])
 by ffbox0-bg.mplayerhq.hu (Postfix) with ESMTPS id 9D9CF687CCC
 for <ffmpeg-devel@ffmpeg.org>; Mon, 14 Apr 2025 15:47:33 +0300 (EEST)
Received: by mail-pf1-f176.google.com with SMTP id
 d2e1a72fcca58-73bb647eb23so3660453b3a.0
 for <ffmpeg-devel@ffmpeg.org>; Mon, 14 Apr 2025 05:47:33 -0700 (PDT)
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
 d=gmail.com; s=20230601; t=1744634852; x=1745239652; darn=ffmpeg.org;
 h=cc:to:mime-version:content-transfer-encoding:fcc:subject:date
 :references:in-reply-to:message-id:from:from:to:cc:subject:date
 :message-id:reply-to;
 bh=1au7eDcnZJTn3MYNSioessw7o53rbN6uBHv+6PGvWhU=;
 b=dq9NZ12NGdwivUlVfa2l2XJsou1eCL0h+VepgwsD3SjIoeDotXkpfEguErCl3t39eq
 veNFa2Cq/On0yDHM2BE6WKA4qnE8qqJ2qBhlQAghmsdiYwoB+Xs+ap6lgwOwRBbNbdSe
 uMimouwJK3/bVOJBneT1wPci7L44lzV14wmLK9TjhGbZcEE9ij+I/lurMSc42eMhPGlD
 Bu7YjsrQu9PrP+nmISPRo5oF8tXceqFESLo8L+eWNAyZXnZjrz1qw2S1X4/jmcnuacgZ
 lLwks/+6VNnMGsECE1qzd0mtmF30NvCKpk7LbjGgzFlzHJzRoKO8iv074yeYfI5hucbA
 +StA==
X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
 d=1e100.net; s=20230601; t=1744634852; x=1745239652;
 h=cc:to:mime-version:content-transfer-encoding:fcc:subject:date
 :references:in-reply-to:message-id:from:x-gm-message-state:from:to
 :cc:subject:date:message-id:reply-to;
 bh=1au7eDcnZJTn3MYNSioessw7o53rbN6uBHv+6PGvWhU=;
 b=GGqsuVsP7SHJMZvM3MyBSonsQYvjILEYjXYRgWjYKEd8uAAZb6z4vOoo437BFYW4bq
 JpPjxJlj9rI0z57Yz0MBvnOFzBSrP6S9d70gQm+FoBJGqKl3MsbQfKB0wFIrwTG+l0S6
 H+nEXV6wM6T1D+hJzz/H7uK42NUieSSSGVLWDRkUDP/JwCWgsnRX/LD0ir81fk8Hqz6w
 cfQkf3B3JFWtBNtd8e1x3A3r2+HWHajO9X5ddXzp0Hv/0uY/gwac1aeQLZTnFZI3fF70
 pYwaXTrjYpZ/28+DZpdaUh49vTB3c3vfVWEoBkIJ04e+NzdkopjVaZ1dlzE7r6lu2fZt
 /S4w==
X-Gm-Message-State: AOJu0Yz+djFIbHA4lfnJpKRs5LBRzZfmpthAt2bUkNoZMIjqrALYTZpy
 Gy03CP95IcnGj3t3JXaB0O5OXEy8/NLX+PXatJccOfAxG2ftArDIfE/Hlg==
X-Gm-Gg: ASbGncuV74XBb5AFUlCi+MpScEyreqF4hGPsDx9KJkfrNKTOxiyOKeWacUd7ru1Txn3
 8/kAmS94UP9q1uwXS6e8dPbHCRs0xfWVBuyRZfyOoaj7xU8ckz8xsZafQrDE5CjQosVsOejnv3b
 sDUayK+UCGi6yanyWcRUP9jph1FRkUVrI+aJHgTCpu3AQnlCdw16IIUvsttGXPM+ohKVTTA41DY
 T0LQDCe8SnqqniunX6Kn/Hv6iuHf9/fdoUEr1TvYptpbU/YwDZeET7J+tzrtSqjjgsc33jMWpPJ
 MjNXCAmgxnHsNmf3QL2Ce1fM5WgsQgOeBz4ivdaRt31fRMwXIvNOUbmtzJHTMzg99jVH3g==
X-Google-Smtp-Source: AGHT+IF/G+qjjgoJQSomngfnkxwUXrzXQdndmSeM+a6DSJMeZQ1jaSMLU8yxmcOCYoWw6dWwD54izw==
X-Received: by 2002:a05:6a21:338d:b0:1f5:8622:5ecd with SMTP id
 adf61e73a8af0-2017996f545mr22243927637.32.1744634851672; 
 Mon, 14 Apr 2025 05:47:31 -0700 (PDT)
Received: from [127.0.0.1] (master.gitmailbox.com. [34.83.118.50])
 by smtp.gmail.com with ESMTPSA id
 41be03b00d2f7-b02a322117bsm7654164a12.64.2025.04.14.05.47.31
 (version=TLS1_2 cipher=ECDHE-ECDSA-AES128-GCM-SHA256 bits=128/128);
 Mon, 14 Apr 2025 05:47:31 -0700 (PDT)
From: softworkz <ffmpegagent@gmail.com>
X-Google-Original-From: softworkz <softworkz@hotmail.com>
Message-Id: <0bd0ec42f188ca3c16c1ed809b89a1bb503fb942.1744634827.git.ffmpegagent@gmail.com>
In-Reply-To: <pull.66.ffstaging.FFmpeg.1744634826.ffmpegagent@gmail.com>
References: <pull.66.ffstaging.FFmpeg.1744634826.ffmpegagent@gmail.com>
Date: Mon, 14 Apr 2025 12:47:00 +0000
Fcc: Sent
MIME-Version: 1.0
To: ffmpeg-devel@ffmpeg.org
Subject: [FFmpeg-devel] [PATCH 3/9] fftools/textformat: Introduce common
 header and deduplicate code
X-BeenThere: ffmpeg-devel@ffmpeg.org
X-Mailman-Version: 2.1.29
Precedence: list
List-Id: FFmpeg development discussions and patches <ffmpeg-devel.ffmpeg.org>
List-Unsubscribe: <https://ffmpeg.org/mailman/options/ffmpeg-devel>,
 <mailto:ffmpeg-devel-request@ffmpeg.org?subject=unsubscribe>
List-Archive: <https://ffmpeg.org/pipermail/ffmpeg-devel>
List-Post: <mailto:ffmpeg-devel@ffmpeg.org>
List-Help: <mailto:ffmpeg-devel-request@ffmpeg.org?subject=help>
List-Subscribe: <https://ffmpeg.org/mailman/listinfo/ffmpeg-devel>,
 <mailto:ffmpeg-devel-request@ffmpeg.org?subject=subscribe>
Reply-To: FFmpeg development discussions and patches <ffmpeg-devel@ffmpeg.org>
Cc: softworkz <softworkz@hotmail.com>
Content-Type: text/plain; charset="us-ascii"
Content-Transfer-Encoding: 7bit
Errors-To: ffmpeg-devel-bounces@ffmpeg.org
Sender: "ffmpeg-devel" <ffmpeg-devel-bounces@ffmpeg.org>
Archived-At: <https://master.gitmailbox.com/ffmpegdev/0bd0ec42f188ca3c16c1ed809b89a1bb503fb942.1744634827.git.ffmpegagent@gmail.com/>
List-Archive: <https://master.gitmailbox.com/ffmpegdev/>
List-Post: <mailto:ffmpegdev@gitmailbox.com>

From: softworkz <softworkz@hotmail.com>

Signed-off-by: softworkz <softworkz@hotmail.com>
---
 fftools/textformat/avtextwriters.h |  2 +-
 fftools/textformat/tf_compact.c    | 31 ++++-------
 fftools/textformat/tf_default.c    | 27 +++-------
 fftools/textformat/tf_flat.c       | 27 +++-------
 fftools/textformat/tf_ini.c        | 24 +++------
 fftools/textformat/tf_internal.h   | 85 ++++++++++++++++++++++++++++++
 fftools/textformat/tf_json.c       | 38 +++++--------
 fftools/textformat/tf_xml.c        | 35 +++++-------
 fftools/textformat/tw_avio.c       |  7 +--
 fftools/textformat/tw_buffer.c     |  7 +--
 fftools/textformat/tw_stdout.c     |  8 +--
 11 files changed, 150 insertions(+), 141 deletions(-)
 create mode 100644 fftools/textformat/tf_internal.h

diff --git a/fftools/textformat/avtextwriters.h b/fftools/textformat/avtextwriters.h
index 9438d21802..0c2ed21a6f 100644
--- a/fftools/textformat/avtextwriters.h
+++ b/fftools/textformat/avtextwriters.h
@@ -41,7 +41,7 @@ typedef struct AVTextWriter {
     void (*uninit)(AVTextWriterContext *wctx);
     void (*writer_w8)(AVTextWriterContext *wctx, int b);
     void (*writer_put_str)(AVTextWriterContext *wctx, const char *str);
-    void (*writer_printf)(AVTextWriterContext *wctx, const char *fmt, ...);
+    void (*writer_printf)(AVTextWriterContext *wctx, const char *fmt, va_list vl);
 } AVTextWriter;
 
 typedef struct AVTextWriterContext {
diff --git a/fftools/textformat/tf_compact.c b/fftools/textformat/tf_compact.c
index 298b840739..52bc8ad927 100644
--- a/fftools/textformat/tf_compact.c
+++ b/fftools/textformat/tf_compact.c
@@ -25,6 +25,7 @@
 #include <string.h>
 
 #include "avtextformat.h"
+#include "tf_internal.h"
 #include <libavutil/mem.h>
 #include <libavutil/avassert.h>
 #include <libavutil/bprint.h>
@@ -33,22 +34,6 @@
 #include <libavutil/opt.h>
 
 
-#define writer_w8(wctx_, b_) (wctx_)->writer->writer->writer_w8((wctx_)->writer, b_)
-#define writer_put_str(wctx_, str_) (wctx_)->writer->writer->writer_put_str((wctx_)->writer, str_)
-#define writer_printf(wctx_, fmt_, ...) (wctx_)->writer->writer->writer_printf((wctx_)->writer, fmt_, __VA_ARGS__)
-
-
-#define DEFINE_FORMATTER_CLASS(name)                   \
-static const char *name##_get_name(void *ctx)       \
-{                                                   \
-    return #name ;                                  \
-}                                                   \
-static const AVClass name##_class = {               \
-    .class_name = #name,                            \
-    .item_name  = name##_get_name,                  \
-    .option     = name##_options                    \
-}
-
 
 /* Compact output */
 
@@ -160,9 +145,12 @@ static av_cold int compact_init(AVTextFormatContext *wctx)
 static void compact_print_section_header(AVTextFormatContext *wctx, const void *data)
 {
     CompactContext *compact = wctx->priv;
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
-    const struct AVTextFormatSection *parent_section = wctx->level ?
-        wctx->section[wctx->level-1] : NULL;
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
+    const AVTextFormatSection *parent_section = tf_get_parent_section(wctx, wctx->level);
+
+    if (!section)
+        return;
+
     compact->terminate_line[wctx->level] = 1;
     compact->has_nested_elems[wctx->level] = 0;
 
@@ -213,8 +201,11 @@ static void compact_print_section_header(AVTextFormatContext *wctx, const void *
 
 static void compact_print_section_footer(AVTextFormatContext *wctx)
 {
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
     CompactContext *compact = wctx->priv;
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
+
+    if (!section)
+        return;
 
     if (!compact->nested_section[wctx->level] &&
         compact->terminate_line[wctx->level] &&
diff --git a/fftools/textformat/tf_default.c b/fftools/textformat/tf_default.c
index 3b05d25f36..a9b247c769 100644
--- a/fftools/textformat/tf_default.c
+++ b/fftools/textformat/tf_default.c
@@ -25,26 +25,12 @@
 #include <string.h>
 
 #include "avtextformat.h"
+#include "tf_internal.h"
 #include <libavutil/mem.h>
 #include <libavutil/avassert.h>
 #include <libavutil/bprint.h>
 #include <libavutil/opt.h>
 
-#define writer_w8(wctx_, b_) (wctx_)->writer->writer->writer_w8((wctx_)->writer, b_)
-#define writer_put_str(wctx_, str_) (wctx_)->writer->writer->writer_put_str((wctx_)->writer, str_)
-#define writer_printf(wctx_, fmt_, ...) (wctx_)->writer->writer->writer_printf((wctx_)->writer, fmt_, __VA_ARGS__)
-
-#define DEFINE_FORMATTER_CLASS(name)                   \
-static const char *name##_get_name(void *ctx)       \
-{                                                   \
-    return #name ;                                  \
-}                                                   \
-static const AVClass name##_class = {               \
-    .class_name = #name,                            \
-    .item_name  = name##_get_name,                  \
-    .option     = name##_options                    \
-}
-
 /* Default output */
 
 typedef struct DefaultContext {
@@ -82,9 +68,11 @@ static void default_print_section_header(AVTextFormatContext *wctx, const void *
 {
     DefaultContext *def = wctx->priv;
     char buf[32];
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
-    const struct AVTextFormatSection *parent_section = wctx->level ?
-        wctx->section[wctx->level-1] : NULL;
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
+    const AVTextFormatSection *parent_section = tf_get_parent_section(wctx, wctx->level);
+
+    if (!section)
+        return;
 
     av_bprint_clear(&wctx->section_pbuf[wctx->level]);
     if (parent_section &&
@@ -106,7 +94,8 @@ static void default_print_section_header(AVTextFormatContext *wctx, const void *
 static void default_print_section_footer(AVTextFormatContext *wctx)
 {
     DefaultContext *def = wctx->priv;
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
+
     char buf[32];
 
     if (!section)
diff --git a/fftools/textformat/tf_flat.c b/fftools/textformat/tf_flat.c
index 41a6b1c812..c0a8d8c437 100644
--- a/fftools/textformat/tf_flat.c
+++ b/fftools/textformat/tf_flat.c
@@ -25,6 +25,7 @@
 #include <string.h>
 
 #include "avtextformat.h"
+#include "tf_internal.h"
 #include <libavutil/mem.h>
 #include <libavutil/avassert.h>
 #include <libavutil/bprint.h>
@@ -32,23 +33,7 @@
 #include <libavutil/macros.h>
 #include <libavutil/opt.h>
 
-#define writer_w8(wctx_, b_) (wctx_)->writer->writer->writer_w8((wctx_)->writer, b_)
-#define writer_put_str(wctx_, str_) (wctx_)->writer->writer->writer_put_str((wctx_)->writer, str_)
-#define writer_printf(wctx_, fmt_, ...) (wctx_)->writer->writer->writer_printf((wctx_)->writer, fmt_, __VA_ARGS__)
-
-#define DEFINE_FORMATTER_CLASS(name)                   \
-static const char *name##_get_name(void *ctx)       \
-{                                                   \
-    return #name ;                                  \
-}                                                   \
-static const AVClass name##_class = {               \
-    .class_name = #name,                            \
-    .item_name  = name##_get_name,                  \
-    .option     = name##_options                    \
-}
-
-
-/* Flat output */
+ /* Flat output */
 
 typedef struct FlatContext {
     const AVClass *class;
@@ -121,9 +106,11 @@ static void flat_print_section_header(AVTextFormatContext *wctx, const void *dat
 {
     FlatContext *flat = wctx->priv;
     AVBPrint *buf = &wctx->section_pbuf[wctx->level];
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
-    const struct AVTextFormatSection *parent_section = wctx->level ?
-        wctx->section[wctx->level-1] : NULL;
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
+    const AVTextFormatSection *parent_section = tf_get_parent_section(wctx, wctx->level);
+
+    if (!section)
+        return;
 
     /* build section header */
     av_bprint_clear(buf);
diff --git a/fftools/textformat/tf_ini.c b/fftools/textformat/tf_ini.c
index ec471fd480..e9a11fde99 100644
--- a/fftools/textformat/tf_ini.c
+++ b/fftools/textformat/tf_ini.c
@@ -25,26 +25,12 @@
 #include <string.h>
 
 #include "avtextformat.h"
+#include "tf_internal.h"
 #include <libavutil/mem.h>
 #include <libavutil/avassert.h>
 #include <libavutil/bprint.h>
 #include <libavutil/opt.h>
 
-#define writer_w8(wctx_, b_) (wctx_)->writer->writer->writer_w8((wctx_)->writer, b_)
-#define writer_put_str(wctx_, str_) (wctx_)->writer->writer->writer_put_str((wctx_)->writer, str_)
-#define writer_printf(wctx_, fmt_, ...) (wctx_)->writer->writer->writer_printf((wctx_)->writer, fmt_, __VA_ARGS__)
-
-#define DEFINE_FORMATTER_CLASS(name)                   \
-static const char *name##_get_name(void *ctx)       \
-{                                                   \
-    return #name ;                                  \
-}                                                   \
-static const AVClass name##_class = {               \
-    .class_name = #name,                            \
-    .item_name  = name##_get_name,                  \
-    .option     = name##_options                    \
-}
-
 /* Default output */
 
 typedef struct DefaultContext {
@@ -105,9 +91,11 @@ static void ini_print_section_header(AVTextFormatContext *wctx, const void *data
 {
     INIContext *ini = wctx->priv;
     AVBPrint *buf = &wctx->section_pbuf[wctx->level];
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
-    const struct AVTextFormatSection *parent_section = wctx->level ?
-        wctx->section[wctx->level-1] : NULL;
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
+    const AVTextFormatSection *parent_section = tf_get_parent_section(wctx, wctx->level);
+
+    if (!section)
+        return;
 
     av_bprint_clear(buf);
     if (!parent_section) {
diff --git a/fftools/textformat/tf_internal.h b/fftools/textformat/tf_internal.h
new file mode 100644
index 0000000000..7b326328cb
--- /dev/null
+++ b/fftools/textformat/tf_internal.h
@@ -0,0 +1,85 @@
+/*
+ * Copyright (c) The FFmpeg developers
+ *
+ * This file is part of FFmpeg.
+ *
+ * FFmpeg is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * FFmpeg 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
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with FFmpeg; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
+ */
+
+/**
+ * @file
+ * Internal utilities for text formatters.
+ */
+
+#ifndef FFTOOLS_TEXTFORMAT_TF_INTERNAL_H
+#define FFTOOLS_TEXTFORMAT_TF_INTERNAL_H
+
+#include "avtextformat.h"
+
+#define DEFINE_FORMATTER_CLASS(name)                \
+static const char *name##_get_name(void *ctx)       \
+{                                                   \
+    return #name ;                                  \
+}                                                   \
+static const AVClass name##_class = {               \
+    .class_name = #name,                            \
+    .item_name  = name##_get_name,                  \
+    .option     = name##_options                    \
+}
+
+
+/**
+ * Safely validate and access a section at a given level
+ */
+static inline const AVTextFormatSection *tf_get_section(AVTextFormatContext *tfc, int level)
+{
+    if (!tfc || level < 0 || level >= SECTION_MAX_NB_LEVELS || !tfc->section[level]) {
+        if (tfc)
+            av_log(tfc, AV_LOG_ERROR, "Invalid section access at level %d\n", level);
+        return NULL;
+    }
+    return tfc->section[level];
+}
+
+/**
+ * Safely access the parent section
+ */
+static inline const AVTextFormatSection *tf_get_parent_section(AVTextFormatContext *tfc, int level)
+{
+    if (level <= 0)
+        return NULL;
+
+    return tf_get_section(tfc, level - 1);
+}
+
+static inline void writer_w8(AVTextFormatContext *wctx, int b)
+{
+    wctx->writer->writer->writer_w8(wctx->writer, b);
+}
+
+static inline void writer_put_str(AVTextFormatContext *wctx, const char *str)
+{
+    wctx->writer->writer->writer_put_str(wctx->writer, str);
+}
+
+static inline void writer_printf(AVTextFormatContext *wctx, const char *fmt, ...)
+{
+    va_list args;
+    va_start(args, fmt);
+    wctx->writer->writer->writer_printf(wctx->writer, fmt, args);
+    va_end(args);
+}
+
+#endif /* FFTOOLS_TEXTFORMAT_TF_INTERNAL_H */
diff --git a/fftools/textformat/tf_json.c b/fftools/textformat/tf_json.c
index f286838d3c..a8f23a989f 100644
--- a/fftools/textformat/tf_json.c
+++ b/fftools/textformat/tf_json.c
@@ -25,27 +25,12 @@
 #include <string.h>
 
 #include "avtextformat.h"
+#include "tf_internal.h"
 #include <libavutil/mem.h>
 #include <libavutil/avassert.h>
 #include <libavutil/bprint.h>
 #include <libavutil/opt.h>
 
-#define writer_w8(wctx_, b_) (wctx_)->writer->writer->writer_w8((wctx_)->writer, b_)
-#define writer_put_str(wctx_, str_) (wctx_)->writer->writer->writer_put_str((wctx_)->writer, str_)
-#define writer_printf(wctx_, fmt_, ...) (wctx_)->writer->writer->writer_printf((wctx_)->writer, fmt_, __VA_ARGS__)
-
-#define DEFINE_FORMATTER_CLASS(name)                   \
-static const char *name##_get_name(void *ctx)       \
-{                                                   \
-    return #name ;                                  \
-}                                                   \
-static const AVClass name##_class = {               \
-    .class_name = #name,                            \
-    .item_name  = name##_get_name,                  \
-    .option     = name##_options                    \
-}
-
-
 /* JSON output */
 
 typedef struct JSONContext {
@@ -105,13 +90,14 @@ static const char *json_escape_str(AVBPrint *dst, const char *src, void *log_ctx
 
 static void json_print_section_header(AVTextFormatContext *wctx, const void *data)
 {
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
+    const AVTextFormatSection *parent_section = tf_get_parent_section(wctx, wctx->level);
     JSONContext *json = wctx->priv;
     AVBPrint buf;
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
-    const struct AVTextFormatSection *parent_section = wctx->level ?
-        wctx->section[wctx->level-1] : NULL;
 
-    if (wctx->level && wctx->nb_item[wctx->level-1])
+    if (!section)
+        return;
+
     if (wctx->level && wctx->nb_item[wctx->level - 1])
         writer_put_str(wctx, ",\n");
 
@@ -145,8 +131,11 @@ static void json_print_section_header(AVTextFormatContext *wctx, const void *dat
 
 static void json_print_section_footer(AVTextFormatContext *wctx)
 {
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
     JSONContext *json = wctx->priv;
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
+
+    if (!section)
+        return;
 
     if (wctx->level == 0) {
         json->indent_level--;
@@ -179,9 +168,8 @@ static inline void json_print_item_str(AVTextFormatContext *wctx,
 
 static void json_print_str(AVTextFormatContext *wctx, const char *key, const char *value)
 {
+    const AVTextFormatSection *parent_section = tf_get_parent_section(wctx, wctx->level);
     JSONContext *json = wctx->priv;
-    const struct AVTextFormatSection *parent_section = wctx->level ?
-        wctx->section[wctx->level-1] : NULL;
 
     if (wctx->nb_item[wctx->level] || (parent_section && parent_section->flags & AV_TEXTFORMAT_SECTION_FLAG_NUMBERING_BY_TYPE))
         writer_put_str(wctx, json->item_sep);
@@ -192,9 +180,8 @@ static void json_print_str(AVTextFormatContext *wctx, const char *key, const cha
 
 static void json_print_int(AVTextFormatContext *wctx, const char *key, int64_t value)
 {
+    const AVTextFormatSection *parent_section = tf_get_parent_section(wctx, wctx->level);
     JSONContext *json = wctx->priv;
-    const struct AVTextFormatSection *parent_section = wctx->level ?
-        wctx->section[wctx->level-1] : NULL;
     AVBPrint buf;
 
     if (wctx->nb_item[wctx->level] || (parent_section && parent_section->flags & AV_TEXTFORMAT_SECTION_FLAG_NUMBERING_BY_TYPE))
@@ -218,4 +205,3 @@ const AVTextFormatter avtextformatter_json = {
     .flags = AV_TEXTFORMAT_FLAG_SUPPORTS_MIXED_ARRAY_CONTENT,
     .priv_class           = &json_class,
 };
-
diff --git a/fftools/textformat/tf_xml.c b/fftools/textformat/tf_xml.c
index eceeda81e5..fd3d73888e 100644
--- a/fftools/textformat/tf_xml.c
+++ b/fftools/textformat/tf_xml.c
@@ -22,6 +22,7 @@
 #include <string.h>
 
 #include "avtextformat.h"
+#include "tf_internal.h"
 #include <libavutil/mem.h>
 #include <libavutil/avassert.h>
 #include <libavutil/bprint.h>
@@ -29,21 +30,6 @@
 #include <libavutil/macros.h>
 #include <libavutil/opt.h>
 
-#define writer_w8(wctx_, b_) (wctx_)->writer->writer->writer_w8((wctx_)->writer, b_)
-#define writer_put_str(wctx_, str_) (wctx_)->writer->writer->writer_put_str((wctx_)->writer, str_)
-#define writer_printf(wctx_, fmt_, ...) (wctx_)->writer->writer->writer_printf((wctx_)->writer, fmt_, __VA_ARGS__)
-
-#define DEFINE_FORMATTER_CLASS(name)                   \
-static const char *name##_get_name(void *ctx)       \
-{                                                   \
-    return #name ;                                  \
-}                                                   \
-static const AVClass name##_class = {               \
-    .class_name = #name,                            \
-    .item_name  = name##_get_name,                  \
-    .option     = name##_options                    \
-}
-
 /* XML output */
 
 typedef struct XMLContext {
@@ -93,9 +79,11 @@ static av_cold int xml_init(AVTextFormatContext *wctx)
 static void xml_print_section_header(AVTextFormatContext *wctx, const void *data)
 {
     XMLContext *xml = wctx->priv;
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
-    const struct AVTextFormatSection *parent_section = wctx->level ?
-        wctx->section[wctx->level-1] : NULL;
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
+    const AVTextFormatSection *parent_section = tf_get_parent_section(wctx, wctx->level);
+
+    if (!section)
+        return;
 
     if (wctx->level == 0) {
         const char *qual = " xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" "
@@ -141,7 +129,10 @@ static void xml_print_section_header(AVTextFormatContext *wctx, const void *data
 static void xml_print_section_footer(AVTextFormatContext *wctx)
 {
     XMLContext *xml = wctx->priv;
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
+
+    if (!section)
+        return;
 
     if (wctx->level == 0) {
         writer_printf(wctx, "</%sffprobe>\n", xml->fully_qualified ? "ffprobe:" : "");
@@ -161,7 +152,10 @@ static void xml_print_value(AVTextFormatContext *wctx, const char *key,
 {
     AVBPrint buf;
     XMLContext *xml = wctx->priv;
-    const struct AVTextFormatSection *section = wctx->section[wctx->level];
+    const AVTextFormatSection *section = tf_get_section(wctx, wctx->level);
+
+    if (!section)
+        return;
 
     av_bprint_init(&buf, 1, AV_BPRINT_SIZE_UNLIMITED);
 
@@ -219,4 +213,3 @@ const AVTextFormatter avtextformatter_xml = {
     .flags = AV_TEXTFORMAT_FLAG_SUPPORTS_MIXED_ARRAY_CONTENT,
     .priv_class           = &xml_class,
 };
-
diff --git a/fftools/textformat/tw_avio.c b/fftools/textformat/tw_avio.c
index 3c7492aa06..f9f9cc6d5c 100644
--- a/fftools/textformat/tw_avio.c
+++ b/fftools/textformat/tw_avio.c
@@ -66,14 +66,11 @@ static void io_put_str(AVTextWriterContext *wctx, const char *str)
     avio_write(ctx->avio_context, (const unsigned char *)str, (int)strlen(str));
 }
 
-static void io_printf(AVTextWriterContext *wctx, const char *fmt, ...)
+static void io_printf(AVTextWriterContext *wctx, const char *fmt, va_list vl)
 {
     IOWriterContext *ctx = wctx->priv;
-    va_list ap;
 
-    va_start(ap, fmt);
-    avio_vprintf(ctx->avio_context, fmt, ap);
-    va_end(ap);
+    avio_vprintf(ctx->avio_context, fmt, vl);
 }
 
 
diff --git a/fftools/textformat/tw_buffer.c b/fftools/textformat/tw_buffer.c
index f8b38414a6..f861722247 100644
--- a/fftools/textformat/tw_buffer.c
+++ b/fftools/textformat/tw_buffer.c
@@ -56,14 +56,11 @@ static void buffer_put_str(AVTextWriterContext *wctx, const char *str)
     av_bprintf(ctx->buffer, "%s", str);
 }
 
-static void buffer_printf(AVTextWriterContext *wctx, const char *fmt, ...)
+static void buffer_printf(AVTextWriterContext *wctx, const char *fmt, va_list vl)
 {
     BufferWriterContext *ctx = wctx->priv;
 
-    va_list vargs;
-    va_start(vargs, fmt);
-    av_vbprintf(ctx->buffer, fmt, vargs);
-    va_end(vargs);
+    av_vbprintf(ctx->buffer, fmt, vl);
 }
 
 
diff --git a/fftools/textformat/tw_stdout.c b/fftools/textformat/tw_stdout.c
index 23de6f671f..dace55f38a 100644
--- a/fftools/textformat/tw_stdout.c
+++ b/fftools/textformat/tw_stdout.c
@@ -53,13 +53,9 @@ static inline void stdout_put_str(AVTextWriterContext *wctx, const char *str)
     printf("%s", str);
 }
 
-static inline void stdout_printf(AVTextWriterContext *wctx, const char *fmt, ...)
+static inline void stdout_printf(AVTextWriterContext *wctx, const char *fmt, va_list vl)
 {
-    va_list ap;
-
-    va_start(ap, fmt);
-    vprintf(fmt, ap);
-    va_end(ap);
+    vprintf(fmt, vl);
 }
 
 
-- 
ffmpeg-codebot

_______________________________________________
ffmpeg-devel mailing list
ffmpeg-devel@ffmpeg.org
https://ffmpeg.org/mailman/listinfo/ffmpeg-devel

To unsubscribe, visit link above, or email
ffmpeg-devel-request@ffmpeg.org with subject "unsubscribe".