Subversion Repositories HelenOS

Rev

Rev 2651 | Go to most recent revision | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 2651 Rev 2657
Line 77... Line 77...
77
    /*
77
    /*
78
     * For now, don't make use of ARG2 and ARG3, but they can be used to
78
     * For now, don't make use of ARG2 and ARG3, but they can be used to
79
     * carry mount options in the future.
79
     * carry mount options in the future.
80
     */
80
     */
81
 
81
 
-
 
82
    ipc_callid_t callid;
-
 
83
    size_t size;
-
 
84
 
82
    /*
85
    /*
83
     * Now, we expect the client to send us data with the name of the file
86
     * Now, we expect the client to send us data with the name of the file
84
     * system and the path of the mountpoint.
87
     * system.
85
     */
88
     */
86
    ipc_callid_t callid;
-
 
87
    size_t size;
-
 
88
    if (!ipc_data_receive(&callid, NULL, &size)) {
89
    if (!ipc_data_receive(&callid, NULL, &size)) {
89
        ipc_answer_0(callid, EINVAL);
90
        ipc_answer_0(callid, EINVAL);
90
        ipc_answer_0(rid, EINVAL);
91
        ipc_answer_0(rid, EINVAL);
91
        return;
92
        return;
92
    }
93
    }
93
 
94
 
94
    /*
95
    /*
95
     * There is no sense in receiving data that can't hold a single
96
     * Don't receive more than is necessary for storing a full file system
96
     * character of path. We won't accept data that exceed certain limits
-
 
97
     * either.
97
     * name.
98
     */
98
     */
99
    if ((size < FS_NAME_MAXLEN + 1) ||
99
    if (size < 1 || size > FS_NAME_MAXLEN) {
100
        (size > FS_NAME_MAXLEN + MAX_PATH_LEN)) {
-
 
101
        ipc_answer_0(callid, EINVAL);
100
        ipc_answer_0(callid, EINVAL);
102
        ipc_answer_0(rid, EINVAL);
101
        ipc_answer_0(rid, EINVAL);
103
        return;
102
        return;
104
    }
103
    }
105
 
104
 
106
    /*
105
    /*
-
 
106
     * Deliver the file system name.
-
 
107
     */
-
 
108
    char fs_name[FS_NAME_MAXLEN + 1];
-
 
109
    (void) ipc_data_deliver(callid, fs_name, size);
-
 
110
    fs_name[size] = '\0';
-
 
111
   
-
 
112
    /*
-
 
113
     * Check if we know a file system with the same name as is in fs_name.
-
 
114
     * This will also give us its file system handle.
-
 
115
     */
-
 
116
    int fs_handle = fs_name_to_handle(fs_name, true);
-
 
117
    if (!fs_handle) {
-
 
118
        ipc_answer_0(rid, ENOENT);
-
 
119
        return;
-
 
120
    }
-
 
121
 
-
 
122
    /*
-
 
123
     * Now, we want the client to send us the mount point.
-
 
124
     */
-
 
125
    if (!ipc_data_receive(&callid, NULL, &size)) {
-
 
126
        ipc_answer_0(callid, EINVAL);
-
 
127
        ipc_answer_0(rid, EINVAL);
-
 
128
        return;
-
 
129
    }
-
 
130
 
-
 
131
    /*
-
 
132
     * Check whether size is reasonable wrt. the mount point.
-
 
133
     */
-
 
134
    if (size < 1 || size > MAX_PATH_LEN) {
-
 
135
        ipc_answer_0(callid, EINVAL);
-
 
136
        ipc_answer_0(rid, EINVAL);
-
 
137
        return;
-
 
138
    }
-
 
139
    /*
107
     * Allocate buffer for the data being received.
140
     * Allocate buffer for the mount point data being received.
108
     */
141
     */
109
    uint8_t *buf;
142
    uint8_t *buf;
110
    buf = malloc(size);
143
    buf = malloc(size);
111
    if (!buf) {
144
    if (!buf) {
112
        ipc_answer_0(callid, ENOMEM);
145
        ipc_answer_0(callid, ENOMEM);
113
        ipc_answer_0(rid, ENOMEM);
146
        ipc_answer_0(rid, ENOMEM);
114
        return;
147
        return;
115
    }
148
    }
116
 
149
 
117
    /*
150
    /*
118
     * Deliver the data.
151
     * Deliver the mount point.
119
     */
152
     */
120
    (void) ipc_data_deliver(callid, buf, size);
153
    (void) ipc_data_deliver(callid, buf, size);
121
 
154
 
122
    char fs_name[FS_NAME_MAXLEN + 1];
-
 
123
    memcpy(fs_name, buf, FS_NAME_MAXLEN);
-
 
124
    fs_name[FS_NAME_MAXLEN] = '\0';
-
 
125
 
-
 
126
    /*
-
 
127
     * Check if we know a file system with the same name as is in fs_name.
-
 
128
     * This will also give us its file system handle.
-
 
129
     */
-
 
130
    int fs_handle = fs_name_to_handle(fs_name, true);
-
 
131
    if (!fs_handle) {
-
 
132
        free(buf);
-
 
133
        ipc_answer_0(rid, ENOENT);
-
 
134
        return;
-
 
135
    }
-
 
136
 
-
 
137
    /*
155
    /*
138
     * Lookup the root node of the filesystem being mounted.
156
     * Lookup the root node of the filesystem being mounted.
139
     * In this case, we don't need to take the unlink_futex as the root node
157
     * In this case, we don't need to take the unlink_futex as the root node
140
     * cannot be removed. However, we do take a reference to it so that
158
     * cannot be removed. However, we do take a reference to it so that
141
     * we can track how many times it has been mounted.
159
     * we can track how many times it has been mounted.
Line 163... Line 181...
163
    if (rootfs.fs_handle) {
181
    if (rootfs.fs_handle) {
164
        /*
182
        /*
165
         * We already have the root FS.
183
         * We already have the root FS.
166
         */
184
         */
167
        futex_down(&unlink_futex);
185
        futex_down(&unlink_futex);
168
        rc = vfs_lookup_internal((char *) (buf + FS_NAME_MAXLEN),
186
        rc = vfs_lookup_internal(buf, size, &mp, NULL);
169
            size - FS_NAME_MAXLEN, &mp, NULL);
-
 
170
        if (rc != EOK) {
187
        if (rc != EOK) {
171
            /*
188
            /*
172
             * The lookup failed for some reason.
189
             * The lookup failed for some reason.
173
             */
190
             */
174
            futex_up(&unlink_futex);
191
            futex_up(&unlink_futex);
Line 195... Line 212...
195
        futex_up(&unlink_futex);
212
        futex_up(&unlink_futex);
196
    } else {
213
    } else {
197
        /*
214
        /*
198
         * We still don't have the root file system mounted.
215
         * We still don't have the root file system mounted.
199
         */
216
         */
200
        if ((size - FS_NAME_MAXLEN == strlen("/")) &&
-
 
201
            (buf[FS_NAME_MAXLEN] == '/')) {
217
        if ((size == 1) && (buf[0] == '/')) {
202
            /*
218
            /*
203
             * For this simple, but important case, we are done.
219
             * For this simple, but important case, we are done.
204
             */
220
             */
205
            rootfs = mounted_root;
221
            rootfs = mounted_root;
206
            futex_up(&rootfs_futex);
222
            futex_up(&rootfs_futex);