2014-06-01 17:55:23 +00:00
/*
* This file is part of the DXX - Rebirth project < http : //www.dxx-rebirth.com/>.
* It is copyright by its individual contributors , as recorded in the
* project ' s Git history . See COPYING . txt at the top level for license
* terms and a link to the Git history .
*/
2006-03-20 17:12:09 +00:00
/*
*
* Some simple physfs extensions
*
*/
2015-01-12 00:26:03 +00:00
# pragma once
2006-03-20 17:12:09 +00:00
2013-12-19 21:32:40 +00:00
# include <cstddef>
2014-07-20 03:48:27 +00:00
# include <memory>
2006-03-20 17:12:09 +00:00
# include <string.h>
# include <stdarg.h>
2010-09-17 10:44:21 +00:00
// When PhysicsFS can *easily* be built as a framework on Mac OS X,
// the framework form will be supported again -kreatordxx
# if 1 //!(defined(__APPLE__) && defined(__MACH__))
2006-03-20 17:12:09 +00:00
# include <physfs.h>
2007-04-09 02:41:45 +00:00
# else
# include <physfs/physfs.h>
# endif
2006-03-20 17:12:09 +00:00
2013-12-08 23:37:40 +00:00
# include "fmtcheck.h"
2013-06-27 02:35:22 +00:00
# include "dxxsconf.h"
2012-07-07 18:35:06 +00:00
# include "dxxerror.h"
2006-03-20 17:12:09 +00:00
# include "vecmat.h"
2014-07-03 01:47:29 +00:00
# include "byteutil.h"
2006-10-02 13:55:58 +00:00
2012-11-11 22:12:51 +00:00
# ifdef __cplusplus
2014-12-20 04:36:10 +00:00
# include <stdexcept>
2014-06-22 03:54:35 +00:00
# include "u_mem.h"
# include "pack.h"
2015-01-12 00:26:02 +00:00
# include "ntstring.h"
2014-06-22 03:54:35 +00:00
# include "compiler-array.h"
# include "compiler-static_assert.h"
# include "compiler-type_traits.h"
# ifdef DXX_HAVE_BUILTIN_CONSTANT_P
2014-09-20 23:47:27 +00:00
# define _DXX_PHYSFS_CHECK_SIZE_CONSTANT(S,v) (__builtin_constant_p((S) > v) && (S) > v)
# define _DXX_PHYSFS_CHECK_SIZE(S,C,v) _DXX_PHYSFS_CHECK_SIZE_CONSTANT(static_cast<size_t>(S) * static_cast<size_t>(C), v)
# define DXX_PHYSFS_CHECK_READ_SIZE_OBJECT_SIZE(S,C,v) \
( void ) ( __builtin_object_size ( v , 1 ) ! = static_cast < size_t > ( - 1 ) & & _DXX_PHYSFS_CHECK_SIZE ( S , C , __builtin_object_size ( v , 1 ) ) & & ( DXX_ALWAYS_ERROR_FUNCTION ( dxx_trap_overwrite , " read size exceeds element size " ) , 0 ) )
# define DXX_PHYSFS_CHECK_READ_SIZE_ARRAY_SIZE(S,C) \
( void ) ( _DXX_PHYSFS_CHECK_SIZE ( S , C , sizeof ( v ) ) & & ( DXX_ALWAYS_ERROR_FUNCTION ( dxx_trap_overwrite , " read size exceeds array size " ) , 0 ) )
# define DXX_PHYSFS_CHECK_WRITE_SIZE_OBJECT_SIZE(S,C,v) \
( void ) ( __builtin_object_size ( v , 1 ) ! = static_cast < size_t > ( - 1 ) & & _DXX_PHYSFS_CHECK_SIZE ( S , C , __builtin_object_size ( v , 1 ) ) & & ( DXX_ALWAYS_ERROR_FUNCTION ( dxx_trap_overwrite , " write size exceeds element size " ) , 0 ) )
2014-06-22 03:54:35 +00:00
# define DXX_PHYSFS_CHECK_WRITE_ELEMENT_SIZE_CONSTANT(S,C) \
2014-07-31 03:52:57 +00:00
( ( void ) ( dxx_builtin_constant_p ( S ) | | dxx_builtin_constant_p ( C ) | | \
( DXX_ALWAYS_ERROR_FUNCTION ( dxx_trap_nonconstant_size , " array element size is not constant " ) , 0 ) ) )
2014-06-22 03:54:35 +00:00
# define DXX_PHYSFS_CHECK_WRITE_SIZE_ARRAY_SIZE(S,C) \
2014-09-20 23:47:27 +00:00
( ( void ) ( _DXX_PHYSFS_CHECK_SIZE ( S , C , sizeof ( v ) ) & & \
2014-07-31 03:52:57 +00:00
( DXX_ALWAYS_ERROR_FUNCTION ( dxx_trap_overread , " write size exceeds array size " ) , 0 ) ) )
2014-06-22 03:54:35 +00:00
# else
2014-09-20 23:47:27 +00:00
# define DXX_PHYSFS_CHECK_READ_SIZE_OBJECT_SIZE(S,C,v) ((void)0)
# define DXX_PHYSFS_CHECK_READ_SIZE_ARRAY_SIZE(S,C) ((void)0)
2014-09-22 03:34:08 +00:00
# define DXX_PHYSFS_CHECK_WRITE_SIZE_OBJECT_SIZE(S,C,v) ((void)0)
2014-07-31 03:52:57 +00:00
# define DXX_PHYSFS_CHECK_WRITE_ELEMENT_SIZE_CONSTANT(S,C) ((void)0)
# define DXX_PHYSFS_CHECK_WRITE_SIZE_ARRAY_SIZE(S,C) ((void)0)
2014-06-22 03:54:35 +00:00
# endif
# define DXX_PHYSFS_CHECK_WRITE_CONSTANTS(S,C) \
2014-07-31 03:52:57 +00:00
( ( void ) ( DXX_PHYSFS_CHECK_WRITE_ELEMENT_SIZE_CONSTANT ( S , C ) , \
DXX_PHYSFS_CHECK_WRITE_SIZE_ARRAY_SIZE ( S , C ) , 0 ) ) \
2014-06-22 03:54:35 +00:00
2014-06-22 03:54:35 +00:00
template < typename V >
static inline typename tt : : enable_if < tt : : is_integral < V > : : value , PHYSFS_sint64 > : : type PHYSFSX_check_read ( PHYSFS_file * file , V * v , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
static_assert ( tt : : is_pod < V > : : value , " non-POD integral value read " ) ;
2014-09-20 23:47:27 +00:00
DXX_PHYSFS_CHECK_READ_SIZE_OBJECT_SIZE ( S , C , v ) ;
2014-06-22 03:54:35 +00:00
return PHYSFS_read ( file , v , S , C ) ;
}
template < typename V >
static inline typename tt : : enable_if < ! tt : : is_integral < V > : : value , PHYSFS_sint64 > : : type PHYSFSX_check_read ( PHYSFS_file * file , V * v , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
static_assert ( tt : : is_pod < V > : : value , " non-POD non-integral value read " ) ;
2014-09-20 23:47:27 +00:00
DXX_PHYSFS_CHECK_READ_SIZE_OBJECT_SIZE ( S , C , v ) ;
2014-06-22 03:54:35 +00:00
return PHYSFS_read ( file , v , S , C ) ;
}
template < typename V >
static inline typename tt : : enable_if < tt : : is_array < V > : : value , PHYSFS_sint64 > : : type PHYSFSX_check_read ( PHYSFS_file * file , V & v , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
typedef typename tt : : remove_extent < V > : : type V0 ;
static_assert ( tt : : is_pod < V0 > : : value , " C array of non-POD elements read " ) ;
2014-09-20 23:47:27 +00:00
DXX_PHYSFS_CHECK_READ_SIZE_ARRAY_SIZE ( S , C ) ;
2014-06-22 03:54:35 +00:00
return PHYSFSX_check_read ( file , & v [ 0 ] , S , C ) ;
}
template < typename V , std : : size_t N >
static inline PHYSFS_sint64 PHYSFSX_check_read ( PHYSFS_file * file , array < V , N > & v , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
static_assert ( tt : : is_pod < V > : : value , " C++ array of non-POD elements read " ) ;
2014-09-20 23:47:27 +00:00
DXX_PHYSFS_CHECK_READ_SIZE_ARRAY_SIZE ( S , C ) ;
2014-06-22 03:54:35 +00:00
return PHYSFSX_check_read ( file , & v [ 0 ] , S , C ) ;
}
2014-07-20 03:48:27 +00:00
template < typename V , typename D >
static inline PHYSFS_sint64 PHYSFSX_check_read ( PHYSFS_file * file , const std : : unique_ptr < V , D > & v , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
2014-09-20 23:47:27 +00:00
return PHYSFSX_check_read ( file , v . get ( ) , S , C ) ;
2014-07-20 03:48:27 +00:00
}
2014-06-22 03:54:35 +00:00
template < typename V >
static inline PHYSFS_sint64 PHYSFSX_check_read ( PHYSFS_file * file , const RAIIdmem < V > & v , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
2015-02-17 03:52:59 +00:00
return PHYSFSX_check_read ( file , v . get ( ) , S , C ) ;
2014-06-22 03:54:35 +00:00
}
2014-06-22 03:54:35 +00:00
template < typename V >
static inline typename tt : : enable_if < tt : : is_integral < V > : : value , PHYSFS_sint64 > : : type PHYSFSX_check_write ( PHYSFS_file * file , const V * v , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
static_assert ( tt : : is_pod < V > : : value , " non-POD integral value written " ) ;
DXX_PHYSFS_CHECK_WRITE_ELEMENT_SIZE_CONSTANT ( S , C ) ;
2014-09-20 23:47:27 +00:00
DXX_PHYSFS_CHECK_WRITE_SIZE_OBJECT_SIZE ( S , C , v ) ;
2014-06-22 03:54:35 +00:00
return PHYSFS_write ( file , v , S , C ) ;
}
template < typename V >
static inline typename tt : : enable_if < ! tt : : is_integral < V > : : value , PHYSFS_sint64 > : : type PHYSFSX_check_write ( PHYSFS_file * file , const V * v , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
static_assert ( tt : : is_pod < V > : : value , " non-POD non-integral value written " ) ;
2014-09-28 21:37:37 +00:00
DXX_PHYSFS_CHECK_WRITE_SIZE_OBJECT_SIZE ( S , C , v ) ;
2014-06-22 03:54:35 +00:00
return PHYSFS_write ( file , v , S , C ) ;
}
template < typename V , std : : size_t N >
static inline typename tt : : enable_if < tt : : is_array < V > : : value , PHYSFS_sint64 > : : type PHYSFSX_check_write ( PHYSFS_file * file , const V ( & v ) [ N ] , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
typedef typename tt : : remove_extent < V > : : type V0 ;
static_assert ( tt : : is_pod < V0 > : : value , " C array of non-POD elements written " ) ;
DXX_PHYSFS_CHECK_WRITE_CONSTANTS ( S , C ) ;
return PHYSFSX_check_write ( file , & v [ 0 ] , S , C ) ;
}
template < typename V , std : : size_t N >
static inline PHYSFS_sint64 PHYSFSX_check_write ( PHYSFS_file * file , const array < V , N > & v , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
static_assert ( tt : : is_pod < V > : : value , " C++ array of non-POD elements written " ) ;
DXX_PHYSFS_CHECK_WRITE_CONSTANTS ( S , C ) ;
return PHYSFSX_check_write ( file , & v [ 0 ] , S , C ) ;
}
2014-07-24 03:12:57 +00:00
template < typename T , typename D >
static inline PHYSFS_sint64 PHYSFSX_check_write ( PHYSFS_file * file , const std : : unique_ptr < T , D > & p , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
2014-09-20 23:47:27 +00:00
return PHYSFSX_check_write ( file , p . get ( ) , S , C ) ;
2014-07-24 03:12:57 +00:00
}
2014-06-22 03:54:35 +00:00
template < typename V >
static inline PHYSFS_sint64 PHYSFSX_check_write ( PHYSFS_file * file , const RAIIdmem < V > & v , PHYSFS_uint32 S , PHYSFS_uint32 C )
{
2015-02-17 03:52:59 +00:00
return PHYSFSX_check_write ( file , v . get ( ) , S , C ) ;
2014-06-22 03:54:35 +00:00
}
2014-06-22 03:54:35 +00:00
template < typename V >
PHYSFS_sint64 PHYSFSX_check_read ( PHYSFS_file * file , exact_type < V > v , PHYSFS_uint32 S , PHYSFS_uint32 C ) DXX_CXX11_EXPLICIT_DELETE ;
2014-06-22 03:54:35 +00:00
template < typename V >
PHYSFS_sint64 PHYSFSX_check_write ( PHYSFS_file * file , exact_type < V > v , PHYSFS_uint32 S , PHYSFS_uint32 C ) DXX_CXX11_EXPLICIT_DELETE ;
2014-09-28 21:41:06 +00:00
template < typename V >
PHYSFS_sint64 PHYSFSX_check_read ( PHYSFS_file * file , V * * v , PHYSFS_uint32 S , PHYSFS_uint32 C ) DXX_CXX11_EXPLICIT_DELETE ;
template < typename V >
PHYSFS_sint64 PHYSFSX_check_write ( PHYSFS_file * file , V * * v , PHYSFS_uint32 S , PHYSFS_uint32 C ) DXX_CXX11_EXPLICIT_DELETE ;
2014-06-22 03:54:35 +00:00
# define PHYSFS_read(F,V,S,C) PHYSFSX_check_read(F,V,S,C)
2014-06-22 03:54:35 +00:00
# define PHYSFS_write(F,V,S,C) PHYSFSX_check_write(F,V,S,C)
2012-11-11 22:12:51 +00:00
2015-01-28 03:42:53 +00:00
bool PHYSFSX_init ( int argc , char * argv [ ] ) ;
2006-03-20 17:12:09 +00:00
2013-12-23 23:12:42 +00:00
static inline PHYSFS_sint16 PHYSFSX_readSXE16 ( PHYSFS_file * file , int swap )
2009-10-05 02:51:37 +00:00
{
PHYSFS_sint16 val ;
2010-06-14 08:13:16 +00:00
2009-10-05 02:51:37 +00:00
PHYSFS_read ( file , & val , sizeof ( val ) , 1 ) ;
2010-06-14 08:13:16 +00:00
2009-10-05 02:51:37 +00:00
return swap ? SWAPSHORT ( val ) : val ;
}
2013-12-23 23:12:42 +00:00
static inline PHYSFS_sint32 PHYSFSX_readSXE32 ( PHYSFS_file * file , int swap )
2009-10-05 02:51:37 +00:00
{
PHYSFS_sint32 val ;
2010-06-14 08:13:16 +00:00
2009-10-05 02:51:37 +00:00
PHYSFS_read ( file , & val , sizeof ( val ) , 1 ) ;
2010-06-14 08:13:16 +00:00
2009-10-05 02:51:37 +00:00
return swap ? SWAPINT ( val ) : val ;
}
2006-03-20 17:12:09 +00:00
static inline int PHYSFSX_writeU8 ( PHYSFS_file * file , PHYSFS_uint8 val )
{
return PHYSFS_write ( file , & val , 1 , 1 ) ;
}
2012-07-22 23:17:54 +00:00
static inline int PHYSFSX_writeString ( PHYSFS_file * file , const char * s )
2006-03-20 17:12:09 +00:00
{
return PHYSFS_write ( file , s , 1 , strlen ( s ) + 1 ) ;
}
2013-12-19 21:32:40 +00:00
static inline int PHYSFSX_puts ( PHYSFS_file * file , const char * s , size_t len ) __attribute_nonnull ( ) ;
static inline int PHYSFSX_puts ( PHYSFS_file * file , const char * s , size_t len )
2006-03-20 17:12:09 +00:00
{
2013-12-19 21:32:40 +00:00
return PHYSFS_write ( file , s , 1 , len ) ;
2006-03-20 17:12:09 +00:00
}
2013-12-19 21:32:40 +00:00
template < size_t len >
static inline int PHYSFSX_puts_literal ( PHYSFS_file * file , const char ( & s ) [ len ] ) __attribute_nonnull ( ) ;
template < size_t len >
static inline int PHYSFSX_puts_literal ( PHYSFS_file * file , const char ( & s ) [ len ] )
{
2014-08-26 02:41:33 +00:00
return PHYSFSX_puts ( file , s , len - 1 ) ;
2013-12-19 21:32:40 +00:00
}
# define PHYSFSX_puts(A1,S,...) (PHYSFSX_puts(A1,S, _dxx_call_puts_parameter2(1, ## __VA_ARGS__, strlen(S))))
2011-06-01 07:59:55 +00:00
static inline int PHYSFSX_fgetc ( PHYSFS_file * const fp )
{
unsigned char c ;
if ( PHYSFS_read ( fp , & c , 1 , 1 ) ! = 1 )
return EOF ;
return c ;
}
static inline int PHYSFSX_fseek ( PHYSFS_file * fp , long int offset , int where )
{
int c , goal_position ;
switch ( where )
{
case SEEK_SET :
goal_position = offset ;
break ;
case SEEK_CUR :
goal_position = PHYSFS_tell ( fp ) + offset ;
break ;
case SEEK_END :
goal_position = PHYSFS_fileLength ( fp ) + offset ;
break ;
default :
return 1 ;
}
c = PHYSFS_seek ( fp , goal_position ) ;
return ! c ;
}
2014-09-07 19:48:10 +00:00
template < std : : size_t N >
struct PHYSFSX_gets_line_t
{
PHYSFSX_gets_line_t ( ) = default ;
PHYSFSX_gets_line_t ( const PHYSFSX_gets_line_t & ) = delete ;
2014-12-18 04:12:38 +00:00
PHYSFSX_gets_line_t & operator = ( const PHYSFSX_gets_line_t & ) = delete ;
PHYSFSX_gets_line_t ( PHYSFSX_gets_line_t & & ) = default ;
PHYSFSX_gets_line_t & operator = ( PHYSFSX_gets_line_t & & ) = default ;
2014-12-20 04:36:10 +00:00
typedef array < char , N > line_t ;
2014-09-07 19:48:10 +00:00
# ifdef DXX_HAVE_POISON
/* Force onto heap to improve checker accuracy */
std : : unique_ptr < line_t > m_line ;
2014-12-20 04:36:10 +00:00
const line_t & line ( ) const { return * m_line . get ( ) ; }
line_t & line ( ) { return * m_line . get ( ) ; }
line_t & next ( )
2014-09-07 19:48:10 +00:00
{
m_line . reset ( new line_t ) ;
2014-12-20 04:36:10 +00:00
return * m_line . get ( ) ;
2014-09-07 19:48:10 +00:00
}
# else
line_t m_line ;
2014-12-20 04:36:10 +00:00
const line_t & line ( ) const { return m_line ; }
line_t & line ( ) { return m_line ; }
line_t & next ( ) { return m_line ; }
2014-09-07 19:48:10 +00:00
# endif
2014-12-20 04:36:10 +00:00
operator line_t & ( ) { return line ( ) ; }
operator const line_t & ( ) const { return line ( ) ; }
operator char * ( ) { return line ( ) . data ( ) ; }
operator const char * ( ) const { return line ( ) . data ( ) ; }
typename line_t : : reference operator [ ] ( typename line_t : : size_type i ) { return line ( ) [ i ] ; }
2015-01-03 23:44:32 +00:00
typename line_t : : reference operator [ ] ( int i ) { return operator [ ] ( static_cast < typename line_t : : size_type > ( i ) ) ; }
2014-12-20 04:36:10 +00:00
typename line_t : : const_reference operator [ ] ( typename line_t : : size_type i ) const { return line ( ) [ i ] ; }
2015-01-03 23:44:32 +00:00
typename line_t : : const_reference operator [ ] ( int i ) const { return operator [ ] ( static_cast < typename line_t : : size_type > ( i ) ) ; }
2014-12-20 04:36:10 +00:00
constexpr std : : size_t size ( ) const { return N ; }
2014-12-22 04:35:48 +00:00
typename line_t : : const_iterator begin ( ) const { return line ( ) . begin ( ) ; }
typename line_t : : const_iterator end ( ) const { return line ( ) . end ( ) ; }
2014-09-07 19:48:10 +00:00
} ;
template < >
struct PHYSFSX_gets_line_t < 0 >
{
std : : unique_ptr < char [ ] > m_line ;
std : : size_t m_length ;
PHYSFSX_gets_line_t ( std : : size_t n ) :
2014-12-20 04:36:10 +00:00
# ifndef DXX_HAVE_POISON
2014-09-07 19:48:10 +00:00
m_line ( new char [ n ] ) ,
2014-12-20 04:36:10 +00:00
# endif
2014-09-07 19:48:10 +00:00
m_length ( n )
{
}
char * line ( ) { return m_line . get ( ) ; }
2014-12-20 04:36:10 +00:00
const char * line ( ) const { return m_line . get ( ) ; }
2014-09-07 19:48:10 +00:00
char * next ( )
{
# ifdef DXX_HAVE_POISON
m_line . reset ( new char [ m_length ] ) ;
# endif
2014-12-20 04:36:10 +00:00
return m_line . get ( ) ;
2014-09-07 19:48:10 +00:00
}
std : : size_t size ( ) const { return m_length ; }
operator const char * ( ) const { return m_line . get ( ) ; }
const char * begin ( ) const { return * this ; }
const char * end ( ) const { return begin ( ) + m_length ; }
2014-10-12 22:11:28 +00:00
operator const void * ( ) const = delete ;
2014-09-07 19:48:10 +00:00
} ;
2015-01-12 00:26:03 +00:00
class PHYSFSX_fgets_t
2015-01-12 00:26:02 +00:00
{
2015-01-12 00:26:03 +00:00
static char * get ( char * buf , std : : size_t n , PHYSFS_file * const fp ) ;
static char * get ( char * buf , std : : size_t offset , std : : size_t n , PHYSFS_file * const fp )
{
if ( offset > n )
throw std : : invalid_argument ( " offset too large " ) ;
return get ( & buf [ offset ] , n - offset , fp ) ;
}
public :
template < std : : size_t n >
__attribute_nonnull ( )
char * operator ( ) ( PHYSFSX_gets_line_t < n > & buf , PHYSFS_file * const fp , std : : size_t offset = 0 ) const
{
return get ( & buf . next ( ) [ 0 ] , offset , buf . size ( ) , fp ) ;
}
template < std : : size_t n >
__attribute_nonnull ( )
char * operator ( ) ( ntstring < n > & buf , PHYSFS_file * const fp , std : : size_t offset = 0 ) const
{
auto r = get ( & buf . data ( ) [ 0 ] , offset , buf . size ( ) , fp ) ;
buf . back ( ) = 0 ;
return r ;
}
} ;
2015-01-12 00:26:02 +00:00
2015-01-12 00:26:03 +00:00
const PHYSFSX_fgets_t PHYSFSX_fgets { } ;
2013-11-23 00:13:36 +00:00
2013-06-27 02:35:22 +00:00
static inline int PHYSFSX_printf ( PHYSFS_file * file , const char * format , . . . ) __attribute_format_printf ( 2 , 3 ) ;
2012-07-22 23:17:54 +00:00
static inline int PHYSFSX_printf ( PHYSFS_file * file , const char * format , . . . )
2013-12-19 21:32:40 +00:00
# define PHYSFSX_printf(A1,F,...) dxx_call_printf_checked(PHYSFSX_printf,PHYSFSX_puts_literal,(A1),(F),##__VA_ARGS__)
2006-03-20 17:12:09 +00:00
{
char buffer [ 1024 ] ;
va_list args ;
va_start ( args , format ) ;
2013-12-19 21:32:40 +00:00
size_t len = vsnprintf ( buffer , sizeof ( buffer ) , format , args ) ;
2013-12-01 18:27:54 +00:00
va_end ( args ) ;
2006-03-20 17:12:09 +00:00
2013-12-19 21:32:40 +00:00
return PHYSFSX_puts ( file , buffer , len ) ;
2006-03-20 17:12:09 +00:00
}
# define PHYSFSX_writeFix PHYSFS_writeSLE32
# define PHYSFSX_writeFixAng PHYSFS_writeSLE16
2014-10-26 22:08:58 +00:00
static inline int PHYSFSX_writeVector ( PHYSFS_file * file , const vms_vector & v )
2006-03-20 17:12:09 +00:00
{
2014-10-26 22:08:58 +00:00
if ( PHYSFSX_writeFix ( file , v . x ) < 1 | |
PHYSFSX_writeFix ( file , v . y ) < 1 | |
PHYSFSX_writeFix ( file , v . z ) < 1 )
2006-03-20 17:12:09 +00:00
return 0 ;
return 1 ;
}
2012-07-07 19:11:48 +00:00
# define define_read_helper(T,N,F) \
static inline T N ( const char * func , const unsigned line , PHYSFS_file * file ) \
{ \
T i ; \
if ( ! ( F ) ( file , & i ) ) \
{ \
2015-02-05 03:03:49 +00:00
( Error ) ( func , line , " reading " # T " in " # N " () at %lu " , static_cast < unsigned long > ( ( PHYSFS_tell ) ( file ) ) ) ; \
2012-07-07 19:11:48 +00:00
} \
return i ; \
2011-06-01 07:59:55 +00:00
}
2012-07-07 19:11:48 +00:00
static inline sbyte PHYSFSX_readS8 ( PHYSFS_file * file , sbyte * b )
2011-06-01 07:59:55 +00:00
{
2012-07-07 19:11:48 +00:00
return ( PHYSFS_read ( file , b , sizeof ( * b ) , 1 ) = = 1 ) ;
2011-06-01 07:59:55 +00:00
}
2012-07-07 19:11:48 +00:00
define_read_helper ( sbyte , PHYSFSX_readByte , PHYSFSX_readS8 ) ;
# define PHYSFSX_readByte(F) ((PHYSFSX_readByte)(__func__, __LINE__, (F)))
2011-06-01 07:59:55 +00:00
2012-07-07 19:11:48 +00:00
define_read_helper ( int , PHYSFSX_readInt , PHYSFS_readSLE32 ) ;
# define PHYSFSX_readInt(F) ((PHYSFSX_readInt)(__func__, __LINE__, (F)))
2011-06-01 07:59:55 +00:00
2012-07-07 19:11:48 +00:00
define_read_helper ( int16_t , PHYSFSX_readShort , PHYSFS_readSLE16 ) ;
# define PHYSFSX_readShort(F) ((PHYSFSX_readShort)(__func__, __LINE__, (F)))
2011-06-01 07:59:55 +00:00
2012-07-07 19:11:48 +00:00
define_read_helper ( fix , PHYSFSX_readFix , PHYSFS_readSLE32 ) ;
# define PHYSFSX_readFix(F) ((PHYSFSX_readFix)(__func__, __LINE__, (F)))
2011-06-01 07:59:55 +00:00
2012-07-07 19:11:48 +00:00
define_read_helper ( fixang , PHYSFSX_readFixAng , PHYSFS_readSLE16 ) ;
# define PHYSFSX_readFixAng(F) ((PHYSFSX_readFixAng)(__func__, __LINE__, (F)))
2011-06-01 07:59:55 +00:00
2014-10-26 22:08:58 +00:00
static inline void PHYSFSX_readVector ( const char * func , const unsigned line , PHYSFS_file * file , vms_vector & v )
2011-06-01 07:59:55 +00:00
{
2014-10-26 22:08:58 +00:00
v . x = ( PHYSFSX_readFix ) ( func , line , file ) ;
v . y = ( PHYSFSX_readFix ) ( func , line , file ) ;
v . z = ( PHYSFSX_readFix ) ( func , line , file ) ;
2011-06-01 07:59:55 +00:00
}
2014-10-26 22:08:58 +00:00
# define PHYSFSX_readVector(F,V) PHYSFSX_readVector(__func__, __LINE__, (F), (V))
2011-06-01 07:59:55 +00:00
2012-07-07 19:11:48 +00:00
static inline void PHYSFSX_readAngleVec ( const char * func , const unsigned line , vms_angvec * v , PHYSFS_file * file )
2011-06-01 07:59:55 +00:00
{
2012-07-07 19:11:48 +00:00
v - > p = ( PHYSFSX_readFixAng ) ( func , line , file ) ;
v - > b = ( PHYSFSX_readFixAng ) ( func , line , file ) ;
v - > h = ( PHYSFSX_readFixAng ) ( func , line , file ) ;
2011-06-01 07:59:55 +00:00
}
2012-07-07 19:11:48 +00:00
# define PHYSFSX_readAngleVec(V,F) ((PHYSFSX_readAngleVec(__func__, __LINE__, (V), (F))))
2011-06-01 07:59:55 +00:00
2012-07-07 19:11:48 +00:00
static inline void PHYSFSX_readMatrix ( const char * func , const unsigned line , vms_matrix * m , PHYSFS_file * file )
2011-06-01 07:59:55 +00:00
{
2014-10-26 22:08:58 +00:00
( PHYSFSX_readVector ) ( func , line , file , m - > rvec ) ;
( PHYSFSX_readVector ) ( func , line , file , m - > uvec ) ;
( PHYSFSX_readVector ) ( func , line , file , m - > fvec ) ;
2011-06-01 07:59:55 +00:00
}
2012-07-07 19:11:48 +00:00
# define PHYSFSX_readMatrix(M,F) ((PHYSFSX_readMatrix)(__func__, __LINE__, (M), (F)))
2011-06-01 07:59:55 +00:00
2012-03-03 08:03:03 +00:00
# define PHYSFSX_contfile_init PHYSFSX_addRelToSearchPath
# define PHYSFSX_contfile_close PHYSFSX_removeRelFromSearchPath
2015-01-17 18:31:42 +00:00
class PHYSFS_File_deleter
{
public :
int operator ( ) ( PHYSFS_File * fp ) const
{
return PHYSFS_close ( fp ) ;
}
} ;
class RAIIPHYSFS_File : public std : : unique_ptr < PHYSFS_File , PHYSFS_File_deleter >
{
typedef std : : unique_ptr < PHYSFS_File , PHYSFS_File_deleter > base_t ;
public :
DXX_INHERIT_CONSTRUCTORS ( RAIIPHYSFS_File , base_t ) ;
using base_t : : operator bool ;
2015-01-29 00:58:53 +00:00
# ifdef DXX_HAVE_CXX11_REF_QUALIFIER
operator PHYSFS_File * ( ) const & & = delete ;
# endif
operator PHYSFS_File * ( ) const
# ifdef DXX_HAVE_CXX11_REF_QUALIFIER
&
# endif
{
return get ( ) ;
}
2015-01-17 18:31:42 +00:00
int close ( )
{
/* Like reset(), but returns result */
int r = get_deleter ( ) ( get ( ) ) ;
if ( r )
release ( ) ;
return r ;
}
template < typename T >
bool operator = = ( T ) const = delete ;
template < typename T >
bool operator ! = ( T ) const = delete ;
} ;
2015-01-23 03:55:05 +00:00
class PHYSFS_list_deleter
{
public :
void operator ( ) ( char * * list ) const
{
PHYSFS_freeList ( list ) ;
}
} ;
typedef std : : unique_ptr < char * [ ] , PHYSFS_list_deleter > PHYSFS_list_t ;
2013-11-26 22:19:52 +00:00
typedef char file_extension_t [ 5 ] ;
2015-02-14 22:48:28 +00:00
__attribute_nonnull ( )
__attribute_warn_unused_result
int PHYSFSX_checkMatchingExtension ( const char * filename , const file_extension_t * exts , const uint_fast32_t count ) ;
template < std : : size_t count >
__attribute_nonnull ( )
__attribute_warn_unused_result
static inline int PHYSFSX_checkMatchingExtension ( const array < file_extension_t , count > & exts , const char * filename )
{
return PHYSFSX_checkMatchingExtension ( filename , exts . data ( ) , count ) ;
}
2012-07-22 23:17:54 +00:00
extern int PHYSFSX_addRelToSearchPath ( const char * relname , int add_to_end ) ;
extern int PHYSFSX_removeRelFromSearchPath ( const char * relname ) ;
extern int PHYSFSX_fsize ( const char * hogname ) ;
2010-11-26 11:50:18 +00:00
extern void PHYSFSX_listSearchPathContent ( ) ;
extern int PHYSFSX_checkSupportedArchiveTypes ( ) ;
2010-08-09 14:04:22 +00:00
extern int PHYSFSX_getRealPath ( const char * stdPath , char * realPath ) ;
2012-07-22 23:17:54 +00:00
extern int PHYSFSX_isNewPath ( const char * path ) ;
extern int PHYSFSX_rename ( const char * oldpath , const char * newpath ) ;
2015-01-23 03:55:05 +00:00
__attribute_nonnull ( )
2015-02-14 22:48:28 +00:00
__attribute_warn_unused_result
PHYSFS_list_t PHYSFSX_findFiles ( const char * path , const file_extension_t * exts , uint_fast32_t count ) ;
template < std : : size_t count >
__attribute_nonnull ( )
__attribute_warn_unused_result
static inline PHYSFS_list_t PHYSFSX_findFiles ( const char * path , const array < file_extension_t , count > & exts )
{
return PHYSFSX_findFiles ( path , exts . data ( ) , count ) ;
}
__attribute_nonnull ( )
__attribute_warn_unused_result
PHYSFS_list_t PHYSFSX_findabsoluteFiles ( const char * path , const char * realpath , const file_extension_t * exts , uint_fast32_t count ) ;
template < std : : size_t count >
2015-01-23 03:55:05 +00:00
__attribute_nonnull ( )
2015-02-14 22:48:28 +00:00
__attribute_warn_unused_result
static inline PHYSFS_list_t PHYSFSX_findabsoluteFiles ( const char * path , const char * realpath , const array < file_extension_t , count > & exts )
{
return PHYSFSX_findabsoluteFiles ( path , realpath , exts . data ( ) , count ) ;
}
2010-08-09 14:04:22 +00:00
extern PHYSFS_sint64 PHYSFSX_getFreeDiskSpace ( ) ;
2011-06-01 07:59:55 +00:00
extern int PHYSFSX_exists ( const char * filename , int ignorecase ) ;
2015-01-17 18:31:42 +00:00
RAIIPHYSFS_File PHYSFSX_openReadBuffered ( const char * filename ) ;
RAIIPHYSFS_File PHYSFSX_openWriteBuffered ( const char * filename ) ;
2010-08-15 06:57:51 +00:00
extern void PHYSFSX_addArchiveContent ( ) ;
extern void PHYSFSX_removeArchiveContent ( ) ;
2007-05-20 02:00:57 +00:00
2012-11-11 22:12:51 +00:00
# endif