Created
October 22, 2009 22:52
-
-
Save mhansen/216423 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| --- oldsrc/drivers/memory/memory.c 2009-10-22 18:26:49.251667100 +1300 | |
| +++ src/drivers/memory/memory.c 2009-10-22 18:34:50.203175900 +1300 | |
| @@ -10,99 +10,104 @@ | |
| * Changes: | |
| * Apr 29, 2005 added null byte generator (Jorrit N. Herder) | |
| * Apr 09, 2005 added support for boot device (Jorrit N. Herder) | |
| * Jul 26, 2004 moved RAM driver to user-space (Jorrit N. Herder) | |
| * Apr 20, 1992 device dependent/independent split (Kees J. Bot) | |
| */ | |
| #include "../drivers.h" | |
| #include "../libdriver/driver.h" | |
| #include <sys/ioc_memory.h> | |
| #include <env.h> | |
| #include <minix/ds.h> | |
| #include <minix/vm.h> | |
| #include <sys/mman.h> | |
| #include "../../kernel/const.h" | |
| #include "../../kernel/config.h" | |
| #include "../../kernel/type.h" | |
| #include <sys/vm.h> | |
| #include <sys/vm_i386.h> | |
| #include "assert.h" | |
| #include "local.h" | |
| /* ramdisks (/dev/ram*) */ | |
| #define RAMDISKS 6 | |
| #define RAM_DEV_LAST (RAM_DEV_FIRST+RAMDISKS-1) | |
| -#define NR_DEVS (7+RAMDISKS) /* number of minor devices */ | |
| +#define NR_DEVS (8+RAMDISKS) /* number of minor devices */ | |
| PRIVATE struct device m_geom[NR_DEVS]; /* base and size of each device */ | |
| PRIVATE vir_bytes m_vaddrs[NR_DEVS]; | |
| PRIVATE int m_device; /* current device */ | |
| PRIVATE struct kinfo kinfo; /* kernel information */ | |
| extern int errno; /* error number for PM calls */ | |
| FORWARD _PROTOTYPE( char *m_name, (void) ); | |
| FORWARD _PROTOTYPE( struct device *m_prepare, (int device) ); | |
| FORWARD _PROTOTYPE( int m_transfer, (int proc_nr, int opcode, u64_t position, | |
| iovec_t *iov, unsigned nr_req, int safe)); | |
| FORWARD _PROTOTYPE( int m_do_open, (struct driver *dp, message *m_ptr) ); | |
| FORWARD _PROTOTYPE( void m_init, (void) ); | |
| FORWARD _PROTOTYPE( int m_ioctl, (struct driver *dp, message *m_ptr, int safe)); | |
| FORWARD _PROTOTYPE( void m_geometry, (struct partition *entry) ); | |
| /* Entry points to this driver. */ | |
| PRIVATE struct driver m_dtab = { | |
| m_name, /* current device's name */ | |
| m_do_open, /* open or mount */ | |
| do_nop, /* nothing on a close */ | |
| m_ioctl, /* specify ram disk geometry */ | |
| m_prepare, /* prepare for I/O on a given minor device */ | |
| m_transfer, /* do the I/O */ | |
| nop_cleanup, /* no need to clean up */ | |
| m_geometry, /* memory device "geometry" */ | |
| nop_signal, /* system signals */ | |
| nop_alarm, | |
| nop_cancel, | |
| nop_select, | |
| NULL, | |
| NULL | |
| }; | |
| /* Buffer for the /dev/zero null byte feed. */ | |
| #define ZERO_BUF_SIZE 1024 | |
| + | |
| +/* Buffer for the /dev/one byte feed */ | |
| +#define ONE_BUF_SIZE 1024 | |
| PRIVATE char dev_zero[ZERO_BUF_SIZE]; | |
| +PRIVATE char dev_one[ONE_BUF_SIZE]; | |
| + | |
| #define click_to_round_k(n) \ | |
| ((unsigned) ((((unsigned long) (n) << CLICK_SHIFT) + 512) / 1024)) | |
| /*===========================================================================* | |
| * main * | |
| *===========================================================================*/ | |
| PUBLIC int main(void) | |
| { | |
| /* Main program. Initialize the memory driver and start the main loop. */ | |
| struct sigaction sa; | |
| sa.sa_handler = SIG_MESS; | |
| sigemptyset(&sa.sa_mask); | |
| sa.sa_flags = 0; | |
| if (sigaction(SIGTERM,&sa,NULL)<0) panic("MEM","sigaction failed", errno); | |
| m_init(); | |
| driver_task(&m_dtab); | |
| return(OK); | |
| } | |
| /*===========================================================================* | |
| * m_name * | |
| *===========================================================================*/ | |
| PRIVATE char *m_name() | |
| { | |
| /* Return a name for the current device. */ | |
| static char name[] = "memory"; | |
| return name; | |
| @@ -247,62 +252,63 @@ | |
| if (opcode == DEV_GATHER_S) { /* copy data */ | |
| s=sys_safecopyto(proc_nr, user_vir, | |
| vir_offset, (vir_bytes) vaddr+page_off, subcount, D); | |
| } else { | |
| s=sys_safecopyfrom(proc_nr, user_vir, | |
| vir_offset, (vir_bytes) vaddr+page_off, subcount, D); | |
| } | |
| if(s != OK) | |
| return s; | |
| count = subcount; | |
| break; | |
| } | |
| /* Null byte stream generator. */ | |
| case ZERO_DEV: | |
| if (opcode == DEV_GATHER_S) { | |
| size_t suboffset = 0; | |
| left = count; | |
| while (left > 0) { | |
| chunk = (left > ZERO_BUF_SIZE) ? ZERO_BUF_SIZE : left; | |
| s=sys_safecopyto(proc_nr, user_vir, | |
| vir_offset+suboffset, (vir_bytes) dev_zero, chunk, D); | |
| if(s != OK) | |
| report("MEM","sys_safecopyto failed", s); | |
| left -= chunk; | |
| suboffset += chunk; | |
| } | |
| } | |
| break; | |
| - | |
| } | |
| + | |
| + | |
| /* Book the number of bytes transferred. */ | |
| position += count; | |
| vir_offset += count; | |
| if ((iov->iov_size -= count) == 0) { iov++; nr_req--; vir_offset = 0; } | |
| } | |
| return(OK); | |
| } | |
| /*===========================================================================* | |
| * m_do_open * | |
| *===========================================================================*/ | |
| PRIVATE int m_do_open(dp, m_ptr) | |
| struct driver *dp; | |
| message *m_ptr; | |
| { | |
| int r; | |
| /* Check device number on open. */ | |
| if (m_prepare(m_ptr->DEVICE) == NIL_DEV) return(ENXIO); | |
| if (m_device == MEM_DEV) | |
| { | |
| r = sys_enable_iop(m_ptr->IO_ENDPT); | |
| if (r != OK) | |
| { | |
| printf("m_do_open: sys_enable_iop failed for %d: %d\n", | |
| m_ptr->IO_ENDPT, r); | |
| return r; | |
| } | |
| @@ -316,60 +322,65 @@ | |
| PRIVATE void m_init() | |
| { | |
| /* Initialize this task. All minor devices are initialized one by one. */ | |
| u32_t ramdev_size; | |
| int i, s; | |
| if (OK != (s=sys_getkinfo(&kinfo))) { | |
| panic("MEM","Couldn't get kernel information.",s); | |
| } | |
| #if 0 | |
| /* Map in kernel memory for /dev/kmem. */ | |
| m_geom[KMEM_DEV].dv_base = cvul64(kinfo.kmem_base); | |
| m_geom[KMEM_DEV].dv_size = cvul64(kinfo.kmem_size); | |
| if((m_vaddrs[KMEM_DEV] = vm_map_phys(SELF, (void *) kinfo.kmem_base, | |
| kinfo.kmem_size)) == MAP_FAILED) { | |
| printf("MEM: Couldn't map in /dev/kmem."); | |
| } | |
| #endif | |
| /* Ramdisk image built into the memory driver */ | |
| m_geom[IMGRD_DEV].dv_base= cvul64(0); | |
| m_geom[IMGRD_DEV].dv_size= cvul64(imgrd_size); | |
| m_vaddrs[IMGRD_DEV] = (vir_bytes) imgrd; | |
| /* Initialize /dev/zero. Simply write zeros into the buffer. */ | |
| for (i=0; i<ZERO_BUF_SIZE; i++) { | |
| dev_zero[i] = '\0'; | |
| } | |
| + /* initialize /dev/one. */ | |
| + for (i=0; i<ONE_BUF_SIZE; i++) { | |
| + dev_one[i] = '1'; | |
| + } | |
| + | |
| /* Set up memory range for /dev/mem. */ | |
| m_geom[MEM_DEV].dv_base = cvul64(0); | |
| m_geom[MEM_DEV].dv_size = cvul64(0xffffffff); | |
| m_vaddrs[MEM_DEV] = (vir_bytes) MAP_FAILED; /* we are not mapping this in. */ | |
| } | |
| /*===========================================================================* | |
| * m_ioctl * | |
| *===========================================================================*/ | |
| PRIVATE int m_ioctl(dp, m_ptr, safe) | |
| struct driver *dp; /* pointer to driver structure */ | |
| message *m_ptr; /* pointer to control message */ | |
| int safe; | |
| { | |
| /* I/O controls for the memory driver. Currently there is one I/O control: | |
| * - MIOCRAMSIZE: to set the size of the RAM disk. | |
| */ | |
| struct device *dv; | |
| if(!safe) { | |
| printf("m_transfer: unsafe?\n"); | |
| return EPERM; | |
| } | |
| switch (m_ptr->REQUEST) { | |
| case MIOCRAMSIZE: { | |
| /* Someone wants to create a new RAM disk with the given size. */ | |
| u32_t ramdev_size; | |
| int s, dev; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment