|
|
1.1 root 1: /*
2: * Copyright (c) 1999 Apple Computer, Inc. All rights reserved.
3: *
4: * @APPLE_LICENSE_HEADER_START@
5: *
6: * Portions Copyright (c) 1999 Apple Computer, Inc. All Rights
7: * Reserved. This file contains Original Code and/or Modifications of
8: * Original Code as defined in and that are subject to the Apple Public
9: * Source License Version 1.1 (the "License"). You may not use this file
10: * except in compliance with the License. Please obtain a copy of the
11: * License at http://www.apple.com/publicsource and read it before using
12: * this file.
13: *
14: * The Original Code and all software distributed under the License are
15: * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
16: * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
17: * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
18: * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT. Please see the
19: * License for the specific language governing rights and limitations
20: * under the License.
21: *
22: * @APPLE_LICENSE_HEADER_END@
23: */
24:
25: /* Copyright (c) 1992 NeXT Computer, Inc. All rights reserved.
26: *
27: * ev.c - Machine dependent code needed to support the Event Driver.
28: *
29: * HISTORY
30: * 22 Sep 92 Joe Pasqua
31: * Created.
32: */
33:
34: #import <mach/mach_types.h>
35:
36: #import <mach/kern_return.h>
37: #import <kern/kern_port.h>
38: #import <vm/vm_kern.h>
39: #import <driverkit/return.h>
40:
41: #ifndef NULL
42: #define NULL ((void *)0)
43: #endif
44:
45: /*
46: * NULL terminated list of event source classes that should be attached
47: * to the Event Driver when the Window Server starts up.
48: * The list is machine dependent.
49: */
50: static const char *defaultEventSrc[] =
51: {
52: "EventSrcPCPointer",
53: "EventSrcPCKeyboard",
54: NULL
55: };
56:
57: /*
58: * Return a NULL terminated list of event sources that should be attached
59: * to the Event Driver when the Window Server starts up.
60: */
61: const char **
62: defaultEventSources()
63: {
64: return defaultEventSrc;
65: }
66:
67: /*
68: * Set up the shared memory area between the Window Server and the kernel.
69: *
70: * Obtain page aligned wired kernel memory for 'size' bytes using
71: * kmem_alloc().
72: * Find a similar sized region in the Window Server task VM map using
73: * vm_map_find(). This function will find an appropriately sized region,
74: * create a memory object, and insert it in the VM map.
75: * For each physical page in the kernel's wired memory we got from
76: * kmem_alloc(), enter that page at the appropriate location in the page
77: * map for the Window Server, in the address range we allocated using
78: * vm_map_find().
79: */
80: kern_return_t
81: createEventShmem( port_t task, // in
82: vm_size_t size, // in
83: struct vm_map **owner, // out
84: vm_offset_t *owner_addr, // out
85: vm_offset_t *shmem_addr ) // out
86: {
87: vm_offset_t off;
88: vm_offset_t phys_addr;
89: kern_return_t krtn;
90: vm_map_t task_map;
91: kern_port_t task_port;
92: vm_size_t shmem_size;
93: extern vm_map_t convert_port_to_map(kern_port_t);
94:
95: *owner = VM_MAP_NULL;
96: // Get the task map
97: if ( (task_port = (kern_port_t)IOGetKernPort(task)) == KERN_PORT_NULL )
98: return KERN_INVALID_ARGUMENT;
99: if ( (task_map = convert_port_to_map(task_port)) == VM_MAP_NULL )
100: {
101: port_release(task_port); // Decrement ref cnt
102: return KERN_INVALID_ARGUMENT;
103: }
104: port_release(task_port); // Decrement ref cnt
105:
106: shmem_size = round_page(size); // Round up to page boundry.
107:
108: /* Find some memory of a suitable size in the kernel VM map. */
109: if ( kmem_alloc_wired( kernel_map, shmem_addr, shmem_size ) )
110: {
111: vm_map_deallocate(task_map); // discard our reference
112: return KERN_NO_SPACE;
113: }
114: /* Find some memory of the same size in 'task'. We use vm_map_find()
115: to do this. vm_map_find inserts the found memory object in the
116: target task's map as a side effect. */
117: *owner_addr = vm_map_min(task_map);
118: krtn = vm_map_find( task_map,
119: VM_OBJECT_NULL,
120: 0, // offset
121: owner_addr,
122: shmem_size,
123: TRUE ); // Find first fit
124: if(krtn)
125: {
126: IOLog("createEventShmem: vm_map_find() returned %d\n", krtn);
127: vm_map_deallocate(task_map); // discard our reference
128: return KERN_NO_SPACE;
129: }
130: /* For each page in the area allocated from the kernel map,
131: find the physical address of the page.
132: Enter the page in the target task's pmap, at the
133: appropriate target task virtual address. */
134: for ( off = 0; off < shmem_size; off += PAGE_SIZE )
135: {
136: phys_addr = pmap_extract( kernel_pmap, (*shmem_addr) + off );
137: if ( phys_addr == 0 )
138: {
139: IOLog("createEventShmem: no paddr for vaddr 0x%x\n",
140: (*shmem_addr) + off );
141: kmem_free( kernel_map, *shmem_addr, size );
142: vm_map_deallocate(task_map); // discard our reference
143: return KERN_NO_SPACE;
144: }
145: pmap_enter(
146: task_map->pmap,
147: *owner_addr + off,
148: phys_addr,
149: VM_PROT_READ|VM_PROT_WRITE,
150: TRUE);
151: }
152: *owner = task_map;
153:
154: return KERN_SUCCESS;
155: }
156:
157:
158: //
159: // Unmap the shared memory area and release the wired memory.
160: //
161: kern_return_t
162: destroyEventShmem( port_t task,
163: struct vm_map *owner,
164: vm_size_t size,
165: vm_offset_t owner_addr,
166: vm_offset_t shmem_addr )
167: {
168: vm_offset_t off;
169: kern_return_t krtn;
170: vm_size_t shmem_size;
171:
172: if ( owner == VM_MAP_NULL )
173: return KERN_INVALID_ARGUMENT;
174: shmem_size = round_page(size);
175:
176: // Pull the shared pages out of the task map
177: for ( off = 0; off < shmem_size; off += PAGE_SIZE )
178: {
179: pmap_remove(
180: owner->pmap,
181: owner_addr + off,
182: owner_addr + off + PAGE_SIZE);
183: }
184: // Free the former shmem area in the task
185: krtn = vm_map_remove(owner,
186: owner_addr,
187: owner_addr + shmem_size );
188: if(krtn) {
189: IOLog("destroyEventShmem: vm_map_remove() returned %d\n",
190: krtn);
191: }
192: // finally, free the memory back to the kernel map.
193: kmem_free( kernel_map, shmem_addr, shmem_size );
194:
195: vm_map_deallocate(owner); // discard our reference
196: return krtn;
197: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.