Subversion Repositories HelenOS

Rev

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

Rev 3448 Rev 3474
Line 44... Line 44...
44
 */
44
 */
45
 
45
 
46
#include <stdio.h>
46
#include <stdio.h>
47
#include <stdlib.h>
47
#include <stdlib.h>
48
#include <unistd.h>
48
#include <unistd.h>
-
 
49
#include <bool.h>
49
#include <fcntl.h>
50
#include <fcntl.h>
50
#include <sys/types.h>
51
#include <sys/types.h>
51
#include <ipc/ipc.h>
52
#include <ipc/ipc.h>
52
#include <ipc/loader.h>
53
#include <ipc/loader.h>
53
#include <loader/pcb.h>
54
#include <loader/pcb.h>
Line 75... Line 76...
75
/** Argument vector */
76
/** Argument vector */
76
static char **argv = NULL;
77
static char **argv = NULL;
77
/** Buffer holding all arguments */
78
/** Buffer holding all arguments */
78
static char *arg_buf = NULL;
79
static char *arg_buf = NULL;
79
 
80
 
-
 
81
static elf_info_t prog_info;
-
 
82
static elf_info_t interp_info;
-
 
83
 
-
 
84
static bool is_dyn_linked;
-
 
85
 
-
 
86
 
80
static int loader_get_taskid(ipc_callid_t rid, ipc_call_t *request)
87
static void loader_get_taskid(ipc_callid_t rid, ipc_call_t *request)
81
{
88
{
82
    ipc_callid_t callid;
89
    ipc_callid_t callid;
83
    task_id_t task_id;
90
    task_id_t task_id;
84
    size_t len;
91
    size_t len;
85
 
92
 
Line 210... Line 217...
210
 
217
 
211
    argc = n;
218
    argc = n;
212
    argv[n] = NULL;
219
    argv[n] = NULL;
213
}
220
}
214
 
221
 
215
 
-
 
216
/** Load and run the previously selected program.
222
/** Load the previously selected program.
217
 *
223
 *
218
 * @param rid
224
 * @param rid
219
 * @param request
225
 * @param request
220
 * @return 0 on success, !0 on error.
226
 * @return 0 on success, !0 on error.
221
 */
227
 */
222
static int loader_run(ipc_callid_t rid, ipc_call_t *request)
228
static int loader_load(ipc_callid_t rid, ipc_call_t *request)
223
{
229
{
224
    int rc;
230
    int rc;
225
 
231
 
226
    elf_info_t prog_info;
-
 
227
    elf_info_t interp_info;
-
 
228
 
-
 
229
//  printf("Load program '%s'\n", pathname);
232
//  printf("Load program '%s'\n", pathname);
230
 
233
 
231
    rc = elf_load_file(pathname, 0, &prog_info);
234
    rc = elf_load_file(pathname, 0, &prog_info);
232
    if (rc < 0) {
235
    if (rc < 0) {
233
        printf("failed to load program\n");
236
        printf("failed to load program\n");
Line 243... Line 246...
243
 
246
 
244
    if (prog_info.interp == NULL) {
247
    if (prog_info.interp == NULL) {
245
        /* Statically linked program */
248
        /* Statically linked program */
246
//      printf("Run statically linked program\n");
249
//      printf("Run statically linked program\n");
247
//      printf("entry point: 0x%llx\n", prog_info.entry);
250
//      printf("entry point: 0x%llx\n", prog_info.entry);
-
 
251
        is_dyn_linked = false;
248
        ipc_answer_0(rid, EOK);
252
        ipc_answer_0(rid, EOK);
249
        close_console();
-
 
250
        elf_run(&prog_info, &pcb);
-
 
251
        return 0;
253
        return 0;
252
    }
254
    }
253
 
255
 
254
    printf("Load dynamic linker '%s'\n", prog_info.interp);
256
    printf("Load dynamic linker '%s'\n", prog_info.interp);
255
    rc = elf_load_file(prog_info.interp, RTLD_BIAS, &interp_info);
257
    rc = elf_load_file(prog_info.interp, RTLD_BIAS, &interp_info);
Line 267... Line 269...
267
 
269
 
268
    printf("run dynamic linker\n");
270
    printf("run dynamic linker\n");
269
    printf("rtld_dynamic = 0x%lx\n", pcb.rtld_dynamic);
271
    printf("rtld_dynamic = 0x%lx\n", pcb.rtld_dynamic);
270
    printf("entry point: 0x%lx\n", interp_info.entry);
272
    printf("entry point: 0x%lx\n", interp_info.entry);
271
    printf("pcb address: 0x%lx\n", &pcb);
273
    printf("pcb address: 0x%lx\n", &pcb);
272
    close_console();
-
 
273
 
274
 
-
 
275
    is_dyn_linked = true;
274
    ipc_answer_0(rid, EOK);
276
    ipc_answer_0(rid, EOK);
275
    elf_run(&interp_info, &pcb);
-
 
276
 
277
 
277
    /* Not reached */
-
 
278
    return 0;
278
    return 0;
279
}
279
}
280
 
280
 
-
 
281
 
-
 
282
/** Run the previously loaded program.
-
 
283
 *
-
 
284
 * @param rid
-
 
285
 * @param request
-
 
286
 * @return 0 on success, !0 on error.
-
 
287
 */
-
 
288
static void loader_run(ipc_callid_t rid, ipc_call_t *request)
-
 
289
{
-
 
290
    if (is_dyn_linked == true) {
-
 
291
        /* Dynamically linked program */
-
 
292
        printf("run dynamic linker\n");
-
 
293
        printf("entry point: 0x%llx\n", interp_info.entry);
-
 
294
        close_console();
-
 
295
 
-
 
296
        ipc_answer_0(rid, EOK);
-
 
297
        elf_run(&interp_info, &pcb);
-
 
298
 
-
 
299
    } else {
-
 
300
        /* Statically linked program */
-
 
301
        close_console();
-
 
302
        ipc_answer_0(rid, EOK);
-
 
303
        elf_run(&prog_info, &pcb);
-
 
304
    }
-
 
305
 
-
 
306
    /* Not reached */
-
 
307
}
-
 
308
 
281
/** Handle loader connection.
309
/** Handle loader connection.
282
 *
310
 *
283
 * Receive and carry out commands (of which the last one should be
311
 * Receive and carry out commands (of which the last one should be
284
 * to execute the loaded program).
312
 * to execute the loaded program).
285
 */
313
 */
Line 292... Line 320...
292
    /* Ignore parameters, the connection is already open */
320
    /* Ignore parameters, the connection is already open */
293
    (void)iid; (void)icall;
321
    (void)iid; (void)icall;
294
 
322
 
295
    while (1) {
323
    while (1) {
296
        callid = async_get_call(&call);
324
        callid = async_get_call(&call);
297
//      printf("received call from phone %d, method=%d\n",
-
 
298
//          call.in_phone_hash, IPC_GET_METHOD(call));
-
 
-
 
325
 
299
        switch (IPC_GET_METHOD(call)) {
326
        switch (IPC_GET_METHOD(call)) {
300
        case LOADER_GET_TASKID:
327
        case LOADER_GET_TASKID:
301
            loader_get_taskid(callid, &call);
328
            loader_get_taskid(callid, &call);
302
            continue;
329
            continue;
303
        case LOADER_SET_PATHNAME:
330
        case LOADER_SET_PATHNAME:
304
            loader_set_pathname(callid, &call);
331
            loader_set_pathname(callid, &call);
305
            continue;
332
            continue;
306
        case LOADER_SET_ARGS:
333
        case LOADER_SET_ARGS:
307
            loader_set_args(callid, &call);
334
            loader_set_args(callid, &call);
-
 
335
            continue;
-
 
336
        case LOADER_LOAD:
-
 
337
            loader_load(callid, &call);
-
 
338
            continue;
308
        case LOADER_RUN:
339
        case LOADER_RUN:
309
            loader_run(callid, &call);
340
            loader_run(callid, &call);
310
            exit(0);
-
 
311
            continue;
341
            /* Not reached */
312
        default:
342
        default:
313
            retval = ENOENT;
343
            retval = ENOENT;
314
            break;
344
            break;
315
        }
345
        }
316
        if ((callid & IPC_CALLID_NOTIFICATION) == 0 &&
346
        if ((callid & IPC_CALLID_NOTIFICATION) == 0 &&