1 /*---------------------------------------------------------------------------- 2 -- 3 -- Module: xtmAccBase 4 -- 5 -- Project: XDiary 6 -- System: xtm - X Desktop Calendar 7 -- Subsystem: <> 8 -- Function block: <> 9 -- 10 -- Description: 11 -- Base access control functions. 12 -- 13 -- Filename: xtmAccBase.c 14 -- 15 -- Authors: Roger Larsson, Ulrika Bornetun 16 -- Creation date: 1995-02-03 17 -- 18 -- 19 -- (C) Copyright Ulrika Bornetun, Roger Larsson (1995) 20 -- All rights reserved 21 -- 22 -- Permission to use, copy, modify, and distribute this software and its 23 -- documentation for any purpose and without fee is hereby granted, 24 -- provided that the above copyright notice appear in all copies. Ulrika 25 -- Bornetun and Roger Larsson make no representations about the usability 26 -- of this software for any purpose. It is provided "as is" without express 27 -- or implied warranty. 28 ----------------------------------------------------------------------------*/ 29 30 /* SCCS module identifier. */ 31 static char SCCSID[] = "@(#) Module: xtmAccBase.c, Version: 1.1, Date: 95/02/18 15:51:49"; 32 33 34 /*---------------------------------------------------------------------------- 35 -- Include files 36 ----------------------------------------------------------------------------*/ 37 38 #include <stdio.h> 39 #include <stdlib.h> 40 #include <string.h> 41 #include <ctype.h> 42 #include <sys/types.h> 43 #include <sys/stat.h> 44 45 #include <X11/Intrinsic.h> 46 47 #include "System.h" 48 #include "LstLinked.h" 49 #include "Message.h" 50 51 #include "msgXdiary.h" 52 #include "xtmGlobal.h" 53 #include "xtmDbTools.h" 54 #include "xitError.h" 55 #include "xtmAccBase.h" 56 57 58 /*---------------------------------------------------------------------------- 59 -- Macro definitions 60 ----------------------------------------------------------------------------*/ 61 62 /* Access control file. */ 63 #define ACCESS_FILE "dbAccess" 64 #define AFS_ACCESS_FILE "dbAfsAccess" 65 66 /* Keys to use in the access file. */ 67 #define KEY_ACCESS_CONTROL "Access" 68 69 70 /*---------------------------------------------------------------------------- 71 -- Type declarations 72 ----------------------------------------------------------------------------*/ 73 74 75 /*---------------------------------------------------------------------------- 76 -- Global definitions 77 ----------------------------------------------------------------------------*/ 78 79 /* Name of module. */ 80 static char *module_name = "xtmAccessBase"; 81 82 83 /*---------------------------------------------------------------------------- 84 -- Function prototypes 85 ----------------------------------------------------------------------------*/ 86 87 88 89 /*---------------------------------------------------------------------------- 90 -- Functions 91 ----------------------------------------------------------------------------*/ 92 93 XTM_AB_STATUS xtmAbGetAccessInfo(char * directory,LST_DESC_TYPE * access_info)94 xtmAbGetAccessInfo( char *directory, 95 LST_DESC_TYPE *access_info ) 96 { 97 98 /* Variables. */ 99 char buffer[ 200 ]; 100 char flags[ 20 ]; 101 char group[ 30 ]; 102 char key[ 50 ]; 103 char user[ 30 ]; 104 char *char_ref; 105 FILE *file_ref; 106 LST_STATUS lst_status; 107 XTM_AB_ACCESS_INFO access; 108 109 110 /* Code. */ 111 112 /* Create an new access list. */ 113 *access_info = LstLinkNew( sizeof( XTM_AB_ACCESS_INFO ), NULL ); 114 115 116 /* Build the filename. */ 117 sprintf( buffer, "%s/%s", directory, ACCESS_FILE ); 118 119 /* Open the access control file. */ 120 file_ref = fopen( buffer, "r" ); 121 if( file_ref == NULL ) 122 return( XTM_AB_ERROR ); 123 124 125 /* Start reading from the file, skip all blank lines and comments. */ 126 do { 127 128 char_ref = fgets( buffer, sizeof( buffer ), file_ref ); 129 if( char_ref == NULL ) { 130 fclose( file_ref ); 131 return( XTM_AB_OK ); 132 } 133 134 /* Skip leading blanks. */ 135 while( isspace( *char_ref ) ) 136 char_ref++; 137 138 139 /* What kind of line is it? */ 140 141 /* Blank line? */ 142 if( *char_ref == '\0' ) { 143 ; 144 145 /* Comment? */ 146 } else if( *char_ref == '#' ) { 147 ; 148 149 /* Access information? */ 150 } else if( strncmp( char_ref, KEY_ACCESS_CONTROL, 151 strlen( KEY_ACCESS_CONTROL) ) == 0 ) { 152 153 user[ 0 ] ='\0'; 154 group[ 0 ] ='\0'; 155 flags[ 0 ] ='\0'; 156 157 sscanf( char_ref, "%[^:]: %[^ ] %[^ ] %[^ \n]", 158 key, 159 user, group, flags ); 160 161 /* Convert user name to uid. */ 162 if( strcmp( user, "*" ) == 0 ) 163 access.uid = -1; 164 else 165 access.uid = atoi( user ); 166 167 if( strcmp( group, "*" ) == 0 ) 168 access.gid = -1; 169 else 170 access.gid = atoi( group ); 171 172 173 /* Check the flags. */ 174 access.flags = 0; 175 176 if( strchr( flags, 'r' ) != NULL ) 177 flagSet( access.flags, XTM_AB_FLAG_READ ); 178 179 if( strchr( flags, 'w' ) != NULL ) 180 flagSet( access.flags, XTM_AB_FLAG_WRITE ); 181 182 if( strchr( flags, 'm' ) != NULL ) 183 flagSet( access.flags, XTM_AB_FLAG_MSG ); 184 185 if( strchr( flags, 'p' ) != NULL ) 186 flagSet( access.flags, XTM_AB_FLAG_PRIV ); 187 188 lst_status = LstLinkInsertLast( *access_info, &access ); 189 190 /* Unknown key. */ 191 } else { 192 sprintf( buffer, "Unknown key %s", char_ref ); 193 194 fprintf( stderr, "XDiary, %s %s: %s\n", 195 module_name, "xtmAbGetAccessInfo", buffer ); 196 } /* if */ 197 198 } while( True ); 199 200 201 } /* xtmAbGetAccessInfo */ 202 203 204 /*----------------------------------------------------------------------*/ 205 206 XTM_AB_STATUS xtmAbGetAfsAccessInfo(char * directory,LST_DESC_TYPE * access_info)207 xtmAbGetAfsAccessInfo( char *directory, 208 LST_DESC_TYPE *access_info ) 209 { 210 211 /* Variables. */ 212 char buffer[ 600 ]; 213 char flags[ 20 ]; 214 char key[ 50 ]; 215 char *char_ref; 216 FILE *file_ref; 217 LST_STATUS lst_status; 218 XTM_AB_AFS_ACL_INFO acl_id; 219 220 221 /* Code. */ 222 223 /* Create an new access list. */ 224 *access_info = LstLinkNew( sizeof( XTM_AB_AFS_ACL_INFO ), NULL ); 225 226 /* Build the filename. */ 227 sprintf( buffer, "%s/%s", directory, AFS_ACCESS_FILE ); 228 229 /* Open the access control file. */ 230 file_ref = fopen( buffer, "r" ); 231 if( file_ref == NULL ) 232 return( XTM_AB_ERROR ); 233 234 235 /* Start reading from the file, skip all blank lines and comments. */ 236 do { 237 238 char_ref = fgets( buffer, sizeof( buffer ), file_ref ); 239 if( char_ref == NULL ) { 240 fclose( file_ref ); 241 return( XTM_AB_OK ); 242 } 243 244 /* Skip leading blanks. */ 245 while( isspace( *char_ref ) ) 246 char_ref++; 247 248 249 /* What kind of line is it? */ 250 251 /* Blank line? */ 252 if( *char_ref == '\0' ) { 253 ; 254 255 /* Comment? */ 256 } else if( *char_ref == '#' ) { 257 ; 258 259 /* Access information? */ 260 } else if( strncmp( char_ref, KEY_ACCESS_CONTROL, 261 strlen( KEY_ACCESS_CONTROL) ) == 0 ) { 262 263 flags[ 0 ] ='\0'; 264 265 sscanf( char_ref, "%[^:]: %[^ ] %[^ ]\n]", key, acl_id.id, flags ); 266 267 /* Check the flags. */ 268 acl_id.flags = 0; 269 270 if( strchr( flags, 'r' ) != NULL ) 271 flagSet( acl_id.flags, XTM_AB_FLAG_READ ); 272 273 if( strchr( flags, 'w' ) != NULL ) 274 flagSet( acl_id.flags, XTM_AB_FLAG_WRITE ); 275 276 if( strchr( flags, 'm' ) != NULL ) 277 flagSet( acl_id.flags, XTM_AB_FLAG_MSG ); 278 279 lst_status = LstLinkInsertLast( *access_info, &acl_id ); 280 281 /* Unknown key. */ 282 } else { 283 sprintf( buffer, "Unknown key %s", char_ref ); 284 285 fprintf( stderr, "XDiary, %s %s: %s\n", 286 module_name, "xtmAbGetAfsAccessInfo", buffer ); 287 } /* if */ 288 289 } while( True ); 290 291 292 } /* xtmAbGetAfsAccessInfo */ 293 294 295 /*----------------------------------------------------------------------*/ 296 297 XTM_AB_STATUS xtmAbSaveAccessInfo(char * directory,LST_DESC_TYPE access_info)298 xtmAbSaveAccessInfo( char *directory, 299 LST_DESC_TYPE access_info ) 300 { 301 302 /* Variables. */ 303 char buffer[ 200 ]; 304 char group[ 30 ]; 305 char user[ 30 ]; 306 FILE *file_ref; 307 LST_STATUS lst_status; 308 XTM_AB_ACCESS_INFO access; 309 310 311 /* Code. */ 312 313 /* Write the database locations. */ 314 if( LstLinkElements( access_info ) == 0 ) 315 return( XTM_AB_OK ); 316 317 318 /* Build the filename. */ 319 sprintf( buffer, "%s/%s", directory, ACCESS_FILE ); 320 321 /* Open the access control file. */ 322 file_ref = fopen( buffer, "w" ); 323 if( file_ref == NULL ) 324 return( XTM_AB_ERROR ); 325 326 327 /* Save all access entries. */ 328 lst_status = LstLinkCurrentFirst( access_info ); 329 330 while( lst_status == LST_OK ) { 331 lst_status = LstLinkGetCurrent( access_info, &access ); 332 333 /* Take care of user and group id. */ 334 if( access.uid == -1 ) 335 sprintf( user, "*" ); 336 else 337 sprintf( user, "%d", access.uid ); 338 339 if( access.gid == -1 ) 340 sprintf( group, "*" ); 341 else 342 sprintf( group, "%d", access.gid ); 343 344 fprintf( file_ref, "%s: %-20.20s %-20.20s ", 345 KEY_ACCESS_CONTROL, 346 user, group ); 347 348 /* Write the flags. */ 349 if( flagIsSet( access.flags, XTM_AB_FLAG_READ ) ) 350 fprintf( file_ref, "r" ); 351 352 if( flagIsSet( access.flags, XTM_AB_FLAG_WRITE ) ) 353 fprintf( file_ref, "w" ); 354 355 if( flagIsSet( access.flags, XTM_AB_FLAG_MSG ) ) 356 fprintf( file_ref, "m" ); 357 358 fprintf( file_ref, "\n" ); 359 360 /* Next entry. */ 361 lst_status = LstLinkCurrentNext( access_info ); 362 363 } /* while */ 364 365 fclose( file_ref ); 366 367 return( XTM_AB_OK ); 368 369 } /* xtmAbSaveAccessInfo */ 370 371 372 /*----------------------------------------------------------------------*/ 373 374 XTM_AB_STATUS xtmAbSaveAfsAccessInfo(char * directory,LST_DESC_TYPE access_info)375 xtmAbSaveAfsAccessInfo( char *directory, 376 LST_DESC_TYPE access_info ) 377 { 378 379 /* Variables. */ 380 char buffer[ 600 ]; 381 FILE *file_ref; 382 LST_STATUS lst_status; 383 XTM_AB_AFS_ACL_INFO acl_id; 384 385 386 /* Code. */ 387 388 /* Write the database locations. */ 389 if( LstLinkElements( access_info ) == 0 ) 390 return( XTM_AB_OK ); 391 392 393 /* Build the filename. */ 394 sprintf( buffer, "%s/%s", directory, AFS_ACCESS_FILE ); 395 396 /* Open the access control file. */ 397 file_ref = fopen( buffer, "w" ); 398 if( file_ref == NULL ) 399 return( XTM_AB_ERROR ); 400 401 402 /* Save all access entries. */ 403 lst_status = LstLinkCurrentFirst( access_info ); 404 405 while( lst_status == LST_OK ) { 406 lst_status = LstLinkGetCurrent( access_info, &acl_id ); 407 408 fprintf( file_ref, "%s: %s ", KEY_ACCESS_CONTROL, acl_id.id ); 409 410 /* Write the flags. */ 411 if( flagIsSet( acl_id.flags, XTM_AB_FLAG_READ ) ) 412 fprintf( file_ref, "r" ); 413 414 if( flagIsSet( acl_id.flags, XTM_AB_FLAG_WRITE ) ) 415 fprintf( file_ref, "w" ); 416 417 if( flagIsSet( acl_id.flags, XTM_AB_FLAG_MSG ) ) 418 fprintf( file_ref, "m" ); 419 420 fprintf( file_ref, "\n" ); 421 422 /* Next entry. */ 423 lst_status = LstLinkCurrentNext( access_info ); 424 425 } /* while */ 426 427 fclose( file_ref ); 428 429 return( XTM_AB_OK ); 430 431 } /* xtmAbSaveAfsAccessInfo */ 432 433 434 /*----------------------------------------------------------------------*/ 435 436 XTM_AB_STATUS xtmAbGetUserOperations(char * directory,int user_id,int group_id,UINT32 * operations)437 xtmAbGetUserOperations( char *directory, 438 int user_id, 439 int group_id, 440 UINT32 *operations ) 441 { 442 443 /* Variables. */ 444 XTM_AB_ACCESS_INFO access; 445 XTM_AB_STATUS ac_status; 446 LST_DESC_TYPE access_info; 447 LST_STATUS lst_status; 448 449 450 /* Code. */ 451 452 *operations = 0; 453 454 /* Fetch the access control list for this database. */ 455 ac_status = xtmAbGetAccessInfo( directory, &access_info ); 456 if( ac_status != XTM_AB_OK ) 457 return( XTM_AB_OK ); 458 459 /* Check the access information. */ 460 lst_status = LstLinkCurrentFirst( access_info ); 461 462 while( lst_status == LST_OK ) { 463 lst_status = LstLinkGetCurrent( access_info, &access ); 464 465 /* Do we have a match? */ 466 if( (access.uid == -1 && access.gid == -1 ) || 467 (access.uid == -1 && access.gid == group_id) || 468 (access.uid == user_id && access.gid == -1 ) || 469 (access.uid == user_id && access.gid == group_id) ) { 470 471 /* Check the flags. */ 472 if( flagIsSet( access.flags, XTM_AB_FLAG_READ ) ) { 473 flagSet( *operations, XTM_DB_FLAG_MODE_READ ); 474 } 475 476 if( flagIsSet( access.flags, XTM_AB_FLAG_WRITE ) ) { 477 flagSet( *operations, XTM_DB_FLAG_MODE_READ ); 478 flagSet( *operations, XTM_DB_FLAG_MODE_WRITE ); 479 flagSet( *operations, XTM_DB_FLAG_MODE_MSG ); 480 } 481 482 if( flagIsSet( access.flags, XTM_AB_FLAG_MSG ) ) { 483 flagSet( *operations, XTM_DB_FLAG_MODE_MSG ); 484 } 485 486 if( flagIsSet( access.flags, XTM_AB_FLAG_PRIV ) ) { 487 flagSet( *operations, XTM_DB_FLAG_MODE_READ ); 488 flagSet( *operations, XTM_DB_FLAG_MODE_WRITE ); 489 flagSet( *operations, XTM_DB_FLAG_MODE_MSG ); 490 flagSet( *operations, XTM_DB_FLAG_MODE_PRIV ); 491 } 492 493 if( *operations != 0 ) 494 flagSet( *operations, XTM_DB_FLAG_MODE_SETID ); 495 496 LstLinkClear( access_info ); 497 498 return( XTM_AB_OK ); 499 500 } /* if */ 501 502 /* Next entry. */ 503 lst_status = LstLinkCurrentNext( access_info ); 504 505 } /* while */ 506 507 LstLinkClear( access_info ); 508 509 510 return( XTM_AB_OK ); 511 512 } /* xtmAbGetUserOperations */ 513