Subversion Repositories Kolibri OS

Rev

Rev 6296 | Go to most recent revision | Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
6283 serge 1
#include 
2
#include "i915_drv.h"
3
#include "intel_drv.h"
4
#include 
5
#include 
6
 
7
static struct mutex cursor_lock;
8
 
9
static void __stdcall move_cursor_kms(cursor_t *cursor, int x, int y)
10
{
11
    struct drm_crtc *crtc = os_display->crtc;
12
    struct drm_plane_state *cursor_state = crtc->cursor->state;
13
 
14
    x-= cursor->hot_x;
15
    y-= cursor->hot_y;
16
 
17
    crtc->cursor_x = x;
18
    crtc->cursor_y = y;
19
 
20
    cursor_state->crtc_x = x;
21
    cursor_state->crtc_y = y;
22
 
23
    intel_crtc_update_cursor(crtc, 1);
24
};
25
 
26
static cursor_t* __stdcall select_cursor_kms(cursor_t *cursor)
27
{
28
    struct drm_i915_private *dev_priv = os_display->ddev->dev_private;
29
    struct drm_crtc   *crtc = os_display->crtc;
30
    struct intel_crtc *intel_crtc = to_intel_crtc(crtc);
31
 
32
    cursor_t *old;
33
 
34
    old = os_display->cursor;
35
 
36
    mutex_lock(&cursor_lock);
37
 
38
    os_display->cursor = cursor;
39
 
40
    if (!dev_priv->info.cursor_needs_physical)
41
       intel_crtc->cursor_addr = i915_gem_obj_ggtt_offset(cursor->cobj);
42
    else
43
        intel_crtc->cursor_addr = (addr_t)cursor->cobj;
44
 
45
    intel_crtc->base.cursor->state->crtc_w = 64;
46
    intel_crtc->base.cursor->state->crtc_h = 64;
47
    intel_crtc->base.cursor->state->rotation = 0;
48
    mutex_unlock(&cursor_lock);
49
 
50
    move_cursor_kms(cursor, crtc->cursor_x, crtc->cursor_y);
51
    return old;
52
};
53
 
54
static void __stdcall restore_cursor(int x, int y){};
55
static void disable_mouse(void){};
56
 
57
static void __attribute__((regparm(1))) destroy_cursor(cursor_t *cursor)
58
{
59
    struct drm_i915_gem_object *obj = cursor->cobj;
60
    list_del(&cursor->list);
61
 
62
    i915_gem_object_ggtt_unpin(cursor->cobj);
63
 
64
    mutex_lock(&main_device->struct_mutex);
65
    drm_gem_object_unreference(&obj->base);
66
    mutex_unlock(&main_device->struct_mutex);
67
 
68
    __DestroyObject(cursor);
69
};
70
 
71
static int init_cursor(cursor_t *cursor)
72
{
73
    display_t *display = GetDisplay();
74
    struct drm_i915_private *dev_priv = display->ddev->dev_private;
75
    struct drm_i915_gem_object *obj;
76
    uint32_t *bits;
77
    uint32_t *src;
78
    void     *mapped;
79
 
80
    int       i,j;
81
    int       ret;
82
 
83
    if (dev_priv->info.cursor_needs_physical)
84
    {
85
        bits = (uint32_t*)KernelAlloc(KMS_CURSOR_WIDTH*KMS_CURSOR_HEIGHT*8);
86
        if (unlikely(bits == NULL))
87
            return ENOMEM;
88
        cursor->cobj = (struct drm_i915_gem_object *)GetPgAddr(bits);
89
    }
90
    else
91
    {
92
        obj = i915_gem_alloc_object(display->ddev, KMS_CURSOR_WIDTH*KMS_CURSOR_HEIGHT*4);
93
        if (unlikely(obj == NULL))
94
            return -ENOMEM;
95
 
96
        ret = i915_gem_object_ggtt_pin(obj, &i915_ggtt_view_normal, 128*1024, PIN_GLOBAL);
97
        if (ret) {
98
            drm_gem_object_unreference(&obj->base);
99
            return ret;
100
        }
101
 
102
        ret = i915_gem_object_set_to_gtt_domain(obj, true);
103
        if (ret)
104
        {
105
            i915_gem_object_ggtt_unpin(obj);
106
            drm_gem_object_unreference(&obj->base);
107
            return ret;
108
        }
109
/* You don't need to worry about fragmentation issues.
110
 * GTT space is continuous. I guarantee it.                           */
111
 
112
        mapped = bits = (u32*)MapIoMem(dev_priv->gtt.mappable_base + i915_gem_obj_ggtt_offset(obj),
113
                    KMS_CURSOR_WIDTH*KMS_CURSOR_HEIGHT*4, PG_SW);
114
 
115
        if (unlikely(bits == NULL))
116
        {
117
            i915_gem_object_ggtt_unpin(obj);
118
            drm_gem_object_unreference(&obj->base);
119
            return -ENOMEM;
120
        };
121
        cursor->cobj = obj;
122
    };
123
 
124
    src = cursor->data;
125
 
126
    for(i = 0; i < 32; i++)
127
    {
128
        for(j = 0; j < 32; j++)
129
            *bits++ = *src++;
130
        for(j = 32; j < KMS_CURSOR_WIDTH; j++)
131
            *bits++ = 0;
132
    }
133
    for(i = 0; i < KMS_CURSOR_WIDTH*(KMS_CURSOR_HEIGHT-32); i++)
134
        *bits++ = 0;
135
 
136
    FreeKernelSpace(mapped);
137
    KernelFree(cursor->data);
138
    cursor->data = bits;
139
    cursor->header.destroy = destroy_cursor;
140
 
141
    return 0;
142
}
143
 
144
void init_system_cursors(struct drm_device *dev)
145
{
146
    cursor_t  *cursor;
147
    display_t *display;
148
    u32      ifl;
149
 
150
    display = GetDisplay();
151
 
152
    mutex_init(&cursor_lock);
153
    mutex_lock(&dev->struct_mutex);
154
 
155
    ifl = safe_cli();
156
    {
157
        list_for_each_entry(cursor, &display->cursors, list)
158
        {
159
            init_cursor(cursor);
160
        };
161
 
162
        display->restore_cursor(0,0);
163
        display->init_cursor    = init_cursor;
164
        display->select_cursor  = select_cursor_kms;
165
        display->show_cursor    = NULL;
166
        display->move_cursor    = move_cursor_kms;
167
        display->restore_cursor = restore_cursor;
168
        display->disable_mouse  = disable_mouse;
169
        display->crtc->cursor_x = display->width/2;
170
        display->crtc->cursor_y = display->height/2;
171
 
172
        select_cursor_kms(display->cursor);
173
    };
174
    safe_sti(ifl);
175
 
176
    mutex_unlock(&dev->struct_mutex);
177
}