3rd-party: Regenerate wrapper on template change

When the template used for creating the wrapper scripts changes, all
exported binaries should have the scripts regenerated during updates
regardless of if the binary changed.

Signed-off-by: Castulo Martinez <castulo.martinez@intel.com>
This commit is contained in:
Castulo Martinez
2020-04-10 11:08:16 -07:00
committed by Castulo J. Martinez
parent 8d6f2f815e
commit d677c42fce
12 changed files with 669 additions and 80 deletions
+29 -19
View File
@@ -27,14 +27,6 @@
#ifdef THIRDPARTY
#define SCRIPT_TEMPLATE "#!/bin/bash\n\n" \
"export PATH=%s:$PATH\n" \
"export LD_LIBRARY_PATH=%s:$LD_LIBRARY_PATH\n" \
"export XDG_DATA_DIRS=%s:$XDG_DATA_DIRS\n" \
"export XDG_CONF_DIRS=%s:$XDG_CONF_DIRS\n" \
"\n" \
"%s \"$@\"\n"
char *third_party_get_bin_dir(void)
{
return sys_path_join("%s/%s", globals_bkp.path_prefix, SWUPD_3RD_PARTY_BIN_DIR);
@@ -294,7 +286,7 @@ enum swupd_code third_party_set_repo(struct repo *repo, bool sigcheck)
/* set up swupd to use the certificate from the 3rd-party repository,
* unless the user is specifying a path for the certificate to use */
string_or_die(&repo_cert_path, "%s%s/%s%s", globals_bkp.path_prefix, SWUPD_3RD_PARTY_BUNDLES_DIR, repo->name, CERT_PATH);
repo_cert_path = sys_path_join("%s/%s/%s/%s", globals_bkp.path_prefix, SWUPD_3RD_PARTY_BUNDLES_DIR, repo->name, CERT_PATH);
if (!globals.user_defined_cert_path) {
/* the user did not specify a cert, use repo's default */
set_cert_path(repo_cert_path);
@@ -615,9 +607,33 @@ enum swupd_code third_party_remove_binary(struct file *file)
return ret_code;
}
static enum swupd_code third_party_bin_directory_exist(void)
{
enum swupd_code ret_code = SWUPD_OK;
char *bin_directory = NULL;
bin_directory = third_party_get_bin_dir();
/* if the SWUPD_3RD_PARTY_BIN_DIR does not exist, attempt to create it */
if (mkdir_p(bin_directory)) {
error("The directory %s for 3rd-party content failed to be created\n", bin_directory);
ret_code = SWUPD_COULDNT_CREATE_DIR;
goto exit;
}
if (!sys_filelink_is_dir(bin_directory)) {
error("The path %s for 3rd-party content exists but is not a directory\n", bin_directory);
ret_code = SWUPD_COULDNT_CREATE_DIR;
}
exit:
free_and_clear_pointer(&bin_directory);
return ret_code;
}
enum swupd_code third_party_create_wrapper_script(struct file *file)
{
enum swupd_code ret_code = 0;
enum swupd_code ret_code = SWUPD_OK;
int fd;
FILE *fp = NULL;
char *bin_directory = NULL;
@@ -652,15 +668,9 @@ enum swupd_code third_party_create_wrapper_script(struct file *file)
goto close_and_exit;
}
/* if the SWUPD_3RD_PARTY_BIN_DIR does not exist, attempt to create it */
if (mkdir_p(bin_directory)) {
ret_code = SWUPD_COULDNT_CREATE_DIR;
goto close_and_exit;
}
if (!sys_filelink_is_dir(bin_directory)) {
error("The path %s for 3rd-party content exists but is not a directory\n", bin_directory);
ret_code = SWUPD_COULDNT_CREATE_DIR;
/* make sure the SWUPD_3RD_PARTY_BIN_DIR exist */
ret_code = third_party_bin_directory_exist();
if (ret_code) {
goto close_and_exit;
}
+12
View File
@@ -14,6 +14,15 @@ extern "C" {
#ifdef THIRDPARTY
/** Template used to generate wrapper scripts for 3rd-party binaries */
#define SCRIPT_TEMPLATE "#!/bin/bash\n\n" \
"export PATH=%s:$PATH\n" \
"export LD_LIBRARY_PATH=%s:$LD_LIBRARY_PATH\n" \
"export XDG_DATA_DIRS=%s:$XDG_DATA_DIRS\n" \
"export XDG_CONF_DIRS=%s:$XDG_CONF_DIRS\n" \
"\n" \
"%s \"$@\"\n"
/** @brief Name of the directory where 3rd-party content and state should be stored */
#define SWUPD_3RD_PARTY_DIRNAME "3rd-party"
@@ -26,6 +35,9 @@ extern "C" {
/** @brief Full path to the directory where 3rd-party binaries are going to be installed */
#define SWUPD_3RD_PARTY_BIN_DIR SWUPD_3RD_PARTY_DIR "/bin"
/** @brief Name of the file that holds the copy of the current script template */
#define SWUPD_3RD_PARTY_TEMPLATE_FILE "script.template"
/** @brief Store information of a repository. */
struct repo {
/** @brief repo's name */
+66
View File
@@ -195,6 +195,43 @@ static enum swupd_code validate_file_permissions(struct list *files_to_be_update
return ret_code;
}
static enum swupd_code regenerate_all_wrapper_scripts(UNUSED_PARAM char *unused)
{
enum swupd_code ret_code;
struct list *current_subs = NULL;
struct manifest *current_mom = NULL;
int version;
/* get currently installed 3rd-party bundles */
read_subscriptions(&current_subs);
/* load the MoM */
version = get_current_version(globals.path_prefix);
current_mom = load_mom(version, NULL);
if (!current_mom) {
ret_code = SWUPD_COULDNT_LOAD_MOM;
goto exit;
}
/* get a list of all 3rd-party files installed */
current_mom->submanifests = recurse_manifest(current_mom, current_subs, NULL, false, NULL);
if (!current_mom->submanifests) {
ret_code = SWUPD_RECURSE_MANIFEST;
goto exit;
}
current_mom->files = consolidate_files_from_bundles(current_mom->submanifests);
ret_code = third_party_process_files(current_mom->files, "Regenerating scripts...\n", "update_binaries", third_party_update_wrapper_script);
if (ret_code == SWUPD_OK) {
info("Scripts regenerated successfully\n");
}
exit:
manifest_free(current_mom);
free_subscriptions(&current_subs);
return ret_code;
}
static enum swupd_code update_exported_binaries(struct list *updated_files)
{
return third_party_process_files(updated_files, "\nUpdating 3rd-party bundle binaries...\n", "update_binaries", third_party_update_wrapper_script);
@@ -217,7 +254,11 @@ static enum swupd_code update_repos(UNUSED_PARAM char *unused)
enum swupd_code third_party_update_main(int argc, char **argv)
{
enum swupd_code ret_code = SWUPD_OK;
char *template_file = NULL;
char *template = NULL;
int steps_in_update;
int ret;
size_t template_len;
if (!parse_options(argc, argv)) {
print("\n");
@@ -260,7 +301,32 @@ enum swupd_code third_party_update_main(int argc, char **argv)
/* update 3rd-party bundles */
ret_code = third_party_run_operation_multirepo(cmdline_option_repo, update_repos, SWUPD_NO, "update", steps_in_update);
if (ret_code) {
goto exit;
}
/* read the current template copy */
template_file = sys_path_join("%s/%s/%s", globals_bkp.path_prefix, SWUPD_3RD_PARTY_DIR, SWUPD_3RD_PARTY_TEMPLATE_FILE);
template = sys_mmap_file(template_file, &template_len);
if (!template || strncmp(template, SCRIPT_TEMPLATE, template_len) != 0) {
/* there is no template file, or the template changed,
* all scripts need to be recreated */
info("The scripts that export binaries from 3rd-party repositories need to be regenerated\n\n");
ret_code = third_party_run_operation_multirepo(NULL, regenerate_all_wrapper_scripts, SWUPD_OK, "regenerate_scripts", steps_in_update);
/* update the template */
ret = sys_write_file(template_file, SCRIPT_TEMPLATE, string_len(SCRIPT_TEMPLATE));
if (ret < 0) {
error("The wrapper scripts template file %s failed to be updated\n", template_file);
ret_code = SWUPD_COULDNT_WRITE_FILE;
}
}
exit:
free_and_clear_pointer(&template_file);
sys_mmap_free(template, template_len);
swupd_deinit();
progress_finish_steps(ret_code);
+59
View File
@@ -36,6 +36,7 @@
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/mman.h>
#include <sys/stat.h>
#include <sys/statvfs.h>
#include <sys/wait.h>
@@ -613,3 +614,61 @@ exit:
closedir(dir);
return ret;
}
int sys_write_file(char *file, void *content, size_t content_size)
{
FILE *fp = NULL;
int ret = 0;
fp = fopen(file, "w");
if (!fp) {
return -errno;
}
if (fwrite(content, content_size, 1, fp) <= 0) {
ret = -1;
error("There was an error writing to file %s\n", file);
}
fclose(fp);
return ret;
}
void *sys_mmap_file(const char *file, size_t *file_length)
{
struct stat st;
int fd = -1;
void *buffer = NULL;
fd = open(file, O_RDONLY);
if (fd == -1) {
debug("Failed to open %s: %s", file, strerror(errno));
goto error;
}
if (fstat(fd, &st) != 0) {
debug("Failed to stat %s file", file);
goto error;
}
*file_length = st.st_size;
buffer = mmap(NULL, *file_length, PROT_READ, MAP_PRIVATE, fd, 0);
if (buffer == MAP_FAILED) {
buffer = NULL;
debug("Failed to mmap %s content", file);
}
error:
if (fd >= 0) {
close(fd);
}
return buffer;
}
void sys_mmap_free(void *buffer, size_t buffer_length)
{
if (buffer && buffer_length > 0) {
munmap(buffer, buffer_length);
}
}
+23
View File
@@ -261,6 +261,29 @@ long sys_get_file_size(const char *filename);
*/
int sys_dir_is_empty(const char *path);
/**
* @brief Writes the specified content into a file
*
* @return 0 on success or a value < 0 on error
*/
int sys_write_file(char *file, void *content, size_t content_size);
/**
* @brief Maps a file into memory.
*
* The function maps the file into a buffer and it also stores the length of the data
* in the file_length
*
* @return 0 on successfull mapping or an errno on error
*/
void *sys_mmap_file(const char *file, size_t *file_length);
/**
* @brief Deletes the mapping for the specified address range
*
*/
void sys_mmap_free(void *buffer, size_t buffer_length);
#ifdef __cplusplus
}
#endif
+1 -1
View File
@@ -335,7 +335,7 @@ retry_load:
return NULL;
}
string_or_die(&filename, "%s/%i/Manifest.MoM", globals.state_dir, version);
filename = sys_path_join("%s/%i/Manifest.MoM", globals.state_dir, version);
string_or_die(&url, "%s/%i/Manifest.MoM", globals.content_url, version);
if (!globals.sigcheck) {
+8 -51
View File
@@ -261,76 +261,33 @@ error:
bool signature_verify(const char *file, const char *sig_file, enum signature_flags flags)
{
struct stat st;
char *errorstr = NULL;
bool result = false;
int data_fd = -1;
size_t data_len;
void *data = NULL;
int sig_fd = -1;
size_t sig_len;
void *sig = NULL;
/* get the signature */
sig_fd = open(sig_file, O_RDONLY);
if (sig_fd == -1) {
string_or_die(&errorstr, "Failed to open %s: %s", sig_file, strerror(errno));
sig = sys_mmap_file(sig_file, &sig_len);
if (!sig) {
goto error;
}
if (fstat(sig_fd, &st) != 0) {
string_or_die(&errorstr, "Failed to stat %s file", sig_file);
goto error;
}
sig_len = st.st_size;
sig = mmap(NULL, sig_len, PROT_READ, MAP_PRIVATE, sig_fd, 0);
if (sig == MAP_FAILED) {
string_or_die(&errorstr, "Failed to mmap %s signature", sig_file);
goto error;
}
/* get the data to be verified */
data_fd = open(file, O_RDONLY);
if (data_fd == -1) {
string_or_die(&errorstr, "Failed to open %s", file);
goto error;
}
if (fstat(data_fd, &st) != 0) {
string_or_die(&errorstr, "Failed to stat %s", file);
goto error;
}
data_len = st.st_size;
data = mmap(NULL, data_len, PROT_READ, MAP_PRIVATE, data_fd, 0);
if (data == MAP_FAILED) {
string_or_die(&errorstr, "Failed to mmap %s", file);
/* get the data to be verified */
data = sys_mmap_file(file, &data_len);
if (!data) {
goto error;
}
result = signature_verify_data(data, data_len, sig, sig_len, flags);
error:
if (!result && flags & SIGNATURE_PRINT_ERRORS) {
if (errorstr) {
debug("%s\n", errorstr);
}
if (!result && (flags & SIGNATURE_PRINT_ERRORS)) {
warn("Signature check failed\n");
}
sys_mmap_free(sig, sig_len);
sys_mmap_free(data, data_len);
free_and_clear_pointer(&errorstr);
if (sig) {
munmap(sig, sig_len);
}
if (sig_fd >= 0) {
close(sig_fd);
}
if (data) {
munmap(data, data_len);
}
if (data_fd >= 0) {
close(data_fd);
}
return result;
}
+1 -1
View File
@@ -62,7 +62,7 @@ void read_subscriptions(struct list **subs)
DIR *dir;
struct dirent *ent;
string_or_die(&path, "%s/%s", globals.path_prefix, BUNDLES_DIR);
path = sys_path_join("%s/%s", globals.path_prefix, BUNDLES_DIR);
dir = opendir(path);
if (dir) {
+2 -2
View File
@@ -257,11 +257,11 @@ static bool get_osrelease_value(char *path_prefix, char *key, char *buff)
int keystring_len = 0;
bool keyfound = false;
string_or_die(&releasefile, "%s/usr/lib/os-release", path_prefix);
releasefile = sys_path_join("%s/usr/lib/os-release", path_prefix);
file = fopen(releasefile, "rm");
if (!file) {
free_and_clear_pointer(&releasefile);
string_or_die(&releasefile, "%s/etc/os-release", path_prefix);
releasefile = sys_path_join("%s/etc/os-release", path_prefix);
file = fopen(releasefile, "rm");
if (!file) {
free_and_clear_pointer(&releasefile);
@@ -0,0 +1,221 @@
#!/usr/bin/env bats
# Author: Castulo Martinez
# Email: castulo.martinez@intel.com
load "../testlib"
test_setup() {
# create a couple of 3rd-party repos with one installed bundle that has
# multiple binaries
create_test_environment -r "$TEST_NAME"
create_third_party_repo -a "$TEST_NAME" 10 staging repo1
create_bundle -L -n test-bundle1 -f /usr/bin/binary_1,/bin/binary_2,/usr/local/bin/binary_3 -u repo1 "$TEST_NAME"
create_third_party_repo -a "$TEST_NAME" 10 staging repo2
create_bundle -L -n test-bundle2 -f /usr/bin/binary_4,/bin/binary_5,/usr/local/bin/binary_6 -u repo2 "$TEST_NAME"
# create an update that updates only one of the bundle's binaries
create_version -r "$TEST_NAME" 20 10 staging repo1
update_bundle "$TEST_NAME" test-bundle1 --update /bin/binary_2 repo1
# add an update to the current template file
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE" "\nA little update\n"
# let's add a line to the scripts for all binaries so we can tell if
# they were re-generated after the update
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1 "TEST_STRING"
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2 "TEST_STRING"
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3 "TEST_STRING"
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_4 "TEST_STRING"
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_5 "TEST_STRING"
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_6 "TEST_STRING"
}
@test "TPR085: Update 3rd-party repositories that have exported binaries when the template has changed" {
# pre-test checks
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_4
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_5
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_6
# If the template file is different than that in the swupd binary,
# all binaries should be re-generated regardless of if they were updated or not,
# also the template file should be updated
run sudo sh -c "$SWUPD 3rd-party update $SWUPD_OPTS"
assert_status_is "$SWUPD_OK"
expected_output=$(cat <<-EOM
_______________________
3rd-Party Repo: repo1
_______________________
Updates from a 3rd-party repository are forced to run with the --no-scripts flag for security reasons
Update started
Preparing to update from 10 to 20
Downloading packs for:
- os-core
- test-bundle1
Finishing packs extraction...
Statistics for going from version 10 to version 20:
changed bundles : 2
new bundles : 0
deleted bundles : 0
changed files : 3
new files : 0
deleted files : 0
Validate downloaded files
No extra files need to be downloaded
Validating 3rd-party bundle file permissions...
Installing files...
Update was applied
Updating 3rd-party bundle binaries...
Warning: post-update helper scripts skipped due to --no-scripts argument
Update successful - System updated from version 10 to version 20
_______________________
3rd-Party Repo: repo2
_______________________
Updates from a 3rd-party repository are forced to run with the --no-scripts flag for security reasons
Update started
Version on server (10) is not newer than system version (10)
Update complete - System already up-to-date at version 10
The scripts that export binaries from 3rd-party repositories need to be regenerated
_______________________
3rd-Party Repo: repo1
_______________________
Regenerating scripts...
Scripts regenerated successfully
_______________________
3rd-Party Repo: repo2
_______________________
Regenerating scripts...
Scripts regenerated successfully
EOM
)
assert_is_output "$expected_output"
# post-test checks
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_4
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_4
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_5
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_5
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_6
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_6
assert_not_in_output "TEST_STRING"
# make sure the template file exists in the system and is correct
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE"
template_file=$(sudo cat "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE")
template=$(echo -e "$SCRIPT_TEMPLATE")
assert_equal "$template_file" "$template"
}
@test "TPR086: Update 3rd-party repository that has exported binaries when the template has changed using --repo" {
# pre-test checks
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_4
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_5
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_6
# If the template file is different than that in the swupd binary,
# all binaries should be re-generated for all repositories,
# regardless of if they were updated or not and regardless of if a
# single repo was specified, also the template file should be updated
run sudo sh -c "$SWUPD 3rd-party update $SWUPD_OPTS --repo repo1"
assert_status_is "$SWUPD_OK"
expected_output=$(cat <<-EOM
Updates from a 3rd-party repository are forced to run with the --no-scripts flag for security reasons
Update started
Preparing to update from 10 to 20
Downloading packs for:
- os-core
- test-bundle1
Finishing packs extraction...
Statistics for going from version 10 to version 20:
changed bundles : 2
new bundles : 0
deleted bundles : 0
changed files : 3
new files : 0
deleted files : 0
Validate downloaded files
No extra files need to be downloaded
Validating 3rd-party bundle file permissions...
Installing files...
Update was applied
Updating 3rd-party bundle binaries...
Warning: post-update helper scripts skipped due to --no-scripts argument
Update successful - System updated from version 10 to version 20
The scripts that export binaries from 3rd-party repositories need to be regenerated
_______________________
3rd-Party Repo: repo1
_______________________
Regenerating scripts...
Scripts regenerated successfully
_______________________
3rd-Party Repo: repo2
_______________________
Regenerating scripts...
Scripts regenerated successfully
EOM
)
assert_is_output "$expected_output"
# post-test checks
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_4
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_4
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_5
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_5
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_6
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_6
assert_not_in_output "TEST_STRING"
# make sure the template file exists in the system and is correct
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE"
template_file=$(sudo cat "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE")
template=$(echo -e "$SCRIPT_TEMPLATE")
assert_equal "$template_file" "$template"
}
+241
View File
@@ -0,0 +1,241 @@
#!/usr/bin/env bats
# Author: Castulo Martinez
# Email: castulo.martinez@intel.com
load "../testlib"
test_setup() {
# create a 3rd-party repo with one installed bundle that has
# multiple binaries
create_test_environment -r "$TEST_NAME"
create_third_party_repo -a "$TEST_NAME" 10 staging repo1
create_bundle -L -n test-bundle1 -f /usr/bin/binary_1,/bin/binary_2,/usr/local/bin/binary_3 -u repo1 "$TEST_NAME"
# create an update that updates only one of the bundle's binaries
create_version -r "$TEST_NAME" 20 10 staging repo1
update_bundle "$TEST_NAME" test-bundle1 --update /bin/binary_2 repo1
# let's add a line to the scripts for all binaries so we can tell if
# they were re-generated after the update
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1 "TEST_STRING"
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2 "TEST_STRING"
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3 "TEST_STRING"
}
@test "TPR082: Update a 3rd-party bundle that has exported binaries when the template has not changed" {
# pre-test checks
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
# If the template file didn't change then only the binary that was
# udpated should be re-generated
run sudo sh -c "$SWUPD 3rd-party update $SWUPD_OPTS"
assert_status_is "$SWUPD_OK"
expected_output=$(cat <<-EOM
_______________________
3rd-Party Repo: repo1
_______________________
Updates from a 3rd-party repository are forced to run with the --no-scripts flag for security reasons
Update started
Preparing to update from 10 to 20
Downloading packs for:
- os-core
- test-bundle1
Finishing packs extraction...
Statistics for going from version 10 to version 20:
changed bundles : 2
new bundles : 0
deleted bundles : 0
changed files : 3
new files : 0
deleted files : 0
Validate downloaded files
No extra files need to be downloaded
Validating 3rd-party bundle file permissions...
Installing files...
Update was applied
Updating 3rd-party bundle binaries...
Warning: post-update helper scripts skipped due to --no-scripts argument
Update successful - System updated from version 10 to version 20
EOM
)
assert_is_output "$expected_output"
# post-test checks
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
assert_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
assert_in_output "TEST_STRING"
# make sure the template file exists in the system and is correct
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE"
template_file=$(sudo cat "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE")
template=$(echo -e "$SCRIPT_TEMPLATE")
assert_equal "$template_file" "$template"
}
@test "TPR083: Update a 3rd-party bundle that has exported binaries when there is no template" {
# pre-test checks
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
# delete the template from the system
sudo rm "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE"
# If the template file is not found all binaries should be re-generated
# regardless of if they were updated or not, also the template file
# should be created
run sudo sh -c "$SWUPD 3rd-party update $SWUPD_OPTS"
assert_status_is "$SWUPD_OK"
expected_output=$(cat <<-EOM
_______________________
3rd-Party Repo: repo1
_______________________
Updates from a 3rd-party repository are forced to run with the --no-scripts flag for security reasons
Update started
Preparing to update from 10 to 20
Downloading packs for:
- os-core
- test-bundle1
Finishing packs extraction...
Statistics for going from version 10 to version 20:
changed bundles : 2
new bundles : 0
deleted bundles : 0
changed files : 3
new files : 0
deleted files : 0
Validate downloaded files
No extra files need to be downloaded
Validating 3rd-party bundle file permissions...
Installing files...
Update was applied
Updating 3rd-party bundle binaries...
Warning: post-update helper scripts skipped due to --no-scripts argument
Update successful - System updated from version 10 to version 20
The scripts that export binaries from 3rd-party repositories need to be regenerated
_______________________
3rd-Party Repo: repo1
_______________________
Regenerating scripts...
Scripts regenerated successfully
EOM
)
assert_is_output "$expected_output"
# post-test checks
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
assert_not_in_output "TEST_STRING"
# make sure the template file exists in the system and is correct
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE"
template_file=$(sudo cat "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE")
template=$(echo -e "$SCRIPT_TEMPLATE")
assert_equal "$template_file" "$template"
}
@test "TPR084: Update a 3rd-party bundle that has exported binaries when the template has changed" {
# pre-test checks
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
# make a change to the template
write_to_protected_file -a "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE" "random update"
# If the template file is different than that in the swupd binary,
# all binaries should be re-generated regardless of if they were updated or not,
# also the template file should be updated
run sudo sh -c "$SWUPD 3rd-party update $SWUPD_OPTS"
assert_status_is "$SWUPD_OK"
expected_output=$(cat <<-EOM
_______________________
3rd-Party Repo: repo1
_______________________
Updates from a 3rd-party repository are forced to run with the --no-scripts flag for security reasons
Update started
Preparing to update from 10 to 20
Downloading packs for:
- os-core
- test-bundle1
Finishing packs extraction...
Statistics for going from version 10 to version 20:
changed bundles : 2
new bundles : 0
deleted bundles : 0
changed files : 3
new files : 0
deleted files : 0
Validate downloaded files
No extra files need to be downloaded
Validating 3rd-party bundle file permissions...
Installing files...
Update was applied
Updating 3rd-party bundle binaries...
Warning: post-update helper scripts skipped due to --no-scripts argument
Update successful - System updated from version 10 to version 20
The scripts that export binaries from 3rd-party repositories need to be regenerated
_______________________
3rd-Party Repo: repo1
_______________________
Regenerating scripts...
Scripts regenerated successfully
EOM
)
assert_is_output "$expected_output"
# post-test checks
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_1
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_2
assert_not_in_output "TEST_STRING"
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/binary_3
assert_not_in_output "TEST_STRING"
run sudo cat "$TARGETDIR"/"$THIRD_PARTY_BIN_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE"
assert_not_in_output "random update"
# make sure the template file exists in the system and is correct
assert_file_exists "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE"
template_file=$(sudo cat "$TARGETDIR"/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE")
template=$(echo -e "$SCRIPT_TEMPLATE")
assert_equal "$template_file" "$template"
}
+6 -6
View File
@@ -1565,6 +1565,7 @@ create_third_party_repo() { #swupd_function
debug_msg "3rd-party repo URL: $TPURL"
# if requested, add the new repo to the repo.ini file
# and the template file
sudo mkdir -p "$env_name"/testfs/target-dir/"$THIRD_PARTY_DIR"
if [ "$add" = true ]; then
{
@@ -1572,6 +1573,7 @@ create_third_party_repo() { #swupd_function
printf 'URL=%s\n\n' "file://$TPURL"
printf 'VERSION=%s\n\n' "$version"
} | sudo tee -a "$env_name"/testfs/target-dir/"$THIRD_PARTY_DIR"/repo.ini > /dev/null
write_to_protected_file "$env_name"/testfs/target-dir/"$THIRD_PARTY_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE" "$SCRIPT_TEMPLATE"
fi
# every 3rd-party repo needs to have at least the special os-core bundle,
@@ -1590,12 +1592,6 @@ create_third_party_repo() { #swupd_function
create_bundle -n os-core -v "$version" -f /usr/lib/os-release:"$OS_RELEASE",/usr/share/clear/update-ca/Swupd_Root.pem:"$cert",/usr/share/defaults/swupd/format:"$FORMAT" -u "$repo_name" "$env_name"
fi
# if requested, add the template file to the target system
if [ "$add" = true ]; then
sudo mkdir -p "$env_name"/testfs/target-dir/"$THIRD_PARTY_BIN_DIR"
write_to_protected_file "$env_name"/testfs/target-dir/"$THIRD_PARTY_BIN_DIR"/"$THIRD_PARTY_SCRIPT_TEMPLATE" "$SCRIPT_TEMPLATE"
fi
if [ "$TEST_ENV_ONLY" = true ]; then
print "\nVariables for 3rd-party repo $repo_name:\n"
print "TPURL=$TPURL"
@@ -4639,6 +4635,10 @@ assert_equal() { # assertion
validate_param "$val2"
if [ "$val1" != "$val2" ]; then
echo "Assertion Failed"
echo "The two items being compared are not equal"
echo -e "Difference:\\n$sep"
diff -u <(echo "$val1") <(echo "$val2") || true
return 1
fi