static DWORD load_header (void) /* 0:Invalid format, 1:I/O error, >=1024:Number of samples */ { DWORD sz, f; BYTE b, al = 0; if (pf_read(Buff, 12, &rb)) return 1; /* Load file header (12 bytes) */ if (rb != 12 || LD_DWORD(Buff+8) != FCC('W','A','V','E')) return 0; for (;;) { wdt_reset(); pf_read(Buff, 8, &rb); /* Get Chunk ID and size */ if (rb != 8) return 0; sz = LD_DWORD(&Buff[4]); /* Chunk size */ switch (LD_DWORD(&Buff[0])) { /* Switch by chunk ID */ case FCC('f','m','t',' ') : /* 'fmt ' chunk */ if (sz & 1) sz++; /* Align chunk size */ if (sz > 100 || sz < 16) return 0; /* Check chunk size */ pf_read(Buff, sz, &rb); /* Get content */ if (rb != sz) return 0; if (Buff[0] != 1) return 0; /* Check coding type (LPCM) */ b = Buff[2]; if (b != 1 && b != 2) return 0; /* Check channels (1/2) */ GPIOR0 = al = b; /* Save channel flag */ b = Buff[14]; if (b != 8 && b != 16) return 0; /* Check resolution (8/16 bit) */ GPIOR0 |= b; /* Save resolution flag */ if (b & 16) al <<= 1; f = LD_DWORD(&Buff[4]); /* Check sampling freqency (8k-48k) */ if (f < 8000 || f > 48000) return 4; OCR0A = (BYTE)(F_CPU / 8 / f) - 1; /* Set sampling interval */ break; case FCC('d','a','t','a') : /* 'data' chunk */ if (!al) return 0; /* Check if format is valid */ if (sz < 1024 || (sz & (al - 1))) return 0; /* Check size */ if (Fs.fptr & (al - 1)) return 0; /* Check word alignment */ return sz; /* Start to play */ case FCC('D','I','S','P') : /* 'DISP' chunk */ case FCC('L','I','S','T') : /* 'LIST' chunk */ case FCC('f','a','c','t') : /* 'fact' chunk */ if (sz & 1) sz++; /* Align chunk size */ pf_lseek(Fs.fptr + sz); /* Skip this chunk */ break; default : /* Unknown chunk */ return 0; } } return 0; }
void Map_Read(uint8_t layer, int x, int y, uint8_t orientation) { WORD bytesRead; #if REMOUNT_ON_READ pf_mount(&FileSystem); pf_open("map.dat"); #endif if(orientation == MapRead_Horizontal) { pf_lseek(sizeof(Map_Header_t) + ((2 * layer) * Map_Header.width * Map_Header.height) + (y * Map_Header.width + x)); } else { pf_lseek(sizeof(Map_Header_t) + ((2 * layer + 1) * Map_Header.width * Map_Header.height) + (x * Map_Header.height + y)); } pf_read(Map_ReadBuffer, MAP_READ_LENGTH, &bytesRead); #if REMOUNT_ON_READ pf_mount(NULL); #endif #if 0 Map_Header.width = 128; Map_Header.height = 128; if(orientation == MapRead_Horizontal) { for(int n = 0; n < MAP_READ_LENGTH; n++) { Map_ReadBuffer[n] = (y % 3) == 0 || ((x + n) % 3) == 0 ? 1 : 0; } } else { for(int n = 0; n < MAP_READ_LENGTH; n++) { Map_ReadBuffer[n] = ((y + n) % 3) == 0 || ((x) % 3) == 0 ? 1 : 0; } } #endif }
tBool play() { bufferPlayed = 0; bufferToDownload = 0; sample = 0; totalPlayed = 0; refil = FALSE; bytesReaded = 0; tU32 i = 0; pf_lseek(ws2.byteToOmmit); //wypełniamy na sam początek czymś do { rc = pf_read(buffer[i], sizeof(buffer[i]), &bytesReaded); i++; } while (i < BUFFCOUNT && !rc && bytesReaded); tU32 uplynelo = 0; tU32 czasCalkowity = ws2.subChunkSize / ws1.byteRate; //ilość próbek przez prędkosć odtwarzania tU32 pozostalo = 0; while (totalPlayed < ws2.subChunkSize) { if (sample >= (BUFFSIZE)) { sample = 0; bufferToDownload = bufferPlayed++; refil = TRUE; } if (bufferPlayed >= BUFFCOUNT) bufferPlayed = 0; if (ws1.bitsPerSample == 8) DACR = buffer[bufferPlayed][sample++] << 5; else if (ws1.bitsPerSample == 16) DACR = ((buffer[bufferPlayed][sample++] << 8) + (buffer[bufferPlayed][sample++])) << 5; if (refil) { //uzupełnij bufor nawet jak zapauzowane rc = pf_read(buffer[bufferToDownload], sizeof(buffer[bufferToDownload]), &bytesReaded); refil = FALSE; } else if (refil == FALSE) { if (totalPlayed % ws1.byteRate != 0) sleep(1000000 / (ws1.byteRate + 2500)); //trzeba przyśpieszyć mimo wszystko o jakieś 2500 próbek //ekran bowiem daje za duże opóźnienia :/ i tak to nie jest //doskonałe //gdy odczyt z karty, to on służy za opóxnienie, więc nie czekaj } totalPlayed++; } return TRUE; }
void SD_::init() { #ifdef SKIPBLANKSD this->WorkingSDCard = true; while ( ! check( pf_mount(&this->SDCard) ) ); while ( ! check( pf_open("data.txt") )); this->SDOffset = 0; while ( ! check( pf_lseek(this->SDOffset) )); WORD written; while ( ! check (pf_write(0,0,&written)); if( WorkingSDCard ) { char InputBuffer[512]; WORD size; while(true) { pf_read(&InputBuffer, 512, &size); if((InputBuffer[0] == '%' && InputBuffer[1] == '$') || (InputBuffer[1] == '%' && InputBuffer[0] == '$')) { this->SDOffset += 512; pf_lseek(this->SDOffset); return; } this->SDOffset += 512; pf_lseek(this->SDOffset); } } #else this->TimeStamp = 0; WorkingSDCard = true; while ( ! check( pf_mount(&this->SDCard) )); while ( ! check( pf_open("data.txt") )); this->SDOffset = 0; while ( ! check( pf_lseek(this->SDOffset) )); #endif }
static DWORD load_header (void) /* 0:Invalid format, 1:I/O error, >1:Number of samples */ { DWORD sz; if (pf_read(Buff1, 12, &rb)) return 1; /* Load file header (12 bytes) */ if (rb != 12 || LD_DWORD(Buff1+8) != FCC('W','A','V','E')) return 0; for (;;) { pf_read(Buff1, 8, &rb); /* Get Chunk ID and size */ if (rb != 8) return 0; sz = LD_DWORD(&Buff1[4]); /* Chunk size */ switch (LD_DWORD(&Buff1[0])) { /* FCC */ case FCC('f','m','t',' ') : /* 'fmt ' chunk */ if (sz > 100 || sz < 16) return 0; /* Check chunk size */ pf_read(Buff1, sz, &rb); /* Get content */ if (rb != sz) return 0; if (Buff1[0] != 1) return 0; /* Check coding type (1) */ if (Buff1[2] != 1 && Buff1[2] != 2) /* Check channels (1/2) */ return 0; if (Buff1[14] != 8 && Buff1[14] != 16) /* Check resolution (8/16) */ return 0; OCR0A = (BYTE)(F_CPU/8/LD_WORD(&Buff1[4]))-1; /* Sampling freq */ break; case FCC('d','a','t','a') : /* 'data' chunk (start to play) */ return sz; case FCC('L','I','S','T') : /* 'LIST' chunk (skip) */ case FCC('f','a','c','t') : /* 'fact' chunk (skip) */ pf_lseek(Fs.fptr + sz); break; default : /* Unknown chunk (error) */ return 0; } } return 0; }
// ****************** funkcja P L A Y ******************************** static UINT play ( const char *fn ) { FRESULT res; if ((res = pf_open(fn)) == FR_OK) { pf_lseek(44); TMR_START; // start Timera0 (samplowanie) pf_read(&buf[0][0], BUF_SIZE , &rb); // za³aduj pierwsz¹ czêœæ bufora pf_read(&buf[1][0], BUF_SIZE , &rb); // za³aduj drug¹ czêœæ bufora //TMR_START; // start Timera0 (samplowanie) while(1) { if( can_read ) { // jeœli flaga ustawiona w obs³udze przerwania pf_read(&buf[ nr_buf ^ 0x01 ][0], BUF_SIZE , &rb); // odczytaj kolejny bufor if( rb < BUF_SIZE ) break; // jeœli koniec pliku przerwij pêtlê while(1) can_read = 0; } if (playstop==1) //przerwanie odtwarzania { playstop=0; break; } if (ButtonPressed(0, PIND, 7, 30000) && buttondisable==0) //aktywowanie sekwencji POWER DOWN { buttondisable=1; shutdown=1; playstop=1; breakdisablehigh=1; breakdisablelow=0; } } TMR_STOP; // wy³¹czenie Timera0 (samplowania) } return res; }
int load_dtb(char *name, void *dest, int max_bytes) { #if CONFIG_DEVTREE == 1 FRESULT res = FR_OK; unsigned int len; unsigned long bytes_read; res = pf_open(name); if (res != FR_OK) { putstr("DTB not found\n"); goto err; } char str[32]; str[0] = '\0'; _strcat(str, "Open "); _strcat(str, name); _strcat(str, " OK"); _strcat(str, "\n"); putstr(str); len = pf_size(); if (len > max_bytes || len == 0) { putstr("Invalid DTB length\n"); goto err; } res = pf_lseek(0); if (res != FR_OK) { putstr("DTB lseek(0) failed"); goto err; } res = pf_read_long(dest, len, &bytes_read); if (res != FR_OK) { putstr("DTB read failed"); goto err; } putstr("Loaded DTB\n"); return 0; err: putstr("Failed to load DTB\n"); return -1; #else return -1; #endif }
int _lseek_r (struct _reent *r, int fd, int ptr, int dir) { (void)r; if(fd>2 && file_open[fd-3]) { #ifdef MEDIA_DRIVE _drive_num = fd == 3 ? 0 : 1; #endif if(dir==SEEK_CUR) { ptr += fat[fd-3].fptr; } else if (dir==SEEK_END) { ptr += fat[fd-3].fsize; } pf_switchfile(&fat[fd-3]); int res=pf_lseek(ptr); if(res==FR_OK) { return fat[fd-3].fptr; } } errno=EINVAL; return -1; }
void PrintImage(char *fileName) { OpenFile(fileName); uint16_t i; uint8_t dataRow[LCD_BYTES_PER_ROW]; pf_lseek(fileHeader.bfOffBits); LCDInitializeDataSend(); for(i = 0; i < LCD_HEIGHT_PIXELS; i++) { pf_read(dataRow, LCD_BYTES_PER_ROW, &br); if (br != LCD_BYTES_PER_ROW) { HollyFuckHappened(); } LCDFillRow(dataRow); } LCDFinishDataSend(); }
FRESULT PFFS::lseek ( DWORD ofs /* File pointer from top of file */ ) { return pf_lseek(ofs); }
void FileSeek(uint32_t pos) { ++fileStateVersion; if (pf_lseek(pos) != FR_OK) ERRORreturn("FileSeek Failure"); }
int main(void) { lcd_init(); ds1307_init(); adc_init(); timer_init(); asm("sei"); /* //test lcd_str("Hello, World"); lcd_gotoxy(1,0); lcd_str("by shtomik"); _delay_ms(1000); lcd_clr(); lcd_str("after clr");*/ start_t(); //test ds1307_setdate(12, 12, 31, 23, 01, 35); //смонтировать microSD res = pf_mount(&fs); if(res == FR_OK) { //диск смонтирован и мы продолжаем работу if(pf_open("test.txt") == FR_OK) { //открыли файл в корне test.txt //... pf_lseek(0); //заполняем буффер, надо набрать 512 байт инфы и писать //иначе будет много лишних пробелов //sprintf(buff, "%s\n%s", "Hello,World!", "by_sht"); //записываем его на карту pf_write(buff, 512, &br); //финализируем запись pf_write(NULL, 0, &br); pf_lseek(512); pf_write(buff, 512, &br); //финализируем запись pf_write(NULL, 0, &br); lcd_clr(); lcd_str("ok"); } else { //file not found or ... lcd_str("file not found"); } //демонтируем диск передав функции нулевой указатель pf_mount(NULL); lcd_clr(); lcd_str("file write"); } else { //не удалось смонтировать диск lcd_clr(); lcd_str("not flash"); } while( 1 ) { ; } return 0; }
void tft_puts_P( int x, int y, char * s, uint32_t color, uint32_t bk_color ) { y+=frame_ptr; if( !currentFont.filename ) { tft_mputs_P(x,y, s, color, bk_color); return; } #if USE_PETIT_FAT == 0 else return; #endif #if USE_PETIT_FAT == 1 char c; uint8_t gH, gW=0, gS, gIS; uint16_t offset; uint8_t startChar = currentFont.startChar; WORD s1; uint16_t pof; char fname1[13]; memset(fname1, 0, 13); memcpy_P(fname1, currentFont.filename, strlen_P( currentFont.filename)); if( pf_open(fname1) ) return; Set_color32(color); Set_bk_color32(bk_color); gH = currentFont.heightPixels; gIS = currentFont.interspacePixels; gS = currentFont.spacePixels; pf_lseek(0); pf_read(sd_buf, 2, &s1); pof = (uint16_t)(sd_buf[1]<<8) | (uint16_t)(sd_buf[0]); while( (c=pgm_read_byte(s)) ) { if( c > ' ') { pf_lseek( (uint16_t)((c-startChar)*3)+2 ); pf_read(sd_buf, 3, &s1); gW = sd_buf[0]; if( !gW ) continue; offset = (uint16_t)(sd_buf[2]<<8) | ( (uint16_t)(sd_buf[1] )); offset+=pof; pf_lseek(offset); pf_read(sd_buf, SD_BUF_SIZE, &s1); send_font_bin(x, y, gH, gW ); x = x + gW + gIS; } else { Set_active_window(x,y,x+gS-1,y+gH-1); Write_command(0x2c); for(offset=0;offset<gS*gH;offset++) { Draw_bk_pixel(); Draw_bk_pixel(); Draw_bk_pixel(); } x+=gS; } s++; } CX=x; CY=y; #endif }
static uint8_t addEntries(const char *filename) { UINT bytes_read; uint8_t i; rc = pf_fnoopen(&sd_fno); if (rc) return 0; // skip to relevant metadata rc = pf_read(buffer, 8, &bytes_read); //uint16_t fpos = 8; // file position, used by lseek replacement if (rc || bytes_read < 8 || buffer[0] != 0xaa) return 0; // not an image uint8_t version = buffer[1]; // version in GPL header uint16_t next = ((uint16_t)buffer[6] << 8) + buffer[7]; uint8_t entry_added = 0; while (next) { uint16_t offset = next - 0x6000; if (offset > 0x1fe0) break; // corrupt image if (images_written >= MAX_ENTRIES) break; // too many images if (pf_lseek(offset)) return entry_added; #if 0 // smaller, but potentially slower replacement for lseek // read ahead to offset position if (fpos > offset) { // rewind rc = pf_open((const char *)filename); if (rc) return; // quite unlikely fpos = 0; } uint16_t bytes_to_skip = offset - fpos; // skip to program entry, which is always within first 8K while (bytes_to_skip > 0) { uint16_t len = bytes_to_skip < sizeof(buffer) ? bytes_to_skip : sizeof(buffer); pf_read(buffer, len, &bytes_read); if (bytes_read < len) return entry_added; // corrupt image bytes_to_skip -= len; } #endif // analyze metadata pf_read(buffer, 6 + ENTRY_NAME_LEN, &bytes_read); //fpos = offset + 6 + ENTRY_NAME_LEN; uint8_t *p = buffer; uint8_t *q = buf_entry; // save next entry next = (*p++ << 8); next += *p++; // filename w/o extension const uint8_t *r = (const uint8_t *)filename; for (i = 8; i > 0 && *r != '.'; --i) *q++ = *r++; while (i-- > 0) *q++ = 0; // GPL header version *q++ = 0; // also doubles as potential \0 for filename *q++ = version; // start address in image *q++ = *p++; *q++ = *p++; // next menu entry (ignored for browser entries) uint16_t next_entry = 0x6000 + MENU_START + MENU_ENTRY_SIZE * (images_written + 1) + MENU_ENTRY_OFFSET; *q++ = next_entry >> 8; *q++ = next_entry & 0xff; // menu handler (ignored for browser entries) *q++ = 0x60; *q++ = 0x10 + MENU_HANDLER_SIZE * images_written; // length and name uint8_t len = *p++; *q++ = ENTRY_NAME_LEN - 1; for (i = 0; i < ENTRY_NAME_LEN; ++i) // always pad name *q++ = i < len ? *p++ : ' '; writeMenuEntry(); writeBrowserEntry(); entry_added = 1; ++images_written; } return entry_added; }
int loadelf_load(char *ch, struct elf_image *img) { unsigned long i, j; struct elf_hdr *ElfHdr = 0; /*elf header struct */ unsigned long p_e_entry; /* elf progamme start address */ unsigned long p_e_phoff; /* Start of program headers */ unsigned short p_e_phentsize; /* Size of program headers */ unsigned short p_e_phnum; /* number of program headers */ struct elf_phdr *ElfPhdr = 0; /* ELF program Header */ struct elf_phdr *phdr = 0; /* ELF program Header */ unsigned char *lptmp; /* load temp address */ WORD brs; unsigned long br; FRESULT res; /* Need to load portions of the ELF file to read metadata. Where should it be loaded? Choose high area of DDR. TODO: Read metadata into SRAM (stack?) instead? */ unsigned char *readbuf = (unsigned char *)0x13000000; img->entry = 0; img->min_addr = (void *) 0xFFFFFFF0; img->max_addr = (void *) 0; /* ELF loader */ /* mount the volume */ lcd_clear(); lcd_print(0, "Pgm load"); lcd_print(1, ch); res = pf_open(ch); if (res != FR_OK) { putstr("ELF not found\n"); lcd_print(1, "not fnd "); return -1; } char str[32]; str[0] = '\0'; _strcat(str, "Open "); _strcat(str, ch); _strcat(str, " OK"); _strcat(str, "\n"); putstr(str); res = pf_lseek(0); if (res != FR_OK) return -1; /* read ELF header length */ pf_lseek(40); //ELF header length stored at 40 res = pf_read(readbuf, 2, &brs); /*read elf magic number */ pf_lseek(0); res = pf_read(readbuf, ((readbuf[0]) << 8) + readbuf[1], &brs); if (res != FR_OK) return -1; ElfHdr = (struct elf_hdr *)readbuf; if ((ElfHdr->e_ident[0] != 0x7f) || (ElfHdr->e_ident[1] != 'E') || (ElfHdr->e_ident[2] != 'L') || (ElfHdr->e_ident[3] != 'F')) return -1; if (ElfHdr->e_type != ET_EXEC) return -1; /* ELF executable programe running start address */ p_e_entry = ElfHdr->e_entry; p_e_phoff = ElfHdr->e_phoff; /*Start of program headers */ p_e_phentsize = ElfHdr->e_phentsize; /*size of program headers */ p_e_phnum = ElfHdr->e_phnum; /*number of program headers */ /* relocate readbuf to avoid conflict */ /* Don't need to play these games as readbuf is now high in DDR memory. if(p_e_entry <= p_e_phentsize + (unsigned)readbuf) { if((p_e_entry - p_e_phentsize) > 0x100000200) readbuf = (unsigned char*)(p_e_entry - p_e_phentsize - 256); else readbuf = (unsigned char*)0x12a00000; }*/ lcd_print(1, "Loading"); /* load all program headers */ pf_lseek(p_e_phoff); res = pf_read_long(readbuf, p_e_phentsize * p_e_phnum, &br); if (res != FR_OK) return -1; /* calculate total in memory size for progress indicator */ unsigned long mem_total = 0; unsigned long mem_progress = 0; ElfPhdr = (struct elf_phdr *)readbuf; for (i = 0; i < p_e_phnum; i++) { if (ElfPhdr[i].p_type == PT_LOAD) { mem_total += ElfPhdr[i].p_memsz; } } /* copy segment section */ for (i = 0; i < p_e_phnum; i++) { /* number of programme header */ phdr = ElfPhdr + i; if (phdr->p_type == PT_LOAD) { /* load to running address */ /* loading */ lptmp = (unsigned char *)phdr->p_paddr; /* assigned physAddr or virtAddr ? */ /* update min and max addresses */ if (img->min_addr > (void*) lptmp) { img->min_addr = lptmp; } if (img->max_addr < (void*)(lptmp + phdr->p_memsz)) { img->max_addr = lptmp + phdr->p_memsz; } if (phdr->p_filesz > 0) { pf_lseek(phdr->p_offset); res = read_progress(lptmp, phdr->p_filesz, &mem_progress, mem_total); if (res != FR_OK) return -1; } /* clean any memory that wasn't loaded */ if (phdr->p_filesz < phdr->p_memsz) { lptmp += phdr->p_filesz; for (j = phdr->p_filesz; j < phdr->p_memsz; j++) { /* clean memory to 0 */ /* TODO: align and write zero ints instead of zero chars */ *lptmp++ = 0; } mem_progress += phdr->p_memsz - phdr->p_filesz; report_load_progress(mem_progress, mem_total); } #ifdef DEBUG printf("loading Segment section No: %lu PhysAdd @ 0x%lX,FileSize=%lu,MemSize=%lu\n", i, phdr->p_paddr, phdr->p_filesz, phdr->p_memsz); #endif } } img->entry = (void *) p_e_entry; return 0; } /* ELF loader */