OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [rc203soc/] [sw/] [uClinux/] [kernel/] [exec_domain.c] - Blame information for rev 1777

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 1634 jcastillo
#include <linux/personality.h>
2
#include <linux/ptrace.h>
3
#include <linux/sched.h>
4
#include <linux/mm.h>
5
 
6
static asmlinkage void no_lcall7(struct pt_regs * regs);
7
 
8
 
9
static unsigned long ident_map[32] = {
10
        0,       1,      2,      3,      4,      5,      6,      7,
11
        8,      9,      10,     11,     12,     13,     14,     15,
12
        16,     17,     18,     19,     20,     21,     22,     23,
13
        24,     25,     26,     27,     28,     29,     30,     31
14
};
15
 
16
struct exec_domain default_exec_domain = {
17
        "Linux",        /* name */
18
        no_lcall7,      /* lcall7 causes a seg fault. */
19
        0, 0xff, /* All personalities. */
20
        ident_map,      /* Identity map signals. */
21
        ident_map,      /*  - both ways. */
22
        NULL,           /* No usage counter. */
23
        NULL            /* Nothing after this in the list. */
24
};
25
 
26
static struct exec_domain *exec_domains = &default_exec_domain;
27
 
28
 
29
static asmlinkage void no_lcall7(struct pt_regs * regs)
30
{
31
 
32
  /*
33
   * This may have been a static linked SVr4 binary, so we would have the
34
   * personality set incorrectly.  Check to see whether SVr4 is available,
35
   * and use it, otherwise give the user a SEGV.
36
   */
37
        if (current->exec_domain && current->exec_domain->use_count)
38
                (*current->exec_domain->use_count)--;
39
 
40
        current->personality = PER_SVR4;
41
        current->exec_domain = lookup_exec_domain(current->personality);
42
 
43
        if (current->exec_domain && current->exec_domain->use_count)
44
                (*current->exec_domain->use_count)++;
45
 
46
        if (current->exec_domain && current->exec_domain->handler
47
        && current->exec_domain->handler != no_lcall7) {
48
                current->exec_domain->handler(regs);
49
                return;
50
        }
51
 
52
        send_sig(SIGSEGV, current, 1);
53
}
54
 
55
struct exec_domain *lookup_exec_domain(unsigned long personality)
56
{
57
        unsigned long pers = personality & PER_MASK;
58
        struct exec_domain *it;
59
 
60
        for (it=exec_domains; it; it=it->next)
61
                if (pers >= it->pers_low
62
                && pers <= it->pers_high)
63
                        return it;
64
 
65
        /* Should never get this far. */
66
        printk(KERN_ERR "No execution domain for personality 0x%02lx\n", pers);
67
        return NULL;
68
}
69
 
70
int register_exec_domain(struct exec_domain *it)
71
{
72
        struct exec_domain *tmp;
73
 
74
        if (!it)
75
                return -EINVAL;
76
        if (it->next)
77
                return -EBUSY;
78
        for (tmp=exec_domains; tmp; tmp=tmp->next)
79
                if (tmp == it)
80
                        return -EBUSY;
81
        it->next = exec_domains;
82
        exec_domains = it;
83
        return 0;
84
}
85
 
86
int unregister_exec_domain(struct exec_domain *it)
87
{
88
        struct exec_domain ** tmp;
89
 
90
        tmp = &exec_domains;
91
        while (*tmp) {
92
                if (it == *tmp) {
93
                        *tmp = it->next;
94
                        it->next = NULL;
95
                        return 0;
96
                }
97
                tmp = &(*tmp)->next;
98
        }
99
        return -EINVAL;
100
}
101
 
102
asmlinkage int sys_personality(unsigned long personality)
103
{
104
        struct exec_domain *it;
105
        unsigned long old_personality;
106
 
107
        if (personality == 0xffffffff)
108
                return current->personality;
109
 
110
        it = lookup_exec_domain(personality);
111
        if (!it)
112
                return -EINVAL;
113
 
114
        old_personality = current->personality;
115
        if (current->exec_domain && current->exec_domain->use_count)
116
                (*current->exec_domain->use_count)--;
117
        current->personality = personality;
118
        current->exec_domain = it;
119
        if (current->exec_domain->use_count)
120
                (*current->exec_domain->use_count)++;
121
 
122
        return old_personality;
123
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.