? config.log ? config.cache ? config.status ? makefile ? auth_modules/Makefile ? auth_modules/LDAP/Makefile ? auth_modules/MSNT/Makefile ? auth_modules/NCSA/Makefile ? auth_modules/PAM/Makefile ? auth_modules/SMB/Makefile ? auth_modules/getpwnam/Makefile ? contrib/Makefile ? errors/Makefile ? icons/Makefile ? include/config.h ? include/autoconf.h ? lib/Makefile ? scripts/Makefile ? scripts/RunCache ? scripts/RunAccel ? src/client ? src/Makefile ? src/cf.data ? src/cf_gen ? src/cf_gen_defines.h ? src/cf_parser.c ? src/squid.conf ? src/globals.c ? src/repl_modules.c ? src/store_modules.c ? src/string_arrays.c ? src/squid ? src/unlinkd ? src/cachemgr.cgi ? src/diskd.core ? src/fs/Makefile ? src/fs/diskd/Makefile ? src/fs/diskd/diskd ? src/repl/Makefile ? src/repl/stamp ? src/repl/lru/Makefile Index: src/fs/diskd/diskd.c =================================================================== RCS file: /server/cvs-server/squid/squid/src/fs/diskd/diskd.c,v retrieving revision 1.6 diff -u -r1.6 diskd.c --- src/fs/diskd/diskd.c 2000/10/03 15:31:40 1.6 +++ src/fs/diskd/diskd.c 2000/10/12 09:06:18 @@ -66,6 +66,8 @@ { int fd; file_state *fs; + struct stat sb; + int retval; /* * note r->offset holds open() flags */ @@ -75,16 +77,29 @@ perror("open"); return -errno; } + /* + * For a create, we open newfile, and stat the fd to get the inode number. + * This is then the file number used for subsequent open/unlink. + */ + retval = fstat(fd, &sb); + if (retval < 0) { + fprintf(stderr, "%d %s: ", (int)mypid, buf); + perror("stat"); + close(fd); + return -errno; + } + r->f_ino = sb.st_ino; fs = xcalloc(1, sizeof(*fs)); fs->id = r->id; fs->key = &fs->id; /* gack */ fs->fd = fd; hash_join(hash, (hash_link *) fs); #if STDERR_DEBUG - fprintf(stderr, "%d OPEN id %d, FD %d, fs %p\n", + fprintf(stderr, "%d OPEN id %d, FD %d, INODE %d, fs %p\n", (int) mypid, fs->id, fs->fd, + r->f_ino, fs); #endif return fd; @@ -233,6 +248,7 @@ assert(0); break; } + s->f_ino = r->f_ino; } int Index: src/fs/diskd/store_dir_diskd.c =================================================================== RCS file: /server/cvs-server/squid/squid/src/fs/diskd/store_dir_diskd.c,v retrieving revision 1.18 diff -u -r1.18 store_dir_diskd.c --- src/fs/diskd/store_dir_diskd.c 2000/10/06 05:21:58 1.18 +++ src/fs/diskd/store_dir_diskd.c 2000/10/12 09:06:18 @@ -93,6 +93,7 @@ static EVH storeDiskdDirRebuildFromDirectory; static EVH storeDiskdDirRebuildFromSwapLog; static int storeDiskdDirGetNextFile(RebuildState *, int *sfileno, int *size); +static int storeDiskdDirGetNextIfsFile(RebuildState *, int *sfileno, int *size); static StoreEntry *storeDiskdDirAddDiskRestore(SwapDir * SD, const cache_key * key, int file_number, size_t swap_file_sz, @@ -425,11 +426,12 @@ commSetTimeout(diskdinfo->wfd, -1, NULL, NULL); commSetNonBlocking(diskdinfo->wfd); storeDiskdDirInitBitmap(sd); - if (storeDiskdDirVerifyCacheDirs(sd) < 0) - fatal(errmsg); + if (!diskdinfo->doifs) + if (storeDiskdDirVerifyCacheDirs(sd) < 0) + fatal(errmsg); storeDiskdDirOpenSwapLog(sd); storeDiskdDirRebuild(sd); - if (!started_clean_event) { + if (!started_clean_event && !diskdinfo->doifs) { eventAdd("storeDirClean", storeDiskdDirCleanEvent, NULL, 15.0, 1); started_clean_event = 1; } @@ -528,13 +530,12 @@ return retval; } - - static void storeDiskdDirRebuildFromDirectory(void *data) { RebuildState *rb = data; SwapDir *SD = rb->sd; + diskdinfo_t *diskdinfo = SD->fsdata; LOCAL_ARRAY(char, hdr_buf, SM_PAGE_SIZE); StoreEntry *e = NULL; StoreEntry tmpe; @@ -551,7 +552,10 @@ debug(20, 3) ("storeDiskdDirRebuildFromDirectory: DIR #%d\n", rb->sd->index); for (count = 0; count < rb->speed; count++) { assert(fd == -1); - fd = storeDiskdDirGetNextFile(rb, &sfileno, &size); + if (diskdinfo->doifs) + fd = storeDiskdDirGetNextIfsFile(rb, &sfileno, &size); + else + fd = storeDiskdDirGetNextFile(rb, &sfileno, &size); if (fd == -2) { debug(20, 1) ("Done scanning %s swaplog (%d entries)\n", rb->sd->path, rb->n_read); @@ -869,7 +873,78 @@ eventAdd("storeRebuild", storeDiskdDirRebuildFromSwapLog, rb, 0.0, 1); } + +/* + * Get the next file from an ifs directory. Much simpler than its UFS + * counterpart. + */ static int +storeDiskdDirGetNextIfsFile(RebuildState * rb, int *sfileno, int *size) +{ + SwapDir *SD = rb->sd; + int fd = -1; + + debug (20, 3) ("storeDiskdDirGetNextIfsFile: flag %d, %d: .. ?\n", + rb->flags.init, + SD->index); + + if (rb->done) + return -2; + + /* Check if we need to open the IFS dir for reading */ + if (rb->flags.init == 0) { + rb->done = 0; + rb->curlvl1 = -1; + rb->curlvl2 = -1; + rb->in_dir = 0; + rb->flags.init = 1; + assert(Config.cacheSwap.n_configured > 0); + rb->td = opendir(SD->path); + rb->entry = readdir(rb->td); /* Skip . and .. */ + rb->entry = readdir(rb->td); + rb->entry = NULL; + if (rb->td == NULL) { + /* Error whilst reading our directory! */ + debug(20, 1) ("storeDiskdDirGetNextIfsFile: readdir failed: %s\n", + xstrerror()); + return -1; + } + } + + retry: + /* Read the next entry */ + rb->entry = readdir(rb->td); + if (rb->entry == NULL) { + /* End of directory, we're finished */ + closedir(rb->td); + rb->td = 0; + rb->done = 1; + return -2; + } + /* Perform sanity check */ + snprintf(rb->fullfilename, SQUID_MAXPATHLEN, "%s/%s",SD->path, + rb->entry->d_name); + debug(20, 3) ("storeDiskdDirGetNextIfsFile: Opening %s\n", + rb->fullfilename); + fd = file_open(rb->fullfilename, O_RDONLY); + if (fd < 0) { + debug(50, 1) ("storeDiskdDirGetNextIfsFile: %s: %s\n", + rb->fullfilename, xstrerror()); + goto retry; + } else + store_open_disk_fd++; + + /* Get the file number */ + if (sscanf(rb->entry->d_name, "%x", &rb->fn) != 1) { + debug(20, 3) ("storeDiskdDirGetNextIfsFile: invalid %s\n", + rb->entry->d_name); + goto retry; + } + *sfileno = rb->fn; + return fd; +} + +static int storeDiskdDirGetNextFile(RebuildState * rb, int *sfileno, int *size) { SwapDir *SD = rb->sd; @@ -1287,9 +1362,15 @@ static void storeDiskdDirNewfs(SwapDir * sd) { - debug(47, 3) ("Creating swap space in %s\n", sd->path); - storeDiskdDirCreateDirectory(sd->path, 0); - storeDiskdDirCreateSwapSubDirs(sd); + diskdinfo_t *diskdinfo = sd->fsdata; + + if (diskdinfo->doifs) { + debug(47, 3) ("No need to newfs for ifs in %s\n", sd->path); + } else { + debug(47, 3) ("Creating swap space in %s\n", sd->path); + storeDiskdDirCreateDirectory(sd->path, 0); + storeDiskdDirCreateSwapSubDirs(sd); + } } static int @@ -1398,10 +1479,13 @@ diskd_dir_index = xcalloc(n_diskd_dirs, sizeof(*diskd_dir_index)); for (i = 0, n = 0; i < Config.cacheSwap.n_configured; i++) { sd = &Config.cacheSwap.swapDirs[i]; + diskdinfo = sd->fsdata; if (!storeDiskdDirIs(sd)) continue; + /* XXX Don't need to clean an IFS partition just yet! */ + if (diskdinfo->doifs) + continue; diskd_dir_index[n++] = i; - diskdinfo = sd->fsdata; j += (diskdinfo->l1 * diskdinfo->l2); } assert(n == n_diskd_dirs); @@ -1458,6 +1542,9 @@ diskdinfo_t *diskdinfo = SD->fsdata; if (filn < 0) return 0; + /* If we are doing IFS, we don't know whether its valid .. */ + if (diskdinfo->doifs) + return 1; /* * If flag is set it means out-of-range file number should * be considered invalid. @@ -1661,9 +1748,12 @@ storeAppendPrintf(sentry, "Current Size: %d KB\n", SD->cur_size); storeAppendPrintf(sentry, "Percent Used: %0.2f%%\n", 100.0 * SD->cur_size / SD->max_size); - storeAppendPrintf(sentry, "Filemap bits in use: %d of %d (%d%%)\n", - diskdinfo->map->n_files_in_map, diskdinfo->map->max_n_files, - percent(diskdinfo->map->n_files_in_map, diskdinfo->map->max_n_files)); + /* These stats are meaningless when doing IFS */ + if (!diskdinfo->doifs) { + storeAppendPrintf(sentry, "Filemap bits in use: %d of %d (%d%%)\n", + diskdinfo->map->n_files_in_map, diskdinfo->map->max_n_files, + percent(diskdinfo->map->n_files_in_map, diskdinfo->map->max_n_files)); + } #if HAVE_STATVFS #define fsbtoblk(num, fsbs, bs) \ (((fsbs) != 0 && (fsbs) < (bs)) ? \ @@ -1759,6 +1849,7 @@ storeDiskdDirDump(StoreEntry * entry, const char *name, SwapDir * s) { diskdinfo_t *diskdinfo = s->fsdata; + /* XXXX need to put whether we're doing IFS or not here! */ storeAppendPrintf(entry, "%s %s %s %d %d %d\n", name, "diskd", @@ -1795,11 +1886,15 @@ if (!fullpath) fullpath = fullfilename; fullpath[0] = '\0'; - snprintf(fullpath, SQUID_MAXPATHLEN, "%s/%02X/%02X/%08X", - SD->path, - ((filn / L2) / L2) % L1, - (filn / L2) % L2, - filn); + if (diskdinfo->doifs) + snprintf(fullpath, SQUID_MAXPATHLEN, "%s/%d", SD->path, filn); + else { + snprintf(fullpath, SQUID_MAXPATHLEN, "%s/%02X/%02X/%08X", + SD->path, + ((filn / L2) / L2) % L1, + (filn / L2) % L2, + filn); + } return fullpath; } @@ -1848,6 +1943,7 @@ int l1; int l2; int magic1, magic2; + int doifs; unsigned int read_only = 0; diskdinfo_t *diskdinfo; @@ -1873,9 +1969,16 @@ fatal("storeDiskdDirParse: invalid magic2 value"); - if ((token = strtok(NULL, w_space))) - if (!strcasecmp(token, "read-only")) + if ((token = strtok(NULL, w_space))) { + if (!strcasecmp(token, "read-only")) { read_only = 1; + token = strtok(NULL, w_space); + } + /* Check IFS */ + if (token && !strcasecmp(token, "ifs")) { + doifs = 1; + } + } sd->fsdata = diskdinfo = xcalloc(1, sizeof(*diskdinfo)); sd->index = index; @@ -1913,6 +2016,9 @@ sd->log.clean.start = storeDiskdDirWriteCleanStart; sd->log.clean.nextentry = storeDiskdDirCleanLogNextEntry; sd->log.clean.done = storeDiskdDirWriteCleanDone; + + /* Now, are we ifs or not? */ + diskdinfo->doifs = doifs; /* Initialise replacement policy stuff */ sd->repl = createRemovalPolicy(Config.replPolicy); Index: src/fs/diskd/store_diskd.h =================================================================== RCS file: /server/cvs-server/squid/squid/src/fs/diskd/store_diskd.h,v retrieving revision 1.5 diff -u -r1.5 store_diskd.h --- src/fs/diskd/store_diskd.h 2000/07/16 07:28:38 1.5 +++ src/fs/diskd/store_diskd.h 2000/10/12 09:06:18 @@ -32,6 +32,7 @@ } shm; int magic1; int magic2; + int doifs; /* Are we doing ifs or not ? */ }; struct _diskdstate_t { @@ -61,6 +62,7 @@ int size; int offset; int status; + int f_ino; /* used for the ifs option */ int shm_offset; } diomsg; Index: src/fs/diskd/store_io_diskd.c =================================================================== RCS file: /server/cvs-server/squid/squid/src/fs/diskd/store_io_diskd.c,v retrieving revision 1.16 diff -u -r1.16 store_io_diskd.c --- src/fs/diskd/store_io_diskd.c 2000/10/06 05:00:24 1.16 +++ src/fs/diskd/store_io_diskd.c 2000/10/12 09:06:19 @@ -76,6 +76,7 @@ sio->swap_dirn = SD->index; sio->mode = O_RDONLY; sio->callback = callback; + sio->file_callback = file_callback; sio->callback_data = callback_data; sio->e = e; cbdataLock(callback_data); @@ -123,10 +124,16 @@ diskd_stats.open_fail_queue_len++; return NULL; } - /* Allocate a number */ - f = storeDiskdDirMapBitAllocate(SD); - debug(81, 3) ("storeDiskdCreate: fileno %08X\n", f); + /* If we are in ifs mode, the FS gives us the file number */ + if (diskdinfo->doifs) + f = -1; + else { + /* Allocate a number */ + f = storeDiskdDirMapBitAllocate(SD); + debug(81, 3) ("storeDiskdCreate: fileno %08X\n", f); + } + sio = memAllocate(MEM_STORE_IO); cbdataAdd(sio, storeDiskdIOFreeEntry, MEM_STORE_IO); sio->fsstate = diskdstate = memPoolAlloc(diskd_state_pool); @@ -135,6 +142,7 @@ sio->swap_dirn = SD->index; sio->mode = O_WRONLY | O_CREAT | O_TRUNC; sio->callback = callback; + sio->file_callback = file_callback; sio->callback_data = callback_data; sio->e = e; cbdataLock(callback_data); @@ -145,7 +153,15 @@ diskdstate->id = diskd_stats.sio_id++; buf = storeDiskdShmGet(SD, &shm_offset); - xstrncpy(buf, storeDiskdDirFullPath(SD, f, NULL), SHMBUF_BLKSZ); + /* + * If we are in ifs mode, we open 'newfile', and do a delayed sfileno + * assignment once the open has completed + */ + if (diskdinfo->doifs) + snprintf(buf, SHMBUF_BLKSZ, "%s/newfile", SD->path); + else + xstrncpy(buf, storeDiskdDirFullPath(SD, f, NULL), SHMBUF_BLKSZ); + x = storeDiskdSend(_MQD_OPEN, SD, diskdstate->id, @@ -269,7 +285,10 @@ debug(81, 3) ("storeDiskdUnlink: dirno %d, fileno %08X\n", SD->index, e->swap_filen); storeDiskdDirReplRemove(e); - storeDiskdDirMapBitReset(SD, e->swap_filen); + if (!diskdinfo->doifs) { + /* If we are in ifs mode, we don't need to do this! */ + storeDiskdDirMapBitReset(SD, e->swap_filen); + } if (diskdinfo->away >= diskdinfo->magic1) { /* Damn, we need to issue a sync unlink here :( */ debug(50, 2) ("storeDiskUnlink: Out of queue space, sync unlink\n"); @@ -301,7 +320,14 @@ storeDiskdOpenDone(diomsg * M) { storeIOState *sio = M->callback_data; + diskdinfo_t *diskdinfo = INDEXSD(sio->swap_dirn)->fsdata; statCounter.syscalls.disk.opens++; + /* If we are in IFS mode, we get f_ino and set the swap filenumber there */ + if (diskdinfo->doifs) { + sio->swap_filen = M->f_ino; + /* Notify the upper levels that we've changed file number */ + sio->file_callback(sio->callback_data, 0, sio); + } debug(81, 3) ("storeDiskdOpenDone: dirno %d, fileno %08x status %d\n", sio->swap_dirn, sio->swap_filen, M->status); if (M->status < 0) {