/* file access control room */
#include <access.h>
#include "path.h"
inherit "/std/room";
#define LOGIN "/secure/login"
void setup() {
string *doms, com;
int i;
set_light(100);
set_short("File access control room");
set_long(
"You are in a room full of filling cabinets. There are filing "
"cabinets everywhere, they are all packed full of papers and look "
"in a horrible mess.\n"
"Available commands:\n"
" read <euid> <path> : add read permison to the path.\n"
" write <euid> <path> : add write permission to the path.\n"
" grant <euid> <path> : add granting privileges to the path.\n"
" noread <euid> <path> : remove read permission from the path.\n"
" nowrite <euid> <path> : remove write permission from the path.\n"
" nogrant <euid> <path> : remove granting privileges to the path.\n"
" summary [path|euid] : give a list of all the read/write perms.\n"
" tidy : tidy away unnecessary perms.\n" );
add_exit("east", ROOM+"domain_control", "corridor");
seteuid("Admin");
} /* setup() */
void init() {
::init();
add_action("do_read", "read");
add_action("do_write", "write");
add_action("do_grant", "grant");
add_action("do_noread", "noread");
add_action("do_nowrite", "nowrite");
add_action("do_nogrant", "nogrant");
add_action("do_summary", "summary", 1);
add_action( "do_tidy", "tidy" );
} /* init() */
int do_read(string str) {
string euid, path, eu;
if (this_player() != this_player(1) || !interactive(previous_object())) {
event(users(), "inform", "Illegal attempt to call do_read by "+
this_player()->query_cap_name(), "cheat");
write_file("/log/CHEAT", ctime(time())+": Illegal attempt to call do_read "+
"by "+this_player()->query_cap_name()+"("+str+")\n");
return 0;
}
if (!str || sscanf(str, "%s %s", euid, path) != 2) {
notify_fail("Syntax: "+query_verb()+" <euid> <path>\n");
return 0;
}
path = (string)this_player()->get_path(path);
if (!master()->high_programmer((eu = geteuid(previous_object()))) &&
!master()->check_permission(eu, path, 4)) {
notify_fail("You do not have permission to add read access.\n");
return 0;
}
notify_fail("Something went wrong.\n");
return (int)master()->add_read_permission(euid, path);
} /* do_read() */
int do_write(string str) {
string euid, path, eu;
if (this_player() != this_player(1) || !interactive(previous_object())) {
event(users(), "inform", "Illegal attempt to call do_write by "+
this_player()->query_cap_name(), "cheat");
write_file("/log/CHEAT", ctime(time())+": Illegal attempt to call "+
"do_write by "+this_player()->query_cap_name()+"("+str+")\n");
return 0;
}
if (!str || sscanf(str, "%s %s", euid, path) != 2) {
notify_fail("Syntax: "+query_verb()+" <creator> <path>\n");
return 0;
}
path = (string)this_player()->get_path(path);
if (!"/secure/master"->high_programmer((eu = geteuid(previous_object()))) &&
!"/secure/master"->check_permission(eu, explode(path,"/"), 4)) {
notify_fail("You do not have permission to add write access.\n");
return 0;
}
notify_fail("Something went wrong.\n");
return (int)"/secure/master"->add_write_permission(euid, path);
} /* do_write() */
int do_grant(string str) {
string euid, path, eu;
if (this_player() != this_player(1) || !interactive(previous_object())) {
event(users(), "inform", "Illegal attempt to call do_grant by "+
this_player()->query_cap_name(), "cheat");
write_file("/log/CHEAT", ctime(time())+": Illegal attempt to call "+
"do_grant by "+this_player()->query_cap_name()+"("+str+")\n");
return 0;
}
if (!str || sscanf(str, "%s %s", euid, path) != 2) {
notify_fail("Syntax: "+query_verb()+" <creator> <path>\n");
return 0;
}
path = (string)this_player()->get_path(path);
if (!"/secure/master"->high_programmer((eu = geteuid(previous_object()))) &&
!"/secure/master"->check_permission(eu, path, 4)) {
notify_fail("You do not have permission to add grant access.\n");
return 0;
}
notify_fail("Something went wrong.\n");
return (int)"/secure/master"->add_grant_permission(euid, path);
} /* do_grant() */
int do_noread(string str) {
string euid, path, eu;
if (this_player() != this_player(1) || !interactive(previous_object())) {
event(users(), "inform", "Illegal attempt to call do_noread by "+
this_player()->query_cap_name(), "cheat");
write_file("/log/CHEAT", ctime(time())+": Illegal attempt to call "+
"do_noread by "+this_player()->query_cap_name()+"("+str+")\n");
return 0;
}
if (!str || sscanf(str, "%s %s", euid, path) != 2) {
notify_fail("Syntax: "+query_verb()+" <creator> <path>\n");
return 0;
}
path = (string)this_player()->get_path(path);
if (!"/secure/master"->high_programmer((eu = geteuid(previous_object()))) &&
!"/secure/master"->check_permission(eu, path, 4)) {
notify_fail("You do not have permission to remove read access.\n");
return 0;
}
notify_fail("Something went wrong.\n");
return (int)"/secure/master"->remove_read_permission(euid, path);
} /* do_noread() */
int do_nowrite(string str) {
string euid, path, eu;
if (this_player() != this_player(1) || !interactive(previous_object())) {
event(users(), "inform", "Illegal attempt to call do_nowrite by "+
this_player()->query_cap_name(), "cheat");
write_file("/log/CHEAT", ctime(time())+": Illegal attempt to call "+
"do_nowrite by "+this_player()->query_cap_name()+"("+str+")\n");
return 0;
}
if (!str || sscanf(str, "%s %s", euid, path) != 2) {
notify_fail("Syntax: "+query_verb()+" <creator> <path>\n");
return 0;
}
path = (string)this_player()->get_path(path);
if (!"/secure/master"->high_programmer((eu = geteuid(previous_object()))) &&
!"/secure/master"->check_permission(eu, path, 4)) {
notify_fail("You do not have permission to remove write access.\n");
return 0;
}
notify_fail("Something went wrong.\n");
return (int)"/secure/master"->remove_write_permission(euid, path);
} /* do_nowrite() */
int do_nogrant(string str) {
string euid, path, eu;
if (this_player() != this_player(1) || !interactive(previous_object())) {
event(users(), "inform", "Illegal attempt to call do_nogrant by "+
this_player()->query_cap_name(), "cheat");
write_file("/log/CHEAT", ctime(time())+": Illegal attempt to call "+
"do_nogrant by "+this_player()->query_cap_name()+"("+str+")\n");
return 0;
}
if (!str || sscanf(str, "%s %s", euid, path) != 2) {
notify_fail("Syntax: "+query_verb()+" <creator> <path>\n");
return 0;
}
path = (string)this_player()->get_path(path);
if (!"/secure/master"->high_programmer((eu = geteuid(previous_object()))) &&
!"/secure/master"->check_permission(eu, path, 4)) {
notify_fail("You do not have permission to remove grant access.\n");
return 0;
}
notify_fail("Something went wrong.\n");
return (int)"/secure/master"->remove_grant_permission(euid, path);
} /* do_nogrant() */
int list_before( string first, string second ) {
if ( first < second )
return -1;
if ( first > second )
return 1;
return 0;
} /* list_before() */
int do_summary(string str) {
mapping perms;
string *paths, *euids, ret, creator;
int i, j, k;
if (this_player() != this_player(1))
return 0;
perms = (mapping)"/secure/master"->query_permissions();
if (str) {
if (!perms[str]) {
if (!LOGIN->test_user( str) && str != "all") {
write("There are no permissions for "+str+".\n");
return 1;
} else {
creator = str;
}
} else {
perms = ([ str : perms[str] ]);
}
}
paths = sort_array( m_indices( perms ), "list_before", this_object() );
if (!sizeof(paths))
ret = "No permissions set.\n";
else
ret = sprintf("%11-s Path\n", "Euid");
for (i=0;i<sizeof(paths);i++) {
euids = m_indices(perms[paths[i]]);
for (j=0;j<sizeof(euids);j++) {
if (!creator || (euids[j] == creator ) ) {
k = perms[paths[i]][euids[j]];
if (!k)
ret += sprintf("%11-s LCK %s\n", euids[j], paths[i]);
else
ret += sprintf("%11-s %c%c%c %s\n", euids[j],(k&1?'R':' '),
(k&2?'W':' '), (k&4?'G':' '), paths[i]);
}
}
}
this_player()->more_string( ret, "Permissions", 1 );
return 1;
} /* do_summary() */
int do_tidy() {
int i, j, perm, same;
string path, creator, *bits;
mapping perms, euids, others;
if ( ( this_player() != this_player( 1 ) ) ||
!interactive( previous_object() ) ) {
event( users(), "inform", "illegal attempt to call do_tidy() by "+
(string)this_player()->query_name(), "cheat" );
log_file( "CHEAT", ctime( time() ) +": illegal attempt to call "+
"do_tidy() by "+ (string)this_player()->query_name() +"\n" );
return notify_fail( "Failed.\n" );
}
perms = (mapping)"/secure/master"->query_permissions();
foreach( path in keys( perms ) ) {
euids = perms[ path ];
foreach( creator in keys( euids ) ) {
perm = euids[ creator ];
if ( !"/secure/login"->test_creator( creator ) ) {
write( "No creator: "+ creator +".\n" );
if ( perm & 1 )
"/secure/master"->remove_read_permission( creator, path );
if ( perm & 2 )
"/secure/master"->remove_write_permission( creator, path );
if ( perm & 4 )
"/secure/master"->remove_grant_permission( creator, path );
continue;
}
if ( path == "/" )
continue;
same = perms[ "/" ][ creator ] & perm;
if ( same ) {
write( "Access to / supercedes "+ path +" for "+ creator +".\n" );
if ( same & 1 )
"/secure/master"->remove_read_permission( creator, path );
if ( same & 2 )
"/secure/master"->remove_write_permission( creator, path );
if ( same & 4 )
"/secure/master"->remove_grant_permission( creator, path );
continue;
}
bits = explode( path, "/" );
j = sizeof( bits ) - 1;
for ( i = 0; i < j; i++ ) {
others = perms[ "/"+ implode( bits[ 0 .. i ], "/" ) ];
if ( !others )
continue;
same = others[ creator ] & perm;
if ( same ) {
write( "Access to /"+ implode( bits[ 0 .. i ], "/" ) +
" supercedes "+ path +" for "+ creator +".\n" );
if ( same & 1 )
"/secure/master"->remove_read_permission( creator, path );
if ( same & 2 )
"/secure/master"->remove_write_permission( creator, path );
if ( same & 4 )
"/secure/master"->remove_grant_permission( creator, path );
break;
}
}
}
}
return 1;
} /* do_tidy() */