ds2.9a10/bin/
ds2.9a10/extra/
ds2.9a10/extra/crat/
ds2.9a10/extra/creremote/
ds2.9a10/extra/mingw/
ds2.9a10/extra/wolfpaw/
ds2.9a10/fluffos-2.14-ds06/
ds2.9a10/fluffos-2.14-ds06/Win32/
ds2.9a10/fluffos-2.14-ds06/compat/
ds2.9a10/fluffos-2.14-ds06/compat/simuls/
ds2.9a10/fluffos-2.14-ds06/include/
ds2.9a10/fluffos-2.14-ds06/testsuite/
ds2.9a10/fluffos-2.14-ds06/testsuite/clone/
ds2.9a10/fluffos-2.14-ds06/testsuite/command/
ds2.9a10/fluffos-2.14-ds06/testsuite/data/
ds2.9a10/fluffos-2.14-ds06/testsuite/etc/
ds2.9a10/fluffos-2.14-ds06/testsuite/include/
ds2.9a10/fluffos-2.14-ds06/testsuite/inherit/
ds2.9a10/fluffos-2.14-ds06/testsuite/inherit/master/
ds2.9a10/fluffos-2.14-ds06/testsuite/log/
ds2.9a10/fluffos-2.14-ds06/testsuite/single/
ds2.9a10/fluffos-2.14-ds06/testsuite/single/tests/compiler/
ds2.9a10/fluffos-2.14-ds06/testsuite/single/tests/efuns/
ds2.9a10/fluffos-2.14-ds06/testsuite/single/tests/operators/
ds2.9a10/fluffos-2.14-ds06/testsuite/u/
ds2.9a10/lib/cmds/admins/
ds2.9a10/lib/cmds/common/
ds2.9a10/lib/cmds/creators/include/
ds2.9a10/lib/daemon/services/
ds2.9a10/lib/daemon/tmp/
ds2.9a10/lib/doc/
ds2.9a10/lib/doc/bguide/
ds2.9a10/lib/doc/efun/all/
ds2.9a10/lib/doc/efun/arrays/
ds2.9a10/lib/doc/efun/buffers/
ds2.9a10/lib/doc/efun/compile/
ds2.9a10/lib/doc/efun/floats/
ds2.9a10/lib/doc/efun/functions/
ds2.9a10/lib/doc/efun/general/
ds2.9a10/lib/doc/efun/mixed/
ds2.9a10/lib/doc/efun/numbers/
ds2.9a10/lib/doc/efun/parsing/
ds2.9a10/lib/doc/hbook/
ds2.9a10/lib/doc/help/classes/
ds2.9a10/lib/doc/help/races/
ds2.9a10/lib/doc/lfun/
ds2.9a10/lib/doc/lfun/all/
ds2.9a10/lib/doc/lfun/lib/abilities/
ds2.9a10/lib/doc/lfun/lib/armor/
ds2.9a10/lib/doc/lfun/lib/bank/
ds2.9a10/lib/doc/lfun/lib/bot/
ds2.9a10/lib/doc/lfun/lib/clay/
ds2.9a10/lib/doc/lfun/lib/clean/
ds2.9a10/lib/doc/lfun/lib/clerk/
ds2.9a10/lib/doc/lfun/lib/client/
ds2.9a10/lib/doc/lfun/lib/combat/
ds2.9a10/lib/doc/lfun/lib/connect/
ds2.9a10/lib/doc/lfun/lib/container/
ds2.9a10/lib/doc/lfun/lib/corpse/
ds2.9a10/lib/doc/lfun/lib/creator/
ds2.9a10/lib/doc/lfun/lib/daemon/
ds2.9a10/lib/doc/lfun/lib/damage/
ds2.9a10/lib/doc/lfun/lib/deterioration/
ds2.9a10/lib/doc/lfun/lib/donate/
ds2.9a10/lib/doc/lfun/lib/door/
ds2.9a10/lib/doc/lfun/lib/equip/
ds2.9a10/lib/doc/lfun/lib/file/
ds2.9a10/lib/doc/lfun/lib/fish/
ds2.9a10/lib/doc/lfun/lib/fishing/
ds2.9a10/lib/doc/lfun/lib/flashlight/
ds2.9a10/lib/doc/lfun/lib/follow/
ds2.9a10/lib/doc/lfun/lib/ftp_client/
ds2.9a10/lib/doc/lfun/lib/ftp_data_connection/
ds2.9a10/lib/doc/lfun/lib/fuel/
ds2.9a10/lib/doc/lfun/lib/furnace/
ds2.9a10/lib/doc/lfun/lib/genetics/
ds2.9a10/lib/doc/lfun/lib/holder/
ds2.9a10/lib/doc/lfun/lib/id/
ds2.9a10/lib/doc/lfun/lib/interactive/
ds2.9a10/lib/doc/lfun/lib/lamp/
ds2.9a10/lib/doc/lfun/lib/leader/
ds2.9a10/lib/doc/lfun/lib/light/
ds2.9a10/lib/doc/lfun/lib/limb/
ds2.9a10/lib/doc/lfun/lib/living/
ds2.9a10/lib/doc/lfun/lib/load/
ds2.9a10/lib/doc/lfun/lib/look/
ds2.9a10/lib/doc/lfun/lib/manipulate/
ds2.9a10/lib/doc/lfun/lib/meal/
ds2.9a10/lib/doc/lfun/lib/messages/
ds2.9a10/lib/doc/lfun/lib/player/
ds2.9a10/lib/doc/lfun/lib/poison/
ds2.9a10/lib/doc/lfun/lib/position/
ds2.9a10/lib/doc/lfun/lib/post_office/
ds2.9a10/lib/doc/lfun/lib/potion/
ds2.9a10/lib/doc/lfun/lib/room/
ds2.9a10/lib/doc/lfun/lib/server/
ds2.9a10/lib/doc/lfun/lib/spell/
ds2.9a10/lib/doc/lfun/lib/torch/
ds2.9a10/lib/doc/lfun/lib/vendor/
ds2.9a10/lib/doc/lfun/lib/virt_sky/
ds2.9a10/lib/doc/lfun/lib/weapon/
ds2.9a10/lib/doc/lfun/lib/worn_storage/
ds2.9a10/lib/doc/lpc/basic/
ds2.9a10/lib/doc/lpc/concepts/
ds2.9a10/lib/doc/lpc/constructs/
ds2.9a10/lib/doc/lpc/etc/
ds2.9a10/lib/doc/lpc/intermediate/
ds2.9a10/lib/doc/lpc/types/
ds2.9a10/lib/doc/misc/
ds2.9a10/lib/doc/old/
ds2.9a10/lib/domains/
ds2.9a10/lib/domains/Praxis/adm/
ds2.9a10/lib/domains/Praxis/attic/
ds2.9a10/lib/domains/Praxis/cemetery/mon/
ds2.9a10/lib/domains/Praxis/data/
ds2.9a10/lib/domains/Praxis/death/
ds2.9a10/lib/domains/Praxis/mountains/
ds2.9a10/lib/domains/Praxis/obj/armour/
ds2.9a10/lib/domains/Praxis/obj/magic/
ds2.9a10/lib/domains/Praxis/obj/weapon/
ds2.9a10/lib/domains/Praxis/orc_valley/
ds2.9a10/lib/domains/Ylsrim/
ds2.9a10/lib/domains/Ylsrim/adm/
ds2.9a10/lib/domains/Ylsrim/armor/
ds2.9a10/lib/domains/Ylsrim/broken/
ds2.9a10/lib/domains/Ylsrim/fish/
ds2.9a10/lib/domains/Ylsrim/meal/
ds2.9a10/lib/domains/Ylsrim/npc/
ds2.9a10/lib/domains/Ylsrim/obj/
ds2.9a10/lib/domains/Ylsrim/virtual/
ds2.9a10/lib/domains/Ylsrim/weapon/
ds2.9a10/lib/domains/campus/adm/
ds2.9a10/lib/domains/campus/etc/
ds2.9a10/lib/domains/campus/meals/
ds2.9a10/lib/domains/campus/save/
ds2.9a10/lib/domains/campus/txt/ai/charles/
ds2.9a10/lib/domains/campus/txt/ai/charles/bak2/
ds2.9a10/lib/domains/campus/txt/ai/charles/bak2/bak1/
ds2.9a10/lib/domains/campus/txt/ai/charly/
ds2.9a10/lib/domains/campus/txt/ai/charly/bak/
ds2.9a10/lib/domains/campus/txt/jenny/
ds2.9a10/lib/domains/default/creator/
ds2.9a10/lib/domains/default/doors/
ds2.9a10/lib/domains/default/etc/
ds2.9a10/lib/domains/default/vehicles/
ds2.9a10/lib/domains/default/virtual/
ds2.9a10/lib/domains/default/weap/
ds2.9a10/lib/domains/town/txt/shame/
ds2.9a10/lib/domains/town/virtual/
ds2.9a10/lib/domains/town/virtual/bottom/
ds2.9a10/lib/domains/town/virtual/space/
ds2.9a10/lib/estates/
ds2.9a10/lib/ftp/
ds2.9a10/lib/lib/comp/
ds2.9a10/lib/lib/daemons/
ds2.9a10/lib/lib/daemons/include/
ds2.9a10/lib/lib/lvs/
ds2.9a10/lib/lib/user/
ds2.9a10/lib/lib/virtual/
ds2.9a10/lib/log/
ds2.9a10/lib/log/adm/
ds2.9a10/lib/log/archive/
ds2.9a10/lib/log/chan/
ds2.9a10/lib/log/errors/
ds2.9a10/lib/log/law/adm/
ds2.9a10/lib/log/law/email/
ds2.9a10/lib/log/law/names/
ds2.9a10/lib/log/law/sites-misc/
ds2.9a10/lib/log/law/sites-register/
ds2.9a10/lib/log/law/sites-tempban/
ds2.9a10/lib/log/law/sites-watch/
ds2.9a10/lib/log/open/
ds2.9a10/lib/log/reports/
ds2.9a10/lib/log/router/
ds2.9a10/lib/log/secure/
ds2.9a10/lib/log/watch/
ds2.9a10/lib/obj/book_source/
ds2.9a10/lib/obj/include/
ds2.9a10/lib/powers/prayers/
ds2.9a10/lib/powers/spells/
ds2.9a10/lib/realms/template/adm/
ds2.9a10/lib/realms/template/area/armor/
ds2.9a10/lib/realms/template/area/npc/
ds2.9a10/lib/realms/template/area/obj/
ds2.9a10/lib/realms/template/area/room/
ds2.9a10/lib/realms/template/area/weap/
ds2.9a10/lib/realms/template/bak/
ds2.9a10/lib/realms/template/cmds/
ds2.9a10/lib/save/kills/o/
ds2.9a10/lib/secure/cfg/classes/
ds2.9a10/lib/secure/cmds/builders/
ds2.9a10/lib/secure/cmds/creators/include/
ds2.9a10/lib/secure/cmds/players/
ds2.9a10/lib/secure/cmds/players/include/
ds2.9a10/lib/secure/daemon/imc2server/
ds2.9a10/lib/secure/daemon/include/
ds2.9a10/lib/secure/lib/
ds2.9a10/lib/secure/lib/include/
ds2.9a10/lib/secure/lib/net/include/
ds2.9a10/lib/secure/lib/std/
ds2.9a10/lib/secure/log/adm/
ds2.9a10/lib/secure/log/bak/
ds2.9a10/lib/secure/log/intermud/
ds2.9a10/lib/secure/log/network/
ds2.9a10/lib/secure/modules/
ds2.9a10/lib/secure/npc/
ds2.9a10/lib/secure/obj/include/
ds2.9a10/lib/secure/room/
ds2.9a10/lib/secure/save/
ds2.9a10/lib/secure/save/backup/
ds2.9a10/lib/secure/save/boards/
ds2.9a10/lib/secure/tmp/
ds2.9a10/lib/secure/upgrades/files/
ds2.9a10/lib/secure/verbs/creators/
ds2.9a10/lib/std/board/
ds2.9a10/lib/std/lib/
ds2.9a10/lib/tmp/
ds2.9a10/lib/verbs/admins/include/
ds2.9a10/lib/verbs/builders/
ds2.9a10/lib/verbs/common/
ds2.9a10/lib/verbs/common/include/
ds2.9a10/lib/verbs/creators/
ds2.9a10/lib/verbs/creators/include/
ds2.9a10/lib/verbs/rooms/
ds2.9a10/lib/verbs/rooms/include/
ds2.9a10/lib/www/client/
ds2.9a10/lib/www/errors/
ds2.9a10/lib/www/images/
ds2.9a10/lib/www/lpmuds/downloads_files/
ds2.9a10/lib/www/lpmuds/intermud_files/
ds2.9a10/lib/www/lpmuds/links_files/
ds2.9a10/win32/
#include <lib.h>
#include <rooms.h>
#include <save.h>
#define ROOM_ZERO "/domains/campus/room/start"

inherit LIB_DAEMON;

mapping Workrooms = ([]);

mapping WorldMap = ([]);
mapping WorldGrid = ([]);
static string last_exit;
static int global_manual;
int debugging;
static string *cards = ({ "north", "south", "east", "west",
  "northeast", "northwest", "southeast", "southwest",
  "up", "down" });
static string *unsafes = ({ "/realms/", "/open/", "/estates/" });

void create(){
    if(!WorldMap) WorldMap = ([]);
    if(!WorldGrid) WorldGrid = ([]);
    if( file_size( SAVE_ROOMS __SAVE_EXTENSION__ ) > 0 )
        unguarded( (: restore_object, SAVE_ROOMS, 1 :) );
    set_heart_beat(300);
}

void heart_beat(){
    unguarded( (: save_object(SAVE_ROOMS, 1) :) );
}

int eventDestruct(){
    unguarded( (: save_object(SAVE_ROOMS, 1) :) );
    return daemon::eventDestruct();
}

int SetDebugging(int i){
    if(!this_player() || !adminp(this_player())) return 0;
    if(i) debugging = 1;
    else debugging = 0;
    return debugging;
}

mixed validate_last_room(string room, object player){
    string location_str, current_room_name;
    object location_ob, current_room;
    mapping origin_room = ([]);
    mapping origin_room_exits = ([]);
    mixed tmp, ret;
    if(debugging) tc("validate "+room+"?","blue");
    if(player) location_str=player->GetProperty("LastLocation");
    if(!location_str) return 0;
    if(location_str) location_ob=load_object(location_str);
    if(location_ob) tmp = this_object()->GetCoordinates(location_ob);
    if(tmp) origin_room = this_object()->GetGrid(tmp);
    current_room = room_environment(player);
    current_room_name = base_name(room_environment(player));
    if(debugging){
        tc("Last Location: "+location_str);
        tc("Last Location coords: "+ tmp);
        if(sizeof(tmp) > 1)
            tc("What those coordinates grid as: "+identify(origin_room));
    }

    if(room == ROOM_ZERO || (mapp(origin_room) &&
        origin_room["room"] && origin_room["room"] == location_str)){
        mapping exits = location_ob->GetExitMap();
        if(location_ob->GetFlyRoom()){
            exits["up"] = location_ob->GetFlyRoom();
        }
        foreach(mixed key, mixed val in exits){
            if(val == current_room_name){
                ret = ([ opposite_dir(key) : location_str ]);
            }
        }
        if(debugging) tc("validation passed","blue");
        if(!ret) ret = 1;
    }
    if(debugging) tc("validation failed","red");
    return ret;
}    

void zero(){
    WorldMap = ([]);
    WorldGrid = ([]);
    Workrooms = ([]);
    ROOM_ZERO->init();
}

mapping GetGridMap(){
    return copy(WorldGrid);
}

mapping GetWorldMap(){
    return copy(WorldMap);
}

string StrCoord(mapping TmpMap){
    string ret = TmpMap["x"] + ",";
    ret += TmpMap["y"] + ",";
    ret += TmpMap["z"];
    return ret;
}

varargs mixed SetGrid(string arg_room, string coord, object player, int unset){
    string room, a, b, c, d, e, f, g, h, i, j, k, l, m, n;
    string hashed_coord = crypt(coord, "xyz");

    if(this_player() && adminp(this_player())){
        room = arg_room;
    }
    else {
        room = base_name(previous_object());
    }

    if(!player->GetProperty("LastLocation")) return 0;
    if(debugging){
        tc("SetGrid received: "+room+", "+coord+", "+
          identify(player)+", "+unset,"blue");
    }
    a = hashed_coord[0..2];
    b = hashed_coord[3..5];
    c = hashed_coord[6..8];
    d = hashed_coord[9..11];
    e = hashed_coord[12..14];
    f = hashed_coord[15..17];
    g = hashed_coord[18..20];
    h = hashed_coord[21..23];
    i = hashed_coord[24..26];
    j = hashed_coord[27..29];
    k = hashed_coord[30..32];
    l = hashed_coord[33..35];
    m = hashed_coord[36..38];
    n = hashed_coord[39..40];
    if(!WorldGrid[a]) WorldGrid[a] = ([]);
    if(!WorldGrid[a][b]) WorldGrid[a][b] = ([]);
    if(!WorldGrid[a][b][c]) WorldGrid[a][b][c] = ([]);
    if(!WorldGrid[a][b][c][d]) WorldGrid[a][b][c][d] = ([]);
    if(!WorldGrid[a][b][c][d][e]) WorldGrid[a][b][c][d][e] = ([]);
    if(!WorldGrid[a][b][c][d][e][f]) WorldGrid[a][b][c][d][e][f] = ([]);
    if(!WorldGrid[a][b][c][d][e][f][g]) WorldGrid[a][b][c][d][e][f][g] = ([]);
    if(!WorldGrid[a][b][c][d][e][f][g][h]) WorldGrid[a][b][c][d][e][f][g][h] = ([]);
    if(!WorldGrid[a][b][c][d][e][f][g][h][i]) WorldGrid[a][b][c][d][e][f][g][h][i] = ([]);
    if(!WorldGrid[a][b][c][d][e][f][g][h][i][j]) WorldGrid[a][b][c][d][e][f][g][h][i][j] = ([]);
    if(!WorldGrid[a][b][c][d][e][f][g][h][i][j][k]) WorldGrid[a][b][c][d][e][f][g][h][i][j][k] = ([]);
    if(!WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l]) WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l] = ([]);
    if(!WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m]) WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m] = ([]);
    if(!WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n]) WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n] = ([]);
    if(unset && sizeof(WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n])){
        if(debugging){
            tc("Unsetting: "+identify(WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n]),"red");
        }
        WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n] = 0;
        return 1;
    }
    if(sizeof(WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n]) ||
      sizeof(this_object()->GetCoordinates(coord))){
        if(debugging) tc("SetGrid coord "+coord+" (aka "+hashed_coord+
              ") is already "+ identify(WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n]));
        return WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n];
    }
    else {
        if(global_manual || validate_last_room(room, player)){ 
            if(debugging) tc("Setting coord "+coord+" (aka "+hashed_coord+
                  ") as "+room, "green");
            global_manual = 0;
            WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n] =
            ([ "room" : room, "coord" : coord ]);
        }
        return WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n];
    }
}

mixed GetGrid(string str){
    string hashed_coord = crypt(str, "xyz");
    string a, b, c, d, e, f, g, h, i, j, k, l, m, n;
    a = hashed_coord[0..2];
    b = hashed_coord[3..5];
    c = hashed_coord[6..8];
    d = hashed_coord[9..11];
    e = hashed_coord[12..14];
    f = hashed_coord[15..17];
    g = hashed_coord[18..20];
    h = hashed_coord[21..23];
    i = hashed_coord[24..26];
    j = hashed_coord[27..29];
    k = hashed_coord[30..32];
    l = hashed_coord[33..35];
    m = hashed_coord[36..38];
    n = hashed_coord[39..40];
    if(!WorldGrid[a] ||
      !WorldGrid[a][b] ||
      !WorldGrid[a][b][c] ||
      !WorldGrid[a][b][c][d] ||
      !WorldGrid[a][b][c][d][e] ||
      !WorldGrid[a][b][c][d][e][f] ||
      !WorldGrid[a][b][c][d][e][f][g] ||
      !WorldGrid[a][b][c][d][e][f][g][h] ||
      !WorldGrid[a][b][c][d][e][f][g][h][i] || 
      !WorldGrid[a][b][c][d][e][f][g][h][i][j] || 
      !WorldGrid[a][b][c][d][e][f][g][h][i][j][k] || 
      !WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l] || 
      !WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m] || 
      !WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n]){
        if(debugging) tc("No joy for "+str+" aka "+hashed_coord,"red");
        return copy(WorldGrid[a]);
    }
    if(debugging) tc("Joy! "+str+" aka "+hashed_coord+" is "+
          identify(WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n]),"white");
    return copy(WorldGrid[a][b][c][d][e][f][g][h][i][j][k][l][m][n]);
}

int UnSetRoom(object arg_ob){
    string creator, name, prefix, room_name;
    string grid;
    object ob;

    if(this_player() && adminp(this_player())){
        ob = arg_ob;
    }
    else{
        ob = previous_object();
    }

    name = base_name(ob);
    grid = this_object()->GetCoordinates(ob);
    if(grid && grid != "0,0,0"){
        SetGrid(name, grid, this_player(), 1);
    }
    prefix = path_prefix(name);
    room_name = last_string_element(name, "/");
    if(WorldMap[prefix] && WorldMap[prefix][room_name]){
        WorldMap[prefix][room_name] = 0;
    }
    if(sscanf(name,"/realms/%s/workroom",creator)){
        Workrooms[creator] = 0;
    }
    return 1;
}

varargs int SetRoom(object arg_ob, object player, string manual){
    string last_str, creator, name, prefix, room_name, coord;
    mapping tmpexits, backup_direction;
    object ob;

    if(this_player() && adminp(this_player())){
        ob = arg_ob;
    }
    else{
        ob = previous_object();
    }

    if(clonep(ob)){
        return 0;
    }
    if(!(last_str = player->GetProperty("LastLocation"))){
        return 0;
    }
    name = base_name(ob);
    prefix = path_prefix(name);
    room_name = last_string_element(name, "/");
    if(!sizeof(WorldMap)){
        if(name == ROOM_FURNACE){
            return 0;
        }
    }
    if(!manual && WorldMap[prefix] && WorldMap[prefix][room_name]){
        if(StrCoord(WorldMap[prefix][room_name]["coords"]) == "0,0,0" &&
          name != ROOM_ZERO){
            UnSetRoom(ob);
        }
        else{
            return 0;
        }
    }
    sscanf(name,"/realms/%s/workroom",creator);
    foreach(string element in unsafes){
        if(!strsrch(last_str, element)){
            if(strsrch(name, element) && !creator)
                return 0;
        }
    }
    if(!WorldMap[prefix]){
        if(debugging) tc("Creating WorldMap["+identify(prefix)+"]","yellow");
        WorldMap[prefix] = ([]);
    }
    if(!WorldMap[prefix][room_name]){
        if(debugging) tc("Creating WorldMap["+identify(prefix)+"]"+
              "["+identify(room_name)+"]","cyan");
        WorldMap[prefix][room_name] = ([ "date" : time(), 
          "coords" : ([ "x" : 0, "y" : 0, "z" : 0 ]),
          "exits" : ob->GetExitMap(),
        ]);
    }
    if(debugging){
    }
    if(creator){
        int x,y,z,next = sizeof(Workrooms);
        if(Workrooms[creator]){
            return 1;
        }
        x = 1000000000;
        y = 1000000000;
        z = -1000000000;
        x += ( next * 10000 );
        manual = x+","+y+","+z;
        Workrooms[creator] = ([ "grid" : manual, 
          "coords" : ([ "x" : x, "y" :y, "z" : z ]),
          "time" : time(), "number" : next ]); 
    }
    if(manual){
        int res, x, y, z;
        res = sscanf(manual,"%d,%d,%d",x,y,z);
        if(res == 3){
            if(debugging) tc("Setting manually.","red");
            WorldMap[prefix][room_name]["coords"] =
            ([ "x" : x, "y" :y, "z" : z ]);
            global_manual = 1;
            SetGrid(name, manual, player);
            return 1;
        }
    }
    if(!(backup_direction = validate_last_room(name, player))){
        if(debugging) tc("Unknown origin. Not mapping.","red");
        if(WorldMap[prefix] && WorldMap[prefix][room_name] &&
          StrCoord(WorldMap[prefix][room_name]["coords"]) == "0,0,0"){
            WorldMap[prefix][room_name] = 0;
        }
        if(!creator) return 0;
    }
    tmpexits = WorldMap[prefix][room_name]["exits"];
    if(!sizeof(tmpexits) || member_array(player->GetProperty("LastLocation"),
        values(tmpexits)) == -1){
        if(debugging)
            tc("USING BACKUP DIRECTION: "+identify(backup_direction),"red");
        tmpexits = backup_direction;
    }
    else {
        if(debugging){
            tc("Using tmpexits from WorldMap[\""+prefix+"\"][\""+
              room_name+"\"] which is: "+identify(WorldMap[prefix][room_name]["exits"]),"white");
        }
    }
    if(!mapp(tmpexits)) tmpexits = ([]);
    if(debugging) tc("tmpexits: "+identify(tmpexits),"white");
    foreach(string key, mixed val in tmpexits){
        string sub_pre = path_prefix(val);
        string sub_name = last_string_element(val, "/");
        int breakout;
        if(member_array(key, cards) == -1) continue;
        if(debugging){
            tc("sub_pre: "+sub_pre);
            tc("sub_name: "+sub_name);
            if(WorldMap[sub_pre] && WorldMap[sub_pre][sub_name])
                tc("WorldMap["+identify(sub_pre)+"]["+identify(sub_name)+
                  "]: "+identify(WorldMap[sub_pre][sub_name]));
            tc("prefix: "+prefix,"yellow");
            tc("room_name: "+room_name,"yellow");
            if(WorldMap[prefix] && WorldMap[prefix][room_name])
                tc("WorldMap["+identify(prefix)+"]["+identify(room_name)+
                  "]: "+identify(WorldMap[prefix][room_name]),"yellow");

        }

        if(WorldMap[sub_pre] && WorldMap[sub_pre][sub_name]){
            last_exit = key;
            switch(key){
            case "north" : WorldMap[prefix][room_name]["coords"]["x"] =
                WorldMap[sub_pre][sub_name]["coords"]["x"];
                WorldMap[prefix][room_name]["coords"]["y"] =
                WorldMap[sub_pre][sub_name]["coords"]["y"] - 1;
                WorldMap[prefix][room_name]["coords"]["z"] =
                WorldMap[sub_pre][sub_name]["coords"]["z"];
                breakout = 1;
                break;
            case "south" : WorldMap[prefix][room_name]["coords"]["x"] =
                WorldMap[sub_pre][sub_name]["coords"]["x"];
                WorldMap[prefix][room_name]["coords"]["y"] =
                WorldMap[sub_pre][sub_name]["coords"]["y"] + 1;
                WorldMap[prefix][room_name]["coords"]["z"] =
                WorldMap[sub_pre][sub_name]["coords"]["z"];
                breakout = 1;
                break;
            case "east" : WorldMap[prefix][room_name]["coords"]["x"] =
                WorldMap[sub_pre][sub_name]["coords"]["x"] - 1;
                WorldMap[prefix][room_name]["coords"]["y"] =
                WorldMap[sub_pre][sub_name]["coords"]["y"];
                WorldMap[prefix][room_name]["coords"]["z"] =
                WorldMap[sub_pre][sub_name]["coords"]["z"];
                breakout = 1;
                break;
            case "west" : WorldMap[prefix][room_name]["coords"]["x"] =
                WorldMap[sub_pre][sub_name]["coords"]["x"] + 1;
                WorldMap[prefix][room_name]["coords"]["y"] =
                WorldMap[sub_pre][sub_name]["coords"]["y"];
                WorldMap[prefix][room_name]["coords"]["z"] =
                WorldMap[sub_pre][sub_name]["coords"]["z"];
                breakout = 1;
                break;
            case "northeast" : WorldMap[prefix][room_name]["coords"]["x"] =
                WorldMap[sub_pre][sub_name]["coords"]["x"] - 1;
                WorldMap[prefix][room_name]["coords"]["y"] =
                WorldMap[sub_pre][sub_name]["coords"]["y"] - 1;
                WorldMap[prefix][room_name]["coords"]["z"] =
                WorldMap[sub_pre][sub_name]["coords"]["z"];
                breakout = 1;
                break;
            case "northwest" : WorldMap[prefix][room_name]["coords"]["x"] =
                WorldMap[sub_pre][sub_name]["coords"]["x"] + 1;
                WorldMap[prefix][room_name]["coords"]["y"] =
                WorldMap[sub_pre][sub_name]["coords"]["y"] - 1;
                WorldMap[prefix][room_name]["coords"]["z"] =
                WorldMap[sub_pre][sub_name]["coords"]["z"];
                breakout = 1;
                break;
            case "southeast" : WorldMap[prefix][room_name]["coords"]["x"] =
                WorldMap[sub_pre][sub_name]["coords"]["x"] - 1;
                WorldMap[prefix][room_name]["coords"]["y"] =
                WorldMap[sub_pre][sub_name]["coords"]["y"] + 1;
                WorldMap[prefix][room_name]["coords"]["z"] =
                WorldMap[sub_pre][sub_name]["coords"]["z"];
                breakout = 1;
                break;
            case "southwest" : WorldMap[prefix][room_name]["coords"]["x"] =
                WorldMap[sub_pre][sub_name]["coords"]["x"] + 1;
                WorldMap[prefix][room_name]["coords"]["y"] =
                WorldMap[sub_pre][sub_name]["coords"]["y"] + 1;
                WorldMap[prefix][room_name]["coords"]["z"] =
                WorldMap[sub_pre][sub_name]["coords"]["z"];
                breakout = 1;
                break;
            case "up" : WorldMap[prefix][room_name]["coords"]["x"] =
                WorldMap[sub_pre][sub_name]["coords"]["x"];
                WorldMap[prefix][room_name]["coords"]["y"] =
                WorldMap[sub_pre][sub_name]["coords"]["y"];
                WorldMap[prefix][room_name]["coords"]["z"] =
                WorldMap[sub_pre][sub_name]["coords"]["z"] - 1;
                breakout = 1;
                break;
            case "down" : WorldMap[prefix][room_name]["coords"]["x"] =
                WorldMap[sub_pre][sub_name]["coords"]["x"];
                WorldMap[prefix][room_name]["coords"]["y"] =
                WorldMap[sub_pre][sub_name]["coords"]["y"];
                WorldMap[prefix][room_name]["coords"]["z"] =
                WorldMap[sub_pre][sub_name]["coords"]["z"] + 1;
                breakout = 1;
                break;
            }
        }
        if(breakout) break;
    }
    coord = WorldMap[prefix][room_name]["coords"]["x"]+","+
    WorldMap[prefix][room_name]["coords"]["y"]+","+
    WorldMap[prefix][room_name]["coords"]["z"];

    if(debugging){
        tc("SetRoom About to send: SetGrid("+identify(name)+", "+
          identify(coord)+", "+identify(player)+")");
    }
    SetGrid(name, coord, player);
    return 1;
}

string GetCoordinates(mixed ob){
    string name, prefix, room_name, ret;
    int err;
    if(clonep(ob)){
        object env = room_environment(ob);
        if(env && !clonep(env)) ob = env;
        else return "";
    }
    name = base_name(ob);
    prefix = path_prefix(name);
    room_name = last_string_element(name, "/");
    if(!WorldMap[prefix] || !WorldMap[prefix][room_name]){
        return "";
    }
    ret = WorldMap[prefix][room_name]["coords"]["x"]+","+
    WorldMap[prefix][room_name]["coords"]["y"]+","+
    WorldMap[prefix][room_name]["coords"]["z"];
    return ret;
} 

mapping GetCoordinateMap(mixed ob){
    string name = base_name(ob);
    string prefix = path_prefix(name);
    string room_name = last_string_element(name, "/");
    if(!WorldMap[prefix] || !WorldMap[prefix][room_name]){
        return ([]);
    }
    return ([ "x" : WorldMap[prefix][room_name]["coords"]["x"],
      "y" : WorldMap[prefix][room_name]["coords"]["y"],
      "z" : WorldMap[prefix][room_name]["coords"]["z"], ]);
}

mixed GetRoom(mixed ob){
    string name, prefix, room_name;
    if(clonep(ob)) return 0;
    name = base_name(ob);
    prefix = path_prefix(name);
    room_name = last_string_element(name, "/");
    if(!WorldMap[prefix]) return "No such prefix.";
    if(!WorldMap[prefix][room_name]) return "No such room.";
    return ([ name : copy(WorldMap[prefix][room_name]) ]); 
}