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

Adding wolfSSL FIPS Ready Docs #117

Merged
merged 1 commit into from
Dec 21, 2023
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.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 8 additions & 1 deletion Makefile
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
DOCKER_CMD=DOCKER_BUILDKIT=1 docker build -t doc_build --build-arg MANPATH=$(MANPATH) --build-arg PDFFILE=$(PDFFILE) --target=manual --output=build -f Dockerfile .

all: wolfssl wolfssh wolfboot wolfclu wolfcrypt-jni wolfmqtt wolfsentry wolfssl-jni wolftpm wolfengine
all: wolfssl wolfssh wolfboot wolfclu wolfcrypt-jni wolfmqtt wolfsentry wolfssl-jni wolftpm wolfengine fips-ready

build:
@mkdir -p build
Expand Down Expand Up @@ -71,5 +71,12 @@ porting: PDFFILE=wolfSSL-Porting-Guide.pdf
porting: build
@$(DOCKER_CMD)

.PHONY: fips-ready
fips-ready: MANPATH=wolfSSL-FIPS-Ready
fips-ready: PDFFILE=wolfSSL-FIPS-Ready.pdf
fips-ready: build
@$(DOCKER_CMD)


clean:
rm -rf build
1 change: 1 addition & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ To build the documentation you will need Docker running on your system. In this
* `make wolfssl-jni`
* `make wolftpm`
* `make porting`
* `make fips-ready`

## Contributing

Expand Down
24 changes: 24 additions & 0 deletions wolfSSL-FIPS-Ready/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
-include ../common/common.am
.DEFAULT_GOAL := all
all: pdf html


SOURCES = section01.md \
section02.md \
section03.md \
section04.md

ifeq ($(DOC_LANG),JA)
PDF = wolfSSL-FIPS-Ready-ja.pdf
DOXYFILE = Doxyfile-ja
else
PDF = wolfSSL-FIPS-Ready.pdf
DOXYFILE = Doxyfile
endif


.PHONY: html-prep
html-prep:

.PHONY: pdf-prep
pdf-prep:
23 changes: 23 additions & 0 deletions wolfSSL-FIPS-Ready/header.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
% wolfSSL FIPS Ready User Guide ![](logo.png)

---
header-includes:
# Blank pages on new sections
- \usepackage{titlesec}
- \newcommand{\sectionbreak}{\clearpage}
- \let\oldsection\section
- \renewcommand\section{\clearpage\oldsection}
# Fancy page headers
- \usepackage{fancyhdr}
- \pagestyle{fancy}
- \fancyfoot[LO,RE]{COPYRIGHT \copyright 2023 wolfSSL Inc.}
# Wrap long syntax highlighting code blocks
- \usepackage{fvextra}
- \DefineVerbatimEnvironment{Highlighting}{Verbatim}{breaklines,commandchars=\\\{\}}
# Wrap long non-sytax highlighted code blocks
- \usepackage{listings}
- \let\verbatim\undefined
- \let\verbatimend\undefined
- \lstnewenvironment{verbatim}{\lstset{breaklines,basicstyle=\ttfamily}}{}
subparagraph: yes
---
27 changes: 27 additions & 0 deletions wolfSSL-FIPS-Ready/mkdocs.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
site_name: FIPS Ready User Guide
site_url: https://wolfssl.com/
docs_dir: build/html/
site_dir: html/
copyright: Copyright © 2023 wolfSSL Inc.
nav:
- "1. Overview of FIPS Ready": index.md
- "2. Building wolfSSL as FIPS Ready": section02.md
- "3. Changes Since FIPS 140-2 Ready": section03.md
- "4. wolfCrypt FIPS Ready API": section04.md
theme:
name: null
custom_dir: ../mkdocs-material/material
language: en
palette:
primary: indigo
accent: indigo
font:
text: roboto
code: roboto mono
icon: "logo.png"
logo: logo.png
favicon: logo.png
feature:
tabs: true
extra_css: [skin.css]
use_directory_urls: false
73 changes: 73 additions & 0 deletions wolfSSL-FIPS-Ready/src/section01.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
# wolfSSL FIPS Ready

Do you have a project that will need a FIPS approved cryptographic library at
a later date, but want to be ready for it now? wolfSSL FIPS Ready includes the
cryptography layer from the public wolfSSL source tree, along with the FIPS
tooling enabled for a FIPS Ready build. FIPS Ready allows application developers
to assure that they have correctly integrated the necessary FIPS setup, and are
correctly using the API and underlying protocols, providing for a seamless
transition to the full FIPS certified wolfSSL library for an application. When
the time comes, we will shepherd your operating environment through testing and
add it to the wolfCrypt FIPS 140-3 certificate. In special situations, a new
FIPS 140-3 certificate will be required, but we are ready to provide guidance
through the testing and certification process. In both scenarios, FIPS Ready
assures that your application will be fully functional with wolfCrypt as
certified.

FIPS Ready is open source and dual-licensed. wolfSSL Inc distributes FIPS
Ready wolfSSL with the GPLv3 license or can negotiate commercial licensing
terms with support if needed beyond the proof of concept phase.

FIPS is a complicated topic. If you have questions after reviewing this
document, then just contact us at facts -at- wolfssl _dot_ calm. The email
address is obfuscated for the spiders, but the calm is for the calm you’ll feel
when you are FIPS Ready.

## What is Different from a non-FIPS build of wolfSSL?

The wolfCrypt FIPS API provides wrappers for all the approved algorithm
functions that are within the FIPS boundary. The FIPS wrappers can be called
directly, or you can keep calling the original APIs; at compile time the API
is swapped by the headers so that the FIPS wrappers will be called either way.
The FIPS wrapper functions check the status of the internal self-testing before
calling the actual function. If the CAST for that specific algorithm has not
been run at least one time previously it will run the first time the algorithm
is used. Users now have the option to either pre-emptively test algorithms at
start up if they wish to avoid the test running at a later time or they can
just let the test run when the algorithm is used.

The wolfCrypt FIPS 140-3 ready code has a required power-on self-test (POST)
that automatically checks the integrity of the executable in memory, this has
not changed since 140-2, only the known answer tests (KATs) for algorithms not
used by the POST are now conditional upon use. The executable is organized so
the code in the FIPS boundary is contiguous in memory. When the application
using the FIPS code starts up, or the shared library is loaded, the default
entry point of the library is called, and the POST runs automatically. It has
two major parts: the in-core memory check and the known answer tests (KAT) for
the algo used by the POST (HMAC-SHA256).

The POST for HMAC-SHA256 is performed first followed by the in-core memory
test. The code in memory is hashed with HMAC-SHA256. If the hash matches, the
test progresses. Otherwise the FIPS module is placed in an error state and all
calls into the module will fail. In this case, the FIPS source code must be
updated with the correct integrity hash, and only after recompilation can the
module successfully initialize.

All other algorithms in the FIPS boundary are tested with canned data the
first time they are used or optionally whenever the developer wants them to
run. The output is compared to pre-computed known answers. The test values are
all inside the boundary and are checked at the time they are called. Several of
the tests have a random component, for example a sign and verify, so a known
piece of data is signed and then verified with a canned key. The key generation
is tested in a similar fashion.

The FIPS boundary provides confirmation about multiple aspects of your
application. The processing of private key access that will assure proper
unlocking and relocking of keys according to the FIPS specification. The
assurance that no FIPS-forbidden modes or key sizes are being used, along with
proper entropy source setup. FIPS Ready also helps discover conflicts with
outside sub-system integration your application needs, for example determining
if other applications or devices on a network support your new FIPS Ready
cipher suites for communication between each other.


145 changes: 145 additions & 0 deletions wolfSSL-FIPS-Ready/src/section02.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,145 @@
# Building wolfSSL as FIPS Ready

Once you have a copy of the source code unarchived into a directory, building
is similar to normal wolfSSL, but with extra steps.

The following steps assume you are on a Linux or macOS box and are using the
GPLv3 distribution of wolfSSL FIPS Ready to make a shared library to be
installed into the system.

## Unarchive the source

```
$ tar xzvf wolfssl-5.6.4-gplv3-fips-ready.tar.gz
```

This unarchives the source into the directory wolfssl-5.6.4-gplv3-fips-ready.
Change into this directory. If you received a commercial release, replace
gplv3 with commercial and .tar.gz with .7z and tar xzvf with 7z x -p<password>
found in the distribution email.

## Configure the build.

```
$ ./configure --enable-fips=ready
```

This command configures the Makefile to build wolfSSL for FIPS Ready.

## Make the library.

```
$ make
```

This compiles all the sources and links together the library. It also builds
the example tools and testing tools.

## Update the in-core memory hash.

```
$ ./fips-hash.sh

$ make # Re-build once the hash has been updated
```

This step is where the hash for the in-core memory test is calculated and will
need to be updated. The wolfCrypt test should fail when called by the
fips-hash.sh script and if you were to echo out the output the following
message would be observed (NOTE the hash value will be unique):

```
in my Fips callback, ok = 0, err = -203

message = In Core Integrity check FIPS error

hash = 8D29242F610EAEA179605BB1A99974EBC72B0ECDB26B483B226A729F36FC82A2

In core integrity hash check failure, copy above hash

into verifyCore[] in fips_test.c and rebuild
```

Should you add other options to the build, this may change the hash value and
this step will need to be repeated. Also modifications to the application may
result in the fips boundary shifting in memory when the application is
re-compiled. The hash changing when only the application is updated is not an
indication of the module being effected, only shifted in place in memory. This
is expected if compiling a static library and application. Shared objects tend
to not experience this issue.

4.1 If one were to do the above without using the provided
fips-hash.sh/span>script one could either edit the file
wolfcrypt/src/fips_test.c and update the hash manually or use a configure
like so:

```
$ ./configure --enable-fips=ready CFLAGS=”-DWOLFCRYPT_FIPS_CORE_HASH_VALUE=8D29242F610EAEA179605BB1A99974EBC72B0ECDB26B483B226A729F36FC82A2”
```

4.2 Make the library again.

## Test the build.

```
$ make check
```

The check target in the Makefile will run all the test tools and scripts we
provide with wolfSSL and wolfCrypt. If everything is OK, you should see the
following output:

```

PASS: scripts/resume.test

PASS: scripts/external.test

PASS: scripts/google.test

PASS: testsuite/testsuite.test

PASS: scripts/openssl.test

PASS: tests/unit.test

=======================================================================

Testsuite summary for wolfssl 4.0.0

=======================================================================

# TOTAL: 6

# PASS: 6

# SKIP: 0

# XFAIL: 0

# FAIL: 0

# XPASS: 0

# ERROR: 0

=======================================================================

```



## Install the library and headers.

```
$ make install
```

The install target in the Makefile will install all the headers and the
library into your system By default, this is into the directory /usr/local.

At this point, wolfSSL FIPS Ready should be ready to be used in your
application builds.



47 changes: 47 additions & 0 deletions wolfSSL-FIPS-Ready/src/section03.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
# What has changed from the original FIPS 140-2 ready?

1. One now needs to call wc_SetSeed_Cb at the application level when running in
FIPS mode.

a. +#ifdef WC_RNG_SEED_CB

b. + wc_SetSeed_Cb(wc_GenerateSeed);

c. +#endif

2. KEY Access Management

a. Users calling wolfSSL (SSL/TLS) APIs’ do not need to worry about the KEY
Access Management item, however for those calling crypto APIs please see
next steps

b. Users invoking wolfcrypt (wc_XXX) APIs’ directly that involve loading or
using a private key must manage the key access at the application level. To
be able to read in or use a private key the application must allow this by
calling PRIVATE_KEY_UNLOCK(); prior to reading a key or using a key. When
finished the application must** lock the key access again before terminating
by calling PRIVATE_KEY_LOCK();

i. The PRIVATE_KEY_UNLOCK and PRIVATE_KEY_LOCK can optionally be invoked
only once on startup and once on shutdown or…

ii. If the application wishes to be very strict, these can be called
immediately before and after each call that involves a private key load
or use.

** “application must lock again before terminating” - This is a
documentation requirement, this is not enforced at run-time by an error
or prevention from exiting. Failing to re-locking the key before exiting
makes the application “not FIPS compliant”.

c. To support an application that can link to both a wolfSSL FIPS library
version and a wolfSSL non-FIPS library version users can implement NO-OP
versions for the non-FIPS cases like so:

```
#if !defined(PRIVATE_KEY_LOCK) && !defined(PRIVATE_KEY_UNLOCK)
#define PRIVATE_KEY_LOCK() do {} while (0)
#define PRIVATE_KEY_UNLOCK() do {} while (0)
#endif
```

Loading
Loading