js_system.c 50.9 KB
Newer Older
1
2
3
4
5
6
7
8
9
10
/* js_system.c */

/* Synchronet JavaScript "system" Object */

/* $Id$ */

/****************************************************************************
 * @format.tab-size 4		(Plain Text/Source Code File Header)			*
 * @format.use-tabs true	(see http://www.synchro.net/ptsc_hdr.html)		*
 *																			*
11
 * Copyright 2008 Rob Swindell - http://www.synchro.net/copyright.html		*
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
 *																			*
 * This program is free software; you can redistribute it and/or			*
 * modify it under the terms of the GNU General Public License				*
 * as published by the Free Software Foundation; either version 2			*
 * of the License, or (at your option) any later version.					*
 * See the GNU General Public License for more details: gpl.txt or			*
 * http://www.fsf.org/copyleft/gpl.html										*
 *																			*
 * Anonymous FTP access to the most recent released source is available at	*
 * ftp://vert.synchro.net, ftp://cvs.synchro.net and ftp://ftp.synchro.net	*
 *																			*
 * Anonymous CVS access to the development source and modification history	*
 * is available at cvs.synchro.net:/cvsroot/sbbs, example:					*
 * cvs -d :pserver:anonymous@cvs.synchro.net:/cvsroot/sbbs login			*
 *     (just hit return, no password is necessary)							*
 * cvs -d :pserver:anonymous@cvs.synchro.net:/cvsroot/sbbs checkout src		*
 *																			*
 * For Synchronet coding style and modification guidelines, see				*
 * http://www.synchro.net/source.html										*
 *																			*
 * You are encouraged to submit any modifications (preferably in Unix diff	*
 * format) via e-mail to mods@synchro.net									*
 *																			*
 * Note: If this box doesn't appear square, then you need to fix your tabs.	*
 ****************************************************************************/

#include "sbbs.h"
39
#include "js_request.h"
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56

#ifdef JAVASCRIPT

/* System Object Properites */
enum {
	 SYS_PROP_NAME
	,SYS_PROP_OP
	,SYS_PROP_ID
	,SYS_PROP_MISC
	,SYS_PROP_PSNAME
	,SYS_PROP_PSNUM
	,SYS_PROP_INETADDR
	,SYS_PROP_LOCATION
	,SYS_PROP_TIMEZONE
	,SYS_PROP_PWDAYS
	,SYS_PROP_DELDAYS

57
	,SYS_PROP_LASTUSER
58
59
	,SYS_PROP_LASTUSERON
	,SYS_PROP_FREEDISKSPACE
60
	,SYS_PROP_FREEDISKSPACEK
61
62
63
64

	,SYS_PROP_NODES
	,SYS_PROP_LASTNODE

65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
	,SYS_PROP_NEW_PASS
	,SYS_PROP_NEW_MAGIC
	,SYS_PROP_NEW_LEVEL
	,SYS_PROP_NEW_FLAGS1
	,SYS_PROP_NEW_FLAGS2
	,SYS_PROP_NEW_FLAGS3
	,SYS_PROP_NEW_FLAGS4
	,SYS_PROP_NEW_REST
	,SYS_PROP_NEW_EXEMPT
	,SYS_PROP_NEW_CDT
	,SYS_PROP_NEW_MIN
	,SYS_PROP_NEW_SHELL
	,SYS_PROP_NEW_XEDIT
	,SYS_PROP_NEW_MISC
	,SYS_PROP_NEW_PROT
	,SYS_PROP_NEW_EXPIRE
	,SYS_PROP_NEW_UQ

	,SYS_PROP_EXPIRED_LEVEL
	,SYS_PROP_EXPIRED_FLAGS1
	,SYS_PROP_EXPIRED_FLAGS2
	,SYS_PROP_EXPIRED_FLAGS3
	,SYS_PROP_EXPIRED_FLAGS4
	,SYS_PROP_EXPIRED_REST
	,SYS_PROP_EXPIRED_EXEMPT

91
92
93
94
95
96
97
	/* directories */
	,SYS_PROP_NODE_DIR
	,SYS_PROP_CTRL_DIR
	,SYS_PROP_DATA_DIR
	,SYS_PROP_TEXT_DIR
	,SYS_PROP_TEMP_DIR
	,SYS_PROP_EXEC_DIR
98
99
	,SYS_PROP_MODS_DIR
	,SYS_PROP_LOGS_DIR
rswindell's avatar
rswindell committed
100

101
	/* msclock() access */
102
103
	,SYS_PROP_CLOCK
	,SYS_PROP_CLOCK_PER_SEC
104
	,SYS_PROP_TIMER
105

106
107
	/* filenames */
	,SYS_PROP_DEVNULL
108
	,SYS_PROP_TEMP_PATH
rswindell's avatar
rswindell committed
109
	,SYS_PROP_CMD_SHELL
110

111
112
	/* last */
	,SYS_PROP_LOCAL_HOSTNAME
113
114
115
116
};

static JSBool js_system_get(JSContext *cx, JSObject *obj, jsval id, jsval *vp)
{
117
	char		str[128];
118
	char*		p=NULL;
119
    jsint       tiny;
120
	JSString*	js_str;
121
	ulong		val;
122
	scfg_t*		cfg;
deuce's avatar
deuce committed
123
	jsrefcount	rc;
124
125

	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
rswindell's avatar
rswindell committed
126
		return(JS_FALSE);
127
128
129
130
131

    tiny = JSVAL_TO_INT(id);

	switch(tiny) {
		case SYS_PROP_NAME:
132
	        p=cfg->sys_name;
133
134
			break;
		case SYS_PROP_OP:
135
			p=cfg->sys_op;
136
137
			break;
		case SYS_PROP_ID:
138
			p=cfg->sys_id;
139
140
			break;
		case SYS_PROP_MISC:
141
			JS_NewNumberValue(cx,cfg->sys_misc,vp);
142
143
			break;
		case SYS_PROP_PSNAME:
144
			p=cfg->sys_psname;
145
146
147
148
149
			break;
		case SYS_PROP_PSNUM:
			*vp = INT_TO_JSVAL(cfg->sys_psnum);
			break;
		case SYS_PROP_INETADDR:
150
			p=cfg->sys_inetaddr;
151
152
			break;
		case SYS_PROP_LOCATION:
153
			p=cfg->sys_location;
154
155
			break;
		case SYS_PROP_TIMEZONE:
156
			sys_timezone(cfg);
157
158
159
160
161
162
163
164
165
166
167
168
169
170
			*vp = INT_TO_JSVAL(cfg->sys_timezone);
			break;
		case SYS_PROP_NODES:
			*vp = INT_TO_JSVAL(cfg->sys_nodes);
			break;
		case SYS_PROP_LASTNODE:
			*vp = INT_TO_JSVAL(cfg->sys_lastnode);
			break;
		case SYS_PROP_PWDAYS:
			*vp = INT_TO_JSVAL(cfg->sys_pwdays);
			break;
		case SYS_PROP_DELDAYS:
			*vp = INT_TO_JSVAL(cfg->sys_deldays);
			break;
171
172
173
		case SYS_PROP_LASTUSER:
			*vp = INT_TO_JSVAL(lastuser(cfg));
			break;
174
		case SYS_PROP_LASTUSERON:
175
			p=lastuseron;
176
177
			break;
		case SYS_PROP_FREEDISKSPACE:
178
		case SYS_PROP_FREEDISKSPACEK:
179
			rc=JS_SUSPENDREQUEST(cx);
180
181
182
183
			if(tiny==SYS_PROP_FREEDISKSPACE)
				val = getfreediskspace(cfg->temp_dir,0);
			else
				val = getfreediskspace(cfg->temp_dir,1024);
184
			JS_RESUMEREQUEST(cx, rc);
185
			JS_NewNumberValue(cx,val,vp);
186
187
			break;

188
		case SYS_PROP_NEW_PASS:
189
			p=cfg->new_pass;
190
191
			break;
		case SYS_PROP_NEW_MAGIC:
192
			p=cfg->new_magic;
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
			break;
		case SYS_PROP_NEW_LEVEL:
			*vp = INT_TO_JSVAL(cfg->new_level);
			break;
		case SYS_PROP_NEW_FLAGS1:
			*vp = INT_TO_JSVAL(cfg->new_flags1);
			break;
		case SYS_PROP_NEW_FLAGS2:
			*vp = INT_TO_JSVAL(cfg->new_flags2);
			break;
		case SYS_PROP_NEW_FLAGS3:
			*vp = INT_TO_JSVAL(cfg->new_flags3);
			break;
		case SYS_PROP_NEW_FLAGS4:
			*vp = INT_TO_JSVAL(cfg->new_flags4);
			break;
		case SYS_PROP_NEW_REST:
			*vp = INT_TO_JSVAL(cfg->new_rest);
			break;
		case SYS_PROP_NEW_EXEMPT:
			*vp = INT_TO_JSVAL(cfg->new_exempt);
			break;
		case SYS_PROP_NEW_CDT:
216
			JS_NewNumberValue(cx,cfg->new_cdt,vp);
217
218
			break;
		case SYS_PROP_NEW_MIN:
219
			JS_NewNumberValue(cx,cfg->new_min,vp);
220
221
			break;
		case SYS_PROP_NEW_SHELL:
222
223
			if(cfg->new_shell<cfg->total_shells)
				p=cfg->shell[cfg->new_shell]->code;
224
225
			break;
		case SYS_PROP_NEW_XEDIT:
226
			p=cfg->new_xedit;
227
228
			break;
		case SYS_PROP_NEW_MISC:
229
			JS_NewNumberValue(cx,cfg->new_misc,vp);
230
231
232
			break;
		case SYS_PROP_NEW_PROT:
			sprintf(str,"%c",cfg->new_prot);
233
			p=str;
234
235
			break;
		case SYS_PROP_NEW_EXPIRE:
236
			JS_NewNumberValue(cx,cfg->new_expire,vp);
237
238
			break;
		case SYS_PROP_NEW_UQ:
239
			JS_NewNumberValue(cx,cfg->uq,vp);
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
			break;

		case SYS_PROP_EXPIRED_LEVEL:
			*vp = INT_TO_JSVAL(cfg->expired_level);
			break;
		case SYS_PROP_EXPIRED_FLAGS1:
			*vp = INT_TO_JSVAL(cfg->expired_flags1);
			break;
		case SYS_PROP_EXPIRED_FLAGS2:
			*vp = INT_TO_JSVAL(cfg->expired_flags2);
			break;
		case SYS_PROP_EXPIRED_FLAGS3:
			*vp = INT_TO_JSVAL(cfg->expired_flags3);
			break;
		case SYS_PROP_EXPIRED_FLAGS4:
			*vp = INT_TO_JSVAL(cfg->expired_flags4);
			break;
		case SYS_PROP_EXPIRED_REST:
			*vp = INT_TO_JSVAL(cfg->expired_rest);
			break;
		case SYS_PROP_EXPIRED_EXEMPT:
			*vp = INT_TO_JSVAL(cfg->expired_exempt);
			break;
263
		case SYS_PROP_NODE_DIR:
264
			p=cfg->node_dir;
265
266
			break;
		case SYS_PROP_CTRL_DIR:
267
			p=cfg->ctrl_dir;
268
269
			break;
		case SYS_PROP_DATA_DIR:
270
			p=cfg->data_dir;
271
272
			break;
		case SYS_PROP_TEXT_DIR:
273
			p=cfg->text_dir;
274
275
			break;
		case SYS_PROP_TEMP_DIR:
276
			p=cfg->temp_dir;
277
278
			break;
		case SYS_PROP_EXEC_DIR:
279
			p=cfg->exec_dir;
280
			break;
281
282
283
284
285
286
		case SYS_PROP_MODS_DIR:
			p=cfg->mods_dir;
			break;
		case SYS_PROP_LOGS_DIR:
			p=cfg->logs_dir;
			break;
287
288
289
290

		case SYS_PROP_DEVNULL:
			p=_PATH_DEVNULL;
			break;
291
292
293
		case SYS_PROP_TEMP_PATH:
			p=_PATH_TMP;
			break;
294

rswindell's avatar
rswindell committed
295
		case SYS_PROP_CMD_SHELL:
296
			rc=JS_SUSPENDREQUEST(cx);
rswindell's avatar
rswindell committed
297
			p=os_cmdshell();
298
			JS_RESUMEREQUEST(cx, rc);
rswindell's avatar
rswindell committed
299
300
			break;

301
		case SYS_PROP_CLOCK:
302
			JS_NewNumberValue(cx,msclock(),vp);
303
304
			break;
		case SYS_PROP_CLOCK_PER_SEC:
305
			JS_NewNumberValue(cx,MSCLOCKS_PER_SEC,vp);
306
			break;
307
308
309
		case SYS_PROP_TIMER:
			JS_NewNumberValue(cx,xp_timer(),vp);
			break;
310

311
		case SYS_PROP_LOCAL_HOSTNAME:
312
			rc=JS_SUSPENDREQUEST(cx);
313
			gethostname(str,sizeof(str));
314
			JS_RESUMEREQUEST(cx, rc);
315
316
			p=str;
			break;
317
318
	}

319
320
321
322
323
324
325
	if(p!=NULL) {	/* string property */
		if((js_str=JS_NewStringCopyZ(cx, p))==NULL)
			return(JS_FALSE);
		*vp = STRING_TO_JSVAL(js_str);
	}

	return(JS_TRUE);
326
327
328
329
330
331
332
333
}

static JSBool js_system_set(JSContext *cx, JSObject *obj, jsval id, jsval *vp)
{
    jsint       tiny;
	scfg_t*		cfg;

	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
rswindell's avatar
rswindell committed
334
		return(JS_FALSE);
335
336
337
338
339

    tiny = JSVAL_TO_INT(id);

	switch(tiny) {
		case SYS_PROP_MISC:
rswindell's avatar
rswindell committed
340
			JS_ValueToInt32(cx, *vp, (int32*)&cfg->sys_misc);
341
342
343
344
345
346
347
348
349
			break;
	}

	return(TRUE);
}


#define SYSOBJ_FLAGS JSPROP_ENUMERATE|JSPROP_READONLY

350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
static jsSyncPropertySpec js_system_properties[] = {
/*		 name,						tinyid,				flags,				ver	*/

	{	"name",						SYS_PROP_NAME,		SYSOBJ_FLAGS,		310  },
	{	"operator",					SYS_PROP_OP,		SYSOBJ_FLAGS,		310  },
	{	"qwk_id",					SYS_PROP_ID,		SYSOBJ_FLAGS,		310  },
	{	"settings",					SYS_PROP_MISC,		JSPROP_ENUMERATE,	310  },
	{	"psname",					SYS_PROP_PSNAME,	SYSOBJ_FLAGS,		310  },
	{	"psnum",					SYS_PROP_PSNUM,		SYSOBJ_FLAGS,		310  },
	{	"inetaddr",					SYS_PROP_INETADDR,	JSPROP_READONLY,	310  },	/* alias */
	{	"inet_addr",				SYS_PROP_INETADDR,	SYSOBJ_FLAGS,		311  },
	{	"location",					SYS_PROP_LOCATION,	SYSOBJ_FLAGS,		310  },
	{	"timezone",					SYS_PROP_TIMEZONE,	SYSOBJ_FLAGS,		310  },
	{	"pwdays",					SYS_PROP_PWDAYS,	SYSOBJ_FLAGS,		310  },
	{	"deldays",					SYS_PROP_DELDAYS,	SYSOBJ_FLAGS,		310  },

	{	"lastuser",					SYS_PROP_LASTUSER		,SYSOBJ_FLAGS,	311  },
	{	"lastuseron",				SYS_PROP_LASTUSERON		,SYSOBJ_FLAGS,	310  },
	{	"freediskspace",			SYS_PROP_FREEDISKSPACE	,SYSOBJ_FLAGS,	310  },
	{	"freediskspacek",			SYS_PROP_FREEDISKSPACEK	,SYSOBJ_FLAGS,	310  },

	{	"nodes",					SYS_PROP_NODES,		SYSOBJ_FLAGS,		310  },
	{	"lastnode",					SYS_PROP_LASTNODE,	SYSOBJ_FLAGS,		310  },

	{	"newuser_password",			SYS_PROP_NEW_PASS		,SYSOBJ_FLAGS,	310  },
	{	"newuser_magic_word",		SYS_PROP_NEW_MAGIC		,SYSOBJ_FLAGS,	310  },
	{	"newuser_level",			SYS_PROP_NEW_LEVEL		,SYSOBJ_FLAGS,	310  },
	{	"newuser_flags1",			SYS_PROP_NEW_FLAGS1		,SYSOBJ_FLAGS,	310  },
	{	"newuser_flags2",			SYS_PROP_NEW_FLAGS2		,SYSOBJ_FLAGS,	310  },
	{	"newuser_flags3",			SYS_PROP_NEW_FLAGS3		,SYSOBJ_FLAGS,	310  },
	{	"newuser_flags4",			SYS_PROP_NEW_FLAGS4		,SYSOBJ_FLAGS,	310  },
	{	"newuser_restrictions",		SYS_PROP_NEW_REST		,SYSOBJ_FLAGS,	310  },
	{	"newuser_exemptions",		SYS_PROP_NEW_EXEMPT		,SYSOBJ_FLAGS,	310  },
	{	"newuser_credits",			SYS_PROP_NEW_CDT		,SYSOBJ_FLAGS,	310  },
	{	"newuser_minutes",			SYS_PROP_NEW_MIN		,SYSOBJ_FLAGS,	310  },
	{	"newuser_command_shell",	SYS_PROP_NEW_SHELL		,SYSOBJ_FLAGS,	310  },
	{	"newuser_editor",			SYS_PROP_NEW_XEDIT		,SYSOBJ_FLAGS,	310  },
	{	"newuser_settings",			SYS_PROP_NEW_MISC		,SYSOBJ_FLAGS,	310  },
	{	"newuser_download_protocol",SYS_PROP_NEW_PROT		,SYSOBJ_FLAGS,	310  },
	{	"newuser_expiration_days",	SYS_PROP_NEW_EXPIRE		,SYSOBJ_FLAGS,	310  },
	{	"newuser_questions",		SYS_PROP_NEW_UQ			,SYSOBJ_FLAGS,	310  },

	{	"expired_level",			SYS_PROP_EXPIRED_LEVEL	,SYSOBJ_FLAGS,	310  },
	{	"expired_flags1",			SYS_PROP_EXPIRED_FLAGS1	,SYSOBJ_FLAGS,	310  },
	{	"expired_flags2",			SYS_PROP_EXPIRED_FLAGS2	,SYSOBJ_FLAGS,	310  },
	{	"expired_flags3",			SYS_PROP_EXPIRED_FLAGS3	,SYSOBJ_FLAGS,	310  },
	{	"expired_flags4",			SYS_PROP_EXPIRED_FLAGS4	,SYSOBJ_FLAGS,	310  },
	{	"expired_restrictions",		SYS_PROP_EXPIRED_REST	,SYSOBJ_FLAGS,	310  },
	{	"expired_exemptions",		SYS_PROP_EXPIRED_EXEMPT	,SYSOBJ_FLAGS,	310  },	
399
400

	/* directories */
401
402
403
404
405
406
407
408
	{	"node_dir",					SYS_PROP_NODE_DIR		,SYSOBJ_FLAGS,	310  },	
	{	"ctrl_dir",					SYS_PROP_CTRL_DIR		,SYSOBJ_FLAGS,	310  },	
	{	"data_dir",					SYS_PROP_DATA_DIR		,SYSOBJ_FLAGS,	310  },	
	{	"text_dir",					SYS_PROP_TEXT_DIR		,SYSOBJ_FLAGS,	310  },	
	{	"temp_dir",					SYS_PROP_TEMP_DIR		,SYSOBJ_FLAGS,	310  },	
	{	"exec_dir",					SYS_PROP_EXEC_DIR		,SYSOBJ_FLAGS,	310  },	
	{	"mods_dir",					SYS_PROP_MODS_DIR		,SYSOBJ_FLAGS,	310  },	
	{	"logs_dir",					SYS_PROP_LOGS_DIR		,SYSOBJ_FLAGS,	310  },	
409

410
	/* filenames */
411
	{	"devnull",					SYS_PROP_DEVNULL		,SYSOBJ_FLAGS,	311  },
412
	{	"temp_path",				SYS_PROP_TEMP_PATH		,SYSOBJ_FLAGS,	312	 },
rswindell's avatar
rswindell committed
413
	{	"cmd_shell",				SYS_PROP_CMD_SHELL		,SYSOBJ_FLAGS,	314	 },
414

415
	/* clock access */
416
417
	{	"clock_ticks",				SYS_PROP_CLOCK			,SYSOBJ_FLAGS,	311  },
	{	"clock_ticks_per_second",	SYS_PROP_CLOCK_PER_SEC	,SYSOBJ_FLAGS,	311  },
rswindell's avatar
rswindell committed
418
	{	"timer",					SYS_PROP_TIMER			,SYSOBJ_FLAGS,	314	 },
419

420
	/* last */
421
	{	"local_host_name",			SYS_PROP_LOCAL_HOSTNAME	,SYSOBJ_FLAGS,	311  },
422
423
424
	{0}
};

425
#ifdef BUILD_JSDOCS
426
427
428
429
static char* sys_prop_desc[] = {
	 "BBS name"
	,"operator name"
	,"system QWK-ID (for QWK packets)"
430
	,"settings bitfield (see <tt>SS_*</tt> in <tt>sbbsdefs.js</tt> for bit definitions)"
431
432
	,"PostLink name"
	,"PostLink system number"
433
	,"Internet address (host or domain name)"
434
	,"location (city, state)"
435
	,"timezone (use <i>system.zonestr()</i> to get string representation)"
436
437
438
	,"days between forced password changes"
	,"days to preserve deleted user records"

439
440
	,"last user record number in user database (includes deleted and inactive user records)"
	,"name of last user to logoff"
441
442
	,"amount of free disk space (in bytes)"
	,"amount of free disk space (in kilobytes)"
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460

	,"total number of BBS nodes"
	,"last displayable node number"

	,"new user password"
	,"new user magic word"
	,"new user level"
	,"new user flag set #1"
	,"new user flag set #2"
	,"new user flag set #3"
	,"new user flag set #4"
	,"new user restriction flags"
	,"new user exemption flags"
	,"new user credits"
	,"new user extra minutes"
	,"new user command shell"
	,"new user external editor"
	,"new user settings"
461
462
463
	,"new user file transfer protocol (command key)"
	,"new user expiration days"
	,"new user questions bitfield (see <tt>UQ_*</tt> in <tt>sbbsdefs.js</tt> for bit definitions)"
464
465
466
467
468
469
470
471
472
473
474

	,"expired user level"
	,"expired user flag set #1"
	,"expired user flag set #2"
	,"expired user flag set #3"
	,"expired user flag set #4"
	,"expired user restriction flags"
	,"expired user exemption flags"

	/* directories */
	,"node directory"
475
	,"control file directory"
476
477
	,"data file directory"
	,"text file directory"
478
	,"temporary file directory"
479
	,"executable file directory"
480
	,"modified modules directory (optional)"
481
	,"log file directory"
482

483
	/* filenames */
484
485
	,"platform-specific \"null\" device filename"
	,"platform-specific temporary file directory"
rswindell's avatar
rswindell committed
486
	,"platform-specific command processor/shell"
487

488
489
490
	/* clock */
	,"amount of elapsed processor time in clock 'ticks'"
	,"number of clock ticks per second"
491
	,"high-resolution timer, in seconds (fractional seconds supported)"
492

493
	/* INSERT new tabled properties here */
494
	,"private host name that uniquely identifies this system on the local network"
495
496

	/* Manually created (non-tabled) properties */
497
	,"public host name that uniquely identifies this system on the Internet (usually the same as <i>system.inet_addr</i>)"
498
499
	,"Synchronet version number (e.g. '3.10')"
	,"Synchronet revision letter (e.g. 'k')"
500
	,"Synchronet alpha/beta designation (e.g. ' beta')"
501
	,"Synchronet full version information (e.g. '3.10k Beta Debug')"
502
	,"Synchronet version notice (includes version and platform)"
503
504
	,"Synchronet version number in decimal (e.g. 31301 for v3.13b)"
	,"Synchronet version number in hexadecimal (e.g. 0x31301 for v3.13b)"
505
506
507
508
509
510
511
512
513
514
	,"platform description (e.g. 'Win32', 'Linux', 'FreeBSD')"
	,"socket library version information"
	,"message base library version information"
	,"compiler used to build Synchronet"
	,"date and time compiled"
	,"Synchronet copyright display"
	,"JavaScript engine version information"
	,"operating system version information"
	,"time/date system was brought online (in time_t format)"

515
	,"array of FidoNet Technology Network (FTN) addresses associated with this system"
516
517
518
519
520
	,NULL
};
#endif


521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
/* System Stats Propertiess */
enum {
	 SYSSTAT_PROP_LOGONS
	,SYSSTAT_PROP_LTODAY
	,SYSSTAT_PROP_TIMEON
	,SYSSTAT_PROP_TTODAY
	,SYSSTAT_PROP_ULS
	,SYSSTAT_PROP_ULB
	,SYSSTAT_PROP_DLS
	,SYSSTAT_PROP_DLB
	,SYSSTAT_PROP_PTODAY
	,SYSSTAT_PROP_ETODAY
	,SYSSTAT_PROP_FTODAY
	,SYSSTAT_PROP_NUSERS

	,SYSSTAT_PROP_TOTALUSERS
	,SYSSTAT_PROP_TOTALFILES
	,SYSSTAT_PROP_TOTALMSGS
	,SYSSTAT_PROP_TOTALMAIL
	,SYSSTAT_PROP_FEEDBACK
rswindell's avatar
rswindell committed
541
542
};

543
544
545
546
547
548
549
static JSBool js_sysstats_get(JSContext *cx, JSObject *obj, jsval id, jsval *vp)
{
    jsint       tiny;
	scfg_t*		cfg;
	stats_t		stats;
	uint		i;
	ulong		l;
deuce's avatar
deuce committed
550
	jsrefcount	rc;
551
552

	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
rswindell's avatar
rswindell committed
553
		return(JS_FALSE);
554
555
556

    tiny = JSVAL_TO_INT(id);

557
	rc=JS_SUSPENDREQUEST(cx);
deuce's avatar
deuce committed
558
	if(!getstats(cfg, 0, &stats)) {
559
		JS_RESUMEREQUEST(cx, rc);
560
		return(FALSE);
deuce's avatar
deuce committed
561
	}
562
	JS_RESUMEREQUEST(cx, rc);
563
564
565

	switch(tiny) {
		case SYSSTAT_PROP_LOGONS:
566
			JS_NewNumberValue(cx,stats.logons,vp);
567
568
			break;
		case SYSSTAT_PROP_LTODAY:
569
			JS_NewNumberValue(cx,stats.ltoday,vp);
570
571
			break;
		case SYSSTAT_PROP_TIMEON:
572
			JS_NewNumberValue(cx,stats.timeon,vp);
573
574
			break;
		case SYSSTAT_PROP_TTODAY:
575
			JS_NewNumberValue(cx,stats.ttoday,vp);
576
577
			break;
		case SYSSTAT_PROP_ULS:
578
			JS_NewNumberValue(cx,stats.uls,vp);
579
580
			break;
		case SYSSTAT_PROP_ULB:
581
			JS_NewNumberValue(cx,stats.ulb,vp);
582
583
			break;
		case SYSSTAT_PROP_DLS:
584
			JS_NewNumberValue(cx,stats.dls,vp);
585
586
			break;
		case SYSSTAT_PROP_DLB:
587
			JS_NewNumberValue(cx,stats.dlb,vp);
588
589
			break;
		case SYSSTAT_PROP_PTODAY:
590
			JS_NewNumberValue(cx,stats.ptoday,vp);
591
592
			break;
		case SYSSTAT_PROP_ETODAY:
593
			JS_NewNumberValue(cx,stats.etoday,vp);
594
595
			break;
		case SYSSTAT_PROP_FTODAY:
596
			JS_NewNumberValue(cx,stats.ftoday,vp);
597
598
			break;
		case SYSSTAT_PROP_NUSERS:
599
			JS_NewNumberValue(cx,stats.nusers,vp);
600
601
602
			break;

		case SYSSTAT_PROP_TOTALUSERS:
603
			rc=JS_SUSPENDREQUEST(cx);
604
			*vp = INT_TO_JSVAL(total_users(cfg));
605
			JS_RESUMEREQUEST(cx, rc);
606
607
608
			break;
		case SYSSTAT_PROP_TOTALMSGS:
			l=0;
609
			rc=JS_SUSPENDREQUEST(cx);
610
611
			for(i=0;i<cfg->total_subs;i++)
				l+=getposts(cfg,i); 
612
			JS_RESUMEREQUEST(cx, rc);
613
			JS_NewNumberValue(cx,l,vp); 
614
615
616
			break;
		case SYSSTAT_PROP_TOTALFILES:
			l=0;
617
			rc=JS_SUSPENDREQUEST(cx);
618
619
			for(i=0;i<cfg->total_dirs;i++)
				l+=getfiles(cfg,i);
620
			JS_RESUMEREQUEST(cx, rc);
621
			JS_NewNumberValue(cx,l,vp);
622
623
			break;
		case SYSSTAT_PROP_TOTALMAIL:
624
			rc=JS_SUSPENDREQUEST(cx);
625
			*vp = INT_TO_JSVAL(getmail(cfg, 0,0));
626
			JS_RESUMEREQUEST(cx, rc);
627
628
			break;
		case SYSSTAT_PROP_FEEDBACK:
629
			rc=JS_SUSPENDREQUEST(cx);
630
			*vp = INT_TO_JSVAL(getmail(cfg, 1,0));
631
			JS_RESUMEREQUEST(cx, rc);
632
633
634
635
636
637
638
639
			break;
	}

	return(TRUE);
}

#define SYSSTAT_FLAGS JSPROP_ENUMERATE|JSPROP_READONLY

640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
static jsSyncPropertySpec js_sysstats_properties[] = {
/*		 name,						tinyid,						flags,			ver	*/

	{	"total_logons",				SYSSTAT_PROP_LOGONS,		SYSSTAT_FLAGS,	310 },
	{	"logons_today",				SYSSTAT_PROP_LTODAY,		SYSSTAT_FLAGS,	310 },
	{	"total_timeon",				SYSSTAT_PROP_TIMEON,		SYSSTAT_FLAGS,	310 },
	{	"timeon_today",				SYSSTAT_PROP_TTODAY,		SYSSTAT_FLAGS,	310 },
	{	"total_files",				SYSSTAT_PROP_TOTALFILES,	SYSSTAT_FLAGS,	310 },
	{	"files_uploaded_today",		SYSSTAT_PROP_ULS,			SYSSTAT_FLAGS,	310 },
	{	"bytes_uploaded_today",		SYSSTAT_PROP_ULB,			SYSSTAT_FLAGS,	310 },
	{	"files_downloaded_today",	SYSSTAT_PROP_DLS,			SYSSTAT_FLAGS,	310 },
	{	"bytes_downloaded_today",	SYSSTAT_PROP_DLB,			SYSSTAT_FLAGS,	310 },
	{	"total_messages",			SYSSTAT_PROP_TOTALMSGS,		SYSSTAT_FLAGS,	310 },
	{	"messages_posted_today",	SYSSTAT_PROP_PTODAY,		SYSSTAT_FLAGS,	310 },
	{	"total_email",				SYSSTAT_PROP_TOTALMAIL,		SYSSTAT_FLAGS,	310 },
	{	"email_sent_today",			SYSSTAT_PROP_ETODAY,		SYSSTAT_FLAGS,	310 },
	{	"total_feedback",			SYSSTAT_PROP_FEEDBACK,		SYSSTAT_FLAGS,	310 },
	{	"feedback_sent_today",		SYSSTAT_PROP_FTODAY,		SYSSTAT_FLAGS,	310 },
	{	"total_users",				SYSSTAT_PROP_TOTALUSERS,	SYSSTAT_FLAGS,	310 },
	{	"new_users_today",			SYSSTAT_PROP_NUSERS,		SYSSTAT_FLAGS,	310 },
660
661
662
	{0}
};

663
#ifdef BUILD_JSDOCS
664
static char* sysstat_prop_desc[] = {
665
666
667
668
669
670
671
672
673
674
675
676
677
	 "total logons"
	,"logons today"
	,"total time used"
	,"time used today"
	,"total files in file bases"
	,"files uploaded today"
	,"bytes uploaded today"
	,"files downloaded today"
	,"bytes downloaded today"
	,"total messages in message bases"
	,"messages posted today"
	,"total messages in mail base"
	,"email sent today"
678
	,"total feedback messages waiting"
679
	,"feedback sent today"
680
	,"total user records (does not include deleted or inactive user records)"
681
	,"new users today"
682
	,NULL
683
684
685
};
#endif

deuce's avatar
deuce committed
686
687
688
689
690
691
692
693
694
695
696
697
698
699
static JSBool js_sysstats_resolve(JSContext *cx, JSObject *obj, jsval id)
{
	char*			name=NULL;

	if(id != JSVAL_NULL)
		name=JS_GetStringBytes(JSVAL_TO_STRING(id));

	return(js_SyncResolve(cx, obj, name, js_sysstats_properties, NULL, NULL, 0));
}

static JSBool js_sysstats_enumerate(JSContext *cx, JSObject *obj)
{
	return(js_sysstats_resolve(cx, obj, JSVAL_NULL));
}
700

701
702
703
704
705
706
707
static JSClass js_sysstats_class = {
     "Stats"				/* name			*/
    ,JSCLASS_HAS_PRIVATE	/* flags		*/
	,JS_PropertyStub		/* addProperty	*/
	,JS_PropertyStub		/* delProperty	*/
	,js_sysstats_get		/* getProperty	*/
	,JS_PropertyStub		/* setProperty	*/
deuce's avatar
deuce committed
708
709
	,js_sysstats_enumerate	/* enumerate	*/
	,js_sysstats_resolve	/* resolve		*/
710
711
712
713
	,JS_ConvertStub			/* convert		*/
	,JS_FinalizeStub		/* finalize		*/
};

714
715
716
717
static JSBool
js_alias(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
{
	char*		p;
718
	char		buf[128];
719
720
	JSString*	js_str;
	scfg_t*		cfg;
deuce's avatar
deuce committed
721
	jsrefcount	rc;
722
723
724
725
726
727
728
729
730
731
732
733
734
735

	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
		return(JS_FALSE);

	if((js_str=JS_ValueToString(cx, argv[0]))==NULL) {
		*rval = INT_TO_JSVAL(0);
		return(JS_TRUE);
	}

	if((p=JS_GetStringBytes(js_str))==NULL) {
		*rval = INT_TO_JSVAL(0);
		return(JS_TRUE);
	}

736
	rc=JS_SUSPENDREQUEST(cx);
737
	p=alias(cfg,p,buf);
738
	JS_RESUMEREQUEST(cx, rc);
739

740
741
	if((js_str = JS_NewStringCopyZ(cx, p))==NULL)
		return(JS_FALSE);
742
743

	*rval = STRING_TO_JSVAL(js_str);
744
745
746
747
748
749
750
751
752
753
	return(JS_TRUE);
}

static JSBool
js_username(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
{
	int32		val;
	char		buf[128];
	JSString*	js_str;
	scfg_t*		cfg;
deuce's avatar
deuce committed
754
755
	char*		cstr;
	jsrefcount	rc;
756

757
758
759
760
761
762
	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
		return(JS_FALSE);

	val=0;
	JS_ValueToInt32(cx,argv[0],&val);

763
	rc=JS_SUSPENDREQUEST(cx);
deuce's avatar
deuce committed
764
	cstr=username(cfg,val,buf);
765
	JS_RESUMEREQUEST(cx, rc);
deuce's avatar
deuce committed
766
	if((js_str = JS_NewStringCopyZ(cx, cstr))==NULL)
767
768
769
		return(JS_FALSE);

	*rval = STRING_TO_JSVAL(js_str);
770
771
772
	return(JS_TRUE);
}

773

774
775
776
777
778
779
static JSBool
js_matchuser(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
{
	char*		p;
	JSString*	js_str;
	scfg_t*		cfg;
780
	BOOL		sysop_alias=TRUE;
deuce's avatar
deuce committed
781
	jsrefcount	rc;
782

783
	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
784
785
786
787
788
789
790
		return(JS_FALSE);

	if((js_str=JS_ValueToString(cx, argv[0]))==NULL) {
		*rval = INT_TO_JSVAL(0);
		return(JS_TRUE);
	}

791
	if(argc>1)
792
		JS_ValueToBoolean(cx,argv[1],&sysop_alias);
793

794
795
796
797
798
	if((p=JS_GetStringBytes(js_str))==NULL) {
		*rval = INT_TO_JSVAL(0);
		return(JS_TRUE);
	}

799
	rc=JS_SUSPENDREQUEST(cx);
800
	*rval = INT_TO_JSVAL(matchuser(cfg,p,sysop_alias));
801
	JS_RESUMEREQUEST(cx, rc);
802
803
804
	return(JS_TRUE);
}

805
806
807
808
809
810
811
812
813
static JSBool
js_matchuserdata(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
{
	char*		p;
	JSString*	js_str;
	int32		offset=0;
	int32		usernumber=0;
	int			len;
	scfg_t*		cfg;
deuce's avatar
deuce committed
814
	jsrefcount	rc;
815
816
817
818
819

	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
		return(JS_FALSE);

	JS_ValueToInt32(cx,argv[0],&offset);
820
	rc=JS_SUSPENDREQUEST(cx);
821
	len=user_rec_len(offset);
822
	JS_RESUMEREQUEST(cx, rc);
823
824
	if(len<0)
		return(JS_FALSE);
825
826
827
828
829
830
831
832
833
834
835
836
837
838

	if((js_str=JS_ValueToString(cx, argv[1]))==NULL) {
		*rval = INT_TO_JSVAL(0);
		return(JS_TRUE);
	}

	if(argc>2)
		JS_ValueToInt32(cx,argv[2],&usernumber);

	if((p=JS_GetStringBytes(js_str))==NULL) {
		*rval = INT_TO_JSVAL(0);
		return(JS_TRUE);
	}

839
	rc=JS_SUSPENDREQUEST(cx);
840
	*rval = INT_TO_JSVAL(userdatdupe(cfg,usernumber,offset,len,p,FALSE /* deleted users */));
841
	JS_RESUMEREQUEST(cx, rc);
842
843
844
	return(JS_TRUE);
}

845
846
847
848
849
850
851
852
static JSBool
js_trashcan(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
{
	char*		str;
	char*		can;
	JSString*	js_str;
	JSString*	js_can;
	scfg_t*		cfg;
deuce's avatar
deuce committed
853
	jsrefcount	rc;
854

855
	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
		return(JS_FALSE);

	if((js_can=JS_ValueToString(cx, argv[0]))==NULL) {
		*rval = BOOLEAN_TO_JSVAL(JS_FALSE);
		return(JS_TRUE);
	}

	if((js_str=JS_ValueToString(cx, argv[1]))==NULL) {
		*rval = BOOLEAN_TO_JSVAL(JS_FALSE);
		return(JS_TRUE);
	}

	if((can=JS_GetStringBytes(js_can))==NULL) {
		*rval = BOOLEAN_TO_JSVAL(JS_FALSE);
		return(JS_TRUE);
	}

	if((str=JS_GetStringBytes(js_str))==NULL) {
		*rval = BOOLEAN_TO_JSVAL(JS_FALSE);
		return(JS_TRUE);
	}

878
	rc=JS_SUSPENDREQUEST(cx);
879
	*rval = BOOLEAN_TO_JSVAL(trashcan(cfg,str,can));	/* user args are reversed */
880
	JS_RESUMEREQUEST(cx, rc);
881
882
883
	return(JS_TRUE);
}

884
885
886
887
888
889
890
static JSBool
js_findstr(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
{
	char*		str;
	char*		fname;
	JSString*	js_str;
	JSString*	js_fname;
deuce's avatar
deuce committed
891
	jsrefcount	rc;
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912

	if((js_fname=JS_ValueToString(cx, argv[0]))==NULL) {
		*rval = BOOLEAN_TO_JSVAL(JS_FALSE);
		return(JS_TRUE);
	}

	if((js_str=JS_ValueToString(cx, argv[1]))==NULL) {
		*rval = BOOLEAN_TO_JSVAL(JS_FALSE);
		return(JS_TRUE);
	}

	if((fname=JS_GetStringBytes(js_fname))==NULL) {
		*rval = BOOLEAN_TO_JSVAL(JS_FALSE);
		return(JS_TRUE);
	}

	if((str=JS_GetStringBytes(js_str))==NULL) {
		*rval = BOOLEAN_TO_JSVAL(JS_FALSE);
		return(JS_TRUE);
	}

913
	rc=JS_SUSPENDREQUEST(cx);
914
	*rval = BOOLEAN_TO_JSVAL(findstr(str,fname));	/* user args are reversed */
915
	JS_RESUMEREQUEST(cx, rc);
916
917
918
919
	return(JS_TRUE);
}


920
921
922
923
static JSBool
js_zonestr(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
{
	JSString*	js_str;
924
	short		zone;
925
	int32		val=0;
926
	scfg_t*		cfg;
deuce's avatar
deuce committed
927
928
	jsrefcount	rc;
	char*		cstr;
929
930
931
932
933

	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
		return(JS_FALSE);

	if(argc<1)
934
		zone=sys_timezone(cfg);
935
936
937
938
	else {
		JS_ValueToInt32(cx,argv[0],&val);
		zone=(short)val;
	}
939

940
	rc=JS_SUSPENDREQUEST(cx);
deuce's avatar
deuce committed
941
	cstr=smb_zonestr(zone,NULL);
942
	JS_RESUMEREQUEST(cx, rc);
deuce's avatar
deuce committed
943
	if((js_str = JS_NewStringCopyZ(cx, cstr))==NULL)
944
		return(JS_FALSE);
945
946
947
948
949

	*rval = STRING_TO_JSVAL(js_str);
	return(JS_TRUE);
}

950
/* Returns a ctime()-like string in the system-preferred time format */
951
952
953
954
static JSBool
js_timestr(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
{
	char		str[128];
955
956
	int32		i=0;
	time_t		t;
957
958
	JSString*	js_str;
	scfg_t*		cfg;
deuce's avatar
deuce committed
959
	jsrefcount	rc;
960
961
962
963
964

	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
		return(JS_FALSE);

	if(argc<1)
965
		i=time(NULL);	/* use current time */
966
	else
967
968
		JS_ValueToInt32(cx,argv[0],&i);
	t=i;
969
	rc=JS_SUSPENDREQUEST(cx);
970
	timestr(cfg,t,str);
971
	JS_RESUMEREQUEST(cx, rc);
972
973
	if((js_str = JS_NewStringCopyZ(cx, str))==NULL)
		return(JS_FALSE);
974
975
976
977
978

	*rval = STRING_TO_JSVAL(js_str);
	return(JS_TRUE);
}

979

980
/* Returns a mm/dd/yy or dd/mm/yy formated string */
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
static JSBool
js_datestr(JSContext *cx, JSObject *obj, uintN argc, jsval *argv, jsval *rval)
{
	char		str[128];
	time_t		t;
	JSString*	js_str;
	scfg_t*		cfg;

	if((cfg=(scfg_t*)JS_GetPrivate(cx,obj))==NULL)
		return(JS_FALSE);

	if(argc<1)
		t=time(NULL);	/* use current time */
	else {
		if(JSVAL_IS_STRING(argv[0])) {	/* convert from string to time_t? */
996
			JS_NewNumberValue(cx,dstrtounix(cfg,JS_GetStringBytes(JS_ValueToString(cx, argv[0]))),rval);
997
998
			return(JS_TRUE);
		}
999
		JS_ValueToInt32(cx,argv[0],(int32*)&t);
1000
	}
For faster browsing, not all history is shown. View entire blame