static int gps_hostwake_probe(struct platform_device *pdev)
{
	int ret;
	int irq;

	struct gps_geofence_wake *ac_data = &g_geofence_wake;
	struct bcm_gps_hostwake_platform_data *pdata;

	/* HOST_WAKE : to indicate that ASIC has an geofence event.
	unsigned int gpio_hostwake; */

	pr_debug(PFX "%s\n", __func__);

	/*  Read device tree information */
	pdata = pdev->dev.platform_data;
	if (!pdata) {
		pr_debug(PFX "%s : fail to get platform_data.\n", __func__);
		return -1;
	}

	/* 1. Init GPIO and IRQ for HOST_WAKE */
	irq = gps_gpio_irq_init(pdata->gpio_hostwake);

	if (irq < 0)
		return -EIO;

	/* 2. Register Driver */
	memset(ac_data, 0, sizeof(struct gps_geofence_wake));

	/* 2.1 Misc device setup */
	ac_data->misc.minor = MISC_DYNAMIC_MINOR;
	ac_data->misc.name = HOST_WAKE_MODULE_NAME;
	ac_data->misc.fops = &gps_geofence_wake_fops;

	/* 2.2 Information that be used later */
	ac_data->irq = irq;
	ac_data->host_req_pin = pdata->gpio_hostwake;

	pr_notice(PFX "misc register, name %s, irq %d, host req pin num %d\n",
		ac_data->misc.name, irq, ac_data->host_req_pin);
	/* 2.3 Register misc driver */
	ret = misc_register(&ac_data->misc);
	if (ret) {
		pr_err(PFX "cannot register gps geofence wake miscdev on minor=%d (%d)\n",
			MISC_DYNAMIC_MINOR, ret);
		return ret;
	}

	/* 3. Init wake_lock */
	wake_lock_init(&ac_data->wake_lock, WAKE_LOCK_SUSPEND,
			"gps_geofence_wakelock");
	return 0;
}
static int k3_gps_bcm_probe(struct platform_device* pdev)
{
	GPS_BCM_INFO* gps_bcm = NULL;
	struct device* gps_power_dev = &pdev->dev;
	struct device_node* np = gps_power_dev->of_node;
	int ret = 0;
	int irq = 0;
	struct gps_geofence_wake* ac_data = &g_geofence_wake;

	printk(KERN_INFO "[GPS] start find gps_power and ic type is 4774\n");
	gps_bcm = kzalloc(sizeof(GPS_BCM_INFO), GFP_KERNEL);
	if (!gps_bcm)
	{
	    printk(KERN_ERR "[GPS] Alloc memory failed\n");
	    return -ENOMEM;
	}

	 gps_dir = proc_mkdir("gps", NULL);
	 if (!gps_dir)
	{
	    printk(KERN_ERR "[GPS] proc dir create failed\n");
	    ret = -ENOMEM;
	    goto err_free_gps;
	}

	ret = gps_bcm4774_node_init(np, &gps_bcm->gpioid_en,  GPS_PROC_EN,   &gps_proc_fops_nstandby);
	if (0 != ret)
	{
	    printk(KERN_ERR "[GPS] gps_bcm4774_node_init  gps_bcm  failed.\n");
	    ret = -1;
	    goto err_free_nstandby;
	}

    gps_bcm->gpioid_hostwake.gpio = of_get_named_gpio(np, "huawei,gps_hostwake", 0);
    if (!gpio_is_valid(gps_bcm->gpioid_hostwake.gpio))
    {
        ret = -1;
        printk(KERN_ERR "[GPS] get huawei,gps_hostwake failed.\n");
        goto err_free_gps_en;
    }
    // 1. Init GPIO and IRQ for HOST_WAKE
    printk("[gps]%s,gps_bcm->gpioid_hostwake.gpio=%d\n", __func__, gps_bcm->gpioid_hostwake.gpio);

    // 2. Register Driver
    memset(ac_data, 0, sizeof(struct gps_geofence_wake));

    // 2.1 Misc device setup
    ac_data->misc.minor = MISC_DYNAMIC_MINOR;
    ac_data->misc.name = HOST_WAKE_MODULE_NAME;
    ac_data->misc.fops = &gps_geofence_wake_fops;

    // 2.2 Information that be used later
    ac_data->irq = irq;
    ac_data->host_req_pin = gps_bcm->gpioid_hostwake.gpio;

    printk("[gps]misc register, name %s, irq %d, host req pin num %d\n", ac_data->misc.name, irq, ac_data->host_req_pin);
    // 2.3 Register misc driver
    if (0 != (ret = misc_register(&ac_data->misc)))
    {
        printk("[gps]cannot register gps geofence wake miscdev on minor=%d (%d)\n", MISC_DYNAMIC_MINOR, ret);
        goto err_free_host_wake;
    }

    // 3. Init wake_lock
    wake_lock_init(&ac_data->wake_lock, WAKE_LOCK_SUSPEND, "gps_geofence_wakelock");
    printk("[gps]wake_lock_init done\n");
    irq = gps_gpio_irq_init(gps_bcm->gpioid_hostwake.gpio);
    if (irq < 0)
    {
        printk("[gps]hostwake irq error\n");
        goto err_free_misc_register;
    }

    /* Set 32KC clock */
    gps_bcm->clk = of_clk_get_by_name(np, "gps_32k");
    if (IS_ERR(gps_bcm->clk))
    {
        printk(KERN_ERR "[GPS] clk_32k get failed!\n");
        ret = -1;
        goto err_free_misc_register;
    }
    ret = clk_prepare_enable(gps_bcm->clk);
    if (ret)
    {
        printk(KERN_ERR "[GPS] clk_32k enable is failed\n");
        goto err_free_clk;
    }
    printk(KERN_INFO "[GPS] clk_32k is finished\n");


   ret = gps_bcm4774_node_init(np, &gps_bcm->mcu_req,  GPS_PROC_MCUREQ,  &gps_proc_fops_mcureq);
   if (0 != ret)
   {
      printk(KERN_ERR "[GPS]gps_bcm4774_node_init  mcu_req  failed \n");
      goto err_free_mcureq;
   }

   ret = gps_bcm4774_node_init(np, &gps_bcm->mcu_req_rsp,  GPS_PROC_MCUREQ_RSP,  &gps_proc_fops_mcureq_rsp);
   if (0 != ret)
   {
       printk(KERN_ERR "[GPS]gps_bcm4774_node_init  mcu_req_rsp  failed \n");
       goto err_free_mcureq_rsp;
    }

    gps_bcm->pctrl = devm_pinctrl_get(gps_power_dev);
    if (IS_ERR(gps_bcm->pctrl))
    {
        printk(KERN_ERR "[GPS] pinctrl get error!\n");
        ret = -1;
        goto err_free_clk;
    }

    gps_bcm->pins_normal = pinctrl_lookup_state(gps_bcm->pctrl, "default");
    if (IS_ERR(gps_bcm->pins_normal))
    {
        printk(KERN_ERR "[GPS] gps_bcm->pins_normal lookup error!\n");
        ret = -1;
        goto err_free_pinctrl;
    }

    gps_bcm->pins_idle = pinctrl_lookup_state(gps_bcm->pctrl, "idle");
    if (IS_ERR(gps_bcm->pins_idle))
    {
        printk(KERN_ERR "[GPS] gps_bcm->pins_idle lookup error!\n");
        ret = -1;
        goto err_free_pinctrl;
    }

    ret = pinctrl_select_state(gps_bcm->pctrl, gps_bcm->pins_normal);
    if (ret)
    {
        printk(KERN_ERR "[GPS] pinctrl_select_state error!\n");
        goto err_free_pinctrl;
    }
    printk(KERN_INFO "[GPS] pinctrl is finish\n");

    gps_bcm->refclk = of_clk_get_by_name(np, "clk_gps");
    if (IS_ERR(gps_bcm->refclk))
    {
        printk(KERN_ERR "[GPS] @@@ref_clk get failed!\n");
        ret = -1;
        goto err_free_pinctrl;
    }

    ret = clk_set_rate(gps_bcm->refclk , GPS_REF_CLK_FREQ_19M);
    if (ret < 0)
    {
        printk(KERN_ERR "[GPS] clk_set_rate HI3635_CLK_RATE failed\n");
        goto err_free_refclk;
    }

    gps_ref_clk = gps_bcm->refclk;

    printk(KERN_INFO "[GPS] ref clk is finished!\n");
    platform_set_drvdata(pdev, gps_bcm);
    g_gps_bcm = gps_bcm;

    return 0;

err_free_refclk:
    clk_put(gps_bcm->refclk);
err_free_pinctrl:
    pinctrl_put(gps_bcm->pctrl);

err_free_mcureq:
err_free_mcureq_rsp:
err_free_clk:
    clk_put(gps_bcm->clk);
err_free_misc_register:
    misc_deregister(&ac_data->misc);
    wake_lock_destroy(&ac_data->wake_lock);
    pr_err("%s: misc_deregister!\n", __func__);
err_free_host_wake:
    gpio_free(gps_bcm->gpioid_hostwake.gpio);
    pr_err("%s: err_free_host_wake!\n", __func__);

err_free_gps_en:
    gpio_free(gps_bcm->gpioid_en.gpio);

err_free_nstandby:
err_free_gps:
    kfree(gps_bcm);
    gps_bcm = NULL;
    g_gps_bcm = NULL;
    return ret;
}