Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

mcu/nrf5340: Add secure functions package #2899

Merged
merged 2 commits into from
Oct 13, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
1 change: 1 addition & 0 deletions hw/mcu/nordic/nrf5340/pkg.yml
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ pkg.deps:
- "@apache-mynewt-core/hw/mcu/nordic"
- "@apache-mynewt-core/hw/cmsis-core"
- "@apache-mynewt-core/hw/hal"
- "@apache-mynewt-core/hw/mcu/nordic/nrf5340/tfm"

pkg.deps.BUS_DRIVER_PRESENT:
- "@apache-mynewt-core/hw/bus/drivers/spi_hal"
Expand Down
9 changes: 0 additions & 9 deletions hw/mcu/nordic/nrf5340/src/hal_system_start.c
Original file line number Diff line number Diff line change
Expand Up @@ -61,9 +61,6 @@ static const struct periph_id_range ns_peripheral_ids[] = {
#define STRIP_PARENS(X) X
#define UNMANGLE_MYNEWT_VAL(X) STRIP_PARENS(_Args X)

#if MYNEWT_VAL(MCU_GPIO_NET)
static const unsigned int net_gpios[] = { UNMANGLE_MYNEWT_VAL(MYNEWT_VAL(MCU_GPIO_NET)) };
#endif
#if MYNEWT_VAL(MCU_GPIO_PERIPH)
static const unsigned int periph_gpios[] = { UNMANGLE_MYNEWT_VAL(MYNEWT_VAL(MCU_GPIO_PERIPH)) };
#endif
Expand Down Expand Up @@ -121,12 +118,6 @@ hal_system_start(void *img_start)
NRF_SPU->GPIOPORT[0].PERM = 0;
NRF_SPU->GPIOPORT[1].PERM = 0;

#if MYNEWT_VAL(MCU_GPIO_NET)
for (i = 0; i < ARRAY_SIZE(net_gpios); ++i) {
nrf_gpio_pin_mcu_select(net_gpios[i], GPIO_PIN_CNF_MCUSEL_NetworkMCU);
}
#endif

#if MYNEWT_VAL(MCU_GPIO_PERIPH)
for (i = 0; i < ARRAY_SIZE(periph_gpios); ++i) {
nrf_gpio_pin_mcu_select(periph_gpios[i], GPIO_PIN_CNF_MCUSEL_Peripheral);
Expand Down
20 changes: 20 additions & 0 deletions hw/mcu/nordic/nrf5340/src/nrf5340_periph.c
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
#include <bsp/bsp.h>
#include <nrfx.h>
#include "hal/hal_spi.h"
#include "tfm/tfm.h"

#if MYNEWT_VAL(BUS_DRIVER_PRESENT)
#include "bus/bus.h"
Expand Down Expand Up @@ -418,9 +419,28 @@ nrf5340_periph_create_i2c(void)
#endif
}

#define _Args(...) __VA_ARGS__
#define STRIP_PARENS(X) X
#define UNMANGLE_MYNEWT_VAL(X) STRIP_PARENS(_Args X)

static void
nrf5340_net_core_pins(void)
{
#ifdef MYNEWT_VAL_MCU_GPIO_NET
unsigned int gpios[] = { UNMANGLE_MYNEWT_VAL(MYNEWT_VAL(MCU_GPIO_NET)) };
int i;

/* Configure GPIOs for Networking Core */
for (i = 0; i < ARRAY_SIZE(gpios); i++) {
tfm_gpio_pin_mcu_select(gpios[i], GPIO_PIN_CNF_MCUSEL_NetworkMCU);
}
#endif
}

void
nrf5340_periph_create(void)
{
nrf5340_net_core_pins();
nrf5340_periph_create_timers();
nrf5340_periph_create_adc();
nrf5340_periph_create_pwm();
Expand Down
55 changes: 55 additions & 0 deletions hw/mcu/nordic/nrf5340/tfm/include/tfm/tfm.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you 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.
*/

#include <stdint.h>
#include <os/mynewt.h>
#include <nrf_gpio.h>

#if (MYNEWT_VAL(BOOT_LOADER) && MYNEWT_VAL(TFM_EXPORT_NSC)) || \
(!MYNEWT_VAL(BOOT_LOADER) && MYNEWT_VAL(MCU_APP_SECURE) && MYNEWT_VAL(TFM_EXPORT_NSC)) || \
(!MYNEWT_VAL(BOOT_LOADER) && !MYNEWT_VAL(MCU_APP_SECURE))
#define SECURE_CALL __attribute__((cmse_nonsecure_entry))
#else
/* Whole application is secure */
#define SECURE_CALL
#endif

#define TFM_ERR_ACCESS_DENIED SYS_EACCES
#define TFM_ERR_INVALID_PARAM SYS_EINVAL

/**
* Read UICR OTP word
*
* @param n - word to read
* @param ret - buffer for received value
* @return 0 on success
* TFM_ERR_INVALID_PARAM - when n is out of range <0-191>
* TFM_ERR_ACCESS_DENIED - when n is denied by secure code
*/
int SECURE_CALL tfm_uicr_otp_read(uint8_t n, uint32_t *ret);

/**
*
* @param pin_number
* @param mcu_sel
* @return 0 on success
* TFM_ERR_INVALID_PARAM - when pin_number is not present on chip
* TFM_ERR_ACCESS_DENIED - when non-secure code is not allowed to change pin's MCU
*/
int SECURE_CALL tfm_gpio_pin_mcu_select(uint32_t pin_number, nrf_gpio_pin_mcusel_t mcu_sel);
37 changes: 37 additions & 0 deletions hw/mcu/nordic/nrf5340/tfm/pkg.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you 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.
#

pkg.name: hw/mcu/nordic/nrf5340/tfm
pkg.description: "NRF5340 secure functions package"
pkg.author: "Apache Mynewt <dev@mynewt.apache.org>"
pkg.homepage: "http://mynewt.apache.org/"
pkg.keywords:
- tfm

pkg.cflags.(BOOT_LOADER && TFM_EXPORT_NSC):
- -mcmse

pkg.cflags.(!BOOT_LOADER && MCU_APP_SECURE && TFM_EXPORT_NSC):
- -mcmse

pkg.cflags.(!BOOT_LOADER && !MCU_APP_SECURE):
- -mcmse

pkg.lflags.(MCU_APP_SECURE && TFM_EXPORT_NSC):
- -utfm_uicr_otp_read
- -utfm_gpio_pin_mcu_select
57 changes: 57 additions & 0 deletions hw/mcu/nordic/nrf5340/tfm/src/tfm.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you 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.
*/

#include <os/mynewt.h>
#include <nrf_gpio.h>
#include <tfm/tfm.h>

int SECURE_CALL
tfm_uicr_otp_read(uint8_t n, uint32_t *ret)
{
int err = 0;

if (n >= 192) {
err = TFM_ERR_INVALID_PARAM;
} else if (n < MYNEWT_VAL(TFM_UICR_OTP_MIN_ADDR) || n > MYNEWT_VAL(TFM_UICR_OTP_MAX_ADDR)) {
err = TFM_ERR_ACCESS_DENIED;
} else {
*ret = NRF_UICR_S->OTP[n];
}

return err;
}

int SECURE_CALL
tfm_gpio_pin_mcu_select(uint32_t pin_number, nrf_gpio_pin_mcusel_t mcu_sel)
{
int err = 0;
uint32_t pin_mask = (1u << (pin_number & 31));

if (!nrf_gpio_pin_present_check(pin_number)) {
err = TFM_ERR_INVALID_PARAM;
} else if (((pin_number < 32) && (MYNEWT_VAL(TFM_MCU_SEL_GPIO0) & pin_mask)) ||
((pin_number >= 32) && (pin_number < 64) &&
(MYNEWT_VAL(TFM_MCU_SEL_GPIO1) & pin_mask))) {
nrf_gpio_pin_mcu_select(pin_number, mcu_sel);
} else {
err = TFM_ERR_ACCESS_DENIED;
}

return err;
}
42 changes: 42 additions & 0 deletions hw/mcu/nordic/nrf5340/tfm/syscfg.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you 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.
#

syscfg.defs:
TFM_EXPORT_NSC:
description: >
Application is secure but there is also unsecure application that
should be able to access some secure functions.
If set to 1 secure function will be exported and can be used by
non secure code.
value:
TFM_MCU_SEL_GPIO0:
description: >
Bit mask of GPIO0 pins that can be assigned between cores by non secure code.
value: 0xFFFFFFFF
TFM_MCU_SEL_GPIO1:
description: >
Bit mask of GPIO1 pins that can be assigned between cores by non secure code.
value: 0xFFFFFFFF
TFM_UICR_OTP_MIN_ADDR:
description: >
Minimum address of UICR OTP that can be read by non-secure core.
value: 0
TFM_UICR_OTP_MAX_ADDR:
description: >
Maximum address of UICR OTP that can be read by non-secure core.
value: 191