
/******************************************************************************
**
**  Copyright (C) 2001  - the shmoo group -
**
**  This program is free software; you can redistribute it and/or
**  modify it, however, you cannot sell it.
**
**  This program is distributed in the hope that it will be useful,
**  but WITHOUT ANY WARRANTY; without even the implied warranty of
**  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
**
**  You should have received a copy of the license attached to the
**  use of this software.  If not, visit www.shmoo.com/osiris for
**  details.
**
******************************************************************************/

/******************************************************************************
**
**    The Shmoo Group (TSG)
**
**    File:      configuration.h
**    Author:    Brian Wotring
**
**    Date:      June 22, 2001.
**    Project:   osiris
**
******************************************************************************/

#ifndef CONFIGURATION_H
#define CONFIGURATION_H


/* config file constants. */

#define CONFIG_MAX_ERRORS         5
#define MAX_LINE_LENGTH           1000
#define MAX_CONFIG_NAME_LENGTH    255
#define MAX_CONFIG_ID_LENGTH	  10

/* hash types. */

#define HASH_NULL       0
#define HASH_DEFAULT 	HASH_MD5
#define HASH_MD5     	1
#define HASH_SHA     	2
#define HASH_RIPEMD  	3

/* config keyword types */

#define CONFIG_KEYWORD_UNKNOWN          -1
#define CONFIG_KEYWORD_NULL              0
#define CONFIG_KEYWORD_RECURSIVE         1
#define CONFIG_KEYWORD_FOLLOWLINKS       2
#define CONFIG_KEYWORD_HASH              3
#define CONFIG_KEYWORD_INCLUDEALL        4
#define CONFIG_KEYWORD_EXCLUDEALL        5
#define CONFIG_KEYWORD_COMMENT           6

#define CONFIG_KEYWORD_DIRECTORY_START   7
#define CONFIG_KEYWORD_DIRECTORY_END     8
#define CONFIG_KEYWORD_INCLUDE           9
#define CONFIG_KEYWORD_EXCLUDE          10
#define CONFIG_KEYWORD_NOENTRY          11
#define CONFIG_KEYWORD_NAME             12


/* action types. */

#define ACTION_TYPE_UNKNOWN        	0
#define ACTION_TYPE_INCLUDE        	1
#define ACTION_TYPE_INCLUDE_ALL    	2
#define ACTION_TYPE_EXCLUDE        	3
#define ACTION_TYPE_EXCLUDE_ALL    	4
#define ACTION_TYPE_NO_ENTRY       	5


static struct keywords config_keywords[] =
{
    { "name", CONFIG_KEYWORD_NAME },
    { "recursive", CONFIG_KEYWORD_RECURSIVE },
    { "followlinks", CONFIG_KEYWORD_FOLLOWLINKS },
    { "hash", CONFIG_KEYWORD_HASH },
    { "includeall", CONFIG_KEYWORD_INCLUDEALL },
    { "excludeall", CONFIG_KEYWORD_EXCLUDEALL },
    { "#", CONFIG_KEYWORD_COMMENT },
    { "<directory", CONFIG_KEYWORD_DIRECTORY_START },
    { "</directory>", CONFIG_KEYWORD_DIRECTORY_END },
    { "include", CONFIG_KEYWORD_INCLUDE },
    { "exclude", CONFIG_KEYWORD_EXCLUDE },
    { "noentry", CONFIG_KEYWORD_NOENTRY },
    { NULL, 0 }
};

static struct keywords boolean_keywords[] =
{
    { "1", TRUE },
    { "y", TRUE },
    { "yes", TRUE },
    { "true", TRUE },
    { "0", FALSE },
    { "n", FALSE },
    { "no", FALSE },
    { "false", FALSE },
    { NULL, 0 }
};

static struct keywords hash_keywords[] =
{
    { "md5", HASH_MD5 },
    { "sha", HASH_SHA },
    { "ripemd", HASH_RIPEMD },
    { NULL, 0 }
};


static char * valid_hash_values[] =
{
    "md5",
    "sha",
    "ripemd",
    NULL
};


static char * valid_boolean_values[] =
{
    "1",
    "y",
    "yes",
    "true",
    "0",
    "n",
    "no",
    "false",
    NULL
};

static char * valid_filter_values[] =
{
    "sticky",
    "suid",
    "guid",
    "executable",
    "perl",
    "python",
    "script",
    "gzip",
    "zip",
    "rpm",
    "tar",
    "pgp",
    "uid",
    "gid",
    "sid",
    "user",
    "group",
    "header",
    "file",
    "suffix",
    "md5",
    "sha",
    "ripemd",
    "permissions",
    NULL
};

/* config file structures. */

typedef struct action
{
    int type;
    filter action_filter;

} action;

typedef struct block
{
    char directory[MAX_PATH_LENGTH];

    osi_bool recursive;
    osi_bool follow_links;

    osi_list actions;
    unsigned int hash;
    string_list *no_entry_list;

} block;


typedef struct configuration
{
    char name[MAX_CONFIG_NAME_LENGTH];

    string_list *data;
    string_list *block_names;

    int state;
    unsigned char id[MAX_CONFIG_ID_LENGTH];
    
    unsigned int error_count;
    unsigned int warning_count;
    
    osi_list blocks;

} configuration;


/* public methods relating to config structures. */

configuration * osi_config_new();
void osi_config_destroy( configuration *cfg );

osi_bool osi_config_receive_first( configuration *cfg, unsigned char *data,
                                   int data_length );

osi_bool osi_config_receive( configuration *cfg, unsigned char *data,
                             int data_length );

osi_bool osi_config_receive_last( configuration *cfg, unsigned char *data,
                                  int data_length );

osi_bool osi_config_parse( configuration *cfg );
osi_bool osi_config_verify( configuration *cfg );

osi_bool osi_config_read_from_file( configuration *cfg, const char *file_path );
osi_bool osi_config_write_to_file( configuration *cfg, const char *file_path );

osi_bool osi_config_generate_id( configuration *cfg );

block * osi_config_get_global_block( configuration *cfg );
block * osi_config_get_first_block( configuration *cfg );
block * osi_config_get_next_block( configuration *cfg, block *current_block );
block * get_block_with_name( configuration *cfg, char *name );

action * get_action_from_block_with_filter( block *config_block,
                                            int filter_type,
                                            char *filter_argument );

/* semi-public */

osi_bool osi_config_parse_globals( configuration *cfg );
osi_bool osi_config_parse_non_globals( configuration *cfg );

osi_bool osi_config_verify_semantics( configuration *cfg );
osi_bool osi_config_verify_syntax( configuration *cfg );

void osi_config_dump( configuration *cfg );
void osi_config_dump_block( block *configuration_block );
void osi_config_dump_action( action *configuration_action );

/* internal config parsing and verification methods. */

int get_keyword_type( char *string );

int get_hash_value( char *keyword, unsigned int *value );
int get_boolean_value( char *keyword, osi_bool *value );
int get_attributes_value( char *keyword, unsigned int *value );

int get_name_value( configuration *cfg, char *line );

char * verify_multiple_values( char *values, char *valid_values[] );
char * verify_single_value( char *value, char *valid_values[] );

void print_config_error( int line_number, char *line, char *error, ... );
char * get_hash_name_from_type( int type );

/* internal block and action methods. */

block *new_block();
action *new_action();

block *new_block_from_block( block *parent_block );

void destroy_block( block *config_block );
void destroy_action( action *config_action );

void destroy_block_list( osi_list block_list );
void destroy_action_list( osi_list action_list );

#endif

