void process_pending(struct pipe *p) { struct pipes_res *res = NULL; switch(p->pending_cmd.command) { case PIPES_READ: res = pread((struct pipes_read *)&p->pending_cmd, p); break; case PIPES_SEEK: res = pseek((struct pipes_seek *)&p->pending_cmd, p, p->taskid2); break; case PIPES_GETS: res = pgets((struct pipes_gets *)&p->pending_cmd, p); break; case PIPES_GETC: res = pgetc((struct pipes_getc *)&p->pending_cmd, p); break; } if(res != NULL) { p->pending = 0; res->thr_id = p->pending_cmd.thr_id; res->command = p->pending_cmd.command; send_msg(p->taskid2, p->pending_cmd.ret_port, res); } }
void process_pipes_cmd(struct pipes_cmd *pcmd, int task) { struct pipes_res *res= NULL; struct pipe *p = NULL; // check for open if(pcmd->command == PIPES_OPENSHARED) { // create a new shared pipe struct pipe *p = (struct pipe*)malloc(sizeof(struct pipe)); p->id = get_new_pipeid(); p->type = PIPES_SHAREDPIPE; p->taskid = ((struct pipes_openshared*)pcmd)->task1; p->taskid2 = ((struct pipes_openshared*)pcmd)->task2; p->pf = NULL; p->creating_task = task; p->pending = 0; p->task1_closed = 0; p->task2_closed = 0; p->buffer = (struct pipe_buffer*)malloc(sizeof(struct pipe_buffer)); p->buffer->rcursor = p->buffer->wcursor = p->buffer->size = 0; init(&p->buffer->blocks); avl_insert(&pipes, p, p->id); res = build_response_msg(PIPESERR_OK); ((struct pipes_open_res*)res)->pipeid = p->id; } else if(pcmd->command == PIPES_OPENFILE) { // create a new file pipe struct pipe *p = (struct pipe*)malloc(sizeof(struct pipe)); char *filepath = get_string(((struct pipes_openfile*)pcmd)->path_smo); p->id = get_new_pipeid(); p->type = PIPES_FILEPIPE; p->taskid = ((struct pipes_openshared*)pcmd)->task1; p->taskid2 = -1; p->pf = fopen(filepath, (char*)((struct pipes_openfile*)pcmd)->open_mode); p->creating_task = task; p->buffer = NULL; p->pending = 0; if(p->pf != NULL) { avl_insert(&pipes, p, p->id); res = build_response_msg(PIPESERR_OK); ((struct pipes_open_res*)res)->pipeid = p->id; } else { res = build_response_msg(PIPESERR_FSERROR); free(p); } free(filepath); } else { p = (struct pipe*)avl_getvalue(pipes, ((struct pipes_close*)pcmd)->pipeid); if(p != NULL) { /* Check permissions */ switch(pcmd->command) { case PIPES_CLOSE: // a shared pipe must be closed on both ends or by the creating task if(p->type == PIPES_SHAREDPIPE) { if(task != p->taskid && task != p->taskid2 && task != p->creating_task) { res = build_response_msg(PIPESERR_ERR); } else if((task == p->taskid && p->task1_closed) || (task == p->taskid2 && p->task2_closed)) { res = build_response_msg(PIPESERR_PIPECLOSED); } } else if(p->type == PIPES_FILEPIPE && task != p->taskid) { res = build_response_msg(PIPESERR_ERR); } break; case PIPES_SEEK: case PIPES_TELL: break; case PIPES_WRITE: case PIPES_PUTS: case PIPES_PUTC: if(p->type == PIPES_SHAREDPIPE && task != p->taskid) { res = build_response_msg(PIPESERR_ERR); } break; case PIPES_READ: case PIPES_GETS: case PIPES_GETC: if(p->type == PIPES_SHAREDPIPE && task != p->taskid2) { res = build_response_msg(PIPESERR_ERR); } break; default: res = build_response_msg(PIPESERR_ERR); } if(res != NULL) { res->thr_id = pcmd->thr_id; res->command = pcmd->command; send_msg(task, pcmd->ret_port, res); return; } /* Process pipe command */ switch(pcmd->command) { case PIPES_CLOSE: res = pclose((struct pipes_close *)pcmd, p, task); if(res->ret == PIPESERR_OK) p = NULL; break; case PIPES_READ: res = pread((struct pipes_read *)pcmd, p); break; case PIPES_WRITE: res = pwrite((struct pipes_write *)pcmd, p); break; case PIPES_SEEK: res = pseek((struct pipes_seek *)pcmd, p, task); break; case PIPES_TELL: res = ptell((struct pipes_tell *)pcmd, p, task); break; case PIPES_PUTS: res = pputs((struct pipes_puts *)pcmd, p); break; case PIPES_PUTC: res = pputc((struct pipes_putc *)pcmd, p); break; case PIPES_GETS: res = pgets((struct pipes_gets *)pcmd, p); break; case PIPES_GETC: res = pgetc((struct pipes_getc *)pcmd, p); break; default: res = build_response_msg(PIPESERR_ERR); } } else { res = build_response_msg(PIPESERR_PIPECLOSED); } } if(p == NULL || (p != NULL && !(p->pending && (pcmd->command == PIPES_READ || (pcmd->command == PIPES_SEEK && task == p->taskid2) || pcmd->command == PIPES_GETS || pcmd->command == PIPES_GETC)))) { if(res == NULL) { res = build_response_msg(PIPESERR_ERR); } res->thr_id = pcmd->thr_id; res->command = pcmd->command; send_msg(task, pcmd->ret_port, res); if(res != NULL) free(res); } else { // check pending read if(p != NULL && p->pending && (pcmd->command == PIPES_WRITE || (pcmd->command == PIPES_SEEK && task == p->taskid2) || pcmd->command == PIPES_READ || pcmd->command == PIPES_PUTS || pcmd->command == PIPES_PUTC)) { // process the pending message process_pending(p); } send_msg(task, pcmd->ret_port, res); if(res != NULL) free(res); } }
void *ZipUnZipV(int fromMemory, FILE *fp, const char *fname, const char *ename, unsigned long *psize){ int reti, isdir = 0; void *ret = NULL, *cret; ZipLocalHeader lh; ZipCentralDirHeader cdh; ZipEndCentDirHeader ecd; char namebuf[256]; unsigned long usize, cmplen; z_stream z; size_t (*pread)(void *, size_t, size_t, FILE*) = fromMemory ? mread : fread; int (*pseek)(FILE *, long, int) = fromMemory ? mseek : fseek; #ifndef NDEBUG timemeas_t tm; TimeMeasStart(&tm); #endif pseek(fp, -(long)sizeof ecd, SEEK_END); pread(&ecd, sizeof ecd, 1, fp); if(ecd.signature != 0x06054B50) goto error_tag; pseek(fp, ecd.startpos, SEEK_SET); while(pread(&cdh, sizeof cdh, 1, fp)){ if(cdh.signature != 0x02014b50 || sizeof namebuf <= cdh.fnamelen) goto error_tag; pread(namebuf, cdh.fnamelen, 1, fp); namebuf[cdh.fnamelen] = '\0'; /* Null terminate to avoid partial matching */ pseek(fp, cdh.extralen, SEEK_CUR); /* skip extra field */ if(ename && (!cdh.fnamelen || pathncmp(ename, namebuf, isdir ? cmplen : cdh.fnamelen + 1))){ continue; } pseek(fp, cdh.headerpos, SEEK_SET); pread(&lh, sizeof lh, 1, fp); /* Raw format can be read without any conversion */ if(lh.method == 0){ ret = malloc(lh.csize); pseek(fp, lh.namelen + lh.extralen, SEEK_CUR); pread(ret, lh.csize, 1, fp); if(psize) *psize = lh.csize; #ifndef NDEBUG fprintf(stderr, "%s(%s) %lu/%lu=%lg%% %lgs\n", fname, ename, lh.csize, lh.usize, (double)100. * lh.csize / lh.usize, TimeMeasLap(&tm)); #endif return ret; } /* Bail if the compression algorithm is not deflate */ if(lh.method != 8) return NULL; pseek(fp, lh.namelen + lh.extralen, SEEK_CUR); cret = malloc(lh.csize); pread(cret, lh.csize, 1, fp); if(isdir){ MPOS mp; mp.org = cret; mp.cur = cret; mp.end = &mp.org[lh.csize]; ret = ZipUnZipV(1, &mp, fname, &ename[cmplen+1], psize); free(cret); return ret; } else{ ret = malloc(lh.usize); usize = lh.usize; z.zalloc = Z_NULL; z.zfree = Z_NULL; z.opaque = Z_NULL; z.next_in = Z_NULL; z.avail_in = 0; inflateInit2(&z, -15); z.next_in = cret; z.avail_in = lh.csize; z.next_out = ret; z.avail_out = usize; reti = inflate(&z, Z_NO_FLUSH); inflateEnd(&z); free(cret); if(psize) *psize = usize; } #ifndef NDEBUG fprintf(stderr, "%s(%s) %lu/%lu=%lg%% %lgs\n", fname, ename, lh.csize, lh.usize, (double)100. * lh.csize / lh.usize, TimeMeasLap(&tm)); #endif break; } error_tag: // fclose(fp); return ret; }
wavc_t *cacheWaveDataV(int fromMemory, FILE *hmmio) { MPOS mp; wavc_t *ret; struct RIFFHEADER head; LPWAVEHDR lpWaveHdr; /* HMMIO hmmio; */ HANDLE hFormat; DWORD data, dwDataSize; HANDLE hData = NULL; // handle of waveform data memory HPSTR lpData = NULL; // pointer to waveform data memory size_t (*pread)(void *, size_t, size_t, FILE*) = fromMemory ? mread : fread; int (*pseek)(FILE *, long, int) = fromMemory ? mseek : fseek; if(!pread(&head, sizeof head, 1, hmmio) || memcmp(head.ckid, "RIFF", sizeof head.ckid) || memcmp(head.fccType, "WAVE", sizeof head.fccType) || memcmp(head.fmtType, "fmt ", sizeof head.fmtType) || head.channels != 1 || head.bitsPerSample != 8){ return NULL; } pseek(hmmio, 20 + head.chunkLength, SEEK_SET); do{ pread(&data, sizeof data, 1, hmmio); if(!memcmp(&data, "data", sizeof data)) break; pread(&dwDataSize, sizeof dwDataSize, 1, hmmio); pseek(hmmio, dwDataSize, SEEK_CUR); } while(1); // Allocate and lock memory for the waveform data. if(pread(&dwDataSize, sizeof dwDataSize, 1, hmmio) <= 0){ return NULL; } ret = malloc(sizeof(wavc_t) + dwDataSize); ret->format.wFormatTag = WAVE_FORMAT_PCM; ret->format.nChannels = head.channels; ret->format.nSamplesPerSec = head.samplesPerSec; ret->format.nAvgBytesPerSec = head.bytesPerSec; ret->format.nBlockAlign = head.channels * head.bitsPerSample / 8; ret->format.wBitsPerSample = head.bitsPerSample; ret->format.cbSize = 0; #if 1 lpData = (HPSTR)&ret[1]; #else hData = GlobalAlloc(GMEM_MOVEABLE | GMEM_SHARE, dwDataSize ); if (!hData) { MessageBox(NULL, "Out of memory.", NULL, MB_OK | MB_ICONEXCLAMATION); /* mmioClose(hmmio, 0); */ fclose(hmmio); return; } if ((lpData = GlobalLock(hData)) == NULL) { MessageBox(NULL, "Failed to lock memory for data chunk.", NULL, MB_OK | MB_ICONEXCLAMATION); GlobalFree(hData); /* mmioClose(hmmio, 0); */ fclose(hmmio); return; } #endif // Read the waveform data subchunk. if(pread(lpData, 1, dwDataSize, hmmio) != dwDataSize) { MessageBox(NULL, ferror(hmmio) ? "Failed to read data chunk. Error" :feof(hmmio) ? "Failed to read data chunk. EOF" : "Failed to read data chunk.", NULL, MB_OK | MB_ICONEXCLAMATION); /* GlobalUnlock(hData); GlobalFree(hData); */ /* mmioClose(hmmio, 0); */ free(ret); return NULL; } // Allocate and lock memory for the header. #if 1 lpWaveHdr = &ret->head; #else hWaveHdr = GlobalAlloc(GMEM_MOVEABLE | GMEM_SHARE, (DWORD) sizeof(WAVEHDR)); if (hWaveHdr == NULL) { GlobalUnlock(hData); GlobalFree(hData); MessageBox(NULL, "Not enough memory for header.", NULL, MB_OK | MB_ICONEXCLAMATION); fclose(hmmio); return; } lpWaveHdr = (LPWAVEHDR) GlobalLock(hWaveHdr); if (lpWaveHdr == NULL) { GlobalUnlock(hData); GlobalFree(hData); MessageBox(NULL, "Failed to lock memory for header.", NULL, MB_OK | MB_ICONEXCLAMATION); fclose(hmmio); return; } #endif // After allocation, set up and prepare header. lpWaveHdr->lpData = lpData; lpWaveHdr->dwBufferLength = dwDataSize; lpWaveHdr->dwFlags = 0L; lpWaveHdr->dwLoops = 0L; return ret; }