mirror of
https://github.com/kingk85/uFTP.git
synced 2025-04-21 00:48:37 +03:00
LIST and NLIST support -a and -A parameters
This commit is contained in:
@ -61,7 +61,7 @@ int parseCommandUser(ftpDataType * data, int socketId)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (strlen(theUserName) >= 1)
|
if (strnlen(theUserName, 1) >= 1)
|
||||||
{
|
{
|
||||||
setDynamicStringDataType(&data->clients[socketId].login.name, theUserName, strlen(theUserName), &data->clients[socketId].memoryTable);
|
setDynamicStringDataType(&data->clients[socketId].login.name, theUserName, strlen(theUserName), &data->clients[socketId].memoryTable);
|
||||||
returnCode = socketPrintf(data, socketId, "s", "331 User ok, Waiting for the password.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "331 User ok, Waiting for the password.\r\n");
|
||||||
@ -118,9 +118,10 @@ int parseCommandSite(ftpDataType *data, int socketId)
|
|||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "s", "500 unknown extension\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "500 unknown extension\r\n");
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
if (returnCode <= 0)
|
if (returnCode <= 0)
|
||||||
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
}
|
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
@ -156,7 +157,7 @@ int parseCommandPass(ftpDataType *data, int socketId)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (strlen(thePass) >= 1)
|
if (strnlen(thePass, 1) >= 1)
|
||||||
{
|
{
|
||||||
|
|
||||||
// my_printf("\nLogin try with user %s, password %s", data->clients[socketId].login.name.text, thePass);
|
// my_printf("\nLogin try with user %s, password %s", data->clients[socketId].login.name.text, thePass);
|
||||||
@ -217,6 +218,7 @@ int parseCommandPass(ftpDataType *data, int socketId)
|
|||||||
my_printf("\ndata->clients[socketId].login.ownerShip.uid = %d", data->clients[socketId].login.ownerShip.uid);
|
my_printf("\ndata->clients[socketId].login.ownerShip.uid = %d", data->clients[socketId].login.ownerShip.uid);
|
||||||
|
|
||||||
returnCode = socketPrintf(data, socketId, "s", "230 Login Ok.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "230 Login Ok.\r\n");
|
||||||
|
|
||||||
if (returnCode <= 0)
|
if (returnCode <= 0)
|
||||||
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
}
|
}
|
||||||
@ -239,6 +241,7 @@ int parseCommandPass(ftpDataType *data, int socketId)
|
|||||||
}
|
}
|
||||||
|
|
||||||
returnCode = socketPrintf(data, socketId, "s", "430 Invalid username or password\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "430 Invalid username or password\r\n");
|
||||||
|
|
||||||
if (returnCode <= 0)
|
if (returnCode <= 0)
|
||||||
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
return 1;
|
return 1;
|
||||||
@ -251,6 +254,7 @@ int parseCommandAuth(ftpDataType *data, int socketId)
|
|||||||
|
|
||||||
#ifndef OPENSSL_ENABLED
|
#ifndef OPENSSL_ENABLED
|
||||||
returnCode = socketPrintf(data, socketId, "s", "502 Security extensions not implemented.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "502 Security extensions not implemented.\r\n");
|
||||||
|
|
||||||
if (returnCode <= 0)
|
if (returnCode <= 0)
|
||||||
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
#endif
|
#endif
|
||||||
@ -258,6 +262,7 @@ int parseCommandAuth(ftpDataType *data, int socketId)
|
|||||||
#ifdef OPENSSL_ENABLED
|
#ifdef OPENSSL_ENABLED
|
||||||
|
|
||||||
returnCode = socketPrintf(data, socketId, "s", "234 AUTH TLS OK..\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "234 AUTH TLS OK..\r\n");
|
||||||
|
|
||||||
if (returnCode <= 0)
|
if (returnCode <= 0)
|
||||||
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
@ -304,6 +309,7 @@ int parseCommandSyst(ftpDataType *data, int socketId)
|
|||||||
{
|
{
|
||||||
int returnCode;
|
int returnCode;
|
||||||
returnCode = socketPrintf(data, socketId, "s", "215 UNIX Type: L8\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "215 UNIX Type: L8\r\n");
|
||||||
|
|
||||||
if (returnCode <= 0)
|
if (returnCode <= 0)
|
||||||
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
@ -328,6 +334,7 @@ int parseCommandFeat(ftpDataType *data, int socketId)
|
|||||||
#ifndef OPENSSL_ENABLED
|
#ifndef OPENSSL_ENABLED
|
||||||
returnCode = socketPrintf(data, socketId, "s", "211-Extensions supported:\r\nPASV\r\nEPSV\r\nUTF8\r\nSIZE\r\nMDTM\r\nREST\r\n211 End.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "211-Extensions supported:\r\nPASV\r\nEPSV\r\nUTF8\r\nSIZE\r\nMDTM\r\nREST\r\n211 End.\r\n");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (returnCode <= 0)
|
if (returnCode <= 0)
|
||||||
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
@ -396,6 +403,7 @@ int parseCommandPbsz(ftpDataType *data, int socketId)
|
|||||||
thePbszSize = getFtpCommandArg("PBSZ", data->clients[socketId].theCommandReceived, 0);
|
thePbszSize = getFtpCommandArg("PBSZ", data->clients[socketId].theCommandReceived, 0);
|
||||||
|
|
||||||
returnCode = socketPrintf(data, socketId, "sss", "200 PBSZ set to ", thePbszSize, "\r\n");
|
returnCode = socketPrintf(data, socketId, "sss", "200 PBSZ set to ", thePbszSize, "\r\n");
|
||||||
|
|
||||||
if (returnCode <= 0)
|
if (returnCode <= 0)
|
||||||
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
@ -588,20 +596,9 @@ int parseCommandAbor(ftpDataType *data, int socketId)
|
|||||||
int parseCommandList(ftpDataType *data, int socketId)
|
int parseCommandList(ftpDataType *data, int socketId)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
-1 List one file per line
|
|
||||||
-A List all files except "." and ".."
|
-A List all files except "." and ".."
|
||||||
-a List all files including those whose names start with "."
|
-a List all files including those whose names start with "."
|
||||||
-C List entries by columns
|
|
||||||
-d List directory entries instead of directory contents
|
|
||||||
-F Append file type indicator (one of "*", "/", "=", "@" or "|") to names
|
|
||||||
-h Print file sizes in human-readable format (e.g. 1K, 234M, 2G)
|
|
||||||
-L List files pointed to by symlinks
|
|
||||||
-l Use a long listing format
|
|
||||||
-n List numeric UIDs/GIDs instead of user/group names
|
|
||||||
-R List subdirectories recursively
|
|
||||||
-r Sort filenames in reverse order
|
|
||||||
-S Sort by file size
|
|
||||||
-t Sort by modification time
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
int isSafePath = 0;
|
int isSafePath = 0;
|
||||||
@ -611,23 +608,29 @@ int parseCommandList(ftpDataType *data, int socketId)
|
|||||||
if(!data->clients[socketId].workerData.socketIsReadyForConnection)
|
if(!data->clients[socketId].workerData.socketIsReadyForConnection)
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "s", "425 Use PORT or PASV first.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "425 Use PORT or PASV first.\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cleanDynamicStringDataType(&data->clients[socketId].workerData.ftpCommand.commandArgs, 0, &data->clients[socketId].workerData.memoryTable);
|
||||||
|
cleanDynamicStringDataType(&data->clients[socketId].workerData.ftpCommand.commandOps, 0, &data->clients[socketId].workerData.memoryTable);
|
||||||
|
|
||||||
theNameToList = getFtpCommandArg("LIST", data->clients[socketId].theCommandReceived, 1);
|
theNameToList = getFtpCommandArg("LIST", data->clients[socketId].theCommandReceived, 1);
|
||||||
getFtpCommandArgWithOptions("LIST", data->clients[socketId].theCommandReceived, &data->clients[socketId].workerData.ftpCommand, &data->clients[socketId].workerData.memoryTable);
|
getFtpCommandArgWithOptions("LIST", data->clients[socketId].theCommandReceived, &data->clients[socketId].workerData.ftpCommand, &data->clients[socketId].workerData.memoryTable);
|
||||||
|
|
||||||
// if (data->clients[socketId].workerData.ftpCommand.commandArgs.text != NULL)
|
|
||||||
// my_printf("\nLIST COMMAND ARG: %s", data->clients[socketId].workerData.ftpCommand.commandArgs.text);
|
|
||||||
// if (data->clients[socketId].workerData.ftpCommand.commandOps.text != NULL)
|
|
||||||
// my_printf("\nLIST COMMAND OPS: %s", data->clients[socketId].workerData.ftpCommand.commandOps.text);
|
|
||||||
// my_printf("\ntheNameToList: %s", theNameToList);
|
|
||||||
|
|
||||||
cleanDynamicStringDataType(&data->clients[socketId].workerData.ftpCommand.commandArgs, 0, &data->clients[socketId].workerData.memoryTable);
|
if (data->clients[socketId].workerData.ftpCommand.commandArgs.text != NULL)
|
||||||
cleanDynamicStringDataType(&data->clients[socketId].workerData.ftpCommand.commandOps, 0, &data->clients[socketId].workerData.memoryTable);
|
my_printf("\nLIST COMMAND ARG: %s", data->clients[socketId].workerData.ftpCommand.commandArgs.text);
|
||||||
|
if (data->clients[socketId].workerData.ftpCommand.commandOps.text != NULL)
|
||||||
|
my_printf("\nLIST COMMAND OPS: %s", data->clients[socketId].workerData.ftpCommand.commandOps.text);
|
||||||
|
|
||||||
|
|
||||||
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
||||||
|
|
||||||
if (strlen(theNameToList) > 0)
|
if (strnlen(theNameToList, 1) > 0)
|
||||||
{
|
{
|
||||||
isSafePath = getSafePath(&data->clients[socketId].listPath, theNameToList, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
isSafePath = getSafePath(&data->clients[socketId].listPath, theNameToList, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
||||||
}
|
}
|
||||||
@ -644,6 +647,10 @@ int parseCommandList(ftpDataType *data, int socketId)
|
|||||||
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
||||||
setDynamicStringDataType(&data->clients[socketId].listPath, data->clients[socketId].login.absolutePath.text, data->clients[socketId].login.absolutePath.textLen, &data->clients[socketId].memoryTable);
|
setDynamicStringDataType(&data->clients[socketId].listPath, data->clients[socketId].login.absolutePath.text, data->clients[socketId].login.absolutePath.textLen, &data->clients[socketId].memoryTable);
|
||||||
returnCode = socketPrintf(data, socketId, "s", "550 wrong path\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "550 wrong path\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -652,6 +659,10 @@ int parseCommandList(ftpDataType *data, int socketId)
|
|||||||
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
||||||
setDynamicStringDataType(&data->clients[socketId].listPath, data->clients[socketId].login.absolutePath.text, data->clients[socketId].login.absolutePath.textLen, &data->clients[socketId].memoryTable);
|
setDynamicStringDataType(&data->clients[socketId].listPath, data->clients[socketId].login.absolutePath.text, data->clients[socketId].login.absolutePath.textLen, &data->clients[socketId].memoryTable);
|
||||||
returnCode = socketPrintf(data, socketId, "s", "550 no permissions.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "550 no permissions.\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -675,17 +686,24 @@ int parseCommandNlst(ftpDataType *data, int socketId)
|
|||||||
if(!data->clients[socketId].workerData.socketIsReadyForConnection)
|
if(!data->clients[socketId].workerData.socketIsReadyForConnection)
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "s", "425 Use PORT or PASV first.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "425 Use PORT or PASV first.\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
cleanDynamicStringDataType(&data->clients[socketId].workerData.ftpCommand.commandArgs, 0, &data->clients[socketId].workerData.memoryTable);
|
||||||
|
cleanDynamicStringDataType(&data->clients[socketId].workerData.ftpCommand.commandOps, 0, &data->clients[socketId].workerData.memoryTable);
|
||||||
|
|
||||||
theNameToNlist = getFtpCommandArg("NLIST", data->clients[socketId].theCommandReceived, 1);
|
theNameToNlist = getFtpCommandArg("NLIST", data->clients[socketId].theCommandReceived, 1);
|
||||||
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
||||||
|
|
||||||
// my_printf("\nNLIST COMMAND ARG: %s", data->clients[socketId].workerData.ftpCommand.commandArgs.text);
|
my_printf("\nNLIST COMMAND ARG: %s", data->clients[socketId].workerData.ftpCommand.commandArgs.text);
|
||||||
// my_printf("\nNLIST COMMAND OPS: %s", data->clients[socketId].workerData.ftpCommand.commandOps.text);
|
my_printf("\nNLIST COMMAND OPS: %s", data->clients[socketId].workerData.ftpCommand.commandOps.text);
|
||||||
// my_printf("\ntheNameToNlist: %s", theNameToNlist);
|
my_printf("\ntheNameToNlist: %s", theNameToNlist);
|
||||||
|
|
||||||
if (strlen(theNameToNlist) > 0)
|
if (strnlen(theNameToNlist,1) > 0)
|
||||||
{
|
{
|
||||||
isSafePath = getSafePath(&data->clients[socketId].listPath, theNameToNlist, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
isSafePath = getSafePath(&data->clients[socketId].listPath, theNameToNlist, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
||||||
}
|
}
|
||||||
@ -701,6 +719,10 @@ int parseCommandNlst(ftpDataType *data, int socketId)
|
|||||||
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
||||||
setDynamicStringDataType(&data->clients[socketId].listPath, data->clients[socketId].login.absolutePath.text, data->clients[socketId].login.absolutePath.textLen, &data->clients[socketId].memoryTable);
|
setDynamicStringDataType(&data->clients[socketId].listPath, data->clients[socketId].login.absolutePath.text, data->clients[socketId].login.absolutePath.textLen, &data->clients[socketId].memoryTable);
|
||||||
returnCode = socketPrintf(data, socketId, "s", "550 wrong path.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "550 wrong path.\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -709,6 +731,11 @@ int parseCommandNlst(ftpDataType *data, int socketId)
|
|||||||
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&data->clients[socketId].listPath, 0, &data->clients[socketId].memoryTable);
|
||||||
setDynamicStringDataType(&data->clients[socketId].listPath, data->clients[socketId].login.absolutePath.text, data->clients[socketId].login.absolutePath.textLen, &data->clients[socketId].memoryTable);
|
setDynamicStringDataType(&data->clients[socketId].listPath, data->clients[socketId].login.absolutePath.text, data->clients[socketId].login.absolutePath.textLen, &data->clients[socketId].memoryTable);
|
||||||
returnCode = socketPrintf(data, socketId, "s", "550 no permissions.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "550 no permissions.\r\n");
|
||||||
|
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -732,13 +759,18 @@ int parseCommandRetr(ftpDataType *data, int socketId)
|
|||||||
if(!data->clients[socketId].workerData.socketIsReadyForConnection)
|
if(!data->clients[socketId].workerData.socketIsReadyForConnection)
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "s", "425 Use PORT or PASV first.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "425 Use PORT or PASV first.\r\n");
|
||||||
|
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
theNameToRetr = getFtpCommandArg("RETR", data->clients[socketId].theCommandReceived, 0);
|
theNameToRetr = getFtpCommandArg("RETR", data->clients[socketId].theCommandReceived, 0);
|
||||||
cleanDynamicStringDataType(&data->clients[socketId].fileToRetr, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&data->clients[socketId].fileToRetr, 0, &data->clients[socketId].memoryTable);
|
||||||
|
|
||||||
if (strlen(theNameToRetr) > 0)
|
if (strnlen(theNameToRetr, 1) > 0)
|
||||||
{
|
{
|
||||||
isSafePath = getSafePath(&data->clients[socketId].fileToRetr, theNameToRetr, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
isSafePath = getSafePath(&data->clients[socketId].fileToRetr, theNameToRetr, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
||||||
}
|
}
|
||||||
@ -746,6 +778,17 @@ int parseCommandRetr(ftpDataType *data, int socketId)
|
|||||||
if (isSafePath == 1 &&
|
if (isSafePath == 1 &&
|
||||||
FILE_IsFile(data->clients[socketId].fileToRetr.text) == 1)
|
FILE_IsFile(data->clients[socketId].fileToRetr.text) == 1)
|
||||||
{
|
{
|
||||||
|
|
||||||
|
if ((checkUserFilePermissions(data->clients[socketId].fileToRetr.text, data->clients[socketId].login.ownerShip.uid, data->clients[socketId].login.ownerShip.gid) & FILE_PERMISSION_R) != FILE_PERMISSION_R)
|
||||||
|
{
|
||||||
|
int writeReturn = socketPrintf(data, socketId, "s", "550 no reading permission on the file\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
|
return FTP_COMMAND_PROCESSED;
|
||||||
|
}
|
||||||
|
|
||||||
pthread_mutex_lock(&data->clients[socketId].conditionMutex);
|
pthread_mutex_lock(&data->clients[socketId].conditionMutex);
|
||||||
|
|
||||||
memset(data->clients[socketId].workerData.theCommandReceived, 0, CLIENT_COMMAND_STRING_SIZE+1);
|
memset(data->clients[socketId].workerData.theCommandReceived, 0, CLIENT_COMMAND_STRING_SIZE+1);
|
||||||
@ -759,6 +802,10 @@ int parseCommandRetr(ftpDataType *data, int socketId)
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "s", "550 Failed to open file.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "550 Failed to open file.\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -774,20 +821,32 @@ int parseCommandStor(ftpDataType *data, int socketId)
|
|||||||
if(!data->clients[socketId].workerData.socketIsReadyForConnection)
|
if(!data->clients[socketId].workerData.socketIsReadyForConnection)
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "s", "425 Use PORT or PASV first.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "425 Use PORT or PASV first.\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
theNameToStor = getFtpCommandArg("STOR", data->clients[socketId].theCommandReceived, 0);
|
theNameToStor = getFtpCommandArg("STOR", data->clients[socketId].theCommandReceived, 0);
|
||||||
cleanDynamicStringDataType(&data->clients[socketId].fileToStor, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&data->clients[socketId].fileToStor, 0, &data->clients[socketId].memoryTable);
|
||||||
|
if (strnlen(theNameToStor, 1) > 0)
|
||||||
if (strlen(theNameToStor) > 0)
|
|
||||||
{
|
{
|
||||||
isSafePath = getSafePath(&data->clients[socketId].fileToStor, theNameToStor, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
isSafePath = getSafePath(&data->clients[socketId].fileToStor, theNameToStor, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isSafePath == 1)
|
if (isSafePath == 1)
|
||||||
{
|
{
|
||||||
|
if ((checkParentDirectoryPermissions(data->clients[socketId].fileToStor.text, data->clients[socketId].login.ownerShip.uid, data->clients[socketId].login.ownerShip.gid) & FILE_PERMISSION_W) != FILE_PERMISSION_W)
|
||||||
|
{
|
||||||
|
returnCode = socketPrintf(data, socketId, "s", "550 No permissions to write the file\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
|
return FTP_COMMAND_PROCESSED;
|
||||||
|
}
|
||||||
|
|
||||||
pthread_mutex_lock(&data->clients[socketId].conditionMutex);
|
pthread_mutex_lock(&data->clients[socketId].conditionMutex);
|
||||||
memset(data->clients[socketId].workerData.theCommandReceived, 0, CLIENT_COMMAND_STRING_SIZE+1);
|
memset(data->clients[socketId].workerData.theCommandReceived, 0, CLIENT_COMMAND_STRING_SIZE+1);
|
||||||
strncpy(data->clients[socketId].workerData.theCommandReceived, data->clients[socketId].theCommandReceived, CLIENT_COMMAND_STRING_SIZE);
|
strncpy(data->clients[socketId].workerData.theCommandReceived, data->clients[socketId].theCommandReceived, CLIENT_COMMAND_STRING_SIZE);
|
||||||
@ -798,6 +857,11 @@ int parseCommandStor(ftpDataType *data, int socketId)
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "s", "550 Wrong path.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "550 Wrong path.\r\n");
|
||||||
|
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -813,19 +877,35 @@ int parseCommandAppe(ftpDataType *data, int socketId)
|
|||||||
if(!data->clients[socketId].workerData.socketIsReadyForConnection)
|
if(!data->clients[socketId].workerData.socketIsReadyForConnection)
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "s", "425 Use PORT or PASV first.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "425 Use PORT or PASV first.\r\n");
|
||||||
|
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
theNameToStor = getFtpCommandArg("APPE", data->clients[socketId].theCommandReceived, 0);
|
theNameToStor = getFtpCommandArg("APPE", data->clients[socketId].theCommandReceived, 0);
|
||||||
cleanDynamicStringDataType(&data->clients[socketId].fileToStor, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&data->clients[socketId].fileToStor, 0, &data->clients[socketId].memoryTable);
|
||||||
|
|
||||||
if (strlen(theNameToStor) > 0)
|
if (strnlen(theNameToStor, 1) > 0)
|
||||||
{
|
{
|
||||||
isSafePath = getSafePath(&data->clients[socketId].fileToStor, theNameToStor, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
isSafePath = getSafePath(&data->clients[socketId].fileToStor, theNameToStor, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isSafePath == 1)
|
if (isSafePath == 1)
|
||||||
{
|
{
|
||||||
|
|
||||||
|
if ((checkParentDirectoryPermissions(data->clients[socketId].fileToStor.text, data->clients[socketId].login.ownerShip.uid, data->clients[socketId].login.ownerShip.gid) & FILE_PERMISSION_W) != FILE_PERMISSION_W)
|
||||||
|
{
|
||||||
|
returnCode = socketPrintf(data, socketId, "s", "550 No permissions to write the file\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
|
return FTP_COMMAND_PROCESSED;
|
||||||
|
}
|
||||||
|
|
||||||
pthread_mutex_lock(&data->clients[socketId].conditionMutex);
|
pthread_mutex_lock(&data->clients[socketId].conditionMutex);
|
||||||
memset(data->clients[socketId].workerData.theCommandReceived, 0, CLIENT_COMMAND_STRING_SIZE+1);
|
memset(data->clients[socketId].workerData.theCommandReceived, 0, CLIENT_COMMAND_STRING_SIZE+1);
|
||||||
strncpy(data->clients[socketId].workerData.theCommandReceived, data->clients[socketId].theCommandReceived, CLIENT_COMMAND_STRING_SIZE);
|
strncpy(data->clients[socketId].workerData.theCommandReceived, data->clients[socketId].theCommandReceived, CLIENT_COMMAND_STRING_SIZE);
|
||||||
@ -836,6 +916,10 @@ int parseCommandAppe(ftpDataType *data, int socketId)
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "s", "550 Wrong path.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "550 Wrong path.\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -857,7 +941,7 @@ int parseCommandCwd(ftpDataType *data, int socketId)
|
|||||||
|
|
||||||
//my_printf("\ncdw requested path: %s", thePath);
|
//my_printf("\ncdw requested path: %s", thePath);
|
||||||
|
|
||||||
if (strlen(thePath) > 0)
|
if (strnlen(thePath, 1) > 0)
|
||||||
{
|
{
|
||||||
// my_printf("Memory data address 1st call : %lld", &data->clients[socketId].memoryTable);
|
// my_printf("Memory data address 1st call : %lld", &data->clients[socketId].memoryTable);
|
||||||
isSafePath = getSafePath(&theSafePath, thePath, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
isSafePath = getSafePath(&theSafePath, thePath, &data->clients[socketId].login, &data->clients[socketId].memoryTable);
|
||||||
@ -902,10 +986,17 @@ int parseCommandCwd(ftpDataType *data, int socketId)
|
|||||||
if ((checkUserFilePermissions(data->clients[socketId].login.absolutePath.text, data->clients[socketId].login.ownerShip.uid, data->clients[socketId].login.ownerShip.gid) & FILE_PERMISSION_R) == FILE_PERMISSION_R)
|
if ((checkUserFilePermissions(data->clients[socketId].login.absolutePath.text, data->clients[socketId].login.ownerShip.uid, data->clients[socketId].login.ownerShip.gid) & FILE_PERMISSION_R) == FILE_PERMISSION_R)
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "sss", "250 OK. Current directory is ", data->clients[socketId].login.ftpPath.text, "\r\n");
|
returnCode = socketPrintf(data, socketId, "sss", "250 OK. Current directory is ", data->clients[socketId].login.ftpPath.text, "\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "sss", "530 Can't change directory to ", data->clients[socketId].login.absolutePath.text, ": no permissions\r\n");
|
returnCode = socketPrintf(data, socketId, "sss", "530 Can't change directory to ", data->clients[socketId].login.absolutePath.text, ": no permissions\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
setDynamicStringDataType(&data->clients[socketId].login.absolutePath, absolutePathPrevious.text, absolutePathPrevious.textLen, &data->clients[socketId].memoryTable);
|
setDynamicStringDataType(&data->clients[socketId].login.absolutePath, absolutePathPrevious.text, absolutePathPrevious.textLen, &data->clients[socketId].memoryTable);
|
||||||
setDynamicStringDataType(&data->clients[socketId].login.ftpPath, ftpPathPrevious.text, ftpPathPrevious.textLen, &data->clients[socketId].memoryTable);
|
setDynamicStringDataType(&data->clients[socketId].login.ftpPath, ftpPathPrevious.text, ftpPathPrevious.textLen, &data->clients[socketId].memoryTable);
|
||||||
}
|
}
|
||||||
@ -913,6 +1004,10 @@ int parseCommandCwd(ftpDataType *data, int socketId)
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
returnCode = socketPrintf(data, socketId, "sss", "530 Can't change directory to ", data->clients[socketId].login.absolutePath.text, ": No such file or directory\r\n");
|
returnCode = socketPrintf(data, socketId, "sss", "530 Can't change directory to ", data->clients[socketId].login.absolutePath.text, ": No such file or directory\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
setDynamicStringDataType(&data->clients[socketId].login.absolutePath, absolutePathPrevious.text, absolutePathPrevious.textLen, &data->clients[socketId].memoryTable);
|
setDynamicStringDataType(&data->clients[socketId].login.absolutePath, absolutePathPrevious.text, absolutePathPrevious.textLen, &data->clients[socketId].memoryTable);
|
||||||
setDynamicStringDataType(&data->clients[socketId].login.ftpPath, ftpPathPrevious.text, ftpPathPrevious.textLen, &data->clients[socketId].memoryTable);
|
setDynamicStringDataType(&data->clients[socketId].login.ftpPath, ftpPathPrevious.text, ftpPathPrevious.textLen, &data->clients[socketId].memoryTable);
|
||||||
}
|
}
|
||||||
@ -932,6 +1027,10 @@ int parseCommandCwd(ftpDataType *data, int socketId)
|
|||||||
cleanDynamicStringDataType(&ftpPathPrevious, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&ftpPathPrevious, 0, &data->clients[socketId].memoryTable);
|
||||||
cleanDynamicStringDataType(&theSafePath, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&theSafePath, 0, &data->clients[socketId].memoryTable);
|
||||||
returnCode = socketPrintf(data, socketId, "s", "550 Wrong path.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "550 Wrong path.\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1050,6 +1149,9 @@ int parseCommandMkd(ftpDataType *data, int socketId)
|
|||||||
{
|
{
|
||||||
cleanDynamicStringDataType(&mkdFileName, 0, &data->clients[socketId].memoryTable);
|
cleanDynamicStringDataType(&mkdFileName, 0, &data->clients[socketId].memoryTable);
|
||||||
returnCode = socketPrintf(data, socketId, "s", "550 Wrong path.\r\n");
|
returnCode = socketPrintf(data, socketId, "s", "550 Wrong path.\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
functionReturnCode = FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
functionReturnCode = FTP_COMMAND_PROCESSED;
|
functionReturnCode = FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1449,6 +1551,19 @@ int parseCommandCdup(ftpDataType *data, int socketId)
|
|||||||
return FTP_COMMAND_PROCESSED;
|
return FTP_COMMAND_PROCESSED;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int parseCommandAcct(ftpDataType *data, int socketId)
|
||||||
|
{
|
||||||
|
int returnCode;
|
||||||
|
|
||||||
|
returnCode = socketPrintf(data, socketId, "s", "502 ACCT not implemented.\r\n");
|
||||||
|
|
||||||
|
if (returnCode <= 0)
|
||||||
|
return FTP_COMMAND_PROCESSED_WRITE_ERROR;
|
||||||
|
|
||||||
|
return FTP_COMMAND_PROCESSED;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
long long int writeRetrFile(ftpDataType *data, int theSocketId, long long int startFrom, FILE *retrFP)
|
long long int writeRetrFile(ftpDataType *data, int theSocketId, long long int startFrom, FILE *retrFP)
|
||||||
{
|
{
|
||||||
long long int readen = 0;
|
long long int readen = 0;
|
||||||
|
@ -88,6 +88,8 @@ int parseCommandMdtm(ftpDataType * data, int socketId);
|
|||||||
int parseCommandOpts(ftpDataType * data, int socketId);
|
int parseCommandOpts(ftpDataType * data, int socketId);
|
||||||
int parseCommandRnfr(ftpDataType * data, int socketId);
|
int parseCommandRnfr(ftpDataType * data, int socketId);
|
||||||
int parseCommandRnto(ftpDataType * data, int socketId);
|
int parseCommandRnto(ftpDataType * data, int socketId);
|
||||||
|
int parseCommandAcct(ftpDataType * data, int socketId);
|
||||||
|
|
||||||
|
|
||||||
long long int writeRetrFile(ftpDataType * data, int theSocketId, long long int startFrom, FILE *retrFP);
|
long long int writeRetrFile(ftpDataType * data, int theSocketId, long long int startFrom, FILE *retrFP);
|
||||||
char *getFtpCommandArg(char * theCommand, char *theCommandString, int skipArgs);
|
char *getFtpCommandArg(char * theCommand, char *theCommandString, int skipArgs);
|
||||||
|
15
ftpData.c
15
ftpData.c
@ -225,13 +225,17 @@ void setRandomicPort(ftpDataType *data, int socketPosition)
|
|||||||
|
|
||||||
int writeListDataInfoToSocket(ftpDataType *ftpData, int clientId, int *filesNumber, int commandType, DYNMEM_MemoryTable_DataType **memoryTable)
|
int writeListDataInfoToSocket(ftpDataType *ftpData, int clientId, int *filesNumber, int commandType, DYNMEM_MemoryTable_DataType **memoryTable)
|
||||||
{
|
{
|
||||||
|
// a --> include . and ..
|
||||||
|
// A --> do not include . and ..
|
||||||
|
// nothing --> no hidden no . and no ..
|
||||||
my_printf("\nFILE_GetDirectoryInodeList arg path: %s", ftpData->clients[clientId].listPath.text);
|
my_printf("\nFILE_GetDirectoryInodeList arg path: %s", ftpData->clients[clientId].listPath.text);
|
||||||
|
my_printf("\nftpData->clients[clientId].workerData.ftpCommand.commandArgs: %s", ftpData->clients[clientId].workerData.ftpCommand.commandArgs.text);
|
||||||
|
my_printf("\nftpData->clients[clientId].workerData.ftpCommand.commandOps: %s", ftpData->clients[clientId].workerData.ftpCommand.commandOps.text);
|
||||||
|
|
||||||
int i, x, returnCode;
|
int i, x, returnCode;
|
||||||
int fileAndFoldersCount = 0;
|
int fileAndFoldersCount = 0;
|
||||||
char **fileList = NULL;
|
char **fileList = NULL;
|
||||||
FILE_GetDirectoryInodeList(ftpData->clients[clientId].listPath.text, &fileList, &fileAndFoldersCount, 0, memoryTable);
|
FILE_GetDirectoryInodeList(ftpData->clients[clientId].listPath.text, &fileList, &fileAndFoldersCount, 0, ftpData->clients[clientId].workerData.ftpCommand.commandOps.text, memoryTable);
|
||||||
*filesNumber = fileAndFoldersCount;
|
*filesNumber = fileAndFoldersCount;
|
||||||
|
|
||||||
returnCode = socketWorkerPrintf(ftpData, clientId, "sds", "total ", fileAndFoldersCount ,"\r\n");
|
returnCode = socketWorkerPrintf(ftpData, clientId, "sds", "total ", fileAndFoldersCount ,"\r\n");
|
||||||
@ -280,7 +284,6 @@ int writeListDataInfoToSocket(ftpDataType *ftpData, int clientId, int *filesNumb
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//my_printf("\nFILE SIZE : %lld", data.fileSize);
|
//my_printf("\nFILE SIZE : %lld", data.fileSize);
|
||||||
|
|
||||||
data.owner = FILE_GetOwner(fileList[i], memoryTable);
|
data.owner = FILE_GetOwner(fileList[i], memoryTable);
|
||||||
@ -428,7 +431,7 @@ void getListDataInfo(char * thePath, DYNV_VectorGenericDataType *directoryInfo,
|
|||||||
int i;
|
int i;
|
||||||
int fileAndFoldersCount = 0;
|
int fileAndFoldersCount = 0;
|
||||||
ftpListDataType data;
|
ftpListDataType data;
|
||||||
FILE_GetDirectoryInodeList(thePath, &data.fileList, &fileAndFoldersCount, 0, memoryTable);
|
FILE_GetDirectoryInodeList(thePath, &data.fileList, &fileAndFoldersCount, 0, "Z", memoryTable);
|
||||||
|
|
||||||
//my_printf("\nNUMBER OF FILES: %d", fileAndFoldersCount);
|
//my_printf("\nNUMBER OF FILES: %d", fileAndFoldersCount);
|
||||||
//fflush(0);
|
//fflush(0);
|
||||||
@ -533,7 +536,6 @@ void getListDataInfo(char * thePath, DYNV_VectorGenericDataType *directoryInfo,
|
|||||||
|
|
||||||
void deleteListDataInfoVector(DYNV_VectorGenericDataType *theVector)
|
void deleteListDataInfoVector(DYNV_VectorGenericDataType *theVector)
|
||||||
{
|
{
|
||||||
|
|
||||||
int i;
|
int i;
|
||||||
for (i = 0; i < theVector->Size; i++)
|
for (i = 0; i < theVector->Size; i++)
|
||||||
{
|
{
|
||||||
@ -576,7 +578,6 @@ void cancelWorker(ftpDataType *data, int clientId)
|
|||||||
|
|
||||||
void resetWorkerData(ftpDataType *data, int clientId, int isInitialization)
|
void resetWorkerData(ftpDataType *data, int clientId, int isInitialization)
|
||||||
{
|
{
|
||||||
|
|
||||||
my_printf("\nReset of worker id: %d", clientId);
|
my_printf("\nReset of worker id: %d", clientId);
|
||||||
data->clients[clientId].workerData.connectionPort = 0;
|
data->clients[clientId].workerData.connectionPort = 0;
|
||||||
data->clients[clientId].workerData.passiveModeOn = 0;
|
data->clients[clientId].workerData.passiveModeOn = 0;
|
||||||
|
52
ftpServer.c
52
ftpServer.c
@ -289,39 +289,18 @@ void *connectionWorkerHandle(void * socketId)
|
|||||||
my_printf("\nWorker %d is waiting for commands!", theSocketId);
|
my_printf("\nWorker %d is waiting for commands!", theSocketId);
|
||||||
//Conditional lock on tconditionVariablehread actions
|
//Conditional lock on tconditionVariablehread actions
|
||||||
pthread_mutex_lock(&ftpData.clients[theSocketId].conditionMutex);
|
pthread_mutex_lock(&ftpData.clients[theSocketId].conditionMutex);
|
||||||
//int sleepTime = 1000;
|
|
||||||
while (ftpData.clients[theSocketId].workerData.commandReceived == 0)
|
while (ftpData.clients[theSocketId].workerData.commandReceived == 0)
|
||||||
{
|
{
|
||||||
//usleep(sleepTime);
|
|
||||||
//if (sleepTime < 200000)
|
|
||||||
//{
|
|
||||||
//sleepTime+= 1000;
|
|
||||||
//}
|
|
||||||
pthread_cond_wait(&ftpData.clients[theSocketId].conditionVariable, &ftpData.clients[theSocketId].conditionMutex);
|
pthread_cond_wait(&ftpData.clients[theSocketId].conditionVariable, &ftpData.clients[theSocketId].conditionMutex);
|
||||||
}
|
}
|
||||||
pthread_mutex_unlock(&ftpData.clients[theSocketId].conditionMutex);
|
pthread_mutex_unlock(&ftpData.clients[theSocketId].conditionMutex);
|
||||||
|
|
||||||
//my_printf("\nWorker %d unlocked", theSocketId);
|
|
||||||
|
|
||||||
if (ftpData.clients[theSocketId].workerData.commandReceived == 1 &&
|
if (ftpData.clients[theSocketId].workerData.commandReceived == 1 &&
|
||||||
(compareStringCaseInsensitive(ftpData.clients[theSocketId].workerData.theCommandReceived, "STOR", strlen("STOR")) == 1 || compareStringCaseInsensitive(ftpData.clients[theSocketId].workerData.theCommandReceived, "APPE", strlen("APPE")) == 1) &&
|
(compareStringCaseInsensitive(ftpData.clients[theSocketId].workerData.theCommandReceived, "STOR", strlen("STOR")) == 1 || compareStringCaseInsensitive(ftpData.clients[theSocketId].workerData.theCommandReceived, "APPE", strlen("APPE")) == 1) &&
|
||||||
ftpData.clients[theSocketId].fileToStor.textLen > 0)
|
ftpData.clients[theSocketId].fileToStor.textLen > 0)
|
||||||
{
|
{
|
||||||
|
|
||||||
if ((checkParentDirectoryPermissions(ftpData.clients[theSocketId].fileToStor.text, ftpData.clients[theSocketId].login.ownerShip.uid, ftpData.clients[theSocketId].login.ownerShip.gid) & FILE_PERMISSION_W) != FILE_PERMISSION_W)
|
|
||||||
{
|
|
||||||
returnCode = socketPrintf(&ftpData, theSocketId, "s", "550 No permissions to write the file\r\n");
|
|
||||||
|
|
||||||
if (returnCode <= 0)
|
|
||||||
{
|
|
||||||
ftpData.clients[theSocketId].closeTheClient = 1;
|
|
||||||
my_printf("\n Closing the client 6");
|
|
||||||
pthread_exit(NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (compareStringCaseInsensitive(ftpData.clients[theSocketId].workerData.theCommandReceived, "APPE", strlen("APPE")) == 1)
|
if (compareStringCaseInsensitive(ftpData.clients[theSocketId].workerData.theCommandReceived, "APPE", strlen("APPE")) == 1)
|
||||||
{
|
{
|
||||||
#ifdef LARGE_FILE_SUPPORT_ENABLED
|
#ifdef LARGE_FILE_SUPPORT_ENABLED
|
||||||
@ -438,18 +417,6 @@ void *connectionWorkerHandle(void * socketId)
|
|||||||
else if (compareStringCaseInsensitive(ftpData.clients[theSocketId].workerData.theCommandReceived, "NLST", strlen("NLST")) == 1)
|
else if (compareStringCaseInsensitive(ftpData.clients[theSocketId].workerData.theCommandReceived, "NLST", strlen("NLST")) == 1)
|
||||||
theCommandType = COMMAND_TYPE_NLST;
|
theCommandType = COMMAND_TYPE_NLST;
|
||||||
|
|
||||||
if ((checkUserFilePermissions(ftpData.clients[theSocketId].listPath.text, ftpData.clients[theSocketId].login.ownerShip.uid, ftpData.clients[theSocketId].login.ownerShip.gid) & FILE_PERMISSION_R) != FILE_PERMISSION_R)
|
|
||||||
{
|
|
||||||
returnCode = socketPrintf(&ftpData, theSocketId, "s", "550 No permissions\r\n");
|
|
||||||
if (returnCode <= 0)
|
|
||||||
{
|
|
||||||
ftpData.clients[theSocketId].closeTheClient = 1;
|
|
||||||
my_printf("\n Closing the client 8");
|
|
||||||
pthread_exit(NULL);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
returnCode = socketPrintf(&ftpData, theSocketId, "s", "150 Accepted data connection\r\n");
|
returnCode = socketPrintf(&ftpData, theSocketId, "s", "150 Accepted data connection\r\n");
|
||||||
if (returnCode <= 0)
|
if (returnCode <= 0)
|
||||||
{
|
{
|
||||||
@ -458,7 +425,6 @@ void *connectionWorkerHandle(void * socketId)
|
|||||||
pthread_exit(NULL);
|
pthread_exit(NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
//returnCode = writeListDataInfoToSocket(ftpData.clients[theSocketId].listPath.text, ftpData.clients[theSocketId].workerData.socketConnection, &theFiles, theCommandType);
|
|
||||||
returnCode = writeListDataInfoToSocket(&ftpData, theSocketId, &theFiles, theCommandType, &ftpData.clients[theSocketId].workerData.memoryTable);
|
returnCode = writeListDataInfoToSocket(&ftpData, theSocketId, &theFiles, theCommandType, &ftpData.clients[theSocketId].workerData.memoryTable);
|
||||||
if (returnCode <= 0)
|
if (returnCode <= 0)
|
||||||
{
|
{
|
||||||
@ -489,19 +455,6 @@ void *connectionWorkerHandle(void * socketId)
|
|||||||
pthread_exit(NULL);
|
pthread_exit(NULL);
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((checkUserFilePermissions(ftpData.clients[theSocketId].fileToRetr.text, ftpData.clients[theSocketId].login.ownerShip.uid, ftpData.clients[theSocketId].login.ownerShip.gid) & FILE_PERMISSION_R) != FILE_PERMISSION_R)
|
|
||||||
{
|
|
||||||
writeReturn = socketPrintf(&ftpData, theSocketId, "s", "550 no reading permission on the file\r\n");
|
|
||||||
if (writeReturn <= 0)
|
|
||||||
{
|
|
||||||
ftpData.clients[theSocketId].closeTheClient = 1;
|
|
||||||
my_printf("\n Closing the client 12");
|
|
||||||
pthread_exit(NULL);
|
|
||||||
}
|
|
||||||
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
writenSize = writeRetrFile(&ftpData, theSocketId, ftpData.clients[theSocketId].workerData.retrRestartAtByte, ftpData.clients[theSocketId].workerData.theStorFile);
|
writenSize = writeRetrFile(&ftpData, theSocketId, ftpData.clients[theSocketId].workerData.retrRestartAtByte, ftpData.clients[theSocketId].workerData.theStorFile);
|
||||||
ftpData.clients[theSocketId].workerData.retrRestartAtByte = 0;
|
ftpData.clients[theSocketId].workerData.retrRestartAtByte = 0;
|
||||||
|
|
||||||
@ -985,6 +938,11 @@ static int processCommand(int processingElement)
|
|||||||
//my_printf("\nNOOP command received");
|
//my_printf("\nNOOP command received");
|
||||||
toReturn = parseCommandNoop(&ftpData, processingElement);
|
toReturn = parseCommandNoop(&ftpData, processingElement);
|
||||||
}
|
}
|
||||||
|
else if(compareStringCaseInsensitive(ftpData.clients[processingElement].theCommandReceived, "ACCT", strlen("ACCT")) == 1)
|
||||||
|
{
|
||||||
|
//my_printf("\nNOOP command received");
|
||||||
|
toReturn = parseCommandAcct(&ftpData, processingElement);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
; //Parse unsupported command not needed
|
; //Parse unsupported command not needed
|
||||||
|
@ -73,7 +73,7 @@ int isProcessAlreadyRunning(void)
|
|||||||
//my_printf("\nFILE_LockFile returnCode = %d", returnCode);
|
//my_printf("\nFILE_LockFile returnCode = %d", returnCode);
|
||||||
ftruncate(fd, 0);
|
ftruncate(fd, 0);
|
||||||
returnCode = snprintf(buf, 100, "%ld", (long)getpid());
|
returnCode = snprintf(buf, 100, "%ld", (long)getpid());
|
||||||
returnCode = write(fd, buf, strlen(buf)+1);
|
returnCode = write(fd, buf, strnlen(buf, 100)+1);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -202,10 +202,11 @@ int FILE_IsFile(const char *TheFileName)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
void FILE_GetDirectoryInodeList(char * DirectoryInodeName, char *** InodeList, int * FilesandFolders, int Recursive, DYNMEM_MemoryTable_DataType ** memoryTable)
|
void FILE_GetDirectoryInodeList(char * DirectoryInodeName, char *** InodeList, int * FilesandFolders, int Recursive, char * commandOps, DYNMEM_MemoryTable_DataType ** memoryTable)
|
||||||
{
|
{
|
||||||
int FileAndFolderIndex = *FilesandFolders;
|
int FileAndFolderIndex = *FilesandFolders;
|
||||||
my_printf("\nLIST DETAILS OF: %s", DirectoryInodeName);
|
my_printf("\nLIST DETAILS OF: %s", DirectoryInodeName);
|
||||||
|
my_printf("\ncommandOps: %s", commandOps);
|
||||||
|
|
||||||
//Allocate the array for the 1st time
|
//Allocate the array for the 1st time
|
||||||
if (*InodeList == NULL)
|
if (*InodeList == NULL)
|
||||||
@ -213,30 +214,30 @@ void FILE_GetDirectoryInodeList(char * DirectoryInodeName, char *** InodeList, i
|
|||||||
(*InodeList) = (char **) DYNMEM_malloc(sizeof(char *), memoryTable, "InodeList");
|
(*InodeList) = (char **) DYNMEM_malloc(sizeof(char *), memoryTable, "InodeList");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (FILE_IsDirectory(DirectoryInodeName))
|
if (FILE_IsDirectory(DirectoryInodeName))
|
||||||
{
|
{
|
||||||
|
|
||||||
|
|
||||||
DIR *TheDirectory;
|
DIR *TheDirectory;
|
||||||
struct dirent *dir;
|
struct dirent *dir;
|
||||||
TheDirectory = opendir(DirectoryInodeName);
|
TheDirectory = opendir(DirectoryInodeName);
|
||||||
if (TheDirectory)
|
if (TheDirectory)
|
||||||
{
|
{
|
||||||
|
|
||||||
|
|
||||||
while ((dir = readdir(TheDirectory)) != NULL)
|
while ((dir = readdir(TheDirectory)) != NULL)
|
||||||
{
|
{
|
||||||
if ( dir->d_name[0] == '.' && strlen(dir->d_name) == 1)
|
|
||||||
|
if ( dir->d_name[0] == '.' && strnlen(dir->d_name, 2) == 1)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if ( dir->d_name[0] == '.' && dir->d_name[1] == '.' && strlen(dir->d_name) == 2)
|
if ( dir->d_name[0] == '.' && dir->d_name[1] == '.' && strnlen(dir->d_name, 3) == 2)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
//Skips all files and dir starting with .
|
||||||
|
if ((dir->d_name[0] == '.' && commandOps == NULL) || (dir->d_name[0] == '.' && commandOps[0] != 'a' && commandOps[0] != 'A'))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
//Set the row to needed size
|
//Set the row to needed size
|
||||||
int ReallocSize = sizeof(char *) * (FileAndFolderIndex+1)+1;
|
int ReallocSize = sizeof(char *) * (FileAndFolderIndex+1)+1;
|
||||||
(*InodeList) = (char ** ) DYNMEM_realloc((*InodeList), ReallocSize, memoryTable);
|
(*InodeList) = (char ** ) DYNMEM_realloc((*InodeList), ReallocSize, memoryTable);
|
||||||
size_t nsize = strlen(dir->d_name) * sizeof(char) + strlen(DirectoryInodeName) * sizeof(char) + 2;
|
size_t nsize = strnlen(dir->d_name, 256) * sizeof(char) + strlen(DirectoryInodeName) * sizeof(char) + 2;
|
||||||
//Allocate the path string size
|
//Allocate the path string size
|
||||||
(*InodeList)[FileAndFolderIndex] = (char *) DYNMEM_malloc (nsize , memoryTable, "InodeList");
|
(*InodeList)[FileAndFolderIndex] = (char *) DYNMEM_malloc (nsize , memoryTable, "InodeList");
|
||||||
strcpy((*InodeList)[FileAndFolderIndex], DirectoryInodeName );
|
strcpy((*InodeList)[FileAndFolderIndex], DirectoryInodeName );
|
||||||
@ -248,7 +249,7 @@ void FILE_GetDirectoryInodeList(char * DirectoryInodeName, char *** InodeList, i
|
|||||||
|
|
||||||
if ( Recursive == 1 && FILE_IsDirectory((*InodeList)[*FilesandFolders-1]) == 1 )
|
if ( Recursive == 1 && FILE_IsDirectory((*InodeList)[*FilesandFolders-1]) == 1 )
|
||||||
{
|
{
|
||||||
FILE_GetDirectoryInodeList ( (*InodeList)[FileAndFolderIndex-1], InodeList, FilesandFolders, Recursive, memoryTable);
|
FILE_GetDirectoryInodeList ( (*InodeList)[FileAndFolderIndex-1], InodeList, FilesandFolders, Recursive, "Z", memoryTable);
|
||||||
FileAndFolderIndex = (*FilesandFolders);
|
FileAndFolderIndex = (*FilesandFolders);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -291,10 +292,10 @@ int FILE_GetDirectoryInodeCount(char * DirectoryInodeName)
|
|||||||
{
|
{
|
||||||
while ((dir = readdir(TheDirectory)) != NULL)
|
while ((dir = readdir(TheDirectory)) != NULL)
|
||||||
{
|
{
|
||||||
if ( dir->d_name[0] == '.' && strlen(dir->d_name) == 1)
|
if ( dir->d_name[0] == '.' && strnlen(dir->d_name, 2) == 1)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
if ( dir->d_name[0] == '.' && dir->d_name[1] == '.' && strlen(dir->d_name) == 2)
|
if ( dir->d_name[0] == '.' && dir->d_name[1] == '.' && strnlen(dir->d_name, 3) == 2)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
FileAndFolderIndex++;
|
FileAndFolderIndex++;
|
||||||
|
@ -60,7 +60,7 @@
|
|||||||
long long int FILE_GetFileSizeFromPath(char *TheFileName);
|
long long int FILE_GetFileSizeFromPath(char *TheFileName);
|
||||||
int FILE_IsFile(const char *theFileName);
|
int FILE_IsFile(const char *theFileName);
|
||||||
int FILE_IsDirectory (char *directory_path);
|
int FILE_IsDirectory (char *directory_path);
|
||||||
void FILE_GetDirectoryInodeList(char * DirectoryInodeName, char *** InodeList, int * filesandfolders, int recursive, DYNMEM_MemoryTable_DataType ** memoryTable);
|
void FILE_GetDirectoryInodeList(char * DirectoryInodeName, char *** InodeList, int * filesandfolders, int recursive, char* commandOps, DYNMEM_MemoryTable_DataType ** memoryTable);
|
||||||
int FILE_GetDirectoryInodeCount(char * DirectoryInodeName);
|
int FILE_GetDirectoryInodeCount(char * DirectoryInodeName);
|
||||||
int FILE_GetStringFromFile(char * filename, char **file_content, DYNMEM_MemoryTable_DataType ** memoryTable);
|
int FILE_GetStringFromFile(char * filename, char **file_content, DYNMEM_MemoryTable_DataType ** memoryTable);
|
||||||
void FILE_ReadStringParameters(char * filename, DYNV_VectorGenericDataType *ParametersVector);
|
void FILE_ReadStringParameters(char * filename, DYNV_VectorGenericDataType *ParametersVector);
|
||||||
|
@ -36,7 +36,6 @@ MAX_CONNECTION_TRY_PER_IP = 10
|
|||||||
#USE , instad of . eg: 192,168,1,1
|
#USE , instad of . eg: 192,168,1,1
|
||||||
#SERVER_IP = 192,168,1,1
|
#SERVER_IP = 192,168,1,1
|
||||||
|
|
||||||
|
|
||||||
#TLS CERTIFICATE FILE PATH
|
#TLS CERTIFICATE FILE PATH
|
||||||
CERTIFICATE_PATH=/etc/uFTP/cert.pem
|
CERTIFICATE_PATH=/etc/uFTP/cert.pem
|
||||||
PRIVATE_CERTIFICATE_PATH=/etc/uFTP/key.pem
|
PRIVATE_CERTIFICATE_PATH=/etc/uFTP/key.pem
|
||||||
|
Reference in New Issue
Block a user