Add filepath size validation

This commit is contained in:
Tina_Azure
2023-07-31 18:00:34 +02:00
parent eb291a90bb
commit 70c474051c
8 changed files with 78 additions and 12 deletions

1
.gitignore vendored
View File

@ -8,3 +8,4 @@ example.crt
example.key
.idea/
log.txt
submissions/

View File

@ -265,4 +265,6 @@ optional:{default}
submissionMaxtotalStorageMB={131072} Filesize in MB;
submissionMaxStorageDurationH={0} Duration in hours 0 = unlimited;
submissionAllowedFiletypes={rar|zip|7z} Allowed file extensions like rar|zip|7z|webm|avi etc;
submissionMaxFileNameSize={255} 12 characters are used for hash, How big a file name can be the default persumes the NAME_MAX length within common file systems
submissionMaxFilePathSize={4096} How big a file path can be the default persumes the PATH_MAX length within common file systems

View File

@ -27,7 +27,8 @@
# submissionMaxtotalStorageMB={131072} # Filesize in MB;
# submissionMaxStorageDurationH={0} # Duration in hours 0 = unlimited;
# submissionAllowedFiletypes={rar|zip|7z} # Allowed file extensions like rar|zip|7z|webm|avi etc;
# submissionDeletedFileRetentionForNextCycle={true} # File deletion will be executed on the execution of the next Regular Task Execution cylce if true, if false file deletion will be executed immediately.
# submissionMaxFileNameSize={255} # 12 characters are used for hash, How big a file name can be the default persumes the NAME_MAX length within common file systems
# submissionMaxFilePathSize={4096} # How big a file path can be the default persumes the PATH_MAX length within common file systems
@ -58,7 +59,7 @@ submissionMaxFileSizeMB=8;
submissionMaxtotalStorageMB=16;
submissionMaxStorageDurationH=24;
submissionAllowedFiletypes=rar|zip|7z|arc|jpg|jpeg|png|mp4|webm;
submissionDeletedFileRetentionForNextCycle=false;
submissionMaxFileNameSize=255;
submissionMaxFilePathSize=4096;
#configend#

View File

@ -33,6 +33,8 @@ int main(int argc, char *argv[]) {
return 1;
}
configuration.calculateBaseDirectoryPathSize(argv[0]);
//simple email test, header validation via https://mailheader.org/
//SMTPManager::sendEmail(configuration, "mail@mail.de", "testsubject", "<h2> bluetest<h2><br>blue<br>yellow");
//return 0;
@ -985,6 +987,7 @@ int main(int argc, char *argv[]) {
size_t maxStorageInMB = configuration.submissionMaxtotalStorageMB;
ctx[MUSTACHE_FREELANCER_AVAILIBLE_STORAGE_IN_MB] = usedStorageInMB;
ctx[MUSTACHE_FREELANCER_MAXIMUM_STORAGE_IN_MB] = maxStorageInMB;
ctx[MUSTACHE_FREELANCER_MAXIMUM_FILE_NAME_SIZE] = configuration.submissionMaxFileNameSize;
string allowedFiletypes;
for (const string &filetype: configuration.submissionAllowedFiletypes) {
@ -1067,11 +1070,14 @@ int main(int argc, char *argv[]) {
string filename = postRequest.body.substr(filenamePositionStart, contentDispositionTypeEnd - filenamePositionStart - 1);
if (!Utilities::checkFiletypeValidity(configuration, filename)) {
if (!Utilities::checkFiletypeValidity(configuration, filename))
return crow::response(400, "Submitted File does not have a valid filetype");
if (!Utilities::validateFileSize(configuration, postRequest.body))
return crow::response(400, "File Size is not valid");
}
if (!Utilities::validateFileNameSize(configuration, filename))
return crow::response(400, "Filename too long");
const std::string outputFolderPath = Utilities::generateSubmissionFolderPath(configuration, freelancerName, freelancerID);
@ -1084,6 +1090,9 @@ int main(int argc, char *argv[]) {
if (!Utilities::validateFilePath(outputFilePath))
return crow::response(400, "file already exists - hash collision");
if (!Utilities::validateFilePathSize(configuration, outputFilePath))
return crow::response(400, "Filepath too long");
std::ofstream outputFileStream(outputFilePath);
if (!outputFileStream)
return crow::response(500, "File could not be written to disk");

View File

@ -89,6 +89,7 @@ namespace TemplateConstCollection {
const static std::string MUSTACHE_FREELANCER_SUBMISSION_NAME = "FILE_SUBMISSION";
const static std::string MUSTACHE_FREELANCER_AVAILIBLE_STORAGE_IN_MB = "AVAILIBLE_STORAGE_IN_MB";
const static std::string MUSTACHE_FREELANCER_MAXIMUM_STORAGE_IN_MB = "MAXIMUM_STORAGE_IN_MB";
const static std::string MUSTACHE_FREELANCER_MAXIMUM_FILE_NAME_SIZE = "MAXIMUM_FILE_NAME_SIZE";
const static std::string MUSTACHE_FREELANCER_ALLOWED_FILE_TYPES_LIST_COMMA_SEPARATED = "ALLOWED_FILE_TYPES_LIST_COMMA_SEPARATED";
const static std::string MUSTACHE_FREELANCER_UPLOAD_AVAILIBLE = "UPLOAD_AVAILIBLE";

View File

@ -142,7 +142,17 @@ namespace Utilities {
int submissionMaxtotalStorageMB = 131072;
int submissionMaxStorageDurationH = 0;
std::vector<std::string> submissionAllowedFiletypes = {"rar", "zip","7z"};
bool submissionDeletedFileRetentionForNextCycle = true;
int submissionMaxFileNameSize = 255;
int submissionMaxFilePathSize = 4096;
int baseDirectoryPathSize = 0;
/*
* calculates absolute file path length based on submission directory and current path
*/
void calculateBaseDirectoryPathSize(const std::string& baseDirectory) {
std::string baseDir = baseDirectory.substr(0, baseDirectory.rfind('/') + 1);
baseDirectoryPathSize = baseDir.size();
}
/*
* validates existence of mandatory variables in config
@ -296,8 +306,12 @@ namespace Utilities {
submissionAllowedFiletypes = Utilities::splitStringIntoVector(lineString, '|');
continue;
}
if (lineVector.at(0) == "submissionDeletedFileRetentionForNextCycle") {
submissionDeletedFileRetentionForNextCycle = (lineString == "true");
if (lineVector.at(0) == "submissionMaxFileNameSize") {
submissionMaxFileNameSize = std::stoi(lineString);
continue;
}
if (lineVector.at(0) == "submissionMaxFilePathSize") {
submissionMaxFilePathSize = std::stoi(lineString);
continue;
}
}
@ -775,6 +789,37 @@ namespace Utilities {
return validity;
}
/*
* Checks if a filename size is within the limit of submissionMaxFileNameSize
* takes the config and the filename which has to include the extension
*/
bool validateFileNameSize(const Utilities::config& configuration, const std::string& fileName){
bool validity = false;
if (configuration.submissionMaxFileNameSize >= fileName.size())
validity = true;
return validity;
}
/*
* Checks if a filepath size is within the limit of submissionMaxFilePathSize
* takes the config and the filename which has to include the extension
*/
bool validateFilePathSize(const Utilities::config& configuration, const std::string& filePath){
bool validity = false;
std::size_t filePathSize = configuration.baseDirectoryPathSize;
std::string submissionPathRelativityValidation = filePath.substr(0, 2);
if (submissionPathRelativityValidation == "./") { //relative path with . token
filePathSize = filePathSize + filePath.size() - 2;
} else if (submissionPathRelativityValidation[0] == '/') { //absolute path
filePathSize = filePath.size();
} else { //relative path without . token
filePathSize = filePathSize + filePath.size();
}
if (configuration.submissionMaxFilePathSize >= filePathSize)
validity = true;
return validity;
}
bool validateFileSize(const Utilities::config& configuration, const std::string& file){
size_t fileSizeMegaBytes = file.size() / 1048576;
if (configuration.submissionMaxFileSizeMB < fileSizeMegaBytes)

View File

@ -16,6 +16,9 @@
<p>
Allowed File Types: {{ALLOWED_FILE_TYPES_LIST_COMMA_SEPARATED}}
</p>
<p>
Allowed File Name Length: {{MAXIMUM_FILE_NAME_SIZE}}
</p>
</div>
{{#UPLOAD_AVAILIBLE}}
<form method="post" enctype="multipart/form-data" action="javascript:upload()">

View File

@ -8,11 +8,15 @@
var file = _("FILE_SUBMISSION").files[0];
const fileSize = file.size / 1024 / 1024;
const maxSize = {{MAXIMUM_STORAGE_IN_MB}} - {{AVAILIBLE_STORAGE_IN_MB}};
const maxFileNameLength = {{MAXIMUM_FILE_NAME_SIZE}};
console.log(maxSize);
console.log(maxFileNameLength);
if (fileSize > maxSize) {
alert('File size exceeds availible space by: ' + (Math.trunc((fileSize - maxSize) * 100) / 100) + ' MB');
unHide();
} else if(file.name.length > maxFileNameLength) {
alert('File name exceeds allowed length by ' + (file.name.length - maxFileNameLength) + ' characters');
unHide();
}
else {
var formdata = new FormData();