📄 ixjwin32.cxx
字号:
return FALSE; ringTimeout = 2500; return TRUE;}BOOL OpalIxJDevice::RingLine(unsigned line, DWORD cadence){ if (line >= GetLineCount()) return FALSE; if (line != POTSLine) return FALSE; DWORD dwResult = 0; return IoControl(IOCTL_DevCtrl_SetRingPattern, cadence, &dwResult) && dwResult != 0;}BOOL OpalIxJDevice::IsLineDisconnected(unsigned line){ if (line >= GetLineCount()) return FALSE; if (line != PSTNLine) return FALSE; DWORD dwResult = 0; return IoControl(IOCTL_DevCtrl_GetLineCallerOnHook, 0, &dwResult) && dwResult != 0;}BOOL OpalIxJDevice::SetLineToLineDirect(unsigned line1, unsigned line2, BOOL connect){ if (line1 >= GetLineCount() || line2 >= GetLineCount()) return FALSE; if (line1 == line2) return FALSE; DWORD dwResult = 0; return IoControl(IOCTL_DevCtrl_SetPotsToSlic, connect ? 0 : 1, &dwResult) && dwResult != 0;}BOOL OpalIxJDevice::IsLineToLineDirect(unsigned line1, unsigned line2){ if (line1 >= GetLineCount() || line2 >= GetLineCount()) return FALSE; if (line1 == line2) return FALSE; DWORD dwResult = 0; return IoControl(IOCTL_DevCtrl_GetPotsToSlic, 0, &dwResult) && dwResult == 0;}static const struct { RTP_DataFrame::PayloadTypes rtpType; unsigned dspBitMask; // bit0=8020,bit1=8021,bit2=8022 PINDEX frameSize; DWORD recordMode; DWORD recordRate; DWORD playbackMode; DWORD playbackRate;} CodecInfo[] = { { RTP_DataFrame::L16_Mono, 0, 0, RECORD_MODE_16LINEAR, 0, PLAYBACK_MODE_16LINEAR, 0 }, { RTP_DataFrame::PCMU, 7, 0, RECORD_MODE_ULAW, 0, PLAYBACK_MODE_ULAW, 0 }, { RTP_DataFrame::PCMA, 7, 0, RECORD_MODE_ALAW, 0, PLAYBACK_MODE_ALAW, 0 }, { RTP_DataFrame::G728, 2, 20, RECORD_MODE_TRUESPEECH, RECORD_RATE_G728, PLAYBACK_MODE_TRUESPEECH, PLAYBACK_RATE_G728 }, { RTP_DataFrame::G729, 6, 10, RECORD_MODE_TRUESPEECH, RECORD_RATE_G729, PLAYBACK_MODE_TRUESPEECH, PLAYBACK_RATE_G729 }, { RTP_DataFrame::G7231, 7, 24, RECORD_MODE_TRUESPEECH, RECORD_RATE_G723_63, PLAYBACK_MODE_TRUESPEECH, PLAYBACK_RATE_G723_63 }};PIntArray OpalIxJDevice::GetPayloadTypes() const{ PIntArray codecs; DWORD dwIdCode = 0; if (((OpalIxJDevice *)this)->IoControl(IOCTL_DevCtrl_GetIdCode, 0, &dwIdCode)) { unsigned dspBit = 1 << (dwIdCode&3); PINDEX codec = PARRAYSIZE(CodecInfo); while (codec-- > 0) { if ((CodecInfo[codec].dspBitMask&dspBit) != 0) codecs.SetAt(codecs.GetSize(), CodecInfo[codec].rtpType); } } return codecs;}BOOL OpalIxJDevice::SetReadCodec(unsigned, RTP_DataFrame::PayloadTypes rtpType){ PTRACE(3, "xJack\tSetReadCodec(" << rtpType << ')'); PINDEX codec; for (codec = 0; codec < PARRAYSIZE(CodecInfo); codec++) if (CodecInfo[codec].rtpType == rtpType) break; if (codec >= PARRAYSIZE(CodecInfo)) return FALSE; IoControl(IOCTL_Record_Stop); if (!IoControl(IOCTL_Codec_SetKHz, 8000)) return FALSE; if (!IoControl(IOCTL_Record_SetBufferChannelLimit, 1)) return FALSE; IoControl(IOCTL_Record_DisableVAD); DWORD mode; do { if (!IoControl(IOCTL_Record_SetRECMODE, CodecInfo[codec].recordMode)) return FALSE; if (!IoControl(IOCTL_Record_GetRECMODE, 0, &mode)) return FALSE;#if PTRACING if (mode != CodecInfo[codec].recordMode) PTRACE(3, "xJack\tSetRECMODE failed (" << mode << " -> " << CodecInfo[codec].recordMode << "), retrying");#endif } while (mode != CodecInfo[codec].recordMode); DWORD rate; do { if (!IoControl(IOCTL_Record_SetRate, CodecInfo[codec].recordRate)) return FALSE; if (!IoControl(IOCTL_Record_GetRate, 0, &rate)) return FALSE;#if PTRACING if (rate != CodecInfo[codec].recordRate) PTRACE(3, "xJack\tRecord_SetRate failed (" << rate << " -> " << CodecInfo[codec].recordRate << "), retrying");#endif } while (rate != CodecInfo[codec].recordRate); readFrameSize = CodecInfo[codec].frameSize; if (readFrameSize == 0) { DWORD frameWords; if (!IoControl(IOCTL_Record_GetFrameSize, 0, &frameWords)) return FALSE; readFrameSize = frameWords*2; } if (!IoControl(IOCTL_Record_Start)) return FALSE; readStopped = FALSE; IoControl(IOCTL_Record_DisableVAD); if (aecLevel == AECOff) IoControl(IOCTL_Speakerphone_AECOff); else { IoControl(IOCTL_Speakerphone_SetAEC, aecLevel); IoControl(IOCTL_Speakerphone_AECOn); } return TRUE;}BOOL OpalIxJDevice::SetWriteCodec(unsigned, RTP_DataFrame::PayloadTypes rtpType){ PTRACE(3, "xJack\tSetWriteCodec(" << rtpType << ')'); PINDEX codec; for (codec = 0; codec < PARRAYSIZE(CodecInfo); codec++) if (CodecInfo[codec].rtpType == rtpType) break; if (codec >= PARRAYSIZE(CodecInfo)) return FALSE; IoControl(IOCTL_Playback_Stop); if (!IoControl(IOCTL_Codec_SetKHz, 8000)) return FALSE; if (!IoControl(IOCTL_Playback_SetBufferChannelLimit, 1)) return FALSE; DWORD mode; do { if (!IoControl(IOCTL_Playback_SetPLAYMODE, CodecInfo[codec].playbackMode)) return FALSE; if (!IoControl(IOCTL_Playback_GetPLAYMODE, 0, &mode)) return FALSE;#if PTRACING if (mode != CodecInfo[codec].playbackMode) PTRACE(2, "xJack\tSetPLAYMODE failed (" << mode << " -> " << CodecInfo[codec].playbackMode << "), retrying");#endif } while (mode != CodecInfo[codec].playbackMode); DWORD rate; do { if (!IoControl(IOCTL_Playback_SetRate, CodecInfo[codec].playbackRate)) return FALSE; if (!IoControl(IOCTL_Playback_GetRate, 0, &rate)) return FALSE;#if PTRACING if (rate != CodecInfo[codec].playbackRate) PTRACE(2, "xJack\tPlayback_SetRate failed (" << rate << " -> " << CodecInfo[codec].playbackRate << "), retrying");#endif } while (rate != CodecInfo[codec].playbackRate); writeFrameSize = CodecInfo[codec].frameSize; if (writeFrameSize == 0) { DWORD frameWords; if (!IoControl(IOCTL_Playback_GetFrameSize, 0, &frameWords)) return FALSE; writeFrameSize = frameWords*2; } if (!IoControl(IOCTL_Playback_Start)) return FALSE; writeStopped = FALSE; return TRUE;}BOOL OpalIxJDevice::StopReadCodec(unsigned){ PTRACE(3, "xJack\tStopping read codec"); readMutex.Wait(); readStopped = TRUE; IoControl(IOCTL_Record_Stop); readMutex.Signal(); return TRUE;}BOOL OpalIxJDevice::StopWriteCodec(unsigned){ PTRACE(3, "xJack\tStopping write codec"); writeMutex.Wait(); writeStopped = TRUE; IoControl(IOCTL_Playback_Stop); writeMutex.Signal(); return TRUE;}PINDEX OpalIxJDevice::GetReadFrameSize(unsigned){ return readFrameSize;}PINDEX OpalIxJDevice::GetWriteFrameSize(unsigned){ return writeFrameSize;}BOOL OpalIxJDevice::ReadFrame(unsigned, void * buf){ PWaitAndSignal mutex(readMutex); if (readStopped) return FALSE; DWORD dwBytesReturned = 0; if (!IoControl(IOCTL_Device_Read, NULL, 0, buf, readFrameSize, &dwBytesReturned, TRUE)) return FALSE; if ((PINDEX)dwBytesReturned == readFrameSize) return TRUE; osError = ERROR_READ_FAULT; return FALSE;}BOOL OpalIxJDevice::WriteFrame(unsigned, const void * buf){ PWaitAndSignal mutex(writeMutex); if (writeStopped) return FALSE; DWORD dwResult = 0; DWORD dwBytesReturned = 0; return IoControl(IOCTL_Device_Write, (void *)buf, writeFrameSize, &dwResult, sizeof(dwResult), &dwBytesReturned, TRUE);}unsigned OpalIxJDevice::GetAverageSignalLevel(unsigned){ DWORD dwLevel; if (!IoControl(IOCTL_Record_GetAvgRecordLevel, 0, &dwLevel)) return UINT_MAX; return dwLevel;}BOOL OpalIxJDevice::EnableAudio(unsigned line, BOOL enable){ if (line >= GetLineCount()) return FALSE; DWORD dwSource = ANALOG_SOURCE_SPEAKERPHONE; if (enable) dwSource = line == POTSLine ? ANALOG_SOURCE_POTSPHONE : ANALOG_SOURCE_PSTNLINE; if (IsLineJACK()) IoControl(IOCTL_DevCtrl_SetLineJackMode, dwSource == ANALOG_SOURCE_PSTNLINE ? LINEJACK_MODE_LINEJACK : LINEJACK_MODE_PHONEJACK); return IoControl(IOCTL_DevCtrl_SetAnalogSource, dwSource);}BOOL OpalIxJDevice::SetRecordVolume(unsigned, unsigned volume){ if (!IsLineJACK()) return IoControl(IOCTL_Record_SetVolume, volume); MIXER_LINE mixer; mixer.dwLineID = 0; DWORD dwSize = 0; if (!IoControl(IOCTL_Mixer_GetRecordLineControls, &mixer, sizeof(mixer), &mixer, sizeof(mixer), &dwSize, FALSE)) return FALSE; mixer.dwLeftVolume = mixer.dwRightVolume = volume*256; DWORD dwReturn; return IoControl(IOCTL_Mixer_SetRecordLineControls, &mixer, sizeof(mixer), &dwReturn, sizeof(dwReturn), &dwSize, FALSE);}BOOL OpalIxJDevice::SetPlayVolume(unsigned, unsigned volume){ if (!IsLineJACK()) return IoControl(IOCTL_Playback_SetVolume, volume); MIXER_LINE mixer; mixer.dwLineID = 0; DWORD dwSize = 0; if (!IoControl(IOCTL_Mixer_GetPlaybackLineControls, &mixer, sizeof(mixer), &mixer, sizeof(mixer), &dwSize, FALSE)) return FALSE; mixer.dwLeftVolume = mixer.dwRightVolume = volume*256; DWORD dwReturn; return IoControl(IOCTL_Mixer_SetPlaybackLineControls, &mixer, sizeof(mixer), &dwReturn, sizeof(dwReturn), &dwSize, FALSE);}BOOL OpalIxJDevice::GetRecordVolume(unsigned, unsigned & volume){ if (!IsLineJACK()) { DWORD value; if (!IoControl(IOCTL_Record_GetVolume, 0, &value)) return FALSE; volume = value; return TRUE; } MIXER_LINE mixer; mixer.dwLineID = 0; DWORD dwSize = 0; if (!IoControl(IOCTL_Mixer_GetRecordLineControls, &mixer, sizeof(mixer), &mixer, sizeof(mixer), &dwSize, FALSE)) return FALSE; volume = mixer.dwLeftVolume/256; return TRUE;}BOOL OpalIxJDevice::GetPlayVolume(unsigned, unsigned & volume){ if (!IsLineJACK()) { DWORD value; if (!IoControl(IOCTL_Playback_GetVolume, 0, &value)) return FALSE; volume = value; return TRUE; } MIXER_LINE mixer; mixer.dwLineID = 0; DWORD dwSize = 0; if (!IoControl(IOCTL_Mixer_GetPlaybackLineControls, &mixer, sizeof(mixer), &mixer, sizeof(mixer), &dwSize, FALSE)) return FALSE; volume = mixer.dwLeftVolume/256; return TRUE;}OpalLineInterfaceDevice::AECLevels OpalIxJDevice::GetAEC(unsigned){ return aecLevel;}BOOL OpalIxJDevice::SetAEC(unsigned, AECLevels level){ PWaitAndSignal mutexr(readMutex); PWaitAndSignal mutexw(writeMutex); aecLevel = level; // 8022 on xJACK goes mad when you set AEC unless have read/write going. if (readStopped && writeStopped) return TRUE; return IoControl(IOCTL_Speakerphone_SetAEC, level);}BOOL OpalIxJDevice::GetCallerID(unsigned, PString & idString, BOOL full){ idString = PString(); BYTE buffer[256]; DWORD dwReturn = 0;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -