[Skiboot] [PATCH 04/40] libc/string: add memcpy_from_ci()

Balbir Singh bsingharora at gmail.com
Tue Oct 11 11:08:30 AEDT 2016



On 10/10/16 19:43, Stewart Smith wrote:
> From: Claudio Carvalho <cclaudio at linux.vnet.ibm.com>
> 
> This adds memcpy_from_ci, a cache inhibited version of memcpy, required
> by secure boot. The secure boot verification code is stored in a secure
> ROM and the logic that contains the ROM within the processor is
> implemented in a way that it only responds to CI (cache inhibited)
> operations. Due to performance issues we copy the verification code from
> the secure ROM to RAM and we use memcpy_ci for that.
> 
> What makes memcpy_ci vs ordinary memcpy?
> 

I think the changelog is not properly all converted over, it still has
references to memcpy_ci as opposed to memcpy_from_ci.

> memcpy copies data like in the example below and the compiler translates that
> to load instructions that are not cache inhibited (e.g. lbzx - load byte and
> zero indexed). In other words, the data is cached.
> 
> a[i] = b[i]
> 
> memcpy_ci copies data using the cache inhibited version of load instructions:
> in_8() and in_be32(), both defined in include/io.h. These functions use lbzcix
> and lwzcix assembly instructions, respectively. In this case, the data is not
> cached as required by the logic that contains the ROM.
> 
> *((uint8_t*) destp) = in_8((uint8_t*)srcp);
> *((uint32_t*) destp) = in_be32((uint32_t*)srcp)
> 
> Signed-off-by: Claudio Carvalho <cclaudio at linux.vnet.ibm.com>
> Signed-off-by: Stewart Smith <stewart at linux.vnet.ibm.com>
> ---
>  libc/include/string.h        |  3 ++-
>  libc/string/Makefile.inc     |  9 +++++----
>  libc/string/memcpy_from_ci.c | 47 ++++++++++++++++++++++++++++++++++++++++++++
>  3 files changed, 54 insertions(+), 5 deletions(-)
>  create mode 100644 libc/string/memcpy_from_ci.c
> 
> diff --git a/libc/include/string.h b/libc/include/string.h
> index 890ffc2..e4b4fac 100644
> --- a/libc/include/string.h
> +++ b/libc/include/string.h
> @@ -1,5 +1,5 @@
>  /******************************************************************************
> - * Copyright (c) 2004, 2008 IBM Corporation
> + * Copyright (c) 2004, 2016 IBM Corporation
>   * All rights reserved.
>   * This program and the accompanying materials
>   * are made available under the terms of the BSD License
> @@ -32,6 +32,7 @@ char *strdup(const char *src);
>  void *memset(void *s, int c, size_t n);
>  void *memchr(const void *s, int c, size_t n);
>  void *memcpy(void *dest, const void *src, size_t n);
> +void *memcpy_from_ci(void *destpp, const void *srcpp, size_t len);
>  void *memmove(void *dest, const void *src, size_t n);
>  int memcmp(const void *s1, const void *s2, size_t n);
>  
> diff --git a/libc/string/Makefile.inc b/libc/string/Makefile.inc
> index 3b7c8ce..fb2f037 100644
> --- a/libc/string/Makefile.inc
> +++ b/libc/string/Makefile.inc
> @@ -1,5 +1,5 @@
>  # *****************************************************************************
> -# * Copyright (c) 2004, 2008 IBM Corporation
> +# * Copyright (c) 2004, 2016 IBM Corporation
>  # * All rights reserved.
>  # * This program and the accompanying materials
>  # * are made available under the terms of the BSD License
> @@ -12,9 +12,10 @@
>  
>  SUBDIRS += $(LIBCDIR)/string
>  
> -STRING_OBJS = strcat.o strchr.o strcmp.o strcpy.o strlen.o strncmp.o \
> -	      strncpy.o strstr.o memset.o memcpy.o memmove.o memchr.o \
> -	      memcmp.o strcasecmp.o strncasecmp.o strtok.o strdup.o
> +STRING_OBJS = strcat.o strchr.o strcmp.o strcpy.o strlen.o \
> +	      strncmp.o strncpy.o strstr.o memset.o memcpy.o memcpy_from_ci.o \
> +	      memmove.o memchr.o memcmp.o strcasecmp.o strncasecmp.o \
> +	      strtok.o strdup.o
>  STRING = $(LIBCDIR)/string/built-in.o
>  $(STRING): $(STRING_OBJS:%=$(LIBCDIR)/string/%)
>  
> diff --git a/libc/string/memcpy_from_ci.c b/libc/string/memcpy_from_ci.c
> new file mode 100644
> index 0000000..02affa3
> --- /dev/null
> +++ b/libc/string/memcpy_from_ci.c
> @@ -0,0 +1,47 @@
> +/* Copyright 2013-2016 IBM Corp
> + *
> + * 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.
> + */
> +
> +#include <string.h>
> +#include <ccan/short_types/short_types.h>
> +#include <io.h>
> +
> +void* memcpy_from_ci(void *destpp, const void *srcpp, size_t len)
> +{
> +	const size_t block = sizeof(uint64_t);
> +	unsigned long int destp = (long int) destpp;
> +	unsigned long int srcp = (long int) srcpp;
> +
> +	/* Copy as many blocks as possible if srcp is block aligned */
> +	if ((srcp % block) == 0) {
> +		while ((len - block) > -1) {
> +			*((uint64_t*) destp) = in_be64((uint64_t*)srcp);
> +			srcp += block;
> +			destp += block;
> +			len -= block;
> +		}
> +	}
> +	/*
> +	 * Byte-by-byte copy if srcp is not block aligned or len is/becomes
> +	 * less than one block
> +	 */

Can we have a pr_log(PR_devel,..) for unaligned copies to warn users?

Balbir Singh.


More information about the Skiboot mailing list