Skip to content
Snippets Groups Projects
Commit 88d0d791 authored by rswindell's avatar rswindell
Browse files

New wrapper module targeted specifically at open file-related RTL functions.

Will replace smbwrap.* at some point.
parent 3598a794
No related branches found
No related tags found
No related merge requests found
/* filewrap.c */
/* File-related system-call wrappers */
/* $Id$ */
/****************************************************************************
* @format.tab-size 4 (Plain Text/Source Code File Header) *
* @format.use-tabs true (see http://www.synchro.net/ptsc_hdr.html) *
* *
* Copyright 2000 Rob Swindell - http://www.synchro.net/copyright.html *
* *
* 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. *
* See the GNU General Public License for more details: gpl.txt or *
* http://www.fsf.org/copyleft/gpl.html *
* *
* Anonymous FTP access to the most recent released source is available at *
* ftp://vert.synchro.net, ftp://cvs.synchro.net and ftp://ftp.synchro.net *
* *
* Anonymous CVS access to the development source and modification history *
* is available at cvs.synchro.net:/cvsroot/sbbs, example: *
* cvs -d :pserver:anonymous@cvs.synchro.net:/cvsroot/sbbs login *
* (just hit return, no password is necessary) *
* cvs -d :pserver:anonymous@cvs.synchro.net:/cvsroot/sbbs checkout src *
* *
* For Synchronet coding style and modification guidelines, see *
* http://www.synchro.net/source.html *
* *
* You are encouraged to submit any modifications (preferably in Unix diff *
* format) via e-mail to mods@synchro.net *
* *
* Note: If this box doesn't appear square, then you need to fix your tabs. *
****************************************************************************/
/* OS-specific */
#if defined(__unix__)
#include <glob.h> /* glob() wildcard matching */
#include <string.h> /* strlen() */
#include <unistd.h> /* getpid() */
#include <fcntl.h> /* fcntl() file/record locking */
#endif
/* ANSI */
#include <sys/types.h> /* _dev_t */
#include <sys/stat.h> /* struct stat */
#include "filewrap.h" /* Verify prototypes */
/****************************************************************************/
/* Returns the modification time of the file in 'fd' */
/****************************************************************************/
time_t DLLCALL filetime(int fd)
{
struct stat st;
if(fstat(fd, &st)!=0)
return(-1);
return(st.st_mtime);
}
#if defined(__unix__)
/****************************************************************************/
/* Returns the length of the file in 'fd' */
/****************************************************************************/
long DLLCALL filelength(int fd)
{
struct stat st;
if(fstat(fd, &st)!=0)
return(-1L);
return(st.st_size);
}
/* Sets a lock on a portion of a file */
int DLLCALL lock(int fd, long pos, int len)
{
int flags;
struct flock alock;
if((flags=fcntl(fd,F_GETFL))<0)
return -1;
if(flags==O_RDONLY)
alock.l_type = F_RDLCK; // set read lock to prevent writes
else
alock.l_type = F_WRLCK; // set write lock to prevent all access
alock.l_whence = L_SET; // SEEK_SET
alock.l_start = pos;
alock.l_len = len;
return fcntl(fd, F_SETLK, &alock);
}
/* Removes a lock from a file record */
int DLLCALL unlock(int fd, long pos, int len)
{
struct flock alock;
alock.l_type = F_UNLCK; // remove the lock
alock.l_whence = L_SET;
alock.l_start = pos;
alock.l_len = len;
return fcntl(fd, F_SETLK, &alock);
}
/* Opens a file in specified sharing (file-locking) mode */
int DLLCALL sopen(char *fn, int access, int share)
{
int fd;
struct flock alock;
if ((fd = open(fn, access, S_IREAD|S_IWRITE)) < 0)
return -1;
if (share == SH_DENYNO)
// no lock needed
return fd;
alock.l_type = share;
alock.l_whence = L_SET;
alock.l_start = 0;
alock.l_len = 0; // lock to EOF
if (fcntl(fd, F_SETLK, &alock) < 0) {
close(fd);
return -1;
}
return fd;
}
#elif defined _MSC_VER || defined __MINGW32__
#include <io.h> /* tell */
#include <stdio.h> /* SEEK_SET */
#include <sys/locking.h> /* _locking */
/* Fix MinGW locking.h typo */
#if defined LK_UNLOCK && !defined LK_UNLCK
#define LK_UNLCK LK_UNLOCK
#endif
int DLLCALL lock(int file, long offset, int size)
{
int i;
long pos;
pos=tell(file);
if(offset!=pos)
lseek(file, offset, SEEK_SET);
i=_locking(file,LK_NBLCK,size);
if(offset!=pos)
lseek(file, pos, SEEK_SET);
return(i);
}
int DLLCALL unlock(int file, long offset, int size)
{
int i;
long pos;
pos=tell(file);
if(offset!=pos)
lseek(file, offset, SEEK_SET);
i=_locking(file,LK_UNLCK,size);
if(offset!=pos)
lseek(file, pos, SEEK_SET);
return(i);
}
#endif /* !Unix && (MSVC || MinGW) */
/* filewrap.h */
/* File system-call wrappers */
/* $Id$ */
/****************************************************************************
* @format.tab-size 4 (Plain Text/Source Code File Header) *
* @format.use-tabs true (see http://www.synchro.net/ptsc_hdr.html) *
* *
* Copyright 2000 Rob Swindell - http://www.synchro.net/copyright.html *
* *
* 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. *
* See the GNU General Public License for more details: gpl.txt or *
* http://www.fsf.org/copyleft/gpl.html *
* *
* Anonymous FTP access to the most recent released source is available at *
* ftp://vert.synchro.net, ftp://cvs.synchro.net and ftp://ftp.synchro.net *
* *
* Anonymous CVS access to the development source and modification history *
* is available at cvs.synchro.net:/cvsroot/sbbs, example: *
* cvs -d :pserver:anonymous@cvs.synchro.net:/cvsroot/sbbs login *
* (just hit return, no password is necessary) *
* cvs -d :pserver:anonymous@cvs.synchro.net:/cvsroot/sbbs checkout src *
* *
* For Synchronet coding style and modification guidelines, see *
* http://www.synchro.net/source.html *
* *
* You are encouraged to submit any modifications (preferably in Unix diff *
* format) via e-mail to mods@synchro.net *
* *
* Note: If this box doesn't appear square, then you need to fix your tabs. *
****************************************************************************/
#ifndef _FILEWRAP_H
#define _FILEWRAP_H
/**********/
/* Macros */
/**********/
#if defined(_WIN32)
#include <io.h> /* _sopen */
#include <sys/stat.h> /* S_IREAD */
#include <fcntl.h> /* O_BINARY */
#include <windows.h> /* OF_SHARE_ */
#define sopen(f,o,s) _sopen(f,o,s,S_IREAD|S_IWRITE)
#define close(f) _close(f)
#ifndef SH_DENYNO
#define SH_DENYNO OF_SHARE_DENY_NONE
#define SH_DENYWR OF_SHARE_DENY_WRITE
#define SH_DENYRW OF_SHARE_EXCLUSIVE
#endif
#ifndef O_DENYNONE
#define O_DENYNONE SH_DENYNO
#endif
#elif defined(__unix__)
#include <fcntl.h>
#define O_TEXT 0 /* all files in binary mode on Unix */
#define O_BINARY 0 /* all files in binary mode on Unix */
#define O_DENYNONE (1<<31) /* req'd for Baja/nopen compatibility */
#define SH_DENYNO 2 // no locks
#define SH_DENYRW F_WRLCK // exclusive lock
#define SH_DENYWR F_RDLCK // shareable lock
#define chsize(fd,size) ftruncate(fd,size)
#define tell(fd) lseek(fd,0,SEEK_CUR)
#endif
/**************/
/* Prototypes */
/**************/
#ifdef DLLEXPORT
#undef DLLEXPORT
#endif
#ifdef DLLCALL
#undef DLLCALL
#endif
#ifdef _WIN32
#ifdef WRAPPER_DLL
#define DLLEXPORT __declspec(dllexport)
#else
#define DLLEXPORT __declspec(dllimport)
#endif
#ifdef __BORLANDC__
#define DLLCALL __stdcall
#else
#define DLLCALL
#endif
#else /* !_WIN32 */
#define DLLEXPORT
#define DLLCALL
#endif
#ifdef __cplusplus
extern "C" {
#endif
#if !defined(__BORLANDC__)
DLLEXPORT int DLLCALL lock(int fd, long pos, int len);
DLLEXPORT int DLLCALL unlock(int fd, long pos, int len);
#endif
#if defined(__unix__)
DLLEXPORT int DLLCALL sopen(char *fn, int access, int share);
DLLEXPORT long DLLCALL filelength(int fd);
#endif
DLLEXPORT time_t DLLCALL filetime(int fd);
#ifdef __cplusplus
}
#endif
#endif /* Don't add anything after this line */
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment