cellAudio: use g_fxo

This commit is contained in:
Nekotekina 2019-09-15 15:19:59 +03:00
parent 75941e62a8
commit 36a528067c
3 changed files with 80 additions and 66 deletions

View file

@ -420,7 +420,7 @@ void cell_audio_thread::reset_ports(s32 offset)
void cell_audio_thread::advance(u64 timestamp, bool reset) void cell_audio_thread::advance(u64 timestamp, bool reset)
{ {
auto _locked = g_idm->lock<named_thread<cell_audio_thread>>(0); std::unique_lock lock(mutex);
// update ports // update ports
if (reset) if (reset)
@ -464,7 +464,7 @@ void cell_audio_thread::advance(u64 timestamp, bool reset)
} }
} }
_locked.unlock(); lock.unlock();
for (u32 i = 0; i < queue_count; i++) for (u32 i = 0; i < queue_count; i++)
{ {
@ -935,10 +935,11 @@ error_code cellAudioInit()
{ {
cellAudio.warning("cellAudioInit()"); cellAudio.warning("cellAudioInit()");
// Start audio thread const auto g_audio = g_fxo->get<cell_audio>();
auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(id_new);
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (g_audio->init)
{ {
return CELL_AUDIO_ERROR_ALREADY_INIT; return CELL_AUDIO_ERROR_ALREADY_INIT;
} }
@ -946,8 +947,6 @@ error_code cellAudioInit()
std::memset(g_audio_buffer.get_ptr(), 0, g_audio_buffer.alloc_size); std::memset(g_audio_buffer.get_ptr(), 0, g_audio_buffer.alloc_size);
std::memset(g_audio_indices.get_ptr(), 0, g_audio_indices.alloc_size); std::memset(g_audio_indices.get_ptr(), 0, g_audio_indices.alloc_size);
g_audio.create("cellAudio Thread");
for (u32 i = 0; i < AUDIO_PORT_COUNT; i++) for (u32 i = 0; i < AUDIO_PORT_COUNT; i++)
{ {
g_audio->ports[i].number = i; g_audio->ports[i].number = i;
@ -955,6 +954,8 @@ error_code cellAudioInit()
g_audio->ports[i].index = g_audio_indices + i; g_audio->ports[i].index = g_audio_indices + i;
} }
g_audio->init = 1;
return CELL_OK; return CELL_OK;
} }
@ -962,35 +963,17 @@ error_code cellAudioQuit(ppu_thread& ppu)
{ {
cellAudio.warning("cellAudioQuit()"); cellAudio.warning("cellAudioQuit()");
// Stop audio thread const auto g_audio = g_fxo->get<cell_audio>();
auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0);
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
// Signal to abort, release lock // TODO
*g_audio.get() = thread_state::aborting; g_audio->init = 0;
g_audio.unlock();
while (true)
{
if (ppu.is_stopped())
{
return 0;
}
thread_ctrl::wait_for(1000);
auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0);
if (*g_audio.get() == thread_state::finished)
{
g_audio.destroy();
break;
}
}
return CELL_OK; return CELL_OK;
} }
@ -999,9 +982,11 @@ error_code cellAudioPortOpen(vm::ptr<CellAudioPortParam> audioParam, vm::ptr<u32
{ {
cellAudio.warning("cellAudioPortOpen(audioParam=*0x%x, portNum=*0x%x)", audioParam, portNum); cellAudio.warning("cellAudioPortOpen(audioParam=*0x%x, portNum=*0x%x)", audioParam, portNum);
const auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1102,9 +1087,11 @@ error_code cellAudioGetPortConfig(u32 portNum, vm::ptr<CellAudioPortConfig> port
{ {
cellAudio.trace("cellAudioGetPortConfig(portNum=%d, portConfig=*0x%x)", portNum, portConfig); cellAudio.trace("cellAudioGetPortConfig(portNum=%d, portConfig=*0x%x)", portNum, portConfig);
const auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1137,9 +1124,11 @@ error_code cellAudioPortStart(u32 portNum)
{ {
cellAudio.warning("cellAudioPortStart(portNum=%d)", portNum); cellAudio.warning("cellAudioPortStart(portNum=%d)", portNum);
const auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1162,9 +1151,11 @@ error_code cellAudioPortClose(u32 portNum)
{ {
cellAudio.warning("cellAudioPortClose(portNum=%d)", portNum); cellAudio.warning("cellAudioPortClose(portNum=%d)", portNum);
const auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1187,9 +1178,11 @@ error_code cellAudioPortStop(u32 portNum)
{ {
cellAudio.warning("cellAudioPortStop(portNum=%d)", portNum); cellAudio.warning("cellAudioPortStop(portNum=%d)", portNum);
const auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1212,9 +1205,11 @@ error_code cellAudioGetPortTimestamp(u32 portNum, u64 tag, vm::ptr<u64> stamp)
{ {
cellAudio.trace("cellAudioGetPortTimestamp(portNum=%d, tag=0x%llx, stamp=*0x%x)", portNum, tag, stamp); cellAudio.trace("cellAudioGetPortTimestamp(portNum=%d, tag=0x%llx, stamp=*0x%x)", portNum, tag, stamp);
const auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1248,9 +1243,11 @@ error_code cellAudioGetPortBlockTag(u32 portNum, u64 blockNo, vm::ptr<u64> tag)
{ {
cellAudio.trace("cellAudioGetPortBlockTag(portNum=%d, blockNo=0x%llx, tag=*0x%x)", portNum, blockNo, tag); cellAudio.trace("cellAudioGetPortBlockTag(portNum=%d, blockNo=0x%llx, tag=*0x%x)", portNum, blockNo, tag);
const auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1281,9 +1278,11 @@ error_code cellAudioSetPortLevel(u32 portNum, float level)
{ {
cellAudio.trace("cellAudioSetPortLevel(portNum=%d, level=%f)", portNum, level); cellAudio.trace("cellAudioSetPortLevel(portNum=%d, level=%f)", portNum, level);
const auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1363,9 +1362,11 @@ error_code cellAudioSetNotifyEventQueue(u64 key)
{ {
cellAudio.warning("cellAudioSetNotifyEventQueue(key=0x%llx)", key); cellAudio.warning("cellAudioSetNotifyEventQueue(key=0x%llx)", key);
const auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1396,9 +1397,11 @@ error_code cellAudioRemoveNotifyEventQueue(u64 key)
{ {
cellAudio.warning("cellAudioRemoveNotifyEventQueue(key=0x%llx)", key); cellAudio.warning("cellAudioRemoveNotifyEventQueue(key=0x%llx)", key);
const auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::lock_guard lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1429,9 +1432,11 @@ error_code cellAudioAddData(u32 portNum, vm::ptr<float> src, u32 samples, float
{ {
cellAudio.trace("cellAudioAddData(portNum=%d, src=*0x%x, samples=%d, volume=%f)", portNum, src, samples, volume); cellAudio.trace("cellAudioAddData(portNum=%d, src=*0x%x, samples=%d, volume=%f)", portNum, src, samples, volume);
auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::unique_lock lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1452,7 +1457,7 @@ error_code cellAudioAddData(u32 portNum, vm::ptr<float> src, u32 samples, float
const auto dst = port.get_vm_ptr(); const auto dst = port.get_vm_ptr();
g_audio.unlock(); lock.unlock();
for (u32 i = 0; i < samples * port.num_channels; i++) for (u32 i = 0; i < samples * port.num_channels; i++)
{ {
@ -1466,9 +1471,11 @@ error_code cellAudioAdd2chData(u32 portNum, vm::ptr<float> src, u32 samples, flo
{ {
cellAudio.trace("cellAudioAdd2chData(portNum=%d, src=*0x%x, samples=%d, volume=%f)", portNum, src, samples, volume); cellAudio.trace("cellAudioAdd2chData(portNum=%d, src=*0x%x, samples=%d, volume=%f)", portNum, src, samples, volume);
auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::unique_lock lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1489,7 +1496,7 @@ error_code cellAudioAdd2chData(u32 portNum, vm::ptr<float> src, u32 samples, flo
const auto dst = port.get_vm_ptr(); const auto dst = port.get_vm_ptr();
g_audio.unlock(); lock.unlock();
if (port.num_channels == 2) if (port.num_channels == 2)
{ {
@ -1537,9 +1544,11 @@ error_code cellAudioAdd6chData(u32 portNum, vm::ptr<float> src, float volume)
{ {
cellAudio.trace("cellAudioAdd6chData(portNum=%d, src=*0x%x, volume=%f)", portNum, src, volume); cellAudio.trace("cellAudioAdd6chData(portNum=%d, src=*0x%x, volume=%f)", portNum, src, volume);
auto g_audio = g_idm->lock<named_thread<cell_audio_thread>>(0); const auto g_audio = g_fxo->get<cell_audio>();
if (!g_audio) std::unique_lock lock(g_audio->mutex);
if (!g_audio->init)
{ {
return CELL_AUDIO_ERROR_NOT_INIT; return CELL_AUDIO_ERROR_NOT_INIT;
} }
@ -1553,7 +1562,7 @@ error_code cellAudioAdd6chData(u32 portNum, vm::ptr<float> src, float volume)
const auto dst = port.get_vm_ptr(); const auto dst = port.get_vm_ptr();
g_audio.unlock(); lock.unlock();
if (port.num_channels == 6) if (port.num_channels == 6)
{ {

View file

@ -338,6 +338,9 @@ class cell_audio_thread
public: public:
cell_audio_config cfg; cell_audio_config cfg;
shared_mutex mutex;
atomic_t<u32> init = 0;
std::vector<u64> keys; std::vector<u64> keys;
std::array<audio_port, AUDIO_PORT_COUNT> ports; std::array<audio_port, AUDIO_PORT_COUNT> ports;
@ -370,6 +373,8 @@ public:
{ {
return ringbuffer->has_capability(cap); return ringbuffer->has_capability(cap);
} }
static constexpr auto thread_name = "cellAudio Thread"sv;
}; };
using cell_audio = named_thread<cell_audio_thread>; using cell_audio = named_thread<cell_audio_thread>;

View file

@ -332,7 +332,7 @@ struct surmixer_thread : ppu_thread
void non_task() void non_task()
{ {
const auto g_audio = fxm::get<cell_audio>(); const auto g_audio = g_fxo->get<cell_audio>();
audio_port& port = g_audio->ports[g_surmx.audio_port]; audio_port& port = g_audio->ports[g_surmx.audio_port];
@ -460,7 +460,7 @@ s32 cellSurMixerCreate(vm::cptr<CellSurMixerConfig> config)
{ {
libmixer.warning("cellSurMixerCreate(config=*0x%x)", config); libmixer.warning("cellSurMixerCreate(config=*0x%x)", config);
const auto g_audio = fxm::get<cell_audio>(); const auto g_audio = g_fxo->get<cell_audio>();
const auto port = g_audio->open_port(); const auto port = g_audio->open_port();
@ -544,7 +544,7 @@ s32 cellSurMixerStart()
{ {
libmixer.warning("cellSurMixerStart()"); libmixer.warning("cellSurMixerStart()");
const auto g_audio = fxm::get<cell_audio>(); const auto g_audio = g_fxo->get<cell_audio>();
if (g_surmx.audio_port >= AUDIO_PORT_COUNT) if (g_surmx.audio_port >= AUDIO_PORT_COUNT)
{ {
@ -566,7 +566,7 @@ s32 cellSurMixerFinalize()
{ {
libmixer.warning("cellSurMixerFinalize()"); libmixer.warning("cellSurMixerFinalize()");
const auto g_audio = fxm::get<cell_audio>(); const auto g_audio = g_fxo->get<cell_audio>();
if (g_surmx.audio_port >= AUDIO_PORT_COUNT) if (g_surmx.audio_port >= AUDIO_PORT_COUNT)
{ {
@ -611,7 +611,7 @@ s32 cellSurMixerPause(u32 type)
{ {
libmixer.warning("cellSurMixerPause(type=%d)", type); libmixer.warning("cellSurMixerPause(type=%d)", type);
const auto g_audio = fxm::get<cell_audio>(); const auto g_audio = g_fxo->get<cell_audio>();
if (g_surmx.audio_port >= AUDIO_PORT_COUNT) if (g_surmx.audio_port >= AUDIO_PORT_COUNT)
{ {
@ -635,7 +635,7 @@ s32 cellSurMixerGetTimestamp(u64 tag, vm::ptr<u64> stamp)
{ {
libmixer.error("cellSurMixerGetTimestamp(tag=0x%llx, stamp=*0x%x)", tag, stamp); libmixer.error("cellSurMixerGetTimestamp(tag=0x%llx, stamp=*0x%x)", tag, stamp);
const auto g_audio = fxm::get<cell_audio>(); const auto g_audio = g_fxo->get<cell_audio>();
*stamp = g_audio->m_start_time + tag * AUDIO_BUFFER_SAMPLES * 1'000'000 / g_audio->cfg.audio_sampling_rate; *stamp = g_audio->m_start_time + tag * AUDIO_BUFFER_SAMPLES * 1'000'000 / g_audio->cfg.audio_sampling_rate;