Subversion Repositories HelenOS

Rev

Rev 1831 | Go to most recent revision | Only display areas with differences | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 1831 Rev 1888
1
/*
1
/*
2
 * Copyright (C) 2006 Martin Decky
2
 * Copyright (C) 2006 Martin Decky
3
 * All rights reserved.
3
 * All rights reserved.
4
 *
4
 *
5
 * Redistribution and use in source and binary forms, with or without
5
 * Redistribution and use in source and binary forms, with or without
6
 * modification, are permitted provided that the following conditions
6
 * modification, are permitted provided that the following conditions
7
 * are met:
7
 * are met:
8
 *
8
 *
9
 * - Redistributions of source code must retain the above copyright
9
 * - Redistributions of source code must retain the above copyright
10
 *   notice, this list of conditions and the following disclaimer.
10
 *   notice, this list of conditions and the following disclaimer.
11
 * - Redistributions in binary form must reproduce the above copyright
11
 * - Redistributions in binary form must reproduce the above copyright
12
 *   notice, this list of conditions and the following disclaimer in the
12
 *   notice, this list of conditions and the following disclaimer in the
13
 *   documentation and/or other materials provided with the distribution.
13
 *   documentation and/or other materials provided with the distribution.
14
 * - The name of the author may not be used to endorse or promote products
14
 * - The name of the author may not be used to endorse or promote products
15
 *   derived from this software without specific prior written permission.
15
 *   derived from this software without specific prior written permission.
16
 *
16
 *
17
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
17
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
18
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19
 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
19
 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20
 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
20
 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
21
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
25
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26
 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26
 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27
 */
27
 */
28
 
28
 
29
#ifndef __xen32_HYPERCALL_H__
29
#ifndef KERN_xen32_HYPERCALL_H_
30
#define __xen32_HYPERCALL_H__
30
#define KERN_xen32_HYPERCALL_H_
31
 
31
 
32
#include <arch/types.h>
32
#include <arch/types.h>
33
#include <macros.h>
33
#include <macros.h>
34
 
34
 
35
 
-
 
36
typedef uint16_t domid_t;
35
typedef uint16_t domid_t;
37
 
36
 
38
 
-
 
39
typedef struct {
37
typedef struct {
40
    uint8_t vector;     /**< Exception vector */
38
    uint8_t vector;     /**< Exception vector */
41
    uint8_t flags;      /**< 0-3: privilege level; 4: clear event enable */
39
    uint8_t flags;      /**< 0-3: privilege level; 4: clear event enable */
42
    uint16_t cs;        /**< Code selector */
40
    uint16_t cs;        /**< Code selector */
43
    void *address;      /**< Code offset */
41
    void *address;      /**< Code offset */
44
} trap_info_t;
42
} trap_info_t;
45
 
43
 
46
 
44
 
47
typedef struct {
45
typedef struct {
48
    evtchn_t port;
46
    evtchn_t port;
49
} evtchn_send_t;
47
} evtchn_send_t;
50
 
48
 
51
typedef struct {
49
typedef struct {
52
    uint32_t cmd;
50
    uint32_t cmd;
53
    union {
51
    union {
54
        evtchn_send_t send;
52
        evtchn_send_t send;
55
    };
53
    };
56
} evtchn_op_t;
54
} evtchn_op_t;
57
 
55
 
58
 
56
 
59
#define XEN_SET_TRAP_TABLE      0
57
#define XEN_SET_TRAP_TABLE      0
60
#define XEN_MMU_UPDATE          1
58
#define XEN_MMU_UPDATE          1
61
#define XEN_SET_CALLBACKS       4
59
#define XEN_SET_CALLBACKS       4
62
#define XEN_UPDATE_VA_MAPPING   14
60
#define XEN_UPDATE_VA_MAPPING   14
63
#define XEN_EVENT_CHANNEL_OP    16
61
#define XEN_EVENT_CHANNEL_OP    16
64
#define XEN_VERSION             17
62
#define XEN_VERSION             17
65
#define XEN_CONSOLE_IO          18
63
#define XEN_CONSOLE_IO          18
66
#define XEN_VM_ASSIST           21
64
#define XEN_VM_ASSIST           21
67
#define XEN_MMUEXT_OP           26
65
#define XEN_MMUEXT_OP           26
68
 
66
 
69
 
67
 
70
/*
68
/*
71
 * Commands for XEN_CONSOLE_IO
69
 * Commands for XEN_CONSOLE_IO
72
 */
70
 */
73
#define CONSOLE_IO_WRITE    0
71
#define CONSOLE_IO_WRITE    0
74
#define CONSOLE_IO_READ     1
72
#define CONSOLE_IO_READ     1
75
 
73
 
76
 
74
 
77
#define MMUEXT_PIN_L1_TABLE      0
75
#define MMUEXT_PIN_L1_TABLE      0
78
#define MMUEXT_PIN_L2_TABLE      1
76
#define MMUEXT_PIN_L2_TABLE      1
79
#define MMUEXT_PIN_L3_TABLE      2
77
#define MMUEXT_PIN_L3_TABLE      2
80
#define MMUEXT_PIN_L4_TABLE      3
78
#define MMUEXT_PIN_L4_TABLE      3
81
#define MMUEXT_UNPIN_TABLE       4
79
#define MMUEXT_UNPIN_TABLE       4
82
#define MMUEXT_NEW_BASEPTR       5
80
#define MMUEXT_NEW_BASEPTR       5
83
#define MMUEXT_TLB_FLUSH_LOCAL   6
81
#define MMUEXT_TLB_FLUSH_LOCAL   6
84
#define MMUEXT_INVLPG_LOCAL      7
82
#define MMUEXT_INVLPG_LOCAL      7
85
#define MMUEXT_TLB_FLUSH_MULTI   8
83
#define MMUEXT_TLB_FLUSH_MULTI   8
86
#define MMUEXT_INVLPG_MULTI      9
84
#define MMUEXT_INVLPG_MULTI      9
87
#define MMUEXT_TLB_FLUSH_ALL    10
85
#define MMUEXT_TLB_FLUSH_ALL    10
88
#define MMUEXT_INVLPG_ALL       11
86
#define MMUEXT_INVLPG_ALL       11
89
#define MMUEXT_FLUSH_CACHE      12
87
#define MMUEXT_FLUSH_CACHE      12
90
#define MMUEXT_SET_LDT          13
88
#define MMUEXT_SET_LDT          13
91
#define MMUEXT_NEW_USER_BASEPTR 15
89
#define MMUEXT_NEW_USER_BASEPTR 15
92
 
90
 
93
 
91
 
94
#define EVTCHNOP_SEND           4
92
#define EVTCHNOP_SEND           4
95
 
93
 
96
 
94
 
97
#define UVMF_NONE               0        /**< No flushing at all */
95
#define UVMF_NONE               0        /**< No flushing at all */
98
#define UVMF_TLB_FLUSH          1        /**< Flush entire TLB(s) */
96
#define UVMF_TLB_FLUSH          1        /**< Flush entire TLB(s) */
99
#define UVMF_INVLPG             2        /**< Flush only one entry */
97
#define UVMF_INVLPG             2        /**< Flush only one entry */
100
#define UVMF_FLUSHTYPE_MASK     3
98
#define UVMF_FLUSHTYPE_MASK     3
101
#define UVMF_MULTI              0        /**< Flush subset of TLBs */
99
#define UVMF_MULTI              0        /**< Flush subset of TLBs */
102
#define UVMF_LOCAL              0        /**< Flush local TLB */
100
#define UVMF_LOCAL              0        /**< Flush local TLB */
103
#define UVMF_ALL                (1 << 2) /**< Flush all TLBs */
101
#define UVMF_ALL                (1 << 2) /**< Flush all TLBs */
104
 
102
 
105
 
103
 
106
/*
104
/*
107
 * Commands to XEN_VM_ASSIST
105
 * Commands to XEN_VM_ASSIST
108
 */
106
 */
109
#define VMASST_CMD_ENABLE               0
107
#define VMASST_CMD_ENABLE               0
110
#define VMASST_CMD_DISABLE              1
108
#define VMASST_CMD_DISABLE              1
111
#define VMASST_TYPE_4GB_SEGMENTS        0
109
#define VMASST_TYPE_4GB_SEGMENTS        0
112
#define VMASST_TYPE_4GB_SEGMENTS_NOTIFY 1
110
#define VMASST_TYPE_4GB_SEGMENTS_NOTIFY 1
113
#define VMASST_TYPE_WRITABLE_PAGETABLES 2
111
#define VMASST_TYPE_WRITABLE_PAGETABLES 2
114
 
112
 
115
 
113
 
116
#define DOMID_SELF (0x7FF0U)
114
#define DOMID_SELF (0x7FF0U)
117
#define DOMID_IO   (0x7FF1U)
115
#define DOMID_IO   (0x7FF1U)
118
 
116
 
119
 
117
 
120
#define force_evtchn_callback() ((void) xen_version(0, 0))
118
#define force_evtchn_callback() ((void) xen_version(0, 0))
121
 
119
 
122
#define hypercall0(id)  \
120
#define hypercall0(id)  \
123
    ({  \
121
    ({  \
124
        unative_t ret;  \
122
        unative_t ret;  \
125
        asm volatile (  \
123
        asm volatile (  \
126
            "call hypercall_page + (" STRING(id) " * 32)\n" \
124
            "call hypercall_page + (" STRING(id) " * 32)\n" \
127
            : "=a" (ret)    \
125
            : "=a" (ret)    \
128
            :   \
126
            :   \
129
            : "memory"  \
127
            : "memory"  \
130
        );  \
128
        );  \
131
        ret;    \
129
        ret;    \
132
    })
130
    })
133
 
131
 
134
#define hypercall1(id, p1)  \
132
#define hypercall1(id, p1)  \
135
    ({  \
133
    ({  \
136
        unative_t ret, __ign1;  \
134
        unative_t ret, __ign1;  \
137
        asm volatile (  \
135
        asm volatile (  \
138
            "call hypercall_page + (" STRING(id) " * 32)\n" \
136
            "call hypercall_page + (" STRING(id) " * 32)\n" \
139
            : "=a" (ret), \
137
            : "=a" (ret), \
140
              "=b" (__ign1) \
138
              "=b" (__ign1) \
141
            : "1" (p1)  \
139
            : "1" (p1)  \
142
            : "memory"  \
140
            : "memory"  \
143
        );  \
141
        );  \
144
        ret;    \
142
        ret;    \
145
    })
143
    })
146
 
144
 
147
#define hypercall2(id, p1, p2)  \
145
#define hypercall2(id, p1, p2)  \
148
    ({  \
146
    ({  \
149
        unative_t ret, __ign1, __ign2;  \
147
        unative_t ret, __ign1, __ign2;  \
150
        asm volatile (  \
148
        asm volatile (  \
151
            "call hypercall_page + (" STRING(id) " * 32)\n" \
149
            "call hypercall_page + (" STRING(id) " * 32)\n" \
152
            : "=a" (ret), \
150
            : "=a" (ret), \
153
              "=b" (__ign1),    \
151
              "=b" (__ign1),    \
154
              "=c" (__ign2) \
152
              "=c" (__ign2) \
155
            : "1" (p1), \
153
            : "1" (p1), \
156
              "2" (p2)  \
154
              "2" (p2)  \
157
            : "memory"  \
155
            : "memory"  \
158
        );  \
156
        );  \
159
        ret;    \
157
        ret;    \
160
    })
158
    })
161
 
159
 
162
#define hypercall3(id, p1, p2, p3)  \
160
#define hypercall3(id, p1, p2, p3)  \
163
    ({  \
161
    ({  \
164
        unative_t ret, __ign1, __ign2, __ign3;  \
162
        unative_t ret, __ign1, __ign2, __ign3;  \
165
        asm volatile (  \
163
        asm volatile (  \
166
            "call hypercall_page + (" STRING(id) " * 32)\n" \
164
            "call hypercall_page + (" STRING(id) " * 32)\n" \
167
            : "=a" (ret), \
165
            : "=a" (ret), \
168
              "=b" (__ign1),    \
166
              "=b" (__ign1),    \
169
              "=c" (__ign2),    \
167
              "=c" (__ign2),    \
170
              "=d" (__ign3) \
168
              "=d" (__ign3) \
171
            : "1" (p1), \
169
            : "1" (p1), \
172
              "2" (p2), \
170
              "2" (p2), \
173
              "3" (p3)  \
171
              "3" (p3)  \
174
            : "memory"  \
172
            : "memory"  \
175
        );  \
173
        );  \
176
        ret;    \
174
        ret;    \
177
    })
175
    })
178
 
176
 
179
#define hypercall4(id, p1, p2, p3, p4)  \
177
#define hypercall4(id, p1, p2, p3, p4)  \
180
    ({  \
178
    ({  \
181
        unative_t ret, __ign1, __ign2, __ign3, __ign4;  \
179
        unative_t ret, __ign1, __ign2, __ign3, __ign4;  \
182
        asm volatile (  \
180
        asm volatile (  \
183
            "call hypercall_page + (" STRING(id) " * 32)\n" \
181
            "call hypercall_page + (" STRING(id) " * 32)\n" \
184
            : "=a" (ret), \
182
            : "=a" (ret), \
185
              "=b" (__ign1),    \
183
              "=b" (__ign1),    \
186
              "=c" (__ign2),    \
184
              "=c" (__ign2),    \
187
              "=d" (__ign3),    \
185
              "=d" (__ign3),    \
188
              "=S" (__ign4) \
186
              "=S" (__ign4) \
189
            : "1" (p1), \
187
            : "1" (p1), \
190
              "2" (p2), \
188
              "2" (p2), \
191
              "3" (p3), \
189
              "3" (p3), \
192
              "4" (p4)  \
190
              "4" (p4)  \
193
            : "memory"  \
191
            : "memory"  \
194
        );  \
192
        );  \
195
        ret;    \
193
        ret;    \
196
    })
194
    })
197
 
195
 
198
#define hypercall5(id, p1, p2, p3, p4, p5)  \
196
#define hypercall5(id, p1, p2, p3, p4, p5)  \
199
    ({  \
197
    ({  \
200
        unative_t ret, __ign1, __ign2, __ign3, __ign4, __ign5;  \
198
        unative_t ret, __ign1, __ign2, __ign3, __ign4, __ign5;  \
201
        asm volatile (  \
199
        asm volatile (  \
202
            "call hypercall_page + (" STRING(id) " * 32)\n" \
200
            "call hypercall_page + (" STRING(id) " * 32)\n" \
203
            : "=a" (ret), \
201
            : "=a" (ret), \
204
              "=b" (__ign1),    \
202
              "=b" (__ign1),    \
205
              "=c" (__ign2),    \
203
              "=c" (__ign2),    \
206
              "=d" (__ign3),    \
204
              "=d" (__ign3),    \
207
              "=S" (__ign4),    \
205
              "=S" (__ign4),    \
208
              "=D" (__ign5) \
206
              "=D" (__ign5) \
209
            : "1" (p1), \
207
            : "1" (p1), \
210
              "2" (p2), \
208
              "2" (p2), \
211
              "3" (p3), \
209
              "3" (p3), \
212
              "4" (p4), \
210
              "4" (p4), \
213
              "5" (p5)  \
211
              "5" (p5)  \
214
            : "memory"  \
212
            : "memory"  \
215
        );  \
213
        );  \
216
        ret;    \
214
        ret;    \
217
    })
215
    })
218
 
216
 
219
 
217
 
220
static inline int xen_console_io(const unsigned int cmd, const unsigned int count, const char *str)
218
static inline int xen_console_io(const unsigned int cmd, const unsigned int count, const char *str)
221
{
219
{
222
    return hypercall3(XEN_CONSOLE_IO, cmd, count, str);
220
    return hypercall3(XEN_CONSOLE_IO, cmd, count, str);
223
}
221
}
224
 
222
 
225
static inline int xen_vm_assist(const unsigned int cmd, const unsigned int type)
223
static inline int xen_vm_assist(const unsigned int cmd, const unsigned int type)
226
{
224
{
227
    return hypercall2(XEN_VM_ASSIST, cmd, type);
225
    return hypercall2(XEN_VM_ASSIST, cmd, type);
228
}
226
}
229
 
227
 
230
static inline int xen_set_callbacks(const unsigned int event_selector, const void *event_address, const unsigned int failsafe_selector, void *failsafe_address)
228
static inline int xen_set_callbacks(const unsigned int event_selector, const void *event_address, const unsigned int failsafe_selector, void *failsafe_address)
231
{
229
{
232
    return hypercall4(XEN_SET_CALLBACKS, event_selector, event_address, failsafe_selector, failsafe_address);
230
    return hypercall4(XEN_SET_CALLBACKS, event_selector, event_address, failsafe_selector, failsafe_address);
233
}
231
}
234
 
232
 
235
static inline int xen_set_trap_table(const trap_info_t *table)
233
static inline int xen_set_trap_table(const trap_info_t *table)
236
{
234
{
237
    return hypercall1(XEN_SET_TRAP_TABLE, table);
235
    return hypercall1(XEN_SET_TRAP_TABLE, table);
238
}
236
}
239
 
237
 
240
static inline int xen_version(const unsigned int cmd, const void *arg)
238
static inline int xen_version(const unsigned int cmd, const void *arg)
241
{
239
{
242
    return hypercall2(XEN_VERSION, cmd, arg);
240
    return hypercall2(XEN_VERSION, cmd, arg);
243
}
241
}
244
 
242
 
245
static inline int xen_notify_remote(evtchn_t channel)
243
static inline int xen_notify_remote(evtchn_t channel)
246
{
244
{
247
    evtchn_op_t op;
245
    evtchn_op_t op;
248
   
246
   
249
    op.cmd = EVTCHNOP_SEND;
247
    op.cmd = EVTCHNOP_SEND;
250
    op.send.port = channel;
248
    op.send.port = channel;
251
    return hypercall1(XEN_EVENT_CHANNEL_OP, &op);
249
    return hypercall1(XEN_EVENT_CHANNEL_OP, &op);
252
}
250
}
253
 
251
 
254
#endif
252
#endif
255
 
253