00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026 #ifdef HAVE_DIRENT_H
00027 # include <dirent.h>
00028 # define NAMLEN(dirent) strlen((dirent)->d_name)
00029 #else
00030 # define dirent direct
00031 # define NAMLEN(dirent) (dirent)->d_namlen
00032 # ifdef HAVE_SYS_NDIR_H
00033 # include <sys/ndir.h>
00034 # endif
00035 # ifdef HAVE_SYS_DIR_H
00036 # include <sys/dir.h>
00037 # endif
00038 # ifdef HAVE_NDIR_H
00039 # include <ndir.h>
00040 # endif
00041 #endif
00042
00043 #include "src/stat.h"
00044
00045
00046
00047
00048 static int too_many_filers()
00049 {
00050 int i, n = 0;
00051
00052 if (dcc_users == 0)
00053 return 0;
00054 for (i = 0; i < dcc_total; i++)
00055 if (dcc[i].type == &DCC_FILES)
00056 n++;
00057 return (n >= dcc_users);
00058 }
00059
00060
00061
00062 static void add_file(char *dir, char *file, char *nick)
00063 {
00064 FILE *f;
00065
00066
00067
00068
00069 if (!strncmp(dccdir, dir, strlen(dccdir)) &&
00070 (f = filedb_open(&dir[strlen(dccdir)], 2))) {
00071 filedb_add(f, file, nick);
00072 filedb_close(f);
00073 }
00074 }
00075
00076 static int welcome_to_files(int idx)
00077 {
00078 struct flag_record fr = { FR_GLOBAL | FR_CHAN, 0, 0, 0, 0, 0 };
00079 FILE *f;
00080 char *p = get_user(&USERENTRY_DCCDIR, dcc[idx].user);
00081
00082 dprintf(idx, "\n");
00083 if (fr.global &USER_JANITOR)
00084 fr.global |=USER_MASTER;
00085
00086
00087
00088
00089 if (!(dcc[idx].status & STAT_CHAT))
00090 show_motd(idx);
00091 sub_lang(idx, FILES_WELCOME);
00092 sub_lang(idx, FILES_WELCOME1);
00093 if (p)
00094 strcpy(dcc[idx].u.file->dir, p);
00095 else
00096 dcc[idx].u.file->dir[0] = 0;
00097
00098 f = filedb_open(dcc[idx].u.file->dir, 0);
00099 if (f == NULL) {
00100 dcc[idx].u.file->dir[0] = 0;
00101 f = filedb_open(dcc[idx].u.file->dir, 0);
00102 if (f == NULL) {
00103 dprintf(idx, FILES_BROKEN);
00104 dprintf(idx, FILES_INVPATH);
00105 dprintf(idx, "\n\n");
00106 dccdir[0] = 0;
00107 chanout_but(-1, dcc[idx].u.file->chat->channel,
00108 "*** %s rejoined the party line.\n", dcc[idx].nick);
00109 botnet_send_join_idx(idx, dcc[idx].u.file->chat->channel);
00110 return 0;
00111 }
00112 }
00113 filedb_close(f);
00114 dprintf(idx, "%s: /%s\n\n", FILES_CURDIR, dcc[idx].u.file->dir);
00115 return 1;
00116 }
00117
00118 static void cmd_optimize(int idx, char *par)
00119 {
00120 struct userrec *u = get_user_by_handle(userlist, dcc[idx].nick);
00121 FILE *fdb = NULL;
00122 char *p = NULL;
00123
00124 putlog(LOG_FILES, "*", "files: #%s# optimize", dcc[idx].nick);
00125 p = get_user(&USERENTRY_DCCDIR, u);
00126
00127 if (p) {
00128 fdb = filedb_open(p, 1);
00129 if (!fdb) {
00130 set_user(&USERENTRY_DCCDIR, u, NULL);
00131 p = NULL;
00132 }
00133 }
00134 if (!p)
00135 fdb = filedb_open("", 1);
00136 if (!fdb) {
00137 dprintf(idx, FILES_ILLDIR);
00138 return;
00139 }
00140 filedb_close(fdb);
00141 dprintf(idx, "Current directory is now optimized.\n");
00142 }
00143
00144
00145
00146
00147
00148
00149 static int resolve_dir(char *current, char *change, char **real, int idx)
00150 {
00151 char *elem = NULL, *s = NULL, *new = NULL, *work = NULL, *p = NULL;
00152 FILE *fdb = NULL;
00153 DIR *dir = NULL;
00154 filedb_entry *fdbe = NULL;
00155 struct flag_record user = { FR_GLOBAL | FR_CHAN, 0, 0, 0, 0, 0 },
00156 req = { FR_GLOBAL | FR_CHAN, 0, 0, 0, 0, 0 };
00157
00158 *real = NULL;
00159 malloc_strcpy(*real, current);
00160 if (!change[0])
00161 return 1;
00162 new = nmalloc(strlen(change) + 2);
00163 strcpy(new, change);
00164 if (new[0] == '/') {
00165
00166 (*real)[0] = 0;
00167 strcpy(new, &new[1]);
00168 }
00169
00170 strcat(new, "/");
00171 p = strchr(new, '/');
00172 while (p) {
00173 *p = 0;
00174 p++;
00175 malloc_strcpy(elem, new);
00176 strcpy(new, p);
00177 if (!elem[0] || !strcmp(elem, ".")) {
00178 p = strchr(new, '/');
00179 continue;
00180 } else if (!strcmp(elem, "..")) {
00181
00182 p = strrchr(*real, '/');
00183 if (p == NULL) {
00184
00185 if (!(*real)[0]) {
00186 my_free(elem);
00187 my_free(new);
00188 malloc_strcpy(*real, current);
00189 return 0;
00190 }
00191 (*real)[0] = 0;
00192 } else
00193 *p = 0;
00194 } else {
00195
00196 fdb = filedb_open(*real, 0);
00197 if (!fdb) {
00198
00199 my_free(elem);
00200 my_free(new);
00201 malloc_strcpy(*real, current);
00202 return 0;
00203 }
00204 filedb_readtop(fdb, NULL);
00205 fdbe = filedb_matchfile(fdb, ftell(fdb), elem);
00206 filedb_close(fdb);
00207 if (!fdbe) {
00208
00209 my_free(elem);
00210 my_free(new);
00211 my_free(s);
00212 malloc_strcpy(*real, current);
00213 return 0;
00214 }
00215 if (!(fdbe->stat & FILE_DIR) || fdbe->sharelink) {
00216
00217 free_fdbe(&fdbe);
00218 my_free(elem);
00219 my_free(new);
00220 my_free(s);
00221 malloc_strcpy(*real, current);
00222 return 0;
00223 }
00224 if (idx >= 0)
00225 get_user_flagrec(dcc[idx].user, &user, fdbe->chan);
00226 else
00227 user.global = USER_OWNER | USER_BOT | USER_MASTER | USER_OP |
00228 USER_FRIEND;
00229
00230 if (fdbe->flags_req) {
00231 break_down_flags(fdbe->flags_req, &req, NULL);
00232 if (!flagrec_ok(&req, &user)) {
00233 free_fdbe(&fdbe);
00234 my_free(elem);
00235 my_free(new);
00236 my_free(s);
00237 malloc_strcpy(*real, current);
00238 return 0;
00239 }
00240 }
00241 free_fdbe(&fdbe);
00242 malloc_strcpy(s, *real);
00243 if (s[0] && s[strlen(s) - 1] != '/') {
00244 s = nrealloc(s, strlen(s) + 2);
00245 strcat(s, "/");
00246 }
00247 work = nmalloc(strlen(s) + strlen(elem) + 1);
00248 sprintf(work, "%s%s", s, elem);
00249 malloc_strcpy(*real, work);
00250 s = nrealloc(s, strlen(dccdir) + strlen(*real) + 1);
00251 sprintf(s, "%s%s", dccdir, *real);
00252 }
00253 p = strchr(new, '/');
00254 }
00255 my_free(new);
00256 if (elem)
00257 my_free(elem);
00258 if (work)
00259 my_free(work);
00260
00261 s = nrealloc(s, strlen(dccdir) + strlen(*real) + 1);
00262 sprintf(s, "%s%s", dccdir, *real);
00263 dir = opendir(s);
00264 my_free(s);
00265 if (!dir)
00266 return 0;
00267 closedir(dir);
00268 return 1;
00269 }
00270
00271 static void incr_file_gots(char *ppath)
00272 {
00273 char *p, *path = NULL, *destdir = NULL, *fn = NULL;
00274 filedb_entry *fdbe;
00275 FILE *fdb;
00276
00277
00278
00279
00280 if ((ppath[0] == '*') || (ppath[0] == '/'))
00281 return;
00282 malloc_strcpy(path, ppath);
00283 p = strrchr(path, '/');
00284 if (p != NULL) {
00285 *p = 0;
00286 malloc_strcpy(destdir, path);
00287 malloc_strcpy(fn, p + 1);
00288 *p = '/';
00289 } else {
00290 malloc_strcpy(destdir, "");
00291 malloc_strcpy(fn, path);
00292 }
00293 fdb = filedb_open(destdir, 0);
00294 if (!fdb) {
00295 my_free(path);
00296 my_free(destdir);
00297 my_free(fn);
00298 return;
00299 }
00300 my_free(path);
00301 my_free(destdir);
00302 filedb_readtop(fdb, NULL);
00303 fdbe = filedb_matchfile(fdb, ftell(fdb), fn);
00304 my_free(fn);
00305 if (fdbe) {
00306 fdbe->gots++;
00307 filedb_updatefile(fdb, fdbe->pos, fdbe, UPDATE_HEADER);
00308 free_fdbe(&fdbe);
00309 }
00310 filedb_close(fdb);
00311 }
00312
00313
00314
00315 static void cmd_pwd(int idx, char *par)
00316 {
00317 putlog(LOG_FILES, "*", "files: #%s# pwd", dcc[idx].nick);
00318 dprintf(idx, "%s: /%s\n", FILES_CURDIR, dcc[idx].u.file->dir);
00319 }
00320
00321 static void cmd_pending(int idx, char *par)
00322 {
00323 show_queued_files(idx);
00324 putlog(LOG_FILES, "*", "files: #%s# pending", dcc[idx].nick);
00325 }
00326
00327 static void cmd_cancel(int idx, char *par)
00328 {
00329 if (!par[0]) {
00330 dprintf(idx, "%s: cancel <file-mask>\n", MISC_USAGE);
00331 return;
00332 }
00333 fileq_cancel(idx, par);
00334 putlog(LOG_FILES, "*", "files: #%s# cancel %s", dcc[idx].nick, par);
00335 }
00336
00337 static void cmd_chdir(int idx, char *msg)
00338 {
00339 char *s = NULL;
00340
00341 if (!msg[0]) {
00342 dprintf(idx, "%s: cd <new-dir>\n", MISC_USAGE);
00343 return;
00344 }
00345 if (!resolve_dir(dcc[idx].u.file->dir, msg, &s, idx)) {
00346 dprintf(idx, FILES_NOSUCHDIR);
00347 my_free(s);
00348 return;
00349 }
00350 strncpy(dcc[idx].u.file->dir, s, 160);
00351 my_free(s);
00352 dcc[idx].u.file->dir[160] = 0;
00353 set_user(&USERENTRY_DCCDIR, dcc[idx].user, dcc[idx].u.file->dir);
00354 putlog(LOG_FILES, "*", "files: #%s# cd /%s", dcc[idx].nick,
00355 dcc[idx].u.file->dir);
00356 dprintf(idx, "%s: /%s\n", FILES_NEWCURDIR, dcc[idx].u.file->dir);
00357 }
00358
00359 static void files_ls(int idx, char *par, int showall)
00360 {
00361 char *p, *s = NULL, *destdir = NULL, *mask = NULL;
00362 FILE *fdb;
00363
00364 if (par[0]) {
00365 putlog(LOG_FILES, "*", "files: #%s# ls %s", dcc[idx].nick, par);
00366 p = strrchr(par, '/');
00367 if (p != NULL) {
00368 *p = 0;
00369 malloc_strcpy(s, par);
00370 malloc_strcpy(mask, p + 1);
00371 if (!resolve_dir(dcc[idx].u.file->dir, s, &destdir, idx)) {
00372 dprintf(idx, FILES_ILLDIR);
00373 my_free(s);
00374 my_free(mask);
00375 my_free(destdir);
00376 return;
00377 }
00378 my_free(s);
00379 } else {
00380 malloc_strcpy(destdir, dcc[idx].u.file->dir);
00381 malloc_strcpy(mask, par);
00382 }
00383
00384 if (resolve_dir(destdir, mask, &s, idx)) {
00385
00386 malloc_strcpy(destdir, s);
00387 malloc_strcpy(mask, "*");
00388 }
00389 my_free(s);
00390 fdb = filedb_open(destdir, 0);
00391 if (!fdb) {
00392 dprintf(idx, FILES_ILLDIR);
00393 my_free(destdir);
00394 my_free(mask);
00395 return;
00396 }
00397 filedb_ls(fdb, idx, mask, showall);
00398 filedb_close(fdb);
00399 my_free(destdir);
00400 my_free(mask);
00401 } else {
00402 putlog(LOG_FILES, "*", "files: #%s# ls", dcc[idx].nick);
00403 fdb = filedb_open(dcc[idx].u.file->dir, 0);
00404 if (fdb) {
00405 filedb_ls(fdb, idx, "*", showall);
00406 filedb_close(fdb);
00407 } else
00408 dprintf(idx, FILES_ILLDIR);
00409 }
00410 }
00411
00412 static void cmd_ls(int idx, char *par)
00413 {
00414 files_ls(idx, par, 0);
00415 }
00416
00417 static void cmd_lsa(int idx, char *par)
00418 {
00419 files_ls(idx, par, 1);
00420 }
00421
00422 static void cmd_reget_get(int idx, char *par, int resend)
00423 {
00424 int ok = 0, i;
00425 char *p, *what, *destdir = NULL, *s = NULL;
00426 filedb_entry *fdbe;
00427 FILE *fdb;
00428 long where = 0;
00429 int nicklen = NICKLEN;
00430
00431
00432 if (NICKLEN > 9) {
00433 module_entry *me = module_find("server", 1, 1);
00434
00435 if (me && me->funcs)
00436 nicklen = (*(int *)me->funcs[SERVER_NICKLEN]);
00437 }
00438 if (!par[0]) {
00439 dprintf(idx, "%s: %sget <file(s)> [nickname]\n", MISC_USAGE,
00440 resend ? "re" : "");
00441 return;
00442 }
00443 what = newsplit(&par);
00444 if (strlen(par) > nicklen) {
00445 dprintf(idx, FILES_BADNICK);
00446 return;
00447 }
00448 p = strrchr(what, '/');
00449 if (p != NULL) {
00450 *p = 0;
00451 malloc_strcpy(s, what);
00452 strcpy(what, p + 1);
00453 if (!resolve_dir(dcc[idx].u.file->dir, s, &destdir, idx)) {
00454 my_free(destdir);
00455 my_free(s);
00456 dprintf(idx, FILES_ILLDIR);
00457 return;
00458 }
00459 my_free(s);
00460 } else
00461 malloc_strcpy(destdir, dcc[idx].u.file->dir);
00462 fdb = filedb_open(destdir, 0);
00463 if (!fdb)
00464 return;
00465 filedb_readtop(fdb, NULL);
00466 fdbe = filedb_matchfile(fdb, ftell(fdb), what);
00467 if (!fdbe) {
00468 filedb_close(fdb);
00469 free_fdbe(&fdbe);
00470 my_free(destdir);
00471 dprintf(idx, FILES_NOMATCH);
00472 return;
00473 }
00474 while (fdbe) {
00475 where = ftell(fdb);
00476 if (!(fdbe->stat & (FILE_HIDDEN | FILE_DIR))) {
00477 ok = 1;
00478 if (fdbe->sharelink) {
00479 char *bot, *whoto = NULL;
00480
00481
00482 bot = nmalloc(strlen(fdbe->sharelink) + 1);
00483 splitc(bot, fdbe->sharelink, ':');
00484 if (!egg_strcasecmp(bot, botnetnick))
00485 dprintf(idx, "Can't get that file, it's linked to this bot!\n");
00486 else if (!in_chain(bot))
00487 dprintf(idx, FILES_NOTAVAIL, fdbe->filename);
00488 else {
00489 i = nextbot(bot);
00490 malloc_strcpy(whoto, par);
00491 if (!whoto[0])
00492 malloc_strcpy(whoto, dcc[idx].nick);
00493 s = nmalloc(strlen(whoto) + strlen(botnetnick) + 13);
00494 simple_sprintf(s, "%d:%s@%s", dcc[idx].sock, whoto, botnetnick);
00495 botnet_send_filereq(i, s, bot, fdbe->sharelink);
00496 dprintf(idx, FILES_REQUESTED, fdbe->sharelink, bot);
00497
00498 fdbe->gots++;
00499 s = nrealloc(s, strlen(bot) + strlen(fdbe->sharelink) + 2);
00500 sprintf(s, "%s:%s", bot, fdbe->sharelink);
00501 malloc_strcpy(fdbe->sharelink, s);
00502 filedb_updatefile(fdb, fdbe->pos, fdbe, UPDATE_ALL);
00503 my_free(whoto);
00504 my_free(s);
00505 }
00506 my_free(bot);
00507 } else {
00508 do_dcc_send(idx, destdir, fdbe->filename, par, resend);
00509
00510 }
00511 }
00512 free_fdbe(&fdbe);
00513 fdbe = filedb_matchfile(fdb, where, what);
00514 }
00515 filedb_close(fdb);
00516 my_free(destdir);
00517 if (!ok)
00518 dprintf(idx, FILES_NOMATCH);
00519 else
00520 putlog(LOG_FILES, "*", "files: #%s# %sget %s %s", dcc[idx].nick,
00521 resend ? "re" : "", what, par);
00522 }
00523
00524 static void cmd_reget(int idx, char *par)
00525 {
00526 cmd_reget_get(idx, par, 1);
00527 }
00528
00529 static void cmd_get(int idx, char *par)
00530 {
00531 cmd_reget_get(idx, par, 0);
00532 }
00533
00534 static void cmd_file_help(int idx, char *par)
00535 {
00536 char *s;
00537 struct flag_record fr = { FR_GLOBAL | FR_CHAN, 0, 0, 0, 0, 0 };
00538
00539 get_user_flagrec(dcc[idx].user, &fr, dcc[idx].u.file->chat->con_chan);
00540 if (par[0]) {
00541 putlog(LOG_FILES, "*", "files: #%s# help %s", dcc[idx].nick, par);
00542 s = nmalloc(strlen(par) + 9);
00543 sprintf(s, "filesys/%s", par);
00544 s[256] = 0;
00545 tellhelp(idx, s, &fr, 0);
00546 my_free(s);
00547 } else {
00548 putlog(LOG_FILES, "*", "files: #%s# help", dcc[idx].nick);
00549 tellhelp(idx, "filesys/help", &fr, 0);
00550 }
00551 }
00552
00553 static void cmd_hide(int idx, char *par)
00554 {
00555 FILE *fdb;
00556 filedb_entry *fdbe;
00557 long where = 0;
00558 int ok = 0;
00559
00560 if (!par[0]) {
00561 dprintf(idx, "%s: hide <file(s)>\n", MISC_USAGE);
00562 return;
00563 }
00564 fdb = filedb_open(dcc[idx].u.file->dir, 0);
00565 if (!fdb)
00566 return;
00567 filedb_readtop(fdb, NULL);
00568 fdbe = filedb_matchfile(fdb, ftell(fdb), par);
00569 if (!fdbe) {
00570 filedb_close(fdb);
00571 dprintf(idx, FILES_NOMATCH);
00572 return;
00573 }
00574 while (fdbe) {
00575 where = ftell(fdb);
00576 if (!(fdbe->stat & FILE_HIDDEN)) {
00577 fdbe->stat |= FILE_HIDDEN;
00578 ok++;
00579 dprintf(idx, "%s: %s\n", FILES_HID, fdbe->filename);
00580 filedb_updatefile(fdb, fdbe->pos, fdbe, UPDATE_HEADER);
00581 }
00582 free_fdbe(&fdbe);
00583 fdbe = filedb_matchfile(fdb, where, par);
00584 }
00585 filedb_close(fdb);
00586 if (!ok)
00587 dprintf(idx, FILES_NOMATCH);
00588 else {
00589 putlog(LOG_FILES, "*", "files: #%s# hide %s", dcc[idx].nick, par);
00590 if (ok > 1)
00591 dprintf(idx, "%s %d file%s.\n", FILES_HID, ok, ok == 1 ? "" : "s");
00592 }
00593 }
00594
00595 static void cmd_unhide(int idx, char *par)
00596 {
00597 FILE *fdb;
00598 filedb_entry *fdbe;
00599 long where;
00600 int ok = 0;
00601
00602 if (!par[0]) {
00603 dprintf(idx, "%s: unhide <file(s)>\n", MISC_USAGE);
00604 return;
00605 }
00606 fdb = filedb_open(dcc[idx].u.file->dir, 0);
00607 if (!fdb)
00608 return;
00609 filedb_readtop(fdb, NULL);
00610 fdbe = filedb_matchfile(fdb, ftell(fdb), par);
00611 if (!fdbe) {
00612 filedb_close(fdb);
00613 dprintf(idx, FILES_NOMATCH);
00614 return;
00615 }
00616 while (fdbe) {
00617 where = ftell(fdb);
00618 if (fdbe->stat & FILE_HIDDEN) {
00619 fdbe->stat &= ~FILE_HIDDEN;
00620 ok++;
00621 dprintf(idx, "%s: %s\n", FILES_UNHID, fdbe->filename);
00622 filedb_updatefile(fdb, fdbe->pos, fdbe, UPDATE_HEADER);
00623 }
00624 free_fdbe(&fdbe);
00625 fdbe = filedb_matchfile(fdb, where, par);
00626 }
00627 filedb_close(fdb);
00628 if (!ok)
00629 dprintf(idx, FILES_NOMATCH);
00630 else {
00631 putlog(LOG_FILES, "*", "files: #%s# unhide %s", dcc[idx].nick, par);
00632 if (ok > 1)
00633 dprintf(idx, "%s %d file%s.\n", FILES_UNHID, ok, ok == 1 ? "" : "s");
00634 }
00635 }
00636
00637 static void cmd_share(int idx, char *par)
00638 {
00639 FILE *fdb;
00640 filedb_entry *fdbe;
00641 long where;
00642 int ok = 0;
00643
00644 if (!par[0]) {
00645 dprintf(idx, "%s: share <file(s)>\n", MISC_USAGE);
00646 return;
00647 }
00648 fdb = filedb_open(dcc[idx].u.file->dir, 0);
00649 if (!fdb)
00650 return;
00651 filedb_readtop(fdb, NULL);
00652 fdbe = filedb_matchfile(fdb, ftell(fdb), par);
00653 if (!fdbe) {
00654 filedb_close(fdb);
00655 dprintf(idx, FILES_NOMATCH);
00656 return;
00657 }
00658 while (fdbe) {
00659 where = ftell(fdb);
00660 if (!(fdbe->stat & (FILE_HIDDEN | FILE_DIR | FILE_SHARE))) {
00661 fdbe->stat |= FILE_SHARE;
00662 ok++;
00663 dprintf(idx, "%s: %s\n", FILES_SHARED, fdbe->filename);
00664 filedb_updatefile(fdb, fdbe->pos, fdbe, UPDATE_HEADER);
00665 }
00666 free_fdbe(&fdbe);
00667 fdbe = filedb_matchfile(fdb, where, par);
00668 }
00669 filedb_close(fdb);
00670 if (!ok)
00671 dprintf(idx, FILES_NOMATCH);
00672 else {
00673 putlog(LOG_FILES, "*", "files: #%s# share %s", dcc[idx].nick, par);
00674 if (ok > 1)
00675 dprintf(idx, "%s %d file%s.\n", FILES_SHARED, ok, ok == 1 ? "" : "s");
00676 }
00677 }
00678
00679 static void cmd_unshare(int idx, char *par)
00680 {
00681 FILE *fdb;
00682 filedb_entry *fdbe;
00683 long where;
00684 int ok = 0;
00685
00686 if (!par[0]) {
00687 dprintf(idx, "%s: unshare <file(s)>\n", MISC_USAGE);
00688 return;
00689 }
00690 fdb = filedb_open(dcc[idx].u.file->dir, 0);
00691 if (!fdb)
00692 return;
00693 filedb_readtop(fdb, NULL);
00694 fdbe = filedb_matchfile(fdb, ftell(fdb), par);
00695 if (!fdbe) {
00696 filedb_close(fdb);
00697 dprintf(idx, FILES_NOMATCH);
00698 return;
00699 }
00700 while (fdbe) {
00701 where = ftell(fdb);
00702 if ((fdbe->stat & FILE_SHARE) &&
00703 !(fdbe->stat & (FILE_DIR | FILE_HIDDEN))) {
00704 fdbe->stat &= ~FILE_SHARE;
00705 ok++;
00706 dprintf(idx, "%s: %s\n", FILES_UNSHARED, fdbe->filename);
00707 filedb_updatefile(fdb, fdbe->pos, fdbe, UPDATE_HEADER);
00708 }
00709 free_fdbe(&fdbe);
00710 fdbe = filedb_matchfile(fdb, where, par);
00711 }
00712 filedb_close(fdb);
00713 if (!ok)
00714 dprintf(idx, FILES_NOMATCH);
00715 else {
00716 putlog(LOG_FILES, "*", "files: #%s# unshare %s", dcc[idx].nick, par);
00717 if (ok > 1)
00718 dprintf(idx, "%s %d file%s.\n", FILES_UNSHARED, ok, ok == 1 ? "" : "s");
00719 }
00720 }
00721
00722
00723
00724 static void cmd_ln(int idx, char *par)
00725 {
00726 char *share, *newpath = NULL, *newfn = NULL, *p;
00727 FILE *fdb;
00728 filedb_entry *fdbe;
00729
00730 share = newsplit(&par);
00731 if (strlen(share) > 60)
00732 share[60] = 0;
00733
00734 if (!(p = strchr(share, ':')) || !par[0])
00735 dprintf(idx, "%s: ln <bot:path> <localfile>\n", MISC_USAGE);
00736 else if (p[1] != '/')
00737 dprintf(idx, "Links to other bots must have absolute paths.\n");
00738 else {
00739 if ((p = strrchr(par, '/'))) {
00740 *p = 0;
00741 malloc_strcpy(newfn, p + 1);
00742 if (!resolve_dir(dcc[idx].u.file->dir, par, &newpath, idx)) {
00743 dprintf(idx, FILES_NOSUCHDIR);
00744 my_free(newfn);
00745 my_free(newpath);
00746 return;
00747 }
00748 } else {
00749 malloc_strcpy(newpath, dcc[idx].u.file->dir);
00750 malloc_strcpy(newfn, par);
00751 }
00752 fdb = filedb_open(newpath, 0);
00753 if (!fdb) {
00754 my_free(newfn);
00755 my_free(newpath);
00756 return;
00757 }
00758 filedb_readtop(fdb, NULL);
00759 fdbe = filedb_matchfile(fdb, ftell(fdb), newfn);
00760 if (fdbe) {
00761 if (!fdbe->sharelink) {
00762 dprintf(idx, FILES_NORMAL, newfn);
00763 filedb_close(fdb);
00764 } else {
00765 malloc_strcpy(fdbe->sharelink, share);
00766 filedb_updatefile(fdb, fdbe->pos, fdbe, UPDATE_ALL);
00767 filedb_close(fdb);
00768 dprintf(idx, FILES_CHGLINK, share);
00769 putlog(LOG_FILES, "*", "files: #%s# ln %s %s",
00770 dcc[idx].nick, par, share);
00771 }
00772 } else {
00773
00774 fdbe = malloc_fdbe();
00775 malloc_strcpy(fdbe->filename, newfn);
00776 malloc_strcpy(fdbe->uploader, dcc[idx].nick);
00777 fdbe->uploaded = now;
00778 malloc_strcpy(fdbe->sharelink, share);
00779 filedb_addfile(fdb, fdbe);
00780 filedb_close(fdb);
00781 dprintf(idx, "%s %s -> %s\n", FILES_ADDLINK, fdbe->filename, share);
00782 putlog(LOG_FILES, "*", "files: #%s# ln /%s%s%s %s", dcc[idx].nick,
00783 newpath, newpath[0] ? "/" : "", newfn, share);
00784 }
00785 free_fdbe(&fdbe);
00786 my_free(newpath);
00787 my_free(newfn);
00788 }
00789 }
00790
00791 static void cmd_desc(int idx, char *par)
00792 {
00793 char *fn, *desc, *p, *q;
00794 int ok = 0, lin;
00795 FILE *fdb;
00796 filedb_entry *fdbe;
00797 long where;
00798
00799 fn = newsplit(&par);
00800 if (!fn[0]) {
00801 dprintf(idx, "%s: desc <filename> <new description>\n", MISC_USAGE);
00802 return;
00803 }
00804
00805 desc = nmalloc(strlen(par) + 2);
00806 strcpy(desc, par);
00807 strcat(desc, "|");
00808
00809 lin = 0;
00810 q = desc;
00811 while ((*q <= 32) && (*q))
00812 strcpy(q, &q[1]);
00813 p = strchr(q, '|');
00814 while (p != NULL) {
00815
00816 *p = 0;
00817 if (strlen(q) > 60) {
00818
00819 *p = '|';
00820 p = q + 60;
00821 while ((*p != ' ') && (p != q))
00822 p--;
00823 if (p == q)
00824 *(q + 60) = '|';
00825 else
00826 *p = '|';
00827 p = strchr(q, '|');
00828 }
00829 *p = '\n';
00830 q = p + 1;
00831 lin++;
00832 while ((*q <= 32) && (*q))
00833 strcpy(q, &q[1]);
00834 if (lin == 5) {
00835 *p = 0;
00836 p = NULL;
00837 } else
00838 p = strchr(q, '|');
00839 }
00840 if (desc[strlen(desc) - 1] == '\n')
00841 desc[strlen(desc) - 1] = 0;
00842 fdb = filedb_open(dcc[idx].u.file->dir, 0);
00843 if (!fdb) {
00844 my_free(desc);
00845 return;
00846 }
00847 filedb_readtop(fdb, NULL);
00848 fdbe = filedb_matchfile(fdb, ftell(fdb), fn);
00849 if (!fdbe) {
00850 filedb_close(fdb);
00851 dprintf(idx, FILES_NOMATCH);
00852 my_free(desc);
00853 return;
00854 }
00855 while (fdbe) {
00856 where = ftell(fdb);
00857 if (!(fdbe->stat & FILE_HIDDEN)) {
00858 ok = 1;
00859 if ((!(dcc[idx].user->flags & USER_JANITOR)) &&
00860 (egg_strcasecmp(fdbe->uploader, dcc[idx].nick)))
00861 dprintf(idx, FILES_NOTOWNER, fdbe->filename);
00862 else {
00863 if (desc[0]) {
00864
00865
00866
00867 if (fdbe->desc && !strcmp(fdbe->desc, desc)) {
00868 free_fdbe(&fdbe);
00869 fdbe = filedb_matchfile(fdb, where, fn);
00870 continue;
00871 }
00872 malloc_strcpy(fdbe->desc, desc);
00873 } else if (fdbe->desc) {
00874 my_free(fdbe->desc);
00875 }
00876 filedb_updatefile(fdb, fdbe->pos, fdbe, UPDATE_ALL);
00877 if (par[0])
00878 dprintf(idx, "%s: %s\n", FILES_CHANGED, fdbe->filename);
00879 else
00880 dprintf(idx, "%s: %s\n", FILES_BLANKED, fdbe->filename);
00881 }
00882 }
00883 free_fdbe(&fdbe);
00884 fdbe = filedb_matchfile(fdb, where, fn);
00885 }
00886 filedb_close(fdb);
00887 if (!ok)
00888 dprintf(idx, FILES_NOMATCH);
00889 else
00890 putlog(LOG_FILES, "*", "files: #%s# desc %s", dcc[idx].nick, fn);
00891 my_free(desc);
00892 }
00893
00894 static void cmd_rm(int idx, char *par)
00895 {
00896 FILE *fdb;
00897 filedb_entry *fdbe;
00898 long where;
00899 int ok = 0;
00900 char *s;
00901
00902 if (!par[0]) {
00903 dprintf(idx, "%s: rm <file(s)>\n", MISC_USAGE);
00904 return;
00905 }
00906 fdb = filedb_open(dcc[idx].u.file->dir, 0);
00907 if (!fdb)
00908 return;
00909 filedb_readtop(fdb, NULL);
00910 fdbe = filedb_matchfile(fdb, ftell(fdb), par);
00911 if (!fdbe) {
00912 filedb_close(fdb);
00913 dprintf(idx, FILES_NOMATCH);
00914 return;
00915 }
00916 while (fdbe) {
00917 where = ftell(fdb);
00918 if (!(fdbe->stat & (FILE_HIDDEN | FILE_DIR))) {
00919 s = nmalloc(strlen(dccdir) + strlen(dcc[idx].u.file->dir)
00920 + strlen(fdbe->filename) + 2);
00921 sprintf(s, "%s%s/%s", dccdir, dcc[idx].u.file->dir, fdbe->filename);
00922 ok++;
00923 filedb_delfile(fdb, fdbe->pos);
00924
00925 if (!(fdbe->sharelink))
00926 unlink(s);
00927 dprintf(idx, "%s: %s\n", FILES_ERASED, fdbe->filename);
00928 my_free(s);
00929 }
00930 free_fdbe(&fdbe);
00931 fdbe = filedb_matchfile(fdb, where, par);
00932 }
00933 filedb_close(fdb);
00934 if (!ok)
00935 dprintf(idx, FILES_NOMATCH);
00936 else {
00937 putlog(LOG_FILES, "*", "files: #%s# rm %s", dcc[idx].nick, par);
00938 if (ok > 1)
00939 dprintf(idx, "%s %d file%s.\n", FILES_ERASED, ok, ok == 1 ? "" : "s");
00940 }
00941 }
00942
00943 static void cmd_mkdir(int idx, char *par)
00944 {
00945 char *name, *flags, *chan, *s;
00946 FILE *fdb;
00947 filedb_entry *fdbe;
00948 int ret;
00949 struct flag_record fr = { FR_GLOBAL | FR_CHAN, 0, 0, 0, 0, 0 };
00950
00951 if (!par[0]) {
00952 dprintf(idx, "%s: mkdir <dir> [required-flags] [channel]\n", MISC_USAGE);
00953 return;
00954 }
00955 name = newsplit(&par);
00956 ret = strlen(name);
00957 if (ret > 60)
00958 name[(ret = 60)] = 0;
00959 if (name[ret] == '/')
00960 name[ret] = 0;
00961 if (strchr(name, '/'))
00962 dprintf(idx, "You can only create directories in the current directory\n");
00963 else {
00964 flags = newsplit(&par);
00965 chan = newsplit(&par);
00966 if (!chan[0] && flags[0] && (strchr(CHANMETA, flags[0]) != NULL)) {
00967
00968
00969
00970 if (!findchan(flags) && flags[0] != '+') {
00971 dprintf(idx, "Invalid channel!\n");
00972 return;
00973 } else if (findchan(flags)) {
00974
00975 chan = flags;
00976 flags = par;
00977 }
00978
00979 }
00980 if (chan[0] && !findchan(chan)) {
00981 dprintf(idx, "Invalid channel!\n");
00982 return;
00983 }
00984 fdb = filedb_open(dcc[idx].u.file->dir, 0);
00985 if (!fdb)
00986 return;
00987 filedb_readtop(fdb, NULL);
00988 fdbe = filedb_matchfile(fdb, ftell(fdb), name);
00989 if (!fdbe) {
00990 s = nmalloc(strlen(dccdir) + strlen(dcc[idx].u.file->dir)
00991 + strlen(name) + 2);
00992 sprintf(s, "%s%s/%s", dccdir, dcc[idx].u.file->dir, name);
00993 if (mkdir(s, 0755) != 0) {
00994 dprintf(idx, MISC_FAILED);
00995 filedb_close(fdb);
00996 my_free(s);
00997 return;
00998 }
00999 my_free(s);
01000 fdbe = malloc_fdbe();
01001 fdbe->stat = FILE_DIR;
01002 malloc_strcpy(fdbe->filename, name);
01003 fdbe->uploaded = now;
01004 dprintf(idx, "%s /%s%s%s\n", FILES_CREADIR, dcc[idx].u.file->dir,
01005 dcc[idx].u.file->dir[0] ? "/" : "", name);
01006 } else if (!(fdbe->stat & FILE_DIR)) {
01007 dprintf(idx, FILES_NOSUCHDIR);
01008 free_fdbe(&fdbe);
01009 filedb_close(fdb);
01010 return;
01011 }
01012 if (flags[0]) {
01013 char buffer[100];
01014
01015 break_down_flags(flags, &fr, NULL);
01016 build_flags(buffer, &fr, NULL);
01017 malloc_strcpy_nocheck(fdbe->flags_req, buffer);
01018 dprintf(idx, FILES_CHGACCESS, name, buffer);
01019 } else if (!chan[0]) {
01020 my_free(fdbe->flags_req);
01021 dprintf(idx, FILES_CHGNACCESS, name);
01022 }
01023 if (chan[0]) {
01024 malloc_strcpy(fdbe->chan, chan);
01025 dprintf(idx, "Access set to channel: %s\n", chan);
01026 } else if (!flags[0]) {
01027 my_free(fdbe->chan);
01028 dprintf(idx, "Access set to all channels.\n");
01029 }
01030 if (!fdbe->pos)
01031 fdbe->pos = POS_NEW;
01032 filedb_updatefile(fdb, fdbe->pos, fdbe, UPDATE_ALL);
01033 filedb_close(fdb);
01034 free_fdbe(&fdbe);
01035 putlog(LOG_FILES, "*", "files: #%s# mkdir %s %s", dcc[idx].nick, name, par);
01036 }
01037 }
01038
01039 static void cmd_rmdir(int idx, char *par)
01040 {
01041 FILE *fdb;
01042 filedb_entry *fdbe;
01043 char *s, *name = NULL;
01044
01045 malloc_strcpy(name, par);
01046 if (name[strlen(name) - 1] == '/')
01047 name[strlen(name) - 1] = 0;
01048 if (strchr(name, '/'))
01049 dprintf(idx, "You can only create directories in the current directory\n");
01050 else {
01051 fdb = filedb_open(dcc[idx].u.file->dir, 0);
01052 if (!fdb) {
01053 my_free(name);
01054 return;
01055 }
01056 filedb_readtop(fdb, NULL);
01057 fdbe = filedb_matchfile(fdb, ftell(fdb), name);
01058 if (!fdbe) {
01059 dprintf(idx, FILES_NOSUCHDIR);
01060 filedb_close(fdb);
01061 my_free(name);
01062 return;
01063 }
01064 if (!(fdbe->stat & FILE_DIR)) {
01065 dprintf(idx, FILES_NOSUCHDIR);
01066 filedb_close(fdb);
01067 my_free(name);
01068 free_fdbe(&fdbe);
01069 return;
01070 }
01071
01072 s = nmalloc(strlen(dccdir) + strlen(dcc[idx].u.file->dir)
01073 + strlen(name) + 10);
01074 sprintf(s, "%s%s/%s/.filedb", dccdir, dcc[idx].u.file->dir, name);
01075 unlink(s);
01076 sprintf(s, "%s%s/%s/.files", dccdir, dcc[idx].u.file->dir, name);
01077 unlink(s);
01078 sprintf(s, "%s%s/%s", dccdir, dcc[idx].u.file->dir, name);
01079 if (rmdir(s) == 0) {
01080 dprintf(idx, "%s /%s%s%s\n", FILES_REMDIR, dcc[idx].u.file->dir,
01081 dcc[idx].u.file->dir[0] ? "/" : "", name);
01082 filedb_delfile(fdb, fdbe->pos);
01083 filedb_close(fdb);
01084 free_fdbe(&fdbe);
01085 my_free(s);
01086 my_free(name);
01087 putlog(LOG_FILES, "*", "files: #%s# rmdir %s", dcc[idx].nick, name);
01088 return;
01089 }
01090 dprintf(idx, MISC_FAILED);
01091 filedb_close(fdb);
01092 free_fdbe(&fdbe);
01093 my_free(s);
01094 my_free(name);
01095 }
01096 }
01097
01098 static void cmd_mv_cp(int idx, char *par, int copy)
01099 {
01100 char *p, *fn, *oldpath = NULL, *s = NULL, *s1, *newfn = NULL;
01101 char *newpath = NULL;
01102 int ok = 0, only_first = 0, skip_this = 0;
01103 FILE *fdb_old = NULL, *fdb_new = NULL;
01104 filedb_entry *fdbe_old = NULL, *fdbe_new = NULL;
01105 long where = 0;
01106
01107 fn = newsplit(&par);
01108 if (!par[0]) {
01109 dprintf(idx, "%s: %s <oldfilepath> <newfilepath>\n",
01110 MISC_USAGE, copy ? "cp" : "mv");
01111 return;
01112 }
01113 p = strrchr(fn, '/');
01114 if (p != NULL) {
01115 *p = 0;
01116 malloc_strcpy(s, fn);
01117 strcpy(fn, p + 1);
01118 if (!resolve_dir(dcc[idx].u.file->dir, s, &oldpath, idx)) {
01119 dprintf(idx, FILES_ILLSOURCE);
01120 my_free(s);
01121 my_free(oldpath);
01122 return;
01123 }
01124 my_free(s);
01125 } else
01126 malloc_strcpy(oldpath, dcc[idx].u.file->dir);
01127 malloc_strcpy(s, par);
01128 if (!resolve_dir(dcc[idx].u.file->dir, s, &newpath, idx)) {
01129 my_free(newpath);
01130
01131 p = strrchr(s, '/');
01132 if (p == NULL) {
01133 malloc_strcpy(newfn, s);
01134 s[0] = 0;
01135 } else {
01136 *p = 0;
01137 malloc_strcpy(newfn, p + 1);
01138 }
01139 if (!resolve_dir(dcc[idx].u.file->dir, s, &newpath, idx)) {
01140 dprintf(idx, FILES_ILLDEST);
01141 my_free(newfn);
01142 my_free(s);
01143 my_free(oldpath);
01144 my_free(newpath);
01145 return;
01146 }
01147 } else
01148 malloc_strcpy(newfn, "");
01149 my_free(s);
01150
01151 if ((!strcmp(oldpath, newpath)) && ((!newfn[0]) || (!strcmp(newfn, fn)))) {
01152 dprintf(idx, FILES_STUPID, copy ? FILES_COPY : FILES_MOVE);
01153 my_free(oldpath);
01154 my_free(newpath);
01155 my_free(newfn);
01156 return;
01157 }
01158
01159 if ((strchr(fn, '?') || strchr(fn, '*')) && newfn[0])
01160 only_first = 1;
01161 else
01162 only_first = 0;
01163
01164 fdb_old = filedb_open(oldpath, 0);
01165 if (!strcmp(oldpath, newpath))
01166 fdb_new = fdb_old;
01167 else
01168 fdb_new = filedb_open(newpath, 0);
01169 if (!fdb_old || !fdb_new) {
01170 my_free(oldpath);
01171 my_free(newpath);
01172 my_free(newfn);
01173 return;
01174 }
01175
01176 filedb_readtop(fdb_old, NULL);
01177 where = ftell(fdb_old);
01178 fdbe_old = filedb_matchfile(fdb_old, where, fn);
01179 if (!fdbe_old) {
01180 if (fdb_new != fdb_old)
01181 filedb_close(fdb_new);
01182 filedb_close(fdb_old);
01183 my_free(oldpath);
01184 my_free(newpath);
01185 my_free(newfn);
01186 return;
01187 }
01188
01189 if (only_first) {
01190
01191
01192
01193 filedb_entry *check_for_more;
01194 check_for_more = filedb_matchfile(fdb_old, ftell(fdb_old), fn);
01195 if (check_for_more) {
01196 dprintf(idx, FILES_ILLDEST);
01197 free_fdbe(&fdbe_old);
01198 free_fdbe(&check_for_more);
01199 if (fdb_new != fdb_old) filedb_close(fdb_new);
01200 filedb_close(fdb_old);
01201 my_free(oldpath);
01202 my_free(newpath);
01203 my_free(newfn);
01204 return;
01205 }
01206 fseek(fdb_old, where, SEEK_SET);
01207 }
01208
01209 while (fdbe_old) {
01210 where = ftell(fdb_old);
01211 skip_this = 0;
01212 if (!(fdbe_old->stat & (FILE_HIDDEN | FILE_DIR))) {
01213 s = nmalloc(strlen(dccdir) + strlen(oldpath)
01214 + strlen(fdbe_old->filename) + 2);
01215 s1 = nmalloc(strlen(dccdir) + strlen(newpath)
01216 + strlen(newfn[0] ? newfn : fdbe_old->filename) + 2);
01217 sprintf(s, "%s%s%s%s", dccdir, oldpath,
01218 oldpath[0] ? "/" : "", fdbe_old->filename);
01219 sprintf(s1, "%s%s%s%s", dccdir, newpath,
01220 newpath[0] ? "/" : "", newfn[0] ? newfn : fdbe_old->filename);
01221 if (!strcmp(s, s1)) {
01222 dprintf(idx, "%s /%s%s%s %s\n", FILES_SKIPSTUPID,
01223 copy ? FILES_COPY : FILES_MOVE, newpath,
01224 newpath[0] ? "/" : "", newfn[0] ? newfn : fdbe_old->filename);
01225 skip_this = 1;
01226 }
01227
01228 filedb_readtop(fdb_new, NULL);
01229 fdbe_new = filedb_matchfile(fdb_new, ftell(fdb_new),
01230 newfn[0] ? newfn : fdbe_old->filename);
01231 if (fdbe_new) {
01232
01233
01234
01235
01236 if (fdbe_new->stat & FILE_DIR)
01237 skip_this = 1;
01238 else
01239 filedb_delfile(fdb_new, fdbe_new->pos);
01240 free_fdbe(&fdbe_new);
01241 }
01242 if (!skip_this) {
01243 if ((fdbe_old->sharelink) ||
01244 ((copy ? copyfile(s, s1) : movefile(s, s1)) == 0)) {
01245
01246 ok++;
01247 fdbe_new = malloc_fdbe();
01248 fdbe_new->stat = fdbe_old->stat;
01249
01250
01251
01252 malloc_strcpy(fdbe_new->flags_req, fdbe_old->flags_req);
01253 malloc_strcpy(fdbe_new->chan, fdbe_old->chan);
01254 malloc_strcpy(fdbe_new->filename, fdbe_old->filename);
01255 malloc_strcpy(fdbe_new->desc, fdbe_old->desc);
01256 if (newfn[0])
01257 malloc_strcpy(fdbe_new->filename, newfn);
01258 malloc_strcpy(fdbe_new->uploader, fdbe_old->uploader);
01259 fdbe_new->uploaded = fdbe_old->uploaded;
01260 fdbe_new->size = fdbe_old->size;
01261 fdbe_new->gots = fdbe_old->gots;
01262 malloc_strcpy(fdbe_new->sharelink, fdbe_old->sharelink);
01263 filedb_addfile(fdb_new, fdbe_new);
01264 if (!copy)
01265 filedb_delfile(fdb_old, fdbe_old->pos);
01266 free_fdbe(&fdbe_new);
01267 }
01268 }
01269 my_free(s);
01270 my_free(s1);
01271 }
01272 free_fdbe(&fdbe_old);
01273 fdbe_old = filedb_matchfile(fdb_old, where, fn);
01274 if (ok && only_first)
01275 free_fdbe(&fdbe_old);
01276 }
01277 if (fdb_old != fdb_new)
01278 filedb_close(fdb_new);
01279 filedb_close(fdb_old);
01280 if (!ok)
01281 dprintf(idx, FILES_NOMATCH);
01282 else {
01283 putlog(LOG_FILES, "*", "files: #%s# %s %s%s%s %s", dcc[idx].nick,
01284 copy ? "cp" : "mv", oldpath, oldpath[0] ? "/" : "", fn, par);
01285 if (ok > 1)
01286 dprintf(idx, "%s %d file%s.\n",
01287 copy ? FILES_COPIED : FILES_MOVED, ok, ok == 1 ? "" : "s");
01288 }
01289 my_free(oldpath);
01290 my_free(newpath);
01291 my_free(newfn);
01292 }
01293
01294 static void cmd_mv(int idx, char *par)
01295 {
01296 cmd_mv_cp(idx, par, 0);
01297 }
01298
01299 static void cmd_cp(int idx, char *par)
01300 {
01301 cmd_mv_cp(idx, par, 1);
01302 }
01303
01304 static int cmd_stats(int idx, char *par)
01305 {
01306 putlog(LOG_FILES, "*", "#%s# stats", dcc[idx].nick);
01307 tell_file_stats(idx, dcc[idx].nick);
01308 return 0;
01309 }
01310
01311 static int cmd_filestats(int idx, char *par)
01312 {
01313 char *nick;
01314 struct userrec *u;
01315
01316 if (!par[0]) {
01317 dprintf(idx, "Usage: filestats <user>\n");
01318 return 0;
01319 }
01320 nick = newsplit(&par);
01321 putlog(LOG_FILES, "*", "#%s# filestats %s", dcc[idx].nick, nick);
01322 if (nick[0] == 0)
01323 tell_file_stats(idx, dcc[idx].nick);
01324 else if (!(u = get_user_by_handle(userlist, nick)))
01325 dprintf(idx, "No such user.\n");
01326 else if (!strcmp(par, "clear") && dcc[idx].user &&
01327 (dcc[idx].user->flags & USER_JANITOR)) {
01328 set_user(&USERENTRY_FSTAT, u, NULL);
01329 dprintf(idx, "Cleared filestats for %s.\n", nick);
01330 } else
01331 tell_file_stats(idx, nick);
01332 return 0;
01333 }
01334
01335
01336
01337
01338 static void filesys_note(int idx, char *par)
01339 {
01340 struct userrec *u = get_user_by_handle(userlist, dcc[idx].nick);
01341 module_entry *me = module_find("notes", 2, 1);
01342
01343 if (me && me->funcs) {
01344 Function f = me->funcs[NOTES_CMD_NOTE];
01345
01346 (f) (u, idx, par);
01347 } else
01348 dprintf(idx, "Sending of notes is not supported.\n");
01349 }
01350
01351 static cmd_t myfiles[] = {
01352 {"cancel", "", (IntFunc) cmd_cancel, NULL},
01353 {"cd", "", (IntFunc) cmd_chdir, NULL},
01354 {"chdir", "", (IntFunc) cmd_chdir, NULL},
01355 {"cp", "j", (IntFunc) cmd_cp, NULL},
01356 {"desc", "", (IntFunc) cmd_desc, NULL},
01357 {"filestats", "j", (IntFunc) cmd_filestats, NULL},
01358 {"get", "", (IntFunc) cmd_get, NULL},
01359 {"reget", "", (IntFunc) cmd_reget, NULL},
01360 {"help", "", (IntFunc) cmd_file_help, NULL},
01361 {"hide", "j", (IntFunc) cmd_hide, NULL},
01362 {"ln", "j", (IntFunc) cmd_ln, NULL},
01363 {"ls", "", (IntFunc) cmd_ls, NULL},
01364 {"lsa", "j", (IntFunc) cmd_lsa, NULL},
01365 {"mkdir", "j", (IntFunc) cmd_mkdir, NULL},
01366 {"mv", "j", (IntFunc) cmd_mv, NULL},
01367 {"note", "", (IntFunc) filesys_note, NULL},
01368 {"pending", "", (IntFunc) cmd_pending, NULL},
01369 {"pwd", "", (IntFunc) cmd_pwd, NULL},
01370 {"quit", "", (IntFunc) CMD_LEAVE, NULL},
01371 {"rm", "j", (IntFunc) cmd_rm, NULL},
01372 {"rmdir", "j", (IntFunc) cmd_rmdir, NULL},
01373 {"share", "j", (IntFunc) cmd_share, NULL},
01374
01375
01376
01377
01378 {"optimise", "j", (IntFunc) cmd_optimize, NULL},
01379 {"optimize", "j", (IntFunc) cmd_optimize, NULL},
01380 {"stats", "", (IntFunc) cmd_stats, NULL},
01381 {"unhide", "j", (IntFunc) cmd_unhide, NULL},
01382 {"unshare", "j", (IntFunc) cmd_unshare, NULL},
01383 {NULL, NULL, NULL, NULL}
01384 };
01385
01386
01387
01388
01389
01390
01391 static int files_reget(int idx, char *fn, char *nick, int resend)
01392 {
01393 int i = 0;
01394 char *p = NULL, *what = NULL, *destdir, *s = NULL;
01395 filedb_entry *fdbe = NULL;
01396 FILE *fdb = NULL;
01397
01398 p = strrchr(fn, '/');
01399 if (p != NULL) {
01400 *p = 0;
01401 malloc_strcpy(s, fn);
01402 malloc_strcpy(what, p + 1);
01403 if (!resolve_dir(dcc[idx].u.file->dir, s, &destdir, idx)) {
01404 my_free(s);
01405 my_free(what);
01406 my_free(destdir);
01407 return 0;
01408 }
01409 my_free(s);
01410 } else {
01411 malloc_strcpy(destdir, dcc[idx].u.file->dir);
01412 malloc_strcpy(what, fn);
01413 }
01414 fdb = filedb_open(destdir, 0);
01415 if (!fdb) {
01416 my_free(what);
01417 my_free(destdir);
01418 return 0;
01419 }
01420 filedb_readtop(fdb, NULL);
01421 fdbe = filedb_matchfile(fdb, ftell(fdb), what);
01422 if (!fdbe) {
01423 filedb_close(fdb);
01424 my_free(what);
01425 my_free(destdir);
01426 return 0;
01427 }
01428 if (fdbe->stat & (FILE_HIDDEN | FILE_DIR)) {
01429 filedb_close(fdb);
01430 my_free(what);
01431 my_free(destdir);
01432 free_fdbe(&fdbe);
01433 return 0;
01434 }
01435 if (fdbe->sharelink) {
01436 char *bot, *whoto = NULL;
01437
01438
01439 bot = nmalloc(strlen(fdbe->sharelink) + 1);
01440 splitc(bot, fdbe->sharelink, ':');
01441 if (!egg_strcasecmp(bot, botnetnick)) {
01442
01443 filedb_close(fdb);
01444 my_free(what);
01445 my_free(destdir);
01446 my_free(bot);
01447 free_fdbe(&fdbe);
01448 return 0;
01449 } else if (!in_chain(bot)) {
01450 filedb_close(fdb);
01451 my_free(what);
01452 my_free(destdir);
01453 my_free(bot);
01454 free_fdbe(&fdbe);
01455 return 0;
01456 } else {
01457 i = nextbot(bot);
01458 if (nick[0]) {
01459 malloc_strcpy(whoto, nick);
01460 } else {
01461 malloc_strcpy(whoto, dcc[idx].nick);
01462 }
01463 s = nmalloc(strlen(whoto) + strlen(botnetnick) + 13);
01464 simple_sprintf(s, "%d:%s@%s", dcc[idx].sock, whoto, botnetnick);
01465 botnet_send_filereq(i, s, bot, fdbe->sharelink);
01466 dprintf(idx, FILES_REQUESTED, fdbe->sharelink, bot);
01467
01468 fdbe->gots++;
01469 s = nrealloc(s, strlen(bot) + strlen(fdbe->sharelink) + 2);
01470 sprintf(s, "%s:%s", bot, fdbe->sharelink);
01471 malloc_strcpy(fdbe->sharelink, s);
01472 filedb_updatefile(fdb, fdbe->pos, fdbe, UPDATE_ALL);
01473 filedb_close(fdb);
01474 free_fdbe(&fdbe);
01475 my_free(what);
01476 my_free(destdir);
01477 my_free(bot);
01478 my_free(whoto);
01479 my_free(s);
01480 return 1;
01481 }
01482 }
01483 filedb_close(fdb);
01484 do_dcc_send(idx, destdir, fdbe->filename, nick, resend);
01485 my_free(what);
01486 my_free(destdir);
01487 free_fdbe(&fdbe);
01488
01489 return 1;
01490 }
01491
01492 static void files_setpwd(int idx, char *where)
01493 {
01494 char *s;
01495
01496 if (!resolve_dir(dcc[idx].u.file->dir, where, &s, idx))
01497 return;
01498 strcpy(dcc[idx].u.file->dir, s);
01499 set_user(&USERENTRY_DCCDIR, get_user_by_handle(userlist, dcc[idx].nick),
01500 dcc[idx].u.file->dir);
01501 my_free(s);
01502 }