I have problems playing uncompressed audio data that come from a raw-file (that is a wave-file without header, 16bit 44.1kHz, little-endian, mono in my case). I chose a raw-file just for testing purposes. The file works fine but I have those crackles coming from the file read or whatever.
I know, that this problem already occured in the past, e.g. in this thread http://forums.ps2dev.org/viewtopic.php?t=5089. But the solution shown there isn't a real solution to my problem I think. I am searching for an explanation of that phenomenon without doing all that stuff of MP3 decoding.
Please take a look at my source:
Code: Select all
#include <pspkernel.h>
#include <pspdebug.h>
#include <pspaudio.h>
#include <pspdisplay.h>
#include <stdlib.h>
#include <limits.h>
/*
This part of the code is more or less identical to the sdktest sample
*/
/* Define the module info section */
PSP_MODULE_INFO("AUDIOTEST", 0, 1, 1);
/* Define the main thread's attribute value (optional) */
PSP_MAIN_THREAD_ATTR(THREAD_ATTR_USER | THREAD_ATTR_VFPU);
/* Define printf, just to make typing easier */
#define printf pspDebugScreenPrintf
/* Exit callback */
int exitCallback(int arg1, int arg2, void *common) {
sceKernelExitGame();
return 0;
}
/* Callback thread */
int callbackThread(SceSize args, void *argp) {
int cbid;
cbid = sceKernelCreateCallback("Exit Callback", exitCallback, NULL);
sceKernelRegisterExitCallback(cbid);
sceKernelSleepThreadCB();
return 0;
}
/* Sets up the callback thread and returns its thread id */
int setupCallbacks(void) {
int thid = 0;
thid = sceKernelCreateThread("update_thread", callbackThread, 0x11, 0xFA0, 0, 0);
if (thid >= 0) {
sceKernelStartThread(thid, 0, 0);
}
return thid;
}
/*
Below this point is the interesting code in this sample
*/
typedef struct {
short l, r;
} sample_t;
int main(void) {
pspDebugScreenInit();
setupCallbacks();
printf("Opening test file.\n");
//opening the test-file
int fd = sceIoOpen("ms0:/mono.raw", PSP_O_RDONLY, 0777);
if(fd <= 0) {
printf("Error opening file.");
return -1;
}
printf("Opening Audio Channel...\n");
//common multiple of 64 and 100
int sampleBufferSize = 1600;
int channel = sceAudioChReserve(PSP_AUDIO_NEXT_CHANNEL,
PSP_AUDIO_SAMPLE_ALIGN(sampleBufferSize),
PSP_AUDIO_FORMAT_STEREO);
if(channel < 0){
printf("Error opening Audio Channel.");
sceIoClose(fd);
return -1;
}
sample_t sampleBuffer[sampleBufferSize];
char byteBuffer[sampleBufferSize*2]; //buffer for reading from file
short sampleValue = 0;
//read the first bytes
int readBytes = sceIoRead(fd, byteBuffer, sampleBufferSize*2);
//samples are 16bit
int readSamples = readBytes/2;
while(readSamples > 0){
int i;
//copy the bytes to the sampleBuffer and convert them to short
for(i = 0; i < readSamples; ++i){
//little endian conversion to short
//wave/raw uses -32768 to 32767
sampleValue = ((short) byteBuffer[2*i]) + (((short)byteBuffer[2*i+1]) << 8);
sampleBuffer[i].l = sampleValue;
sampleBuffer[i].r = sampleValue;
}
sceAudioOutputPannedBlocking(channel, PSP_AUDIO_VOLUME_MAX, PSP_AUDIO_VOLUME_MAX, sampleBuffer);
//reading the next samples
readSamples = sceIoRead(fd, byteBuffer, sampleBufferSize*2) / 2;
}
sceAudioChRelease(channel);
sceIoClose(fd);
printf("Reached Audio File End.\n");
return 0;
}
Studying the sources, I could not really imagine, how the solution in the thread I cited above fits to my needs. I also took a look at the PSPRadio-sources. But also that software is much more complex than this (simple?) problem. They do a lot of messaging stuff because they have to load the audio from the internet. Or did I oversee something?
I also tried the callback-function method from pspaudiolib.h. That didn't work either. I took a look into pspaudiolib.c, but no magic, just the way I'm trying to do it here? Or am I wrong?
Please help.