map->offset += dev->sg->handle; 
map->offset += (unsigned long)dev->sg->virtual; 
int drm_addmap(drm_device_t * dev, unsigned int offset,	       unsigned int size, drm_map_type_t type,	       drm_map_flags_t flags, drm_local_map_t ** map_ptr){	drm_map_t *map;	drm_map_list_t *list;	drm_dma_handle_t *dmah;	drm_local_map_t *found_map;	map = drm_alloc( sizeof(*map), DRM_MEM_MAPS );	if ( !map )		return -ENOMEM;	map->offset = offset;	map->size = size;	map->flags = flags;	map->type = type;	/* Only allow shared memory to be removable since we only keep enough	 * book keeping information about shared memory to allow for removal	 * when processes fork.	 */	if ( (map->flags & _DRM_REMOVABLE) && map->type != _DRM_SHM ) {		drm_free( map, sizeof(*map), DRM_MEM_MAPS );		return -EINVAL;	}	DRM_DEBUG( "offset = 0x%08lx, size = 0x%08lx, type = %d\n",		   map->offset, map->size, map->type );	if ( (map->offset & (~PAGE_MASK)) || (map->size & (~PAGE_MASK)) ) {		drm_free( map, sizeof(*map), DRM_MEM_MAPS );		return -EINVAL;	}	map->mtrr   = -1;	map->handle = NULL;	switch ( map->type ) {	case _DRM_REGISTERS:	case _DRM_FRAME_BUFFER:#if !defined(__sparc__) && !defined(__alpha__) && !defined(__ia64__)		if ( map->offset + map->size < map->offset ||		     map->offset < virt_to_phys(high_memory) ) {			drm_free( map, sizeof(*map), DRM_MEM_MAPS );			return -EINVAL;		}#endif#ifdef __alpha__		map->offset += dev->hose->mem_space->start;#endif		/* Some drivers preinitialize some maps, without the X Server		 * needing to be aware of it.  Therefore, we just return success		 * when the server tries to create a duplicate map.		 */		found_map = drm_find_matching_map(dev, map);		if (found_map != NULL) {			if (found_map->size != map->size) {				DRM_DEBUG("Matching maps of type %d with "				   "mismatched sizes, (%ld vs %ld)\n",				    map->type, map->size, found_map->size);				found_map->size = map->size;			}			drm_free(map, sizeof(*map), DRM_MEM_MAPS);			*map_ptr = found_map;			return 0;		}		if (drm_core_has_MTRR(dev)) {			if ( map->type == _DRM_FRAME_BUFFER ||			     (map->flags & _DRM_WRITE_COMBINING) ) {				map->mtrr = mtrr_add( map->offset, map->size,						      MTRR_TYPE_WRCOMB, 1 );			}		}		if (map->type == _DRM_REGISTERS)			map->handle = drm_ioremap( map->offset, map->size,						    dev );		break;	case _DRM_SHM:		map->handle = vmalloc_32(map->size);		DRM_DEBUG( "%lu %d %p\n",			   map->size, drm_order( map->size ), map->handle );		if ( !map->handle ) {			drm_free( map, sizeof(*map), DRM_MEM_MAPS );			return -ENOMEM;		}		map->offset = (unsigned long)map->handle;		if ( map->flags & _DRM_CONTAINS_LOCK ) {			/* Prevent a 2nd X Server from creating a 2nd lock */			if (dev->lock.hw_lock != NULL) {				vfree( map->handle );				drm_free( map, sizeof(*map), DRM_MEM_MAPS );				return -EBUSY;			}			dev->sigdata.lock =			dev->lock.hw_lock = map->handle; /* Pointer to lock */		}		break;	case _DRM_AGP:		if (drm_core_has_AGP(dev)) {#ifdef __alpha__			map->offset += dev->hose->mem_space->start;#endif			map->offset += dev->agp->base;			map->mtrr   = dev->agp->agp_mtrr; /* for getmap */		}		break;	case _DRM_SCATTER_GATHER:		if (!dev->sg) {			drm_free(map, sizeof(*map), DRM_MEM_MAPS);			return -EINVAL;		}		map->offset += dev->sg->handle;		break;	case _DRM_CONSISTENT: 		/* dma_addr_t is 64bit on i386 with CONFIG_HIGHMEM64G,		 * As we're limiting the address to 2^32-1 (or less),		 * casting it down to 32 bits is no problem, but we		 * need to point to a 64bit variable first. */		dmah = drm_pci_alloc(dev, map->size, map->size, 0xffffffffUL);		if (!dmah) {			drm_free(map, sizeof(*map), DRM_MEM_MAPS);			return -ENOMEM;		}		map->handle = dmah->vaddr;		map->offset = (unsigned long)dmah->busaddr;		kfree(dmah);		break;	default:		drm_free( map, sizeof(*map), DRM_MEM_MAPS );		return -EINVAL;	}	list = drm_alloc(sizeof(*list), DRM_MEM_MAPS);	if(!list) {		drm_free(map, sizeof(*map), DRM_MEM_MAPS);		return -EINVAL;	}	memset(list, 0, sizeof(*list));	list->map = map;	down(&dev->struct_sem);	list_add(&list->head, &dev->maplist->head);#ifdef CONFIG_COMPAT	/* Assign a 32-bit handle for _DRM_SHM mappings */	/* We do it here so that dev->struct_sem protects the increment */	if (map->type == _DRM_SHM)		map->offset = map32_handle += PAGE_SIZE;#endif 	up(&dev->struct_sem);	*map_ptr = map;	return 0;}
4520	/local/tlutelli/issta_data/temp/c/2005_temp/2005/4520/d1f2b55ad2c11f46e30547a9f7754e99b478348e/drm_bufs.c/buggy/drivers/char/drm/drm_bufs.c