Commit 95dcbe56 authored by wangliang.wang's avatar wangliang.wang Committed by sam.xiang

[linux] Upgrade the MMF SDK from V4.0.0 to V4.1.0

	1. 181x support secureboot
	2. add .gitignore

Change-Id: I34cd45663d92eeb8e3b5ddfbf1a876111ce46bd1
parent 221f3d93
build/
scripts/dtc/include-prefixes/cvi_board_memmap.h
......@@ -370,6 +370,16 @@ config ARCH_CV181X
help
This enables support for Cvitek's CV181X
config ARCH_ATHENA2
bool "Cvitek ATHENA2 SoC"
select PINCTRL
select PINCTRL_BM
select PINMUX
select PINCONF
select GENERIC_PINCONF
help
This enables support for Cvitek's ATHENA2
config ARCH_CV952X
bool "Cvitek CV952X SoC"
select PINCTRL
......@@ -476,6 +486,39 @@ config ARCH_CV181X_ASIC
endchoice
endif # end ARCH_CV181X
if ARCH_ATHENA2
config ARCH_CVITEK_CHIP
string "athena2"
help
This enables support for Cvitek ATHENA2 series
choice
prompt "Select the platform of SoC"
default ARCH_ATHENA2_FPGA
help
Select the platform of SoC
FPGA
PALLADIUM
ASIC
config ARCH_ATHENA2_PALLADIUM
bool "Cvitek ATHENA2 SoC - Palladium"
help
This enables support for Cvitek's ATHENA2 SoC on Palladium platform
config ARCH_ATHENA2_FPGA
bool "Cvitek ATHENA2 SoC - FPGA"
help
This enables support for Cvitek's ATHENA2 SoC on FPGA platform
config ARCH_ATHENA2_ASIC
bool "Cvitek ATHENA2 SoC- ASIC"
help
This enables support for Cvitek's ATHENA2 SoC ASIC
endchoice
endif # end ARCH_ATHENA2
if ARCH_CV952X
config ARCH_CVITEK_CHIP
string "cv952x"
......
......@@ -235,4 +235,6 @@ source "drivers/interconnect/Kconfig"
source "drivers/counter/Kconfig"
source "drivers/most/Kconfig"
source "drivers/efuse/Kconfig"
endmenu
......@@ -189,3 +189,4 @@ obj-$(CONFIG_GNSS) += gnss/
obj-$(CONFIG_INTERCONNECT) += interconnect/
obj-$(CONFIG_COUNTER) += counter/
obj-$(CONFIG_MOST) += most/
obj-$(CONFIG_EFUSE) += efuse/
# SPDX-License-Identifier: GPL-2.0-only
#
# Generic efuse drivers configuration
#
menuconfig EFUSE
bool "Efuse drivers"
default y
help
Efuse drivers offer a generic mechanism for
efuse management.
Only support cv181x and cv180x currently
Efuse driver build-in is better
if EFUSE
config CV181X_EFUSE
tristate "Efuse driver for CVITEK CV181X"
depends on ARCH_CV181X || COMPILE_TEST
default y
help
Select this driver for CVITEK CV181X efuse
This driver is used for program and read efuse
This driver can also be built as a module
But build-in is better.
config CV180X_EFUSE
tristate "Efuse driver for CVITEK CV180X"
depends on ARCH_CV180X || COMPILE_TEST
default y
help
Select this driver for CVITEK CV180X efuse op
This driver is used for program and read efuse
This driver can also be built as a module
But build-in is better.
endif
# SPDX-License-Identifier: GPL-2.0
#
# Makefile for sensor chip drivers.
#
# platform efuse drivers
obj-$(CONFIG_CV181X_EFUSE) += cv181x_efuse.o
obj-$(CONFIG_CV180X_EFUSE) += cv180x_efuse.o
// SPDX-License-Identifier: GPL-2.0+
//
// EFUSE implementation
//
#include <linux/kernel.h>
#include <linux/io.h>
#include <linux/clk.h>
#include <linux/module.h>
#include "linux/cv180x_efuse.h"
#define ERROR(fmt, ...) pr_err(fmt, ##__VA_ARGS__)
#define VERBOSE(fmt, ...) pr_debug(fmt, ##__VA_ARGS__)
#define EFUSE_BASE (0x03050000)
#define EFUSE_SHADOW_REG (efuse_base + 0x100)
#define EFUSE_SIZE 0x100
#define EFUSE_MODE (efuse_base + 0x0)
#define EFUSE_ADR (efuse_base + 0x4)
#define EFUSE_DIR_CMD (efuse_base + 0x8)
#define EFUSE_RD_DATA (efuse_base + 0xC)
#define EFUSE_STATUS (efuse_base + 0x10)
#define EFUSE_ONE_WAY (efuse_base + 0x14)
#define EFUSE_BIT_AREAD BIT(0)
#define EFUSE_BIT_MREAD BIT(1)
#define EFUSE_BIT_PRG BIT(2)
#define EFUSE_BIT_PWR_DN BIT(3)
#define EFUSE_BIT_CMD BIT(4)
#define EFUSE_BIT_BUSY BIT(0)
#define EFUSE_CMD_REFRESH (0x30)
enum EFUSE_READ_TYPE { EFUSE_AREAD, EFUSE_MREAD };
static void __iomem *efuse_base;
static struct clk *efuse_clk;
static inline void mmio_write_32(void __iomem *addr, uint32_t value)
{
iowrite32(value, addr);
}
static inline uint32_t mmio_read_32(void __iomem *addr)
{
return ioread32(addr);
}
static inline void mmio_setbits_32(void __iomem *addr, uint32_t set)
{
mmio_write_32(addr, mmio_read_32(addr) | set);
}
void cvi_efuse_wait_for_ready(void)
{
while (mmio_read_32(EFUSE_STATUS) & EFUSE_BIT_BUSY)
;
}
static void cvi_efuse_power_on(uint32_t on)
{
if (on)
mmio_setbits_32(EFUSE_MODE, EFUSE_BIT_CMD);
else
mmio_setbits_32(EFUSE_MODE, EFUSE_BIT_PWR_DN | EFUSE_BIT_CMD);
}
static void cvi_efuse_refresh(void)
{
mmio_write_32(EFUSE_MODE, EFUSE_CMD_REFRESH);
}
static void cvi_efuse_prog_bit(uint32_t word_addr, uint32_t bit_addr,
uint32_t high_row)
{
uint32_t phy_addr;
// word_addr: virtual addr, take "lower 6-bits" from 7-bits (0-127)
// bit_addr: virtual addr, 5-bits (0-31)
// composite physical addr[11:0] = [11:7]bit_addr + [6:0]word_addr
phy_addr =
((bit_addr & 0x1F) << 7) | ((word_addr & 0x3F) << 1) | high_row;
cvi_efuse_wait_for_ready();
// send efuse program cmd
mmio_write_32(EFUSE_ADR, phy_addr);
mmio_write_32(EFUSE_MODE, EFUSE_BIT_PRG | EFUSE_BIT_CMD);
}
static uint32_t cvi_efuse_read_from_phy(uint32_t phy_word_addr,
enum EFUSE_READ_TYPE type)
{
// power on efuse macro
cvi_efuse_power_on(1);
cvi_efuse_wait_for_ready();
mmio_write_32(EFUSE_ADR, phy_word_addr);
if (type == EFUSE_AREAD) // array read
mmio_write_32(EFUSE_MODE, EFUSE_BIT_AREAD | EFUSE_BIT_CMD);
else if (type == EFUSE_MREAD) // margin read
mmio_write_32(EFUSE_MODE, EFUSE_BIT_MREAD | EFUSE_BIT_CMD);
else {
ERROR("EFUSE: Unsupported read type!");
return (uint32_t)-1;
}
cvi_efuse_wait_for_ready();
return mmio_read_32(EFUSE_RD_DATA);
}
static int cvi_efuse_write_word(uint32_t vir_word_addr, uint32_t val)
{
uint32_t i, j, row_val, zero_bit;
uint32_t new_value;
int err_cnt = 0;
for (j = 0; j < 2; j++) {
VERBOSE("EFUSE: Program physical word addr #%d\n",
(vir_word_addr << 1) | j);
// array read by word address
row_val = cvi_efuse_read_from_phy(
(vir_word_addr << 1) | j,
EFUSE_AREAD); // read low word of word_addr
zero_bit = val & (~row_val); // only program zero bit
// program row which bit is zero
for (i = 0; i < 32; i++) {
if ((zero_bit >> i) & 1)
cvi_efuse_prog_bit(vir_word_addr, i, j);
}
// check by margin read
new_value = cvi_efuse_read_from_phy((vir_word_addr << 1) | j,
EFUSE_MREAD);
VERBOSE("%s(): val=0x%x new_value=0x%x\n", __func__, val,
new_value);
if ((val & new_value) != val) {
err_cnt += 1;
ERROR("EFUSE: Program bits check failed (%d)!\n",
err_cnt);
}
}
cvi_efuse_refresh();
return err_cnt >= 2 ? -EIO : 0;
}
int __init cvi_efuse_init(void)
{
efuse_base = ioremap(EFUSE_BASE, 0x1000);
if (efuse_base == NULL)
return -ENOMEM;
efuse_clk = clk_get_sys(NULL, "clk_efuse");
if (IS_ERR(efuse_clk)) {
pr_err("%s: efuse clock not found %ld\n", __func__,
PTR_ERR(efuse_clk));
return PTR_ERR(efuse_clk);
}
return 0;
}
void __exit cvi_efuse_exit(void)
{
iounmap(efuse_base);
}
int64_t cvi_efuse_read_from_shadow(uint32_t addr)
{
int64_t ret = -1;
if (addr >= EFUSE_SIZE)
return -EFAULT;
if (addr % 4 != 0)
return -EFAULT;
ret = clk_prepare_enable(efuse_clk);
if (ret) {
pr_err("%s: clock failed to prepare+enable: %lld\n", __func__,
(long long)ret);
return ret;
}
ret = mmio_read_32(EFUSE_SHADOW_REG + addr);
clk_disable_unprepare(efuse_clk);
return ret;
}
EXPORT_SYMBOL(cvi_efuse_read_from_shadow);
int cvi_efuse_write(uint32_t addr, uint32_t value)
{
int ret;
VERBOSE("%s(): 0x%x = 0x%x\n", __func__, addr, value);
if (addr >= EFUSE_SIZE)
return -EFAULT;
if (addr % 4 != 0)
return -EFAULT;
ret = clk_prepare_enable(efuse_clk);
if (ret) {
pr_err("%s: clock failed to prepare+enable: %lld\n", __func__,
(long long)ret);
return ret;
}
ret = cvi_efuse_write_word(addr / 4, value);
VERBOSE("%s(): ret=%d\n", __func__, ret);
cvi_efuse_power_on(1);
cvi_efuse_refresh();
cvi_efuse_wait_for_ready();
clk_disable_unprepare(efuse_clk);
return ret;
}
EXPORT_SYMBOL(cvi_efuse_write);
int cvi_efuse_read_buf(u32 addr, void *buf, size_t buf_size)
{
int64_t ret = -1;
int i;
if (!buf)
return -EFAULT;
if (buf_size > EFUSE_SIZE)
buf_size = EFUSE_SIZE;
memset(buf, 0, buf_size);
for (i = 0; i < buf_size; i += 4) {
ret = cvi_efuse_read_from_shadow(addr + i);
if (ret < 0)
return ret;
if (ret > 0) {
u32 v = ret;
memcpy(buf + i, &v, sizeof(v));
}
}
return buf_size;
}
EXPORT_SYMBOL(cvi_efuse_read_buf);
module_init(cvi_efuse_init);
module_exit(cvi_efuse_exit);
MODULE_AUTHOR("leon.liao@cvitek.com");
MODULE_DESCRIPTION("cv180x efuse driver");
MODULE_LICENSE("GPL");
// SPDX-License-Identifier: GPL-2.0+
//
// EFUSE implementation
//
#include <linux/kernel.h>
#include <linux/io.h>
#include <linux/clk.h>
#include <linux/module.h>
#include "linux/cv180x_efuse.h"
#define ERROR(fmt, ...) pr_err(fmt, ##__VA_ARGS__)
#define VERBOSE(fmt, ...) pr_debug(fmt, ##__VA_ARGS__)
#define EFUSE_BASE (0x03050000)
#define EFUSE_SHADOW_REG (efuse_base + 0x100)
#define EFUSE_SIZE 0x100
#define EFUSE_MODE (efuse_base + 0x0)
#define EFUSE_ADR (efuse_base + 0x4)
#define EFUSE_DIR_CMD (efuse_base + 0x8)
#define EFUSE_RD_DATA (efuse_base + 0xC)
#define EFUSE_STATUS (efuse_base + 0x10)
#define EFUSE_ONE_WAY (efuse_base + 0x14)
#define EFUSE_BIT_AREAD BIT(0)
#define EFUSE_BIT_MREAD BIT(1)
#define EFUSE_BIT_PRG BIT(2)
#define EFUSE_BIT_PWR_DN BIT(3)
#define EFUSE_BIT_CMD BIT(4)
#define EFUSE_BIT_BUSY BIT(0)
#define EFUSE_CMD_REFRESH (0x30)
enum EFUSE_READ_TYPE { EFUSE_AREAD, EFUSE_MREAD };
static void __iomem *efuse_base;
static struct clk *efuse_clk;
static inline void mmio_write_32(void __iomem *addr, uint32_t value)
{
iowrite32(value, addr);
}
static inline uint32_t mmio_read_32(void __iomem *addr)
{
return ioread32(addr);
}
static inline void mmio_setbits_32(void __iomem *addr, uint32_t set)
{
mmio_write_32(addr, mmio_read_32(addr) | set);
}
void cvi_efuse_wait_for_ready(void)
{
while (mmio_read_32(EFUSE_STATUS) & EFUSE_BIT_BUSY)
;
}
static void cvi_efuse_power_on(uint32_t on)
{
if (on)
mmio_setbits_32(EFUSE_MODE, EFUSE_BIT_CMD);
else
mmio_setbits_32(EFUSE_MODE, EFUSE_BIT_PWR_DN | EFUSE_BIT_CMD);
}
static void cvi_efuse_refresh(void)
{
mmio_write_32(EFUSE_MODE, EFUSE_CMD_REFRESH);
}
static void cvi_efuse_prog_bit(uint32_t word_addr, uint32_t bit_addr,
uint32_t high_row)
{
uint32_t phy_addr;
// word_addr: virtual addr, take "lower 6-bits" from 7-bits (0-127)
// bit_addr: virtual addr, 5-bits (0-31)
// composite physical addr[11:0] = [11:7]bit_addr + [6:0]word_addr
phy_addr =
((bit_addr & 0x1F) << 7) | ((word_addr & 0x3F) << 1) | high_row;
cvi_efuse_wait_for_ready();
// send efuse program cmd
mmio_write_32(EFUSE_ADR, phy_addr);
mmio_write_32(EFUSE_MODE, EFUSE_BIT_PRG | EFUSE_BIT_CMD);
}
static uint32_t cvi_efuse_read_from_phy(uint32_t phy_word_addr,
enum EFUSE_READ_TYPE type)
{
// power on efuse macro
cvi_efuse_power_on(1);
cvi_efuse_wait_for_ready();
mmio_write_32(EFUSE_ADR, phy_word_addr);
if (type == EFUSE_AREAD) // array read
mmio_write_32(EFUSE_MODE, EFUSE_BIT_AREAD | EFUSE_BIT_CMD);
else if (type == EFUSE_MREAD) // margin read
mmio_write_32(EFUSE_MODE, EFUSE_BIT_MREAD | EFUSE_BIT_CMD);
else {
ERROR("EFUSE: Unsupported read type!");
return (uint32_t)-1;
}
cvi_efuse_wait_for_ready();
return mmio_read_32(EFUSE_RD_DATA);
}
static int cvi_efuse_write_word(uint32_t vir_word_addr, uint32_t val)
{
uint32_t i, j, row_val, zero_bit;
uint32_t new_value;
int err_cnt = 0;
for (j = 0; j < 2; j++) {
VERBOSE("EFUSE: Program physical word addr #%d\n",
(vir_word_addr << 1) | j);
// array read by word address
row_val = cvi_efuse_read_from_phy(
(vir_word_addr << 1) | j,
EFUSE_AREAD); // read low word of word_addr
zero_bit = val & (~row_val); // only program zero bit
// program row which bit is zero
for (i = 0; i < 32; i++) {
if ((zero_bit >> i) & 1)
cvi_efuse_prog_bit(vir_word_addr, i, j);
}
// check by margin read
new_value = cvi_efuse_read_from_phy((vir_word_addr << 1) | j,
EFUSE_MREAD);
VERBOSE("%s(): val=0x%x new_value=0x%x\n", __func__, val,
new_value);
if ((val & new_value) != val) {
err_cnt += 1;
ERROR("EFUSE: Program bits check failed (%d)!\n",
err_cnt);
}
}
cvi_efuse_refresh();
return err_cnt >= 2 ? -EIO : 0;
}
int __init cvi_efuse_init(void)
{
efuse_base = ioremap(EFUSE_BASE, 0x1000);
if (efuse_base == NULL)
return -ENOMEM;
efuse_clk = clk_get_sys(NULL, "clk_efuse");
if (IS_ERR(efuse_clk)) {
pr_err("%s: efuse clock not found %ld\n", __func__,
PTR_ERR(efuse_clk));
return PTR_ERR(efuse_clk);
}
return 0;
}
void __exit cvi_efuse_exit(void)
{
iounmap(efuse_base);
}
int64_t cvi_efuse_read_from_shadow(uint32_t addr)
{
int64_t ret = -1;
if (addr >= EFUSE_SIZE)
return -EFAULT;
if (addr % 4 != 0)
return -EFAULT;
ret = clk_prepare_enable(efuse_clk);
if (ret) {
pr_err("%s: clock failed to prepare+enable: %lld\n", __func__,
(long long)ret);
return ret;
}
ret = mmio_read_32(EFUSE_SHADOW_REG + addr);
clk_disable_unprepare(efuse_clk);
return ret;
}
EXPORT_SYMBOL(cvi_efuse_read_from_shadow);
int cvi_efuse_write(uint32_t addr, uint32_t value)
{
int ret;
VERBOSE("%s(): 0x%x = 0x%x\n", __func__, addr, value);
if (addr >= EFUSE_SIZE)
return -EFAULT;
if (addr % 4 != 0)
return -EFAULT;
ret = clk_prepare_enable(efuse_clk);
if (ret) {
pr_err("%s: clock failed to prepare+enable: %lld\n", __func__,
(long long)ret);
return ret;
}
ret = cvi_efuse_write_word(addr / 4, value);
VERBOSE("%s(): ret=%d\n", __func__, ret);
cvi_efuse_power_on(1);
cvi_efuse_refresh();
cvi_efuse_wait_for_ready();
clk_disable_unprepare(efuse_clk);
return ret;
}
EXPORT_SYMBOL(cvi_efuse_write);
int cvi_efuse_read_buf(u32 addr, void *buf, size_t buf_size)
{
int64_t ret = -1;
int i;
if (!buf)
return -EFAULT;
if (buf_size > EFUSE_SIZE)
buf_size = EFUSE_SIZE;
memset(buf, 0, buf_size);
for (i = 0; i < buf_size; i += 4) {
ret = cvi_efuse_read_from_shadow(addr + i);
if (ret < 0)
return ret;
if (ret > 0) {
u32 v = ret;
memcpy(buf + i, &v, sizeof(v));
}
}
return buf_size;
}
EXPORT_SYMBOL(cvi_efuse_read_buf);
module_init(cvi_efuse_init);
module_exit(cvi_efuse_exit);
MODULE_AUTHOR("leon.liao@cvitek.com");
MODULE_DESCRIPTION("cv180x efuse driver");
MODULE_LICENSE("GPL");
......@@ -157,6 +157,12 @@ static const struct flash_info cvitek_parts[] = {
{ "FM25Q64", INFO(0xF83217, 0x0, 64 * 1024, 128,
SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_OP)
.fixups = &sr_bit1_qe_fixups },
{ "FM25Q128A", INFO(0xA14018, 0x0, 64 * 1024, 256,
SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_OP)
.fixups = &sr_bit1_qe_fixups },
{ "FM25W128A", INFO(0xA12818, 0x0, 64 * 1024, 256,
SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_OP)
.fixups = &sr_bit1_qe_fixups },
{ "BY25Q128AS", INFO(0x684018, 0x0, 64 * 1024, 256,
SECT_4K | SPI_NOR_DUAL_READ | SPI_NOR_QUAD_OP)
.fixups = &sr_bit1_qe_fixups },
......
......@@ -158,11 +158,11 @@ config CICADA_PHY
help
Currently supports the cis8204
config CV182XA_PHY
tristate "CV182XA PHYs"
config CVITEK_PHY
tristate "CVITEK PHYs"
help
Enable support for RMII PHYs manufactured by CVITEK
Include driver for cv182xa.
Include driver for cvitek.
This is an internal ethernet phy.
And support 100Mbs full duplex.
......
......@@ -48,7 +48,6 @@ obj-$(CONFIG_BCM_CYGNUS_PHY) += bcm-cygnus.o
obj-$(CONFIG_BCM_NET_PHYLIB) += bcm-phy-lib.o
obj-$(CONFIG_BROADCOM_PHY) += broadcom.o
obj-$(CONFIG_CICADA_PHY) += cicada.o
obj-$(CONFIG_CV182XA_PHY) += cv182xa.o
obj-$(CONFIG_CVITEK_PHY) += cvitek.o
obj-$(CONFIG_CORTINA_PHY) += cortina.o
obj-$(CONFIG_DAVICOM_PHY) += davicom.o
......
This diff is collapsed.
......@@ -22,7 +22,7 @@
#include <linux/slab.h>
#include <linux/memblock.h>
#define MAX_RESERVED_REGIONS 64
#define MAX_RESERVED_REGIONS 4
#if defined(CONFIG_ARCH_CVITEK)
struct reserved_mem_size_entry {
......@@ -69,7 +69,7 @@ void __init fdt_reserved_mem_save_node(unsigned long node, const char *uname,
}
rmem->fdt_node = node;
rmem->name = uname;
strncpy(rmem->name, uname, 8);
rmem->base = base;
rmem->size = size;
......
#ifndef __CVI_EFUSE_H__
#define __CVI_EFUSE_H__
#include <linux/types.h>
int64_t cvi_efuse_read_from_shadow(uint32_t addr);
int cvi_efuse_write(uint32_t addr, uint32_t value);
int cvi_efuse_read_buf(u32 addr, void *buf, size_t buf_size);
#endif /* __CVI_EFUSE_H__ */
......@@ -9,7 +9,7 @@ struct of_phandle_args;
struct reserved_mem_ops;
struct reserved_mem {
const char *name;
char name[8];
unsigned long fdt_node;
unsigned long phandle;
const struct reserved_mem_ops *ops;
......
../../../../build/output/cv1800b_wdmb_0008a_spinor/cvi_board_memmap.h
\ No newline at end of file
......@@ -30,14 +30,32 @@ static int cv1835_pdm_codec_init(struct snd_soc_pcm_runtime *rtd)
static struct snd_soc_ops cv1835_pdm_ops = {
.hw_params = cv1835_pdm_hw_params,
};
static struct snd_soc_dai_link_component cv1835_pdm_cpus = {
.name = "4110000.i2s",
.dai_name = "4110000.i2s",
};
static struct snd_soc_dai_link_component cv1835_pdm_codecs = {
.name = "41d0c00.pdm",
.dai_name = "cv1835pdm",
};
static struct snd_soc_dai_link_component cv1835_pdm_platform = {
.name = "4110000.i2s",
.dai_name = "4110000.i2s",
};
static struct snd_soc_dai_link cv1835_pdm_dai = {
.name = "cv1835-i2s-1",
.stream_name = "cv1835-pdm",
.cpu_dai_name = "4110000.i2s",
.codec_dai_name = "cv1835pdm",
.platform_name = "4110000.i2s",
.codec_name = "41d0c00.pdm",
.cpus = &cv1835_pdm_cpus,
.num_cpus = 1,
.codecs = &cv1835_pdm_codecs,
.num_codecs = 1,
.platforms = &cv1835_pdm_platform,
.num_platforms = 1,
.ops = &cv1835_pdm_ops,
.init = cv1835_pdm_codec_init,
.dai_fmt = SND_SOC_DAIFMT_I2S
......@@ -56,7 +74,7 @@ static struct snd_soc_card cv1835_pdm = {
static const struct of_device_id cvi_audio_match_ids[] = {
{
.compatible = "cvitek,cv1835-pdm",
.compatible = "cvitek,cv182x-pdm",
//.data = (void *) &cv1835_pdm_dai,
},
{ }
......
......@@ -223,6 +223,8 @@ static int cv1835pdm_probe(struct platform_device *pdev)
{
struct cvi1835pdm *pdm;
struct resource *res;
struct miscdevice *miscdev;
int ret;
dev_info(&pdev->dev, "%s\n", __func__);
......@@ -236,6 +238,17 @@ static int cv1835pdm_probe(struct platform_device *pdev)
if (IS_ERR(pdm->pdm_base))
return PTR_ERR(pdm->pdm_base);
miscdev = &pdm->miscdev;
miscdev->minor = MISC_DYNAMIC_MINOR;
miscdev->name = "cv1835pdm";
//miscdev->fops = &adc_fops;
miscdev->parent = NULL;
ret = misc_register(miscdev);
if (ret) {
pr_err("pdm: failed to register misc device.\n");
return ret;
}
dev_set_drvdata(&pdev->dev, pdm);
pdm->dev = &pdev->dev;
......
......@@ -11,7 +11,7 @@
#define __CV1835PDM_H__
#include <linux/clk.h>
#include <linux/miscdevice.h>
/* register offset */
#define PDM_EN_REG 0x30
#define PDM_EN 0x1
......@@ -56,6 +56,7 @@ struct cvi1835pdm {
void __iomem *pdm_base;
struct clk *clk;
struct device *dev;
struct miscdevice miscdev;
};
#endif /* __CV1835PDM_H__ */
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment