74 lines
2.4 KiB
C
74 lines
2.4 KiB
C
|
/* pinmux_quark_mcu.h - pinmux operation for generic Quark MCU boards */
|
||
|
|
||
|
/*
|
||
|
* Copyright (c) 2016 Intel Corporation
|
||
|
*
|
||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||
|
* you may not use this file except in compliance with the License.
|
||
|
* You may obtain a copy of the License at
|
||
|
*
|
||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||
|
*
|
||
|
* Unless required by applicable law or agreed to in writing, software
|
||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||
|
* See the License for the specific language governing permissions and
|
||
|
* limitations under the License.
|
||
|
*/
|
||
|
|
||
|
#define PINMUX_PULLUP_OFFSET 0x00
|
||
|
#define PINMUX_SLEW_OFFSET 0x10
|
||
|
#define PINMUX_INPUT_OFFSET 0x20
|
||
|
#define PINMUX_SELECT_OFFSET 0x30
|
||
|
|
||
|
#define PINMUX_SELECT_REGISTER(base, reg_offset) \
|
||
|
(base + PINMUX_SELECT_OFFSET + (reg_offset << 2))
|
||
|
|
||
|
/*
|
||
|
* A little decyphering of what is going on here:
|
||
|
*
|
||
|
* Each pinmux register rperesents a bank of 16 pins, 2 bits per pin for a total
|
||
|
* of four possible settings per pin.
|
||
|
*
|
||
|
* The first argument to the macro is name of the uint32_t's that is being used
|
||
|
* to contain the bit patterns for all the configuration registers. The pin
|
||
|
* number divided by 16 selects the correct register bank based on the pin
|
||
|
* number.
|
||
|
*
|
||
|
* The pin number % 16 * 2 selects the position within the register bank for the
|
||
|
* bits controlling the pin.
|
||
|
*
|
||
|
* All but the lower two bits of the config values are masked off to ensure
|
||
|
* that we don't inadvertently affect other pins in the register bank.
|
||
|
*/
|
||
|
#define PIN_CONFIG(A, _pin, _func) \
|
||
|
(A[((_pin) / 16)] |= ((0x3 & (_func)) << (((_pin) % 16) * 2)))
|
||
|
|
||
|
static inline int _quark_mcu_set_mux(uint32_t base, uint32_t pin, uint8_t func)
|
||
|
{
|
||
|
/*
|
||
|
* the registers are 32-bit wide, but each pin requires 1 bit
|
||
|
* to set the input enable bit.
|
||
|
*/
|
||
|
uint32_t register_offset = (pin / 32) * 4;
|
||
|
/*
|
||
|
* Now figure out what is the full address for the register
|
||
|
* we are looking for. Add the base register to the register_mask
|
||
|
*/
|
||
|
volatile uint32_t *mux_register = (uint32_t *)(base + register_offset);
|
||
|
|
||
|
/*
|
||
|
* Finally grab the pin offset within the register
|
||
|
*/
|
||
|
uint32_t pin_offset = pin % 32;
|
||
|
|
||
|
/*
|
||
|
* MAGIC NUMBER: 0x1 is used as the pullup is a single bit in a
|
||
|
* 32-bit register.
|
||
|
*/
|
||
|
(*(mux_register)) = ((*(mux_register)) & ~(0x1 << pin_offset)) |
|
||
|
((func & 0x01) << pin_offset);
|
||
|
|
||
|
return 0;
|
||
|
}
|