blob: 01d7849cb2cc1635050ecdc3bcffba9538d520a0 [file] [log] [blame]
/*
* tansen_gti.c - GTI port support for the Tansen Codec.
*
* Copyright (C) 2010-2013 Imagination Technologies
*
* This file is subject to the terms and conditions of the GNU General Public
* License. See the file COPYING in the main directory of this archive
* for more details.
*
*/
#include <linux/export.h>
#include <linux/kernel.h>
#include <linux/delay.h>
#include <linux/io.h>
#include <sound/tansen.h>
#include "tansen_gti.h"
__u32 gti_read(void __iomem *port, unsigned long reg)
{
int i;
unsigned long data_in = 0, data_out = 0, ctrl, bit, ret;
/* Construct the data input to the port */
data_in |= ((reg & GTI_CTRL_REG_ADDR_MASK) << GTI_CTRL_REG_ADDR_SHIFT);
data_in |= ((0 & GTI_CTRL_DATA_MASK) << GTI_CTRL_DATA_SHIFT);
data_in |= ((GTI_CTRL_OP_READ & GTI_CTRL_OP_MASK) << GTI_CTRL_OP_SHIFT);
/* Ensure GTI port is in the right state */
ctrl = GTI_MAKE_CTRL_REG(0, GTI_CLK_LO, GTI_NOT_IN_RESET,
GTI_NOT_TEST_MODE);
iowrite32(ctrl, port);
udelay(1);
/* Clock out & in the bits, starting with the MSB */
for (i = 0; i < 32; i++) {
bit = (data_in & 0x80000000) >> 31;
data_in <<= 1;
ctrl = GTI_MAKE_CTRL_REG(bit, GTI_CLK_HI, GTI_NOT_IN_RESET,
GTI_NOT_TEST_MODE);
iowrite32(ctrl, port);
udelay(1);
ctrl = GTI_MAKE_CTRL_REG(bit, GTI_CLK_LO, GTI_NOT_IN_RESET,
GTI_NOT_TEST_MODE);
iowrite32(ctrl, port);
udelay(1);
bit = ioread32(port + 4);
data_out = (data_out << 1) | bit;
}
ret = (data_out >> GTI_CTRL_DATA_SHIFT) & GTI_CTRL_DATA_MASK;
return ret;
}
EXPORT_SYMBOL_GPL(gti_read);
void gti_write(void __iomem *port, unsigned long reg, unsigned long value)
{
int i;
unsigned long data_in = 0, ctrl, bit;
/* Construct the data input to the port */
data_in |= ((reg & GTI_CTRL_REG_ADDR_MASK) << GTI_CTRL_REG_ADDR_SHIFT);
data_in |= ((value & GTI_CTRL_DATA_MASK) << GTI_CTRL_DATA_SHIFT);
data_in |= ((GTI_CTRL_OP_WRITE & GTI_CTRL_OP_MASK)
<< GTI_CTRL_OP_SHIFT);
/* Ensure GTI port is in the right state */
ctrl = GTI_MAKE_CTRL_REG(0, GTI_CLK_LO, GTI_NOT_IN_RESET,
GTI_NOT_TEST_MODE);
iowrite32(ctrl, port);
udelay(1);
/* Clock out & in the bits, starting with the MSB */
for (i = 0; i < 32; i++) {
bit = (data_in & 0x80000000) >> 31;
data_in <<= 1;
ctrl = GTI_MAKE_CTRL_REG(bit, GTI_CLK_HI, GTI_NOT_IN_RESET,
GTI_NOT_TEST_MODE);
iowrite32(ctrl, port);
udelay(1);
ctrl = GTI_MAKE_CTRL_REG(bit, GTI_CLK_LO, GTI_NOT_IN_RESET,
GTI_NOT_TEST_MODE);
iowrite32(ctrl, port);
udelay(1);
}
}
EXPORT_SYMBOL_GPL(gti_write);
void gti_reset(void __iomem *port, int reset)
{
unsigned long ctrl;
ctrl = GTI_MAKE_CTRL_REG(0, GTI_CLK_LO,
reset ? GTI_IN_RESET : GTI_NOT_IN_RESET,
GTI_NOT_TEST_MODE);
iowrite32(ctrl, port);
}
EXPORT_SYMBOL_GPL(gti_reset);