Subversion Repositories Kolibri OS

Rev

Rev 9346 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
4921 Serge 1
/* open.c -- open a file.
2
 *
3
 * Copyright (c) 1995 Cygnus Support
4
 *
5
 * The authors hereby grant permission to use, copy, modify, distribute,
6
 * and license this software and its documentation for any purpose, provided
7
 * that existing copyright notices are retained in all copies and that this
8
 * notice is included verbatim in any distributions. No written agreement,
9
 * license, or royalty fee is required for any of the authorized uses.
10
 * Modifications to this software may be copyrighted by their authors
11
 * and need not follow the licensing terms described here, provided that
12
 * the new terms are clearly indicated on the first page of each file where
13
 * they apply.
14
 */
15
#include 
16
#include 
17
#include 
9952 turbocat 18
#include 
19
 
4921 Serge 20
#include "glue.h"
21
#include "io.h"
22
 
9952 turbocat 23
#undef errno
4921 Serge 24
extern int errno;
25
 
9952 turbocat 26
extern int write_file(const char *path,const void *buff,
27
                      size_t offset, size_t count, size_t *writes);
28
 
29
extern int read_file(const char *path, void *buff,
30
               size_t offset, size_t count, size_t *reads);
31
 
5198 serge 32
static inline int is_slash(char c)
33
{
34
    return c=='/' || c=='\\';
35
}
36
 
37
void fix_slashes(char * in,char * out)
38
{
39
    int slash_count;
40
 
41
    for(slash_count=1;in && out && *in;in++)
42
    {
43
        if(is_slash(*in))
44
        {
45
            slash_count++;
46
            continue;
47
        }
48
        else
49
        {
50
            if(slash_count)
51
            {
52
                slash_count=0;
53
                *out++='/';
54
            }
55
            *out++=*in;
56
        }
57
    }
58
    *out='\0';
9952 turbocat 59
}
5198 serge 60
 
61
 
62
void buildpath(char *buf, const char* file)
63
{
64
    char *ptr;
65
 
66
    ptr = buf + strlen(buf);
67
 
68
    while (*file)
69
    {
70
        if (file[0] == '.' && file[1] == 0)
71
            break;
72
 
73
        if (file[0] == '.' && file[1] == '/')
74
        {
75
            file+=2;
76
            continue;
77
        };
78
 
79
        if (file[0] == '.' && file[1] == '.' &&
80
            (file[2] == 0 || file[2] == '/'))
81
        {
82
            while (ptr > buf && ptr[-1] != '/')
83
                --ptr;
84
            file+=2;
85
            if (*file == 0)
86
                break;
87
            ++file;
9346 Coldy 88
            //continue;
89
            goto __do_until_slash;
5198 serge 90
        }
91
        *ptr++ = '/';
9346 Coldy 92
__do_until_slash:
5198 serge 93
        if (*file == '/')
94
            ++file;
95
        while (*file && *file!='/')
96
            *ptr++ = *file++;
97
    }
98
    *ptr = 0;
9952 turbocat 99
}
5198 serge 100
 
4921 Serge 101
int open (const char * filename, int flags, ...)
102
{
5198 serge 103
    char buf[1024];
104
 
4921 Serge 105
    __io_handle *ioh;
9952 turbocat 106
    ksys_file_info_t info;
4921 Serge 107
    int iomode, rwmode, offset;
108
    int hid;
109
    int err;
110
 
111
    hid = __io_alloc();
112
    if(hid < 0)
113
    {
114
        errno = EMFILE;
6744 siemargl 115
        __io_free(hid);
4921 Serge 116
        return (-1);
117
    };
118
 
5198 serge 119
    if (filename[0]=='/')
120
    {
121
        strcpy(buf,filename);
122
    }
123
    else
124
    {
9952 turbocat 125
        _ksys_getcwd(buf, 1024);
5198 serge 126
        buildpath(buf, filename);
127
    }
4921 Serge 128
 
9952 turbocat 129
    err = _ksys_file_info(buf, &info);
5198 serge 130
 
9952 turbocat 131
    if (flags & O_EXCL &&
4921 Serge 132
        flags & O_CREAT )
133
    {
9952 turbocat 134
        if (!err)
4921 Serge 135
        {
136
            errno = EEXIST;
6744 siemargl 137
            __io_free(hid);
4921 Serge 138
            return (-1);
9952 turbocat 139
        }
4921 Serge 140
    }
141
 
9952 turbocat 142
    if (err)
4921 Serge 143
    {
144
        if(flags & O_CREAT)
9952 turbocat 145
            err = _ksys_file_create(buf).status;
146
        if(err)
4921 Serge 147
        {
148
            errno = EACCES;
6744 siemargl 149
            __io_free(hid);
4921 Serge 150
            return -1;
151
        };
152
    };
153
 
9952 turbocat 154
    if (flags & O_TRUNC)
155
        _ksys_file_set_size(buf, 0);
4921 Serge 156
 
157
    ioh = &__io_tab[hid];
158
 
159
    rwmode = flags & ( O_RDONLY | O_WRONLY | O_RDWR );
160
 
161
    iomode = 0;
162
    offset = 0;
163
 
9952 turbocat 164
    if (rwmode == O_RDWR)
4921 Serge 165
        iomode |= _READ | _WRITE;
9952 turbocat 166
    else if (rwmode == O_RDONLY)
4921 Serge 167
        iomode |= _READ;
9952 turbocat 168
    else if (rwmode == O_WRONLY)
4921 Serge 169
        iomode |= _WRITE;
170
 
9952 turbocat 171
    if (flags & O_APPEND)
4921 Serge 172
    {
173
        iomode |= _APPEND;
174
        offset = info.size;
9952 turbocat 175
    }
4921 Serge 176
 
9952 turbocat 177
    if (flags & (O_BINARY|O_TEXT))
4921 Serge 178
    {
9952 turbocat 179
        if (flags & O_BINARY)
4921 Serge 180
            iomode |= _BINARY;
9952 turbocat 181
    }
182
    else
183
    {
4921 Serge 184
        iomode |= _BINARY;
9952 turbocat 185
    }
4921 Serge 186
 
5198 serge 187
    ioh->name   = strdup(buf);
4921 Serge 188
    ioh->offset = offset;
189
    ioh->mode   = iomode;
190
    ioh->read   = read_file;
191
    ioh->write  = write_file;
192
 
193
    return hid;
9952 turbocat 194
}