static int z2_open()

in z2ram.c [143:291]


static int z2_open(struct block_device *bdev, fmode_t mode)
{
	int device;
	int max_z2_map = (Z2RAM_SIZE / Z2RAM_CHUNKSIZE) * sizeof(z2ram_map[0]);
	int max_chip_map = (amiga_chip_size / Z2RAM_CHUNKSIZE) *
	    sizeof(z2ram_map[0]);
	int rc = -ENOMEM;

	device = MINOR(bdev->bd_dev);

	mutex_lock(&z2ram_mutex);
	if (current_device != -1 && current_device != device) {
		rc = -EBUSY;
		goto err_out;
	}

	if (current_device == -1) {
		z2_count = 0;
		chip_count = 0;
		list_count = 0;
		z2ram_size = 0;

		/* Use a specific list entry. */
		if (device >= Z2MINOR_MEMLIST1 && device <= Z2MINOR_MEMLIST4) {
			int index = device - Z2MINOR_MEMLIST1 + 1;
			unsigned long size, paddr, vaddr;

			if (index >= m68k_realnum_memory) {
				printk(KERN_ERR DEVICE_NAME
				       ": no such entry in z2ram_map\n");
				goto err_out;
			}

			paddr = m68k_memory[index].addr;
			size = m68k_memory[index].size & ~(Z2RAM_CHUNKSIZE - 1);

#ifdef __powerpc__
			/* FIXME: ioremap doesn't build correct memory tables. */
			{
				vfree(vmalloc(size));
			}

			vaddr = (unsigned long)ioremap_wt(paddr, size);

#else
			vaddr =
			    (unsigned long)z_remap_nocache_nonser(paddr, size);
#endif
			z2ram_map =
			    kmalloc_array(size / Z2RAM_CHUNKSIZE,
					  sizeof(z2ram_map[0]), GFP_KERNEL);
			if (z2ram_map == NULL) {
				printk(KERN_ERR DEVICE_NAME
				       ": cannot get mem for z2ram_map\n");
				goto err_out;
			}

			while (size) {
				z2ram_map[z2ram_size++] = vaddr;
				size -= Z2RAM_CHUNKSIZE;
				vaddr += Z2RAM_CHUNKSIZE;
				list_count++;
			}

			if (z2ram_size != 0)
				printk(KERN_INFO DEVICE_NAME
				       ": using %iK List Entry %d Memory\n",
				       list_count * Z2RAM_CHUNK1024, index);
		} else
			switch (device) {
			case Z2MINOR_COMBINED:

				z2ram_map =
				    kmalloc(max_z2_map + max_chip_map,
					    GFP_KERNEL);
				if (z2ram_map == NULL) {
					printk(KERN_ERR DEVICE_NAME
					       ": cannot get mem for z2ram_map\n");
					goto err_out;
				}

				get_z2ram();
				get_chipram();

				if (z2ram_size != 0)
					printk(KERN_INFO DEVICE_NAME
					       ": using %iK Zorro II RAM and %iK Chip RAM (Total %dK)\n",
					       z2_count * Z2RAM_CHUNK1024,
					       chip_count * Z2RAM_CHUNK1024,
					       (z2_count +
						chip_count) * Z2RAM_CHUNK1024);

				break;

			case Z2MINOR_Z2ONLY:
				z2ram_map = kmalloc(max_z2_map, GFP_KERNEL);
				if (!z2ram_map)
					goto err_out;

				get_z2ram();

				if (z2ram_size != 0)
					printk(KERN_INFO DEVICE_NAME
					       ": using %iK of Zorro II RAM\n",
					       z2_count * Z2RAM_CHUNK1024);

				break;

			case Z2MINOR_CHIPONLY:
				z2ram_map = kmalloc(max_chip_map, GFP_KERNEL);
				if (!z2ram_map)
					goto err_out;

				get_chipram();

				if (z2ram_size != 0)
					printk(KERN_INFO DEVICE_NAME
					       ": using %iK Chip RAM\n",
					       chip_count * Z2RAM_CHUNK1024);

				break;

			default:
				rc = -ENODEV;
				goto err_out;

				break;
			}

		if (z2ram_size == 0) {
			printk(KERN_NOTICE DEVICE_NAME
			       ": no unused ZII/Chip RAM found\n");
			goto err_out_kfree;
		}

		current_device = device;
		z2ram_size <<= Z2RAM_CHUNKSHIFT;
		set_capacity(z2ram_gendisk[device], z2ram_size >> 9);
	}

	mutex_unlock(&z2ram_mutex);
	return 0;

err_out_kfree:
	kfree(z2ram_map);
err_out:
	mutex_unlock(&z2ram_mutex);
	return rc;
}