Merge pull request #2179 from aliaspider/master

(CTR/3DS) improve audio/video sync.
This commit is contained in:
Twinaphex 2015-09-28 21:50:10 +02:00
commit 4f02326171
6 changed files with 24 additions and 17 deletions

View File

@ -393,7 +393,7 @@ $(TARGET)_stripped.elf: $(TARGET).elf
cp $(TARGET).elf $@
$(STRIP) $@
$(TARGET).cia: $(TARGET)_stripped.elf $(TARGET).bnr $(TARGET).icn
$(TARGET).cia: $(TARGET)_stripped.elf $(TARGET).bnr $(TARGET).icn $(APP_CIA_RSF)
$(MAKEROM) -f cia -o $@ -rsf $(APP_CIA_RSF) -target t -exefslogo -elf $(TARGET)_stripped.elf -icon $(TARGET).icn -banner $(TARGET).bnr -DAPP_TITLE="$(APP_TITLE)" -DAPP_PRODUCT_CODE="$(APP_PRODUCT_CODE)" -DAPP_UNIQUE_ID=$(APP_UNIQUE_ID)
clean:

View File

@ -31,10 +31,7 @@ typedef struct
uint32_t pos;
uint32_t playpos;
uint32_t cpu_ticks_per_sample;
uint64_t cpu_ticks_last;
int rate;
} ctr_audio_t;
#define CTR_AUDIO_COUNT (1u << 11u)
@ -42,19 +39,23 @@ typedef struct
#define CTR_AUDIO_SIZE (CTR_AUDIO_COUNT * sizeof(int16_t))
#define CTR_AUDIO_SIZE_MASK (CTR_AUDIO_SIZE - 1u)
#define CTR_AUDIO_RATE 32730
#define CTR_CSND_TICKS_PER_SAMPLE 2048
#define CTR_CPU_TICKS_PER_SAMPLE (CTR_CSND_TICKS_PER_SAMPLE * 4)
static void ctr_audio_update_playpos(ctr_audio_t* ctr)
{
uint32_t samples_played;
uint64_t current_tick;
current_tick = svcGetSystemTick();
samples_played = (current_tick - ctr->cpu_ticks_last) / ctr->cpu_ticks_per_sample;
samples_played = (current_tick - ctr->cpu_ticks_last) / CTR_CPU_TICKS_PER_SAMPLE;
ctr->playpos = (ctr->playpos + samples_played) & CTR_AUDIO_COUNT_MASK;
ctr->cpu_ticks_last += samples_played * ctr->cpu_ticks_per_sample;
ctr->cpu_ticks_last += samples_played * CTR_CPU_TICKS_PER_SAMPLE;
}
Result csndPlaySound_custom(int chn, u32 flags, u32 sampleRate, float vol, float pan, void* data0, void* data1, u32 size)
Result csndPlaySound_custom(int chn, u32 flags, float vol, float pan, void* data0, void* data1, u32 size)
{
if (!(csndChannels & BIT(chn)))
return 1;
@ -79,11 +80,8 @@ Result csndPlaySound_custom(int chn, u32 flags, u32 sampleRate, float vol, float
}
}
u32 timer = CSND_TIMER(sampleRate);
if (timer < 0x0042) timer = 0x0042;
else if (timer > 0xFFFF) timer = 0xFFFF;
flags &= ~0xFFFF001F;
flags |= SOUND_ENABLE | SOUND_CHANNEL(chn) | (timer << 16);
flags |= SOUND_ENABLE | SOUND_CHANNEL(chn) | (CTR_CSND_TICKS_PER_SAMPLE << 16);
u32 volumes = CSND_VOL(vol, pan);
CSND_SetChnRegs(flags, paddr0, paddr1, size, volumes, volumes);
@ -98,10 +96,10 @@ Result csndPlaySound_custom(int chn, u32 flags, u32 sampleRate, float vol, float
return 0;
}
static void *ctr_audio_init(const char *device, unsigned rate, unsigned latency)
{
ctr_audio_t *ctr = (ctr_audio_t*)calloc(1, sizeof(ctr_audio_t));
settings_t *settings = config_get_ptr();
if (!ctr)
return NULL;
@ -110,6 +108,8 @@ static void *ctr_audio_init(const char *device, unsigned rate, unsigned latency)
(void)rate;
(void)latency;
settings->audio.out_rate = CTR_AUDIO_RATE;
ctr->l = linearAlloc(CTR_AUDIO_SIZE);
ctr->r = linearAlloc(CTR_AUDIO_SIZE);
@ -120,16 +120,14 @@ static void *ctr_audio_init(const char *device, unsigned rate, unsigned latency)
ctr->r_paddr = osConvertVirtToPhys((u32)ctr->r);
ctr->pos = 0;
ctr->rate = rate;
ctr->cpu_ticks_per_sample = CSND_TIMER(rate) * 4;
GSPGPU_FlushDataCache(NULL, (u8*)ctr->l_paddr, CTR_AUDIO_SIZE);
GSPGPU_FlushDataCache(NULL, (u8*)ctr->r_paddr, CTR_AUDIO_SIZE);
csndPlaySound_custom(0x8, SOUND_LOOPMODE(CSND_LOOPMODE_NORMAL)| SOUND_FORMAT(CSND_ENCODING_PCM16),
rate, 1.0, -1.0, ctr->l, ctr->l, CTR_AUDIO_SIZE);
1.0, -1.0, ctr->l, ctr->l, CTR_AUDIO_SIZE);
csndPlaySound_custom(0x9, SOUND_LOOPMODE(CSND_LOOPMODE_NORMAL)| SOUND_FORMAT(CSND_ENCODING_PCM16),
rate, 1.0, 1.0, ctr->r, ctr->r, CTR_AUDIO_SIZE);
1.0, 1.0, ctr->r, ctr->r, CTR_AUDIO_SIZE);
csndExecCmds(true);
ctr->playpos = 0;

View File

@ -582,7 +582,9 @@ static const bool font_enable = true;
* This value should stay close to 60Hz to avoid large pitch changes.
* If your monitor does not run at 60Hz, or something close to it,
* disable VSync, and leave this at its default. */
#if defined(RARCH_CONSOLE)
#ifdef _3DS
static const float refresh_rate = (32730.0 * 8192.0) / 4481134.0 ;
#elif defined(RARCH_CONSOLE)
static const float refresh_rate = 60/1.001;
#else
static const float refresh_rate = 59.95;
@ -601,6 +603,8 @@ static const bool audio_enable = true;
/* Output samplerate. */
#ifdef GEKKO
static const unsigned out_rate = 32000;
#elif defined(_3DS)
static const unsigned out_rate = 32730;
#else
static const unsigned out_rate = 48000;
#endif

View File

@ -91,6 +91,7 @@ AccessControlInfo:
MaxCpu : 0x9E # Default
CpuSpeed : 804mhz
EnableL2Cache : true
DisableDebug : false
EnableForceDebug : false

View File

@ -345,6 +345,8 @@ static void* ctr_init(const video_info_t* video,
ctr->empty_framebuffer = linearAlloc(320 * 240 * 2);
memset(ctr->empty_framebuffer, 0, 320 * 240 * 2);
driver_set_refresh_rate((32730.0 * 8192.0) / 4481134.0);
return ctr;
}

View File

@ -49,6 +49,8 @@
#define CTRGU_MULTISAMPLE_2x2 (2 << 24)
#define CTR_CPU_TICKS_PER_SECOND 268123480
#define CTR_CPU_TICKS_PER_FRAME 4481134
extern Handle gspEvents[GSPEVENT_MAX];
extern u32* gpuCmdBuf;