Bug 1770395

Summary: Implement logging callback in luksmeta to receive only desired log level
Product: Red Hat Enterprise Linux 8 Reporter: Renaud Métrich <rmetrich>
Component: luksmetaAssignee: Sergio Correia <scorreia>
Status: CLOSED ERRATA QA Contact: Martin Zelený <mzeleny>
Severity: urgent Docs Contact:
Priority: urgent    
Version: 8.1CC: agk, cww, dapospis, guazhang, jbrassow, mbroz, mzeleny, okozina, prajnoha, scorreia, tjaros
Target Milestone: rcKeywords: Regression, Triaged, ZStream
Target Release: 8.0Flags: pm-rhel: mirror+
Hardware: All   
OS: Linux   
Whiteboard:
Fixed In Version: luksmeta-9-4.el8 Doc Type: If docs needed, set a value
Doc Text:
Story Points: ---
Clone Of:
: 1798627 (view as bug list) Environment:
Last Closed: 2020-04-28 16:00:02 UTC Type: Bug
Regression: --- Mount Type: ---
Documentation: --- CRM:
Verified Versions: Category: ---
oVirt Team: --- RHEL 7.3 requirements from Atomic Host:
Cloudforms Team: --- Target Upstream Version:
Embargoed:
Bug Depends On:    
Bug Blocks: 1798627    
Attachments:
Description Flags
Proposed patch to implement log callback in luksmeta with log level error and outputting to stderr none

Description Renaud Métrich 2019-11-08 21:48:10 UTC
Description of problem:

Tools using libcryptsetup print "Running in FIPS mode." constantly on STDOUT, which makes the output not be parse-able.
This in particular breaks Clevis when it tries to unlock LUKS1 devices on boot:

/usr/bin/clevis-decrypt gets "Running in FIPS mode." input instead of expected Slot and UUID when being called from /usr/libexec/clevis-luks-askpass below:
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------
 62                 if pt="`luksmeta load -d $d -s $slot -u $UUID | clevis decrypt`"; then
 63                     echo -n "+$pt" | nc -U -u --send-only "$s"
 64                     unlocked=true
 65                     break
 66                 fi
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------

After booting and enabling FIPS, we can indeed see that "luksmeta" command shows logs on stdout constantly:

RHEL 8.0 (OK):
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------
# luksmeta show -d /dev/rhel/00 
0   active empty
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------

RHEL 8.1 (FAIL):
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------
# luksmeta show -d /dev/rhel/00
Running in FIPS mode.
0   active empty
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------



Version-Release number of selected component (if applicable):

cryptsetup-2.2.0-2.el8.x86_64


How reproducible:

Always with FIPS

Additional info:

commit 493e8580d6c4f0f4128c4035005e1be0fc015398
Author: Milan Broz <gmazyland>
Date:   Sun Oct 21 11:25:13 2018 +0200
 
    Log all debug messages through log callback.
   
    This cahnge allow to redirect all output of library
    to a log processor.

is the culprit:

-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------
@@ -111,21 +103,18 @@ void tool_log(int level, const char *msg, void *usrptr __attribute__((unused)))
        switch(level) {
 
        case CRYPT_LOG_NORMAL:
-               fputs(msg, stdout);
+               fprintf(stdout, "%s", msg);
                break;
        case CRYPT_LOG_VERBOSE:
                if (opt_verbose)
-                       fputs(msg, stdout);
+                       fprintf(stdout, "%s", msg);
                break;
        case CRYPT_LOG_ERROR:
-               fputs(msg, stderr);
+               fprintf(stderr, "%s", msg);
                break;
        case CRYPT_LOG_DEBUG:
                if (opt_debug)
-                       printf("# %s\n", msg);
-               break;
-       default:
-               fprintf(stderr, "Internal error on logging class for msg: %s", msg);
+                       fprintf(stdout, "# %s\n", msg);
                break;
        }
 }
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------

Comment 1 Ondrej Kozina 2019-11-11 16:38:34 UTC
Yes, cryptsetup library logs all messages (with normal, verbose or error level) unless application provides own log callback function since version 2.1.0. The custom log callbacke can be set per context crypt_set_log_callback(cd != NULL) or default for whole library crypt_set_log_callback(cd == NULL). I can't simply revert this commit because we fixed another more severe problem with libcryptsetup logging with that commit.

Sergoi,

what is desired log level from libcryptsetup for luksmeta utility?

Comment 2 Renaud Métrich 2019-11-11 19:12:41 UTC
The issue there is log goes to STDOUT, not STDERR, "corrupting" the output of the command using libcryptsetup.

Comment 3 Sergio Correia 2019-11-11 23:26:06 UTC
(In reply to Ondrej Kozina from comment #1)
> Yes, cryptsetup library logs all messages (with normal, verbose or error
> level) unless application provides own log callback function since version
> 2.1.0. The custom log callbacke can be set per context
> crypt_set_log_callback(cd != NULL) or default for whole library
> crypt_set_log_callback(cd == NULL). I can't simply revert this commit
> because we fixed another more severe problem with libcryptsetup logging with
> that commit.
> 
> Sergoi,
> 
> what is desired log level from libcryptsetup for luksmeta utility?

CRYPT_LOG_ERROR should be enough for us. As Renaud pointed out, the issue is that the verbose log ("Running in FIPS mode.") is going to stdout. Probably something like this can help here, as now the log will go to stderr: https://github.com/latchset/luksmeta/pull/12

Comment 6 Ondrej Kozina 2019-11-12 11:32:06 UTC
With updated patch based on https://github.com/latchset/luksmeta/pull/12 (see the comment) it should work as expected. Anyway let me know, if there other issues with libcryptsetup logging.

Comment 7 Martin Zelený 2019-11-12 15:30:18 UTC
The new test coverage will be necessary to test combination of NBDE for non-default LUKSv1 on RHEL-8 and performed in FIPS mode.

Comment 8 Renaud Métrich 2019-11-12 15:50:27 UTC
Note LUKSv1 is not the default, but due to BZ 1759972 and related reproducer customers will probably use it without noticing at all:

-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------
When installing a system using the GUI and choosing "Custom" for Storage Configuration and "Encryption", the MANUAL PARTITIONING panel opens.
Then there are 2 possibilities:

1. Clicking on "Click here to create them automatically"
or
2. Press the "+" button to start creating partitions

When using option 2. and adding partitions, the following happens:
- /boot is hosted on /dev/vda1 (OK)
- / is hosted on luks-rhel-00 logical volume
- /usr is hosted on luks-rhel-01 logical volume
- ...

It appears that all this ends up with having 1 VG created on /dev/vda2 and one LUKS1 device per logical volume.
There are then multiple issues appearing:
- Logical Volume name cannot be renamed through "Name:" field (e.g. from "00" to "root"): the description under the mount point left is updated, but not the "Name:" field
- LUKS2 cannot be chosen, the installer forces using LUKS1
-------- 8< ---------------- 8< ---------------- 8< ---------------- 8< --------

Comment 9 Sergio Correia 2019-11-13 12:52:48 UTC
Created attachment 1635759 [details]
Proposed patch to implement log callback in luksmeta with log level error and outputting to stderr

Comment 15 errata-xmlrpc 2020-04-28 16:00:02 UTC
Since the problem described in this bug report should be
resolved in a recent advisory, it has been closed with a
resolution of ERRATA.

For information on the advisory, and where to find the updated
files, follow the link below.

If the solution does not work for you, open a new bug report.

https://access.redhat.com/errata/RHBA-2020:1695