void UpdatePositionDisplay( int train_number, int speed, char* pos_node, int pos_offset, int error, int max_error, char* dest_node, int dest_offset, char* state ) { int tid = -1; tid = WhoIs( "trainsTAB" ); //check the return value of WhoIs if( tid < 0 ) { return; } //create the message struct train_position_output_message msg; msg.message_type = TRAIN_POSITION_OUTPUT_MESSAGE; msg.train_nums = train_number; msg.train_speeds = speed; safestrcpy( msg.train_pos_node, pos_node, 6 ); msg.train_pos_off = pos_offset; msg.train_err = error; msg.train_max_err = max_error; safestrcpy( msg.train_dest_node, dest_node, 6 ); msg.train_dest_off = dest_offset; safestrcpy( msg.train_state, state, 6 ); //send the message via courier CourierSend( tid, (char *)&msg, sizeof (msg) ); }
//PAGEBREAK: 32 // Set up first user process. void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); initproc = p; initproc->uid = 0; if((p->pgdir = setupkvm()) == 0) panic("userinit: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE; p->tf->eip = 0; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); safestrcpy(p->wdpath, "/\n", 2); //start in the root directory p->state = RUNNABLE; }
/** * sysfs_open_class_device_path: Opens and populates class device * @path: path to class device. * returns struct sysfs_class_device with success and NULL with error. */ struct sysfs_class_device *sysfs_open_class_device_path(const char *path) { struct sysfs_class_device *cdev; char temp_path[SYSFS_PATH_MAX]; if (!path) { errno = EINVAL; return NULL; } /* * Post linux-2.6.14 driver model supports nested classes with * links to the nested hierarchy at /sys/class/xxx/. Check for * a link to the actual class device if a directory isn't found */ if (sysfs_path_is_dir(path)) { dprintf("%s: Directory not found, checking for a link\n", path); if (!sysfs_path_is_link(path)) { if (sysfs_get_link(path, temp_path, SYSFS_PATH_MAX)) { dprintf("Error retrieving link at %s\n", path); return NULL; } } else { dprintf("%s is not a valid class device path\n", path); return NULL; } } else safestrcpy(temp_path, path); cdev = alloc_class_device(); if (!cdev) { dprintf("calloc failed\n"); return NULL; } if (sysfs_get_name_from_path(temp_path, cdev->name, SYSFS_NAME_LEN)) { errno = EINVAL; dprintf("Error getting class device name\n"); sysfs_close_class_device(cdev); return NULL; } safestrcpy(cdev->path, temp_path); if (sysfs_remove_trailing_slash(cdev->path)) { dprintf("Invalid path to class device %s\n", cdev->path); sysfs_close_class_device(cdev); return NULL; } set_classdev_classname(cdev); return cdev; }
/** * sysfs_get_bus_devices: gets all devices for bus * @bus: bus to get devices for * returns dlist of devices with success and NULL with failure */ struct dlist *sysfs_get_bus_devices(struct sysfs_bus *bus) { struct sysfs_device *dev; struct dlist *linklist; char path[SYSFS_PATH_MAX], devpath[SYSFS_PATH_MAX]; char target[SYSFS_PATH_MAX]; char *curlink; if (!bus) { errno = EINVAL; return NULL; } memset(path, 0, SYSFS_PATH_MAX); safestrcpy(path, bus->path); safestrcat(path, "/"); safestrcat(path, SYSFS_DEVICES_NAME); linklist = read_dir_links(path); if (linklist) { dlist_for_each_data(linklist, curlink, char) { if (bus->devices) { dev = (struct sysfs_device *) dlist_find_custom(bus->devices, (void *)curlink, name_equal); if (dev) continue; } safestrcpy(devpath, path); safestrcat(devpath, "/"); safestrcat(devpath, curlink); if (sysfs_get_link(devpath, target, SYSFS_PATH_MAX)) { dprintf("Error getting link - %s\n", devpath); continue; } dev = sysfs_open_device_path(target); if (!dev) { dprintf("Error opening device at %s\n", target); continue; } if (!bus->devices) bus->devices = dlist_new_with_delete (sizeof(struct sysfs_device), sysfs_close_dev); dlist_unshift_sorted(bus->devices, dev, sort_list); } sysfs_close_list(linklist); } return (bus->devices); }
/** * sysfs_open_class: opens specific class and all its devices on system * returns sysfs_class structure with success or NULL with error. */ struct sysfs_class *sysfs_open_class(const char *name) { struct sysfs_class *cls = NULL; char *c, classpath[SYSFS_PATH_MAX]; if (!name) { errno = EINVAL; return NULL; } memset(classpath, 0, SYSFS_PATH_MAX); if ((sysfs_get_mnt_path(classpath, SYSFS_PATH_MAX)) != 0) { dprintf("Sysfs not supported on this system\n"); return NULL; } safestrcat(classpath, "/"); if (strcmp(name, SYSFS_BLOCK_NAME) == 0) { safestrcat(classpath, SYSFS_BLOCK_NAME); if (!sysfs_path_is_dir(classpath)) goto done; c = strrchr(classpath, '/'); *(c+1) = '\0'; } safestrcat(classpath, SYSFS_CLASS_NAME); safestrcat(classpath, "/"); safestrcat(classpath, name); done: if (sysfs_path_is_dir(classpath)) { dprintf("Class %s not found on the system\n", name); return NULL; } cls = alloc_class(); if (cls == NULL) { dprintf("calloc failed\n"); return NULL; } safestrcpy(cls->name, name); safestrcpy(cls->path, classpath); if ((sysfs_remove_trailing_slash(cls->path)) != 0) { dprintf("Invalid path to class device %s\n", cls->path); sysfs_close_class(cls); return NULL; } return cls; }
/** * sysfs_get_bus_driver: Get specific driver on bus using driver name * @bus: bus to find driver on * @drvname: name of driver * returns struct sysfs_driver reference or NULL if not found. */ struct sysfs_driver *sysfs_get_bus_driver(struct sysfs_bus *bus, const char *drvname) { struct sysfs_driver *drv; char drvpath[SYSFS_PATH_MAX]; if (!bus || !drvname) { errno = EINVAL; return NULL; } if (bus->drivers) { drv = (struct sysfs_driver *)dlist_find_custom (bus->drivers, (void *)drvname, name_equal); if (drv) return drv; } safestrcpy(drvpath, bus->path); safestrcat(drvpath, "/"); safestrcat(drvpath, SYSFS_DRIVERS_NAME); safestrcat(drvpath, "/"); safestrcat(drvpath, drvname); drv = sysfs_open_driver_path(drvpath); if (!drv) { dprintf("Error opening driver at %s\n", drvpath); return NULL; } if (!bus->drivers) bus->drivers = dlist_new_with_delete (sizeof(struct sysfs_driver), sysfs_close_drv); dlist_unshift_sorted(bus->drivers, drv, sort_list); return drv; }
// Set up internal proccess for swap managment (inswapper) void createInternalProcess(const char *name, void (*entrypoint)()) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); inswapper = p; if((p->pgdir = setupkvm(kalloc)) == 0) panic("inswapper: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE; p->tf->eip = 0; p->context->eip = (uint) entrypoint; // beginning of inswapper safestrcpy(p->name, name, sizeof(p->name)); p->cwd = namei("/"); // start sleeping until first proccess is created p->state = SLEEPING; }
//PAGEBREAK: 32 // Set up first user process. void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); initproc = p; if((p->pgdir = setupkvm()) == 0) panic("userinit: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE; p->tf->eip = 0; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); p->state = RUNNABLE; #ifndef __ORIGINAL_SCHED__ penqueue(p); #endif }
// Set up first user process. void userinit(void) { struct proc *p; extern uchar _binary_initcode_start[], _binary_initcode_size[]; p = copyproc(0); p->sz = PAGE; p->mem = kalloc(p->sz); p->cwd = namei("/"); memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = p->sz; // Make return address readable; needed for some gcc. p->tf->esp -= 4; *(uint*)(p->mem + p->tf->esp) = 0xefefefef; // On entry to user space, start executing at beginning of initcode.S. p->tf->eip = 0; memmove(p->mem, _binary_initcode_start, (int)_binary_initcode_size); safestrcpy(p->name, "initcode", sizeof(p->name)); #ifdef LOTTERY p->tickets = INIT_TICKETS; #endif p->state = UNUSED; setstate(p, RUNNABLE); initproc = p; }
//PAGEBREAK: 32 // Set up first user process. void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); initproc = p; if((p->pgdir = setupkvm()) == 0) panic("userinit: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE; p->tf->eip = 0; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); p->state = RUNNABLE; p->next = NULL; // initialize queue next pointer p->priority = 15; // initialize priority //**** //cprintf("add in userinit\n"); acquire(&ptable.lock); addtoq(p); release(&ptable.lock); //**** }
//PAGEBREAK: 32 // Set up first user process. void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); initproc = p; if((p->pgdir = setupkvm()) == 0) panic("userinit: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE; p->tf->eip = 0; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); // this assignment to p->state lets other cores // run this process. the acquire forces the above // writes to be visible, and the lock is also needed // because the assignment might not be atomic. acquire(&ptable.lock); p->state = RUNNABLE; release(&ptable.lock); }
// Create a new process copying p as the parent. // Sets up stack to return as if from system call. static int checkpoint(struct proc *p) { // Allocate process. //if((checkpoint_proc = allocproc()) == 0) // return -1; // Copy process state from p. if((p->pgdir = copyuvm(proc->pgdir, proc->sz)) == 0){ kfree(p->kstack); p->kstack = 0; p->state = UNUSED; return -1; } p->sz = proc->sz; p->parent = proc; // *p->tf = *proc->tf; // Clear %eax so that fork returns 0 in the child. // p->tf->eax = 0; /* for(i = 0; i < NOFILE; i++) if(proc->ofile[i]) p->ofile[i] = filedup(proc->ofile[i]); p->cwd = idup(proc->cwd); */ safestrcpy(p->name, proc->name, sizeof(proc->name)); cprintf("Your process name was: %s\n", p->name); return 0; }
/** * sysfs_open_attribute: creates sysfs_attribute structure * @path: path to attribute. * returns sysfs_attribute struct with success and NULL with error. */ struct sysfs_attribute *sysfs_open_attribute(const char *path) { struct sysfs_attribute *sysattr = NULL; struct stat fileinfo; if (path == NULL) { errno = EINVAL; return NULL; } sysattr = alloc_attribute(); if (sysattr == NULL) { dprintf("Error allocating attribute at %s\n", path); return NULL; } if (sysfs_get_name_from_path(path, sysattr->name, SYSFS_NAME_LEN) != 0) { dprintf("Error retrieving attrib name from path: %s\n", path); sysfs_close_attribute(sysattr); return NULL; } safestrcpy(sysattr->path, path); if ((stat(sysattr->path, &fileinfo)) != 0) { dprintf("Stat failed: No such attribute?\n"); sysattr->method = 0; free(sysattr); sysattr = NULL; } else { if (fileinfo.st_mode & S_IRUSR) sysattr->method |= SYSFS_METHOD_SHOW; if (fileinfo.st_mode & S_IWUSR) sysattr->method |= SYSFS_METHOD_STORE; } return sysattr; }
//PAGEBREAK: 32 // Set up first user process. void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); initproc = p; if ((p->pgdir = setupkvm()) == 0) panic("userinit: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int) _binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE; p->tf->eip = 0; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); p->parent=0; setpriority(p,0); SetProcessRunnable(p); }
//PAGEBREAK: 32 // Set up first user process. void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); initproc = p; if((p->pgdir = setupkvm(kalloc)) == 0) panic("userinit: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE; p->tf->eip = 0; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); p->state = RUNNABLE; createInternalProcess("inSwapper",(void*)inSwapper); }
//PAGEBREAK: 32 // hand-craft the first user process. We link initcode.S into the kernel // as a binary, the linker will generate __binary_initcode_start/_size void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); initproc = p; if((p->pgdir = kpt_alloc()) == NULL) { panic("userinit: out of memory?"); } inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PTE_SZ; // craft the trapframe as if memset(p->tf, 0, sizeof(*p->tf)); p->tf->r14_svc = (uint)error_init; p->tf->spsr = spsr_usr (); p->tf->sp_usr = PTE_SZ; // set the user stack p->tf->lr_usr = 0; // set the user pc. The actual pc loaded into r15_usr is in // p->tf, the trapframe. p->tf->pc = 0; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); p->state = RUNNABLE; }
//PAGEBREAK: 32 // Set up first user process. void userinit(void) { #ifndef SELECTION_NONE //get num of free pages after kernel finished loading free_pages_after_kernel = get_freepages_num(); #endif struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); initproc = p; if((p->pgdir = setupkvm()) == 0) panic("userinit: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE; p->tf->eip = 0; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); p->state = RUNNABLE; }
// Set up first user process. void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); initproc = p; if(!(p->pgdir = setupkvm())) panic("userinit: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE; p->tf->eip = 0; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); p->state = RUNNABLE; // START HW4 p->priority = 0; p->affinity = -1; acquire(&runqueue.lock); enqueue( p->pid, 0 ); release(&runqueue.lock); // END HW4 }
// Create a new process copying p as the parent. // Sets up stack to return as if from system call. // Caller must set state of returned proc to RUNNABLE. int fork(void) { int i, pid; struct proc *np; // Allocate process. if((np = allocproc()) == 0) return -1; // Copy process state from p. if((np->pgdir = copyuvm(proc->pgdir, proc->sz)) == 0){ kfree(np->kstack); np->kstack = 0; np->state = UNUSED; return -1; } np->sz = proc->sz; np->parent = proc; *np->tf = *proc->tf; // Clear %eax so that fork returns 0 in the child. np->tf->eax = 0; for(i = 0; i < NOFILE; i++) if(proc->ofile[i]) np->ofile[i] = filedup(proc->ofile[i]); np->cwd = idup(proc->cwd); pid = np->pid; np->state = RUNNABLE; safestrcpy(np->name, proc->name, sizeof(proc->name)); return pid; }
// Set up first user process. void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); initproc = p; // Initialize memory from initcode.S p->sz = PAGE; p->mem = kalloc(p->sz); memset(p->mem, 0, p->sz); memmove(p->mem, _binary_initcode_start, (int)_binary_initcode_size); memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = p->sz; p->tf->eip = 0; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); p->state = RUNNABLE; }
/** * read_dir_subdirs: grabs subdirs in a specific directory * @sysdir: sysfs directory to read * returns list of directory names with success and NULL with error. */ struct sysfs_device *sysfs_read_dir_subdirs(const char *path) { DIR *dir = NULL; struct dirent *dirent = NULL; char file_path[SYSFS_PATH_MAX]; struct sysfs_device *dev = NULL; if (!path) { errno = EINVAL; return NULL; } dev = sysfs_open_device_path(path); dir = opendir(path); if (!dir) { dprintf("Error opening directory %s\n", path); return NULL; } while ((dirent = readdir(dir)) != NULL) { if (0 == strcmp(dirent->d_name, ".")) continue; if (0 == strcmp(dirent->d_name, "..")) continue; memset(file_path, 0, SYSFS_PATH_MAX); safestrcpy(file_path, path); safestrcat(file_path, "/"); safestrcat(file_path, dirent->d_name); if (!sysfs_path_is_dir(file_path)) add_subdirectory(dev, file_path); } closedir(dir); return dev; }
//PAGEBREAK: 32 // Set up first user process. void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; //cprintf("in user init"); p = allocproc(); initproc = p; if((p->pgdir = setupkvm()) == 0) panic("userinit: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE; p->tf->eip = 0; // beginning of initcode.S p->priority = 14; p->prev = 0; p->next = 0; safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); p->state = RUNNABLE; //cprintf("userinit setting on ready\n"); ready(p); }
void taskinit(void) { struct task_t *t; struct proc *p; for (t = ktasks; t < ktasks + LEN(ktasks); t++) { p = allocproc(); assert(p); assert(p - ptable == t - ktasks); p->pgdir = kpgdir; safestrcpy(p->name, t->name, sizeof(p->name)); memset(p->tf, 1, sizeof(*p->tf));//debug p->tf->cs = (SEG_KCODE << 3); p->tf->ss = (SEG_KDATA << 3); p->tf->ds = p->tf->es = p->tf->fs = p->tf->gs = p->tf->ss; p->tf->esp = (u32)p->kstack + KSTACKSZ; p->tf->eip = (u32)t->start; p->tf->eflags = FL_IF; p->brk = 0; // never used p->state = RUNNABLE; p->counter = p->priority = 20; if (t - ktasks == TASK_IDLE) p->counter = p->priority = 1; } }
/** * sysfs_get_class_devices: get all class devices in the given class * @cls: sysfs_class whose devices list is needed * * Returns a dlist of sysfs_class_device * on success and NULL on failure */ struct dlist *sysfs_get_class_devices(struct sysfs_class *cls) { char path[SYSFS_PATH_MAX]; struct dlist *dirlist, *linklist; if (!cls) { errno = EINVAL; return NULL; } /* * Post linux-2.6.14, we have nested classes and links under * /sys/class/xxx/. are also valid class devices */ safestrcpy(path, cls->path); dirlist = read_dir_subdirs(path); if (dirlist) { add_cdevs_to_classlist(cls, dirlist); sysfs_close_list(dirlist); } linklist = read_dir_links(path); if (linklist) { add_cdevs_to_classlist(cls, linklist); sysfs_close_list(linklist); } return cls->devices; }
// Set up first user process. void userinit(void) { struct proc *p; extern char _binary_initcode_start[], _binary_initcode_size[]; p = allocproc(); acquire(&ptable.lock); initproc = p; if((p->pgdir = setupkvm()) == 0) panic("userinit: out of memory?"); inituvm(p->pgdir, _binary_initcode_start, (int)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); p->tf->cs = (SEG_UCODE << 3) | DPL_USER; p->tf->ds = (SEG_UDATA << 3) | DPL_USER; p->tf->es = p->tf->ds; p->tf->ss = p->tf->ds; p->tf->eflags = FL_IF; p->tf->esp = PGSIZE+4096; p->tf->eip = 4096; // beginning of initcode.S safestrcpy(p->name, "initcode", sizeof(p->name)); p->cwd = namei("/"); p->state = RUNNABLE; release(&ptable.lock); }
/** * Add class devices to list */ static void add_cdevs_to_classlist(struct sysfs_class *cls, struct dlist *list) { char path[SYSFS_PATH_MAX], *cdev_name; struct sysfs_class_device *cdev = NULL; if (cls == NULL || list == NULL) return; dlist_for_each_data(list, cdev_name, char) { if (cls->devices) { cdev = (struct sysfs_class_device *) dlist_find_custom(cls->devices, (void *)cdev_name, cdev_name_equal); if (cdev) continue; } safestrcpy(path, cls->path); safestrcat(path, "/"); safestrcat(path, cdev_name); cdev = sysfs_open_class_device_path(path); if (cdev) { if (!cls->devices) cls->devices = dlist_new_with_delete (sizeof(struct sysfs_class_device), sysfs_close_cls_dev); dlist_unshift_sorted(cls->devices, cdev, sort_list); } } }
/** * sysfs_get_class_device: get specific class device using the device's id * @cls: sysfs_class to find the device on * @name: name of the class device to look for * * Returns sysfs_class_device * on success and NULL on failure */ struct sysfs_class_device *sysfs_get_class_device(struct sysfs_class *cls, const char *name) { char path[SYSFS_PATH_MAX]; struct sysfs_class_device *cdev = NULL; if (!cls || !name) { errno = EINVAL; return NULL; } if (cls->devices) { cdev = (struct sysfs_class_device *)dlist_find_custom (cls->devices, (void *)name, cdev_name_equal); if (cdev) return cdev; } safestrcpy(path, cls->path); safestrcat(path, "/"); safestrcat(path, name); cdev = sysfs_open_class_device_path(path); if (!cdev) { dprintf("Error opening class device at %s\n", path); return NULL; } if (!cls->devices) cls->devices = dlist_new_with_delete (sizeof(struct sysfs_class_device), sysfs_close_cls_dev); dlist_unshift_sorted(cls->devices, cdev, sort_list); return cdev; }
int clone(void(*fcn)(void*), void *arg, void *stack) { int i, pid; struct proc *np; uint * sp; // ALLOCATES A NEW THREAD // // Allocate process. if((np = allocproc()) == 0) return -1; //if a thread calls clone it makes its parent the parent of the new thread if(proc->isThread == 1){ np->parent = proc->parent; *np->tf = *proc->parent->tf; np->sz = proc->parent->sz; np->pgdir = proc->parent->pgdir; } else{ np->parent = proc; *np->tf = *proc->tf; np->sz = proc->sz; np->pgdir = proc->pgdir; } np->isThread = 1; np->state = RUNNABLE; // Clear %eax so that fork returns 0 in the child. np->tf->eax = 0; pid = np->pid; for(i = 0; i < NOFILE; i++) if(proc->ofile[i]) np->ofile[i] = filedup(proc->ofile[i]); np->cwd = idup(proc->cwd); safestrcpy(np->name, proc->name, sizeof(proc->name)); //safestrcpy(np->name, "ThreadChildren", sizeof("ThreadChildren")); // Push argument strings, prepare rest of stack in ustack. sp = (uint *) ((char *)stack + PGSIZE); sp -= 2; sp[0] = 0xffffffff; // fake return PC sp[1] = (uint) arg; // Commit to the user image.s np->tf->eip = (uint) fcn; // main np->tf->esp = (uint) sp; //cprintf("[proc clone]-pid-%d\n",pid); switchuvm(np); //return pid on success not 0 yo return pid; }
/** * sysfs_get_bus_drivers: gets all drivers for bus * @bus: bus to get devices for * returns dlist of devices with success and NULL with failure */ struct dlist *sysfs_get_bus_drivers(struct sysfs_bus *bus) { struct sysfs_driver *drv; struct dlist *dirlist; char path[SYSFS_PATH_MAX], drvpath[SYSFS_PATH_MAX]; char *curdir; if (!bus) { errno = EINVAL; return NULL; } memset(path, 0, SYSFS_PATH_MAX); safestrcpy(path, bus->path); safestrcat(path, "/"); safestrcat(path, SYSFS_DRIVERS_NAME); dirlist = read_dir_subdirs(path); if (dirlist) { dlist_for_each_data(dirlist, curdir, char) { if (bus->drivers) { drv = (struct sysfs_driver *) dlist_find_custom(bus->drivers, (void *)curdir, name_equal); if (drv) continue; } safestrcpy(drvpath, path); safestrcat(drvpath, "/"); safestrcat(drvpath, curdir); drv = sysfs_open_driver_path(drvpath); if (!drv) { dprintf("Error opening driver at %s\n", drvpath); continue; } if (!bus->drivers) bus->drivers = dlist_new_with_delete (sizeof(struct sysfs_driver), sysfs_close_drv); dlist_unshift_sorted(bus->drivers, drv, sort_list); } sysfs_close_list(dirlist); } return (bus->drivers); }
/** * get_dev_attributes_list: build a list of attributes for the given device * @dev: devices whose attributes list is required * returns dlist of attributes on success and NULL on failure */ struct dlist *get_dev_attributes_list(void *dev) { DIR *dir = NULL; struct dirent *dirent = NULL; struct sysfs_attribute *attr = NULL; char file_path[SYSFS_PATH_MAX], path[SYSFS_PATH_MAX]; if (!dev) { errno = EINVAL; return NULL; } memset(path, 0, SYSFS_PATH_MAX); safestrcpy(path, ((struct sysfs_device *)dev)->path); dir = opendir(path); if (!dir) { dprintf("Error opening directory %s\n", path); return NULL; } while ((dirent = readdir(dir)) != NULL) { if (0 == strcmp(dirent->d_name, ".")) continue; if (0 == strcmp(dirent->d_name, "..")) continue; memset(file_path, 0, SYSFS_PATH_MAX); safestrcpy(file_path, path); safestrcat(file_path, "/"); safestrcat(file_path, dirent->d_name); if (!sysfs_path_is_file(file_path)) { if (((struct sysfs_device *)dev)->attrlist) { /* check if attr is already in the list */ attr = (struct sysfs_attribute *) dlist_find_custom ((((struct sysfs_device *)dev)->attrlist), (void *)dirent->d_name, attr_name_equal); if (attr) continue; else add_attribute(dev, file_path); } else attr = add_attribute(dev, file_path); } } closedir(dir); return ((struct sysfs_device *)dev)->attrlist; }