[COMMON] media: mfc: added register test mode
authorJeonghee Kim <jhhhh.kim@samsung.com>
Mon, 20 Aug 2018 07:22:15 +0000 (16:22 +0900)
committerhskang <hs1218.kang@samsung.com>
Sun, 9 Sep 2018 21:39:17 +0000 (06:39 +0900)
It is added for OTF bit-matching test.
However, it can be used anytime
when performing an encoding test using register dump.

Change-Id: I0f68cbf0690ef920a73b892c46d9b2ece85ba463
Signed-off-by: Jeonghee Kim <jhhhh.kim@samsung.com>
drivers/media/platform/exynos/mfc/mfc_cmd.c
drivers/media/platform/exynos/mfc/mfc_data_struct.h
drivers/media/platform/exynos/mfc/mfc_debug.h
drivers/media/platform/exynos/mfc/mfc_debugfs.c
drivers/media/platform/exynos/mfc/mfc_debugfs.h
drivers/media/platform/exynos/mfc/mfc_enc_param.c
drivers/media/platform/exynos/mfc/mfc_enc_param.h
drivers/media/platform/exynos/mfc/mfc_otf.c
drivers/media/platform/exynos/mfc/mfc_run.c

index c9278aa86b1ffe51b9dc3db6b8f4659c96047d24..9323384d08fc3df8f4588171a9d8a0fd590974ee 100644 (file)
@@ -260,6 +260,9 @@ int mfc_cmd_enc_seq_header(struct mfc_ctx *ctx)
 
        MFC_WRITEL(ctx->inst_no, MFC_REG_INSTANCE_ID);
 
+       if (reg_test)
+               mfc_set_test_params(dev);
+
        if (sfr_dump & MFC_DUMP_ENC_SEQ_START)
                call_dop(dev, dump_regs, dev);
 
index 282997639e2dc133d96496638db14b68ddd35cb6..953370b20e6b0cfb478218c46a60eaacba007920 100644 (file)
@@ -320,6 +320,10 @@ struct mfc_debugfs {
        struct dentry *root;
        struct dentry *mfc_info;
        struct dentry *debug_info;
+#ifdef CONFIG_MFC_REG_TEST
+       struct dentry *reg_info;
+       struct dentry *reg_test;
+#endif
        struct dentry *debug_level;
        struct dentry *debug_ts;
        struct dentry *dbg_enable;
@@ -838,6 +842,10 @@ struct mfc_dev {
        struct notifier_block itmon_nb;
 #endif
        int itmon_notified;
+
+       char *reg_buf;
+       unsigned int *reg_val;
+       unsigned int reg_cnt;
 };
 
 /**
index 22eda0a3bfbf6abaa7c9b0d8f578894eba0dfc9d..b18b0a8788f7c83744bfdf6ab0e4cce7509745f0 100644 (file)
@@ -28,6 +28,7 @@ extern unsigned int sfr_dump;
 extern unsigned int mmcache_dump;
 extern unsigned int mmcache_disable;
 extern unsigned int perf_boost_mode;
+extern unsigned int reg_test;
 
 #define mfc_debug(level, fmt, args...)                         \
        do {                                                    \
index dfa8e7cbc3bf1160316750f1877b5292b4c1006a..824471bd00fa3fabaa60d2e19100151bd4d7301b 100644 (file)
@@ -32,6 +32,7 @@ unsigned int sfr_dump;
 unsigned int mmcache_dump;
 unsigned int mmcache_disable;
 unsigned int perf_boost_mode;
+unsigned int reg_test;
 
 static int __mfc_info_show(struct seq_file *s, void *unused)
 {
@@ -123,6 +124,76 @@ static int __mfc_debug_info_show(struct seq_file *s, void *unused)
        return 0;
 }
 
+#ifdef CONFIG_MFC_REG_TEST
+static int __mfc_reg_info_show(struct seq_file *s, void *unused)
+{
+       struct mfc_dev *dev = g_mfc_dev;
+       unsigned int i;
+
+       seq_puts(s, ">> MFC REG test(encoder)\n");
+
+       seq_printf(s, "-----Register test on/off: %s\n", reg_test ? "on" : "off");
+       seq_printf(s, "-----Register number: %d\n", dev->reg_cnt);
+
+       if (dev->reg_val) {
+               seq_puts(s, "-----Register values\n");
+               for (i = 0; i < dev->reg_cnt; i++) {
+                       seq_printf(s, "%08x ", dev->reg_val[i]);
+                       if ((i % 8) == 7)
+                               seq_printf(s, "\n");
+               }
+       } else {
+               seq_puts(s, "-----There is no reg_buf, set the register value\n");
+       }
+
+       return 0;
+}
+
+static ssize_t __mfc_reg_info_write(struct file *file, const char __user *user_buf,
+                                       size_t count, loff_t *ppos)
+{
+       struct mfc_dev *dev = g_mfc_dev;
+       ssize_t len;
+       unsigned int index = 0;
+       char temp_char;
+
+       if (!dev->reg_buf) {
+               dev->reg_buf = kzalloc(SZ_1M, GFP_KERNEL);
+               mfc_info_dev("[REGTEST] alloc reg_buf\n");
+       }
+
+       if (!dev->reg_val) {
+               dev->reg_val = kzalloc(SZ_1M, GFP_KERNEL);
+               mfc_info_dev("[REGTEST] alloc reg_val\n");
+       }
+
+       len = simple_write_to_buffer(dev->reg_buf, SZ_1M - 1,
+                                       ppos, user_buf, count);
+       if (len <= 0)
+               return len;
+
+       mfc_info_dev("[REGTEST] len: %d, ppos: %llu\n", len, *ppos);
+
+       dev->reg_buf[*ppos] = '\0';
+
+       dev->reg_cnt = 0;
+       while (index + 7 < *ppos) {
+               temp_char = dev->reg_buf[index];
+               if ((temp_char >= '0' && temp_char <= '9') ||
+                               (temp_char >= 'A' && temp_char <= 'F') ||
+                               (temp_char >= 'a' && temp_char <= 'f')) {
+                       sscanf(&dev->reg_buf[index], "%08x", &dev->reg_val[dev->reg_cnt]);
+                       index += 8;
+                       dev->reg_cnt++;
+               } else {
+                       index++;
+               }
+       }
+
+       return len;
+}
+#endif
+
 static int __mfc_info_open(struct inode *inode, struct file *file)
 {
        return single_open(file, __mfc_info_show, inode->i_private);
@@ -133,6 +204,13 @@ static int __mfc_debug_info_open(struct inode *inode, struct file *file)
        return single_open(file, __mfc_debug_info_show, inode->i_private);
 }
 
+#ifdef CONFIG_MFC_REG_TEST
+static int __mfc_reg_info_open(struct inode *inode, struct file *file)
+{
+       return single_open(file, __mfc_reg_info_show, inode->i_private);
+}
+#endif
+
 static const struct file_operations mfc_info_fops = {
        .open = __mfc_info_open,
        .read = seq_read,
@@ -147,13 +225,23 @@ static const struct file_operations debug_info_fops = {
        .release = single_release,
 };
 
+#ifdef CONFIG_MFC_REG_TEST
+static const struct file_operations reg_info_fops = {
+       .open = __mfc_reg_info_open,
+       .read = seq_read,
+       .write = __mfc_reg_info_write,
+       .llseek = seq_lseek,
+       .release = single_release,
+};
+#endif
+
 void mfc_init_debugfs(struct mfc_dev *dev)
 {
        struct mfc_debugfs *debugfs = &dev->debugfs;
 
        debugfs->root = debugfs_create_dir("mfc", NULL);
        if (!debugfs->root) {
-               mfc_err_dev("debugfs: failed to create root derectory\n");
+               mfc_err_dev("debugfs: failed to create root directory\n");
                return;
        }
 
@@ -161,6 +249,12 @@ void mfc_init_debugfs(struct mfc_dev *dev)
                        0444, debugfs->root, dev, &mfc_info_fops);
        debugfs->debug_info = debugfs_create_file("debug_info",
                        0444, debugfs->root, dev, &debug_info_fops);
+#ifdef CONFIG_MFC_REG_TEST
+       debugfs->reg_info = debugfs_create_file("reg_info",
+                       0644, debugfs->root, dev, &reg_info_fops);
+       debugfs->reg_test = debugfs_create_u32("reg_test",
+                       0644, debugfs->root, &reg_test);
+#endif
        debugfs->debug_level = debugfs_create_u32("debug",
                        0644, debugfs->root, &debug_level);
        debugfs->debug_ts = debugfs_create_u32("debug_ts",
index 97f2ba086d15432e4f500d546a4999dd5a7e316d..1ffb1f21a39fe13205e850ab99e075cf592f21cd 100644 (file)
@@ -15,6 +15,8 @@
 
 #include "mfc_common.h"
 
+extern struct mfc_dev *g_mfc_dev;
+
 void mfc_init_debugfs(struct mfc_dev *dev);
 
 #endif /* __MFC_DEBUGFS_H */
index c72b3de1c9654fd36c7a9e23114496fb3da88fd1..ddf79f4e8f26c3ab2ea9778fc02158af8e04ad0b 100644 (file)
@@ -372,7 +372,7 @@ static void __mfc_set_fmo_slice_map_h264(struct mfc_ctx *ctx, struct mfc_h264_en
        }
 }
 
-void mfc_set_enc_params_h264(struct mfc_ctx *ctx)
+static void __mfc_set_enc_params_h264(struct mfc_ctx *ctx)
 {
        struct mfc_dev *dev = ctx->dev;
        struct mfc_enc *enc = ctx->enc_priv;
@@ -584,7 +584,7 @@ void mfc_set_enc_params_h264(struct mfc_ctx *ctx)
        mfc_debug_leave();
 }
 
-void mfc_set_enc_params_mpeg4(struct mfc_ctx *ctx)
+static void __mfc_set_enc_params_mpeg4(struct mfc_ctx *ctx)
 {
        struct mfc_dev *dev = ctx->dev;
        struct mfc_enc *enc = ctx->enc_priv;
@@ -658,7 +658,7 @@ void mfc_set_enc_params_mpeg4(struct mfc_ctx *ctx)
        mfc_debug_leave();
 }
 
-void mfc_set_enc_params_h263(struct mfc_ctx *ctx)
+static void __mfc_set_enc_params_h263(struct mfc_ctx *ctx)
 {
        struct mfc_dev *dev = ctx->dev;
        struct mfc_enc *enc = ctx->enc_priv;
@@ -715,7 +715,7 @@ void mfc_set_enc_params_h263(struct mfc_ctx *ctx)
        mfc_debug_leave();
 }
 
-void mfc_set_enc_params_vp8(struct mfc_ctx *ctx)
+static void __mfc_set_enc_params_vp8(struct mfc_ctx *ctx)
 {
        struct mfc_dev *dev = ctx->dev;
        struct mfc_enc *enc = ctx->enc_priv;
@@ -829,7 +829,7 @@ void mfc_set_enc_params_vp8(struct mfc_ctx *ctx)
        mfc_debug_leave();
 }
 
-void mfc_set_enc_params_vp9(struct mfc_ctx *ctx)
+static void __mfc_set_enc_params_vp9(struct mfc_ctx *ctx)
 {
        struct mfc_dev *dev = ctx->dev;
        struct mfc_enc *enc = ctx->enc_priv;
@@ -969,7 +969,7 @@ void mfc_set_enc_params_vp9(struct mfc_ctx *ctx)
        mfc_debug_leave();
 }
 
-void mfc_set_enc_params_hevc(struct mfc_ctx *ctx)
+static void __mfc_set_enc_params_hevc(struct mfc_ctx *ctx)
 {
        struct mfc_dev *dev = ctx->dev;
        struct mfc_enc *enc = ctx->enc_priv;
@@ -1221,7 +1221,7 @@ void mfc_set_enc_params_hevc(struct mfc_ctx *ctx)
        mfc_debug_leave();
 }
 
-void mfc_set_enc_params_bpg(struct mfc_ctx *ctx)
+static void __mfc_set_enc_params_bpg(struct mfc_ctx *ctx)
 {
        struct mfc_dev *dev = ctx->dev;
        struct mfc_enc *enc = ctx->enc_priv;
@@ -1255,19 +1255,19 @@ int mfc_set_enc_params(struct mfc_ctx *ctx)
        struct mfc_dev *dev = ctx->dev;
 
        if (IS_H264_ENC(ctx))
-               mfc_set_enc_params_h264(ctx);
+               __mfc_set_enc_params_h264(ctx);
        else if (IS_MPEG4_ENC(ctx))
-               mfc_set_enc_params_mpeg4(ctx);
+               __mfc_set_enc_params_mpeg4(ctx);
        else if (IS_H263_ENC(ctx))
-               mfc_set_enc_params_h263(ctx);
+               __mfc_set_enc_params_h263(ctx);
        else if (IS_VP8_ENC(ctx))
-               mfc_set_enc_params_vp8(ctx);
+               __mfc_set_enc_params_vp8(ctx);
        else if (IS_VP9_ENC(ctx))
-               mfc_set_enc_params_vp9(ctx);
+               __mfc_set_enc_params_vp9(ctx);
        else if (IS_HEVC_ENC(ctx))
-               mfc_set_enc_params_hevc(ctx);
+               __mfc_set_enc_params_hevc(ctx);
        else if (IS_BPG_ENC(ctx))
-               mfc_set_enc_params_bpg(ctx);
+               __mfc_set_enc_params_bpg(ctx);
        else {
                mfc_err_ctx("Unknown codec for encoding (%x)\n",
                        ctx->codec_mode);
@@ -1282,3 +1282,26 @@ int mfc_set_enc_params(struct mfc_ctx *ctx)
 
        return 0;
 }
+
+void mfc_set_test_params(struct mfc_dev *dev)
+{
+
+       unsigned int base_addr = 0xF000;
+       unsigned int i;
+
+       if (!dev->reg_val) {
+               mfc_err_dev("[REGTEST] There is no reg_val set the register value\n");
+               return;
+       }
+
+       mfc_info_dev("[REGTEST] Overwrite register value for encoder register test\n");
+
+       for (i = 0; i < dev->reg_cnt; i++)
+               if (((base_addr + (i * 4)) != MFC_REG_E_STREAM_BUFFER_ADDR) &&
+                               ((base_addr + (i * 4)) != MFC_REG_E_SOURCE_FIRST_STRIDE) &&
+                               ((base_addr + (i * 4)) != MFC_REG_E_SOURCE_SECOND_STRIDE) &&
+                               ((base_addr + (i * 4)) != MFC_REG_E_SOURCE_THIRD_STRIDE) &&
+                               ((base_addr + (i * 4)) != MFC_REG_PIXEL_FORMAT))
+                       MFC_RAW_WRITEL(dev->reg_val[i], base_addr + (i * 4));
+
+}
index 383c3a198c39a4d17f452bb86214337c16a32ab2..8c75491519d3a0eea92c4e1edc3d30eb045201e5 100644 (file)
@@ -18,5 +18,6 @@
 void mfc_set_slice_mode(struct mfc_ctx *ctx);
 void mfc_set_aso_slice_order_h264(struct mfc_ctx *ctx);
 int mfc_set_enc_params(struct mfc_ctx *ctx);
+void mfc_set_test_params(struct mfc_dev *dev);
 
 #endif /* __MFC_ENC_PARAM_H */
index e0d232637422a9c7bb724ce7a0305f76012e8871..5b6f9137af021bcdc69eaebe63af1f2ff4b683ef 100644 (file)
@@ -387,14 +387,46 @@ int mfc_otf_ctx_ready(struct mfc_ctx *ctx)
        return 0;
 }
 
+static int __check_disable_header_gen(struct mfc_dev *dev)
+{
+       unsigned int base_addr = 0xF000;
+       unsigned int shift = 6;
+       unsigned int mask = 1;
+
+       if (!dev->reg_val)
+               return 0;
+
+       if ((dev->reg_val[MFC_REG_E_ENC_OPTIONS - base_addr] >> shift) & mask)
+               return 1;
+
+       return 0;
+}
+
 int mfc_otf_run_enc_init(struct mfc_ctx *ctx)
 {
+       struct mfc_dev *dev = ctx->dev;
+       struct mfc_raw_info *raw = &ctx->raw_buf;
+#ifdef CONFIG_VIDEO_EXYNOS_TSMUX
+       struct packetizing_param packet_param;
+#endif
+
        int ret;
 
        mfc_debug_enter();
 
        mfc_set_enc_stride(ctx);
        mfc_clean_ctx_int_flags(ctx);
+
+       if (reg_test && !__check_disable_header_gen(dev)) {
+#ifdef CONFIG_VIDEO_EXYNOS_TSMUX
+               packet_param.time_stamp = 0;
+               ret = packetize(&packet_param);
+               if (ret)
+                       return ret;
+#endif
+               mfc_otf_set_stream_size(ctx, raw->total_plane_size);
+       }
+
        ret = mfc_cmd_enc_seq_header(ctx);
 
        mfc_debug_leave();
index 2301dc5a7af35e956d3767b0cf74e77e0b60b9f6..f38c33d0d20c5b60a29389c6521e0176120b9a40 100644 (file)
@@ -570,7 +570,9 @@ int mfc_run_enc_frame(struct mfc_ctx *ctx)
 
        if (IS_H264_ENC(ctx))
                mfc_set_aso_slice_order_h264(ctx);
-       mfc_set_slice_mode(ctx);
+
+       if (!reg_test)
+               mfc_set_slice_mode(ctx);
 
        mfc_cmd_enc_one_frame(ctx, last_frame);