1
/* aide, Advanced Intrusion Detection Environment
3
* Copyright (C) 1999,2000 Rami Lehti, Pablo Virolainen
4
* $Header: /cvs-root-aide/aide/src/db_file.c,v 1.59 2002/02/10 19:10:32 rammer Exp $
6
* This program is free software; you can redistribute it and/or
7
* modify it under the terms of the GNU General Public License as
8
* published by the Free Software Foundation; either version 2 of the
9
* License, or (at your option) any later version.
11
* This program is distributed in the hope that it will be useful, but
12
* WITHOUT ANY WARRANTY; without even the implied warranty of
13
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14
* General Public License for more details.
16
* You should have received a copy of the GNU General Public License
17
* along with this program; if not, write to the Free Software
18
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
23
#include <sys/types.h>
32
#include "conf_yacc.h"
35
#include "db_sql.h" /* typedefs */
36
#include "commandconf.h"
37
/*for locale support*/
38
#include "locale-aide.h"
39
/*for locale support*/
53
extern int db_scan(); /* Rumaa.... */
54
extern char* dbtext; /* Todella rumaa... */
55
extern long db_lineno;
58
extern void db_buff(FILE*);
61
#define ZBUFSIZE 16384
63
void handle_gzipped_input(int out){
67
int* buf=malloc(ZBUFSIZE);
69
error(200,"handle_gzipped_input(),%d\n",out);
70
while(!gzeof(conf->db_gzin)){
71
if((nread=gzread(conf->db_gzin,buf,ZBUFSIZE))<0){
72
error(0,"gzread() failed!\n");
75
/* gzread returns 0 even if uncompressed bytes were read*/
77
write(out, buf,strlen((char*)buf));
79
write(out, buf,nread);
81
error(240,"nread=%d,strlen(buf)=%d,errno=%s,gzerr=%s\n",
82
nread,strlen((char*)buf),strerror(errno),
83
gzerror(conf->db_gzin,&err));
88
error(240,"handle_gzipped_input() exiting\n");
101
if(conf->gzip_dbout){
102
retval=gzflush(conf->db_gzout,Z_SYNC_FLUSH);
105
retval=fflush(conf->db_out);
113
int dofprintf( const char* s,...)
121
if(conf->gzip_dbout){
122
temp=(char*)malloc(BUFSIZE);
124
error(0,"Unable to alloc %i bytes\n",BUFSIZE);
127
retval=vsnprintf(temp,BUFSIZE,s,ap);
128
retval=gzwrite(conf->db_gzout,temp,retval);
132
retval=vfprintf(conf->db_out,s,ap);
143
int db_file_read_spec(db_config* conf){
147
conf->db_in_order=(DB_FIELD*) malloc(1*sizeof(DB_FIELD));
149
while ((i=db_scan())!=TNEWLINE){
156
/* Yes... we do not check if realloc returns nonnull */
158
conf->db_in_order=(DB_FIELD*)
159
realloc((void*)conf->db_in_order,
160
(conf->db_in_size+1)*sizeof(DB_FIELD));
163
conf->db_in_order[conf->db_in_size]=db_unknown;
165
for (l=0;l<db_unknown;l++){
167
if (strcmp(db_names[l],dbtext)==0) {
169
if (check_db_order(conf->db_in_order, conf->db_in_size,
170
db_value[l])==RETFAIL) {
171
error(0,"Field %s redefined in @@dbspec\n",dbtext);
172
conf->db_in_order[conf->db_in_size]=db_unknown;
174
conf->db_in_order[conf->db_in_size]=db_value[l];
180
for (l=0;l<db_alias_size;l++){
182
if (strcmp(db_namealias[l],dbtext)==0) {
184
if (check_db_order(conf->db_in_order, conf->db_in_size,
185
db_aliasvalue[l])==RETFAIL) {
186
error(0,"Field %s redefined in @@dbspec\n",dbtext);
187
conf->db_in_order[conf->db_in_size]=db_unknown;
189
conf->db_in_order[conf->db_in_size]=db_aliasvalue[l];
196
error(0,"Unknown field %s in database\n",dbtext);
203
error(0,"Only one @@dbspec in inputdatabase.\n");
209
error(0,"Aide internal error while reading inputdatabase.\n");
215
/* Lets generate attr from db_in_order if database does not have attr */
218
for (i=0;i<conf->db_in_size;i++) {
219
if (conf->db_in_order[i]==db_attr) {
223
if (conf->attr==-1) {
225
error(0,"Database does not have attr field.\nComparation may be incorrect\nGenerating attr-field from dbspec\nIt might be a good Idea to regenerate databases. Sorry.\n");
226
for(i=0;i<conf->db_in_size;i++) {
227
conf->attr|=1<<conf->db_in_order[i];
233
char** db_readline_file(db_config* conf){
242
if (conf->db_in_size==0) {
243
db_buff(conf->db_in);
246
while((token!=TDBSPEC)){
256
error(0,"Zlib support is not compiled in.\n");
261
/* Is this safe? Can we always fseek back? Probably.*/
262
fseek(conf->db_in,0L,SEEK_SET);
264
error(0,"Couldn't open a pipe for zipped input\n");
267
if((retval=fork())==0){
268
/* The child process */
270
conf->db_gzin=gzdopen(fileno(conf->db_in),"rb");
271
/* WARNING This causes weird problems. Don't do it.
274
handle_gzipped_input(pipefd[1]);
278
conf->db_in=fdopen(pipefd[0],"r");
279
db_buff(conf->db_in);
286
/* If it is anything else we quit */
299
if (token!=TDBSPEC) {
301
* error.. must be a @@dbspec line
304
switch (conf->db_in_url->type) {
306
error(0,"Filedatabase must have one db_spec spesification\n");
311
error(0,"Pipedatabase must have one db_spec spesification\n");
316
error(0,"FD-database must have one db_spec spesification\n");
321
error(0,"db_readline_file():Unknown or unsupported db in type.\n");
331
* Here we read da spec
334
if (db_file_read_spec(conf)!=0) {
335
/* somethin went wrong */
341
s=(char**)malloc(sizeof(char*)*db_unknown);
343
/* We NEED this to avoid Bus errors on Suns */
344
for(i=0;i<db_unknown;i++){
348
for(i=0;i<conf->db_in_size;i++){
349
switch (r=db_scan()) {
353
error(0,"Databasefile can have only one db_spec.\nTrying to continue on line %i\n",db_lineno);
356
if (conf->db_in_order[i]!=db_unknown) {
357
s[conf->db_in_order[i]]=(char*)strdup(dbtext);
364
if (conf->db_in_order[i]!=db_unknown) {
365
s[conf->db_in_order[i]]=(char*)strdup(dbtext);
371
if (conf->db_in_order[i]!=db_unknown) {
372
s[conf->db_in_order[i]]=(char*)strdup(dbtext);
386
error(0,"Not enough parameters in db:%i. Trying to continue.\n",
389
free(s[conf->db_in_order[a]]);
390
s[conf->db_in_order[a]]=NULL;
399
/* This can be the first token on a line */
401
error(0,"Not enough parameters in db:%i\n",db_lineno);
404
free(s[conf->db_in_order[a]]);
411
error(0,"There was an error in the database file on line:%i.\n",db_lineno);
417
error(0,"Not implemented in db_readline_file %i\n\"%s\"",r,dbtext);
430
* If we don't get newline after reading all sells we print an error
434
if (a!=TNEWLINE&&a!=TEOF) {
435
error(0,"Newline exptexted in database. Readin until end of line\n");
438
error(0,"Skipped value %s\n",dbtext);
444
}while(a!=TNEWLINE&&a!=TEOF);
452
int db_writechar(char* s,FILE* file,int i)
462
retval=dofprintf("0");
466
retval=dofprintf("0-");
470
retval=dofprintf("00");
478
retval=dofprintf("%s",r);
484
int db_writeint(long i,FILE* file,int a)
490
return dofprintf("%li",i);
494
int db_write_byte_base64(byte*data,size_t len,FILE* file,int i )
499
tmpstr=encode_base64(data,len);
505
retval=dofprintf(tmpstr);
509
return dofprintf("0");
515
int db_write_time_base64(time_t i,FILE* file,int a)
517
static char* ptr=NULL;
526
retval=dofprintf("0");
531
ptr=(char*)malloc(sizeof(char)*TIMEBUFSIZE);
533
error(0,"\nCannot allocate memory..\n");
536
memset((void*)ptr,0,sizeof(char)*TIMEBUFSIZE);
538
sprintf(ptr,"%li",i);
541
tmpstr=encode_base64(ptr,strlen(ptr));
542
retval=dofprintf(tmpstr);
550
int db_writeoct(long i, FILE* file,int a)
556
return dofprintf("%lo",i);
560
int db_writespec_file(db_config* conf)
566
time_t tim=time(&tim);
570
"# This file was generated by Aide, version %s\n"
571
"# Time of generation was %.4u-%.2u-%.2u %.2u:%.2u:%.2u\n",
573
st->tm_year+1900, st->tm_mon+1, st->tm_mday,
574
st->tm_hour, st->tm_min, st->tm_sec
580
retval=dofprintf("@@db_spec ");
584
for(i=0;i<conf->db_out_size;i++){
585
for(j=0;j<db_unknown;j++){
586
if(db_value[j]==conf->db_out_order[i]){
587
retval=dofprintf("%s ",db_names[j]);
595
retval=dofprintf("\n");
603
int db_writeacl(acl_type* acl,FILE* file,int a){
614
dofprintf("%i",acl->entries);
616
for (i=0;i<acl->entries;i++) {
617
dofprintf(",%i,%i,%i", acl->acl[i].a_type, acl->acl[i].a_id,
625
int db_writeline_file(db_line* line,db_config* conf){
628
for(i=0;i<conf->db_out_size;i++){
629
switch (conf->db_out_order[i]) {
631
db_writechar(line->filename,conf->db_out,i);
635
db_writechar(line->linkname,conf->db_out,i);
639
db_writeint(line->bcount,conf->db_out,i);
644
db_write_time_base64(line->mtime,conf->db_out,i);
648
db_write_time_base64(line->atime,conf->db_out,i);
652
db_write_time_base64(line->ctime,conf->db_out,i);
656
db_writeint(line->inode,conf->db_out,i);
660
db_writeint(line->nlink,conf->db_out,i);
664
db_writeint(line->uid,conf->db_out,i);
668
db_writeint(line->gid,conf->db_out,i);
672
db_writeint(line->size,conf->db_out,i);
676
db_write_byte_base64(line->md5,
677
gcry_md_get_algo_dlen(GCRY_MD_MD5),conf->db_out,i);
681
db_write_byte_base64(line->sha1,
682
gcry_md_get_algo_dlen(GCRY_MD_SHA1),conf->db_out,i);
686
db_write_byte_base64(line->rmd160,
687
gcry_md_get_algo_dlen(GCRY_MD_RMD160),
692
db_write_byte_base64(line->tiger,
693
gcry_md_get_algo_dlen(GCRY_MD_TIGER),
698
db_writeoct(line->perm,conf->db_out,i);
703
db_write_byte_base64(line->crc32,
704
mhash_get_block_size(MHASH_CRC32),
709
db_write_byte_base64(line->crc32b,
710
mhash_get_block_size(MHASH_CRC32B),
715
db_write_byte_base64(line->haval,
716
mhash_get_block_size(MHASH_HAVAL256),
721
db_write_byte_base64(line->gost ,
722
mhash_get_block_size(MHASH_GOST),
728
db_writeint(line->attr,
734
db_writeacl(line->acl,conf->db_out,i);
738
case db_checkmask : {
739
db_writeoct(line->attr,conf->db_out,i);
743
error(0,"Not implemented in db_writeline_file %i\n",
744
conf->db_out_order[i]);
753
/* Can't use fflush because of zlib.*/
759
int db_close_file(db_config* conf){
762
if(fclose(conf->db_out)){
763
error(0,"Unable to close database:%s\n",strerror(errno));
767
if(conf->gzip_dbout){
768
if(gzclose(conf->db_gzout)){
769
error(0,"Unable to close gzdatabase:%s\n",strerror(errno));
773
if(fclose(conf->db_out)){
774
error(0,"Unable to close database:%s\n",strerror(errno));