diff --git a/ctrl/modopts.ini b/ctrl/modopts.ini index 17858a2b0a24ab11eaeea4b0c94983452d13515e..d4d256699d861da7ca0a9bbfbc2356f2bd0cb50c 100644 --- a/ctrl/modopts.ini +++ b/ctrl/modopts.ini @@ -59,6 +59,11 @@ backup_level = 10 [xtrn_sec] +; Set to true to disable execution of prextrn.js and postxtrn.js for external programs +; when they are running as a logon event + disable_xtrnpre_on_logon_event = false + disable_xtrnpost_on_logon_event = false + ; Enable multi-column display (when more than 10 external programs in a section) multicolumn = true ; Sort the list of external programs alphabetically by name diff --git a/ctrl/text.dat b/ctrl/text.dat index a2b4bf512a306bcace791e5175a661b764b99472..9a4594afef769f9cc4fc129022bfb8f7bd47e52e 100644 --- a/ctrl/text.dat +++ b/ctrl/text.dat @@ -1023,4 +1023,5 @@ "\xdc\xdd\xdf\xde" 841 SpinningCursor8 "\xfa\xf9\xfe\xf9" 842 SpinningCursor9 "\1_\1b\1h[\1c@CHECKMARK@\1b] \1yTerminal columns "\ 843 HowManyColumns - "[\1wAuto\1y]: \1n" \ No newline at end of file + "[\1wAuto\1y]: \1n" +"\r\nExternal program not found\r\n" 844 NoXtrnProgram diff --git a/exec/postxtrn.js b/exec/postxtrn.js new file mode 100644 index 0000000000000000000000000000000000000000..7eb3b3e13db3ba1d3d1b7667e64bb331c00eee3b --- /dev/null +++ b/exec/postxtrn.js @@ -0,0 +1,62 @@ +// postxtrn.js + +// External Program Post Module +// These actions execute after an external program is launched via bbs.exec_xtrn() + +// $Id: xtrn_sec.js,v 1.29 2020/05/09 10:11:23 rswindell Exp $ + +"use strict"; + +load("sbbsdefs.js"); + +/* text.dat entries */ +load("text.js"); + +var options, program; + +if((options=load({}, "modopts.js","xtrn_sec")) == null) + options = {}; // default values + +if(options.restricted_user_msg === undefined) + options.restricted_user_msg = bbs.text(R_ExternalPrograms); + +if(options.clear_screen === undefined) + options.clear_screen = true; + +function exec_xtrn_post(program) +{ + if ((options.disable_xtrnpost_on_logon_event) && (bbs.node_action == NODE_LOGN)) { + return; + } + + console.attributes = 0; + console.attributes = LIGHTGRAY; + + load('fonts.js', 'default'); + + if(options.eval_after_exec) + eval(options.eval_after_exec); +} + + +/* main: */ +{ + if(!argv[0]) { + write(bbs.text(NoXtrnProgram)); + } else { + xtrn_area.sec_list.some(function(sec) { + sec.prog_list.some(function (prog) { + if (prog.code.toLowerCase() == argv[0]) { + program = prog; + return true; + } + }); + }); + + if (!program) { + write(bbs.text(NoXtrnProgram)); + } else { + exec_xtrn_post(program); + } + } +} diff --git a/exec/prextrn.js b/exec/prextrn.js new file mode 100644 index 0000000000000000000000000000000000000000..40c0e339c25e8ab9d01d470039053b7d8dc6d1f1 --- /dev/null +++ b/exec/prextrn.js @@ -0,0 +1,73 @@ +// prextrn.js + +// External Program Pre Module +// These actions execute before an external program is launched via bbs.exec_xtrn() + +// $Id: xtrn_sec.js,v 1.29 2020/05/09 10:11:23 rswindell Exp $ + +"use strict"; + +load("sbbsdefs.js"); + +/* text.dat entries */ +load("text.js"); + +var options, program; + +if((options=load({}, "modopts.js","xtrn_sec")) == null) + options = {}; // default values + + +function exec_xtrn_pre(program) +{ + if ((options.disable_xtrnpre_on_logon_event) && (bbs.node_action == NODE_LOGN)) { + return; + } + + if(options.restricted_user_msg === undefined) + options.restricted_user_msg = bbs.text(R_ExternalPrograms); + + if(user.security.restrictions&UFLAG_X) { + write(options.restricted_user_msg); + return; + } + + if(bbs.menu_exists("xtrn/" + program.code)) { + bbs.menu("xtrn/" + program.code); + console.pause(); + console.line_counter=0; + } + + console.attributes = LIGHTGRAY; + + if(options.clear_screen_on_exec) + console.clear(); + + if(options.eval_before_exec) + eval(options.eval_before_exec); + + load('fonts.js', 'xtrn:' + program.code); +} + + +/* main: */ +{ + if(!argv[0]) { + write(bbs.text(NoXtrnProgram)); + } else { + xtrn_area.sec_list.some(function(sec) { + sec.prog_list.some(function (prog) { + if (prog.code.toLowerCase() == argv[0]) { + program = prog; + return true; + } + }); + }); + + if (!program) { + write(bbs.text(NoXtrnProgram)); + } else { + exec_xtrn_pre(program); + } + } +} diff --git a/exec/xtrn_sec.js b/exec/xtrn_sec.js index f312d5e904e21e13c78e8f041bb96e021feff914..b55d3f10cd7262667522f027a47986bd439ebd15 100644 --- a/exec/xtrn_sec.js +++ b/exec/xtrn_sec.js @@ -80,22 +80,6 @@ function sort_by_name(a, b) return 0; } -function exec_xtrn(prog) -{ - console.attributes = LIGHTGRAY; - if(options.clear_screen_on_exec) - console.clear(); - if(options.eval_before_exec) - eval(options.eval_before_exec); - load('fonts.js', 'xtrn:' + prog.code); - bbs.exec_xtrn(prog.code); - console.attributes = 0; - console.attributes = LIGHTGRAY; - load('fonts.js', 'default'); - if(options.eval_after_exec) - eval(options.eval_after_exec); -} - function external_program_menu(xsec) { var i,j; @@ -118,7 +102,7 @@ function external_program_menu(xsec) // If there's only one program available to the user in the section, just run it (or try to) if(options.autoexec && prog_list.length == 1) { - exec_xtrn(prog_list[0]); + bbs.exec_xtrn(prog_list[0].code); break; } @@ -190,11 +174,8 @@ function external_program_menu(xsec) if((i=console.getnum(prog_list.length))<1) break; i--; - if(bbs.menu_exists("xtrn/" + prog_list[i].code)) { - bbs.menu("xtrn/" + prog_list[i].code); - console.line_counter=0; - } - exec_xtrn(prog_list[i]); + + bbs.exec_xtrn(prog_list[i].code); } } diff --git a/src/sbbs2/xtrn_ovl.c b/src/sbbs2/xtrn_ovl.c index 3066305eb9778d1bb7a4bdfbbd4cba62889715ce..c0c3a5493134ae2c6d245d1fb8f46250f5115b63 100644 --- a/src/sbbs2/xtrn_ovl.c +++ b/src/sbbs2/xtrn_ovl.c @@ -1275,7 +1275,6 @@ void exec_xtrn(uint xtrnnum) node_t node; time_t start,end; - if(!chk_ar(xtrn[xtrnnum]->run_ar,useron) || !chk_ar(xtrnsec[xtrn[xtrnnum]->sec]->ar,useron)) { bputs(text[CantRunThatProgram]); diff --git a/src/sbbs3/scfg/scfgsys.c b/src/sbbs3/scfg/scfgsys.c index d6b0e86fc103da75db9adf434a565487250694e8..271e677047111f420cb45751b2716e88064ea9a9 100644 --- a/src/sbbs3/scfg/scfgsys.c +++ b/src/sbbs3/scfg/scfgsys.c @@ -1669,6 +1669,8 @@ void sys_cfg(void) sprintf(opt[i++],"%-16.16s%s","Auto Message",cfg.automsg_mod); sprintf(opt[i++],"%-16.16s%s","Text Section",cfg.textsec_mod); sprintf(opt[i++],"%-16.16s%s","Xtrn Section",cfg.xtrnsec_mod); + sprintf(opt[i++],"%-16.16s%s","Xtrn Prog Pre",cfg.xtrnprogpre_mod); + sprintf(opt[i++],"%-16.16s%s","Xtrn Prog Post",cfg.xtrnprogpost_mod); sprintf(opt[i++],"%-16.16s%s","Read Mail",cfg.readmail_mod); sprintf(opt[i++],"%-16.16s%s","Scan Msgs",cfg.scanposts_mod); sprintf(opt[i++],"%-16.16s%s","Scan Subs",cfg.scansubs_mod); @@ -1696,6 +1698,8 @@ void sys_cfg(void) "`Auto Message` Executed when a user chooses to edit the auto-message\n" "`Text Section` Executed to handle general text file (viewing) section\n" "`Xtrn Section` Executed to handle external programs (doors) section\n" + "`Xtrn Prog Pre` Executed before external programs (doors) run\n" + "`Xtrn Prog Post` Executed after external programs (doors) run\n" "\n" "Full module command-lines may be used for the operations listed below:\n" "\n" @@ -1759,34 +1763,42 @@ void sys_cfg(void) ,cfg.xtrnsec_mod,sizeof(cfg.xtrnsec_mod)-1,K_EDIT); break; case 10: + uifc.input(WIN_MID|WIN_SAV,0,0,"External Program Pre Module" + ,cfg.xtrnprogpre_mod,sizeof(cfg.xtrnprogpre_mod)-1,K_EDIT); + break; + case 11: + uifc.input(WIN_MID|WIN_SAV,0,0,"External Program Post Module" + ,cfg.xtrnprogpost_mod,sizeof(cfg.xtrnprogpost_mod)-1,K_EDIT); + break; + case 12: uifc.input(WIN_MID|WIN_SAV,0,0,"Read Mail Command" ,cfg.readmail_mod,sizeof(cfg.readmail_mod)-1,K_EDIT); break; - case 11: + case 13: uifc.input(WIN_MID|WIN_SAV,0,0,"Scan Msgs Command" ,cfg.scanposts_mod,sizeof(cfg.scanposts_mod)-1,K_EDIT); break; - case 12: + case 14: uifc.input(WIN_MID|WIN_SAV,0,0,"Scan Subs Command" ,cfg.scansubs_mod,sizeof(cfg.scansubs_mod)-1,K_EDIT); break; - case 13: + case 15: uifc.input(WIN_MID|WIN_SAV,0,0,"List Msgs Command" ,cfg.listmsgs_mod,sizeof(cfg.listmsgs_mod)-1,K_EDIT); break; - case 14: + case 16: uifc.input(WIN_MID|WIN_SAV,0,0,"List Logons Command" ,cfg.logonlist_mod,sizeof(cfg.logonlist_mod)-1,K_EDIT); break; - case 15: + case 17: uifc.input(WIN_MID|WIN_SAV,0,0,"List Nodes Command" ,cfg.nodelist_mod,sizeof(cfg.nodelist_mod)-1,K_EDIT); break; - case 16: + case 18: uifc.input(WIN_MID|WIN_SAV,0,0,"Who's Online Command" ,cfg.whosonline_mod,sizeof(cfg.whosonline_mod)-1,K_EDIT); break; - case 17: + case 19: uifc.input(WIN_MID|WIN_SAV,0,0,"Private Message Command" ,cfg.privatemsg_mod,sizeof(cfg.privatemsg_mod)-1,K_EDIT); break; diff --git a/src/sbbs3/scfgdefs.h b/src/sbbs3/scfgdefs.h index 84d28f8a83df032c7764104ac140d567115905b3..37433c554a9442078705145d909ccb77946813cd 100644 --- a/src/sbbs3/scfgdefs.h +++ b/src/sbbs3/scfgdefs.h @@ -610,6 +610,8 @@ typedef struct char whosonline_mod[LEN_CMD+1]; char privatemsg_mod[LEN_CMD+1]; char logonlist_mod[LEN_CMD+1]; + char xtrnprogpre_mod[LEN_MODNAME+1]; /* External Program pre-execution module */ + char xtrnprogpost_mod[LEN_MODNAME+1]; /* External Program post-execution module */ char scfg_cmd[LEN_CMD+1]; /* SCFG command line - unused! */ uchar smb_retry_time; /* Seconds to retry on SMBs */ uint16_t sec_warn; /* Seconds before inactivity warning */ diff --git a/src/sbbs3/scfglib1.c b/src/sbbs3/scfglib1.c index 2b8e2210a647c550ede4a9fc0c8615727378c127..543b5306e752b9041f3f9014be12870ec319881d 100644 --- a/src/sbbs3/scfglib1.c +++ b/src/sbbs3/scfglib1.c @@ -291,7 +291,15 @@ BOOL read_main_cfg(scfg_t* cfg, char* error) get_str(cfg->logonlist_mod,instream); if(cfg->logonlist_mod[0] == '\xff') SAFECOPY(cfg->logonlist_mod, "logonlist"); - for(i=0;i<126;i++) /* unused - initialized to 0xff */ + + get_str(cfg->xtrnprogpre_mod,instream); + if(cfg->xtrnprogpre_mod[0] == '\xff') + SAFECOPY(cfg->xtrnprogpre_mod, "prextrn"); + get_str(cfg->xtrnprogpost_mod,instream); + if(cfg->xtrnprogpost_mod[0] == '\xff') + SAFECOPY(cfg->xtrnprogpost_mod, "postxtrn"); + + for(i=0;i<117;i++) /* unused - initialized to 0xff */ get_int(n,instream); get_int(cfg->user_backup_level,instream); diff --git a/src/sbbs3/scfgsave.c b/src/sbbs3/scfgsave.c index 85877f9dd8d60f4dadfe2032e22cd44cb7b200c6..e891cb0aa21a4f80c4e162320ed13c9b42ded026 100644 --- a/src/sbbs3/scfgsave.c +++ b/src/sbbs3/scfgsave.c @@ -261,8 +261,12 @@ BOOL DLLCALL write_main_cfg(scfg_t* cfg, int backup_level) put_str(cfg->whosonline_mod, stream); put_str(cfg->privatemsg_mod, stream); put_str(cfg->logonlist_mod, stream); + + put_str(cfg->xtrnprogpre_mod,stream); + put_str(cfg->xtrnprogpost_mod,stream); + n=0xffff; - for(i=0;i<126;i++) + for(i=0;i<117;i++) put_int(n,stream); put_int(cfg->user_backup_level,stream); diff --git a/src/sbbs3/text.h b/src/sbbs3/text.h index 0578967d3928e2c284ada20927740b0b16c097e7..6e54d190d1add14ec1d1b4d1a568dfa891e52569 100644 --- a/src/sbbs3/text.h +++ b/src/sbbs3/text.h @@ -854,6 +854,7 @@ enum { ,SpinningCursor8 ,SpinningCursor9 ,HowManyColumns + ,NoXtrnProgram ,TOTAL_TEXT }; diff --git a/src/sbbs3/text_defaults.c b/src/sbbs3/text_defaults.c index 9261f22165e9060c2e1dfa88a8dd8b797021afb3..a9428805cee30ee02604dbc5a0993576d24fd892 100644 --- a/src/sbbs3/text_defaults.c +++ b/src/sbbs3/text_defaults.c @@ -1385,4 +1385,5 @@ const char * const text_defaults[TOTAL_TEXT]={ ,"\xfa\xf9\xfe\xf9" // 842 SpinningCursor9 ,"\x01\x5f\x01\x62\x01\x68\x5b\x01\x63\x40\x43\x48\x45\x43\x4b\x4d\x41\x52\x4b\x40\x01\x62\x5d\x20\x01\x79\x54\x65\x72\x6d\x69\x6e" "\x61\x6c\x20\x63\x6f\x6c\x75\x6d\x6e\x73\x20\x5b\x01\x77\x41\x75\x74\x6f\x01\x79\x5d\x3a\x20\x01\x6e" // 843 HowManyColumns + ,"\x0d\x0a\x4e\x6f\x20\x65\x78\x74\x65\x72\x6e\x61\x6c\x20\x70\x72\x6f\x67\x72\x61\x6d\x73\x20\x61\x76\x61\x69\x6c\x61\x62\x6c\x65\x0d\x0a" // 844 NoXtrnProgram }; diff --git a/src/sbbs3/xtrn_sec.cpp b/src/sbbs3/xtrn_sec.cpp index d6654bcb95c6e47f5c2135571e4ab4ed279f189e..f8260144131f1f1da19375698c9163ca28ad2fcd 100644 --- a/src/sbbs3/xtrn_sec.cpp +++ b/src/sbbs3/xtrn_sec.cpp @@ -1487,6 +1487,11 @@ bool sbbs_t::exec_xtrn(uint xtrnnum) subtract_cdt(&cfg,&useron,cfg.xtrn[xtrnnum]->cost); } + if(cfg.xtrnprogpre_mod[0] != '\0') { + SAFEPRINTF2(str, "%s %s", cfg.xtrnprogpre_mod,cfg.xtrn[xtrnnum]->code); + exec_bin(str, &main_csi); + } + if(!(cfg.xtrn[xtrnnum]->misc&MULTIUSER)) { for(i=1;i<=cfg.sys_nodes;i++) { getnodedat(i,&node,0); @@ -1652,6 +1657,11 @@ bool sbbs_t::exec_xtrn(uint xtrnnum) else lncntr = 0; + if(cfg.xtrnprogpost_mod[0] != '\0') { + SAFEPRINTF2(str, "%s %s", cfg.xtrnprogpost_mod,cfg.xtrn[xtrnnum]->code); + exec_bin(str, &main_csi); + } + return(true); }