/* ARISA - Admin Interface - Packlist Menu * Copyright (C) 2003 Carl Ritson * * 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. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA */ static int is_packlist_new(packlist_t *p) { int i; LOCK(global); for(i = 0; i < global->no_packlists; ++i) { if(global->packlists[i] == p) { UNLOCK(global); return 0; } } UNLOCK(global); return 1; } /** Pool Menu Commands **/ MENU_HELPER(cmd_packlists_helper) { int i,j; for(j = 0; args[1][j] != '\0'; ++j) { if(args[1][j] == '?') break; } LOCK(ac->user); if(ac->user->packlists != NULL && !(PRIV_ISSET(ac->user,PRIV_ALL_PACKLISTS) || PRIV_ISSET(ac->user,PRIV_PACKLISTS))) { for(i = 0; i < ac->user->no_packlists; ++i) { LOCK(ac->user->packlists[i]); if(ac->user->packlists[i]->deleted == 0 && (j == 0 || strncasecmp(ac->user->packlists[i]->name,args[1],j) == 0)) admin_msg(ac,"%s",ac->user->packlists[i]->name); UNLOCK(ac->user->packlists[i]); } UNLOCK(ac->user); } else { UNLOCK(ac->user); LOCK(global); for(i = 0; i < global->no_packlists; ++i) { LOCK(global->packlists[i]); if(global->packlists[i]->deleted == 0 && (j == 0 || strncasecmp(global->packlists[i]->name,args[1],j) == 0)) admin_msg(ac,"%s",global->packlists[i]->name); UNLOCK(global->packlists[i]); } UNLOCK(global); } } MENU_CMD(cmd_packlist_delete) { packlist_t *p = (packlist_t *)ins->data; if(!is_packlist_new(p)) { packlist_del(p); LOCK(p); admin_msg(ac,"Packlist %s Deleted",p->name); UNLOCK(p); } return RET_UP; } MENU_CMD(cmd_packlist_rename) { char buffer[96]; packlist_t *p = (packlist_t *)ins->data; int i; LOCK(global); for(i = 0; i < global->no_packlists; ++i) { if(global->packlists[i] != p) { LOCK(global->packlists[i]); if(global->packlists[i]->deleted == 0 && strcasecmp(global->packlists[i]->name,args[1]) == 0) { UNLOCK(global->packlists[i]); UNLOCK(global); admin_msg(ac,"Rename Failed, Packlist %s Already Exists",args[1]); return 0; } UNLOCK(global->packlists[i]); } } LOCK(p); if(p->name != NULL) xfree(p->name); p->name = xstrdup(args[1]); UNLOCK(p); UNLOCK(global); if(ins->prompt != NULL && ins->free_prompt != 0) xfree(ins->prompt); snprintf(buffer,sizeof(buffer),"Packlist: %s",args[1]); ins->prompt = xstrdup(buffer); ins->free_prompt = 1; admin_output_prompt(ac); return 0; } MENU_CMD(cmd_packlist_save) { packlist_t *p = (packlist_t *)ins->data; int ret; if(is_packlist_new(p)) { LOCK(p); if(p->queue != NULL) { LOCK(p->queue); if(p->queue->deleted != 0) { UNLOCK(p->queue); p->queue = NULL; } else UNLOCK(p->queue); } if(p->queue != NULL) { UNLOCK(p); ret = packlist_add(p); if(ret == 0) { ins->free = NULL; LOCK(p); LOCK(p->queue); if(p->queue->deleted != 0) { UNLOCK(p->queue); UNLOCK(p); packlist_del(p); admin_msg(ac,"Queue was deleted as Packlist was saved, Packlist has now also been deleted."); return RET_UP; } UNLOCK(p->queue); UNLOCK(p); admin_msg(ac,"Successfully Saved."); } else admin_msg(ac,"Save Failed."); } else { UNLOCK(p); admin_msg(ac,"Unable to save no Queue set."); } } else admin_msg(ac,"Packlist already saved."); return 0; } MENU_CMD(cmd_packlist_settings) { packlist_t *p = (packlist_t *)ins->data; if(no_args == 1) { pqueue_t settings; pqueue_init(&settings,0); LOCK(p); if(p->queue != NULL) { LOCK(p->queue); pqueue_push_back(&settings, value_string("queue",p->queue->name)); UNLOCK(p->queue); } else { pqueue_push_back(&settings, value_string("queue","not set")); } if(p->type == LIST_CHAT) { interface_t *intf = p->chat_interface; UNLOCK(p); if(intf != NULL) { LOCK(intf); pqueue_push_back(&settings, value_string("chat-interface",intf->name)); UNLOCK(intf); } else { pqueue_push_back(&settings, value_string("chat-interface","not set")); } } else UNLOCK(p); packlist_read_settings(p,&settings); LOCK(p); output_settings(ac,"-- Packlist Settings for %s --", p->name,&settings); UNLOCK(p); } else if(strncasecmp(args[1],"q",1) == 0 && no_args >= 3) { if(strchr(args[2],'?') != NULL) { cmd_queues_helper(ins,ac,args,no_args); } else { queue_t *q = queue_find(args[2]); if(q != NULL) { LOCK(p); LOCK(q); if(q->deleted == 0) p->queue = q; UNLOCK(q); UNLOCK(p); } else admin_msg(ac,"Invalid queue %s.",args[2]); } } else if(strncasecmp(args[1],"ch",2) == 0 && no_args >= 3) { if(strcmp(args[2],"-") == 0) { LOCK(p); p->chat_interface = NULL; UNLOCK(p); } else { interface_t *i = interface_find(args[2]); if(i != NULL) { LOCK(i); if(i->deleted != 0 || i->type != INTERFACE_CHAT) { UNLOCK(i); i = NULL; } else UNLOCK(i); } if(i != NULL) { LOCK(p); p->chat_interface = i; UNLOCK(p); LOCK(i); if(i->deleted != 0) { UNLOCK(i); LOCK(p); p->chat_interface = NULL; UNLOCK(p); } else UNLOCK(i); } else admin_msg(ac,"Invalid chat interface: %s.", args[2]); } } else if(no_args >= 3) { if(packlist_apply_setting(p,args[1],args[2]) == -1) admin_msg(ac,"Invalid setting: %s",args[1]); } else admin_msg(ac,"%s [ ]",args[0]); return 0; } // declared in settings_menu.c static int cmd_ignore_list(acontext_t *ac, ignore_list_t *l, char **args, int no_args); MENU_CMD(cmd_packlist_ignore_list) { packlist_t *p = (packlist_t *)ins->data; int ret; LOCK(p); ret = cmd_ignore_list(ac,p->ignore_list,args,no_args); UNLOCK(p); return ret; } MENU_CMD(cmd_packlist_taglines) { packlist_t *p = (packlist_t *)ins->data; int ret; LOCK(p); ret = cmd_strarr(ac,&p->taglines,&p->no_taglines,args,no_args); UNLOCK(p); return ret; } MENU_CMD(cmd_packlist_dirs) { packlist_t *p = (packlist_t *)ins->data; int ret; LOCK(p); ret = cmd_strarr(ac,&p->dirs,&p->no_dirs,args,no_args); UNLOCK(p); return ret; } MENU_CMD(cmd_packlist_filters) { packlist_t *p = (packlist_t *)ins->data; int ret; LOCK(p); ret = cmd_strarr(ac,&p->filters,&p->no_filters,args,no_args); UNLOCK(p); return ret; } MENU_CMD(cmd_packlist_access) { packlist_t *p = (packlist_t *)ins->data; char title[128]; access_t *acc; LOCK(p); snprintf(title,sizeof(title),"Packlist %s",p->name); if(p->access == NULL && no_args > 1) p->access = alloc_access(); acc = p->access; UNLOCK(p); return cmd_access_list(ac,acc,title,args,no_args); } MENU_CMD(cmd_packlist_info) { packlist_t *p = (packlist_t *)ins->data; if(no_args == 1) { char buffer[32]; unsigned long long size; unsigned long gets; int i; LOCK(p); admin_msg(ac,"-- Packlist %s --",p->name); for(i = 0,size = 0,gets = 0; i < p->no_packs; ++i) { RLOCK(p->packs[i]); size += (unsigned long long) p->packs[i]->size; gets += p->packs[i]->no_gets; RUNLOCK(p->packs[i]); } admin_msg(ac,"Offering: %d Packs, %s",p->no_packs, format_bytes(buffer,sizeof(buffer),size,1)); admin_msg(ac,"Total Packs Sent: %lu",gets); admin_msg(ac,"Last Scan: %s", p->last_scan == 0 ? "Unknown" : timestr(p->last_scan,buffer,sizeof(buffer))); if(p->nolist != 0 && p->nolist > xtime()) { if(p->nolist != TIME_MAX) admin_msg(ac,"No List Till: %s (Reason: %s)", timestr(p->nolist,buffer, sizeof(buffer)), p->nolist_reason != NULL ? p->nolist_reason : ""); else admin_msg(ac,"Permanent No List (Reason: %s)", p->nolist_reason != NULL ? p->nolist_reason : ""); } if(p->nosend != 0 && p->nosend > xtime()) { if(p->nosend != TIME_MAX) admin_msg(ac,"No Send Till: %s (Reason: %s)", timestr(p->nosend,buffer, sizeof(buffer)), p->nosend_reason != NULL ? p->nosend_reason : ""); else admin_msg(ac,"Permanent No Send (Reason: %s)", p->nosend_reason != NULL ? p->nosend_reason : ""); } UNLOCK(p); } else if(tolower(args[1][0]) == 'p') { pool_t *pool; LOCK(p); if(p->queue != NULL) { LOCK(p->queue); pool = p->queue->pool; UNLOCK(p->queue); UNLOCK(p); cmd_pool_show_info(ac,pool); } else { UNLOCK(p); admin_msg(ac,"No Queue Set"); } } else if(tolower(args[1][0]) == 'q') { queue_t *q; LOCK(p); if(p->queue != NULL) { q = p->queue; UNLOCK(p); cmd_queue_show_info(ac,q); } else { UNLOCK(p); admin_msg(ac,"No Queue Set"); } } else admin_msg(ac,"%s []",args[0]); return 0; } MENU_CMD(cmd_packlist_nolist) { packlist_t *p = (packlist_t *)ins->data; long sec = strtol(args[1],NULL,10); LOCK(p); if(sec == -1) p->nolist = TIME_MAX; else if(sec > 0) p->nolist = xtime() + sec; else p->nolist = 0; if(p->nolist_reason != NULL) xfree(p->nolist_reason); if(p->nolist != 0 && no_args > 2) p->nolist_reason = xstrdup(args[2]); else p->nolist_reason = NULL; UNLOCK(p); return 0; } MENU_CMD(cmd_packlist_nosend) { packlist_t *p = (packlist_t *)ins->data; long sec = strtol(args[1],NULL,10); LOCK(p); if(sec == -1) p->nosend = TIME_MAX; else if(sec > 0) p->nosend = xtime() + sec; else p->nosend = 0; if(p->nosend_reason != NULL) xfree(p->nosend_reason); if(p->nosend != 0 && no_args > 2) p->nosend_reason = xstrdup(args[2]); else p->nosend_reason = NULL; UNLOCK(p); return 0; } MENU_CMD(cmd_packlist_sq_add) { packlist_t *p = (packlist_t *)ins->data; char buffer[96]; network_t *n; send_t *s; int i; if(no_args >= 5) { n = irc_network_find(args[2]); if(n != NULL) { LOCK(p); if(p->queue == NULL) { UNLOCK(p); admin_msg(ac,"Queue Not Set"); return 0; } i = atoi(args[4]); if(i > 0 && i <= p->no_packs) { queue_t *queue = p->queue; s = alloc_send(); s->network = n; s->nick = xstrdup(args[3]); s->pack = pack_clone(p->packs[i-1]); s->queue = p->queue; s->retries = p->retries; if(tolower(args[0][0]) == 's') { UNLOCK(p); if(queue_enqueue(queue,s,SEND_FORCE,NULL) == -1) { admin_msg(ac,"Failed to add send"); free_send(s); } } else { /* strcasecmp(args[0],"queues") == 0 */ UNLOCK(p); if(queue_enqueue(queue,s,QUEUE_NO_ULIMIT|QUEUE_NO_CLIMIT,NULL) == -1) { admin_msg(ac,"Failed to add queue"); free_send(s); } } snprintf(buffer,sizeof(buffer),"USERHOST %s",args[3]); irc_send_raw(n,buffer); } else { UNLOCK(p); admin_msg(ac,"Invalid Pack Number: %d",i); } } else admin_msg(ac,"Invalid Network: %s",args[2]); } else if(no_args == 3) { if(strchr(args[2],'?') != NULL) cmd_networks_helper(ins,ac,args,no_args); else admin_msg(ac,"%s add ", args[0]); } else admin_msg(ac,"%s add ",args[0]); return 0; } MENU_CMD(cmd_packlist_sq) { packlist_t *p = (packlist_t *)ins->data; unsigned long privs; queue_t *queue; pool_t *pool; int ret = RET_OK; LOCK(p); if(p->queue == NULL) { UNLOCK(p); admin_msg(ac,"Queue Not Set"); return 0; } queue = p->queue; LOCK(p->queue); pool = p->queue->pool; UNLOCK(p->queue); UNLOCK(p); LOCK(ac->user); privs = ac->user->uprivs; UNLOCK(ac->user); if(no_args >= 2) { if(tolower(args[1][0]) == 'd' || tolower(args[1][0]) == 'c') { if(PRIV_U_ISSET(privs,PRIV_SEND_DEL)) { if(tolower(args[0][0]) == 's') ret = cmd_pool_sends_p(pool,ac,args,no_args); else /* strcasecmp(args[0],"queues") == 0 */ ret = cmd_queue_queues_q(queue,ac,args,no_args); } else admin_msg(ac,"Insufficient Privileges"); } else if(tolower(args[1][0]) == 'a' || tolower(args[1][0]) == 'o') { if(PRIV_U_ISSET(privs,PRIV_SEND_ADD)) ret = CHAIN_CMD(cmd_packlist_sq_add); else admin_msg(ac,"Insufficient Privileges"); } else if(PRIV_U_ISSET(privs,PRIV_SEND_MOD)) { if(tolower(args[0][0]) == 's') ret = cmd_pool_sends_p(pool,ac,args,no_args); else /* strcasecmp(args[0],"queues") == 0 */ ret = cmd_queue_queues_q(queue,ac,args,no_args); } else admin_msg(ac,"Insufficient Privileges"); } else { if(tolower(args[0][0]) == 's') ret = cmd_pool_sends_p(pool,ac,args,no_args); else /* strcasecmp(args[0],"queues") == 0 */ ret = cmd_queue_queues_q(queue,ac,args,no_args); } return ret; } MENU_CMD(cmd_packlist_packs) { packlist_t *p = (packlist_t *)ins->data; unsigned long privs; colourtype_t colour; LOCK(ac->user); privs = ac->user->uprivs; UNLOCK(ac->user); colour = ac->colour; if(no_args == 1) { packlist_xdl_body(p,ac->msgqueue,colour,"",""); } else if(tolower(args[1][0]) == 'a') { if(PRIV_U_ISSET(privs,PRIV_PACK_ADD)) { if(no_args >= 3) { char pathbuf[512],fn[512]; char **dirs; struct stat sdata; int i,ret = -1,no_dirs; clean_ds_path(args[2],fn,sizeof(fn)); LOCK(p); dirs = strarr_dup(p->dirs,p->no_dirs,&no_dirs); UNLOCK(p); for(i = 0; i < no_dirs && ret != 0; ++i) { snprintf(pathbuf,sizeof(pathbuf), "%s/%s",dirs[i],fn); ret = stat(pathbuf,&sdata); if(ret == 0 && S_ISREG(sdata.st_mode)) ret = pack_add_file(p,pathbuf, NULL,&sdata,NULL); else ret = -1; } if(dirs != NULL) strarr_free(&dirs,&no_dirs); if(ret == 0) { if(no_args >= 4) { LOCK(p); for(i = (p->no_packs-1),ret = 0; i >= 0 && !ret; --i) { WLOCK(p->packs[i]); if(strcmp(p->packs[i]->file,pathbuf) == 0) { if(p->packs[i]->label != NULL) xfree(p->packs[i]->label); p->packs[i]->label = xstrdup(args[3]); ret = 1; } WUNLOCK(p->packs[i]); } UNLOCK(p); } admin_msg(ac,"Pack Added"); } else admin_msg(ac,"Error Occured Adding: \"%s\"",fn); } else admin_msg(ac,"%s add [