Version 15.169.1

This commit is contained in:
Antonio Cañas Vargas 2016-03-31 10:11:36 +02:00
parent 04f30ff800
commit a4f4855de2
5 changed files with 103 additions and 107 deletions

View File

@ -138,13 +138,14 @@
/****************************** Public constants *****************************/ /****************************** Public constants *****************************/
/*****************************************************************************/ /*****************************************************************************/
#define Log_PLATFORM_VERSION "SWAD 15.169 (2016-03-31)" #define Log_PLATFORM_VERSION "SWAD 15.169.1 (2016-03-31)"
#define CSS_FILE "swad15.165.5.css" #define CSS_FILE "swad15.165.5.css"
#define JS_FILE "swad15.131.3.js" #define JS_FILE "swad15.131.3.js"
// Number of lines (includes comments but not blank lines) has been got with the following command: // Number of lines (includes comments but not blank lines) has been got with the following command:
// nl swad*.c swad*.h css/swad*.css py/swad*.py js/swad*.js soap/swad*.h sql/swad*.sql | tail -1 // nl swad*.c swad*.h css/swad*.css py/swad*.py js/swad*.js soap/swad*.h sql/swad*.sql | tail -1
/* /*
Version 15.169.1: Mar 31, 2016 Code refactoring in list of parameters. (197298 lines)
Version 15.169: Mar 31, 2016 When content is data, all parameters are retrieved in a list. (197306 lines) Version 15.169: Mar 31, 2016 When content is data, all parameters are retrieved in a list. (197306 lines)
Version 15.168.3: Mar 30, 2016 Code refactoring in list of parameters. (197124 lines) Version 15.168.3: Mar 30, 2016 Code refactoring in list of parameters. (197124 lines)
Version 15.168.2: Mar 30, 2016 Code refactoring in list of parameters. (197128 lines) Version 15.168.2: Mar 30, 2016 Code refactoring in list of parameters. (197128 lines)

View File

@ -108,6 +108,7 @@ struct Globals
Act_CONTENT_NORM (if CONTENT_TYPE==text/plain) or Act_CONTENT_NORM (if CONTENT_TYPE==text/plain) or
Act_CONTENT_DATA (if CONTENT_TYPE==multipart/form-data) */ Act_CONTENT_DATA (if CONTENT_TYPE==multipart/form-data) */
char DelimiterString[1000]; char DelimiterString[1000];
size_t LengthDelimiterString;
char DelimiterStringIncludingInitialRet[2+1000]; char DelimiterStringIncludingInitialRet[2+1000];
struct soap *soap; // gSOAP runtime environment struct soap *soap; // gSOAP runtime environment

View File

@ -62,6 +62,7 @@ extern struct Globals Gbl;
static void Par_CreateListOfParams (void); static void Par_CreateListOfParams (void);
static void Par_CreateListOfParamsFromQueryString (void); static void Par_CreateListOfParamsFromQueryString (void);
static void Par_CreateListOfParamsFromTmpFile (void); static void Par_CreateListOfParamsFromTmpFile (void);
static bool Par_ReadTmpFileUntilDelimitStr (void);
static int Par_ReadTmpFileUntilQuote (void); static int Par_ReadTmpFileUntilQuote (void);
static int Par_ReadTmpFileUntilReturn (void); static int Par_ReadTmpFileUntilReturn (void);
@ -125,8 +126,15 @@ bool Par_GetQueryString (void)
"\r\n-----------------------------7d13ca2e948" "\r\n-----------------------------7d13ca2e948"
I.e. 0x0D, 0x0A, '-', '-', and boundary. I.e. 0x0D, 0x0A, '-', '-', and boundary.
*/ */
sprintf (Gbl.DelimiterString,"--%s",strstr (getenv ("CONTENT_TYPE"),"boundary=") + strlen ("boundary=")); sprintf (Gbl.DelimiterString,"--%s",
strstr (getenv ("CONTENT_TYPE"),"boundary=") + strlen ("boundary="));
Gbl.LengthDelimiterString = strlen (Gbl.DelimiterString);
if (Gbl.LengthDelimiterString == 0 ||
Gbl.LengthDelimiterString > Par_MAX_LENGTH_STR_DELIMIT)
Lay_ShowErrorAndExit ("Wrong delimiter string.");
sprintf (Gbl.DelimiterStringIncludingInitialRet,"%c%c%s",0x0D,0x0A,Gbl.DelimiterString); sprintf (Gbl.DelimiterStringIncludingInitialRet,"%c%c%s",0x0D,0x0A,Gbl.DelimiterString);
return Fil_ReadStdinIntoTmpFile (); return Fil_ReadStdinIntoTmpFile ();
} }
else if (!strncmp (ContentType,"text/xml",strlen ("text/xml"))) else if (!strncmp (ContentType,"text/xml",strlen ("text/xml")))
@ -151,11 +159,12 @@ bool Par_GetQueryString (void)
} }
} }
if (Gbl.ContentReceivedByCGI == Act_CONTENT_NORM) /***** Create list of parameters *****/
Par_CreateListOfParams (); Par_CreateListOfParams ();
return true; return true;
} }
/*****************************************************************************/ /*****************************************************************************/
/************************ Create list of parameters **************************/ /************************ Create list of parameters **************************/
/*****************************************************************************/ /*****************************************************************************/
@ -184,15 +193,20 @@ List --> |Name.Start | -> |Name.Start |
static void Par_CreateListOfParams (void) static void Par_CreateListOfParams (void)
{ {
switch (Gbl.ContentReceivedByCGI) /***** Initialize empty list of parameters *****/
{ Gbl.Params.List = NULL;
case Act_CONTENT_NORM:
Par_CreateListOfParamsFromQueryString (); /***** Get list *****/
break; if (Gbl.Params.ContentLength)
case Act_CONTENT_DATA: switch (Gbl.ContentReceivedByCGI)
Par_CreateListOfParamsFromTmpFile (); {
break; case Act_CONTENT_NORM:
} Par_CreateListOfParamsFromQueryString ();
break;
case Act_CONTENT_DATA:
Par_CreateListOfParamsFromTmpFile ();
break;
}
} }
/*****************************************************************************/ /*****************************************************************************/
@ -206,13 +220,8 @@ static void Par_CreateListOfParamsFromQueryString (void)
struct Param *NewParam; struct Param *NewParam;
/***** Check if query string is empty *****/ /***** Check if query string is empty *****/
Gbl.Params.List = NULL; if (!Gbl.Params.QueryString) return;
if (!Gbl.Params.ContentLength) if (!Gbl.Params.QueryString[0]) return;
return;
if (Gbl.Params.QueryString == NULL)
return;
if (!Gbl.Params.QueryString[0])
return;
/***** Go over the query string /***** Go over the query string
getting start positions and lengths of parameters *****/ getting start positions and lengths of parameters *****/
@ -262,41 +271,31 @@ static void Par_CreateListOfParamsFromQueryString (void)
// TODO: Rename Gbl.F.Tmp to Gbl.F.In (InFile, QueryFile)? // TODO: Rename Gbl.F.Tmp to Gbl.F.In (InFile, QueryFile)?
#define Par_MAX_BYTES_STR_AUX 1024 #define Par_MAX_BYTES_STR_AUX 1024
#define Par_LENGTH_OF_STR_BEFORE_PARAM 38 // Length of "Content-Disposition: form-data; name=\""
#define Par_LENGTH_OF_STR_FILENAME 12 // Length of "; filename=\""
#define Par_LENGTH_OF_STR_CONTENT_TYPE 14 // Length of "Content-Type: "
static void Par_CreateListOfParamsFromTmpFile (void) static void Par_CreateListOfParamsFromTmpFile (void)
{ {
static const char *StringBeforeParam = "Content-Disposition: form-data; name=\""; static const char *StringBeforeParam = "Content-Disposition: form-data; name=\"";
#define Par_LENGTH_OF_STR_BEFORE_PARAM 38 // Length of "Content-Disposition: form-data; name=\""
static const char *StringFilename = "; filename=\""; static const char *StringFilename = "; filename=\"";
#define Par_LENGTH_OF_STR_FILENAME 12 // Length of "; filename=\""
static const char *StringContentType = "Content-Type: "; static const char *StringContentType = "Content-Type: ";
#define Par_LENGTH_OF_STR_CONTENT_TYPE 14 // Length of "Content-Type: " unsigned long CurPos; // Current position in temporal file
unsigned long CurPos; // Current position in query string
struct Param *Param; struct Param *Param;
struct Param *NewParam; struct Param *NewParam;
int Result;
int Ch; int Ch;
char StrAux[Par_MAX_BYTES_STR_AUX+1]; char StrAux[Par_MAX_BYTES_STR_AUX+1];
/***** Check if file is empty *****/
Gbl.Params.List = NULL;
if (!Gbl.Params.ContentLength)
return;
/***** Go over the file /***** Go over the file
getting start positions and lengths of parameters *****/ getting start positions and lengths of parameters *****/
Result = Str_SkipFileUntilDelimitStr (Gbl.F.Tmp,Gbl.DelimiterString); if (Par_ReadTmpFileUntilDelimitStr ()) // Delimiter string found
if (Result == 1) // Delimiter string found
for (CurPos = 0; for (CurPos = 0;
CurPos < Gbl.Params.ContentLength; CurPos < Gbl.Params.ContentLength;
) )
{ {
/***** Skip \r\n after delimiter string *****/ /***** Skip \r\n after delimiter string *****/
if (fgetc (Gbl.F.Tmp) != 0x0D) // '\r' if (fgetc (Gbl.F.Tmp) != 0x0D) break; // '\r'
break; if (fgetc (Gbl.F.Tmp) != 0x0A) break; // '\n'
if (fgetc (Gbl.F.Tmp) != 0x0A) // '\n'
break;
Str_GetNextStrFromFileConvertingToLower (Gbl.F.Tmp,StrAux, Str_GetNextStrFromFileConvertingToLower (Gbl.F.Tmp,StrAux,
Par_LENGTH_OF_STR_BEFORE_PARAM); Par_LENGTH_OF_STR_BEFORE_PARAM);
@ -323,8 +322,7 @@ static void Par_CreateListOfParamsFromTmpFile (void)
Param->Name.Length = CurPos - Param->Name.Start; Param->Name.Length = CurPos - Param->Name.Start;
/* Check if last character read after parameter name is a quote */ /* Check if last character read after parameter name is a quote */
if (Ch != (int) '\"') if (Ch != (int) '\"') break; // '\"'
break;
/* Get next char after parameter name */ /* Get next char after parameter name */
Ch = fgetc (Gbl.F.Tmp); Ch = fgetc (Gbl.F.Tmp);
@ -344,14 +342,11 @@ static void Par_CreateListOfParamsFromTmpFile (void)
Param->Filename.Length = CurPos - Param->Filename.Start; Param->Filename.Length = CurPos - Param->Filename.Start;
/* Check if last character read after filename is a quote */ /* Check if last character read after filename is a quote */
if (Ch != (int) '\"') if (Ch != (int) '\"') break; // '\"'
break;
/* Skip \r\n */ /* Skip \r\n */
if (fgetc (Gbl.F.Tmp) != 0x0D) // '\r' if (fgetc (Gbl.F.Tmp) != 0x0D) break; // '\r'
break; if (fgetc (Gbl.F.Tmp) != 0x0A) break; // '\n'
if (fgetc (Gbl.F.Tmp) != 0x0A) // '\n'
break;
/* Check if Content-Type is present */ /* Check if Content-Type is present */
Str_GetNextStrFromFileConvertingToLower (Gbl.F.Tmp,StrAux, Str_GetNextStrFromFileConvertingToLower (Gbl.F.Tmp,StrAux,
@ -370,31 +365,76 @@ static void Par_CreateListOfParamsFromTmpFile (void)
/***** Now \r\n\r\n is expected just before parameter value or file content *****/ /***** Now \r\n\r\n is expected just before parameter value or file content *****/
/* Check if last character read is '\r' */ /* Check if last character read is '\r' */
if (Ch != 0x0D) if (Ch != 0x0D) break; // '\r'
break;
/* Skip \n\r\n */ /* Skip \n\r\n */
if (fgetc (Gbl.F.Tmp) != 0x0A) // '\n' if (fgetc (Gbl.F.Tmp) != 0x0A) break; // '\n'
break; if (fgetc (Gbl.F.Tmp) != 0x0D) break; // '\r'
if (fgetc (Gbl.F.Tmp) != 0x0D) // '\r' if (fgetc (Gbl.F.Tmp) != 0x0A) break; // '\n'
break;
if (fgetc (Gbl.F.Tmp) != 0x0A) // '\n'
break;
/***** Get parameter value or file content *****/ /***** Get parameter value or file content *****/
CurPos = (unsigned long) ftell (Gbl.F.Tmp); CurPos = (unsigned long) ftell (Gbl.F.Tmp);
Result = Str_SkipFileUntilDelimitStr (Gbl.F.Tmp,Gbl.DelimiterString); if (!Par_ReadTmpFileUntilDelimitStr ()) break; // Delimiter string not found
if (Result != 1) // Delimiter string not found
break;
// Delimiter string found // Delimiter string found
Param->Value.Start = CurPos; Param->Value.Start = CurPos;
CurPos = (unsigned long) ftell (Gbl.F.Tmp); CurPos = (unsigned long) ftell (Gbl.F.Tmp); // Just after delimiter string
Param->Value.Length = CurPos - Param->Filename.Start; Param->Value.Length = CurPos - Gbl.LengthDelimiterString -
Param->Filename.Start;
} }
} }
} }
/*****************************************************************************/
/******************** Read from file until quote '\"' ************************/
/*****************************************************************************/
// Return true if delimiter string is found.
// File is positioned just after the last character in delimiter string
static bool Par_ReadTmpFileUntilDelimitStr (void)
{
unsigned NumBytesIdentical; // Number of characters identical in each iteration of the loop
unsigned NumBytesReadButNoWritten = 0; // Number of characters read from the source file
// and not written in the destination file
int Buffer[Par_MAX_LENGTH_STR_DELIMIT+1];
unsigned StartIndex = 0;
unsigned i;
for (;;)
{
if (!NumBytesReadButNoWritten)
{ // Read next character
Buffer[StartIndex] = fgetc (Gbl.F.Tmp);
if (feof (Gbl.F.Tmp))
return false;
NumBytesReadButNoWritten++;
}
if (Buffer[StartIndex] == (int) Gbl.DelimiterString[0]) // First character identical
{
for (NumBytesIdentical = 1, i = (StartIndex + 1) % Gbl.LengthDelimiterString;
NumBytesIdentical < Gbl.LengthDelimiterString;
NumBytesIdentical++, i = (i + 1) % Gbl.LengthDelimiterString)
{
if (NumBytesReadButNoWritten == NumBytesIdentical) // Next character identical
{
Buffer[i] = fgetc (Gbl.F.Tmp); // Read next character
if (feof (Gbl.F.Tmp))
return false;
NumBytesReadButNoWritten++;
}
if (Buffer[i] != (int) Gbl.DelimiterString[NumBytesIdentical]) // Next different character
break;
}
if (NumBytesIdentical == Gbl.LengthDelimiterString) // Str found
return true;
}
NumBytesReadButNoWritten--;
StartIndex = (StartIndex + 1) % Gbl.LengthDelimiterString;
}
return false; // Not reached
}
/*****************************************************************************/ /*****************************************************************************/
/******************** Read from file until quote '\"' ************************/ /******************** Read from file until quote '\"' ************************/
/*****************************************************************************/ /*****************************************************************************/

View File

@ -34,6 +34,8 @@
/************************** Public types and constants ***********************/ /************************** Public types and constants ***********************/
/*****************************************************************************/ /*****************************************************************************/
#define Par_MAX_LENGTH_STR_DELIMIT 100
struct StartLength struct StartLength
{ {
unsigned long Start; unsigned long Start;

View File

@ -2502,6 +2502,7 @@ If StrDelimit is not found, return -1.
*/ */
#define MAX_LENGTH_STR_DELIMIT 100 #define MAX_LENGTH_STR_DELIMIT 100
int Str_ReceiveFileUntilDelimitStr (FILE *FileSrc, FILE *FileTgt, char *StrDst, const char *StrDelimit, unsigned long long MaxLength) int Str_ReceiveFileUntilDelimitStr (FILE *FileSrc, FILE *FileTgt, char *StrDst, const char *StrDelimit, unsigned long long MaxLength)
{ {
int NumBytesIdentical, // Number of characters identical in each iteration of the loop int NumBytesIdentical, // Number of characters identical in each iteration of the loop
@ -2581,55 +2582,6 @@ int Str_ReceiveFileUntilDelimitStr (FILE *FileSrc, FILE *FileTgt, char *StrDst,
return 0; // Not reached return 0; // Not reached
} }
int Str_SkipFileUntilDelimitStr (FILE *FileSrc, const char *StrDelimit)
{
int NumBytesIdentical; // Number of characters identical in each iteration of the loop
int NumBytesReadButNoWritten = 0; // Number of characters read from the source file
// and not written in the destination file
int LengthStrDelimit = strlen (StrDelimit);
int Buffer[MAX_LENGTH_STR_DELIMIT+1];
int StartIndex = 0;
int i;
if (LengthStrDelimit == 0 ||
LengthStrDelimit > MAX_LENGTH_STR_DELIMIT)
Lay_ShowErrorAndExit ("Wrong delimiter string.");
for (;;)
{
if (!NumBytesReadButNoWritten)
{ // Read next character
Buffer[StartIndex] = fgetc (FileSrc);
if (feof (FileSrc))
return -1;
NumBytesReadButNoWritten++;
}
if (Buffer[StartIndex] == (int) StrDelimit[0]) // First character identical
{
for (NumBytesIdentical = 1, i = (StartIndex + 1) % LengthStrDelimit;
NumBytesIdentical < LengthStrDelimit;
NumBytesIdentical++, i = (i + 1) % LengthStrDelimit)
{
if (NumBytesReadButNoWritten == NumBytesIdentical) // Next character identical
{
Buffer[i] = fgetc (FileSrc); // Read next character
if (feof (FileSrc))
return -1;
NumBytesReadButNoWritten++;
}
if (Buffer[i] != (int) StrDelimit[NumBytesIdentical]) // Next different character
break;
}
if (NumBytesIdentical == LengthStrDelimit) // Str found
return 1;
}
NumBytesReadButNoWritten--;
StartIndex = (StartIndex+1) % LengthStrDelimit;
}
return 0; // Not reached
}
/*****************************************************************************/ /*****************************************************************************/
/****** Convert invalid characters in a file name to valid characters ********/ /****** Convert invalid characters in a file name to valid characters ********/
/*****************************************************************************/ /*****************************************************************************/