Subversion Repositories Kolibri OS

Rev

Rev 548 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
548 serge 1
/****************************************************************************
2
*
3
*                            Open Watcom Project
4
*
5
*    Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
6
*
7
*  ========================================================================
8
*
9
*    This file contains Original Code and/or Modifications of Original
10
*    Code as defined in and that are subject to the Sybase Open Watcom
11
*    Public License version 1.0 (the 'License'). You may not use this file
12
*    except in compliance with the License. BY USING THIS FILE YOU AGREE TO
13
*    ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
14
*    provided with the Original Code and Modifications, and is also
15
*    available at www.sybase.com/developer/opensource.
16
*
17
*    The Original Code and all software distributed under the License are
18
*    distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
19
*    EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
20
*    ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
21
*    MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
22
*    NON-INFRINGEMENT. Please see the License for the specific language
23
*    governing rights and limitations under the License.
24
*
25
*  ========================================================================
26
*
27
* Description:  Win32 implementation of open() and sopen().
28
*
29
****************************************************************************/
30
 
31
 
32
#include "variety.h"
33
#include "widechar.h"
34
#include 
35
#include 
36
#include 
37
#include 
38
#include 
39
#include 
40
#include 
41
#include 
42
#include 
43
#include "liballoc.h"
44
#include "iomode.h"
45
#include "fileacc.h"
46
#include "openmode.h"
47
#include "rtdata.h"
48
#include "seterrno.h"
49
 
50
extern unsigned __NFiles;
51
extern char *__appcwd;
52
extern int __appcwdlen;
53
 
54
#if (defined(__WINDOWS__) || defined(__NT__))
55
 
56
typedef struct
57
{   DWORD    attr;
58
    DWORD    flags;
59
    DWORD    cr_time;
60
    DWORD    cr_date;
61
    DWORD    acc_time;
62
    DWORD    acc_date;
63
    DWORD    mod_time;
64
    DWORD    mod_date;
65
    DWORD    size;
66
    DWORD    size_high;
67
} FILEINFO;
68
 
69
int _stdcall get_fileinfo(const char *name,FILEINFO* pinfo);
550 serge 70
int _stdcall create_file(const char *name);
548 serge 71
 
72
 
73
typedef struct
74
{
75
  char     *name;
76
  unsigned int offset;
77
}__file_handle;
78
 
79
 
550 serge 80
char* getfullpath(const char* path)
548 serge 81
{
82
    int prev_is_slash=0;
83
    int len=0, depth=0, i;
84
    char* buff;
85
    char c;
86
 
87
    if(*path == '/')
88
    {
89
      buff = (char*)lib_malloc(strlen(path)+1);
90
      buff[0] = '\0';
91
      len=0;
92
    }
93
    else
94
    {
95
      len= __appcwdlen;
96
      buff = (char*)lib_malloc(len+strlen(path)+1);
97
      strncpy(buff, __appcwd, __appcwdlen);
98
 
99
      prev_is_slash = 1;
100
      buff[len] = 0;
101
      for(i=0; buff[i]; i++)
102
        if(buff[i] == '/' && i < len-1) depth++;
103
    }
104
 
105
    while(c=*path++)
106
    {
107
      switch (c)
108
      {
109
 
110
        case '.':
111
          if((*path == '.')&&
112
             (*path+1)== '/')
113
          { if(!depth)
114
            {  free(buff);
115
               return 0;
116
            };
117
            buff[len-1] = 0;
118
            len = strrchr(buff, '/') + 1 - buff;
119
            buff[len] = 0;
120
            depth--;
121
            path +=2;
122
            prev_is_slash = 1;
123
            continue;
124
          }
125
          if(*path == '/')
126
          {
127
            path++;
128
            prev_is_slash = 1;
129
            continue;
130
          }
131
          buff[len++] = c;
132
          continue;
133
 
134
        case '/':
135
          prev_is_slash = 1;
136
          buff[len++] = c;
137
          continue;
138
 
139
        default:
140
          prev_is_slash = 0;
141
          buff[len++] = c;
142
          continue;
143
        };
144
    };
145
    buff[len]= '\0';
146
    return buff;
147
};
148
 
149
 
150
size_t FileSize(FILE *fp)
151
{
152
  int hdl;
153
  __file_handle *fh;
154
  FILEINFO info;
155
 
156
  hdl = fileno( fp );
157
 // __handle_check( hdl, -1 );
158
 
159
  fh = (__file_handle*) __getOSHandle(hdl);
160
 
161
 
162
  get_fileinfo(fh->name,&info);
163
 
164
  return info.size;
165
 
166
}
167
 
168
int access(const char *path, int mode)
169
{ size_t retval;
170
  FILEINFO info;
171
  char *p;
172
 
173
  p = getfullpath(path);
174
  retval=get_fileinfo(p,&info);
175
  free(p);
176
 
177
  return retval;
178
 
179
}
180
 
550 serge 181
static HANDLE __openFileHandle(const CHAR_TYPE *name, int mode)
548 serge 182
{
183
  FILEINFO info;
184
  __file_handle *handle;
185
  char *path;
550 serge 186
  int err;
187
 
548 serge 188
  path = getfullpath(name);
189
 
550 serge 190
  if(err=get_fileinfo(path,&info))
548 serge 191
  {
550 serge 192
//    printf("failed getfileinfo %s\n\r", path);
193
 
194
    if(mode & O_CREAT)
195
      err=create_file(path);
196
 
197
    if(err)
198
    {
199
      lib_free(path);
200
      return (HANDLE)-1;
201
    };
548 serge 202
  };
203
 
204
  if ( !(handle=(__file_handle*)lib_malloc(sizeof( __file_handle) )))
205
  { lib_free(path);
206
    return (HANDLE)-1;
207
  };
208
 
209
  handle->name = path;
210
  handle->offset = 0;
211
 
212
  return (HANDLE)handle;
213
};
214
 
215
 
216
static int __F_NAME(_sopen,__wsopen)( const CHAR_TYPE *name, int mode, int share, va_list args )
217
{
218
    HANDLE              handle;
219
    int                 hid, rwmode;
220
    unsigned            iomode_flags;
221
 
222
    // First try to get the required slot.
223
    // No point in creating a file only to not use it.  JBS 99/10/26
224
    hid = __allocPOSIXHandle( DUMMY_HANDLE );
225
    if( hid == -1 )
226
     {
227
        return( -1 );
228
    }
229
 
230
    rwmode = mode;
231
 
232
 
233
    /*** Open the file ***/
234
 
550 serge 235
    handle = __openFileHandle( name, mode);
548 serge 236
 
237
    if( handle==(HANDLE)-1 )
238
    {
550 serge 239
      __freePOSIXHandle( hid );
240
      return( -1 ); //error
548 serge 241
    }
242
 
243
// Now use the slot we got.
244
    __setOSHandle( hid, handle );   // JBS 99/11/01
245
 
246
    iomode_flags = 0;
247
 
248
 
249
    if( rwmode == O_RDWR )       iomode_flags |= _READ | _WRITE;
250
    else if( rwmode == O_RDONLY) iomode_flags |= _READ;
251
    else if( rwmode == O_WRONLY) iomode_flags |= _WRITE;
252
    if( mode & O_APPEND )        iomode_flags |= _APPEND;
253
    if( mode & (O_BINARY|O_TEXT) ) {
254
        if( mode & O_BINARY )    iomode_flags |= _BINARY;
255
    } else {
256
        if( _RWD_fmode == O_BINARY ) iomode_flags |= _BINARY;
257
    }
258
    __SetIOMode( hid, iomode_flags );
259
    return( hid );
260
}
261
 
262
#elif
263
static int __F_NAME(_sopen,__wsopen)( const CHAR_TYPE *name, int mode, int share, va_list args )
264
{
265
    DWORD               create_disp, exists_disp;
266
    DWORD               perm, fileattr;
267
    DWORD               desired_access, share_mode;
268
    SECURITY_ATTRIBUTES security;
269
    HANDLE              handle;
270
    int                 hid, rwmode;
271
    unsigned            iomode_flags;
272
 
273
    // First try to get the required slot.
274
    // No point in creating a file only to not use it.  JBS 99/10/26
275
    hid = __allocPOSIXHandle( DUMMY_HANDLE );
276
    if( hid == -1 ) {
277
        return( -1 );
278
    }
279
 
280
    rwmode = mode & OPENMODE_ACCESS_MASK;
281
    __GetNTAccessAttr( rwmode, &desired_access, &perm );
282
    __GetNTShareAttr( share|rwmode, &share_mode );
283
    fileattr = FILE_ATTRIBUTE_NORMAL;
284
 
285
    security.nLength = sizeof( SECURITY_ATTRIBUTES );
286
    security.lpSecurityDescriptor = NULL;
287
    security.bInheritHandle = mode&O_NOINHERIT ? FALSE : TRUE;
288
 
289
#ifdef DEFAULT_WINDOWING
290
#ifdef __WIDECHAR__
291
    if( _WindowsNewWindow != 0 && !_wcsicmp( name, L"con" ) )
292
#else
293
    if( _WindowsNewWindow != 0 && !stricmp( name, "con" ) )
294
#endif
295
    {
296
        handle = (HANDLE) __NTGetFakeHandle();
297
 
298
        // Now use the slot we got.
299
        __setOSHandle( hid, handle );   // JBS 99/11/01
300
        _WindowsNewWindow( NULL, hid, -1 );
301
 
302
        iomode_flags = _ISTTY;
303
    } else {
304
#endif
305
        if( mode & O_CREAT ) {
306
            perm = va_arg( args, int );
307
                va_end( args );
308
                perm &= ~_RWD_umaskval;             /* 05-jan-95 */
309
            if( ( perm & S_IREAD ) && !( perm & S_IWRITE ) ) {
310
                fileattr = FILE_ATTRIBUTE_READONLY;
311
            }
312
            if( mode & O_EXCL ) {
313
                create_disp = CREATE_NEW;
314
                exists_disp = CREATE_NEW;
315
            } else if( mode & O_TRUNC ) {
316
                create_disp = CREATE_ALWAYS;
317
                exists_disp = CREATE_NEW;
318
            } else {
319
                create_disp = OPEN_ALWAYS;
320
                exists_disp = OPEN_EXISTING;
321
            }
322
        } else if( mode & O_TRUNC ) {
323
            exists_disp = TRUNCATE_EXISTING;
324
        } else {
325
            exists_disp = OPEN_EXISTING;
326
        }
327
 
328
        /*** Open the file ***/
329
        #ifdef __WIDECHAR__
330
            handle = __lib_CreateFileW( name, desired_access, share_mode,
331
                                        &security, exists_disp, fileattr,
332
                                        NULL );
333
        #else
334
            handle = CreateFileA( name, desired_access, share_mode,
335
                                  &security, exists_disp, fileattr, NULL );
336
        #endif
337
        if( handle==(HANDLE)-1 ) {
338
            if( mode&O_CREAT ) {
339
                #ifdef __WIDECHAR__
340
                    handle = __lib_CreateFileW( name, desired_access,
341
                                                share_mode, NULL, create_disp,
342
                                                fileattr, NULL );
343
                #else
344
                    handle = CreateFileA( name, desired_access,
345
                                          share_mode, NULL, create_disp,
346
                                          fileattr, NULL );
347
                #endif
348
            }
349
            if( handle == (HANDLE)-1 ) {
350
                __freePOSIXHandle( hid );
351
                return( __set_errno_nt() );
352
            }
353
        }
354
 
355
        // Now use the slot we got.
356
        __setOSHandle( hid, handle );   // JBS 99/11/01
357
 
358
        iomode_flags = 0;
359
 
360
        if( isatty(hid) ) {
361
            iomode_flags = _ISTTY;
362
        }
363
#ifdef DEFAULT_WINDOWING
364
    }
365
#endif
366
 
367
    if( rwmode == O_RDWR )       iomode_flags |= _READ | _WRITE;
368
    else if( rwmode == O_RDONLY) iomode_flags |= _READ;
369
    else if( rwmode == O_WRONLY) iomode_flags |= _WRITE;
370
    if( mode & O_APPEND )        iomode_flags |= _APPEND;
371
    if( mode & (O_BINARY|O_TEXT) ) {
372
        if( mode & O_BINARY )    iomode_flags |= _BINARY;
373
    } else {
374
        if( _RWD_fmode == O_BINARY ) iomode_flags |= _BINARY;
375
    }
376
    __SetIOMode( hid, iomode_flags );
377
    return( hid );
378
}
379
#endif
380
 
381
_WCRTLINK int __F_NAME(open,_wopen)( const CHAR_TYPE *name, int mode, ... )
382
{
383
    int         permission;
384
    va_list     args;
385
 
386
    va_start( args, mode );
387
    permission = va_arg( args, int );
388
    va_end( args );
389
    return( __F_NAME(sopen,_wsopen)( name, mode, SH_COMPAT, permission ) );
390
}
391
 
392
 
393
_WCRTLINK int __F_NAME(sopen,_wsopen)( const CHAR_TYPE *name, int mode, int shflag, ... )
394
{
395
    va_list             args;
396
 
397
    va_start( args, shflag );
398
    return( __F_NAME(_sopen,__wsopen)( name, mode, shflag, args ) );
399
}