Merge android.googlesource.com/kernel/common
authorChristian Hoffmann <chrmhoffmann@gmail.com>
Sun, 12 Feb 2023 08:26:28 +0000 (09:26 +0100)
committerChristian Hoffmann <chrmhoffmann@gmail.com>
Sun, 12 Feb 2023 08:26:28 +0000 (09:26 +0100)
* Branch: android-4.9-q
* SHA1: b6d8afc10b82f168c3a97896d8ecd623da4a59bc
* Version: 4.9.336

135 files changed:
1  2 
MAINTAINERS
Makefile
arch/arm/Kconfig
arch/arm/Kconfig.debug
arch/arm/Makefile
arch/arm/boot/compressed/Makefile
arch/arm/include/asm/assembler.h
arch/arm/include/asm/perf_event.h
arch/arm/kernel/Makefile
arch/arm/kernel/entry-armv.S
arch/arm/kernel/ftrace.c
arch/arm/kernel/setup.c
arch/arm/kernel/traps.c
arch/arm/mm/mmu.c
arch/arm64/include/asm/assembler.h
arch/arm64/kernel/armv8_deprecated.c
arch/arm64/kernel/cpu_errata.c
arch/arm64/kernel/cpufeature.c
arch/arm64/kernel/cpuinfo.c
arch/arm64/kernel/entry.S
arch/arm64/kernel/head.S
arch/arm64/kernel/perf_event.c
arch/arm64/kernel/process.c
arch/arm64/kernel/smp.c
arch/arm64/kernel/traps.c
arch/arm64/mm/fault.c
arch/arm64/mm/mmu.c
arch/arm64/mm/proc.S
drivers/amlogic/media/dtv_demod/amlfrontend.c
drivers/android/binder.c
drivers/base/power/main.c
drivers/base/regmap/regcache-rbtree.c
drivers/block/loop.c
drivers/block/zram/zram_drv.c
drivers/clocksource/arm_arch_timer.c
drivers/gpu/drm/drm_edid.c
drivers/gpu/drm/drm_ioctl.c
drivers/input/input.c
drivers/media/dvb-core/dmxdev.c
drivers/media/dvb-core/dvb_frontend.c
drivers/media/dvb-frontends/drxk_hard.c
drivers/mmc/card/block.c
drivers/mmc/core/core.c
drivers/mmc/core/mmc_ops.c
drivers/net/ethernet/stmicro/stmmac/stmmac_main.c
drivers/net/ethernet/stmicro/stmmac/stmmac_platform.c
drivers/net/phy/phy_device.c
drivers/net/usb/r8152.c
drivers/net/usb/usbnet.c
drivers/of/fdt.c
drivers/of/of_reserved_mem.c
drivers/pci/quirks.c
drivers/pinctrl/pinconf-generic.c
drivers/staging/android/ion/ion-ioctl.c
drivers/staging/android/ion/ion.c
drivers/staging/android/ion/ion_priv.h
drivers/staging/android/ion/ion_system_heap.c
drivers/tee/optee/call.c
drivers/thermal/thermal_core.c
drivers/usb/Kconfig
drivers/usb/core/hcd.c
drivers/usb/core/hub.c
drivers/usb/core/hub.h
drivers/usb/core/quirks.c
drivers/usb/core/urb.c
drivers/usb/dwc3/core.c
drivers/usb/gadget/configfs.c
drivers/usb/gadget/function/f_fs.c
drivers/usb/host/xhci-hub.c
drivers/usb/host/xhci-mem.c
drivers/usb/host/xhci.c
drivers/usb/host/xhci.h
drivers/video/fbdev/core/fbmem.c
fs/ext4/dir.c
fs/ext4/extents.c
fs/ext4/file.c
fs/ext4/ialloc.c
fs/ext4/inode.c
fs/ext4/ioctl.c
fs/ext4/namei.c
fs/ext4/super.c
fs/f2fs/inode.c
fs/f2fs/namei.c
fs/inode.c
fs/namespace.c
include/drm/drm_edid.h
include/linux/device.h
include/linux/fs.h
include/linux/mm.h
include/linux/module.h
include/linux/pci_ids.h
include/linux/sched.h
include/linux/serial_core.h
include/linux/string.h
include/linux/usb.h
include/linux/usb/hcd.h
include/net/cfg80211.h
include/net/tcp.h
include/uapi/linux/dvb/frontend.h
include/uapi/linux/videodev2.h
init/main.c
kernel/cgroup.c
kernel/cpu.c
kernel/fork.c
kernel/gcov/gcc_4_7.c
kernel/irq/handle.c
kernel/printk/printk.c
kernel/sched/core.c
kernel/sched/cpufreq_schedutil.c
kernel/sched/debug.c
kernel/sched/fair.c
kernel/sysctl.c
kernel/trace/Kconfig
kernel/workqueue.c
lib/Kconfig.debug
lib/string.c
mm/gup.c
mm/kmemleak.c
mm/memory.c
mm/page_alloc.c
mm/shmem.c
mm/slub.c
mm/vmstat.c
net/ipv4/tcp.c
net/ipv4/tcp_input.c
net/mac80211/mlme.c
net/mac80211/tx.c
net/unix/af_unix.c
net/wireless/nl80211.c
net/wireless/util.c
scripts/dtc/dtx_diff
security/selinux/include/security.h
security/selinux/ss/policydb.c
security/selinux/ss/services.c
sound/soc/soc-core.c

diff --cc MAINTAINERS
Simple merge
diff --cc Makefile
Simple merge
Simple merge
index 15bb7a46c6f04c1160f1bda934bd892f96f569af,f2b3bdcb63a829b98960e5ea19f2f03278117408..ea11e4f1b2f2125ae74c865b139868b2a8741422
@@@ -15,32 -15,28 +15,36 @@@ config ARM_PTDUM
          kernel.
          If in doubt, say "N"
  
- # RMK wants arm kernels compiled with frame pointers or stack unwinding.
- # If you know what you are doing and are willing to live without stack
- # traces, you can get a slightly smaller kernel by setting this option to
- # n, but then RMK will have to kill you ;).
- config FRAME_POINTER
-       bool
-       depends on !THUMB2_KERNEL
-       default y if !ARM_UNWIND || FUNCTION_GRAPH_TRACER
+ choice
+       prompt "Choose kernel unwinder"
+       default UNWINDER_ARM if AEABI
+       default UNWINDER_FRAME_POINTER if !AEABI
        help
-         If you say N here, the resulting kernel will be slightly smaller and
-         faster. However, if neither FRAME_POINTER nor ARM_UNWIND are enabled,
-         when a problem occurs with the kernel, the information that is
-         reported is severely limited.
+         This determines which method will be used for unwinding kernel stack
+         traces for panics, oopses, bugs, warnings, perf, /proc/<pid>/stack,
+         livepatch, lockdep, and more.
  
- config ARM_UNWIND
-       bool "Enable stack unwinding support (EXPERIMENTAL)"
-       depends on AEABI
-       default y
 +config AMLOGIC_USER_FAULT
 +      bool "Amlogic user fault helper"
 +      help
 +        show more information when catch user fault. Including:
 +        memory around all registers
 +        maps with pc/lr
 +        pfn for all virtual address of regirsters
 +
+ config UNWINDER_FRAME_POINTER
+       bool "Frame pointer unwinder"
+       depends on !THUMB2_KERNEL && !CC_IS_CLANG
+       select ARCH_WANT_FRAME_POINTERS
+       select FRAME_POINTER
+       help
+         This option enables the frame pointer unwinder for unwinding
+         kernel stack traces.
+ config UNWINDER_ARM
+       bool "ARM EABI stack unwinder"
+       depends on AEABI && !FUNCTION_GRAPH_TRACER
+       select ARM_UNWIND
        help
          This option enables stack unwinding support in the kernel
          using the information automatically generated by the
Simple merge
Simple merge
Simple merge
Simple merge
index d0d44500a2edf95630c2694e4ce0b906588e9c88,1738d5b61eaa1cd5080bd83dc1b49a242250612b..568ce7c4d57fa5e6118d757b7b86a4fca79b7246
@@@ -96,7 -100,6 +100,9 @@@ endi
  
  obj-$(CONFIG_HAVE_ARM_SMCCC)  += smccc-call.o
  
+ obj-$(CONFIG_GENERIC_CPU_VULNERABILITIES) += spectre.o
  extra-y := $(head-y) vmlinux.lds
 +
 +KASAN_SANITIZE_process.o := n
 +KASAN_SANITIZE_unwind.o := n
Simple merge
Simple merge
index db1fe8cda3d269c7e5317c1cb480704b1207e4ca,627889ea89eff51341e2565ffd16d7ec75df4a5d..1c5134cfd02501f2aeea868fc97e563f14b3cd70
@@@ -590,19 -573,16 +592,19 @@@ void notrace cpu_init(void
        "msr    cpsr_c, %9"
            :
            : "r" (stk),
-             PLC (PSR_F_BIT | PSR_I_BIT | IRQ_MODE),
+             PLC_r (PSR_F_BIT | PSR_I_BIT | IRQ_MODE),
              "I" (offsetof(struct stack, irq[0])),
-             PLC (PSR_F_BIT | PSR_I_BIT | ABT_MODE),
+             PLC_r (PSR_F_BIT | PSR_I_BIT | ABT_MODE),
              "I" (offsetof(struct stack, abt[0])),
-             PLC (PSR_F_BIT | PSR_I_BIT | UND_MODE),
+             PLC_r (PSR_F_BIT | PSR_I_BIT | UND_MODE),
              "I" (offsetof(struct stack, und[0])),
-             PLC (PSR_F_BIT | PSR_I_BIT | FIQ_MODE),
+             PLC_r (PSR_F_BIT | PSR_I_BIT | FIQ_MODE),
              "I" (offsetof(struct stack, fiq[0])),
-             PLC (PSR_F_BIT | PSR_I_BIT | SVC_MODE)
+             PLC_l (PSR_F_BIT | PSR_I_BIT | SVC_MODE)
            : "r14");
 +#ifdef CONFIG_AMLOGIC_VMAP
 +      __setup_vmap_stack(cpu);
 +#endif
  #endif
  }
  
Simple merge
Simple merge
Simple merge
Simple merge
index 6c488afb179bdb284c885b44ddda24af5bee3527,ae11af9c8cbdea8e647eb74c8f75be55527a269c..f33970bdbdb0be7cbfd31928220899f1b47acdcb
@@@ -196,11 -223,29 +223,33 @@@ enable_smccc_arch_workaround_1(const st
  }
  #endif        /* CONFIG_HARDEN_BRANCH_PREDICTOR */
  
+ void __init arm64_update_smccc_conduit(struct alt_instr *alt,
+                                      __le32 *origptr, __le32 *updptr,
+                                      int nr_inst)
+ {
+       u32 insn;
+       BUG_ON(nr_inst != 1);
+       switch (psci_ops.conduit) {
+       case PSCI_CONDUIT_HVC:
+               insn = aarch64_insn_get_hvc_value();
+               break;
+       case PSCI_CONDUIT_SMC:
+               insn = aarch64_insn_get_smc_value();
+               break;
+       default:
+               return;
+       }
+       *updptr = cpu_to_le32(insn);
+ }
  #ifdef CONFIG_ARM64_SSBD
 +#include <uapi/linux/psci.h>
 +#include <linux/arm-smccc.h>
 +#include <linux/psci.h>
 +
  DEFINE_PER_CPU_READ_MOSTLY(u64, arm64_ssbd_callback_required);
  
  int ssbd_state __read_mostly = ARM64_SSBD_KERNEL;
index 8c883c8574d3a892fd7a076fe91271efc34454ee,72c4171dcb25efc613feaa201d97980cfeb7445e..a5813c30a587685ca87f04bd75c108fd442894ca
@@@ -849,6 -876,28 +881,14 @@@ static int __init parse_kpti(char *str
  early_param("kpti", parse_kpti);
  #endif        /* CONFIG_UNMAP_KERNEL_AT_EL0 */
  
 -static void cpu_copy_el2regs(const struct arm64_cpu_capabilities *__unused)
 -{
 -      /*
 -       * Copy register values that aren't redirected by hardware.
 -       *
 -       * Before code patching, we only set tpidr_el1, all CPUs need to copy
 -       * this value to tpidr_el2 before we patch the code. Once we've done
 -       * that, freshly-onlined CPUs will set tpidr_el2, so we don't need to
 -       * do anything here.
 -       */
 -      if (!alternatives_applied)
 -              write_sysreg(read_sysreg(tpidr_el1), tpidr_el2);
 -}
 -
+ static void elf_hwcap_fixup(void)
+ {
+ #ifdef CONFIG_ARM64_ERRATUM_1742098
+       if (cpus_have_const_cap(ARM64_WORKAROUND_1742098))
+               compat_elf_hwcap2 &= ~COMPAT_HWCAP2_AES;
+ #endif /* ARM64_ERRATUM_1742098 */
+ }
  static const struct arm64_cpu_capabilities arm64_features[] = {
        {
                .desc = "GIC system register CPU interface",
        {
                .desc = "Virtualization Host Extensions",
                .capability = ARM64_HAS_VIRT_HOST_EXTN,
-               .def_scope = SCOPE_SYSTEM,
+               .type = ARM64_CPUCAP_SYSTEM_FEATURE,
                .matches = runs_at_el2,
 -              .cpu_enable = cpu_copy_el2regs,
        },
        {
                .desc = "32-bit EL0 Support",
Simple merge
index 3530d705ae05158d7d9b4c4dbe4f84b210539a56,4889b4a0ce17db3c8fd96b2e545f7851f878b0b7..8e00c6b4074a2169a3504b964d94524199e64edf
@@@ -304,30 -307,20 +311,32 @@@ alternative_else_nop_endi
        ldp     x24, x25, [sp, #16 * 12]
        ldp     x26, x27, [sp, #16 * 13]
        ldp     x28, x29, [sp, #16 * 14]
+       .if     \el == 0
+ alternative_if_not ARM64_UNMAP_KERNEL_AT_EL0
        ldr     lr, [sp, #S_LR]
 +#ifdef CONFIG_AMLOGIC_VMAP
 +      /* restore context sp and per-cpu vmap stack */
 +      .if     \swap == 1
 +      stp     x19, x20, [sp]
 +      mov     x20, sp
 +      add     x19, x20, #S_FRAME_SIZE
 +      msr     DBGWVR3_EL1, x19
 +      mrs     x19, DBGWVR2_EL1
 +      mov     sp,  x19
 +      ldp     x19, x20, [x20]
 +      .endif
 +#endif /* CONFIG_AMLOGIC_VMAP */
        add     sp, sp, #S_FRAME_SIZE           // restore sp
-       .if     \el == 0
- alternative_insn eret, nop, ARM64_UNMAP_KERNEL_AT_EL0
+       eret
+ alternative_else_nop_endif
  #ifdef CONFIG_UNMAP_KERNEL_AT_EL0
        bne     4f
-       msr     far_el1, x30
-       tramp_alias     x30, tramp_exit_native
+       msr     far_el1, x29
+       tramp_alias     x30, tramp_exit_native, x29
        br      x30
  4:
-       tramp_alias     x30, tramp_exit_compat
+       tramp_alias     x30, tramp_exit_compat, x29
        br      x30
  #endif
        .else
Simple merge
index 29fc7214f990e0448eddfd51f286b9be9118da06,7f95d6ac20110e4170a3e9d7a2c282588832d572..69efa5a0f30a054542942d92d6b44a22a7ca1540
@@@ -836,10 -748,28 +836,32 @@@ static void armv8pmu_disable_event(stru
        raw_spin_unlock_irqrestore(&events->pmu_lock, flags);
  }
  
 +#ifdef CONFIG_AMLOGIC_MODIFY
 +#include <linux/perf/arm_pmu.h>
 +#endif
 +
+ static void armv8pmu_start(struct arm_pmu *cpu_pmu)
+ {
+       unsigned long flags;
+       struct pmu_hw_events *events = this_cpu_ptr(cpu_pmu->hw_events);
+       raw_spin_lock_irqsave(&events->pmu_lock, flags);
+       /* Enable all counters */
+       armv8pmu_pmcr_write(armv8pmu_pmcr_read() | ARMV8_PMU_PMCR_E);
+       raw_spin_unlock_irqrestore(&events->pmu_lock, flags);
+ }
+ static void armv8pmu_stop(struct arm_pmu *cpu_pmu)
+ {
+       unsigned long flags;
+       struct pmu_hw_events *events = this_cpu_ptr(cpu_pmu->hw_events);
+       raw_spin_lock_irqsave(&events->pmu_lock, flags);
+       /* Disable all counters */
+       armv8pmu_pmcr_write(armv8pmu_pmcr_read() & ~ARMV8_PMU_PMCR_E);
+       raw_spin_unlock_irqrestore(&events->pmu_lock, flags);
+ }
  static irqreturn_t armv8pmu_handle_irq(int irq_num, void *dev)
  {
        u32 pmovsr;
index 4a159176d553d52da23c419ada2d9639f0134f96,a53d81b83c4dc5eaeaed880b8093689dc0a5eb2b..4064217398b33d86759415a686ad59f81487b965
@@@ -199,28 -183,7 +199,28 @@@ static void show_data(unsigned long add
        if (addr < PAGE_OFFSET || addr > -256UL)
                return;
  
-       printk("\n%s: %#lx:\n", name, addr);
 +#ifdef CONFIG_AMLOGIC_MODIFY
 +      /*
 +       * Treating data in general purpose register as an address
 +       * and dereferencing it is quite a dangerous behaviour,
 +       * especially when it belongs to secure monotor region or
 +       * ioremap region(for arm64 vmalloc region is already filtered
 +       * out), which can lead to external abort on non-linefetch and
 +       * can not be protected by probe_kernel_address.
 +       * We need more strict filtering rules
 +       */
 +
 +#ifdef CONFIG_AMLOGIC_SEC
 +      /*
 +       * filter out secure monitor region
 +       */
 +      if (addr <= (unsigned long)high_memory)
 +              if (within_secmon_region(addr))
 +                      return;
 +#endif
 +#endif
 +
+       printk("\n%s: %pS:\n", name, addr);
  
        /*
         * round address down to a 32 bit boundary
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
index 3b570887865b45607431645040b4f24c1c68aa32,0000000000000000000000000000000000000000..d4633f19b930a32c8143e5cda06fededf00cac77
mode 100644,000000..100644
--- /dev/null
@@@ -1,5011 -1,0 +1,4999 @@@
- static int aml_dtvdm_get_property(struct dvb_frontend *dev,
-                       struct dtv_property *tvp)
- {
-       return 0;
- }
 +/*
 + * drivers/amlogic/media/dtv_demod/amlfrontend.c
 + *
 + * Copyright (C) 2017 Amlogic, Inc. All rights reserved.
 + *
 + * This program is free software; you can redistribute it and/or modify
 + * it under the terms of the GNU General Public License as published by
 + * the Free Software Foundation; either version 2 of the License, or
 + * (at your option) any later version.
 + *
 + * This program 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 General Public License for
 + * more details.
 + *
 + */
 +
 +/*****************************************************************
 + **  author :
 + **        Shijie.Rong@amlogic.com
 + **  version :
 + **   v1.0      12/3/13
 + **   v2.0     15/10/12
 + **   v3.0      17/11/15
 + *****************************************************************/
 +#define __DVB_CORE__  /*ary 2018-1-31*/
 +
 +#include <linux/init.h>
 +#include <linux/kernel.h>
 +#include <linux/module.h>
 +#include <linux/string.h>
 +#include <linux/delay.h>
 +#include <linux/jiffies.h>
 +#include <linux/slab.h>
 +#include <linux/platform_device.h>
 +
 +#include <linux/err.h>        /*IS_ERR*/
 +#include <linux/clk.h>        /*clk tree*/
 +#include <linux/of_device.h>
 +#include <linux/of_reserved_mem.h>
 +
 +#ifdef ARC_700
 +#include <asm/arch/am_regs.h>
 +#else
 +/* #include <mach/am_regs.h> */
 +#endif
 +#include <linux/i2c.h>
 +#include <linux/gpio.h>
 +
 +
 +#include <linux/dvb/aml_demod.h>
 +#include "demod_func.h"
 +
 +/*dma_get_cma_size_int_byte*/
 +#include <linux/amlogic/media/codec_mm/codec_mm.h>
 +#include <linux/dma-contiguous.h>
 +
 +#include <linux/amlogic/media/frame_provider/tvin/tvin.h>
 +#include <linux/amlogic/media/vout/vdac_dev.h>
 +#include <linux/amlogic/aml_dtvdemod.h>
 +
 +
 +MODULE_PARM_DESC(debug_aml, "\n\t\t Enable frontend debug information");
 +static int debug_aml = 1;
 +module_param(debug_aml, int, 0644);
 +
 +MODULE_PARM_DESC(auto_search_std, "\n\t\t atsc-c std&hrc search");
 +static unsigned int auto_search_std;
 +module_param(auto_search_std, int, 0644);
 +
 +MODULE_PARM_DESC(std_lock_timeout, "\n\t\t atsc-c std lock timeout");
 +static unsigned int std_lock_timeout = 1000;
 +module_param(std_lock_timeout, int, 0644);
 +
 +/*0.001for field,0.002 for performance
 + *0.04: new method of tl1 dvbc channel fast search(Hisense project)
 + */
 +static char *demod_version = "V0.04";
 +
 +
 +int aml_demod_debug = DBG_INFO;
 +
 +/*use this flag to mark the new method for dvbc channel fast search
 + *it's disabled as default, can be enabled if needed
 + *we can make it always enabled after all testing are passed
 + */
 +static unsigned int demod_dvbc_speedup_en = 1;
 +
 +
 +#if 0
 +#define PR_DBG(fmt, args ...) \
 +      do { \
 +              if (aml_demod_debug & DBG_INFO) { \
 +                      pr_info("dtv_dmd:"fmt, ##args); \
 +              } \
 +      } while (0)
 +
 +#endif
 +
 +/* debug info------------------------*/
 +
 +
 +module_param(aml_demod_debug, int, 0644);
 +MODULE_PARM_DESC(aml_demod_debug, "set debug level (info=bit1, reg=bit2, atsc=bit4,");
 +
 +/*-----------------------------------*/
 +struct amldtvdemod_device_s *dtvdd_devp;
 +
 +static int last_lock = -1;    /*debug only*/
 +#define DEMOD_DEVICE_NAME  "Amlogic_Demod"
 +static int cci_thread;
 +static int freq_dvbc;
 +static struct aml_demod_sta demod_status;
 +static enum fe_modulation atsc_mode = VSB_8;
 +static struct aml_demod_para para_demod;
 +static int atsc_flag;
 +
 +static int memstart = 0x1ef00000;/* move to aml_dtv_demod*/
 +
 +long *mem_buf;
 +
 +MODULE_PARM_DESC(frontend_mode, "\n\t\t Frontend mode 0-DVBC, 1-DVBT");
 +static int frontend_mode = -1;
 +module_param(frontend_mode, int, 0444);
 +
 +MODULE_PARM_DESC(frontend_i2c, "\n\t\t IIc adapter id of frontend");
 +static int frontend_i2c = -1;
 +module_param(frontend_i2c, int, 0444);
 +
 +MODULE_PARM_DESC(frontend_tuner,
 +               "\n\t\t Frontend tuner type 0-NULL, 1-DCT7070, 2-Maxliner, 3-FJ2207, 4-TD1316");
 +static int frontend_tuner = -1;
 +module_param(frontend_tuner, int, 0444);
 +
 +MODULE_PARM_DESC(frontend_tuner_addr, "\n\t\t Tuner IIC address of frontend");
 +static int frontend_tuner_addr = -1;
 +module_param(frontend_tuner_addr, int, 0444);
 +
 +MODULE_PARM_DESC(demod_thread, "\n\t\t demod thread");
 +static int demod_thread = 1;
 +module_param(demod_thread, int, 0644);
 +
 +
 +static int dvb_tuner_delay = 100;
 +module_param(dvb_tuner_delay, int, 0644);
 +MODULE_PARM_DESC(dvb_atsc_count, "dvb_tuner_delay");
 +#define THRD_TUNER_STRENTH_ATSC (-87)
 +#define THRD_TUNER_STRENTH_J83 (-76)
 +
 +
 +static int autoflags, autoFlagsTrig;
 +
 +/*static struct mutex aml_lock;move to dtvdd_devp->lock*/
 +const char *name_reg[] = {
 +      "demod",
 +      "iohiu",
 +      "aobus",
 +      "reset",
 +};
 +/*also see: IC_VER_NUB*/
 +const char *name_ic[] = {
 +      "gxtvbb",
 +      "txl",
 +      "txlx",
 +      "gxlx",
 +      "txhd",
 +      "tl1",
 +      "tm2",
 +};
 +
 +#define END_SYS_DELIVERY      19
 +const char *name_fe_delivery_system[] = {
 +      "UNDEFINED",
 +      "DVBC_ANNEX_A",
 +      "DVBC_ANNEX_B",
 +      "DVBT",
 +      "DSS",
 +      "DVBS",
 +      "DVBS2",
 +      "DVBH",
 +      "ISDBT",
 +      "ISDBS",
 +      "ISDBC",
 +      "ATSC",
 +      "ATSCMH",
 +      "DTMB",
 +      "CMMB",
 +      "DAB",
 +      "DVBT2",
 +      "TURBO",
 +      "DVBC_ANNEX_C",
 +      "ANALOG",       /*19*/
 +};
 +
 +static const char * const name_fe_n_mode[] = {
 +      "AM_FE_UNKNOWN_N",
 +      "AM_FE_QPSK_N",
 +      "AM_FE_QAM_N",
 +      "AM_FE_OFDM_N",
 +      "AM_FE_ATSC_N",
 +      "AM_FE_DTMB_N",
 +      "AM_FE_ISDBT_N",
 +      "AM_FE_NUM",
 +};
 +
 +static void dtvdemod_vdac_enable(bool on);
 +static void dtvdemod_set_agc_pinmux(int on);
 +
 +static int Gxtv_Demod_Dvbc_Init(/*struct aml_fe_dev *dev, */int mode);
 +static ssize_t dvbc_auto_sym_show(struct class *cls,
 +                                struct class_attribute *attr, char *buf)
 +{
 +      return sprintf(buf, "dvbc_autoflags: %s\n", autoflags ? "on" : "off");
 +}
 +
 +static ssize_t dvbc_auto_sym_store(struct class *cls,
 +                                 struct class_attribute *attr,
 +                                 const char *buf, size_t count)
 +{
 +
 +      return 0;
 +}
 +
 +static unsigned int dtmb_mode;
 +static unsigned int atsc_mode_para;
 +static enum demod_md demod_mode_para;
 +
 +
 +enum {
 +      DTMB_READ_STRENGTH = 0,
 +      DTMB_READ_SNR = 1,
 +      DTMB_READ_LOCK = 2,
 +      DTMB_READ_BCH = 3,
 +};
 +
 +enum {
 +      ATSC_READ_STRENGTH = 0,
 +      ATSC_READ_SNR = 1,
 +      ATSC_READ_LOCK = 2,
 +      ATSC_READ_SER = 3,
 +      ATSC_READ_FREQ = 4,
 +};
 +
 +enum demod_md demod_get_current_mode(void)
 +{
 +      return demod_mode_para;
 +}
 +
 +int convert_snr(int in_snr)
 +{
 +      int out_snr;
 +      static int calce_snr[40] = {
 +              5, 6, 8, 10, 13,
 +              16, 20, 25, 32, 40,
 +              50, 63, 80, 100, 126,
 +              159, 200, 252, 318, 400,
 +              504, 634, 798, 1005, 1265,
 +              1592, 2005, 2524, 3177, 4000,
 +              5036, 6340, 7981, 10048, 12649,
 +              15924, 20047, 25238, 31773, 40000};
 +      for (out_snr = 1 ; out_snr < 40; out_snr++)
 +              if (in_snr <= calce_snr[out_snr])
 +                      break;
 +
 +      return out_snr;
 +}
 +
 +static int freq_p;
 +static ssize_t atsc_para_show(struct class *cls,
 +                                struct class_attribute *attr, char *buf)
 +{
 +      int snr, lock_status, ser;
 +      struct dvb_frontend *dvbfe;
 +      int strength = 0;
 +
 +      if (atsc_mode != VSB_8)
 +              return 0;
 +
 +      if (atsc_mode_para == ATSC_READ_STRENGTH) {
 +              dvbfe = aml_get_fe();/*get_si2177_tuner();*/
 +#if 0
 +              if (dvbfe != NULL) {
 +                      if (dvbfe->ops.tuner_ops.get_strength) {
 +                              strength =
 +                              dvbfe->ops.tuner_ops.get_strength(dvbfe);
 +                      }
 +                      strength -= 100;
 +              }
 +#else
 +              strength = tuner_get_ch_power2();
 +#endif
 +              return sprintf(buf, "strength is %d\n", strength);
 +      } else if (atsc_mode_para == ATSC_READ_SNR) {
 +              snr = atsc_read_snr();
 +              return sprintf(buf, "snr is %d\n", snr);
 +      } else if (atsc_mode_para == ATSC_READ_LOCK) {
 +              lock_status =
 +                      atsc_read_reg(0x0980);
 +              return sprintf(buf, "lock_status is %x\n", lock_status);
 +      } else if (atsc_mode_para == ATSC_READ_SER) {
 +              ser = atsc_read_ser();
 +              return sprintf(buf, "ser is %d\n", ser);
 +      } else if (atsc_mode_para == ATSC_READ_FREQ) {
 +              return sprintf(buf, "freq is %d\n", freq_p);
 +      } else {
 +              return sprintf(buf, "atsc_para_show can't match mode\n");
 +      }
 +}
 +
 +static ssize_t atsc_para_store(struct class *cls,
 +                                 struct class_attribute *attr,
 +                                 const char *buf, size_t count)
 +{
 +      if (buf[0] == '0')
 +              atsc_mode_para = ATSC_READ_STRENGTH;
 +      else if (buf[0] == '1')
 +              atsc_mode_para = ATSC_READ_SNR;
 +      else if (buf[0] == '2')
 +              atsc_mode_para = ATSC_READ_LOCK;
 +      else if (buf[0] == '3')
 +              atsc_mode_para = ATSC_READ_SER;
 +      else if (buf[0] == '4')
 +              atsc_mode_para = ATSC_READ_FREQ;
 +
 +      return count;
 +}
 +
 +static ssize_t demod_para_store(struct class *cls,
 +                                 struct class_attribute *attr,
 +                                 const char *buf, size_t count)
 +{
 +      if (buf[0] == '0')
 +              demod_mode_para = UNKNOWN;
 +      else if (buf[0] == '1')
 +              demod_mode_para = AML_DVBC;
 +      else if (buf[0] == '2')
 +              demod_mode_para = AML_DTMB;
 +      else if (buf[0] == '3')
 +              demod_mode_para = AML_DVBT;
 +      else if (buf[0] == '4')
 +              demod_mode_para = AML_ATSC;
 +      else if (buf[0] == '5')
 +              demod_mode_para = AML_J83B;
 +      else if (buf[0] == '6')
 +              demod_mode_para = AML_ISDBT;
 +      else if (buf[0] == '7')
 +              demod_mode_para = AML_DVBT2;
 +
 +      return count;
 +}
 +
 +void store_dvbc_qam_mode(int qam_mode, int symbolrate)
 +{
 +      int qam_para;
 +
 +      switch (qam_mode) {
 +      case QAM_16:
 +              qam_para = 4;
 +              break;
 +      case QAM_32:
 +              qam_para = 5;
 +              break;
 +      case QAM_64:
 +              qam_para = 6;
 +              break;
 +      case QAM_128:
 +              qam_para = 7;
 +              break;
 +      case QAM_256:
 +              qam_para = 8;
 +              break;
 +      case QAM_AUTO:
 +              qam_para = 6;
 +              break;
 +      default:
 +              qam_para = 6;
 +              break;
 +      }
 +      para_demod.dvbc_qam = qam_para;
 +      para_demod.dvbc_symbol = symbolrate;
 +      PR_DBG("dvbc_qam is %d, symbolrate is %d\n",
 +              para_demod.dvbc_qam, para_demod.dvbc_symbol);
 +}
 +
 +static ssize_t demod_para_show(struct class *cls,
 +                                struct class_attribute *attr, char *buf)
 +{
 +      int rate, symolrate, qam, coderate, a;
 +
 +      if (demod_mode_para == AML_DVBC) {
 +              symolrate = para_demod.dvbc_symbol;
 +              qam = para_demod.dvbc_qam;
 +              rate = 944*symolrate*qam;
 +              rate /= 1000;
 +      } else if (demod_mode_para == AML_DTMB) {
 +              coderate = para_demod.dtmb_coderate;
 +              qam = para_demod.dtmb_qam;
 +              a = 4725;
 +              rate = 25614*qam*coderate/a;
 +              rate *= 1024;
 +      } else if (demod_mode_para == AML_DVBT) {
 +              rate = 19855;
 +      } else if (demod_mode_para == AML_ATSC) {
 +              if (atsc_mode == VSB_8)
 +                      rate = 19855;
 +              else if (atsc_mode == QAM_64)
 +                      rate = 27617;
 +              else if (atsc_mode == QAM_256)
 +                      rate = 39741;
 +              else
 +                      rate = 19855;
 +      } else {
 +              return sprintf(buf, "can't match mode\n");
 +      }
 +      return sprintf(buf, "rate %d\n", rate);
 +}
 +
 +
 +
 +
 +
 +static ssize_t dtmb_para_show(struct class *cls,
 +                                struct class_attribute *attr, char *buf)
 +{
 +      int snr, lock_status, bch, agc_if_gain[3];
 +      struct dvb_frontend *dvbfe;
 +      int strength = 0;
 +
 +      if (dtmb_mode == DTMB_READ_STRENGTH) {
 +              dvbfe = aml_get_fe();/*get_si2177_tuner();*/
 +
 +#if 0
 +              if (dvbfe != NULL)
 +                      if (dvbfe->ops.tuner_ops.get_strength) {
 +                              strength =
 +                              dvbfe->ops.tuner_ops.get_strength(dvbfe);
 +                      }
 +#else
 +              strength = tuner_get_ch_power2();
 +#endif
 +              if (strength <= -56) {
 +                      dtmb_read_agc(DTMB_D9_IF_GAIN, &agc_if_gain[0]);
 +                      strength = dtmb_get_power_strength(agc_if_gain[0]);
 +              }
 +              return sprintf(buf, "strength is %d\n", strength);
 +      } else if (dtmb_mode == DTMB_READ_SNR) {
 +              /*snr = dtmb_read_reg(DTMB_TOP_FEC_LOCK_SNR) & 0x3fff;*/
 +              snr = dtmb_reg_r_che_snr();
 +              snr = convert_snr(snr);
 +              return sprintf(buf, "snr is %d\n", snr);
 +      } else if (dtmb_mode == DTMB_READ_LOCK) {
 +              lock_status = dtmb_reg_r_fec_lock();
 +              return sprintf(buf, "lock_status is %d\n", lock_status);
 +      } else if (dtmb_mode == DTMB_READ_BCH) {
 +              bch = dtmb_reg_r_bch();
 +              return sprintf(buf, "bch is %d\n", bch);
 +      } else {
 +              return sprintf(buf, "dtmb_para_show can't match mode\n");
 +      }
 +}
 +
 +
 +static ssize_t dtmb_para_store(struct class *cls,
 +                                 struct class_attribute *attr,
 +                                 const char *buf, size_t count)
 +{
 +      if (buf[0] == '0')
 +              dtmb_mode = DTMB_READ_STRENGTH;
 +      else if (buf[0] == '1')
 +              dtmb_mode = DTMB_READ_SNR;
 +      else if (buf[0] == '2')
 +              dtmb_mode = DTMB_READ_LOCK;
 +      else if (buf[0] == '3')
 +              dtmb_mode = DTMB_READ_BCH;
 +
 +      return count;
 +}
 +
 +static int readregdata;
 +
 +static ssize_t dvbc_reg_show(struct class *cls, struct class_attribute *attr,
 +                           char *buf)
 +{
 +/*      int readregaddr=0;*/
 +      char *pbuf = buf;
 +
 +      pbuf += sprintf(pbuf, "%x", readregdata);
 +
 +      PR_INFO("read dvbc_reg\n");
 +      return pbuf - buf;
 +}
 +
 +static ssize_t dvbc_reg_store(struct class *cls, struct class_attribute *attr,
 +                            const char *buf, size_t count)
 +{
 +      return 0;
 +}
 +
 +
 +static ssize_t info_show(struct class *cls,
 +                                struct class_attribute *attr, char *buf)
 +{
 +      int pos = 0;
 +      unsigned int size = PAGE_SIZE;
 +
 +      int snr, lock_status, bch, agc_if_gain[3], ser;
 +      struct dvb_frontend *dvbfe;
 +      int strength = 0;
 +
 +      pos += snprintf(buf+pos, size-pos, "dtv demod info:\n");
 +
 +      switch (demod_mode_para) {
 +      case AML_DVBC:
 +              pos += snprintf(buf+pos, size-pos, "mode:AML_DVBC\n");
 +              break;
 +
 +      case AML_DTMB:
 +              pos += snprintf(buf+pos, size-pos, "mode:AML_DTMB\n");
 +
 +              /* DTMB_READ_STRENGTH */
 +              dvbfe = aml_get_fe();/*get_si2177_tuner();*/
 +#if 0
 +              if (dvbfe != NULL)
 +                      if (dvbfe->ops.tuner_ops.get_strength) {
 +                              strength =
 +                              dvbfe->ops.tuner_ops.get_strength(dvbfe);
 +                      }
 +#else
 +              strength = tuner_get_ch_power2();
 +#endif
 +              if (strength <= -56) {
 +                      dtmb_read_agc(DTMB_D9_IF_GAIN, &agc_if_gain[0]);
 +                      strength = dtmb_get_power_strength(agc_if_gain[0]);
 +              }
 +              pos += snprintf(buf+pos, size-pos,
 +                                      "strength: %d\n", strength);
 +
 +              /* DTMB_READ_SNR */
 +              /*snr = dtmb_read_reg(DTMB_TOP_FEC_LOCK_SNR) & 0x3fff;*/
 +              snr = dtmb_reg_r_che_snr();
 +              snr = convert_snr(snr);
 +              pos += snprintf(buf+pos, size-pos, "snr: %d\n", snr);
 +
 +              /* DTMB_READ_LOCK */
 +              /*lock_status = */
 +              /*      (dtmb_read_reg(DTMB_TOP_FEC_LOCK_SNR) >> 14) & 0x1;*/
 +              lock_status = dtmb_reg_r_fec_lock();
 +              pos += snprintf(buf+pos, size-pos, "lock: %d\n", lock_status);
 +
 +              /* DTMB_READ_BCH */
 +              bch = dtmb_reg_r_bch();
 +
 +              pos += snprintf(buf+pos, size-pos, "bch: %d\n", bch);
 +
 +              break;
 +      case AML_DVBT:
 +              pos += snprintf(buf+pos, size-pos, "mode:AML_DVBT\n");
 +              break;
 +      case AML_ATSC:
 +              pos += snprintf(buf+pos, size-pos, "mode:AML_ATSC\n");
 +              if (atsc_mode != VSB_8)
 +                      return pos;
 +
 +
 +              /* ATSC_READ_STRENGTH */
 +              dvbfe = aml_get_fe();/*get_si2177_tuner();*/
 +              if (dvbfe != NULL) {
 +#if 0
 +                      if (dvbfe->ops.tuner_ops.get_strength) {
 +                              strength =
 +                              dvbfe->ops.tuner_ops.get_strength(dvbfe);
 +                      }
 +#else
 +                      strength = tuner_get_ch_power2();
 +#endif
 +                      /*strength -= 100;*/
 +              }
 +              pos += snprintf(buf+pos, size-pos, "strength: %d\n", strength);
 +
 +
 +              /* ATSC_READ_SNR */
 +              snr = atsc_read_snr();
 +              pos += snprintf(buf+pos, size-pos, "snr: %d\n", snr);
 +
 +              /* ATSC_READ_LOCK */
 +              lock_status = atsc_read_reg(0x0980);
 +              pos += snprintf(buf+pos, size-pos, "lock: %d\n", lock_status);
 +
 +              /* ATSC_READ_SER */
 +              ser = atsc_read_ser();
 +              pos += snprintf(buf+pos, size-pos, "ser: %d\n", ser);
 +
 +              /* ATSC_READ_FREQ */
 +              pos += snprintf(buf+pos, size-pos, "freq: %d\n", freq_p);
 +
 +              break;
 +      case AML_J83B:
 +              pos += snprintf(buf+pos, size-pos, "mode:AML_J83B\n");
 +              break;
 +      case AML_ISDBT:
 +              pos += snprintf(buf+pos, size-pos, "mode:AML_ISDBT\n");
 +              break;
 +      case AML_DVBT2:
 +              pos += snprintf(buf+pos, size-pos, "mode:AML_DVBT2\n");
 +              break;
 +      default:
 +              pos += snprintf(buf+pos, size-pos, "mode:Unknown\n");
 +              break;
 +      }
 +
 +      return pos;
 +}
 +
 +
 +static CLASS_ATTR(auto_sym, 0644, dvbc_auto_sym_show, dvbc_auto_sym_store);
 +static CLASS_ATTR(dtmb_para, 0644, dtmb_para_show, dtmb_para_store);
 +/*from 666 to 644*/
 +static CLASS_ATTR(dvbc_reg, 0644, dvbc_reg_show, dvbc_reg_store);
 +static CLASS_ATTR(atsc_para, 0644, atsc_para_show, atsc_para_store);
 +static CLASS_ATTR(demod_rate, 0644, demod_para_show, demod_para_store);
 +/* DebugInfo */
 +static CLASS_ATTR(info, 0444, info_show, NULL);
 +
 +
 +/*static void dtvdemod_version(struct aml_fe_dev *dev)*/
 +static void dtvdemod_version(struct amldtvdemod_device_s *dev)
 +
 +{
 +      char soc_version[20];
 +      char *atsc_version = "1";
 +      int ic_v = get_ic_ver();
 +
 +      if (dev->atsc_version == 1)
 +              atsc_version = "1";
 +      else if (dev->atsc_version == 2)
 +              atsc_version = "2";
 +      else
 +              atsc_version = "1";
 +      atsc_set_version(dev->atsc_version);
 +
 +      if (ic_v < IC_VER_NUB && strlen(name_ic[ic_v]) < 10) {
 +              strcpy(soc_version, name_ic[ic_v]);
 +              strcat(soc_version, "-");
 +      } else {
 +              strcpy(soc_version, "other-");
 +      }
 +      if (strlen(demod_version) < 8)
 +              strcat(soc_version, demod_version);
 +      strcat(soc_version, atsc_version);
 +      PR_INFO("[dtvdemod_version] [%s]\n", soc_version);
 +}
 +
 +
 +static int amdemod_qam(enum fe_modulation qam)
 +{
 +      switch (qam) {
 +      case QAM_16:
 +              return 0;
 +      case QAM_32:
 +              return 1;
 +      case QAM_64:
 +              return 2;
 +      case QAM_128:
 +              return 3;
 +      case QAM_256:
 +              return 4;
 +      case VSB_8:
 +              return 5;
 +      case QAM_AUTO:
 +              return 6;
 +      default:
 +              return 2;
 +      }
 +      return 2;
 +}
 +
 +static int amdemod_stat_islock(/*struct aml_fe_dev *dev,*/ int mode)
 +{
 +      struct aml_demod_sts demod_sts;
 +      int lock_status;
 +      int dvbt_status1;
 +      int atsc_fsm;
 +      int ret = 0;
 +
 +      if (mode == 0) {
 +              /*DVBC*/
 +
 +              demod_sts.ch_sts = dvbc_get_ch_sts();
 +              return demod_sts.ch_sts & 0x1;
 +      } else if (mode == 1) {
 +              /*DVBT*/
 +              dvbt_status1 =
 +                      ((dvbt_read_reg((0x0a << 2)) >> 20) & 0x3ff);
 +              lock_status = (dvbt_read_reg((0x2a << 2))) & 0xf;
 +              if ((((lock_status) == 9) || ((lock_status) == 10))
 +                  && ((dvbt_status1) != 0))
 +                      return 1;
 +              else
 +                      return 0;
 +              /*((apb_read_reg(DVBT_BASE+0x0)>>12)&0x1);// */
 +              /* dvbt_get_status_ops()->get_status(&demod_sts, &demod_sta);*/
 +      } else if (mode == 2) {
 +
 +      } else if (mode == 3) {
 +              /*ATSC*/
 +              if ((atsc_mode == QAM_64) || (atsc_mode == QAM_256)) {
 +                      /*return (atsc_read_iqr_reg() >> 16) == 0x1f;*/
 +                      if ((atsc_read_iqr_reg() >> 16) == 0x1f)
 +                              ret = 1;
 +              } else if (atsc_mode == VSB_8) {
 +                      if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2)) {
 +                              if (atsc_read_reg_v4(0x2e) >= 0x76)
 +                                      ret = 1;
 +                      } else {
 +                      atsc_fsm = atsc_read_reg(0x0980);
 +                      PR_DBGL("atsc status [%x]\n", atsc_fsm);
 +                      /*return atsc_read_reg(0x0980) >= 0x79;*/
 +                      if (atsc_read_reg(0x0980) >= 0x79)
 +                              ret = 1;
 +                      }
 +              } else {
 +                      atsc_fsm = atsc_read_reg(0x0980);
 +                      PR_DBGL("atsc status [%x]\n", atsc_fsm);
 +                      /*return atsc_read_reg(0x0980) >= 0x79;*/
 +                      if (atsc_read_reg(0x0980) >= 0x79)
 +                              ret = 1;
 +              }
 +
 +              return ret;
 +      } else if (mode == 4) {
 +              /*DTMB*/
 +
 +              /*return (dtmb_read_reg(DTMB_TOP_FEC_LOCK_SNR) >> 14) & 0x1;*/
 +              return dtmb_reg_r_fec_lock();
 +      }
 +      return 0;
 +}
 +
 +#define amdemod_dvbc_stat_islock()  amdemod_stat_islock(0)
 +#define amdemod_dvbt_stat_islock()  amdemod_stat_islock(1)
 +#define amdemod_isdbt_stat_islock()  amdemod_stat_islock(2)
 +#define amdemod_atsc_stat_islock()  amdemod_stat_islock(3)
 +#define amdemod_dtmb_stat_islock()  amdemod_stat_islock(4)
 +
 +#if 0
 +/*this function is not use for txlx*/
 +static int gxtv_demod_dvbc_set_qam_mode(struct dvb_frontend *fe)
 +{
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      struct aml_demod_dvbc param;    /*mode 0:16, 1:32, 2:64, 3:128, 4:256*/
 +
 +      memset(&param, 0, sizeof(param));
 +      param.mode = amdemod_qam(c->modulation);
 +      dvbc_set_qam_mode(param.mode);
 +      return 0;
 +}
 +static int aml_dtvdm_set_qam_mode(struct dvb_frontend *fe)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +      int ret = 0;
 +
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              ret = gxtv_demod_dvbc_set_qam_mode(fe);
 +              break;
 +      case AM_FE_OFDM_N:
 +
 +              break;
 +      case AM_FE_ATSC_N:
 +              ret = gxtv_demod_atsc_set_qam_mode(fe);
 +              break;
 +      case AM_FE_DTMB_N:
 +
 +              break;
 +      case AM_FE_UNKNOWN_N:
 +      default:
 +
 +              break;
 +      }
 +
 +      return ret;
 +}
 +static int gxtv_demod_atsc_set_qam_mode(struct dvb_frontend *fe)
 +{
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      struct aml_demod_atsc param;    /*mode  3:64,  5:256, 7:vsb*/
 +      enum fe_modulation mode;
 +
 +      memset(&param, 0, sizeof(param));
 +      mode = c->modulation;
 +      /*pr_dbg("mode is %d\n", mode);*/
 +      PR_ATSC("mode is %d\n", mode);
 +      atsc_qam_set(mode);
 +      return 0;
 +}
 +
 +#endif
 +static void gxtv_demod_dvbc_release(struct dvb_frontend *fe)
 +{
 +
 +}
 +#if 0
 +static int gxtv_demod_dvbc_read_status
 +      (struct dvb_frontend *fe, enum fe_status *status)
 +{
 +/*      struct aml_fe_dev *dev = afe->dtv_demod;*/
 +      struct aml_demod_sts demod_sts;
 +      struct aml_demod_sta demod_sta;
 +      /*struct aml_demod_i2c demod_i2c;*/
 +      int ilock;
 +
 +      /*demod_sts.ch_sts = qam_read_reg(0x6);*/
 +      demod_sts.ch_sts = dvbc_get_ch_sts();
 +      dvbc_status(&demod_sta, /*&demod_i2c,*/ &demod_sts);
 +      if (demod_sts.ch_sts & 0x1) {
 +              ilock = 1;
 +              *status =
 +                      FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +                      FE_HAS_VITERBI | FE_HAS_SYNC;
 +      } else {
 +              ilock = 0;
 +              *status = FE_TIMEDOUT;
 +      }
 +      if (last_lock != ilock) {
 +              PR_DBG("%s.\n",
 +                       ilock ? "!!  >> LOCK << !!" : "!! >> UNLOCK << !!");
 +              last_lock = ilock;
 +      }
 +
 +      return 0;
 +}
 +#endif
 +struct timer_t {
 +      int enable;
 +      unsigned int start;
 +      unsigned int max;
 +};
 +static struct timer_t gtimer[4];
 +enum ddemod_timer_s {
 +      D_TIMER_DETECT,
 +      D_TIMER_SET,
 +      D_TIMER_DBG1,
 +      D_TIMER_DBG2,
 +};
 +int timer_set_max(enum ddemod_timer_s tmid, unsigned int max_val)
 +{
 +      gtimer[tmid].max = max_val;
 +      return 0;
 +}
 +int timer_begain(enum ddemod_timer_s tmid)
 +{
 +      gtimer[tmid].start = jiffies_to_msecs(jiffies);
 +      gtimer[tmid].enable = 1;
 +
 +      PR_DBG("st %d=%d\n", tmid, (int)gtimer[tmid].start);
 +      return 0;
 +}
 +int timer_disable(enum ddemod_timer_s tmid)
 +{
 +
 +      gtimer[tmid].enable = 0;
 +
 +      return 0;
 +}
 +
 +int timer_is_en(enum ddemod_timer_s tmid)
 +{
 +      return gtimer[tmid].enable;
 +}
 +
 +int timer_not_enough(enum ddemod_timer_s tmid)
 +{
 +      int ret = 0;
 +      unsigned int time;
 +
 +      if (gtimer[tmid].enable) {
 +              time = jiffies_to_msecs(jiffies);
 +              if ((time - gtimer[tmid].start) < gtimer[tmid].max) {
 +                      PR_DBG("now=%d\n", (int)time);
 +                      ret = 1;
 +              }
 +      }
 +      return ret;
 +}
 +int timer_is_enough(enum ddemod_timer_s tmid)
 +{
 +      int ret = 0;
 +      unsigned int time;
 +
 +      /*Signal stability takes 200ms */
 +      if (gtimer[tmid].enable) {
 +              time = jiffies_to_msecs(jiffies);
 +              if ((time - gtimer[tmid].start) >= gtimer[tmid].max) {
 +                      PR_DBG("now=%d\n", (int)time);
 +                      ret = 1;
 +              }
 +      }
 +      return ret;
 +}
 +
 +int timer_tuner_not_enough(void)
 +{
 +      int ret = 0;
 +      unsigned int time;
 +      enum ddemod_timer_s tmid;
 +
 +      tmid = D_TIMER_DETECT;
 +
 +      /*Signal stability takes 200ms */
 +      if (gtimer[tmid].enable) {
 +              time = jiffies_to_msecs(jiffies);
 +              if ((time - gtimer[tmid].start) < 200) {
 +                      PR_DBG("nowt=%d\n", (int)time);
 +                      ret = 1;
 +              }
 +      }
 +      return ret;
 +}
 +
 +
 +unsigned int demod_get_adc_clk(void)
 +{
 +      return demod_status.adc_freq;
 +}
 +
 +unsigned int demod_get_sys_clk(void)
 +{
 +      return demod_status.clk_freq;
 +}
 +
 +static int gxtv_demod_dvbc_read_status_timer
 +      (struct dvb_frontend *fe, enum fe_status *status)
 +{
 +      struct aml_demod_sts demod_sts;
 +      struct aml_demod_sta demod_sta;
 +      int strenth;
 +      int ilock = 0;
 +
 +      /*check tuner*/
 +      if (!timer_tuner_not_enough()) {
 +              strenth = tuner_get_ch_power2();
 +
 +              /*agc control,fine tune strength*/
 +              if (is_ic_ver(IC_VER_TL1) && (dtvdd_devp->pin_name != NULL) &&
 +                      (strncmp(fe->ops.tuner_ops.info.name, "r842", 4)
 +                      == 0)) {
 +                      strenth += 22;
 +
 +                      if (strenth <= -80)
 +                              strenth = dvbc_get_power_strength(
 +                                      qam_read_reg(0x27) & 0x7ff, strenth);
 +              }
 +
 +              if (strenth < -87) {
 +                      *status = FE_TIMEDOUT;
 +                      return 0;
 +              }
 +      }
 +
 +      /*demod_sts.ch_sts = qam_read_reg(0x6);*/
 +      demod_sts.ch_sts = dvbc_get_ch_sts();
 +      dvbc_status(&demod_sta, /*&demod_i2c,*/ &demod_sts);
 +
 +      if (demod_sts.ch_sts & 0x1) {
 +              ilock = 1;
 +              *status =
 +                      FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +                      FE_HAS_VITERBI | FE_HAS_SYNC;
 +      } else {
 +              ilock = 0;
 +
 +              if (timer_not_enough(D_TIMER_DETECT)) {
 +                      *status = 0;
 +                      PR_DBG("s=0\n");
 +              } else {
 +                      *status = FE_TIMEDOUT;
 +                      timer_disable(D_TIMER_DETECT);
 +              }
 +      }
 +
 +      if (last_lock != ilock) {
 +              PR_DBG("%s.\n",
 +                       ilock ? "!!  >> LOCK << !!" : "!! >> UNLOCK << !!");
 +              last_lock = ilock;
 +      }
 +
 +      return 0;
 +}
 +
 +static int demod_dvbc_speed_up(enum fe_status *status)
 +{
 +      unsigned int cnt, i, sts, check_ok = 0;
 +      struct aml_demod_sts demod_sts;
 +      const int dvbc_count = 5;
 +      int ilock = 0;
 +
 +      if (*status == 0) {
 +              for (cnt = 0; cnt < 10; cnt++) {
 +                      demod_sts.ch_sts = dvbc_get_ch_sts();
 +
 +                      if (demod_sts.ch_sts & 0x1) {
 +                              /*have signal*/
 +                              *status =
 +                                      FE_HAS_LOCK | FE_HAS_SIGNAL |
 +                                      FE_HAS_CARRIER |
 +                                      FE_HAS_VITERBI | FE_HAS_SYNC;
 +                              ilock = 1;
 +                              check_ok = 1;
 +                      } else {
 +                              for (i = 0; i < dvbc_count; i++) {
 +                                      msleep(25);
 +                                      sts = dvbc_get_status();
 +
 +                                      if (sts >= 0x3)
 +                                              break;
 +                              }
 +
 +                              PR_DBG("[rsj]dvbc_status is 0x%x\n", sts);
 +
 +                              if (sts < 0x3) {
 +                                      *status = FE_TIMEDOUT;
 +                                      ilock = 0;
 +                                      check_ok = 1;
 +                                      timer_disable(D_TIMER_DETECT);
 +                              }
 +                      }
 +
 +                      if (check_ok == 1)
 +                              break;
 +
 +                      msleep(20);
 +              }
 +      }
 +
 +      if (last_lock != ilock) {
 +              PR_DBG("%s : %s.\n", __func__,
 +                       ilock ? "!!  >> LOCK << !!" : "!! >> UNLOCK << !!");
 +              last_lock = ilock;
 +      }
 +
 +      return 0;
 +}
 +
 +static int gxtv_demod_dvbc_read_ber(struct dvb_frontend *fe, u32 *ber)
 +{
 +      /*struct aml_fe_dev *dev = afe->dtv_demod;*/
 +      struct aml_demod_sts demod_sts;
 +      /*struct aml_demod_i2c demod_i2c;*/
 +      struct aml_demod_sta demod_sta;
 +
 +      dvbc_status(&demod_sta, /*&demod_i2c,*/ &demod_sts);
 +      *ber = demod_sts.ch_ber;
 +      return 0;
 +}
 +
 +static int gxtv_demod_dvbc_read_signal_strength
 +      (struct dvb_frontend *fe, u16 *strength)
 +{
 +      int tuner_sr;
 +
 +
 +#if 0
 +      if (fe->ops.tuner_ops.get_strength)
 +              tn_strength = fe->ops.tuner_ops.get_strength(fe);
 +      *strength = 256 - tn_strength;
 +#else
 +      if (is_ic_ver(IC_VER_TL1) &&
 +              (dtvdd_devp->pin_name != NULL) &&
 +              (strncmp(fe->ops.tuner_ops.info.name, "r842", 4) == 0)) {
 +              tuner_sr = tuner_get_ch_power2();
 +              tuner_sr += 22;
 +
 +              if (tuner_sr <= -80)
 +                      tuner_sr = dvbc_get_power_strength(
 +                              qam_read_reg(0x27) & 0x7ff, tuner_sr);
 +
 +              if (tuner_sr < -100)
 +                      *strength = 0;
 +              else
 +                      *strength = tuner_sr + 100;
 +      } else
 +              *strength = tuner_get_ch_power3();
 +#endif
 +
 +      return 0;
 +}
 +
 +static int gxtv_demod_dvbc_read_snr(struct dvb_frontend *fe, u16 *snr)
 +{
 +      struct aml_demod_sts demod_sts;
 +      /*struct aml_demod_i2c demod_i2c;*/
 +      struct aml_demod_sta demod_sta;
 +
 +      dvbc_status(&demod_sta, /*&demod_i2c,*/ &demod_sts);
 +      *snr = demod_sts.ch_snr / 100;
 +      return 0;
 +}
 +
 +static int gxtv_demod_dvbc_read_ucblocks(struct dvb_frontend *fe, u32 *ucblocks)
 +{
 +      *ucblocks = 0;
 +      return 0;
 +}
 +
 +/*extern int aml_fe_analog_set_frontend(struct dvb_frontend *fe);*/
 +static int gxtv_demod_dvbc_set_frontend(struct dvb_frontend *fe)
 +{
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      struct aml_demod_dvbc param;    /*mode 0:16, 1:32, 2:64, 3:128, 4:256*/
 +      struct aml_demod_sts demod_sts;
 +
 +      PR_INFO("%s\n", __func__);
 +      /*timer_set_max(D_TIMER_DETECT, 4000);*/
 +      /*timer_begain(D_TIMER_DETECT);*/
 +      memset(&param, 0, sizeof(param));
 +      param.ch_freq = c->frequency / 1000;
 +      param.mode = amdemod_qam(c->modulation);
 +      param.symb_rate = c->symbol_rate / 1000;
 +      store_dvbc_qam_mode(c->modulation, param.symb_rate);
 +
 +      if (!is_ic_ver(IC_VER_TL1) && !is_ic_ver(IC_VER_TM2)) {
 +              if ((param.mode == 3) && (demod_status.tmp != Adc_mode)) {
 +                      Gxtv_Demod_Dvbc_Init(/*dev,*/ Adc_mode);
 +                      /*pr_dbg("Gxtv_Demod_Dvbc_Init,Adc_mode\n");*/
 +              } else {
 +                      /*Gxtv_Demod_Dvbc_Init(dev,Cry_mode);*/
 +              }
 +      }
 +
 +
 +      if (autoflags == 0) {
 +              /*pr_dbg("QAM_TUNING mode\n");*/
 +              /*flag=0;*/
 +      }
 +      if ((autoflags == 1) && (autoFlagsTrig == 0)
 +          && (freq_dvbc == param.ch_freq)) {
 +              PR_DBG("now is auto symbrating\n");
 +              return 0;
 +      }
 +      autoFlagsTrig = 0;
 +      last_lock = -1;
 +      PR_DBG("[gxtv_demod_dvbc_set_frontend]PARA\t"
 +             "param.ch_freq is %d||||param.symb_rate is %d,\t"
 +             "param.mode is %d\n",
 +             param.ch_freq, param.symb_rate, param.mode);
 +      tuner_set_params(fe);/*aml_fe_analog_set_frontend(fe);*/
 +      dvbc_set_ch(&demod_status, /*&demod_i2c,*/ &param);
 +      /*0xf33 dvbc mode, 0x10f33 j.83b mode*/
 +      #if 0
 +      if (is_meson_txlx_cpu() || is_meson_gxlx_cpu())
 +              /*qam_write_reg(0x7, 0xf33);*/
 +              dvbc_init_reg_ext();
 +      #endif
 +      if (is_dvbc_ver(IC_DVBC_V3))
 +              dvbc_init_reg_ext();
 +
 +      if (autoflags == 1) {
 +              PR_DBG("QAM_PLAYING mode,start auto sym\n");
 +              dvbc_set_auto_symtrack();
 +              /*      flag=1;*/
 +      }
 +      dvbc_status(&demod_status, /*&demod_i2c,*/ &demod_sts);
 +      freq_dvbc = param.ch_freq;
 +
 +      PR_DBG("AML amldemod => frequency=%d,symbol_rate=%d\r\n", c->frequency,
 +             c->symbol_rate);
 +      return 0;
 +}
 +
 +static int gxtv_demod_dvbc_get_frontend(struct dvb_frontend *fe)
 +{
 +      #if 0
 +      /*these content will be writed into eeprom .*/
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      u32 qam_mode;
 +
 +
 +      qam_mode = dvbc_get_qam_mode();
 +      c->modulation = qam_mode + 1;
 +      PR_DBG("[mode] is %d\n", c->modulation);
 +      #endif
 +
 +      return 0;
 +}
 +
 +static int Gxtv_Demod_Dvbc_Init(/*struct aml_fe_dev *dev, */int mode)
 +{
 +      struct aml_demod_sys sys;
 +      /*struct aml_demod_i2c i2c;*/
 +
 +      PR_DBG("%s\n", __func__);
 +      memset(&sys, 0, sizeof(sys));
 +      /*memset(&i2c, 0, sizeof(i2c));*/
 +      /*i2c.tuner = dev->drv->id;*/
 +      /*i2c.addr = dev->i2c_addr;*/
 +      /* 0 -DVBC, 1-DVBT, ISDBT, 2-ATSC*/
 +      demod_status.dvb_mode = Gxtv_Dvbc;
 +
 +      if (mode == Adc_mode) {
 +              sys.adc_clk = Adc_Clk_25M;
 +              sys.demod_clk = Demod_Clk_200M;
 +              demod_status.tmp = Adc_mode;
 +      } else {
 +              sys.adc_clk = ADC_CLK_24M;
 +              sys.demod_clk = Demod_Clk_72M;
 +              demod_status.tmp = Cry_mode;
 +      }
 +
 +      if (is_ic_ver(IC_VER_TL1)) {
 +              sys.adc_clk = ADC_CLK_24M;
 +              /*for timeshift mosaic issue,already fixed with tm2*/
 +              sys.demod_clk = Demod_Clk_167M;
 +              demod_status.tmp = Cry_mode;
 +      } else if (is_ic_ver(IC_VER_TM2)) {
 +              sys.adc_clk = ADC_CLK_24M;
 +              sys.demod_clk = Demod_Clk_250M;
 +              demod_status.tmp = Cry_mode;
 +      }
 +
 +      demod_status.ch_if = SI2176_5M_IF * 1000;
 +      PR_DBG("[%s]adc_clk is %d,demod_clk is %d\n", __func__, sys.adc_clk,
 +             sys.demod_clk);
 +      autoFlagsTrig = 0;
 +      /*demod_set_sys(&demod_status, &i2c, &sys);*/
 +      demod_set_sys(&demod_status, &sys);
 +      demod_mode_para = AML_DVBC;
 +      return 0;
 +}
 +
 +static void gxtv_demod_dvbt_release(struct dvb_frontend *fe)
 +{
 +
 +}
 +
 +static int gxtv_demod_dvbt_read_status
 +      (struct dvb_frontend *fe, enum fe_status *status)
 +{
 +/*      struct aml_fe *afe = fe->demodulator_priv;*/
 +      /*struct aml_demod_i2c demod_i2c;*/
 +      struct aml_demod_sta demod_sta;
 +      int ilock;
 +      unsigned char s = 0;
 +
 +      s = dvbt_get_status_ops()->get_status(&demod_sta/*, &demod_i2c*/);
 +      if (s == 1) {
 +              ilock = 1;
 +              *status =
 +                      FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +                      FE_HAS_VITERBI | FE_HAS_SYNC;
 +      } else {
 +              if (timer_not_enough(D_TIMER_DETECT)) {
 +                      ilock = 0;
 +                      *status = 0;
 +                      PR_INFO("timer not enough\n");
 +
 +              } else {
 +                      ilock = 0;
 +                      *status = FE_TIMEDOUT;
 +                      timer_disable(D_TIMER_DETECT);
 +              }
 +      }
 +      if (last_lock != ilock) {
 +              PR_INFO("%s.\n",
 +                       ilock ? "!!  >> LOCK << !!" : "!! >> UNLOCK << !!");
 +              last_lock = ilock;
 +      }
 +
 +      return 0;
 +}
 +
 +static int gxtv_demod_dvbt_read_ber(struct dvb_frontend *fe, u32 *ber)
 +{
 +/*      struct aml_fe *afe = fe->demodulator_priv;*/
 +      /*struct aml_demod_i2c demod_i2c;*/
 +      struct aml_demod_sta demod_sta;
 +
 +      *ber = dvbt_get_status_ops()->get_ber(&demod_sta) & 0xffff;
 +      return 0;
 +}
 +
 +static int gxtv_demod_dvbt_read_signal_strength
 +      (struct dvb_frontend *fe, u16 *strength)
 +{
 +      /*struct aml_fe *afe = fe->demodulator_priv;*/
 +      /*struct aml_fe_dev *dev = afe->dtv_demod;*/
 +
 +      /**strength = 256 - tuner_get_ch_power(fe);*/
 +
 +      *strength = tuner_get_ch_power3();
 +
 +      PR_DBGL("[RSJ]tuner strength is %d dbm\n", *strength);
 +      return 0;
 +}
 +
 +static int gxtv_demod_dvbt_read_snr(struct dvb_frontend *fe, u16 *snr)
 +{
 +/*      struct aml_fe *afe = fe->demodulator_priv;*/
 +/*      struct aml_demod_sts demod_sts;*/
 +/*    struct aml_demod_i2c demod_i2c;*/
 +      struct aml_demod_sta demod_sta;
 +
 +      *snr = dvbt_get_status_ops()->get_snr(&demod_sta/*, &demod_i2c*/);
 +      *snr /= 8;
 +      PR_DBGL("[RSJ]snr is %d dbm\n", *snr);
 +      return 0;
 +}
 +
 +static int gxtv_demod_dvbt_read_ucblocks(struct dvb_frontend *fe, u32 *ucblocks)
 +{
 +      *ucblocks = 0;
 +      return 0;
 +}
 +int convert_bandwidth(unsigned int input)
 +{
 +      /*int output;*/
 +      enum fe_bandwidth output;
 +
 +      output = 3;
 +      switch (input) {
 +      case 10000000:
 +              output = BANDWIDTH_10_MHZ;
 +              break;
 +      case 8000000:
 +              output = BANDWIDTH_8_MHZ;
 +              break;
 +      case 7000000:
 +              output = BANDWIDTH_7_MHZ;
 +              break;
 +      case 6000000:
 +              output = BANDWIDTH_6_MHZ;
 +              break;
 +      case 5000000:
 +              output = BANDWIDTH_5_MHZ;
 +              break;
 +      case 1712000:
 +              output = BANDWIDTH_1_712_MHZ;
 +              break;
 +      case 0:
 +              output = BANDWIDTH_AUTO;
 +              break;
 +      }
 +      return output;
 +
 +
 +}
 +
 +static int gxtv_demod_dvbt_set_frontend(struct dvb_frontend *fe)
 +{
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      /*struct aml_demod_sts demod_sts;*/
 +      struct aml_demod_dvbt param;
 +
 +
 +
 +
 +      /*////////////////////////////////////*/
 +      /* bw == 0 : 8M*/
 +      /*       1 : 7M*/
 +      /*       2 : 6M*/
 +      /*       3 : 5M*/
 +      /* agc_mode == 0: single AGC*/
 +      /*             1: dual AGC*/
 +      /*////////////////////////////////////*/
 +      memset(&param, 0, sizeof(param));
 +      param.ch_freq = c->frequency / 1000;
 +
 +      //param.bw = c->bandwidth_hz;
 +      param.bw = convert_bandwidth(c->bandwidth_hz);
 +      PR_INFO("%s:bw=%d\n", __func__, c->bandwidth_hz);
 +      param.agc_mode = 1;
 +      /*ISDBT or DVBT : 0 is QAM, 1 is DVBT, 2 is ISDBT,*/
 +      /* 3 is DTMB, 4 is ATSC */
 +      param.dat0 = 1;
 +      last_lock = -1;
 +
 +      tuner_set_params(fe);/*aml_fe_analog_set_frontend(fe);*/
 +      dvbt_set_ch(&demod_status, /*&demod_i2c,*/ &param);
 +
 +
 +      /*pr_dbg("AML amldemod => frequency=%d,symbol_rate=%d\r\n",*/
 +      /* p->frequency,p->u.qam.symbol_rate);*/
 +      return 0;
 +}
 +
 +static int gxtv_demod_dvbt_get_frontend(struct dvb_frontend *fe)
 +{                               /*these content will be writed into eeprom .*/
 +
 +      return 0;
 +}
 +
 +/*int Gxtv_Demod_Dvbt_Init(struct aml_fe_dev *dev)*/
 +int Gxtv_Demod_Dvbt_Init(void)
 +{
 +      struct aml_demod_sys sys;
 +
 +      PR_DBG("AML Demod DVB-T init\r\n");
 +
 +      memset(&sys, 0, sizeof(sys));
 +
 +      memset(&demod_status, 0, sizeof(demod_status));
 +
 +      /* 0 -DVBC, 1-DVBT, ISDBT, 2-ATSC*/
 +      demod_status.dvb_mode = Gxtv_Dvbt_Isdbt;
 +      sys.adc_clk = ADC_CLK_24M;
 +      sys.demod_clk = Demod_Clk_60M;
 +      demod_status.ch_if = SI2176_5M_IF * 1000;
 +
 +      demod_set_sys(&demod_status, &sys);
 +      demod_mode_para = AML_DVBT;
 +      return 0;
 +}
 +
 +static void gxtv_demod_atsc_release(struct dvb_frontend *fe)
 +{
 +
 +}
 +
 +
 +static int gxtv_demod_atsc_get_frontend_algo(struct dvb_frontend *fe)
 +{
 +      return DVBFE_ALGO_HW;
 +}
 +static int gxtv_demod_txlx_get_frontend_algo(struct dvb_frontend *fe)
 +{
 +
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      int ret = DVBFE_ALGO_HW;
 +
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              /*dvbc*/
 +              ret = DVBFE_ALGO_HW;
 +              break;
 +
 +      case AM_FE_OFDM_N:
 +      case AM_FE_ISDBT_N:
 +              /*dvbt*/
 +              ret = DVBFE_ALGO_HW;
 +
 +              break;
 +      case AM_FE_ATSC_N:
 +              ret = DVBFE_ALGO_HW;
 +              break;
 +      case AM_FE_DTMB_N:
 +              ret = DVBFE_ALGO_HW;
 +              break;
 +      case AM_FE_UNKNOWN_N:
 +      default:
 +
 +              break;
 +      }
 +
 +      return ret;
 +
 +}
 +
 +unsigned  int ats_thread_flg;
 +static int gxtv_demod_atsc_read_status
 +      (struct dvb_frontend *fe, enum fe_status *status)
 +{
 +
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      struct aml_demod_sts demod_sts;
 +      /*struct aml_demod_i2c demod_i2c;*/
 +      struct aml_demod_sta demod_sta;
 +      int ilock;
 +      /*struct dvb_frontend *dvbfe;*/
 +      unsigned char s = 0;
 +      int strength = 0;
 +
 +      /*debug only*/
 +      static enum fe_status dbg_lst_status;   /* last status */
 +
 +
 +      if (!demod_thread) {
 +              ilock = 1;
 +              *status =
 +                      FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +                      FE_HAS_VITERBI | FE_HAS_SYNC;
 +              return 0;
 +      }
 +      if (!get_dtvpll_init_flag())
 +              return 0;
 +
 +      if ((c->modulation <= QAM_AUTO) && (c->modulation != QPSK)
 +              && (atsc_flag == QAM_AUTO)) {
 +              s = amdemod_dvbc_stat_islock();
 +              dvbc_status(&demod_sta,/* &demod_i2c, */&demod_sts);
 +      } else if ((c->modulation > QAM_AUTO)
 +              && (atsc_flag == VSB_8)) {
 +              /*atsc_thread();*/
 +              s = amdemod_atsc_stat_islock();
 +
 +              if (!is_ic_ver(IC_VER_TL1) && !is_ic_ver(IC_VER_TM2)) {
 +                      if ((s == 0) && (last_lock == 1)
 +                              && (atsc_read_reg(0x0980) >= 0x76)) {
 +                              s = 1;
 +                              PR_ATSC("[rsj] unlock,but fsm >= 0x76\n");
 +                      }
 +              }
 +      }
 +#if 0 /*debug only move to end*/
 +      dvbfe = get_si2177_tuner();
 +      if (dvbfe != NULL)
 +              if (dvbfe->ops.tuner_ops.get_strength) {
 +                      strength =
 +                      dvbfe->ops.tuner_ops.get_strength(dvbfe);
 +              }
 +      /*strength -= 100;*/
 +      pr_dbg("[rsj_test]freq[%d] strength[%d]\n", freq_p, strength);
 +#endif
 +      if (s == 1) {
 +              ilock = 1;
 +              *status =
 +                      FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +                      FE_HAS_VITERBI | FE_HAS_SYNC;
 +      } else {
 +              ilock = 0;
 +              if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2)) {
 +                      if (timer_not_enough(D_TIMER_DETECT)) {
 +                              *status = 0;
 +                              PR_DBG("s=0\n");
 +                      } else {
 +                              *status = FE_TIMEDOUT;
 +                              timer_disable(D_TIMER_DETECT);
 +                      }
 +              } else {
 +                      *status = FE_TIMEDOUT;
 +              }
 +              #if 0
 +              if (ats_thread_flg)
 +                      *status = FE_TIMEDOUT;
 +              else
 +                      *status = 0;
 +              #endif
 +
 +      }
 +#if 1 /*debug only*/
 +      if (last_lock != ilock) {
 +              PR_INFO("%s.\n",
 +                       ilock ? "!!  >> LOCK << !!" : "!! >> UNLOCK << !!");
 +              last_lock = ilock;
 +      }
 +#endif
 +      /*debug only*/
 +      if (aml_demod_debug & DBG_ATSC) {
 +              if ((dbg_lst_status != s) || (last_lock != ilock)) {
 +                      /* check tuner */
 +                      strength = tuner_get_ch_power2();
 +
 +                      PR_ATSC("s=%d(1 is lock),lock=%d\n", s, ilock);
 +                      PR_ATSC("[rsj_test]freq[%d] strength[%d]\n",
 +                              freq_p, strength);
 +
 +                      /*update */
 +                      dbg_lst_status = s;
 +                      last_lock = ilock;
 +              }
 +              /*aml_dbgatscl(".");*/
 +      }
 +      return 0;
 +}
 +
 +static int gxtv_demod_atsc_read_ber(struct dvb_frontend *fe, u32 *ber)
 +{
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +
 +      if (!get_dtvpll_init_flag())
 +              return 0;
 +      if ((c->modulation > QAM_AUTO)
 +              && (atsc_flag == VSB_8))
 +              *ber = atsc_read_reg(0x980)&0xffff;
 +      else if (((c->modulation == QAM_256)
 +              || (c->modulation == QAM_64))
 +              && (atsc_flag == QAM_AUTO))
 +
 +              *ber = dvbc_get_status();
 +      return 0;
 +}
 +
 +static int gxtv_demod_atsc_read_signal_strength
 +      (struct dvb_frontend *fe, u16 *strength)
 +{
 +      int strenth;
 +
 +      strenth = tuner_get_ch_power(fe);
 +/*    struct aml_fe *afe = fe->demodulator_priv;*/
 +      /*struct aml_fe_dev *dev = afe->dtv_demod; */
 +      if (is_ic_ver(IC_VER_TL1) && (dtvdd_devp->pin_name != NULL) &&
 +              (strncmp(fe->ops.tuner_ops.info.name, "r842", 4) == 0)) {
 +              if ((fe->dtv_property_cache.modulation <= QAM_AUTO) &&
 +                      (fe->dtv_property_cache.modulation != QPSK))
 +                      strenth += 18;
 +              else {
 +                      strenth += 15;
 +                      if (strenth <= -80)
 +                              strenth = atsc_get_power_strength(
 +                                      atsc_read_reg_v4(0x44) & 0xfff,
 +                                              strenth);
 +              }
 +
 +              if (strenth < -100)
 +                      *strength = 0;
 +              else
 +                      *strength = strenth + 100;
 +      } else
 +              *strength = tuner_get_ch_power3();
 +
 +      if (*strength > 100)
 +              *strength = 100;
 +
 +      return 0;
 +}
 +
 +static int gxtv_demod_atsc_read_snr(struct dvb_frontend *fe, u16 *snr)
 +{
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      struct aml_demod_sts demod_sts;
 +      /*struct aml_demod_i2c demod_i2c;*/
 +      struct aml_demod_sta demod_sta;
 +
 +      if ((c->modulation <= QAM_AUTO)
 +              && (c->modulation != QPSK)
 +              && (atsc_flag == QAM_AUTO)) {
 +              dvbc_status(&demod_sta, /*&demod_i2c, */&demod_sts);
 +              *snr = demod_sts.ch_snr / 100;
 +      } else if ((c->modulation > QAM_AUTO)
 +              && (atsc_flag == VSB_8))
 +              *snr = atsc_read_snr();
 +      return 0;
 +}
 +
 +static int gxtv_demod_atsc_read_ucblocks(struct dvb_frontend *fe, u32 *ucblocks)
 +{
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +
 +      if (!demod_thread)
 +              return 0;
 +      if ((c->modulation > QAM_AUTO)
 +              && (atsc_flag == VSB_8))
 +              atsc_thread();
 +      *ucblocks = 0;
 +      return 0;
 +}
 +
 +static int gxtv_demod_atsc_set_frontend(struct dvb_frontend *fe)
 +{
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      struct aml_demod_atsc param_atsc;
 +      struct aml_demod_dvbc param_j83b;
 +      int temp_freq = 0;
 +      union ATSC_DEMOD_REG_0X6A_BITS Val_0x6a;
 +      union ATSC_CNTR_REG_0X20_BITS Val_0x20;
 +      int nco_rate;
 +      /*[0]: specturm inverse(1),normal(0); [1]:if_frequency*/
 +      unsigned int tuner_freq[2] = {0};
 +
 +      memset(&param_atsc, 0, sizeof(param_atsc));
 +      memset(&param_j83b, 0, sizeof(param_j83b));
 +      if (!demod_thread)
 +              return 0;
 +      freq_p = c->frequency / 1000;
 +      PR_INFO("c->modulation is %d,freq_p is %d, atsc_flag is %d\n",
 +              c->modulation, freq_p, atsc_flag);
 +      last_lock = -1;
 +      atsc_mode = c->modulation;
 +      /* param.mode = amdemod_qam(p->u.vsb.modulation);*/
 +      tuner_set_params(fe);/*aml_fe_analog_set_frontend(fe);*/
 +      if ((c->modulation <= QAM_AUTO) && (c->modulation != QPSK)) {
 +              if (atsc_flag != QAM_AUTO)
 +                      atsc_flag = QAM_AUTO;
 +              /* demod_set_demod_reg(0x502, TXLX_ADC_REG6);*/
 +              /*sys_clk=167M*/
 +              if (!is_ic_ver(IC_VER_TM2))
 +                      dd_tvafe_hiu_reg_write(D_HHI_DEMOD_CLK_CNTL, 0x502);
 +
 +              demod_set_mode_ts(Gxtv_Dvbc);
 +              param_j83b.ch_freq = c->frequency / 1000;
 +              param_j83b.mode = amdemod_qam(c->modulation);
 +              if (c->modulation == QAM_64)
 +                      param_j83b.symb_rate = 5057;
 +              else if (c->modulation == QAM_256)
 +                      param_j83b.symb_rate = 5361;
 +              else
 +                      param_j83b.symb_rate = 5361;
 +
 +              if (is_ic_ver(IC_VER_TL1)) {
 +                      /*for timeshift mosaic issue,already fixed with tm2*/
 +                      demod_status.clk_freq = Demod_Clk_167M;
 +                      nco_rate = (demod_status.adc_freq * 256)
 +                              / demod_status.clk_freq + 2;
 +                      front_write_reg_v4(0x20,
 +                              ((front_read_reg_v4(0x20) & ~0xff)
 +                              | (nco_rate & 0xff)));
 +                      /*for timeshift mosaic issue,already fixed with tm2*/
 +                      front_write_reg_v4(0x2f, 0x5);
 +              } else if (is_ic_ver(IC_VER_TM2)) {
 +                      nco_rate = (demod_status.adc_freq * 256)
 +                              / demod_status.clk_freq + 2;
 +                      front_write_reg_v4(0x20,
 +                              ((front_read_reg_v4(0x20) & ~0xff)
 +                              | (nco_rate & 0xff)));
 +              }
 +
 +              dvbc_set_ch(&demod_status, /*&demod_i2c, */&param_j83b);
 +
 +              if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2)) {
 +                      qam_write_reg(0x7, 0x10f33);
 +
 +                      /*don't bypass afifo,can run demod at 250M
 +                       *for timeshift mosaic issue
 +                       */
 +                      if (is_ic_ver(IC_VER_TM2))
 +                              qam_write_reg(0x87,
 +                                      qam_read_reg(0x87) & 0xfffffffe);
 +
 +                      set_j83b_filter_reg_v4();
 +                      qam_write_reg(0x12, 0x50e1000);
 +                      qam_write_reg(0x30, 0x41f2f69);
 +              }
 +      } else if (c->modulation > QAM_AUTO) {
 +              if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2)) {
 +                      Val_0x6a.bits = atsc_read_reg_v4(ATSC_DEMOD_REG_0X6A);
 +                      Val_0x6a.b.peak_thd = 0x6;//Let CCFO Quality over 6
 +                      atsc_write_reg_v4(ATSC_DEMOD_REG_0X6A, Val_0x6a.bits);
 +                      atsc_write_reg_v4(ATSC_EQ_REG_0XA5, 0x8c);
 +
 +                      if (fe->ops.tuner_ops.get_if_frequency)
 +                              fe->ops.tuner_ops.
 +                                      get_if_frequency(fe, tuner_freq);
 +
 +                      /*bit 2: invert specturm, for r842 tuner AGC control*/
 +                      if (tuner_freq[0] == 1)
 +                              atsc_write_reg_v4(ATSC_DEMOD_REG_0X56, 0x4);
 +                      else
 +                              atsc_write_reg_v4(ATSC_DEMOD_REG_0X56, 0x0);
 +
 +                      if (demod_status.adc_freq == ADC_CLK_24M) {
 +                              atsc_write_reg_v4(ATSC_DEMOD_REG_0X54,
 +                                      0x1aaaaa);
 +
 +                              atsc_write_reg_v4(ATSC_DEMOD_REG_0X55,
 +                                      0x3ae28d);
 +
 +                              atsc_write_reg_v4(ATSC_DEMOD_REG_0X6E,
 +                                      0x16e3600);
 +                      }
 +
 +                      /*for timeshift mosaic issue*/
 +                      atsc_write_reg_v4(0x12, 0x18);
 +                      Val_0x20.bits = atsc_read_reg_v4(ATSC_CNTR_REG_0X20);
 +                      Val_0x20.b.cpu_rst = 1;
 +                      atsc_write_reg_v4(ATSC_CNTR_REG_0X20, Val_0x20.bits);
 +                      Val_0x20.b.cpu_rst = 0;
 +                      atsc_write_reg_v4(ATSC_CNTR_REG_0X20, Val_0x20.bits);
 +                      usleep_range(5000, 5001);
 +              } else {
 +                      if (atsc_flag != VSB_8)
 +                              atsc_flag = VSB_8;
 +                      /*demod_set_demod_reg(0x507, TXLX_ADC_REG6);*/
 +                      dd_tvafe_hiu_reg_write(D_HHI_DEMOD_CLK_CNTL, 0x507);
 +                      demod_set_mode_ts(Gxtv_Atsc);
 +                      param_atsc.ch_freq = c->frequency / 1000;
 +                      param_atsc.mode = c->modulation;
 +                      atsc_set_ch(&demod_status, /*&demod_i2c,*/ &param_atsc);
 +              }
 +      }
 +
 +      if ((auto_search_std == 1) && ((c->modulation <= QAM_AUTO)
 +      && (c->modulation != QPSK))) {
 +              unsigned char s = 0;
 +
 +              msleep(std_lock_timeout);
 +              s = amdemod_dvbc_stat_islock();
 +              if (s == 1) {
 +                      PR_DBG("atsc std mode is %d locked\n", atsc_mode);
 +
 +                      return 0;
 +              }
 +              if ((c->frequency == 79000000) || (c->frequency == 85000000)) {
 +                      temp_freq = (c->frequency + 2000000) / 1000;
 +                      param_j83b.ch_freq = temp_freq;
 +                      PR_DBG("irc fre:%d\n", param_j83b.ch_freq);
 +                      c->frequency = param_j83b.ch_freq * 1000;
 +
 +
 +                      tuner_set_params(fe);
 +                      demod_set_mode_ts(Gxtv_Dvbc);
 +                      param_j83b.mode = amdemod_qam(c->modulation);
 +                      if (c->modulation == QAM_64)
 +                              param_j83b.symb_rate = 5057;
 +                      else if (c->modulation == QAM_256)
 +                              param_j83b.symb_rate = 5361;
 +                      else
 +                              param_j83b.symb_rate = 5361;
 +                      dvbc_set_ch(&demod_status, /*&demod_i2c,*/
 +                      &param_j83b);
 +
 +                      msleep(std_lock_timeout);
 +                      s = amdemod_dvbc_stat_islock();
 +                      if (s == 1) {
 +                              PR_DBG("irc mode is %d locked\n", atsc_mode);
 +                      } else {
 +                              temp_freq = (c->frequency - 1250000) / 1000;
 +                              param_j83b.ch_freq = temp_freq;
 +                              PR_DBG("hrc fre:%d\n", param_j83b.ch_freq);
 +                              c->frequency = param_j83b.ch_freq * 1000;
 +
 +                              tuner_set_params(fe);
 +                              demod_set_mode_ts(Gxtv_Dvbc);
 +                              param_j83b.mode = amdemod_qam(c->modulation);
 +                              if (c->modulation == QAM_64)
 +                                      param_j83b.symb_rate = 5057;
 +                              else if (c->modulation == QAM_256)
 +                                      param_j83b.symb_rate = 5361;
 +                              else
 +                                      param_j83b.symb_rate = 5361;
 +                              dvbc_set_ch(&demod_status, /*&demod_i2c,*/
 +                              &param_j83b);
 +                      }
 +              } else {
 +                      param_j83b.ch_freq = (c->frequency - 1250000) / 1000;
 +                      PR_DBG("hrc fre:%d\n", param_j83b.ch_freq);
 +                      c->frequency = param_j83b.ch_freq * 1000;
 +
 +                      demod_set_mode_ts(Gxtv_Dvbc);
 +                      param_j83b.mode = amdemod_qam(c->modulation);
 +                      if (c->modulation == QAM_64)
 +                              param_j83b.symb_rate = 5057;
 +                      else if (c->modulation == QAM_256)
 +                              param_j83b.symb_rate = 5361;
 +                      else
 +                              param_j83b.symb_rate = 5361;
 +                      dvbc_set_ch(&demod_status, /*&demod_i2c,*/
 +                      &param_j83b);
 +              }
 +      }
 +      PR_DBG("atsc_mode is %d\n", atsc_mode);
 +      /*pr_dbg("AML amldemod => frequency=%d,symbol_rate=%d\r\n",*/
 +      /* p->frequency,p->u.qam.symbol_rate);*/
 +      return 0;
 +}
 +
 +static int gxtv_demod_atsc_get_frontend(struct dvb_frontend *fe)
 +{                               /*these content will be writed into eeprom .*/
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +
 +      PR_DBG("c->frequency is %d\n", c->frequency);
 +      return 0;
 +}
 +
 +void atsc_detect_first(struct dvb_frontend *fe, enum fe_status *status)
 +{
 +      unsigned int ucblocks;
 +      unsigned int atsc_status;
 +      enum fe_status s;
 +      int strenth;
 +      int cnt;
 +      int check_ok;
 +
 +      /*tuner strength*/
 +      if (dvb_tuner_delay > 9)
 +              msleep(dvb_tuner_delay);
 +
 +      strenth = tuner_get_ch_power(fe);
 +
 +      /*agc control,fine tune strength*/
 +      if (is_ic_ver(IC_VER_TL1) && (dtvdd_devp->pin_name != NULL) &&
 +              (strncmp(fe->ops.tuner_ops.info.name, "r842", 4) == 0)) {
 +              strenth += 15;
 +              if (strenth <= -80)
 +                      strenth = atsc_get_power_strength(
 +                              atsc_read_reg_v4(0x44) & 0xfff, strenth);
 +      }
 +
 +      if (strenth < THRD_TUNER_STRENTH_ATSC) {
 +              *status = FE_TIMEDOUT;
 +              PR_ATSC("tuner:no signal!\n");
 +              return;
 +      }
 +      #define CNT_FIRST_ATSC  (2)
 +      check_ok = 0;
 +
 +      for (cnt = 0; cnt < CNT_FIRST_ATSC; cnt++) {
 +              if (!is_ic_ver(IC_VER_TL1) && !is_ic_ver(IC_VER_TM2))
 +                      gxtv_demod_atsc_read_ucblocks(fe, &ucblocks);
 +
 +              gxtv_demod_atsc_read_status(fe, &s);
 +
 +              if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2)) {
 +                      *status = s;
 +                      break;
 +              }
 +
 +              //      *status = s;
 +
 +              if (s != 0x1f) {
 +                      gxtv_demod_atsc_read_ber(fe, &atsc_status);
 +                      if ((atsc_status < 0x60)) {
 +                              *status = FE_TIMEDOUT;
 +                              check_ok = 1;
 +                      }
 +              } else {
 +                      check_ok = 1;
 +                      *status = s;
 +              }
 +
 +              if (check_ok)
 +                      break;
 +
 +      }
 +      PR_ATSC("%s,detect=0x%x,cnt=%d\n", __func__,
 +                      (unsigned int)*status, cnt);
 +}
 +
 +
 +static int dvb_j83b_count = 5;
 +module_param(dvb_j83b_count, int, 0644);
 +MODULE_PARM_DESC(dvb_atsc_count, "dvb_j83b_count");
 +/*come from j83b_speedup_func*/
 +
 +static int atsc_j83b_detect_first(struct dvb_frontend *fe, enum fe_status *s)
 +{
 +      int j83b_status, i;
 +      /*struct dvb_frontend_private *fepriv = fe->frontend_priv;*/
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      int strenth;
 +      enum fe_status cs;
 +      int cnt;
 +      int check_ok;
 +
 +      j83b_status = 0;
 +
 +      /*tuner:*/
 +      if (dvb_tuner_delay > 9)
 +              msleep(dvb_tuner_delay);
 +
 +      strenth = tuner_get_ch_power(fe);
 +
 +      /*agc control,fine tune strength*/
 +      if (is_ic_ver(IC_VER_TL1) && (dtvdd_devp->pin_name != NULL) &&
 +              (strncmp(fe->ops.tuner_ops.info.name, "r842", 4) == 0))
 +              strenth += 18;
 +
 +      if (strenth < THRD_TUNER_STRENTH_J83) {
 +              *s = FE_TIMEDOUT;
 +              PR_ATSC("tuner:no signal!j83\n");
 +              return 0;
 +      }
 +      check_ok = 0;
 +
 +      /*first check signal max time*/
 +      #define CNT_FIRST  (10)
 +
 +      for (cnt = 0; cnt < CNT_FIRST; cnt++) {
 +              gxtv_demod_atsc_read_status(fe, &cs);
 +
 +              if (cs != 0x1f) {
 +                      /*msleep(200);*/
 +                      PR_DBG("[j.83b] 1\n");
 +                      for (i = 0; i < dvb_j83b_count; i++) {
 +                              msleep(25);
 +                              gxtv_demod_atsc_read_ber(fe, &j83b_status);
 +
 +                              /*J.83 status >=0x38,has signal*/
 +                              if (j83b_status >= 0x3)
 +                                      break;
 +                      }
 +                      PR_DBG("[rsj]j.83b_status is %x,modulation is %d\n",
 +                                      j83b_status,
 +                                      c->modulation);
 +
 +                      if (j83b_status < 0x3) {
 +                              *s = FE_TIMEDOUT;
 +                              check_ok = 1;
 +                      }
 +
 +              } else {
 +                      /*have signal*/
 +                      *s = cs;
 +                      check_ok = 1;
 +              }
 +
 +              if (check_ok)
 +                      break;
 +
 +              msleep(50);
 +      }
 +
 +
 +      if (!check_ok)
 +              *s = FE_TIMEDOUT;
 +
 +      PR_ATSC("j83 first:cnt:%d,sgn:0x%x\n", cnt, *s);
 +      return 0;
 +}
 +static int atsc_j83b_polling(struct dvb_frontend *fe, enum fe_status *s)
 +{
 +      int j83b_status, i;
 +      /*struct dvb_frontend_private *fepriv = fe->frontend_priv;*/
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      int strenth;
 +
 +      PR_DBG("+7+");
 +
 +      j83b_status = 0;
 +      strenth = tuner_get_ch_power(fe);
 +      if (strenth < THRD_TUNER_STRENTH_J83) {
 +              *s = FE_TIMEDOUT;
 +              PR_DBGL("tuner:no signal!j83\n");
 +              return 0;
 +      }
 +
 +      gxtv_demod_atsc_read_status(fe, s);
 +
 +      if (*s != 0x1f) {
 +              /*msleep(200);*/
 +              PR_DBG("[j.83b] 1\n");
 +              for (i = 0; i < dvb_j83b_count; i++) {
 +                      msleep(25);
 +                      gxtv_demod_atsc_read_ber(fe, &j83b_status);
 +
 +                      /*J.83 status >=0x38,has signal*/
 +                      if (j83b_status >= 0x3)
 +                              break;
 +              }
 +              PR_DBG("[rsj]j.83b_status is %x,modulation is %d\n",
 +                              j83b_status,
 +                              c->modulation);
 +
 +              if (j83b_status < 0x3)
 +                      *s = FE_TIMEDOUT;
 +      }
 +
 +
 +
 +
 +      return 0;
 +}
 +
 +void atsc_polling(struct dvb_frontend *fe, enum fe_status *status)
 +{
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +
 +      if (!demod_thread)
 +              return;
 +
 +      if (c->modulation == QPSK) {
 +              PR_DBG("mode is qpsk, return;\n");
 +              /*return;*/
 +      } else if (c->modulation <= QAM_AUTO) {
 +              atsc_j83b_polling(fe, status);
 +      } else {
 +              atsc_thread();
 +              gxtv_demod_atsc_read_status(fe, status);
 +      }
 +
 +
 +
 +}
 +
 +static int gxtv_demod_atsc_tune(struct dvb_frontend *fe, bool re_tune,
 +      unsigned int mode_flags, unsigned int *delay, enum fe_status *status)
 +{
 +      /*
 +       * It is safe to discard "params" here, as the DVB core will sync
 +       * fe->dtv_property_cache with fepriv->parameters_in, where the
 +       * DVBv3 params are stored. The only practical usage for it indicate
 +       * that re-tuning is needed, e. g. (fepriv->state & FESTATE_RETUNE) is
 +       * true.
 +       */
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      /*int ret = 0;*/
 +
 +      PR_ATSC("%s:\n", __func__);
 +      *delay = HZ/2;
 +      if (re_tune) {
 +              dtvdd_devp->en_detect = 1; /*fist set*/
 +              /*c->delivery_system = aml_demod_delivery_sys;*/
 +      /*PR_ATSC("delivery_system=%d\n", aml_demod_delivery_sys);*/
 +              gxtv_demod_atsc_set_frontend(fe);
 +
 +              if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2))
 +                      timer_begain(D_TIMER_DETECT);
 +
 +              if (c->modulation ==  QPSK) {
 +                      PR_ATSC("modulation is QPSK do nothing!");
 +              } else if (c->modulation <= QAM_AUTO) {
 +                      PR_ATSC("j83\n");
 +                      atsc_j83b_detect_first(fe, status);
 +              } else if (c->modulation > QAM_AUTO) {
 +                      atsc_detect_first(fe, status);
 +              }
 +
 +              return 0;
 +      }
 +#if 1
 +      if (!dtvdd_devp->en_detect) {
 +              PR_DBGL("tune:not enable\n");
 +              return 0;
 +      }
 +#endif
 +      if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2)) {
 +              if (c->modulation > QAM_AUTO)
 +                      atsc_detect_first(fe, status);
 +              else if (c->modulation <= QAM_AUTO &&
 +                      (c->modulation !=  QPSK))
 +                      atsc_j83b_detect_first(fe, status);
 +      } else {
 +              atsc_polling(fe, status);
 +      }
 +
 +      return 0;
 +
 +}
 +
 +static int gxtv_demod_dvbt_tune(struct dvb_frontend *fe, bool re_tune,
 +      unsigned int mode_flags, unsigned int *delay, enum fe_status *status)
 +{
 +      /*
 +       * It is safe to discard "params" here, as the DVB core will sync
 +       * fe->dtv_property_cache with fepriv->parameters_in, where the
 +       * DVBv3 params are stored. The only practical usage for it indicate
 +       * that re-tuning is needed, e. g. (fepriv->state & FESTATE_RETUNE) is
 +       * true.
 +       */
 +
 +      *delay = HZ/2;
 +
 +      /*PR_ATSC("%s:\n", __func__);*/
 +#if 1
 +      if (re_tune) {
 +
 +              timer_begain(D_TIMER_DETECT);
 +              PR_INFO("%s:\n", __func__);
 +              dtvdd_devp->en_detect = 1; /*fist set*/
 +
 +              gxtv_demod_dvbt_set_frontend(fe);
 +              gxtv_demod_dvbt_read_status(fe, status);
 +              return 0;
 +      }
 +#endif
 +      if (!dtvdd_devp->en_detect) {
 +              PR_DBGL("tune:not enable\n");
 +              return 0;
 +      }
 +      /*polling*/
 +      gxtv_demod_dvbt_read_status(fe, status);
 +
 +      if (*status & FE_HAS_LOCK) {
 +              timer_disable(D_TIMER_SET);
 +      } else {
 +              if (!timer_is_en(D_TIMER_SET))
 +                      timer_begain(D_TIMER_SET);
 +      }
 +
 +      if (timer_is_enough(D_TIMER_SET)) {
 +              gxtv_demod_dvbt_set_frontend(fe);
 +              timer_disable(D_TIMER_SET);
 +      }
 +
 +
 +
 +      return 0;
 +
 +}
 +
 +int Gxtv_Demod_Atsc_Init(void/*struct aml_fe_dev *dev*/)
 +{
 +      struct aml_demod_sys sys;
 +      /*struct aml_demod_i2c i2c;*/
 +
 +      PR_DBG("%s\n", __func__);
 +
 +      memset(&sys, 0, sizeof(sys));
 +      /*memset(&i2c, 0, sizeof(i2c));*/
 +      memset(&demod_status, 0, sizeof(demod_status));
 +      /* 0 -DVBC, 1-DVBT, ISDBT, 2-ATSC*/
 +      demod_status.dvb_mode = Gxtv_Atsc;
 +      sys.adc_clk = ADC_CLK_24M;    /*Adc_Clk_26M;*/
 +      if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2))
 +              sys.demod_clk = Demod_Clk_250M;
 +      else
 +              sys.demod_clk = Demod_Clk_225M;
 +      demod_status.ch_if = 5000;
 +      demod_status.tmp = Adc_mode;
 +      /*demod_set_sys(&demod_status, &i2c, &sys);*/
 +      demod_set_sys(&demod_status, &sys);
 +      demod_mode_para = AML_ATSC;
 +      atsc_flag = VSB_8;
 +      return 0;
 +}
 +
 +static void gxtv_demod_dtmb_release(struct dvb_frontend *fe)
 +{
 +
 +}
 +
 +static int gxtv_demod_dtmb_read_status
 +      (struct dvb_frontend *fe, enum fe_status *status)
 +{
 +      struct poll_machie_s *pollm = &dtvdd_devp->poll_machie;
 +
 +      *status = pollm->last_s;
 +      return 0;
 +}
 +
 +void dtmb_save_status(unsigned int s)
 +{
 +      struct poll_machie_s *pollm = &dtvdd_devp->poll_machie;
 +
 +      if (s) {
 +              pollm->last_s =
 +                      FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +                      FE_HAS_VITERBI | FE_HAS_SYNC;
 +
 +      } else {
 +              pollm->last_s = FE_TIMEDOUT;
 +      }
 +}
 +
 +void dtmb_poll_start(void)
 +{
 +      struct poll_machie_s *pollm = &dtvdd_devp->poll_machie;
 +
 +      pollm->last_s = 0;
 +      pollm->flg_restart = 1;
 +      /*pr_dbg("dtmb_poll_start!\n");*/
 +      PR_DTMB("dtmb_poll_start2\n");
 +
 +}
 +
 +
 +void dtmb_poll_stop(void)
 +{
 +      struct poll_machie_s *pollm = &dtvdd_devp->poll_machie;
 +
 +      pollm->flg_stop = 1;
 +
 +}
 +void dtmb_set_delay(unsigned int delay)
 +{
 +      struct poll_machie_s *pollm = &dtvdd_devp->poll_machie;
 +
 +      pollm->delayms = delay;
 +      pollm->flg_updelay = 1;
 +}
 +unsigned int dtmb_is_update_delay(void)
 +{
 +      struct poll_machie_s *pollm = &dtvdd_devp->poll_machie;
 +
 +      return pollm->flg_updelay;
 +}
 +unsigned int dtmb_get_delay_clear(void)
 +{
 +      struct poll_machie_s *pollm = &dtvdd_devp->poll_machie;
 +
 +      pollm->flg_updelay = 0;
 +
 +      return pollm->delayms;
 +}
 +
 +void dtmb_poll_clear(void)
 +{
 +      struct poll_machie_s *pollm = &dtvdd_devp->poll_machie;
 +
 +      memset(pollm, 0, sizeof(struct poll_machie_s));
 +
 +}
 +
 +#define DTMBM_NO_SIGNEL_CHECK 0x01
 +#define DTMBM_HV_SIGNEL_CHECK 0x02
 +#define DTMBM_BCH_OVER_CHEK   0x04
 +
 +#define DTMBM_CHEK_NO         (DTMBM_NO_SIGNEL_CHECK)
 +#define DTMBM_CHEK_HV         (DTMBM_HV_SIGNEL_CHECK | DTMBM_BCH_OVER_CHEK)
 +#define DTMBM_WORK            (DTMBM_NO_SIGNEL_CHECK | DTMBM_HV_SIGNEL_CHECK\
 +                                      | DTMBM_BCH_OVER_CHEK)
 +
 +#define DTMBM_POLL_CNT_NO_SIGNAL      (10)
 +#define DTMBM_POLL_CNT_WAIT_LOCK      (3) /*from 30 to 3 */
 +#define DTMBM_POLL_DELAY_NO_SIGNAL    (120)
 +#define DTMBM_POLL_DELAY_HAVE_SIGNAL  (100)
 +/*dtmb_poll_v3 is same as dtmb_check_status_txl*/
 +void dtmb_poll_v3(void)
 +{
 +      struct poll_machie_s *pollm = &dtvdd_devp->poll_machie;
 +      unsigned int bch_tmp;
 +      unsigned int s;
 +
 +      if (!pollm->state) {
 +              /* idle */
 +              /* idle -> start check */
 +              if (!pollm->flg_restart) {
 +                      PR_DBG("x");
 +                      return;
 +              }
 +      } else {
 +              if (pollm->flg_stop) {
 +                      PR_DBG("dtmb poll stop !\n");
 +                      dtmb_poll_clear();
 +                      dtmb_set_delay(3*HZ);
 +                      return;
 +              }
 +      }
 +
 +      /* restart: clear */
 +      if (pollm->flg_restart) {
 +              PR_DBG("dtmb poll restart!\n");
 +              dtmb_poll_clear();
 +
 +      }
 +      PR_DBG("-");
 +      s = check_dtmb_fec_lock();
 +
 +      /* bch exceed the threshold: wait lock*/
 +      if (pollm->state & DTMBM_BCH_OVER_CHEK) {
 +              if (pollm->crrcnt < DTMBM_POLL_CNT_WAIT_LOCK) {
 +                      pollm->crrcnt++;
 +
 +                      if (s) {
 +                              PR_DBG("after reset get lock again!cnt=%d\n",
 +                                      pollm->crrcnt);
 +                              dtmb_constell_check();
 +                              pollm->state = DTMBM_HV_SIGNEL_CHECK;
 +                              pollm->crrcnt = 0;
 +                              pollm->bch = dtmb_reg_r_bch();
 +
 +
 +                              dtmb_save_status(s);
 +                      }
 +              } else {
 +                      PR_DBG("can't lock after reset!\n");
 +                      pollm->state = DTMBM_NO_SIGNEL_CHECK;
 +                      pollm->crrcnt = 0;
 +                      /* to no signal*/
 +                      dtmb_save_status(s);
 +              }
 +              return;
 +      }
 +
 +
 +      if (s) {
 +              /*have signal*/
 +              if (!pollm->state) {
 +                      pollm->state = DTMBM_CHEK_NO;
 +                      PR_DBG("from idle to have signal wait 1\n");
 +                      return;
 +              }
 +              if (pollm->state & DTMBM_CHEK_NO) {
 +                      /*no to have*/
 +                      PR_DBG("poll machie: from no signal to have signal\n");
 +                      pollm->bch = dtmb_reg_r_bch();
 +                      pollm->state = DTMBM_HV_SIGNEL_CHECK;
 +
 +                      dtmb_set_delay(DTMBM_POLL_DELAY_HAVE_SIGNAL);
 +                      return;
 +              }
 +
 +
 +              bch_tmp = dtmb_reg_r_bch();
 +              if (bch_tmp > (pollm->bch + 50)) {
 +                      pollm->state = DTMBM_BCH_OVER_CHEK;
 +
 +                      PR_DBG("bch add ,need reset,wait not to reset\n");
 +                      dtmb_reset();
 +
 +                      pollm->crrcnt = 0;
 +                      dtmb_set_delay(DTMBM_POLL_DELAY_HAVE_SIGNAL);
 +              } else {
 +                      pollm->bch = bch_tmp;
 +                      pollm->state = DTMBM_HV_SIGNEL_CHECK;
 +
 +                      dtmb_save_status(s);
 +                      /*have signale to have signal*/
 +                      dtmb_set_delay(300);
 +              }
 +              return;
 +      }
 +
 +
 +      /*no signal */
 +      if (!pollm->state) {
 +              /* idle -> no signal */
 +              PR_DBG("poll machie: from idle to no signal\n");
 +              pollm->crrcnt = 0;
 +
 +              pollm->state = DTMBM_NO_SIGNEL_CHECK;
 +      } else if (pollm->state & DTMBM_CHEK_HV) {
 +              /*have signal -> no signal*/
 +              PR_DBG("poll machie: from have signal to no signal\n");
 +              pollm->crrcnt = 0;
 +              pollm->state = DTMBM_NO_SIGNEL_CHECK;
 +              dtmb_save_status(s);
 +      }
 +
 +      /*no siganel check process */
 +      if (pollm->crrcnt < DTMBM_POLL_CNT_NO_SIGNAL) {
 +              dtmb_no_signal_check_v3();
 +              pollm->crrcnt++;
 +
 +              dtmb_set_delay(DTMBM_POLL_DELAY_NO_SIGNAL);
 +      } else {
 +              dtmb_no_signal_check_finishi_v3();
 +              pollm->crrcnt = 0;
 +
 +              dtmb_save_status(s);
 +              /*no signal to no signal*/
 +              dtmb_set_delay(300);
 +      }
 +
 +}
 +
 +void dtmb_poll_start_tune(unsigned int state)
 +{
 +      struct poll_machie_s *pollm = &dtvdd_devp->poll_machie;
 +
 +      dtmb_poll_clear();
 +
 +      pollm->state = state;
 +      if (state & DTMBM_NO_SIGNEL_CHECK)
 +              dtmb_save_status(0);
 +      else
 +              dtmb_save_status(1);
 +      PR_DTMB("dtmb_poll_start tune to %d\n", state);
 +
 +}
 +
 +/*come from gxtv_demod_dtmb_read_status, have ms_delay*/
 +int dtmb_poll_v2(struct dvb_frontend *fe, enum fe_status *status)
 +{
 +      int ilock;
 +      unsigned char s = 0;
 +
 +      s = dtmb_check_status_gxtv(fe);
 +
 +      if (s == 1) {
 +              ilock = 1;
 +              *status =
 +                      FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +                      FE_HAS_VITERBI | FE_HAS_SYNC;
 +      } else {
 +              ilock = 0;
 +              *status = FE_TIMEDOUT;
 +      }
 +      if (last_lock != ilock) {
 +              PR_INFO("%s.\n",
 +                       ilock ? "!!  >> LOCK << !!" : "!! >> UNLOCK << !!");
 +              last_lock = ilock;
 +      }
 +
 +      return 0;
 +}
 +
 +
 +/*this is ori gxtv_demod_dtmb_read_status*/
 +static int gxtv_demod_dtmb_read_status_old
 +      (struct dvb_frontend *fe, enum fe_status *status)
 +{
 +
 +      int ilock;
 +      unsigned char s = 0;
 +
 +      if (is_dtmb_ver(IC_DTMB_V2)) {
 +              s = dtmb_check_status_gxtv(fe);
 +      } else if (is_dtmb_ver(IC_DTMB_V3)) {
 +              if (!is_ic_ver(IC_VER_TL1) && !is_ic_ver(IC_VER_TM2))
 +                      s = dtmb_check_status_txl(fe);
 +      } else {
 +
 +              PR_ERR("%s:not support %d!\n", __func__, get_dtmb_ver());
 +              return -1;
 +      }
 +
 +      s = amdemod_dtmb_stat_islock();
 +
 +      if (s == 1) {
 +              ilock = 1;
 +              *status =
 +                      FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +                      FE_HAS_VITERBI | FE_HAS_SYNC;
 +      } else {
 +              ilock = 0;
 +              *status = FE_TIMEDOUT;
 +      }
 +      if (last_lock != ilock) {
 +              PR_INFO("%s.\n",
 +                       ilock ? "!!  >> LOCK << !!" : "!! >> UNLOCK << !!");
 +              last_lock = ilock;
 +      }
 +
 +      return 0;
 +}
 +
 +static int gxtv_demod_dtmb_read_ber(struct dvb_frontend *fe, u32 *ber)
 +{
 +      *ber = 0;
 +
 +      return 0;
 +}
 +
 +static int gxtv_demod_dtmb_read_signal_strength
 +              (struct dvb_frontend *fe, u16 *strength)
 +{
 +      int tuner_sr;
 +
 +      if (is_ic_ver(IC_VER_TL1) &&
 +              (dtvdd_devp->pin_name != NULL) &&
 +              (strncmp(fe->ops.tuner_ops.info.name, "r842", 4) == 0)) {
 +              tuner_sr = tuner_get_ch_power2();
 +              tuner_sr += 16;
 +
 +              if (tuner_sr < -100)
 +                      *strength = 0;
 +              else
 +                      *strength = tuner_sr + 100;
 +      } else
 +              *strength = tuner_get_ch_power3();
 +      return 0;
 +}
 +
 +static int gxtv_demod_dtmb_read_snr(struct dvb_frontend *fe, u16 *snr)
 +{
 +      int tmp, snr_avg;
 +
 +      tmp = snr_avg = 0;
 +      /* tmp = dtmb_read_reg(DTMB_TOP_FEC_LOCK_SNR);*/
 +      tmp = dtmb_reg_r_che_snr();
 +
 +      *snr = convert_snr(tmp);
 +
 +      return 0;
 +}
 +
 +static int gxtv_demod_dtmb_read_ucblocks(struct dvb_frontend *fe, u32 *ucblocks)
 +{
 +      *ucblocks = 0;
 +      return 0;
 +}
 +
 +
 +static int gxtv_demod_dtmb_set_frontend(struct dvb_frontend *fe)
 +{
 +      struct dtv_frontend_properties *c = &fe->dtv_property_cache;
 +      struct aml_demod_dtmb param;
 +      int times;
 +
 +      if (!demod_thread)
 +              return 0;
 +
 +      times = 2;
 +      PR_DBG("gxtv_demod_dtmb_set_frontend,freq is %d\n", c->frequency);
 +      memset(&param, 0, sizeof(param));
 +      param.ch_freq = c->frequency / 1000;
 +
 +      last_lock = -1;
 +/* demod_power_switch(PWR_OFF); */
 +      tuner_set_params(fe);   /*aml_fe_analog_set_frontend(fe);*/
 +      msleep(100);
 +/* demod_power_switch(PWR_ON); */
 +
 +      dtmb_set_ch(&demod_status, /*&demod_i2c,*/ &param);
 +
 +      return 0;
 +}
 +
 +
 +static int gxtv_demod_dtmb_get_frontend(struct dvb_frontend *fe)
 +{                               /*these content will be writed into eeprom .*/
 +
 +      return 0;
 +}
 +
 +/*int Gxtv_Demod_Dtmb_Init(struct aml_fe_dev *dev)*/
 +int Gxtv_Demod_Dtmb_Init(struct amldtvdemod_device_s *dev)
 +{
 +      struct aml_demod_sys sys;
 +      /*struct aml_demod_i2c i2c;*/
 +      PR_DBG("AML Demod DTMB init\r\n");
 +
 +      memset(&sys, 0, sizeof(sys));
 +      /*memset(&i2c, 0, sizeof(i2c));*/
 +      memset(&demod_status, 0, sizeof(demod_status));
 +      /* 0 -DVBC, 1-DVBT, ISDBT, 2-ATSC*/
 +      demod_status.dvb_mode = Gxtv_Dtmb;
 +
 +      if (is_dtmb_ver(IC_DTMB_V2)) {
 +              sys.adc_clk = Adc_Clk_25M;      /*Adc_Clk_26M;*/
 +              sys.demod_clk = Demod_Clk_200M;
 +      } else if (is_dtmb_ver(IC_DTMB_V3)) {
 +              if (is_ic_ver(IC_VER_TXL)) {
 +                      sys.adc_clk = Adc_Clk_25M;
 +                      sys.demod_clk = Demod_Clk_225M;
 +              } else if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2)) {
 +                      sys.adc_clk = ADC_CLK_24M;
 +                      sys.demod_clk = Demod_Clk_250M;
 +              } else {
 +                      sys.adc_clk = ADC_CLK_24M;
 +                      sys.demod_clk = Demod_Clk_225M;
 +              }
 +      } else {
 +              PR_ERR("%s:not support %d\n", __func__, get_dtmb_ver());
 +              return -1;
 +      }
 +
 +      demod_status.ch_if = SI2176_5M_IF;
 +      demod_status.tmp = Adc_mode;
 +      demod_status.spectrum = dev->spectrum;
 +      /*demod_set_sys(&demod_status, &i2c, &sys);*/
 +      demod_set_sys(&demod_status, &sys);
 +      demod_mode_para = AML_DTMB;
 +
 +      return 0;
 +}
 +
 +#ifdef DVB_CORE_ORI
 +unsigned int demod_dvbc_get_fast_search(void)
 +{
 +      return demod_dvbc_speedup_en;
 +}
 +
 +void demod_dvbc_set_fast_search(unsigned int en)
 +{
 +      if (en)
 +              demod_dvbc_speedup_en = 1;
 +      else
 +              demod_dvbc_speedup_en = 0;
 +}
 +
 +void demod_dvbc_fsm_reset(void)
 +{
 +      //qam_write_reg(0x7, 0xf23);
 +      qam_write_reg(0x7, qam_read_reg(0x7) & ~(1 << 4));
 +      qam_write_reg(0x3a, 0x0);
 +      //qam_write_reg(0x7, 0xf33);
 +      qam_write_reg(0x7, qam_read_reg(0x7) | (1 << 4));
 +      qam_write_reg(0x3a, 0x4);
 +}
 +
 +//return val : 0=no signal,1=has signal,2=waiting
 +unsigned int demod_dvbc_64_256_auto_fast(unsigned int *delay)
 +{
 +      static unsigned int times, no_sig_cnt;
 +      static unsigned int qam64 = 1;
 +
 +      if (tuner_get_ch_power2() < -87)
 +              return 0;
 +
 +      times++;
 +      PR_DVBC("fast search : times = %d\n", times);
 +      if (times < 6)
 +              *delay = HZ / 8;//125ms
 +      else
 +              *delay = HZ / 2;//500ms
 +
 +      if ((qam_read_reg(0x31) & 0xf) < 3) {
 +              no_sig_cnt++;
 +
 +              if (no_sig_cnt == 2 && times == 2) {//250ms
 +                      no_sig_cnt = 0;
 +                      times = 0;
 +                      *delay = HZ / 4;
 +                      qam64 = 1;
 +                      return 0;
 +              }
 +      } else if ((qam_read_reg(0x31) & 0xf) == 5) {
 +              no_sig_cnt = 0;
 +              times = 0;
 +              *delay = HZ / 4;
 +              qam64 = 1;
 +              return 1;
 +      }
 +
 +      if (times == 14) {
 +              times = 0;
 +              no_sig_cnt = 0;
 +              *delay = HZ / 4;
 +              qam64 = 1;
 +              return 0;
 +      }
 +
 +      qam64 = !qam64;
 +
 +      PR_DVBC("fast search : qam64 = %d\n", qam64);
 +      if (qam64)
 +              demod_dvbc_set_qam(2);//64qam
 +      else
 +              demod_dvbc_set_qam(4);//256qam
 +
 +      demod_dvbc_fsm_reset();
 +
 +      return 2;
 +}
 +
 +//return val : 0=no signal,1=has signal,2=waiting
 +unsigned int demod_dvbc_fast_search(unsigned int *delay)
 +{
 +      static unsigned int times, no_sig_cnt;
 +
 +      if (tuner_get_ch_power2() < -87)
 +              return 0;
 +
 +      times++;
 +      PR_DVBC("fast search : times = %d\n", times);
 +      if (times < 3)
 +              *delay = HZ / 8;//125ms
 +      else
 +              *delay = HZ / 2;//500ms
 +
 +      if ((qam_read_reg(0x31) & 0xf) < 3) {
 +              no_sig_cnt++;
 +
 +              if (no_sig_cnt == 2 && times == 2) {//250ms
 +                      no_sig_cnt = 0;
 +                      times = 0;
 +                      *delay = HZ / 4;
 +                      return 0;
 +              }
 +      } else if ((qam_read_reg(0x31) & 0xf) == 5) {
 +              no_sig_cnt = 0;
 +              times = 0;
 +              *delay = HZ / 4;
 +              return 1;
 +      }
 +
 +      if (times == 7) {
 +              times = 0;
 +              no_sig_cnt = 0;
 +              *delay = HZ / 4;
 +              return 0;
 +      }
 +
 +      demod_dvbc_fsm_reset();
 +
 +      return 2;
 +}
 +
 +static int gxtv_demod_dvbc_tune(struct dvb_frontend *fe, bool re_tune,
 +      unsigned int mode_flags, unsigned int *delay, enum fe_status *status)
 +{
 +      /*struct dtv_frontend_properties *c = &fe->dtv_property_cache;*/
 +      int ret = 0;
 +      unsigned int sig_flg;
 +      static unsigned int fast_search_finish = 1;
 +      /*unsigned int up_delay;*/
 +      /*unsigned int firstdetet;*/
 +
 +      *delay = HZ / 4;
 +
 +      if (!demod_thread)
 +              return 0;
 +
 +      if (re_tune) {
 +              /*first*/
 +              dtvdd_devp->en_detect = 1;
 +
 +              gxtv_demod_dvbc_set_frontend(fe);
 +
 +              if (demod_dvbc_speedup_en == 1) {
 +                      fast_search_finish = 0;
 +                      *status = 0;
 +                      *delay = HZ / 8;
 +                      qam_write_reg(0x65, 0x400c);
 +                      qam_write_reg(0x60, 0x10466000);
 +                      qam_write_reg(0xac, (qam_read_reg(0xac) & (~0xff00))
 +                              | 0x800);
 +                      qam_write_reg(0xae, (qam_read_reg(0xae)
 +                              & (~0xff000000)) | 0x8000000);
 +
 +                      if (fe->dtv_property_cache.modulation == QAM_AUTO)
 +                              demod_dvbc_set_qam(2);//64 QAM
 +              } else
 +                      qam_write_reg(0x65, 0x800c);
 +
 +              if (demod_dvbc_speedup_en == 1)
 +                      return 0;
 +
 +              /*timer_set_max(D_TIMER_DETECT, 4000);*/
 +              timer_begain(D_TIMER_DETECT);
 +              gxtv_demod_dvbc_read_status_timer(fe, status);
 +
 +              if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2))
 +                      demod_dvbc_speed_up(status);
 +
 +              PR_DBG("tune finish!\n");
 +
 +              return ret;
 +      }
 +
 +      if (!dtvdd_devp->en_detect) {
 +              PR_DBGL("tune:not enable\n");
 +              return ret;
 +      }
 +
 +      if (demod_dvbc_speedup_en == 1) {
 +              if (!fast_search_finish) {
 +                      if (fe->dtv_property_cache.modulation == QAM_AUTO)
 +                              sig_flg = demod_dvbc_64_256_auto_fast(delay);
 +                      else
 +                              sig_flg = demod_dvbc_fast_search(delay);
 +
 +                      switch (sig_flg) {
 +                      case 0:
 +                              *status = FE_TIMEDOUT;
 +                              fast_search_finish = 1;
 +                              PR_DVBC(">>>unlock<<<\n");
 +                              break;
 +                      case 1:
 +                              *status =
 +                              FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +                              FE_HAS_VITERBI | FE_HAS_SYNC;
 +                              fast_search_finish = 1;
 +                              PR_DVBC(">>>lock<<<\n");
 +                              break;
 +                      case 2:
 +                              *status = 0;
 +                              break;
 +                      default:
 +                              PR_DVBC("wrong return value\n");
 +                              break;
 +                      }
 +              }       else {
 +                      gxtv_demod_dvbc_read_status_timer(fe, status);
 +              }
 +      }       else {
 +              gxtv_demod_dvbc_read_status_timer(fe, status);
 +      }
 +
 +      if (demod_dvbc_speedup_en == 1)
 +              return 0;
 +
 +      #if 0
 +      if (is_ic_ver(IC_VER_TL1))
 +              return ret;
 +      #endif
 +
 +      if (*status & FE_HAS_LOCK) {
 +              timer_disable(D_TIMER_SET);
 +      } else {
 +              if (!timer_is_en(D_TIMER_SET))
 +                      timer_begain(D_TIMER_SET);
 +      }
 +
 +      if (timer_is_enough(D_TIMER_SET)) {
 +              gxtv_demod_dvbc_set_frontend(fe);
 +              timer_disable(D_TIMER_SET);
 +      }
 +
 +      return ret;
 +
 +}
 +
 +static int gxtv_demod_dtmb_tune(struct dvb_frontend *fe, bool re_tune,
 +      unsigned int mode_flags, unsigned int *delay, enum fe_status *status)
 +{
 +      /*struct dtv_frontend_properties *c = &fe->dtv_property_cache;*/
 +      int ret = 0;
 +//    unsigned int up_delay;
 +      unsigned int firstdetet;
 +
 +
 +
 +      if (re_tune) {
 +              /*first*/
 +              dtvdd_devp->en_detect = 1;
 +
 +              *delay = HZ / 4;
 +              gxtv_demod_dtmb_set_frontend(fe);
 +              firstdetet = dtmb_detect_first();
 +
 +              if (firstdetet == 1) {
 +                      *status = FE_TIMEDOUT;
 +                      /*polling mode*/
 +                      dtmb_poll_start_tune(DTMBM_NO_SIGNEL_CHECK);
 +
 +              } else if (firstdetet == 2) {  /*need check*/
 +                      *status = FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +                      FE_HAS_VITERBI | FE_HAS_SYNC;
 +                      dtmb_poll_start_tune(DTMBM_HV_SIGNEL_CHECK);
 +
 +              } else if (firstdetet == 0) {
 +                      PR_DBG("use read_status\n");
 +                      gxtv_demod_dtmb_read_status_old(fe, status);
 +                      if (*status == (0x1f))
 +                              dtmb_poll_start_tune(DTMBM_HV_SIGNEL_CHECK);
 +                      else
 +                              dtmb_poll_start_tune(DTMBM_NO_SIGNEL_CHECK);
 +
 +
 +              }
 +              PR_DBG("tune finish!\n");
 +
 +              return ret;
 +      }
 +
 +      if (!dtvdd_devp->en_detect) {
 +              PR_DBG("tune:not enable\n");
 +              return ret;
 +      }
 +
 +#if 1 /**/
 +      *delay = HZ / 4;
 +      gxtv_demod_dtmb_read_status_old(fe, status);
 +
 +      if (*status == (FE_HAS_LOCK | FE_HAS_SIGNAL | FE_HAS_CARRIER |
 +              FE_HAS_VITERBI | FE_HAS_SYNC))
 +              dtmb_poll_start_tune(DTMBM_HV_SIGNEL_CHECK);
 +      else
 +              dtmb_poll_start_tune(DTMBM_NO_SIGNEL_CHECK);
 +
 +#else /*try polling*/
 +
 +      /*pr_dbg("+");*/
 +      if (is_dtmb_ver(IC_DTMB_V3)) {
 +              dtmb_poll_v3();
 +              gxtv_demod_dtmb_read_status(fe, status);
 +              if (dtmb_is_update_delay()) {
 +                      up_delay = (dtmb_get_delay_clear()*HZ)/1000;
 +                      if (up_delay > 0)
 +                              *delay = up_delay;
 +                      else
 +                              PR_DBG("warning:delay is 0\n");
 +              }
 +      } else if (is_dtmb_ver(IC_DTMB_V2)) {
 +              *delay = HZ / 3;
 +              dtmb_poll_v2(fe, status);
 +      }
 +
 +#endif
 +      return ret;
 +
 +}
 +
 +#endif
 +
 +
 +
 +#ifdef CONFIG_CMA
 +/*void dtmb_cma_alloc(struct aml_fe_dev *devp)*/
 +bool dtmb_cma_alloc(struct amldtvdemod_device_s *devp)
 +{
 +      bool ret;
 +
 +      unsigned int mem_size = devp->cma_mem_size;
 +      /*      dma_alloc_from_contiguous*/
 +      devp->venc_pages =
 +              dma_alloc_from_contiguous(&(devp->this_pdev->dev),
 +                      mem_size >> PAGE_SHIFT, 0);
 +      PR_DBG("[cma]mem_size is %d,%d\n",
 +              mem_size, mem_size >> PAGE_SHIFT);
 +      if (devp->venc_pages) {
 +              devp->mem_start = page_to_phys(devp->venc_pages);
 +              devp->mem_size  = mem_size;
 +              devp->flg_cma_allc = true;
 +              PR_DBG("demod mem_start = 0x%x, mem_size = 0x%x\n",
 +                      devp->mem_start, devp->mem_size);
 +              PR_DBG("demod cma alloc ok!\n");
 +              ret = true;
 +      } else {
 +              PR_DBG("demod cma mem undefined2.\n");
 +              ret = false;
 +      }
 +      return ret;
 +}
 +
 +/*void dtmb_cma_release(struct aml_fe_dev *devp)*/
 +void dtmb_cma_release(struct amldtvdemod_device_s *devp)
 +{
 +      /*      dma_release_from_contiguous*/
 +      dma_release_from_contiguous(&(devp->this_pdev->dev),
 +                      devp->venc_pages,
 +                      devp->cma_mem_size>>PAGE_SHIFT);
 +              PR_DBG("demod cma release ok!\n");
 +      devp->mem_start = 0;
 +      devp->mem_size = 0;
 +}
 +#endif
 +
 +static bool enter_mode(enum aml_fe_n_mode_t mode)
 +{
 +      /*struct aml_fe_dev *dev = fe->dtv_demod;*/
 +      struct amldtvdemod_device_s *devn = dtvdd_devp;
 +      int memstart_dtmb;
 +      bool ret = true;
 +
 +      if (mode < AM_FE_NUM)
 +              PR_INFO("%s:%s\n", __func__, name_fe_n_mode[mode]);
 +      else
 +              PR_ERR("%s:%d\n", __func__, mode);
 +
 +      dtvdemod_set_agc_pinmux(1);
 +
 +      /*-------------------*/
 +      /* must enable the adc ref signal for demod, */
 +      /*vdac_enable(1, VDAC_MODULE_DTV_DEMOD);*/
 +      dtvdemod_vdac_enable(1);/*on*/
 +      dtvdd_devp->en_detect = 0;/**/
 +      dtvdd_devp->n_mode = mode;
 +      dtmb_poll_stop();/*polling mode*/
 +
 +      autoFlagsTrig = 1;
 +      if (cci_thread)
 +              if (dvbc_get_cci_task() == 1)
 +                      dvbc_create_cci_task();
 +      /*mem_buf = (long *)phys_to_virt(memstart);*/
 +      if (mode == AM_FE_DTMB_N) {
 +              Gxtv_Demod_Dtmb_Init(devn);
 +
 +              if (devn->cma_flag == 1) {
 +                      PR_DBG("CMA MODE, cma flag is %d,mem size is %d",
 +                              devn->cma_flag, devn->cma_mem_size);
 +
 +                      if (dtmb_cma_alloc(devn)) {
 +                              memstart_dtmb = devn->mem_start;
 +                      } else {
 +                              ret = false;
 +                              return ret;
 +                      }
 +              } else {
 +                      memstart_dtmb = devn->mem_start;/*??*/
 +              }
 +
 +              devn->act_dtmb = true;
 +              dtmb_set_mem_st(memstart_dtmb);
 +
 +              //?, already set in Gxtv_Demod_Dtmb_Init()
 +              if (!is_ic_ver(IC_VER_TL1) && !is_ic_ver(IC_VER_TM2))
 +                      demod_write_reg(DEMOD_TOP_REGC, 0x8);
 +      } else if (mode == AM_FE_QAM_N) {
 +              Gxtv_Demod_Dvbc_Init(/*dev,*/ Adc_mode);
 +
 +              /*The maximum time of signal detection is 3s*/
 +              timer_set_max(D_TIMER_DETECT, 3000);
 +              /*reset is 4s*/
 +              timer_set_max(D_TIMER_SET, 4000);
 +      } else if (mode == AM_FE_ATSC_N) {
 +              Gxtv_Demod_Atsc_Init();
 +
 +              if (is_ic_ver(IC_VER_TL1) || is_ic_ver(IC_VER_TM2))
 +                      timer_set_max(D_TIMER_DETECT, 4000);
 +      } else if (mode == AM_FE_OFDM_N || mode == AM_FE_ISDBT_N) {
 +              Gxtv_Demod_Dvbt_Init();
 +              /*The maximum time of signal detection is 2s */
 +              timer_set_max(D_TIMER_DETECT, 2000);
 +              /*reset is 4s*/
 +              timer_set_max(D_TIMER_SET, 4000);
 +
 +              if (devn->cma_flag == 1) {
 +                      PR_DBG("CMA MODE, cma flag is %d,mem size is %d",
 +                              devn->cma_flag,
 +                              devn->cma_mem_size);
 +                      if (dtmb_cma_alloc(devn)) {
 +                              memstart_dtmb = devn->mem_start;
 +                      } else {
 +                              ret = false;
 +                              return ret;
 +                      }
 +              } else {
 +                      memstart_dtmb = devn->mem_start;/*??*/
 +              }
 +
 +              PR_DBG("[im]memstart is %x\n", memstart_dtmb);
 +              dvbt_write_reg((0x10 << 2), memstart_dtmb);
 +      }
 +
 +      return ret;
 +
 +}
 +
 +static int leave_mode(enum aml_fe_n_mode_t mode)
 +{
 +/*    struct aml_fe_dev *dev = fe->dtv_demod;*/
 +      struct amldtvdemod_device_s *devn = dtvdd_devp;
 +
 +      if (mode < AM_FE_NUM)
 +              PR_INFO("%s:%s\n", __func__, name_fe_n_mode[mode]);
 +      else
 +              PR_ERR("%s:%d\n", __func__, mode);
 +
 +      dtvdd_devp->en_detect = 0;
 +      dtvdd_devp->last_delsys = SYS_UNDEFINED;
 +      dtvdd_devp->n_mode = AM_FE_UNKNOWN_N;
 +
 +      dtvpll_init_flag(0);
 +      /*dvbc_timer_exit();*/
 +      if (cci_thread)
 +              dvbc_kill_cci_task();
 +
 +      if (mode == AM_FE_DTMB_N) {
 +              if (dtvdd_devp->act_dtmb) {
 +                      dtmb_poll_stop();       /*polling mode*/
 +                      /* close arbit */
 +                      demod_write_reg(DEMOD_TOP_REGC, 0x0);
 +                      dtvdd_devp->act_dtmb = false;
 +              }
 +
 +              if ((devn->cma_flag == 1) && dtvdd_devp->flg_cma_allc) {
 +                      dtmb_cma_release(devn);
 +                      dtvdd_devp->flg_cma_allc = false;
 +              }
 +      } else if (mode == AM_FE_OFDM_N || mode == AM_FE_ISDBT_N) {
 +              if ((devn->cma_flag == 1) && dtvdd_devp->flg_cma_allc) {
 +                      dtmb_cma_release(devn);
 +                      dtvdd_devp->flg_cma_allc = false;
 +              }
 +      }
 +
 +      adc_set_pll_cntl(0, 0x4, NULL);
 +      adc_set_pll_cntl(0, 0x8, NULL);
 +      demod_mode_para = UNKNOWN;
 +      /* should disable the adc ref signal for demod */
 +      /*vdac_enable(0, VDAC_MODULE_DTV_DEMOD);*/
 +      dtvdemod_vdac_enable(0);/*off*/
 +      dtvdemod_set_agc_pinmux(0);
 +      msleep(200);
 +
 +      return 0;
 +}
 +/* when can't get ic_config by dts, use this*/
 +const struct meson_ddemod_data  data_gxtvbb = {
 +      .name = "ddmode_gxtvbb",
 +      .icver = {
 +              .atsc = IC_MD_NONE,
 +              .dvbt = IC_MD_NONE,
 +              .dtmb = IC_DTMB_V2,
 +              .dvbc = IC_DVBC_V2,
 +              .reserved = 0,
 +              .offset = IC_OFFS_V2,
 +              .ic = IC_VER_GTVBB,
 +      },
 +
 +};
 +
 +const struct meson_ddemod_data  data_txl = {
 +      .name = "ddmode_txl",
 +      .icver = {
 +              .atsc = IC_MD_NONE,
 +              .dvbt = IC_MD_NONE,
 +              .dtmb = IC_DTMB_V3,
 +              .dvbc = IC_DVBC_V2,
 +              .reserved = 0,
 +              .offset = IC_OFFS_V2,
 +              .ic = IC_VER_TXL,
 +      },
 +
 +};
 +
 +const struct meson_ddemod_data  data_txlx = {
 +      .name = "ddmode_txlx",
 +      .icver = {
 +              .atsc = IC_ATSC_V2,
 +              .dvbt = IC_DVBT_V2,
 +              .dtmb = IC_MD_NONE,
 +              .dvbc = IC_DVBC_V3,
 +              .reserved = 0,
 +              .offset = IC_OFFS_V3,
 +              .ic = IC_VER_TXLX,
 +      },
 +
 +};
 +
 +const struct meson_ddemod_data  data_gxlx = {
 +      .name = "ddmode_gxlx",
 +      .icver = {
 +              .atsc = IC_MD_NONE,
 +              .dvbt = IC_MD_NONE,
 +              .dtmb = IC_MD_NONE,
 +              .dvbc = IC_DVBC_V3,
 +              .reserved = 0,
 +              .offset = IC_OFFS_V3,
 +              .ic = IC_VER_GXLX,
 +      },
 +
 +};
 +
 +const struct meson_ddemod_data  data_txhd = {
 +      .name = "ddmode_txhd",
 +      .icver = {
 +              .atsc = IC_MD_NONE,
 +              .dvbt = IC_MD_NONE,
 +              .dtmb = IC_DTMB_V3,
 +              .dvbc = IC_MD_NONE,
 +              .reserved = 0,
 +              .offset = IC_OFFS_V3,
 +              .ic = IC_VER_TXHD,
 +      },
 +
 +};
 +
 +const struct meson_ddemod_data  data_tl1 = {
 +      .name = "ddmode_tl1",
 +      .icver = {
 +              .atsc = IC_ATSC_V2,
 +              .dvbt = IC_MD_NONE,
 +              .dtmb = IC_DTMB_V3,
 +              .dvbc = IC_DVBC_V3,
 +              .reserved = 0,
 +              .offset = IC_OFFS_V4,
 +              .ic = IC_VER_TL1,
 +      }
 +};
 +
 +const struct meson_ddemod_data  data_tm2 = {
 +      .name = "ddmode_tm2",
 +      .icver = {
 +              .atsc = IC_ATSC_V2,
 +              .dvbt = IC_MD_NONE,
 +              .dtmb = IC_DTMB_V3,
 +              .dvbc = IC_DVBC_V3,
 +              .reserved = 0,
 +              .offset = IC_OFFS_V4,
 +              .ic = IC_VER_TM2,
 +      }
 +};
 +
 +static const struct of_device_id meson_ddemod_match[] = {
 +      {
 +              .compatible = "amlogic, ddemod-gxtvbb",
 +              .data           = &data_gxtvbb,
 +      }, {
 +              .compatible = "amlogic, ddemod-txl",
 +              .data           = &data_txl,
 +      }, {
 +              .compatible = "amlogic, ddemod-txlx",
 +              .data           = &data_txlx,
 +      }, {
 +              .compatible = "amlogic, ddemod-gxlx",
 +              .data           = &data_gxlx,
 +      }, {
 +              .compatible = "amlogic, ddemod-txhd",
 +              .data           = &data_txhd,
 +      }, {
 +              .compatible = "amlogic, ddemod-tl1",
 +              .data           = &data_tl1,
 +      }, {
 +              .compatible = "amlogic, ddemod-tm2",
 +              .data           = &data_tm2,
 +      },
 +      {},
 +};
 +
 +
 +
 +/*
 + * dds_init_reg_map - physical addr map
 + *
 + * map physical address of I/O memory resources
 + * into the core virtual address space
 + */
 +static int dds_init_reg_map(struct platform_device *pdev)
 +{
 +
 +      struct ss_reg_phy *preg = &dtvdd_devp->reg_p[0];
 +      struct ss_reg_vt *pv = &dtvdd_devp->reg_v[0];
 +      int i;
 +      struct resource *res = 0;
 +      int size = 0;
 +      int ret = 0;
 +
 +      for (i = 0; i < ES_MAP_ADDR_NUM; i++) {
 +              res = platform_get_resource(pdev, IORESOURCE_MEM, i);
 +              if (!res) {
 +                      PR_ERR("%s: res %d is faile\n", __func__, i);
 +                      ret = -ENOMEM;
 +                      break;
 +              }
 +              size = resource_size(res);
 +              preg[i].size = size;
 +              preg[i].phy_addr = res->start;
 +
 +              pv[i].v = devm_ioremap_nocache(&pdev->dev,
 +                                              res->start, size);
 +      }
 +      return ret;
 +}
 +
 +int dtvdemod_set_iccfg_by_dts(struct platform_device *pdev)
 +{
 +
 +      /*struct ic_cfg_s *ic_cfg = &dtvdd_devp->iccfg;*/
 +
 +      /*int size_io_reg;*/
 +      u32 value;
 +      int ret;
 +      /*struct resource *res = &dtvdemod_mem;*/
 +
 +
 +      PR_DBG("%s:\n", __func__);
 +
 +      ret = of_reserved_mem_device_init(&pdev->dev);
 +      if (ret != 0)
 +              PR_INFO("no reserved mem.\n");
 +
 +
 +      /*agc pinmux: option*/
 +      ret = of_property_read_string(pdev->dev.of_node, "pinctrl-names",
 +                      &dtvdd_devp->pin_name);
 +
 +      if (ret)
 +              PR_INFO("pinmux:not define in dts\n");
 +      else
 +              PR_INFO("pinmux name:%s\n", dtvdd_devp->pin_name);
 +
 +/*move from aml_fe*/
 +      /*snprintf(buf, sizeof(buf), "%s%d_spectrum", name, id);*/
 +#ifdef CONFIG_OF
 +      ret = of_property_read_u32(pdev->dev.of_node, "spectrum", &value);
 +      if (!ret) {
 +              dtvdd_devp->spectrum = value;
 +              PR_INFO("spectrum: %d\n", value);
 +      } else {
 +              dtvdd_devp->spectrum = 2;
 +      }
 +#else                         /*CONFIG_OF */
 +      res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "spectrum");
 +      if (res) {
 +              int spectrum = res->start;
 +
 +              dtvdd_devp->spectrum = spectrum;
 +      } else {
 +              dtvdd_devp->spectrum = 0;
 +      }
 +#endif
 +      /*snprintf(buf, sizeof(buf), "%s%d_cma_flag", name, id);*/
 +#ifdef CONFIG_OF
 +      ret = of_property_read_u32(pdev->dev.of_node, "cma_flag", &value);
 +      if (!ret) {
 +              dtvdd_devp->cma_flag = value;
 +              PR_INFO("cma_flag: %d\n", value);
 +      } else {
 +              dtvdd_devp->cma_flag = 0;
 +      }
 +#else                         /*CONFIG_OF */
 +      res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "cma_flag");
 +      if (res) {
 +              int cma_flag = res->start;
 +
 +              dtvdd_devp->cma_flag = cma_flag;
 +      } else {
 +              dtvdd_devp->cma_flag = 0;
 +      }
 +#endif
 +      /*snprintf(buf, sizeof(buf), "%s%d_atsc_version", name, id);*/
 +#ifdef CONFIG_OF
 +      ret = of_property_read_u32(pdev->dev.of_node, "atsc_version", &value);
 +      if (!ret) {
 +              dtvdd_devp->atsc_version = value;
 +              PR_INFO("atsc_version: %d\n", value);
 +      } else {
 +              dtvdd_devp->atsc_version = 0;
 +      }
 +#else /*CONFIG_OF */
 +      res = platform_get_resource_byname(pdev, IORESOURCE_MEM,
 +                                      "atsc_version");
 +      if (res) {
 +              int atsc_version = res->start;
 +
 +              dtvdd_devp->atsc_version = atsc_version;
 +      } else {
 +              dtvdd_devp->atsc_version = 0;
 +      }
 +#endif
 +
 +      if (dtvdd_devp->cma_flag == 1) {
 +              /*snprintf(buf, sizeof(buf), "%s%d_cma_mem_size", name, id);*/
 +#ifdef CONFIG_CMA
 +#ifdef CONFIG_OF
 +              ret = of_property_read_u32(pdev->dev.of_node,
 +                                      "cma_mem_size", &value);
 +              if (!ret) {
 +                      dtvdd_devp->cma_mem_size = value;
 +                      PR_INFO("cma_mem_size: %d\n", value);
 +              } else {
 +                      dtvdd_devp->cma_mem_size = 0;
 +              }
 +#else                         /*CONFIG_OF */
 +              res = platform_get_resource_byname(pdev, IORESOURCE_MEM,
 +                                                      "cma_mem_size");
 +              if (res) {
 +                      int cma_mem_size = res->start;
 +
 +                      dtvdd_devp->cma_mem_size = cma_mem_size;
 +              } else {
 +                      dtvdd_devp->cma_mem_size = 0;
 +              }
 +#endif
 +              dtvdd_devp->cma_mem_size =
 +                              dma_get_cma_size_int_byte(&pdev->dev);
 +                      dtvdd_devp->this_pdev = pdev;
 +                      dtvdd_devp->cma_mem_alloc = 0;
 +                      PR_INFO("[cma]demod cma_mem_size = %d MB\n",
 +                                      (u32)dtvdd_devp->cma_mem_size/SZ_1M);
 +#endif
 +              } else {
 +#ifdef CONFIG_OF
 +              dtvdd_devp->mem_start = memstart;
 +#endif
 +      }
 +
 +/*end-------------*/
 +      return 0;
 +
 +}
 +#if (defined CONFIG_AMLOGIC_DTV_DEMOD)        /*move to aml_dtv_demod*/
 +static int rmem_demod_device_init(struct reserved_mem *rmem, struct device *dev)
 +{
 +      unsigned int demod_mem_start;
 +      unsigned int demod_mem_size;
 +
 +      demod_mem_start = rmem->base;
 +      demod_mem_size = rmem->size;
 +      memstart = demod_mem_start;
 +      pr_info("demod reveser memory 0x%x, size %dMB.\n",
 +              demod_mem_start, (demod_mem_size >> 20));
 +      return 1;
 +}
 +
 +static void rmem_demod_device_release(struct reserved_mem *rmem,
 +                                    struct device *dev)
 +{
 +}
 +
 +static const struct reserved_mem_ops rmem_demod_ops = {
 +      .device_init = rmem_demod_device_init,
 +      .device_release = rmem_demod_device_release,
 +};
 +
 +static int __init rmem_demod_setup(struct reserved_mem *rmem)
 +{
 +      /*
 +       * struct cma *cma;
 +       * int err;
 +       * pr_info("%s setup.\n",__func__);
 +       * err = cma_init_reserved_mem(rmem->base, rmem->size, 0, &cma);
 +       * if (err) {
 +       *      pr_err("Reserved memory: unable to setup CMA region\n");
 +       *      return err;
 +       * }
 +       */
 +      rmem->ops = &rmem_demod_ops;
 +      /* rmem->priv = cma; */
 +
 +      pr_info
 +          ("DTV demod reserved memory: %pa, size %ld MiB\n",
 +           &rmem->base, (unsigned long)rmem->size / SZ_1M);
 +
 +      return 0;
 +}
 +
 +RESERVEDMEM_OF_DECLARE(demod, "amlogic, demod-mem", rmem_demod_setup);
 +#endif
 +
 +int dtvdemod_init_regaddr_byversion(struct platform_device *pdev)
 +{
 +      struct ic_ver *pic = &dtvdd_devp->icver;        /*in*/
 +      struct ddemod_reg_off *ireg = &dtvdd_devp->ireg;        /*set*/
 +
 +      unsigned int off_ver = pic->offset;
 +      int ret = 0;
 +
 +      /*clear*/
 +      ireg->off_demod_top = 0x00;
 +      ireg->off_dvbc = 0x00;
 +      ireg->off_dtmb = 0x00;
 +      ireg->off_dvbt = 0x00;
 +      ireg->off_atsc = 0x00;
 +      ireg->off_front = 0x00;
 +      ireg->off_isdbt = 0x00;
 +
 +      if (is_offset_ver(IC_OFFS_V2)) {
 +              ireg->off_demod_top = 0xc00;
 +              ireg->off_dvbc = 0x400;
 +              ireg->off_dtmb = 0x00;
 +      } else if (is_offset_ver(IC_OFFS_V3)) {
 +              ireg->off_demod_top = 0xf00;
 +              ireg->off_dvbc = 0xc00;
 +              ireg->off_dtmb = 0x000;
 +              ireg->off_dvbt = 0x400;
 +              ireg->off_isdbt = ireg->off_dvbt;
 +              ireg->off_atsc = 0x800;
 +      } else if (is_offset_ver(IC_OFFS_V4)) {
 +              ireg->off_demod_top = 0x3c00;
 +              ireg->off_dvbc = 0x1000;
 +              ireg->off_dtmb = 0x0000;
 +              ireg->off_dvbt = 0x0400;
 +              ireg->off_isdbt = 0x0800;
 +              ireg->off_atsc = 0x0c00;
 +              ireg->off_front = 0x3800;
 +      } else {
 +              PR_ERR("ic_offset_version[%d] is not support!\n", off_ver);
 +              ireg->off_demod_top = 0xf00;
 +              ireg->off_dvbc = 0xc00;
 +              ireg->off_dtmb = 0x000;
 +              ireg->off_dvbt = 0x400;
 +              ireg->off_atsc = 0x800;
 +
 +              ret = -1;
 +      }
 +
 +
 +      return ret;
 +}
 +
 +
 +
 +
 +
 +/* It's a correspondence with enum es_map_addr*/
 +
 +void dbg_ic_cfg(void)
 +{
 +      struct ic_ver *pic = &dtvdd_devp->icver;
 +      struct ss_reg_phy *preg = &dtvdd_devp->reg_p[0];
 +      int i;
 +
 +      PR_INFO("ic_version=0x%x\n", pic->ic);
 +      PR_INFO("\tver_dvbc:\t%d\n", pic->dvbc);
 +      PR_INFO("\tver_dtmb:\t%d\n", pic->dtmb);
 +      PR_INFO("\tver_dvbt:\t%d\n", pic->dvbt);
 +      PR_INFO("\tver_atsc:\t%d\n", pic->atsc);
 +      PR_INFO("\tver_offset:\t%d\n", pic->offset);
 +
 +
 +      for (i = 0; i < ES_MAP_ADDR_NUM; i++)
 +              PR_INFO("reg:%s:st=0x%x,size=0x%x\n",
 +                      name_reg[i], preg[i].phy_addr, preg[i].size);
 +
 +
 +}
 +
 +void dbg_reg_addr(void)
 +{
 +      struct ddemod_reg_off *ireg = &dtvdd_devp->ireg;
 +      struct ss_reg_vt *regv = &dtvdd_devp->reg_v[0];
 +      int i;
 +
 +      PR_INFO("%s\n", __func__);
 +
 +      PR_INFO("reg address offset:\n");
 +      PR_INFO("\tdemod top:\t0x%x\n", ireg->off_demod_top);
 +      PR_INFO("\tdvbc:\t0x%x\n", ireg->off_dvbc);
 +      PR_INFO("\tdtmb:\t0x%x\n", ireg->off_dtmb);
 +      PR_INFO("\tdvbt:\t0x%x\n", ireg->off_dvbt);
 +      PR_INFO("\tisdbt:\t0x%x\n", ireg->off_isdbt);
 +      PR_INFO("\tatsc:\t0x%x\n", ireg->off_atsc);
 +      PR_INFO("\tfront:\t0x%x\n", ireg->off_front);
 +
 +      PR_INFO("virtual addr:\n");
 +      for (i = 0; i < ES_MAP_ADDR_NUM; i++)
 +              PR_INFO("\t%s:\t0x%p\n", name_reg[i], regv[i].v);
 +
 +
 +}
 +static void dtvdemod_set_agc_pinmux(int on)
 +{
 +      if (dtvdd_devp->pin_name == NULL) {
 +              PR_INFO("no pinmux control\n");
 +              return;
 +      }
 +
 +      if (on) {
 +              dtvdd_devp->pin = devm_pinctrl_get_select(dtvdd_devp->dev,
 +                                                      dtvdd_devp->pin_name);
 +              if (IS_ERR(dtvdd_devp->pin)) {
 +                      dtvdd_devp->pin = NULL;
 +                      PR_ERR("get agc pins fail\n");
 +              }
 +      } else {
 +              /*off*/
 +              if (!IS_ERR_OR_NULL(dtvdd_devp->pin)) {
 +                      devm_pinctrl_put(dtvdd_devp->pin);
 +                      dtvdd_devp->pin = NULL;
 +              }
 +      }
 +
 +}
 +
 +static void dtvdemod_clktree_probe(struct device *dev)
 +{
 +      dtvdd_devp->clk_gate_state = 0;
 +
 +      dtvdd_devp->vdac_clk_gate = devm_clk_get(dev, "vdac_clk_gate");
 +      if (IS_ERR(dtvdd_devp->vdac_clk_gate))
 +              PR_ERR("error: %s: clk vdac_clk_gate\n", __func__);
 +}
 +
 +static void dtvdemod_clktree_remove(struct device *dev)
 +{
 +      if (!IS_ERR(dtvdd_devp->vdac_clk_gate))
 +              devm_clk_put(dev, dtvdd_devp->vdac_clk_gate);
 +}
 +static void vdac_clk_gate_ctrl(int status)
 +{
 +      if (status) {
 +              if (dtvdd_devp->clk_gate_state) {
 +                      PR_INFO("clk_gate is already on\n");
 +                      return;
 +              }
 +
 +              if (IS_ERR(dtvdd_devp->vdac_clk_gate))
 +                      PR_ERR("error: %s: vdac_clk_gate\n", __func__);
 +              else
 +                      clk_prepare_enable(dtvdd_devp->vdac_clk_gate);
 +
 +              dtvdd_devp->clk_gate_state = 1;
 +      } else {
 +              if (dtvdd_devp->clk_gate_state == 0) {
 +                      PR_INFO("clk_gate is already off\n");
 +                      return;
 +              }
 +
 +              if (IS_ERR(dtvdd_devp->vdac_clk_gate))
 +                      PR_ERR("error: %s: vdac_clk_gate\n", __func__);
 +              else
 +                      clk_disable_unprepare(dtvdd_devp->vdac_clk_gate);
 +
 +              dtvdd_devp->clk_gate_state = 0;
 +      }
 +}
 +/*
 + * use dtvdemod_vdac_enable replace vdac_enable
 + */
 +static void dtvdemod_vdac_enable(bool on)
 +{
 +      if (on) {
 +              vdac_clk_gate_ctrl(1);
 +              vdac_enable(1, VDAC_MODULE_DTV_DEMOD);
 +      } else {
 +              vdac_clk_gate_ctrl(0);
 +              vdac_enable(0, VDAC_MODULE_DTV_DEMOD);
 +      }
 +}
 +
 +/* platform driver*/
 +static int aml_dtvdemod_probe(struct platform_device *pdev)
 +{
 +      int ret = 0;
 +      const struct of_device_id *match;
 +
 +      PR_INFO("%s\n", __func__);
 +      /*memory*/
 +      dtvdd_devp = kzalloc(sizeof(struct amldtvdemod_device_s),
 +                      GFP_KERNEL);
 +
 +      if (!dtvdd_devp)
 +              goto fail_alloc_region;
 +
 +      dtvdd_devp->state = DTVDEMOD_ST_NOT_INI;
 +
 +
 +      /*class attr */
 +      dtvdd_devp->clsp = class_create(THIS_MODULE, DEMOD_DEVICE_NAME);
 +      if (!dtvdd_devp->clsp)
 +              goto fail_create_class;
 +
 +      ret = class_create_file(dtvdd_devp->clsp, &class_attr_auto_sym);
 +      if (ret)
 +              goto fail_class_create_file;
 +
 +      ret = class_create_file(dtvdd_devp->clsp, &class_attr_dtmb_para);
 +      if (ret)
 +              goto fail_class_create_file;
 +
 +      ret = class_create_file(dtvdd_devp->clsp, &class_attr_dvbc_reg);
 +      if (ret)
 +              goto fail_class_create_file;
 +
 +      ret = class_create_file(dtvdd_devp->clsp, &class_attr_atsc_para);
 +      if (ret)
 +              goto fail_class_create_file;
 +
 +      ret = class_create_file(dtvdd_devp->clsp, &class_attr_demod_rate);
 +      if (ret)
 +              goto fail_class_create_file;
 +
 +      ret = class_create_file(dtvdd_devp->clsp, &class_attr_info);
 +      if (ret)
 +              goto fail_class_create_file;
 +
 +      /**/
 +      match = of_match_device(meson_ddemod_match, &pdev->dev);
 +      if (match == NULL) {
 +              PR_ERR("%s,no matched table\n", __func__);
 +              goto fail_ic_config;
 +      }
 +      dtvdd_devp->data = (struct meson_ddemod_data *)match->data;
 +      dtvdd_devp->icver = dtvdd_devp->data->icver;
 +
 +      /*reg*/
 +      ret = dds_init_reg_map(pdev);
 +      if (ret)
 +              goto fail_ic_config;
 +
 +      /*mem info from dts*/
 +      ret = dtvdemod_set_iccfg_by_dts(pdev);
 +      if (ret)
 +              goto fail_ic_config;
 +              /*dtvdemod_set_iccfg_by_cputype();*/
 +
 +      ret = dtvdemod_init_regaddr_byversion(pdev);
 +      if (ret)
 +              goto fail_ic_config;
 +
 +      /*debug:*/
 +      dbg_ic_cfg();
 +      dbg_reg_addr();
 +
 +      /**/
 +      dtvpll_lock_init();
 +      /* init */
 +      /*dtvdemod_base_add_init();*/
 +      mutex_init(&dtvdd_devp->lock);
 +
 +      dtvdd_devp->dev = &pdev->dev;
 +
 +      dtvdemod_clktree_probe(&pdev->dev);
 +
 +
 +      dtvdd_devp->state = DTVDEMOD_ST_IDLE;
 +      dtvdemod_version(dtvdd_devp);
 +      dtvdd_devp->flg_cma_allc = false;
 +      dtvdd_devp->act_dtmb = false;
 +      //ary temp:
 +      aml_demod_init();
 +
 +      PR_INFO("[amldtvdemod.] : probe ok.\n");
 +      return 0;
 +fail_ic_config:
 +      PR_ERR("ic config error.\n");
 +fail_class_create_file:
 +      PR_ERR("dtvdemod class file create error.\n");
 +      class_destroy(dtvdd_devp->clsp);
 +fail_create_class:
 +      PR_ERR("dtvdemod class create error.\n");
 +      kfree(dtvdd_devp);
 +fail_alloc_region:
 +      PR_ERR("dtvdemod alloc error.\n");
 +      PR_ERR("dtvdemod_init fail.\n");
 +
 +
 +      return ret;
 +}
 +
 +static int __exit aml_dtvdemod_remove(struct platform_device *pdev)
 +{
 +      if (dtvdd_devp == NULL)
 +              return -1;
 +
 +      dtvdemod_clktree_remove(&pdev->dev);
 +
 +      mutex_destroy(&dtvdd_devp->lock);
 +
 +      class_remove_file(dtvdd_devp->clsp, &class_attr_auto_sym);
 +      class_remove_file(dtvdd_devp->clsp, &class_attr_dtmb_para);
 +      class_remove_file(dtvdd_devp->clsp, &class_attr_dvbc_reg);
 +      class_remove_file(dtvdd_devp->clsp, &class_attr_atsc_para);
 +      class_remove_file(dtvdd_devp->clsp, &class_attr_demod_rate);
 +      class_remove_file(dtvdd_devp->clsp, &class_attr_info);
 +
 +      class_destroy(dtvdd_devp->clsp);
 +
 +      kfree(dtvdd_devp);
 +      PR_INFO("%s:remove.\n", __func__);
 +
 +      aml_demod_exit();//ary temp
 +      return 0;
 +}
 +
 +static void aml_dtvdemod_shutdown(struct platform_device *pdev)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      pr_info("%s\n", __func__);
 +
 +      if (dtvdd_devp->state != DTVDEMOD_ST_IDLE) {
 +              if (nmode != AM_FE_UNKNOWN_N)
 +                      leave_mode(nmode);
 +              dtvdd_devp->state = DTVDEMOD_ST_IDLE;
 +      }
 +      adc_pll_down();
 +
 +}
 +
 +static int aml_dtvdemod_suspend(struct platform_device *pdev,
 +                                      pm_message_t state)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      PR_INFO("%s, mode = %d\n", __func__, nmode);
 +
 +      if (nmode != AM_FE_UNKNOWN_N)
 +              leave_mode(nmode);
 +
 +      return 0;
 +}
 +
 +static int aml_dtvdemod_resume(struct platform_device *pdev)
 +{
 +      PR_INFO("%s is called\n", __func__);
 +      return 0;
 +}
 +
 +static struct platform_driver aml_dtvdemod_driver = {
 +      .driver = {
 +              .name = "aml_dtv_demod",
 +              .owner = THIS_MODULE,
 +              /*aml_dtvdemod_dt_match*/
 +              .of_match_table = meson_ddemod_match,
 +      },
 +      .shutdown   = aml_dtvdemod_shutdown,
 +      .probe = aml_dtvdemod_probe,
 +      .remove = __exit_p(aml_dtvdemod_remove),
 +#ifdef CONFIG_PM
 +      .suspend  = aml_dtvdemod_suspend,
 +      .resume   = aml_dtvdemod_resume,
 +#endif
 +};
 +
 +
 +static int __init aml_dtvdemod_init(void)
 +{
 +      if (platform_driver_register(&aml_dtvdemod_driver)) {
 +              pr_err("failed to register amldtvdemod driver module\n");
 +              return -ENODEV;
 +      }
 +      PR_INFO("[amldtvdemod..]%s.\n", __func__);
 +      return 0;
 +}
 +
 +static void __exit aml_dtvdemod_exit(void)
 +{
 +      platform_driver_unregister(&aml_dtvdemod_driver);
 +      PR_INFO("[amldtvdemod..]%s: driver removed ok.\n", __func__);
 +}
 +
 +#if 0
 +static int delsys_confirm(struct dvb_frontend *fe)
 +{
 +      enum fe_delivery_system ldelsys = dtvdd_devp->last_delsys;
 +      enum fe_delivery_system cdelsys;
 +
 +      int ncaps, support;
 +      enum aml_fe_n_mode_t mode = AM_FE_UNKNOWN_N;
 +
 +      cdelsys = fe->dtv_property_cache.delivery_system;
 +
 +      /*same*/
 +      if (ldelsys == cdelsys) {
 +              //PR_DBG("delsys is same, do nothing\n");
 +              return 0;
 +      }
 +
 +      /*support ?*/
 +      ncaps = 0;
 +      support = 0;
 +      while (ncaps < MAX_DELSYS && fe->ops.delsys[ncaps]) {
 +              if (fe->ops.delsys[ncaps] == cdelsys) {
 +
 +                      support = 1;
 +                      break;
 +              }
 +              ncaps++;
 +      }
 +
 +      if (!support) {
 +              PR_INFO("delsys:%d is not support!\n", cdelsys);
 +              return 0;
 +      }
 +
 +      PR_DBG("%s:l=%d,c=%d\n", __func__, ldelsys, cdelsys);
 +
 +      switch (cdelsys) {
 +
 +      case SYS_DVBC_ANNEX_A:
 +      case SYS_DVBC_ANNEX_C:
 +              /*dvbc*/
 +              if (ldelsys == SYS_DVBC_ANNEX_A
 +                      || ldelsys == SYS_DVBC_ANNEX_C) {
 +                      break;
 +              }
 +              mode = AM_FE_QAM_N;
 +              break;
 +      case SYS_ATSC:
 +      case SYS_ATSCMH:
 +      case SYS_DVBC_ANNEX_B:
 +              /*atsc*/
 +              if (ldelsys  == SYS_ATSC
 +                      || ldelsys == SYS_ATSCMH
 +                      || ldelsys == SYS_DVBC_ANNEX_B) {
 +                      break;
 +
 +              }
 +              mode = AM_FE_ATSC_N;
 +              break;
 +      case SYS_DVBT:
 +      case SYS_DVBT2:
 +              /*dvbt, OFDM*/
 +              if (ldelsys  == SYS_DVBT
 +                      || ldelsys == SYS_DVBT2) {
 +                      break;
 +
 +              }
 +              mode = AM_FE_OFDM_N;
 +              break;
 +      case SYS_ISDBT:
 +              if (ldelsys != SYS_ISDBT)
 +                      mode = AM_FE_ISDBT_N;
 +              break;
 +      case SYS_DTMB:
 +              /*dtmb*/
 +              mode = AM_FE_DTMB_N;
 +              break;
 +      case SYS_DVBS:
 +      case SYS_DVBS2:
 +              /*QPSK*/
 +              if (ldelsys  == SYS_DVBS
 +                      || ldelsys == SYS_DVBS2) {
 +
 +                      break;
 +
 +              }
 +              mode = AM_FE_QPSK_N;
 +              break;
 +
 +      case SYS_DSS:
 +      case SYS_DVBH:
 +
 +      case SYS_ISDBS:
 +      case SYS_ISDBC:
 +      case SYS_CMMB:
 +      case SYS_DAB:
 +      case SYS_TURBO:
 +      case SYS_UNDEFINED:
 +#ifdef CONFIG_AMLOGIC_DVB_COMPAT
 +      case SYS_ANALOG:
 +#endif
 +              mode = AM_FE_UNKNOWN_N;
 +              PR_INFO("delsys not support!%d=\n", cdelsys);
 +              return 0;
 +      }
 +
 +      if (mode != AM_FE_UNKNOWN_N)
 +              enter_mode(mode);
 +
 +      if (!get_dtvpll_init_flag()) {
 +              PR_INFO("pll is not set!\n");
 +              leave_mode(mode);
 +
 +              if (fe->ops.tuner_ops.release)
 +                      fe->ops.tuner_ops.release(fe);
 +              dtvdd_devp->last_delsys = SYS_UNDEFINED;
 +              dtvdd_devp->n_mode = AM_FE_UNKNOWN_N;
 +              return 0;
 +      }
 +
 +      dtvdd_devp->last_delsys = cdelsys;
 +
 +      return 0;
 +}
 +#endif
 +static int delsys_set(struct dvb_frontend *fe, unsigned int delsys)
 +{
 +      enum fe_delivery_system ldelsys = dtvdd_devp->last_delsys;
 +      enum fe_delivery_system cdelsys;
 +
 +      int ncaps, support;
 +      enum aml_fe_n_mode_t mode = AM_FE_UNKNOWN_N;
 +      enum aml_fe_n_mode_t lmode = dtvdd_devp->n_mode;
 +
 +      cdelsys = delsys; /*diff*/
 +
 +      /*same*/
 +      if (ldelsys == cdelsys) {
 +              //PR_DBG("delsys is same, do nothing\n");
 +              return 0;
 +      }
 +
 +      /*support ?*/
 +      ncaps = 0;
 +      support = 0;
 +      while (ncaps < MAX_DELSYS && fe->ops.delsys[ncaps]) {
 +              if (fe->ops.delsys[ncaps] == cdelsys) {
 +
 +                      support = 1;
 +                      break;
 +              }
 +              ncaps++;
 +      }
 +
 +      if (!support) {
 +              #if 0
 +              if (get_dtvpll_init_flag()) {
 +                      /**/
 +                      PR_INFO("delsys:%d is not support!\n", cdelsys);
 +                      leave_mode(lmode);
 +                      if (fe->ops.tuner_ops.release)
 +                              fe->ops.tuner_ops.release(fe);
 +                      dtvdd_devp->last_delsys = SYS_UNDEFINED;
 +                      dtvdd_devp->n_mode = AM_FE_UNKNOWN_N;
 +              }
 +              #endif
 +              PR_INFO("delsys:%d is not support!\n", cdelsys);
 +              return 0;
 +      }
 +
 +      if (ldelsys <= END_SYS_DELIVERY && cdelsys <= END_SYS_DELIVERY) {
 +              PR_DBG("%s:l=%s,c=%s\n", __func__,
 +                      name_fe_delivery_system[ldelsys],
 +                      name_fe_delivery_system[cdelsys]);
 +      } else
 +              PR_ERR("%s:last=%d,cur=%d\n", __func__, ldelsys, cdelsys);
 +
 +      switch (cdelsys) {
 +
 +      case SYS_DVBC_ANNEX_A:
 +      case SYS_DVBC_ANNEX_C:
 +              /*dvbc*/
 +              if (ldelsys == SYS_DVBC_ANNEX_A
 +                      || ldelsys == SYS_DVBC_ANNEX_C) {
 +                      break;
 +              }
 +              mode = AM_FE_QAM_N;
 +              break;
 +      case SYS_ATSC:
 +      case SYS_ATSCMH:
 +      case SYS_DVBC_ANNEX_B:
 +              /*atsc*/
 +              if (ldelsys  == SYS_ATSC
 +                      || ldelsys == SYS_ATSCMH
 +                      || ldelsys == SYS_DVBC_ANNEX_B) {
 +                      break;
 +
 +              }
 +              mode = AM_FE_ATSC_N;
 +              break;
 +      case SYS_DVBT:
 +      case SYS_DVBT2:
 +              /*dvbt, OFDM*/
 +              if (ldelsys  == SYS_DVBT
 +                      || ldelsys == SYS_DVBT2) {
 +                      break;
 +
 +              }
 +              mode = AM_FE_OFDM_N;
 +              break;
 +      case SYS_ISDBT:
 +              if (ldelsys != SYS_ISDBT)
 +                      mode = AM_FE_ISDBT_N;
 +              break;
 +      case SYS_DTMB:
 +              /*dtmb*/
 +              mode = AM_FE_DTMB_N;
 +              break;
 +      case SYS_DVBS:
 +      case SYS_DVBS2:
 +              /*QPSK*/
 +              if (ldelsys  == SYS_DVBS
 +                      || ldelsys == SYS_DVBS2) {
 +
 +                      break;
 +
 +              }
 +              mode = AM_FE_QPSK_N;
 +              break;
 +
 +      case SYS_DSS:
 +      case SYS_DVBH:
 +
 +      case SYS_ISDBS:
 +      case SYS_ISDBC:
 +      case SYS_CMMB:
 +      case SYS_DAB:
 +      case SYS_TURBO:
 +      case SYS_UNDEFINED:
 +              return 0;
 +
 +#ifdef CONFIG_AMLOGIC_DVB_COMPAT
 +      case SYS_ANALOG:
 +              if (get_dtvpll_init_flag()) {
 +                      PR_INFO("delsys not support : %d\n", cdelsys);
 +                      leave_mode(lmode);
 +
 +                      if (fe->ops.tuner_ops.release)
 +                              fe->ops.tuner_ops.release(fe);
 +              }
 +
 +              return 0;
 +#endif
 +      }
 +
 +      if (mode != AM_FE_UNKNOWN_N) {
 +              if (lmode != AM_FE_UNKNOWN_N) {
 +                      leave_mode(lmode);
 +
 +                      if (fe->ops.tuner_ops.release)
 +                              fe->ops.tuner_ops.release(fe);
 +              }
 +
 +              if (!enter_mode(mode)) {
 +                      PR_INFO("enter_mode failed,leave!\n");
 +                      leave_mode(mode);
 +
 +                      if (fe->ops.tuner_ops.release)
 +                              fe->ops.tuner_ops.release(fe);
 +                      return 0;
 +              }
 +      }
 +
 +      if (!get_dtvpll_init_flag()) {
 +              PR_INFO("pll is not set!\n");
 +              leave_mode(mode);
 +
 +              if (fe->ops.tuner_ops.release)
 +                      fe->ops.tuner_ops.release(fe);
 +              return 0;
 +      }
 +
 +      dtvdd_devp->last_delsys = cdelsys;
 +      PR_INFO("info type:%d", fe->ops.info.type);
 +
 +      if (mode == AM_FE_ATSC_N)
 +              fe->ops.info.type = FE_ATSC;
 +      else if (mode == AM_FE_OFDM_N)
 +              fe->ops.info.type = FE_OFDM;
 +      else if (mode == AM_FE_DTMB_N)
 +              fe->ops.info.type = FE_DTMB;
 +      else if (mode == AM_FE_QAM_N)
 +              fe->ops.info.type = FE_QAM;
 +      else if (mode == AM_FE_ISDBT_N)
 +              fe->ops.info.type = FE_ISDBT;
 +
 +      if (fe->ops.tuner_ops.set_config)
 +              fe->ops.tuner_ops.set_config(fe, NULL);
 +
 +      return 0;
 +}
 +
 +static int is_not_active(struct dvb_frontend *fe)
 +{
 +      enum fe_delivery_system cdelsys;
 +      enum fe_delivery_system ldelsys = dtvdd_devp->last_delsys;
 +
 +      if (!get_dtvpll_init_flag())
 +              return 1;
 +
 +      cdelsys = fe->dtv_property_cache.delivery_system;
 +      if (ldelsys != cdelsys)
 +              return 2;
 +
 +
 +      return 0;/*active*/
 +}
 +/*ko attach==============================*/
 +static int aml_dtvdm_init(struct dvb_frontend *fe)
 +{
 +
 +      return 0;
 +}
 +static int aml_dtvdm_sleep(struct dvb_frontend *fe)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      if (get_dtvpll_init_flag()) {
 +              PR_INFO("%s\n", __func__);
 +              if (nmode != AM_FE_UNKNOWN_N)
 +                      leave_mode(nmode);
 +
 +              if (fe->ops.tuner_ops.release)
 +                      fe->ops.tuner_ops.release(fe);
 +      }
 +      return 0;
 +}
 +static int aml_dtvdm_set_parameters(struct dvb_frontend *fe)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +      int ret = 0;
 +
 +      PR_INFO("%s", __func__);
 +
 +      /*delsys_confirm(fe);*/
 +      if (is_not_active(fe)) {
 +              PR_DBG("set parm:not active\n");
 +              return 0;
 +      }
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +      case AM_FE_QAM_N:
 +              PR_INFO("FE_QAM\n");
 +              timer_begain(D_TIMER_DETECT);
 +              dtvdd_devp->en_detect = 1; /*fist set*/
 +              ret = gxtv_demod_dvbc_set_frontend(fe);
 +              break;
 +      case AM_FE_OFDM_N:
 +              PR_INFO("FE_OFDM\n");
 +              timer_begain(D_TIMER_DETECT);
 +              dtvdd_devp->en_detect = 1; /*fist set*/
 +
 +              ret = gxtv_demod_dvbt_set_frontend(fe);
 +
 +              break;
 +      case AM_FE_ISDBT_N:     /*same as dvbt*/
 +              PR_INFO("FE_ISDBT\n");
 +
 +              timer_begain(D_TIMER_DETECT);
 +              dtvdd_devp->en_detect = 1; /*fist set*/
 +              ret = gxtv_demod_dvbt_set_frontend(fe);
 +
 +              break;
 +      case AM_FE_ATSC_N:
 +              PR_INFO("FE_ATSC\n");
 +              ret = gxtv_demod_atsc_set_frontend(fe);
 +              break;
 +      case AM_FE_DTMB_N:
 +              PR_INFO("FE_DTMB\n");
 +              ret = gxtv_demod_dtmb_set_frontend(fe);
 +              break;
 +      case AM_FE_UNKNOWN_N:
 +      default:
 +
 +              break;
 +      }
 +      return ret;
 +}
 +
 +static int aml_dtvdm_get_frontend(struct dvb_frontend *fe,
 +                               struct dtv_frontend_properties *p)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      int ret = 0;
 +
 +      if (is_not_active(fe)) {
 +              PR_DBGL("get parm:not active\n");
 +              return 0;
 +      }
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              ret = gxtv_demod_dvbc_get_frontend(fe);
 +              break;
 +      case AM_FE_OFDM_N:
 +              ret = gxtv_demod_dvbt_get_frontend(fe);
 +              break;
 +      case AM_FE_ISDBT_N:     /*same as dvbt*/
 +              ret = gxtv_demod_dvbt_get_frontend(fe);
 +              break;
 +      case AM_FE_ATSC_N:
 +              ret = gxtv_demod_atsc_get_frontend(fe);
 +              break;
 +      case AM_FE_DTMB_N:
 +              ret = gxtv_demod_dtmb_get_frontend(fe);
 +              break;
 +      case AM_FE_UNKNOWN_N:
 +      default:
 +
 +              break;
 +      }
 +      return ret;
 +}
 +static int aml_dtvdm_get_tune_settings(struct dvb_frontend *fe,
 +                                    struct dvb_frontend_tune_settings
 +                                      *fe_tune_settings)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      int ret = 0;
 +
 +      if (is_not_active(fe)) {
 +              PR_DBGL("get parm:not active\n");
 +              return 0;
 +      }
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              fe_tune_settings->min_delay_ms = 300;
 +              fe_tune_settings->step_size = 0; /* no zigzag */
 +              fe_tune_settings->max_drift = 0;
 +
 +              break;
 +      case AM_FE_OFDM_N:
 +              /*dvbt*/
 +              fe_tune_settings->min_delay_ms = 500;
 +              fe_tune_settings->step_size = 0;
 +              fe_tune_settings->max_drift = 0;
 +              break;
 +      case AM_FE_ISDBT_N:     /*same as dvbt*/
 +              /*isdbt*/
 +              fe_tune_settings->min_delay_ms = 300;
 +              fe_tune_settings->step_size = 0;
 +              fe_tune_settings->max_drift = 0;
 +
 +              break;
 +      case AM_FE_ATSC_N:
 +
 +              break;
 +      case AM_FE_DTMB_N:
 +
 +              break;
 +      case AM_FE_UNKNOWN_N:
 +      default:
 +
 +              break;
 +      }
 +      return ret;
 +}
 +static int aml_dtvdm_read_status(struct dvb_frontend *fe,
 +                                      enum fe_status *status)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      int ret = 0;
 +
 +      if (nmode == AM_FE_UNKNOWN_N)
 +              return 0;
 +
 +      if (is_not_active(fe)) {
 +              PR_DBGL("read status:not active\n");
 +              return 0;
 +      }
 +
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              ret = gxtv_demod_dvbc_read_status_timer(fe, status);
 +              break;
 +      case AM_FE_OFDM_N:
 +              ret = gxtv_demod_dvbt_read_status(fe, status);
 +              break;
 +      case AM_FE_ISDBT_N:
 +              ret = gxtv_demod_dvbt_read_status(fe, status);
 +              break;
 +      case AM_FE_ATSC_N:
 +              ret = gxtv_demod_atsc_read_status(fe, status);
 +              break;
 +      case AM_FE_DTMB_N:
 +              ret = gxtv_demod_dtmb_read_status(fe, status);
 +              break;
 +      /*case AM_FE_UNKNOWN_N:*/
 +      default:
 +
 +              break;
 +      }
 +      return ret;
 +
 +}
 +static int aml_dtvdm_read_ber(struct dvb_frontend *fe, u32 *ber)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      int ret = 0;
 +
 +      if (is_not_active(fe)) {
 +              PR_DBGL("read ber:not active\n");
 +              return 0;
 +      }
 +
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              ret = gxtv_demod_dvbc_read_ber(fe, ber);
 +              break;
 +      case AM_FE_OFDM_N:
 +              ret = gxtv_demod_dvbt_read_ber(fe, ber);
 +              break;
 +      case AM_FE_ISDBT_N:     /*same as dvbt*/
 +              ret = gxtv_demod_dvbt_read_ber(fe, ber);
 +              break;
 +      case AM_FE_ATSC_N:
 +              ret = gxtv_demod_atsc_read_ber(fe, ber);
 +              break;
 +      case AM_FE_DTMB_N:
 +              ret = gxtv_demod_dtmb_read_ber(fe, ber);
 +              break;
 +      case AM_FE_UNKNOWN_N:
 +      default:
 +
 +              break;
 +      }
 +      return ret;
 +
 +}
 +
 +static int aml_dtvdm_read_signal_strength(struct dvb_frontend *fe,
 +                                       u16 *strength)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      int ret = 0;
 +
 +      if (is_not_active(fe)) {
 +              PR_DBGL("read strength:not active\n");
 +              return 0;
 +      }
 +
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              ret = gxtv_demod_dvbc_read_signal_strength(fe, strength);
 +              break;
 +      case AM_FE_OFDM_N:
 +              ret = gxtv_demod_dvbt_read_signal_strength(fe, strength);
 +              break;
 +      case AM_FE_ISDBT_N:     /*same as dvbt*/
 +              ret = gxtv_demod_dvbt_read_signal_strength(fe, strength);
 +              break;
 +      case AM_FE_ATSC_N:
 +              ret = gxtv_demod_atsc_read_signal_strength(fe, strength);
 +              break;
 +      case AM_FE_DTMB_N:
 +              ret = gxtv_demod_dtmb_read_signal_strength(fe, strength);
 +              break;
 +      case AM_FE_UNKNOWN_N:
 +      default:
 +
 +              break;
 +      }
 +      return ret;
 +
 +}
 +static int aml_dtvdm_read_snr(struct dvb_frontend *fe, u16 *snr)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      int ret = 0;
 +
 +      if (is_not_active(fe)) {
 +              PR_DBGL("read snr :not active\n");
 +              return 0;
 +      }
 +
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              ret = gxtv_demod_dvbc_read_snr(fe, snr);
 +              break;
 +      case AM_FE_OFDM_N:
 +              ret = gxtv_demod_dvbt_read_snr(fe, snr);
 +              break;
 +      case AM_FE_ISDBT_N:
 +              ret = gxtv_demod_dvbt_read_snr(fe, snr);
 +              break;
 +      case AM_FE_ATSC_N:
 +              ret = gxtv_demod_atsc_read_snr(fe, snr);
 +              break;
 +      case AM_FE_DTMB_N:
 +              ret = gxtv_demod_dtmb_read_snr(fe, snr);
 +              break;
 +      case AM_FE_UNKNOWN_N:
 +      default:
 +
 +              break;
 +      }
 +      return ret;
 +
 +}
 +
 +static int aml_dtvdm_read_ucblocks(struct dvb_frontend *fe, u32 *ucblocks)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      int ret = 0;
 +
 +      if (is_not_active(fe)) {
 +              PR_DBGL("read ucblocks :not active\n");
 +              return 0;
 +      }
 +
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              ret = gxtv_demod_dvbc_read_ucblocks(fe, ucblocks);
 +              break;
 +      case AM_FE_OFDM_N:
 +              ret = gxtv_demod_dvbt_read_ucblocks(fe, ucblocks);
 +              break;
 +      case AM_FE_ISDBT_N:
 +              ret = gxtv_demod_dvbt_read_ucblocks(fe, ucblocks);
 +              break;
 +      case AM_FE_ATSC_N:
 +              ret = gxtv_demod_atsc_read_ucblocks(fe, ucblocks);
 +              break;
 +      case AM_FE_DTMB_N:
 +              ret = gxtv_demod_dtmb_read_ucblocks(fe, ucblocks);
 +              break;
 +      case AM_FE_UNKNOWN_N:
 +      default:
 +
 +              break;
 +      }
 +      return ret;
 +
 +}
 +static void aml_dtvdm_release(struct dvb_frontend *fe)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              gxtv_demod_dvbc_release(fe);
 +              break;
 +      case AM_FE_OFDM_N:
 +      case AM_FE_ISDBT_N:
 +              gxtv_demod_dvbt_release(fe);
 +              break;
 +      case AM_FE_ATSC_N:
 +              gxtv_demod_atsc_release(fe);
 +              break;
 +      case AM_FE_DTMB_N:
 +              gxtv_demod_dtmb_release(fe);
 +              break;
 +      case AM_FE_UNKNOWN_N:
 +      default:
 +
 +              break;
 +      }
 +
 +      if (get_dtvpll_init_flag()) {
 +              PR_INFO("%s\n", __func__);
 +              if (nmode != AM_FE_UNKNOWN_N)
 +                      leave_mode(nmode);
 +
 +              if (fe->ops.tuner_ops.release)
 +                      fe->ops.tuner_ops.release(fe);
 +      }
 +}
 +
 +
 +static int aml_dtvdm_tune(struct dvb_frontend *fe, bool re_tune,
 +      unsigned int mode_flags, unsigned int *delay, enum fe_status *status)
 +{
 +      enum aml_fe_n_mode_t nmode = dtvdd_devp->n_mode;
 +      int ret = 0;
 +      static int flg; /*debug only*/
 +
 +      if (re_tune)
 +              ;//delsys_confirm(fe);
 +
 +      if (nmode == AM_FE_UNKNOWN_N) {
 +              *delay = HZ * 5;
 +              *status = 0;
 +              return 0;
 +      }
 +
 +      if (is_not_active(fe)) {
 +              *status = 0;
 +              PR_DBGL("tune :not active\n");
 +              return 0;
 +      }
 +
 +      if ((flg > 0) && (flg < 5))
 +              PR_INFO("%s\n", __func__);
 +
 +
 +      switch (nmode) {
 +      case AM_FE_QPSK_N:
 +
 +              break;
 +
 +      case AM_FE_QAM_N:
 +              gxtv_demod_dvbc_tune(fe, re_tune, mode_flags,
 +                                              delay, status);
 +
 +              break;
 +      case AM_FE_OFDM_N:
 +      case AM_FE_ISDBT_N:
 +              ret = gxtv_demod_dvbt_tune(fe, re_tune, mode_flags,
 +                                              delay, status);
 +              break;
 +      case AM_FE_ATSC_N:
 +              ret = gxtv_demod_atsc_tune(fe, re_tune, mode_flags,
 +                                              delay, status);
 +              flg++;
 +              break;
 +      case AM_FE_DTMB_N:
 +              ret = gxtv_demod_dtmb_tune(fe, re_tune, mode_flags,
 +                                              delay, status);
 +
 +              break;
 +      /*case AM_FE_UNKNOWN_N:*/
 +      default:
 +              flg = 0;
 +              break;
 +      }
 +
 +      return ret;
 +
 +}
 +static int aml_dtvdm_set_property(struct dvb_frontend *dev,
 +                      struct dtv_property *tvp)
 +{
 +      int r = 0;
 +      u32 delsys;
 +
 +      switch (tvp->cmd) {
 +      case DTV_DELIVERY_SYSTEM:
 +              delsys = tvp->u.data;
 +              delsys_set(dev, delsys);
 +              break;
 +
 +      default:
 +              break;
 +      }
 +
 +
 +      return r;
 +
 +}
-       .get_property         = aml_dtvdm_get_property,
 +
 +static struct dvb_frontend_ops aml_dtvdm_gxtvbb_ops = {
 +      .delsys = { SYS_DVBC_ANNEX_A, SYS_DTMB},
 +      .info = {
 +              /*in aml_fe, it is 'amlogic dvb frontend' */
 +              .name = "amlogic dtv demod txlx",
 +              .frequency_min      = 51000000,
 +              .frequency_max      = 900000000,
 +              .frequency_stepsize = 0,
 +              .frequency_tolerance = 0,               /**/
 +              .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
 +                      FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
 +                      FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 |
 +                      FE_CAN_QAM_AUTO | FE_CAN_TRANSMISSION_MODE_AUTO |
 +                      FE_CAN_GUARD_INTERVAL_AUTO | FE_CAN_HIERARCHY_AUTO |
 +                      FE_CAN_RECOVER | FE_CAN_MUTE_TS
 +      },
 +      .init                 = aml_dtvdm_init,
 +      .sleep                = aml_dtvdm_sleep,
 +      .set_frontend         = aml_dtvdm_set_parameters,
 +      .get_frontend         = aml_dtvdm_get_frontend,
 +      .get_tune_settings    = aml_dtvdm_get_tune_settings,
 +      .read_status          = aml_dtvdm_read_status,
 +      .read_ber             = aml_dtvdm_read_ber,
 +      .read_signal_strength = aml_dtvdm_read_signal_strength,
 +      .read_snr             = aml_dtvdm_read_snr,
 +      .read_ucblocks        = aml_dtvdm_read_ucblocks,
 +      .release              = aml_dtvdm_release,
 +      .set_property         = aml_dtvdm_set_property,
-       .get_property         = aml_dtvdm_get_property,
 +
 +/*-------------*/
 +      .tune                   = aml_dtvdm_tune,
 +      .get_frontend_algo      = gxtv_demod_atsc_get_frontend_algo,
 +
 +};
 +
 +static struct dvb_frontend_ops aml_dtvdm_txl_ops = {
 +      .delsys = { SYS_DVBC_ANNEX_A, SYS_DTMB, SYS_ANALOG},
 +      .info = {
 +              /*in aml_fe, it is 'amlogic dvb frontend' */
 +              .name = "amlogic dtv demod txl",
 +              .frequency_min      = 51000000,
 +              .frequency_max      = 900000000,
 +              .frequency_stepsize = 0,
 +              .frequency_tolerance = 0,               /**/
 +              .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
 +                      FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
 +                      FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 |
 +                      FE_CAN_QAM_AUTO | FE_CAN_TRANSMISSION_MODE_AUTO |
 +                      FE_CAN_GUARD_INTERVAL_AUTO | FE_CAN_HIERARCHY_AUTO |
 +                      FE_CAN_RECOVER | FE_CAN_MUTE_TS
 +      },
 +      .init                 = aml_dtvdm_init,
 +      .sleep                = aml_dtvdm_sleep,
 +      .set_frontend         = aml_dtvdm_set_parameters,
 +      .get_frontend         = aml_dtvdm_get_frontend,
 +      .get_tune_settings    = aml_dtvdm_get_tune_settings,
 +      .read_status          = aml_dtvdm_read_status,
 +      .read_ber             = aml_dtvdm_read_ber,
 +      .read_signal_strength = aml_dtvdm_read_signal_strength,
 +      .read_snr             = aml_dtvdm_read_snr,
 +      .read_ucblocks        = aml_dtvdm_read_ucblocks,
 +      .release              = aml_dtvdm_release,
 +      .set_property         = aml_dtvdm_set_property,
-       .get_property         = aml_dtvdm_get_property,
 +
 +/*-------------*/
 +      .tune                   = aml_dtvdm_tune,
 +      .get_frontend_algo      = gxtv_demod_atsc_get_frontend_algo,
 +
 +};
 +
 +static struct dvb_frontend_ops aml_dtvdm_txlx_ops = {
 +#ifdef CONFIG_AMLOGIC_DVB_COMPAT
 +      .delsys = { SYS_ATSC, SYS_DVBC_ANNEX_B,  SYS_DVBC_ANNEX_A, SYS_DVBT,
 +              SYS_ANALOG, SYS_ISDBT},
 +#else
 +      .delsys = { SYS_ATSC, SYS_DVBC_ANNEX_B,  SYS_DVBC_ANNEX_A, SYS_DVBT},
 +#endif
 +      .info = {
 +              /*in aml_fe, it is 'amlogic dvb frontend' */
 +              .name = "amlogic dtv demod txlx",
 +              .frequency_min      = 51000000,
 +              .frequency_max      = 900000000,
 +              .frequency_stepsize = 0,
 +              .frequency_tolerance = 0,               /**/
 +              .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
 +                      FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
 +                      FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 |
 +                      FE_CAN_QAM_AUTO | FE_CAN_TRANSMISSION_MODE_AUTO |
 +                      FE_CAN_GUARD_INTERVAL_AUTO | FE_CAN_HIERARCHY_AUTO |
 +                      FE_CAN_RECOVER | FE_CAN_MUTE_TS
 +      },
 +      .init                 = aml_dtvdm_init,
 +      .sleep                = aml_dtvdm_sleep,
 +      .set_frontend         = aml_dtvdm_set_parameters,
 +      .get_frontend         = aml_dtvdm_get_frontend,
 +      .get_tune_settings    = aml_dtvdm_get_tune_settings,
 +      .read_status          = aml_dtvdm_read_status,
 +      .read_ber             = aml_dtvdm_read_ber,
 +      .read_signal_strength = aml_dtvdm_read_signal_strength,
 +      .read_snr             = aml_dtvdm_read_snr,
 +      .read_ucblocks        = aml_dtvdm_read_ucblocks,
 +      .release              = aml_dtvdm_release,
 +      .set_property         = aml_dtvdm_set_property,
-       .get_property         = aml_dtvdm_get_property,
 +
 +/*-------------*/
 +      .tune                   = aml_dtvdm_tune,
 +      .get_frontend_algo      = gxtv_demod_txlx_get_frontend_algo,
 +
 +};
 +
 +static struct dvb_frontend_ops aml_dtvdm_gxlx_ops = {
 +      .delsys = { SYS_DVBC_ANNEX_A },
 +      .info = {
 +              /*in aml_fe, it is 'amlogic dvb frontend' */
 +              .name = "amlogic dtv demod txlx",
 +              .frequency_min      = 51000000,
 +              .frequency_max      = 900000000,
 +              .frequency_stepsize = 0,
 +              .frequency_tolerance = 0,               /**/
 +              .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
 +                      FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
 +                      FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 |
 +                      FE_CAN_QAM_AUTO | FE_CAN_TRANSMISSION_MODE_AUTO |
 +                      FE_CAN_GUARD_INTERVAL_AUTO | FE_CAN_HIERARCHY_AUTO |
 +                      FE_CAN_RECOVER | FE_CAN_MUTE_TS
 +      },
 +      .init                 = aml_dtvdm_init,
 +      .sleep                = aml_dtvdm_sleep,
 +      .set_frontend         = aml_dtvdm_set_parameters,
 +      .get_frontend         = aml_dtvdm_get_frontend,
 +      .get_tune_settings    = aml_dtvdm_get_tune_settings,
 +      .read_status          = aml_dtvdm_read_status,
 +      .read_ber             = aml_dtvdm_read_ber,
 +      .read_signal_strength = aml_dtvdm_read_signal_strength,
 +      .read_snr             = aml_dtvdm_read_snr,
 +      .read_ucblocks        = aml_dtvdm_read_ucblocks,
 +      .release              = aml_dtvdm_release,
 +      .set_property         = aml_dtvdm_set_property,
-       .get_property         = aml_dtvdm_get_property,
 +
 +/*-------------*/
 +      .tune                   = aml_dtvdm_tune,
 +      .get_frontend_algo      = gxtv_demod_atsc_get_frontend_algo,
 +
 +};
 +
 +static struct dvb_frontend_ops aml_dtvdm_txhd_ops = {
 +      .delsys = { SYS_DTMB },
 +      .info = {
 +              /*in aml_fe, it is 'amlogic dvb frontend' */
 +              .name = "amlogic dtv demod txlx",
 +              .frequency_min      = 51000000,
 +              .frequency_max      = 900000000,
 +              .frequency_stepsize = 0,
 +              .frequency_tolerance = 0,               /**/
 +              .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
 +                      FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
 +                      FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 |
 +                      FE_CAN_QAM_AUTO | FE_CAN_TRANSMISSION_MODE_AUTO |
 +                      FE_CAN_GUARD_INTERVAL_AUTO | FE_CAN_HIERARCHY_AUTO |
 +                      FE_CAN_RECOVER | FE_CAN_MUTE_TS
 +      },
 +      .init                 = aml_dtvdm_init,
 +      .sleep                = aml_dtvdm_sleep,
 +      .set_frontend         = aml_dtvdm_set_parameters,
 +      .get_frontend         = aml_dtvdm_get_frontend,
 +      .get_tune_settings    = aml_dtvdm_get_tune_settings,
 +      .read_status          = aml_dtvdm_read_status,
 +      .read_ber             = aml_dtvdm_read_ber,
 +      .read_signal_strength = aml_dtvdm_read_signal_strength,
 +      .read_snr             = aml_dtvdm_read_snr,
 +      .read_ucblocks        = aml_dtvdm_read_ucblocks,
 +      .release              = aml_dtvdm_release,
 +      .set_property         = aml_dtvdm_set_property,
-       .get_property         = aml_dtvdm_get_property,
 +
 +/*-------------*/
 +      .tune                   = aml_dtvdm_tune,
 +      .get_frontend_algo      = gxtv_demod_atsc_get_frontend_algo,
 +
 +};
 +
 +static struct dvb_frontend_ops aml_dtvdm_tl1_ops = {
 +#ifdef CONFIG_AMLOGIC_DVB_COMPAT
 +      .delsys = {SYS_DVBC_ANNEX_A, SYS_DVBC_ANNEX_B, SYS_ATSC, SYS_DTMB,
 +              SYS_ANALOG},
 +#else
 +      .delsys = { SYS_ATSC, SYS_DVBC_ANNEX_B,  SYS_DVBC_ANNEX_A, SYS_DVBT},
 +#endif
 +      .info = {
 +              /*in aml_fe, it is 'amlogic dvb frontend' */
 +              .name = "amlogic dtv demod tl1",
 +              .frequency_min      = 51000000,
 +              .frequency_max      = 900000000,
 +              .frequency_stepsize = 0,
 +              .frequency_tolerance = 0,               /**/
 +              .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
 +                      FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
 +                      FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 |
 +                      FE_CAN_QAM_AUTO | FE_CAN_TRANSMISSION_MODE_AUTO |
 +                      FE_CAN_GUARD_INTERVAL_AUTO | FE_CAN_HIERARCHY_AUTO |
 +                      FE_CAN_RECOVER | FE_CAN_MUTE_TS
 +      },
 +      .init                 = aml_dtvdm_init,
 +      .sleep                = aml_dtvdm_sleep,
 +      .set_frontend         = aml_dtvdm_set_parameters,
 +      .get_frontend         = aml_dtvdm_get_frontend,
 +      .get_tune_settings    = aml_dtvdm_get_tune_settings,
 +      .read_status          = aml_dtvdm_read_status,
 +      .read_ber             = aml_dtvdm_read_ber,
 +      .read_signal_strength = aml_dtvdm_read_signal_strength,
 +      .read_snr             = aml_dtvdm_read_snr,
 +      .read_ucblocks        = aml_dtvdm_read_ucblocks,
 +      .release              = aml_dtvdm_release,
 +      .set_property         = aml_dtvdm_set_property,
-       .get_property         = aml_dtvdm_get_property,
 +
 +/*-------------*/
 +      .tune                   = aml_dtvdm_tune,
 +      .get_frontend_algo      = gxtv_demod_txlx_get_frontend_algo,
 +
 +};
 +
 +static struct dvb_frontend_ops aml_dtvdm_tm2_ops = {
 +#ifdef CONFIG_AMLOGIC_DVB_COMPAT
 +      .delsys = {SYS_DVBC_ANNEX_A, SYS_DVBC_ANNEX_B, SYS_ATSC, SYS_DTMB,
 +              SYS_ANALOG},
 +#else
 +      .delsys = { SYS_ATSC, SYS_DVBC_ANNEX_B,  SYS_DVBC_ANNEX_A, SYS_DVBT},
 +#endif
 +      .info = {
 +              /*in aml_fe, it is 'amlogic dvb frontend' */
 +              .name = "amlogic dtv demod tm2",
 +              .frequency_min      = 51000000,
 +              .frequency_max      = 900000000,
 +              .frequency_stepsize = 0,
 +              .frequency_tolerance = 0,               /**/
 +              .caps = FE_CAN_FEC_1_2 | FE_CAN_FEC_2_3 | FE_CAN_FEC_3_4 |
 +                      FE_CAN_FEC_5_6 | FE_CAN_FEC_7_8 | FE_CAN_FEC_AUTO |
 +                      FE_CAN_QPSK | FE_CAN_QAM_16 | FE_CAN_QAM_64 |
 +                      FE_CAN_QAM_AUTO | FE_CAN_TRANSMISSION_MODE_AUTO |
 +                      FE_CAN_GUARD_INTERVAL_AUTO | FE_CAN_HIERARCHY_AUTO |
 +                      FE_CAN_RECOVER | FE_CAN_MUTE_TS
 +      },
 +      .init                 = aml_dtvdm_init,
 +      .sleep                = aml_dtvdm_sleep,
 +      .set_frontend         = aml_dtvdm_set_parameters,
 +      .get_frontend         = aml_dtvdm_get_frontend,
 +      .get_tune_settings    = aml_dtvdm_get_tune_settings,
 +      .read_status          = aml_dtvdm_read_status,
 +      .read_ber             = aml_dtvdm_read_ber,
 +      .read_signal_strength = aml_dtvdm_read_signal_strength,
 +      .read_snr             = aml_dtvdm_read_snr,
 +      .read_ucblocks        = aml_dtvdm_read_ucblocks,
 +      .release              = aml_dtvdm_release,
 +      .set_property         = aml_dtvdm_set_property,
 +
 +/*-------------*/
 +      .tune                   = aml_dtvdm_tune,
 +      .get_frontend_algo      = gxtv_demod_txlx_get_frontend_algo,
 +
 +};
 +
 +struct dvb_frontend *aml_dtvdm_attach(const struct demod_config *config)
 +{
 +      int ic_version = get_ic_ver();
 +
 +
 +      /*mem setting is in prob*/
 +
 +      struct dvb_frontend *fe = &dtvdd_devp->frontend;
 +
 +      /* mem of dvb_frontend is define in aml_fe*/
 +
 +      switch (ic_version) {
 +
 +      case IC_VER_GTVBB:
 +              memcpy(&fe->ops, &aml_dtvdm_gxtvbb_ops,
 +                                     sizeof(struct dvb_frontend_ops));
 +              break;
 +      case IC_VER_TXL:
 +              memcpy(&fe->ops, &aml_dtvdm_txl_ops,
 +                     sizeof(struct dvb_frontend_ops));
 +              break;
 +      case IC_VER_TXLX:
 +              memcpy(&fe->ops, &aml_dtvdm_txlx_ops,
 +                     sizeof(struct dvb_frontend_ops));
 +              break;
 +      case IC_VER_GXLX:
 +              memcpy(&fe->ops, &aml_dtvdm_gxlx_ops,
 +                     sizeof(struct dvb_frontend_ops));
 +              break;
 +      case IC_VER_TXHD:
 +              memcpy(&fe->ops, &aml_dtvdm_txhd_ops,
 +                                     sizeof(struct dvb_frontend_ops));
 +              break;
 +      case IC_VER_TL1:
 +              memcpy(&fe->ops, &aml_dtvdm_tl1_ops,
 +                     sizeof(struct dvb_frontend_ops));
 +              break;
 +      case IC_VER_TM2:
 +              memcpy(&fe->ops, &aml_dtvdm_tm2_ops,
 +                     sizeof(struct dvb_frontend_ops));
 +              break;
 +      default:
 +              PR_ERR("attach fail! ic=%d\n", ic_version);
 +              /*return NULL;*/
 +              fe = NULL;
 +              break;
 +      }
 +              /* mem of dvb_frontend is define in aml_fe*/
 +
 +      dtvdd_devp->last_delsys = SYS_UNDEFINED;
 +
 +
 +      return fe;
 +}
 +EXPORT_SYMBOL(aml_dtvdm_attach);
 +
 +/*-------------------------*/
 +static struct aml_exp_func aml_exp_ops = {
 +      .leave_mode = leave_mode,
 +};
 +
 +struct aml_exp_func *aml_dtvdm_exp_attach(struct aml_exp_func *exp)
 +{
 +      if (exp) {
 +              memcpy(exp, &aml_exp_ops, sizeof(struct aml_exp_func));
 +      } else {
 +              PR_ERR("%s:fail!\n", __func__);
 +              return NULL;
 +
 +      }
 +      return exp;
 +}
 +EXPORT_SYMBOL(aml_dtvdm_exp_attach);
 +
 +/*-------------------------*/
 +struct dvb_frontend *aml_get_fe(void)
 +{
 +
 +      return &dtvdd_devp->frontend;
 +
 +}
 +
 +void aml_exp_attach(struct aml_exp_func *afe)
 +{
 +
 +}
 +EXPORT_SYMBOL(aml_exp_attach);
 +
 +/*=======================================*/
 +
 +fs_initcall(aml_dtvdemod_init);
 +module_exit(aml_dtvdemod_exit);
 +
 +MODULE_DESCRIPTION("gxtv_demod DVB-T/DVB-C/DTMB Demodulator driver");
 +MODULE_AUTHOR("RSJ");
 +MODULE_LICENSE("GPL");
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
index d9a820257b4e17f08b06c5da0b799d12cb48c289,cd45b38946616dc139af070503f91912352784bc..395ec751164fb98e2df9711098a55080375ba7c2
@@@ -1524,13 -1504,6 +1524,12 @@@ static int dtv_property_process_get(str
        case DTV_STAT_TOTAL_BLOCK_COUNT:
                tvp->u.st = c->block_count;
                break;
-               r = 0;
 +#ifdef CONFIG_AMLOGIC_DVB_COMPAT
 +      case DTV_DELIVERY_SUB_SYSTEM:
 +      case DTV_TS_INPUT:
 +              //printk("dvb-core get sub sys\r\n");
 +              break;
 +#endif
        default:
                dev_dbg(fe->dvb->device,
                        "%s: FE property %d doesn't exist\n",
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
index 68abab53b149c7ee06a9035fc0cba4c837a4f56e,67bfef9d838374504688adde22b43dd30dc94d77..7f1b430f6ca9243426a7c465aaca4b302a6d91b9
@@@ -606,21 -605,12 +607,21 @@@ static int __init __reserved_mem_reserv
                size = dt_mem_next_cell(dt_root_size_cells, &prop);
  
                if (size &&
 -                  early_init_dt_reserve_memory_arch(base, size, nomap) == 0)
 +                  early_init_dt_reserve_memory_arch(base, size, nomap) == 0) {
 +              #ifdef CONFIG_AMLOGIC_MODIFY
 +                      if (console_loglevel > 1)
 +                              pr_emerg("\t%08lx - %08lx, %8ld KB, %s\n",
 +                                       (unsigned long)base,
 +                                       (unsigned long)(base + size),
 +                                       (unsigned long)(size >> 10),
 +                                       uname);
 +              #else
-                       pr_debug("Reserved memory: reserved region for node '%s': base %pa, size %ld MiB\n",
-                               uname, &base, (unsigned long)size / SZ_1M);
+                       pr_debug("Reserved memory: reserved region for node '%s': base %pa, size %lu MiB\n",
+                               uname, &base, (unsigned long)(size / SZ_1M));
 -              else
 +              #endif
 +              } else
-                       pr_info("Reserved memory: failed to reserve memory for node '%s': base %pa, size %ld MiB\n",
-                               uname, &base, (unsigned long)size / SZ_1M);
+                       pr_info("Reserved memory: failed to reserve memory for node '%s': base %pa, size %lu MiB\n",
+                               uname, &base, (unsigned long)(size / SZ_1M));
  
                len -= t_len;
                if (first) {
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
index 59deeeb1b24e1af57346db3404b00781eca04557,bff5a15e59c00455dfe19b1de0f9dc41ef060600..613ccf73327c7b2d681be70f8a28f22ba5b48812
@@@ -158,14 -158,9 +158,13 @@@ source "drivers/usb/phy/Kconfig
  
  source "drivers/usb/gadget/Kconfig"
  
 +source "drivers/usb/typec/Kconfig"
 +
 +source "drivers/usb/roles/Kconfig"
 +
  config USB_LED_TRIG
        bool "USB LED Triggers"
-       depends on LEDS_CLASS && LEDS_TRIGGERS
-       select USB_COMMON
+       depends on LEDS_CLASS && USB_COMMON && LEDS_TRIGGERS
        help
          This option adds LED triggers for USB host and/or gadget activity.
  
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
index f8d5eb0ac4537f75c36d7194f7cdee46d420c1a5,4fc2999a5f79c9efb8dc88cdd08824c6536f9e2f..f01b07790105d0867452220fc0d8f4e5060180d7
@@@ -1531,15 -1492,14 +1531,18 @@@ static void configfs_composite_unbind(s
        purge_configs_funcs(gi);
        composite_dev_cleanup(cdev);
        usb_ep_autoconfig_reset(cdev->gadget);
 +#ifdef CONFIG_AMLOGIC_USB
 +      wakeup_source_trash(&Gadget_Lock.wakesrc);
 +#endif
        spin_lock_irqsave(&gi->spinlock, flags);
        cdev->gadget = NULL;
+       cdev->deactivations = 0;
+       gadget->deactivated = false;
        set_gadget_data(gadget, NULL);
        spin_unlock_irqrestore(&gi->spinlock, flags);
  }
  
++#ifndef CONFIG_USB_CONFIGFS_UEVENT
  static int configfs_composite_setup(struct usb_gadget *gadget,
                const struct usb_ctrlrequest *ctrl)
  {
@@@ -1586,6 -1546,6 +1589,7 @@@ static void configfs_composite_disconne
        composite_disconnect(gadget);
        spin_unlock_irqrestore(&gi->spinlock, flags);
  }
++#endif
  
  static void configfs_composite_suspend(struct usb_gadget *gadget)
  {
Simple merge
Simple merge
Simple merge
index a755c8b843f9f0634e2b5d5338f2ab3c00c1f47c,ceb0a02c4ac37b6a90c89d8842a60cfb86c16154..cad3d4cf9e3f152d2550d9035ccceb7e407f4128
@@@ -1396,12 -1409,13 +1409,16 @@@ int xhci_urb_enqueue(struct usb_hcd *hc
        unsigned int slot_id, ep_index;
        struct urb_priv *urb_priv;
        int size, i;
-       if (!urb || xhci_check_args(hcd, urb->dev, urb->ep,
-                                       true, true, __func__) <= 0)
 +#ifdef CONFIG_AMLOGIC_USB
 +      struct usb_ctrlrequest *setup;
 +#endif
+       if (!urb)
                return -EINVAL;
+       ret = xhci_check_args(hcd, urb->dev, urb->ep,
+                                       true, true, __func__);
+       if (ret <= 0)
+               return ret ? ret : -EINVAL;
  
        slot_id = urb->dev->slot_id;
        ep_index = xhci_get_endpoint_index(&urb->ep->desc);
Simple merge
Simple merge
diff --cc fs/ext4/dir.c
Simple merge
Simple merge
diff --cc fs/ext4/file.c
Simple merge
Simple merge
diff --cc fs/ext4/inode.c
Simple merge
diff --cc fs/ext4/ioctl.c
Simple merge
diff --cc fs/ext4/namei.c
index 7791eceba65a3796976aeb474e1e1975c11641cc,2da44d47b3ad2004faadf82db8b3d808133bfcee..c27ee2d5db3546bbca4fcbbaee12a477db5715dc
@@@ -3195,8 -3219,7 +3219,8 @@@ static int ext4_link(struct dentry *old
  
        if (inode->i_nlink >= EXT4_LINK_MAX)
                return -EMLINK;
 -      if (ext4_encrypted_inode(dir) &&
 +
-       if (ext4_encrypted_inode(dir) &&
++      if (IS_ENCRYPTED(dir) &&
                        !fscrypt_has_permitted_context(dir, inode))
                return -EXDEV;
  
@@@ -3550,13 -3603,13 +3598,6 @@@ static int ext4_rename(struct inode *ol
        if (!old.bh || le32_to_cpu(old.de->inode) != old.inode->i_ino)
                goto release_bh;
  
--      if ((old.dir != new.dir) &&
--          ext4_encrypted_inode(new.dir) &&
--          !fscrypt_has_permitted_context(new.dir, old.inode)) {
--              retval = -EXDEV;
--              goto release_bh;
--      }
--
        new.bh = ext4_find_entry(new.dir, &new.dentry->d_name,
                                 &new.de, &new.inlined);
        if (IS_ERR(new.bh)) {
@@@ -3725,19 -3778,19 +3766,6 @@@ static int ext4_cross_rename(struct ino
        u8 new_file_type;
        int retval;
  
--      if ((ext4_encrypted_inode(old_dir) &&
--           !fscrypt_has_encryption_key(old_dir)) ||
--          (ext4_encrypted_inode(new_dir) &&
--           !fscrypt_has_encryption_key(new_dir)))
--              return -ENOKEY;
--
--      if ((ext4_encrypted_inode(old_dir) ||
--           ext4_encrypted_inode(new_dir)) &&
--          (old_dir != new_dir) &&
--          (!fscrypt_has_permitted_context(new_dir, old.inode) ||
--           !fscrypt_has_permitted_context(old_dir, new.inode)))
--              return -EXDEV;
--
        if ((ext4_test_inode_flag(new_dir, EXT4_INODE_PROJINHERIT) &&
             !projid_eq(EXT4_I(new_dir)->i_projid,
                        EXT4_I(old_dentry->d_inode)->i_projid)) ||
diff --cc fs/ext4/super.c
Simple merge
diff --cc fs/f2fs/inode.c
index ccb02226dd2c0c28722ecafd61ce657975e441cd,972c8899a4c20a576262f1b98fa9af7bcd911673..1defb2992af6b9256059f187e0a2d2ccb4414f8f
@@@ -467,9 -466,9 +467,9 @@@ make_now
                inode->i_op = &f2fs_dir_inode_operations;
                inode->i_fop = &f2fs_dir_operations;
                inode->i_mapping->a_ops = &f2fs_dblock_aops;
-               inode_nohighmem(inode);
+               mapping_set_gfp_mask(inode->i_mapping, GFP_NOFS);
        } else if (S_ISLNK(inode->i_mode)) {
 -              if (f2fs_encrypted_inode(inode))
 +              if (file_is_encrypt(inode))
                        inode->i_op = &f2fs_encrypted_symlink_inode_operations;
                else
                        inode->i_op = &f2fs_symlink_inode_operations;
diff --cc fs/f2fs/namei.c
Simple merge
diff --cc fs/inode.c
Simple merge
diff --cc fs/namespace.c
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
index 7172b6501a471f0b61868405edc6ec8e985edfcf,33e086778856687919e49b3a95a7f66f99f21fe4..d798674261aa887a144b29814953ef677eaf6ed1
mode 100755,100644..100755
Simple merge
Simple merge
Simple merge
index 87a3583db1271f788c0fb31a2fddcd5616c020f1,b653754ee9cfaec709787c793d8937946faf2995..6941c25275806115e215d3cec56c727e7a98a6ff
@@@ -116,12 -109,7 +116,12 @@@ enum fe_type 
        FE_QPSK,
        FE_QAM,
        FE_OFDM,
--      FE_ATSC
++      FE_ATSC,
 +#ifdef CONFIG_AMLOGIC_DVB_COMPAT
 +      FE_ANALOG,
 +      FE_DTMB,
 +      FE_ISDBT
 +#endif
  };
  
  /**
Simple merge
diff --cc init/main.c
Simple merge
diff --cc kernel/cgroup.c
Simple merge
diff --cc kernel/cpu.c
Simple merge
diff --cc kernel/fork.c
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
diff --cc kernel/sysctl.c
Simple merge
Simple merge
Simple merge
Simple merge
diff --cc lib/string.c
Simple merge
diff --cc mm/gup.c
Simple merge
diff --cc mm/kmemleak.c
Simple merge
diff --cc mm/memory.c
Simple merge
diff --cc mm/page_alloc.c
index 101bdd9ef7dabd08506d5dc8ac5a8d03cfe7e9c5,c007e94cba47e185c3befc6fbd060943a6a2c932..3128b4cdba1aa15366ec359f63b39fa249d2f972
@@@ -829,13 -826,8 +829,13 @@@ static inline void __free_one_page(stru
        unsigned long uninitialized_var(buddy_idx);
        struct page *buddy;
        unsigned int max_order;
 +#ifdef CONFIG_AMLOGIC_MEMORY_EXTEND
 +      int buddy_mg;
 +
 +      migratetype = get_pageblock_migratetype(page);
 +#endif /* CONFIG_AMLOGIC_MEMORY_EXTEND */
  
-       max_order = min_t(unsigned int, MAX_ORDER, pageblock_order + 1);
+       max_order = min_t(unsigned int, MAX_ORDER - 1, pageblock_order);
  
        VM_BUG_ON(!zone_is_initialized(zone));
        VM_BUG_ON_PAGE(page->flags & PAGE_FLAGS_CHECK_AT_PREP, page);
diff --cc mm/shmem.c
Simple merge
diff --cc mm/slub.c
index 4567b0aaae849bdb6403adbc1a14f55d8589b3d2,9bfbfc5dda94d9962ebde93cd947fed587ccb8dc..b9e175141ca1c72310a444dc0896882dad9102df
+++ b/mm/slub.c
@@@ -2636,9 -2631,7 +2640,10 @@@ new_slab
        deactivate_slab(s, page, get_freepointer(s, freelist));
        c->page = NULL;
        c->freelist = NULL;
 +#ifdef CONFIG_AMLOGIC_SLAB_TRACE
 +      slab_trace_mark_object(freelist, addr, s);
 +#endif
+       c->tid = next_tid(c->tid);
        return freelist;
  }
  
diff --cc mm/vmstat.c
Simple merge
diff --cc net/ipv4/tcp.c
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
Simple merge
index 12553cbe0b4832c06ecdab5031fd20ca554c0e1f,bddc8d363cb8e06dbf11074268797b89863a4a70..9373efa02c8e0630fedb168dc39d5f79ba7311f5
@@@ -2335,11 -2335,11 +2335,15 @@@ int policydb_read(struct policydb *p, v
        if ((le32_to_cpu(buf[1]) & POLICYDB_CONFIG_ANDROID_NETLINK_ROUTE)) {
                p->android_netlink_route = 1;
        }
 +      if ((le32_to_cpu(buf[1]) & POLICYDB_CONFIG_ANDROID_NETLINK_GETNEIGH)) {
 +              p->android_netlink_getneigh = 1;
 +      }
 +
  
+       if ((le32_to_cpu(buf[1]) & POLICYDB_CONFIG_ANDROID_NETLINK_GETNEIGH)) {
+               p->android_netlink_getneigh = 1;
+       }
        if (p->policyvers >= POLICYDB_VERSION_POLCAP) {
                rc = ebitmap_read(&p->policycaps, fp);
                if (rc)
Simple merge
Simple merge