i915_dma.c 25.6 KB
Newer Older
Linus Torvalds's avatar
Linus Torvalds committed
1
2
/* i915_dma.c -- DMA support for the I915 -*- linux-c -*-
 */
Dave Airlie's avatar
Dave Airlie committed
3
/*
Linus Torvalds's avatar
Linus Torvalds committed
4
5
 * Copyright 2003 Tungsten Graphics, Inc., Cedar Park, Texas.
 * All Rights Reserved.
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
 *
 * Permission is hereby granted, free of charge, to any person obtaining a
 * copy of this software and associated documentation files (the
 * "Software"), to deal in the Software without restriction, including
 * without limitation the rights to use, copy, modify, merge, publish,
 * distribute, sub license, and/or sell copies of the Software, and to
 * permit persons to whom the Software is furnished to do so, subject to
 * the following conditions:
 *
 * The above copyright notice and this permission notice (including the
 * next paragraph) shall be included in all copies or substantial portions
 * of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
 * IN NO EVENT SHALL TUNGSTEN GRAPHICS AND/OR ITS SUPPLIERS BE LIABLE FOR
 * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
 * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
 * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 *
Dave Airlie's avatar
Dave Airlie committed
27
 */
Linus Torvalds's avatar
Linus Torvalds committed
28
29
30
31
32
33
34
35
36
37
38

#include "drmP.h"
#include "drm.h"
#include "i915_drm.h"
#include "i915_drv.h"

/* Really want an OS-independent resettable timer.  Would like to have
 * this loop run for (eg) 3 sec, but have the timer reset every time
 * the head pointer changes, so that EBUSY only happens if the ring
 * actually stalls for (eg) 3 seconds.
 */
39
int i915_wait_ring(struct drm_device * dev, int n, const char *caller)
Linus Torvalds's avatar
Linus Torvalds committed
40
41
42
{
	drm_i915_private_t *dev_priv = dev->dev_private;
	drm_i915_ring_buffer_t *ring = &(dev_priv->ring);
43
44
45
	u32 acthd_reg = IS_I965G(dev) ? ACTHD_I965 : ACTHD;
	u32 last_acthd = I915_READ(acthd_reg);
	u32 acthd;
46
	u32 last_head = I915_READ(PRB0_HEAD) & HEAD_ADDR;
Linus Torvalds's avatar
Linus Torvalds committed
47
48
	int i;

49
	for (i = 0; i < 100000; i++) {
50
		ring->head = I915_READ(PRB0_HEAD) & HEAD_ADDR;
51
		acthd = I915_READ(acthd_reg);
Linus Torvalds's avatar
Linus Torvalds committed
52
53
54
55
56
57
		ring->space = ring->head - (ring->tail + 8);
		if (ring->space < 0)
			ring->space += ring->Size;
		if (ring->space >= n)
			return 0;

58
59
		if (dev_priv->sarea_priv)
			dev_priv->sarea_priv->perf_boxes |= I915_BOX_WAIT;
Linus Torvalds's avatar
Linus Torvalds committed
60
61
62

		if (ring->head != last_head)
			i = 0;
63
64
		if (acthd != last_acthd)
			i = 0;
Linus Torvalds's avatar
Linus Torvalds committed
65
66

		last_head = ring->head;
67
68
69
		last_acthd = acthd;
		msleep_interruptible(10);

Linus Torvalds's avatar
Linus Torvalds committed
70
71
	}

Eric Anholt's avatar
Eric Anholt committed
72
	return -EBUSY;
Linus Torvalds's avatar
Linus Torvalds committed
73
74
}

75
76
77
78
/**
 * Sets up the hardware status page for devices that need a physical address
 * in the register.
 */
79
static int i915_init_phys_hws(struct drm_device *dev)
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
{
	drm_i915_private_t *dev_priv = dev->dev_private;
	/* Program Hardware Status Page */
	dev_priv->status_page_dmah =
		drm_pci_alloc(dev, PAGE_SIZE, PAGE_SIZE, 0xffffffff);

	if (!dev_priv->status_page_dmah) {
		DRM_ERROR("Can not allocate hardware status page\n");
		return -ENOMEM;
	}
	dev_priv->hw_status_page = dev_priv->status_page_dmah->vaddr;
	dev_priv->dma_status_page = dev_priv->status_page_dmah->busaddr;

	memset(dev_priv->hw_status_page, 0, PAGE_SIZE);

	I915_WRITE(HWS_PGA, dev_priv->dma_status_page);
	DRM_DEBUG("Enabled hardware status page\n");
	return 0;
}

/**
 * Frees the hardware status page, whether it's a physical address or a virtual
 * address set up by the X Server.
 */
104
static void i915_free_hws(struct drm_device *dev)
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
{
	drm_i915_private_t *dev_priv = dev->dev_private;
	if (dev_priv->status_page_dmah) {
		drm_pci_free(dev, dev_priv->status_page_dmah);
		dev_priv->status_page_dmah = NULL;
	}

	if (dev_priv->status_gfx_addr) {
		dev_priv->status_gfx_addr = 0;
		drm_core_ioremapfree(&dev_priv->hws_map, dev);
	}

	/* Need to rewrite hardware status page */
	I915_WRITE(HWS_PGA, 0x1ffff000);
}

121
void i915_kernel_lost_context(struct drm_device * dev)
Linus Torvalds's avatar
Linus Torvalds committed
122
123
124
125
{
	drm_i915_private_t *dev_priv = dev->dev_private;
	drm_i915_ring_buffer_t *ring = &(dev_priv->ring);

126
127
	ring->head = I915_READ(PRB0_HEAD) & HEAD_ADDR;
	ring->tail = I915_READ(PRB0_TAIL) & TAIL_ADDR;
Linus Torvalds's avatar
Linus Torvalds committed
128
129
130
131
	ring->space = ring->head - (ring->tail + 8);
	if (ring->space < 0)
		ring->space += ring->Size;

132
	if (ring->head == ring->tail && dev_priv->sarea_priv)
Linus Torvalds's avatar
Linus Torvalds committed
133
134
135
		dev_priv->sarea_priv->perf_boxes |= I915_BOX_RING_EMPTY;
}

136
static int i915_dma_cleanup(struct drm_device * dev)
Linus Torvalds's avatar
Linus Torvalds committed
137
{
138
	drm_i915_private_t *dev_priv = dev->dev_private;
Linus Torvalds's avatar
Linus Torvalds committed
139
140
141
142
	/* Make sure interrupts are disabled here because the uninstall ioctl
	 * may not have been called from userspace and after dev_private
	 * is freed, it's too late.
	 */
143
	if (dev->irq_enabled)
Dave Airlie's avatar
Dave Airlie committed
144
		drm_irq_uninstall(dev);
Linus Torvalds's avatar
Linus Torvalds committed
145

146
147
	if (dev_priv->ring.virtual_start) {
		drm_core_ioremapfree(&dev_priv->ring.map, dev);
148
149
		dev_priv->ring.virtual_start = NULL;
		dev_priv->ring.map.handle = NULL;
150
151
		dev_priv->ring.map.size = 0;
	}
152

153
154
155
	/* Clear the HWS virtual address at teardown */
	if (I915_NEED_GFX_HWS(dev))
		i915_free_hws(dev);
Linus Torvalds's avatar
Linus Torvalds committed
156

157
158
159
	dev_priv->sarea = NULL;
	dev_priv->sarea_priv = NULL;

Linus Torvalds's avatar
Linus Torvalds committed
160
161
162
	return 0;
}

163
static int i915_initialize(struct drm_device * dev, drm_i915_init_t * init)
Linus Torvalds's avatar
Linus Torvalds committed
164
{
165
	drm_i915_private_t *dev_priv = dev->dev_private;
Linus Torvalds's avatar
Linus Torvalds committed
166

167
	dev_priv->sarea = drm_getsarea(dev);
Linus Torvalds's avatar
Linus Torvalds committed
168
169
170
	if (!dev_priv->sarea) {
		DRM_ERROR("can not find sarea!\n");
		i915_dma_cleanup(dev);
Eric Anholt's avatar
Eric Anholt committed
171
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
172
173
174
175
176
	}

	dev_priv->sarea_priv = (drm_i915_sarea_t *)
	    ((u8 *) dev_priv->sarea->handle + init->sarea_priv_offset);

177
178
179
180
181
182
183
	if (init->ring_size != 0) {
		if (dev_priv->ring.ring_obj != NULL) {
			i915_dma_cleanup(dev);
			DRM_ERROR("Client tried to initialize ringbuffer in "
				  "GEM mode\n");
			return -EINVAL;
		}
Linus Torvalds's avatar
Linus Torvalds committed
184

185
186
		dev_priv->ring.Size = init->ring_size;
		dev_priv->ring.tail_mask = dev_priv->ring.Size - 1;
Linus Torvalds's avatar
Linus Torvalds committed
187

188
189
190
191
192
		dev_priv->ring.map.offset = init->ring_start;
		dev_priv->ring.map.size = init->ring_size;
		dev_priv->ring.map.type = 0;
		dev_priv->ring.map.flags = 0;
		dev_priv->ring.map.mtrr = 0;
Linus Torvalds's avatar
Linus Torvalds committed
193

194
195
196
197
198
199
200
201
		drm_core_ioremap(&dev_priv->ring.map, dev);

		if (dev_priv->ring.map.handle == NULL) {
			i915_dma_cleanup(dev);
			DRM_ERROR("can not ioremap virtual address for"
				  " ring buffer\n");
			return -ENOMEM;
		}
Linus Torvalds's avatar
Linus Torvalds committed
202
203
204
205
	}

	dev_priv->ring.virtual_start = dev_priv->ring.map.handle;

206
	dev_priv->cpp = init->cpp;
Linus Torvalds's avatar
Linus Torvalds committed
207
208
209
210
211
212
213
214
215
216
217
218
	dev_priv->back_offset = init->back_offset;
	dev_priv->front_offset = init->front_offset;
	dev_priv->current_page = 0;
	dev_priv->sarea_priv->pf_current_page = dev_priv->current_page;

	/* Allow hardware batchbuffers unless told otherwise.
	 */
	dev_priv->allow_batchbuffer = 1;

	return 0;
}

219
static int i915_dma_resume(struct drm_device * dev)
Linus Torvalds's avatar
Linus Torvalds committed
220
221
222
{
	drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private;

223
	DRM_DEBUG("%s\n", __func__);
Linus Torvalds's avatar
Linus Torvalds committed
224
225
226

	if (!dev_priv->sarea) {
		DRM_ERROR("can not find sarea!\n");
Eric Anholt's avatar
Eric Anholt committed
227
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
228
229
230
231
232
	}

	if (dev_priv->ring.map.handle == NULL) {
		DRM_ERROR("can not ioremap virtual address for"
			  " ring buffer\n");
Eric Anholt's avatar
Eric Anholt committed
233
		return -ENOMEM;
Linus Torvalds's avatar
Linus Torvalds committed
234
235
236
237
238
	}

	/* Program Hardware Status Page */
	if (!dev_priv->hw_status_page) {
		DRM_ERROR("Can not find hardware status page\n");
Eric Anholt's avatar
Eric Anholt committed
239
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
240
241
242
	}
	DRM_DEBUG("hw status page @ %p\n", dev_priv->hw_status_page);

243
	if (dev_priv->status_gfx_addr != 0)
244
		I915_WRITE(HWS_PGA, dev_priv->status_gfx_addr);
245
	else
246
		I915_WRITE(HWS_PGA, dev_priv->dma_status_page);
Linus Torvalds's avatar
Linus Torvalds committed
247
248
249
250
251
	DRM_DEBUG("Enabled hardware status page\n");

	return 0;
}

252
253
static int i915_dma_init(struct drm_device *dev, void *data,
			 struct drm_file *file_priv)
Linus Torvalds's avatar
Linus Torvalds committed
254
{
255
	drm_i915_init_t *init = data;
Linus Torvalds's avatar
Linus Torvalds committed
256
257
	int retcode = 0;

258
	switch (init->func) {
Linus Torvalds's avatar
Linus Torvalds committed
259
	case I915_INIT_DMA:
260
		retcode = i915_initialize(dev, init);
Linus Torvalds's avatar
Linus Torvalds committed
261
262
263
264
265
		break;
	case I915_CLEANUP_DMA:
		retcode = i915_dma_cleanup(dev);
		break;
	case I915_RESUME_DMA:
Dave Airlie's avatar
Dave Airlie committed
266
		retcode = i915_dma_resume(dev);
Linus Torvalds's avatar
Linus Torvalds committed
267
268
		break;
	default:
Eric Anholt's avatar
Eric Anholt committed
269
		retcode = -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
		break;
	}

	return retcode;
}

/* Implement basically the same security restrictions as hardware does
 * for MI_BATCH_NON_SECURE.  These can be made stricter at any time.
 *
 * Most of the calculations below involve calculating the size of a
 * particular instruction.  It's important to get the size right as
 * that tells us where the next instruction to check is.  Any illegal
 * instruction detected will be given a size of zero, which is a
 * signal to abort the rest of the buffer.
 */
static int do_validate_cmd(int cmd)
{
	switch (((cmd >> 29) & 0x7)) {
	case 0x0:
		switch ((cmd >> 23) & 0x3f) {
		case 0x0:
			return 1;	/* MI_NOOP */
		case 0x4:
			return 1;	/* MI_FLUSH */
		default:
			return 0;	/* disallow everything else */
		}
		break;
	case 0x1:
		return 0;	/* reserved */
	case 0x2:
		return (cmd & 0xff) + 2;	/* 2d commands */
	case 0x3:
		if (((cmd >> 24) & 0x1f) <= 0x18)
			return 1;

		switch ((cmd >> 24) & 0x1f) {
		case 0x1c:
			return 1;
		case 0x1d:
Dave Airlie's avatar
Dave Airlie committed
310
			switch ((cmd >> 16) & 0xff) {
Linus Torvalds's avatar
Linus Torvalds committed
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
			case 0x3:
				return (cmd & 0x1f) + 2;
			case 0x4:
				return (cmd & 0xf) + 2;
			default:
				return (cmd & 0xffff) + 2;
			}
		case 0x1e:
			if (cmd & (1 << 23))
				return (cmd & 0xffff) + 1;
			else
				return 1;
		case 0x1f:
			if ((cmd & (1 << 23)) == 0)	/* inline vertices */
				return (cmd & 0x1ffff) + 2;
			else if (cmd & (1 << 17))	/* indirect random */
				if ((cmd & 0xffff) == 0)
					return 0;	/* unknown length, too hard */
				else
					return (((cmd & 0xffff) + 1) / 2) + 1;
			else
				return 2;	/* indirect sequential */
		default:
			return 0;
		}
	default:
		return 0;
	}

	return 0;
}

static int validate_cmd(int cmd)
{
	int ret = do_validate_cmd(cmd);

347
/*	printk("validate_cmd( %x ): %d\n", cmd, ret); */
Linus Torvalds's avatar
Linus Torvalds committed
348
349
350
351

	return ret;
}

352
static int i915_emit_cmds(struct drm_device * dev, int __user * buffer, int dwords)
Linus Torvalds's avatar
Linus Torvalds committed
353
354
355
356
357
{
	drm_i915_private_t *dev_priv = dev->dev_private;
	int i;
	RING_LOCALS;

358
	if ((dwords+1) * sizeof(int) >= dev_priv->ring.Size - 8)
Eric Anholt's avatar
Eric Anholt committed
359
		return -EINVAL;
360

361
	BEGIN_LP_RING((dwords+1)&~1);
362

Linus Torvalds's avatar
Linus Torvalds committed
363
364
365
366
	for (i = 0; i < dwords;) {
		int cmd, sz;

		if (DRM_COPY_FROM_USER_UNCHECKED(&cmd, &buffer[i], sizeof(cmd)))
Eric Anholt's avatar
Eric Anholt committed
367
			return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
368
369

		if ((sz = validate_cmd(cmd)) == 0 || i + sz > dwords)
Eric Anholt's avatar
Eric Anholt committed
370
			return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
371
372
373
374
375
376

		OUT_RING(cmd);

		while (++i, --sz) {
			if (DRM_COPY_FROM_USER_UNCHECKED(&cmd, &buffer[i],
							 sizeof(cmd))) {
Eric Anholt's avatar
Eric Anholt committed
377
				return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
378
379
380
381
382
			}
			OUT_RING(cmd);
		}
	}

383
384
385
386
387
	if (dwords & 1)
		OUT_RING(0);

	ADVANCE_LP_RING();

Linus Torvalds's avatar
Linus Torvalds committed
388
389
390
	return 0;
}

391
392
393
394
int
i915_emit_box(struct drm_device *dev,
	      struct drm_clip_rect __user *boxes,
	      int i, int DR1, int DR4)
Linus Torvalds's avatar
Linus Torvalds committed
395
396
{
	drm_i915_private_t *dev_priv = dev->dev_private;
397
	struct drm_clip_rect box;
Linus Torvalds's avatar
Linus Torvalds committed
398
399
400
	RING_LOCALS;

	if (DRM_COPY_FROM_USER_UNCHECKED(&box, &boxes[i], sizeof(box))) {
Eric Anholt's avatar
Eric Anholt committed
401
		return -EFAULT;
Linus Torvalds's avatar
Linus Torvalds committed
402
403
404
405
406
	}

	if (box.y2 <= box.y1 || box.x2 <= box.x1 || box.y2 <= 0 || box.x2 <= 0) {
		DRM_ERROR("Bad box %d,%d..%d,%d\n",
			  box.x1, box.y1, box.x2, box.y2);
Eric Anholt's avatar
Eric Anholt committed
407
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
408
409
	}

410
411
412
413
	if (IS_I965G(dev)) {
		BEGIN_LP_RING(4);
		OUT_RING(GFX_OP_DRAWRECT_INFO_I965);
		OUT_RING((box.x1 & 0xffff) | (box.y1 << 16));
Andrew Morton's avatar
Andrew Morton committed
414
		OUT_RING(((box.x2 - 1) & 0xffff) | ((box.y2 - 1) << 16));
415
416
417
418
419
420
421
422
423
424
425
426
		OUT_RING(DR4);
		ADVANCE_LP_RING();
	} else {
		BEGIN_LP_RING(6);
		OUT_RING(GFX_OP_DRAWRECT_INFO);
		OUT_RING(DR1);
		OUT_RING((box.x1 & 0xffff) | (box.y1 << 16));
		OUT_RING(((box.x2 - 1) & 0xffff) | ((box.y2 - 1) << 16));
		OUT_RING(DR4);
		OUT_RING(0);
		ADVANCE_LP_RING();
	}
Linus Torvalds's avatar
Linus Torvalds committed
427
428
429
430

	return 0;
}

431
432
433
434
/* XXX: Emitting the counter should really be moved to part of the IRQ
 * emit. For now, do it in both places:
 */

435
static void i915_emit_breadcrumb(struct drm_device *dev)
436
437
438
439
{
	drm_i915_private_t *dev_priv = dev->dev_private;
	RING_LOCALS;

440
	dev_priv->counter++;
441
	if (dev_priv->counter > 0x7FFFFFFFUL)
442
443
444
		dev_priv->counter = 0;
	if (dev_priv->sarea_priv)
		dev_priv->sarea_priv->last_enqueue = dev_priv->counter;
445
446

	BEGIN_LP_RING(4);
447
	OUT_RING(MI_STORE_DWORD_INDEX);
448
	OUT_RING(I915_BREADCRUMB_INDEX << MI_STORE_DWORD_INDEX_SHIFT);
449
450
451
452
453
	OUT_RING(dev_priv->counter);
	OUT_RING(0);
	ADVANCE_LP_RING();
}

454
static int i915_dispatch_cmdbuffer(struct drm_device * dev,
Linus Torvalds's avatar
Linus Torvalds committed
455
456
457
458
459
460
461
				   drm_i915_cmdbuffer_t * cmd)
{
	int nbox = cmd->num_cliprects;
	int i = 0, count, ret;

	if (cmd->sz & 0x3) {
		DRM_ERROR("alignment");
Eric Anholt's avatar
Eric Anholt committed
462
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
	}

	i915_kernel_lost_context(dev);

	count = nbox ? nbox : 1;

	for (i = 0; i < count; i++) {
		if (i < nbox) {
			ret = i915_emit_box(dev, cmd->cliprects, i,
					    cmd->DR1, cmd->DR4);
			if (ret)
				return ret;
		}

		ret = i915_emit_cmds(dev, (int __user *)cmd->buf, cmd->sz / 4);
		if (ret)
			return ret;
	}

482
	i915_emit_breadcrumb(dev);
Linus Torvalds's avatar
Linus Torvalds committed
483
484
485
	return 0;
}

486
static int i915_dispatch_batchbuffer(struct drm_device * dev,
Linus Torvalds's avatar
Linus Torvalds committed
487
488
489
				     drm_i915_batchbuffer_t * batch)
{
	drm_i915_private_t *dev_priv = dev->dev_private;
490
	struct drm_clip_rect __user *boxes = batch->cliprects;
Linus Torvalds's avatar
Linus Torvalds committed
491
492
493
494
495
496
	int nbox = batch->num_cliprects;
	int i = 0, count;
	RING_LOCALS;

	if ((batch->start | batch->used) & 0x7) {
		DRM_ERROR("alignment");
Eric Anholt's avatar
Eric Anholt committed
497
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
498
499
500
501
502
503
504
505
506
507
508
509
510
511
	}

	i915_kernel_lost_context(dev);

	count = nbox ? nbox : 1;

	for (i = 0; i < count; i++) {
		if (i < nbox) {
			int ret = i915_emit_box(dev, boxes, i,
						batch->DR1, batch->DR4);
			if (ret)
				return ret;
		}

512
		if (!IS_I830(dev) && !IS_845G(dev)) {
Linus Torvalds's avatar
Linus Torvalds committed
513
			BEGIN_LP_RING(2);
514
515
516
517
518
519
520
			if (IS_I965G(dev)) {
				OUT_RING(MI_BATCH_BUFFER_START | (2 << 6) | MI_BATCH_NON_SECURE_I965);
				OUT_RING(batch->start);
			} else {
				OUT_RING(MI_BATCH_BUFFER_START | (2 << 6));
				OUT_RING(batch->start | MI_BATCH_NON_SECURE);
			}
Linus Torvalds's avatar
Linus Torvalds committed
521
522
523
524
525
526
527
528
529
530
531
			ADVANCE_LP_RING();
		} else {
			BEGIN_LP_RING(4);
			OUT_RING(MI_BATCH_BUFFER);
			OUT_RING(batch->start | MI_BATCH_NON_SECURE);
			OUT_RING(batch->start + batch->used - 4);
			OUT_RING(0);
			ADVANCE_LP_RING();
		}
	}

532
	i915_emit_breadcrumb(dev);
Linus Torvalds's avatar
Linus Torvalds committed
533
534
535
536

	return 0;
}

537
static int i915_dispatch_flip(struct drm_device * dev)
Linus Torvalds's avatar
Linus Torvalds committed
538
539
540
541
{
	drm_i915_private_t *dev_priv = dev->dev_private;
	RING_LOCALS;

542
543
544
	if (!dev_priv->sarea_priv)
		return -EINVAL;

545
	DRM_DEBUG("%s: page=%d pfCurrentPage=%d\n",
546
		  __func__,
547
548
		  dev_priv->current_page,
		  dev_priv->sarea_priv->pf_current_page);
Linus Torvalds's avatar
Linus Torvalds committed
549

550
551
552
	i915_kernel_lost_context(dev);

	BEGIN_LP_RING(2);
553
	OUT_RING(MI_FLUSH | MI_READ_FLUSH);
554
555
	OUT_RING(0);
	ADVANCE_LP_RING();
Linus Torvalds's avatar
Linus Torvalds committed
556

557
558
559
560
561
562
	BEGIN_LP_RING(6);
	OUT_RING(CMD_OP_DISPLAYBUFFER_INFO | ASYNC_FLIP);
	OUT_RING(0);
	if (dev_priv->current_page == 0) {
		OUT_RING(dev_priv->back_offset);
		dev_priv->current_page = 1;
Linus Torvalds's avatar
Linus Torvalds committed
563
	} else {
564
565
		OUT_RING(dev_priv->front_offset);
		dev_priv->current_page = 0;
Linus Torvalds's avatar
Linus Torvalds committed
566
	}
567
568
	OUT_RING(0);
	ADVANCE_LP_RING();
Linus Torvalds's avatar
Linus Torvalds committed
569

570
571
572
573
	BEGIN_LP_RING(2);
	OUT_RING(MI_WAIT_FOR_EVENT | MI_WAIT_FOR_PLANE_A_FLIP);
	OUT_RING(0);
	ADVANCE_LP_RING();
Linus Torvalds's avatar
Linus Torvalds committed
574

575
	dev_priv->sarea_priv->last_enqueue = dev_priv->counter++;
Linus Torvalds's avatar
Linus Torvalds committed
576
577

	BEGIN_LP_RING(4);
578
	OUT_RING(MI_STORE_DWORD_INDEX);
579
	OUT_RING(I915_BREADCRUMB_INDEX << MI_STORE_DWORD_INDEX_SHIFT);
580
581
	OUT_RING(dev_priv->counter);
	OUT_RING(0);
Linus Torvalds's avatar
Linus Torvalds committed
582
583
	ADVANCE_LP_RING();

584
585
	dev_priv->sarea_priv->pf_current_page = dev_priv->current_page;
	return 0;
Linus Torvalds's avatar
Linus Torvalds committed
586
587
}

588
static int i915_quiescent(struct drm_device * dev)
Linus Torvalds's avatar
Linus Torvalds committed
589
590
591
592
{
	drm_i915_private_t *dev_priv = dev->dev_private;

	i915_kernel_lost_context(dev);
593
	return i915_wait_ring(dev, dev_priv->ring.Size - 8, __func__);
Linus Torvalds's avatar
Linus Torvalds committed
594
595
}

596
597
static int i915_flush_ioctl(struct drm_device *dev, void *data,
			    struct drm_file *file_priv)
Linus Torvalds's avatar
Linus Torvalds committed
598
{
599
600
601
	int ret;

	RING_LOCK_TEST_WITH_RETURN(dev, file_priv);
Linus Torvalds's avatar
Linus Torvalds committed
602

603
604
605
606
607
	mutex_lock(&dev->struct_mutex);
	ret = i915_quiescent(dev);
	mutex_unlock(&dev->struct_mutex);

	return ret;
Linus Torvalds's avatar
Linus Torvalds committed
608
609
}

610
611
static int i915_batchbuffer(struct drm_device *dev, void *data,
			    struct drm_file *file_priv)
Linus Torvalds's avatar
Linus Torvalds committed
612
613
614
615
{
	drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private;
	drm_i915_sarea_t *sarea_priv = (drm_i915_sarea_t *)
	    dev_priv->sarea_priv;
616
	drm_i915_batchbuffer_t *batch = data;
Linus Torvalds's avatar
Linus Torvalds committed
617
618
619
620
	int ret;

	if (!dev_priv->allow_batchbuffer) {
		DRM_ERROR("Batchbuffer ioctl disabled\n");
Eric Anholt's avatar
Eric Anholt committed
621
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
622
623
624
	}

	DRM_DEBUG("i915 batchbuffer, start %x used %d cliprects %d\n",
625
		  batch->start, batch->used, batch->num_cliprects);
Linus Torvalds's avatar
Linus Torvalds committed
626

627
	RING_LOCK_TEST_WITH_RETURN(dev, file_priv);
Linus Torvalds's avatar
Linus Torvalds committed
628

629
630
	if (batch->num_cliprects && DRM_VERIFYAREA_READ(batch->cliprects,
						       batch->num_cliprects *
631
						       sizeof(struct drm_clip_rect)))
Eric Anholt's avatar
Eric Anholt committed
632
		return -EFAULT;
Linus Torvalds's avatar
Linus Torvalds committed
633

634
	mutex_lock(&dev->struct_mutex);
635
	ret = i915_dispatch_batchbuffer(dev, batch);
636
	mutex_unlock(&dev->struct_mutex);
Linus Torvalds's avatar
Linus Torvalds committed
637

638
	if (sarea_priv)
639
		sarea_priv->last_dispatch = READ_BREADCRUMB(dev_priv);
Linus Torvalds's avatar
Linus Torvalds committed
640
641
642
	return ret;
}

643
644
static int i915_cmdbuffer(struct drm_device *dev, void *data,
			  struct drm_file *file_priv)
Linus Torvalds's avatar
Linus Torvalds committed
645
646
647
648
{
	drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private;
	drm_i915_sarea_t *sarea_priv = (drm_i915_sarea_t *)
	    dev_priv->sarea_priv;
649
	drm_i915_cmdbuffer_t *cmdbuf = data;
Linus Torvalds's avatar
Linus Torvalds committed
650
651
652
	int ret;

	DRM_DEBUG("i915 cmdbuffer, buf %p sz %d cliprects %d\n",
653
		  cmdbuf->buf, cmdbuf->sz, cmdbuf->num_cliprects);
Linus Torvalds's avatar
Linus Torvalds committed
654

655
	RING_LOCK_TEST_WITH_RETURN(dev, file_priv);
Linus Torvalds's avatar
Linus Torvalds committed
656

657
658
659
	if (cmdbuf->num_cliprects &&
	    DRM_VERIFYAREA_READ(cmdbuf->cliprects,
				cmdbuf->num_cliprects *
660
				sizeof(struct drm_clip_rect))) {
Linus Torvalds's avatar
Linus Torvalds committed
661
		DRM_ERROR("Fault accessing cliprects\n");
Eric Anholt's avatar
Eric Anholt committed
662
		return -EFAULT;
Linus Torvalds's avatar
Linus Torvalds committed
663
664
	}

665
	mutex_lock(&dev->struct_mutex);
666
	ret = i915_dispatch_cmdbuffer(dev, cmdbuf);
667
	mutex_unlock(&dev->struct_mutex);
Linus Torvalds's avatar
Linus Torvalds committed
668
669
670
671
672
	if (ret) {
		DRM_ERROR("i915_dispatch_cmdbuffer failed\n");
		return ret;
	}

673
	if (sarea_priv)
674
		sarea_priv->last_dispatch = READ_BREADCRUMB(dev_priv);
Linus Torvalds's avatar
Linus Torvalds committed
675
676
677
	return 0;
}

678
679
static int i915_flip_bufs(struct drm_device *dev, void *data,
			  struct drm_file *file_priv)
Linus Torvalds's avatar
Linus Torvalds committed
680
{
681
682
	int ret;

683
	DRM_DEBUG("%s\n", __func__);
Linus Torvalds's avatar
Linus Torvalds committed
684

685
	RING_LOCK_TEST_WITH_RETURN(dev, file_priv);
Linus Torvalds's avatar
Linus Torvalds committed
686

687
688
689
690
691
	mutex_lock(&dev->struct_mutex);
	ret = i915_dispatch_flip(dev);
	mutex_unlock(&dev->struct_mutex);

	return ret;
Linus Torvalds's avatar
Linus Torvalds committed
692
693
}

694
695
static int i915_getparam(struct drm_device *dev, void *data,
			 struct drm_file *file_priv)
Linus Torvalds's avatar
Linus Torvalds committed
696
697
{
	drm_i915_private_t *dev_priv = dev->dev_private;
698
	drm_i915_getparam_t *param = data;
Linus Torvalds's avatar
Linus Torvalds committed
699
700
701
	int value;

	if (!dev_priv) {
702
		DRM_ERROR("called with no initialization\n");
Eric Anholt's avatar
Eric Anholt committed
703
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
704
705
	}

706
	switch (param->param) {
Linus Torvalds's avatar
Linus Torvalds committed
707
	case I915_PARAM_IRQ_ACTIVE:
708
		value = dev->pdev->irq ? 1 : 0;
Linus Torvalds's avatar
Linus Torvalds committed
709
710
711
712
		break;
	case I915_PARAM_ALLOW_BATCHBUFFER:
		value = dev_priv->allow_batchbuffer ? 1 : 0;
		break;
Dave Airlie's avatar
Dave Airlie committed
713
714
715
	case I915_PARAM_LAST_DISPATCH:
		value = READ_BREADCRUMB(dev_priv);
		break;
716
717
718
	case I915_PARAM_CHIPSET_ID:
		value = dev->pci_device;
		break;
719
	case I915_PARAM_HAS_GEM:
720
		value = dev_priv->has_gem;
721
		break;
Linus Torvalds's avatar
Linus Torvalds committed
722
	default:
723
		DRM_ERROR("Unknown parameter %d\n", param->param);
Eric Anholt's avatar
Eric Anholt committed
724
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
725
726
	}

727
	if (DRM_COPY_TO_USER(param->value, &value, sizeof(int))) {
Linus Torvalds's avatar
Linus Torvalds committed
728
		DRM_ERROR("DRM_COPY_TO_USER failed\n");
Eric Anholt's avatar
Eric Anholt committed
729
		return -EFAULT;
Linus Torvalds's avatar
Linus Torvalds committed
730
731
732
733
734
	}

	return 0;
}

735
736
static int i915_setparam(struct drm_device *dev, void *data,
			 struct drm_file *file_priv)
Linus Torvalds's avatar
Linus Torvalds committed
737
738
{
	drm_i915_private_t *dev_priv = dev->dev_private;
739
	drm_i915_setparam_t *param = data;
Linus Torvalds's avatar
Linus Torvalds committed
740
741

	if (!dev_priv) {
742
		DRM_ERROR("called with no initialization\n");
Eric Anholt's avatar
Eric Anholt committed
743
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
744
745
	}

746
	switch (param->param) {
Linus Torvalds's avatar
Linus Torvalds committed
747
748
749
	case I915_SETPARAM_USE_MI_BATCHBUFFER_START:
		break;
	case I915_SETPARAM_TEX_LRU_LOG_GRANULARITY:
750
		dev_priv->tex_lru_log_granularity = param->value;
Linus Torvalds's avatar
Linus Torvalds committed
751
752
		break;
	case I915_SETPARAM_ALLOW_BATCHBUFFER:
753
		dev_priv->allow_batchbuffer = param->value;
Linus Torvalds's avatar
Linus Torvalds committed
754
755
		break;
	default:
756
		DRM_ERROR("unknown parameter %d\n", param->param);
Eric Anholt's avatar
Eric Anholt committed
757
		return -EINVAL;
Linus Torvalds's avatar
Linus Torvalds committed
758
759
760
761
762
	}

	return 0;
}

763
764
static int i915_set_status_page(struct drm_device *dev, void *data,
				struct drm_file *file_priv)
765
766
{
	drm_i915_private_t *dev_priv = dev->dev_private;
767
	drm_i915_hws_addr_t *hws = data;
768
769
770

	if (!I915_NEED_GFX_HWS(dev))
		return -EINVAL;
771
772

	if (!dev_priv) {
773
		DRM_ERROR("called with no initialization\n");
Eric Anholt's avatar
Eric Anholt committed
774
		return -EINVAL;
775
776
	}

777
778
779
	printk(KERN_DEBUG "set status page addr 0x%08x\n", (u32)hws->addr);

	dev_priv->status_gfx_addr = hws->addr & (0x1ffff<<12);
780

781
	dev_priv->hws_map.offset = dev->agp->base + hws->addr;
782
783
784
785
786
787
788
789
790
791
792
	dev_priv->hws_map.size = 4*1024;
	dev_priv->hws_map.type = 0;
	dev_priv->hws_map.flags = 0;
	dev_priv->hws_map.mtrr = 0;

	drm_core_ioremap(&dev_priv->hws_map, dev);
	if (dev_priv->hws_map.handle == NULL) {
		i915_dma_cleanup(dev);
		dev_priv->status_gfx_addr = 0;
		DRM_ERROR("can not ioremap virtual address for"
				" G33 hw status page\n");
Eric Anholt's avatar
Eric Anholt committed
793
		return -ENOMEM;
794
795
796
797
	}
	dev_priv->hw_status_page = dev_priv->hws_map.handle;

	memset(dev_priv->hw_status_page, 0, PAGE_SIZE);
798
799
	I915_WRITE(HWS_PGA, dev_priv->status_gfx_addr);
	DRM_DEBUG("load hws HWS_PGA with gfx mem 0x%x\n",
800
801
802
803
804
			dev_priv->status_gfx_addr);
	DRM_DEBUG("load hws at %p\n", dev_priv->hw_status_page);
	return 0;
}

805
int i915_driver_load(struct drm_device *dev, unsigned long flags)
806
{
807
808
809
810
	struct drm_i915_private *dev_priv = dev->dev_private;
	unsigned long base, size;
	int ret = 0, mmio_bar = IS_I9XX(dev) ? 0 : 1;

811
812
813
814
815
816
817
	/* i915 has 4 more counters */
	dev->counters += 4;
	dev->types[6] = _DRM_STAT_IRQ;
	dev->types[7] = _DRM_STAT_PRIMARY;
	dev->types[8] = _DRM_STAT_SECONDARY;
	dev->types[9] = _DRM_STAT_DMA;

818
819
820
821
822
823
824
	dev_priv = drm_alloc(sizeof(drm_i915_private_t), DRM_MEM_DRIVER);
	if (dev_priv == NULL)
		return -ENOMEM;

	memset(dev_priv, 0, sizeof(drm_i915_private_t));

	dev->dev_private = (void *)dev_priv;
825
	dev_priv->dev = dev;
826
827
828
829
830

	/* Add register map (needed for suspend/resume) */
	base = drm_get_resource_start(dev, mmio_bar);
	size = drm_get_resource_len(dev, mmio_bar);

831
	dev_priv->regs = ioremap(base, size);
832

833
834
835
836
837
838
839
840
#ifdef CONFIG_HIGHMEM64G
	/* don't enable GEM on PAE - needs agp + set_memory_* interface fixes */
	dev_priv->has_gem = 0;
#else
	/* enable GEM by default */
	dev_priv->has_gem = 1;
#endif

841
842
	i915_gem_load(dev);

843
844
845
846
847
848
	/* Init HWS */
	if (!I915_NEED_GFX_HWS(dev)) {
		ret = i915_init_phys_hws(dev);
		if (ret != 0)
			return ret;
	}
849
850
851
852
853
854
855

	/* On the 945G/GM, the chipset reports the MSI capability on the
	 * integrated graphics even though the support isn't actually there
	 * according to the published specs.  It doesn't appear to function
	 * correctly in testing on 945G.
	 * This may be a side effect of MSI having been made available for PEG
	 * and the registers being closely associated.
856
857
	 *
	 * According to chipset errata, on the 965GM, MSI interrupts may
858
859
	 * be lost or delayed, but we use them anyways to avoid
	 * stuck interrupts on some machines.
860
	 */
861
	if (!IS_I945G(dev) && !IS_I945GM(dev))
862
		pci_enable_msi(dev->pdev);
863

864
865
	intel_opregion_init(dev);

866
867
	spin_lock_init(&dev_priv->user_irq_lock);

868
869
870
871
872
873
874
	ret = drm_vblank_init(dev, I915_NUM_PIPE);

	if (ret) {
		(void) i915_driver_unload(dev);
		return ret;
	}

875
876
877
878
879
880
881
	return ret;
}

int i915_driver_unload(struct drm_device *dev)
{
	struct drm_i915_private *dev_priv = dev->dev_private;

882
883
884
	if (dev->pdev->msi_enabled)
		pci_disable_msi(dev->pdev);

885
886
	i915_free_hws(dev);

887
888
	if (dev_priv->regs != NULL)
		iounmap(dev_priv->regs);
889

890
891
	intel_opregion_free(dev);

892
893
894
	drm_free(dev->dev_private, sizeof(drm_i915_private_t),
		 DRM_MEM_DRIVER);

895
896
897
	return 0;
}

898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
int i915_driver_open(struct drm_device *dev, struct drm_file *file_priv)
{
	struct drm_i915_file_private *i915_file_priv;

	DRM_DEBUG("\n");
	i915_file_priv = (struct drm_i915_file_private *)
	    drm_alloc(sizeof(*i915_file_priv), DRM_MEM_FILES);

	if (!i915_file_priv)
		return -ENOMEM;

	file_priv->driver_priv = i915_file_priv;

	i915_file_priv->mm.last_gem_seqno = 0;
	i915_file_priv->mm.last_gem_throttle_seqno = 0;

	return 0;
}

917
void i915_driver_lastclose(struct drm_device * dev)
Linus Torvalds's avatar
Linus Torvalds committed
918
{
919
920
	drm_i915_private_t *dev_priv = dev->dev_private;

Dave Airlie's avatar
Dave Airlie committed
921
922
923
	if (!dev_priv)
		return;

924
925
	i915_gem_lastclose(dev);

926
	if (dev_priv->agp_heap)
Dave Airlie's avatar
Dave Airlie committed
927
		i915_mem_takedown(&(dev_priv->agp_heap));
928

Dave Airlie's avatar
Dave Airlie committed
929
	i915_dma_cleanup(dev);
Linus Torvalds's avatar
Linus Torvalds committed
930
931
}

932
void i915_driver_preclose(struct drm_device * dev, struct drm_file *file_priv)
Linus Torvalds's avatar
Linus Torvalds committed
933
{
934
935
	drm_i915_private_t *dev_priv = dev->dev_private;
	i915_mem_release(dev, file_priv, dev_priv->agp_heap);
Linus Torvalds's avatar
Linus Torvalds committed
936
937
}

938
939
940
941
942
943
944
void i915_driver_postclose(struct drm_device *dev, struct drm_file *file_priv)
{
	struct drm_i915_file_private *i915_file_priv = file_priv->driver_priv;

	drm_free(i915_file_priv, sizeof(*i915_file_priv), DRM_MEM_FILES);
}

945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
struct drm_ioctl_desc i915_ioctls[] = {
	DRM_IOCTL_DEF(DRM_I915_INIT, i915_dma_init, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
	DRM_IOCTL_DEF(DRM_I915_FLUSH, i915_flush_ioctl, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_FLIP, i915_flip_bufs, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_BATCHBUFFER, i915_batchbuffer, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_IRQ_EMIT, i915_irq_emit, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_IRQ_WAIT, i915_irq_wait, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_GETPARAM, i915_getparam, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_SETPARAM, i915_setparam, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
	DRM_IOCTL_DEF(DRM_I915_ALLOC, i915_mem_alloc, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_FREE, i915_mem_free, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_INIT_HEAP, i915_mem_init_heap, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
	DRM_IOCTL_DEF(DRM_I915_CMDBUFFER, i915_cmdbuffer, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_DESTROY_HEAP,  i915_mem_destroy_heap, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY ),
	DRM_IOCTL_DEF(DRM_I915_SET_VBLANK_PIPE,  i915_vblank_pipe_set, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY ),
	DRM_IOCTL_DEF(DRM_I915_GET_VBLANK_PIPE,  i915_vblank_pipe_get, DRM_AUTH ),
	DRM_IOCTL_DEF(DRM_I915_VBLANK_SWAP, i915_vblank_swap, DRM_AUTH),
962
	DRM_IOCTL_DEF(DRM_I915_HWS_ADDR, i915_set_status_page, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
963
	DRM_IOCTL_DEF(DRM_I915_GEM_INIT, i915_gem_init_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
964
965
966
967
968
	DRM_IOCTL_DEF(DRM_I915_GEM_EXECBUFFER, i915_gem_execbuffer, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_GEM_PIN, i915_gem_pin_ioctl, DRM_AUTH|DRM_ROOT_ONLY),
	DRM_IOCTL_DEF(DRM_I915_GEM_UNPIN, i915_gem_unpin_ioctl, DRM_AUTH|DRM_ROOT_ONLY),
	DRM_IOCTL_DEF(DRM_I915_GEM_BUSY, i915_gem_busy_ioctl, DRM_AUTH),
	DRM_IOCTL_DEF(DRM_I915_GEM_THROTTLE, i915_gem_throttle_ioctl, DRM_AUTH),
969
970
	DRM_IOCTL_DEF(DRM_I915_GEM_ENTERVT, i915_gem_entervt_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
	DRM_IOCTL_DEF(DRM_I915_GEM_LEAVEVT, i915_gem_leavevt_ioctl, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
971
972
973
974
975
976
977
978
	DRM_IOCTL_DEF(DRM_I915_GEM_CREATE, i915_gem_create_ioctl, 0),
	DRM_IOCTL_DEF(DRM_I915_GEM_PREAD, i915_gem_pread_ioctl, 0),
	DRM_IOCTL_DEF(DRM_I915_GEM_PWRITE, i915_gem_pwrite_ioctl, 0),
	DRM_IOCTL_DEF(DRM_I915_GEM_MMAP, i915_gem_mmap_ioctl, 0),
	DRM_IOCTL_DEF(DRM_I915_GEM_SET_DOMAIN, i915_gem_set_domain_ioctl, 0),
	DRM_IOCTL_DEF(DRM_I915_GEM_SW_FINISH, i915_gem_sw_finish_ioctl, 0),
	DRM_IOCTL_DEF(DRM_I915_GEM_SET_TILING, i915_gem_set_tiling, 0),
	DRM_IOCTL_DEF(DRM_I915_GEM_GET_TILING, i915_gem_get_tiling, 0),
979
	DRM_IOCTL_DEF(DRM_I915_GEM_GET_APERTURE, i915_gem_get_aperture_ioctl, 0),
Dave Airlie's avatar
Dave Airlie committed
980
981
982
};

int i915_max_ioctl = DRM_ARRAY_SIZE(i915_ioctls);
983
984
985
986
987
988
989
990
991
992
993
994

/**
 * Determine if the device really is AGP or not.
 *
 * All Intel graphics chipsets are treated as AGP, even if they are really
 * PCI-e.
 *
 * \param dev   The device to be tested.
 *
 * \returns
 * A value of 1 is always retured to indictate every i9x5 is AGP.
 */
995
int i915_driver_device_is_agp(struct drm_device * dev)
996
997
998
{
	return 1;
}