MG Mud User | 88f1247 | 2016-06-24 23:31:02 +0200 | [diff] [blame^] | 1 | // MorgenGrauen MUDlib |
| 2 | // |
| 3 | // Pubmaster.c -- Registrating the heal-values of pubs |
| 4 | // |
| 5 | // $Id: pubmaster.c 9373 2015-10-22 19:02:42Z Zesstra $ |
| 6 | |
| 7 | #include <pub.h> |
| 8 | |
| 9 | #define SAVEFILE "/secure/ARCH/pub" |
| 10 | #define CLOGFILE "/log/ARCH/pubchange" |
| 11 | #define DUMPFILE "/log/ARCH/PUBS" |
| 12 | #define DUMPLIST "/log/ARCH/PUBLIST" |
| 13 | |
| 14 | #define DUMPF(str) write_file(DUMPFILE,str) |
| 15 | #define DUMPL(str) write_file(DUMPLIST,str) |
| 16 | |
| 17 | #pragma strong_types |
| 18 | |
| 19 | #include <properties.h> |
| 20 | #include <wizlevels.h> |
| 21 | #include <health.h> |
| 22 | |
| 23 | mapping pubs; |
| 24 | nosave string *watchprops; |
| 25 | nosave int watchsize; |
| 26 | |
| 27 | void create() |
| 28 | { |
| 29 | seteuid(getuid(this_object())); |
| 30 | if (clonep(this_object())) |
| 31 | { |
| 32 | destruct(this_object()); |
| 33 | return; |
| 34 | } |
| 35 | if (!restore_object(SAVEFILE)) |
| 36 | pubs = ([]); |
| 37 | |
| 38 | watchprops = ({ P_HP, P_SP, P_ALCOHOL, P_DRINK, P_FOOD, P_VALUE, |
| 39 | "rate", "delay" }); |
| 40 | watchsize = sizeof(watchprops); |
| 41 | } |
| 42 | |
| 43 | void save_data() |
| 44 | { |
| 45 | save_object(SAVEFILE); |
| 46 | } |
| 47 | |
| 48 | int CalcMax(mapping info, string fn) |
| 49 | { float heal,delay,factor; |
| 50 | |
| 51 | if (!info || !mappingp(info)) |
| 52 | return 0; |
| 53 | if ( (info[P_ALCOHOL]+info[P_DRINK]+info[P_FOOD])<=0 || |
| 54 | (info[P_ALCOHOL] && !(info[P_DRINK]||info[P_FOOD])) ) |
| 55 | return 0; |
| 56 | |
| 57 | delay = to_float(info["delay"]); |
| 58 | if (delay>PUB_MAXDELAY) |
| 59 | delay=PUB_MAXDELAY; |
| 60 | |
| 61 | if (!stringp(fn) || !member(pubs,fn)) // External query? |
| 62 | factor=1.0; |
| 63 | else |
| 64 | factor=pubs[fn,1]; |
| 65 | |
| 66 | heal = to_float( info[P_ALCOHOL]*ALCOHOL_DELAY + |
| 67 | info[P_DRINK] *DRINK_DELAY + |
| 68 | info[P_FOOD] *FOOD_DELAY ) |
| 69 | * PUB_SOAKMULT |
| 70 | / to_float( ALCOHOL_DELAY + DRINK_DELAY + FOOD_DELAY ); |
| 71 | heal = heal + |
| 72 | to_float(info[P_VALUE])/(PUB_VALUEDIV+to_float(info["rate"])) - |
| 73 | exp(to_float(info["rate"])/PUB_RATEDIV1)/PUB_RATEDIV2; |
| 74 | heal = heal * factor * |
| 75 | (PUB_WAITOFFS + (exp(delay/PUB_WAITDIV1)/PUB_WAITDIV2)); |
| 76 | |
| 77 | return to_int(heal); |
| 78 | } |
| 79 | |
| 80 | int RegisterItem(string item, mapping info) |
| 81 | { object pub; |
| 82 | string fn; |
| 83 | int i,c,cmax,max,heal; |
| 84 | |
| 85 | if (!objectp(pub=previous_object())) |
| 86 | return -1; |
| 87 | if (member(inherit_list(pub), "/std/room/pub.c") == -1) |
| 88 | return -1; |
| 89 | if (!item || !stringp(item) || !info || !mappingp(info)) |
| 90 | return -2; |
| 91 | |
| 92 | if (info["rate"]<1) |
| 93 | info["rate"]=1; |
| 94 | if (info["delay"]<0) |
| 95 | info["delay"]=0; |
| 96 | |
| 97 | // Loadname, weil VCs als ein Pub zaehlen sollen (das Tutorial hat ein |
| 98 | // VC-Pub fuer jeden Spieler. Die sollen nicht alle einzeln hier erfasst |
| 99 | // werden. |
| 100 | fn = load_name(pub); |
| 101 | c = 0; |
| 102 | |
| 103 | heal=info[P_HP]+info[P_SP]; |
| 104 | |
| 105 | if (!member(pubs,fn)) |
| 106 | pubs += ([ fn : ([]); 1.0 ]); |
| 107 | |
| 108 | if (!member(pubs[fn],item)) |
| 109 | { |
| 110 | max=CalcMax(info,fn); |
| 111 | pubs[fn] += ([ |
| 112 | item : ([ |
| 113 | P_HP : info[P_HP], |
| 114 | P_SP : info[P_SP], |
| 115 | P_VALUE : info[P_VALUE], |
| 116 | P_DRINK : info[P_DRINK], |
| 117 | P_ALCOHOL : info[P_ALCOHOL], |
| 118 | P_FOOD : info[P_FOOD], |
| 119 | "rate" : info["rate"], |
| 120 | "delay" : info["delay"], |
| 121 | "maxheal" : heal, |
| 122 | "maxrate" : 10 |
| 123 | ]) |
| 124 | ]); |
| 125 | c=1; |
| 126 | } |
| 127 | else |
| 128 | { |
| 129 | for (i=watchsize-1;i>=0;i--) |
| 130 | if (info[watchprops[i]]!=pubs[fn][item][watchprops[i]]) |
| 131 | { |
| 132 | pubs[fn][item][watchprops[i]]=info[watchprops[i]]; |
| 133 | c=1; |
| 134 | } |
| 135 | if (heal>pubs[fn][item]["maxheal"]) |
| 136 | { |
| 137 | pubs[fn][item]["maxheal"]=heal; |
| 138 | c=1; |
| 139 | } |
| 140 | max=pubs[fn][item]["maxset"]; |
| 141 | cmax=CalcMax(info,fn); |
| 142 | if (cmax>max) |
| 143 | max=cmax; |
| 144 | } |
| 145 | |
| 146 | if (c) |
| 147 | save_data(); |
| 148 | |
| 149 | if ( heal>max || info["rate"]>pubs[fn][item]["maxrate"] ) |
| 150 | return 0; |
| 151 | |
| 152 | return 1; |
| 153 | } |
| 154 | |
| 155 | private int allowed() |
| 156 | { |
| 157 | if (previous_object() && geteuid(previous_object())==ROOTID) |
| 158 | return 1; |
| 159 | if (!process_call() && previous_object() && ARCH_SECURITY) |
| 160 | return 1; |
| 161 | return 0; |
| 162 | } |
| 163 | |
| 164 | |
| 165 | |
| 166 | int SetMaxHeal(string pub, string item, int new) |
| 167 | { int old; |
| 168 | |
| 169 | if (!allowed()) |
| 170 | return -2; |
| 171 | if (!pub || !stringp(pub) || !item || !stringp(item) || !new) |
| 172 | return -1; |
| 173 | if (!member(pubs,pub) || !member(pubs[pub],item)) |
| 174 | return 0; |
| 175 | old=pubs[pub][item]["maxset"]; |
| 176 | pubs[pub][item]["maxset"]=new; |
| 177 | write_file(CLOGFILE, |
| 178 | sprintf("%s - %s\n%s:%s HEAL %d > %d\n", |
| 179 | dtime(time()), |
| 180 | (this_interactive() ? getuid(this_interactive()) : "???"), |
| 181 | pub,item,old,new)); |
| 182 | save_data(); |
| 183 | return 1; |
| 184 | } |
| 185 | |
| 186 | int SetMaxRate(string pub, string item, int new) |
| 187 | { int old; |
| 188 | |
| 189 | if (!allowed()) |
| 190 | return -2; |
| 191 | if (!pub || !stringp(pub) || !item || !stringp(item) || !new) |
| 192 | return -1; |
| 193 | if (!member(pubs,pub) || !member(pubs[pub],item)) |
| 194 | return 0; |
| 195 | old=pubs[pub][item]["maxrate"]; |
| 196 | pubs[pub][item]["maxrate"]=new; |
| 197 | write_file(CLOGFILE, |
| 198 | sprintf("%s - %s\n%s:%s RATE %d > %d\n", |
| 199 | dtime(time()), |
| 200 | (this_interactive() ? getuid(this_interactive()) : "???"), |
| 201 | pub,item,old,new)); |
| 202 | save_data(); |
| 203 | return 1; |
| 204 | } |
| 205 | |
| 206 | int SetPubFactor(string pub, float new) |
| 207 | { float old; |
| 208 | |
| 209 | if (!allowed()) |
| 210 | return -2; |
| 211 | if (!pub || !stringp(pub) || !new || !floatp(new) || new<1.0 || new>1.5) |
| 212 | return -1; |
| 213 | if (!member(pubs,pub)) |
| 214 | return 0; |
| 215 | old=pubs[pub,1]; |
| 216 | pubs[pub,1]=new; |
| 217 | write_file(CLOGFILE, |
| 218 | sprintf("%s - %s\n%s FACT %6.4f > %6.4f\n", |
| 219 | dtime(time()), |
| 220 | (this_interactive() ? getuid(this_interactive()) : "???"), |
| 221 | pub,old,new)); |
| 222 | save_data(); |
| 223 | return 1; |
| 224 | } |
| 225 | |
| 226 | varargs int ClearPub(string pub, string item) |
| 227 | { |
| 228 | if (!allowed()) |
| 229 | return -2; |
| 230 | if (!pub || !stringp(pub) || (item && !stringp(item))) |
| 231 | return -1; |
| 232 | if (!member(pubs,pub)) |
| 233 | return 0; |
| 234 | if (!item) |
| 235 | m_delete(pubs,pub); |
| 236 | else if (!member(pubs[pub],item)) |
| 237 | return 0; |
| 238 | else |
| 239 | m_delete(pubs[pub],item); |
| 240 | save_data(); |
| 241 | return 1; |
| 242 | } |
| 243 | |
| 244 | int DumpPubs() |
| 245 | { string *publist,*itemlist; |
| 246 | int pubi,itemi; |
| 247 | |
| 248 | if (!allowed()) |
| 249 | return -2; |
| 250 | if (file_size(DUMPFILE)>1) |
| 251 | rm(DUMPFILE); |
| 252 | if (file_size(DUMPLIST)>1) |
| 253 | rm(DUMPLIST); |
| 254 | DUMPF(sprintf("Kneipen-Menu-Liste vom %s:\n\n",dtime(time()))); |
| 255 | DUMPL(sprintf("Kneipenliste vom %s:\n\n",dtime(time()))); |
| 256 | publist=sort_array(m_indices(pubs),#'</*'*/); |
| 257 | if ((pubi=sizeof(publist))<1) |
| 258 | { |
| 259 | DUMPF("No pubs in List\n"); |
| 260 | DUMPL("No pubs in List\n"); |
| 261 | return -1; |
| 262 | } |
| 263 | for (--pubi;pubi>=0;pubi--) |
| 264 | { |
| 265 | DUMPL(sprintf("%-'.'70s %6.4f\n", |
| 266 | publist[pubi],pubs[publist[pubi],1])); |
| 267 | DUMPF(sprintf("PUB: %s\nFAC: %6.4f\n\n", |
| 268 | publist[pubi],pubs[publist[pubi],1])); |
| 269 | itemlist=sort_array(m_indices(pubs[publist[pubi]]),#'</*'*/); |
| 270 | if ((itemi=sizeof(itemlist))<1) |
| 271 | { |
| 272 | DUMPF(" No items in list\n\n"); |
| 273 | continue; |
| 274 | } |
| 275 | DUMPF(sprintf( |
| 276 | " %|'_'30.30s %5s %3s %3s %3s %3s %3s %2s %2s %3s %3s\n", |
| 277 | "ITEM","VALUE","HPH","SPH","DRI","ALC","FOO","RA","MR","MAX", |
| 278 | "FND")); |
| 279 | for (--itemi;itemi>=0;itemi--) |
| 280 | DUMPF(sprintf( |
| 281 | " %-'.'30.30s %5d %3d %3d %3d %3d %3d %2d %2d %3d %3d\n", |
| 282 | itemlist[itemi], |
| 283 | (int)pubs[publist[pubi]][itemlist[itemi]][P_VALUE], |
| 284 | (int)pubs[publist[pubi]][itemlist[itemi]][P_HP], |
| 285 | (int)pubs[publist[pubi]][itemlist[itemi]][P_SP], |
| 286 | (int)pubs[publist[pubi]][itemlist[itemi]][P_DRINK], |
| 287 | (int)pubs[publist[pubi]][itemlist[itemi]][P_ALCOHOL], |
| 288 | (int)pubs[publist[pubi]][itemlist[itemi]][P_FOOD], |
| 289 | (int)pubs[publist[pubi]][itemlist[itemi]]["rate"], |
| 290 | (int)pubs[publist[pubi]][itemlist[itemi]]["maxrate"], |
| 291 | (int)pubs[publist[pubi]][itemlist[itemi]]["maxset"], |
| 292 | (int)pubs[publist[pubi]][itemlist[itemi]]["maxheal"] )); |
| 293 | DUMPF("\n"); |
| 294 | } |
| 295 | return sizeof(publist); |
| 296 | } |
| 297 | |
| 298 | // bereinigt die Kneipenliste von allen Kneipen, die auf der Platte nicht mehr |
| 299 | // existieren. |
| 300 | public void CleanPublist() { |
| 301 | foreach(string pub: pubs) { |
| 302 | if (file_size(pub+".c") <= 0) |
| 303 | m_delete(pubs,pub); |
| 304 | } |
| 305 | save_data(); |
| 306 | } |
| 307 | |