Audio-RaveMP
view release on metacpan or search on metacpan
XP("\n");
if (i%32==31) {
XP("--more--\n");
if (getchar()=='q')
break;
}
}
#endif
free(blkbuff);
return 1;
}
/************************ upload_file *********************/
/* Upload a file to the device */
int ravemp_upload_file(char *fname, char *dest_name)
{
int i,j,mp3file,uploadok;
int block,blk1no,blk2no,prvblk,nxtblk,page;
unsigned fsize,fblocks,avail,namelen;
unsigned char *p,*t,*firstblk,*datablk,*filebuff;
unsigned char fat[TOTAL_BLOCKS];
FILE *fp;
struct stat fileinfo;
uploadok = 0;
/* Read device FAT */
if (!load_fat(fat)) {
RMP_TRACE(fprintf(stderr, "Unable to load allocation table\n"));
return 0;
}
/* Count free blocks and determine header block numbers */
avail = 0;
blk1no = blk2no = -1;
for (i=0;i<TOTAL_BLOCKS;i++) {
if (fat[i]==0xff) {
if (blk1no == -1)
blk1no = i;
else if (blk2no == -1)
blk2no = i;
avail++;
}
}
/* Get file information (note we simplistically determine if it's an MP3
file or not by checking for a .mp3 extension) */
if (stat(fname,&fileinfo) != 0) {
RMP_TRACE(fprintf(stderr, "Unable to access file %s\n",fname));
return 0;
}
fsize = fileinfo.st_size;
fblocks = (fsize+DATA_SIZE-1)/DATA_SIZE;
RMP_TRACE(fprintf(stderr, "File size: %u bytes [%u blocks needed, %u available]\n",fsize,fblocks,avail));
if (fblocks+2 > avail) { /* +2 for 2 header blocks */
RMP_TRACE(fprintf(stderr, "Not enough space available for file\n"));
return 0;
}
mp3file = ((p=strrchr(fname,'.')) != NULL && strcasecmp(p,".mp3")==0);
/* Open file for upload */
if ((fp=fopen(fname,"r"))==NULL) {
RMP_TRACE(fprintf(stderr, "Unable to open file %s\n",fname));
return 0;
}
/* Allocate memory for block buffers */
if ((firstblk=malloc(MAX_BLOCK_SIZE))==NULL ||
(datablk=malloc(MAX_BLOCK_SIZE)) == NULL ||
(filebuff=malloc(DATA_SIZE)) == NULL) {
RMP_TRACE(fprintf(stderr, "Unable to allocate memory for data buffers\n"));
fclose(fp);
return 0;
}
/* Build block list for file and put tag characters into FAT buffer */
memset(firstblk,0xff,MAX_BLOCK_SIZE); /* Set every value to "unused" */
p = firstblk;
*p++ = (blk1no>>8) & 0xff;
*p++ = blk1no & 0xff;
fat[blk1no] = mp3file?'M':'E';
*p++ = (blk2no>>8) &0xff;
*p++ = blk2no &0xff;
fat[blk2no] = mp3file?'m':'e';
for (i=TOTAL_BLOCKS-1,j=fblocks;i>=0&&j>0;i--) {
if (fat[i]==0xff) {
fat[i]=mp3file?'m':'e';
*p++ = ((unsigned)i>>8) & 0xff;
*p++ = i & 0xff;
j--;
}
}
/* Debug */
#if 0
struct stat fileinfo;
struct page xpage;
FILE *fp;
/* Determine buffer size and allocate it */
chunksize = PAGE_SIZE+TAG_SIZE;
buffsize = PAGES_PER_BLOCK * chunksize;
if ((baseblk=malloc(buffsize)) == NULL || (datablk=malloc(buffsize)) == NULL) {
RMP_TRACE(fprintf(stderr, "Memory Allocation failure\n"));
return 0;
}
/* Read first block of file, which contains the list of blocks used */
if (!read_block(firstblock,baseblk)) {
RMP_TRACE(fprintf(stderr, "Read of First Block failed\n"));
free(baseblk);
free(datablk);
return 0;
}
/* Read second block of file, which holds the file information */
j = (*(baseblk+2)<<8) | *(baseblk+3);
if (!read_block(j,datablk)) {
RMP_TRACE(fprintf(stderr, "Read of Second Block failed\n"));
free(baseblk);
free(datablk);
return 0;
}
/* Extract file size */
p = datablk+PAGE_SIZE+TAG_SIZE+PAGE_SIZE; /* Point to second page tag area */
fsize = 0;
for (i=0;i<4;i++)
fsize = (fsize<<8) | *p++;
if (fsize==0 || fsize > TOTAL_BLOCKS*PAGE_SIZE*PAGES_PER_BLOCK) {
RMP_TRACE(fprintf(stderr, "Bad file size: %u bytes reported\n",fsize));
free(baseblk);
free(datablk);
return 0;
}
/* Extract filename, which is spread across the tags, starting at offset 20 (we
assume the name length to less than 256-20 or 226 characters) */
for (i=0;i<256/TAG_SIZE;i++) /* Collect all tags into buffer */
memcpy(&tagbuff[i*TAG_SIZE],datablk+i*(PAGE_SIZE+TAG_SIZE)+PAGE_SIZE,TAG_SIZE);
RMP_TRACE(fprintf(stderr, "File Name: %s File Size: %u\n",&tagbuff[20],fsize)); /**/
/* Check if file already exists */
if (stat(&tagbuff[20],&fileinfo) == 0) {
RMP_TRACE(fprintf(stderr, "\n*** File with same name already exists - download cancelled ***\n"));
free(baseblk);
free(datablk);
return 0;
}
/* Create file to save data in */
if (dest == NULL) {
dest = &tagbuff[20];
}
if ((fp=fopen(dest, "w"))==NULL) {
RMP_TRACE(fprintf(stderr, "Unable to create file to download into!\n"));
free(baseblk);
free(datablk);
return 0;
}
/* Read all file blocks in turn */
dlok = 1;
for (page=0;page<PAGES_PER_BLOCK&&dlok&&fsize>0;page++) {
memcpy(&xpage,baseblk+page*chunksize,chunksize);
p = &xpage.data[4]; /* Pointer to block list (skipping first 2 blocks) */
for (i=0;i<PAGE_SIZE/2&&fsize;i++) {
j = *p++<<8;
j |= *p++;
if (j<MIN_DATA_BLOCK || j>=TOTAL_BLOCKS) {
RMP_TRACE(fprintf(stderr, "Download Failure: Bad Block number %u [Outside Range %u-%u]\n",j,MIN_DATA_BLOCK,TOTAL_BLOCKS-1));
dlok = 0;
break;
}
if (!read_block(j,datablk)) {
RMP_TRACE(fprintf(stderr, "Error reading Block %u\n",j));
dlok = 0;
break;
}
for (k=0;k<PAGES_PER_BLOCK&&fsize;k++) {
wrsize = fsize>PAGE_SIZE?PAGE_SIZE:fsize;
if (fwrite(datablk+k*(PAGE_SIZE+TAG_SIZE),1,wrsize,fp) != wrsize) {
RMP_TRACE(fprintf(stderr, "File Write Error!\n"));
dlok = 0;
break;
}
fsize -= wrsize;
}
ravemp_status_dot();
fflush(stdout);
( run in 0.598 second using v1.01-cache-2.11-cpan-df04353d9ac )