コード例 #1
0
/* should return an index or handle to list of included files */
int findFileInDir(char *dir, char *name)
{
  char * buf, *p1, *p2, *peon;
  char *suffix=option_isuffix;
  unsigned int buflen;


  debugParserpp("include findFileInDir: dir %s, name %s, suffix %s\n",dir,name,suffix);
  
  buflen=strlen(dir)+strlen(name)+5;
  if(suffix!=NULL) buflen+=strlen(suffix);
  buf=malloc(buflen);
  
  for(p1=buf,p2=dir;*p2;p2++) *p1++=*p2;
  
  /* check if last copied char is '/', and if not then addit */
  

  if(*(p1-1)!='/') *p1++='/'; 
  *p1='\0';
  
  for(p2=name;*p2;p2++)  *p1++=*p2;
  *p1='\0';
  
  /* TODO: how should the search be done ? */  
  /* if suffix is specified, then always use the suffix */
  
  peon=p1; /* pointer to end of name without suffix */
  
  if(suffix!=NULL)
  {
  for(p2=suffix;*p2;p2++)  *p1++=*p2;
  *p1='\0';
  
  debugVerbose("include: looking for file with suffix %s\n",suffix);
  if(fileExists(buf)) goto out_found;
  }
  
  /* look for file without suffix */
  *peon='\0'; /* terminate string in buf */
  debugVerbose("include: looking for without suffix:%s\n",name);
  
  if(fileExists(buf)) goto out_found;
  
    
    /* file not found */
	free(buf);
	return 0;

out_found:;
   /* free(buf); dont free just pass buf */
   scannerContext->ppreturn->type=LIT_INCLUDE_FILE_NAME;
   scannerContext->ppreturn->string=buf;
  return 1;
}
コード例 #2
0
ファイル: filehandling.c プロジェクト: gnux/tiniweb
ssize_t pollAndRead(int fd, int timeout, char* cp_buffer, ssize_t num)
{
    struct pollfd poll_fd;
    ssize_t i = 0;
    ssize_t in_size = 0;
    int i_poll_result = 0;
    poll_fd.fd = fd;
    poll_fd.events = POLLIN;
    poll_fd.revents = 0;
    
    // Poll for every byte
    for(i=0; i<num; ++i)
    {
        i_poll_result = poll(&poll_fd, 1, timeout);
        if (i_poll_result == -1) 
        {
            debugVerbose(FILEHANDLING, "I/O error during poll.\n");
            secAbort();
        } else if (i_poll_result == 0) 
        {
            debugVerbose(FILEHANDLING, "poll timed out\n");
            return EXIT_FAILURE;
        }
        // Evaluate poll
        if((poll_fd.revents & ~POLLIN && !(poll_fd.revents & POLLIN)))
            break;    
        if(!(poll_fd.revents & POLLIN))
            break;
        
        // Read 1 Byte
        in_size= read(fd, &cp_buffer[i], 1);
        if (in_size < 0)
        {
            debugVerbose(FILEHANDLING, "I/O error on inbound file.\n");
            secAbort();
        }
        else if (in_size == 0) 
        {
            break;
        }
    }
    return i;
}
コード例 #3
0
int findFileInDirList(char *dirList, char *name)
{
	char * buf=malloc(512);
	char * p1,*p2;
	int isOK;
	if (!buf) error("Internal compiler error: out of mem");
  debugParserpp("include findFileInDirList: dirlist %s, name %s\n",dirList,name);
	
	debugVerbose("include: Looking for file %s in directory list %s\n",name,dirList);
	/* the separator is either ':' or ';' */
	for(isOK=0,p1=buf,p2=dirList;*p2;p2++)
	{
		if(*p2==':' || *p2==';')
		{ // TODO also check last dir list ! *(p2+1)=='\0'
			*p1++='\0';
		    debugParserpp("include findFileInDirList: buf %s, name %s\n",buf,name);
			isOK=findFileInDir(buf,name);
			if(isOK) goto out_found;
			
			*buf='\0';
			p1=buf;
		}
		else
		{ /* TODO: check length of buf, and if >512 allocate larger */
			*p1++=*p2;
		}
	}
	
	goto out_not_found;
	
 out_found: ;
  debugVerbose("include: found the file %s in path %s\n",name,buf);
  free(buf);
  return 1;

out_not_found:;
  free(buf);
  return 0;
  
}
コード例 #4
0
/** 
 * 
 * return 0 File not found
 *        1 File found
 * 
 * if the file is found the return area is set as follows:
 *    scannerContext->ppreturn->type=LIT_INCLUDE_FILE_NAME;
 *    scannerContext->ppreturn->string=<name of file>;;
 * 
 * 
 * 
 * 
 */
int findFile(char *name)
{
  char defaultSearchDirs[]= "./:./include";

  option_i=scannerContext->ppp->includePath;
  option_isuffix=scannerContext->ppp->includeSuffix;
  
  char *pathToUse;
  
  int isOK=0;
  
  if (!isOK&&option_i!=NULL) 
  { /* if option -I is specified, look there */
  	debugVerbose("include: looking in compiler option -I%s\n",option_i);
  	isOK=findFileInDirList(option_i,name);
  }

  if(!isOK)
  { /* look in default directories */
  	debugVerbose("include: looking in default search dirs: %s\n",defaultSearchDirs);
  	isOK=findFileInDirList(defaultSearchDirs,name);
  }

  if(!isOK)
  { /* look in directory list PL1SYSLIB */
  	pathToUse = getenv("PL1SYSLIB");
  	if(pathToUse) 
  	{
  	debugVerbose("include: looking in environment variable PL1SYSLIB: %s\n",pathToUse);
  	isOK=findFileInDirList(pathToUse,name);
  	}
  	else
  	isOK=0; 
  }

  return isOK;
}
コード例 #5
0
int fileExists(char *fullname)
{
 debugVerbose("include: Checking existence of file %s\n",fullname);  

  FILE *input = fopen(fullname, "r");

  if(input==NULL) {
  	if(errno!=ENOENT)
  	{ /* only show detailed message if different from not found. */
    perror(fullname);
    debugParserpp("include: Could not open file %s, errno %i ...\n",fullname,errno);
  	}
    return 0;
  }
  
  fclose(input);

  return 1;
}
コード例 #6
0
int findEnvFile(char *env, char *name)
{ char *pathToUse;
  
  int isOK=0;
	
  if(!isOK)
  { /* look in directory list contained in environment variable */
  	pathToUse = getenv(env);
  	debugVerbose("include: looking in environment variable %s: %s\n",env,pathToUse);
  	isOK=findFileInDirList(pathToUse,name);
  }

  /* TODO: should the default search be performed if search in env fails ? */
  /* if(!isOK) 
   *   isOK=findFile(name); 
   */
	
  return isOK;
}
コード例 #7
0
ファイル: Preferences.cpp プロジェクト: ecashin/aoe-osx
int AoEPreferences::SetSettingsInKEXT(void)
{
	int nRet;
	
	nRet = m_pInterface->connect_to_driver();
	if ( nRet )
	{
		debugVerbose("Unable to connect to driver\n");
		return nRet;
	}

	nRet = m_pInterface->set_preference_settings(&m_PreferenceData);
	if ( nRet )
	{
		debugError("Unable to set settings in driver\n");
		return nRet;
	}
	
	m_pInterface->disconnect();
	return 0;
}
コード例 #8
0
ファイル: staticfile.c プロジェクト: gnux/tiniweb
void processStaticFile(const char* ccp_path)
{
    FILE* file = NULL;
    int i_fd = -1;
    struct stat stat_buffer;
    char* cp_content_type = NULL;
    int i_content_length = 0;
    int i_success = 0;
    
    if(ccp_path == NULL)
    {
        debugVerbose(STATIC_FILE, "Error, no file path specified.\n");
        secExit(STATUS_INTERNAL_SERVER_ERROR);
    }
    
    if(lstat(ccp_path, &stat_buffer) < 0)
    {
        debugVerbose(STATIC_FILE, "Opening file %s failed: %d\n", ccp_path, errno);
        secExit(STATUS_INTERNAL_SERVER_ERROR);
    }
    
    i_content_length = stat_buffer.st_size;
    
    file = fopen(ccp_path, "r");
        
    if(file == NULL)
    {
        debugVerbose(STATIC_FILE, "Opening file %s failed: %d\n", ccp_path, errno);
        secExit(STATUS_INTERNAL_SERVER_ERROR);
    }
    
    i_fd = fileno(file);
    if(i_fd < 0)
    {
        debugVerbose(STATIC_FILE, "Retreiving a file descriptor from file pointer failed.\n");
        secExit(STATUS_INTERNAL_SERVER_ERROR);
    }
    
    cp_content_type = parseExtension(ccp_path);


    i_success = sendHTTPResponseHeaderExplicit("200 OK", cp_content_type, i_content_length);
    
    if(i_success == EXIT_FAILURE)
    {
        debugVerbose(STATIC_FILE, "Sending header failed.\n");
        secExit(STATUS_CANCEL);
    }
    
    debugVerbose(STATIC_FILE, "Sent HTTP response header to client.\n");
    
    if(e_used_method != HEAD)
    { 
        i_success = writeFileTo(i_fd, STDOUT_FILENO);
        
        if(i_success == EXIT_FAILURE)
        {
            debugVerbose(STATIC_FILE, "Sending file failed.\n");
            fclose(file);
            secExit(STATUS_CANCEL);
        }
        
        debugVerbose(STATIC_FILE, "Sent file to client.\n");
    }
    
    if(fclose(file) != 0)
    {
        //Everything is finished, here, no need to do something special
        debugVerbose(STATIC_FILE, "Could not close file.\n");
    }
      
}
コード例 #9
0
ファイル: tiniweb.c プロジェクト: gnux/tiniweb
/** tiniweb main routine
* @param argc number of commandline arguments
* @param argv arguments itself
* @return tiniweb return value
*/
int main(int argc, char** argv) {
    
    int c = 0;
    int i_option_index = 0;
    bool b_static = FALSE;
    char* cp_mapped_path = NULL;
    char* cp_path_to_htdigest_file = NULL;
    char* cp_search_path_root = NULL;
    bool b_digest_file_available = FALSE;
    bool b_authenticated = FALSE;
    
    
    // command line parsing: like done in example from
    // http://www.gnu.org/s/libc/manual/html_node/Getopt-Long-Option-Example.html
    while (1) {
        
        static struct option long_options[] = {
            { "web-dir", required_argument, 0, 0 },
            { "cgi-dir", required_argument, 0, 1 },
            { "cgi-timeout", required_argument, 0, 2 },
            { "secret", required_argument, 0, 3},
            { "verbose", no_argument, 0, 4 },
            { 0, 0, 0, 0 }
        };
            i_option_index = 0;
            c = getopt_long(argc, argv, "", long_options, &i_option_index);
            
            if (c == -1)
                break;
            
            switch (c) {
                case 0:
                    scp_web_dir_ = secPrint2String("%s", optarg);
                    debugVerbose(MAIN, "option web-dir used with argument: %s \n", scp_web_dir_);
                    break;
                case 1:
                    scp_cgi_dir_ = secPrint2String("%s",optarg);
                    debugVerbose(MAIN, "option cgi-dir used with argument: %s \n", scp_cgi_dir_);
                    break;
                case 2:
                    debugVerbose(MAIN, "option cgi-timeout used with argument: %s \n",
                    optarg);
                    si_cgi_timeout_ = (int) strtol(optarg, NULL, 10);
                    si_cgi_timeout_ *= 1000;
                    break;
                case 3:
                    scp_secret_ = secPrint2String("%s", optarg);
                    debugVerbose(MAIN, "option secret used with argument: %s \n", scp_secret_);
                    break;
                case 4:
                    b_flag_verbose_ = TRUE;
                    debugVerbose(MAIN, "switching to verbose mode \n");
                    break;
                default:
                    debug(MAIN, "encountert unknown argument \n");
                    secExit(STATUS_CANCEL);
                    break;
            }
    }
    
    if(!scp_cgi_dir_ || !scp_web_dir_ || !scp_secret_){
        debug(MAIN, "Mandatory parameter missing\n");
        debug(MAIN, "usage: ./tiniweb (--verbose) --web-dir <path> --cgi-dir <path> --secret <secret> (--cgi-timeout <msec>)\n");
        secExit(STATUS_CANCEL);
    }
    if (performPathChecking(&scp_cgi_dir_, &scp_web_dir_) == FALSE)
    {
        debug(MAIN, "ERROR, Paths not valid!\n");
        secExit(STATUS_CANCEL);
    }
    
    if(si_cgi_timeout_ < CGI_TIME_OUT_MIN)
    {
        debug(MAIN, "cgi-timeout is too short, using default value (%d)\n", CGI_TIME_OUT_MIN);
        si_cgi_timeout_ = CGI_TIME_OUT_MIN;
    }
    else if(si_cgi_timeout_ > CGI_TIME_OUT_MAX)
    {
        debug(MAIN, "cgi-timeout is too long, using default value (%d)\n", CGI_TIME_OUT_MAX);
        si_cgi_timeout_ = CGI_TIME_OUT_MAX;
    }
    
    
    
    debug(MAIN, "Argument parsing finished\n");
    debugVerbose(MAIN, "WEB_DIR = %s \n", scp_web_dir_);
    debugVerbose(MAIN, "CGI_DIR = %s \n", scp_cgi_dir_);
    debugVerbose(MAIN, "SECRET = %s \n", scp_secret_);
    debugVerbose(MAIN, "CGI_TIMEOUT = %d \n", si_cgi_timeout_);
    
    
    debugVerbose(MAIN, "Switching stdin to non_blocking mode\n");
    if(setNonblocking(STDIN_FILENO))
    {
        debug(MAIN, "Switching stdin to non_blocking mode failed!\n");
        secAbort();
    }
    
    char* cp_header = retrieveHeader(STDIN_FILENO, STDIN_TIMEOUT);
    if(cp_header == NULL)
    {
        debug(MAIN,"STDIN has to talk to use! We don't like DoS\n");
        secExit(STATUS_CANCEL);
    }
    
    http_norm *hnp_info = normalizeHttp(cp_header, FALSE);
    
    
    debugVerbose(MAIN, "Normalize finished \n");
    parse(hnp_info);
    debugVerbose(MAIN, "Parsing finished \n"); 
    
    
    if (mapRequestPath(&cp_mapped_path, &b_static) == FALSE)
    {
        secExit(STATUS_NOT_FOUND);
    }
    
    if (checkRequestPath(cp_mapped_path) == FALSE)
    {
        secExit(STATUS_NOT_FOUND);
    }
    
    cp_search_path_root = b_static ? scp_web_dir_ : scp_cgi_dir_;
    
    if (searchForHTDigestFile(cp_mapped_path, cp_search_path_root, &b_digest_file_available, 
        &cp_path_to_htdigest_file) == EXIT_FAILURE)
    {
        
        //  We found two .htdigest Files in the path! File is protected!
        secExit(STATUS_FORBIDDEN);
    }
    
    if (b_digest_file_available)
    {
        b_authenticated = authenticate(cp_path_to_htdigest_file);
    }
    
    
    if(b_authenticated == TRUE || b_digest_file_available == FALSE)
    {
        if(b_static == TRUE)
        {
            processStaticFile(cp_mapped_path);
        }
        else
        {
            setupEnvVarList(scp_web_dir_, cp_mapped_path, hnp_info, b_authenticated);
            processCGIScript(cp_mapped_path);
        }
    }
    
    secExit(STATUS_OK);
    return EXIT_SUCCESS;
}
コード例 #10
0
ファイル: filehandling.c プロジェクト: gnux/tiniweb
char* retrieveHeader(int fd, int timeout)
{
    char* cp_header = NULL;
    ssize_t i = 0;
    ssize_t in_size = 0;
    bool b_gotnl = FALSE;
    bool b_gotcr = FALSE;
    
    // first of all allocated our big buffer
    cp_header = secCalloc(MAX_HEADER_SIZE + 1, sizeof(char));
    
    for(i=0; i<MAX_HEADER_SIZE; ++i)
    {
        in_size = pollAndRead(fd, timeout, &cp_header[i], 1);
        // Error from file is never good
        if(in_size == EXIT_FAILURE)
        {
            debugVerbose(FILEHANDLING, "Got problems with our fds\n");
            secFree(cp_header);
            return NULL;
        }
        // Header has to end with \n\n
        if(in_size == 0)
        {
            debugVerbose(NORMALISE, "Invalid Header delimiter detected\n");
            secExit(STATUS_BAD_REQUEST);
        }
        // register a \r
        if(cp_header[i] == '\r')
        {
            b_gotcr = TRUE;
            continue;
        }
        // special things to do on \n
        if(cp_header[i] == '\n')
        {
            // replace previous \r by \n
            if(b_gotcr == TRUE)
            {
                cp_header[i-1] = '\n';
                cp_header[i] = '\0';
                --i;
                b_gotcr = FALSE;
            }
            // break up if we had found a previous \n, thats the only right way to get out here
            if(b_gotnl == TRUE)
            {
                ++i;
                break;
            }
            b_gotnl = TRUE;
            continue;
        }
        // if we found a non character or a single \r we will break
        if(isValid(cp_header, i) == EXIT_FAILURE || b_gotcr == TRUE)
        {
            debugVerbose(FILEHANDLING, "Detected invalid char while retrieving header\n");
            secExit(STATUS_BAD_REQUEST);
        }
        b_gotnl = FALSE;
        b_gotcr = FALSE;
    }
    
    // Header is too large
    if(i == MAX_HEADER_SIZE)
    {
        debug(FILEHANDLING, "Too long header! We don't like to get overflowed, bye bye\n");
        secExit(STATUS_BAD_REQUEST);
    }
    
    cp_header[i] = '\0';
    return secRealloc(cp_header, (i + 1) * sizeof(char));
}