Commit 0c267e4e authored by Maarten de Waard's avatar Maarten de Waard 🤘🏻
Browse files

Merge branch '21-free-memory' into 'master'

Free memory after use

Closes #21

See merge request !21
parents 4caaf4d1 63a06146
......@@ -34,6 +34,7 @@ int callback_encryption_get(const struct _u_request * request,
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR, "mounting root device failed: return code %d", r);
json_decref(messages);
return send_simple_response(response, 500, "error",
"mounting root device failed");
}
......
......@@ -35,10 +35,11 @@ int callback_encryption_init_post(const struct _u_request * request,
// Read the encryption password from the request body.
json_t * json_input = ulfius_get_json_body_request(request, NULL);
const char * password = password = json_string_value(
const char * password = json_string_value(
json_object_get(json_input, "password"));
if (password == NULL)
{
json_decref(json_input);
return send_simple_response(response, 400, "error", "missing password");
}
......@@ -48,6 +49,7 @@ int callback_encryption_init_post(const struct _u_request * request,
if (path_exists(config.info_partition_device))
{
// The device is already encrypted; we don't want to encrypt it again.
json_decref(json_input);
return send_simple_response(response, 500, "error",
"already encrypted");
}
......@@ -59,6 +61,7 @@ int callback_encryption_init_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"mounting root device failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"mounting root device failed");
}
......@@ -69,6 +72,7 @@ int callback_encryption_init_post(const struct _u_request * request,
if (! fits)
{
// Projected memory usage is really high, so abort.
json_decref(json_input);
return send_simple_response(response, 500, "error",
"device too large");
}
......@@ -80,17 +84,22 @@ int callback_encryption_init_post(const struct _u_request * request,
asprintf(&command, "rsync -a %s/ %s", UNENCRYPTED_TMP_MOUNTPOINT,
config.tmp_data_location);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"copying root device contents into memory failed: return code %d",
r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"copying root device contents into memory failed");
}
// Unmount unencrypted device.
y_log_message(Y_LOG_LEVEL_ERROR,
y_log_message(Y_LOG_LEVEL_DEBUG,
"unmounting unencrypted device at %s",
UNENCRYPTED_TMP_MOUNTPOINT);
r = umount(UNENCRYPTED_TMP_MOUNTPOINT);
......@@ -98,6 +107,7 @@ int callback_encryption_init_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"unmounting encrypted device failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"unmounting unencrypted device failed");
}
......@@ -112,20 +122,34 @@ int callback_encryption_init_post(const struct _u_request * request,
y_log_message(Y_LOG_LEVEL_ERROR,
"authorized_keys not found on root device at %s",
authorized_keys_path);
if (authorized_keys_path)
{
free(authorized_keys_path);
}
json_decref(json_input);
return send_simple_response(response, 500, "error",
"authorized_keys not found on root device");
}
if (authorized_keys_path)
{
free(authorized_keys_path);
}
// Re-partition device.
y_log_message(Y_LOG_LEVEL_ERROR, "repartitioning device %s",
y_log_message(Y_LOG_LEVEL_DEBUG, "repartitioning device %s",
config.root_device);
command = NULL;
asprintf(&command, "sgdisk -a 8192 -n 1:0:48M -N 2 %s", config.root_device);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"partitioning root device failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"partitioning root device failed");
}
......@@ -135,10 +159,15 @@ int callback_encryption_init_post(const struct _u_request * request,
command = NULL;
asprintf(&command, "partprobe");
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR, "partprobe failed: return code %d",
r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"partprobe failed");
}
......@@ -155,10 +184,15 @@ int callback_encryption_init_post(const struct _u_request * request,
config.info_partition_device);
y_log_message(Y_LOG_LEVEL_DEBUG, "command: %s", command);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"creating filesystem failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"creating filesystem inside encrypted container failed");
}
......@@ -171,6 +205,7 @@ int callback_encryption_init_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"mounting encrypted device failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"mounting encrypted root device failed");
}
......@@ -181,10 +216,15 @@ int callback_encryption_init_post(const struct _u_request * request,
asprintf(&command, "mkdir -p %s%s %s%s", INFO_TMP_MOUNTPOINT,
AUTHORIZED_KEYS_DIR, INFO_TMP_MOUNTPOINT, SSH_HOST_KEY_DIR);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"creating directories failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"creating directories in info partition failed");
}
......@@ -195,10 +235,15 @@ int callback_encryption_init_post(const struct _u_request * request,
asprintf(&command, "cp %s %s%s",
AUTHORIZED_KEYS_PATH, INFO_TMP_MOUNTPOINT, AUTHORIZED_KEYS_PATH);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"copying authorized_keys failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"copying authorized_keys failed");
}
......@@ -209,10 +254,15 @@ int callback_encryption_init_post(const struct _u_request * request,
asprintf(&command, "cp /etc/dropbear/* %s%s/", INFO_TMP_MOUNTPOINT,
SSH_HOST_KEY_DIR);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_DEBUG,
"copying dropbear ssh host keys failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"copying dropbear ssh host keys failed");
}
......@@ -225,6 +275,7 @@ int callback_encryption_init_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"unmounting failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"unmounting configuration partition failed");
}
......@@ -237,6 +288,7 @@ int callback_encryption_init_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"creating encrypted container failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"creating encryption container failed");
}
......@@ -249,6 +301,7 @@ int callback_encryption_init_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"unlocking encrypted container failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"unlocking new encryption container failed");
}
......@@ -259,10 +312,15 @@ int callback_encryption_init_post(const struct _u_request * request,
asprintf(&command, "mkfs -t %s %s",
FILESYSTEM_TYPE, config.mapped_device_path);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"creating filesystem failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"creating filesystem inside encrypted container failed");
}
......@@ -275,6 +333,7 @@ int callback_encryption_init_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"mounting encrypted device failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"mounting encrypted root device failed");
}
......@@ -286,11 +345,16 @@ int callback_encryption_init_post(const struct _u_request * request,
asprintf(&command, "rsync -a %s/ %s",
config.tmp_data_location, DATA_TMP_MOUNTPOINT);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"copying from memory to encrypted device failed: return code %d",
r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"copying root device contents from memory failed");
}
......@@ -303,6 +367,7 @@ int callback_encryption_init_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"unmounting encrypted device failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"unmounting encrypted device failed");
}
......@@ -314,6 +379,7 @@ int callback_encryption_init_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"locking encrypted container failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"locking container failed");
}
......@@ -321,6 +387,7 @@ int callback_encryption_init_post(const struct _u_request * request,
// Record that we want to reboot the machine.
*reboot = true;
json_decref(json_input);
r = send_simple_response(response, 200, "status", "ok");
stop_server();
return r;
......
......@@ -91,11 +91,15 @@ int callback_encryption_keys_delete(const struct _u_request * request,
char * error = keyslot_only_active(cd, keyslot, &only_active);
if (error != NULL)
{
return send_simple_response(response, 500, "error", error);
crypt_free(cd);
r = send_simple_response(response, 500, "error", error);
free(error);
return r;
}
if (only_active)
{
// The keyslot we're asked to delete is the only active one; deny this.
crypt_free(cd);
return send_simple_response(response, 500, "error",
"not deleting only active keyslot");
}
......@@ -107,10 +111,12 @@ int callback_encryption_keys_delete(const struct _u_request * request,
{
// Something else went wrong.
printf("crypt_keyslot_destroy failed with status %d\n", r);
crypt_free(cd);
return send_simple_response(response, 500, "error",
"error deleting encryption password");
}
// If we reach this point, apparently everything went well.
crypt_free(cd);
return send_simple_response(response, 200, "status", "ok");
}
......@@ -38,6 +38,7 @@ int callback_encryption_keys_get(const struct _u_request * request,
int keyslot_max = crypt_keyslot_max(CRYPT_LUKS1);
if (keyslot_max < 0)
{
crypt_free(cd);
return send_simple_response(response, 500, "error",
"crypt_keyslot_max failed");
}
......@@ -75,6 +76,10 @@ int callback_encryption_keys_get(const struct _u_request * request,
// Add keyslot json object to json response.
asprintf(&field, "%d", keyslot);
json_object_set_new(keys, field, key);
if (field)
{
free(field);
}
}
// Create json response.
......@@ -84,5 +89,6 @@ int callback_encryption_keys_get(const struct _u_request * request,
// Send response.
ulfius_set_json_body_response(response, 200, json_body);
json_decref(json_body);
crypt_free(cd);
return U_CALLBACK_CONTINUE;
}
......@@ -18,6 +18,7 @@ int encryption_keys_change(const struct _u_request * request,
password = json_string_value(json_object_get(json_input, "password"));
if (password == NULL)
{
json_decref(json_input);
return send_simple_response(response, 400, "error", "missing password");
}
......@@ -27,6 +28,7 @@ int encryption_keys_change(const struct _u_request * request,
"new-password"));
if (new_password == NULL)
{
json_decref(json_input);
return send_simple_response(response, 400, "error",
"missing new password");
}
......@@ -44,6 +46,7 @@ int encryption_keys_change(const struct _u_request * request,
const char * keyslot_string = u_map_get(request->map_url, "slot");
if (keyslot_string == NULL)
{
json_decref(json_input);
return send_simple_response(response, 400, "error",
"missing url parameter `slot`");
}
......@@ -52,6 +55,7 @@ int encryption_keys_change(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_WARNING,
"invalid url parameter `slot`: %s", keyslot_string);
json_decref(json_input);
return send_simple_response(response, 400, "error",
"invalid url parameter `slot`");
}
......@@ -68,6 +72,7 @@ int encryption_keys_change(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"container_initialise failed with status %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"initialising encrypted container failed");
}
......@@ -88,6 +93,8 @@ int encryption_keys_change(const struct _u_request * request,
if (r == -1)
{
// Experience learns that -1 is returned when the password is wrong.
crypt_free(cd);
json_decref(json_input);
return send_simple_response(response, 403, "error",
"incorrect password");
}
......@@ -105,11 +112,15 @@ int encryption_keys_change(const struct _u_request * request,
y_log_message(Y_LOG_LEVEL_ERROR,
"crypt_keyslot_change_by_passphrase failed with status %d", r);
}
crypt_free(cd);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"error changing password");
}
// If we reach this point, apparently everything went well.
crypt_free(cd);
json_decref(json_input);
return send_simple_response(response, 200, "status", "ok");
}
......
......@@ -34,6 +34,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
json_object_get(json_input, "password"));
if (password == NULL)
{
json_decref(json_input);
return send_simple_response(response, 400, "error", "missing password");
}
......@@ -41,6 +42,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
if (! is_encrypted_device(config.data_partition_device))
{
// The device is not encrypted, so this command does not make sense.
json_decref(json_input);
return send_simple_response(response, 400, "error",
"not encrypted");
}
......@@ -52,6 +54,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
if (r == -1)
{
// The return code -1 signals that the password is wrong.
json_decref(json_input);
return send_simple_response(response, 403, "error",
"incorrect password");
}
......@@ -59,6 +62,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"unlocking encrypted container failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"unlocking encrypted container failed");
}
......@@ -70,6 +74,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"mounting root device failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"mounting root device failed");
}
......@@ -79,6 +84,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
if (! fits)
{
// Projected memory usage is really high, so abort.
json_decref(json_input);
return send_simple_response(response, 500, "error",
"device too large");
}
......@@ -90,11 +96,16 @@ int callback_encryption_remove_post(const struct _u_request * request,
asprintf(&command, "rsync -a %s/ %s",
DATA_TMP_MOUNTPOINT, config.tmp_data_location);
r = system(command);
if (command)
{
free(command);
}
if(r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"copying root device contents into memory failed: return code %d",
r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"copying root device contents into memory failed");
}
......@@ -107,6 +118,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"unmounting encrypted device failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"unmounting encrypted device failed");
}
......@@ -118,6 +130,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"locking encrypted container failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"locking encrypted container failed");
}
......@@ -132,6 +145,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"unmounting info partition failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"unmounting info partition failed");
}
......@@ -142,10 +156,15 @@ int callback_encryption_remove_post(const struct _u_request * request,
command = NULL;
asprintf(&command, "sgdisk -Z %s", config.root_device);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"removing partitions failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"removing partitions failed");
}
......@@ -156,10 +175,15 @@ int callback_encryption_remove_post(const struct _u_request * request,
command = NULL;
asprintf(&command, "mkfs -t %s %s", FILESYSTEM_TYPE, config.root_device);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"creating filesystem failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"creating filesystem on unencrypted device failed");
}
......@@ -172,6 +196,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"mounting unencrypted device failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"mounting unencrypted root device failed");
}
......@@ -183,11 +208,16 @@ int callback_encryption_remove_post(const struct _u_request * request,
asprintf(&command, "rsync -a %s/ %s",
config.tmp_data_location, UNENCRYPTED_TMP_MOUNTPOINT);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
"copying from memory to unencrypted device failed: return code %d",
r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"copying root device contents from memory failed");
}
......@@ -200,6 +230,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
{
y_log_message(Y_LOG_LEVEL_ERROR,
"unmounting unencrypted device failed: return code %d", r);
json_decref(json_input);
return send_simple_response(response, 500, "error",
"unmounting unencrypted device failed");
}
......@@ -207,6 +238,7 @@ int callback_encryption_remove_post(const struct _u_request * request,
// Record that we want to reboot the machine.
*reboot = true;
json_decref(json_input);
r = send_simple_response(response, 200, "status", "ok");
stop_server();
return r;
......
......@@ -52,6 +52,7 @@ int destroy_active_keyslots()
}
}
crypt_free(cd);
return result;
}
......@@ -82,6 +83,10 @@ int callback_encryption_selfdestruct_post(const struct _u_request * request,
asprintf(&command, "head -c %d /dev/zero > %s; sync",
LUKS_HEADER_SIZE, config.data_partition_device);
r = system(command);
if (command)
{
free(command);
}
if (r != 0)
{
y_log_message(Y_LOG_LEVEL_ERROR,
......
......@@ -15,6 +15,7 @@ int callback_encryption_unlock_post(const struct _u_request * request,
if (password == NULL)
{
json_decref(json_input);
return send_simple_response(response, 400, "error", "missing password");
}
......@@ -23,6 +24,7 @@ int callback_encryption_unlock_post(const struct _u_request * request,
if (unlock_status == -1)
{
json_decref(json_input);
// Experience learns that -1 is returned when the password is wrong.
return send_simple_response(response, 403, "error",
"incorrect password");
......@@ -30,6 +32,7 @@ int callback_encryption_unlock_post(const struct _u_request * request,
if (unlock_status != 0)
{
json_decref(json_input);
// Something else went wrong with unlocking.
y_log_message(Y_LOG_LEVEL_ERROR,
"encryption_unlock failed with status %d", unlock_status);
......@@ -38,6 +41,7 @@ int callback_encryption_unlock_post(const struct _u_request * request,
}
// If we reach this point, apparently everything went well.
json_decref(json_input);
int r = send_simple_response(response, 200, "status", "ok");
stop_server();
return r;
......
......@@ -29,7 +29,11 @@ json_t * readAuthorizedKeysToJson()
asprintf(&field, "%d", index);
// Remove trailing newline.
line[strcspn(line, "\n")] = 0;
json_object_set(keys, field, json_string(line));
json_object_set_new(keys, field, json_string(line));
if (field)
{
free(field);
}
}
index++;
}
......
......@@ -47,9 +47,10 @@ int callback_ssh_keys_post(const struct _u_request * request,
add_ssh_command(&ssh_key_with_command, ssh_key);
// Write SSH key to file
asprintf(&ssh_key_with_command, "%s\n", ssh_key_with_command);
fprintf(authorized_keys, ssh_key_with_command);
fprintf(authorized_keys, "%s\n", ssh_key_with_command);
fclose(authorized_keys);
free(ssh_key_with_command);
json_decref(json_input);
return send_simple_response(response, 200, "status", "ok");
}