/*************************************************************************** * Original Diku Mud copyright (C) 1990, 1991 by Sebastian Hammer, * * Michael Seifert, Hans Henrik St{rfeldt, Tom Madsen, and Katja Nyboe. * * * * Merc Diku Mud improvments copyright (C) 1992, 1993 by Michael * * Chastain, Michael Quan, and Mitchell Tse. * * * * Ack 2.2 improvements copyright (C) 1994 by Stephen Dooley * * * * In order to use any part of this Merc Diku Mud, you must comply with * * both the original Diku license in 'license.doc' as well the Merc * * license in 'license.txt'. In particular, you may not remove either of * * these copyright notices. * * * * _/ _/_/_/ _/ _/ _/ ACK! MUD is modified * * _/_/ _/ _/ _/ _/ Merc2.0/2.1/2.2 code * * _/ _/ _/ _/_/ _/ (c)Stephen Zepp 1998 * * _/_/_/_/ _/ _/ _/ Version #: 4.3 * * _/ _/ _/_/_/ _/ _/ _/ * * * * http://ackmud.nuc.net/ * * zenithar@ackmud.nuc.net * * Much time and thought has gone into this software and you are * * benefitting. We hope that you share your changes too. What goes * * around, comes around. * ***************************************************************************/ /* * This program goes through each area. It checks all vnums to see if * they are in the allowed range. If not it moves them, and updates all * references. */ #if defined(macintosh) #include <types.h> #else #include <sys/types.h> #endif #include <ctype.h> #include <stdio.h> #include <stdlib.h> #include <string.h> #include "ack.h" #include "hash.h" void swap_global_hash(char Tp, void * Ptr, int old_vnum, int new_vnum) { ROOM_INDEX_DATA * pRoomIndex,* prevRoomIndex; OBJ_INDEX_DATA * pObjIndex ,* prevObjIndex; MOB_INDEX_DATA * pMobIndex ,* prevMobIndex; extern ROOM_INDEX_DATA * room_index_hash[]; extern OBJ_INDEX_DATA * obj_index_hash[]; extern MOB_INDEX_DATA * mob_index_hash[]; int iHash; switch (Tp) { case 'R': /* Delete old hash table entry */ iHash = old_vnum % MAX_KEY_HASH; prevRoomIndex = NULL; for (pRoomIndex = room_index_hash[iHash]; pRoomIndex != NULL; pRoomIndex=pRoomIndex->next) { if (pRoomIndex == (ROOM_INDEX_DATA *) Ptr) break; prevRoomIndex = pRoomIndex; } if (pRoomIndex != NULL) { if (prevRoomIndex == NULL) room_index_hash[iHash]=pRoomIndex->next; else prevRoomIndex->next=pRoomIndex->next; } /* Add another */ iHash = new_vnum % MAX_KEY_HASH; pRoomIndex->next = room_index_hash[iHash]; room_index_hash[iHash] = pRoomIndex; break; case 'M': /* Delete old hash table entry */ iHash = old_vnum % MAX_KEY_HASH; prevMobIndex = NULL; for (pMobIndex = mob_index_hash[iHash]; pMobIndex != NULL; pMobIndex=pMobIndex->next) { if (pMobIndex == (MOB_INDEX_DATA *) Ptr) break; prevMobIndex = pMobIndex; } if (pMobIndex != NULL) { if (prevMobIndex == NULL) mob_index_hash[iHash]=pMobIndex->next; else prevMobIndex->next=pMobIndex->next; } /* Add another */ iHash = new_vnum % MAX_KEY_HASH; pMobIndex->next = mob_index_hash[iHash]; mob_index_hash[iHash] = pMobIndex; break; case 'O': /* Delete old hash table entry */ iHash = old_vnum % MAX_KEY_HASH; prevObjIndex = NULL; for (pObjIndex = obj_index_hash[iHash]; pObjIndex != NULL; pObjIndex=pObjIndex->next) { if (pObjIndex == (OBJ_INDEX_DATA *) Ptr) break; prevObjIndex = pObjIndex; } if (pObjIndex != NULL) { if (prevObjIndex == NULL) obj_index_hash[iHash]=pObjIndex->next; else prevObjIndex->next=pObjIndex->next; } /* Add another */ iHash = new_vnum % MAX_KEY_HASH; pObjIndex->next = obj_index_hash[iHash]; obj_index_hash[iHash] = pObjIndex; break; } return; } void do_check_areas(CHAR_DATA * ch, char * argument) { hash_table * room_hash; hash_table * obj_hash; hash_table * mob_hash; int min_vnum,max_vnum; int new_vnum,old_vnum; char buffer[MAX_INPUT_LENGTH]; FILE * out_file; int a; RESET_DATA * pReset; AREA_DATA * CurArea; BUILD_DATA_LIST * pList; ROOM_INDEX_DATA * pRoomIndex; OBJ_INDEX_DATA * pObjIndex; MOB_INDEX_DATA * pMobIndex; /* Create hash tables for rooms, mobiles, objects */ room_hash=create_hash_table(MAX_KEY_HASH); obj_hash=create_hash_table(MAX_KEY_HASH); mob_hash=create_hash_table(MAX_KEY_HASH); out_file=fopen("area_changes.txt","a"); for (CurArea=first_area; CurArea != NULL; CurArea=CurArea->next) { min_vnum=CurArea->min_vnum; max_vnum=CurArea->max_vnum; fprintf(out_file,"%s:\n",CurArea->name); /* Go through rooms */ for (pList=CurArea->first_area_room; pList != NULL; pList=pList->next) { pRoomIndex=pList->data; if (pRoomIndex->vnum < min_vnum || pRoomIndex->vnum > max_vnum) { old_vnum=pRoomIndex->vnum; /* Find a free slot */ for (new_vnum=min_vnum; new_vnum <= max_vnum; new_vnum++) if (get_room_index(new_vnum)==NULL) break; if (new_vnum > max_vnum) { sprintf(buffer,"Not enough vnums in area %s\n\r",CurArea->name); send_to_char(buffer,ch); } else { fprintf(out_file,"Room: [%5i] -> [%5i] %s\n",old_vnum,new_vnum,pRoomIndex->name); /* Delete from room hashing table, and put new vnum in. */ add_hash_entry(room_hash,old_vnum,(void *) new_vnum); swap_global_hash('R',pRoomIndex,old_vnum,new_vnum); pRoomIndex->vnum=new_vnum; area_modified(CurArea); } } } /* Go through objs */ for (pList=CurArea->first_area_object; pList != NULL; pList=pList->next) { pObjIndex=pList->data; if (pObjIndex->vnum < min_vnum || pObjIndex->vnum > max_vnum) { old_vnum=pObjIndex->vnum; /* Find a free slot */ for (new_vnum=min_vnum; new_vnum <= max_vnum; new_vnum++) if (get_obj_index(new_vnum)==NULL) break; if (new_vnum > max_vnum) { sprintf(buffer,"Not enough vnums in area %s\n\r",CurArea->name); send_to_char(buffer,ch); } else { fprintf(out_file,"Obj: [%5i] -> [%5i] %s\n",old_vnum,new_vnum,pObjIndex->short_descr); /* Delete from obj hashing table, and put new vnum in. */ add_hash_entry(obj_hash,old_vnum,(void *) new_vnum); swap_global_hash('O',pObjIndex,old_vnum,new_vnum); pObjIndex->vnum=new_vnum; area_modified(CurArea); } } } /* Go through mobs */ for (pList=CurArea->first_area_mobile; pList != NULL; pList=pList->next) { pMobIndex=pList->data; if (pMobIndex->vnum < min_vnum || pMobIndex->vnum > max_vnum) { old_vnum=pMobIndex->vnum; /* Find a free slot */ for (new_vnum=min_vnum; new_vnum <= max_vnum; new_vnum++) if (get_mob_index(new_vnum)==NULL) break; if (new_vnum > max_vnum) { sprintf(buffer,"Not enough vnums in area %s\n\r",CurArea->name); send_to_char(buffer,ch); } else { fprintf(out_file,"Mob: [%5i] -> [%5i] %s\n",old_vnum,new_vnum,pMobIndex->short_descr); /* Delete from mob hashing table, and put new vnum in. */ add_hash_entry(mob_hash,old_vnum,(void *) new_vnum); swap_global_hash('M',pMobIndex,old_vnum,new_vnum); pMobIndex->vnum=new_vnum; area_modified(CurArea); /* Check for shops */ if (pMobIndex->pShop != NULL) pMobIndex->pShop->keeper=new_vnum; } } } } fclose(out_file); /* Now go through all things referencing the changes * * Resets * exit->key * */ for (CurArea=first_area; CurArea != NULL; CurArea=CurArea->next) { for (pList=CurArea->first_area_room; pList != NULL; pList=pList->next) { /* Check keys and exits*/ pRoomIndex=pList->data; for (a=0; a<=5; a++) { if ( pRoomIndex->exit[a] != NULL ) { if ( pRoomIndex->exit[a]->key != 0 && (new_vnum=(int) get_hash_entry(obj_hash,pRoomIndex->exit[a]->key)) != 0) { pRoomIndex->exit[a]->key = new_vnum; area_modified(CurArea); } if ( (new_vnum=(int) get_hash_entry(room_hash,pRoomIndex->exit[a]->vnum)) != 0) { pRoomIndex->exit[a]->vnum = new_vnum; area_modified(CurArea); } } } } /* Scan through resets */ for (pReset=CurArea->first_reset; pReset != NULL; pReset=pReset->next) { switch (pReset->command) { case 'M': if ( (new_vnum=(int) get_hash_entry(mob_hash,pReset->arg1)) != 0) { area_modified(CurArea); pReset->arg1=new_vnum; } if ( (new_vnum=(int) get_hash_entry(room_hash,pReset->arg3)) != 0) { area_modified(CurArea); pReset->arg3=new_vnum; } break; case 'O': if ( (new_vnum=(int) get_hash_entry(obj_hash,pReset->arg1)) != 0) { area_modified(CurArea); pReset->arg1=new_vnum; } if ( (new_vnum=(int) get_hash_entry(room_hash,pReset->arg3)) != 0) { area_modified(CurArea); pReset->arg3=new_vnum; } break; case 'P': if ( (new_vnum=(int) get_hash_entry(obj_hash,pReset->arg1)) != 0) { area_modified(CurArea); pReset->arg1=new_vnum; } if ( (new_vnum=(int) get_hash_entry(obj_hash,pReset->arg3)) != 0) { area_modified(CurArea); pReset->arg3=new_vnum; } break; case 'G': case 'E': if ( (new_vnum=(int) get_hash_entry(obj_hash,pReset->arg1)) != 0) { area_modified(CurArea); pReset->arg1=new_vnum; } break; case 'D': case 'R': if ( (new_vnum=(int) get_hash_entry(room_hash,pReset->arg1)) != 0) { area_modified(CurArea); pReset->arg1=new_vnum; } break; } } } /* FINISHED */ delete_hash_table(room_hash); delete_hash_table(obj_hash); delete_hash_table(mob_hash); return; } void do_check_area(CHAR_DATA * ch, char * argument) { send_to_char("You must say check_areas in full.\n\r",ch); return; }