//////////////////////////////////////////////////// // 功能: 把DMA中的数据送入I2S // 输入: // 输出: // 返回: // 说明: //////////////////////////////////////////////////// static void StartDmaPcmTrans(int mute, unsigned int sour) { PRESAMPLE pResample; static DWORD mute_data; pResample = &DacDevice; //判断是否能传递数据 if(!mute) { //传送PCM数据 DmaDataToAic(0,(unsigned int)sour, DAC_PCMBUF_SIZE,1); nMplayerDmaStart = 1; #ifdef DAC_SAVE_PCM kmemcpy(&dac_buf[dac_offset],(BYTE*)sour,DAC_PCMBUF_SIZE); dac_offset += DAC_PCMBUF_SIZE; if( dac_offset >= 4 * 1024 * 1024 ) dac_offset = 0; #endif mute_data = 0; } else { //传送空的数据 DmaDataToAic(0, (unsigned int)NullBuf, DAC_PCMBUF_SIZE,1); nMplayerDmaStart = 0; #ifdef DAC_SAVE_PCM kmemcpy(&dac_buf[dac_offset],(BYTE*)NullBuf,DAC_PCMBUF_SIZE); dac_offset += DAC_PCMBUF_SIZE; if( dac_offset >= 4 * 1024 * 1024 ) dac_offset = 0; #endif if( !fPause ) kdebug(mod_audio, PRINT_INFO, "MUTE: %d-%d\n", ++mute_data, fBeginDma); } }
void* loadFile(char *filename){ DirLayout *dir = searchFile(filename); UCHAR *start = kmalloc(dir->size); //コピー先確保 UCHAR *seek = start; int cl_num = dir->head_cluster; int limit = dir->size / CLUSTER_SIZE + (dir->size % CLUSTER_SIZE==0?0:1); int cnt=1; if(start == 0)return 0;//mallocできなかった while(cl_num != 0xfff){ if(cnt==INF)return 0;//FATがうまく読めてない //最後のあまりをコピー if(cnt==limit){ kmemcpy(seek,getClusterAdd(cl_num),dir->size%CLUSTER_SIZE); break; } kmemcpy(seek,getClusterAdd(cl_num),CLUSTER_SIZE); cl_num = getNextCluster(cl_num); seek += CLUSTER_SIZE; cnt++; } /* if(filename[0]=='l' && filename[1]=='i'){ asm volatile("cli"); asm volatile("mov %0,%%eax"::"r"((int)dir):"eax"); for(;;)asm volatile("hlt"); } */ return start; }
void smp_parse_configuration_table(u32 TableAddress) { T_SMP_CONFIGURATION_HEADER Header; physmem_read(TableAddress, 44, &Header); s8 OEMName[9]; kmemcpy(OEMName, Header.OEMName, 8); OEMName[8] = 0x00; s8 ProductName[13]; kmemcpy(ProductName, Header.ProductName, 12); ProductName[12] = 0x00; kprintf("[i] SMP OEM: %s\n", OEMName); kprintf("[i] SMP Product: %s\n", ProductName); kprintf("[i] SMP Base Configuration Table address: %x, length: %i bytes.\n", TableAddress, Header.BaseTableLength); if (Header.BaseTableLength > SMP_TESMP_BUFFER_LENGTH) PANIC("SMP BCT too big!"); physmem_read(TableAddress + 44, Header.BaseTableLength - 44, g_EntriesBuffer); u32 EntryAddress = 0; g_SMP.NumCPUs = 0; g_SMP.NumIOAPICs = 0; while (EntryAddress < Header.BaseTableLength - sizeof(T_SMP_CONFIGURATION_HEADER)) { u8 EntryType = g_EntriesBuffer[EntryAddress]; switch (EntryType) { case 0x00: EntryAddress += smp_parse_cpu(EntryAddress); break; case 0x01: EntryAddress += smp_parse_bus(EntryAddress); break; case 0x02: EntryAddress += smp_parse_ioapic(EntryAddress); break; case 0x03: EntryAddress += smp_parse_io_interrupt(EntryAddress); break; case 0x04: EntryAddress += smp_parse_local_interrupt(EntryAddress); break; } } }
static struct dirent *get_dirent(char *filepath, struct fat_part_desc *desc, int current_cluster, int dircount) { struct dirent *dir, *ret; char cl[desc->bootrecord.spc * desc->bootrecord.bps]; char *ptr, *name; name = filepath + 1; ptr = kstrchr(name, '/'); while (ptr != NULL) { *ptr = 0; dir = search_dir(name, desc, current_cluster, dircount, cl); if (dir != NULL) { name = ptr + 1; *ptr = '/'; ptr = kstrchr(name, '/'); current_cluster = (dir->cluster_hi << 16) | dir->cluster_lo; } else { /* file does not exist! */ *ptr = '/'; return 0; } } /* check current directory for 'name' */ dir = search_dir(name, desc, current_cluster, dircount, cl); if (dir == NULL) return NULL; ret = kmalloc(sizeof(struct dirent)); kmemcpy(ret, dir, sizeof(struct dirent)); return ret; }
void pcnet_receive(struct pcnet *l) { size_t len; uint8_t *buf; struct sockbuf *sb; while((l->rx_descs[l->cur_rx].status & 0x8000) == 0) { if(!(l->rx_descs[l->cur_rx].status & 0x4000) && (l->rx_descs[l->cur_rx].status & 0x0300) == 0x0300) { len = l->rx_descs[l->cur_rx].flags2 & 0xFFFF; buf = l->rx_buffers[l->cur_rx]; sb = sockbuf_alloc(l->dev, len); kmemcpy(sb->data, buf, len); network_received(sb); } l->rx_descs[l->cur_rx].addr = V2P(l->rx_buffers[l->cur_rx]); l->rx_descs[l->cur_rx].status = 0x8000; l->rx_descs[l->cur_rx].len = -2048; l->rx_descs[l->cur_rx].flags2 = 0; l->cur_rx++; if(l->cur_rx == 8) l->cur_rx = 0; } }
void vbeint10(void) { #if (SMP) long id = k_curcpu->id; #endif static int first = 1; uint64_t *gdt; struct m_farptr *farptr; if (first) { kmemcpy((void *)BOOTREALBASE, &realstart, (unsigned long)&realend - (unsigned long)&realstart); first = 0; } realint10(); #if (SMP) gdt = &kerngdt[id][0]; #else gdt = kerngdt; #endif farptr = &realgdtptr; farptr->lim = NGDT * sizeof(uint64_t) - 1; farptr->adr = (uint32_t)gdt; gdtinit(farptr); return; }
/** * Intializes an ELF32-TASK * TODO: Check Length of image * TODO: US-Mode * @param image The image * @param pri Priority */ void* initELF(void* image, int pri, size_t size, char *args) { /* * TODO Wir muessen eigentlich die Laenge vom Image pruefen, damit wir bei * korrupten ELF-Dateien nicht ueber das Dateiende hinauslesen. */ DEBUG_MSG("ELF: Init ELF32-File..."); struct elf_header* header = image; struct elf_program_header* ph; int i; /* Ist es ueberhaupt eine ELF-Datei? */ if (header->magic != ELF_MAGIC) { dbg(false); kprintf("Keine gueltige ELF-Magic!\n"); return 0; } /* * Alle Program Header durchgehen und den Speicher an die passende Stelle * kopieren. * * TODO Wir erlauben der ELF-Datei hier, jeden beliebigen Speicher zu * ueberschreiben, einschliesslich dem Kernel selbst. */ ph = (struct elf_program_header*) (((char*) image) + header->ph_offset); for (i = 0; i < 2/*header->ph_entry_count*/; i++, ph++) { void* dest = (void*) ph->virt_addr; void* src = ((char*) image) + ph->offset; /* Nur Program Header vom Typ LOAD laden */ if (ph->type != 1) continue; kmemset(dest, 0, ph->mem_size); kmemcpy(dest, src, ph->file_size); } //size /= PAGE_SIZE; pageDir_t page = vmmCreateContext(); void *paddr = pmm_malloc(PAGE_SIZE); kmemset((void*) page, 0, PAGE_SIZE); for(i=0; i<size;i +=PAGE_SIZE) { vmmMapPage( page, (void*) 0xfffff000+i, paddr+i, USER_PRV ); //0xfffff000 } vmmActivateContext( page ); initTask( (void *)header->entry, pri, page, args); dbg(true); return (void*) header->entry; }
int fat_init(struct ptable_entry *part, struct fat_part_desc *desc) { char tmpb[512]; block_read_lba(part->start_lba, tmpb); kmemcpy(&desc->bootrecord, tmpb, sizeof(struct bpb)); if (kstrcmp(desc->bootrecord.OEM_ID, "mkdosfs")) return 0; /* error */ desc->root_cyl_start_lba = part->start_lba + desc->bootrecord.reserved_sectors + fat_sectors(&desc->bootrecord); desc->type = fat_version(&desc->bootrecord); desc->fat_start_lba = part->start_lba + desc->bootrecord.reserved_sectors; if (desc->type == 32) { struct fat32_ebpb *eb = (struct fat32_ebpb *)&desc->bootrecord.ebpb[0]; desc->root_cluster = eb->root_cluster; } else { desc->root_cluster = 2; } desc->fat = kmalloc(desc->bootrecord.sectors_pr_FAT * sizeof(long *)); if (desc->fat == NULL) return 1; return 1; }
int e1000_sendpkt(const u8 *pkt, u32 len, struct netdev *netdev) { u32 tdh; struct e1000_device *dev; int tx_avl; struct e1000_tx_desc *txdesc; dev = (struct e1000_device *)netdev->vendor; tdh = mmio_read32(dev->mmio, E1000_REG_TDH); tx_avl = dev->tx_bufsz - ((dev->tx_bufsz - tdh + dev->tx_tail) % dev->tx_bufsz); if ( tx_avl > 0 ) { /* Check the head of TX ring buffer */ txdesc = (struct e1000_tx_desc *) (dev->tx_base + (dev->tx_tail % dev->tx_bufsz) * sizeof(struct e1000_tx_desc)); kmemcpy((void *)txdesc->address, pkt, len); txdesc->length = len; txdesc->sta = 0; txdesc->css = 0; txdesc->cso = 0; txdesc->special = 0; txdesc->cmd = (1<<3) | (1<<1) | 1; dev->tx_tail = (dev->tx_tail + 1) % dev->tx_bufsz; mmio_write32(dev->mmio, E1000_REG_TDT, dev->tx_tail); return len; } return -1; }
//////////////////////////////////////////////////// // 功能: // 输入: // 输出: // 返回: // 说明: //////////////////////////////////////////////////// int MediaSrvRegistCallback(int type, DWORD device, PMEDIA_CALLBACK callback) { PLIST n; PLIST head; PCALLBACK_LINK check; PCALLBACK_LINK link; // 申请节点,并初始化 link = kmalloc(sizeof(CALLBACK_LINK)); if(link == NULL) return -1; kmemcpy(&link->Callback, callback, sizeof(MEDIA_CALLBACK)); link->Type = type; link->Device = device; ListInit(&link->Link); // 检查设备是否已经注册 head = &MediaCallbackList; for(n=ListFirst(head); n!=head; n=ListNext(n)) { check = ListEntry(n, CALLBACK_LINK, Link); if(&check->Callback == callback) { kfree(link); return -1; } } ListInsert(&MediaCallbackList, &link->Link); return 0; }
int MediaSrvGetName(HANDLE hmedia, char *name, int max) #endif { PMEDIA_OBJECT obj; int ret; kMutexWait(hMediaMutex); obj = (PMEDIA_OBJECT)HandleGet(hmedia, MEDIA_MAGIC); if(obj == NULL) { kMutexRelease(hMediaMutex); return -1; } ret = kstrlen(obj->MediaInfo); if(ret <= max) { kstrcpy(name, obj->MediaInfo); } else { kmemcpy(name, obj->MediaInfo, max); ret = max; } kMutexRelease(hMediaMutex); return ret; }
//////////////////////////////////////////////////// // 功能: // 输入: // 输出: // 返回: // 说明: //////////////////////////////////////////////////// static int DacPcmQueue(short *dst, short *src, int *outsize, int *insize, int chs) { short pcm; int rsize, wsize; int cpysize; // 局部变量初始化 rsize = *insize; wsize = *outsize; // 检查是否为单声道数据 if(chs == 1) { while((rsize>0) && (wsize>0)) { pcm = *src++; *dst++ = pcm; *dst++ = pcm; wsize -= 2*sizeof(short); rsize -= sizeof(short); } *outsize -= wsize; *insize -= rsize; return *insize; } cpysize = (rsize > wsize) ? wsize : rsize; kmemcpy(dst, src, cpysize); *insize = cpysize; *outsize = cpysize; return cpysize; }
int e1000_recvpkt(u8 *pkt, u32 len, struct netdev *netdev) { u32 rdh; struct e1000_device *dev; int rx_que; struct e1000_rx_desc *rxdesc; int ret; dev = (struct e1000_device *)netdev->vendor; rdh = mmio_read32(dev->mmio, E1000_REG_RDH); rx_que = (dev->rx_bufsz - dev->rx_tail + rdh) % dev->rx_bufsz; if ( rx_que > 0 ) { /* Check the head of RX ring buffer */ rxdesc = (struct e1000_rx_desc *) (dev->rx_base + (dev->rx_tail % dev->rx_bufsz) * sizeof(struct e1000_rx_desc)); ret = len < rxdesc->length ? len : rxdesc->length; kmemcpy(pkt, (void *)rxdesc->address, ret); mmio_write32(dev->mmio, E1000_REG_RDT, dev->rx_tail); dev->rx_tail = (dev->rx_tail + 1) % dev->rx_bufsz; return ret; } return -1; }
uint8_t pluginloader_addPluginToList(struct pluginloader_t* loader, struct loaderplugin_t* pluginEntry) { if (!loader || !pluginEntry) return false; // CHeck if we have a plugin list at all if (!loader->pluginList || !loader->pluginCount) { // Calculate the new size (sizeof(pointer) * however many in list) size_t newListSize = sizeof(pluginEntry) * 1; struct loaderplugin_t** newList = (struct loaderplugin_t**)kmalloc(newListSize); if (!newList) { WriteLog(LL_Error, "could not allocate new list"); return false; } // Assign our new entry newList[0] = pluginEntry; // Assign our new plugin list loader->pluginList = newList; loader->pluginCount = 1; return true; } // Am I bat-shit insane for this?... probably // This screams, I need locks // If there exist a list already add a new entry struct loaderplugin_t** oldList = loader->pluginList; size_t oldPluginCount = loader->pluginCount; size_t oldListSize = sizeof(struct loaderplugin_t*) * oldPluginCount; size_t newPluginCount = oldPluginCount + 1; size_t newListSize = sizeof(struct loaderplugin_t*) * (newPluginCount); struct loaderplugin_t** newList = (struct loaderplugin_t**)kmalloc(newListSize); if (!newList) { WriteLog(LL_Error, "could not allocate new list"); return false; } kmemset(newList, 0, newListSize); // Copy over the old list kmemcpy(newList, oldList, oldListSize); // Add our final entry newList[oldPluginCount] = pluginEntry; // Assign everything loader->pluginList = newList; loader->pluginCount = newPluginCount; return true; }
static void dict_ensure_size(dict *d, int count) { int c = (d->count+3)/4; if ((count+3)/4 == c) return; dict_item* dip = kmalloc(((count+3)/4)*sizeof(dict_item)); kmemcpy(dip, d->items, sizeof(dict_item)*count); kfree(d->items); d->items = dip; }
void dict_add(dict *d, const char* name, void* value, int size) { dict_ensure_size(d, d->count+1); d->items[d->count].name = kmalloc(kstrlen(name)+1); d->items[d->count].value = kmalloc(size); kstrcpy(d->items[d->count].name, name); kmemcpy(d->items[d->count].value, value, size); d->count++; }
/* * Gets tty settings. */ PRIVATE int tty_gets(struct tty *tty, struct termios *termiosp) { /* Invalid termios pointer. */ if (!chkmem(termiosp, sizeof(struct termios), MAY_WRITE)) return (-EINVAL); kmemcpy(termiosp, &tty->term, sizeof(struct termios)); return (0); }
/* * Reads a block from a RAM disk device. */ PRIVATE int ramdisk_readblk(unsigned minor, buffer_t buf) { addr_t ptr; ptr = ramdisks[minor].start + (buffer_num(buf) << BLOCK_SIZE_LOG2); kmemcpy(buffer_data(buf), (void *)ptr, BLOCK_SIZE); return (0); }
/* we want to call this gadget: FFFFFFF0071E1998 MSR #0, c0, c2, #2, X8 ; [>] MDSCR_EL1 (Monitor Debug System Control Register) FFFFFFF0071E199C ISB // this a workaround for some errata... FFFFFFF0071E19A0 B loc_FFFFFFF0071E19F8 ... FFFFFFF0071E19F8 BL _ml_set_interrupts_enabled FFFFFFF0071E19FC ADD SP, SP, #0x220 FFFFFFF0071E1A00 LDP X29, X30, [SP,#0x20+var_s0] FFFFFFF0071E1A04 LDP X20, X19, [SP,#0x20+var_10] FFFFFFF0071E1A08 LDP X28, X27, [SP+0x20+var_20],#0x30 FFFFFFF0071E1A0C RET lets just use the ERET case to get full register control an run that on a little ROP stack which then returns to thread_exception_return */ void set_MDSCR_EL1_KDE(mach_port_t target_thread_port) { /* this state will be restored by an eret */ arm_context_t eret_return_state = {0}; // allocate a stack for the rop: //uint64_t rop_stack_kern_base = kmem_alloc_wired(0x4000); uint64_t rop_stack_kern_base = early_kalloc(0x1000); uint64_t rop_stack_kern_middle = rop_stack_kern_base + 0xc00; eret_return_state.ss.ss_64.sp = rop_stack_kern_middle; uint64_t rop_stack_kern_popped_base = rop_stack_kern_middle + 0x220; // x28, x27, x20, x19, fp, lr uint64_t popped_regs[] = {0, 0, 0, 0, 0x414243444546, ksym(KSYMBOL_THREAD_EXCEPTION_RETURN)}; // directly return back to userspace after this kmemcpy(rop_stack_kern_popped_base, (uint64_t)popped_regs, sizeof(popped_regs)); #define MDSCR_EL1_KDE (1<<13) eret_return_state.ss.ss_64.x[8] = MDSCR_EL1_KDE; // the target place to eret to eret_return_state.ss.ss_64.pc = ksym(KSYMBOL_SET_MDSCR_EL1_GADGET); // we want to return on to SP0 and to EL1 // A,I,F should still be masked, D unmasked (here we could actually mask D?) #define SPSR_A (1<<8) #define SPSR_I (1<<7) #define SPSR_F (1<<6) #define SPSR_EL1_SP0 (0x4) eret_return_state.ss.ss_64.cpsr = SPSR_A | SPSR_I | SPSR_F | SPSR_EL1_SP0; //uint64_t eret_return_state_kern = kmem_alloc_wired(sizeof(arm_context_t)); uint64_t eret_return_state_kern = early_kalloc(sizeof(arm_context_t)); kmemcpy(eret_return_state_kern, (uint64_t)&eret_return_state, sizeof(arm_context_t)); // make the arbitrary call kcall(ksym(KSYMBOL_X21_JOP_GADGET), 2, eret_return_state_kern, ksym(KSYMBOL_EXCEPTION_RETURN)); printf("returned from trying to set the KDE bit\n"); // free the stack we used: //kmem_free(rop_stack_kern_base, 0x4000); }
void scroll() { int i; for (i = 1; i < CON_ROWS; i++) { kmemcpy(cur_c->buffer + ((i - 1) * CON_COLUMNS), cur_c->buffer + (i * CON_COLUMNS), CON_COLUMNS); } kmemset(cur_c->buffer + ((CON_ROWS - 1) * CON_COLUMNS), 0, CON_COLUMNS); }
void add_handler(u_int16_t offset, void (*handler)(void)) { union uptr hptr = { .vp = handler }; void *idtEntry = &(idt[offset]); kmemcpy(idtEntry, (void *)(&_idt_interrupt_template), sizeof(interrupt_desc_t)); idt[offset].offset_0_15 = hptr.w[0]; idt[offset].offset_16_31 = hptr.w[1]; #ifdef DEBUG dump_idt_entry(offset); #endif }
void vbeint10(struct realregs *regs) { static int first = 1; if (first) { kmemcpy((void *)KERNREALBASE, &realstart, (unsigned long)&realend - (unsigned long)&realstart); first = 0; } #if 0 kmemcpy((void *)(KERNREALSTK - sizeof(struct realregs)), regs, sizeof(struct realregs)); #endif realint10(); gdtinit(); return; }
u8 smp_parse_bus(u32 EntryAddress) { T_SMP_ENTRY_BUS *Bus = (T_SMP_ENTRY_BUS *)&g_EntriesBuffer[EntryAddress]; s8 Name[7]; kmemcpy(Name, Bus->BusType, 6); Name[6] = 0x00; kprintf(" Bus #%i, %s\n", Bus->BusID, Name); return 8; }
static void scroll() { int j; kmemcpy( screen, screen + WIDTH*2, (HEIGHT-1) * WIDTH * 2 ); for ( j = 0; j < (WIDTH * 2); j += 2 ) { screen[ (HEIGHT - 1) * WIDTH * 2 + j ] = ' '; screen[ (HEIGHT - 1) * WIDTH * 2 + j + 1 ] = SCREEN_ATTR; } }
void rtl_receive(struct rtl8139 *rtl) { uint16_t status, len; int16_t offset; struct sockbuf *sb; while(!(rtl_inw(rtl, CMD) & 0x1)) { //now check the rx_status from the packet status = *(uint16_t *)(rtl->rx_buffer + rtl->rx_offset); len = *(uint16_t *)(rtl->rx_buffer + rtl->rx_offset + 2); if(status & 0x1) { // printf("received packet! status %X len %X\n", status, len); //need to have function that allocates this for us sb = sockbuf_alloc(rtl->dev,len); if(sb == NULL) { printf("out of memory error in %s\n",__func__); break; } //have to account for wrapping the buffer offset = rtl->rx_offset + 4 + len - RX_BUF_LEN; if(offset < 0) offset = 0; kmemcpy(sb->data, rtl->rx_buffer + rtl->rx_offset + 4, len - offset); //uintptr_t off2 = len - offset; kmemcpy(sb->data + (len - offset), rtl->rx_buffer, offset); network_received(sb); }else{ printf("receive error\n"); } rtl->rx_offset = ((rtl->rx_offset + 3 + 4 + len) & ~3) % RX_BUF_LEN; rtl_outw(rtl, 0x38, rtl->rx_offset -16);//set receive pointer } }
/* * Writes a block to a RAM disk device. */ PRIVATE int ramdisk_writeblk(unsigned minor, buffer_t buf) { addr_t ptr; ptr = ramdisks[minor].start + (buffer_num(buf) << BLOCK_SIZE_LOG2); kmemcpy((void *)ptr, buffer_data(buf), BLOCK_SIZE); buffer_dirty(buf, 0); brelse(buf); return (0); }
/* * Reads from a regular file. */ PUBLIC ssize_t file_read(struct inode *i, void *buf, size_t n, off_t off) { char *p; /* Writing pointer. */ size_t blkoff; /* Block offset. */ size_t chunk; /* Data chunk size. */ block_t blk; /* Working block number. */ struct buffer *bbuf; /* Working block buffer. */ p = buf; inode_lock(i); /* Read data. */ do { blk = block_map(i, off, 0); /* End of file reached. */ if (blk == BLOCK_NULL) goto out; bbuf = bread(i->dev, blk); blkoff = off % BLOCK_SIZE; /* Calculate read chunk size. */ chunk = (n < BLOCK_SIZE - blkoff) ? n : BLOCK_SIZE - blkoff; if ((off_t)chunk > i->size - off) { chunk = i->size - off; if (chunk == 0) { brelse(bbuf); goto out; } } kmemcpy(p, (char *)bbuf->data + blkoff, chunk); brelse(bbuf); n -= chunk; off += chunk; p += chunk; } while (n > 0); out: inode_touch(i); inode_unlock(i); return ((ssize_t)(p - (char *)buf)); }
/* * Writes to a regular file. */ PUBLIC ssize_t file_write(struct inode *i, const void *buf, size_t n, off_t off) { const char *p; /* Reading pointer. */ size_t blkoff; /* Block offset. */ size_t chunk; /* Data chunk size. */ block_t blk; /* Working block number. */ struct buffer *bbuf; /* Working block buffer. */ p = buf; inode_lock(i); /* Write data. */ do { blk = block_map(i, off, 1); /* End of file reached. */ if (blk == BLOCK_NULL) goto out; bbuf = bread(i->dev, blk); blkoff = off % BLOCK_SIZE; chunk = (n < BLOCK_SIZE - blkoff) ? n : BLOCK_SIZE - blkoff; kmemcpy((char *)bbuf->data + blkoff, buf, chunk); bbuf->flags |= BUFFER_DIRTY; brelse(bbuf); n -= chunk; off += chunk; p += chunk; /* Update file size. */ if (off > i->size) { i->size = off; i->flags |= INODE_DIRTY; } } while (n > 0); out: inode_touch(i); inode_unlock(i); return ((ssize_t)(p - (char *)buf)); }
void pluginloader_init(struct pluginloader_t* loader) { if (!loader) return; // Initialize all fields loader->pluginList = NULL; loader->pluginCount = 0; loader->pluginDirectory = NULL; // Get the currently configured framework plugin path char* frameworkPluginPath = gFramework->pluginsPath; if (!frameworkPluginPath) { WriteLog(LL_Error, "could not initialize pluginloader, plugin path not set"); return; } // Calculate the path length // TODO: Unhack this size_t pluginPathLength = strlen(frameworkPluginPath); if (pluginPathLength == 0 || pluginPathLength > 260) { WriteLog(LL_Error, "path length is either zero, or > 260"); return; } // Update the length loader->pluginDirectoryLength = pluginPathLength; // Allocate space for the plugin path char* pluginPath = (char*)kmalloc(pluginPathLength + 1); if (!pluginPath) { WriteLog(LL_Error, "could not allocate space for plugin path."); return; } kmemset(pluginPath, 0, pluginPathLength + 1); // Copy over our string kmemcpy(pluginPath, frameworkPluginPath, pluginPathLength); loader->pluginDirectory = pluginPath; // Assign our plugin loader params gLoaderPluginInit.framework = gFramework; gLoaderPluginInit.kernelBase = gKernelBase; gLoaderPluginInit.logger = gLogger; }
//指定アドレスにファイルをロード void* loadFileToMem(void *add,char *filename){ DirLayout *dir = searchFile(filename); UCHAR *start = add; //コピー先確保 UCHAR *seek = start; int cl_num = dir->head_cluster; int limit = dir->size / CLUSTER_SIZE + (dir->size % CLUSTER_SIZE==0?0:1); int cnt=1; if(start == 0)return 0;//mallocできなかった while(cl_num != 0xfff){ if(cnt==INF)return 0;//FATがうまく読めてない //最後のあまりをコピー if(cnt==limit){ kmemcpy(seek,getClusterAdd(cl_num),dir->size%CLUSTER_SIZE); break; } kmemcpy(seek,getClusterAdd(cl_num),CLUSTER_SIZE); cl_num = getNextCluster(cl_num); seek += CLUSTER_SIZE; cnt++; } return start; }