/* worker_lfs.h
 * This file belongs to Worker, a filemanager for UNIX/X11.
 * Copyright (C) 2002-2005 Ralf Hoffmann.
 * You can contact me at: ralf@boomerangsworld.de
 *   or http://www.boomerangsworld.de/worker
 *
 * 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., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
 */
/* $Id: worker_lfs.h,v 1.11 2005/03/14 21:27:28 ralf Exp $ */

#ifndef WORKER_LFS_H
#define WORKER_LFS_H

#ifndef HAVE_AVFS

// this is for getting ???64 functions
#  ifdef HAVE_EXPLICIT_LFS
#    define _LARGEFILE64_SOURCE 1
  // that are standards. LARGEFILE64 should imply LARGEFILE but...
#    define _LARGEFILE_SOURCE 1
  // check for support
#    include <unistd.h>
#    ifndef _LFS_LARGEFILE
#      undef HAVE_EXPLICIT_LFS
#    endif
#    ifndef _LFS64_LARGEFILE
#      undef HAVE_EXPLICIT_LFS
#    endif
#    ifndef _LFS64_STDIO
#      undef HAVE_EXPLICIT_LFS
#    endif
#  endif

/* finally check if sizeof(loff_t) < 8 and undef HAVE_EXPL
   for the case the user set this define but loff_t cannot store
   big values */
#  if ( ! defined SIZEOF_LOFF_T ) || ( SIZEOF_LOFF_T < 8 )
#    undef HAVE_EXPLICIT_LFS
#  endif

#endif

// now some defines for this functions so I can use them transparently

#ifdef HAVE_AVFS
#  define worker_stat(x,y) virt_stat(x,y)
#  define worker_struct_stat struct stat
#elif defined HAVE_EXPLICIT_LFS
#  define worker_stat(x,y) stat64(x,y)
#  define worker_struct_stat struct stat64
#else
#  define worker_stat(x,y) stat(x,y)
#  define worker_struct_stat struct stat
#endif

#ifdef HAVE_AVFS
#  define worker_lstat(x,y) virt_lstat(x,y)
#elif defined HAVE_EXPLICIT_LFS
#  define worker_lstat(x,y) lstat64(x,y)
#else
#  define worker_lstat(x,y) lstat(x,y)
#endif

#ifdef HAVE_AVFS
#  define worker_open(x,y,z) virt_open(x,y,z)
#elif defined HAVE_EXPLICIT_LFS
#  define worker_open open64
#else
#  define worker_open open
#endif

#ifdef HAVE_AVFS
#  define worker_read(x,y,z) virt_read(x,y,z)
#else
#  define worker_read(x,y,z) read(x,y,z)
#endif

#ifdef HAVE_AVFS
#  define worker_write(x,y,z) virt_write(x,y,z)
#else
#  define worker_write(x,y,z) write(x,y,z)
#endif

#ifdef HAVE_AVFS
#  define worker_close(x) virt_close(x)
#else
#  define worker_close(x) close(x)
#endif

// fopen is not available for VFS
// if this will change in the future keep an eye
// on the code as the parser uses FILE pointers
// put does not use the VFS functions
// it is perhaps a good idea to leaf the fopen
// function outside VFS for this reason
#if defined HAVE_EXPLICIT_LFS
#  define worker_fopen(x,y) fopen64(x,y)
#else
#  define worker_fopen(x,y) fopen(x,y)
#endif

// fseek is not available for VFS
// read note for fopen too
#if defined HAVE_EXPLICIT_LFS
#  define worker_fseek(x,y,z) fseeko(x,y,z)
#else
#  define worker_fseek(x,y,z) fseek(x,y,z)
#endif

// fread/fwrite/fclose is not available for VFS
// read note for fopen too
#define worker_fread(a,b,c,d) fread(a,b,c,d)
#define worker_fwrite(a,b,c,d) fwrite(a,b,c,d)
#define worker_fclose(x) fclose(x)

#ifdef HAVE_AVFS
#  define worker_readdir(x) virt_readdir(x)
#  define worker_struct_dirent struct dirent
#elif defined HAVE_EXPLICIT_LFS
#  define worker_readdir(x) readdir64(x)
#  define worker_struct_dirent struct dirent64
#else
#  define worker_readdir(x) readdir(x)
#  define worker_struct_dirent struct dirent
#endif

// statvfs is not available for VFS
#if defined HAVE_EXPLICIT_LFS
#  define worker_statvfs(x,y) statvfs64(x,y)
#  define worker_struct_statvfs struct statvfs64
#else
#  define worker_statvfs(x,y) statvfs(x,y)
#  if defined HAVE_STATVFS_T
#    define worker_struct_statvfs statvfs_t
#  else
#    define worker_struct_statvfs struct statvfs
#  endif
#endif

#ifdef HAVE_AVFS
#  define worker_lseek virt_lseek
#else
#  define worker_lseek lseek
#endif

// doesn't exists for vfs so it can only be used for real directories
#define worker_chdir chdir

#ifdef HAVE_AVFS
#  define worker_opendir virt_opendir
#else
#  define worker_opendir opendir
#endif

#ifdef HAVE_AVFS
#  define worker_closedir virt_closedir
#else
#  define worker_closedir closedir
#endif

#ifdef HAVE_AVFS
#  define worker_fstat virt_fstat
#else
#  define worker_fstat fstat
#endif

#ifdef HAVE_AVFS
#  define worker_chmod virt_chmod
#else
#  define worker_chmod chmod
#endif

#ifdef HAVE_AVFS
#  define worker_chown virt_chown
#else
#  define worker_chown chown
#endif

#ifdef HAVE_AVFS
#  define worker_utime virt_utime
#else
#  define worker_utime utime
#endif

#ifdef HAVE_AVFS
#  define worker_readlink virt_readlink
#else
#  define worker_readlink readlink
#endif

#ifdef HAVE_AVFS
#  define worker_unlink virt_unlink
#else
#  define worker_unlink unlink
#endif

#ifdef HAVE_AVFS
#  define worker_symlink virt_symlink
#else
#  define worker_symlink symlink
#endif

#ifdef HAVE_AVFS
#  define worker_link virt_link
#else
#  define worker_link link
#endif

#ifdef HAVE_AVFS
#  define worker_mknod virt_mknod
#else
#  define worker_mknod mknod
#endif

#ifdef HAVE_AVFS
#  define worker_rename virt_rename
#else
#  define worker_rename rename
#endif

#ifdef HAVE_AVFS
#  define worker_rmdir virt_rmdir
#else
#  define worker_rmdir rmdir
#endif

#ifdef HAVE_AVFS
#  define worker_mkdir virt_mkdir
#else
#  define worker_mkdir mkdir
#endif

#ifdef HAVE_AVFS
#  define worker_access virt_access
#else
#  define worker_access access
#endif

#ifdef HAVE_AVFS
#  define worker_truncate virt_truncate
#else
#  define worker_truncate truncate
#endif

#ifdef HAVE_AVFS
#  define worker_lchown virt_lchown
#else
#  define worker_lchown lchown
#endif

#ifdef HAVE_AVFS
#  define worker_ftruncate virt_ftruncate
#else
#  define worker_ftruncate ftruncate
#endif

#ifdef HAVE_AVFS
#  define worker_fchmod virt_fchmod
#else
#  define worker_fchmod fchmod
#endif

#ifdef HAVE_AVFS
#  define worker_fchown virt_fchown
#else
#  define worker_fchown fchown
#endif

#ifdef HAVE_AVFS
#  define worker_rewinddir virt_rewinddir
#else
#  define worker_rewinddir rewinddir
#endif

// mmap/munmap is not supported by the VFS
// but I just prevent the compilation
#ifdef HAVE_AVFS
#  define worker_mmap mmap_UNSUPPORTED_BY_VFS
#  define worker_munmap munmap_UNSUPPORTED_BY_VFS
#else
#  define wokrer_mmap mmap
#  define worker_munmap munmap
#endif

// remove is only a wrapper for unlink/rmdir
// There is also a wrapper "worker_myremove"
// if this is not available
#ifdef HAVE_AVFS
#  define worker_remove virt_remove
#else
#  define worker_remove remove
#endif

#ifdef HAVE_AVFS
#  define worker_islocal virt_islocal
#else
#  define worker_islocal worker_myislocal
#endif

// now some final define if we support LFS
// this define doesn't change anything about the support
// but helps me to simplify coding
// at the time of this writing it's only used for the about
// requester
#undef WORKER_LFS_SUPPORTED
#if ( defined SIZEOF_LOFF_T ) && ( SIZEOF_LOFF_T == 8 )
#  if ( defined HAVE_EXPLICIT_LFS ) || ( ( defined SIZEOF_OFF_T ) && ( SIZEOF_OFF_T == 8 ) )
#    define WORKER_LFS_SUPPORTED
#  endif
#endif

#endif
