Skip to content

Commit

Permalink
update artifact-signing script for release signing
Browse files Browse the repository at this point in the history
  • Loading branch information
anmol372 committed Aug 21, 2024
1 parent 310117d commit bcd922f
Show file tree
Hide file tree
Showing 4 changed files with 155 additions and 26 deletions.
3 changes: 2 additions & 1 deletion docker/rpms/my_setup_dev.sh
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
# shellcheck disable=all
set -a

# if dev=1, then we recompile tools before each invocation, even if binaries already exist (not recommended for signing users)
Expand All @@ -10,7 +11,7 @@ dev=0
## Use ./signContent-swims for SWIMS
signing_helper=./signContent-swims

key_creation_time=0 # If set to 1, a timestamp of current time will be added to the signature in the public key file, otherwise
key_creation_time=1 # If set to 1, a timestamp of current time will be added to the signature in the public key file, otherwise
# a static timestamp of "2017-Jan-01" will be used (when set to 0)

sig_creation_time=0 # If set to 0, or not set, a timestamp of current time will be added to the signature file (common case).
Expand Down
102 changes: 102 additions & 0 deletions docker/rpms/my_setup_rel.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
# shellcheck disable=all
set -a

# if dev=1, then we recompile tools before each invocation, even if binaries already exist (this is for batch-mode development team only)
dev=0

# If you are running rpm signing tools from a daemon process, set the Environment Variable RPM_SIGN_DAEMON=1, otherwise leave it unset.
# This will prevent output to a tty, which doesn't exist on a daemon process
#RPM_SIGN_DAEMON=1

## Use ./signContent-swims for SWIMS
signing_helper=./signContent-swims

key_creation_time=1 # If 1, a timestamp of current time will be added to the signature in the public key file, otherwise
# a static timestamp of "2017-Jan-01" will be used (when set to 0)

sig_creation_time=0 # If set to 0, or not set, a timestamp of current time will be added to the signature file (common case).
# If set to 1, a static timestamp (of 2017-Jan-02) will be added to the signature file. This
# aligns with the 'key_creation_time' timestamp setting above, the key must be equal to or of older age than the
# signature to verify successfully.
# If set to > 0, it is assumed to be seconds since the epoch, 1970-01-01 00:00:00 UTC
# This value can typically be determined using the date unix command for a particular date, e.g.
# $ date --date='2018-01-01' +%s
# 1514782800
#
# $ date --date='2021-07-11 11:43:40' +%s
# 1626018220


## comment these out to use the production SWIMS server
##swims_certfile=swims_root_ca.pem # if set, alternate cert to validate host, typically don't use
##swims_host='swims-stg.cisco.com' # if set, alternate host to use

swims_client_log="swims_client.log"

#For the swims_client command, you have options:
# 1) For newer 64-bit machines (e.g. RHEL7, RHEL8, Ubuntu16, ubuntu18, Ubuntu20, and future), use the code_sign7.x86_64 executable provided in this repo (built on py3 RHEL7)
# 2) For python2 and/or older 64-bit machines (e.g. CentOs6, CEL6, etc), use the code_sign.x86_64 executable provided in this repo
# 3) For 32-bit machines, use the code_sign6_32 executable provided in this repo
# 4) Use your own code_sign executable copy (not recommended), provide the path to it
# 5) A copy of the swims_client.py script (see below)

#This example uses option 1, always include the keyword 'swims' (except for option 5)
swims_client_cmd=$1' swims'
#swims_client_cmd='<path to code_sign executable>/code_sign7.x86_64 swims'
#swims_client_cmd="$PWD"'/code_sign.x86_64 swims'

## un-comment this to use option 5, a swims_client.py python script (not provided in repo)
##swims_client_cmd='python swims_client.py' # eval-able string

sig_type=rel # must be either "dev" or "rel"

#gpgkeydir=<path to the directory to store/retrieve the gpg key> # if you want to create the gpgkey (i.e. run-make-cert) into or retrieve the gpgkey from someplace other than
# this scripts directory, set this parameter to the directory path only. Otherwise don't set. Include final
# slash if you do set it, e.g. /tmp/ . The keys must be named rel.gpg or dev.gpg regardless.


notes="RPM Test REL for ISC"
user1=$2 # CEC name; only user required for dev signatures
pass1=push # For DUO push request
user2=$3 # CEC name; only used when sig_type=rel, otherwise use tickets or tokens
pass2=push # For DUO push request

# To use tickets rather than OTP (for SWIMS), specify the ticket_file path
# e.g. ticket_file=/home/swims/RPM/rpm_deb_signing-master/Linux-64/swims-openpgp/myticket
#ticket_file=<path to ticket> # if this is specified, uses a ticket rather than OTP (for SWIMS)
#ticket_file=/home/swims/repo-rpm-deb-sign-src/rpm_deb_sign_src/Linux-64/swims-openpgp/mph-2987471-REL-ticket

# To use session tokens, use the SWIMS_SESSION_TOKEN and SWIMS_TREAT_TICKET_AS_TOKEN Environment Variables. See
# https://docs.cisco.com/share/page/site/nextgen-edcs/document-details?nodeRef=workspace://SpacesStore/44769d41-9bb4-4a4e-b6c1-cbfd1a7184a1 for more details.

# If using a token, "SWIMS_SESSION_TOKEN" must be set to the raw token string or the path to the file containing the token.
#SWIMS_SESSION_TOKEN=
# If using a token for a legacy build script that cannot easily utilize the "SWIMS_SESSION_TOKEN" variable,
# the "ticket_file" variable must be set to the path to the file containing the token,
# and "SWIMS_TREAT_TICKET_AS_TOKEN" must be set to "True."
#SWIMS_TREAT_TICKET_AS_TOKEN=True

# User provided encoded JSON string or file path to the file containing the encoded JSON string that includes
# all mandatory and optional build or artifact metadata regarding the build session. (See code_sign tool: "code_sign build-data -h")
#BUILD_METADATA=
#ARTIFACT_METADATA=

product=dcn-container-vm-plugins # Product name (also key name for Abraxas, which only has one key for product)
product_key=dcn-container-vm-release
#product_pid=testPid # PID for SWIMS; if commented out, no PID will be given. If your PID is not marked as 'Real Pid' in your Product Entry in SWIMs, don't set this.

#armored_pgp_sig=yes # Uncomment to make run-extsign produce an armored base64 gpg signature file

#If you are using GRUB2 to verify gpg signatures for files (e.g. the kernel), then the file must be signed with RPM_MAJOR_VERSION = 5. This allows the key id to be placed
#in the unhashed sub-components within the signature, which GRUB2 currently expects.
#RPM_MAJOR_VERSION = 5

## Customer-visible identity for "who signed this code?"
# Do not include invalid characters like '\x00', '(', ')', '<' and '>' in <identity_*> fields
identity_name=$2
identity_email=$2'@cisco.com'
#identity_comment="${product}.${sig_type}" # if commented out / undefined, default will be built per this pattern

set +a

# vim: filetype=sh
73 changes: 49 additions & 24 deletions docker/rpms/sign-rpm.sh
Original file line number Diff line number Diff line change
@@ -1,8 +1,7 @@
#!/bin/bash

set -x
#set -x
#TODO: add verification
#TODO: add release signing

# Ensure the script is called with the correct number of arguments
if [ "$#" -ne 4 ]; then
Expand All @@ -29,8 +28,30 @@ VAULT_SECRET_ID=$KEEPER_SECRET
# Signing CECs
USER1=$2
USER2=$3

# Check if SIGNUSER1 is set
if [ "$USER1" == "empty" ]; then
echo "NO RPMS signed, please provide a valid CEC user for dev signing."
exit 0
fi

# Release Signing or not
RELEASE=$4

BUILD_TYPE="DEV"
VARSOURCE="$WORKSPACE/docker/rpms/my_setup_dev.sh"
GPG_FILE="dev.gpg"
# Check if RELEASE is True and validate SIGNUSER1 and SIGNUSER2
if [ "$RELEASE" == "true" ]; then
if [ "$USER1" == "empty" ] || [ "$USER2" == "empty" ]; then
echo "Two valid CEC users required for release signing."
exit 1
fi
BUILD_TYPE="RELEASE"
VARSOURCE="$WORKSPACE/docker/rpms/my_setup_rel.sh"
GPG_FILE="rel.gpg"
fi

# Constants from Travis CI environment variables
BRANCH_NAME=$GIT_BRANCH
PROJECT_NAME=$GIT_URL
Expand All @@ -43,7 +64,6 @@ CODE_SIGN_EXEC="$RPM_DEB_SIGN/Linux-64/swims-openpgp/code_sign.x86_64"
RPM_SIGN_SCRIPTDIR="$RPM_DEB_SIGN/Linux-64/swims-openpgp"
RPM_BATCH_SIGN="$RPM_SIGN_SCRIPTDIR/rpm_sign_batchmode.py3"
RUN_EXT_SIGN="$RPM_SIGN_SCRIPTDIR/run-extsign"
RPMMACROS="$WORKSPACE/signedRPMS"

WORKING_DIR="$WORKSPACE/SIGNRPMS"
OUTPUT_TOKEN="$WORKING_DIR/dcn-bld.tkn"
Expand All @@ -55,19 +75,18 @@ SESSION_TOKEN_OUTPUT="$WORKING_DIR/build-session.tkn"

REASON="CLI Test #1"
BUILD_INITIATOR=$USER1
BUILD_TYPE="DEV"
ATTESTATION_KEY_NAME="dcn-plugin-build"
PRODUCT="dcn-container-vm-plugins"
AUTH_TYPE="OTP"
USERNAME=$USER1
PASSWORD="push"
PASS="push"


# Step 0: Clone the repository if it does not exist and navigate into it
mkdir -p $SIGNHELPER_DIR
rm -rf $RPM_DEB_SIGN
git clone $REPO_URL $RPM_DEB_SIGN
mkdir -p "$SIGNHELPER_DIR"
rm -rf "$RPM_DEB_SIGN"
git clone "$REPO_URL" "$RPM_DEB_SIGN"

mkdir -p $WORKING_DIR
mkdir -p "$WORKING_DIR"

# Find RPM files in the RPM directory
RPM_FILES=$(find "$RPM_DIR_PATH" -type f -name "*.rpm")
Expand All @@ -87,13 +106,19 @@ for RPM_FILE in $RPM_FILES; do
done

# Step 1: Create build authorization token
$CODE_SIGN_EXEC swims build authorization create -product $PRODUCT -buildType $BUILD_TYPE \
-attestationKeyName $ATTESTATION_KEY_NAME -reason "$REASON" -buildInitiators $BUILD_INITIATOR \
-authType $AUTH_TYPE -username1 $USERNAME -password1 $PASSWORD -out $OUTPUT_TOKEN -logFile $LOG_FILE
if [ "$RELEASE" == "true" ]; then
"$CODE_SIGN_EXEC" swims build authorization create -product "$PRODUCT" -buildType "$BUILD_TYPE" \
-attestationKeyName "$ATTESTATION_KEY_NAME" -reason "$REASON" -buildInitiators "$BUILD_INITIATOR" \
-authType "$AUTH_TYPE" -username1 "$USER1" -password1 "$PASS" -username2 "$USER2" -password2 "$PASS" -approvers "$USER2" -out "$OUTPUT_TOKEN" -logFile "$LOG_FILE"
else
"$CODE_SIGN_EXEC" swims build authorization create -product "$PRODUCT" -buildType "$BUILD_TYPE" \
-attestationKeyName "$ATTESTATION_KEY_NAME" -reason "$REASON" -buildInitiators "$BUILD_INITIATOR" \
-authType "$AUTH_TYPE" -username1 "$USER1" -password1 "$PASS" -out "$OUTPUT_TOKEN" -logFile "$LOG_FILE"
fi

# Step 2: Encode payload for build session
$CODE_SIGN_EXEC swims build session encodePayload -buildInitiator $BUILD_INITIATOR -branchName $BRANCH_NAME \
-projectName $PROJECT_NAME -buildAuthToken $OUTPUT_TOKEN -out $PAYLOAD_OUTPUT -logFile $LOG_FILE
"$CODE_SIGN_EXEC" swims build session encodePayload -buildInitiator "$BUILD_INITIATOR" -branchName "$BRANCH_NAME" \
-projectName "$PROJECT_NAME" -buildAuthToken "$OUTPUT_TOKEN" -out "$PAYLOAD_OUTPUT" -logFile "$LOG_FILE"

# Step 3: Set Vault environment variables
export VAULT_ADDR=$VAULT_ADDR
Expand All @@ -102,21 +127,21 @@ export VAULT_ROLE_ID=$VAULT_ROLE_ID
export VAULT_SECRET_ID=$VAULT_SECRET_ID

# Step 4: Sign the payload with attestation key
$CODE_SIGN_EXEC swims utils vault signWithAttestationKey -attestationKeyName $ATTESTATION_KEY_NAME \
-input $PAYLOAD_OUTPUT -out $SIGNATURE_OUTPUT -logFile $LOG_FILE
"$CODE_SIGN_EXEC" swims utils vault signWithAttestationKey -attestationKeyName "$ATTESTATION_KEY_NAME" \
-input "$PAYLOAD_OUTPUT" -out "$SIGNATURE_OUTPUT" -logFile "$LOG_FILE"

# Step 5: Create build session token
$CODE_SIGN_EXEC swims build session create -requestPayload $PAYLOAD_OUTPUT -requestSignature $SIGNATURE_OUTPUT \
-out $SESSION_TOKEN_OUTPUT -logFile $LOG_FILE
"$CODE_SIGN_EXEC" swims build session create -requestPayload "$PAYLOAD_OUTPUT" -requestSignature "$SIGNATURE_OUTPUT" \
-out "$SESSION_TOKEN_OUTPUT" -logFile "$LOG_FILE"

# Print completion message
echo "Build session token created successfully and stored in $SESSION_TOKEN_OUTPUT"

export SWIMS_SESSION_TOKEN=$SESSION_TOKEN_OUTPUT
source $WORKSPACE/docker/rpms/my_setup_dev.sh $CODE_SIGN_EXEC $USER1
cd $RPM_SIGN_SCRIPTDIR
cd "$RPM_SIGN_SCRIPTDIR"
source "$VARSOURCE" "$CODE_SIGN_EXEC" "$USER1" "$USER2"
./run-make-cert.exp
gpg --import dev.gpg
gpg --import "$GPG_FILE"
#gpg --list-keys

# Create the ~/.rpmmacros file with the specified configuration
Expand All @@ -127,6 +152,6 @@ cat >"$WORKING_DIR/.rpmmacros" <<EOF
run-extsign %{__plaintext_filename} %{__signature_filename}
EOF

python3 $RPM_BATCH_SIGN -f $CSV_FILE -m $WORKING_DIR/.rpmmacros
python3 "$RPM_BATCH_SIGN" -f "$CSV_FILE" -m "$WORKING_DIR/.rpmmacros"

#rm -rf $WORKING_DIR
#rm -rf "$WORKING_DIR"
3 changes: 2 additions & 1 deletion pipeline-rpm-script
Original file line number Diff line number Diff line change
Expand Up @@ -42,11 +42,12 @@ pipeline {
conjurSecretCredential(credentialsId: 'noiro-conjur-keeper-secret-id', variable: 'KEEPER_SECRET')
]) {
script {
def signUser1 = params.SIGNUSER1 ?: 'empty'
// Handle empty params.SIGNUSER2 and pass empty string if it is
def signUser2 = params.SIGNUSER2 ?: 'empty'
// Execute sign-rpm.sh with Vault credentials passed as parameters
sh """
./docker/rpms/sign-rpm.sh ${SIGNED_RPMS} ${params.SIGNUSER1} ${signUser2} ${params.ReleaseBuild}
./docker/rpms/sign-rpm.sh ${SIGNED_RPMS} ${signUser1} ${signUser2} ${params.ReleaseBuild}
"""
}
}
Expand Down

0 comments on commit bcd922f

Please sign in to comment.