mirror of
https://github.com/Telecominfraproject/OpenCellular.git
synced 2025-12-27 18:25:05 +00:00
ite: Add initial support for ITE IT8380 chip
Initial support for the ITE IT8380 chip with the following peripherals : - 8250-like UART module. - HW timer (with a 128-us tick period). - GPIO with pins initialization and edge interrupt support. other functions are stubbed. - Clock : basic fixed frequency setup only. It also add the dev board configuration as a test vehicle. Signed-off-by: Alec Berg <alecaberg@chromium.org> Signed-off-by: Vincent Palatin <vpalatin@chromium.org> BRANCH=none BUG=chrome-os-partner:23575 TEST=make BOARD=it8380dev on IT8380 dev board, use the EC serial console, use gettime from console. Change-Id: Id4bf37d1beb21d1a4bee404c9a0bc500025fe787 Reviewed-on: https://chromium-review.googlesource.com/175481 Reviewed-by: Vincent Palatin <vpalatin@chromium.org> Commit-Queue: Alec Berg <alecaberg@chromium.org> Tested-by: Alec Berg <alecaberg@chromium.org>
This commit is contained in:
committed by
chrome-internal-fetch
parent
375e75de27
commit
4cf4fcf1cb
@@ -12,7 +12,10 @@ build-utils := $(foreach u,$(build-util-bin),$(out)/util/$(u))
|
||||
host-utils := $(foreach u,$(host-util-bin),$(out)/util/$(u))
|
||||
build-srcs := $(foreach u,$(build-util-bin),$(sort $($(u)-objs:%.o=util/%.c) util/$(u).c))
|
||||
host-srcs := $(foreach u,$(host-util-bin),$(sort $($(u)-objs:%.o=util/%.c) util/$(u).c))
|
||||
boards := $(filter-out host,$(subst board/,,$(wildcard board/*)))
|
||||
|
||||
# Don't do a build test on the following boards:
|
||||
skip_boards = host it8380dev
|
||||
boards := $(filter-out $(skip_boards),$(subst board/,,$(wildcard board/*)))
|
||||
|
||||
# Create output directories if necessary
|
||||
_dir_create := $(foreach d,$(dirs),$(shell [ -d $(out)/$(d) ] || \
|
||||
|
||||
106
board/it8380dev/board.c
Normal file
106
board/it8380dev/board.c
Normal file
@@ -0,0 +1,106 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
/* IT8380 development board configuration */
|
||||
|
||||
#include "common.h"
|
||||
#include "console.h"
|
||||
#include "gpio.h"
|
||||
#include "hooks.h"
|
||||
#include "registers.h"
|
||||
#include "task.h"
|
||||
#include "util.h"
|
||||
|
||||
/* Test GPIO interrupt function that toggles one LED. */
|
||||
void test_interrupt(enum gpio_signal signal)
|
||||
{
|
||||
static int busy_state;
|
||||
|
||||
/* toggle LED */
|
||||
busy_state = !busy_state;
|
||||
gpio_set_level(GPIO_BUSY_LED, busy_state);
|
||||
}
|
||||
|
||||
/* GPIO signal list. Must match order from enum gpio_signal. */
|
||||
const struct gpio_info gpio_list[] = {
|
||||
{"H_LED0", GPIO_A, (1<<0), GPIO_ODR_HIGH},
|
||||
{"H_LED1", GPIO_A, (1<<1), GPIO_ODR_HIGH},
|
||||
{"H_LED2", GPIO_A, (1<<2), GPIO_ODR_HIGH},
|
||||
{"H_LED3", GPIO_A, (1<<3), GPIO_ODR_HIGH},
|
||||
{"H_LED4", GPIO_A, (1<<4), GPIO_ODR_HIGH},
|
||||
{"H_LED5", GPIO_A, (1<<5), GPIO_ODR_HIGH},
|
||||
{"H_LED6", GPIO_A, (1<<6), GPIO_ODR_HIGH},
|
||||
{"L_LED0", GPIO_I, (1<<0), GPIO_ODR_HIGH},
|
||||
{"L_LED1", GPIO_I, (1<<1), GPIO_ODR_HIGH},
|
||||
{"L_LED2", GPIO_I, (1<<2), GPIO_ODR_HIGH},
|
||||
{"L_LED3", GPIO_I, (1<<3), GPIO_ODR_HIGH},
|
||||
{"L_LED4", GPIO_I, (1<<4), GPIO_ODR_HIGH},
|
||||
{"L_LED5", GPIO_I, (1<<5), GPIO_ODR_HIGH},
|
||||
{"L_LED6", GPIO_I, (1<<6), GPIO_ODR_HIGH},
|
||||
{"BUSY_LED", GPIO_J, (1<<0), GPIO_OUT_LOW},
|
||||
{"GOOD_LED", GPIO_J, (1<<1), GPIO_OUT_HIGH},
|
||||
{"FAIL_LED", GPIO_J, (1<<2), GPIO_OUT_LOW},
|
||||
{"SW0", GPIO_E, (1<<0), GPIO_INPUT},
|
||||
{"SW1", GPIO_E, (1<<1), GPIO_INPUT | GPIO_PULL_DOWN},
|
||||
{"SW2", GPIO_E, (1<<2), GPIO_INPUT | GPIO_PULL_DOWN},
|
||||
{"SW3", GPIO_E, (1<<3), GPIO_INPUT | GPIO_PULL_DOWN},
|
||||
{"START_SW", GPIO_E, (1<<4), GPIO_INT_FALLING, test_interrupt},
|
||||
/* Unimplemented signals which we need to emulate for now */
|
||||
GPIO_SIGNAL_NOT_IMPLEMENTED("ENTERING_RW"),
|
||||
};
|
||||
BUILD_ASSERT(ARRAY_SIZE(gpio_list) == GPIO_COUNT);
|
||||
|
||||
/* Pins with alternate functions */
|
||||
const struct gpio_alt_func gpio_alt_funcs[] = {
|
||||
{GPIO_B, 0x03, 1, MODULE_UART, GPIO_PULL_UP}, /* UART0 */
|
||||
};
|
||||
const int gpio_alt_funcs_count = ARRAY_SIZE(gpio_alt_funcs);
|
||||
|
||||
/* Initialize board. */
|
||||
static void board_init(void)
|
||||
{
|
||||
gpio_enable_interrupt(GPIO_START_SW);
|
||||
}
|
||||
DECLARE_HOOK(HOOK_INIT, board_init, HOOK_PRIO_DEFAULT);
|
||||
|
||||
/*****************************************************************************/
|
||||
/* Console commands */
|
||||
|
||||
void display_7seg(uint8_t val)
|
||||
{
|
||||
int i;
|
||||
static const uint8_t digits[16] = {
|
||||
0xc0, 0xf9, 0xa8, 0xb0,
|
||||
0x99, 0x92, 0x82, 0xf8,
|
||||
0x80, 0x98, 0x88, 0x83,
|
||||
0xc6, 0xa1, 0x86, 0x8e,
|
||||
};
|
||||
|
||||
for (i = 0; i < 7; i++)
|
||||
gpio_set_level(GPIO_H_LED0 + i, digits[val >> 4] & (1 << i));
|
||||
for (i = 0; i < 7; i++)
|
||||
gpio_set_level(GPIO_L_LED0 + i, digits[val & 0xf] & (1 << i));
|
||||
}
|
||||
|
||||
static int command_7seg(int argc, char **argv)
|
||||
{
|
||||
uint8_t val;
|
||||
char *e;
|
||||
|
||||
if (argc != 2)
|
||||
return EC_ERROR_PARAM_COUNT;
|
||||
|
||||
val = strtoi(argv[1], &e, 16);
|
||||
if (*e)
|
||||
return EC_ERROR_PARAM1;
|
||||
|
||||
ccprintf("display 0x%02x\n", val);
|
||||
display_7seg(val);
|
||||
|
||||
return EC_SUCCESS;
|
||||
}
|
||||
DECLARE_CONSOLE_COMMAND(seg7, command_7seg,
|
||||
"<hex>",
|
||||
"Print 8-bit value on 7-segment display",
|
||||
NULL);
|
||||
47
board/it8380dev/board.h
Normal file
47
board/it8380dev/board.h
Normal file
@@ -0,0 +1,47 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
|
||||
/* IT8380 development board configuration */
|
||||
|
||||
#ifndef __BOARD_H
|
||||
#define __BOARD_H
|
||||
|
||||
#ifndef __ASSEMBLER__
|
||||
|
||||
/* stubbed features */
|
||||
#undef CONFIG_LID_SWITCH
|
||||
|
||||
enum gpio_signal {
|
||||
GPIO_H_LED0,
|
||||
GPIO_H_LED1,
|
||||
GPIO_H_LED2,
|
||||
GPIO_H_LED3,
|
||||
GPIO_H_LED4,
|
||||
GPIO_H_LED5,
|
||||
GPIO_H_LED6,
|
||||
GPIO_L_LED0,
|
||||
GPIO_L_LED1,
|
||||
GPIO_L_LED2,
|
||||
GPIO_L_LED3,
|
||||
GPIO_L_LED4,
|
||||
GPIO_L_LED5,
|
||||
GPIO_L_LED6,
|
||||
GPIO_BUSY_LED,
|
||||
GPIO_GOOD_LED,
|
||||
GPIO_FAIL_LED,
|
||||
GPIO_SW1,
|
||||
GPIO_SW2,
|
||||
GPIO_SW3,
|
||||
GPIO_SW4,
|
||||
GPIO_START_SW,
|
||||
/* Unimplemented GPIOs */
|
||||
GPIO_ENTERING_RW,
|
||||
|
||||
/* Number of GPIOs; not an actual GPIO */
|
||||
GPIO_COUNT
|
||||
};
|
||||
|
||||
#endif /* !__ASSEMBLER__ */
|
||||
#endif /* __BOARD_H */
|
||||
11
board/it8380dev/build.mk
Normal file
11
board/it8380dev/build.mk
Normal file
@@ -0,0 +1,11 @@
|
||||
# -*- makefile -*-
|
||||
# Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
# Use of this source code is governed by a BSD-style license that can be
|
||||
# found in the LICENSE file.
|
||||
#
|
||||
# Board specific files build
|
||||
|
||||
# the IC is ITE 8380
|
||||
CHIP:=it83xx
|
||||
|
||||
board-y=board.o
|
||||
21
board/it8380dev/ec.tasklist
Normal file
21
board/it8380dev/ec.tasklist
Normal file
@@ -0,0 +1,21 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
|
||||
/**
|
||||
* List of enabled tasks in the priority order
|
||||
*
|
||||
* The first one has the lowest priority.
|
||||
*
|
||||
* For each task, use the macro TASK_ALWAYS(n, r, d, s) for base tasks and
|
||||
* TASK_NOTEST(n, r, d, s) for tasks that can be excluded in test binaries,
|
||||
* where :
|
||||
* 'n' in the name of the task
|
||||
* 'r' in the main routine of the task
|
||||
* 'd' in an opaque parameter passed to the routine at startup
|
||||
* 's' is the stack size in bytes; must be a multiple of 8
|
||||
*/
|
||||
#define CONFIG_TASK_LIST \
|
||||
TASK_ALWAYS(HOOKS, hook_task, NULL, TASK_STACK_SIZE) \
|
||||
TASK_ALWAYS(CONSOLE, console_task, NULL, TASK_STACK_SIZE)
|
||||
16
chip/it83xx/build.mk
Normal file
16
chip/it83xx/build.mk
Normal file
@@ -0,0 +1,16 @@
|
||||
# -*- makefile -*-
|
||||
# Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
# Use of this source code is governed by a BSD-style license that can be
|
||||
# found in the LICENSE file.
|
||||
#
|
||||
# IT83xx chip specific files build
|
||||
#
|
||||
|
||||
# IT83xx SoC family has an Andes N801 core.
|
||||
CORE:=nds32
|
||||
|
||||
# Required chip modules
|
||||
chip-y=hwtimer.o uart.o gpio.o system.o jtag.o clock.o irq.o
|
||||
|
||||
# Optional chip modules
|
||||
chip-$(CONFIG_WATCHDOG)+=watchdog.o
|
||||
92
chip/it83xx/clock.c
Normal file
92
chip/it83xx/clock.c
Normal file
@@ -0,0 +1,92 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
|
||||
/* Clocks and power management settings */
|
||||
|
||||
#include "clock.h"
|
||||
#include "common.h"
|
||||
#include "console.h"
|
||||
#include "registers.h"
|
||||
#include "task.h"
|
||||
#include "timer.h"
|
||||
#include "util.h"
|
||||
|
||||
/* Console output macros. */
|
||||
#define CPUTS(outstr) cputs(CC_CLOCK, outstr)
|
||||
#define CPRINTF(format, args...) cprintf(CC_CLOCK, format, ## args)
|
||||
|
||||
static int freq;
|
||||
|
||||
struct clock_gate_ctrl {
|
||||
volatile uint8_t *reg;
|
||||
uint8_t mask;
|
||||
};
|
||||
|
||||
void clock_init(void)
|
||||
{
|
||||
#if PLL_CLOCK == 48000000
|
||||
/* Set PLL frequency to 48MHz. */
|
||||
IT83XX_ECPM_PLLFREQR = 0x04;
|
||||
freq = PLL_CLOCK;
|
||||
#else
|
||||
#error "Support only for PLL clock speed of 48MHz."
|
||||
#endif
|
||||
|
||||
/* Set EC Clock Frequency to PLL frequency. */
|
||||
IT83XX_ECPM_SCDCR3 &= 0xf0;
|
||||
|
||||
/* Turn off auto clock gating. */
|
||||
IT83XX_ECPM_AUTOCG = 0x00;
|
||||
}
|
||||
|
||||
int clock_get_freq(void)
|
||||
{
|
||||
return freq;
|
||||
}
|
||||
|
||||
/**
|
||||
* Enable clock to specified peripheral
|
||||
*
|
||||
* @param offset Should be element of clock_gate_offsets enum.
|
||||
* Bits 8-15 specify the ECPM offset of the specific clock reg.
|
||||
* Bits 0-7 specify the mask for the clock register.
|
||||
* @param mask Unused
|
||||
* @param mode Unused
|
||||
*/
|
||||
void clock_enable_peripheral(uint32_t offset, uint32_t mask, uint32_t mode)
|
||||
{
|
||||
volatile uint8_t *reg = (volatile uint8_t *)
|
||||
(IT83XX_ECPM_BASE + (offset >> 8));
|
||||
uint8_t reg_mask = offset & 0xff;
|
||||
|
||||
/*
|
||||
* Note: CGCTRL3R, bit 6, must always write 1, but since there is no
|
||||
* offset argument that addresses this bit, then we are guaranteed
|
||||
* that this line will write a 1 to that bit.
|
||||
*/
|
||||
*reg &= ~reg_mask;
|
||||
}
|
||||
|
||||
/**
|
||||
* Disable clock to specified peripheral
|
||||
*
|
||||
* @param offset Should be element of clock_gate_offsets enum.
|
||||
* Bits 8-15 specify the ECPM offset of the specific clock reg.
|
||||
* Bits 0-7 specify the mask for the clock register.
|
||||
* @param mask Unused
|
||||
* @param mode Unused
|
||||
*/
|
||||
void clock_disable_peripheral(uint32_t offset, uint32_t mask, uint32_t mode)
|
||||
{
|
||||
volatile uint8_t *reg = (volatile uint8_t *)
|
||||
(IT83XX_ECPM_BASE + (offset >> 8));
|
||||
uint8_t reg_mask = offset & 0xff;
|
||||
uint8_t tmp_mask = 0;
|
||||
|
||||
/* CGCTRL3R, bit 6, must always write a 1. */
|
||||
tmp_mask |= ((offset >> 8) == IT83XX_ECPM_CGCTRL3R_OFF) ? 0x40 : 0x00;
|
||||
|
||||
*reg |= reg_mask | tmp_mask;
|
||||
}
|
||||
106
chip/it83xx/config_chip.h
Normal file
106
chip/it83xx/config_chip.h
Normal file
@@ -0,0 +1,106 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
|
||||
#ifndef __CROS_EC_CONFIG_CHIP_H
|
||||
#define __CROS_EC_CONFIG_CHIP_H
|
||||
|
||||
/* CPU core BFD configuration */
|
||||
#include "core/nds32/config_core.h"
|
||||
|
||||
/* Number of IRQ vectors on the IVIC */
|
||||
#define CONFIG_IRQ_COUNT 16
|
||||
|
||||
/* Interval between HOOK_TICK notifications */
|
||||
#define HOOK_TICK_INTERVAL (500 * MSEC)
|
||||
|
||||
/* Maximum number of deferrable functions */
|
||||
#define DEFERRABLE_MAX_COUNT 8
|
||||
|
||||
/* Default PLL frequency. */
|
||||
#define PLL_CLOCK 48000000
|
||||
|
||||
/****************************************************************************/
|
||||
/* Memory mapping */
|
||||
|
||||
#define CONFIG_RAM_BASE 0x00080000
|
||||
#define CONFIG_RAM_SIZE 0x00004000
|
||||
|
||||
/* System stack size */
|
||||
#define CONFIG_STACK_SIZE 1024
|
||||
|
||||
/* non-standard task stack sizes */
|
||||
#define IDLE_TASK_STACK_SIZE 512
|
||||
#define LARGER_TASK_STACK_SIZE 640
|
||||
|
||||
/* Default task stack size */
|
||||
#define TASK_STACK_SIZE 512
|
||||
|
||||
#define CONFIG_FLASH_BASE 0x00000000
|
||||
#define CONFIG_FLASH_BANK_SIZE 0x00000800 /* protect bank size */
|
||||
#define CONFIG_FLASH_ERASE_SIZE 0x00000400 /* erase bank size */
|
||||
#define CONFIG_FLASH_WRITE_SIZE 0x00000004 /* minimum write size */
|
||||
|
||||
/* Ideal flash write size fills the 32-entry flash write buffer */
|
||||
#define CONFIG_FLASH_WRITE_IDEAL_SIZE (32 * 4)
|
||||
|
||||
/* This is the physical size of the flash on the chip. We'll reserve one bank
|
||||
* in order to emulate per-bank write-protection UNTIL REBOOT. The hardware
|
||||
* doesn't support a write-protect pin, and if we make the write-protection
|
||||
* permanent, it can't be undone easily enough to support RMA. */
|
||||
#define CONFIG_FLASH_PHYSICAL_SIZE 0x00020000
|
||||
|
||||
/****************************************************************************/
|
||||
/* Define our flash layout. */
|
||||
|
||||
/* Size of one firmware image in flash */
|
||||
#ifndef CONFIG_FW_IMAGE_SIZE
|
||||
#define CONFIG_FW_IMAGE_SIZE (CONFIG_FLASH_PHYSICAL_SIZE / 2)
|
||||
#endif
|
||||
|
||||
/* RO firmware must start at beginning of flash */
|
||||
#define CONFIG_FW_RO_OFF 0
|
||||
|
||||
/*
|
||||
* The EC uses the one bank of flash to emulate a SPI-like write protect
|
||||
* register with persistent state.
|
||||
*/
|
||||
#define CONFIG_FW_PSTATE_SIZE CONFIG_FLASH_BANK_SIZE
|
||||
|
||||
#ifdef CONFIG_PSTATE_AT_END
|
||||
/* PSTATE is at end of flash */
|
||||
#define CONFIG_FW_RO_SIZE CONFIG_FW_IMAGE_SIZE
|
||||
#define CONFIG_FW_PSTATE_OFF (CONFIG_FLASH_PHYSICAL_SIZE \
|
||||
- CONFIG_FW_PSTATE_SIZE)
|
||||
/* Don't claim PSTATE is part of flash */
|
||||
#define CONFIG_FLASH_SIZE CONFIG_FW_PSTATE_OFF
|
||||
|
||||
#else
|
||||
/* PSTATE immediately follows RO, in the first half of flash */
|
||||
#define CONFIG_FW_RO_SIZE (CONFIG_FW_IMAGE_SIZE \
|
||||
- CONFIG_FW_PSTATE_SIZE)
|
||||
#define CONFIG_FW_PSTATE_OFF CONFIG_FW_RO_SIZE
|
||||
#define CONFIG_FLASH_SIZE CONFIG_FLASH_PHYSICAL_SIZE
|
||||
#endif
|
||||
|
||||
/* Either way, RW firmware is one firmware image offset from the start */
|
||||
#define CONFIG_FW_RW_OFF CONFIG_FW_IMAGE_SIZE
|
||||
#define CONFIG_FW_RW_SIZE CONFIG_FW_IMAGE_SIZE
|
||||
|
||||
/* TODO: why 2 sets of configs with the same numbers? */
|
||||
#define CONFIG_FW_WP_RO_OFF CONFIG_FW_RO_OFF
|
||||
#define CONFIG_FW_WP_RO_SIZE CONFIG_FW_RO_SIZE
|
||||
|
||||
/****************************************************************************/
|
||||
/* Customize the build */
|
||||
|
||||
/* Use hardware specific udelay() for this chip */
|
||||
#define CONFIG_HW_SPECIFIC_UDELAY
|
||||
|
||||
/* Optional features present on this chip */
|
||||
#undef CONFIG_I2C
|
||||
#undef CONFIG_FLASH
|
||||
#undef CONFIG_WATCHDOG
|
||||
|
||||
#endif /* __CROS_EC_CONFIG_CHIP_H */
|
||||
381
chip/it83xx/gpio.c
Normal file
381
chip/it83xx/gpio.c
Normal file
@@ -0,0 +1,381 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
|
||||
/* GPIO module for Chrome EC */
|
||||
|
||||
#include "clock.h"
|
||||
#include "common.h"
|
||||
#include "gpio.h"
|
||||
#include "hooks.h"
|
||||
#include "registers.h"
|
||||
#include "switch.h"
|
||||
#include "task.h"
|
||||
#include "timer.h"
|
||||
#include "util.h"
|
||||
|
||||
/*
|
||||
* Converts port (ie GPIO A) to base address offset of the control register
|
||||
* (GPCRx0) for that port.
|
||||
*/
|
||||
#define CTRL_BASE(port) ((port)*8 + 8)
|
||||
|
||||
/**
|
||||
* Convert wake-up controller (WUC) group to the corresponding wake-up edge
|
||||
* sense register (WUESR). Return pointer to the register.
|
||||
*
|
||||
* @param grp WUC group.
|
||||
*
|
||||
* @return Pointer to corresponding WUESR register.
|
||||
*/
|
||||
static volatile uint8_t *wuesr(uint8_t grp)
|
||||
{
|
||||
/*
|
||||
* From WUESR1-WUESR4, the address increases by ones. From WUESR6 on
|
||||
* the address increases by fours.
|
||||
*/
|
||||
return (grp <= 4) ?
|
||||
(volatile uint8_t *)(IT83XX_WUC_WUESR1 + grp-1) :
|
||||
(volatile uint8_t *)(IT83XX_WUC_WUESR6 + 4*(grp-6));
|
||||
}
|
||||
|
||||
/**
|
||||
* Convert wake-up controller (WUC) group to the corresponding wake-up edge
|
||||
* mode register (WUEMR). Return pointer to the register.
|
||||
*
|
||||
* @param grp WUC group.
|
||||
*
|
||||
* @return Pointer to corresponding WUEMR register.
|
||||
*/
|
||||
static volatile uint8_t *wuemr(uint8_t grp)
|
||||
{
|
||||
/*
|
||||
* From WUEMR1-WUEMR4, the address increases by ones. From WUEMR6 on
|
||||
* the address increases by fours.
|
||||
*/
|
||||
return (grp <= 4) ?
|
||||
(volatile uint8_t *)(IT83XX_WUC_WUEMR1 + grp-1) :
|
||||
(volatile uint8_t *)(IT83XX_WUC_WUEMR6 + 4*(grp-6));
|
||||
}
|
||||
|
||||
/*
|
||||
* Array to store the corresponding GPIO port and mask, and WUC group and mask
|
||||
* for each WKO interrupt. This allows GPIO interrupts coming in through WKO
|
||||
* to easily identify which pin caused the interrupt.
|
||||
* Note: Using designated initializers here in addition to using the array size
|
||||
* assert because many rows are purposely skipped. Not all IRQs are WKO IRQs,
|
||||
* so the IRQ index skips around. But, we still want the entire array to take
|
||||
* up the size of the total number of IRQs because the index to the array could
|
||||
* be any IRQ number.
|
||||
*/
|
||||
static const struct {
|
||||
uint8_t gpio_port;
|
||||
uint8_t gpio_mask;
|
||||
uint8_t wuc_group;
|
||||
uint8_t wuc_mask;
|
||||
} gpio_irqs[] = {
|
||||
/* irq gpio_port,gpio_mask,wuc_group,wuc_mask */
|
||||
[IT83XX_IRQ_WKO20] = {GPIO_D, (1<<0), 2, (1<<0)},
|
||||
[IT83XX_IRQ_WKO21] = {GPIO_D, (1<<1), 2, (1<<1)},
|
||||
[IT83XX_IRQ_WKO22] = {GPIO_C, (1<<4), 2, (1<<2)},
|
||||
[IT83XX_IRQ_WKO23] = {GPIO_C, (1<<6), 2, (1<<3)},
|
||||
[IT83XX_IRQ_WKO24] = {GPIO_D, (1<<2), 2, (1<<4)},
|
||||
/* E4 is also on WKO114: this one might be a documentation error ? */
|
||||
/* [IT83XX_IRQ_WKO25] = {GPIO_E, (1<<4), 2, (1<<5)},*/
|
||||
[IT83XX_IRQ_WKO60] = {GPIO_H, (1<<0), 6, (1<<0)},
|
||||
[IT83XX_IRQ_WKO61] = {GPIO_H, (1<<1), 6, (1<<1)},
|
||||
[IT83XX_IRQ_WKO62] = {GPIO_H, (1<<2), 6, (1<<2)},
|
||||
[IT83XX_IRQ_WKO63] = {GPIO_H, (1<<3), 6, (1<<3)},
|
||||
[IT83XX_IRQ_WKO64] = {GPIO_F, (1<<4), 6, (1<<4)},
|
||||
[IT83XX_IRQ_WKO65] = {GPIO_F, (1<<5), 6, (1<<5)},
|
||||
[IT83XX_IRQ_WKO65] = {GPIO_F, (1<<6), 6, (1<<6)},
|
||||
[IT83XX_IRQ_WKO67] = {GPIO_F, (1<<7), 6, (1<<7)},
|
||||
[IT83XX_IRQ_WKO70] = {GPIO_E, (1<<0), 7, (1<<0)},
|
||||
[IT83XX_IRQ_WKO71] = {GPIO_E, (1<<1), 7, (1<<1)},
|
||||
[IT83XX_IRQ_WKO72] = {GPIO_E, (1<<2), 7, (1<<2)},
|
||||
[IT83XX_IRQ_WKO73] = {GPIO_E, (1<<3), 7, (1<<3)},
|
||||
[IT83XX_IRQ_WKO74] = {GPIO_I, (1<<4), 7, (1<<4)},
|
||||
[IT83XX_IRQ_WKO75] = {GPIO_I, (1<<5), 7, (1<<5)},
|
||||
[IT83XX_IRQ_WKO76] = {GPIO_I, (1<<6), 7, (1<<6)},
|
||||
[IT83XX_IRQ_WKO77] = {GPIO_I, (1<<7), 7, (1<<7)},
|
||||
[IT83XX_IRQ_WKO80] = {GPIO_A, (1<<3), 8, (1<<0)},
|
||||
[IT83XX_IRQ_WKO81] = {GPIO_A, (1<<4), 8, (1<<1)},
|
||||
[IT83XX_IRQ_WKO82] = {GPIO_A, (1<<5), 8, (1<<2)},
|
||||
[IT83XX_IRQ_WKO83] = {GPIO_A, (1<<6), 8, (1<<3)},
|
||||
[IT83XX_IRQ_WKO84] = {GPIO_B, (1<<2), 8, (1<<4)},
|
||||
[IT83XX_IRQ_WKO85] = {GPIO_C, (1<<0), 8, (1<<5)},
|
||||
[IT83XX_IRQ_WKO86] = {GPIO_C, (1<<7), 8, (1<<6)},
|
||||
[IT83XX_IRQ_WKO87] = {GPIO_D, (1<<7), 8, (1<<7)},
|
||||
[IT83XX_IRQ_WKO88] = {GPIO_H, (1<<4), 9, (1<<0)},
|
||||
[IT83XX_IRQ_WKO89] = {GPIO_H, (1<<5), 9, (1<<1)},
|
||||
[IT83XX_IRQ_WKO90] = {GPIO_H, (1<<6), 9, (1<<2)},
|
||||
[IT83XX_IRQ_WKO91] = {GPIO_A, (1<<0), 9, (1<<3)},
|
||||
[IT83XX_IRQ_WKO92] = {GPIO_A, (1<<1), 9, (1<<4)},
|
||||
[IT83XX_IRQ_WKO93] = {GPIO_A, (1<<2), 9, (1<<5)},
|
||||
[IT83XX_IRQ_WKO94] = {GPIO_B, (1<<4), 9, (1<<6)},
|
||||
[IT83XX_IRQ_WKO95] = {GPIO_C, (1<<2), 9, (1<<7)},
|
||||
[IT83XX_IRQ_WKO96] = {GPIO_F, (1<<0), 10, (1<<0)},
|
||||
[IT83XX_IRQ_WKO97] = {GPIO_F, (1<<1), 10, (1<<1)},
|
||||
[IT83XX_IRQ_WKO98] = {GPIO_F, (1<<2), 10, (1<<2)},
|
||||
[IT83XX_IRQ_WKO99] = {GPIO_F, (1<<3), 10, (1<<3)},
|
||||
[IT83XX_IRQ_WKO100] = {GPIO_A, (1<<7), 10, (1<<4)},
|
||||
[IT83XX_IRQ_WKO101] = {GPIO_B, (1<<0), 10, (1<<5)},
|
||||
[IT83XX_IRQ_WKO102] = {GPIO_B, (1<<1), 10, (1<<6)},
|
||||
[IT83XX_IRQ_WKO103] = {GPIO_B, (1<<3), 10, (1<<7)},
|
||||
[IT83XX_IRQ_WKO104] = {GPIO_B, (1<<5), 11, (1<<0)},
|
||||
[IT83XX_IRQ_WKO105] = {GPIO_B, (1<<6), 11, (1<<1)},
|
||||
[IT83XX_IRQ_WKO106] = {GPIO_B, (1<<7), 11, (1<<2)},
|
||||
[IT83XX_IRQ_WKO107] = {GPIO_C, (1<<1), 11, (1<<3)},
|
||||
[IT83XX_IRQ_WKO108] = {GPIO_C, (1<<3), 11, (1<<4)},
|
||||
[IT83XX_IRQ_WKO109] = {GPIO_C, (1<<5), 11, (1<<5)},
|
||||
[IT83XX_IRQ_WKO110] = {GPIO_D, (1<<3), 11, (1<<6)},
|
||||
[IT83XX_IRQ_WKO111] = {GPIO_D, (1<<4), 11, (1<<7)},
|
||||
[IT83XX_IRQ_WKO112] = {GPIO_D, (1<<5), 12, (1<<0)},
|
||||
[IT83XX_IRQ_WKO113] = {GPIO_D, (1<<6), 12, (1<<1)},
|
||||
[IT83XX_IRQ_WKO114] = {GPIO_E, (1<<4), 12, (1<<2)},
|
||||
[IT83XX_IRQ_WKO115] = {GPIO_G, (1<<0), 12, (1<<3)},
|
||||
[IT83XX_IRQ_WKO116] = {GPIO_G, (1<<1), 12, (1<<4)},
|
||||
[IT83XX_IRQ_WKO117] = {GPIO_G, (1<<2), 12, (1<<5)},
|
||||
[IT83XX_IRQ_WKO118] = {GPIO_G, (1<<6), 12, (1<<6)},
|
||||
[IT83XX_IRQ_WKO119] = {GPIO_I, (1<<0), 12, (1<<7)},
|
||||
[IT83XX_IRQ_WKO120] = {GPIO_I, (1<<1), 13, (1<<0)},
|
||||
[IT83XX_IRQ_WKO121] = {GPIO_I, (1<<2), 13, (1<<1)},
|
||||
[IT83XX_IRQ_WKO122] = {GPIO_I, (1<<3), 13, (1<<2)},
|
||||
[IT83XX_IRQ_WKO128] = {GPIO_J, (1<<0), 14, (1<<0)},
|
||||
[IT83XX_IRQ_WKO129] = {GPIO_J, (1<<1), 14, (1<<1)},
|
||||
[IT83XX_IRQ_WKO130] = {GPIO_J, (1<<2), 14, (1<<2)},
|
||||
[IT83XX_IRQ_WKO131] = {GPIO_J, (1<<3), 14, (1<<3)},
|
||||
[IT83XX_IRQ_WKO132] = {GPIO_J, (1<<4), 14, (1<<4)},
|
||||
[IT83XX_IRQ_WKO133] = {GPIO_J, (1<<5), 14, (1<<5)},
|
||||
[IT83XX_IRQ_COUNT-1] = {0, 0, 0, 0},
|
||||
};
|
||||
BUILD_ASSERT(ARRAY_SIZE(gpio_irqs) == IT83XX_IRQ_COUNT);
|
||||
|
||||
/**
|
||||
* Given a GPIO port and mask, find the corresponding WKO interrupt number.
|
||||
*
|
||||
* @param port GPIO port
|
||||
* @param mask GPIO mask
|
||||
*
|
||||
* @return IRQ for the WKO interrupt on the corresponding input pin.
|
||||
*/
|
||||
static int gpio_to_irq(uint8_t port, uint8_t mask)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < IT83XX_IRQ_COUNT; i++) {
|
||||
if (gpio_irqs[i].gpio_port == port &&
|
||||
gpio_irqs[i].gpio_mask == mask)
|
||||
return i;
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
void gpio_set_alternate_function(uint32_t port, uint32_t mask, int func)
|
||||
{
|
||||
uint32_t pin = 0;
|
||||
|
||||
/* For each bit high in the mask, set that pin to use alt. func. */
|
||||
while (mask > 0) {
|
||||
/*
|
||||
* If func is non-negative, set for alternate function.
|
||||
* Otherwise, turn the pin into an input as it's default.
|
||||
*/
|
||||
if ((mask & 1) && func >= 0)
|
||||
IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) &= ~0xc0;
|
||||
else if ((mask & 1) && func < 0)
|
||||
IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) =
|
||||
(IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) | 0x80) & ~0x40;
|
||||
|
||||
pin++;
|
||||
mask >>= 1;
|
||||
}
|
||||
}
|
||||
|
||||
test_mockable int gpio_get_level(enum gpio_signal signal)
|
||||
{
|
||||
return (IT83XX_GPIO_DATA(gpio_list[signal].port) &
|
||||
gpio_list[signal].mask) ? 1 : 0;
|
||||
}
|
||||
|
||||
void gpio_set_level(enum gpio_signal signal, int value)
|
||||
{
|
||||
if (value)
|
||||
IT83XX_GPIO_DATA(gpio_list[signal].port) |=
|
||||
gpio_list[signal].mask;
|
||||
else
|
||||
IT83XX_GPIO_DATA(gpio_list[signal].port) &=
|
||||
~gpio_list[signal].mask;
|
||||
}
|
||||
|
||||
void gpio_set_flags_by_mask(uint32_t port, uint32_t mask, uint32_t flags)
|
||||
{
|
||||
uint32_t pin = 0;
|
||||
uint32_t mask_copy = mask;
|
||||
int irq;
|
||||
|
||||
/*
|
||||
* Select open drain first, so that we don't glitch the signal
|
||||
* when changing the line to an output.
|
||||
*/
|
||||
if (flags & GPIO_OPEN_DRAIN)
|
||||
IT83XX_GPIO_GPOT(port) |= mask;
|
||||
else
|
||||
IT83XX_GPIO_GPOT(port) &= ~mask;
|
||||
|
||||
/* If output, set level before changing type to an output. */
|
||||
if (flags & GPIO_OUTPUT) {
|
||||
if (flags & GPIO_HIGH)
|
||||
IT83XX_GPIO_DATA(port) |= mask;
|
||||
else if (flags & GPIO_LOW)
|
||||
IT83XX_GPIO_DATA(port) &= ~mask;
|
||||
}
|
||||
|
||||
/* For each bit high in the mask, set input/output and pullup/down. */
|
||||
while (mask_copy > 0) {
|
||||
if (mask_copy & 1) {
|
||||
/* Set input or output. */
|
||||
if (flags & GPIO_OUTPUT)
|
||||
IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) =
|
||||
(IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) | 0x40)
|
||||
& ~0x80;
|
||||
else
|
||||
IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) =
|
||||
(IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) | 0x80)
|
||||
& ~0x40;
|
||||
|
||||
/* Handle pullup / pulldown */
|
||||
if (flags & GPIO_PULL_UP) {
|
||||
IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) =
|
||||
(IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) | 0x04)
|
||||
& ~0x02;
|
||||
} else if (flags & GPIO_PULL_DOWN) {
|
||||
IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) =
|
||||
(IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) | 0x02)
|
||||
& ~0x04;
|
||||
} else {
|
||||
/* No pull up/down */
|
||||
IT83XX_GPIO_CTRL(CTRL_BASE(port), pin) &= ~0x06;
|
||||
}
|
||||
}
|
||||
|
||||
pin++;
|
||||
mask_copy >>= 1;
|
||||
}
|
||||
|
||||
/* Set rising edge interrupt. */
|
||||
if (flags & GPIO_INT_F_RISING) {
|
||||
irq = gpio_to_irq(port, mask);
|
||||
|
||||
*(wuemr(gpio_irqs[irq].wuc_group)) &= ~gpio_irqs[irq].wuc_mask;
|
||||
}
|
||||
|
||||
/*
|
||||
* Set falling edge or both edges interrupt. Note that pins in WUC
|
||||
* groups 7, 10, and 12 can only declare a falling edge trigger. All
|
||||
* other pins can only declare both edges as the trigger.
|
||||
*
|
||||
* TODO: use an assert to catch if a developer tries to declare one
|
||||
* type of interrupt on a pin that doesn't support that type.
|
||||
*/
|
||||
if (flags & GPIO_INT_F_FALLING) {
|
||||
irq = gpio_to_irq(port, mask);
|
||||
|
||||
*(wuemr(gpio_irqs[irq].wuc_group)) |= gpio_irqs[irq].wuc_mask;
|
||||
}
|
||||
}
|
||||
|
||||
int gpio_enable_interrupt(enum gpio_signal signal)
|
||||
{
|
||||
int irq = gpio_to_irq(gpio_list[signal].port, gpio_list[signal].mask);
|
||||
|
||||
if (irq == -1)
|
||||
return EC_ERROR_UNKNOWN;
|
||||
else
|
||||
task_enable_irq(irq);
|
||||
|
||||
return EC_SUCCESS;
|
||||
}
|
||||
|
||||
int gpio_disable_interrupt(enum gpio_signal signal)
|
||||
{
|
||||
int irq = gpio_to_irq(gpio_list[signal].port, gpio_list[signal].mask);
|
||||
|
||||
if (irq == -1)
|
||||
return EC_ERROR_UNKNOWN;
|
||||
else
|
||||
task_disable_irq(irq);
|
||||
|
||||
return EC_SUCCESS;
|
||||
}
|
||||
|
||||
void gpio_pre_init(void)
|
||||
{
|
||||
const struct gpio_info *g = gpio_list;
|
||||
int flags;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < GPIO_COUNT; i++, g++) {
|
||||
flags = g->flags;
|
||||
|
||||
if (flags & GPIO_DEFAULT)
|
||||
continue;
|
||||
|
||||
/* Set up GPIO based on flags */
|
||||
gpio_set_flags_by_mask(g->port, g->mask, flags);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**
|
||||
* Handle a GPIO interrupt by calling the pins corresponding handler if
|
||||
* one exists.
|
||||
*
|
||||
* @param port GPIO port (GPIO_*)
|
||||
* @param mask GPIO mask
|
||||
*/
|
||||
static void gpio_interrupt(int port, uint8_t mask)
|
||||
{
|
||||
int i = 0;
|
||||
const struct gpio_info *g = gpio_list;
|
||||
|
||||
for (i = 0; i < GPIO_COUNT; i++, g++) {
|
||||
if (port == g->port && (mask & g->mask) && g->irq_handler) {
|
||||
g->irq_handler(i);
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Define one IRQ function to handle all GPIO interrupts. The IRQ determines
|
||||
* the interrupt number which was triggered, calls the master handler above,
|
||||
* and clears status registers.
|
||||
*/
|
||||
static void __gpio_irq(void)
|
||||
{
|
||||
/* Determine interrupt number. */
|
||||
int irq = IT83XX_INTC_IVCT2 - 16;
|
||||
|
||||
/* Run the GPIO master handler above with corresponding port/mask. */
|
||||
gpio_interrupt(gpio_irqs[irq].gpio_port, gpio_irqs[irq].gpio_mask);
|
||||
|
||||
/*
|
||||
* Clear the WUC status register. Note the external pin first goes
|
||||
* to the WUC module and is always edge triggered.
|
||||
*/
|
||||
*(wuesr(gpio_irqs[irq].wuc_group)) = gpio_irqs[irq].wuc_mask;
|
||||
|
||||
/*
|
||||
* Clear the interrupt controller status register. Note the interrupt
|
||||
* controller is level triggered from the WUC status.
|
||||
*/
|
||||
task_clear_pending_irq(irq);
|
||||
}
|
||||
|
||||
/* Route all WKO interrupts coming from INT#2 into __gpio_irq. */
|
||||
DECLARE_IRQ(CPU_INT_2_ALL_GPIOS, __gpio_irq, 1);
|
||||
170
chip/it83xx/hwtimer.c
Normal file
170
chip/it83xx/hwtimer.c
Normal file
@@ -0,0 +1,170 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
|
||||
/* Hardware timers driver */
|
||||
|
||||
#include "cpu.h"
|
||||
#include "common.h"
|
||||
#include "hooks.h"
|
||||
#include "hwtimer.h"
|
||||
#include "registers.h"
|
||||
#include "task.h"
|
||||
#include "timer.h"
|
||||
#include "util.h"
|
||||
|
||||
/* 128us (2^7 us) between 2 ticks */
|
||||
#define TICK_INTERVAL_LOG2 7
|
||||
|
||||
#define TICK_INTERVAL (1 << TICK_INTERVAL_LOG2)
|
||||
#define TICK_INTERVAL_MASK (TICK_INTERVAL - 1)
|
||||
|
||||
/*
|
||||
* Tick interval must fit in one byte, and must be greater than two
|
||||
* so that the duty cycle does not equal the cycle time (IT83XX_TMR_DCR_B0 must
|
||||
* be less than IT83XX_TMR_CTR_B0).
|
||||
*/
|
||||
BUILD_ASSERT(TICK_INTERVAL < 256 && TICK_INTERVAL > 2);
|
||||
|
||||
static volatile uint32_t time_us;
|
||||
|
||||
/*
|
||||
* Next event time of 0 represents "no event set". But, when we actually want
|
||||
* to trigger when the event time is 0, it is handled implicitly by calling
|
||||
* process_timers(1) when the timer value rolls over.
|
||||
*/
|
||||
static uint32_t next_event_time;
|
||||
|
||||
void __hw_clock_event_set(uint32_t deadline)
|
||||
{
|
||||
next_event_time = deadline;
|
||||
}
|
||||
|
||||
uint32_t __hw_clock_event_get(void)
|
||||
{
|
||||
return next_event_time;
|
||||
}
|
||||
|
||||
void __hw_clock_event_clear(void)
|
||||
{
|
||||
next_event_time = 0;
|
||||
}
|
||||
|
||||
uint32_t __hw_clock_source_read(void)
|
||||
{
|
||||
return time_us;
|
||||
}
|
||||
|
||||
void __hw_clock_source_set(uint32_t ts)
|
||||
{
|
||||
time_us = ts & TICK_INTERVAL_MASK;
|
||||
}
|
||||
|
||||
|
||||
static void __hw_clock_source_irq(void)
|
||||
{
|
||||
/*
|
||||
* If this is a SW interrupt, then process the timers, but don't
|
||||
* increment the time_us.
|
||||
*/
|
||||
if (get_itype() & 8) {
|
||||
process_timers(0);
|
||||
return;
|
||||
}
|
||||
|
||||
/* clear interrupt status */
|
||||
task_clear_pending_irq(IT83XX_IRQ_TMR_B0);
|
||||
|
||||
time_us += TICK_INTERVAL;
|
||||
|
||||
/*
|
||||
* Find expired timers and set the new timer deadline; check the IRQ
|
||||
* status to determine if the free-running counter overflowed. Note
|
||||
* since each tick is greater than 1us and events can be set in
|
||||
* increments of 1us, in order to find expired timers we have to
|
||||
* check two conditions: the current time is exactly the next event
|
||||
* time, or this tick just caused us to pass the next event time.
|
||||
*/
|
||||
if (time_us == next_event_time ||
|
||||
(time_us-TICK_INTERVAL) ==
|
||||
(next_event_time & ~TICK_INTERVAL_MASK))
|
||||
process_timers(0);
|
||||
else if (time_us == 0)
|
||||
process_timers(1);
|
||||
}
|
||||
DECLARE_IRQ(IT83XX_IRQ_TMR_B0, __hw_clock_source_irq, 1);
|
||||
|
||||
static void setup_gpio(void)
|
||||
{
|
||||
/* TMB0 enabled */
|
||||
IT83XX_GPIO_GRC2 |= 0x04;
|
||||
|
||||
/* Pin muxing (TMB0) */
|
||||
IT83XX_GPIO_GPCRF0 = 0x00;
|
||||
}
|
||||
|
||||
static void hw_timer_enable_int(void)
|
||||
{
|
||||
/* clear interrupt status */
|
||||
task_clear_pending_irq(IT83XX_IRQ_TMR_B0);
|
||||
|
||||
/* enable interrupt B0 */
|
||||
task_enable_irq(IT83XX_IRQ_TMR_B0);
|
||||
}
|
||||
|
||||
int __hw_clock_source_init(uint32_t start_t)
|
||||
{
|
||||
__hw_clock_source_set(start_t);
|
||||
|
||||
/* GPIO module should do this. */
|
||||
setup_gpio();
|
||||
|
||||
#if PLL_CLOCK == 48000000
|
||||
/* Set prescaler divider value (PRSC0 = /8). */
|
||||
IT83XX_TMR_PRSC = 0x04;
|
||||
|
||||
/* Tim B: 8 bit pulse mode, 8MHz clock. */
|
||||
IT83XX_TMR_GCSMS = 0x01;
|
||||
#else
|
||||
#error "Support only for PLL clock speed of 48MHz."
|
||||
#endif
|
||||
|
||||
/* Set timer B to use PRSC0. */
|
||||
IT83XX_TMR_CCGSR = 0x00;
|
||||
|
||||
/*
|
||||
* Set the 8-bit cycle time, duty time for timer B. Note 0 < DCR < CTR
|
||||
* in order for timer interrupt to properly fire when cycle time is
|
||||
* reached.
|
||||
*/
|
||||
IT83XX_TMR_CTR_B0 = TICK_INTERVAL - 1;
|
||||
IT83XX_TMR_DCR_B0 = 0x01;
|
||||
|
||||
/* Enable the cycle time interrupt for timer B0. */
|
||||
IT83XX_TMR_TMRIE |= 0x10;
|
||||
|
||||
hw_timer_enable_int();
|
||||
|
||||
/* Enable TMR clock counter. */
|
||||
IT83XX_TMR_TMRCE |= 0x02;
|
||||
|
||||
return IT83XX_IRQ_TMR_B0;
|
||||
}
|
||||
|
||||
void udelay(unsigned us)
|
||||
{
|
||||
/*
|
||||
* When WNCKR register is set, the CPU pauses until a low to
|
||||
* high transition on an internal 65kHz clock (~15.25us). We need to
|
||||
* make sure though that we don't ever delay less than the requested
|
||||
* amount, so we always have to add an extra wait.
|
||||
*
|
||||
* TODO: This code has a few limitations, the math isn't exact so
|
||||
* the larger the delay the farther off it will be, it uses a divide,
|
||||
* and the resolution is only about 15us.
|
||||
*/
|
||||
int waits = us*4/61 + 1;
|
||||
while (waits-- >= 0)
|
||||
IT83XX_GCTRL_WNCKR = 0;
|
||||
}
|
||||
87
chip/it83xx/irq.c
Normal file
87
chip/it83xx/irq.c
Normal file
@@ -0,0 +1,87 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*
|
||||
* IT83xx chip-specific part of the IRQ handling.
|
||||
*/
|
||||
|
||||
#include "common.h"
|
||||
#include "irq_chip.h"
|
||||
#include "registers.h"
|
||||
|
||||
#define IRQ_GROUP(n, cpu_ints...) \
|
||||
{(uint32_t)&CONCAT2(IT83XX_INTC_ISR, n) - IT83XX_INTC_BASE, \
|
||||
(uint32_t)&CONCAT2(IT83XX_INTC_IER, n) - IT83XX_INTC_BASE, \
|
||||
##cpu_ints}
|
||||
|
||||
static const struct {
|
||||
uint8_t isr_off;
|
||||
uint8_t ier_off;
|
||||
uint8_t cpu_int[8];
|
||||
} irq_groups[20] = {
|
||||
IRQ_GROUP(0, {-1, 2, 5, 4, 6, 2, 2, 4}),
|
||||
IRQ_GROUP(1, { 7, 6, 6, 5, 2, 2, 2, 8}),
|
||||
IRQ_GROUP(2, { 6, 2, 8, 8, 8, 2, 12, -1}),
|
||||
IRQ_GROUP(3, { 5, 4, 4, 4, 11, 11, 3, 2}),
|
||||
IRQ_GROUP(4, {11, 11, 11, 11, 8, 9, 9, 9}),
|
||||
IRQ_GROUP(5, {-1, -1, -1, -1, -1, -1, -1, -1}),
|
||||
IRQ_GROUP(6, { 2, 2, 2, 2, 2, 2, 2, 2}),
|
||||
IRQ_GROUP(7, {10, 10, 3, -1, 3, 3, 3, 3}),
|
||||
IRQ_GROUP(8, { 4, 4, 4, 4, 4, 4, 12, 12}),
|
||||
IRQ_GROUP(9, { 2, 2, 2, 2, 2, 2, 2, 2}),
|
||||
IRQ_GROUP(10, { 3, 6, 12, 12, 5, 2, 2, 2}),
|
||||
IRQ_GROUP(11, { 2, 2, 2, 2, 2, 2, 2, 2}),
|
||||
IRQ_GROUP(12, { 2, 2, 2, 2, 2, 2, 2, 2}),
|
||||
IRQ_GROUP(13, { 2, 2, 2, 2, 2, 2, 2, 2}),
|
||||
IRQ_GROUP(14, { 2, 2, 2, 2, 2, 2, 2, 2}),
|
||||
IRQ_GROUP(15, { 2, 2, 2, 2, 2, 2, 2, 2}),
|
||||
IRQ_GROUP(16, { 2, 2, 2, 2, 2, 2, 2, -1}),
|
||||
IRQ_GROUP(17, {-1, -1, -1, -1, -1, -1, -1, -1}),
|
||||
IRQ_GROUP(18, { 2, 2, 2, 2, 2, 4, 4, 7}),
|
||||
IRQ_GROUP(19, { 6, 6, 12, 3, 3, 3, 3, 3}),
|
||||
};
|
||||
|
||||
int chip_enable_irq(int irq)
|
||||
{
|
||||
int group = irq / 8;
|
||||
int bit = irq % 8;
|
||||
|
||||
IT83XX_INTC_REG(irq_groups[group].ier_off) |= 1 << bit;
|
||||
IT83XX_INTC_REG(IT83XX_INTC_EXT_IER_OFF(group)) |= 1 << bit;
|
||||
|
||||
return irq_groups[group].cpu_int[bit];
|
||||
}
|
||||
|
||||
int chip_disable_irq(int irq)
|
||||
{
|
||||
int group = irq / 8;
|
||||
int bit = irq % 8;
|
||||
|
||||
IT83XX_INTC_REG(irq_groups[group].ier_off) &= ~(1 << bit);
|
||||
IT83XX_INTC_REG(IT83XX_INTC_EXT_IER_OFF(group)) &= ~(1 << bit);
|
||||
|
||||
return -1; /* we don't want to mask other IRQs */
|
||||
}
|
||||
|
||||
int chip_clear_pending_irq(int irq)
|
||||
{
|
||||
int group = irq / 8;
|
||||
int bit = irq % 8;
|
||||
|
||||
IT83XX_INTC_REG(irq_groups[group].isr_off) |= 1 << bit;
|
||||
|
||||
return -1; /* everything has been done */
|
||||
}
|
||||
|
||||
int chip_trigger_irq(int irq)
|
||||
{
|
||||
int group = irq / 8;
|
||||
int bit = irq % 8;
|
||||
|
||||
return irq_groups[group].cpu_int[bit];
|
||||
}
|
||||
|
||||
void chip_init_irqs(void)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
}
|
||||
15
chip/it83xx/jtag.c
Normal file
15
chip/it83xx/jtag.c
Normal file
@@ -0,0 +1,15 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
|
||||
#include "clock.h"
|
||||
#include "gpio.h"
|
||||
#include "jtag.h"
|
||||
#include "registers.h"
|
||||
#include "system.h"
|
||||
|
||||
void jtag_pre_init(void)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
}
|
||||
558
chip/it83xx/registers.h
Normal file
558
chip/it83xx/registers.h
Normal file
@@ -0,0 +1,558 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*
|
||||
* Register map for IT83xx processor
|
||||
*/
|
||||
|
||||
#ifndef __CROS_EC_REGISTERS_H
|
||||
#define __CROS_EC_REGISTERS_H
|
||||
|
||||
#include "common.h"
|
||||
|
||||
/* IRQ numbers */
|
||||
#define IT83XX_IRQ_WKO20 1
|
||||
#define IT83XX_IRQ_KBC_OUT 2
|
||||
#define IT83XX_IRQ_PMC_OUT 3
|
||||
#define IT83XX_IRQ_SMB_D 4
|
||||
#define IT83XX_IRQ_WKINTAD 5
|
||||
#define IT83XX_IRQ_WKO23 6
|
||||
#define IT83XX_IRQ_PWM 7
|
||||
#define IT83XX_IRQ_ADC 8
|
||||
#define IT83XX_IRQ_SMB_A 9
|
||||
#define IT83XX_IRQ_SMB_B 10
|
||||
#define IT83XX_IRQ_KB_MATRIX 11
|
||||
#define IT83XX_IRQ_WKO26 12
|
||||
#define IT83XX_IRQ_WKINTC 13
|
||||
#define IT83XX_IRQ_WKO25 14
|
||||
#define IT83XX_IRQ_CIR 15
|
||||
#define IT83XX_IRQ_SMB_C 16
|
||||
#define IT83XX_IRQ_WKO24 17
|
||||
#define IT83XX_IRQ_PS2_2 18
|
||||
#define IT83XX_IRQ_PS2_1 19
|
||||
#define IT83XX_IRQ_PS2_0 20
|
||||
#define IT83XX_IRQ_WKO22 21
|
||||
#define IT83XX_IRQ_SMFI 22
|
||||
#define IT83XX_IRQ_KBC_IN 24
|
||||
#define IT83XX_IRQ_PMC_IN 25
|
||||
#define IT83XX_IRQ_PMC2_OUT 26
|
||||
#define IT83XX_IRQ_PMC2_IN 27
|
||||
#define IT83XX_IRQ_GINT 28
|
||||
#define IT83XX_IRQ_EGPC 29
|
||||
#define IT83XX_IRQ_EXT_TIMER1 30
|
||||
#define IT83XX_IRQ_WKO21 31
|
||||
#define IT83XX_IRQ_GPINT0 32
|
||||
#define IT83XX_IRQ_GPINT1 33
|
||||
#define IT83XX_IRQ_GPINT2 34
|
||||
#define IT83XX_IRQ_GPINT3 35
|
||||
#define IT83XX_IRQ_CIR_GPINT 36
|
||||
#define IT83XX_IRQ_SSPI 37
|
||||
#define IT83XX_IRQ_UART1 38
|
||||
#define IT83XX_IRQ_UART2 39
|
||||
#define IT83XX_IRQ_WKO60 48
|
||||
#define IT83XX_IRQ_WKO61 49
|
||||
#define IT83XX_IRQ_WKO62 50
|
||||
#define IT83XX_IRQ_WKO63 51
|
||||
#define IT83XX_IRQ_WKO64 52
|
||||
#define IT83XX_IRQ_WKO65 53
|
||||
#define IT83XX_IRQ_WKO66 54
|
||||
#define IT83XX_IRQ_WKO67 55
|
||||
#define IT83XX_IRQ_RTCT_ALARM1 56
|
||||
#define IT83XX_IRQ_RTCT_ALARM2 57
|
||||
#define IT83XX_IRQ_EXT_TIMER2 58
|
||||
#define IT83XX_IRQ_TMR_A0 60
|
||||
#define IT83XX_IRQ_TMR_A1 61
|
||||
#define IT83XX_IRQ_TMR_B0 62
|
||||
#define IT83XX_IRQ_TMR_B1 63
|
||||
#define IT83XX_IRQ_PMC2EX_OUT 64
|
||||
#define IT83XX_IRQ_PMC2EX_IN 65
|
||||
#define IT83XX_IRQ_PMC3_OUT 66
|
||||
#define IT83XX_IRQ_PMC3_IN 67
|
||||
#define IT83XX_IRQ_PMC4_OUT 68
|
||||
#define IT83XX_IRQ_PMC4_IN 69
|
||||
#define IT83XX_IRQ_I2BRAM 71
|
||||
#define IT83XX_IRQ_WKO70 72
|
||||
#define IT83XX_IRQ_WKO71 73
|
||||
#define IT83XX_IRQ_WKO72 74
|
||||
#define IT83XX_IRQ_WKO73 75
|
||||
#define IT83XX_IRQ_WKO74 76
|
||||
#define IT83XX_IRQ_WKO75 77
|
||||
#define IT83XX_IRQ_WKO76 78
|
||||
#define IT83XX_IRQ_WKO77 79
|
||||
#define IT83XX_IRQ_EXT_TMR8 80
|
||||
#define IT83XX_IRQ_SMB_CLOCK_HELD 81
|
||||
#define IT83XX_IRQ_CEC 82
|
||||
#define IT83XX_IRQ_H2RAM_LPC 83
|
||||
#define IT83XX_IRQ_WKO88 85
|
||||
#define IT83XX_IRQ_WKO89 86
|
||||
#define IT83XX_IRQ_WKO90 87
|
||||
#define IT83XX_IRQ_WKO80 88
|
||||
#define IT83XX_IRQ_WKO81 89
|
||||
#define IT83XX_IRQ_WKO82 90
|
||||
#define IT83XX_IRQ_WKO83 91
|
||||
#define IT83XX_IRQ_WKO84 92
|
||||
#define IT83XX_IRQ_WKO85 93
|
||||
#define IT83XX_IRQ_WKO86 94
|
||||
#define IT83XX_IRQ_WKO87 95
|
||||
#define IT83XX_IRQ_WKO91 96
|
||||
#define IT83XX_IRQ_WKO92 97
|
||||
#define IT83XX_IRQ_WKO93 98
|
||||
#define IT83XX_IRQ_WKO94 99
|
||||
#define IT83XX_IRQ_WKO95 100
|
||||
#define IT83XX_IRQ_WKO96 101
|
||||
#define IT83XX_IRQ_WKO97 102
|
||||
#define IT83XX_IRQ_WKO98 103
|
||||
#define IT83XX_IRQ_WKO99 104
|
||||
#define IT83XX_IRQ_WKO100 105
|
||||
#define IT83XX_IRQ_WKO101 106
|
||||
#define IT83XX_IRQ_WKO102 107
|
||||
#define IT83XX_IRQ_WKO103 108
|
||||
#define IT83XX_IRQ_WKO104 109
|
||||
#define IT83XX_IRQ_WKO105 110
|
||||
#define IT83XX_IRQ_WKO106 111
|
||||
#define IT83XX_IRQ_WKO107 112
|
||||
#define IT83XX_IRQ_WKO108 113
|
||||
#define IT83XX_IRQ_WKO109 114
|
||||
#define IT83XX_IRQ_WKO110 115
|
||||
#define IT83XX_IRQ_WKO111 116
|
||||
#define IT83XX_IRQ_WKO112 117
|
||||
#define IT83XX_IRQ_WKO113 118
|
||||
#define IT83XX_IRQ_WKO114 119
|
||||
#define IT83XX_IRQ_WKO115 120
|
||||
#define IT83XX_IRQ_WKO116 121
|
||||
#define IT83XX_IRQ_WKO117 122
|
||||
#define IT83XX_IRQ_WKO118 123
|
||||
#define IT83XX_IRQ_WKO119 124
|
||||
#define IT83XX_IRQ_WKO120 125
|
||||
#define IT83XX_IRQ_WKO121 126
|
||||
#define IT83XX_IRQ_WKO122 127
|
||||
#define IT83XX_IRQ_WKO128 128
|
||||
#define IT83XX_IRQ_WKO129 129
|
||||
#define IT83XX_IRQ_WKO130 130
|
||||
#define IT83XX_IRQ_WKO131 131
|
||||
#define IT83XX_IRQ_WKO132 132
|
||||
#define IT83XX_IRQ_WKO133 133
|
||||
#define IT83XX_IRQ_WKO134 134
|
||||
#define IT83XX_IRQ_PMC5_OUT 149
|
||||
#define IT83XX_IRQ_PMC5_IN 150
|
||||
#define IT83XX_IRQ_V_COMP 151
|
||||
#define IT83XX_IRQ_SMB_E 152
|
||||
#define IT83XX_IRQ_SMB_F 153
|
||||
#define IT83XX_IRQ_OSC_DMA 154
|
||||
#define IT83XX_IRQ_EXT_TIMER3 155
|
||||
#define IT83XX_IRQ_EXT_TIMER4 156
|
||||
#define IT83XX_IRQ_EXT_TIMER5 157
|
||||
#define IT83XX_IRQ_EXT_TIMER6 158
|
||||
#define IT83XX_IRQ_EXT_TIMER7 159
|
||||
#define IT83XX_IRQ_COUNT 160
|
||||
|
||||
/* IRQ dispatching to CPU INT vectors */
|
||||
#define IT83XX_CPU_INT_IRQ_1 2
|
||||
#define IT83XX_CPU_INT_IRQ_2 5
|
||||
#define IT83XX_CPU_INT_IRQ_3 4
|
||||
#define IT83XX_CPU_INT_IRQ_4 6
|
||||
#define IT83XX_CPU_INT_IRQ_5 2
|
||||
#define IT83XX_CPU_INT_IRQ_6 2
|
||||
#define IT83XX_CPU_INT_IRQ_7 4
|
||||
#define IT83XX_CPU_INT_IRQ_8 7
|
||||
#define IT83XX_CPU_INT_IRQ_9 6
|
||||
#define IT83XX_CPU_INT_IRQ_10 6
|
||||
#define IT83XX_CPU_INT_IRQ_11 5
|
||||
#define IT83XX_CPU_INT_IRQ_12 2
|
||||
#define IT83XX_CPU_INT_IRQ_13 2
|
||||
#define IT83XX_CPU_INT_IRQ_14 2
|
||||
#define IT83XX_CPU_INT_IRQ_15 8
|
||||
#define IT83XX_CPU_INT_IRQ_16 6
|
||||
#define IT83XX_CPU_INT_IRQ_17 2
|
||||
#define IT83XX_CPU_INT_IRQ_18 8
|
||||
#define IT83XX_CPU_INT_IRQ_19 8
|
||||
#define IT83XX_CPU_INT_IRQ_20 8
|
||||
#define IT83XX_CPU_INT_IRQ_21 2
|
||||
#define IT83XX_CPU_INT_IRQ_22 12
|
||||
#define IT83XX_CPU_INT_IRQ_24 5
|
||||
#define IT83XX_CPU_INT_IRQ_25 4
|
||||
#define IT83XX_CPU_INT_IRQ_26 4
|
||||
#define IT83XX_CPU_INT_IRQ_27 4
|
||||
#define IT83XX_CPU_INT_IRQ_28 11
|
||||
#define IT83XX_CPU_INT_IRQ_29 11
|
||||
#define IT83XX_CPU_INT_IRQ_30 3
|
||||
#define IT83XX_CPU_INT_IRQ_31 2
|
||||
#define IT83XX_CPU_INT_IRQ_32 11
|
||||
#define IT83XX_CPU_INT_IRQ_33 11
|
||||
#define IT83XX_CPU_INT_IRQ_34 11
|
||||
#define IT83XX_CPU_INT_IRQ_35 11
|
||||
#define IT83XX_CPU_INT_IRQ_36 8
|
||||
#define IT83XX_CPU_INT_IRQ_37 9
|
||||
#define IT83XX_CPU_INT_IRQ_38 9
|
||||
#define IT83XX_CPU_INT_IRQ_39 9
|
||||
#define IT83XX_CPU_INT_IRQ_48 2
|
||||
#define IT83XX_CPU_INT_IRQ_49 2
|
||||
#define IT83XX_CPU_INT_IRQ_50 2
|
||||
#define IT83XX_CPU_INT_IRQ_51 2
|
||||
#define IT83XX_CPU_INT_IRQ_52 2
|
||||
#define IT83XX_CPU_INT_IRQ_53 2
|
||||
#define IT83XX_CPU_INT_IRQ_54 2
|
||||
#define IT83XX_CPU_INT_IRQ_55 2
|
||||
#define IT83XX_CPU_INT_IRQ_56 10
|
||||
#define IT83XX_CPU_INT_IRQ_57 10
|
||||
#define IT83XX_CPU_INT_IRQ_58 3
|
||||
#define IT83XX_CPU_INT_IRQ_60 3
|
||||
#define IT83XX_CPU_INT_IRQ_61 3
|
||||
#define IT83XX_CPU_INT_IRQ_62 3
|
||||
#define IT83XX_CPU_INT_IRQ_63 3
|
||||
#define IT83XX_CPU_INT_IRQ_64 4
|
||||
#define IT83XX_CPU_INT_IRQ_65 4
|
||||
#define IT83XX_CPU_INT_IRQ_66 4
|
||||
#define IT83XX_CPU_INT_IRQ_67 4
|
||||
#define IT83XX_CPU_INT_IRQ_68 4
|
||||
#define IT83XX_CPU_INT_IRQ_69 4
|
||||
#define IT83XX_CPU_INT_IRQ_70 12
|
||||
#define IT83XX_CPU_INT_IRQ_71 12
|
||||
#define IT83XX_CPU_INT_IRQ_72 2
|
||||
#define IT83XX_CPU_INT_IRQ_73 2
|
||||
#define IT83XX_CPU_INT_IRQ_74 2
|
||||
#define IT83XX_CPU_INT_IRQ_75 2
|
||||
#define IT83XX_CPU_INT_IRQ_76 2
|
||||
#define IT83XX_CPU_INT_IRQ_77 2
|
||||
#define IT83XX_CPU_INT_IRQ_78 2
|
||||
#define IT83XX_CPU_INT_IRQ_79 2
|
||||
#define IT83XX_CPU_INT_IRQ_80 3
|
||||
#define IT83XX_CPU_INT_IRQ_81 6
|
||||
#define IT83XX_CPU_INT_IRQ_82 12
|
||||
#define IT83XX_CPU_INT_IRQ_83 12
|
||||
#define IT83XX_CPU_INT_IRQ_84 5
|
||||
#define IT83XX_CPU_INT_IRQ_85 2
|
||||
#define IT83XX_CPU_INT_IRQ_86 2
|
||||
#define IT83XX_CPU_INT_IRQ_87 2
|
||||
#define IT83XX_CPU_INT_IRQ_88 2
|
||||
#define IT83XX_CPU_INT_IRQ_89 2
|
||||
#define IT83XX_CPU_INT_IRQ_90 2
|
||||
#define IT83XX_CPU_INT_IRQ_91 2
|
||||
#define IT83XX_CPU_INT_IRQ_92 2
|
||||
#define IT83XX_CPU_INT_IRQ_93 2
|
||||
#define IT83XX_CPU_INT_IRQ_94 2
|
||||
#define IT83XX_CPU_INT_IRQ_95 2
|
||||
#define IT83XX_CPU_INT_IRQ_96 2
|
||||
#define IT83XX_CPU_INT_IRQ_97 2
|
||||
#define IT83XX_CPU_INT_IRQ_98 2
|
||||
#define IT83XX_CPU_INT_IRQ_99 2
|
||||
#define IT83XX_CPU_INT_IRQ_100 2
|
||||
#define IT83XX_CPU_INT_IRQ_101 2
|
||||
#define IT83XX_CPU_INT_IRQ_102 2
|
||||
#define IT83XX_CPU_INT_IRQ_103 2
|
||||
#define IT83XX_CPU_INT_IRQ_104 2
|
||||
#define IT83XX_CPU_INT_IRQ_105 2
|
||||
#define IT83XX_CPU_INT_IRQ_106 2
|
||||
#define IT83XX_CPU_INT_IRQ_107 2
|
||||
#define IT83XX_CPU_INT_IRQ_108 2
|
||||
#define IT83XX_CPU_INT_IRQ_109 2
|
||||
#define IT83XX_CPU_INT_IRQ_110 2
|
||||
#define IT83XX_CPU_INT_IRQ_111 2
|
||||
#define IT83XX_CPU_INT_IRQ_112 2
|
||||
#define IT83XX_CPU_INT_IRQ_113 2
|
||||
#define IT83XX_CPU_INT_IRQ_114 2
|
||||
#define IT83XX_CPU_INT_IRQ_115 2
|
||||
#define IT83XX_CPU_INT_IRQ_116 2
|
||||
#define IT83XX_CPU_INT_IRQ_117 2
|
||||
#define IT83XX_CPU_INT_IRQ_118 2
|
||||
#define IT83XX_CPU_INT_IRQ_119 2
|
||||
#define IT83XX_CPU_INT_IRQ_120 2
|
||||
#define IT83XX_CPU_INT_IRQ_121 2
|
||||
#define IT83XX_CPU_INT_IRQ_122 2
|
||||
#define IT83XX_CPU_INT_IRQ_123 2
|
||||
#define IT83XX_CPU_INT_IRQ_124 2
|
||||
#define IT83XX_CPU_INT_IRQ_125 2
|
||||
#define IT83XX_CPU_INT_IRQ_126 2
|
||||
#define IT83XX_CPU_INT_IRQ_127 2
|
||||
#define IT83XX_CPU_INT_IRQ_128 2
|
||||
#define IT83XX_CPU_INT_IRQ_129 2
|
||||
#define IT83XX_CPU_INT_IRQ_130 2
|
||||
#define IT83XX_CPU_INT_IRQ_131 2
|
||||
#define IT83XX_CPU_INT_IRQ_132 2
|
||||
#define IT83XX_CPU_INT_IRQ_133 2
|
||||
#define IT83XX_CPU_INT_IRQ_134 2
|
||||
#define IT83XX_CPU_INT_IRQ_144 2
|
||||
#define IT83XX_CPU_INT_IRQ_145 2
|
||||
#define IT83XX_CPU_INT_IRQ_146 2
|
||||
#define IT83XX_CPU_INT_IRQ_147 2
|
||||
#define IT83XX_CPU_INT_IRQ_148 2
|
||||
#define IT83XX_CPU_INT_IRQ_149 4
|
||||
#define IT83XX_CPU_INT_IRQ_150 4
|
||||
#define IT83XX_CPU_INT_IRQ_151 7
|
||||
#define IT83XX_CPU_INT_IRQ_152 6
|
||||
#define IT83XX_CPU_INT_IRQ_153 6
|
||||
#define IT83XX_CPU_INT_IRQ_154 12
|
||||
#define IT83XX_CPU_INT_IRQ_155 3
|
||||
#define IT83XX_CPU_INT_IRQ_156 3
|
||||
#define IT83XX_CPU_INT_IRQ_157 3
|
||||
#define IT83XX_CPU_INT_IRQ_158 3
|
||||
#define IT83XX_CPU_INT_IRQ_159 3
|
||||
|
||||
/* "Fake" IRQ to declare in readable fashion all WKO IRQ routed to INT#2 */
|
||||
#define CPU_INT_2_ALL_GPIOS 255
|
||||
#define IT83XX_CPU_INT_IRQ_255 2
|
||||
|
||||
#define CPU_INT(irq) CONCAT2(IT83XX_CPU_INT_IRQ_, irq)
|
||||
|
||||
/* --- INTC --- */
|
||||
#define IT83XX_INTC_BASE 0x00F01100
|
||||
|
||||
#define IT83XX_INTC_REG(n) REG8(IT83XX_INTC_BASE+(n))
|
||||
|
||||
#define IT83XX_INTC_AIVCT REG8(IT83XX_INTC_BASE+0x10)
|
||||
|
||||
#define IT83XX_INTC_IER0 REG8(IT83XX_INTC_BASE+0x04)
|
||||
#define IT83XX_INTC_IER1 REG8(IT83XX_INTC_BASE+0x05)
|
||||
#define IT83XX_INTC_IER2 REG8(IT83XX_INTC_BASE+0x06)
|
||||
#define IT83XX_INTC_IER3 REG8(IT83XX_INTC_BASE+0x07)
|
||||
#define IT83XX_INTC_IER4 REG8(IT83XX_INTC_BASE+0x15)
|
||||
#define IT83XX_INTC_IER5 REG8(IT83XX_INTC_BASE+0x19)
|
||||
#define IT83XX_INTC_IER6 REG8(IT83XX_INTC_BASE+0x1d)
|
||||
#define IT83XX_INTC_IER7 REG8(IT83XX_INTC_BASE+0x21)
|
||||
#define IT83XX_INTC_IER8 REG8(IT83XX_INTC_BASE+0x25)
|
||||
#define IT83XX_INTC_IER9 REG8(IT83XX_INTC_BASE+0x29)
|
||||
#define IT83XX_INTC_IER10 REG8(IT83XX_INTC_BASE+0x2d)
|
||||
#define IT83XX_INTC_IER11 REG8(IT83XX_INTC_BASE+0x31)
|
||||
#define IT83XX_INTC_IER12 REG8(IT83XX_INTC_BASE+0x35)
|
||||
#define IT83XX_INTC_IER13 REG8(IT83XX_INTC_BASE+0x39)
|
||||
#define IT83XX_INTC_IER14 REG8(IT83XX_INTC_BASE+0x3d)
|
||||
#define IT83XX_INTC_IER15 REG8(IT83XX_INTC_BASE+0x41)
|
||||
#define IT83XX_INTC_IER16 REG8(IT83XX_INTC_BASE+0x45)
|
||||
#define IT83XX_INTC_IER17 REG8(IT83XX_INTC_BASE+0x49)
|
||||
#define IT83XX_INTC_IER18 REG8(IT83XX_INTC_BASE+0x4d)
|
||||
#define IT83XX_INTC_IER19 REG8(IT83XX_INTC_BASE+0x51)
|
||||
|
||||
#define IT83XX_INTC_ISR0 REG8(IT83XX_INTC_BASE+0x00)
|
||||
#define IT83XX_INTC_ISR1 REG8(IT83XX_INTC_BASE+0x01)
|
||||
#define IT83XX_INTC_ISR2 REG8(IT83XX_INTC_BASE+0x02)
|
||||
#define IT83XX_INTC_ISR3 REG8(IT83XX_INTC_BASE+0x03)
|
||||
#define IT83XX_INTC_ISR4 REG8(IT83XX_INTC_BASE+0x14)
|
||||
#define IT83XX_INTC_ISR5 REG8(IT83XX_INTC_BASE+0x18)
|
||||
#define IT83XX_INTC_ISR6 REG8(IT83XX_INTC_BASE+0x1c)
|
||||
#define IT83XX_INTC_ISR7 REG8(IT83XX_INTC_BASE+0x20)
|
||||
#define IT83XX_INTC_ISR8 REG8(IT83XX_INTC_BASE+0x24)
|
||||
#define IT83XX_INTC_ISR9 REG8(IT83XX_INTC_BASE+0x28)
|
||||
#define IT83XX_INTC_ISR10 REG8(IT83XX_INTC_BASE+0x2c)
|
||||
#define IT83XX_INTC_ISR11 REG8(IT83XX_INTC_BASE+0x30)
|
||||
#define IT83XX_INTC_ISR12 REG8(IT83XX_INTC_BASE+0x34)
|
||||
#define IT83XX_INTC_ISR13 REG8(IT83XX_INTC_BASE+0x38)
|
||||
#define IT83XX_INTC_ISR14 REG8(IT83XX_INTC_BASE+0x3c)
|
||||
#define IT83XX_INTC_ISR15 REG8(IT83XX_INTC_BASE+0x40)
|
||||
#define IT83XX_INTC_ISR16 REG8(IT83XX_INTC_BASE+0x44)
|
||||
#define IT83XX_INTC_ISR17 REG8(IT83XX_INTC_BASE+0x48)
|
||||
#define IT83XX_INTC_ISR18 REG8(IT83XX_INTC_BASE+0x4c)
|
||||
#define IT83XX_INTC_ISR19 REG8(IT83XX_INTC_BASE+0x50)
|
||||
|
||||
#define IT83XX_INTC_EXT_IER0 REG8(IT83XX_INTC_BASE+0x60)
|
||||
#define IT83XX_INTC_EXT_IER1 REG8(IT83XX_INTC_BASE+0x61)
|
||||
#define IT83XX_INTC_EXT_IER2 REG8(IT83XX_INTC_BASE+0x62)
|
||||
#define IT83XX_INTC_EXT_IER3 REG8(IT83XX_INTC_BASE+0x63)
|
||||
#define IT83XX_INTC_EXT_IER4 REG8(IT83XX_INTC_BASE+0x64)
|
||||
#define IT83XX_INTC_EXT_IER5 REG8(IT83XX_INTC_BASE+0x65)
|
||||
#define IT83XX_INTC_EXT_IER6 REG8(IT83XX_INTC_BASE+0x66)
|
||||
#define IT83XX_INTC_EXT_IER7 REG8(IT83XX_INTC_BASE+0x67)
|
||||
#define IT83XX_INTC_EXT_IER8 REG8(IT83XX_INTC_BASE+0x68)
|
||||
#define IT83XX_INTC_EXT_IER9 REG8(IT83XX_INTC_BASE+0x69)
|
||||
#define IT83XX_INTC_EXT_IER10 REG8(IT83XX_INTC_BASE+0x6A)
|
||||
#define IT83XX_INTC_EXT_IER11 REG8(IT83XX_INTC_BASE+0x6B)
|
||||
#define IT83XX_INTC_EXT_IER12 REG8(IT83XX_INTC_BASE+0x6C)
|
||||
#define IT83XX_INTC_EXT_IER13 REG8(IT83XX_INTC_BASE+0x6D)
|
||||
#define IT83XX_INTC_EXT_IER14 REG8(IT83XX_INTC_BASE+0x6E)
|
||||
#define IT83XX_INTC_EXT_IER15 REG8(IT83XX_INTC_BASE+0x6F)
|
||||
#define IT83XX_INTC_EXT_IER16 REG8(IT83XX_INTC_BASE+0x70)
|
||||
#define IT83XX_INTC_EXT_IER17 REG8(IT83XX_INTC_BASE+0x71)
|
||||
#define IT83XX_INTC_EXT_IER18 REG8(IT83XX_INTC_BASE+0x72)
|
||||
#define IT83XX_INTC_EXT_IER19 REG8(IT83XX_INTC_BASE+0x73)
|
||||
|
||||
#define IT83XX_INTC_EXT_IER_OFF(n) (0x60 + (n))
|
||||
|
||||
#define IT83XX_INTC_IVCT0 REG8(IT83XX_INTC_BASE+0x80)
|
||||
#define IT83XX_INTC_IVCT1 REG8(IT83XX_INTC_BASE+0x81)
|
||||
#define IT83XX_INTC_IVCT2 REG8(IT83XX_INTC_BASE+0x82)
|
||||
#define IT83XX_INTC_IVCT3 REG8(IT83XX_INTC_BASE+0x83)
|
||||
#define IT83XX_INTC_IVCT4 REG8(IT83XX_INTC_BASE+0x84)
|
||||
#define IT83XX_INTC_IVCT5 REG8(IT83XX_INTC_BASE+0x85)
|
||||
#define IT83XX_INTC_IVCT6 REG8(IT83XX_INTC_BASE+0x86)
|
||||
#define IT83XX_INTC_IVCT7 REG8(IT83XX_INTC_BASE+0x87)
|
||||
#define IT83XX_INTC_IVCT8 REG8(IT83XX_INTC_BASE+0x88)
|
||||
#define IT83XX_INTC_IVCT9 REG8(IT83XX_INTC_BASE+0x89)
|
||||
#define IT83XX_INTC_IVCT10 REG8(IT83XX_INTC_BASE+0x8A)
|
||||
#define IT83XX_INTC_IVCT11 REG8(IT83XX_INTC_BASE+0x8B)
|
||||
#define IT83XX_INTC_IVCT12 REG8(IT83XX_INTC_BASE+0x8C)
|
||||
#define IT83XX_INTC_IVCT13 REG8(IT83XX_INTC_BASE+0x8D)
|
||||
#define IT83XX_INTC_IVCT14 REG8(IT83XX_INTC_BASE+0x8E)
|
||||
#define IT83XX_INTC_IVCT15 REG8(IT83XX_INTC_BASE+0x8F)
|
||||
|
||||
/* --- Wake-Up Control (WUC) --- */
|
||||
#define IT83XX_WUC_BASE 0x00F01B00
|
||||
|
||||
#define IT83XX_WUC_WUEMR1 (IT83XX_WUC_BASE+0x00)
|
||||
#define IT83XX_WUC_WUEMR6 (IT83XX_WUC_BASE+0x10)
|
||||
#define IT83XX_WUC_WUESR1 (IT83XX_WUC_BASE+0x04)
|
||||
#define IT83XX_WUC_WUESR6 (IT83XX_WUC_BASE+0x11)
|
||||
|
||||
#define IT83XX_WUC_WUESR10 REG8(IT83XX_WUC_BASE+0x21)
|
||||
#define IT83XX_WUC_WUESR11 REG8(IT83XX_WUC_BASE+0x25)
|
||||
|
||||
/* --- UART --- */
|
||||
#define IT83XX_UART0_BASE 0x00F02700
|
||||
#define IT83XX_UART1_BASE 0x00F02800
|
||||
|
||||
#define IT83XX_UART_BASE(n) CONCAT3(IT83XX_UART, n, _BASE)
|
||||
#define IT83XX_UART_REG(n, offset) REG8(IT83XX_UART_BASE(n) + (offset))
|
||||
|
||||
#define IT83XX_UART_DLL(n) IT83XX_UART_REG(n, 0x00)
|
||||
#define IT83XX_UART_DLM(n) IT83XX_UART_REG(n, 0x01)
|
||||
#define IT83XX_UART_RBR(n) IT83XX_UART_REG(n, 0x00)
|
||||
#define IT83XX_UART_THR(n) IT83XX_UART_REG(n, 0x00)
|
||||
#define IT83XX_UART_IER(n) IT83XX_UART_REG(n, 0x01)
|
||||
#define IT83XX_UART_IIR(n) IT83XX_UART_REG(n, 0x02)
|
||||
#define IT83XX_UART_FCR(n) IT83XX_UART_REG(n, 0x02)
|
||||
#define IT83XX_UART_LCR(n) IT83XX_UART_REG(n, 0x03)
|
||||
#define IT83XX_UART_MCR(n) IT83XX_UART_REG(n, 0x04)
|
||||
#define IT83XX_UART_LSR(n) IT83XX_UART_REG(n, 0x05)
|
||||
#define IT83XX_UART_MSR(n) IT83XX_UART_REG(n, 0x06)
|
||||
#define IT83XX_UART_SCR(n) IT83XX_UART_REG(n, 0x07)
|
||||
#define IT83XX_UART_ECSMPR(n) IT83XX_UART_REG(n, 0x08)
|
||||
#define IT83XX_UART_CSSR(n) IT83XX_UART_REG(n, 0x09)
|
||||
|
||||
/* --- GPIO --- */
|
||||
|
||||
#define IT83XX_GPIO_BASE 0x00F01600
|
||||
|
||||
#define IT83XX_GPIO_GPCRF0 REG8(IT83XX_GPIO_BASE+0x38)
|
||||
|
||||
#define IT83XX_GPIO_GRC1 REG8(IT83XX_GPIO_BASE+0xF0)
|
||||
#define IT83XX_GPIO_GRC2 REG8(IT83XX_GPIO_BASE+0xF1)
|
||||
#define IT83XX_GPIO_GRC3 REG8(IT83XX_GPIO_BASE+0xF2)
|
||||
#define IT83XX_GPIO_GRC4 REG8(IT83XX_GPIO_BASE+0xF3)
|
||||
#define IT83XX_GPIO_GRC5 REG8(IT83XX_GPIO_BASE+0xF4)
|
||||
#define IT83XX_GPIO_GRC6 REG8(IT83XX_GPIO_BASE+0xF5)
|
||||
#define IT83XX_GPIO_GRC7 REG8(IT83XX_GPIO_BASE+0xF6)
|
||||
#define IT83XX_GPIO_GRC8 REG8(IT83XX_GPIO_BASE+0xF7)
|
||||
|
||||
#define IT83XX_GPIO_DATA_BASE (IT83XX_GPIO_BASE + 0x00)
|
||||
#define IT83XX_GPIO_OUTPUT_TYPE_BASE (IT83XX_GPIO_BASE + 0x70)
|
||||
|
||||
|
||||
enum {
|
||||
GPIO_A = 0x1,
|
||||
GPIO_B = 0x2,
|
||||
GPIO_C = 0x3,
|
||||
GPIO_D = 0x4,
|
||||
GPIO_E = 0x5,
|
||||
GPIO_F = 0x6,
|
||||
GPIO_G = 0x7,
|
||||
GPIO_H = 0x8,
|
||||
GPIO_I = 0x9,
|
||||
GPIO_J = 0xa,
|
||||
GPIO_M = 0xd,
|
||||
};
|
||||
#define DUMMY_GPIO_BANK GPIO_A
|
||||
|
||||
#define IT83XX_GPIO_DATA(port) REG8(IT83XX_GPIO_DATA_BASE + port)
|
||||
#define IT83XX_GPIO_GPOT(port) REG8(IT83XX_GPIO_OUTPUT_TYPE_BASE + port)
|
||||
#define IT83XX_GPIO_CTRL(port_offset, pin_offset) \
|
||||
REG8(IT83XX_GPIO_BASE + port_offset + pin_offset)
|
||||
|
||||
/* --- Clock and Power Management (ECPM) --- */
|
||||
|
||||
#define IT83XX_ECPM_BASE 0x00F01E00
|
||||
|
||||
#define IT83XX_ECPM_CGCTRL1R_OFF 0x01
|
||||
#define IT83XX_ECPM_CGCTRL2R_OFF 0x02
|
||||
#define IT83XX_ECPM_CGCTRL3R_OFF 0x05
|
||||
#define IT83XX_ECPM_CGCTRL4R_OFF 0x09
|
||||
|
||||
#define IT83XX_ECPM_PLLCTRL REG8(IT83XX_ECPM_BASE+0x03)
|
||||
#define IT83XX_ECPM_AUTOCG REG8(IT83XX_ECPM_BASE+0x04)
|
||||
#define IT83XX_ECPM_PLLFREQR REG8(IT83XX_ECPM_BASE+0x06)
|
||||
#define IT83XX_ECPM_PLLCSS REG8(IT83XX_ECPM_BASE+0x08)
|
||||
#define IT83XX_ECPM_SCDCR0 REG8(IT83XX_ECPM_BASE+0x0c)
|
||||
#define IT83XX_ECPM_SCDCR1 REG8(IT83XX_ECPM_BASE+0x0d)
|
||||
#define IT83XX_ECPM_SCDCR2 REG8(IT83XX_ECPM_BASE+0x0e)
|
||||
#define IT83XX_ECPM_SCDCR3 REG8(IT83XX_ECPM_BASE+0x0f)
|
||||
|
||||
/*
|
||||
* The clock gate offsets combine the register offset from ECPM_BASE and the
|
||||
* mask within that register into one value. These are used for
|
||||
* clock_enable_peripheral() and clock_disable_peripheral()
|
||||
*/
|
||||
enum clock_gate_offsets {
|
||||
CGC_OFFSET_EGPC = ((IT83XX_ECPM_CGCTRL2R_OFF << 8) | 0x40),
|
||||
CGC_OFFSET_CIR = ((IT83XX_ECPM_CGCTRL2R_OFF << 8) | 0x20),
|
||||
CGC_OFFSET_SWUC = ((IT83XX_ECPM_CGCTRL2R_OFF << 8) | 0x10),
|
||||
CGC_OFFSET_USB = ((IT83XX_ECPM_CGCTRL3R_OFF << 8) | 0x20),
|
||||
CGC_OFFSET_PECI = ((IT83XX_ECPM_CGCTRL3R_OFF << 8) | 0x08),
|
||||
CGC_OFFSET_UART = ((IT83XX_ECPM_CGCTRL3R_OFF << 8) | 0x04),
|
||||
CGC_OFFSET_SSPI = ((IT83XX_ECPM_CGCTRL3R_OFF << 8) | 0x02),
|
||||
CGC_OFFSET_DBGR = ((IT83XX_ECPM_CGCTRL3R_OFF << 8) | 0x01),
|
||||
CGC_OFFSET_SMB = ((IT83XX_ECPM_CGCTRL4R_OFF << 8) | 0x02),
|
||||
CGC_OFFSET_CEC = ((IT83XX_ECPM_CGCTRL4R_OFF << 8) | 0x01)
|
||||
};
|
||||
|
||||
/* --- Timer (TMR) --- */
|
||||
#define IT83XX_TMR_BASE 0x00F02900
|
||||
|
||||
#define IT83XX_TMR_PRSC REG8(IT83XX_TMR_BASE+0x00)
|
||||
#define IT83XX_TMR_GCSMS REG8(IT83XX_TMR_BASE+0x01)
|
||||
#define IT83XX_TMR_CTR_A0 REG8(IT83XX_TMR_BASE+0x02)
|
||||
#define IT83XX_TMR_CTR_A1 REG8(IT83XX_TMR_BASE+0x03)
|
||||
#define IT83XX_TMR_CTR_B0 REG8(IT83XX_TMR_BASE+0x04)
|
||||
#define IT83XX_TMR_CTR_B1 REG8(IT83XX_TMR_BASE+0x05)
|
||||
#define IT83XX_TMR_DCR_A0 REG8(IT83XX_TMR_BASE+0x06)
|
||||
#define IT83XX_TMR_DCR_A1 REG8(IT83XX_TMR_BASE+0x07)
|
||||
#define IT83XX_TMR_DCR_B0 REG8(IT83XX_TMR_BASE+0x08)
|
||||
#define IT83XX_TMR_DCR_B1 REG8(IT83XX_TMR_BASE+0x09)
|
||||
#define IT83XX_TMR_CCGSR REG8(IT83XX_TMR_BASE+0x0A)
|
||||
#define IT83XX_TMR_TMRCE REG8(IT83XX_TMR_BASE+0x0B)
|
||||
#define IT83XX_TMR_TMRIE REG8(IT83XX_TMR_BASE+0x0C)
|
||||
|
||||
/* --- External Timer and Watchdog (ETWD) --- */
|
||||
#define IT83XX_ETWD_BASE 0x00F01F00
|
||||
|
||||
#define IT83XX_ETWD_ETWCFG REG8(IT83XX_ETWD_BASE+0x01)
|
||||
#define IT83XX_ETWD_ET1PSR REG8(IT83XX_ETWD_BASE+0x02)
|
||||
#define IT83XX_ETWD_ET1CNTLHR REG8(IT83XX_ETWD_BASE+0x03)
|
||||
#define IT83XX_ETWD_ET1CNTLLR REG8(IT83XX_ETWD_BASE+0x04)
|
||||
#define IT83XX_ETWD_ETWCTRL REG8(IT83XX_ETWD_BASE+0x05)
|
||||
#define IT83XX_ETWD_EWDCNTLLR REG8(IT83XX_ETWD_BASE+0x06)
|
||||
#define IT83XX_ETWD_EWDKEYR REG8(IT83XX_ETWD_BASE+0x07)
|
||||
#define IT83XX_ETWD_EWDCNTLHR REG8(IT83XX_ETWD_BASE+0x09)
|
||||
#define IT83XX_ETWD_ET3CTRL REG8(IT83XX_ETWD_BASE+0x10)
|
||||
#define IT83XX_ETWD_ET3PSR REG8(IT83XX_ETWD_BASE+0x11)
|
||||
#define IT83XX_ETWD_ET3CNTLLR REG8(IT83XX_ETWD_BASE+0x14)
|
||||
#define IT83XX_ETWD_ET3CNTLHR REG8(IT83XX_ETWD_BASE+0x15)
|
||||
#define IT83XX_ETWD_ET3CNTLH2R REG8(IT83XX_ETWD_BASE+0x16)
|
||||
|
||||
/* --- General Control (GCTRL) --- */
|
||||
#define IT83XX_GCTRL_BASE 0x00F02000
|
||||
|
||||
#define IT83XX_GCTRL_WNCKR REG8(IT83XX_GCTRL_BASE+0x0B)
|
||||
|
||||
/* --- MISC (not implemented yet) --- */
|
||||
|
||||
#define IT83XX_SMFI_BASE 0x00F01000
|
||||
#define IT83XX_EC2I_BASE 0x00F01200
|
||||
#define IT83XX_KBC_BASE 0x00F01300
|
||||
#define IT83XX_SWUC_BASE 0x00F01400
|
||||
#define IT83XX_PMC_BASE 0x00F01500
|
||||
#define IT83XX_PS2_BASE 0x00F01700
|
||||
#define IT83XX_PWM_BASE 0x00F01800
|
||||
#define IT83XX_ADC_BASE 0x00F01900
|
||||
#define IT83XX_DAC_BASE 0x00F01A00
|
||||
#define IT83XX_WUC_BASE 0x00F01B00
|
||||
#define IT83XX_SMB_BASE 0x00F01C00
|
||||
#define IT83XX_KBS_BASE 0x00F01D00
|
||||
#define IT83XX_EGPIO_BASE 0x00F02100
|
||||
#define IT83XX_BRAM_BASE 0x00F02200
|
||||
#define IT83XX_CIR_BASE 0x00F02300
|
||||
#define IT83XX_DBGR_BASE 0x00F02500
|
||||
#define IT83XX_SSPI_BASE 0x00F02600
|
||||
#define IT83XX_OW_BASE 0x00F02A00
|
||||
#define IT83XX_PECI_BASE 0x00F02C00
|
||||
#define IT83XX_I2C_BASE 0x00F02D00
|
||||
#define IT83XX_CEC_BASE 0x00F02E00
|
||||
#define IT83XX_USB_BASE 0x00F02F00
|
||||
|
||||
#endif /* __CROS_EC_REGISTERS_H */
|
||||
82
chip/it83xx/system.c
Normal file
82
chip/it83xx/system.c
Normal file
@@ -0,0 +1,82 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
|
||||
/* System module for Chrome EC : hardware specific implementation */
|
||||
|
||||
#include "console.h"
|
||||
#include "cpu.h"
|
||||
#include "flash.h"
|
||||
#include "registers.h"
|
||||
#include "system.h"
|
||||
#include "task.h"
|
||||
#include "util.h"
|
||||
#include "version.h"
|
||||
#include "watchdog.h"
|
||||
|
||||
void system_hibernate(uint32_t seconds, uint32_t microseconds)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
}
|
||||
|
||||
void system_pre_init(void)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
}
|
||||
|
||||
void system_reset(int flags)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
}
|
||||
|
||||
int system_set_scratchpad(uint32_t value)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint32_t system_get_scratchpad(void)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
return 0;
|
||||
}
|
||||
|
||||
const char *system_get_chip_vendor(void)
|
||||
{
|
||||
return "ite";
|
||||
}
|
||||
|
||||
const char *system_get_chip_name(void)
|
||||
{
|
||||
return "it83xx";
|
||||
}
|
||||
|
||||
const char *system_get_chip_revision(void)
|
||||
{
|
||||
return "";
|
||||
}
|
||||
|
||||
int system_get_vbnvcontext(uint8_t *block)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
return EC_SUCCESS;
|
||||
}
|
||||
|
||||
int system_set_vbnvcontext(const uint8_t *block)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
return EC_SUCCESS;
|
||||
}
|
||||
|
||||
int system_set_console_force_enabled(int val)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
return 0;
|
||||
}
|
||||
|
||||
int system_get_console_force_enabled(void)
|
||||
{
|
||||
/* TODO(crosbug.com/p/23575): IMPLEMENT ME ! */
|
||||
return 0;
|
||||
}
|
||||
177
chip/it83xx/uart.c
Normal file
177
chip/it83xx/uart.c
Normal file
@@ -0,0 +1,177 @@
|
||||
/* Copyright (c) 2013 The Chromium OS Authors. All rights reserved.
|
||||
* Use of this source code is governed by a BSD-style license that can be
|
||||
* found in the LICENSE file.
|
||||
*/
|
||||
|
||||
/* UART module for Chrome EC */
|
||||
|
||||
#include "clock.h"
|
||||
#include "common.h"
|
||||
#include "console.h"
|
||||
#include "gpio.h"
|
||||
#include "registers.h"
|
||||
#include "system.h"
|
||||
#include "task.h"
|
||||
#include "uart.h"
|
||||
#include "util.h"
|
||||
|
||||
/* Traces on UART0 */
|
||||
#define UART_PORT 0
|
||||
|
||||
static int init_done;
|
||||
|
||||
int uart_init_done(void)
|
||||
{
|
||||
return init_done;
|
||||
}
|
||||
|
||||
void uart_tx_start(void)
|
||||
{
|
||||
/* If interrupt is already enabled, nothing to do */
|
||||
if (IT83XX_UART_IER(UART_PORT) & 0x02)
|
||||
return;
|
||||
|
||||
/* Do not allow deep sleep while transmit in progress */
|
||||
disable_sleep(SLEEP_MASK_UART);
|
||||
|
||||
/* Re-enable the transmit interrupt. */
|
||||
IT83XX_UART_IER(UART_PORT) |= 0x02;
|
||||
}
|
||||
|
||||
void uart_tx_stop(void)
|
||||
{
|
||||
IT83XX_UART_IER(UART_PORT) &= ~0x02;
|
||||
|
||||
/* Re-allow deep sleep */
|
||||
enable_sleep(SLEEP_MASK_UART);
|
||||
}
|
||||
|
||||
void uart_tx_flush(void)
|
||||
{
|
||||
/*
|
||||
* Wait for transmit FIFO empty (TEMT) and transmitter holder
|
||||
* register and transmitter shift registers to be empty (THRE).
|
||||
*/
|
||||
while ((IT83XX_UART_LSR(UART_PORT) & 0x60) != 0x60)
|
||||
;
|
||||
}
|
||||
|
||||
int uart_tx_ready(void)
|
||||
{
|
||||
/* Transmit is ready when FIFO is empty (THRE). */
|
||||
return IT83XX_UART_LSR(UART_PORT) & 0x20;
|
||||
}
|
||||
|
||||
int uart_tx_in_progress(void)
|
||||
{
|
||||
/*
|
||||
* Transmit is in progress if transmit holding register or transmitter
|
||||
* shift register are not empty (TEMT).
|
||||
*/
|
||||
return !(IT83XX_UART_LSR(UART_PORT) & 0x40);
|
||||
}
|
||||
|
||||
int uart_rx_available(void)
|
||||
{
|
||||
return IT83XX_UART_LSR(UART_PORT) & 0x01;
|
||||
}
|
||||
|
||||
void uart_write_char(char c)
|
||||
{
|
||||
/* Wait for space in transmit FIFO. */
|
||||
while (!uart_tx_ready())
|
||||
;
|
||||
|
||||
IT83XX_UART_THR(UART_PORT) = c;
|
||||
}
|
||||
|
||||
int uart_read_char(void)
|
||||
{
|
||||
return IT83XX_UART_RBR(UART_PORT);
|
||||
}
|
||||
|
||||
void uart_disable_interrupt(void)
|
||||
{
|
||||
task_disable_irq(IT83XX_IRQ_UART1);
|
||||
}
|
||||
|
||||
void uart_enable_interrupt(void)
|
||||
{
|
||||
task_enable_irq(IT83XX_IRQ_UART1);
|
||||
}
|
||||
|
||||
static void uart_ec_interrupt(void)
|
||||
{
|
||||
/* clear interrupt status */
|
||||
task_clear_pending_irq(IT83XX_IRQ_UART1);
|
||||
|
||||
/* Read input FIFO until empty, then fill output FIFO */
|
||||
uart_process_input();
|
||||
uart_process_output();
|
||||
}
|
||||
DECLARE_IRQ(IT83XX_IRQ_UART1, uart_ec_interrupt, 1);
|
||||
|
||||
static void uart_config(void)
|
||||
{
|
||||
#if PLL_CLOCK == 48000000
|
||||
/* Set CLK_UART_DIV_SEL to /2. Assumes PLL is 48 MHz. */
|
||||
IT83XX_ECPM_SCDCR1 |= 0x01;
|
||||
|
||||
/*
|
||||
* Specify clock source of the UART is 24MHz,
|
||||
* must match CLK_UART_DIV_SEL.
|
||||
*/
|
||||
IT83XX_UART_CSSR(UART_PORT) = 0x01;
|
||||
#else
|
||||
#error "Support only for PLL clock speed of 48MHz."
|
||||
#endif
|
||||
|
||||
/* 8-N-1 and DLAB set to allow access to DLL and DLM registers. */
|
||||
IT83XX_UART_LCR(UART_PORT) = 0x83;
|
||||
|
||||
/* Set divisor to set baud rate to 115200 */
|
||||
IT83XX_UART_DLM(UART_PORT) = 0x00;
|
||||
IT83XX_UART_DLL(UART_PORT) = 0x01;
|
||||
|
||||
/*
|
||||
* Clear DLAB bit to exclude access to DLL and DLM and give access to
|
||||
* RBR and THR.
|
||||
*/
|
||||
IT83XX_UART_LCR(UART_PORT) = 0x03;
|
||||
|
||||
/*
|
||||
* Enable TX and RX FIFOs and set RX FIFO interrupt level to the
|
||||
* minimum 1 byte.
|
||||
*/
|
||||
IT83XX_UART_FCR(UART_PORT) = 0x07;
|
||||
|
||||
/*
|
||||
* set OUT2 bit to enable interrupt logic.
|
||||
*/
|
||||
IT83XX_UART_MCR(UART_PORT) = 0x08;
|
||||
}
|
||||
|
||||
void uart_init(void)
|
||||
{
|
||||
/* Waiting for when we can use the GPIO module to set pin muxing */
|
||||
gpio_config_module(MODULE_UART, 1);
|
||||
|
||||
/* switch UART0 on without hardware flow control */
|
||||
IT83XX_GPIO_GRC1 = 0x01;
|
||||
IT83XX_GPIO_GRC6 |= 0x03;
|
||||
|
||||
/* Enable clocks to UART 1 and 2. */
|
||||
clock_enable_peripheral(CGC_OFFSET_UART, 0, 0);
|
||||
|
||||
/* Config UART 0 only for now. */
|
||||
uart_config();
|
||||
|
||||
/* clear interrupt status */
|
||||
task_clear_pending_irq(IT83XX_IRQ_UART1);
|
||||
|
||||
/* Enable interrupts */
|
||||
IT83XX_UART_IER(UART_PORT) = 0x03;
|
||||
task_enable_irq(IT83XX_IRQ_UART1);
|
||||
|
||||
init_done = 1;
|
||||
}
|
||||
@@ -94,6 +94,7 @@ void process_timers(int overflow)
|
||||
} while (next.val <= get_time().val);
|
||||
}
|
||||
|
||||
#ifndef CONFIG_HW_SPECIFIC_UDELAY
|
||||
void udelay(unsigned us)
|
||||
{
|
||||
unsigned t0 = __hw_clock_source_read();
|
||||
@@ -111,6 +112,7 @@ void udelay(unsigned us)
|
||||
while (__hw_clock_source_read() - t0 < us)
|
||||
;
|
||||
}
|
||||
#endif
|
||||
|
||||
int timer_arm(timestamp_t tstamp, task_id_t tskid)
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user