Fixed bug in modfl and in fread and fwrite and added

some permission checks in stdio.

svn path=/trunk/; revision=413
This commit is contained in:
Boudewijn Dekker 1999-04-27 06:15:27 +00:00
parent 2890508a82
commit 9f95b317f2
46 changed files with 842 additions and 255 deletions

View file

@ -1,8 +1,7 @@
/* Copyright (C) 1996 DJ Delorie, see COPYING.DJ for details */
#include <crtdll/io.h>
int
chsize(int _fd, long size)
int _chsize(int _fd, long size)
{
if (lseek(_fd, size, 0) == -1)
return -1;

View file

@ -3,6 +3,7 @@
#include <crtdll/errno.h>
#include <crtdll/internal/file.h>
//fixme change this constant to _OCOMMIT
int _commode_dll = _IOCOMMIT;
int _commit(int _fd)

View file

@ -1,8 +1,12 @@
#include <windows.h>
#include <crtdll/io.h>
// fixme change type of mode argument to mode_t
int __fileno_alloc(HANDLE hFile, int mode);
int __fileno_getmode(int _fd);
int _dup( int handle )
{
return _open_osfhandle(_get_osfhandle(handle), 0666);
return __fileno_alloc(_get_osfhandle(handle), __fileno_getmode(handle));
}

View file

@ -231,6 +231,19 @@ int __fileno_setmode(int _fd, int _newmode)
return m;
}
int __fileno_getmode(int _fd)
{
if ( _fd < minfno )
return -1;
if ( _fd >= maxfno )
return -1;
return fileno_modes[_fd].mode;
}
int __fileno_close(int _fd)
{
if ( _fd < 0 )

View file

@ -52,7 +52,7 @@ STDIO_OBJECTS = stdio/getenv.o stdio/filbuf.o \
stdio/fopen.o stdio/fprintf.o stdio/fputc.o stdio/fputs.o stdio/setvbuf.o\
stdio/fread.o stdio/freopen.o stdio/fscanf.o stdio/fseek.o \
stdio/fsetpos.o stdio/ftell.o stdio/fwalk.o stdio/fwrite.o stdio/getc.o \
stdio/getchar.o stdio/gets.o stdio/getw.o stdio/perror.o \
stdio/getchar.o stdio/gets.o stdio/getw.o stdio/perror.o stdio/clearerr.o \
stdio/putc.o stdio/putchar.o stdio/puts.o stdio/putw.o \
stdio/remove.o stdio/rename.o stdio/rewind.o stdio/allocfil.o\
stdio/setbuf.o stdio/setbuffe.o stdlib/obsol.o stdio/setlineb.o\

View file

@ -26,3 +26,19 @@ void *_expand( void *pold, size_t size )
return NULL;
}
size_t _msize (void* pBlock)
{
PHEAP_BUCKET pbucket;
PHEAP_SUBALLOC psub;
PHEAP_FRAGMENT pfrag=(PHEAP_FRAGMENT)((LPVOID)pBlock-HEAP_FRAG_ADMIN_SIZE);
/* sanity checks */
if(pfrag->Magic!=HEAP_FRAG_MAGIC)
return 0;
/* get bucket size */
psub=pfrag->Sub;
pbucket=psub->Bucket;
return pbucket->Size;
}

View file

@ -33,6 +33,12 @@ double modf(double __x, double *__i)
iptr->sign = x->sign;
return __x;
} else {
if ( x->mantissah == 0 && x->mantissal == 0 ) {
*__i = __x;
return 0.0;
}
i = (0x000fffff)>>j0;
iptr->sign = x->sign;
iptr->exponent = x->exponent;
@ -43,7 +49,6 @@ double modf(double __x, double *__i)
x->sign = iptr->sign;
return __x;
}
return __x - *__i;
}
} else if (j0>51) { /* no fraction part */
@ -72,6 +77,7 @@ double modf(double __x, double *__i)
}
}
long double modfl(long double __x, long double *__i)
{
@ -86,21 +92,23 @@ long double modfl(long double __x, long double *__i)
if(j0<32) { /* integer part in high x */
if(j0<0) { /* |x|<1 */
*__i = 0.0;
*__i = 0.0L;
iptr->sign = x->sign;
return __x;
} else {
i = ((unsigned int)(0xffffffff))>>(j0);
i = ((unsigned int)(0xffffffff))>>(j0+1);
if ( x->mantissal == 0 && (x->mantissal & i) == 0 ) {
*__i = __x;
__x = 0.0L;
x->sign = iptr->sign;
return __x;
}
iptr->sign = x->sign;
iptr->exponent = x->exponent;
iptr->mantissah = x->mantissah&((~i));
iptr->mantissal = 0;
if ( __x == *__i ) {
__x = 0.0;
x->sign = iptr->sign;
return __x;
}
return __x - *__i;
}
@ -109,25 +117,25 @@ long double modfl(long double __x, long double *__i)
if ( _isnanl(__x) || _isinfl(__x) )
return __x;
__x = 0.0;
__x = 0.0L;
x->sign = iptr->sign;
return __x;
} else { /* fraction part in low x */
i = ((unsigned int)(0xffffffff))>>(j0-32);
if ( x->mantissal == 0 ) {
*__i = __x;
__x = 0.0L;
x->sign = iptr->sign;
return __x;
}
iptr->sign = x->sign;
iptr->exponent = x->exponent;
iptr->mantissah = x->mantissah;
iptr->mantissal = x->mantissal&(~i);
if ( __x == *__i ) {
__x = 0.0;
x->sign = iptr->sign;
return __x;
}
return __x - *__i;
}
}

View file

@ -1,12 +1,91 @@
unsigned int _mbcjistojms( unsigned int c )
static unsigned short han_to_zen_ascii_table[0x5f] = {
0x8140, 0x8149, 0x8168, 0x8194, 0x8190, 0x8193, 0x8195, 0x8166,
0x8169, 0x816a, 0x8196, 0x817b, 0x8143, 0x817c, 0x8144, 0x815e,
0x824f, 0x8250, 0x8251, 0x8252, 0x8253, 0x8254, 0x8255, 0x8256,
0x8257, 0x8258, 0x8146, 0x8147, 0x8183, 0x8181, 0x8184, 0x8148,
0x8197, 0x8260, 0x8261, 0x8262, 0x8263, 0x8264, 0x8265, 0x8266,
0x8267, 0x8268, 0x8269, 0x826a, 0x826b, 0x826c, 0x826d, 0x826e,
0x826f, 0x8270, 0x8271, 0x8272, 0x8273, 0x8274, 0x8275, 0x8276,
0x8277, 0x8278, 0x8279, 0x816d, 0x818f, 0x816e, 0x814f, 0x8151,
0x8165, 0x8281, 0x8282, 0x8283, 0x8284, 0x8285, 0x8286, 0x8287,
0x8288, 0x8289, 0x828a, 0x828b, 0x828c, 0x828d, 0x828e, 0x828f,
0x8290, 0x8291, 0x8292, 0x8293, 0x8294, 0x8295, 0x8296, 0x8297,
0x8298, 0x8299, 0x829a, 0x816f, 0x8162, 0x8170, 0x8150
};
static unsigned short han_to_zen_kana_table[0x40] = {
0x8140, 0x8142, 0x8175, 0x8176, 0x8141, 0x8145, 0x8392, 0x8340,
0x8342, 0x8344, 0x8346, 0x8348, 0x8383, 0x8385, 0x8387, 0x8362,
0x815b, 0x8341, 0x8343, 0x8345, 0x8347, 0x8349, 0x834a, 0x834c,
0x834e, 0x8350, 0x8352, 0x8354, 0x8356, 0x8358, 0x835a, 0x835c,
0x835e, 0x8360, 0x8363, 0x8365, 0x8367, 0x8369, 0x836a, 0x836b,
0x836c, 0x836d, 0x836e, 0x8371, 0x8374, 0x8377, 0x837a, 0x837d,
0x837e, 0x8380, 0x8381, 0x8382, 0x8384, 0x8386, 0x8388, 0x8389,
0x838a, 0x838b, 0x838c, 0x838d, 0x838f, 0x8393, 0x814a, 0x814b
};
static unsigned char zen_to_han_kana_table[0x8396-0x8340+1] = {
0xa7, 0xb1, 0xa8, 0xb2, 0xa9, 0xb3, 0xaa, 0xb4,
0xab, 0xb5, 0xb6, 0xb6, 0xb7, 0xb7, 0xb8, 0xb8,
0xb9, 0xb9, 0xba, 0xba, 0xbb, 0xbb, 0xbc, 0xbc,
0xbd, 0xbd, 0xbe, 0xbe, 0xbf, 0xbf, 0xc0, 0xc0,
0xc1, 0xc1, 0xaf, 0xc2, 0xc2, 0xc3, 0xc3, 0xc4,
0xc4, 0xc5, 0xc6, 0xc7, 0xc8, 0xc9, 0xca, 0xca,
0xca, 0xcb, 0xcb, 0xcb, 0xcc, 0xcc, 0xcc, 0xcd,
0xcd, 0xcd, 0xce, 0xce, 0xce, 0xcf, 0xd0, 0,
0xd1, 0xd2, 0xd3, 0xac, 0xd4, 0xad, 0xd5, 0xae,
0xd6, 0xd7, 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdc,
0xb2, 0xb4, 0xa6, 0xdd, 0xb3, 0xb6, 0xb9
};
#define ZTOH_SYMBOLS 9
static unsigned short zen_to_han_symbol_table_1[ZTOH_SYMBOLS] = {
0x8142, 0x8175, 0x8176, 0x8141, 0x8145, 0x815b, 0x814a, 0x814b
};
static unsigned char zen_to_han_symbol_table_2[ZTOH_SYMBOLS] = {
0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xb0, 0xde, 0xdf
};
#define ISKANA(c) ((c) >= 0xa1 && (c) <= 0xdf)
#define JISHIRA(c) ((c) >= 0x829f && (c) <= 0x82f1)
#define JISKANA(c) ((c) >= 0x8340 && (c) <= 0x8396 && (c) != 0x837f)
#define JTOKANA(c) ((c) <= 0x82dd ? (c) + 0xa1 : (c) + 0xa2)
static unsigned short _mbbtombc(unsigned short c)
{
if (c >= 0x20 && c <= 0x7e) {
return han_to_zen_ascii_table[c - 0x20];
} else if (ISKANA(c)) {
return han_to_zen_kana_table[c - 0xa0];
}
return c;
}
unsigned int _mbcjmstojis( unsigned int c )
static unsigned short _mbctombb(unsigned short c)
{
int i;
unsigned short *p;
if (JISKANA(c)) {
return zen_to_han_kana_table[c - 0x8340];
} else if (JISHIRA(c)) {
c = JTOKANA(c);
return zen_to_han_kana_table[c - 0x8340];
} else if (c <= 0x8396) {
for (i = 0x20, p = han_to_zen_ascii_table; i <= 0x7e; i++, p++) {
if (*p == c) {
return i;
}
}
for (i = 0; i < ZTOH_SYMBOLS; i++) {
if (zen_to_han_symbol_table_1[i] == c) {
return zen_to_han_symbol_table_2[i];
}
}
}
return c;
}
#endif
unsigned int _mbctohira( unsigned int c )
{

View file

@ -10,11 +10,48 @@
#include <crtdll/mbstring.h>
int _ismbblead(unsigned int byte)
{
return (int)IsDBCSLeadByte(byte)
#define ___ 0
#define _1_ _KNJ_1 /* Legal 1st byte of double byte code */
#define __2 _KNJ_2 /* Legal 2nd byte of double byte code */
#define _M_ _KNJ_M /* Non-puntuation in Kana-set */
#define _P_ _KNJ_P /* Punctuation of Kana-set */
#define _12 (_1_|__2)
#define _M2 (_M_|__2)
#define _P2 (_P_|__2)
static char _jctype[257] = {
/*-1*/ ___,
/*0x*/ ___,___,___,___,___,___,___,___,___,___,___,___,___,___,___,___,
/*1x*/ ___,___,___,___,___,___,___,___,___,___,___,___,___,___,___,___,
/*2x*/ ___,___,___,___,___,___,___,___,___,___,___,___,___,___,___,___,
/*3x*/ ___,___,___,___,___,___,___,___,___,___,___,___,___,___,___,___,
/*4x*/ __2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,
/*5x*/ __2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,
/*6x*/ __2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,
/*7x*/ __2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,__2,___,
/*8x*/ __2,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,
/*9x*/ _12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,
/*Ax*/ __2,_P2,_P2,_P2,_P2,_P2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,
/*Bx*/ _M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,
/*Cx*/ _M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,
/*Dx*/ _M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,_M2,
/*Ex*/ _12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,
/*Fx*/ _12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,_12,___,___,___
};
iskanji() : ƒVƒtƒg JIS ƒR<EFBFBD>[ƒhÌ1ƒoƒCƒgÚ(0x81 <= c <= 0x9F é
¢Í0xE0 <= c <= 0xFC) ©Ç¤©
int _ismbblead(char c)
{
return ((_jctype+1)[(unsigned char)(c)] & _KNJ_1);
}
//int _ismbblead(unsigned int byte)
//{
//
// return (int)IsDBCSLeadByte(byte)
//}
int _ismbslead( const unsigned char *str, const unsigned char *t)
{

View file

@ -10,11 +10,19 @@
#include <crtdll/mbstring.h>
int _ismbbtrail( unsigned int b)
iskanji2() : ƒVƒtƒg JIS ƒR<EFBFBD>[ƒhÌ2ƒoƒCƒgÚ(0x40 <= c <= 0x7E é
¢Í0x80 <= c <= 0xFC) ©Ç¤©
int _ismbbtrail(unsigned int c)
{
return ((b >= 0x40 && b <= 0x7e ) || (b >= 0x80 && b <= 0xfc ) );
return ((_jctype+1)[(unsigned char)(c)] & _KNJ_2);
}
//int _ismbbtrail( unsigned int b)
//{
// return ((b >= 0x40 && b <= 0x7e ) || (b >= 0x80 && b <= 0xfc ) );
//}
int _ismbstrail( const unsigned char *str, const unsigned char *t)
{

View file

@ -6,7 +6,15 @@
int _execl(const char* szPath, const char* szArgv0, ...)
{
va_list a = 0;
va_start(a,szArgv0);
return _spawnve(P_OVERLAY, szPath, (char *const*)a, _environ);
char *szArg[100];
const char *a;
int i = 0;
va_list l = 0;
va_start(l,szArgv0);
do {
a = va_arg(l,const char *);
szArg[i++] = (char *)a;
} while ( a != NULL && i < 100 );
return _spawnve(P_OVERLAY, szPath, szArg, _environ);
}

View file

@ -1,17 +1,33 @@
/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */
#include <crtdll/process.h>
#include <crtdll/stdlib.h>
#include <crtdll/stdarg.h>
#define scan_ptr() \
const char **ptr; \
union { const char **ccpp; const char *ccp; } u; \
for (ptr = &argv0; *ptr; ptr++); \
u.ccp = *++ptr; \
ptr = u.ccpp;
int _execle(const char *path, const char *argv0, ... /*, const char **envp */)
// fixme rewrite to pass the array variants to va_list variant
int _execle(const char *path, const char *szArgv0, ... /*, const char **envp */)
{
scan_ptr();
return _spawnve(P_OVERLAY, path, (char *const *)&argv0, (char *const *)ptr);
char *szArg[100];
const char *a;
char *ptr;
int i = 0;
va_list l = 0;
va_start(l,szArgv0);
do {
a = (const char *)va_arg(l,const char *);
szArg[i++] = (char *)a;
} while ( a != NULL && i < 100 );
// szArg0 is passed and not environment if there is only one parameter;
if ( i >=2 ) {
ptr = szArg[i-2];
szArg[i-2] = NULL;
}
else
ptr = NULL;
return _spawnve(P_OVERLAY, path, (char * const *)szArg, (char * const *)ptr);
}

View file

@ -1,9 +1,17 @@
/* Copyright (C) 1995 DJ Delorie, see COPYING.DJ for details */
#include <crtdll/process.h>
#include <crtdll/stdlib.h>
#include <crtdll/stdarg.h>
int _execlp(const char *path, const char *argv0, ...)
int _execlp(const char *szPath, const char *szArgv0, ...)
{
return _spawnvpe(P_OVERLAY, path, (char * const *)&argv0, _environ);
char *szArg[100];
const char *a;
int i = 0;
va_list l = 0;
va_start(l,szArgv0);
do {
a = (const char *)va_arg(l,const char *);
szArg[i++] = (char *)a;
} while ( a != NULL && i < 100 );
return _spawnvpe(P_OVERLAY, szPath,szArg, _environ);
}

View file

@ -1,17 +1,29 @@
/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */
#include <crtdll/process.h>
#include <crtdll/stdlib.h>
#include <crtdll/stdarg.h>
#define scan_ptr() \
const char **ptr; \
union { const char **ccpp; const char *ccp; } u; \
for (ptr = &argv0; *ptr; ptr++); \
u.ccp = *++ptr; \
ptr = u.ccpp;
int execlpe(const char *path, const char *argv0, ... /*, const char **envp */)
int execlpe(const char *path, const char *szArgv0, ... /*, const char **envp */)
{
scan_ptr();
return spawnvpe(P_OVERLAY, path, (char * const *)&argv0, (char * const *)ptr);
char *szArg[100];
const char *a;
char *ptr;
int i = 0;
va_list l = 0;
va_start(l,szArgv0);
do {
a = (const char *)va_arg(l,const char *);
szArg[i++] = (char *)a;
} while ( a != NULL && i < 100 );
// szArg0 is passed and not environment if there is only one parameter;
if ( i >=2 ) {
ptr = szArg[i-2];
szArg[i-2] = NULL;
}
else
ptr = NULL;
return spawnvpe(P_OVERLAY, path, (char * const *)szArg, (char * const *)ptr);
}

View file

@ -6,7 +6,15 @@
int _spawnl(int nMode, const char* szPath, const char* szArgv0,...)
{
va_list a = 0;
va_start(a,szArgv0);
return _spawnve(nMode, szPath, (char * const *)a, _environ);
char *szArg[100];
const char *a;
int i = 0;
va_list l = 0;
va_start(l,szArgv0);
do {
a = va_arg(l,const char *);
szArg[i++] = (char *)a;
} while ( a != NULL && i < 100 );
return _spawnve(nMode, szPath, szArg, _environ);
}

View file

@ -1,16 +1,30 @@
/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */
#include <crtdll/process.h>
#include <crtdll/stdlib.h>
#include <crtdll/stdarg.h>
#define scan_ptr() \
const char **ptr; \
union { const char **ccpp; const char *ccp; } u; \
for (ptr = &argv0; *ptr; ptr++); \
u.ccp = *++ptr; \
ptr = u.ccpp;
int _spawnle(int mode, const char *path, const char *argv0, ... /*, const char **envp */)
int _spawnle(int mode, const char *path, const char *szArgv0, ... /*, const char **envp */)
{
scan_ptr();
return _spawnve(mode, path, (char * const *)&argv0, (char * const *)ptr);
char *szArg[100];
char *a;
char *ptr;
int i = 0;
va_list l = 0;
va_start(l,szArgv0);
do {
a = (const char *)va_arg(l,const char *);
szArg[i++] = (char *)a;
} while ( a != NULL && i < 100 );
// szArg0 is passed and not environment if there is only one parameter;
if ( i >=2 ) {
ptr = szArg[i-2];
szArg[i-2] = NULL;
}
else
ptr = NULL;
return _spawnve(mode, path, (char * const *)szArg, (char * const *)ptr);
}

View file

@ -6,7 +6,14 @@
int _spawnlp(int nMode, const char* szPath, const char* szArgv0, ...)
{
va_list a = 0;
va_start(a,szArgv0);
return _spawnvpe(nMode, szPath, (char * const *)a, _environ);
char *szArg[100];
const char *a;
int i = 0;
va_list l = 0;
va_start(l,szArgv0);
do {
a = (const char *)va_arg(l,const char *);
szArg[i++] = (char *)a;
} while ( a != NULL && i < 100 );
return _spawnvpe(nMode, szPath,szArg, _environ);
}

View file

@ -1,15 +1,30 @@
/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */
#include <crtdll/process.h>
#define scan_ptr() \
const char **ptr; \
union { const char **ccpp; const char *ccp; } u; \
for (ptr = &argv0; *ptr; ptr++); \
u.ccp = *++ptr; \
ptr = u.ccpp;
#include <crtdll/stdlib.h>
#include <crtdll/stdarg.h>
int _spawnlpe(int mode, const char *path, const char *argv0, ... /*, const char **envp */)
int _spawnlpe(int mode, const char *path, const char *szArgv0, ... /*, const char **envp */)
{
scan_ptr();
return _spawnvpe(mode, path, (char * const *)&argv0, (char * const *)ptr);
char *szArg[100];
const char *a;
char *ptr;
int i = 0;
va_list l = 0;
va_start(l,szArgv0);
do {
a = (const char *)va_arg(l,const char *);
szArg[i++] = (char *)a;
} while ( a != NULL && i < 100 );
// szArg0 is passed and not environment if there is only one parameter;
if ( i >=2 ) {
ptr = szArg[i-2];
szArg[i-2] = NULL;
}
else
ptr = NULL;
return _spawnvpe(mode, path, (char * const *)szArg, (char * const *)ptr);
}

View file

@ -3,7 +3,7 @@
#include <crtdll/process.h>
#include <crtdll/stdlib.h>
int _spawnv (int nMode, const char* szPath, char* const* szaArgv)
int _spawnv(int nMode, const char* szPath, char* const* szaArgv)
{
return _spawnve(nMode, szPath, (char * const *)szaArgv, _environ);
}

View file

@ -22,8 +22,8 @@ size of the buffer
int _flag;
_IORW file is used for both read and write
_IOWRT file was last used for write
_IOREAD file was last used for read
_IOWRT file is opened for write
_IOREAD file is opened for read
_IOMYBUF buffer needs to be freed
_IOEOF file is at EOF
_IOERR error occurred
@ -40,8 +40,4 @@ char *_name_to_remove;
If nonzero, the named file is removed when the file is fclosed.
int _fillsize;
The number of bytes to read this time. Used to slow-start the read,
in case the program seeks a lot we won't waste time reading large
blocks, but if you read a lot, we use bigger transfers.

View file

@ -7,6 +7,16 @@
FILE * __alloc_file(void);
char __validfp (FILE *f)
{
if ( (unsigned int)f < 256)
return FALSE;
if( f == NULL || (int)f== -1 )
return FALSE;
return TRUE;
}
/* A FILE* is considered "free" if its flag is zero. */

View file

@ -1,5 +1,6 @@
/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */
#include <crtdll/stdio.h>
#include <crtdll/errno.h>
#include <crtdll/internal/file.h>
#ifdef clearerr
@ -10,7 +11,7 @@ void clearerr(FILE *stream);
void
clearerr(FILE *f)
{
if (!f) {
if (!__validfp (f)) {
__set_errno (EINVAL);
return;
}

View file

@ -25,7 +25,7 @@ fclose(FILE *f)
// flush only if stream was opened for writing
if ( !(f->_flag&_IOSTRG) ) {
if ( WRITE_STREAM(f) )
if ( OPEN4WRITING(f) )
r = fflush(f);
if (_close(fileno(f)) < 0)

View file

@ -36,8 +36,12 @@ FILE *_fdopen(int handle, char *mode)
file->_cnt = 0;
file->_file = handle;
file->_bufsiz = 0;
// The mode of the stream must be compatible with the mode of the file descriptor.
// this should be checked.
if (rw)
file->_flag = _IORW;
file->_flag = _IOREAD | _IOWRT;
else if (*mode == 'r')
file->_flag = _IOREAD;
else

View file

@ -33,30 +33,46 @@ int fflush(FILE *f)
// nothing to do if stream can not be written to
//if ( !WRITE_STREAM(f) )
// return 0;
if ( !OPEN4WRITING(f) ) {
__set_errno (EINVAL);
return 0;
}
// discard any unget characters
f->_flag &= ~_IOUNGETC;
// if ((f->_flag&(_IONBF|_IOWRT))==_IOWRT
// && (base = f->_base) != NULL
// && (rn = n = f->_ptr - base) > 0)
if ((f->_flag&(_IODIRTY|_IONBF))==_IODIRTY
&& (base = f->_base) != NULL
&& (rn = n = f->_ptr - base) > 0)
// check for buffered dirty block
if ( (f->_flag&(_IODIRTY|_IONBF)) ==_IODIRTY && f->_base != NULL)
{
base = f->_base;
// if the buffer is read ahead and dirty we will flush it entirely
// else the buffer is appended to the file to the extend it has valid bytes
if ( (f->_flag & _IOAHEAD) == _IOAHEAD )
rn = n = f->_ptr - base + f->_cnt;
else
rn = n = f->_ptr - base;
f->_ptr = base;
if ((f->_flag & _IOFBF) == _IOFBF) {
if ( (f->_flag & _IOAHEAD) == _IOAHEAD )
_lseek(fileno(f),-(rn+f->_cnt), SEEK_CUR);
_lseek(fileno(f),-rn, SEEK_CUR);
}
f->_flag &= ~_IOAHEAD;
f->_cnt = (f->_flag&(_IOLBF|_IONBF)) ? 0 : f->_bufsiz;
f->_flag &= ~_IODIRTY;
// how can write return less than rn without being on error ???
do {
n = _write(fileno(f), base, rn);
if (n <= 0) {
@ -66,11 +82,12 @@ int fflush(FILE *f)
rn -= n;
base += n;
} while (rn > 0);
f->_flag &= ~_IODIRTY;
}
if (f->_flag & _IORW)
if (OPEN4READING(f) && OPEN4WRITING(f) )
{
f->_cnt = 0;
//f->_flag &= ~(_IOWRT|_IOREAD);
f->_ptr = f->_base;
}
return 0;

View file

@ -9,6 +9,7 @@
#include <crtdll/internal/file.h>
#include <crtdll/io.h>
#include <crtdll/wchar.h>
#include <crtdll/errno.h>
int _readcnv(int fn, void *buf, size_t siz );
@ -19,8 +20,10 @@ _filbuf(FILE *f)
char c;
// if ( !READ_STREAM(f))
// return EOF;
if ( !OPEN4READING(f)) {
__set_errno (EINVAL);
return EOF;
}
if (f->_flag&(_IOSTRG|_IOEOF))
@ -31,6 +34,7 @@ _filbuf(FILE *f)
size = 4096;
if ((f->_base = malloc(size+1)) == NULL)
{
// error ENOMEM
f->_flag |= _IONBF;
f->_flag &= ~(_IOFBF|_IOLBF);
}
@ -41,9 +45,12 @@ _filbuf(FILE *f)
}
}
if (f->_flag&_IONBF)
f->_base = &c;
// fush stdout before reading from stdin
if (f == stdin) {
if (stdout->_flag&_IOLBF)
fflush(stdout);
@ -51,14 +58,13 @@ _filbuf(FILE *f)
fflush(stderr);
}
// if(__is_text_file(f))
// f->_cnt = _readcnv(fileno(f), f->_base,
// f->_flag & _IONBF ? 1 : f->_bufsiz );
// else
// if we have a dirty stream we flush it
if ( f->_flag &_IODIRTY == _IODIRTY )
fflush(f);
f->_cnt = _read(fileno(f), f->_base,
f->_flag & _IONBF ? 1 : f->_bufsiz );
f->_cnt = _read(fileno(f), f->_base, f->_flag & _IONBF ? 1 : f->_bufsiz );
f->_flag |= _IOAHEAD;
if(__is_text_file(f) && f->_cnt>0)
@ -72,18 +78,23 @@ _filbuf(FILE *f)
f->_cnt = newcnt;
}
}
f->_ptr = f->_base;
if (f->_flag & _IONBF)
f->_base = NULL; // statically allocated buffer for sprintf
//check for error
if (--f->_cnt < 0) {
if (f->_cnt == -1) {
f->_flag |= _IOEOF;
//if (f->_flag & _IORW)
//f->_flag &= ~_IOREAD;
} else
f->_flag |= _IOERR;
f->_cnt = 0;
// should set errno
return EOF;
}

View file

@ -7,6 +7,7 @@
#include <crtdll/stdlib.h>
#include <crtdll/internal/file.h>
#include <crtdll/io.h>
#include <crtdll/errno.h>
int cntcr(char *bufp, int bufsiz);
int convert(char *endp, int bufsiz,int n);
@ -22,8 +23,10 @@ _flsbuf(int c, FILE *f)
// if (!WRITE_STREAM(f))
// return EOF;
if (!OPEN4WRITING(f)) {
__set_errno (EINVAL);
return EOF;
}
/* if the buffer is not yet allocated, allocate it */
if ((base = f->_base) == NULL && (f->_flag & _IONBF) == 0)
@ -87,9 +90,6 @@ _flsbuf(int c, FILE *f)
f->_flag &= ~_IODIRTY;
while (rn > 0)
{
// if(__is_text_file(f) )
// n = _writecnv(fileno(f), base, rn);
// else
n = _write(fileno(f), base, rn);
if (n <= 0)
{

View file

@ -56,6 +56,8 @@ FILE* fopen(const char *file, const char *mode)
if (fd < 0)
return NULL;
// ms crtdll ensures that writes will end up at the end of file in append mode
// we just move the file pointer to the end of file initially
if (*mode == 'a')
lseek(fd, 0, SEEK_END);
@ -63,7 +65,7 @@ FILE* fopen(const char *file, const char *mode)
f->_file = fd;
f->_bufsiz = 0;
if (rw)
f->_flag = _IORW;
f->_flag = _IOREAD | _IOWRT;
else if (*mode == 'r')
f->_flag = _IOREAD;
else

View file

@ -39,13 +39,13 @@ size_t fread(void *vptr, size_t size, size_t count, FILE *iop)
to_read = size * count;
//if (!READ_STREAM(iop))
//{
// __set_errno (EINVAL);
// return 0;
//}
if (!OPEN4READING(iop))
{
__set_errno (EINVAL);
return 0;
}
if (iop == NULL )
if (!__validfp (iop) )
{
__set_errno (EINVAL);
return 0;
@ -57,17 +57,26 @@ size_t fread(void *vptr, size_t size, size_t count, FILE *iop)
return 0;
while(iop->_cnt > 0) {
while(iop->_cnt > 0 && to_read > 0 ) {
to_read--;
*ptr++ = getc(iop);
}
// if the buffer is dirty it will have to be written now
// otherwise the file pointer won't match anymore.
fflush(iop);
// check to see if this will work with in combination with ungetc
n_read = _read(fileno(iop), ptr, to_read);
if ( n_read != -1 )
to_read -= n_read;
// the file buffer is empty and there is no read ahead information anymore.
iop->_flag &= ~_IOAHEAD;
return count- (to_read/size);
}
#endif

View file

@ -56,7 +56,7 @@ freopen(const char *file, const char *mode, FILE *f)
f->_file = fd;
f->_bufsiz = 0;
if (rw)
f->_flag = _IORW;
f->_flag = _IOREAD | _IOWRT;
else if (*mode == 'r')
f->_flag = _IOREAD;
else

View file

@ -22,7 +22,7 @@ Cambridge, MA 02139, USA. */
#include <crtdll/wchar.h>
#include <crtdll/alloc.h>
#if 1
#if 0
int fscanf(FILE *stream,const char *format, ...)
{

View file

@ -18,7 +18,7 @@ int fseek(FILE *f, long offset, int ptrname)
}
f->_flag &= ~_IOEOF;
if (!WRITE_STREAM(f))
if (!OPEN4WRITING(f))
{
if (f->_base && !(f->_flag & _IONBF))
{
@ -30,7 +30,7 @@ int fseek(FILE *f, long offset, int ptrname)
}
/* check if the target position is in the buffer and
optimize seek by moving inside the buffer */
if (ptrname == SEEK_SET && (f->_flag & (_IOUNGETC|_IORW)) == 0
if (ptrname == SEEK_SET && (f->_flag & (_IOUNGETC|_IOREAD|_IOWRT )) == 0
&& p-offset <= f->_ptr-f->_base && offset-p <= f->_cnt)
{
f->_ptr+=offset-p;
@ -39,8 +39,6 @@ int fseek(FILE *f, long offset, int ptrname)
}
}
// if (f->_flag & _IORW)
// f->_flag &= ~_IOREAD;
p = lseek(fileno(f), offset, ptrname);
f->_cnt = 0;

View file

@ -21,9 +21,9 @@ ftell(FILE *f)
{
adjust = - f->_cnt;
}
else if (f->_flag&(_IOWRT|_IORW))
else if (f->_flag&(_IOWRT))
{
if (f->_flag&_IOWRT && f->_base && (f->_flag&_IONBF)==0)
if (f->_base && (f->_flag&_IONBF)==0)
adjust = f->_ptr - f->_base;
}

View file

@ -37,11 +37,11 @@ size_t fwrite(const void *vptr, size_t size, size_t count, FILE *iop)
char *ptr = (char *)vptr;
to_write = size*count;
//if (!WRITE_STREAM(iop) )
//{
// __set_errno (EINVAL);
// return 0;
//}
if (!OPEN4WRITING(iop) )
{
__set_errno (EINVAL);
return 0;
}
if (iop == NULL )
@ -56,11 +56,15 @@ size_t fwrite(const void *vptr, size_t size, size_t count, FILE *iop)
return 0;
while(iop->_cnt > 0 ) {
while(iop->_cnt > 0 && to_write > 0 ) {
to_write--;
putc(*ptr++,iop);
}
// if the buffer is dirty it will have to be written now
// otherwise the file pointer won't match anymore.
fflush(iop);
n_written = _write(fileno(iop), ptr,to_write);
if ( n_written != -1 )
@ -68,6 +72,11 @@ size_t fwrite(const void *vptr, size_t size, size_t count, FILE *iop)
// check to see if this will work with in combination with ungetc
// the file buffer is empty and there is no read ahead information anymore.
iop->_flag &= ~_IOAHEAD;
return count - (to_write/size);
}

View file

@ -4,22 +4,24 @@
#include <crtdll/errno.h>
#include <crtdll/internal/file.h>
//getc can be a macro
#undef getc
int getc(FILE *fp)
{
// check for invalid stream
if ( (int)fp == NULL ) {
if ( !__validfp (fp) ) {
__set_errno(EINVAL);
return -1;
return EOF;
}
// check for read access on stream
//if ( !READ_STREAM(fp) ) {
// __set_errno(EINVAL);
// return -1;
//}
if ( !OPEN4READING(fp) ) {
__set_errno(EINVAL);
return -1;
}
if(fp->_cnt > 0) {
fp->_cnt--;

View file

@ -1,18 +1,33 @@
/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */
#include <crtdll/stdio.h>
#include <crtdll/internal/file.h>
/* Copyright (C) 1991 Free Software Foundation, Inc.
This file is part of the GNU C Library.
The GNU C Library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public License as
published by the Free Software Foundation; either version 2 of the
License, or (at your option) any later version.
The GNU C Library 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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with the GNU C Library; see the file COPYING.LIB. If
not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA. */
#include <crtdll/stdio.h>
/* Read a word (int) from STREAM. */
int
getw(FILE *f)
getw(FILE *stream)
{
int i;
char *p;
int w;
p = (char *)&w;
for (i=sizeof(int); --i>=0;)
*p++ = getc(f);
if (feof(f))
return EOF;
return w;
/* Is there a better way? */
if (fread( &w, sizeof(w), 1, stream) != 1)
return(EOF);
return(w);
}

View file

@ -5,36 +5,35 @@
#include <crtdll/errno.h>
#include <crtdll/internal/file.h>
// putc can be a macro
#undef putc
int putc(int c, FILE *fp)
{
if ( c == 0 )
c = ' ';
// valid stream macro should check that fp
// is dword aligned
if ( fp == NULL ) {
if (!__validfp (fp)) {
__set_errno(EINVAL);
return -1;
}
// check for write access on fp
//if ( !WRITE_STREAM(fp) ) {
// __set_errno(EINVAL);
// return -1;
//}
if ( !OPEN4WRITING(fp) ) {
__set_errno(EINVAL);
return -1;
}
fp->_flag |= _IODIRTY;
if (fp->_cnt > 0 ) {
fp->_cnt--;
*(fp)->_ptr++ = (char)c;
return (int)c;
*(fp)->_ptr++ = (unsigned char)c;
return (int)(unsigned char)c;
}
else {
return _flsbuf(c,fp);
return _flsbuf((unsigned char)c,fp);
}
return -1;
return EOF;
}
wint_t putwc(wchar_t c, FILE *fp)

View file

@ -5,7 +5,9 @@
int rename(const char *old_, const char *new_)
{
if ( !MoveFile(old_,new_) )
if ( old_ == NULL || new_ == NULL )
return -1;
if ( !MoveFileA(old_,new_) )
return -1;
return 0;

View file

@ -4,26 +4,34 @@
#include <crtdll/stdio.h>
#include <crtdll/stdlib.h>
#include <crtdll/io.h>
#include <crtdll/errno.h>
#include <crtdll/internal/file.h>
int setvbuf(FILE *f, char *buf, int type, size_t len)
{
int mine=0;
if (!f)
return -1;
if (!__validfp (f) ) {
__set_errno (EINVAL);
return 0;
}
if ( f->_base != NULL )
fflush(f);
switch (type)
{
case _IOFBF:
case _IOLBF:
if (len <= 0)
return -1;
if (len <= 0) {
__set_errno (EINVAL);
return EOF;
}
if (buf == 0)
{
buf = (char *)malloc(len);
if (buf == 0)
buf = (char *)malloc(len+1);
if (buf == NULL) {
__set_errno (ENOMEM);
return -1;
}
mine = 1;
}
/* FALLTHROUGH */
@ -48,6 +56,7 @@ int setvbuf(FILE *f, char *buf, int type, size_t len)
}
return 0;
default:
return -1;
__set_errno (EINVAL);
return EOF;
}
}

View file

@ -28,7 +28,7 @@ FILE _crtdll_iob[5] =
// stdaux
{
NULL, 0, NULL,
_IORW | _IONBF,
_IOREAD | _IOWRT | _IONBF,
3,0,0, NULL
},
// stdprn

View file

@ -57,7 +57,7 @@ tmpfile(void)
f->_file = temp_fd;
f->_cnt = 0;
f->_bufsiz = 0;
f->_flag = _IORMONCL | _IORW;
f->_flag = _IORMONCL | _IOREAD | _IOWRT;
f->_name_to_remove = n_t_r;
strcpy(f->_name_to_remove, temp_name);
f->_base = f->_ptr = NULL;

View file

@ -3,14 +3,23 @@
#include <crtdll/stdio.h>
#include <crtdll/internal/file.h>
#include <crtdll/wchar.h>
#include <crtdll/errno.h>
int
ungetc(int c, FILE *f)
{
if (c == EOF
|| (f->_flag & (_IOREAD|_IORW)) == 0
|| f->_ptr == NULL
|| f->_base == NULL)
if (!__validfp (f) || !OPEN4READING(f)) {
__set_errno (EINVAL);
return EOF;
}
if (c == EOF )
return EOF;
if ( f->_ptr == NULL || f->_base == NULL)
return EOF;
if (f->_ptr == f->_base)
@ -36,10 +45,17 @@ ungetc(int c, FILE *f)
wint_t
ungetwc(wchar_t c, FILE *f)
{
if ((char)c == EOF
|| (f->_flag & (_IOREAD|_IORW)) == 0
|| f->_ptr == NULL
|| f->_base == NULL)
if (!__validfp (f) || !OPEN4READING(f)) {
__set_errno (EINVAL);
return EOF;
}
if (c == (wchar_t)EOF )
return EOF;
if ( f->_ptr == NULL || f->_base == NULL)
return EOF;
if (f->_ptr == f->_base)

View file

@ -1,11 +1,13 @@
/* Copyright (C) 1994 DJ Delorie, see COPYING.DJ for details */
#include <crtdll/stdio.h>
#include <crtdll/stdarg.h>
#include <stdarg.h>
#include <crtdll/malloc.h>
#include <crtdll/internal/file.h>
int _isnanl(double x);
int _isinfl(double x);
int _isnan(double x);
int _isinf(double x);
@ -168,7 +170,202 @@ static char * number(FILE * f, long num, int base, int size, int precision
void numberf(FILE * f, long double __n, char exp_sign, int size, int precision, int type)
void numberf(FILE * f, double __n, char exp_sign, int size, int precision, int type)
{
double exponent = 0.0;
double e;
long ie;
//int x;
char *buf, *tmp;
int i = 0;
int j = 0;
//int k = 0;
double frac, intr;
double p;
char sign;
char c;
char ro = 0;
double_t *n = (double_t *)&__n;
if ( exp_sign == 'g' || exp_sign == 'G' || exp_sign == 'e' || exp_sign == 'E' ) {
ie = ((unsigned int)n->exponent - (unsigned int)0x3ff);
exponent = ie/3.321928;
}
if ( exp_sign == 'g' || exp_sign == 'G' ) {
type |= ZEROTRUNC;
if ( exponent < -4 || fabs(exponent) >= precision )
exp_sign -= 2; // g -> e and G -> E
}
if ( exp_sign == 'e' || exp_sign == 'E' ) {
frac = modf(exponent,&e);
if ( frac > 0.5 )
e++;
else if ( frac < -0.5 )
e--;
numberf(f,__n/pow(10.0L,e),'f',size-4, precision, type);
putc( exp_sign,f);
size--;
ie = (long)e;
type = LEFT | PLUS;
if ( ie < 0 )
type |= SIGN;
number(f,ie, 10,2, 2,type );
return;
}
if ( exp_sign == 'f' ) {
buf = alloca(4096);
if (type & LEFT) {
type &= ~ZEROPAD;
}
c = (type & ZEROPAD) ? '0' : ' ';
sign = 0;
if (type & SIGN) {
if (__n < 0) {
sign = '-';
__n = fabs(__n);
size--;
} else if (type & PLUS) {
sign = '+';
size--;
} else if (type & SPACE) {
sign = ' ';
size--;
}
}
frac = modf(__n,&intr);
// # flags forces a . and prevents trucation of trailing zero's
if ( precision > 0 ) {
//frac = modfl(__n,&intr);
i = precision-1;
while ( i >= 0 ) {
frac*=10.0L;
frac = modf(frac, &p);
buf[i] = (int)p + '0';
i--;
}
i = precision;
size -= precision;
ro = 0;
if ( frac > 0.5 ) {
ro = 1;
}
if ( precision >= 1 || type & SPECIAL) {
buf[i++] = '.';
size--;
}
}
if ( intr == 0.0 ) {
buf[i++] = '0';
size--;
}
else {
while ( intr > 0.0 ) {
intr/=10.0L;
p = modf(intr, &intr);
p *=10;
buf[i++] = (int)p + '0';
size--;
}
}
j = 0;
while ( j < i && ro == 1) {
if ( buf[j] >= '0' && buf[j] <= '8' ) {
buf[j]++;
ro = 0;
}
else if ( buf[j] == '9' ) {
buf[j] = '0';
}
j++;
}
if ( ro == 1 )
buf[i++] = '1';
buf[i] = 0;
size -= precision;
if (!(type&(ZEROPAD+LEFT)))
while(size-->0)
putc( ' ',f);
if (sign)
putc( sign,f);
if (!(type&(ZEROPAD+LEFT)))
while(size-->0)
putc( ' ',f);
if (type & SPECIAL) {
}
if (!(type & LEFT))
while (size-- > 0)
putc( c,f);
tmp = buf;
if ( type & ZEROTRUNC && ((type & SPECIAL) != SPECIAL) ) {
j = 0;
while ( j < i && ( *tmp == '0' || *tmp == '.' )) {
tmp++;
i--;
}
}
// else
// while (i < precision--)
// putc( '0', f);
while (i-- > 0)
putc( tmp[i],f);
while (size-- > 0)
putc( ' ', f);
}
}
void numberfl(FILE * f, long double __n, char exp_sign, int size, int precision, int type)
{
long double exponent = 0.0;
@ -185,7 +382,7 @@ void numberf(FILE * f, long double __n, char exp_sign, int size, int precision,
long double p;
char sign;
char c;
char ro;
char ro = 0;
long_double_t *n = (long_double_t *)&__n;
@ -259,7 +456,7 @@ void numberf(FILE * f, long double __n, char exp_sign, int size, int precision,
if ( precision > 0 ) {
frac = modfl(__n,&intr);
//frac = modfl(__n,&intr);
i = precision-1;
while ( i >= 0 ) {
@ -370,6 +567,7 @@ __vfprintf(FILE *f, const char *fmt, va_list args)
unsigned long num;
int i, base;
long double _ldouble;
double _double;
const char *s;
const short int* sw;
@ -378,7 +576,7 @@ __vfprintf(FILE *f, const char *fmt, va_list args)
int field_width; /* width of output field */
int precision; /* min. # of digits for integers; max
number of chars for from string */
int qualifier; /* 'h', 'l', or 'L' for integer fields */
int qualifier = 0; /* 'h', 'l', or 'L' for integer fields */
for (; *fmt ; ++fmt) {
if (*fmt != '%') {
@ -498,10 +696,8 @@ __vfprintf(FILE *f, const char *fmt, va_list args)
case 'g':
case 'G':
if (qualifier == 'l' || qualifier == 'L' )
if (qualifier == 'l' || qualifier == 'L' ) {
_ldouble = va_arg(args, long double);
else
_ldouble = (long double)va_arg(args, double);
if ( _isnanl(_ldouble) ) {
s = "Nan";
@ -531,9 +727,46 @@ __vfprintf(FILE *f, const char *fmt, va_list args)
else {
if ( precision == -1 )
precision = 6;
numberf(f,_ldouble,*fmt,field_width,precision,flags);
numberfl(f,_ldouble,*fmt,field_width,precision,flags);
}
}
else {
_double = (double)va_arg(args, double);
if ( _isnan(_double) ) {
s = "Nan";
len = 3;
while ( len > 0 ) {
putc(*s++,f);
len --;
}
}
else if ( _isinf(_double) < 0 ) {
s = "-Inf";
len = 4;
while ( len > 0 ) {
putc(*s++,f);
len --;
}
}
else if ( _isinf(_double) > 0 ) {
s = "+Inf";
len = 4;
while ( len > 0 ) {
putc(*s++,f);
len --;
}
}
else {
if ( precision == -1 )
precision = 6;
numberf(f,_double,*fmt,field_width,precision,flags);
}
}
continue;
case 's':
s = va_arg(args, char *);

View file

@ -20,7 +20,7 @@
#include <crtdll/errno.h>
#include <limits.h>
#include <crtdll/ctype.h>
#include <crtdll/stdarg.h>
#include <stdarg.h>
#include <crtdll/stdio.h>
#include <crtdll/stdlib.h>
#include <crtdll/string.h>

View file

@ -17,7 +17,7 @@ not, write to the Free Software Foundation, Inc., 675 Mass Ave,
Cambridge, MA 02139, USA. */
#include <crtdll/errno.h>
#include <crtdll/stdarg.h>
#include <stdarg.h>
#include <crtdll/stdio.h>
#include <crtdll/string.h>
#include <crtdll/internal/file.h>

View file

@ -2,6 +2,7 @@
#include <crtdll/stdlib.h>
#include <crtdll/sys/utime.h>
#include <crtdll/io.h>
#include <crtdll/time.h>
#include <crtdll/errno.h>
#include <crtdll/internal/file.h>
@ -18,8 +19,8 @@ int _futime (int nHandle, struct _utimbuf *pTimes)
if ( pTimes == NULL ) {
pTimes = alloca(sizeof(struct _utimbuf));
time(pTimes->actime);
time(pTimes->modtime);
time(&pTimes->actime);
time(&pTimes->modtime);
}
if ( pTimes->actime < pTimes->modtime ) {