/* asm_inline_gcc.h - ARC inline assembler and macros for public functions */

/*
 * Copyright (c) 2015 Intel Corporation.
 *
 * SPDX-License-Identifier: Apache-2.0
 */

#ifndef __ASM_INLINE_GCC_H__
#define __ASM_INLINE_GCC_H__

#ifdef __cplusplus
extern "C" {
#endif

#ifndef _ASMLANGUAGE

#include <sys_io.h>
#include <arch/arc/v2/aux_regs.h>

#include <stdint.h>
#include <stddef.h>

/* Implementation of sys_io.h's documented functions */

static ALWAYS_INLINE
	void sys_out8(uint8_t data, io_port_t port)
{
	_arc_v2_aux_reg_write(port, data);
}

static ALWAYS_INLINE
	uint8_t sys_in8(io_port_t port)
{
	return (uint8_t)(_arc_v2_aux_reg_read(port) & 0x000000ff);
}

static ALWAYS_INLINE
	void sys_out16(uint16_t data, io_port_t port)
{
	_arc_v2_aux_reg_write(port, data);
}

static ALWAYS_INLINE
	uint16_t sys_in16(io_port_t port)
{
	return (uint16_t)(_arc_v2_aux_reg_read(port) & 0x0000ffff);
}

static ALWAYS_INLINE
	void sys_out32(uint32_t data, io_port_t port)
{
	_arc_v2_aux_reg_write(port, data);
}

static ALWAYS_INLINE
	uint32_t sys_in32(io_port_t port)
{
	return _arc_v2_aux_reg_read(port);
}

static ALWAYS_INLINE
	void sys_io_set_bit(io_port_t port, unsigned int bit)
{
	uint32_t reg = 0;

	__asm__ volatile("lr	%1, [%0]\n"
			 "bset	%1, %1, %2\n"
			 "sr	%1, [%0];\n\t"
			 :
			 : "ir" (port),
			   "r" (reg), "Mr" (bit)
			 : "memory", "cc");
}

static ALWAYS_INLINE
	void sys_io_clear_bit(io_port_t port, unsigned int bit)
{
	uint32_t reg = 0;

	__asm__ volatile("lr	%1, [%0]\n"
			 "bclr	%1, %1, %2\n"
			 "sr	%1, [%0];\n\t"
			 :
			 : "ir" (port),
			   "r" (reg), "Mr" (bit)
			 : "memory", "cc");
}

static ALWAYS_INLINE
	int sys_io_test_bit(io_port_t port, unsigned int bit)
{
	uint32_t status = _ARC_V2_STATUS32;
	uint32_t reg = 0;
	uint32_t ret;

	__asm__ volatile("lr	%2, [%1]\n"
			 "btst	%2, %3\n"
			 "lr	%0, [%4];\n\t"
			 : "=r" (ret)
			 : "ir" (port),
			   "r" (reg), "Mr" (bit), "i" (status)
			 : "memory", "cc");

	return !(ret & _ARC_V2_STATUS32_Z);
}

static ALWAYS_INLINE
	int sys_io_test_and_set_bit(io_port_t port, unsigned int bit)
{
	int ret;

	ret = sys_io_test_bit(port, bit);
	sys_io_set_bit(port, bit);

	return ret;
}

static ALWAYS_INLINE
	int sys_io_test_and_clear_bit(io_port_t port, unsigned int bit)
{
	int ret;

	ret = sys_io_test_bit(port, bit);
	sys_io_clear_bit(port, bit);

	return ret;
}

static ALWAYS_INLINE
	void sys_write8(uint8_t data, mm_reg_t addr)
{
	__asm__ volatile("stb%U1	%0, %1;\n\t"
			 :
			 : "r" (data), "m" (*(volatile uint8_t *) addr)
			 : "memory");
}

static ALWAYS_INLINE
	uint8_t sys_read8(mm_reg_t addr)
{
	uint8_t ret;

	__asm__ volatile("ldb%U1	%0, %1;\n\t"
			 : "=r" (ret)
			 : "m" (*(volatile uint8_t *) addr)
			 : "memory");

	return ret;
}

static ALWAYS_INLINE
	void sys_write16(uint16_t data, mm_reg_t addr)
{
	__asm__ volatile("sth%U1	%0, %1;\n\t"
			 :
			 : "r" (data), "m" (*(volatile uint16_t *) addr)
			 : "memory");
}

static ALWAYS_INLINE
	uint16_t sys_read16(mm_reg_t addr)
{
	uint16_t ret;

	__asm__ volatile("ldh%U1	%0, %1;\n\t"
			 : "=r" (ret)
			 : "m" (*(volatile uint16_t *) addr)
			 : "memory");

	return ret;
}

static ALWAYS_INLINE
	void sys_write32(uint32_t data, mm_reg_t addr)
{
	__asm__ volatile("st%U1	%0, %1;\n\t"
			 :
			 : "r" (data), "m" (*(volatile uint32_t *) addr)
			 : "memory");
}

static ALWAYS_INLINE
	uint32_t sys_read32(mm_reg_t addr)
{
	uint32_t ret;

	__asm__ volatile("ld%U1	%0, %1;\n\t"
			 : "=r" (ret)
			 : "m" (*(volatile uint32_t *) addr)
			 : "memory");

	return ret;
}

static ALWAYS_INLINE
	void sys_set_bit(mem_addr_t addr, unsigned int bit)
{
	uint32_t reg = 0;

	__asm__ volatile("ld	%1, %0\n"
			 "bset	%1, %1, %2\n"
			 "st	%1, %0;\n\t"
			 : "+m" (*(volatile uint32_t *) addr)
			 : "r" (reg), "Mr" (bit)
			 : "memory", "cc");
}

static ALWAYS_INLINE
	void sys_clear_bit(mem_addr_t addr, unsigned int bit)
{
	uint32_t reg = 0;

	__asm__ volatile("ld	%1, %0\n"
			 "bclr	%1, %1, %2\n"
			 "st	%1, %0;\n\t"
			 : "+m" (*(volatile uint32_t *) addr)
			 : "r" (reg), "Mr" (bit)
			 : "memory", "cc");
}

static ALWAYS_INLINE
	int sys_test_bit(mem_addr_t addr, unsigned int bit)
{
	uint32_t status = _ARC_V2_STATUS32;
	uint32_t reg = 0;
	uint32_t ret;

	__asm__ volatile("ld	%2, %1\n"
			 "btst	%2, %3\n"
			 "lr	%0, [%4];\n\t"
			 : "=r" (ret)
			 : "m" (*(volatile uint32_t *) addr),
			   "r" (reg), "Mr" (bit), "i" (status)
			 : "memory", "cc");

	return !(ret & _ARC_V2_STATUS32_Z);
}

static ALWAYS_INLINE
	int sys_test_and_set_bit(mem_addr_t addr, unsigned int bit)
{
	int ret;

	ret = sys_test_bit(addr, bit);
	sys_set_bit(addr, bit);

	return ret;
}

static ALWAYS_INLINE
	int sys_test_and_clear_bit(mem_addr_t addr, unsigned int bit)
{
	int ret;

	ret = sys_test_bit(addr, bit);
	sys_clear_bit(addr, bit);

	return ret;
}

static ALWAYS_INLINE
	void sys_bitfield_set_bit(mem_addr_t addr, unsigned int bit)
{
	/* Doing memory offsets in terms of 32-bit values to prevent
	 * alignment issues
	 */
	sys_set_bit(addr + ((bit >> 5) << 2), bit & 0x1F);
}

static ALWAYS_INLINE
	void sys_bitfield_clear_bit(mem_addr_t addr, unsigned int bit)
{
	sys_clear_bit(addr + ((bit >> 5) << 2), bit & 0x1F);
}

static ALWAYS_INLINE
	int sys_bitfield_test_bit(mem_addr_t addr, unsigned int bit)
{
	return sys_test_bit(addr + ((bit >> 5) << 2), bit & 0x1F);
}


static ALWAYS_INLINE
	int sys_bitfield_test_and_set_bit(mem_addr_t addr, unsigned int bit)
{
	int ret;

	ret = sys_bitfield_test_bit(addr, bit);
	sys_bitfield_set_bit(addr, bit);

	return ret;
}

static ALWAYS_INLINE
	int sys_bitfield_test_and_clear_bit(mem_addr_t addr, unsigned int bit)
{
	int ret;

	ret = sys_bitfield_test_bit(addr, bit);
	sys_bitfield_clear_bit(addr, bit);

	return ret;
}

#endif /* _ASMLANGUAGE */

#ifdef __cplusplus
}
#endif

#endif /* __ASM_INLINE_GCC_H__ */
