diff mbox

[U-Boot,PATCHv5,4/4] Add support the Avionic Design Meerkat COM and Kein Baseboard

Message ID 20160905132952.27280-5-julian@jusst.de
State Changes Requested
Delegated to: Tom Warren
Headers show

Commit Message

Julian Scheel Sept. 5, 2016, 1:29 p.m. UTC
Add support for platforms based on the Meerkat COM module. Includes support
for the minimal reference platform called Kein Baseboard, which in fact is
sufficient to run most existing Meerkat carriers.

Change-Id: I00e74a42c33afa782bb6109aab34d91e6f16fbb0
Signed-off-by: Julian Scheel <julian@jusst.de>
Reviewed-by: Alban Bedel <alban.bedel@avionic-design.de>
---
 arch/arm/dts/Makefile                              |   1 +
 arch/arm/dts/tegra124-kein-baseboard.dts           |  66 ++++
 arch/arm/dts/tegra124-meerkat.dtsi                 | 409 +++++++++++++++++++++
 arch/arm/mach-tegra/tegra124/Kconfig               |   9 +
 board/avionic-design/common/meerkat.c              |  57 +++
 .../avionic-design/common/pinmux-config-meerkat.h  | 233 ++++++++++++
 board/avionic-design/kein-baseboard/Kconfig        |  15 +
 board/avionic-design/kein-baseboard/MAINTAINERS    |   7 +
 board/avionic-design/kein-baseboard/Makefile       |   9 +
 configs/kein-baseboard_defconfig                   |  42 +++
 include/configs/kein-baseboard.h                   |  65 ++++
 11 files changed, 913 insertions(+)
 create mode 100644 arch/arm/dts/tegra124-kein-baseboard.dts
 create mode 100644 arch/arm/dts/tegra124-meerkat.dtsi
 create mode 100644 board/avionic-design/common/meerkat.c
 create mode 100644 board/avionic-design/common/pinmux-config-meerkat.h
 create mode 100644 board/avionic-design/kein-baseboard/Kconfig
 create mode 100644 board/avionic-design/kein-baseboard/MAINTAINERS
 create mode 100644 board/avionic-design/kein-baseboard/Makefile
 create mode 100644 configs/kein-baseboard_defconfig
 create mode 100644 include/configs/kein-baseboard.h

Comments

Stephen Warren Sept. 6, 2016, 5:15 p.m. UTC | #1
On 09/05/2016 07:29 AM, Julian Scheel wrote:
> Add support for platforms based on the Meerkat COM module. Includes support
> for the minimal reference platform called Kein Baseboard, which in fact is
> sufficient to run most existing Meerkat carriers.

> diff --git a/arch/arm/dts/tegra124-meerkat.dtsi b/arch/arm/dts/tegra124-meerkat.dtsi

> @@ -0,0 +1,409 @@
> +
> +#include "tegra124.dtsi"

There's an unnecessary blank line at the top of the file.

> diff --git a/board/avionic-design/common/meerkat.c b/board/avionic-design/common/meerkat.c

> +void pinmux_init(void)
> +{
> +	pinmux_set_tristate_input_clamping();

That should be pinmux_clear_tristate_input_clamping();

gpio_config_table() is missing here.

> +	pinmux_config_pingrp_table(meerkat_pingrps,
> +				   ARRAY_SIZE(meerkat_pingrps));
> +
> +	pinmux_config_drvgrp_table(meerkat_drvgrps,
> +				   ARRAY_SIZE(meerkat_drvgrps));

pinmux_config_mipipadctrlgrp_table() is missing here.

Most/all of these are related to not using the latest 
tegra-pinmux-scripts to generate the pin config table; see the comments 
on that below.

> diff --git a/board/avionic-design/common/pinmux-config-meerkat.h b/board/avionic-design/common/pinmux-config-meerkat.h

> +/*
> + * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved.
> + * Copyright (c) 2015, Avionic Design GmbH
> + *
> + * SPDX-License-Identifier: GPL-2.0+
> + */

Can you please also add support for this board to tegra-pinmux-scripts, 
so that anyone can generate this file? That will also allow you to 
re-generate the file using the latest version of tegra-pinmux-scripts 
which will add (a) the missing "this file is auto-generated" notice, (b) 
the GPIO initialization table, (c) the MIPI padctl initialization table.

> diff --git a/configs/kein-baseboard_defconfig b/configs/kein-baseboard_defconfig

> +CONFIG_CMD_EXT4=y

Relative to Jetson TK1, CONFIG_CMD_EXT4_WRITE is missing. Was that 
deliberate? I'd rather keep all the Tegra configs as similar as 
possible, at least in the upstream code.

> +CONFIG_DM_I2C_COMPAT=y

That's not required on any Tegra board these days. Is it necessary?

> +CONFIG_E1000=y

I notice that CONFIG_CMD_MII isn't present, yet Ethernet is. For 
consistency with other Tegra boards, does it make sense to add 
CONFIG_CMD_MII?

> +CONFIG_USB_STORAGE=y

For Jetson TK1, this is defined in include/configs/jetson-tk1.h. I'd 
expect the two board configs to work the same way.

CONFIG_USE_PRIVATE_LIBGCC=y is missing.
Julian Scheel Sept. 6, 2016, 6:14 p.m. UTC | #2
On 06.09.16 19:15, Stephen Warren wrote:
> On 09/05/2016 07:29 AM, Julian Scheel wrote:
>> Add support for platforms based on the Meerkat COM module. Includes
>> support
>> for the minimal reference platform called Kein Baseboard, which in
>> fact is
>> sufficient to run most existing Meerkat carriers.
>
>> diff --git a/arch/arm/dts/tegra124-meerkat.dtsi
>> b/arch/arm/dts/tegra124-meerkat.dtsi
>
>> @@ -0,0 +1,409 @@
>> +
>> +#include "tegra124.dtsi"
>
> There's an unnecessary blank line at the top of the file.

Ack.

>> diff --git a/board/avionic-design/common/meerkat.c
>> b/board/avionic-design/common/meerkat.c
>
>> +void pinmux_init(void)
>> +{
>> +    pinmux_set_tristate_input_clamping();
>
> That should be pinmux_clear_tristate_input_clamping();

Ack.

> gpio_config_table() is missing here.

If I recall correctly we did remove it for some reason. I need to check 
our internal history.

>> +    pinmux_config_pingrp_table(meerkat_pingrps,
>> +                   ARRAY_SIZE(meerkat_pingrps));
>> +
>> +    pinmux_config_drvgrp_table(meerkat_drvgrps,
>> +                   ARRAY_SIZE(meerkat_drvgrps));
>
> pinmux_config_mipipadctrlgrp_table() is missing here.
>
> Most/all of these are related to not using the latest
> tegra-pinmux-scripts to generate the pin config table; see the comments
> on that below.
>> diff --git a/board/avionic-design/common/pinmux-config-meerkat.h
>> b/board/avionic-design/common/pinmux-config-meerkat.h
>
>> +/*
>> + * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved.
>> + * Copyright (c) 2015, Avionic Design GmbH
>> + *
>> + * SPDX-License-Identifier: GPL-2.0+
>> + */
>
> Can you please also add support for this board to tegra-pinmux-scripts,
> so that anyone can generate this file? That will also allow you to
> re-generate the file using the latest version of tegra-pinmux-scripts
> which will add (a) the missing "this file is auto-generated" notice, (b)
> the GPIO initialization table, (c) the MIPI padctl initialization table.

I'll discuss this internally. We have never used those scripts at all, 
but did handwrite this code, based from Jetson code.

>> diff --git a/configs/kein-baseboard_defconfig
>> b/configs/kein-baseboard_defconfig
>
>> +CONFIG_CMD_EXT4=y
>
> Relative to Jetson TK1, CONFIG_CMD_EXT4_WRITE is missing. Was that
> deliberate? I'd rather keep all the Tegra configs as similar as
> possible, at least in the upstream code.

We can add it.

>> +CONFIG_DM_I2C_COMPAT=y
>
> That's not required on any Tegra board these days. Is it necessary?

Good question, probably not. I'll check and remove.

>> +CONFIG_E1000=y
>
> I notice that CONFIG_CMD_MII isn't present, yet Ethernet is. For
> consistency with other Tegra boards, does it make sense to add
> CONFIG_CMD_MII?

We can add it.

>> +CONFIG_USB_STORAGE=y
>
> For Jetson TK1, this is defined in include/configs/jetson-tk1.h. I'd
> expect the two board configs to work the same way.

Actually we have moved this to defconfig, as we decided that all options 
that are Kconfig options by now shall be selectable via Kconfig by the user.

> CONFIG_USE_PRIVATE_LIBGCC=y is missing.

Ack.

Thanks for the review :)
-Julian
Stephen Warren Sept. 6, 2016, 6:53 p.m. UTC | #3
On 09/05/2016 07:29 AM, Julian Scheel wrote:
> Add support for platforms based on the Meerkat COM module. Includes support
> for the minimal reference platform called Kein Baseboard, which in fact is
> sufficient to run most existing Meerkat carriers.

> diff --git a/board/avionic-design/common/meerkat.c b/board/avionic-design/common/meerkat.c

> +int tegra_pcie_board_init(void)

> +	err = as3722_init(&pmic, 4, 0x40);

Thinking about this more: Why I2C bus 4 not 0? All other boards set up 
the PMIC I2C bus to be I2C bus 0 in U-Boot's numbering scheme. I'm not 
sure we should deviate from that since it will provide users (running 
the i2c command at the U-Boot shell) with an inconsistent experience.

Also, 0x40 is the I2C address that's used before this series, so I don't 
think there's a need to pass the value in as a parameter since all 
boards use the same value. In fact, that value is part of the AS3722 HW 
itself, so I'm not sure that it could actually vary, unless there are 
address strapping pins on the chip. Even if so, it seems a bit unlikely 
someone would actually use them to select a non-default address, at 
least in situations likely to be encountered on any Tegra board.
Stephen Warren Sept. 6, 2016, 6:58 p.m. UTC | #4
On 09/06/2016 12:14 PM, Julian Scheel wrote:
> On 06.09.16 19:15, Stephen Warren wrote:
>> On 09/05/2016 07:29 AM, Julian Scheel wrote:
>>> Add support for platforms based on the Meerkat COM module. Includes
>>> support
>>> for the minimal reference platform called Kein Baseboard, which in
>>> fact is
>>> sufficient to run most existing Meerkat carriers.

>>> diff --git a/board/avionic-design/common/pinmux-config-meerkat.h
>>> b/board/avionic-design/common/pinmux-config-meerkat.h
>>
>>> +/*
>>> + * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved.
>>> + * Copyright (c) 2015, Avionic Design GmbH
>>> + *
>>> + * SPDX-License-Identifier: GPL-2.0+
>>> + */
>>
>> Can you please also add support for this board to tegra-pinmux-scripts,
>> so that anyone can generate this file? That will also allow you to
>> re-generate the file using the latest version of tegra-pinmux-scripts
>> which will add (a) the missing "this file is auto-generated" notice, (b)
>> the GPIO initialization table, (c) the MIPI padctl initialization table.
>
> I'll discuss this internally. We have never used those scripts at all,
> but did handwrite this code, based from Jetson code.

Hmm. Do you use the Excel pinmux spreadsheet that NVIDIA syseng 
supplies? That performs a variety of error-checking, so I'd certainly 
advocate using that. If you do, then supporting tegra-pinmux-script is a 
simple matter of saving the spreadsheet as CSV and running the import 
script in tegra-pinmux-scripts. If not, I worry that the spreadsheet's 
error-checking rules haven't been validated.

>>> +CONFIG_USB_STORAGE=y
>>
>> For Jetson TK1, this is defined in include/configs/jetson-tk1.h. I'd
>> expect the two board configs to work the same way.
>
> Actually we have moved this to defconfig, as we decided that all options
> that are Kconfig options by now shall be selectable via Kconfig by the
> user.

Who's "we" here; has this conversion happened in mainline? If so, it 
looks like the author of the conversion commit forgot to convert all the 
existing configuration headers and defconfigs, so someone should go back 
and fix up that commit. If the conversion hasn't happened in mainline, I 
imagine it would be welcome so feel free to send it, but if this series 
gets submitted before the conversion is submitted, it can't assume the 
conversion has happened.
Julian Scheel Sept. 7, 2016, 6:03 a.m. UTC | #5
On 06.09.2016 20:53, Stephen Warren wrote:
> On 09/05/2016 07:29 AM, Julian Scheel wrote:
>> Add support for platforms based on the Meerkat COM module. Includes
>> support
>> for the minimal reference platform called Kein Baseboard, which in
>> fact is
>> sufficient to run most existing Meerkat carriers.
>
>> diff --git a/board/avionic-design/common/meerkat.c
>> b/board/avionic-design/common/meerkat.c
>
>> +int tegra_pcie_board_init(void)
>
>> +    err = as3722_init(&pmic, 4, 0x40);
>
> Thinking about this more: Why I2C bus 4 not 0? All other boards set up
> the PMIC I2C bus to be I2C bus 0 in U-Boot's numbering scheme. I'm not
> sure we should deviate from that since it will provide users (running
> the i2c command at the U-Boot shell) with an inconsistent experience.

Please see the discussion from earlier this year, when I initially sent 
this patches:
http://lists.denx.de/pipermail/u-boot/2016-February/246952.html

Still if you're too unhappy about it now we would change it, but if not 
we'd rather keep it that way. Having a user being confused because of 
different mapping in our l4t kernel and uboot seems to be more likely 
than a user being confused because of different mappings on different 
boards to me.

> Also, 0x40 is the I2C address that's used before this series, so I don't
> think there's a need to pass the value in as a parameter since all
> boards use the same value. In fact, that value is part of the AS3722 HW
> itself, so I'm not sure that it could actually vary, unless there are
> address strapping pins on the chip. Even if so, it seems a bit unlikely
> someone would actually use them to select a non-default address, at
> least in situations likely to be encountered on any Tegra board.

I'd be ok with dropping that. I think Alban simply added it because he 
was at it and it was an obvious parameter which might need to be changed 
sometime.

-Julian
Julian Scheel Sept. 7, 2016, 6:08 a.m. UTC | #6
On 06.09.2016 20:58, Stephen Warren wrote:
> On 09/06/2016 12:14 PM, Julian Scheel wrote:
>> On 06.09.16 19:15, Stephen Warren wrote:
>>> On 09/05/2016 07:29 AM, Julian Scheel wrote:
>>>> Add support for platforms based on the Meerkat COM module. Includes
>>>> support
>>>> for the minimal reference platform called Kein Baseboard, which in
>>>> fact is
>>>> sufficient to run most existing Meerkat carriers.
>
>>>> diff --git a/board/avionic-design/common/pinmux-config-meerkat.h
>>>> b/board/avionic-design/common/pinmux-config-meerkat.h
>>>
>>>> +/*
>>>> + * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved.
>>>> + * Copyright (c) 2015, Avionic Design GmbH
>>>> + *
>>>> + * SPDX-License-Identifier: GPL-2.0+
>>>> + */
>>>
>>> Can you please also add support for this board to tegra-pinmux-scripts,
>>> so that anyone can generate this file? That will also allow you to
>>> re-generate the file using the latest version of tegra-pinmux-scripts
>>> which will add (a) the missing "this file is auto-generated" notice, (b)
>>> the GPIO initialization table, (c) the MIPI padctl initialization table.
>>
>> I'll discuss this internally. We have never used those scripts at all,
>> but did handwrite this code, based from Jetson code.
>
> Hmm. Do you use the Excel pinmux spreadsheet that NVIDIA syseng
> supplies? That performs a variety of error-checking, so I'd certainly
> advocate using that. If you do, then supporting tegra-pinmux-script is a
> simple matter of saving the spreadsheet as CSV and running the import
> script in tegra-pinmux-scripts. If not, I worry that the spreadsheet's
> error-checking rules haven't been validated.

No, we do not use that spreadsheet, but did all pinmux and gpio 
configuration manually. This pinmux has actually matured over more than 
2 years of usage now, so I'm pretty confident it's fine.
But I'll discuss once more whether we can fill the magic excel sheet and 
use tegra-pinmux-scripts.

>>>> +CONFIG_USB_STORAGE=y
>>>
>>> For Jetson TK1, this is defined in include/configs/jetson-tk1.h. I'd
>>> expect the two board configs to work the same way.
>>
>> Actually we have moved this to defconfig, as we decided that all options
>> that are Kconfig options by now shall be selectable via Kconfig by the
>> user.
>
> Who's "we" here; has this conversion happened in mainline? If so, it
> looks like the author of the conversion commit forgot to convert all the
> existing configuration headers and defconfigs, so someone should go back
> and fix up that commit. If the conversion hasn't happened in mainline, I
> imagine it would be welcome so feel free to send it, but if this series
> gets submitted before the conversion is submitted, it can't assume the
> conversion has happened.

Sorry the wording might have been misleading. In this case "we" refers 
to Avionic Design developers. And the discussion was not meant to be 
applicable to u-boot in general, but for our board. We simply found it 
to be useful to allow a maximum grade of u-boot customisation without 
having to change source files.
If you would like to have this discussed in general beforehands, I'd be 
happy to start the discussion on the list. But in that case we might 
resubmit the patch, having the config options synced with jetson-tk1.h, 
just to get these patches finally in.

-Julian
Stephen Warren Sept. 7, 2016, 4:05 p.m. UTC | #7
On 09/07/2016 12:03 AM, Julian Scheel wrote:
> On 06.09.2016 20:53, Stephen Warren wrote:
>> On 09/05/2016 07:29 AM, Julian Scheel wrote:
>>> Add support for platforms based on the Meerkat COM module. Includes
>>> support
>>> for the minimal reference platform called Kein Baseboard, which in
>>> fact is
>>> sufficient to run most existing Meerkat carriers.
>>
>>> diff --git a/board/avionic-design/common/meerkat.c
>>> b/board/avionic-design/common/meerkat.c
>>
>>> +int tegra_pcie_board_init(void)
>>
>>> +    err = as3722_init(&pmic, 4, 0x40);
>>
>> Thinking about this more: Why I2C bus 4 not 0? All other boards set up
>> the PMIC I2C bus to be I2C bus 0 in U-Boot's numbering scheme. I'm not
>> sure we should deviate from that since it will provide users (running
>> the i2c command at the U-Boot shell) with an inconsistent experience.
>
> Please see the discussion from earlier this year, when I initially sent
> this patches:
> http://lists.denx.de/pipermail/u-boot/2016-February/246952.html
>
> Still if you're too unhappy about it now we would change it, but if not
> we'd rather keep it that way. Having a user being confused because of
> different mapping in our l4t kernel and uboot seems to be more likely
> than a user being confused because of different mappings on different
> boards to me.

OK, I guess that's fine. As I mentioned before, let's make sure there 
are aliases for the I2C controllers in the kernel DT file - otherwise, 
there's no guarantee of a particular ordering of I2C adapter IDs.
Stephen Warren Sept. 7, 2016, 4:10 p.m. UTC | #8
On 09/07/2016 12:08 AM, Julian Scheel wrote:
> On 06.09.2016 20:58, Stephen Warren wrote:
>> On 09/06/2016 12:14 PM, Julian Scheel wrote:
>>> On 06.09.16 19:15, Stephen Warren wrote:
>>>> On 09/05/2016 07:29 AM, Julian Scheel wrote:
>>>>> Add support for platforms based on the Meerkat COM module. Includes support
>>>>> for the minimal reference platform called Kein Baseboard, which in fact is
>>>>> sufficient to run most existing Meerkat carriers.

>>>>> +CONFIG_USB_STORAGE=y
>>>>
>>>> For Jetson TK1, this is defined in include/configs/jetson-tk1.h. I'd
>>>> expect the two board configs to work the same way.
>>>
>>> Actually we have moved this to defconfig, as we decided that all options
>>> that are Kconfig options by now shall be selectable via Kconfig by the
>>> user.
>>
>> Who's "we" here; has this conversion happened in mainline? If so, it
>> looks like the author of the conversion commit forgot to convert all the
>> existing configuration headers and defconfigs, so someone should go back
>> and fix up that commit. If the conversion hasn't happened in mainline, I
>> imagine it would be welcome so feel free to send it, but if this series
>> gets submitted before t conversion is submitted, it can't assume the
>> conversion has happened.
>
> Sorry the wording might have been misleading. In this case "we" refers
> to Avionic Design developers. And the discussion was not meant to be
> applicable to u-boot in general, but for our board. We simply found it
> to be useful to allow a maximum grade of u-boot customisation without
> having to change source files.
> If you would like to have this discussed in general beforehands, I'd be
> happy to start the discussion on the list. But in that case we might
> resubmit the patch, having the config options synced with jetson-tk1.h,
> just to get these patches finally in.

Hmm. It looks like CONFIG_USB_STORAGE is defined in Kconfig in mainline, 
so this patch (at least this part) is actually OK. The patch which added 
it to Kconfig in mainline didn't convert all the board config files 
properly, which is why it's still set in many include/configs/*.h. I'll 
contact the author of that patch...
Julian Scheel Sept. 12, 2016, 2:03 p.m. UTC | #9
On 06.09.2016 19:15, Stephen Warren wrote:
>> diff --git a/board/avionic-design/common/meerkat.c
>> b/board/avionic-design/common/meerkat.c
>
>> +void pinmux_init(void)
>> +{
>> +    pinmux_set_tristate_input_clamping();
>
> That should be pinmux_clear_tristate_input_clamping();
>
> gpio_config_table() is missing here.

I checked back our internal history. In fact we had this first (starting 
from Jetson TK1 as base), but later on removed it. The reason for 
removing it, was the assumption that whenever a driver wants to use a 
GPIO it will request it anyway, so that it will be confiured correctly. 
As this init code is generic for our SoM there is no predefined 
functionality for certain GPIOs which would make sense to preinit in the 
bootloader.
In fact we even had some issues when the init was there because 
customers did not expect the pin to be a GPIO and wondered why a certain 
special function did not work as expected.

Do you see any other reason why a gpio init would be really needed here?

-Julian
Stephen Warren Sept. 12, 2016, 4:54 p.m. UTC | #10
On 09/12/2016 08:03 AM, Julian Scheel wrote:
> On 06.09.2016 19:15, Stephen Warren wrote:
>>> diff --git a/board/avionic-design/common/meerkat.c
>>> b/board/avionic-design/common/meerkat.c
>>
>>> +void pinmux_init(void)
>>> +{
>>> +    pinmux_set_tristate_input_clamping();
>>
>> That should be pinmux_clear_tristate_input_clamping();
>>
>> gpio_config_table() is missing here.
>
> I checked back our internal history. In fact we had this first (starting
> from Jetson TK1 as base), but later on removed it. The reason for
> removing it, was the assumption that whenever a driver wants to use a
> GPIO it will request it anyway, so that it will be confiured correctly.
> As this init code is generic for our SoM there is no predefined
> functionality for certain GPIOs which would make sense to preinit in the
> bootloader.
> In fact we even had some issues when the init was there because
> customers did not expect the pin to be a GPIO and wondered why a certain
> special function did not work as expected.
>
> Do you see any other reason why a gpio init would be really needed here?

Definitely. Without explicitly setting a pin to a GPIO, its currently 
muxed special function will be active. If multiple pins are muxed to the 
same signal, it's undefined which pin will actually transmit/receive 
that signal. To avoid such conflicts in the pinmux, any pin that isn't 
actively used needs to be either set to a guaranteed-non-conflicting mux 
function or, much easier, be set to a GPIO input. I suppose if your mux 
table has been manually gone over with a fine toothcomb and you're 100% 
sure there are no conflicts even if no driver requests the GPIO 
functionality on any pin, then you're fine. However, my instinct is that 
this is unlikely.

Note that the pinmux setup in U-Boot should be complete; if a customer 
ends up assigning a particular use to a pin that's otherwise not 
assigned/dedicated by the SOM's design, then the U-Boot pinmux table 
needs to be updated to reflect that. Tegra HW doesn't support changing 
pin mux functions at run-time (it can be done register-wise, but there's 
no guarantee that doing so won't cause at least glitches on the pins 
while changing the mux functions). This means that it's perfectly safe 
to program unused/unassigned pins to GPIO in the U-Boot pinmux tables, 
since the user is required to regenerate those in order to use the pins 
as anything other than GPIO anyway.
Julian Scheel Sept. 19, 2016, 1:35 p.m. UTC | #11
On 12.09.2016 18:54, Stephen Warren wrote:
> On 09/12/2016 08:03 AM, Julian Scheel wrote:
>> On 06.09.2016 19:15, Stephen Warren wrote:
>>>> diff --git a/board/avionic-design/common/meerkat.c
>>>> b/board/avionic-design/common/meerkat.c
>>>
>>>> +void pinmux_init(void)
>>>> +{
>>>> +    pinmux_set_tristate_input_clamping();
>>>
>>> That should be pinmux_clear_tristate_input_clamping();
>>>
>>> gpio_config_table() is missing here.
>>
>> I checked back our internal history. In fact we had this first (starting
>> from Jetson TK1 as base), but later on removed it. The reason for
>> removing it, was the assumption that whenever a driver wants to use a
>> GPIO it will request it anyway, so that it will be confiured correctly.
>> As this init code is generic for our SoM there is no predefined
>> functionality for certain GPIOs which would make sense to preinit in the
>> bootloader.
>> In fact we even had some issues when the init was there because
>> customers did not expect the pin to be a GPIO and wondered why a certain
>> special function did not work as expected.
>>
>> Do you see any other reason why a gpio init would be really needed here?
>
> Definitely. Without explicitly setting a pin to a GPIO, its currently
> muxed special function will be active. If multiple pins are muxed to the
> same signal, it's undefined which pin will actually transmit/receive
> that signal. To avoid such conflicts in the pinmux, any pin that isn't
> actively used needs to be either set to a guaranteed-non-conflicting mux
> function or, much easier, be set to a GPIO input. I suppose if your mux
> table has been manually gone over with a fine toothcomb and you're 100%
> sure there are no conflicts even if no driver requests the GPIO
> functionality on any pin, then you're fine. However, my instinct is that
> this is unlikely.

I'm pretty sure we do not have any conflicts in there ;)

> Note that the pinmux setup in U-Boot should be complete; if a customer
> ends up assigning a particular use to a pin that's otherwise not
> assigned/dedicated by the SOM's design, then the U-Boot pinmux table
> needs to be updated to reflect that. Tegra HW doesn't support changing
> pin mux functions at run-time (it can be done register-wise, but there's
> no guarantee that doing so won't cause at least glitches on the pins
> while changing the mux functions).

Why would you consider a glitch on a pin more harmful when triggered 
from a running kernel compared to be trigerred from u-boot?

Anyway, we'll regenerate a pinmux/gpio init set for the kein-baseboard, 
that fully matches the configuration used in the kernel. Unfortunately 
it'll take me a few more days before I'll get to it.

-Julian
Stephen Warren Sept. 20, 2016, 4:07 p.m. UTC | #12
On 09/19/2016 07:35 AM, Julian Scheel wrote:
> On 12.09.2016 18:54, Stephen Warren wrote:
>> On 09/12/2016 08:03 AM, Julian Scheel wrote:
>>> On 06.09.2016 19:15, Stephen Warren wrote:
>>>>> diff --git a/board/avionic-design/common/meerkat.c
>>>>> b/board/avionic-design/common/meerkat.c
>>>>
>>>>> +void pinmux_init(void)
>>>>> +{
>>>>> +    pinmux_set_tristate_input_clamping();
>>>>
>>>> That should be pinmux_clear_tristate_input_clamping();
>>>>
>>>> gpio_config_table() is missing here.
>>>
>>> I checked back our internal history. In fact we had this first (starting
>>> from Jetson TK1 as base), but later on removed it. The reason for
>>> removing it, was the assumption that whenever a driver wants to use a
>>> GPIO it will request it anyway, so that it will be confiured correctly.
>>> As this init code is generic for our SoM there is no predefined
>>> functionality for certain GPIOs which would make sense to preinit in the
>>> bootloader.
>>> In fact we even had some issues when the init was there because
>>> customers did not expect the pin to be a GPIO and wondered why a certain
>>> special function did not work as expected.
>>>
>>> Do you see any other reason why a gpio init would be really needed here?
>>
>> Definitely. Without explicitly setting a pin to a GPIO, its currently
>> muxed special function will be active. If multiple pins are muxed to the
>> same signal, it's undefined which pin will actually transmit/receive
>> that signal. To avoid such conflicts in the pinmux, any pin that isn't
>> actively used needs to be either set to a guaranteed-non-conflicting mux
>> function or, much easier, be set to a GPIO input. I suppose if your mux
>> table has been manually gone over with a fine toothcomb and you're 100%
>> sure there are no conflicts even if no driver requests the GPIO
>> functionality on any pin, then you're fine. However, my instinct is that
>> this is unlikely.
>
> I'm pretty sure we do not have any conflicts in there ;)
>
>> Note that the pinmux setup in U-Boot should be complete; if a customer
>> ends up assigning a particular use to a pin that's otherwise not
>> assigned/dedicated by the SOM's design, then the U-Boot pinmux table
>> needs to be updated to reflect that. Tegra HW doesn't support changing
>> pin mux functions at run-time (it can be done register-wise, but there's
>> no guarantee that doing so won't cause at least glitches on the pins
>> while changing the mux functions).
>
> Why would you consider a glitch on a pin more harmful when triggered
> from a running kernel compared to be trigerred from u-boot?

I wouldn't.

I've been told by syseng that pins need to be configured once to their 
final setting. If SW attempts to configure only a subset of the pins, 
then likely other pins' default settings will conflict, and the 
conflicts will have to be resolved by programming those conflicting pins 
too. To do that, you have to pick some non-conflicting configuration, 
which may or may not just happen to match the intended final 
configuration. If it doesn't, then the pin will be reprogrammed again 
later, and it's my understanding that is the issue syseng wants to 
avoid. Still, there aren't many details, so it's hard to understand the 
problem completely, and whether it's a practical or theoretical issue. 
IIUC the safest and only supported way is to just program the entire 
pinmux once and completely as early as possible during boot.

> Anyway, we'll regenerate a pinmux/gpio init set for the kein-baseboard,
> that fully matches the configuration used in the kernel. Unfortunately
> it'll take me a few more days before I'll get to it.
>
> -Julian
diff mbox

Patch

diff --git a/arch/arm/dts/Makefile b/arch/arm/dts/Makefile
index 223124e..379367b 100644
--- a/arch/arm/dts/Makefile
+++ b/arch/arm/dts/Makefile
@@ -56,6 +56,7 @@  dtb-$(CONFIG_TEGRA) += tegra20-harmony.dtb \
 	tegra30-tec-ng.dtb \
 	tegra114-dalmore.dtb \
 	tegra124-jetson-tk1.dtb \
+	tegra124-kein-baseboard.dtb \
 	tegra124-nyan-big.dtb \
 	tegra124-venice2.dtb \
 	tegra186-p2771-0000-a02.dtb \
diff --git a/arch/arm/dts/tegra124-kein-baseboard.dts b/arch/arm/dts/tegra124-kein-baseboard.dts
new file mode 100644
index 0000000..75a0b99
--- /dev/null
+++ b/arch/arm/dts/tegra124-kein-baseboard.dts
@@ -0,0 +1,66 @@ 
+/dts-v1/;
+
+#include "tegra124-meerkat.dtsi"
+
+/ {
+	model = "Avionic Design Kein Baseboard";
+	compatible = "ad,kein-baseboard", "ad,meerkat", "nvidia,tegra124";
+
+	chosen {
+		stdout-path = &uartd;
+	};
+
+	serial@70006300 {
+		status = "okay";
+	};
+
+	sdhci@700b0400 {
+		status = "okay";
+	};
+
+	usb@7d000000 {
+		status = "okay";
+	};
+
+	usb@7d004000 {
+		status = "okay";
+	};
+
+	usb@7d008000 {
+		status = "okay";
+	};
+
+	pcie-controller@01003000 {
+		status = "okay";
+
+		pci@1,0 {
+			status = "okay";
+		};
+
+		pci@2,0 {
+			status = "okay";
+		};
+	};
+
+	regulators {
+		vdd_5v0: regulator@100 {
+			compatible = "regulator-fixed";
+			reg = <100>;
+			regulator-name = "+VDD_5V";
+			regulator-min-microvolt = <5000000>;
+			regulator-max-microvolt = <5000000>;
+			regulator-always-on;
+			regulator-boot-on;
+		};
+
+		vdd_3v3: regulator@101 {
+			compatible = "regulator-fixed";
+			reg = <101>;
+			regulator-name = "+VDD_3V3";
+			regulator-min-microvolt = <3300000>;
+			regulator-max-microvolt = <3300000>;
+			regulator-always-on;
+			regulator-boot-on;
+		};
+	};
+};
diff --git a/arch/arm/dts/tegra124-meerkat.dtsi b/arch/arm/dts/tegra124-meerkat.dtsi
new file mode 100644
index 0000000..76af83d
--- /dev/null
+++ b/arch/arm/dts/tegra124-meerkat.dtsi
@@ -0,0 +1,409 @@ 
+
+#include "tegra124.dtsi"
+
+/ {
+	model = "Avionic-Design Meerkat";
+	compatible = "ad,meerkat", "nvidia,tegra124";
+
+	aliases {
+		i2c0 = "/i2c@7000c000";
+		i2c1 = "/i2c@7000c400";
+		i2c2 = "/i2c@7000c500";
+		i2c3 = "/i2c@7000c700";
+		i2c4 = "/i2c@7000d000";
+		i2c5 = "/i2c@7000d100";
+
+		sdhci0 = "/sdhci@700b0600";
+		sdhci1 = "/sdhci@700b0400";
+
+		usb0 = "/usb@7d000000";
+		usb1 = "/usb@7d004000";
+		usb2 = "/usb@7d008000";
+	};
+
+	memory {
+		device_type = "memory";
+		reg = <0x80000000 0x80000000>;
+	};
+
+	pcie-controller@01003000 {
+		avddio-pex-supply = <&vdd_1v05_run>;
+		dvddio-pex-supply = <&vdd_1v05_run>;
+		avdd-pex-pll-supply = <&vdd_1v05_run>;
+		hvdd-pex-supply = <&vdd_3v3_lp0>;
+		hvdd-pex-pll-e-supply = <&vdd_3v3_lp0>;
+		vddio-pex-ctl-supply = <&vdd_3v3_lp0>;
+		avdd-pll-erefe-supply = <&avdd_1v05_run>;
+	};
+
+	/* Expansion GEN1_I2C_* */
+	i2c@7000c000 {
+		clock-frequency = <100000>;
+	};
+
+	/* Expansion GEN2_I2C_* */
+	i2c@7000c400 {
+		clock-frequency = <100000>;
+	};
+
+	/* Expansion CAM_I2C_* */
+	i2c@7000c500 {
+		clock-frequency = <100000>;
+	};
+
+	/* HDMI DDC */
+	hdmi_ddc: i2c@7000c700 {
+		clock-frequency = <100000>;
+	};
+
+	/* Expansion PWR_I2C_*, on-board components */
+	i2c@7000d000 {
+		status = "okay";
+		clock-frequency = <400000>;
+
+		pmic: pmic@40 {
+			compatible = "ams,as3722";
+			reg = <0x40>;
+			interrupts = <0 86 IRQ_TYPE_LEVEL_HIGH>;
+
+			ams,system-power-controller;
+
+			#interrupt-cells = <2>;
+			interrupt-controller;
+
+			gpio-controller;
+			#gpio-cells = <2>;
+
+			pinctrl-names = "default";
+			pinctrl-0 = <&as3722_default>;
+
+			as3722_default: pinmux {
+				gpio0 {
+					pins = "gpio0";
+					function = "gpio";
+					bias-pull-down;
+				};
+
+				gpio1_2_4_7 {
+					pins = "gpio1", "gpio2", "gpio4", "gpio7";
+					function = "gpio";
+					bias-pull-up;
+				};
+
+				gpio3_5_6 {
+					pins = "gpio3", "gpio5", "gpio6";
+					bias-high-impedance;
+				};
+			};
+
+			regulators {
+				vsup-sd2-supply = <&vdd_5v0_sys>;
+				vsup-sd3-supply = <&vdd_5v0_sys>;
+				vsup-sd4-supply = <&vdd_5v0_sys>;
+				vsup-sd5-supply = <&vdd_5v0_sys>;
+				vin-ldo0-supply = <&vdd_1v35_lp0>;
+				vin-ldo1-6-supply = <&vdd_3v3_run>;
+				vin-ldo2-5-7-supply = <&vddio_1v8>;
+				vin-ldo3-4-supply = <&vdd_3v3_sys>;
+				vin-ldo9-10-supply = <&vdd_5v0_sys>;
+				vin-ldo11-supply = <&vdd_3v3_run>;
+
+				vdd_cpu: sd0 {
+					regulator-name = "+VDD_CPU_AP";
+					regulator-min-microvolt = <700000>;
+					regulator-max-microvolt = <1400000>;
+					regulator-min-microamp = <3500000>;
+					regulator-max-microamp = <3500000>;
+					regulator-always-on;
+					regulator-boot-on;
+					ams,ext-control = <2>;
+				};
+
+				sd1 {
+					regulator-name = "+VDD_CORE";
+					regulator-min-microvolt = <700000>;
+					regulator-max-microvolt = <1350000>;
+					regulator-min-microamp = <2500000>;
+					regulator-max-microamp = <2500000>;
+					regulator-always-on;
+					regulator-boot-on;
+					ams,ext-control = <1>;
+				};
+
+				vdd_1v35_lp0: sd2 {
+					regulator-name = "+1V35_LP0(sd2)";
+					regulator-min-microvolt = <1350000>;
+					regulator-max-microvolt = <1350000>;
+					regulator-always-on;
+					regulator-boot-on;
+				};
+
+				sd3 {
+					regulator-name = "+1V35_LP0(sd3)";
+					regulator-min-microvolt = <1350000>;
+					regulator-max-microvolt = <1350000>;
+					regulator-always-on;
+					regulator-boot-on;
+				};
+
+				vdd_1v05_run: sd4 {
+					regulator-name = "+1V05_RUN";
+					regulator-min-microvolt = <1050000>;
+					regulator-max-microvolt = <1050000>;
+				};
+
+				vddio_1v8: sd5 {
+					regulator-name = "+1V8_VDDIO";
+					regulator-min-microvolt = <1800000>;
+					regulator-max-microvolt = <1800000>;
+					regulator-boot-on;
+					regulator-always-on;
+				};
+
+				vdd_gpu: sd6 {
+					regulator-name = "+VDD_GPU_AP";
+					regulator-min-microvolt = <650000>;
+					regulator-max-microvolt = <1200000>;
+					regulator-min-microamp = <3500000>;
+					regulator-max-microamp = <3500000>;
+					regulator-boot-on;
+					regulator-always-on;
+				};
+
+				avdd_1v05_run: ldo0 {
+					regulator-name = "+1V05_RUN_AVDD";
+					regulator-min-microvolt = <1050000>;
+					regulator-max-microvolt = <1050000>;
+					regulator-boot-on;
+					regulator-always-on;
+					ams,ext-control = <1>;
+				};
+
+				ldo1 {
+					regulator-name = "+1V8_RUN_CAM";
+					regulator-min-microvolt = <1800000>;
+					regulator-max-microvolt = <1800000>;
+				};
+
+				ldo2 {
+					regulator-name = "+1V2_GEN_AVDD";
+					regulator-min-microvolt = <1200000>;
+					regulator-max-microvolt = <1200000>;
+					regulator-boot-on;
+					regulator-always-on;
+				};
+
+				ldo3 {
+					regulator-name = "+1V05_LP0_VDD_RTC";
+					regulator-min-microvolt = <1000000>;
+					regulator-max-microvolt = <1000000>;
+					regulator-boot-on;
+					regulator-always-on;
+					ams,enable-tracking;
+				};
+
+				ldo4 {
+					regulator-name = "+2V8_RUN_CAM";
+					regulator-min-microvolt = <2800000>;
+					regulator-max-microvolt = <2800000>;
+				};
+
+				ldo5 {
+					regulator-name = "+1V2_RUN_CAM_FRONT";
+					regulator-min-microvolt = <1200000>;
+					regulator-max-microvolt = <1200000>;
+				};
+
+				vddio_sdmmc3: ldo6 {
+					regulator-name = "+VDDIO_SDMMC3";
+					regulator-min-microvolt = <1800000>;
+					regulator-max-microvolt = <3300000>;
+				};
+
+				ldo7 {
+					regulator-name = "+1V05_RUN_CAM_REAR";
+					regulator-min-microvolt = <1050000>;
+					regulator-max-microvolt = <1050000>;
+				};
+
+				ldo9 {
+					regulator-name = "+3V3_RUN_TOUCH";
+					regulator-min-microvolt = <2800000>;
+					regulator-max-microvolt = <2800000>;
+				};
+
+				ldo10 {
+					regulator-name = "+2V8_RUN_CAM_AF";
+					regulator-min-microvolt = <2800000>;
+					regulator-max-microvolt = <2800000>;
+				};
+
+				ldo11 {
+					regulator-name = "+1V8_RUN_VPP_FUSE";
+					regulator-min-microvolt = <1800000>;
+					regulator-max-microvolt = <1800000>;
+				};
+			};
+		};
+	};
+
+	i2c@7000d100 {
+		clock-frequency = <400000>;
+	};
+
+	spi@7000d400 {
+		spi-max-frequency = <25000000>;
+	};
+
+	spi@7000da00 {
+		spi-max-frequency = <25000000>;
+	};
+
+	padctl@7009f000 {
+		pinctrl-0 = <&padctl_default>;
+		pinctrl-names = "default";
+
+		padctl_default: pinmux {
+			usb3 {
+				nvidia,lanes = "pcie-0", "pcie-1";
+				nvidia,function = "usb3";
+				nvidia,iddq = <0>;
+			};
+
+			pcie {
+				nvidia,lanes = "pcie-2", "pcie-3",
+					       "pcie-4";
+				nvidia,function = "pcie";
+				nvidia,iddq = <0>;
+			};
+
+			sata {
+				nvidia,lanes = "sata-0";
+				nvidia,function = "sata";
+				nvidia,iddq = <0>;
+			};
+		};
+	};
+
+	sdhci@700b0400 {
+		cd-gpios = <&gpio TEGRA_GPIO(V, 2) GPIO_ACTIVE_LOW>;
+		power-gpios = <&gpio TEGRA_GPIO(R, 0) GPIO_ACTIVE_HIGH>;
+		bus-width = <4>;
+	};
+
+	sdhci@700b0600 {
+		status = "okay";
+		bus-width = <8>;
+	};
+
+	usb@7d000000 {
+		dr_mode = "otg";
+		nvidia,vbus-gpio = <&gpio TEGRA_GPIO(N, 4) GPIO_ACTIVE_HIGH>;
+	};
+
+	usb@7d004000 {
+		phy_type = "utmi";
+		nvidia,vbus-gpio = <&gpio TEGRA_GPIO(N, 5) GPIO_ACTIVE_HIGH>;
+	};
+
+	usb@7d008000 {
+		nvidia,vbus-gpio = <&gpio TEGRA_GPIO(FF, 1) GPIO_ACTIVE_HIGH>;
+	};
+
+	clocks {
+		compatible = "simple-bus";
+		#address-cells = <1>;
+		#size-cells = <0>;
+
+		clk32k_in: clock@0 {
+			compatible = "fixed-clock";
+			reg = <0>;
+			#clock-cells = <0>;
+			clock-frequency = <32768>;
+		};
+	};
+
+	regulators {
+		compatible = "simple-bus";
+		#address-cells = <1>;
+		#size-cells = <0>;
+
+		vdd_mux: regulator@0 {
+			compatible = "regulator-fixed";
+			reg = <0>;
+			regulator-name = "+VDD_MUX";
+			regulator-min-microvolt = <12000000>;
+			regulator-max-microvolt = <12000000>;
+			regulator-always-on;
+			regulator-boot-on;
+			vin-supply = <&vdd_5v0>;
+		};
+
+		vdd_5v0_sys: regulator@1 {
+			compatible = "regulator-fixed";
+			reg = <1>;
+			regulator-name = "+5V_SYS";
+			regulator-min-microvolt = <5000000>;
+			regulator-max-microvolt = <5000000>;
+			regulator-always-on;
+			regulator-boot-on;
+			vin-supply = <&vdd_mux>;
+		};
+
+		vdd_3v3_sys: regulator@2 {
+			compatible = "regulator-fixed";
+			reg = <2>;
+			regulator-name = "+3.3V_SYS";
+			regulator-min-microvolt = <3300000>;
+			regulator-max-microvolt = <3300000>;
+			regulator-always-on;
+			regulator-boot-on;
+			vin-supply = <&vdd_3v3>;
+		};
+
+		vdd_3v3_run: regulator@3 {
+			compatible = "regulator-fixed";
+			reg = <3>;
+			regulator-name = "+3.3V_RUN";
+			regulator-min-microvolt = <3300000>;
+			regulator-max-microvolt = <3300000>;
+			regulator-always-on;
+			regulator-boot-on;
+			gpio = <&pmic 1 GPIO_ACTIVE_HIGH>;
+			enable-active-high;
+			vin-supply = <&vdd_3v3_sys>;
+		};
+
+		vdd_3v3_hdmi: regulator@4 {
+			compatible = "regulator-fixed";
+			reg = <4>;
+			regulator-name = "+3.3V_AVDD_HDMI_AP_GATED";
+			regulator-min-microvolt = <3300000>;
+			regulator-max-microvolt = <3300000>;
+			vin-supply = <&vdd_3v3_run>;
+		};
+
+		vdd_3v3_lp0: regulator@5 {
+			compatible = "regulator-fixed";
+			reg = <5>;
+			regulator-name = "+3.3V_LP0";
+			regulator-min-microvolt = <3300000>;
+			regulator-max-microvolt = <3300000>;
+			regulator-always-on;
+			regulator-boot-on;
+			gpio = <&pmic 2 GPIO_ACTIVE_HIGH>;
+			enable-active-high;
+			vin-supply = <&vdd_3v3_sys>;
+		};
+
+		vdd_hdmi_pll: regulator@6 {
+			compatible = "regulator-fixed";
+			reg = <6>;
+			regulator-name = "+1.05V_RUN_AVDD_HDMI_PLL";
+			regulator-min-microvolt = <1050000>;
+			regulator-max-microvolt = <1050000>;
+			gpio = <&gpio TEGRA_GPIO(H, 7) GPIO_ACTIVE_LOW>;
+			vin-supply = <&vdd_1v05_run>;
+		};
+	};
+};
diff --git a/arch/arm/mach-tegra/tegra124/Kconfig b/arch/arm/mach-tegra/tegra124/Kconfig
index f3324ff..dd65d5d 100644
--- a/arch/arm/mach-tegra/tegra124/Kconfig
+++ b/arch/arm/mach-tegra/tegra124/Kconfig
@@ -21,6 +21,14 @@  config TARGET_NYAN_BIG
 config TARGET_VENICE2
 	bool "NVIDIA Tegra124 Venice2"
 
+config TARGET_KEIN_BASEBOARD
+	bool "Avionic Design Kein Baseboard"
+	select CPU_V7_HAS_NONSEC if !SPL_BUILD
+	select CPU_V7_HAS_VIRT if !SPL_BUILD
+	help
+	  Minimal baseboard for Avionic Design Meerkat COM. Should work with most
+	  baseboard that follow the reference design.
+
 endchoice
 
 config SYS_SOC
@@ -29,5 +37,6 @@  config SYS_SOC
 source "board/nvidia/jetson-tk1/Kconfig"
 source "board/nvidia/nyan-big/Kconfig"
 source "board/nvidia/venice2/Kconfig"
+source "board/avionic-design/kein-baseboard/Kconfig"
 
 endif
diff --git a/board/avionic-design/common/meerkat.c b/board/avionic-design/common/meerkat.c
new file mode 100644
index 0000000..30def80
--- /dev/null
+++ b/board/avionic-design/common/meerkat.c
@@ -0,0 +1,57 @@ 
+/*
+ * (C) Copyright 2014, NVIDIA Corporation <www.nvidia.com>
+ * (C) Copyright 2015, Avionic Design <www.avionic-design.de>
+ *
+ * SPDX-License-Identifier:     GPL-2.0+
+ */
+
+#include <common.h>
+#include <errno.h>
+#include <power/as3722.h>
+
+#include <asm/arch/gpio.h>
+#include <asm/arch/pinmux.h>
+#include "pinmux-config-meerkat.h"
+
+/*
+ * Routine: pinmux_init
+ * Description: Do individual peripheral pinmux configs
+ */
+void pinmux_init(void)
+{
+	pinmux_set_tristate_input_clamping();
+
+	pinmux_config_pingrp_table(meerkat_pingrps,
+				   ARRAY_SIZE(meerkat_pingrps));
+
+	pinmux_config_drvgrp_table(meerkat_drvgrps,
+				   ARRAY_SIZE(meerkat_drvgrps));
+}
+
+#ifdef CONFIG_PCI_TEGRA
+int tegra_pcie_board_init(void)
+{
+	struct udevice *pmic;
+	int err;
+
+	err = as3722_init(&pmic, 4, 0x40);
+	if (err) {
+		error("failed to initialize AS3722 PMIC: %d\n", err);
+		return err;
+	}
+
+	err = as3722_sd_enable(pmic, 4);
+	if (err < 0) {
+		error("failed to enable SD4: %d\n", err);
+		return err;
+	}
+
+	err = as3722_sd_set_voltage(pmic, 4, 0x24);
+	if (err < 0) {
+		error("failed to set SD4 voltage: %d\n", err);
+		return err;
+	}
+
+	return 0;
+}
+#endif /* PCI */
diff --git a/board/avionic-design/common/pinmux-config-meerkat.h b/board/avionic-design/common/pinmux-config-meerkat.h
new file mode 100644
index 0000000..6be55fd
--- /dev/null
+++ b/board/avionic-design/common/pinmux-config-meerkat.h
@@ -0,0 +1,233 @@ 
+/*
+ * Copyright (c) 2014, NVIDIA CORPORATION. All rights reserved.
+ * Copyright (c) 2015, Avionic Design GmbH
+ *
+ * SPDX-License-Identifier: GPL-2.0+
+ */
+
+#ifndef _PINMUX_CONFIG_MEERKAT_H_
+#define _PINMUX_CONFIG_MEERKAT_H_
+
+#define PINCFG(_pingrp, _mux, _pull, _tri, _io, _od, _rcv_sel)	\
+	{							\
+		.pingrp		= PMUX_PINGRP_##_pingrp,	\
+		.func		= PMUX_FUNC_##_mux,		\
+		.pull		= PMUX_PULL_##_pull,		\
+		.tristate	= PMUX_TRI_##_tri,		\
+		.io		= PMUX_PIN_##_io,		\
+		.od		= PMUX_PIN_OD_##_od,		\
+		.rcv_sel	= PMUX_PIN_RCV_SEL_##_rcv_sel,	\
+		.lock		= PMUX_PIN_LOCK_DEFAULT,	\
+		.ioreset	= PMUX_PIN_IO_RESET_DEFAULT,	\
+	}
+
+static const struct pmux_pingrp_config meerkat_pingrps[] = {
+	/*     pingrp,                 mux,          pull,   tri,      e_input, od,      rcv_sel */
+	PINCFG(CLK_32K_OUT_PA0,        SOC,          UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(UART3_CTS_N_PA1,        UARTC,        UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP2_FS_PA2,            I2S1,         NORMAL, NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP2_SCLK_PA3,          I2S1,         NORMAL, NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP2_DIN_PA4,           I2S1,         NORMAL, NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP2_DOUT_PA5,          I2S1,         NORMAL, NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC3_CLK_PA6,         SDMMC3,       NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(SDMMC3_CMD_PA7,         SDMMC3,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PB0,                    UARTD,        UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PB1,                    UARTD,        UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC3_DAT3_PB4,        SDMMC3,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC3_DAT2_PB5,        SDMMC3,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC3_DAT1_PB6,        SDMMC3,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC3_DAT0_PB7,        SDMMC3,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(UART3_RTS_N_PC0,        UARTC,        NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(UART2_TXD_PC2,          IRDA,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(UART2_RXD_PC3,          IRDA,         UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(GEN1_I2C_SCL_PC4,       I2C1,         NORMAL, NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(GEN1_I2C_SDA_PC5,       I2C1,         NORMAL, NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(PC7,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PG0,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PG1,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PG2,                    DEFAULT,      DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PG3,                    DEFAULT,      DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PG4,                    SPI4,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PG5,                    SPI4,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PG6,                    SPI4,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PG7,                    SPI4,         NORMAL, NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PH0,                    GMI,          DOWN,   TRISTATE, OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PH1,                    PWM1,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PH2,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PH3,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PH4,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PH5,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PH6,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PH7,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PI0,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PI1,                    RSVD1,        DOWN,   TRISTATE, OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PI2,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PI3,                    SPI4,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PI4,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PI5,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PI6,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PI7,                    RSVD1,        DOWN,   TRISTATE, OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PJ0,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PJ2,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(UART2_CTS_N_PJ5,        UARTB,        UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(UART2_RTS_N_PJ6,        UARTB,        NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PJ7,                    UARTD,        NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PK0,                    SOC,          UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PK1,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PK2,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PK3,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PK4,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(SPDIF_OUT_PK5,          DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(SPDIF_IN_PK6,           DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PK7,                    UARTD,        NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(DAP1_FS_PN0,            I2S0,         DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP1_DIN_PN1,           I2S0,         DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP1_DOUT_PN2,          SATA,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(DAP1_SCLK_PN3,          I2S0,         DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(USB_VBUS_EN0_PN4,       USB,          UP,     NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(USB_VBUS_EN1_PN5,       USB,          UP,     NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(HDMI_INT_PN7,           DEFAULT,      DOWN,   NORMAL,   INPUT,   DEFAULT, NORMAL),
+	PINCFG(ULPI_DATA7_PO0,         DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(ULPI_DATA0_PO1,         DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(ULPI_DATA1_PO2,         DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(ULPI_DATA2_PO3,         DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(ULPI_DATA3_PO4,         DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(ULPI_DATA4_PO5,         DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(ULPI_DATA5_PO6,         DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(ULPI_DATA6_PO7,         DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP3_FS_PP0,            DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(DAP3_DIN_PP1,           DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(DAP3_DOUT_PP2,          DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(DAP3_SCLK_PP3,          RSVD3,        DOWN,   TRISTATE, OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(DAP4_FS_PP4,            I2S3,         DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP4_DIN_PP5,           I2S3,         DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP4_DOUT_PP6,          I2S3,         DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP4_SCLK_PP7,          I2S3,         DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_COL0_PQ0,            DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_COL1_PQ1,            DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_COL2_PQ2,            DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_COL3_PQ3,            KBC,          DOWN,   TRISTATE, OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_COL4_PQ4,            SDMMC3,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_COL5_PQ5,            DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_COL6_PQ6,            DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_COL7_PQ7,            DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_ROW0_PR0,            DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_ROW1_PR1,            DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_ROW2_PR2,            DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_ROW3_PR3,            SYS,          NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_ROW4_PR4,            DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_ROW5_PR5,            DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_ROW6_PR6,            DISPLAYA_ALT, DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_ROW7_PR7,            DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_ROW8_PS0,            DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_ROW9_PS1,            RSVD2,        NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_ROW10_PS2,           RSVD2,        UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_ROW11_PS3,           DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_ROW12_PS4,           DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_ROW13_PS5,           DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_ROW14_PS6,           DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_ROW15_PS7,           SOC,          UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(KB_ROW16_PT0,           DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(KB_ROW17_PT1,           DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(GEN2_I2C_SCL_PT5,       I2C2,         NORMAL, NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(GEN2_I2C_SDA_PT6,       I2C2,         NORMAL, NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(SDMMC4_CMD_PT7,         SDMMC4,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PU0,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PU1,                    DEFAULT,      DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PU2,                    DEFAULT,      DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PU3,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PU4,                    DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PU5,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PU6,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PV0,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PV1,                    DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC3_CD_N_PV2,        SDMMC3,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC1_WP_N_PV3,        SDMMC1,       DOWN,   TRISTATE, OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(DDC_SCL_PV4,            I2C4,         NORMAL, NORMAL,   INPUT,   DEFAULT, NORMAL),
+	PINCFG(DDC_SDA_PV5,            I2C4,         NORMAL, NORMAL,   INPUT,   DEFAULT, NORMAL),
+	PINCFG(GPIO_W2_AUD_PW2,        DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(GPIO_W3_AUD_PW3,        DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DAP_MCLK1_PW4,          EXTPERIPH1,   NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(CLK2_OUT_PW5,           EXTPERIPH2,   NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(UART3_TXD_PW6,          UARTC,        NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(UART3_RXD_PW7,          UARTC,        UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DVFS_PWM_PX0,           CLDVFS,       NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(GPIO_X1_AUD_PX1,        DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(DVFS_CLK_PX2,           CLDVFS,       NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(GPIO_X3_AUD_PX3,        DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(GPIO_X4_AUD_PX4,        DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(GPIO_X5_AUD_PX5,        DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(GPIO_X6_AUD_PX6,        DEFAULT,      UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(GPIO_X7_AUD_PX7,        DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(ULPI_CLK_PY0,           SPI1,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(ULPI_DIR_PY1,           SPI1,         DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(ULPI_NXT_PY2,           SPI1,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(ULPI_STP_PY3,           SPI1,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(SDMMC1_DAT3_PY4,        SDMMC1,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC1_DAT2_PY5,        SDMMC1,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC1_DAT1_PY6,        SDMMC1,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC1_DAT0_PY7,        SDMMC1,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC1_CLK_PZ0,         SDMMC1,       NORMAL, NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC1_CMD_PZ1,         SDMMC1,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PWR_I2C_SCL_PZ6,        I2CPWR,       NORMAL, NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(PWR_I2C_SDA_PZ7,        I2CPWR,       NORMAL, NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(SDMMC4_DAT0_PAA0,       SDMMC4,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC4_DAT1_PAA1,       SDMMC4,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC4_DAT2_PAA2,       SDMMC4,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC4_DAT3_PAA3,       SDMMC4,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC4_DAT4_PAA4,       SDMMC4,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC4_DAT5_PAA5,       SDMMC4,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC4_DAT6_PAA6,       SDMMC4,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC4_DAT7_PAA7,       SDMMC4,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PBB0,                   VIMCLK2_ALT,  NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(CAM_I2C_SCL_PBB1,       I2C3,         NORMAL, NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(CAM_I2C_SDA_PBB2,       I2C3,         NORMAL, NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(PBB3,                   DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PBB4,                   VGP4,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PBB5,                   DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PBB6,                   DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PBB7,                   DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(CAM_MCLK_PCC0,          VI_ALT3,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PCC1,                   DEFAULT,      DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PCC2,                   DEFAULT,      DOWN,   NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC4_CLK_PCC4,        SDMMC4,       NORMAL, NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(CLK2_REQ_PCC5,          DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PEX_L0_RST_N_PDD1,      PE0,          NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PEX_L0_CLKREQ_N_PDD2,   PE0,          UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PEX_WAKE_N_PDD3,        PE,           UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(PEX_L1_RST_N_PDD5,      PE1,          NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PEX_L1_CLKREQ_N_PDD6,   PE1,          UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(CLK3_OUT_PEE0,          EXTPERIPH3,   NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(CLK3_REQ_PEE1,          DEFAULT,      NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(DAP_MCLK1_REQ_PEE2,     SATA,         NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(HDMI_CEC_PEE3,          CEC,          NORMAL, NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(SDMMC3_CLK_LB_OUT_PEE4, SDMMC3,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(SDMMC3_CLK_LB_IN_PEE5,  SDMMC3,       UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(DP_HPD_PFF0,            DP,           UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(USB_VBUS_EN2_PFF1,      USB,          UP,     NORMAL,   INPUT,   ENABLE,  DEFAULT),
+	PINCFG(PFF2,                   DEFAULT,      UP,     NORMAL,   INPUT,   DISABLE, DEFAULT),
+	PINCFG(CORE_PWR_REQ,           PWRON,        NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(CPU_PWR_REQ,            RSVD2,        NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(PWR_INT_N,              PMI,          UP,     NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(RESET_OUT_N,            RESET_OUT_N,  NORMAL, NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+	PINCFG(OWR,                    RSVD2,        DOWN,   TRISTATE, OUTPUT,  DEFAULT, NORMAL),
+	PINCFG(CLK_32K_IN,             RSVD2,        NORMAL, NORMAL,   INPUT,   DEFAULT, DEFAULT),
+	PINCFG(JTAG_RTCK,              RTCK,         UP,     NORMAL,   OUTPUT,  DEFAULT, DEFAULT),
+};
+
+#define DRVCFG(_drvgrp, _slwf, _slwr, _drvup, _drvdn, _lpmd, _schmt, _hsm) \
+	{						\
+		.drvgrp = PMUX_DRVGRP_##_drvgrp,	\
+		.slwf   = _slwf,			\
+		.slwr   = _slwr,			\
+		.drvup  = _drvup,			\
+		.drvdn  = _drvdn,			\
+		.lpmd   = PMUX_LPMD_##_lpmd,		\
+		.schmt  = PMUX_SCHMT_##_schmt,		\
+		.hsm    = PMUX_HSM_##_hsm,		\
+	}
+
+static const struct pmux_drvgrp_config meerkat_drvgrps[] = {
+};
+
+#endif /* PINMUX_CONFIG_MEERKAT_H */
diff --git a/board/avionic-design/kein-baseboard/Kconfig b/board/avionic-design/kein-baseboard/Kconfig
new file mode 100644
index 0000000..a185a54
--- /dev/null
+++ b/board/avionic-design/kein-baseboard/Kconfig
@@ -0,0 +1,15 @@ 
+if TARGET_KEIN_BASEBOARD
+
+config SYS_BOARD
+	string
+	default "kein-baseboard"
+
+config SYS_VENDOR
+	string
+	default "avionic-design"
+
+config SYS_CONFIG_NAME
+	string
+	default "kein-baseboard"
+
+endif
diff --git a/board/avionic-design/kein-baseboard/MAINTAINERS b/board/avionic-design/kein-baseboard/MAINTAINERS
new file mode 100644
index 0000000..4fa20a9
--- /dev/null
+++ b/board/avionic-design/kein-baseboard/MAINTAINERS
@@ -0,0 +1,7 @@ 
+Kein Baseboard
+M:	Julian Scheel <julian@jusst.de>
+M:	Alban Bedel <alban.bedel@avionic-design.de>
+S:	Maintained
+F:	board/avionic-design/kein-baseboard
+F:	include/configs/kein-baseboard.h
+F:	configs/kein-baseboard_defconfig
diff --git a/board/avionic-design/kein-baseboard/Makefile b/board/avionic-design/kein-baseboard/Makefile
new file mode 100644
index 0000000..59760f6
--- /dev/null
+++ b/board/avionic-design/kein-baseboard/Makefile
@@ -0,0 +1,9 @@ 
+#
+# (C) Copyright 2015
+# Avionic Design GmbH <www.avionic-design.de>
+#
+# SPDX-License-Identifier:      GPL-2.0+
+#
+
+obj-y	+= ../../nvidia/venice2/as3722_init.o
+obj-y	+= ../common/meerkat.o
diff --git a/configs/kein-baseboard_defconfig b/configs/kein-baseboard_defconfig
new file mode 100644
index 0000000..497a6e4
--- /dev/null
+++ b/configs/kein-baseboard_defconfig
@@ -0,0 +1,42 @@ 
+CONFIG_ARM=y
+CONFIG_TEGRA=y
+CONFIG_SPL_DM=y
+CONFIG_TEGRA124=y
+CONFIG_TARGET_KEIN_BASEBOARD=y
+CONFIG_DEFAULT_DEVICE_TREE="tegra124-kein-baseboard"
+CONFIG_FIT=y
+CONFIG_FIT_SIGNATURE=y
+CONFIG_HUSH_PARSER=y
+CONFIG_SYS_PROMPT="Tegra124 (kein-baseboard) # "
+CONFIG_CMD_BOOTZ=y
+# CONFIG_CMD_IMLS is not set
+# CONFIG_CMD_FLASH is not set
+CONFIG_CMD_MMC=y
+CONFIG_CMD_I2C=y
+CONFIG_CMD_USB=y
+CONFIG_CMD_DFU=y
+CONFIG_CMD_USB_MASS_STORAGE=y
+# CONFIG_CMD_FPGA is not set
+CONFIG_CMD_GPIO=y
+# CONFIG_CMD_SETEXPR is not set
+CONFIG_CMD_DHCP=y
+# CONFIG_CMD_NFS is not set
+CONFIG_CMD_PING=y
+CONFIG_CMD_EXT2=y
+CONFIG_CMD_EXT4=y
+CONFIG_CMD_FAT=y
+CONFIG_CMD_FS_GENERIC=y
+CONFIG_DM_I2C_COMPAT=y
+CONFIG_E1000=y
+CONFIG_CMD_E1000=y
+CONFIG_PCI_TEGRA=y
+CONFIG_SYS_NS16550=y
+CONFIG_USB=y
+CONFIG_DM_USB=y
+CONFIG_USB_STORAGE=y
+CONFIG_USB_GADGET=y
+CONFIG_CI_UDC=y
+CONFIG_USB_GADGET_DOWNLOAD=y
+CONFIG_G_DNL_MANUFACTURER="NVIDIA"
+CONFIG_G_DNL_VENDOR_NUM=0x0955
+CONFIG_G_DNL_PRODUCT_NUM=0x701a
diff --git a/include/configs/kein-baseboard.h b/include/configs/kein-baseboard.h
new file mode 100644
index 0000000..e1e8eb8
--- /dev/null
+++ b/include/configs/kein-baseboard.h
@@ -0,0 +1,65 @@ 
+/*
+ * (C) Copyright 2014-2016 Avionic Design GmbH
+ *
+ * SPDX-License-Identifier:     GPL-2.0
+ */
+
+#ifndef __CONFIG_H
+#define __CONFIG_H
+
+#include <linux/sizes.h>
+
+/* enable PMIC */
+#define CONFIG_AS3722_POWER
+
+#include "tegra124-common.h"
+
+/* High-level configuration options */
+#define CONFIG_TEGRA_BOARD_STRING	"Avionic-Design Kein Baseboard"
+
+/* Board-specific serial config */
+#define CONFIG_TEGRA_ENABLE_UARTD
+#define CONFIG_SYS_NS16550_COM1		NV_PA_APB_UARTD_BASE
+
+/* I2C */
+#define CONFIG_SYS_I2C_TEGRA
+
+/* SD/MMC */
+#define CONFIG_MMC
+#define CONFIG_GENERIC_MMC
+#define CONFIG_TEGRA_MMC
+#define CONFIG_CMD_GPT
+#define CONFIG_RANDOM_UUID
+
+/* Environment in eMMC, at the end of 2nd "boot sector" */
+#define CONFIG_ENV_IS_IN_MMC
+#define CONFIG_ENV_OFFSET		(-CONFIG_ENV_SIZE)
+#define CONFIG_SYS_MMC_ENV_DEV		0
+#define CONFIG_SYS_MMC_ENV_PART		2
+
+/* USB Host support */
+#define CONFIG_USB_EHCI
+#define CONFIG_USB_EHCI_TEGRA
+
+/* USB networking support */
+#define CONFIG_USB_HOST_ETHER
+#define CONFIG_USB_ETHER_RNDIS
+#define CONFIG_USB_ETHER_ASIX
+#define CONFIG_USB_ETHER_ASIX88179
+#define CONFIG_USB_ETHER_MCS7830
+#define CONFIG_USB_ETHER_SMSC95XX
+
+/* PCI host support */
+#define CONFIG_PCI
+#define CONFIG_PCI_PNP
+#define CONFIG_CMD_PCI
+
+#include "tegra-common-usb-gadget.h"
+#include "tegra-common-post.h"
+
+#define CONFIG_ARMV7_PSCI			1
+/* Reserve top 1M for secure RAM */
+#define CONFIG_ARMV7_SECURE_BASE		0xfff00000
+#define CONFIG_ARMV7_SECURE_RESERVE_SIZE	0x00100000
+
+#endif /* __CONFIG_H */