void prim_ftostr(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if ( oper1->type == PROG_INTEGER ) { oper1->type = PROG_FLOAT; oper1->data.fnumber = oper1->data.number; } if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (1)"); sprintf(buf, "%#g", oper1->data.fnumber); CLEAR(oper1); PushString(buf); }
void prim_rotate(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_INTEGER) abort_interp("Invalid argument type."); int n = oper1->data.number; /* Depth on stack */ if (n == INT_MIN) abort_interp("Stack underflow."); EXPECT_WRITE_STACK(abs(n)); if (n > 0) { temp2 = arg[*top - n]; for (tmp = n; tmp > 0; tmp--) arg[*top - tmp] = arg[*top - tmp + 1]; arg[*top - 1] = temp2; } else if (n < 0) { temp2 = arg[*top - 1]; for (tmp = -1; tmp > n; tmp--) arg[*top + tmp] = arg[*top + tmp - 1]; arg[*top + tmp] = temp2; } CLEAR(oper1); }
void prim_restart(PRIM_PROTOTYPE) { /* (s<message> -- ) */ CHECKOP(1); oper1 = POP(); if (mlev < LBOY) abort_interp("W4 primitive."); if (oper1->type != PROG_STRING) abort_interp("String expected."); log_status("RESTART(MUF: %d): by %s(%d)\n", program, OkObj(player) ? NAME(player) : "(login)", player); shutdown_flag = 1; restart_flag = 1; if (oper1->data.string) { strcat(restart_message, SYSWHITE MARK SYSNORMAL); strcat(restart_message, oper1->data.string->data); strcat(restart_message, "\r\n"); } CLEAR(oper1); }
void prim_atan(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (1)"); if (!no_good(oper1->data.fnumber)) { fresult = atan(oper1->data.fnumber); } else { fresult = H_PI; } CLEAR(oper1); PushFloat(fresult); }
void prim_online(PRIM_PROTOTYPE) { CHECKOP(0); if (mlev < (tp_compatible_muf ? LM3 : LM2)) abort_interp(tp_compatible_muf ? "M3 prim" : "M2 prim"); result = pcount(); CHECKOFLOW(result + 1); while (result) { ref = pdbref(result--); PushObject(ref); } result = pcount(); PushInt(result); }
void prim_put(PRIM_PROTOTYPE) { CHECKOP(2); oper1 = POP(); oper2 = POP(); if (oper1->type != PROG_INTEGER || oper1->data.number <= 0) abort_interp("Operand not a positive integer"); tmp = oper1->data.number; CHECKOP(tmp); CLEAR(&arg[*top - tmp]); copyinst(oper2, &arg[*top - tmp]); CLEAR(oper1); CLEAR(oper2); }
void prim_testlock(PRIM_PROTOTYPE) { /* d d - i */ CHECKOP(2); oper1 = POP(); /* boolexp lock */ oper2 = POP(); /* player dbref */ if (fr->level > 8) abort_interp("Interp call loops not allowed"); if (!valid_object(oper2)) abort_interp("Invalid argument (1)."); if (Typeof(oper2->data.objref) != TYPE_PLAYER && Typeof(oper2->data.objref) != TYPE_THING ) { abort_interp("Invalid object type (1)."); } CHECKREMOTE(oper2->data.objref); if (oper1->type != PROG_LOCK) abort_interp("Invalid argument (2)"); result = eval_boolexp(fr->descr, oper2->data.objref, oper1->data.lock, player); CLEAR(oper1); CLEAR(oper2); PushInt(result); }
void prim_acos(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (1)"); if ((oper1->data.fnumber >= -1.0) && (oper1->data.fnumber <= 1.0)) { fresult = acos(oper1->data.fnumber); } else { fresult = 0.0; fr->error.error_flags.nan = 1; } CLEAR(oper1); PushFloat(fresult); }
void prim_sysparm_array(PRIM_PROTOTYPE) { stk_array *nu; int security = TUNE_MLEV(player); CHECKOP(1); oper1 = POP(); /* string: match pattern */ if (oper1->type != PROG_STRING) abort_interp("Expected a string smatch pattern."); nu = tune_parms_array(DoNullInd(oper1->data.string), security, fr->pinning); CLEAR(oper1); PushArrayRaw(nu); }
void prim_floor(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (1)"); if (!no_good(oper1->data.fnumber)) { fresult = (float) floor((double) oper1->data.fnumber); } else { fresult = 0.0; fr->error.error_flags.f_bounds = 1; } CLEAR(oper1); PushFloat(fresult); }
void prim_forpop(PRIM_PROTOTYPE) { CHECKOP(0); if (!(fr->fors.top)) abort_interp("Internal error; FOR stack underflow."); CLEAR(&fr->fors.st->cur); CLEAR(&fr->fors.st->end); if (fr->trys.st) fr->trys.st->for_count--; fr->fors.top--; fr->fors.st = pop_for(fr->fors.st); }
void prim_ispidp(PRIM_PROTOTYPE) { /* i -- i */ CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_INTEGER) abort_interp("Non-integer argument (1)"); if (oper1->data.number == fr->pid) { result = 1; } else { result = in_timequeue(oper1->data.number); } CLEAR(oper1); PushInt(result); }
void prim_bread(PRIM_PROTOTYPE) { FILE *fh; /* Should return -1 for file open error. */ char *filename; /* -2 for EOF. */ double offset; int result; CHECKOP(2); oper1 = POP(); oper2 = POP(); if (getuid() == 0 ) abort_interp("Muck is running under root privs, file prims disabled."); if (mlev < LBOY) abort_interp("BOY primitive only."); if(oper1->type != PROG_INTEGER) abort_interp("Arguement 1 is not an integer."); if(oper1->data.number < 0 ) abort_interp("Arguement 1 is a negative number."); if(oper2->type != PROG_STRING) abort_interp("Arguement 2 is not a string."); if(!oper2->data.string) abort_interp("Argueemnt 2 is a null string."); offset = oper1->data.number; filename = oper2->data.string->data; #ifdef SECURE_FILE_PRIMS if (!(valid_name(filename))) abort_interp( "Invalid file name."); if ( strchr( filename, '$' ) == NULL ) filename = set_directory(filename); else filename = parse_token( filename ); if ( filename == NULL ) abort_interp( "Invalid shortcut used." ); #endif fh = fopen(filename, "r"); if (fh == NULL) { result = -1; } else { fseek(fh, offset, SEEK_SET); result = fgetc(fh); if(tp_log_files) log2filetime("logs/files", "#%d by %s BREAD: %s \n", program, unparse_object(player, player), oper2->data.string->data); if (result == EOF) { result = -2; } fclose(fh); } CLEAR(oper1); CLEAR(oper2); PushInt(result); }
void prim_cos(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (1)"); if (!no_good(oper1->data.fnumber)) { fresult = cos(oper1->data.fnumber); } else { /* FIXME: This should be NaN. */ fresult = 0.0; fr->error.error_flags.f_bounds = 1; } CLEAR(oper1); PushFloat(fresult); }
void prim_sysparm_array(PRIM_PROTOTYPE) { stk_array *nu; /* string */ CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_STRING) abort_interp("Expected a string smatch pattern. (1)"); nu = tune_parms_array(DoNullInd(oper1->data.string), mlev); CLEAR(oper1); PushArrayRaw(nu); }
void prim_mod(PRIM_PROTOTYPE) { CHECKOP(2); oper1 = POP(); oper2 = POP(); if ((!arith_type(oper2, oper1)) || (oper1->type == PROG_FLOAT) || (oper2->type == PROG_FLOAT)) abort_interp("Invalid argument type."); if (oper1->data.number) result = oper2->data.number % oper1->data.number; else result = 0; tmp = oper2->type; CLEAR(oper1); CLEAR(oper2); push(arg, top, tmp, MIPSCAST & result); }
void prim_strtof(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_STRING) abort_interp("Non-string argument. (1)"); fresult = 0.0; if (!oper1->data.string || !ifloat(oper1->data.string->data)) { fresult = 0.0; fr->error.error_flags.nan = 1; } else { sscanf(oper1->data.string->data, "%g", &fresult); } CLEAR(oper1); PushFloat(fresult); }
void prim_diff3(PRIM_PROTOTYPE) { double xout, yout, zout; double x, y, z; double x2, y2, z2; CHECKOP(3); oper3 = POP(); oper2 = POP(); oper1 = POP(); if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (4)"); if (oper2->type != PROG_FLOAT) abort_interp("Non-float argument. (5)"); if (oper3->type != PROG_FLOAT) abort_interp("Non-float argument. (6)"); x = oper1->data.fnumber; y = oper2->data.fnumber; z = oper3->data.fnumber; CLEAR(oper1); CLEAR(oper2); CLEAR(oper3); CHECKOP(3); oper3 = POP(); oper2 = POP(); oper1 = POP(); if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (1)"); if (oper2->type != PROG_FLOAT) abort_interp("Non-float argument. (2)"); if (oper3->type != PROG_FLOAT) abort_interp("Non-float argument. (3)"); x2 = oper1->data.fnumber; y2 = oper2->data.fnumber; z2 = oper3->data.fnumber; CLEAR(oper1); CLEAR(oper2); CLEAR(oper3); xout = x - x2; yout = y - y2; zout = z - z2; PushFloat(xout); PushFloat(yout); PushFloat(zout); }
void prim_sysparm(PRIM_PROTOTYPE) { const char *ptr; CHECKOP(1); oper1 = POP(); /* string: system parm name */ if (oper1->type != PROG_STRING) abort_interp("Invalid argument."); if (oper1->data.string) { ptr = tune_get_parmstring(oper1->data.string->data, TUNE_MLEV(player)); } else { ptr = ""; } CHECKOFLOW(1); CLEAR(oper1); PushString(ptr); }
void prim_parselock(PRIM_PROTOTYPE) { struct boolexp *lok; CHECKOP(1); oper1 = POP(); /* string: lock string */ CHECKOFLOW(1); if (oper1->type != PROG_STRING) abort_interp("Invalid argument"); if (oper1->data.string != (struct shared_string *) NULL) { lok = parse_boolexp(fr->descr, ProgUID, oper1->data.string->data, 0); } else { lok = TRUE_BOOLEXP; } CLEAR(oper1); PushLock(lok); }
void prim_error_str(PRIM_PROTOTYPE) { int loop; CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_STRING && oper1->type != PROG_INTEGER) abort_interp("Invalid argument type. (1)"); if (!err_init) init_err_val(); if (oper1->type == PROG_INTEGER) { if ((oper1->data.number < 0) || (oper1->data.number >= ERROR_NUM)) { result = -1; } else { result = oper1->data.number; } } else { if (!oper1->data.string) { result = -1; } else { loop = 0; result = strlen(oper1->data.string->data); for (loop = 0; loop < result; loop++) buf[loop] = toupper(oper1->data.string->data[loop]); result = -1; loop = 0; while (loop < ERROR_NUM) { if (!strcmp(buf, err_defs[loop].error_name)) { result = loop; break; } else { loop++; } } } } CLEAR(oper1); if (result == -1) { PushNullStr; } else { PushString(err_defs[result].error_string); } }
void prim_ftostrc(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if (oper1->type == PROG_INTEGER) { oper1->type = PROG_FLOAT; oper1->data.fnumber = oper1->data.number; } if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (1)"); snprintf(buf,sizeof(buf), "%.15g", oper1->data.fnumber); if (!strchr(buf, '.') && !strchr(buf, 'e') && !strchr(buf, 'n')) { strcatn(buf, sizeof(buf), ".0"); } CLEAR(oper1); PushString(buf); }
void prim_subtract(PRIM_PROTOTYPE) { CHECKOP(2); oper1 = POP(); oper2 = POP(); if (!arith_type(oper2, oper1)) abort_interp("Invalid argument type."); if ((oper1->type == PROG_FLOAT) || (oper2->type == PROG_FLOAT)) { tf1 = (oper2->type == PROG_FLOAT) ? oper2->data.fnumber : oper2->data.number; tf2 = (oper1->type == PROG_FLOAT) ? oper1->data.fnumber : oper1->data.number; if (!no_good(tf1) && !no_good(tf2)) { fresult = tf1 - tf2; } else { if (ISNAN(tf1) || ISNAN(tf2)) { fresult = tp_alt_infinity_handler ? NAN : 0.0; if (!tp_alt_infinity_handler) fr->error.error_flags.nan = 1; } else { fresult = tp_alt_infinity_handler ? (tf1 + tf2) : 0.0; if (!tp_alt_infinity_handler) fr->error.error_flags.f_bounds = 1; } } } else { result = oper2->data.number - oper1->data.number; tl = (double) oper2->data.number - (double) oper1->data.number; if (!arith_good(tl)) fr->error.error_flags.i_bounds = 1; } tmp = (oper2->type == PROG_FLOAT || oper1->type == PROG_FLOAT) ? PROG_FLOAT : oper2->type; CLEAR(oper1); CLEAR(oper2); if (tmp == PROG_FLOAT) push(arg, top, tmp, MIPSCAST & fresult); else push(arg, top, tmp, MIPSCAST & result); }
void prim_log10(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (1)"); if (!no_good(oper1->data.fnumber) && oper1->data.fnumber > 0.0) { fresult = log10(oper1->data.fnumber); } else if (oper1->data.fnumber > 0.0) { fresult = INF; fr->error.error_flags.f_bounds = 1; } else { fresult = 0.0; fr->error.error_flags.imaginary = 1; } CLEAR(oper1); PushFloat(fresult); }
void prim_atan(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if ( oper1->type == PROG_INTEGER ) { oper1->type = PROG_FLOAT; oper1->data.fnumber = oper1->data.number; } if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (1)"); if (!no_good(oper1->data.fnumber)) { fresult = (float) atan((double) oper1->data.fnumber); } else { fresult = H_PI; } CLEAR(oper1); PushFloat(fresult); }
void prim_setsysparm(PRIM_PROTOTYPE) { CHECKOP(2); oper1 = POP(); /* string: new parameter value */ oper2 = POP(); /* string: parameter to tune */ if (mlev < 6) abort_interp("Archwizards or higher only."); if (oper2->type != PROG_STRING) abort_interp("Invalid argument. (1)"); if (!oper2->data.string) abort_interp("Null string argument. (1)"); if (oper1->type != PROG_STRING) abort_interp("Invalid argument. (2)"); if (!oper1->data.string) abort_interp("Null string argument. (2)"); result = tune_setparm(program, oper2->data.string->data, oper1->data.string->data); switch (result) { case 0: /* TUNESET_SUCCESS */ log_status("TUNED (MUF): %s(%d) tuned %s to %s\n", OkObj(player) ? NAME(player) : "(Login)", player, oper2->data.string->data, oper1->data.string->data); break; case 1: /* TUNESET_UNKNOWN */ abort_interp("Unknown parameter. (1)"); break; case 2: /* TUNESET_SYNTAX */ abort_interp("Bad parameter syntax. (2)"); break; case 3: /* TUNESET_BADVAL */ abort_interp("Bad parameter value. (2)"); break; } CLEAR(oper1); CLEAR(oper2); }
void prim_clear_error(PRIM_PROTOTYPE) { int loop; CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_STRING && oper1->type != PROG_INTEGER) abort_interp("Invalid argument type. (1)"); if (!err_init) init_err_val(); if (oper1->type == PROG_INTEGER) { if ((oper1->data.number < 0) || (oper1->data.number >= ERROR_NUM)) { result = 0; } else { fr->error.is_flags = fr->error.is_flags & (~err_bits[oper1->data.number].is_flags); result = 1; } } else { if (!oper1->data.string) { result = 0; } else { loop = 0; result = strlen(oper1->data.string->data); for (loop = 0; loop < result; loop++) buf[loop] = toupper(oper1->data.string->data[loop]); result = 0; loop = 0; while (loop < ERROR_NUM) { if (!strcmp(buf, err_defs[loop].error_name)) { result = 1; fr->error.is_flags = fr->error.is_flags & (~err_bits[loop].is_flags); break; } else { loop++; } } } } CLEAR(oper1); PushInt(result); }
void prim_bappend(PRIM_PROTOTYPE) { FILE *fh; char *filename; int result, tempdat; CHECKOP(2); oper1 = POP(); oper2 = POP(); if (getuid() == 0 ) abort_interp("Muck is running under root privs, file prims disabled."); if (mlev < LBOY) abort_interp("BOY primitive only."); if (oper1->type != PROG_STRING) abort_interp("Arguement 1 is not a string."); if (!oper1->data.string) abort_interp("Arguement 1 is a null string."); if (oper2->type != PROG_INTEGER) abort_interp("Arguement 2 is not an integer."); if (oper2->data.number < 0 ) abort_interp("Arguement 2 is a negative number."); filename = oper1->data.string->data; tempdat = (int) oper2->data.string->data; #ifdef SECURE_FILE_PRIMS if (!(valid_name(filename))) abort_interp( "Invalid file name."); if ( strchr( filename, '$' ) == NULL ) filename = set_directory(filename); else filename = parse_token( filename ); if ( filename == NULL ) abort_interp( "Invalid shortcut used." ); #endif fh = fopen(filename, "a"); if (fh == NULL) { result = 0; } else { fputc(tempdat - 8, fh); result = 1; if(tp_log_files) log2filetime("logs/files", "#%d by %s BAPPEND : %s \n", program, unparse_object(player, player), oper1->data.string->data); } fclose(fh); CLEAR(oper1); CLEAR(oper2); PushInt(result); }
void prim_acos(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if ( oper1->type == PROG_INTEGER ) { oper1->type = PROG_FLOAT; oper1->data.fnumber = oper1->data.number; } if (oper1->type != PROG_FLOAT) abort_interp("Non-float argument. (1)"); if (!((oper1->data.fnumber < -1.0) || (oper1->data.fnumber > 1.0))) { fresult = (float) acos((double) oper1->data.fnumber); } else { fresult = 0.0; fr->error.error_flags.nan = 1; } CLEAR(oper1); PushFloat(fresult); }
void prim_error_name(PRIM_PROTOTYPE) { CHECKOP(1); oper1 = POP(); if (oper1->type != PROG_INTEGER) abort_interp("Invalid argument type. (1)"); if (!err_init) init_err_val(); if ((oper1->data.number < 0) || (oper1->data.number >= ERROR_NUM)) { result = -1; } else { result = oper1->data.number; } CLEAR(oper1); if (result == -1) { PushNullStr; } else { PushString(err_defs[result].error_name); } }